From a6d59d589b14bac0fa8d20ea9d61b1804ee7dee4 Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Sat, 3 Jun 2006 15:53:57 +0000 Subject: [PATCH 01/27] creating undo/redo serialization branch git-svn-id: svn://localhost/ardour2/branches/undo@562 d708f5d6-7413-0410-9779-e7cbd77b26cf From 3038d8ce4aa0627847bdcbd8140447fb306ef7fb Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Wed, 7 Jun 2006 23:08:56 +0000 Subject: [PATCH 02/27] r42@gandalf: fugalh | 2006-06-07 17:08:39 -0600 Memento skeleton. RFC Compiles, but obviously somewhat unimplemented. git-svn-id: svn://localhost/ardour2/branches/undo@572 d708f5d6-7413-0410-9779-e7cbd77b26cf --- libs/pbd3/pbd/undo.h | 32 ++++++++++++++++++++++++++++++++ 1 file changed, 32 insertions(+) diff --git a/libs/pbd3/pbd/undo.h b/libs/pbd3/pbd/undo.h index f067635ed3..b540179012 100644 --- a/libs/pbd3/pbd/undo.h +++ b/libs/pbd3/pbd/undo.h @@ -24,13 +24,45 @@ #include #include #include +#include #include +#include using std::string; using std::list; typedef sigc::slot UndoAction; +class Serializable; + +class MementoBase +{ +public: + MementoBase(std::string key); + void operator() () { return _slot(); } + XMLNode &serialize(); +protected: + sigc::slot _slot; + std::list _args; +}; + +template +class Memento; + +template <> +class Memento <> : public MementoBase {}; + +template +class Memento : public MementoBase +{ +public: + Memento(std::string key, T1 arg1) : MementoBase(key) + { + _args.push_back(arg1); + _slot = sigc::bind(_slot, arg1); + } +}; + class UndoCommand { public: From eb3f77df5748e81c4a6bfe737cd9b5a3d721a86c Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Wed, 14 Jun 2006 18:37:57 +0000 Subject: [PATCH 03/27] pulling trunk git-svn-id: svn://localhost/ardour2/branches/undo@586 d708f5d6-7413-0410-9779-e7cbd77b26cf --- SConstruct | 42 +- gtk2_ardour/analysis_window.cc | 2 +- gtk2_ardour/analysis_window.h | 4 +- gtk2_ardour/ardour_ui.cc | 23 +- gtk2_ardour/audio_clock.cc | 1 + gtk2_ardour/connection_editor.cc | 4 +- gtk2_ardour/connection_editor.h | 4 +- gtk2_ardour/editor.cc | 5 +- gtk2_ardour/editor_audio_import.cc | 2 +- gtk2_ardour/export_dialog.cc | 3 +- gtk2_ardour/export_range_markers_dialog.cc | 4 +- gtk2_ardour/fft_graph.cc | 4 +- gtk2_ardour/gtk-custom-hruler.c | 2 - gtk2_ardour/io_selector.cc | 8 +- gtk2_ardour/io_selector.h | 6 +- gtk2_ardour/main.cc | 3 + gtk2_ardour/mixer_ui.cc | 2 +- gtk2_ardour/new_session_dialog.cc | 4 +- gtk2_ardour/pixmaps/h_meter_strip.xpm | 195 - gtk2_ardour/pixmaps/v_meter_strip.xpm | 483 - gtk2_ardour/route_params_ui.cc | 2 +- gtk2_ardour/sfdb_ui.cc | 3 +- libs/ardour/SConscript | 18 +- libs/ardour/ardour/ardour.h | 3 - libs/ardour/ardour/audioengine.h | 24 +- libs/ardour/ardour/auditioner.h | 12 +- libs/ardour/ardour/automation_event.h | 10 +- libs/ardour/ardour/connection.h | 4 +- libs/ardour/ardour/control_protocol_manager.h | 4 +- libs/ardour/ardour/coreaudio_source.h | 2 +- libs/ardour/ardour/curve.h | 3 +- libs/ardour/ardour/diskstream.h | 10 +- libs/ardour/ardour/io.h | 23 +- libs/ardour/ardour/location.h | 10 +- libs/ardour/ardour/logcurve.h | 4 +- libs/ardour/ardour/playlist.h | 13 +- libs/ardour/ardour/redirect.h | 5 +- libs/ardour/ardour/region.h | 2 +- libs/ardour/ardour/route.h | 13 +- libs/ardour/ardour/session.h | 60 +- libs/ardour/ardour/session_connection.h | 2 +- libs/ardour/ardour/session_diskstream.h | 2 +- libs/ardour/ardour/session_playlist.h | 2 +- libs/ardour/ardour/session_region.h | 2 +- libs/ardour/ardour/session_route.h | 9 +- libs/ardour/ardour/session_selection.h | 2 +- libs/ardour/ardour/slave.h | 1 - libs/ardour/ardour/sndfilesource.h | 2 +- libs/ardour/ardour/source.h | 8 +- libs/ardour/ardour/tempo.h | 7 +- libs/ardour/audio_playlist.cc | 4 +- libs/ardour/audio_track.cc | 10 +- libs/ardour/audioengine.cc | 85 +- libs/ardour/audioregion.cc | 3 +- libs/ardour/auditioner.cc | 18 +- libs/ardour/automation_event.cc | 38 +- libs/ardour/connection.cc | 13 +- libs/ardour/control_protocol_manager.cc | 11 +- libs/ardour/coreaudio_source.cc | 58 +- libs/ardour/curve.cc | 7 +- libs/ardour/destructive_filesource.cc | 2 +- libs/ardour/diskstream.cc | 35 +- libs/ardour/filesource.cc | 27 +- libs/ardour/gdither.cc | 2 +- libs/ardour/globals.cc | 12 +- libs/ardour/import.cc | 9 +- libs/ardour/insert.cc | 6 +- libs/ardour/io.cc | 114 +- libs/ardour/location.cc | 28 +- libs/ardour/panner.cc | 5 +- libs/ardour/playlist.cc | 12 +- libs/ardour/redirect.cc | 8 +- libs/ardour/region.cc | 8 +- libs/ardour/route.cc | 46 +- libs/ardour/session.cc | 148 +- libs/ardour/session_butler.cc | 37 +- libs/ardour/session_click.cc | 4 +- libs/ardour/session_events.cc | 2 +- libs/ardour/session_export.cc | 8 +- libs/ardour/session_feedback.cc | 4 +- libs/ardour/session_midi.cc | 14 +- libs/ardour/session_process.cc | 41 +- libs/ardour/session_state.cc | 51 +- libs/ardour/session_transport.cc | 32 +- libs/ardour/sndfilesource.cc | 2 +- libs/ardour/source.cc | 35 +- libs/ardour/tempo.cc | 32 +- libs/gtkmm2ext/fastmeter.cc | 351 +- libs/gtkmm2ext/gtkmm2ext/fastmeter.h | 27 +- libs/gtkmm2ext/gtkmm2ext/gtk_ui.h | 3 +- libs/libsndfile/AUTHORS | 14 + libs/libsndfile/ChangeLog | 6107 +++++++ libs/libsndfile/Mingw-make-dist.sh | 113 + libs/libsndfile/NEWS | 126 + libs/libsndfile/README | 71 + libs/libsndfile/SConscript | 43 + libs/libsndfile/acinclude.m4 | 579 + libs/libsndfile/aclocal.m4 | 72 + libs/libsndfile/compile | 107 + libs/libsndfile/config.guess | 1497 ++ libs/libsndfile/config.sub | 1608 ++ libs/libsndfile/configure | 13925 ++++++++++++++++ libs/libsndfile/configure.ac | 541 + libs/libsndfile/depcomp | 479 + libs/libsndfile/install-sh | 294 + libs/libsndfile/libsndfile.spec.in | 69 + libs/libsndfile/missing | 336 + libs/libsndfile/mkinstalldirs | 111 + libs/libsndfile/sndfile.pc.in | 11 + libs/libsndfile/src/G72x/ChangeLog | 50 + libs/libsndfile/src/G72x/README | 0 libs/libsndfile/src/G72x/README.original | 94 + libs/libsndfile/src/G72x/g721.c | 162 + libs/libsndfile/src/G72x/g723_16.c | 169 + libs/libsndfile/src/G72x/g723_24.c | 146 + libs/libsndfile/src/G72x/g723_40.c | 160 + libs/libsndfile/src/G72x/g72x.c | 652 + libs/libsndfile/src/G72x/g72x.h | 99 + libs/libsndfile/src/G72x/g72x_priv.h | 118 + libs/libsndfile/src/G72x/g72x_test.c | 222 + libs/libsndfile/src/GSM610/COPYRIGHT | 16 + libs/libsndfile/src/GSM610/ChangeLog | 56 + libs/libsndfile/src/GSM610/README | 36 + libs/libsndfile/src/GSM610/add.c | 248 + libs/libsndfile/src/GSM610/code.c | 97 + libs/libsndfile/src/GSM610/config.h | 33 + libs/libsndfile/src/GSM610/decode.c | 67 + libs/libsndfile/src/GSM610/gsm.h | 58 + libs/libsndfile/src/GSM610/gsm610_priv.h | 308 + libs/libsndfile/src/GSM610/gsm_create.c | 44 + libs/libsndfile/src/GSM610/gsm_decode.c | 366 + libs/libsndfile/src/GSM610/gsm_destroy.c | 31 + libs/libsndfile/src/GSM610/gsm_encode.c | 456 + libs/libsndfile/src/GSM610/gsm_option.c | 74 + libs/libsndfile/src/GSM610/long_term.c | 951 ++ libs/libsndfile/src/GSM610/lpc.c | 341 + libs/libsndfile/src/GSM610/preprocess.c | 115 + libs/libsndfile/src/GSM610/rpe.c | 490 + libs/libsndfile/src/GSM610/short_term.c | 427 + libs/libsndfile/src/GSM610/table.c | 69 + libs/libsndfile/src/Symbols.darwin | 36 + libs/libsndfile/src/Symbols.linux | 42 + libs/libsndfile/src/aiff.c | 1482 ++ libs/libsndfile/src/alaw.c | 544 + libs/libsndfile/src/au.c | 453 + libs/libsndfile/src/avr.c | 254 + libs/libsndfile/src/broadcast.c | 89 + libs/libsndfile/src/caf.c | 538 + libs/libsndfile/src/command.c | 367 + libs/libsndfile/src/common.c | 1290 ++ libs/libsndfile/src/common.h | 766 + libs/libsndfile/src/config.h.in | 247 + libs/libsndfile/src/cygsndfile.def | 39 + libs/libsndfile/src/dither.c | 535 + libs/libsndfile/src/double64.c | 1009 ++ libs/libsndfile/src/dwd.c | 210 + libs/libsndfile/src/dwvw.c | 671 + libs/libsndfile/src/file_io.c | 1537 ++ libs/libsndfile/src/flac.c | 1156 ++ libs/libsndfile/src/float32.c | 961 ++ libs/libsndfile/src/float_cast.h | 262 + libs/libsndfile/src/g72x.c | 615 + libs/libsndfile/src/gsm610.c | 628 + libs/libsndfile/src/htk.c | 225 + libs/libsndfile/src/ima_adpcm.c | 976 ++ libs/libsndfile/src/interleave.c | 306 + libs/libsndfile/src/ircam.c | 331 + libs/libsndfile/src/libsndfile.def | 39 + libs/libsndfile/src/macbinary3.c | 58 + libs/libsndfile/src/macos.c | 63 + libs/libsndfile/src/mat4.c | 394 + libs/libsndfile/src/mat5.c | 507 + libs/libsndfile/src/ms_adpcm.c | 834 + libs/libsndfile/src/nist.c | 367 + libs/libsndfile/src/ogg.c | 44 + libs/libsndfile/src/paf.c | 843 + libs/libsndfile/src/pcm.c | 2899 ++++ libs/libsndfile/src/pvf.c | 199 + libs/libsndfile/src/raw.c | 111 + libs/libsndfile/src/rx2.c | 326 + libs/libsndfile/src/sd2.c | 613 + libs/libsndfile/src/sds.c | 993 ++ libs/libsndfile/src/sf_unistd.h | 67 + libs/libsndfile/src/sfconfig.h | 108 + libs/libsndfile/src/sfendian.h | 256 + libs/libsndfile/src/sndfile.c | 2694 +++ libs/libsndfile/src/sndfile.h.in | 554 + libs/libsndfile/src/stamp-h1 | 1 + libs/libsndfile/src/strings.c | 204 + libs/libsndfile/src/svx.c | 410 + libs/libsndfile/src/txw.c | 379 + libs/libsndfile/src/ulaw.c | 1047 ++ libs/libsndfile/src/voc.c | 878 + libs/libsndfile/src/vox_adpcm.c | 537 + libs/libsndfile/src/w64.c | 578 + libs/libsndfile/src/wav.c | 1633 ++ libs/libsndfile/src/wav_w64.c | 494 + libs/libsndfile/src/wav_w64.h | 283 + libs/libsndfile/src/wve.c | 125 + libs/libsndfile/src/xi.c | 1204 ++ libs/midi++2/SConscript | 2 +- libs/midi++2/midi++/port.h | 3 +- libs/midi++2/midimanager.cc | 11 +- libs/midi++2/midiport.cc | 4 +- libs/pbd3/SConscript | 6 +- libs/pbd3/basename.cc | 31 +- libs/pbd3/dirname.cc | 51 - libs/pbd3/pbd/abstract_ui.cc | 2 +- libs/pbd3/pbd/abstract_ui.h | 5 +- libs/pbd3/pbd/atomic.h | 1232 -- libs/pbd3/pbd/basename.h | 4 +- libs/pbd3/pbd/datum.h | 57 - libs/pbd3/pbd/dirname.h | 11 - libs/pbd3/pbd/ellipsoid.h | 74 - libs/pbd3/pbd/foreach.h | 42 - libs/pbd3/pbd/lock_free_fifo.h | 86 - libs/pbd3/pbd/lockmonitor.h | 325 - libs/pbd3/pbd/pool.h | 9 +- libs/pbd3/pbd/position.h | 38 - libs/pbd3/pbd/precision_timer.h | 61 - libs/pbd3/pbd/pthread_spinlock.h | 29 - libs/pbd3/pbd/rcpointer.h | 61 - libs/pbd3/pbd/relation.h | 35 - libs/pbd3/pbd/ringbuffer.h | 51 +- libs/pbd3/pbd/ringbufferNPT.h | 51 +- libs/pbd3/pbd/rt.h | 25 - libs/pbd3/pbd/rtthread.h | 30 - libs/pbd3/pbd/scale.h | 53 - libs/pbd3/pbd/thread.h | 127 - libs/pbd3/pbd/types.h | 32 - libs/pbd3/pbd/unescape.h | 6 - libs/pbd3/pool.cc | 30 +- libs/pbd3/unescape.cc | 137 - libs/surfaces/control_protocol/SConscript | 4 +- libs/surfaces/generic_midi/SConscript | 4 +- libs/surfaces/tranzport/SConscript | 4 +- .../tranzport/tranzport_control_protocol.h | 7 +- 237 files changed, 68673 insertions(+), 4051 deletions(-) delete mode 100644 gtk2_ardour/pixmaps/h_meter_strip.xpm delete mode 100644 gtk2_ardour/pixmaps/v_meter_strip.xpm create mode 100644 libs/libsndfile/AUTHORS create mode 100644 libs/libsndfile/ChangeLog create mode 100755 libs/libsndfile/Mingw-make-dist.sh create mode 100644 libs/libsndfile/NEWS create mode 100644 libs/libsndfile/README create mode 100644 libs/libsndfile/SConscript create mode 100644 libs/libsndfile/acinclude.m4 create mode 100644 libs/libsndfile/aclocal.m4 create mode 100755 libs/libsndfile/compile create mode 100755 libs/libsndfile/config.guess create mode 100755 libs/libsndfile/config.sub create mode 100755 libs/libsndfile/configure create mode 100644 libs/libsndfile/configure.ac create mode 100755 libs/libsndfile/depcomp create mode 100755 libs/libsndfile/install-sh create mode 100644 libs/libsndfile/libsndfile.spec.in create mode 100755 libs/libsndfile/missing create mode 100755 libs/libsndfile/mkinstalldirs create mode 100644 libs/libsndfile/sndfile.pc.in create mode 100644 libs/libsndfile/src/G72x/ChangeLog create mode 100644 libs/libsndfile/src/G72x/README create mode 100644 libs/libsndfile/src/G72x/README.original create mode 100644 libs/libsndfile/src/G72x/g721.c create mode 100644 libs/libsndfile/src/G72x/g723_16.c create mode 100644 libs/libsndfile/src/G72x/g723_24.c create mode 100644 libs/libsndfile/src/G72x/g723_40.c create mode 100644 libs/libsndfile/src/G72x/g72x.c create mode 100644 libs/libsndfile/src/G72x/g72x.h create mode 100644 libs/libsndfile/src/G72x/g72x_priv.h create mode 100644 libs/libsndfile/src/G72x/g72x_test.c create mode 100644 libs/libsndfile/src/GSM610/COPYRIGHT create mode 100644 libs/libsndfile/src/GSM610/ChangeLog create mode 100644 libs/libsndfile/src/GSM610/README create mode 100644 libs/libsndfile/src/GSM610/add.c create mode 100644 libs/libsndfile/src/GSM610/code.c create mode 100644 libs/libsndfile/src/GSM610/config.h create mode 100644 libs/libsndfile/src/GSM610/decode.c create mode 100644 libs/libsndfile/src/GSM610/gsm.h create mode 100644 libs/libsndfile/src/GSM610/gsm610_priv.h create mode 100644 libs/libsndfile/src/GSM610/gsm_create.c create mode 100644 libs/libsndfile/src/GSM610/gsm_decode.c create mode 100644 libs/libsndfile/src/GSM610/gsm_destroy.c create mode 100644 libs/libsndfile/src/GSM610/gsm_encode.c create mode 100644 libs/libsndfile/src/GSM610/gsm_option.c create mode 100644 libs/libsndfile/src/GSM610/long_term.c create mode 100644 libs/libsndfile/src/GSM610/lpc.c create mode 100644 libs/libsndfile/src/GSM610/preprocess.c create mode 100644 libs/libsndfile/src/GSM610/rpe.c create mode 100644 libs/libsndfile/src/GSM610/short_term.c create mode 100644 libs/libsndfile/src/GSM610/table.c create mode 100644 libs/libsndfile/src/Symbols.darwin create mode 100644 libs/libsndfile/src/Symbols.linux create mode 100644 libs/libsndfile/src/aiff.c create mode 100644 libs/libsndfile/src/alaw.c create mode 100644 libs/libsndfile/src/au.c create mode 100644 libs/libsndfile/src/avr.c create mode 100644 libs/libsndfile/src/broadcast.c create mode 100644 libs/libsndfile/src/caf.c create mode 100644 libs/libsndfile/src/command.c create mode 100644 libs/libsndfile/src/common.c create mode 100644 libs/libsndfile/src/common.h create mode 100644 libs/libsndfile/src/config.h.in create mode 100644 libs/libsndfile/src/cygsndfile.def create mode 100644 libs/libsndfile/src/dither.c create mode 100644 libs/libsndfile/src/double64.c create mode 100644 libs/libsndfile/src/dwd.c create mode 100644 libs/libsndfile/src/dwvw.c create mode 100644 libs/libsndfile/src/file_io.c create mode 100644 libs/libsndfile/src/flac.c create mode 100644 libs/libsndfile/src/float32.c create mode 100644 libs/libsndfile/src/float_cast.h create mode 100644 libs/libsndfile/src/g72x.c create mode 100644 libs/libsndfile/src/gsm610.c create mode 100644 libs/libsndfile/src/htk.c create mode 100644 libs/libsndfile/src/ima_adpcm.c create mode 100644 libs/libsndfile/src/interleave.c create mode 100644 libs/libsndfile/src/ircam.c create mode 100644 libs/libsndfile/src/libsndfile.def create mode 100644 libs/libsndfile/src/macbinary3.c create mode 100644 libs/libsndfile/src/macos.c create mode 100644 libs/libsndfile/src/mat4.c create mode 100644 libs/libsndfile/src/mat5.c create mode 100644 libs/libsndfile/src/ms_adpcm.c create mode 100644 libs/libsndfile/src/nist.c create mode 100644 libs/libsndfile/src/ogg.c create mode 100644 libs/libsndfile/src/paf.c create mode 100644 libs/libsndfile/src/pcm.c create mode 100644 libs/libsndfile/src/pvf.c create mode 100644 libs/libsndfile/src/raw.c create mode 100644 libs/libsndfile/src/rx2.c create mode 100644 libs/libsndfile/src/sd2.c create mode 100644 libs/libsndfile/src/sds.c create mode 100644 libs/libsndfile/src/sf_unistd.h create mode 100644 libs/libsndfile/src/sfconfig.h create mode 100644 libs/libsndfile/src/sfendian.h create mode 100644 libs/libsndfile/src/sndfile.c create mode 100644 libs/libsndfile/src/sndfile.h.in create mode 100644 libs/libsndfile/src/stamp-h1 create mode 100644 libs/libsndfile/src/strings.c create mode 100644 libs/libsndfile/src/svx.c create mode 100644 libs/libsndfile/src/txw.c create mode 100644 libs/libsndfile/src/ulaw.c create mode 100644 libs/libsndfile/src/voc.c create mode 100644 libs/libsndfile/src/vox_adpcm.c create mode 100644 libs/libsndfile/src/w64.c create mode 100644 libs/libsndfile/src/wav.c create mode 100644 libs/libsndfile/src/wav_w64.c create mode 100644 libs/libsndfile/src/wav_w64.h create mode 100644 libs/libsndfile/src/wve.c create mode 100644 libs/libsndfile/src/xi.c delete mode 100644 libs/pbd3/dirname.cc delete mode 100644 libs/pbd3/pbd/atomic.h delete mode 100644 libs/pbd3/pbd/datum.h delete mode 100644 libs/pbd3/pbd/dirname.h delete mode 100644 libs/pbd3/pbd/ellipsoid.h delete mode 100644 libs/pbd3/pbd/foreach.h delete mode 100644 libs/pbd3/pbd/lock_free_fifo.h delete mode 100644 libs/pbd3/pbd/lockmonitor.h delete mode 100644 libs/pbd3/pbd/position.h delete mode 100644 libs/pbd3/pbd/precision_timer.h delete mode 100644 libs/pbd3/pbd/pthread_spinlock.h delete mode 100644 libs/pbd3/pbd/rcpointer.h delete mode 100644 libs/pbd3/pbd/relation.h delete mode 100644 libs/pbd3/pbd/rt.h delete mode 100644 libs/pbd3/pbd/rtthread.h delete mode 100644 libs/pbd3/pbd/scale.h delete mode 100644 libs/pbd3/pbd/thread.h delete mode 100644 libs/pbd3/pbd/types.h delete mode 100644 libs/pbd3/pbd/unescape.h delete mode 100644 libs/pbd3/unescape.cc diff --git a/SConstruct b/SConstruct index 1403b69c8a..b0c0bb07cc 100644 --- a/SConstruct +++ b/SConstruct @@ -36,8 +36,10 @@ opts.AddOptions( BoolOption('FPU_OPTIMIZATION', 'Build runtime checked assembler code', 1), BoolOption('FFT_ANALYSIS', 'Include FFT analysis window', 0), BoolOption('SURFACES', 'Build support for control surfaces', 0), - BoolOption('DMALLOC', 'Compile and link using the dmalloc library', 0) - ) + BoolOption('DMALLOC', 'Compile and link using the dmalloc library', 0), + BoolOption('LIBLO', 'Compile with support for liblo library', 1), + BoolOption('COREAUDIO', 'Compile with Apple\'s CoreAudio library -- UNSTABLE', 0) +) #---------------------------------------------------------------------- # a handy helper that provides a way to merge compile/link information @@ -351,8 +353,8 @@ libraries = { } libraries['core'] = LibraryInfo (CCFLAGS = '-Ilibs') -libraries['sndfile'] = LibraryInfo() -libraries['sndfile'].ParseConfig('pkg-config --cflags --libs sndfile') +#libraries['sndfile'] = LibraryInfo(CCFLAGS = '-Ilibs/libsndfile/src') +#libraries['sndfile'].ParseConfig('pkg-config --cflags --libs sndfile') libraries['lrdf'] = LibraryInfo() libraries['lrdf'].ParseConfig('pkg-config --cflags --libs lrdf') @@ -380,6 +382,7 @@ libraries['glib2'] = LibraryInfo() libraries['glib2'].ParseConfig ('pkg-config --cflags --libs glib-2.0') libraries['glib2'].ParseConfig ('pkg-config --cflags --libs gobject-2.0') libraries['glib2'].ParseConfig ('pkg-config --cflags --libs gmodule-2.0') +libraries['glib2'].ParseConfig ('pkg-config --cflags --libs gthread-2.0') libraries['gtk2'] = LibraryInfo() libraries['gtk2'].ParseConfig ('pkg-config --cflags --libs gtk+-2.0') @@ -425,14 +428,15 @@ libraries['usb'] = conf.Finish () # # Check for liblo -libraries['lo'] = LibraryInfo () +if env['LIBLO']: + libraries['lo'] = LibraryInfo () -conf = Configure (libraries['lo']) -if conf.CheckLib ('lo', 'lo_server_new') == False: - print "liblo does not appear to be installed." - exit (0) + conf = Configure (libraries['lo']) + if conf.CheckLib ('lo', 'lo_server_new') == False: + print "liblo does not appear to be installed." + sys.exit (1) -libraries['lo'] = conf.Finish () + libraries['lo'] = conf.Finish () # # Check for dmalloc @@ -470,7 +474,10 @@ elif conf.CheckCHeader('/System/Library/Frameworks/CoreMIDI.framework/Headers/Co env['SYSMIDI'] = 'CoreMIDI' subst_dict['%MIDITAG%'] = "ardour" subst_dict['%MIDITYPE%'] = "coremidi" - +else: + print "It appears you don't have the required MIDI libraries installed." + sys.exit (1) + env = conf.Finish() if env['SYSLIBS']: @@ -539,6 +546,9 @@ else: libraries['soundtouch'] = LibraryInfo(LIBS='soundtouch', LIBPATH='#libs/soundtouch', CPPPATH=['#libs', '#libs/soundtouch']) + libraries['sndfile'] = LibraryInfo(LIBS='libsndfile', + LIBPATH='#libs/libsndfile', + CPPPATH='#libs/libsndfile') # libraries['libglademm'] = LibraryInfo(LIBS='libglademm', # LIBPATH='#libs/libglademm', # CPPPATH='#libs/libglademm') @@ -551,6 +561,7 @@ else: subdirs = [ # 'libs/cassowary', 'libs/sigc++2', + 'libs/libsndfile', 'libs/pbd3', 'libs/midi++2', 'libs/ardour' @@ -729,6 +740,12 @@ if env['FPU_OPTIMIZATION']: print "\nWarning: you are building Ardour with SSE support even though your system does not support these instructions. (This may not be an error, especially if you are a package maintainer)" # end optimization section +# +# save off guessed arch element in an env +# +env.Append(CONFIG_ARCH=config[config_arch]) + + # # ARCH="..." overrides all # @@ -757,6 +774,9 @@ env.Append(CCFLAGS="-Wall") if env['VST']: env.Append(CCFLAGS="-DVST_SUPPORT") +if env['LIBLO']: + env.Append(CCFLAGS="-DHAVE_LIBLO") + # # everybody needs this # diff --git a/gtk2_ardour/analysis_window.cc b/gtk2_ardour/analysis_window.cc index 014aeaaabc..f044ca7388 100644 --- a/gtk2_ardour/analysis_window.cc +++ b/gtk2_ardour/analysis_window.cc @@ -211,7 +211,7 @@ AnalysisWindow::analyze_data (Gtk::Button *button) { track_list_ready = false; { - LockMonitor lm (track_list_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (track_list_lock); // Empty track list & free old graphs clear_tracklist(); diff --git a/gtk2_ardour/analysis_window.h b/gtk2_ardour/analysis_window.h index a5ca5b3c26..cd1243bb6a 100644 --- a/gtk2_ardour/analysis_window.h +++ b/gtk2_ardour/analysis_window.h @@ -34,7 +34,7 @@ #include -#include +#include #include "ardour_dialog.h" @@ -106,7 +106,7 @@ class AnalysisWindow : public ArdourDialog FFTGraph fft_graph; bool track_list_ready; - PBD::Lock track_list_lock; + Glib::Mutex track_list_lock; friend class FFTGraph; }; diff --git a/gtk2_ardour/ardour_ui.cc b/gtk2_ardour/ardour_ui.cc index 146d4d2ffe..640b62df1f 100644 --- a/gtk2_ardour/ardour_ui.cc +++ b/gtk2_ardour/ardour_ui.cc @@ -33,7 +33,6 @@ #include #include -#include #include #include #include @@ -210,22 +209,6 @@ ARDOUR_UI::set_engine (AudioEngine& e) keyboard = new Keyboard; - string meter_path; - - meter_path = ARDOUR::find_data_file("v_meter_strip.xpm", "pixmaps"); - if (meter_path.empty()) { - error << _("no vertical meter strip image found") << endmsg; - exit (1); - } - FastMeter::set_vertical_xpm (meter_path); - - meter_path = ARDOUR::find_data_file("h_meter_strip.xpm", "pixmaps"); - if (meter_path.empty()) { - error << _("no horizontal meter strip image found") << endmsg; - exit (1); - } - FastMeter::set_horizontal_xpm (meter_path); - if (setup_windows ()) { throw failed_constructor (); } @@ -717,7 +700,7 @@ ARDOUR_UI::redisplay_recent_sessions () TreeModel::Row row = *(recent_session_model->append()); - row[recent_session_columns.visible_name] = PBD::basename (fullpath); + row[recent_session_columns.visible_name] = Glib::path_get_basename (fullpath); row[recent_session_columns.fullpath] = fullpath; if (states->size() > 1) { @@ -824,9 +807,11 @@ ARDOUR_UI::filter_ardour_session_dirs (const FileFilter::Info& info) return false; } + // XXX Portability + string session_file = info.filename; session_file += '/'; - session_file += PBD::basename (info.filename); + session_file += Glib::path_get_basename (info.filename); session_file += ".ardour"; if (stat (session_file.c_str(), &statbuf) != 0) { diff --git a/gtk2_ardour/audio_clock.cc b/gtk2_ardour/audio_clock.cc index 506b082b53..a5e7aa7193 100644 --- a/gtk2_ardour/audio_clock.cc +++ b/gtk2_ardour/audio_clock.cc @@ -41,6 +41,7 @@ using namespace sigc; using namespace Gtk; using PBD::atoi; +using PBD::atof; const uint32_t AudioClock::field_length[(int) AudioClock::AudioFrames+1] = { 2, /* SMPTE_Hours */ diff --git a/gtk2_ardour/connection_editor.cc b/gtk2_ardour/connection_editor.cc index 596029eeb3..f411f945c8 100644 --- a/gtk2_ardour/connection_editor.cc +++ b/gtk2_ardour/connection_editor.cc @@ -490,7 +490,7 @@ ConnectionEditor::display_ports () void ConnectionEditor::display_connection_state (bool for_input) { - LockMonitor lm (port_display_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (port_display_lock); uint32_t limit; if (session == 0 || current_connection == 0) { @@ -601,7 +601,7 @@ ConnectionEditor::add_port () void ConnectionEditor::connection_port_button_press_event (GdkEventButton* ev, TreeView* tview) { - LockMonitor lm (port_display_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (port_display_lock); int which_port = reinterpret_cast (treeview->get_data ("port")); diff --git a/gtk2_ardour/connection_editor.h b/gtk2_ardour/connection_editor.h index 1d6dd7d7fc..71d201cd8d 100644 --- a/gtk2_ardour/connection_editor.h +++ b/gtk2_ardour/connection_editor.h @@ -39,7 +39,7 @@ using __gnu_cxx::slist; #include "ardour_dialog.h" -#include +#include namespace ARDOUR { class Session; @@ -116,7 +116,7 @@ class ConnectionEditor : public ArdourDialog { Gtk::Button clear_button; Gtk::Button add_port_button; - PBD::Lock port_display_lock; + Glib::Mutex port_display_lock; slist port_displays; Gtk::Button ok_button; diff --git a/gtk2_ardour/editor.cc b/gtk2_ardour/editor.cc index 6dc3b955f1..c7956386ce 100644 --- a/gtk2_ardour/editor.cc +++ b/gtk2_ardour/editor.cc @@ -90,6 +90,7 @@ using namespace Gtkmm2ext; using namespace Editing; using PBD::internationalize; +using PBD::atoi; const double Editor::timebar_height = 15.0; @@ -2191,7 +2192,7 @@ Editor::set_state (const XMLNode& node) } if ((prop = node.property ("zoom"))) { - set_frames_per_unit (atof (prop->value())); + set_frames_per_unit (PBD::atof (prop->value())); } if ((prop = node.property ("snap-to"))) { @@ -2899,7 +2900,7 @@ Editor::convert_drop_to_paths (vector& paths, for (vector::iterator i = uris.begin(); i != uris.end(); ++i) { if ((*i).substr (0,7) == "file://") { string p = *i; - url_decode (p); + PBD::url_decode (p); paths.push_back (p.substr (7)); } } diff --git a/gtk2_ardour/editor_audio_import.cc b/gtk2_ardour/editor_audio_import.cc index 184c1757f2..ee73c46b24 100644 --- a/gtk2_ardour/editor_audio_import.cc +++ b/gtk2_ardour/editor_audio_import.cc @@ -203,7 +203,7 @@ Editor::embed_sndfile (Glib::ustring path, bool split, bool multiple_files, bool /* lets see if we can link it into the session */ linked_path = session->sound_dir(); - linked_path += PBD::basename (path); + linked_path += Glib::path_get_basename (path); if (link (path.c_str(), linked_path.c_str()) == 0) { diff --git a/gtk2_ardour/export_dialog.cc b/gtk2_ardour/export_dialog.cc index 1293fca34b..834127e042 100644 --- a/gtk2_ardour/export_dialog.cc +++ b/gtk2_ardour/export_dialog.cc @@ -27,7 +27,6 @@ #include #include -#include #include #include @@ -1154,7 +1153,7 @@ ExportDialog::is_filepath_valid(string &filepath) // directory needs to exist and be writable - string dirpath = PBD::dirname (filepath); + string dirpath = Glib::path_get_dirname (filepath); if (::access (dirpath.c_str(), W_OK) != 0) { string txt = _("Cannot write file in: ") + dirpath; MessageDialog msg (*this, txt, false, MESSAGE_ERROR, BUTTONS_OK, true); diff --git a/gtk2_ardour/export_range_markers_dialog.cc b/gtk2_ardour/export_range_markers_dialog.cc index 07ce651e62..3ff6ae783d 100644 --- a/gtk2_ardour/export_range_markers_dialog.cc +++ b/gtk2_ardour/export_range_markers_dialog.cc @@ -25,8 +25,6 @@ #include #include -#include - #include "ardour_ui.h" #include "export_range_markers_dialog.h" @@ -149,7 +147,7 @@ ExportRangeMarkersDialog::is_filepath_valid(string &filepath) } // directory needs to exist and be writable - string dirpath = PBD::dirname (filepath); + string dirpath = Glib::path_get_dirname (filepath); if (::access (dirpath.c_str(), W_OK) != 0) { string txt = _("Cannot write file in: ") + dirpath; MessageDialog msg (*this, txt, false, MESSAGE_ERROR, BUTTONS_OK, true); diff --git a/gtk2_ardour/fft_graph.cc b/gtk2_ardour/fft_graph.cc index df13614ecf..c2d81abf3c 100644 --- a/gtk2_ardour/fft_graph.cc +++ b/gtk2_ardour/fft_graph.cc @@ -58,7 +58,7 @@ void FFTGraph::setWindowSize(int windowSize) { if (_a_window) { - LockMonitor lm (_a_window->track_list_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (_a_window->track_list_lock); setWindowSize_internal(windowSize); } else { setWindowSize_internal(windowSize); @@ -261,7 +261,7 @@ FFTGraph::draw_scales(Glib::RefPtr window) void FFTGraph::redraw() { - LockMonitor lm (_a_window->track_list_lock, __LINE__, __FILE__ ); + Glib::Mutex::Lock lm (_a_window->track_list_lock); draw_scales(get_window()); diff --git a/gtk2_ardour/gtk-custom-hruler.c b/gtk2_ardour/gtk-custom-hruler.c index baa006a355..f0bbb9152e 100644 --- a/gtk2_ardour/gtk-custom-hruler.c +++ b/gtk2_ardour/gtk-custom-hruler.c @@ -133,7 +133,6 @@ gtk_custom_hruler_draw_ticks (GtkCustomRuler * ruler) { GtkWidget *widget; GdkGC *gc, *bg_gc; - GdkFont *font; gint i; GtkCustomRulerMark *marks; gint xthickness; @@ -154,7 +153,6 @@ gtk_custom_hruler_draw_ticks (GtkCustomRuler * ruler) gc = widget->style->fg_gc[GTK_STATE_NORMAL]; bg_gc = widget->style->bg_gc[GTK_STATE_NORMAL]; - font = gtk_style_get_font(widget->style); layout = gtk_widget_create_pango_layout (widget, "012456789"); pango_layout_get_extents (layout, &ink_rect, &logical_rect); diff --git a/gtk2_ardour/io_selector.cc b/gtk2_ardour/io_selector.cc index 247ad602bd..b45966c5e3 100644 --- a/gtk2_ardour/io_selector.cc +++ b/gtk2_ardour/io_selector.cc @@ -23,7 +23,7 @@ #include -#include +#include #include #include @@ -368,7 +368,7 @@ IOSelector::display_ports () TreeView *selected_port_tview = 0; { - LockMonitor lm (port_display_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (port_display_lock); Port *port; uint32_t limit; @@ -670,7 +670,7 @@ IOSelector::port_column_button_release (GdkEventButton* event, TreeView* treevie if (Keyboard::is_delete_event (event)) { Port* port; { - LockMonitor lm (port_display_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (port_display_lock); port = static_cast (treeview->get_data (_("port"))); @@ -724,7 +724,7 @@ IOSelector::select_treeview (TreeView* tview) switch. */ - LockMonitor lm (port_display_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (port_display_lock); Port* port = reinterpret_cast (tview->get_data (_("port"))); if (port != selected_port) { diff --git a/gtk2_ardour/io_selector.h b/gtk2_ardour/io_selector.h index 1dd77dd5a1..44518e6759 100644 --- a/gtk2_ardour/io_selector.h +++ b/gtk2_ardour/io_selector.h @@ -29,6 +29,9 @@ using __gnu_cxx::slist; #endif #include + +#include + #include #include #include @@ -39,6 +42,7 @@ using __gnu_cxx::slist; #include + namespace ARDOUR { class IO; class Session; @@ -105,7 +109,7 @@ class IOSelector : public Gtk::VBox { Gtk::Button clear_connections_button; Gtk::ScrolledWindow port_display_scroller; - PBD::Lock port_display_lock; + Glib::Mutex port_display_lock; slist port_displays; void display_ports (); diff --git a/gtk2_ardour/main.cc b/gtk2_ardour/main.cc index 20630e4f1c..e9ac25a8f8 100644 --- a/gtk2_ardour/main.cc +++ b/gtk2_ardour/main.cc @@ -367,6 +367,9 @@ main (int argc, char *argv[]) ARDOUR::AudioEngine *engine; vector null_file_list; + // needs a better home. + Glib::thread_init(); + gtk_set_locale (); (void) bindtextdomain (PACKAGE, LOCALEDIR); diff --git a/gtk2_ardour/mixer_ui.cc b/gtk2_ardour/mixer_ui.cc index 2d0a37cd47..1ded8625c6 100644 --- a/gtk2_ardour/mixer_ui.cc +++ b/gtk2_ardour/mixer_ui.cc @@ -24,7 +24,7 @@ #include #include -#include +#include #include #include diff --git a/gtk2_ardour/new_session_dialog.cc b/gtk2_ardour/new_session_dialog.cc index b7b448b677..88944aacb7 100644 --- a/gtk2_ardour/new_session_dialog.cc +++ b/gtk2_ardour/new_session_dialog.cc @@ -24,8 +24,6 @@ #include #include -#include - #include #include #include @@ -659,7 +657,7 @@ NewSessionDialog::reset_recent() Gtk::TreeModel::Row row = *(recent_model->append()); - row[recent_columns.visible_name] = PBD::basename (fullpath); + row[recent_columns.visible_name] = Glib::path_get_basename (fullpath); row[recent_columns.fullpath] = fullpath; if (states->size() > 1) { diff --git a/gtk2_ardour/pixmaps/h_meter_strip.xpm b/gtk2_ardour/pixmaps/h_meter_strip.xpm deleted file mode 100644 index b112772e33..0000000000 --- a/gtk2_ardour/pixmaps/h_meter_strip.xpm +++ /dev/null @@ -1,195 +0,0 @@ -/* XPM */ -static const gchar *h_meter_strip_xpm[] = { -"186 5 187 2", -" c None", -". c #2BFE00", -"+ c #2DFE00", -"@ c #2FFE01", -"# c #32FE01", -"$ c #34FE02", -"% c #36FE02", -"& c #38FE03", -"* c #3BFE03", -"= c #3DFD04", -"- c #3FFD04", -"; c #41FD05", -"> c #44FD05", -", c #46FD06", -"' c #48FD06", -") c #4AFD07", -"! c #4DFD07", -"~ c #4FFD08", -"{ c #51FC08", -"] c #53FC09", -"^ c #56FC09", -"/ c #58FC09", -"( c #5AFC0A", -"_ c #5CFC0A", -": c #5FFC0B", -"< c #61FC0B", -"[ c #63FB0C", -"} c #65FB0C", -"| c #68FB0D", -"1 c #6AFB0D", -"2 c #6CFB0E", -"3 c #6EFB0E", -"4 c #71FB0F", -"5 c #73FB0F", -"6 c #75FB10", -"7 c #77FA10", -"8 c #7AFA11", -"9 c #7CFA11", -"0 c #7EFA12", -"a c #80FA12", -"b c #83FA12", -"c c #85FA13", -"d c #87FA13", -"e c #89FA14", -"f c #8CF914", -"g c #8EF915", -"h c #90F915", -"i c #92F916", -"j c #95F916", -"k c #97F917", -"l c #99F917", -"m c #9BF918", -"n c #9EF818", -"o c #A0F819", -"p c #A2F819", -"q c #A4F81A", -"r c #A7F81A", -"s c #A9F81A", -"t c #ABF81B", -"u c #ADF81B", -"v c #B0F81C", -"w c #B2F71C", -"x c #B4F71D", -"y c #B6F71D", -"z c #B9F71E", -"A c #BBF71E", -"B c #BDF71F", -"C c #BFF71F", -"D c #C2F720", -"E c #C4F720", -"F c #C6F621", -"G c #C8F621", -"H c #CBF622", -"I c #CDF622", -"J c #CFF623", -"K c #D1F623", -"L c #D4F624", -"M c #D6F624", -"N c #D8F524", -"O c #DAF525", -"P c #DDF525", -"Q c #DFF526", -"R c #E1F526", -"S c #E3F527", -"T c #E6F527", -"U c #E8F528", -"V c #EAF528", -"W c #ECF429", -"X c #EFF429", -"Y c #F1F42A", -"Z c #F3F42A", -"` c #F5F42B", -" . c #F8F42B", -".. c #FAF42C", -"+. c #FCF42C", -"@. c #FFF42D", -"#. c #FFF22C", -"$. c #FFF12B", -"%. c #FFF02A", -"&. c #FFEF2A", -"*. c #FFEE29", -"=. c #FFED28", -"-. c #FFEC28", -";. c #FFEB27", -">. c #FFE926", -",. c #FFE826", -"'. c #FFE725", -"). c #FFE624", -"!. c #FFE524", -"~. c #FFE423", -"{. c #FFE322", -"]. c #FFE222", -"^. c #FFE021", -"/. c #FFDF20", -"(. c #FFDE20", -"_. c #FFDD1F", -":. c #FFDC1E", -"<. c #FFDB1E", -"[. c #FFDA1D", -"}. c #FFD91C", -"|. c #FFD71B", -"1. c #FFD61B", -"2. c #FFD51A", -"3. c #FFD419", -"4. c #FFD319", -"5. c #FFD218", -"6. c #FFD117", -"7. c #FFD017", -"8. c #FFCF16", -"9. c #FFCD15", -"0. c #FFCC15", -"a. c #FFCB14", -"b. c #FFCA13", -"c. c #FFC913", -"d. c #FFC812", -"e. c #FFC711", -"f. c #FFC611", -"g. c #FFC410", -"h. c #FFC30F", -"i. c #FFC20F", -"j. c #FFC10E", -"k. c #FFC00D", -"l. c #FFBF0C", -"m. c #FFBE0C", -"n. c #FFBD0B", -"o. c #FFBB0A", -"p. c #FFBA0A", -"q. c #FFB909", -"r. c #FFB808", -"s. c #FFB708", -"t. c #FFB607", -"u. c #FFB506", -"v. c #FFB406", -"w. c #FFB205", -"x. c #FFB104", -"y. c #FFB004", -"z. c #FFAF03", -"A. c #FFAE02", -"B. c #FFAD02", -"C. c #FFAC01", -"D. c #FFAB00", -"E. c #FFA900", -"F. c #F11F00", -"G. c #F21E00", -"H. c #F21C00", -"I. c #F31B00", -"J. c #F31A00", -"K. c #F41800", -"L. c #F41700", -"M. c #F51600", -"N. c #F61400", -"O. c #F61300", -"P. c #F71100", -"Q. c #F71000", -"R. c #F80F00", -"S. c #F90D00", -"T. c #F90C00", -"U. c #FA0B00", -"V. c #FA0900", -"W. c #FB0800", -"X. c #FC0600", -"Y. c #FC0500", -"Z. c #FD0400", -"`. c #FD0200", -" + c #FE0100", -".+ c #FE0000", -"++ c #FF0000", -". + @ # $ % & * = - ; > , ' ) ! ~ { ] ^ / ( _ : < [ } | 1 2 3 4 5 6 7 8 9 0 a b c d e f g h i j k l m n o p q r s t u v w x y z A B C D E F G H I J K L M N O P Q R S T U V W X Y Z ` ...+.@.@.#.$.%.&.*.=.-.;.>.,.'.).!.~.{.].^./.(._.:.<.[.}.|.1.2.3.4.5.6.7.8.9.0.a.b.c.d.e.f.g.h.i.j.k.l.m.n.o.p.q.r.s.t.u.v.w.x.y.z.A.B.C.D.E.F.G.H.I.J.K.L.M.N.O.P.Q.R.S.T.U.V.W.X.Y.Z.`. +.+", -". + @ # $ % & * = - ; > , ' ) ! ~ { ] ^ / ( _ : < [ } | 1 2 3 4 5 6 7 8 9 0 a b c d e f g h i j k l m n o p q r s t u v w x y z A B C D E F G H I J K L M N O P Q R S T U V W X Y Z ` ...+.@.@.#.$.%.&.*.=.-.;.>.,.'.).!.~.{.].^./.(._.:.<.[.}.|.1.2.3.4.5.6.7.8.9.0.a.b.c.d.e.f.g.h.i.j.k.l.m.n.o.p.q.r.s.t.u.v.w.x.y.z.A.B.C.D.E.F.G.H.I.J.K.L.M.N.O.P.Q.R.S.T.U.V.W.X.Y.Z.`. +.+", -". + @ # $ % & * = - ; > , ' ) ! ~ { ] ^ / ( _ : < [ } | 1 2 3 4 5 6 7 8 9 0 a b c d e f g h i j k l m n o p q r s t u v w x y z A B C D E F G H I J K L M N O P Q R S T U V W X Y Z ` ...+.@.@.#.$.%.&.*.=.-.;.>.,.'.).!.~.{.].^./.(._.:.<.[.}.|.1.2.3.4.5.6.7.8.9.0.a.b.c.d.e.f.g.h.i.j.k.l.m.n.o.p.q.r.s.t.u.v.w.x.y.z.A.B.C.D.E.F.G.H.I.J.K.L.M.N.O.P.Q.R.S.T.U.V.W.X.Y.Z.`. +++", -". + @ # $ % & * = - ; > , ' ) ! ~ { ] ^ / ( _ : < [ } | 1 2 3 4 5 6 7 8 9 0 a b c d e f g h i j k l m n o p q r s t u v w x y z A B C D E F G H I J K L M N O P Q R S T U V W X Y Z ` ...+.@.@.#.$.%.&.*.=.-.;.>.,.'.).!.~.{.].^./.(._.:.<.[.}.|.1.2.3.4.5.6.7.8.9.0.a.b.c.d.e.f.g.h.i.j.k.l.m.n.o.p.q.r.s.t.u.v.w.x.y.z.A.B.C.D.E.F.G.H.I.J.K.L.M.N.O.P.Q.R.S.T.U.V.W.X.Y.Z.`. +++", -". + @ # $ % & * = - ; > , ' ) ! ~ { ] ^ / ( _ : < [ } | 1 2 3 4 5 6 7 8 9 0 a b c d e f g h i j k l m n o p q r s t u v w x y z A B C D E F G H I J K L M N O P Q R S T U V W X Y Z ` ...+.@.@.#.$.%.&.*.=.-.;.>.,.'.).!.~.{.].^./.(._.:.<.[.}.|.1.2.3.4.5.6.7.8.9.0.a.b.c.d.e.f.g.h.i.j.k.l.m.n.o.p.q.r.s.t.u.v.w.x.y.z.A.B.C.D.E.F.G.H.I.J.K.L.M.N.O.P.Q.R.S.T.U.V.W.X.Y.Z.`. +++"}; diff --git a/gtk2_ardour/pixmaps/v_meter_strip.xpm b/gtk2_ardour/pixmaps/v_meter_strip.xpm deleted file mode 100644 index d673c1da0b..0000000000 --- a/gtk2_ardour/pixmaps/v_meter_strip.xpm +++ /dev/null @@ -1,483 +0,0 @@ -/* XPM */ -static const gchar * v_meter_strip_xpm[] = { -"5 250 230 2", -" c None", -". c #FE0000", -"+ c #FF0000", -"@ c #FE0100", -"# c #FD0200", -"$ c #FD0300", -"% c #FD0400", -"& c #FC0500", -"* c #FC0600", -"= c #FC0700", -"- c #FB0800", -"; c #FA0900", -"> c #FA0A00", -", c #FA0B00", -"' c #F90C00", -") c #F90D00", -"! c #F80E00", -"~ c #F80F00", -"{ c #F71000", -"] c #F71100", -"^ c #F61200", -"/ c #F61300", -"( c #F61400", -"_ c #F51600", -": c #F41700", -"< c #F41800", -"[ c #F31A00", -"} c #F31B00", -"| c #F21C00", -"1 c #F21E00", -"2 c #F11F00", -"3 c #F54A00", -"4 c #FFA900", -"5 c #FFAB00", -"6 c #FFAC01", -"7 c #FFAD02", -"8 c #FFAE02", -"9 c #FFAF03", -"0 c #FFB004", -"a c #FFB104", -"b c #FFB205", -"c c #FFB406", -"d c #FFB506", -"e c #FFB607", -"f c #FFB708", -"g c #FFB808", -"h c #FFB909", -"i c #FFBA0A", -"j c #FFBB0A", -"k c #FFBC0A", -"l c #FFBD0B", -"m c #FFBE0C", -"n c #FFBF0C", -"o c #FFC00D", -"p c #FFC10E", -"q c #FFC20F", -"r c #FFC30F", -"s c #FFC410", -"t c #FFC511", -"u c #FFC611", -"v c #FFC711", -"w c #FFC812", -"x c #FFC913", -"y c #FFCA13", -"z c #FFCB14", -"A c #FFCC15", -"B c #FFCD15", -"C c #FFCF16", -"D c #FFD017", -"E c #FFD117", -"F c #FFD218", -"G c #FFD319", -"H c #FFD419", -"I c #FFD51A", -"J c #FFD61B", -"K c #FFD71B", -"L c #FFD81C", -"M c #FFD91C", -"N c #FFDA1D", -"O c #FFDB1E", -"P c #FFDC1E", -"Q c #FFDD1F", -"R c #FFDE20", -"S c #FFDF20", -"T c #FFE021", -"U c #FFE222", -"V c #FFE322", -"W c #FFE423", -"X c #FFE524", -"Y c #FFE624", -"Z c #FFE725", -"` c #FFE826", -" . c #FFE926", -".. c #FFEA26", -"+. c #FFEB27", -"@. c #FFEC28", -"#. c #FFED28", -"$. c #FFEE29", -"%. c #FFEF2A", -"&. c #FFF02A", -"*. c #FFF12B", -"=. c #FFF22C", -"-. c #FFF32D", -";. c #FFF42D", -">. c #FDF42C", -",. c #FBF42C", -"'. c #FAF42C", -"). c #F8F42B", -"!. c #F6F42B", -"~. c #F4F42B", -"{. c #F3F42A", -"]. c #F1F42A", -"^. c #F0F429", -"/. c #EEF429", -"(. c #ECF429", -"_. c #EAF528", -":. c #E9F528", -"<. c #E7F528", -"[. c #E5F527", -"}. c #E3F527", -"|. c #E2F526", -"1. c #E0F526", -"2. c #DFF526", -"3. c #DDF525", -"4. c #DBF525", -"5. c #D9F525", -"6. c #D8F524", -"7. c #D6F624", -"8. c #D5F624", -"9. c #D3F624", -"0. c #D1F623", -"a. c #CFF623", -"b. c #CEF622", -"c. c #CCF622", -"d. c #CBF622", -"e. c #C9F621", -"f. c #C7F621", -"g. c #C5F621", -"h. c #C4F720", -"i. c #C2F720", -"j. c #C0F71F", -"k. c #BEF71F", -"l. c #BDF71F", -"m. c #BBF71E", -"n. c #BAF71E", -"o. c #B8F71E", -"p. c #B6F71D", -"q. c #B5F71D", -"r. c #B3F71D", -"s. c #B2F71C", -"t. c #B0F81C", -"u. c #AEF81B", -"v. c #ACF81B", -"w. c #ABF81B", -"x. c #A9F81A", -"y. c #A8F81A", -"z. c #A6F81A", -"A. c #A4F81A", -"B. c #A2F819", -"C. c #A1F819", -"D. c #9FF819", -"E. c #9EF818", -"F. c #9BF918", -"G. c #9AF917", -"H. c #98F917", -"I. c #97F917", -"J. c #95F916", -"K. c #93F916", -"L. c #91F916", -"M. c #90F915", -"N. c #8EF915", -"O. c #8DF914", -"P. c #8BF914", -"Q. c #89FA14", -"R. c #87FA13", -"S. c #86FA13", -"T. c #84FA13", -"U. c #83FA12", -"V. c #81FA12", -"W. c #7FFA12", -"X. c #7DFA12", -"Y. c #7CFA11", -"Z. c #7AFA11", -"`. c #78FA10", -" + c #76FA10", -".+ c #75FB10", -"++ c #73FB0F", -"@+ c #72FB0F", -"#+ c #70FB0F", -"$+ c #6EFB0E", -"%+ c #6DFB0E", -"&+ c #6BFB0E", -"*+ c #6AFB0D", -"=+ c #68FB0D", -"-+ c #66FB0C", -";+ c #64FB0C", -">+ c #63FB0C", -",+ c #61FC0B", -"'+ c #60FC0B", -")+ c #5EFC0B", -"!+ c #5CFC0A", -"~+ c #5AFC0A", -"{+ c #59FC09", -"]+ c #57FC09", -"^+ c #56FC09", -"/+ c #53FC09", -"(+ c #52FC08", -"_+ c #50FC08", -":+ c #4FFD08", -"<+ c #4DFD07", -"[+ c #4BFD07", -"}+ c #49FD07", -"|+ c #48FD06", -"1+ c #46FD06", -"2+ c #45FD05", -"3+ c #43FD05", -"4+ c #41FD05", -"5+ c #3FFD04", -"6+ c #3EFD04", -"7+ c #3CFD04", -"8+ c #3BFE03", -"9+ c #39FE03", -"0+ c #37FE02", -"a+ c #35FE02", -"b+ c #34FE02", -"c+ c #32FE01", -"d+ c #30FE01", -"e+ c #2EFE01", -"f+ c #2DFE00", -"g+ c #2BFE00", -". . + + + ", -". . + + + ", -"@ @ @ @ @ ", -"# # # # # ", -"$ $ $ $ $ ", -"% % % % % ", -"& & & & & ", -"* * * * * ", -"= = = = = ", -"- - - - - ", -"; ; ; ; ; ", -"> > > > > ", -", , , , , ", -"' ' ' ' ' ", -") ) ) ) ) ", -"! ! ! ! ! ", -"~ ~ ~ ~ ~ ", -"{ { { { { ", -"] ] ] ] ] ", -"^ ^ ^ ^ ^ ", -"/ / / / / ", -"( ( ( ( ( ", -"_ _ _ _ _ ", -": : : : : ", -": : : : : ", -"< < < < < ", -"[ [ [ [ [ ", -"} } } } } ", -"} } } } } ", -"| | | | | ", -"1 1 1 1 1 ", -"2 2 2 2 2 ", -"3 3 3 3 3 ", -"4 4 4 4 4 ", -"5 5 5 5 5 ", -"6 6 6 6 6 ", -"6 6 6 6 6 ", -"7 7 7 7 7 ", -"8 8 8 8 8 ", -"9 9 9 9 9 ", -"9 9 9 9 9 ", -"0 0 0 0 0 ", -"a a a a a ", -"a a a a a ", -"b b b b b ", -"c c c c c ", -"d d d d d ", -"d d d d d ", -"e e e e e ", -"f f f f f ", -"g g g g g ", -"g g g g g ", -"h h h h h ", -"i i i i i ", -"j j j j j ", -"k k k k k ", -"l l l l l ", -"m m m m m ", -"n n n n n ", -"n n n n n ", -"o o o o o ", -"p p p p p ", -"q q q q q ", -"q q q q q ", -"r r r r r ", -"s s s s s ", -"t t t t t ", -"u u u u u ", -"v v v v v ", -"w w w w w ", -"x x x x x ", -"x x x x x ", -"y y y y y ", -"z z z z z ", -"A A A A A ", -"A A A A A ", -"B B B B B ", -"C C C C C ", -"D D D D D ", -"D D D D D ", -"E E E E E ", -"F F F F F ", -"G G G G G ", -"G G G G G ", -"H H H H H ", -"I I I I I ", -"I I I I I ", -"J J J J J ", -"K K K K K ", -"L L L L L ", -"M M M M M ", -"N N N N N ", -"O O O O O ", -"P P P P P ", -"P P P P P ", -"Q Q Q Q Q ", -"R R R R R ", -"S S S S S ", -"S S S S S ", -"T T T T T ", -"U U U U U ", -"V V V V V ", -"V V V V V ", -"W W W W W ", -"X X X X X ", -"Y Y Y Y Y ", -"Y Y Y Y Y ", -"Z Z Z Z Z ", -"` ` ` ` ` ", -" . . . . .", -"..........", -"+.+.+.+.+.", -"@.@.@.@.@.", -"#.#.#.#.#.", -"#.#.#.#.#.", -"$.$.$.$.$.", -"%.%.%.%.%.", -"&.&.&.&.&.", -"&.&.&.&.&.", -"*.*.*.*.*.", -"=.=.=.=.=.", -"-.-.-.-.-.", -";.;.;.;.;.", -";.;.;.;.;.", -">.>.>.>.>.", -",.,.,.,.,.", -"'.'.'.'.'.", -").).).).).", -"!.!.!.!.!.", -"~.~.~.~.~.", -"{.{.{.{.{.", -"].].].].].", -"^.^.^.^.^.", -"/././././.", -"(.(.(.(.(.", -"_._._._._.", -":.:.:.:.:.", -"<.<.<.<.<.", -"[.[.[.[.[.", -"}.}.}.}.}.", -"|.|.|.|.|.", -"1.1.1.1.1.", -"2.2.2.2.2.", -"3.3.3.3.3.", -"4.4.4.4.4.", -"5.5.5.5.5.", -"6.6.6.6.6.", -"7.7.7.7.7.", -"8.8.8.8.8.", -"9.9.9.9.9.", -"0.0.0.0.0.", -"a.a.a.a.a.", -"b.b.b.b.b.", -"c.c.c.c.c.", -"d.d.d.d.d.", -"e.e.e.e.e.", -"f.f.f.f.f.", -"g.g.g.g.g.", -"h.h.h.h.h.", -"i.i.i.i.i.", -"j.j.j.j.j.", -"k.k.k.k.k.", -"l.l.l.l.l.", -"m.m.m.m.m.", -"n.n.n.n.n.", -"o.o.o.o.o.", -"p.p.p.p.p.", -"q.q.q.q.q.", -"r.r.r.r.r.", -"s.s.s.s.s.", -"t.t.t.t.t.", -"u.u.u.u.u.", -"v.v.v.v.v.", -"w.w.w.w.w.", -"x.x.x.x.x.", -"y.y.y.y.y.", -"z.z.z.z.z.", -"A.A.A.A.A.", -"B.B.B.B.B.", -"C.C.C.C.C.", -"D.D.D.D.D.", -"E.E.E.E.E.", -"F.F.F.F.F.", -"G.G.G.G.G.", -"H.H.H.H.H.", -"I.I.I.I.I.", -"J.J.J.J.J.", -"K.K.K.K.K.", -"L.L.L.L.L.", -"M.M.M.M.M.", -"N.N.N.N.N.", -"O.O.O.O.O.", -"P.P.P.P.P.", -"Q.Q.Q.Q.Q.", -"R.R.R.R.R.", -"S.S.S.S.S.", -"T.T.T.T.T.", -"U.U.U.U.U.", -"V.V.V.V.V.", -"W.W.W.W.W.", -"X.X.X.X.X.", -"Y.Y.Y.Y.Y.", -"Z.Z.Z.Z.Z.", -"`.`.`.`.`.", -" + + + + +", -".+.+.+.+.+", -"++++++++++", -"@+@+@+@+@+", -"#+#+#+#+#+", -"$+$+$+$+$+", -"%+%+%+%+%+", -"&+&+&+&+&+", -"*+*+*+*+*+", -"=+=+=+=+=+", -"-+-+-+-+-+", -";+;+;+;+;+", -">+>+>+>+>+", -",+,+,+,+,+", -"'+'+'+'+'+", -")+)+)+)+)+", -"!+!+!+!+!+", -"~+~+~+~+~+", -"{+{+{+{+{+", -"]+]+]+]+]+", -"^+^+^+^+^+", -"/+/+/+/+/+", -"(+(+(+(+(+", -"_+_+_+_+_+", -":+:+:+:+:+", -"<+<+<+<+<+", -"[+[+[+[+[+", -"}+}+}+}+}+", -"|+|+|+|+|+", -"1+1+1+1+1+", -"2+2+2+2+2+", -"3+3+3+3+3+", -"4+4+4+4+4+", -"5+5+5+5+5+", -"6+6+6+6+6+", -"7+7+7+7+7+", -"8+8+8+8+8+", -"9+9+9+9+9+", -"0+0+0+0+0+", -"a+a+a+a+a+", -"b+b+b+b+b+", -"c+c+c+c+c+", -"d+d+d+d+d+", -"e+e+e+e+e+", -"f+f+f+f+f+", -"g+g+g+g+g+"}; diff --git a/gtk2_ardour/route_params_ui.cc b/gtk2_ardour/route_params_ui.cc index a52cf79f3f..aee247df02 100644 --- a/gtk2_ardour/route_params_ui.cc +++ b/gtk2_ardour/route_params_ui.cc @@ -20,7 +20,7 @@ #include -#include +#include #include #include diff --git a/gtk2_ardour/sfdb_ui.cc b/gtk2_ardour/sfdb_ui.cc index a8b2510cf5..947f470ac8 100644 --- a/gtk2_ardour/sfdb_ui.cc +++ b/gtk2_ardour/sfdb_ui.cc @@ -25,7 +25,6 @@ #include #include -#include #include #include @@ -206,7 +205,7 @@ SoundFileBox::play_btn_clicked () } string result; - _session->region_name (result, PBD::basename(srclist[0]->name()), false); + _session->region_name (result, Glib::path_get_basename(srclist[0]->name()), false); AudioRegion* a_region = new AudioRegion(srclist, 0, srclist[0]->length(), result, 0, Region::DefaultFlags, false); region_cache[path] = a_region; } diff --git a/libs/ardour/SConscript b/libs/ardour/SConscript index 93593bad18..0fb5cfc788 100644 --- a/libs/ardour/SConscript +++ b/libs/ardour/SConscript @@ -58,7 +58,6 @@ ladspa_plugin.cc location.cc mtc_slave.cc named_selection.cc -osc.cc panner.cc pcm_utils.cc playlist.cc @@ -97,6 +96,7 @@ mix.cc arch_specific_objects = [ ] +osc_files = [ 'osc.cc' ] vst_files = [ 'vst_plugin.cc', 'session_vst.cc' ] coreaudio_files = [ 'coreaudio_source.cc' ] extra_sources = [ ] @@ -104,6 +104,9 @@ extra_sources = [ ] if ardour['VST']: extra_sources += vst_files +if ardour['LIBLO']: + extra_sources += osc_files + ardour.Append(CCFLAGS="-D_REENTRANT -D_LARGEFILE_SOURCE -D_LARGEFILE64_SOURCE") ardour.Append(CXXFLAGS="-DDATA_DIR=\\\""+final_prefix+"/share\\\"") ardour.Append(CXXFLAGS="-DMODULE_DIR=\\\""+final_prefix+"/lib\\\"") @@ -172,13 +175,16 @@ if conf.CheckCHeader('sys/vfs.h'): if conf.CheckCHeader('/System/Library/Frameworks/CoreMIDI.framework/Headers/CoreMIDI.h'): ardour.Append(LINKFLAGS="-framework CoreMIDI") -if conf.CheckCHeader('/System/Library/Frameworks/AudioToolbox.framework/Headers/ExtendedAudioFile.h'): +if conf.CheckCHeader('/System/Library/Frameworks/AudioToolbox.framework/Headers/ExtendedAudioFile.h') and ardour['COREAUDIO'] == 1: ardour.Append(CXXFLAGS="-DHAVE_COREAUDIO") ardour.Append(LINKFLAGS="-framework AudioToolbox") - # + + +if env['CONFIG_ARCH'] == 'apple': # this next line avoids issues with circular dependencies between libardour and libardour_cp. # it is based on the (entirely reasonable) assumption that a system with CoreAudio is OS X # + print 'APPLE CONFIG' ardour.Append(LINKFLAGS='-undefined suppress -flat_namespace') extra_sources += coreaudio_files @@ -188,15 +194,19 @@ ardour.Merge ([ libraries['core'], libraries['xml'], libraries['sndfile'], + libraries['raptor'], libraries['lrdf'], libraries['samplerate'], libraries['sigc2'], libraries['pbd3'], libraries['soundtouch'], libraries['midi++2'], - libraries['lo'], + libraries['glib2'], + libraries['glibmm2'] ]) +if ardour['LIBLO']: + ardour.Merge ([ libraries['lo'] ]) ardour.VersionBuild(['version.cc', 'ardour/version.h'], 'SConscript') diff --git a/libs/ardour/ardour/ardour.h b/libs/ardour/ardour/ardour.h index 3308266f2f..fee6c601a2 100644 --- a/libs/ardour/ardour/ardour.h +++ b/libs/ardour/ardour/ardour.h @@ -26,14 +26,11 @@ #include #include -#include #include #include #include -using namespace PBD; - namespace MIDI { class MachineControl; class Port; diff --git a/libs/ardour/ardour/audioengine.h b/libs/ardour/ardour/audioengine.h index 36dbbd1dbe..50bf7dddcc 100644 --- a/libs/ardour/ardour/audioengine.h +++ b/libs/ardour/ardour/audioengine.h @@ -28,7 +28,9 @@ #include #include -#include + +#include + #include #include #include @@ -59,7 +61,7 @@ class AudioEngine : public sigc::trackable int start (); bool running() const { return _running; } - PBD::NonBlockingLock& process_lock() { return _process_lock; } + Glib::Mutex& process_lock() { return _process_lock; } jack_nframes_t frame_rate(); jack_nframes_t frames_per_cycle(); @@ -185,10 +187,10 @@ class AudioEngine : public sigc::trackable ARDOUR::Session *session; jack_client_t *_jack; std::string jack_client_name; - PBD::NonBlockingLock port_lock; - PBD::NonBlockingLock _process_lock; - PBD::Lock session_remove_lock; - pthread_cond_t session_removed; + Glib::Mutex port_lock; + Glib::Mutex _process_lock; + Glib::Mutex session_remove_lock; + Glib::Cond session_removed; bool session_remove_pending; bool _running; bool _has_run; @@ -202,8 +204,6 @@ class AudioEngine : public sigc::trackable sigc::slot freewheel_action; bool reconnect_on_halt; int _usecs_per_cycle; - jack_nframes_t last_meter_point; - jack_nframes_t meter_interval; typedef std::set Ports; Ports ports; @@ -237,10 +237,10 @@ class AudioEngine : public sigc::trackable int connect_to_jack (std::string client_name); - static void* _meter_thread (void* arg); - void* meter_thread (); - pthread_t meter_thread_id; - void maybe_start_metering_thread (); + void meter_thread (); + void start_metering_thread (); + Glib::Thread* m_meter_thread; + mutable gint m_meter_exit; }; }; /* namespace ARDOUR */ diff --git a/libs/ardour/ardour/auditioner.h b/libs/ardour/ardour/auditioner.h index b79620eaa2..434ec32f97 100644 --- a/libs/ardour/ardour/auditioner.h +++ b/libs/ardour/ardour/auditioner.h @@ -22,10 +22,8 @@ #define __ardour_auditioner_h__ #include -#include -#include -#include +#include #include #include @@ -50,16 +48,16 @@ class Auditioner : public AudioTrack int play_audition (jack_nframes_t nframes); void cancel_audition () { - atomic_set (&_active, 0); + g_atomic_int_set (&_active, 0); } - bool active() const { return atomic_read (&_active); } + bool active() const { return g_atomic_int_get (&_active); } private: AudioRegion *the_region; jack_nframes_t current_frame; - atomic_t _active; - PBD::Lock lock; + mutable gint _active; + Glib::Mutex lock; jack_nframes_t length; void drop_ports (); diff --git a/libs/ardour/ardour/automation_event.h b/libs/ardour/ardour/automation_event.h index f26828a114..78daa531dd 100644 --- a/libs/ardour/ardour/automation_event.h +++ b/libs/ardour/ardour/automation_event.h @@ -26,7 +26,7 @@ #include #include -#include +#include #include #include #include @@ -144,7 +144,7 @@ class AutomationList : public StateManager std::pair control_points_adjacent (double when); template void apply_to_points (T& obj, void (T::*method)(const AutomationList&)) { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); (obj.*method)(*this); } @@ -157,13 +157,13 @@ class AutomationList : public StateManager double get_max_xval() const { return max_xval; } double eval (double where) { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); return unlocked_eval (where); } double rt_safe_eval (double where, bool& ok) { - TentativeLockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock, Glib::TRY_LOCK); if ((ok = lm.locked())) { return unlocked_eval (where); @@ -186,7 +186,7 @@ class AutomationList : public StateManager }; AutomationEventList events; - mutable PBD::NonBlockingLock lock; + mutable Glib::Mutex lock; bool _frozen; bool changed_when_thawed; bool _dirty; diff --git a/libs/ardour/ardour/connection.h b/libs/ardour/ardour/connection.h index b33af9cb21..899bffc06a 100644 --- a/libs/ardour/ardour/connection.h +++ b/libs/ardour/ardour/connection.h @@ -24,7 +24,7 @@ #include #include #include -#include +#include #include using std::vector; @@ -67,7 +67,7 @@ class Connection : public Stateful, public sigc::trackable { Connection (const XMLNode&); private: - mutable PBD::Lock port_lock; + mutable Glib::Mutex port_lock; vector _ports; string _name; bool _sysdep; diff --git a/libs/ardour/ardour/control_protocol_manager.h b/libs/ardour/ardour/control_protocol_manager.h index 42b5a69a48..03b21a299c 100644 --- a/libs/ardour/ardour/control_protocol_manager.h +++ b/libs/ardour/ardour/control_protocol_manager.h @@ -6,7 +6,7 @@ #include -#include +#include #include @@ -52,7 +52,7 @@ struct ControlProtocolInfo { static ControlProtocolManager* _instance; Session* _session; - PBD::Lock protocols_lock; + Glib::Mutex protocols_lock; std::list control_protocols; void drop_session (); diff --git a/libs/ardour/ardour/coreaudio_source.h b/libs/ardour/ardour/coreaudio_source.h index 4193623006..736ea32df7 100644 --- a/libs/ardour/ardour/coreaudio_source.h +++ b/libs/ardour/ardour/coreaudio_source.h @@ -40,7 +40,7 @@ class CoreAudioSource : public ExternalSource { mutable float *tmpbuf; mutable jack_nframes_t tmpbufsize; - mutable PBD::Lock _tmpbuf_lock; + mutable Glib::Mutex _tmpbuf_lock; void init (const string &str, bool build_peak); }; diff --git a/libs/ardour/ardour/curve.h b/libs/ardour/ardour/curve.h index 1c6a4c5bc4..ede060e1cb 100644 --- a/libs/ardour/ardour/curve.h +++ b/libs/ardour/ardour/curve.h @@ -23,11 +23,10 @@ #include #include -#include +#include #include #include #include -#include #include namespace ARDOUR { diff --git a/libs/ardour/ardour/diskstream.h b/libs/ardour/ardour/diskstream.h index 8838177f14..316daba52f 100644 --- a/libs/ardour/ardour/diskstream.h +++ b/libs/ardour/ardour/diskstream.h @@ -33,7 +33,7 @@ #include #include -#include + #include #include @@ -115,7 +115,7 @@ class DiskStream : public Stateful, public sigc::trackable } void set_record_enabled (bool yn, void *src); - bool record_enabled() const { return atomic_read (&_record_enabled); } + bool record_enabled() const { return g_atomic_int_get (&_record_enabled); } void punch_in (); void punch_out (); @@ -320,7 +320,7 @@ class DiskStream : public Stateful, public sigc::trackable uint32_t _n_channels; id_t _id; - atomic_t _record_enabled; + mutable gint _record_enabled; AudioPlaylist* _playlist; double _visible_speed; double _actual_speed; @@ -365,7 +365,7 @@ class DiskStream : public Stateful, public sigc::trackable AlignStyle _persistent_alignment_style; bool first_input_change; - PBD::NonBlockingLock state_lock; + Glib::Mutex state_lock; jack_nframes_t scrub_start; jack_nframes_t scrub_buffer_size; @@ -404,7 +404,7 @@ class DiskStream : public Stateful, public sigc::trackable }; vector capture_info; - PBD::Lock capture_info_lock; + Glib::Mutex capture_info_lock; void init (Flag); diff --git a/libs/ardour/ardour/io.h b/libs/ardour/ardour/io.h index 8321e9afda..c80a7abfaa 100644 --- a/libs/ardour/ardour/io.h +++ b/libs/ardour/ardour/io.h @@ -27,10 +27,11 @@ #include #include -#include +#include + #include #include -#include + #include #include @@ -205,7 +206,15 @@ class IO : public Stateful, public ARDOUR::StateManager } } - static sigc::signal Meter; + static void update_meters(); + +private: + + static sigc::signal Meter; + static Glib::StaticMutex m_meter_signal_lock; + sigc::connection m_meter_connection; + +public: /* automation */ @@ -261,7 +270,7 @@ class IO : public Stateful, public ARDOUR::StateManager int ports_became_legal (); private: - mutable PBD::Lock io_lock; + mutable Glib::Mutex io_lock; protected: Session& _session; @@ -269,7 +278,7 @@ class IO : public Stateful, public ARDOUR::StateManager gain_t _gain; gain_t _effective_gain; gain_t _desired_gain; - PBD::NonBlockingLock declick_lock; + Glib::Mutex declick_lock; vector _outputs; vector _inputs; vector _peak_power; @@ -322,7 +331,7 @@ class IO : public Stateful, public ARDOUR::StateManager jack_nframes_t last_automation_snapshot; static jack_nframes_t _automation_interval; - AutoState _gain_automation_state; + AutoState _gain_automation_state; AutoStyle _gain_automation_style; bool apply_gain_automation; @@ -331,7 +340,7 @@ class IO : public Stateful, public ARDOUR::StateManager int save_automation (const string&); int load_automation (const string&); - PBD::NonBlockingLock automation_lock; + Glib::Mutex automation_lock; /* AudioTrack::deprecated_use_diskstream_connections() needs these */ diff --git a/libs/ardour/ardour/location.h b/libs/ardour/ardour/location.h index bb744c95be..75f4c5d12a 100644 --- a/libs/ardour/ardour/location.h +++ b/libs/ardour/ardour/location.h @@ -27,10 +27,10 @@ #include #include -#include #include -#include +#include + #include #include "ardour.h" @@ -168,12 +168,12 @@ class Locations : public Stateful, public StateManager sigc::signal removed; template void apply (T& obj, void (T::*method)(LocationList&)) { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); (obj.*method)(locations); } template void apply (T1& obj, void (T1::*method)(LocationList&, T2& arg), T2& arg) { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); (obj.*method)(locations, arg); } @@ -190,7 +190,7 @@ class Locations : public Stateful, public StateManager LocationList locations; Location *current_location; - mutable PBD::Lock lock; + mutable Glib::Mutex lock; int set_current_unlocked (Location *); void location_changed (Location*); diff --git a/libs/ardour/ardour/logcurve.h b/libs/ardour/ardour/logcurve.h index 84911b0369..e65be55772 100644 --- a/libs/ardour/ardour/logcurve.h +++ b/libs/ardour/ardour/logcurve.h @@ -22,7 +22,7 @@ #define __ardour_logcurve_h__ #include -#include +#include namespace ARDOUR { @@ -94,7 +94,7 @@ class LogCurve { } void set_length (uint32_t len) { l = len; } - mutable PBD::NonBlockingLock lock; + mutable Glib::Mutex lock; protected: float a; diff --git a/libs/ardour/ardour/playlist.h b/libs/ardour/ardour/playlist.h index c6cb65efc5..d322f564ee 100644 --- a/libs/ardour/ardour/playlist.h +++ b/libs/ardour/ardour/playlist.h @@ -28,8 +28,9 @@ #include +#include + #include -#include #include #include @@ -169,9 +170,9 @@ class Playlist : public Stateful, public StateManager { RegionList regions; string _name; Session& _session; - atomic_t block_notifications; - atomic_t ignore_state_changes; - mutable PBD::NonBlockingLock region_lock; + mutable gint block_notifications; + mutable gint ignore_state_changes; + mutable Glib::Mutex region_lock; RegionList pending_removals; RegionList pending_adds; RegionList pending_bounds; @@ -197,8 +198,8 @@ class Playlist : public Stateful, public StateManager { void init (bool hide); bool holding_state () const { - return atomic_read (&block_notifications) != 0 || - atomic_read (&ignore_state_changes) != 0; + return g_atomic_int_get (&block_notifications) != 0 || + g_atomic_int_get (&ignore_state_changes) != 0; } /* prevent the compiler from ever generating these */ diff --git a/libs/ardour/ardour/redirect.h b/libs/ardour/ardour/redirect.h index b370589079..ede55a1d80 100644 --- a/libs/ardour/ardour/redirect.h +++ b/libs/ardour/ardour/redirect.h @@ -27,7 +27,8 @@ #include #include -#include +#include + #include #include @@ -131,7 +132,7 @@ class Redirect : public IO map parameter_automation; set visible_parameter_automation; - mutable PBD::NonBlockingLock _automation_lock; + mutable Glib::Mutex _automation_lock; void can_automate (uint32_t); set can_automate_list; diff --git a/libs/ardour/ardour/region.h b/libs/ardour/ardour/region.h index 5af5a660c1..3c94dad6fd 100644 --- a/libs/ardour/ardour/region.h +++ b/libs/ardour/ardour/region.h @@ -221,7 +221,7 @@ class Region : public Stateful, public StateManager string _name; mutable RegionEditState _first_edit; int _frozen; - PBD::Lock lock; + Glib::Mutex lock; ARDOUR::id_t _id; ARDOUR::Playlist* _playlist; mutable uint32_t _read_data_count; // modified in read() diff --git a/libs/ardour/ardour/route.h b/libs/ardour/ardour/route.h index 8a707eb902..5699d9ef14 100644 --- a/libs/ardour/ardour/route.h +++ b/libs/ardour/ardour/route.h @@ -27,11 +27,8 @@ #include #include -#include - -#include #include -#include +#include #include #include #include @@ -142,14 +139,14 @@ class Route : public IO void flush_redirects (); template void foreach_redirect (T *obj, void (T::*func)(Redirect *)) { - RWLockMonitor lm (redirect_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (redirect_lock); for (RedirectList::iterator i = _redirects.begin(); i != _redirects.end(); ++i) { (obj->*func) (*i); } } Redirect *nth_redirect (uint32_t n) { - RWLockMonitor lm (redirect_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (redirect_lock); RedirectList::iterator i; for (i = _redirects.begin(); i != _redirects.end() && n; ++i, --n); if (i == _redirects.end()) { @@ -294,9 +291,9 @@ class Route : public IO jack_nframes_t _roll_delay; jack_nframes_t _own_latency; RedirectList _redirects; - PBD::NonBlockingRWLock redirect_lock; + Glib::RWLock redirect_lock; IO *_control_outs; - PBD::NonBlockingLock control_outs_lock; + Glib::Mutex control_outs_lock; RouteGroup *_edit_group; RouteGroup *_mix_group; std::string _comment; diff --git a/libs/ardour/ardour/session.h b/libs/ardour/ardour/session.h index 0d968fcff1..83acb3f82a 100644 --- a/libs/ardour/ardour/session.h +++ b/libs/ardour/ardour/session.h @@ -31,9 +31,9 @@ #include +#include + #include -#include -#include #include #include @@ -274,7 +274,7 @@ class Session : public sigc::trackable, public Stateful typedef list DiskStreamList; Session::DiskStreamList disk_streams() const { - RWLockMonitor lm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (diskstream_lock); return diskstreams; /* XXX yes, force a copy */ } @@ -284,7 +284,7 @@ class Session : public sigc::trackable, public Stateful typedef list RouteList; RouteList get_routes() const { - RWLockMonitor rlock (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock rlock (route_lock); return routes; /* XXX yes, force a copy */ } @@ -310,7 +310,7 @@ class Session : public sigc::trackable, public Stateful } RecordState record_status() const { - return (RecordState) atomic_read (&_record_status); + return (RecordState) g_atomic_int_get (&_record_status); } bool actively_recording () { @@ -1004,12 +1004,12 @@ class Session : public sigc::trackable, public Stateful typedef void (Session::*process_function_type)(jack_nframes_t); AudioEngine &_engine; - atomic_t processing_prohibited; + mutable gint processing_prohibited; process_function_type process_function; process_function_type last_process_function; jack_nframes_t _current_frame_rate; int transport_sub_state; - atomic_t _record_status; + mutable gint _record_status; jack_nframes_t _transport_frame; Location* end_location; Location* start_location; @@ -1166,14 +1166,14 @@ class Session : public sigc::trackable, public Stateful bool pending_abort; bool pending_auto_loop; - Sample* butler_mixdown_buffer; - float* butler_gain_buffer; - pthread_t butler_thread; - PBD::NonBlockingLock butler_request_lock; - pthread_cond_t butler_paused; - bool butler_should_run; - atomic_t butler_should_do_transport_work; - int butler_request_pipe[2]; + Sample* butler_mixdown_buffer; + float* butler_gain_buffer; + pthread_t butler_thread; + Glib::Mutex butler_request_lock; + Glib::Cond butler_paused; + bool butler_should_run; + mutable gint butler_should_do_transport_work; + int butler_request_pipe[2]; struct ButlerRequest { enum Type { @@ -1417,10 +1417,10 @@ class Session : public sigc::trackable, public Stateful static MultiAllocSingleReleasePool pool; }; - PBD::Lock midi_lock; + Glib::Mutex midi_lock; pthread_t midi_thread; int midi_request_pipe[2]; - atomic_t butler_active; + mutable gint butler_active; RingBuffer midi_requests; int start_midi_thread (); @@ -1471,7 +1471,7 @@ class Session : public sigc::trackable, public Stateful /* disk-streams */ DiskStreamList diskstreams; - mutable PBD::NonBlockingRWLock diskstream_lock; + mutable Glib::RWLock diskstream_lock; uint32_t dstream_buffer_size; void add_diskstream (DiskStream*); int load_diskstreams (const XMLNode&); @@ -1479,7 +1479,7 @@ class Session : public sigc::trackable, public Stateful /* routes stuff */ RouteList routes; - mutable PBD::NonBlockingRWLock route_lock; + mutable Glib::RWLock route_lock; void add_route (Route*); uint32_t destructive_index; @@ -1502,7 +1502,7 @@ class Session : public sigc::trackable, public Stateful /* REGION MANAGEMENT */ - mutable PBD::Lock region_lock; + mutable Glib::Mutex region_lock; typedef map AudioRegionList; AudioRegionList audio_regions; @@ -1515,7 +1515,7 @@ class Session : public sigc::trackable, public Stateful /* SOURCES */ - mutable PBD::Lock source_lock; + mutable Glib::Mutex source_lock; typedef std::map SourceList; SourceList sources; @@ -1529,7 +1529,7 @@ class Session : public sigc::trackable, public Stateful /* PLAYLISTS */ - mutable PBD::Lock playlist_lock; + mutable Glib::Mutex playlist_lock; typedef set PlaylistList; PlaylistList playlists; PlaylistList unused_playlists; @@ -1547,7 +1547,7 @@ class Session : public sigc::trackable, public Stateful /* NAMED SELECTIONS */ - mutable PBD::Lock named_selection_lock; + mutable Glib::Mutex named_selection_lock; typedef set NamedSelectionList; NamedSelectionList named_selections; @@ -1607,7 +1607,7 @@ class Session : public sigc::trackable, public Stateful vector session_dirs; vector::iterator last_rr_session_dir; uint32_t _total_free_4k_blocks; - PBD::Lock space_lock; + Glib::Mutex space_lock; static const char* sound_dir_name; static const char* tape_dir_name; @@ -1618,15 +1618,15 @@ class Session : public sigc::trackable, public Stateful int ensure_sound_dir (string, string&); void refresh_disk_space (); - atomic_t _playback_load; - atomic_t _capture_load; - atomic_t _playback_load_min; - atomic_t _capture_load_min; + mutable gint _playback_load; + mutable gint _capture_load; + mutable gint _playback_load_min; + mutable gint _capture_load_min; /* I/O Connections */ typedef list ConnectionList; - mutable PBD::Lock connection_lock; + mutable Glib::Mutex connection_lock; ConnectionList _connections; int load_connections (const XMLNode&); @@ -1685,7 +1685,7 @@ class Session : public sigc::trackable, public Stateful Sample* click_emphasis_data; jack_nframes_t click_length; jack_nframes_t click_emphasis_length; - mutable PBD::NonBlockingRWLock click_lock; + mutable Glib::RWLock click_lock; static const Sample default_click[]; static const jack_nframes_t default_click_length; diff --git a/libs/ardour/ardour/session_connection.h b/libs/ardour/ardour/session_connection.h index caa20ed387..addc896b0b 100644 --- a/libs/ardour/ardour/session_connection.h +++ b/libs/ardour/ardour/session_connection.h @@ -29,7 +29,7 @@ namespace ARDOUR { template void Session::foreach_connection (T *obj, void (T::*func)(Connection *)) { - LockMonitor lm (connection_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (connection_lock); for (ConnectionList::iterator i = _connections.begin(); i != _connections.end(); i++) { (obj->*func) (*i); } diff --git a/libs/ardour/ardour/session_diskstream.h b/libs/ardour/ardour/session_diskstream.h index 24693c5793..3c888c92c3 100644 --- a/libs/ardour/ardour/session_diskstream.h +++ b/libs/ardour/ardour/session_diskstream.h @@ -29,7 +29,7 @@ namespace ARDOUR { template void Session::foreach_diskstream (T *obj, void (T::*func)(DiskStream&)) { - RWLockMonitor lm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (diskstream_lock); for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); i++) { if (!(*i)->hidden()) { (obj->*func) (**i); diff --git a/libs/ardour/ardour/session_playlist.h b/libs/ardour/ardour/session_playlist.h index 925a60182a..6f1b8dbd12 100644 --- a/libs/ardour/ardour/session_playlist.h +++ b/libs/ardour/ardour/session_playlist.h @@ -29,7 +29,7 @@ namespace ARDOUR { template void Session::foreach_playlist (T *obj, void (T::*func)(Playlist *)) { - LockMonitor lm (playlist_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (playlist_lock); for (PlaylistList::iterator i = playlists.begin(); i != playlists.end(); i++) { if (!(*i)->hidden()) { (obj->*func) (*i); diff --git a/libs/ardour/ardour/session_region.h b/libs/ardour/ardour/session_region.h index 16580d8e73..13d88a9aa4 100644 --- a/libs/ardour/ardour/session_region.h +++ b/libs/ardour/ardour/session_region.h @@ -8,7 +8,7 @@ namespace ARDOUR { template void Session::foreach_audio_region (T *obj, void (T::*func)(AudioRegion *)) { - LockMonitor lm (region_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (region_lock); for (AudioRegionList::iterator i = audio_regions.begin(); i != audio_regions.end(); i++) { (obj->*func) ((*i).second); } diff --git a/libs/ardour/ardour/session_route.h b/libs/ardour/ardour/session_route.h index f3c8e3f5fb..afe78b394e 100644 --- a/libs/ardour/ardour/session_route.h +++ b/libs/ardour/ardour/session_route.h @@ -23,7 +23,8 @@ #include -#include +#include + #include #include @@ -35,7 +36,7 @@ Session::foreach_route (T *obj, void (T::*func)(Route&)) RouteList public_order; { - RWLockMonitor lm (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (route_lock); public_order = routes; } @@ -53,7 +54,7 @@ Session::foreach_route (T *obj, void (T::*func)(Route*)) RouteList public_order; { - RWLockMonitor lm (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (route_lock); public_order = routes; } @@ -72,7 +73,7 @@ Session::foreach_route (T *obj, void (T::*func)(Route&, A), A arg1) RouteList public_order; { - RWLockMonitor lm (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (route_lock); public_order = routes; } diff --git a/libs/ardour/ardour/session_selection.h b/libs/ardour/ardour/session_selection.h index a1dd31d7ff..a110c2c3da 100644 --- a/libs/ardour/ardour/session_selection.h +++ b/libs/ardour/ardour/session_selection.h @@ -29,7 +29,7 @@ namespace ARDOUR { template void Session::foreach_named_selection (T& obj, void (T::*func)(NamedSelection&)) { - LockMonitor lm (named_selection_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (named_selection_lock); for (NamedSelectionList::iterator i = named_selections.begin(); i != named_selections.end(); i++) { (obj.*func) (**i); } diff --git a/libs/ardour/ardour/slave.h b/libs/ardour/ardour/slave.h index 90e63aed83..0079c10e0a 100644 --- a/libs/ardour/ardour/slave.h +++ b/libs/ardour/ardour/slave.h @@ -25,7 +25,6 @@ #include -#include #include #include #include diff --git a/libs/ardour/ardour/sndfilesource.h b/libs/ardour/ardour/sndfilesource.h index 2bd6042ec2..5d11c9ef09 100644 --- a/libs/ardour/ardour/sndfilesource.h +++ b/libs/ardour/ardour/sndfilesource.h @@ -43,7 +43,7 @@ class SndFileSource : public ExternalSource { mutable float *tmpbuf; mutable jack_nframes_t tmpbufsize; - mutable PBD::Lock _tmpbuf_lock; + mutable Glib::Mutex _tmpbuf_lock; void init (const string &str, bool build_peak); }; diff --git a/libs/ardour/ardour/source.h b/libs/ardour/ardour/source.h index 2eee7a7634..3781950fbf 100644 --- a/libs/ardour/ardour/source.h +++ b/libs/ardour/ardour/source.h @@ -25,10 +25,12 @@ #include #include -#include +#include #include +#include + #include #include #include @@ -125,7 +127,7 @@ class Source : public Stateful, public sigc::trackable string _name; uint32_t _use_cnt; bool _peaks_built; - mutable PBD::Lock _lock; + mutable Glib::Mutex _lock; jack_nframes_t _length; bool next_peak_clear_should_notify; string peakpath; @@ -156,7 +158,7 @@ class Source : public Stateful, public sigc::trackable }; static vector pending_peak_sources; - static PBD::Lock pending_peak_sources_lock; + static Glib::StaticMutex pending_peak_sources_lock; static void queue_for_peaks (Source&); static void clear_queue_for_peaks (); diff --git a/libs/ardour/ardour/tempo.h b/libs/ardour/ardour/tempo.h index 2f04f603e7..13e8eb6348 100644 --- a/libs/ardour/ardour/tempo.h +++ b/libs/ardour/ardour/tempo.h @@ -25,8 +25,7 @@ #include #include #include -#include -#include +#include #include #include @@ -198,7 +197,7 @@ class TempoMap : public Stateful, public StateManager { typedef vector BBTPointList; template void apply_with_metrics (T& obj, void (T::*method)(const Metrics&)) { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); (obj.*method)(*metrics); } @@ -285,7 +284,7 @@ class TempoMap : public Stateful, public StateManager { jack_nframes_t last_bbt_when; bool last_bbt_valid; BBT_Time last_bbt; - mutable PBD::Lock lock; + mutable Glib::Mutex lock; void timestamp_metrics (); diff --git a/libs/ardour/audio_playlist.cc b/libs/ardour/audio_playlist.cc index a0d43d5575..9f3c02ce43 100644 --- a/libs/ardour/audio_playlist.cc +++ b/libs/ardour/audio_playlist.cc @@ -203,7 +203,7 @@ AudioPlaylist::read (Sample *buf, Sample *mixdown_buffer, float *gain_buffer, ch its OK to block (for short intervals). */ - LockMonitor rm (region_lock, __LINE__, __FILE__); + Glib::Mutex::Lock rm (region_lock); end = start + cnt - 1; @@ -504,7 +504,7 @@ AudioPlaylist::add_crossfade (Crossfade& xfade) void AudioPlaylist::notify_crossfade_added (Crossfade *x) { - if (atomic_read(&block_notifications)) { + if (g_atomic_int_get(&block_notifications)) { _pending_xfade_adds.insert (_pending_xfade_adds.end(), x); } else { NewCrossfade (x); /* EMIT SIGNAL */ diff --git a/libs/ardour/audio_track.cc b/libs/ardour/audio_track.cc index 702d167a4f..30adc54d1a 100644 --- a/libs/ardour/audio_track.cc +++ b/libs/ardour/audio_track.cc @@ -625,7 +625,7 @@ AudioTrack::roll (jack_nframes_t nframes, jack_nframes_t start_frame, jack_nfram jack_nframes_t transport_frame; { - TentativeRWLockMonitor lm (redirect_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (redirect_lock, Glib::TRY_LOCK); if (lm.locked()) { // automation snapshot can also be called from the non-rt context // and it uses the redirect list, so we take the lock out here @@ -709,7 +709,7 @@ AudioTrack::roll (jack_nframes_t nframes, jack_nframes_t start_frame, jack_nfram /* don't waste time with automation if we're recording or we've just stopped (yes it can happen) */ if (!diskstream->record_enabled() && _session.transport_rolling()) { - TentativeLockMonitor am (automation_lock, __LINE__, __FILE__); + Glib::Mutex::Lock am (automation_lock, Glib::TRY_LOCK); if (am.locked() && gain_automation_playback()) { apply_gain_automation = _gain_automation_curve.rt_safe_get_vector (start_frame, end_frame, _session.gain_automation_buffer(), nframes); @@ -789,7 +789,7 @@ AudioTrack::export_stuff (vector& buffers, char * workbuf, uint32_t nbu vector::iterator bi; Sample * b; - RWLockMonitor rlock (redirect_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock rlock (redirect_lock); if (diskstream->playlist()->read (buffers[0], mix_buffer, gain_buffer, workbuf, start, nframes) != nframes) { return -1; @@ -958,7 +958,7 @@ AudioTrack::freeze (InterThreadInfo& itt) _freeze_record.have_mementos = true; { - RWLockMonitor lm (redirect_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (redirect_lock); for (RedirectList::iterator r = _redirects.begin(); r != _redirects.end(); ++r) { @@ -1015,7 +1015,7 @@ AudioTrack::unfreeze () } else { - RWLockMonitor lm (redirect_lock, false, __LINE__, __FILE__); // should this be a write lock? jlc + Glib::RWLock::ReaderLock lm (redirect_lock); // should this be a write lock? jlc for (RedirectList::iterator i = _redirects.begin(); i != _redirects.end(); ++i) { for (vector::iterator ii = _freeze_record.insert_info.begin(); ii != _freeze_record.insert_info.end(); ++ii) { if ((*ii)->id == (*i)->id()) { diff --git a/libs/ardour/audioengine.cc b/libs/ardour/audioengine.cc index 9d736f765e..87866e7b31 100644 --- a/libs/ardour/audioengine.cc +++ b/libs/ardour/audioengine.cc @@ -22,6 +22,7 @@ #include #include +#include #include #include @@ -45,7 +46,6 @@ jack_nframes_t Port::long_over_length = 10; AudioEngine::AudioEngine (string client_name) { - pthread_cond_init (&session_removed, 0); session = 0; session_remove_pending = false; _running = false; @@ -60,10 +60,12 @@ AudioEngine::AudioEngine (string client_name) _buffer_size = 0; _freewheeling = false; _freewheel_thread_registered = false; - last_meter_point = 0; - meter_interval = 0; - meter_thread_id = (pthread_t) 0; + + m_meter_thread = 0; + m_meter_exit = false; + start_metering_thread(); + if (connect_to_jack (client_name)) { throw NoBackendAvailable (); } @@ -76,9 +78,9 @@ AudioEngine::~AudioEngine () jack_client_close (_jack); } - if (meter_thread_id != (pthread_t) 0) { - pthread_cancel (meter_thread_id); - } + if(m_meter_thread) { + g_atomic_int_inc(&m_meter_exit); + } } void @@ -227,7 +229,7 @@ AudioEngine::_freewheel_callback (int onoff, void *arg) int AudioEngine::process_callback (jack_nframes_t nframes) { - TentativeLockMonitor tm (_process_lock, __LINE__, __FILE__); + Glib::Mutex::Lock tm (_process_lock, Glib::TRY_LOCK); jack_nframes_t next_processed_frames; /* handle wrap around of total frames counter */ @@ -246,7 +248,7 @@ AudioEngine::process_callback (jack_nframes_t nframes) if (session_remove_pending) { session = 0; session_remove_pending = false; - pthread_cond_signal (&session_removed); + session_removed.signal(); _processed_frames = next_processed_frames; return 0; } @@ -269,14 +271,7 @@ AudioEngine::process_callback (jack_nframes_t nframes) _processed_frames = next_processed_frames; return 0; } - - /* manage meters */ - if ((meter_interval > _buffer_size) && (last_meter_point + meter_interval < next_processed_frames)) { - IO::Meter (); - last_meter_point = next_processed_frames; - } - if (last_monitor_check + monitor_check_interval < next_processed_frames) { for (Ports::iterator i = ports.begin(); i != ports.end(); ++i) { @@ -315,11 +310,6 @@ AudioEngine::jack_sample_rate_callback (jack_nframes_t nframes) monitor_check_interval = nframes / 10; last_monitor_check = 0; - meter_interval = nframes / 100; - last_meter_point = 0; - - maybe_start_metering_thread (); - if (session) { session->set_frame_rate (nframes); } @@ -350,48 +340,25 @@ AudioEngine::jack_bufsize_callback (jack_nframes_t nframes) session->set_block_size (_buffer_size); } - maybe_start_metering_thread (); - return 0; } void -AudioEngine::maybe_start_metering_thread () +AudioEngine::start_metering_thread () { - if (meter_interval == 0) { - return; - } - - if (_buffer_size == 0) { - return; - } - - if (meter_interval < _buffer_size) { - if (meter_thread_id != (pthread_t) 0) { - pthread_cancel (meter_thread_id); - } - pthread_create (&meter_thread_id, 0, _meter_thread, this); - } + if(m_meter_thread == 0) { + m_meter_thread = Glib::Thread::create (sigc::mem_fun(this, &AudioEngine::meter_thread), false); + } } -void* -AudioEngine::_meter_thread (void *arg) -{ - return static_cast(arg)->meter_thread (); -} - -void* +void AudioEngine::meter_thread () { - PBD::ThreadCreated (pthread_self(), "Metering"); - - while (true) { - usleep (10000); /* 1/100th sec interval */ - pthread_testcancel(); - IO::Meter (); + while (g_atomic_int_get(&m_meter_exit) != true) { + Glib::usleep (10000); /* 1/100th sec interval */ + IO::update_meters (); } - - return 0; + return; } void @@ -405,13 +372,13 @@ AudioEngine::set_session (Session *s) void AudioEngine::remove_session () { - LockMonitor lm (_process_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (_process_lock); if (_running) { if (session) { session_remove_pending = true; - pthread_cond_wait (&session_removed, _process_lock.mutex()); + session_removed.wait(_process_lock); } } else { @@ -448,7 +415,7 @@ AudioEngine::register_audio_input_port (const string& portname) } else { - pthread_mutex_unlock (_process_lock.mutex()); + _process_lock.unlock(); throw PortRegistrationFailure(); } @@ -476,7 +443,7 @@ AudioEngine::register_audio_output_port (const string& portname) } else { - pthread_mutex_unlock (_process_lock.mutex()); + _process_lock.unlock(); throw PortRegistrationFailure (); } @@ -633,7 +600,7 @@ AudioEngine::frames_per_cycle () Port * AudioEngine::get_port_by_name (const string& portname, bool keep) { - LockMonitor lm (_process_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (_process_lock); if (!_running) { if (!_has_run) { @@ -966,7 +933,7 @@ AudioEngine::reconnect_to_jack () if (_jack) { disconnect_from_jack (); /* XXX give jackd a chance */ - usleep (250000); + Glib::usleep (250000); } if (connect_to_jack (jack_client_name)) { diff --git a/libs/ardour/audioregion.cc b/libs/ardour/audioregion.cc index eb8dfbc123..21773d9222 100644 --- a/libs/ardour/audioregion.cc +++ b/libs/ardour/audioregion.cc @@ -27,8 +27,9 @@ #include #include +#include + #include -#include #include #include diff --git a/libs/ardour/auditioner.cc b/libs/ardour/auditioner.cc index ed97cf7b39..ce7b9a3e6f 100644 --- a/libs/ardour/auditioner.cc +++ b/libs/ardour/auditioner.cc @@ -18,7 +18,7 @@ $Id$ */ -#include +#include #include #include @@ -57,7 +57,7 @@ Auditioner::Auditioner (Session& s) IO::output_changed.connect (mem_fun (*this, &Auditioner::output_changed)); the_region = 0; - atomic_set (&_active, 0); + g_atomic_int_set (&_active, 0); } Auditioner::~Auditioner () @@ -74,14 +74,14 @@ Auditioner::prepare_playlist () void Auditioner::audition_current_playlist () { - if (atomic_read (&_active)) { + if (g_atomic_int_get (&_active)) { /* don't go via session for this, because we are going to remain active. */ cancel_audition (); } - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); diskstream->seek (0); length = diskstream->playlist()->get_maximum_extent(); current_frame = 0; @@ -90,20 +90,20 @@ Auditioner::audition_current_playlist () _panner->reset (n_outputs(), diskstream->n_channels()); - atomic_set (&_active, 1); + g_atomic_int_set (&_active, 1); } void Auditioner::audition_region (AudioRegion& region) { - if (atomic_read (&_active)) { + if (g_atomic_int_get (&_active)) { /* don't go via session for this, because we are going to remain active. */ cancel_audition (); } - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); the_region = new AudioRegion (region); the_region->set_position (0, this); @@ -126,7 +126,7 @@ Auditioner::audition_region (AudioRegion& region) length = the_region->length(); diskstream->seek (0); current_frame = 0; - atomic_set (&_active, 1); + g_atomic_int_set (&_active, 1); } int @@ -136,7 +136,7 @@ Auditioner::play_audition (jack_nframes_t nframes) jack_nframes_t this_nframes; int ret; - if (atomic_read (&_active) == 0) { + if (g_atomic_int_get (&_active) == 0) { silence (nframes, 0); return 0; } diff --git a/libs/ardour/automation_event.cc b/libs/ardour/automation_event.cc index 88932009bf..17888c4a7c 100644 --- a/libs/ardour/automation_event.cc +++ b/libs/ardour/automation_event.cc @@ -225,7 +225,7 @@ void AutomationList::clear () { { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); events.clear (); if (!no_state) { save_state (_("cleared")); @@ -239,14 +239,14 @@ AutomationList::clear () void AutomationList::x_scale (double factor) { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); _x_scale (factor); } bool AutomationList::extend_to (double when) { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); if (events.empty() || events.back()->when == when) { return false; } @@ -285,7 +285,7 @@ AutomationList::rt_add (double when, double value) // cerr << "RT: alist @ " << this << " add " << value << " @ " << when << endl; { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); iterator where; TimeComparator cmp; @@ -369,7 +369,7 @@ AutomationList::add (double when, double value, bool for_loading) /* this is for graphical editing and loading data from storage */ { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); TimeComparator cmp; ControlEvent cp (when, 0.0f); bool insert = true; @@ -413,7 +413,7 @@ void AutomationList::erase (AutomationList::iterator i) { { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); events.erase (i); reposition_for_rt_add (0); if (!no_state) { @@ -428,7 +428,7 @@ void AutomationList::erase (AutomationList::iterator start, AutomationList::iterator end) { { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); events.erase (start, end); reposition_for_rt_add (0); if (!no_state) { @@ -445,7 +445,7 @@ AutomationList::reset_range (double start, double endt) bool reset = false; { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); TimeComparator cmp; ControlEvent cp (start, 0.0f); iterator s; @@ -481,7 +481,7 @@ AutomationList::erase_range (double start, double endt) bool erased = false; { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); TimeComparator cmp; ControlEvent cp (start, 0.0f); iterator s; @@ -515,7 +515,7 @@ AutomationList::move_range (iterator start, iterator end, double xdelta, double */ { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); while (start != end) { (*start)->when += xdelta; @@ -542,7 +542,7 @@ AutomationList::modify (iterator iter, double when, double val) */ { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); (*iter)->when = when; (*iter)->value = val; if (!no_state) { @@ -558,7 +558,7 @@ AutomationList::modify (iterator iter, double when, double val) std::pair AutomationList::control_points_adjacent (double xval) { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); iterator i; TimeComparator cmp; ControlEvent cp (xval, 0.0f); @@ -620,7 +620,7 @@ Change AutomationList::restore_state (StateManager::State& state) { { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); State* lstate = dynamic_cast (&state); events.clear (); @@ -655,7 +655,7 @@ void AutomationList::truncate_end (double last_coordinate) { { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); ControlEvent cp (last_coordinate, 0); list::reverse_iterator i; double last_val; @@ -760,7 +760,7 @@ void AutomationList::truncate_start (double overall_length) { { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); AutomationList::iterator i; double first_legal_value; double first_legal_coordinate; @@ -998,7 +998,7 @@ AutomationList::cut (iterator start, iterator end) AutomationList* nal = new AutomationList (default_value); { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); for (iterator x = start; x != end; ) { iterator tmp; @@ -1032,7 +1032,7 @@ AutomationList::cut_copy_clear (double start, double end, int op) bool changed = false; { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); if ((s = lower_bound (events.begin(), events.end(), &cp, cmp)) == events.end()) { return nal; @@ -1094,7 +1094,7 @@ AutomationList::copy (iterator start, iterator end) AutomationList* nal = new AutomationList (default_value); { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); for (iterator x = start; x != end; ) { iterator tmp; @@ -1141,7 +1141,7 @@ AutomationList::paste (AutomationList& alist, double pos, float times) } { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); iterator where; iterator prev; double end = 0; diff --git a/libs/ardour/connection.cc b/libs/ardour/connection.cc index 83e0a87dc1..719751f7ba 100644 --- a/libs/ardour/connection.cc +++ b/libs/ardour/connection.cc @@ -28,7 +28,6 @@ #include "i18n.h" using namespace ARDOUR; -using namespace PBD; Connection::Connection (const XMLNode& node) { @@ -58,7 +57,7 @@ void Connection::add_connection (int port, string portname) { { - LockMonitor lm (port_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (port_lock); _ports[port].push_back (portname); } ConnectionsChanged (port); /* EMIT SIGNAL */ @@ -70,7 +69,7 @@ Connection::remove_connection (int port, string portname) bool changed = false; { - LockMonitor lm (port_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (port_lock); PortList& pl = _ports[port]; PortList::iterator i = find (pl.begin(), pl.end(), portname); @@ -88,7 +87,7 @@ Connection::remove_connection (int port, string portname) const Connection::PortList& Connection::port_connections (int port) const { - LockMonitor lm (port_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (port_lock); return _ports[port]; } @@ -102,7 +101,7 @@ void Connection::add_port () { { - LockMonitor lm (port_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (port_lock); _ports.push_back (PortList()); } ConfigurationChanged(); /* EMIT SIGNAL */ @@ -114,7 +113,7 @@ Connection::remove_port (int which_port) bool changed = false; { - LockMonitor lm (port_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (port_lock); vector::iterator i; int n; @@ -135,7 +134,7 @@ void Connection::clear () { { - LockMonitor lm (port_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (port_lock); _ports.clear (); } diff --git a/libs/ardour/control_protocol_manager.cc b/libs/ardour/control_protocol_manager.cc index ca1eefc3fe..57a89cc2d9 100644 --- a/libs/ardour/control_protocol_manager.cc +++ b/libs/ardour/control_protocol_manager.cc @@ -13,7 +13,6 @@ using namespace ARDOUR; -using namespace PBD; using namespace std; #include "i18n.h" @@ -32,7 +31,7 @@ ControlProtocolManager::ControlProtocolManager () ControlProtocolManager::~ControlProtocolManager() { - LockMonitor lm (protocols_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (protocols_lock); for (list::iterator i = control_protocols.begin(); i != control_protocols.end(); ++i) { delete (*i); @@ -62,7 +61,7 @@ ControlProtocolManager::drop_session () _session = 0; { - LockMonitor lm (protocols_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (protocols_lock); for (list::iterator p = control_protocols.begin(); p != control_protocols.end(); ++p) { delete *p; } @@ -89,7 +88,7 @@ ControlProtocolManager::instantiate (ControlProtocolInfo& cpi) return 0; } - LockMonitor lm (protocols_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (protocols_lock); control_protocols.push_back (cpi.protocol); return cpi.protocol; @@ -113,7 +112,7 @@ ControlProtocolManager::teardown (ControlProtocolInfo& cpi) cpi.descriptor->destroy (cpi.descriptor, cpi.protocol); { - LockMonitor lm (protocols_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (protocols_lock); list::iterator p = find (control_protocols.begin(), control_protocols.end(), cpi.protocol); if (p != control_protocols.end()) { control_protocols.erase (p); @@ -281,7 +280,7 @@ XMLNode& ControlProtocolManager::get_state (void) { XMLNode* root = new XMLNode (state_node_name); - LockMonitor lm (protocols_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (protocols_lock); for (list::iterator i = control_protocol_info.begin(); i != control_protocol_info.end(); ++i) { XMLNode* child = new XMLNode (X_("Protocol")); diff --git a/libs/ardour/coreaudio_source.cc b/libs/ardour/coreaudio_source.cc index d81630d6b7..67aaabfb88 100644 --- a/libs/ardour/coreaudio_source.cc +++ b/libs/ardour/coreaudio_source.cc @@ -66,29 +66,34 @@ CoreAudioSource::init (const string& idstr, bool build_peak) } /* note that we temporarily truncated _id at the colon */ - FSRef ref; - err = FSPathMakeRef ((UInt8*)file.c_str(), &ref, 0); + FSRef fsr; + err = FSPathMakeRef ((UInt8*)file.c_str(), &fsr, 0); if (err != noErr) { + cerr << "FSPathMakeRef " << err << endl; throw failed_constructor(); } - err = ExtAudioFileOpen (&ref, &af); + err = ExtAudioFileOpen (&fsr, &af); if (err != noErr) { + cerr << "ExtAudioFileOpen " << err << endl; ExtAudioFileDispose (af); throw failed_constructor(); } AudioStreamBasicDescription file_asbd; - memset(&file_asbd, 0, sizeof(file_asbd)); - size_t asbd_size = sizeof(file_asbd); + memset(&file_asbd, 0, sizeof(AudioStreamBasicDescription)); + size_t asbd_size = sizeof(AudioStreamBasicDescription); err = ExtAudioFileGetProperty(af, kExtAudioFileProperty_FileDataFormat, &asbd_size, &file_asbd); if (err != noErr) { + cerr << "ExtAudioFileGetProperty1 " << err << endl; ExtAudioFileDispose (af); throw failed_constructor(); } n_channels = file_asbd.mChannelsPerFrame; + cerr << "number of channels: " << n_channels << endl; + if (channel >= n_channels) { error << string_compose(_("CoreAudioSource: file only contains %1 channels; %2 is invalid as a channel number"), n_channels, channel) << endmsg; ExtAudioFileDispose (af); @@ -96,17 +101,36 @@ CoreAudioSource::init (const string& idstr, bool build_peak) } int64_t ca_frames; - size_t prop_size = sizeof(ca_frames); + size_t prop_size = sizeof(int64_t); err = ExtAudioFileGetProperty(af, kExtAudioFileProperty_FileLengthFrames, &prop_size, &ca_frames); if (err != noErr) { + cerr << "ExtAudioFileGetProperty2 " << err << endl; ExtAudioFileDispose (af); throw failed_constructor(); } - _length = ca_frames; + _length = ca_frames; _path = file; + AudioStreamBasicDescription client_asbd; + memset(&client_asbd, 0, sizeof(AudioStreamBasicDescription)); + client_asbd.mSampleRate = file_asbd.mSampleRate; + client_asbd.mFormatID = kAudioFormatLinearPCM; + client_asbd.mFormatFlags = kLinearPCMFormatFlagIsFloat; + client_asbd.mBytesPerPacket = file_asbd.mChannelsPerFrame * 4; + client_asbd.mFramesPerPacket = 1; + client_asbd.mBytesPerFrame = client_asbd.mBytesPerPacket; + client_asbd.mChannelsPerFrame = file_asbd.mChannelsPerFrame; + client_asbd.mBitsPerChannel = 32; + + err = ExtAudioFileSetProperty (af, kExtAudioFileProperty_ClientDataFormat, asbd_size, &client_asbd); + if (err != noErr) { + cerr << "ExtAudioFileSetProperty3 " << err << endl; + ExtAudioFileDispose (af); + throw failed_constructor (); + } + if (build_peak) { if (initialize_peakfile (false, file)) { error << "initialize peakfile failed" << endmsg; @@ -114,24 +138,6 @@ CoreAudioSource::init (const string& idstr, bool build_peak) throw failed_constructor (); } } - - AudioStreamBasicDescription client_asbd; - memset(&client_asbd, 0, sizeof(client_asbd)); - client_asbd.mFormatID = kAudioFormatLinearPCM; - client_asbd.mFormatFlags = kLinearPCMFormatFlagIsFloat; - client_asbd.mSampleRate = file_asbd.mSampleRate; - - err = AudioFormatGetProperty(kAudioFormatProperty_FormatInfo, 0, NULL, &asbd_size, &client_asbd); - if (err != noErr) { - ExtAudioFileDispose (af); - throw failed_constructor (); - } - - err = ExtAudioFileSetProperty (af, kExtAudioFileProperty_ClientDataFormat, asbd_size, &client_asbd); - if (err != noErr) { - ExtAudioFileDispose (af); - throw failed_constructor (); - } } CoreAudioSource::~CoreAudioSource () @@ -173,7 +179,7 @@ CoreAudioSource::read (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, ch uint32_t real_cnt = cnt * n_channels; { - LockMonitor lm (_tmpbuf_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (_tmpbuf_lock); if (tmpbufsize < real_cnt) { diff --git a/libs/ardour/curve.cc b/libs/ardour/curve.cc index 613222020c..a515c3a39a 100644 --- a/libs/ardour/curve.cc +++ b/libs/ardour/curve.cc @@ -28,7 +28,7 @@ #include #include -#include +#include #include #include "ardour/curve.h" @@ -37,7 +37,6 @@ using namespace std; using namespace ARDOUR; -using namespace PBD; using namespace sigc; Curve::Curve (double minv, double maxv, double canv, bool nostate) @@ -204,7 +203,7 @@ Curve::solve () bool Curve::rt_safe_get_vector (double x0, double x1, float *vec, int32_t veclen) { - TentativeLockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock, Glib::TRY_LOCK); if (!lm.locked()) { return false; @@ -217,7 +216,7 @@ Curve::rt_safe_get_vector (double x0, double x1, float *vec, int32_t veclen) void Curve::get_vector (double x0, double x1, float *vec, int32_t veclen) { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); _get_vector (x0, x1, vec, veclen); } diff --git a/libs/ardour/destructive_filesource.cc b/libs/ardour/destructive_filesource.cc index eaa1242f8c..9a4c2425e9 100644 --- a/libs/ardour/destructive_filesource.cc +++ b/libs/ardour/destructive_filesource.cc @@ -268,7 +268,7 @@ jack_nframes_t DestructiveFileSource::write (Sample* data, jack_nframes_t cnt, char * workbuf) { { - LockMonitor lm (_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (_lock); jack_nframes_t old_file_pos; diff --git a/libs/ardour/diskstream.cc b/libs/ardour/diskstream.cc index 4fb13210fa..90e8387f3f 100644 --- a/libs/ardour/diskstream.cc +++ b/libs/ardour/diskstream.cc @@ -33,7 +33,7 @@ #include #include -#include +#include #include #include @@ -139,7 +139,7 @@ DiskStream::init (Flag f) first_input_change = true; _playlist = 0; i_am_the_modifier = 0; - atomic_set (&_record_enabled, 0); + g_atomic_int_set (&_record_enabled, 0); was_recording = false; capture_start_frame = 0; capture_captured = 0; @@ -213,7 +213,7 @@ DiskStream::destroy_channel (ChannelInfo &chan) DiskStream::~DiskStream () { - LockMonitor lm (state_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (state_lock); if (_playlist) { _playlist->unref (); @@ -229,7 +229,7 @@ DiskStream::~DiskStream () void DiskStream::handle_input_change (IOChange change, void *src) { - LockMonitor lm (state_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (state_lock); if (!(input_change_pending & change)) { input_change_pending = IOChange (input_change_pending|change); @@ -241,7 +241,7 @@ void DiskStream::non_realtime_input_change () { { - LockMonitor lm (state_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (state_lock); if (input_change_pending == NoChange) { return; @@ -349,7 +349,7 @@ int DiskStream::use_playlist (AudioPlaylist* playlist) { { - LockMonitor lm (state_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (state_lock); if (playlist == _playlist) { return 0; @@ -565,7 +565,7 @@ DiskStream::non_realtime_set_speed () { if (_buffer_reallocation_required) { - LockMonitor lm (state_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (state_lock); allocate_temporary_buffers (); _buffer_reallocation_required = false; @@ -753,7 +753,8 @@ DiskStream::process (jack_nframes_t transport_frame, jack_nframes_t nframes, jac returns a non-zero value, in which case, ::commit should not be called. */ - if (pthread_mutex_trylock (state_lock.mutex())) { + // If we can't take the state lock return. + if (!state_lock.trylock()) { return 1; } @@ -1002,7 +1003,7 @@ DiskStream::process (jack_nframes_t transport_frame, jack_nframes_t nframes, jac be called. unlock the state lock. */ - pthread_mutex_unlock (state_lock.mutex()); + state_lock.unlock(); } return ret; @@ -1011,7 +1012,7 @@ DiskStream::process (jack_nframes_t transport_frame, jack_nframes_t nframes, jac void DiskStream::recover () { - pthread_mutex_unlock (state_lock.mutex()); + state_lock.unlock(); _processed = false; } @@ -1047,7 +1048,7 @@ DiskStream::commit (jack_nframes_t nframes) || channels[0].capture_buf->read_space() >= disk_io_chunk_frames; } - pthread_mutex_unlock (state_lock.mutex()); + state_lock.unlock(); _processed = false; @@ -1140,7 +1141,7 @@ DiskStream::overwrite_existing_buffers () int DiskStream::seek (jack_nframes_t frame, bool complete_refill) { - LockMonitor lm (state_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (state_lock); uint32_t n; int ret; ChannelList::iterator chan; @@ -1702,7 +1703,7 @@ DiskStream::transport_stopped (struct tm& when, time_t twhen, bool abort_capture } /* XXX is there anything we can do if err != 0 ? */ - LockMonitor lm (capture_info_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (capture_info_lock); if (capture_info.empty()) { return; @@ -1925,7 +1926,7 @@ DiskStream::set_record_enabled (bool yn, void* src) if (record_enabled() != yn) { if (yn) { - atomic_set (&_record_enabled, 1); + g_atomic_int_set (&_record_enabled, 1); capturing_sources.clear (); if (Config->get_use_hardware_monitoring()) { for (ChannelList::iterator chan = channels.begin(); chan != channels.end(); ++chan) { @@ -1941,7 +1942,7 @@ DiskStream::set_record_enabled (bool yn, void* src) } } else { - atomic_set (&_record_enabled, 0); + g_atomic_int_set (&_record_enabled, 0); if (Config->get_use_hardware_monitoring()) { for (ChannelList::iterator chan = channels.begin(); chan != channels.end(); ++chan) { if ((*chan).source) { @@ -2415,7 +2416,7 @@ DiskStream::set_loop (Location *location) jack_nframes_t DiskStream::get_capture_start_frame (uint32_t n) { - LockMonitor lm (capture_info_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (capture_info_lock); if (capture_info.size() > n) { return capture_info[n]->start; @@ -2428,7 +2429,7 @@ DiskStream::get_capture_start_frame (uint32_t n) jack_nframes_t DiskStream::get_captured_frames (uint32_t n) { - LockMonitor lm (capture_info_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (capture_info_lock); if (capture_info.size() > n) { return capture_info[n]->frames; diff --git a/libs/ardour/filesource.cc b/libs/ardour/filesource.cc index 568ce46bd1..63a9a3d014 100644 --- a/libs/ardour/filesource.cc +++ b/libs/ardour/filesource.cc @@ -53,10 +53,11 @@ #include #include /* for rename(2) */ +#include + #include -#include -#include -#include + +#include #include #include @@ -351,7 +352,7 @@ FileSource::set_allow_remove_if_empty (bool yn) int FileSource::set_name (string newname, bool destructive) { - LockMonitor lm (_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (_lock); string oldpath = _path; string newpath = Session::change_audio_path_by_name (oldpath, _name, newname, destructive); @@ -365,7 +366,7 @@ FileSource::set_name (string newname, bool destructive) return -1; } - _name = basename (newpath); + _name = Glib::path_get_basename (newpath); _path = newpath; return rename_peakfile (peak_path (_path)); @@ -680,7 +681,7 @@ FileSource::compute_header_size () int FileSource::update_header (jack_nframes_t when, struct tm& now, time_t tnow) { - LockMonitor lm (_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (_lock); if (is_bwf) { /* random code is 9 digits */ @@ -1009,7 +1010,7 @@ FileSource::mark_for_remove () jack_nframes_t FileSource::read (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const { - LockMonitor lm (_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (_lock); return read_unlocked (dst, start, cnt, workbuf); } @@ -1055,7 +1056,7 @@ jack_nframes_t FileSource::write (Sample *data, jack_nframes_t cnt, char * workbuf) { { - LockMonitor lm (_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (_lock); jack_nframes_t oldlen; int32_t frame_pos = _length; @@ -1287,7 +1288,7 @@ FileSource::is_empty (string path) void FileSource::mark_streaming_write_completed () { - LockMonitor lm (_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (_lock); next_peak_clear_should_notify = true; @@ -1313,13 +1314,15 @@ FileSource::move_to_trash (const string trash_dir_name) on whichever filesystem it was already on. */ - newpath = PBD::dirname (_path); - newpath = PBD::dirname (newpath); + // XXX Portability + + newpath = Glib::path_get_dirname (_path); + newpath = Glib::path_get_dirname (newpath); newpath += '/'; newpath += trash_dir_name; newpath += '/'; - newpath += PBD::basename (_path); + newpath += Glib::path_get_basename (_path); if (access (newpath.c_str(), F_OK) == 0) { diff --git a/libs/ardour/gdither.cc b/libs/ardour/gdither.cc index 3cdd7ee89e..ec6bfaa2ea 100644 --- a/libs/ardour/gdither.cc +++ b/libs/ardour/gdither.cc @@ -175,7 +175,7 @@ inline static void gdither_innner_loop(const GDitherType dt, const int clamp_l) { uint32_t pos, i; - u_int8_t *o8 = (u_int8_t*) y; + uint8_t *o8 = (uint8_t*) y; int16_t *o16 = (int16_t*) y; int32_t *o32 = (int32_t*) y; float tmp, r, ideal; diff --git a/libs/ardour/globals.cc b/libs/ardour/globals.cc index 23e93ee2a9..762ee101f8 100644 --- a/libs/ardour/globals.cc +++ b/libs/ardour/globals.cc @@ -47,7 +47,10 @@ #include #include #include + +#ifdef HAVE_LIBLO #include +#endif #include @@ -59,7 +62,10 @@ ARDOUR::Configuration* ARDOUR::Config = 0; ARDOUR::AudioLibrary* ARDOUR::Library = 0; + +#ifdef HAVE_LIBLO ARDOUR::OSC* ARDOUR::osc = 0; +#endif using namespace ARDOUR; using namespace std; @@ -74,6 +80,7 @@ Change ARDOUR::PositionChanged = ARDOUR::new_change (); Change ARDOUR::NameChanged = ARDOUR::new_change (); Change ARDOUR::BoundsChanged = Change (0); // see init(), below +#ifdef HAVE_LIBLO static int setup_osc () { @@ -89,6 +96,7 @@ setup_osc () return 0; } } +#endif static int setup_midi () @@ -197,10 +205,12 @@ ARDOUR::init (AudioEngine& engine, bool use_vst, bool try_optimization, void (*s if (setup_midi ()) { return -1; } - + +#ifdef HAVE_LIBLO if (setup_osc ()) { return -1; } +#endif #ifdef VST_SUPPORT if (Config->get_use_vst() && fst_init (sighandler)) { diff --git a/libs/ardour/import.cc b/libs/ardour/import.cc index 69d5ee7b11..c13816e648 100644 --- a/libs/ardour/import.cc +++ b/libs/ardour/import.cc @@ -30,7 +30,10 @@ #include #include +#include + #include + #include #include #include @@ -212,7 +215,7 @@ Session::import_audiofile (import_status& status) sources.push_back(newfiles[n]); } - AudioRegion *r = new AudioRegion (sources, 0, newfiles[0]->length(), region_name_from_path (PBD::basename(basepath)), + AudioRegion *r = new AudioRegion (sources, 0, newfiles[0]->length(), region_name_from_path (Glib::path_get_basename (basepath)), 0, AudioRegion::Flag (AudioRegion::DefaultFlags | AudioRegion::WholeFile)); status.new_regions.push_back (r); @@ -228,7 +231,7 @@ Session::import_audiofile (import_status& status) did not bother to create whole-file AudioRegions for them. Do it now. */ - AudioRegion *r = new AudioRegion (*newfiles[n], 0, newfiles[n]->length(), region_name_from_path (PBD::basename (newfiles[n]->name())), + AudioRegion *r = new AudioRegion (*newfiles[n], 0, newfiles[n]->length(), region_name_from_path (Glib::path_get_basename (newfiles[n]->name())), 0, AudioRegion::Flag (AudioRegion::DefaultFlags | AudioRegion::WholeFile | AudioRegion::Import)); status.new_regions.push_back (r); @@ -285,7 +288,7 @@ Session::import_audiofile (import_status& status) string Session::build_tmp_convert_name(string infile) { - string tmp_name(_path + "/." + PBD::basename (infile.c_str()) + "XXXXXX"); + string tmp_name(_path + "/." + Glib::path_get_basename (infile.c_str()) + "XXXXXX"); char* tmp = new char[tmp_name.length() + 1]; tmp_name.copy(tmp, string::npos); tmp[tmp_name.length()] = 0; diff --git a/libs/ardour/insert.cc b/libs/ardour/insert.cc index 2c74bdc1c0..c3c3462016 100644 --- a/libs/ardour/insert.cc +++ b/libs/ardour/insert.cc @@ -76,7 +76,7 @@ PluginInsert::PluginInsert (Session& s, Plugin& plug, Placement placement) save_state (_("initial state")); { - LockMonitor em (_session.engine().process_lock(), __LINE__, __FILE__); + Glib::Mutex::Lock em (_session.engine().process_lock()); IO::MoreOutputs (output_streams ()); } @@ -97,7 +97,7 @@ PluginInsert::PluginInsert (Session& s, const XMLNode& node) _plugins[0]->ParameterChanged.connect (mem_fun (*this, &PluginInsert::parameter_changed)); { - LockMonitor em (_session.engine().process_lock(), __LINE__, __FILE__); + Glib::Mutex::Lock em (_session.engine().process_lock()); IO::MoreOutputs (output_streams()); } } @@ -410,7 +410,7 @@ PluginInsert::automation_run (vector& bufs, uint32_t nbufs, jack_nfram jack_nframes_t now = _session.transport_frame (); jack_nframes_t end = now + nframes; - TentativeLockMonitor lm (_automation_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (_automation_lock, Glib::TRY_LOCK); if (!lm.locked()) { connect_and_run (bufs, nbufs, nframes, offset, false); diff --git a/libs/ardour/io.cc b/libs/ardour/io.cc index b6ea1eee6e..fa30463bd4 100644 --- a/libs/ardour/io.cc +++ b/libs/ardour/io.cc @@ -25,7 +25,8 @@ #include -#include +#include + #include #include @@ -70,6 +71,8 @@ sigc::signal IO::PannersLegal; sigc::signal IO::MoreOutputs; sigc::signal IO::PortsCreated; +Glib::StaticMutex IO::m_meter_signal_lock = GLIBMM_STATIC_MUTEX_INIT; + /* this is a default mapper of MIDI control values to a gain coefficient. others can be imagined. see IO::set_midi_to_gain_function(). */ @@ -126,13 +129,20 @@ IO::IO (Session& s, string name, _gain_automation_state = Off; _gain_automation_style = Absolute; - - Meter.connect (mem_fun (*this, &IO::meter)); + + { + // IO::Meter is emitted from another thread so the + // Meter signal must be protected. + Glib::Mutex::Lock guard (m_meter_signal_lock); + m_meter_connection = Meter.connect (mem_fun (*this, &IO::meter)); + } } IO::~IO () { - LockMonitor lm (io_lock, __LINE__, __FILE__); + + Glib::Mutex::Lock guard (m_meter_signal_lock); + Glib::Mutex::Lock lm (io_lock); vector::iterator i; for (i = _inputs.begin(); i != _inputs.end(); ++i) { @@ -142,6 +152,8 @@ IO::~IO () for (i = _outputs.begin(); i != _outputs.end(); ++i) { _session.engine().unregister_port (*i); } + + m_meter_connection.disconnect(); } void @@ -380,7 +392,7 @@ IO::deliver_output (vector& bufs, uint32_t nbufs, jack_nframes_t nfram gain_t pangain = _gain; { - TentativeLockMonitor dm (declick_lock, __LINE__, __FILE__); + Glib::Mutex::Lock dm (declick_lock, Glib::TRY_LOCK); if (dm.locked()) { dg = _desired_gain; @@ -427,7 +439,7 @@ IO::deliver_output_no_pan (vector& bufs, uint32_t nbufs, jack_nframes_ } else { - TentativeLockMonitor dm (declick_lock, __LINE__, __FILE__); + Glib::Mutex::Lock dm (declick_lock, Glib::TRY_LOCK); if (dm.locked()) { dg = _desired_gain; @@ -568,10 +580,10 @@ IO::disconnect_input (Port* our_port, string other_port, void* src) } { - LockMonitor em (_session.engine().process_lock(), __LINE__, __FILE__); + Glib::Mutex::Lock em (_session.engine().process_lock()); { - LockMonitor lm (io_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (io_lock); /* check that our_port is really one of ours */ @@ -604,10 +616,10 @@ IO::connect_input (Port* our_port, string other_port, void* src) } { - LockMonitor em(_session.engine().process_lock(), __LINE__, __FILE__); + Glib::Mutex::Lock em(_session.engine().process_lock()); { - LockMonitor lm (io_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (io_lock); /* check that our_port is really one of ours */ @@ -638,10 +650,10 @@ IO::disconnect_output (Port* our_port, string other_port, void* src) } { - LockMonitor em(_session.engine().process_lock(), __LINE__, __FILE__); + Glib::Mutex::Lock em(_session.engine().process_lock()); { - LockMonitor lm (io_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (io_lock); if (find (_outputs.begin(), _outputs.end(), our_port) == _outputs.end()) { return -1; @@ -671,10 +683,10 @@ IO::connect_output (Port* our_port, string other_port, void* src) } { - LockMonitor em(_session.engine().process_lock(), __LINE__, __FILE__); + Glib::Mutex::Lock em(_session.engine().process_lock()); { - LockMonitor lm (io_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (io_lock); /* check that our_port is really one of ours */ @@ -730,10 +742,10 @@ IO::remove_output_port (Port* port, void* src) IOChange change (NoChange); { - LockMonitor em(_session.engine().process_lock(), __LINE__, __FILE__); + Glib::Mutex::Lock em(_session.engine().process_lock()); { - LockMonitor lm (io_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (io_lock); if (_noutputs - 1 == (uint32_t) _output_minimum) { /* sorry, you can't do this */ @@ -779,10 +791,10 @@ IO::add_output_port (string destination, void* src) char buf[64]; { - LockMonitor em(_session.engine().process_lock(), __LINE__, __FILE__); + Glib::Mutex::Lock em(_session.engine().process_lock()); { - LockMonitor lm (io_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (io_lock); if (_output_maximum >= 0 && (int) _noutputs == _output_maximum) { return -1; @@ -830,10 +842,10 @@ IO::remove_input_port (Port* port, void* src) IOChange change (NoChange); { - LockMonitor em(_session.engine().process_lock(), __LINE__, __FILE__); + Glib::Mutex::Lock em(_session.engine().process_lock()); { - LockMonitor lm (io_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (io_lock); if (((int)_ninputs - 1) < _input_minimum) { /* sorry, you can't do this */ @@ -880,10 +892,10 @@ IO::add_input_port (string source, void* src) char buf[64]; { - LockMonitor em (_session.engine().process_lock(), __LINE__, __FILE__); + Glib::Mutex::Lock em (_session.engine().process_lock()); { - LockMonitor lm (io_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (io_lock); if (_input_maximum >= 0 && (int) _ninputs == _input_maximum) { return -1; @@ -931,10 +943,10 @@ int IO::disconnect_inputs (void* src) { { - LockMonitor em (_session.engine().process_lock(), __LINE__, __FILE__); + Glib::Mutex::Lock em (_session.engine().process_lock()); { - LockMonitor lm (io_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (io_lock); for (vector::iterator i = _inputs.begin(); i != _inputs.end(); ++i) { _session.engine().disconnect (*i); @@ -951,10 +963,10 @@ int IO::disconnect_outputs (void* src) { { - LockMonitor em (_session.engine().process_lock(), __LINE__, __FILE__); + Glib::Mutex::Lock em (_session.engine().process_lock()); { - LockMonitor lm (io_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (io_lock); for (vector::iterator i = _outputs.begin(); i != _outputs.end(); ++i) { _session.engine().disconnect (*i); @@ -1063,8 +1075,8 @@ IO::ensure_io (uint32_t nin, uint32_t nout, bool clear, void* src) } { - LockMonitor em (_session.engine().process_lock(), __LINE__, __FILE__); - LockMonitor lm (io_lock, __LINE__, __FILE__); + Glib::Mutex::Lock em (_session.engine().process_lock()); + Glib::Mutex::Lock lm (io_lock); Port* port; @@ -1212,8 +1224,8 @@ IO::ensure_inputs (uint32_t n, bool clear, bool lockit, void* src) } if (lockit) { - LockMonitor em (_session.engine().process_lock(), __LINE__, __FILE__); - LockMonitor im (io_lock, __LINE__, __FILE__); + Glib::Mutex::Lock em (_session.engine().process_lock()); + Glib::Mutex::Lock im (io_lock); changed = ensure_inputs_locked (n, clear, src); } else { changed = ensure_inputs_locked (n, clear, src); @@ -1314,8 +1326,8 @@ IO::ensure_outputs (uint32_t n, bool clear, bool lockit, void* src) /* XXX caller should hold io_lock, but generally doesn't */ if (lockit) { - LockMonitor em (_session.engine().process_lock(), __LINE__, __FILE__); - LockMonitor im (io_lock, __LINE__, __FILE__); + Glib::Mutex::Lock em (_session.engine().process_lock()); + Glib::Mutex::Lock im (io_lock); changed = ensure_outputs_locked (n, clear, src); } else { changed = ensure_outputs_locked (n, clear, src); @@ -1389,7 +1401,7 @@ IO::state (bool full_state) bool need_ins = true; bool need_outs = true; LocaleGuard lg (X_("POSIX")); - LockMonitor lm (io_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (io_lock); node->add_property("name", _name); snprintf (buf, sizeof(buf), "%" PRIu64, id()); @@ -2058,7 +2070,7 @@ IO::set_output_maximum (int n) void IO::set_port_latency (jack_nframes_t nframes) { - LockMonitor lm (io_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (io_lock); for (vector::iterator i = _outputs.begin(); i != _outputs.end(); ++i) { (*i)->set_latency (nframes); @@ -2109,8 +2121,8 @@ IO::use_input_connection (Connection& c, void* src) uint32_t limit; { - LockMonitor lm (_session.engine().process_lock(), __LINE__, __FILE__); - LockMonitor lm2 (io_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (_session.engine().process_lock()); + Glib::Mutex::Lock lm2 (io_lock); limit = c.nports(); @@ -2187,8 +2199,8 @@ IO::use_output_connection (Connection& c, void* src) uint32_t limit; { - LockMonitor lm (_session.engine().process_lock(), __LINE__, __FILE__); - LockMonitor lm2 (io_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (_session.engine().process_lock()); + Glib::Mutex::Lock lm2 (io_lock); limit = c.nports(); @@ -2437,10 +2449,26 @@ IO::send_state_changed () return; } +/** + Update the peak meters. + + The meter signal lock is taken to prevent modification of the + Meter signal while updating the meters, taking the meter signal + lock prior to taking the io_lock ensures that all IO will remain + valid while metering. +*/ +void +IO::update_meters() +{ + Glib::Mutex::Lock guard (m_meter_signal_lock); + + Meter(); +} + void IO::meter () { - LockMonitor lm (io_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (io_lock); // READER: meter thread. uint32_t limit = max (_ninputs, _noutputs); for (uint32_t n = 0; n < limit; ++n) { @@ -2602,7 +2630,7 @@ IO::load_automation (const string& path) void IO::clear_automation () { - LockMonitor lm (automation_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (automation_lock); _gain_automation_curve.clear (); _panner->clear_automation (); } @@ -2613,7 +2641,7 @@ IO::set_gain_automation_state (AutoState state) bool changed = false; { - LockMonitor lm (automation_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (automation_lock); if (state != _gain_automation_curve.automation_state()) { changed = true; @@ -2638,7 +2666,7 @@ IO::set_gain_automation_style (AutoStyle style) bool changed = false; { - LockMonitor lm (automation_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (automation_lock); if (style != _gain_automation_curve.automation_style()) { changed = true; @@ -2666,7 +2694,7 @@ IO::set_gain (gain_t val, void *src) if (val>1.99526231f) val=1.99526231f; { - LockMonitor dm (declick_lock, __LINE__, __FILE__); + Glib::Mutex::Lock dm (declick_lock); _desired_gain = val; } diff --git a/libs/ardour/location.cc b/libs/ardour/location.cc index 7d479637e3..28ec42a394 100644 --- a/libs/ardour/location.cc +++ b/libs/ardour/location.cc @@ -371,7 +371,7 @@ Locations::set_current (Location *loc, bool want_lock) int ret; if (want_lock) { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); ret = set_current_unlocked (loc); } else { ret = set_current_unlocked (loc); @@ -399,7 +399,7 @@ void Locations::clear () { { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); LocationList::iterator tmp; for (LocationList::iterator i = locations.begin(); i != locations.end(); ) { tmp = i; @@ -424,7 +424,7 @@ void Locations::clear_markers () { { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); LocationList::iterator tmp; for (LocationList::iterator i = locations.begin(); i != locations.end(); ) { @@ -448,7 +448,7 @@ void Locations::clear_ranges () { { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); LocationList::iterator tmp; for (LocationList::iterator i = locations.begin(); i != locations.end(); ) { @@ -477,7 +477,7 @@ void Locations::add (Location *loc, bool make_current) { { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); locations.push_back (loc); if (make_current) { @@ -507,7 +507,7 @@ Locations::remove (Location *loc) } { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); for (i = locations.begin(); i != locations.end(); ++i) { if ((*i) == loc) { @@ -547,7 +547,7 @@ Locations::get_state () { XMLNode *node = new XMLNode ("Locations"); LocationList::iterator iter; - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); for (iter = locations.begin(); iter != locations.end(); ++iter) { node->add_child_nocopy ((*iter)->get_state ()); @@ -570,7 +570,7 @@ Locations::set_state (const XMLNode& node) nlist = node.children(); { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); for (niter = nlist.begin(); niter != nlist.end(); ++niter) { Location *loc = new Location; @@ -614,7 +614,7 @@ Locations::first_location_before (jack_nframes_t frame) LocationList locs; { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); locs = locations; } @@ -638,7 +638,7 @@ Locations::first_location_after (jack_nframes_t frame) LocationList locs; { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); locs = locations; } @@ -662,7 +662,7 @@ Locations::first_mark_before (jack_nframes_t frame) LocationList locs; { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); locs = locations; } @@ -699,7 +699,7 @@ Locations::first_mark_after (jack_nframes_t frame) LocationList locs; { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); locs = locations; } @@ -792,7 +792,7 @@ Change Locations::restore_state (StateManager::State& state) { { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); State* lstate = dynamic_cast (&state); locations = lstate->locations; @@ -817,7 +817,7 @@ uint32_t Locations::num_range_markers () const { uint32_t cnt = 0; - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); for (LocationList::const_iterator i = locations.begin(); i != locations.end(); ++i) { if ((*i)->is_range_marker()) { ++cnt; diff --git a/libs/ardour/panner.cc b/libs/ardour/panner.cc index 6b0013cada..bc7b472732 100644 --- a/libs/ardour/panner.cc +++ b/libs/ardour/panner.cc @@ -28,9 +28,10 @@ #include #include +#include + #include #include -#include #include #include @@ -1369,7 +1370,7 @@ Panner::state (bool full) if (full) { if (save () == 0) { - root->add_property (X_("automation"), PBD::basename (automation_path)); + root->add_property (X_("automation"), Glib::path_get_basename (automation_path)); } } diff --git a/libs/ardour/playlist.cc b/libs/ardour/playlist.cc index 73be1da86d..1bc6ccac6d 100644 --- a/libs/ardour/playlist.cc +++ b/libs/ardour/playlist.cc @@ -225,8 +225,8 @@ Playlist::copy_regions (RegionList& newlist) const void Playlist::init (bool hide) { - atomic_set (&block_notifications, 0); - atomic_set (&ignore_state_changes, 0); + g_atomic_int_set (&block_notifications, 0); + g_atomic_int_set (&ignore_state_changes, 0); pending_modified = false; pending_length = false; _refcnt = 0; @@ -292,13 +292,13 @@ void Playlist::freeze () { delay_notifications (); - atomic_inc (&ignore_state_changes); + g_atomic_int_inc (&ignore_state_changes); } void Playlist::thaw () { - atomic_dec (&ignore_state_changes); + g_atomic_int_dec_and_test (&ignore_state_changes); release_notifications (); } @@ -306,14 +306,14 @@ Playlist::thaw () void Playlist::delay_notifications () { - atomic_inc (&block_notifications); + g_atomic_int_inc (&block_notifications); freeze_length = _get_maximum_extent(); } void Playlist::release_notifications () { - if (atomic_dec_and_test(&block_notifications)) { + if (g_atomic_int_dec_and_test (&block_notifications)) { flush_notifications (); } } diff --git a/libs/ardour/redirect.cc b/libs/ardour/redirect.cc index 403e6edddd..746d2790e2 100644 --- a/libs/ardour/redirect.cc +++ b/libs/ardour/redirect.cc @@ -126,7 +126,7 @@ Redirect::load_automation (string path) return 1; } - LockMonitor lm (_automation_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (_automation_lock); set tosave; parameter_automation.clear (); @@ -159,7 +159,7 @@ Redirect::load_automation (string path) int Redirect::save_automation (string path) { - LockMonitor lm (_automation_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (_automation_lock); string fullpath; if (parameter_automation.empty()) { @@ -268,7 +268,7 @@ Redirect::state (bool full_state) void Redirect::what_has_automation (set& s) const { - LockMonitor lm (_automation_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (_automation_lock); map::const_iterator li; for (li = parameter_automation.begin(); li != parameter_automation.end(); ++li) { @@ -279,7 +279,7 @@ Redirect::what_has_automation (set& s) const void Redirect::what_has_visible_automation (set& s) const { - LockMonitor lm (_automation_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (_automation_lock); set::const_iterator li; for (li = visible_parameter_automation.begin(); li != visible_parameter_automation.end(); ++li) { diff --git a/libs/ardour/region.cc b/libs/ardour/region.cc index 91d5704db2..08df23146b 100644 --- a/libs/ardour/region.cc +++ b/libs/ardour/region.cc @@ -26,7 +26,7 @@ #include #include -#include +#include #include #include @@ -178,7 +178,7 @@ Region::restore_and_return_flags (RegionState& state) Change what_changed = Change (0); { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); if (_start != state._start) { what_changed = Change (what_changed|StartChanged); @@ -947,7 +947,7 @@ Region::thaw (const string& why) Change what_changed = Change (0); { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); if (_frozen && --_frozen > 0) { return; @@ -978,7 +978,7 @@ void Region::send_change (Change what_changed) { { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); if (_frozen) { pending_changed = Change (pending_changed|what_changed); return; diff --git a/libs/ardour/route.cc b/libs/ardour/route.cc index 71beb945bf..93fbb85e49 100644 --- a/libs/ardour/route.cc +++ b/libs/ardour/route.cc @@ -235,7 +235,7 @@ Route::process_output_buffers (vector& bufs, uint32_t nbufs, declick = _pending_declick; { - TentativeLockMonitor cm (control_outs_lock, __LINE__, __FILE__); + Glib::Mutex::Lock cm (control_outs_lock, Glib::TRY_LOCK); if (cm.locked()) { co = _control_outs; @@ -245,7 +245,7 @@ Route::process_output_buffers (vector& bufs, uint32_t nbufs, } { - TentativeLockMonitor dm (declick_lock, __LINE__, __FILE__); + Glib::Mutex::Lock dm (declick_lock, Glib::TRY_LOCK); if (dm.locked()) { dmg = desired_mute_gain; @@ -330,7 +330,7 @@ Route::process_output_buffers (vector& bufs, uint32_t nbufs, -------------------------------------------------------------------------------------------------- */ if (with_redirects) { - TentativeRWLockMonitor rm (redirect_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock rm (redirect_lock, Glib::TRY_LOCK); if (rm.locked()) { if (mute_gain > 0 || !_mute_affects_pre_fader) { for (i = _redirects.begin(); i != _redirects.end(); ++i) { @@ -499,7 +499,7 @@ Route::process_output_buffers (vector& bufs, uint32_t nbufs, if (post_fader_work) { - TentativeRWLockMonitor rm (redirect_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock rm (redirect_lock, Glib::TRY_LOCK); if (rm.locked()) { if (mute_gain > 0 || !_mute_affects_post_fader) { for (i = _redirects.begin(); i != _redirects.end(); ++i) { @@ -723,7 +723,7 @@ Route::set_solo (bool yn, void *src) void Route::set_solo_mute (bool yn) { - LockMonitor lm (declick_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (declick_lock); /* Called by Session in response to another Route being soloed. */ @@ -757,7 +757,7 @@ Route::set_mute (bool yn, void *src) _midi_mute_control.send_feedback (_muted); } - LockMonitor lm (declick_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (declick_lock); desired_mute_gain = (yn?0.0f:1.0f); } } @@ -772,7 +772,7 @@ Route::add_redirect (Redirect *redirect, void *src, uint32_t* err_streams) } { - RWLockMonitor lm (redirect_lock, true, __LINE__, __FILE__); + Glib::RWLock::WriterLock lm (redirect_lock); PluginInsert* pi; PortInsert* porti; @@ -845,7 +845,7 @@ Route::add_redirects (const RedirectList& others, void *src, uint32_t* err_strea } { - RWLockMonitor lm (redirect_lock, true, __LINE__, __FILE__); + Glib::RWLock::WriterLock lm (redirect_lock); RedirectList::iterator existing_end = _redirects.end(); --existing_end; @@ -904,7 +904,7 @@ Route::clear_redirects (void *src) } { - RWLockMonitor lm (redirect_lock, true, __LINE__, __FILE__); + Glib::RWLock::WriterLock lm (redirect_lock); for (RedirectList::iterator i = _redirects.begin(); i != _redirects.end(); ++i) { delete *i; @@ -934,7 +934,7 @@ Route::remove_redirect (Redirect *redirect, void *src, uint32_t* err_streams) redirect_max_outs = 0; { - RWLockMonitor lm (redirect_lock, true, __LINE__, __FILE__); + Glib::RWLock::WriterLock lm (redirect_lock); RedirectList::iterator i; bool removed = false; @@ -1013,7 +1013,7 @@ Route::remove_redirect (Redirect *redirect, void *src, uint32_t* err_streams) int Route::reset_plugin_counts (uint32_t* lpc) { - RWLockMonitor lm (redirect_lock, true, __LINE__, __FILE__); + Glib::RWLock::WriterLock lm (redirect_lock); return _reset_plugin_counts (lpc); } @@ -1183,7 +1183,7 @@ Route::copy_redirects (const Route& other, Placement placement, uint32_t* err_st RedirectList to_be_deleted; { - RWLockMonitor lm (redirect_lock, true, __LINE__, __FILE__); + Glib::RWLock::WriterLock lm (redirect_lock); RedirectList::iterator tmp; RedirectList the_copy; @@ -1262,7 +1262,7 @@ Route::copy_redirects (const Route& other, Placement placement, uint32_t* err_st void Route::all_redirects_flip () { - RWLockMonitor lm (redirect_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (redirect_lock); if (_redirects.empty()) { return; @@ -1278,7 +1278,7 @@ Route::all_redirects_flip () void Route::all_redirects_active (bool state) { - RWLockMonitor lm (redirect_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (redirect_lock); if (_redirects.empty()) { return; @@ -1300,7 +1300,7 @@ Route::sort_redirects (uint32_t* err_streams) { { RedirectSorter comparator; - RWLockMonitor lm (redirect_lock, true, __LINE__, __FILE__); + Glib::RWLock::WriterLock lm (redirect_lock); uint32_t old_rmo = redirect_max_outs; /* the sweet power of C++ ... */ @@ -1779,7 +1779,7 @@ Route::silence (jack_nframes_t nframes, jack_nframes_t offset) } { - TentativeRWLockMonitor lm (redirect_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (redirect_lock, Glib::TRY_LOCK); if (lm.locked()) { for (RedirectList::iterator i = _redirects.begin(); i != _redirects.end(); ++i) { @@ -1804,7 +1804,7 @@ Route::silence (jack_nframes_t nframes, jack_nframes_t offset) int Route::set_control_outs (const vector& ports) { - LockMonitor lm (control_outs_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (control_outs_lock); vector::const_iterator i; if (_control_outs) { @@ -2007,7 +2007,7 @@ Route::transport_stopped (bool abort_ignored, bool did_locate, bool can_flush_re jack_nframes_t now = _session.transport_frame(); { - RWLockMonitor lm (redirect_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (redirect_lock); if (!did_locate) { automation_snapshot (now); @@ -2126,7 +2126,7 @@ Route::roll (jack_nframes_t nframes, jack_nframes_t start_frame, jack_nframes_t bool can_record, bool rec_monitors_input) { { - TentativeRWLockMonitor lm(redirect_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (redirect_lock, Glib::TRY_LOCK); if (lm.locked()) { // automation snapshot can also be called from the non-rt context // and it uses the redirect list, so we take the lock out here @@ -2150,7 +2150,7 @@ Route::roll (jack_nframes_t nframes, jack_nframes_t start_frame, jack_nframes_t apply_gain_automation = false; { - TentativeLockMonitor am (automation_lock, __LINE__, __FILE__); + Glib::Mutex::Lock am (automation_lock, Glib::TRY_LOCK); if (am.locked() && _session.transport_rolling()) { @@ -2242,7 +2242,7 @@ Route::send_all_midi_feedback () if (_session.get_midi_feedback()) { { - RWLockMonitor lm (redirect_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (redirect_lock); for (RedirectList::iterator i = _redirects.begin(); i != _redirects.end(); ++i) { (*i)->send_all_midi_feedback (); } @@ -2262,7 +2262,7 @@ Route::write_midi_feedback (MIDI::byte* buf, int32_t& bufsize) buf = _midi_mute_control.write_feedback (buf, bufsize, _muted); { - RWLockMonitor lm (redirect_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (redirect_lock); for (RedirectList::iterator i = _redirects.begin(); i != _redirects.end(); ++i) { buf = (*i)->write_midi_feedback (buf, bufsize); } @@ -2278,7 +2278,7 @@ Route::flush_redirects () this is called from the RT audio thread. */ - RWLockMonitor lm (redirect_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (redirect_lock); for (RedirectList::iterator i = _redirects.begin(); i != _redirects.end(); ++i) { (*i)->deactivate (); diff --git a/libs/ardour/session.cc b/libs/ardour/session.cc index a8ab2204dc..d729b5d7f7 100644 --- a/libs/ardour/session.cc +++ b/libs/ardour/session.cc @@ -32,12 +32,13 @@ #include #include +#include + #include -#include +#include #include #include #include -#include #include #include @@ -64,7 +65,10 @@ #include #include #include + +#ifdef HAVE_LIBLO #include +#endif #include "i18n.h" @@ -550,7 +554,7 @@ Session::set_worst_io_latencies (bool take_lock) } if (take_lock) { - route_lock.read_lock (); + route_lock.reader_lock (); } for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) { @@ -559,7 +563,7 @@ Session::set_worst_io_latencies (bool take_lock) } if (take_lock) { - route_lock.unlock (); + route_lock.reader_unlock (); } } @@ -794,10 +798,12 @@ Session::when_engine_running () _engine.set_session (this); +#ifdef HAVE_LIBLO /* and to OSC */ osc->set_session (*this); - +#endif + _state_of_the_state = Clean; DirtyChanged (); /* EMIT SIGNAL */ @@ -954,7 +960,7 @@ Session::set_auto_input (bool yn) a non-tentative rwlock here, because the action must occur. The rarity and short potential lock duration makes this "OK" */ - RWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock dsm (diskstream_lock); for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { if ((*i)->record_enabled ()) { //cerr << "switching to input = " << !auto_input << __FILE__ << __LINE__ << endl << endl; @@ -972,7 +978,7 @@ void Session::reset_input_monitor_state () { if (transport_rolling()) { - RWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock dsm (diskstream_lock); for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { if ((*i)->record_enabled ()) { //cerr << "switching to input = " << !auto_input << __FILE__ << __LINE__ << endl << endl; @@ -980,7 +986,7 @@ Session::reset_input_monitor_state () } } } else { - RWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock dsm (diskstream_lock); for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { if ((*i)->record_enabled ()) { //cerr << "switching to input = " << !auto_input << __FILE__ << __LINE__ << endl << endl; @@ -1247,8 +1253,8 @@ void Session::enable_record () { /* XXX really atomic compare+swap here */ - if (atomic_read (&_record_status) != Recording) { - atomic_set (&_record_status, Recording); + if (g_atomic_int_get (&_record_status) != Recording) { + g_atomic_int_set (&_record_status, Recording); _last_record_location = _transport_frame; send_mmc_in_another_thread (MIDI::MachineControl::cmdRecordStrobe); @@ -1257,7 +1263,7 @@ Session::enable_record () a non-tentative rwlock here, because the action must occur. The rarity and short potential lock duration makes this "OK" */ - RWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock dsm (diskstream_lock); for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { if ((*i)->record_enabled ()) { @@ -1275,13 +1281,13 @@ Session::disable_record (bool rt_context, bool force) { RecordState rs; - if ((rs = (RecordState) atomic_read (&_record_status)) != Disabled) { + if ((rs = (RecordState) g_atomic_int_get (&_record_status)) != Disabled) { if (!Config->get_latched_record_enable () || force) { - atomic_set (&_record_status, Disabled); + g_atomic_int_set (&_record_status, Disabled); } else { if (rs == Recording) { - atomic_set (&_record_status, Enabled); + g_atomic_int_set (&_record_status, Enabled); } } @@ -1292,7 +1298,7 @@ Session::disable_record (bool rt_context, bool force) a non-tentative rwlock here, because the action must occur. The rarity and short potential lock duration makes this "OK" */ - RWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock dsm (diskstream_lock); for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { if ((*i)->record_enabled ()) { @@ -1312,14 +1318,14 @@ Session::disable_record (bool rt_context, bool force) void Session::step_back_from_record () { - atomic_set (&_record_status, Enabled); + g_atomic_int_set (&_record_status, Enabled); if (Config->get_use_hardware_monitoring()) { /* Even though this can be called from RT context we are using a non-tentative rwlock here, because the action must occur. The rarity and short potential lock duration makes this "OK" */ - RWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock dsm (diskstream_lock); for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { if (auto_input && (*i)->record_enabled ()) { @@ -1333,7 +1339,7 @@ Session::step_back_from_record () void Session::maybe_enable_record () { - atomic_set (&_record_status, Enabled); + g_atomic_int_set (&_record_status, Enabled); /* XXX this save should really happen in another thread. its needed so that pending capture state can be recovered if we crash. @@ -1441,8 +1447,8 @@ Session::set_block_size (jack_nframes_t nframes) */ { - RWLockMonitor lm (route_lock, false, __LINE__, __FILE__); - RWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (route_lock); + Glib::RWLock::ReaderLock dsm (diskstream_lock); vector::iterator i; uint32_t np; @@ -1519,7 +1525,7 @@ Session::set_default_fade (float steepness, float fade_msecs) { // jlc, WTF is this! - RWLockMonitor lm (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (route_lock); AudioRegion::set_default_fade (steepness, fade_frames); } @@ -1670,7 +1676,7 @@ Session::new_audio_track (int input_channels, int output_channels, TrackMode mod /* count existing audio tracks */ { - RWLockMonitor lm (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (route_lock); for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) { if (dynamic_cast(*i) != 0) { if (!(*i)->hidden()) { @@ -1786,7 +1792,7 @@ Session::new_audio_route (int input_channels, int output_channels) /* count existing audio busses */ { - RWLockMonitor lm (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (route_lock); for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) { if (dynamic_cast(*i) == 0) { if (!(*i)->hidden()) { @@ -1869,7 +1875,7 @@ void Session::add_route (Route* route) { { - RWLockMonitor lm (route_lock, true, __LINE__, __FILE__); + Glib::RWLock::WriterLock lm (route_lock); routes.push_front (route); resort_routes(0); } @@ -1900,7 +1906,7 @@ Session::add_diskstream (DiskStream* dstream) dstream->do_refill(0, 0, 0); { - RWLockMonitor lm (diskstream_lock, true, __LINE__, __FILE__); + Glib::RWLock::WriterLock lm (diskstream_lock); diskstreams.push_back (dstream); } @@ -1928,7 +1934,7 @@ void Session::remove_route (Route& route) { { - RWLockMonitor lm (route_lock, true, __LINE__, __FILE__); + Glib::RWLock::WriterLock lm (route_lock); routes.remove (&route); /* deleting the master out seems like a dumb @@ -1956,7 +1962,7 @@ Session::remove_route (Route& route) } { - RWLockMonitor lm (diskstream_lock, true, __LINE__, __FILE__); + Glib::RWLock::WriterLock lm (diskstream_lock); AudioTrack* at; @@ -1992,7 +1998,7 @@ Session::route_solo_changed (void* src, Route* route) return; } - RWLockMonitor lm (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (route_lock); bool is_track; is_track = (dynamic_cast(route) != 0); @@ -2191,14 +2197,14 @@ Session::catch_up_on_solo () basis, but needs the global overview that only the session has. */ - RWLockMonitor lm (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (route_lock); update_route_solo_state(); } Route * Session::route_by_name (string name) { - RWLockMonitor lm (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (route_lock); for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) { if ((*i)->name() == name) { @@ -2212,7 +2218,7 @@ Session::route_by_name (string name) Route * Session::route_by_remote_id (uint32_t id) { - RWLockMonitor lm (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (route_lock); for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) { if ((*i)->remote_control_id() == id) { @@ -2262,7 +2268,7 @@ Session::get_maximum_extent () const DiskStream * Session::diskstream_by_name (string name) { - RWLockMonitor lm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (diskstream_lock); for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { if ((*i)->name() == name) { @@ -2276,7 +2282,7 @@ Session::diskstream_by_name (string name) DiskStream * Session::diskstream_by_id (id_t id) { - RWLockMonitor lm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (diskstream_lock); for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { if ((*i)->id() == id) { @@ -2348,7 +2354,7 @@ Session::region_name (string& result, string base, bool newlevel) const if (base == "") { - LockMonitor lm (region_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (region_lock); snprintf (buf, sizeof (buf), "%d", (int)audio_regions.size() + 1); @@ -2376,7 +2382,7 @@ Session::region_name (string& result, string base, bool newlevel) const bool name_taken = true; { - LockMonitor lm (region_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (region_lock); for (int n = 1; n < 5000; ++n) { @@ -2415,7 +2421,7 @@ Session::add_region (Region* region) bool added = false; { - LockMonitor lm (region_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (region_lock); if ((ar = dynamic_cast (region)) != 0) { @@ -2492,7 +2498,7 @@ Session::remove_region (Region* region) bool removed = false; { - LockMonitor lm (region_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (region_lock); if ((ar = dynamic_cast (region)) != 0) { if ((i = audio_regions.find (region->id())) != audio_regions.end()) { @@ -2523,7 +2529,7 @@ Session::find_whole_file_parent (AudioRegion& child) { AudioRegionList::iterator i; AudioRegion* region; - LockMonitor lm (region_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (region_lock); for (i = audio_regions.begin(); i != audio_regions.end(); ++i) { @@ -2599,7 +2605,7 @@ Session::remove_last_capture () { list r; - RWLockMonitor lm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (diskstream_lock); for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { list& l = (*i)->last_capture_regions(); @@ -2629,7 +2635,7 @@ Session::add_source (Source* source) pair entry; { - LockMonitor lm (source_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (source_lock); entry.first = source->id(); entry.second = source; sources.insert (entry); @@ -2647,7 +2653,7 @@ Session::remove_source (Source* source) SourceList::iterator i; { - LockMonitor lm (source_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (source_lock); if ((i = sources.find (source->id())) != sources.end()) { sources.erase (i); @@ -2669,7 +2675,7 @@ Session::remove_source (Source* source) Source * Session::get_source (ARDOUR::id_t id) { - LockMonitor lm (source_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (source_lock); SourceList::iterator i; Source* source = 0; @@ -2687,8 +2693,8 @@ Session::peak_path_from_audio_path (string audio_path) string res; - res = PBD::dirname (audio_path); - res = PBD::dirname (res); + res = Glib::path_get_dirname (audio_path); + res = Glib::path_get_dirname (res); res += '/'; res += peak_dir_name; res += '/'; @@ -2702,7 +2708,7 @@ string Session::change_audio_path_by_name (string path, string oldname, string newname, bool destructive) { string look_for; - string old_basename = basename_nosuffix (oldname); + string old_basename = PBD::basename_nosuffix (oldname); string new_legalized = legalize_for_path (newname); /* note: we know (or assume) the old path is already valid */ @@ -2915,7 +2921,7 @@ Session::get_playlist (string name) Playlist * Session::playlist_by_name (string name) { - LockMonitor lm (playlist_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (playlist_lock); for (PlaylistList::iterator i = playlists.begin(); i != playlists.end(); ++i) { if ((*i)->name() == name) { return* i; @@ -2937,7 +2943,7 @@ Session::add_playlist (Playlist* playlist) } { - LockMonitor lm (playlist_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (playlist_lock); if (find (playlists.begin(), playlists.end(), playlist) == playlists.end()) { playlists.insert (playlists.begin(), playlist); // playlist->ref(); @@ -2957,7 +2963,7 @@ Session::track_playlist (Playlist* pl, bool inuse) PlaylistList::iterator x; { - LockMonitor lm (playlist_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (playlist_lock); if (!inuse) { //cerr << "shifting playlist to unused: " << pl->name() << endl; @@ -2989,7 +2995,7 @@ Session::remove_playlist (Playlist* playlist) } { - LockMonitor lm (playlist_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (playlist_lock); // cerr << "removing playlist: " << playlist->name() << endl; PlaylistList::iterator i; @@ -3105,7 +3111,7 @@ void Session::set_all_solo (bool yn) { { - RWLockMonitor lm (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (route_lock); for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) { if (!(*i)->hidden()) { @@ -3121,7 +3127,7 @@ void Session::set_all_mute (bool yn) { { - RWLockMonitor lm (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (route_lock); for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) { if (!(*i)->hidden()) { @@ -3136,7 +3142,7 @@ Session::set_all_mute (bool yn) uint32_t Session::n_diskstreams () const { - RWLockMonitor lm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (diskstream_lock); uint32_t n = 0; for (DiskStreamList::const_iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { @@ -3150,7 +3156,7 @@ Session::n_diskstreams () const void Session::foreach_diskstream (void (DiskStream::*func)(void)) { - RWLockMonitor lm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (diskstream_lock); for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { if (!(*i)->hidden()) { ((*i)->*func)(); @@ -3169,8 +3175,8 @@ Session::graph_reordered () return; } - RWLockMonitor lm1 (route_lock, true, __LINE__, __FILE__); - RWLockMonitor lm2 (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::WriterLock lm1 (route_lock); + Glib::RWLock::ReaderLock lm2 (diskstream_lock); resort_routes (0); @@ -3198,7 +3204,7 @@ Session::record_enable_all () void Session::record_enable_change_all (bool yn) { - RWLockMonitor lm1 (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm1 (route_lock); for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) { AudioTrack* at; @@ -3283,7 +3289,7 @@ void Session::add_connection (ARDOUR::Connection* connection) { { - LockMonitor (connection_lock, __LINE__, __FILE__); + Glib::Mutex::Lock guard (connection_lock); _connections.push_back (connection); } @@ -3298,7 +3304,7 @@ Session::remove_connection (ARDOUR::Connection* connection) bool removed = false; { - LockMonitor (connection_lock, __LINE__, __FILE__); + Glib::Mutex::Lock guard (connection_lock); ConnectionList::iterator i = find (_connections.begin(), _connections.end(), connection); if (i != _connections.end()) { @@ -3317,7 +3323,7 @@ Session::remove_connection (ARDOUR::Connection* connection) ARDOUR::Connection * Session::connection_by_name (string name) const { - LockMonitor lm (connection_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (connection_lock); for (ConnectionList::const_iterator i = _connections.begin(); i != _connections.end(); ++i) { if ((*i)->name() == name) { @@ -3334,7 +3340,7 @@ Session::set_edit_mode (EditMode mode) _edit_mode = mode; { - LockMonitor lm (playlist_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (playlist_lock); for (PlaylistList::iterator i = playlists.begin(); i != playlists.end(); ++i) { (*i)->set_edit_mode (mode); @@ -3409,7 +3415,7 @@ Session::next_insert_name () NamedSelection * Session::named_selection_by_name (string name) { - LockMonitor lm (named_selection_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (named_selection_lock); for (NamedSelectionList::iterator i = named_selections.begin(); i != named_selections.end(); ++i) { if ((*i)->name == name) { return* i; @@ -3422,7 +3428,7 @@ void Session::add_named_selection (NamedSelection* named_selection) { { - LockMonitor lm (named_selection_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (named_selection_lock); named_selections.insert (named_selections.begin(), named_selection); } @@ -3437,7 +3443,7 @@ Session::remove_named_selection (NamedSelection* named_selection) bool removed = false; { - LockMonitor lm (named_selection_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (named_selection_lock); NamedSelectionList::iterator i = find (named_selections.begin(), named_selections.end(), named_selection); @@ -3459,7 +3465,7 @@ Session::reset_native_file_format () { // jlc - WHY take routelock? //RWLockMonitor lm1 (route_lock, true, __LINE__, __FILE__); - RWLockMonitor lm2 (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm2 (diskstream_lock); for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { (*i)->reset_write_sources (false); @@ -3469,7 +3475,7 @@ Session::reset_native_file_format () bool Session::route_name_unique (string n) const { - RWLockMonitor lm (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (route_lock); for (RouteList::const_iterator i = routes.begin(); i != routes.end(); ++i) { if ((*i)->name() == n) { @@ -3489,7 +3495,7 @@ Session::remove_file_source (FileSource& fs) uint32_t Session::n_playlists () const { - LockMonitor lm (playlist_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (playlist_lock); return playlists.size(); } @@ -3538,7 +3544,7 @@ Session::add_instant_xml (XMLNode& node, const std::string& dir) int Session::freeze (InterThreadInfo& itt) { - RWLockMonitor lm (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (route_lock); for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) { @@ -3573,7 +3579,7 @@ Session::write_one_track (AudioTrack& track, jack_nframes_t start, jack_nframes_ char * workbuf = 0; const jack_nframes_t chunk_size = (256 * 1024)/4; - atomic_set (&processing_prohibited, 1); + g_atomic_int_set (&processing_prohibited, 1); /* call tree *MUST* hold route_lock */ @@ -3694,7 +3700,7 @@ Session::write_one_track (AudioTrack& track, jack_nframes_t start, jack_nframes_ delete [] workbuf; } - atomic_set (&processing_prohibited, 0); + g_atomic_int_set (&processing_prohibited, 0); itt.done = true; @@ -3714,7 +3720,7 @@ uint32_t Session::ntracks () const { uint32_t n = 0; - RWLockMonitor lm (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (route_lock); for (RouteList::const_iterator i = routes.begin(); i != routes.end(); ++i) { if (dynamic_cast (*i)) { @@ -3729,7 +3735,7 @@ uint32_t Session::nbusses () const { uint32_t n = 0; - RWLockMonitor lm (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (route_lock); for (RouteList::const_iterator i = routes.begin(); i != routes.end(); ++i) { if (dynamic_cast (*i) == 0) { diff --git a/libs/ardour/session_butler.cc b/libs/ardour/session_butler.cc index dafc28385b..ebe0d64548 100644 --- a/libs/ardour/session_butler.cc +++ b/libs/ardour/session_butler.cc @@ -26,8 +26,9 @@ #include #include +#include + #include -#include #include #include @@ -73,8 +74,6 @@ Session::start_butler_thread () Crossfade::set_buffer_size (dstream_buffer_size); - pthread_cond_init (&butler_paused, 0); - butler_should_run = false; if (pipe (butler_request_pipe)) { @@ -114,7 +113,7 @@ Session::terminate_butler_thread () void Session::schedule_butler_transport_work () { - atomic_inc (&butler_should_do_transport_work); + g_atomic_int_inc (&butler_should_do_transport_work); summon_butler (); } @@ -135,19 +134,19 @@ Session::summon_butler () void Session::stop_butler () { - LockMonitor lm (butler_request_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (butler_request_lock); char c = ButlerRequest::Pause; ::write (butler_request_pipe[1], &c, 1); - pthread_cond_wait (&butler_paused, butler_request_lock.mutex()); + butler_paused.wait(butler_request_lock); } void Session::wait_till_butler_finished () { - LockMonitor lm (butler_request_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (butler_request_lock); char c = ButlerRequest::Wake; ::write (butler_request_pipe[1], &c, 1); - pthread_cond_wait (&butler_paused, butler_request_lock.mutex()); + butler_paused.wait(butler_request_lock); } void * @@ -158,7 +157,7 @@ Session::_butler_thread_work (void* arg) return 0; } -#define transport_work_requested() atomic_read(&butler_should_do_transport_work) +#define transport_work_requested() g_atomic_int_get(&butler_should_do_transport_work) void * Session::butler_thread_work () @@ -256,7 +255,7 @@ Session::butler_thread_work () gettimeofday (&begin, 0); - RWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock dsm (diskstream_lock); for (i = diskstreams.begin(); !transport_work_requested() && butler_should_run && i != diskstreams.end(); ++i) { @@ -355,7 +354,7 @@ Session::butler_thread_work () { - LockMonitor lm (butler_request_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (butler_request_lock); if (butler_should_run && (disk_work_outstanding || transport_work_requested())) { // for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { @@ -365,7 +364,7 @@ Session::butler_thread_work () continue; } - pthread_cond_signal (&butler_paused); + butler_paused.signal(); } } @@ -398,7 +397,7 @@ Session::overwrite_some_buffers (DiskStream* ds) } else { - RWLockMonitor dm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock dm (diskstream_lock); for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { (*i)->set_pending_overwrite (true); } @@ -429,36 +428,36 @@ Session::write_data_rate () const uint32_t Session::playback_load () { - return (uint32_t) atomic_read (&_playback_load); + return (uint32_t) g_atomic_int_get (&_playback_load); } uint32_t Session::capture_load () { - return (uint32_t) atomic_read (&_capture_load); + return (uint32_t) g_atomic_int_get (&_capture_load); } uint32_t Session::playback_load_min () { - return (uint32_t) atomic_read (&_playback_load_min); + return (uint32_t) g_atomic_int_get (&_playback_load_min); } uint32_t Session::capture_load_min () { - return (uint32_t) atomic_read (&_capture_load_min); + return (uint32_t) g_atomic_int_get (&_capture_load_min); } void Session::reset_capture_load_min () { - atomic_set (&_capture_load_min, 100); + g_atomic_int_set (&_capture_load_min, 100); } void Session::reset_playback_load_min () { - atomic_set (&_playback_load_min, 100); + g_atomic_int_set (&_playback_load_min, 100); } diff --git a/libs/ardour/session_click.cc b/libs/ardour/session_click.cc index c9777500a2..4503287da1 100644 --- a/libs/ardour/session_click.cc +++ b/libs/ardour/session_click.cc @@ -47,7 +47,7 @@ Session::click (jack_nframes_t start, jack_nframes_t nframes, jack_nframes_t off return; } - TentativeRWLockMonitor clickm (click_lock, true, __LINE__, __FILE__); + Glib::RWLock::WriterLock clickm (click_lock, Glib::TRY_LOCK); if (!clickm.locked() || _transport_speed != 1.0 || !_clicking || click_data == 0) { _click_io->silence (nframes, offset); @@ -209,7 +209,7 @@ Session::setup_click_sounds (int which) void Session::clear_clicks () { - RWLockMonitor lm (click_lock, true, __LINE__, __FILE__); + Glib::RWLock::WriterLock lm (click_lock); for (Clicks::iterator i = clicks.begin(); i != clicks.end(); ++i) { delete *i; diff --git a/libs/ardour/session_events.cc b/libs/ardour/session_events.cc index 2aeace81f4..d48bbe3053 100644 --- a/libs/ardour/session_events.cc +++ b/libs/ardour/session_events.cc @@ -24,7 +24,7 @@ #include #include -#include +#include #include #include diff --git a/libs/ardour/session_export.cc b/libs/ardour/session_export.cc index 677b2c1258..183b6df237 100644 --- a/libs/ardour/session_export.cc +++ b/libs/ardour/session_export.cc @@ -37,7 +37,7 @@ #include #include -#include +#include #include #include @@ -485,7 +485,7 @@ Session::prepare_to_export (AudioExportSpecification& spec) /* take everyone out of awrite to avoid disasters */ { - RWLockMonitor lm (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (route_lock); for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) { (*i)->protect_automation (); } @@ -494,7 +494,7 @@ Session::prepare_to_export (AudioExportSpecification& spec) /* get everyone to the right position */ { - RWLockMonitor lm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (diskstream_lock); for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { if ((*i)-> seek (spec.start_frame, true)) { error << string_compose (_("%1: cannot seek to %2 for export"), @@ -524,7 +524,7 @@ Session::prepare_to_export (AudioExportSpecification& spec) set_transport_speed (1.0, false); butler_transport_work (); - atomic_set (&butler_should_do_transport_work, 0); + g_atomic_int_set (&butler_should_do_transport_work, 0); post_transport (); /* we are ready to go ... */ diff --git a/libs/ardour/session_feedback.cc b/libs/ardour/session_feedback.cc index 600567892e..ea8580b3c2 100644 --- a/libs/ardour/session_feedback.cc +++ b/libs/ardour/session_feedback.cc @@ -28,8 +28,10 @@ #include #include #include + +#include + #include -#include #include #include diff --git a/libs/ardour/session_midi.cc b/libs/ardour/session_midi.cc index aa079f8827..d8382c69a4 100644 --- a/libs/ardour/session_midi.cc +++ b/libs/ardour/session_midi.cc @@ -30,7 +30,7 @@ #include #include #include -#include +#include #include #include @@ -110,7 +110,7 @@ Session::set_midi_control (bool yn) poke_midi_thread (); if (_midi_port) { - RWLockMonitor lm (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock guard (route_lock); for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) { (*i)->reset_midi_control (_midi_port, midi_control); } @@ -601,7 +601,7 @@ Session::mmc_record_strobe (MIDI::MachineControl &mmc) */ save_state ("", true); - atomic_set (&_record_status, Enabled); + g_atomic_int_set (&_record_status, Enabled); RecordStateChanged (); /* EMIT SIGNAL */ request_transport_speed (1.0); @@ -783,7 +783,7 @@ Session::mmc_record_enable (MIDI::MachineControl &mmc, size_t trk, bool enabled) if (mmc_control) { RouteList::iterator i; - RWLockMonitor (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock guard (route_lock); for (i = routes.begin(); i != routes.end(); ++i) { AudioTrack *at; @@ -908,7 +908,7 @@ Session::send_full_time_code () msg[8] = smpte.frames; { - LockMonitor lm (midi_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (midi_lock); if (_mtc_port->midimsg (msg, sizeof (msg))) { error << _("Session: could not send full MIDI time code") << endmsg; @@ -940,7 +940,7 @@ Session::send_midi_time_code () // Send quarter frames up to current time { - LockMonitor lm (midi_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (midi_lock); switch(next_quarter_frame_to_send) { case 0: @@ -1075,7 +1075,7 @@ Session::deliver_mmc (MIDI::MachineControl::Command cmd, jack_nframes_t where) mmc_buffer[nbytes++] = 0xf7; // terminate SysEx/MMC message - LockMonitor lm (midi_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (midi_lock); if (_mmc_port->write (mmc_buffer, nbytes) != nbytes) { error << string_compose(_("MMC: cannot send command %1%2%3"), &hex, cmd, &dec) << endmsg; diff --git a/libs/ardour/session_process.cc b/libs/ardour/session_process.cc index 3280a5f4bb..2f098a384f 100644 --- a/libs/ardour/session_process.cc +++ b/libs/ardour/session_process.cc @@ -23,14 +23,13 @@ #include #include -#include - #include -#include -#include + +#include #include #include +#include #include #include #include @@ -54,7 +53,7 @@ Session::process (jack_nframes_t nframes) } if (non_realtime_work_pending()) { - if (atomic_read (&butler_should_do_transport_work) == 0) { + if (g_atomic_int_get (&butler_should_do_transport_work) == 0) { post_transport (); } } @@ -85,7 +84,7 @@ Session::no_roll (jack_nframes_t nframes, jack_nframes_t offset) this is really bad ... */ - if (atomic_read (&processing_prohibited)) { + if (g_atomic_int_get (&processing_prohibited)) { for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) { (*i)->silence (nframes, offset); } @@ -222,15 +221,15 @@ Session::commit_diskstreams (jack_nframes_t nframes, bool &needs_butler) cworst = min (cworst, (*i)->capture_buffer_load()); } - uint32_t pmin = atomic_read (&_playback_load); - uint32_t pminold = atomic_read (&_playback_load_min); - uint32_t cmin = atomic_read (&_capture_load); - uint32_t cminold = atomic_read (&_capture_load_min); + uint32_t pmin = g_atomic_int_get (&_playback_load); + uint32_t pminold = g_atomic_int_get (&_playback_load_min); + uint32_t cmin = g_atomic_int_get (&_capture_load); + uint32_t cminold = g_atomic_int_get (&_capture_load_min); - atomic_set (&_playback_load, (uint32_t) floor (pworst * 100.0f)); - atomic_set (&_capture_load, (uint32_t) floor (cworst * 100.0f)); - atomic_set (&_playback_load_min, min (pmin, pminold)); - atomic_set (&_capture_load_min, min (cmin, cminold)); + g_atomic_int_set (&_playback_load, (uint32_t) floor (pworst * 100.0f)); + g_atomic_int_set (&_capture_load, (uint32_t) floor (cworst * 100.0f)); + g_atomic_int_set (&_playback_load_min, min (pmin, pminold)); + g_atomic_int_set (&_capture_load_min, min (cmin, cminold)); if (actively_recording()) { set_dirty(); @@ -280,8 +279,8 @@ Session::process_with_events (jack_nframes_t nframes) end_frame = _transport_frame + nframes; { - TentativeRWLockMonitor rm (route_lock, false, __LINE__, __FILE__); - TentativeRWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock rm (route_lock, Glib::TRY_LOCK); + Glib::RWLock::ReaderLock dsm (diskstream_lock, Glib::TRY_LOCK); Event* this_event; Events::iterator the_next_one; @@ -557,7 +556,7 @@ Session::follow_slave (jack_nframes_t nframes, jack_nframes_t offset) if (slave_state == Waiting) { // cerr << "waiting at " << slave_transport_frame << endl; - TentativeRWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock dsm (diskstream_lock, Glib::TRY_LOCK); if (dsm.locked() && slave_transport_frame >= slave_wait_end) { // cerr << "\tstart at " << _transport_frame << endl; @@ -679,7 +678,7 @@ Session::follow_slave (jack_nframes_t nframes, jack_nframes_t offset) bool need_butler; - TentativeRWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock dsm (diskstream_lock, Glib::TRY_LOCK); if (!dsm.locked()) { goto noroll; } @@ -730,8 +729,8 @@ Session::process_without_events (jack_nframes_t nframes) long frames_moved; { - TentativeRWLockMonitor rm (route_lock, false, __LINE__, __FILE__); - TentativeRWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock rm (route_lock, Glib::TRY_LOCK); + Glib::RWLock::ReaderLock dsm (diskstream_lock, Glib::TRY_LOCK); if (!rm.locked() || !dsm.locked() || (post_transport_work & (PostTransportLocate|PostTransportStop))) { no_roll (nframes, 0); @@ -802,7 +801,7 @@ Session::process_without_events (jack_nframes_t nframes) void Session::process_audition (jack_nframes_t nframes) { - TentativeRWLockMonitor rm (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock rm (route_lock, Glib::TRY_LOCK); Event* ev; if (rm.locked()) { diff --git a/libs/ardour/session_state.cc b/libs/ardour/session_state.cc index eaadec0fd3..cf510e9881 100644 --- a/libs/ardour/session_state.cc +++ b/libs/ardour/session_state.cc @@ -44,14 +44,15 @@ #include #endif +#include + #include #include #include -#include -#include + +#include #include #include -#include #include #include @@ -118,7 +119,7 @@ Session::first_stage_init (string fullpath, string snapshot_name) _tempo_map = new TempoMap (_current_frame_rate); _tempo_map->StateChanged.connect (mem_fun (*this, &Session::tempo_map_changed)); - atomic_set (&processing_prohibited, 0); + g_atomic_int_set (&processing_prohibited, 0); send_cnt = 0; insert_cnt = 0; _transport_speed = 0; @@ -129,7 +130,7 @@ Session::first_stage_init (string fullpath, string snapshot_name) end_location = new Location (0, 0, _("end"), Location::Flags ((Location::IsMark|Location::IsEnd))); start_location = new Location (0, 0, _("start"), Location::Flags ((Location::IsMark|Location::IsStart))); _end_location_is_free = true; - atomic_set (&_record_status, Disabled); + g_atomic_int_set (&_record_status, Disabled); auto_play = false; punch_in = false; punch_out = false; @@ -170,12 +171,12 @@ Session::first_stage_init (string fullpath, string snapshot_name) midi_control = true; mmc = 0; post_transport_work = PostTransportWork (0); - atomic_set (&butler_should_do_transport_work, 0); - atomic_set (&butler_active, 0); - atomic_set (&_playback_load, 100); - atomic_set (&_capture_load, 100); - atomic_set (&_playback_load_min, 100); - atomic_set (&_capture_load_min, 100); + g_atomic_int_set (&butler_should_do_transport_work, 0); + g_atomic_int_set (&butler_active, 0); + g_atomic_int_set (&_playback_load, 100); + g_atomic_int_set (&_capture_load, 100); + g_atomic_int_set (&_playback_load_min, 100); + g_atomic_int_set (&_capture_load_min, 100); pending_audition_region = 0; _edit_mode = Slide; pending_edit_mode = _edit_mode; @@ -1334,7 +1335,7 @@ Session::state(bool full_state) child = node->add_child ("Sources"); if (full_state) { - LockMonitor sl (source_lock, __LINE__, __FILE__); + Glib::Mutex::Lock sl (source_lock); for (SourceList::iterator siter = sources.begin(); siter != sources.end(); ++siter) { @@ -1363,7 +1364,7 @@ Session::state(bool full_state) child = node->add_child ("Regions"); if (full_state) { - LockMonitor rl (region_lock, __LINE__, __FILE__); + Glib::Mutex::Lock rl (region_lock); for (AudioRegionList::const_iterator i = audio_regions.begin(); i != audio_regions.end(); ++i) { @@ -1378,7 +1379,7 @@ Session::state(bool full_state) child = node->add_child ("DiskStreams"); { - RWLockMonitor dl (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock dl (diskstream_lock); for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { if (!(*i)->hidden()) { child->add_child_nocopy ((*i)->get_state()); @@ -1390,7 +1391,7 @@ Session::state(bool full_state) child = node->add_child ("Connections"); { - LockMonitor lm (connection_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (connection_lock); for (ConnectionList::iterator i = _connections.begin(); i != _connections.end(); ++i) { if (!(*i)->system_dependent()) { child->add_child_nocopy ((*i)->get_state()); @@ -1400,7 +1401,7 @@ Session::state(bool full_state) child = node->add_child ("Routes"); { - RWLockMonitor lm (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (route_lock); RoutePublicOrderSorter cmp; RouteList public_order(routes); @@ -1803,7 +1804,7 @@ Session::get_sources_as_xml () { XMLNode* node = new XMLNode (X_("Sources")); - LockMonitor lm (source_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (source_lock); for (SourceList::iterator i = sources.begin(); i != sources.end(); ++i) { node->add_child_nocopy ((*i).second->get_state()); @@ -1958,7 +1959,7 @@ Session::refresh_disk_space () #if HAVE_SYS_VFS_H struct statfs statfsbuf; vector::iterator i; - LockMonitor lm (space_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (space_lock); double scale; /* get freespace on every FS that is part of the session path */ @@ -2399,7 +2400,7 @@ Session::load_route_groups (const XMLNode& node, bool edit) void Session::swap_configuration(Configuration** new_config) { - RWLockMonitor lm (route_lock, true, __LINE__, __FILE__); // jlc - WHY? + Glib::RWLock::WriterLock lm (route_lock); // jlc - WHY? Configuration* tmp = *new_config; *new_config = Config; Config = tmp; @@ -2409,7 +2410,7 @@ Session::swap_configuration(Configuration** new_config) void Session::copy_configuration(Configuration* new_config) { - RWLockMonitor lm (route_lock, true, __LINE__, __FILE__); + Glib::RWLock::WriterLock lm (route_lock); new_config = new Configuration(*Config); } @@ -2588,7 +2589,7 @@ Session::GlobalRouteBooleanState Session::get_global_route_boolean (bool (Route::*method)(void) const) { GlobalRouteBooleanState s; - RWLockMonitor lm (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (route_lock); for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) { if (!(*i)->hidden()) { @@ -2608,7 +2609,7 @@ Session::GlobalRouteMeterState Session::get_global_route_metering () { GlobalRouteMeterState s; - RWLockMonitor lm (route_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (route_lock); for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) { if (!(*i)->hidden()) { @@ -3065,13 +3066,13 @@ Session::cleanup_sources (Session::cleanup_report& rep) on whichever filesystem it was already on. */ - newpath = PBD::dirname (*x); - newpath = PBD::dirname (newpath); + newpath = Glib::path_get_dirname (*x); + newpath = Glib::path_get_dirname (newpath); newpath += '/'; newpath += dead_sound_dir_name; newpath += '/'; - newpath += PBD::basename ((*x)); + newpath += Glib::path_get_basename ((*x)); if (access (newpath.c_str(), F_OK) == 0) { diff --git a/libs/ardour/session_transport.cc b/libs/ardour/session_transport.cc index 6e756b28b7..db15b64c32 100644 --- a/libs/ardour/session_transport.cc +++ b/libs/ardour/session_transport.cc @@ -27,7 +27,7 @@ #include #include -#include +#include #include #include @@ -190,8 +190,8 @@ Session::realtime_stop (bool abort) void Session::butler_transport_work () { - RWLockMonitor rm (route_lock, false, __LINE__, __FILE__); - RWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock rm (route_lock); + Glib::RWLock::ReaderLock dsm (diskstream_lock); if (post_transport_work & PostTransportCurveRealloc) { for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) { @@ -240,13 +240,13 @@ Session::butler_transport_work () non_realtime_set_audition (); } - atomic_dec (&butler_should_do_transport_work); + g_atomic_int_dec_and_test (&butler_should_do_transport_work); } void Session::non_realtime_set_speed () { - RWLockMonitor lm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (diskstream_lock); for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { (*i)->non_realtime_set_speed (); @@ -256,7 +256,7 @@ Session::non_realtime_set_speed () void Session::non_realtime_overwrite () { - RWLockMonitor lm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (diskstream_lock); for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { if ((*i)->pending_overwrite) { @@ -395,9 +395,9 @@ Session::non_realtime_stop (bool abort) */ if (!Config->get_latched_record_enable()) { - atomic_set (&_record_status, Disabled); + g_atomic_int_set (&_record_status, Disabled); } else { - atomic_set (&_record_status, Enabled); + g_atomic_int_set (&_record_status, Enabled); } RecordStateChanged (); /* emit signal */ } @@ -625,7 +625,7 @@ Session::locate (jack_nframes_t target_frame, bool with_roll, bool with_flush, b /* this is functionally what clear_clicks() does but with a tentative lock */ - TentativeRWLockMonitor clickm (click_lock, true, __LINE__, __FILE__); + Glib::RWLock::WriterLock clickm (click_lock, Glib::TRY_LOCK); if (clickm.locked()) { @@ -644,7 +644,7 @@ Session::locate (jack_nframes_t target_frame, bool with_roll, bool with_flush, b a non-tentative rwlock here, because the action must occur. The rarity and short potential lock duration makes this "OK" */ - RWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock dsm (diskstream_lock); for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { if ((*i)->record_enabled ()) { //cerr << "switching from input" << __FILE__ << __LINE__ << endl << endl; @@ -659,7 +659,7 @@ Session::locate (jack_nframes_t target_frame, bool with_roll, bool with_flush, b a non-tentative rwlock here, because the action must occur. The rarity and short potential lock duration makes this "OK" */ - RWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock dsm (diskstream_lock); for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { if ((*i)->record_enabled ()) { //cerr << "switching to input" << __FILE__ << __LINE__ << endl << endl; @@ -703,7 +703,7 @@ Session::set_transport_speed (float speed, bool abort) a non-tentative rwlock here, because the action must occur. The rarity and short potential lock duration makes this "OK" */ - RWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock dsm (diskstream_lock); for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { if ((*i)->record_enabled ()) { //cerr << "switching to input" << __FILE__ << __LINE__ << endl << endl; @@ -729,7 +729,7 @@ Session::set_transport_speed (float speed, bool abort) a non-tentative rwlock here, because the action must occur. The rarity and short potential lock duration makes this "OK" */ - RWLockMonitor dsm (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock dsm (diskstream_lock); for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { if (auto_input && (*i)->record_enabled ()) { //cerr << "switching from input" << __FILE__ << __LINE__ << endl << endl; @@ -1156,7 +1156,7 @@ Session::engine_halted () the picture. */ - atomic_set (&butler_should_do_transport_work, 0); + g_atomic_int_set (&butler_should_do_transport_work, 0); post_transport_work = PostTransportWork (0); stop_butler (); @@ -1192,8 +1192,8 @@ Session::update_latency_compensation (bool with_stop, bool abort) return; } - RWLockMonitor lm (route_lock, false, __LINE__, __FILE__); - RWLockMonitor lm2 (diskstream_lock, false, __LINE__, __FILE__); + Glib::RWLock::ReaderLock lm (route_lock); + Glib::RWLock::ReaderLock lm2 (diskstream_lock); _worst_track_latency = 0; for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) { diff --git a/libs/ardour/sndfilesource.cc b/libs/ardour/sndfilesource.cc index e547b212a0..87f7faf423 100644 --- a/libs/ardour/sndfilesource.cc +++ b/libs/ardour/sndfilesource.cc @@ -138,7 +138,7 @@ SndFileSource::read (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char real_cnt = cnt * _info.channels; { - LockMonitor lm (_tmpbuf_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (_tmpbuf_lock); if (tmpbufsize < real_cnt) { diff --git a/libs/ardour/source.cc b/libs/ardour/source.cc index ffb067733d..7d790a036d 100644 --- a/libs/ardour/source.cc +++ b/libs/ardour/source.cc @@ -29,7 +29,7 @@ #include #include -#include +#include #include #include @@ -41,13 +41,12 @@ using std::min; using std::max; using namespace ARDOUR; -using namespace PBD; -sigc::signal Source::SourceCreated; +sigc::signal Source::SourceCreated; pthread_t Source::peak_thread; bool Source::have_peak_thread = false; vector Source::pending_peak_sources; -PBD::Lock Source::pending_peak_sources_lock; +Glib::StaticMutex Source::pending_peak_sources_lock = GLIBMM_STATIC_MUTEX_INIT; int Source::peak_request_pipe[2]; bool Source::_build_missing_peakfiles = false; @@ -142,19 +141,19 @@ Source::peak_thread_work (void* arg) PBD::ThreadCreated (pthread_self(), X_("Peak")); struct pollfd pfd[1]; - LockMonitor lm (pending_peak_sources_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (pending_peak_sources_lock); while (true) { pfd[0].fd = peak_request_pipe[0]; pfd[0].events = POLLIN|POLLERR|POLLHUP; - pthread_mutex_unlock (pending_peak_sources_lock.mutex()); + pending_peak_sources_lock.unlock(); if (poll (pfd, 1, -1) < 0) { if (errno == EINTR) { - pthread_mutex_lock (pending_peak_sources_lock.mutex()); + pending_peak_sources_lock.lock(); continue; } @@ -204,16 +203,16 @@ Source::peak_thread_work (void* arg) } } - pthread_mutex_lock (pending_peak_sources_lock.mutex()); + pending_peak_sources_lock.lock(); while (!pending_peak_sources.empty()) { Source* s = pending_peak_sources.front(); pending_peak_sources.erase (pending_peak_sources.begin()); - pthread_mutex_unlock (pending_peak_sources_lock.mutex()); + pending_peak_sources_lock.unlock(); s->build_peaks(); - pthread_mutex_lock (pending_peak_sources_lock.mutex()); + pending_peak_sources_lock.lock(); } } @@ -272,7 +271,7 @@ Source::queue_for_peaks (Source& source) { if (have_peak_thread) { - LockMonitor lm (pending_peak_sources_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (pending_peak_sources_lock); source.next_peak_clear_should_notify = true; @@ -291,7 +290,7 @@ void Source::clear_queue_for_peaks () { /* this is done to cancel a group of running peak builds */ if (have_peak_thread) { - LockMonitor lm (pending_peak_sources_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (pending_peak_sources_lock); pending_peak_sources.clear (); } } @@ -301,7 +300,7 @@ bool Source::peaks_ready (sigc::slot the_slot, sigc::connection& conn) const { bool ret; - LockMonitor lm (_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (_lock); /* check to see if the peak data is ready. if not connect the slot while still holding the lock. @@ -388,7 +387,7 @@ Source::initialize_peakfile (bool newfile, string audio_path) int Source::read_peaks (PeakData *peaks, jack_nframes_t npeaks, jack_nframes_t start, jack_nframes_t cnt, double samples_per_visual_peak) const { - LockMonitor lm (_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (_lock); double scale; double expected_peaks; PeakData::PeakDatum xmax; @@ -699,7 +698,7 @@ Source::build_peaks () list copy; { - LockMonitor lm (_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (_lock); copy = pending_peak_builds; pending_peak_builds.clear (); } @@ -719,7 +718,7 @@ Source::build_peaks () } { - LockMonitor lm (_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (_lock); if (status == 0) { _peaks_built = true; @@ -830,7 +829,7 @@ Source::do_build_peak (jack_nframes_t first_frame, jack_nframes_t cnt) void Source::build_peaks_from_scratch () { - LockMonitor lp (_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lp (_lock); next_peak_clear_should_notify = true; pending_peak_builds.push_back (new PeakBuildRecord (0, _length)); @@ -883,7 +882,7 @@ Source::available_peaks (double zoom_factor) const } { - LockMonitor lm (_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (_lock); end = lseek (peakfile, 0, SEEK_END); } diff --git a/libs/ardour/tempo.cc b/libs/ardour/tempo.cc index 5d6365cff3..64964b29dd 100644 --- a/libs/ardour/tempo.cc +++ b/libs/ardour/tempo.cc @@ -25,7 +25,7 @@ #include -#include +#include #include #include #include @@ -240,7 +240,7 @@ TempoMap::move_metric_section (MetricSection& section, const BBT_Time& when) return 1; } - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); MetricSectionSorter cmp; BBT_Time corrected (when); @@ -283,7 +283,7 @@ TempoMap::remove_tempo (const TempoSection& tempo) bool removed = false; { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); Metrics::iterator i; for (i = metrics->begin(); i != metrics->end(); ++i) { @@ -310,7 +310,7 @@ TempoMap::remove_meter (const MeterSection& tempo) bool removed = false; { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); Metrics::iterator i; for (i = metrics->begin(); i != metrics->end(); ++i) { @@ -361,7 +361,7 @@ void TempoMap::add_tempo (const Tempo& tempo, BBT_Time where) { { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); /* new tempos always start on a beat */ @@ -381,7 +381,7 @@ TempoMap::replace_tempo (TempoSection& existing, const Tempo& replacement) bool replaced = false; { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); Metrics::iterator i; for (i = metrics->begin(); i != metrics->end(); ++i) { @@ -411,7 +411,7 @@ void TempoMap::add_meter (const Meter& meter, BBT_Time where) { { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); /* a new meter always starts a new bar on the first beat. so round the start time appropriately. remember that @@ -443,7 +443,7 @@ TempoMap::replace_meter (MeterSection& existing, const Meter& replacement) bool replaced = false; { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); Metrics::iterator i; for (i = metrics->begin(); i != metrics->end(); ++i) { @@ -611,7 +611,7 @@ TempoMap::metric_at (BBT_Time bbt) const void TempoMap::bbt_time (jack_nframes_t frame, BBT_Time& bbt) const { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); bbt_time_unlocked (frame, bbt); } @@ -759,7 +759,7 @@ TempoMap::bbt_duration_at (jack_nframes_t pos, const BBT_Time& bbt, int dir) con bbt_time(pos,when); { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); frames = bbt_duration_at_unlocked (when, bbt,dir); } @@ -896,7 +896,7 @@ TempoMap::bbt_duration_at_unlocked (const BBT_Time& when, const BBT_Time& bbt, i jack_nframes_t TempoMap::round_to_bar (jack_nframes_t fr, int dir) { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); return round_to_type (fr, dir, Bar); } @@ -904,7 +904,7 @@ TempoMap::round_to_bar (jack_nframes_t fr, int dir) jack_nframes_t TempoMap::round_to_beat (jack_nframes_t fr, int dir) { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); return round_to_type (fr, dir, Beat); } @@ -912,7 +912,7 @@ jack_nframes_t TempoMap::round_to_beat_subdivision (jack_nframes_t fr, int sub_num) { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); TempoMap::BBTPointList::iterator i; TempoMap::BBTPointList *more_zoomed_bbt_points; jack_nframes_t frame_one_beats_worth; @@ -1185,7 +1185,7 @@ TempoMap::meter_at (jack_nframes_t frame) XMLNode& TempoMap::get_state () { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); Metrics::const_iterator i; XMLNode *root = new XMLNode ("TempoMap"); @@ -1200,7 +1200,7 @@ int TempoMap::set_state (const XMLNode& node) { { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); XMLNodeList nlist; XMLNodeConstIterator niter; @@ -1292,7 +1292,7 @@ TempoMap::get_memento () const Change TempoMap::restore_state (StateManager::State& state) { - LockMonitor lm (lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (lock); TempoMapState* tmstate = dynamic_cast (&state); diff --git a/libs/gtkmm2ext/fastmeter.cc b/libs/gtkmm2ext/fastmeter.cc index 2e20c49868..f0ee0ddea1 100644 --- a/libs/gtkmm2ext/fastmeter.cc +++ b/libs/gtkmm2ext/fastmeter.cc @@ -25,6 +25,7 @@ #include #include #include +#include using namespace Gtk; using namespace Gdk; @@ -32,15 +33,15 @@ using namespace Glib; using namespace Gtkmm2ext; using namespace std; -string FastMeter::v_image_path; -string FastMeter::h_image_path; -RefPtr FastMeter::v_pixbuf; -gint FastMeter::v_pixheight = 0; -gint FastMeter::v_pixwidth = 0; -RefPtr FastMeter::h_pixbuf; -gint FastMeter::h_pixheight = 0; -gint FastMeter::h_pixwidth = 0; +int FastMeter::min_v_pixbuf_size = 50; +int FastMeter::max_v_pixbuf_size = 1024; +Glib::RefPtr* FastMeter::v_pixbuf_cache = 0; + +int FastMeter::min_h_pixbuf_size = 50; +int FastMeter::max_h_pixbuf_size = 1024; +Glib::RefPtr* FastMeter::h_pixbuf_cache = 0; + FastMeter::FastMeter (long hold, unsigned long dimen, Orientation o) { @@ -56,46 +57,184 @@ FastMeter::FastMeter (long hold, unsigned long dimen, Orientation o) pixrect.x = 0; pixrect.y = 0; - if (!v_image_path.empty() && v_pixbuf == 0) { - v_pixbuf = Pixbuf::create_from_file (v_image_path); - v_pixheight = v_pixbuf->get_height(); - v_pixwidth = v_pixbuf->get_width(); - } - - if (!h_image_path.empty() && h_pixbuf == 0) { - h_pixbuf = Pixbuf::create_from_file (h_image_path); - h_pixheight = h_pixbuf->get_height(); - h_pixwidth = h_pixbuf->get_width(); - } if (orientation == Vertical) { - pixrect.width = min (v_pixwidth, (gint) dimen); - pixrect.height = v_pixheight; + pixbuf = request_vertical_meter(250); } else { - pixrect.width = h_pixwidth; - pixrect.height = min (h_pixheight, (gint) dimen); + pixbuf = request_horizontal_meter(186); + } + + pixheight = pixbuf->get_height(); + pixwidth = pixbuf->get_width(); + + if (orientation == Vertical) { + pixrect.width = min (pixwidth, (gint) dimen); + pixrect.height = pixheight; + } else { + pixrect.width = pixwidth; + pixrect.height = min (pixheight, (gint) dimen); } request_width = pixrect.width; request_height= pixrect.height; } +Glib::RefPtr FastMeter::request_vertical_meter(int length) +{ + if (length < min_v_pixbuf_size) + length = min_v_pixbuf_size; + if (length > max_v_pixbuf_size) + length = max_v_pixbuf_size; + + int index = length - 1; + + if (v_pixbuf_cache == 0) { + v_pixbuf_cache = (Glib::RefPtr*) malloc(sizeof(Glib::RefPtr) * max_v_pixbuf_size); + memset(v_pixbuf_cache,0,sizeof(Glib::RefPtr) * max_v_pixbuf_size); + } + Glib::RefPtr ret = v_pixbuf_cache[index]; + if (ret) + return ret; + + guint8* data; + int width = 5; + int height = length; + + data = (guint8*) malloc(width*height * 3); + + guint8 r,g,b; + r=0; + g=255; + b=0; + + // fake log calculation copied from log_meter.h + // actual calculation: + // log_meter(0.0f) = + // def = (0.0f + 20.0f) * 2.5f + 50f + // return def / 115.0f + int knee = (int)floor((float)height * 100.0f / 115.0f); + + int y; + + for (y = 0; y < knee / 2; y++) { + + r = (guint8)floor(255.0 * (float)y/(float)(knee / 2)); + + for (int x = 0; x < width; x++) { + data[ (x+(height-y-1)*width) * 3 + 0 ] = r; + data[ (x+(height-y-1)*width) * 3 + 1 ] = g; + data[ (x+(height-y-1)*width) * 3 + 2 ] = b; + } + } + + for (; y < knee; y++) { + + g = 255 - (guint8)floor(170.0 * (float)(y - knee/ 2)/(float)(knee / 2)); + + for (int x = 0; x < width; x++) { + data[ (x+(height-y-1)*width) * 3 + 0 ] = r; + data[ (x+(height-y-1)*width) * 3 + 1 ] = g; + data[ (x+(height-y-1)*width) * 3 + 2 ] = b; + } + } + + r=255; + g=0; + b=0; + for (; y < height; y++) { + for (int x = 0; x < width; x++) { + data[ (x+(height-y-1)*width) * 3 + 0 ] = r; + data[ (x+(height-y-1)*width) * 3 + 1 ] = g; + data[ (x+(height-y-1)*width) * 3 + 2 ] = b; + } + } + + ret = Pixbuf::create_from_data(data, COLORSPACE_RGB, false, 8, width, height, width * 3); + v_pixbuf_cache[index] = ret; + + return ret; +} + +Glib::RefPtr FastMeter::request_horizontal_meter(int length) +{ + if (length < min_h_pixbuf_size) + length = min_h_pixbuf_size; + if (length > max_h_pixbuf_size) + length = max_h_pixbuf_size; + + int index = length - 1; + + if (h_pixbuf_cache == 0) { + h_pixbuf_cache = (Glib::RefPtr*) malloc(sizeof(Glib::RefPtr) * max_h_pixbuf_size); + memset(h_pixbuf_cache,0,sizeof(Glib::RefPtr) * max_h_pixbuf_size); + } + Glib::RefPtr ret = h_pixbuf_cache[index]; + if (ret) + return ret; + + guint8* data; + int width = length; + int height = 5; + + data = (guint8*) malloc(width*height * 3); + + guint8 r,g,b; + r=0; + g=255; + b=0; + + // fake log calculation copied from log_meter.h + // actual calculation: + // log_meter(0.0f) = + // def = (0.0f + 20.0f) * 2.5f + 50f + // return def / 115.0f + int knee = (int)floor((float)width * 100.0f / 115.0f); + + int x; + + for (x = 0; x < knee / 2; x++) { + + r = (guint8)floor(255.0 * (float)x/(float)(knee / 2)); + + for (int y = 0; y < height; y++) { + data[ (x+(height-y-1)*width) * 3 + 0 ] = r; + data[ (x+(height-y-1)*width) * 3 + 1 ] = g; + data[ (x+(height-y-1)*width) * 3 + 2 ] = b; + } + } + + for (; x < knee; x++) { + + g = 255 - (guint8)floor(170.0 * (float)(x - knee/ 2)/(float)(knee / 2)); + + for (int y = 0; y < height; y++) { + data[ (x+(height-y-1)*width) * 3 + 0 ] = r; + data[ (x+(height-y-1)*width) * 3 + 1 ] = g; + data[ (x+(height-y-1)*width) * 3 + 2 ] = b; + } + } + + r=255; + g=0; + b=0; + for (; x < width; x++) { + for (int y = 0; y < height; y++) { + data[ (x+(height-y-1)*width) * 3 + 0 ] = r; + data[ (x+(height-y-1)*width) * 3 + 1 ] = g; + data[ (x+(height-y-1)*width) * 3 + 2 ] = b; + } + } + + ret = Pixbuf::create_from_data(data, COLORSPACE_RGB, false, 8, width, height, width * 3); + h_pixbuf_cache[index] = ret; + + return ret; +} + FastMeter::~FastMeter () { } -void -FastMeter::set_vertical_xpm (std::string path) -{ - v_image_path = path; -} - -void -FastMeter::set_horizontal_xpm (std::string path) -{ - h_image_path = path; -} - void FastMeter::set_hold_count (long val) { @@ -113,8 +252,63 @@ FastMeter::set_hold_count (long val) void FastMeter::on_size_request (GtkRequisition* req) { - req->width = request_width; - req->height = request_height; + if (orientation == Vertical) { + req->height = request_height; + + req->height = max(req->height, min_v_pixbuf_size); + req->height = min(req->height, max_v_pixbuf_size); + + req->width = 5; + } else { + req->width = request_width; + + req->width = max(req->width, min_h_pixbuf_size); + req->width = min(req->width, max_h_pixbuf_size); + + req->height = 5; + } + +} + +void +FastMeter::on_size_allocate (Gtk::Allocation &alloc) +{ + if (orientation == Vertical) { + if (alloc.get_width() != 5) { + alloc.set_width(5); + } + + int h = alloc.get_height(); + h = max(h, min_v_pixbuf_size); + h = min(h, max_v_pixbuf_size); + + if ( h != alloc.get_height()) + alloc.set_height(h); + + if (pixheight != h) { + pixbuf = request_vertical_meter(h); + } + } else { + if (alloc.get_height() != 5) { + alloc.set_height(5); + } + + int w = alloc.get_width(); + w = max(w, min_h_pixbuf_size); + w = min(w, max_h_pixbuf_size); + + if ( w != alloc.get_width()) + alloc.set_width(w); + + if (pixwidth != w) { + pixbuf = request_horizontal_meter(w); + } + } + + pixheight = pixbuf->get_height(); + pixwidth = pixbuf->get_width(); + + DrawingArea::on_size_allocate(alloc); } bool @@ -134,78 +328,87 @@ FastMeter::vertical_expose (GdkEventExpose* ev) GdkRectangle intersection; GdkRectangle background; - top_of_meter = (gint) floor (v_pixheight * current_level); + top_of_meter = (gint) floor (pixheight * current_level); pixrect.height = top_of_meter; background.x = 0; background.y = 0; background.width = pixrect.width; - background.height = v_pixheight - top_of_meter; + background.height = pixheight - top_of_meter; - if (gdk_rectangle_intersect (&background, &ev->area, &intersection)) { + if (gdk_rectangle_intersect (&background, &ev->area, &intersection)) { get_window()->draw_rectangle (get_style()->get_black_gc(), true, intersection.x, intersection.y, intersection.width, intersection.height); } if (gdk_rectangle_intersect (&pixrect, &ev->area, &intersection)) { - - /* draw the part of the meter image that we need. the area we draw is bounded "in reverse" (top->bottom) - */ - - get_window()->draw_pixbuf(get_style()->get_fg_gc(get_state()), v_pixbuf, - intersection.x, v_pixheight - top_of_meter, - intersection.x, v_pixheight - top_of_meter, + // draw the part of the meter image that we need. the area we draw is bounded "in reverse" (top->bottom) + get_window()->draw_pixbuf(get_style()->get_fg_gc(get_state()), pixbuf, + intersection.x, pixheight - top_of_meter, + intersection.x, pixheight - top_of_meter, intersection.width, intersection.height, Gdk::RGB_DITHER_NONE, 0, 0); } - /* draw peak bar */ - - if (hold_state) { - get_window()->draw_pixbuf (get_style()->get_fg_gc(get_state()), v_pixbuf, - intersection.x, v_pixheight - (gint) floor (v_pixheight * current_peak), - intersection.x, v_pixheight - (gint) floor (v_pixheight * current_peak), + // draw peak bar + if (hold_state && intersection.width > 0) { + gint y = pixheight - (gint) floor (pixheight * current_peak); + + get_window()->draw_pixbuf (get_style()->get_fg_gc(get_state()), pixbuf, + intersection.x, y, + intersection.x, y, intersection.width, 3, Gdk::RGB_DITHER_NONE, 0, 0); } - return true; + return TRUE; } bool FastMeter::horizontal_expose (GdkEventExpose* ev) { - GdkRectangle intersection; gint right_of_meter; + GdkRectangle intersection; + GdkRectangle background; - right_of_meter = (gint) floor (h_pixwidth * current_level); + right_of_meter = (gint) floor (pixwidth * current_level); pixrect.width = right_of_meter; - if (gdk_rectangle_intersect (&pixrect, &ev->area, &intersection)) { - - /* draw the part of the meter image that we need. - */ - - get_window()->draw_pixbuf (get_style()->get_fg_gc(get_state()), h_pixbuf, - intersection.x, intersection.y, - intersection.x, intersection.y, - intersection.width, intersection.height, - Gdk::RGB_DITHER_NONE, 0, 0); + background.x = 0; + background.y = 0; + background.width = pixwidth - right_of_meter; + background.height = pixrect.height; + if (gdk_rectangle_intersect (&background, &ev->area, &intersection)) { + get_window()->draw_rectangle (get_style()->get_black_gc(), true, + intersection.x + right_of_meter, intersection.y, + intersection.width, intersection.height); } - /* draw peak bar */ - - if (hold_state) { - get_window()->draw_pixbuf (get_style()->get_fg_gc(get_state()), h_pixbuf, - right_of_meter, intersection.y, - right_of_meter, intersection.y, + if (gdk_rectangle_intersect (&pixrect, &ev->area, &intersection)) { + // draw the part of the meter image that we need. the area we draw is bounded "in reverse" (top->bottom) + get_window()->draw_pixbuf(get_style()->get_fg_gc(get_state()), pixbuf, + intersection.x, intersection.y, + intersection.x, intersection.y, + intersection.width, intersection.height, + Gdk::RGB_DITHER_NONE, 0, 0); + } + + // draw peak bar + // XXX: peaks don't work properly + /* + if (hold_state && intersection.height > 0) { + gint x = (gint) floor(pixwidth * current_peak); + + get_window()->draw_pixbuf (get_style()->get_fg_gc(get_state()), pixbuf, + x, intersection.y, + x, intersection.y, 3, intersection.height, Gdk::RGB_DITHER_NONE, 0, 0); - } - + */ + return true; } diff --git a/libs/gtkmm2ext/gtkmm2ext/fastmeter.h b/libs/gtkmm2ext/gtkmm2ext/fastmeter.h index c59e85b674..d624f29afb 100644 --- a/libs/gtkmm2ext/gtkmm2ext/fastmeter.h +++ b/libs/gtkmm2ext/gtkmm2ext/fastmeter.h @@ -46,23 +46,16 @@ class FastMeter : public Gtk::DrawingArea { long hold_count() { return hold_cnt; } void set_hold_count (long); - static void set_horizontal_xpm (std::string); - static void set_vertical_xpm (std::string); - protected: bool on_expose_event (GdkEventExpose*); void on_size_request (GtkRequisition*); + void on_size_allocate (Gtk::Allocation&); private: - static std::string h_image_path; - static std::string v_image_path; - static Glib::RefPtr h_pixbuf; - static gint h_pixheight; - static gint h_pixwidth; - static Glib::RefPtr v_pixbuf; - static gint v_pixheight; - static gint v_pixwidth; + Glib::RefPtr pixbuf; + gint pixheight; + gint pixwidth; Orientation orientation; GdkRectangle pixrect; @@ -76,6 +69,18 @@ class FastMeter : public Gtk::DrawingArea { bool vertical_expose (GdkEventExpose*); bool horizontal_expose (GdkEventExpose*); + + static Glib::RefPtr request_vertical_meter(int); + + static Glib::RefPtr *v_pixbuf_cache; + static int min_v_pixbuf_size; + static int max_v_pixbuf_size; + + static Glib::RefPtr request_horizontal_meter(int); + + static Glib::RefPtr *h_pixbuf_cache; + static int min_h_pixbuf_size; + static int max_h_pixbuf_size; }; diff --git a/libs/gtkmm2ext/gtkmm2ext/gtk_ui.h b/libs/gtkmm2ext/gtkmm2ext/gtk_ui.h index 5446374d7b..14af137680 100644 --- a/libs/gtkmm2ext/gtkmm2ext/gtk_ui.h +++ b/libs/gtkmm2ext/gtkmm2ext/gtk_ui.h @@ -36,11 +36,10 @@ #include #include #include -#include + #include #include #include -#include using std::string; using std::queue; diff --git a/libs/libsndfile/AUTHORS b/libs/libsndfile/AUTHORS new file mode 100644 index 0000000000..95770ab52d --- /dev/null +++ b/libs/libsndfile/AUTHORS @@ -0,0 +1,14 @@ +The main author of libsndfile is Erik de Castro Lopo . + +The code in the src/GSM610 directory was written by Jutta Degener + and Carsten Bormann . +They should not be contacted in relation to libsndfile or the GSM 6.10 code +that is part of libsndfile. Their original code can be found at: + + http://kbs.cs.tu-berlin.de/~jutta/toast.html + +Code in the src/G72x directory was released by Sun Microsystems, Inc. to the +public domain. Minor modifications were required to integrate these files +into libsndfile. The changes are listed in src/G72x/ChangeLog. + + diff --git a/libs/libsndfile/ChangeLog b/libs/libsndfile/ChangeLog new file mode 100644 index 0000000000..df89771c7a --- /dev/null +++ b/libs/libsndfile/ChangeLog @@ -0,0 +1,6107 @@ +2006-04-29 Erik de Castro Lopo + + * tests/util.tpl + Add function testing function exit_if_true(). + + * tests/floating_point_test.tpl + Fix a problem where the test program was not exiting when the test failed. + +2006-04-15 Erik de Castro Lopo + + * src/sndfile.h.in src/sndfile.c src/common.h src/command.c + Implement new commands SFC_GET_SIGNAL_MAX and SFC_GET_MAX_ALL_CHANNELS. + + * doc/commands.html + Document new commands. Other minor updates. + + * tests/peak_chunk_test.c + Update tests for new commands. + +2006-04-02 Erik de Castro Lopo + + * tests/peak_chunk_test.c + Add test for RIFX and WAVEX files. + Try and confuse the PEAK chunk writing by enabling and disabling it. + + * src/sndfile.c + Fix a bug where enabling and disabling PEAK chunk was screwing up. + +2006-03-31 Erik de Castro Lopo + + * src/sndfile.h.in + Add the block of 190 reserved bytes into this struct to allow for + future expansion. + + * src/wav.c src/sndfile.c src/broadcast.c + Significant cleanup of broadcast wave stuff. + + * examples/sndfile-info.c + Fix print message. + + * tests/command_test.c tests/Makefile.am + Complete bext tests, hook test in test suite. + +2006-03-30 Erik de Castro Lopo + + * src/sndfile.h.in + Make coding_history field of SF_BROADCAST_INFO struct a char array instead + of a char pointer. + + * src/sndfile.c src/common.h src/wav.c + Clean up knock on effects of above chnage. + + * examples/sndfile-info.c + Add -b command line option to usage message. + Clean up output of broadcast wave info. + + * src/wav.c + Ignore and skip the 'levl' chunk. + +2006-03-26 Erik de Castro Lopo + + * configure.ac + Fix handling of --enable and --disable configure args. Thanks to Diego + 'Flameeyes' Pettenò who sent the patch. + +2006-03-22 Erik de Castro Lopo + + * doc/win32.html + Make it really clear that although the MSVC++ cannot compile libsndfile, + the precompiled DLL can be used in C++ programs compiled with MSVC++. + +2006-03-18 Erik de Castro Lopo + + * src/aiff.c + Fix bug in writing of INST chunk in AIFF files. + Fix potential bug in writing MARK chunks. + + * src/sndfile.c + Make sure the instrument chunk can only be written at the start of the file. + + * tests/command_test.c + Add check of log buffer. + + * tests/utils.tpl + Add usage of space character to psf_binheader_writef. + +2006-03-17 Erik de Castro Lopo + + * src/Makefile.am tests/Makefile.am + Remove --source-time argument from autogen command lines. + + * src/broadcast.c + New file for EBU Broadcast chunk in WAV files. + + * src/sndfile.c src/sndfile.h.in src/wav.c src/common.h + Add patch from Paul Davis implementing read/write of the BEXT chunk. + +2006-03-16 Erik de Castro Lopo + + * Win32/README-precompiled-dll.txt + New file descibing how to use the precompiled DLL. + + * Win32/Makefile.am + Add Win32/README-precompiled-dll.txt to EXTRA_DIST files. + + * configure.ac + Bump version to 1.0.15. + +2006-03-11 Erik de Castro Lopo + + * src/wav.c + On read, only add the endian flag if the file is big endian. + + * src/ms_adpcm.c + Fixed writing of APDCM coeffs in RIFX files. + + * tests/write_read_test.tpl tests/lossy_comp_test.c + Add tests for RIFX files. + +2006-03-10 Erik de Castro Lopo + + * Mingw-make-dist.sh + Bunch of improvements. + + * doc/win32.html + Update MinGW program versions. + +2006-03-09 Erik de Castro Lopo + + * src/create_symbols_file.py + Fix the library name in created win32 DEF file. Add correct DLL name for + Cygwin DLL. + + * Win32/Makefile.am tests/Makefile.am + Remove redundant files, add win32_ordinal_test to test suite. + + * tests/win32_ordinal_test.c + Update to do test in cygsndfile-1.dll as well. + + * doc/win32.html + Fix typo, mention that -mno-cygwin with the Cygwin compiler does not work. + + * src/wav.c src/wav_w64.c src/sndfile.c src/sndfile.h.in + Apply large patch from Jesse Chappell which adds support for RIFX files. + +2006-03-08 Erik de Castro Lopo + + * Makefile.am + Add Mingw-make-dist.sh to the extra dist files. + + * configure.ac + Fix setting SHLIB_VERSION_ARG for MinGW. + + * tests/win32_ordinal_test.c + New test program to test that the win32 DLL ordinals agree with the DEF + file. + +2006-03-04 Erik de Castro Lopo + + * src/common.h + Add a static inline function to convert an int to a size_t. This will be + a compile to nothing on 32 bit CPUs and a sign extension on 64 bit CPUs. + + * src/aiff.c src/avr.c src/common.c src/xi.c src/gsm610.c + Fix an ia64 problem where a varargs function was being passed an int in + some places and a size_t in other places. + + * src/sd2.c + Add a workaround for situations where OSX seems to add an extra 0x52 bytes + to the start of the resource fork. + +2006-02-19 Erik de Castro Lopo + + * Mingw-make-dist.sh + Add a shell script to build the windows binary/source ZIP file. + + * doc/index.html + Add download link for windows binary/source ZIP file. Add links for GPG + signatures. + + * doc/win32.html + Remove info about building using microsoft compiler. + + * configure.ac + Bump version to 1.0.14. + +2006-02-11 Erik de Castro Lopo + + * src/sd2.c + Improve logging of errors in resource fork parser. + +2006-01-31 Erik de Castro Lopo + + * Win32/Makefile.msvc + Replace au_g72x.* with g72x.*. Thanks to ussell Borogove. + +2006-01-29 Erik de Castro Lopo + + * src/common.c + Make sure return values are initialised header buffer is full. + + * src/wav.c + Add workarounds for messed up WAV files. + +2006-01-21 Erik de Castro Lopo + + * Win32/config.h + Undef HAVE_INTTYPES_H for win32. + + * tests/command_test.c + Don't exit on error in instrument test for XI files. + + * configure.ac + Bump version to 1.0.13. + + * doc/*.html NEWS README + Update version numbers. + +2006-01-19 Erik de Castro Lopo + + * src/xi.c + Start work on add read/write of instrument chunks. + + * src/command_test.c + Add tests for XI instrument chunk. + + * tests/largefile_test.c tests/Makefile.am + Add new test and hook it into the build system. This test will not be run + automatically because it requires 3 Gig of disk space and takes 3 minutes + to run. + +2006-01-10 Erik de Castro Lopo + + * examples/sndfile-play.c + Fix calculation of samples remaining in win32 code. Thanks Axel Roebel. + + * src/common.h + Make sure length of header buffer can hold header plus strings. Thanks Axel + Roebel. + +2006-01-09 Erik de Castro Lopo + + * src/sndfile.h.in src/aiff.c src/wav.c + Apply a patch from John Fitch (Csound project). + Add detune field to SF_INSTRUMENT struct. + Add reading/writing instrument chunks to WAV files. + + * tests/command_test.c + Update SF_INSTRUMENT tests. + + * tests/Makefile.am + Hook instrument tests into test suite. + +2006-01-05 Erik de Castro Lopo + + * configure.ac + Check for because some broken systems (like Solaris) don't have + which is the 1999 ISO C standard file containing int64_t. + + * src/sfendian.h src/common.h + Use if is not available. + +2005-12-30 Erik de Castro Lopo + + * tests/peak_chunk_test.c + Extend and clean up tests. + + * src/sndfile.c + Fix a bug that prevented the turning off of PEAK chunks. + +2005-12-29 Erik de Castro Lopo + + * tests/error_test.c + Make the test distclean correct. + + * src/file_io.c + Fix an SD2 MacOSX bug (reported by vince schwarzinger). + +2005-12-28 Erik de Castro Lopo + + * src/aiff.c tests/command_test.c + Apply a big patch from John ffitch (Csound project) to add reading and + writing of instrument chunks to AIFF files. Also update the test. + +2005-12-10 Erik de Castro Lopo + + * tests/aiff_rw_test.c tests/virtual_io_test.c tests/utils.tpl + Move test function dump_data_to_file() to utils.tpl. + + * tests/error_test.c tests/Makefile.am + Updates, including a new test to test that sf_error() returns a valid error + number. + +2005-12-07 Erik de Castro Lopo + + * examples/list_formats.c + Make sure the SF_INFO struct is memset to all zero before being used. + Thanks to Stephen F. Booth. + + * src/sndfile.c + Make the return value of sf_error() match the API documentation. + +2005-11-19 Erik de Castro Lopo + + * examples/sndfile-convert.c + Allow conversion to raw gsm610. + + * src/common.h src/sndfile.c src/au.c + Remove au_nh_open() and all references to it (wasn't working anyway). + + * tests/headerless_test.c + Add new test for file extension based detection. + + * src/sndfile.c + Rejig file extension based file type detection. + +2005-11-16 Erik de Castro Lopo + + * src/sndfile.c + Add "gsm" as a recognised file extension when no magic number can be found. + + * tests/lossy_comp_test.c tests/Makefile.am + Test headerless GSM610. + +2005-11-13 Erik de Castro Lopo + + * doc/api.html + Fix a minor typo and a minor error. Thanks Christoph Kobe and John Pavel. + +2005-10-30 Erik de Castro Lopo + + * src/wav_w64.c + Add more reporting of 'fmt ' chunk for G721 encoded files. + + * src/wav.c + Gernerate a more correct 20 byte 'fmt ' chunk rather than a 16 byte one. + +2005-10-29 Erik de Castro Lopo + + * src/G72x/g72x.[ch] + Minor cleanup of interface. + +2005-10-28 Erik de Castro Lopo + + * src/ogg.c + Removed the horribly broken and non-functional OGG implementation when + --enable-experimental was enabled. When OGG does finally work it will be + merged. + + * src/caf.c + Fix a memory leak. + +2005-10-27 Erik de Castro Lopo + + * src/g72x.c src/G72x/*.(c|h) src/common.h src/sndfile.c src/wav.c src/au.c + Add support for G721 encoded WAV files. + + * doc/index.html + Update support matrix. + + * tests/lossy_comp_test.c + For file formats that support it, add string data after the audio data and + make sure it isn't treated as audio data on read. + + * src/gsm610.c + Add code to ensure that the container close function (ie for WAV files) gets + called after the codec's close function. This allows GSM610 encoded WAV files + to have string data following the audio data. + Add an AIFF specific check on psf->datalength. + + * src/wav.c + Simplify wav_close function. + + * src/aiff.c + Make sure the tailer data gets written at an even file offset. Pad if + necessary. + + * src/common.h + Replace the close function pointer in SF_PRIVATE with separate functions + codec_close and container_close. The former is always called first. + + * src/*.c + Fix knock on effects of above. + +2005-10-26 Erik de Castro Lopo + + * examples/sndfile-info.c + Complete dumping SF_INSTRUMENT data. + + * src/dwvw.c src/ima_adpcm.c src/gsm610.c src/ms_adpcm.c + Add extra checks in *_init function. + + * tests/lossy_comp_test.c + Add a string comment to the end of the files to make sure that the decoder + doesn't decode beyond the end of the audio data section. + +2005-10-25 Erik de Castro Lopo + + * examples/sndfile-info.c + Minor code cleanup. + Start work on dumping SF_INSTRUMENT data. + +2005-10-23 Erik de Castro Lopo + + * src/sndfile.h.in src/common.h src/common.c + Update definition of SF_INSTRUMENT struct and create a function to allocate + and initialize the struct (input from David Viens). + Clean up definition of SF_INSTRUMENT struct. + + * src/wav.c src/wav_w64.c + Add support for Ambisoncs B WAVEX files (David Viens). + + * src/aiff.c src/wav.c src/wav_w64.c + Start work on reading/writing the SF_INSTRUMENT data. + + * src/sndfile.c + Add code to get and set SF_INSTRUMENT data. + + * tests/command_test.* tests/Makefile.am + Add test for set and getof SF_INSTRUMENT data. + The file command_test.c is no longer autogen generated. + +2005-10-15 Erik de Castro Lopo + + * src/gsm610.c + Minor cleanup. + +2005-10-14 Erik de Castro Lopo + + * tests/lossy_comp_test.c + Minor cleanup. + +2005-10-13 Erik de Castro Lopo + + * src/*.c + Ensure sfconfig.h is included before any other header file. + + * src/file_io.c + Add comments documenting the three sections of the file. + + * src/gsm610.c + Make sure SF_FORMAT_WAVEX are handled correctly. + +2005-10-07 Erik de Castro Lopo + + * configure.ac + Add options to allow disabling of FLAC and ALSA. Suggested by Ben Greear. + +2005-09-30 Erik de Castro Lopo + + * tests/locale_test.c + Modify the way the unicode strings were encoded so that older compilers + do not complain. Thanks Axel Roebel. + + * configure.ac + Bump the version to 1.0.12 for release. + + * NEWS README Win32/config.h doc/(FAQ|index.html|command|api).html + Update version numbers. + +2005-09-26 Erik de Castro Lopo + + * src/flac.c + Fix valgrind error and minor cleanup. + +2005-09-25 Erik de Castro Lopo + + * src/(au|paf|aiff|w64|wav|svx).c + Make sure structs are initialised. + +2005-09-24 Erik de Castro Lopo + + * configure.ac + Make -Wdeclaration-after-statement work with --enable-gcc-werror configure + option. + Add -std=gnu99 (C99 plus posix style stuff like gmtime_r) to CFLAGS if the + compiler supports it. + +2005-09-23 Erik de Castro Lopo + + * configure.ac acinclude.m4 + Add -Wdeclaration-after-statement to CFLAGS if the compilers supports it. + +2005-09-22 Erik de Castro Lopo + + * tests/util.(tpl|def) + Make the test_write_*_or_die() functions const safe. + +2005-09-21 Erik de Castro Lopo + + * src/nist.c + Make sure the data offset is read from the file header. Thanks to + David A. van Leeuwen for a patch. + +2005-09-20 Erik de Castro Lopo + + * configure.ac src/sfconfig.h + Check for and the function setlocale(). + Set config variables to zero if not found. + + * tests/locale_test.c tests/Makefile.am + Add new test program and hook into build/test system. + +2005-09-18 Erik de Castro Lopo + + * src/common.h src/file_io.c + On windows, use windows specific types for file handles. + Add functions psf_init_files() and psf_use_rsrc(). + + * src/sd2.c + Make resource fork handling independant of file desciptor/handles. + + * src/sndfile.c src/test_file_io.c + Fix knock on effects. + +2005-09-06 Erik de Castro Lopo + + * src/float_cast.h + The lrint and lrintf implementations in Cygwin are both buggy and slow. + Add replacements which were pulled from the Public Domain MinGW math.h + header file. + +2005-09-05 Erik de Castro Lopo + + * tests/(lossy_comp_test|virtual_io_test).c + More Valgrind fixups. + + * configure.ac + Simplify and correct configuring for Cygwin. + + * Win32/config.h Win32/sndfile.h Win32/Makefile.msvc + Update build for MSVC. + +2005-09-04 Erik de Castro Lopo + + * tests/lossy_comp_test.c + Make sure to close SNDFILE when exiting test when file format is not seekable. + + * tests/(aiff_rw_test|virtual_io_test).c + Do a few valgrind fix ups. + +2005-09-03 Erik de Castro Lopo + + * src/float32.c src/double64.c + Replace floating point equality comparisons with greater/less comparisons. + Found by John Pavel using the Intel compiler. + + * src/sfconfig.h + New file to clean up issues surrounding autoconf generated preprocessor + symbols. + + * src/*.(c|h) tests/*.(c|tpl) examples/*.c + Fixed a bunch of other stuff found by John Pavel using the Intel compiler. + + * src/file_io.c + Remove Mac OS9 Metrowerks compiler specific hacks. + +2005-08-31 Erik de Castro Lopo + + * src/w64.c + Cast integer literal to sf_count_t in call to psf_binheader_writef() to + prevent Valgrind error. + +2005-08-30 Erik de Castro Lopo + + * doc/command.html + Improve documentation of SF_GET_FORMAT_SUBTYPE. + +2005-08-26 Erik de Castro Lopo + + * examples/sndfile-convert.c + Allow files to be converted to SD2 format. + + * src/sd2.c + Fix a bug in reading and writing of SD2 files on little endian CPUs. + Thanks to Matthew Willis for finding this. + +2005-08-25 Erik de Castro Lopo + + * doc/api.html + Update Note2 to point to SFC_SET_SCALE_FLOAT_INT_READ. + +2005-08-16 Erik de Castro Lopo + + * configure.ac + Use $host_os instead of $target_os (thanks to Mo De Jong). + +2005-08-15 Erik de Castro Lopo + + * src/Makefile.am + Apply a patch from Mo DeJong to allow building outside of the source dir. + + * src/file_io.c + Fix psf_fsync() for win32. + + * src/wav.c src/wav_w64.(c|h) + Move some code from wav.c to wav_w64.c to improve the log output of files of + type WAVE_FORMAT_EXTENSIBLE. + +2005-08-10 Erik de Castro Lopo + + * src/create_symbols_file.py + Make sure sf_write_fsync is an exported symbol. + + * examples/sndfile-convert.c + Add support for writing VOX adpcm files. + +2005-07-31 Erik de Castro Lopo + + * doc/api.html + Document the new function sf_write_sync(). + + * doc/FAQ.html + Do you plan to support XYZ codec. + +2005-07-28 Erik de Castro Lopo + + * src/sndfile.h.in src/sndfile.c + Add function sf_write_sync() to the API. + + * src/common.h src/file_io.c + Low level implementation (win32 not done yet). + + * tests/write_read_test.tpl + Use the new function in the tests. + +2005-07-24 Erik de Castro Lopo + + * src/common.h src/double64.c src/float32.c src/sndfile.c + Change the way PEAK chunk info is stored. Peaks now stored as an sf_count_t + for position and a double as the value. + + * src/aiff.c src/caf.c src/wav.c + Fix knock on effects of above changes. + + * src/caf.c + Implement 'peak' chunk for file wuth data in SF_FORMAT_FLOAT or + SF_FORMAT_DOUBLE format. + +2005-07-23 Erik de Castro Lopo + + * src/nist.c + Fix a bug where a variable was being used without being initialized. + + * src/flac.c + Add extra debug in sf_flac_meta_callback. + Make a bunch of private functions static. + + * src/aiff.c src/wav.c + Fix allocation for PEAK_CHUNK (bug found using valgrind). + +2005-07-21 Erik de Castro Lopo + + * src/common.h + Move the peak_loc field of SF_PRIVATE to the PEAK_CHUNK struct. + Remove had_peak field of SF_PRIVATE, use pchunk != NULL instead. + Rename PEAK_CHUNK and PEAK_POS to PEAK_CHUNK_32 and PEAK_POS_32. + + * src/aiff.c src/caf.c src/wav.c src/float32.c src/double64.c + Fix knock on effects from above. + +2005-07-19 Erik de Castro Lopo + + * src/wav.c + Prevent files with unknown chunks from being opened read/write. + +2005-07-14 Erik de Castro Lopo + + * src/flac.c + Do not use psf->end_of_file because it never gets set to anything. + + * src/common.h + Remove unused SF_PRIVATE field end_of_file. + +2005-07-12 Erik de Castro Lopo + + * src/common.c + Change the 'S' format specifier of psf_binheader_writef() to write AIFF + style strings (no terminating character). + + * src/aiff.c + Move to new (correct) AIFF string style. Thanks to Axel Roebel for being + so persistent on this issue. + +2005-07-11 Erik de Castro Lopo + + * src/sndfile.c + Allow SFE_UNSUPPORTED_FORMAT as an error from sf_open(). + + * doc/api.html doc/command.html + Documentation updates (thanks to Kyroz for promoting these updates). + + * src/mat5.c + Modify the way the header is written. + +2005-07-10 Erik de Castro Lopo + + * src/caf.c + Add a 'free' chunk to the written file so that the audio data starts at + an offset of 0x1000. + + * src/sndfile.c + Allow SFE_UNSUPPORTED_FORMAT as an error from sf_open(). + +2005-07-09 Erik de Castro Lopo + + * src/caf.c src/sndfile.c + Add support for signed 8 bit integers. + + * tests/write_read_test.tpl + Add test for signed 8 bit integers in CAF files. + + * doc/index.html + Update matrix for signed 8 bit integers in CAF files. + +2005-07-08 Erik de Castro Lopo + + * src/sndfile.c + Update sf_check_format() to support CAF. + + * examples/sndfile-convert.c + Add support for ".caf" file extension. + + * doc/index.html + Add Apple CAF to the support matrix. + + * src/caf.c + Add file write support. + + * src/common.c + Fix printing of Frames. + + * tests/Makefile.am tests/write_read_test.tpl tests/lossy_comp_test.c + tests/header_test.tpl misc_test.c + Add tests for CAF files. + +2005-07-07 Erik de Castro Lopo + + * doc/FAQ.html + Fix Q/A about reading/writing memory buffers. + + * src/caf.c + Bunch of work to support reading of CAF files. + +2005-07-04 Erik de Castro Lopo + + * src/(aiff|ima_adpcm|mat4|mat5|ms_adpcm).c examples/sndfile-play.c + Fix sign conversion errors reported by gcc-4.0. + + * src/caf.c + New file for Apple's Core Audio File format. + + * src/sndfile.c src/common.h src/sndfile.h.in src/Makefile.am + Hook new file into build system. + +2005-06-21 Erik de Castro Lopo + + * src_wav_w64.c + Fix handling of stupidly large 'fmt ' chunks. Thanks to Vadim Berezniker + for supplying an example file. + + * src/common.h src/sndfile.c + Remove redundant error code SFE_WAV_FMT_TOO_BIG. + +2005-06-20 Erik de Castro Lopo + + * src/sndfile.h.in src/common.h src/sndfile.c + Add public error value SF_ERR_MALFORMED_FILE. + + * src/sndfile.c + When parsing a file header fails and we don't have a system error, then set + the error number to SF_ERR_MALFORMED_FILE (suggested by Kyroz). + + * configure.ac + Allow sqlite support to be disabled in configure script. + + * regtest/database.c regtest/sndfile-regtest.c + Fix compiling when sqlite is missing. + +2005-06-11 Erik de Castro Lopo + + * src/file_io.c + Fix psf_is_pipe() and return value of psf_fread() when using virtual i/o. + + * src/sndfile.c + Fix VALIDATE_AND_ASSIGN_PSF macro for virtual i/o. + + * tests/virtual_io_test.c + Fill in skeleton test program. + + * tests/Makefile.am + Move virtual i/o tests to end of tests with stdio/pipe tests. + + * src/(sndfile.h.in|file_io.c|common.h|sndfile.c) tests/virtual_io_test.c + Rename some of the virtual i/o functions and data types. + +2005-06-10 Erik de Castro Lopo + + * src/sndfile.c + Fix the return values of sf_commands : SFC_SET_NORM_DOUBLE, + SFC_SET_NORM_FLOAT, SFC_GET_LIB_VERSION and SFC_GET_LOG_INFO. Thanks to + Kyroz for pointing out these errors. + + * doc/command.html + Correct documented return values for SFC_SET_NORM_DOUBLE and + SFC_SET_NORM_FLOAT. Thanks to Kyroz again. + +2005-05-17 Erik de Castro Lopo + + * regtest/* + Add new files for sndfile-regtest program. + + * configure.ac Makefile.am + Hook regetest into build. + + * src/wav.c src/common.c + Fix a regression where long ICMT chunks were causing the WAV parser + to exit. + +2005-05-15 Erik de Castro Lopo + + * libsndfile.spec.in + Add html docs to the files section as suggested by Karsten Jeppesen. + + * src/aiff.c + Fix parsing of odd length ANNO chunks. + +2005-05-13 Erik de Castro Lopo + + * src/common.h + Change the include guard to prevent clashes with other code. + +2005-05-12 Erik de Castro Lopo + + * examples/sndfile-play.c + Improve error handling in code for playback under Linux/ALSA. + +2005-05-10 Erik de Castro Lopo + + * src/ircam.c + Fix writing of IRCAM files on big endian systems (thanks to Axel Roebel). + + * src/wav.c + Add workaround for files created by the Peak audio editor on Mac which can + produce files with very short LIST chunks (thanks to Jonathan Segel who + supplied the file). + +2005-04-30 Erik de Castro Lopo + + * src/aiff.c + Apply a patch From David Viens to make the parsing of basc chunks more + robust. + + * src/wav.c + Another patch from David Viens to write correct wavex channel masks for + the most common channel configurations. + +2005-04-08 Erik de Castro Lopo + + * src/command.c + Only allow FLAC in the format arrays if FLAC is enabled. Thanks to + Leigh Smith. + +2005-03-09 Erik de Castro Lopo + + * src/common.h + Add a directory field for storing the file directory to the SF_PRIVATE + struct. + + * src/sndfile.c + Grab the directory name when copying the file path. + + * src/file_io.c + Cleanup psf_open_rsrc() and also check for resource fork in + .AppleDouble/filename. + +2005-03-01 Erik de Castro Lopo + + * src/svx.c + Fix a bug in the printing of the channel count. Bug reported by Michael + Schwendt. Thanks. + +2005-01-26 Erik de Castro Lopo + + * src/paf.c + Fix a seek bug for 24 bit PAF files. + + * tests/write_read_test.tpl + Update write_read_test to trigger the previously hidden PAF seek bug. + +2005-01-25 Erik de Castro Lopo + + * src/aiff.c src/w64.c src/wav.c + Do not return a header parse error when the log buffer overflows. + Continuing parsing works even on files where the log buffer does overflow. + This avoids a bug on some weirdo WAV (and other) files. + + * src/common.h src/sndfile.c + Remove SFE_LOG_OVERRIN error and its associated error message. + + * src/file_io.c + Fix a rsrc fork problem on MacOSX. + +2004-12-31 Erik de Castro Lopo + + * src/sndfile-play.c + In the ALSA output code, added call to snd_pcm_drain() just before + snd_pcm_close() as suggested by Thomas Kaeding. + In the OSS output code, added two ioctls (SNDCTL_DSP_POST and + SNDCTL_DSP_SYNC) just before the close of the audio device. + + * tests/virtual_io_test.c tests/Makefile.am + Add a new test program (currently empty) and add it to the build. + +2004-12-29 Erik de Castro Lopo + + * src/sndfile.h.in src/sndfile.h src/common.h src/file_io.c + src/create_symbols_file.py + Apply patch from Steve Baker which is the beginnings of a virtual + I/O interface. + +2004-12-23 Erik de Castro Lopo + + * src/*.c src/sndfile.h.in + Const-ify the write path throughout the library. + +2004-12-14 Erik de Castro Lopo + + * doc/development.html + Minor improvements. + +2004-11-29 Erik de Castro Lopo + + * doc/bugs.html + Minor improvements. + +2004-11-18 Erik de Castro Lopo + + * src/aiff.c + Add workaround for Logic Platinum AIFF files with broken COMT chunks. + +2004-11-16 Erik de Castro Lopo + + * doc/FAQ.html + Remove some ambiguities in the SD2 FAQ answer. + +2004-11-15 Erik de Castro Lopo + + * Win32/sndfile.h Win32/config.h MacOS9/sndfile.h MacOS9/config.h + Updates from autoconfig versions. + +2004-11-13 Erik de Castro Lopo + + * src/aiff.c + Fix parsing of COMT chunks. Store SF_STR_COMMENT data in ANNO chunks + instead of COMT chunk. + +2004-11-07 Erik de Castro Lopo + + * src/file_io.c src/common.h + Change the ptr argument to psf_write() from "void*" to a "const void*". + Thanks to Tobias Gehrig for suggesting this. + +2004-10-31 Erik de Castro Lopo + + * src/file_io.c src/common.h + Add functions psf_close_rsrc() and read length of resourse fork into + rsrclength field of SF_PRIVATE. + + * src/sd2.c + Make sure resource fork gets closed. + + * tests/util.tpl + Add functions to check for file descriptor leakage. + + * src/write_read_test.tpl + Use the file descriptor leak checks. + + * src/sndfile.h.in + Add SFC_GET_LOOP_INFO and SF_LOOP_INFO struct. + + * src/common.h + Add SF_LOOP_INFO pointer to SF_PRIVATE. + + * src/wav.c src/aiff.c + Improve and add parsing of 'ACID' and 'basc' chunks, filling in + SF_LOOP_INFO data in SF_PRIVATE. + +2004-10-30 Erik de Castro Lopo + + * src/sd2.c + Further cleanup: remove printfs, change snprintf to LSF_SNPRINTF. + + * Win32/config.h Win32/sndfile.h + Updates. + + * tests/util.tpl + Add win32 macro for snprintf. + +2004-10-29 Erik de Castro Lopo + + * src/sfendian.h + Add macros : H2BE_SHORT, H2BE_INT, H2LE_SHORT and H2LE_INT. + + * src/sd2.c + Use macros to make sure writing SD2 files on little endian machines works + correctly. + + * tests/util.tpl + Add a delete_file() function which also deletes the resource fork of SD2 + files. + + * tests/write_read_test.tpl + Use delete_file() so that "make distcheck" works. + +2004-10-28 Erik de Castro Lopo + + * src/sndfile.c src/file_io.c + Move resource filename construction and testing to psf_open_rsrc(). + + * src/common.h src/sndfile.c + Add error SFE_SD2_FD_DISALLOWED. + + * tests/util.tpl tests/*.(c|tpl) + Add and allow_fd parameter to test_open_file_or_die() so that use of + sf_open_fd() can be avoided when opening SD2 files. + +2004-10-27 Erik de Castro Lopo + + * src/wav.c + Update ACID chunk parsing. + + * src/sd2.c + More fixes for files with large resource forks. + +2004-10-23 Erik de Castro Lopo + + * src/common.h src/sndfile.c + Add error numbers and messages for sd2 files. + + * src/sd2.c + Reading of sd2 (resource fork version) now seems to be working. + +2004-10-17 Erik de Castro Lopo + + * src/file_io.h + Update file_io.c to include win32 psf_rsrc_open(). + + * tests/floating_point_test.tpl + Remove use of __func__ in test programs (MSVC++ doesn't grok this). + + * Win32/(config|sndfile).h MacOS9/(config|sndfile).h + Updates. + +2004-10-13 Erik de Castro Lopo + + * src/sfendian.h + Fix endswap_int64_t_(array|copy). + + * src/test_endswap.(tpl|def) + Add tests for above and inprove all tests. + +2004-10-12 Erik de Castro Lopo + + * src/sfendian.h + Improve type safety, add endswap_double_array(). + + * src/double64.c + Use endswap_double_array() instead of endswap_long_array(). + + * src/test_endswap.(tpl|def) src/Makefile.am + Add preliminary endswap tests and hook into build system. + +2004-10-06 Erik de Castro Lopo + + * src/configure.ac src/makefile.am + Finally fix the bulding of DLLs on Win32/MinGW. + + * tests/makefile.am + Fix running of tests on Win32/MinGW. + +2004-10-01 Erik de Castro Lopo + + * src/sndfile.h.in src/sndfile.c tests/floating_point_test.tpl + Rename SFC_SET_FLOAT_INT_MULTIPLIER to SFC_SET_SCALE_FLOAT_INT_READ. + + * doc/command.html + Document SFC_SET_SCALE_FLOAT_INT_READ. + +2004-09-30 Erik de Castro Lopo + + * tests/floating_point_test.(tpl|def) + Derived from floating_point_test.c. + Add (float|double)_(short|int)_test functions. + + * tests/util.(tpl|def) + Make separate float and double versions of gen_windowed_sine(). + + * tests/write_read_test.tpl + Fix after changes to gen_windowed_sine(). + + * src/(float32|double64).c + Implement SFC_SET_FLOAT_INT_MULTIPPLIER. + +2004-09-29 Erik de Castro Lopo + + * acinclude.m4 + Fix warnings from automake 1.8 and later. + + * examples/sndfile-info.c + Add a "fflush (stdout)" after printing Win32 message. + +2004-09-28 Erik de Castro Lopo + + * Win32/Makefile.mingw.in + Add a "make install" target. + +2004-09-24 Erik de Castro Lopo + + * src/sndfile.h.in src/common.h src/sndfile.c src/command.c + Start work on adding command SFC_SET_FLOAT_INT_MULTIPLIER. + +2004-09-22 Erik de Castro Lopo + + * examples/sndfile-convert.c + Fix a bug converting stereo integer PCM files to float. + +2004-09-22 Erik de Castro Lopo + + * examples/sndfile-play.c + Appy patch from Conrad Parker to make Mac OSX error messages more + consistent and informative. + + * doc/api.html + Fix a HTML HREF which was wrong. + + * doc/win32.html + Add information about when nmake fails. + +2004-09-05 Erik de Castro Lopo + + * examples/sndfile-play.c + Another patch from Denis Cote to prevent race conditions. + +2004-09-02 Erik de Castro Lopo + + * src/common.h src/ms_adpcm.c src/ima_adpcm.c + Fix alternative to ISO standard flexible struct array feature for broken + compilers. + +2004-08-31 Erik de Castro Lopo + + * src/common.h src/string.c src/sndfile.c + Make sf_set_string() return an error if trying to set a string when in + read mode. + +2004-08-29 Erik de Castro Lopo + + * src/common.h + Change the unnamed union into a named union so gcc-2.95 will compile it. + + * src/*.c + Fixes to allow for the above change. + +2004-08-20 Erik de Castro Lopo + + * examples/sndfile-play.c + Fixes for Win32. Thanks to Denis Cote. + + * Win32/Win32/Makefile.(msvc|mingw.in) + Fix build system after removal of sfendian.h. + Build sndfile-convert. + + * src/Makefile.am + Remove sfendian.c from dependancies. + +2004-08-10 Erik de Castro Lopo + + * src/sndfile.h.in + Fix typo in comments (thanks Tommi Sakari Uimonen). + +2004-07-31 Erik de Castro Lopo + + * tests/(a|u)law_test.c + Minor cleanup. + +2004-07-29 Erik de Castro Lopo + + * src/(pcm|float|double64|ulaw|alaw|xi).c + Optimise read/write loops by removing a redundant variable. + +2004-07-24 Erik de Castro Lopo + + * src/file_io.c + Remove call to fsync() in psf_close(). + +2004-07-19 Erik de Castro Lopo + + * src/pcm.c + Inline x2y_array() functions where possible. + + * configure.ac + Detect presence of type int64_t. + + * src/sfendian.c src/sfendian.h + Move functions in the first file to the sfendian.h as static inline + functions. + Improve endswap_long_*() where possible. + +2004-07-17 Erik de Castro Lopo + + * src/pcm.c + When converting from unsigned char to float or double, subtract 128 before + converting to float/double rather than after to save a floating point + operation as suggested by Stefan Briesenick. + + * src/(pcm|sfendian|alaw|ulaw|double64|float32).c + Optimize inner loops by changing the loop counting slightly as suggested + by Stefan Briesenick. + + * configure.ac + Detect presence of . + + * src/sfendian.h + Use if present as suggested by Stefan Briesenick. + + * src/pcm.c + Update bytewapping. + +2004-07-02 Erik de Castro Lopo + + * src/common.h src/*.c + Change the psf->buffer field of SF_PRIVATE into a more type safe union with + double, float, int etc elements. + +2004-06-28 Erik de Castro Lopo + + * examples/sndfile-play.c + Merge slightly modifed patch from Stanko Juzbasic which allows playback of + mono files on MacOSX. + +2004-06-25 Erik de Castro Lopo + + * examples/sndfile-convert.c + Move copy_metadata() after the second sf_open(). + +2004-06-21 Erik de Castro Lopo + + * examples/sndfile-convert.c + Fix a bug which caused the program to go into an infinite loop if the source + file has no meta-data. Thanks to Ron Parker for reporting this. + + * src/sndfile.h.in + Add SF_STR_FIRST and SF_STR_LAST to allow enumeration of string types. + + * Win32/sndfile.h MacOS9/sndfile.h + Update these as per the above file. + +2004-06-17 Erik de Castro Lopo + + * configure.ac src/common.h src/ogg.c src/sndfile.c src/sndfile.h.in + src/Makefile.am + Apply large patch from Conrad Parker implementing Ogg Vorbis, Ogg Speex and + Annodex support via liboggz and libfishsound. Thanks Conrad. + +2004-06-15 Erik de Castro Lopo + + * src/avr.c src/ircam.c src/nist.c src/paf.c src/xi.c + Add cast to size_t for some parameters passed to psf_binheader_writef. This + is Debian bug number 253490. Thanks to Anand Kumria and Andreas Jochens. + + * src/w64.c + Found and fixed a bug resulting from use of size_t when writing W64 'fmt ' + chunk. + +2004-06-14 Erik de Castro Lopo + + * configure.ac + Bump version to 1.0.10 ready for release. + + * Makefile.am + Remove redundant files (check_libsndfile.py libsndfile_version_convert.py) + from distribution tarball. + + * tests/header_test.tpl + Fix uninitialised variable. + + * src/GSM610/short_term.c + Fix compiler warning on MSVC++. + +2004-05-23 Erik de Castro Lopo + + * src/wav.c + Improve record keeping of chunks seen and return an error if a file with + unusual chunks is opened in mode SFM_RDWR. + + * src/mmreg.h + This file not needed so remove it. + +2004-05-22 Erik de Castro Lopo + + * tests/header_test.tpl + Add extra_header_test(). + + * src/common.h src/sndfile.c + Add SFE_RDWR_BAD_HEADER error number and string. + +2004-05-21 Erik de Castro Lopo + + * tests/utils.tpl tests/*.c tests/*.tpl + Add a line number argument to check_log_buffer_or_die() and update all + files that use that function. + + * tests/header_test.tpl + Modify/update tests for files opened SFM_RDWR and SFC_UPDATE_HEADER_AUTO. + + * src/aiff.c src/wav.c + Fix another bug in AIFF and WAV files opened in SFM_RDWR and using + SFC_UPDATE_HEADER_AUTO. + + * src/test_file_io.c + Add a test for psf_ftruncate() function. + +2004-05-19 Erik de Castro Lopo + + * src/sndfile.c + Fix another weird corner case bug found by Martin Rumori. Thanks. + + * tests/header_test.(tpl|def) + Two new files to test for the absence of the above bug and include tests + moved from tests/misc_test.c. + + * tests/Makefile.am + Hook new tests into build/test system. + + * tests/misc_test.c + Remove update_header_test() which has been moved to the new files above. + +2004-05-16 Erik de Castro Lopo + + * src/aiff.c + Fixed a bug reported by Martin Rumori on the LAD list. If a file created + with a format of SF_FORMAT_FLOAT and then closed before any data is written + to it, the header can get screwed up (PEAK chunk gets overwritten). + + * tests/write_read_test.tpl + Add a test (empty_file_test) for the above bug. + +2004-05-13 Erik de Castro Lopo + + * Win32/Makefile.mingw.in + Added a Makefile for MinGW (needs to be processed by configure). + + * src/mmsystem.h src/mmreg.h + Add files from the Wine project (under the LGPL) to allow build of + sndfile-play.exe under MinGW. + +2004-05-12 Erik de Castro Lopo + + * src/GSM610/gsm610_priv.h + Replace ugly macros with inline functions. + + * src/GSM610/*.c + Remove temporary variables used by macros and other minor fixes required by + above change. + +2004-05-10 Erik de Castro Lopo + + * tests/pipe_test.tpl tests/stdio_test.c Win32/Makefile.msvc + Make sure these programs compile (even though they do nothing) on Win32 + and add them to the "make check" target. + + * src/sfendian.h + Fix warning on Sparc CPU and code cleanup. + +2004-05-09 Erik de Castro Lopo + + * src/file_io.c + Fix warning messages when compiling under MinGW. + +2004-05-01 Erik de Castro Lopo + + * configure.ac + Set HAVE_FLEXIBLE_ARRAY in src/config.h depending on whether the compiler + accepts the flexible array struct member as per 1999 ISO C standard. + + * src/common.h src/ima_adpcm.c src/paf.c src/ms_adpcm.c + Added ugly #if HAVE_FLEXIBLE_ARRAY and provided a non-standards compliant + hack for non 1999 ISO C compliant compilers. + +2004-04-26 Erik de Castro Lopo + + * src/strings.c + If adding an SF_STR_SOFTWARE string, only append libsndfile-X.Y.Z if the + string does not already have libsndfile in the string. Thanks to Conrad + Parker. + + * tests/string_test.c + Add test to verify the above. + + * examples/sndfile-convert.c + Add ability to transcode meta data as well (Conrad Parker). + +2004-04-25 Erik de Castro Lopo + + * doc/command.html + Fix minor error. Thanks to Simon Burton. + + * doc/win32.html + Started adding instructions for compiling libsndfile under MinGW. + + * configure.ac + Add --enable-bow-docs to enable black text on a white background HTML docs. + + * doc/libsndfile.css.in + This is now a template file for configure which sets the foreground and + background colours. + +2004-04-20 Erik de Castro Lopo + + * configure.ac + Do some MinGW fixes. + + * configure.ac doc/Makefile.am + Install HTML docs when doing make install. + +2004-04-19 Erik de Castro Lopo + + * examples/sndfile-info.c + Print out the dB level with the signal max. + +2004-04-15 Erik de Castro Lopo + + * src/file_io.c + Define S_ISSOCK in src/file_io.c if required. + +2004-04-03 Erik de Castro Lopo + + * configure.ac + Improve printout configuration summary (as suggested by Axel Röbel). + + * doc/index.html + Add link to pre-release location. + + * src/sndfile.h.in + Remove comma after last element of enum. + + * src/float32.c src/double64.c + Fix read/write of float/double encoded raw files to/from pipes. + + * tests/pipe_test.c tests/pipe_test.tpl tests/pipe_test.def + Turn pipe_test.c into an autogenerated file and add tests for reading/ + writing floats and doubles. + + * tests/Makefile.am + Hook tests/pipe_test.* into build system. + +2004-04-02 Erik de Castro Lopo + + * configure.ac acinclude.m4 + Rename AC_C_STRUCT_HACK macro to AC_C99_FLEXIBLE_ARRAY. + +2004-03-31 Erik de Castro Lopo + + * tests/misc_test.c + Perform update_header_test in RDWR mode as well. + + * src/aiff.c + Fix problems when updating header in RDWR mode. + +2004-03-30 Erik de Castro Lopo + + * src/wav.c src/w64.c src/wav_w64.c + Integrate code supplied by David Viens for supporting microsoft's + WAVEFORMATEXTENSIBLE stuff. Thanks David for supplying this. + + * configure.ac doc/*.html + Bump version to 1.0.9. + +2004-03-28 Erik de Castro Lopo + + * src/command.c src/sndfile.c src/sndfile.h.in src/wav.c + Started work on supporting microsoft's WAVEFORMATEXTENSIBLE gunk. + +2004-03-26 Erik de Castro Lopo + + * src/avr.c + New file to handle Audio Visual Resaerch files. + + * src/sndfile.h.in src/common.h src/sndfile.c src/command.c + Hook AVR into everything else. + + * tests/Makefile.am tests/write_read_test.tpl tests/misc_test.c + Add testing for AVR files. + +2004-03-22 Erik de Castro Lopo + + * src/file_io.c + Fix psf_set_file() for win32. Thanks to Vincent Trussart (Plogue Art et + Technologie) for coming up with the solution. + +2004-03-21 Erik de Castro Lopo + + * tests/write_read_test.tpl + Fixed a bug that was causing valgrind to report a memory leak. The bug was + in the test code itself, not the library. + +2004-03-20 Erik de Castro Lopo + + * examples/generate.cs + An example showing how to use libsndfile from C#. Thanks to James Robson + for providing this. + +2004-03-19 Erik de Castro Lopo + + * src/common.c + Fix problems with WAV files containing large chunks after the 'data' + chunk. Thanks to Koen Tanghe for providing a sample file. + +2004-03-17 Erik de Castro Lopo + + * configure.ac + Detect presense of ALSA (Advanced Linux Sound Architecture). + + * examples/sndfile-play.c + Add ALSA output support. + + * examples/Makefile.am + Add ALSA_LIBS to link line of sndfile-play.c. + +2004-03-15 Erik de Castro Lopo + + * acinclude.m4 + Add new macro (AC_C_STRUCT_HACK) to detect whether the C compiler allows + the use of the what is known as the struct hack introduced by the 1999 ISO + C Standard. + + * configure.ac + The last release would not compile with gcc-2.95 due to the use of features + (ie struct hack) introduced by the 1999 ISO C Standard. + Add check to make sure compiler handles this and bomb out if it doesn't. + +2004-03-14 Erik de Castro Lopo + + * tests/write_read_test.tpl + Fix compiler warning on Win32. + + * src/file_io.c + Fix use of an un-initialised variable in Win32 stuff. + + * Win32/config.h examples/sndfile-play.c + Win32 fixes. + +2004-03-10 Erik de Castro Lopo + + * configure.ac + Fix bug which occurres when configuring for MinGW. + If compiler is gcc and cross compiling use -nostdinc. + +2004-03-09 Erik de Castro Lopo + + * src/common.h src/aiff.c src/wav.c src/float32.c src/double64.c + src/sndfile.c + Fix a bug with PEAK chunk handling for files with more than 16 channels. + Thanks to Remy Bruno for finding this. + +2004-03-08 Erik de Castro Lopo + + * src/common.c + Fix a bug which was preventing WAV files being openned correctly if the + file had a very large header. Thanks to Eldad Zack for finding this. + +2004-03-04 Erik de Castro Lopo + + * configure.ac src/file_io.c + Fix cross-compiling from Linux to Win32 using the MinGW tools. + +2004-03-01 Erik de Castro Lopo + + * src/create_symbols_file.sh + Christian Weisgerber pointed out that the shell script did not run on a + real Bourne shell although it did run under Bash in Bourne shell mode. + + * src/create_symbols_file.py + Rewrite of above in Python. Also add support for writing Win32 .def files. + The Python script generates Symbols.linux, Symbols.darwin and + libsndfile.def (Win32 version). These files get shipped with the tarball + so there should not be necessary to run the Python script when building + the code from the tarball. + + * configure.ac src/Makefile.am Win32/Makefile.am + Hook new Python script into the build system. + +2004-02-25 Erik de Castro Lopo + + * src/configure.ac + Add --enable-gcc-werror option and move GCC specific stuff down. + +2004-02-24 Erik de Castro Lopo + + * acinclude.m4 configure.ac + Fix clip mode detection (tested in one of HP's testdrive Itanium II boxes). + + * src/file_io.c + Added check for sizeof (off_t) != sizeof (sf_count_t) to prevent recurrence + of missing large file support on Linux and Solaris. + +2004-02-19 Erik de Castro Lopo + + * examples/sndfile-play.c + Fix a MacOSX specific bug which was caused by a space being inserted in + the middle of a file name. + + * configure.ac src/Makefile.am examples/Makefile.am + Fix a couple of MacOSX build issues. + +2004-02-17 Erik de Castro Lopo + + * doc/command.html + Document SFC_SET_CLIPPING and SFC_GET_CLIPPING. + +2004-02-14 Erik de Castro Lopo + + * doc/*.html + Applied patch from Frank Neumann (author of lakai) which fixes many minor + typos in documentation. Thanks Frank. + +2004-02-13 Erik de Castro Lopo + + * ChangeLog + Changed my email address throughout source and docs. + +2004-02-08 Erik de Castro Lopo + + * src/file_io.c + Make sure config.h is included before stdio.h to make sure large file + support is enabled on Linux (and Solaris). + + * tests/misc_test.c + Disable update_header test on Win32. This should work but doesn't and + I'm not sure why. + + * Make.bat Win32/Makefile.msvc + Updates. + +2004-01-07 Erik de Castro Lopo + + * src/common.h + Changed logindex, headindex and headend files of SF_PRIVATE from unsigned + int to int to prevent weird arithmetic bugs. + + * src/common.c src/aiff.c src/wav.c src/w64.c + Fixed compiler warnings resulting from above change. + +2004-01-06 Erik de Castro Lopo + + * src/common.c + Fixed a bug in header reader for some files with data after the sample data. + +2003-12-29 Erik de Castro Lopo + + * tests/lossy_comp_test.c tests/Makefile.am + Add tests for AIFF/IMA files. + +2003-12-26 Erik de Castro Lopo + + * src/macbinary3.c src/macos.c + Two new files required for handling SD2 files. + + * src/common.h + Add prototypes for functions in above two files. + + * src/Makefile.am + Hook new files into build system. + +2003-12-21 Erik de Castro Lopo + + * configure.ac + Add checks for mmap() and getpagesize() which might be used at some time + for faster file reads. + Add detection of MacOSX. + +2003-12-13 Erik de Castro Lopo + + * doc/FAQ.html + Minor mods to pkg-config section. + +2003-12-12 Erik de Castro Lopo + + * src/create_symbols_file.sh + Andre Pang (also known as Ozone) pointed out that on MacOSX, all non + static symbols are exported causing troubles when trying to link + libsndfile with another library which has any of the same symbols. + He fixed this by supplying the MacOSX linker with a file containing + all the public symbols so that only they would be exported and then + supplied a patch for libsndfile. + This wasn't quite ideal, because I would have to maintain two (3 if + you include Win32) separate files containing the exported symbols. + A better solution was to create this script which can generate a + Symbols file for Linux, MacoSX and any other OS that supports + minimising the number of exported symbols. + + * configure.ac src/Makefile.am + Hook the new script into the build process. + +2003-12-10 Erik de Castro Lopo + + * doc/index.html + Added comments about Steve Dekorte's SoundConverter scam. + +2003-12-07 Erik de Castro Lopo + + * src/file_io.c + Axel Roebel pointed out that on Mac OSX a pipe is not considered a fifo + (S_ISFIFO (st.st_mode) is false) but a socket (S_ISSOCK (st.st_mode) is + true). The test has therefore been changed to is S_ISREG and anything + which which does not return true for S_ISREG is considered a pipe. + +2003-11-25 Erik de Castro Lopo + + * tests/misc_test.c + Fix update_header_test to pass SDS. + + * src/sds.c + More minor fixes. + + * tests/floating_point_test.c + Add test for SDS files. + + * src/command.c + Add SDS to major_formats array. + +2003-11-24 Erik de Castro Lopo + + * tests/write_read_test.tpl tests/misc_test.c + Add tests for SDS files. + + * src/sds.c + Fix a bug in header update code. + +2003-11-23 Erik de Castro Lopo + + * src/sds.c + Get file write working. + + * src/paf.c + Fix a potential bug in paf24_seek(). + +2003-11-04 Erik de Castro Lopo + + * doc/FAQ.html + Add Q/A about u-law encoded WAV files. + + * Win32/*.h + Updated so it compiles on Win32. + +2003-11-03 Erik de Castro Lopo + + * examples/sndfile-convert.c + Add -alaw and -ulaw command line arguments. + + * configure.ac + Add library versioning comments. + Add arguments to AC_INIT. + +2003-10-28 Erik de Castro Lopo + + * src/file_io.c + Ross Bencina has contributed code to replace all of the (mostly broken) + Win32 POSIX emulation calls with calls the native Win32 file I/O API. + This code still needs testing but is likely to be a huge improvemnt + of support for Win32. Thanks Ross. + +2003-10-27 Erik de Castro Lopo + + * src/dwvw.c + Removed filedes field from the DWVW_PRIVATE struct. + + * src/file_io.c + Change psf_fopen() so it returns psf->error instead of the file descriptor. + Add new functions psf_set_stdio() and psf_set_file(). + + * src/sndfile.c + Change these to work with changed psf_fopen() return value. + Remove all uses of psf->filedes from sndfile, making it easier to slot native + Win32 API file handling functions. + + * src/test_file_io.c + Minor changes to make it compile with new file_io.c stuff. + +2003-10-26 Erik de Castro Lopo + + * src/gsm610.h + Rename a variable from true to true_flag. As Ross Bencina points out, + true is defined in the C99 header . + + * src/file_io.c + If fstat() fails, return SF_TRUE instead of -1 (Ross Bencina). + +2003-10-09 Erik de Castro Lopo + + * src/common.h + Increase the size of SF_BUFFER_LEN and SF_HEADER_LEN. + + * src/sndfile.c + Fix sf_read/write_raw which were dividing by psf->bytwidth and + psf->blockwidth which can both be zero. + + * examples/sndfile-info.c + Increase size of BUFFER_LEN. + +2003-09-21 Erik de Castro Lopo + + * configure.ac + Add checks for and ssize_t. + Other Win32/MinGW checks. + + * src/aiff.c src/au_g72x.c src/file_io.c src/gsm610.c src/interleave.c + src/paf.c src/sds.c src/svx.c src/voc.c src/w64.c src/wav.c src/xi.c + Fix compiler warnings. + +2003-09-20 Erik de Castro Lopo + + * tests/scale_clip_test.tpl + Add definition of M_PI if needed. + +2003-09-19 Erik de Castro Lopo + + * configure.ac + Detect if S_IRGRP is declared in . + + * src/file_io.c tests/*.tpl tests/*.c + More fixes for Win32/MSVC++ and MinGW. MinGW does have but that + file doesn't declare S_IRGRP. + +2003-10-18 Erik de Castro Lopo + + * src/config.h.in + Add comment stating that the sf_count_t typedef is determined when + libsndfile is being compiled. + + * tests/utils.tpl + Modified so that utils.c gets one copy of the GPL and not two. + + +2003-09-17 Erik de Castro Lopo + + * Win32/unistd.h src/sf_unistd.h + Move first file to the second. This will help for Win32/MSVC++ and MinGW. + + * Win32/Makefile.am src/Makefile.am + Changed in line with above. + + * Win32/Makefile.msvc + Removed "/I Win32" which is no longer required. + + * src/file_io.c src/test_file_io.c tests/*.tpl tests/*.c + If HAVE_UNISTD_H include else include . This should + work for Win32, MinGW and other fakes Unix-like OSes. + + * src/*.c + Removed #include from files which didn't need it. + +2003-09-16 Erik de Castro Lopo + + * libsndfile.spec.in + Apply fix from Andrew Schultz. + +2003-09-07 Erik de Castro Lopo + + * src/vox_adpcm.c + Only set psf->sf.samplerate if the existing value is invalid. + +2003-09-06 Erik de Castro Lopo + + * examples/sndfile-play.c + Started adding support for ALSA output. + +2003-09-04 Erik de Castro Lopo + + * src/sndfile.h.in + Removed from sndfile.h. + + * src/*.c examples/*.c tests/*.c tests/*.tpl + Added where needed. + +2003-09-02 Erik de Castro Lopo + + * src/common.h + Added ARRAY_LEN, SF_MAX and SF_MIN macros. + +2003-08-19 Erik de Castro Lopo + + * doc/index.html + Remove statements about alternative licensing arrangements. + +2003-08-17 Erik de Castro Lopo + + * MacOS MacOS9 Makefile.am configure.ac + Change directory name from MacOS to MacOS9 + + * MacOS9/MacOS9-readme.txt + Change name to make it really obvious, add text to top of file to make it + still more obvious again. + +2003-08-16 Erik de Castro Lopo + + * src/test_log_printf.c + Add tests for %u conversions. + + * src/common.c + Fix psf_log_printf() %u conversions. + +2003-08-15 Erik de Castro Lopo + + * src/aiff.c + Fixed a bug where opening a file with a non-trival header in SFM_RDWR mode + would over-write part of the header. Thanks to Axel Roebel for pointing + this out. Axel also provided a patch to fix this but I came up with a + neater and more general solution. + Return error when openning an AIFF file with data after the SSND chunk + (Thanks Axel Roebel). + + * tests/aiff_rw_test.c + Improvements to test program which will later allow it to be generalised to + test WAV, SVX and others as required. + +2003-08-14 Erik de Castro Lopo + + * tests/pipe_test.c + Add useek_pipe_rw_test() submitted by Russell Francis. + + * src/sndfile.c + In sf_open_fd(), check if input file descriptor is a pipe. + + * src/sndfile.[ch] + Fix typo in variable name do_not_close_descriptor. + +2003-08-13 Erik de Castro Lopo + + * src/test_log_printf.c + Improve the tests for %d and %s conversions. + + * src/common.c + Fixed a few problems in psf_log_printf() found using new tests. + +2003-08-06 Erik de Castro Lopo + + * configure.ac + Add -Wwrite-strings warning to CFLAGS if the compiler is GCC. Thanks to + Peter Miller (Aegis author) for suggesting this and supplying a patch. + + * src/*.c examples/*.c tests/*.c + Fix all compiler warnings arising from the above. + +2003-08-02 + + * tests/aiff_rw_test.c tests/Makefile.am + New test program to check for errors re-writing the headers of AIFC files + opened in mode SFM_RDWR. + +2003-07-21 Erik de Castro Lopo + + * examples/sndfile-play.c + Applied a patch from Tero Pelander to allow this program to run on systems + using devfs which used /dev/sound/dsp instead of /dev/dsp. + +2003-07-11 Erik de Castro Lopo + + * doc/new_file_type.HOWTO + Updated document. Still incomplete. + +2003-06-29 Erik de Castro Lopo + + * src/sndfile.c + Fix VALIDATE_SNDFILE_AND_ASSIGN_PSF which was returning an error rather + than saving it and returning zero. + +2003-06-25 Erik de Castro Lopo + + * src/file_io.c + Two fixes for Mac OS9. + Fix all casts from sf_count_t to ssize_t (not size_t). + +2003-06-22 Erik de Castro Lopo + + * src/wav.c + Fix for reading files with RIFF length of 8 and data length of 0. + +2003-06-14 Erik de Castro Lopo + + * src/*.c tests/*.c tests/*.tpl + Added comments to mark code for removal when make Lite version of + libsndfile. + +2003-06-09 Erik de Castro Lopo + + * examples/sndfile-convert.c + Add extra error checking for unrecognised arguments. + +2003-06-08 Erik de Castro Lopo + + * src/ima_adpcm.c + Started adding code to write IMA ADPCM encoded AIFF files. + + * src/test_log_printf.c src/Makefile.am + New file to test psf_log_printf() function and add hooks into build system. + + * src/common.c + Move psf_log_printf() function to top of the file and only compile the rest + of the file if if PSF_LOG_PRINTF_ONLY is not defined. + +2003-06-03 Erik de Castro Lopo + + * Win32/config.h Win32/sndfile.h + Updated with new config variables. + + * Win32/unistd.h src/file_io.c + Added implementation of S_ISFIFO macro which Win32 seems to lack and is + used in src/file_io.c. + + * tests/utils.tpl + Added #include to pull in Win32/unistd.h so it compiles for + Win32. + + * src/Makefile.msvc + Added src\test_file_io.exe build target and run this as the very first + test. + + * tests/win32_test.c + Add support for testing Cygwin32. + + * configure.ac + Detect POSIX fsync() and fdatasync() functions. + + * src/file_io.c + If compiling for Cygwin, call fsync() before calling fstat() to retrieve + file length. + + * tests/pcm_test.tpl + Add a test for lrintf() function. This was required to detect a really + broken lrint() and lrintf() on Cygwin. + + * tests/misc_test.c + Don't run permission test when compiling under Cygwin. + + * src/float_cast.h + Fix fallback macro for lrint() and lrintf() to cast to long instead of int + to match official function prototypes. + +2003-06-02 Erik de Castro Lopo + + * examples/sndfile-convert.c + Modifications to improve accuracy of conversions; use double data for + floating point and int for everything else. + + * src/ima_apdcm.c + Completed work on decoding IMA ADPCM encoded AIFF files. Still need to + get encoding working. + +2003-05-28 Erik de Castro Lopo + + * src/aiff.c src/ima_adpcm.c + Start working on getting IMA ADPCM encoded AIFF files working. + +2003-05-27 Erik de Castro Lopo + + * configure.ac + Fixed the touch command for when the autogen program is not found (Matt + Flax). + + * src/ulaw.c src/alaw.c + Made these pipe-able. + +2003-05-24 Erik de Castro Lopo + + * src/paf.c src/ircam.c + Fixed writing to pipe. + + * src/wav.c src/aiff.c src/nist.c src/mat*.c src/svx.c src/w64.c + Return SFE_NO_PIPE_WRITE if an attempt is made to write to a pipe. + +2003-05-23 Erik de Castro Lopo + + * examples/sndfile-info.c + Modified to detect unknown file lengths. + + * src/mat4.c + Fix reading from a pipe. + +2003-05-22 Erik de Castro Lopo + + * tests/pipe_test.c + Add more file types to tests. + + * src/mat4.c + Removed explicit setting of psf->sf.seekable to SF_TRUE. + + * tests/utils.tpl + Add macro for generating and check data in the stdio and pipe tests. + + * tests/stdout_test.c tests/stdin_test.c + Use the above macro to generate known data on output and check data on + input. + + * src/voc.c src/htk.c common.h sndfile.c + Disallow reading/writing VOC and HTK files from/to pipes be returning new + error values. + + * src/w64.c + Fixes to allow reading from a pipe. + +2003-05-21 Erik de Castro Lopo + + * configure.ac src/sndfile.h.in + When the configure script determines the sizeof (sf_count_t), also set the + value of SF_COUNT_MAX in sndfile.h. + + * configure.ac + Remove -pedantic flag from default GCC compiler flags. + + * tests/pipe_test.c + Add a pipe_read_test() before doing pipe_write_test(). + + * tests/scale_clip_test.c + Add test to make sure non-normalized values also clip in the right way. + +2003-05-18 Erik de Castro Lopo + + * configure.ac + Add test to detect processor clipping capabilities. + + * tests/stdin_test.c tests/stdout_test.c + Fix a pair of compiler warnings. + + * src/common.h + Add new pipeoffset field to SF_PRIVATE. This will contain the current file + offset when operating on a pipe. + + * src/common.c + Removed direct calls to psf_fread()/psf_fseek()/psf_fgets() etc from + psf_binheader_readf and redirect them to new buffered versions + header_read(), header_seek() and header_gets(). + Add "G" format specifier to emulate fgets() functionality with buffering. + This will allow reading some file types from pipes. + + * src/file_io.c + When the file descriptor is a pipe, manintain psf->pipeoffset. + + * src/pvf.c + Change use of psf_fgets() to psf_binheader_readf() as required but changes to header re + + * src/au.c + Fix reading from a pipe. + +2003-05-17 Erik de Castro Lopo + + * src/pcm.c + Add clipping versions of the f2XXX_array() functions to allow option of + clipping data that would otherwise overflow. + + * tests/scale_clip_test.tpl tests/scale_clip_test.def + New files test that clipping option does actually work. + +2003-05-14 Erik de Castro Lopo + + * doc/index.html + Fixed a typo ("OS(" instead of "OS9"). + +2003-05-13 Erik de Castro Lopo + + * tests/open_fail_test.c + Include to prevent warning message of missing declaration of + memset(). + +2003-05-12 Erik de Castro Lopo + + * src/common.h + Add new "add_clipping" field to SF_PRIVATE. + + * src/sndfile.h.in src/sndfile.c + Add command SFC_SET_CLIPPING which sets/resets add_clipping field. + +2003-05-11 Erik de Castro Lopo + + * doc/api.html + Add docs for sf_set_string() and sf_get_string(). + + * src/common.h src/sndfile.c + Add new SFE_STR_BAD_STRING error. + + * tests/stdin_test.c tests/stdout_test.c + Removed all non-error print statements. + + * tests/stdio_test.c tests/pipe_test.c tests/Makefile.am + Add print statements removed from two files above. + +2003-05-10 Erik de Castro Lopo + + * libsndfile.spec.in + Fixed a coulpe of minor errors discovered by someone calling themselves + Agent Smith. + + * src/common.c src/common.h src/file_io.h + Added is_pipe field to SF_PRIVATE and declaration of psf_is_pipe() + function. (Axel Roebel) + + * src/sndfile.c + Fixed determination of whether the file is a pipe. (Axel Roebel) + + * src/paf.c + Force paf24 to start with undefined mode. (Axel Roebel) + + * tests/pipe_test.c + Mods to make this test work and actually do the test on RAW files. (Axel + Roebel). + +2003-05-05 Erik de Castro Lopo + + * src/sndfile.c + Fixed a potential bug where psf->sf.seekable was being set to FALSE when + operating on stdin or stdout but then the default initialiser was reseting + it to TRUE. Thanks to Axel Roebel. + + * src/aiff.c + Fixed a bug in the header parser where it was not handling an odd length + COMM chunk correctly. Thanks to Axel Roebel. + + * src/test_file_io.c + Add more tests. + + * tests/win32_test.c + New file for showing the bugs in the Win32 implementation of the POSIX API. + It also runs on Linux for sanity checking. + + * tests/Makefile.am Win32/Makefile.msvc + Hook the new test program into the build system. + +2003-05-04 Erik de Castro Lopo + + * src/test_file_io.c + New test program to test operation of functions defined in file_io.c. This + should make supporting win32 significantly easier. + + * src/Makefile.am + Hook new test program into the build system. + + * src/file_io.c + Add compile/run time check that sizeof statbuf.st_size and sf_count_t are + the same. + + * src/common.h src/sndfile.c + Added new error code and error message for new check. + + * tests/benchmark.tpl + Fix to use frames instead of samples in SF_INFO. + +2003-05-03 Erik de Castro Lopo + + * src/file_io.c + More stuffing about working around PLAIN OLD-FASHIONED **BUGS** in Win32. + + * examples/sndfile-info.c + Applied patch from Conrad Parker to add "--help" and "-h" options as + well as an improved usage message. + +2003-05-02 Erik de Castro Lopo + + * src/au.c + Added embedded file support. + + * tests/multi_file_test.c + Added tests for embedded AU files. + Added verbose testing mode. + + * src/common.h src/sndfile.c + Added an embedded AU specific error code and message. + + * src/wav.c + Added patch from Conrad Parker which filled in a little more information + about ACIDized WAV files. + +2003-04-30 Erik de Castro Lopo + + * src/file_io.c + Fixed Win32 version of psf_fseek() which was calling psf_get_filelen() + which was in turn calling psf_fseek() which in the end blew the stack. + Now of course this would have been easy to find on Linux, but this blow + up was happening in kernel32.dll and the fscking MSVC++ debugger couldn't + figure out what call caused this (it couldn't even tell me the stack had + overflowed) and was absolutley useless for this debugging exercise. + On top of that, the reason I got into this mess was that windoze doesn't + have a working fstat() function which can return file lengths > 2 Gig. It + HAS a fscking _fstati64() but the file length value is only updated AFTER + the bloody file is closed. That makes it completely useless. + How the hell do people stand working on this crap excuse of an OS? + +2003-04-29 Erik de Castro Lopo + + * Win32/unistd.h src/file_io.c + Moved definitions of S_IGRP etc from file_io.c to unistd.h so that these + can be used in the test programs. + + * Win32/libsndfile.def + Added sf_open_fd. + + * Win32/sndfile.h + Updated to match src/sndfile.h.in. + + * Win32/Makefile.msvc + Added dither.c and htk.c to libsndfile.dll target. + +2003-04-28 Erik de Castro Lopo + + * src/file_io.c + First attempt at getting the Win32 versions of the these functions working. + They still need to be tested. + +2003-04-27 Erik de Castro Lopo + + * src/strings.c + Found and fixed a bug which was causing psf_store_string() to fail on + Motorola 68k processors. Many thanks fo Joshua Haberman (Debian maintainer + of libsndfile) for compiling and running debug code to help me debug the + problem. + +2003-04-26 Erik de Castro Lopo + + * src/sndfile.c src/file_io.c src/wav.c src/aiff.c + Much hacking to get reading and writing of embedded files working (ie sound + files at a non-zero files offset). + + * doc/embedded_files.html + First pass atempt at documenting reading/writing embedded files. + +2003-04-21 Erik de Castro Lopo + + * doc/FAQ.html + Updated answer to "Why doesn't libsndfile do interleaving/de-interleaving?" + +2003-04-19 Erik de Castro Lopo + + * src/wav.c src/aiff.c + Fix retrieving and storing of string data from files. Need to be careful + about using psf->buffer for strings. + +2003-04-18 Erik de Castro Lopo + + * src/file_io.c + Fix psf_fseek() for seeks withing embedded files. + +2003-04-15 Erik de Castro Lopo + + * src/sndfile.h.in + Changed the definition of SNDFILE slightly to produce warnings when it isn't + used correctly. This should have zero affect in code which uses the SNDFILE + type correctly. + + * src/sndfile.c + Fixed a few compiler warnings cause by the changes to the SNDFILE type. + +2003-04-12 Erik de Castro Lopo + + * doc/FAQ.html + Added question and answer to the question "How about adding the ability + to write/read sound files to/from memory buffers?". + +2003-04-08 Erik de Castro Lopo + + * tests/write_read_test.tpl + Removed un-needed enums declaring TRUE and FALSE and replaced usage of + these with SF_TRUE and SF_FALSE. + + * tests/multi_file_test.c + New test program to test sf_open_fd() on files containing data other than + a single sound file. + +2003-04-06 Erik de Castro Lopo + + * src/file_io.c + When creating files, set the readable by others flag. This still allows + further restrictions to be enforced by use of the user's umask. Fix + suggested by Eric Lyon. + +2003-04-05 Erik de Castro Lopo + + * src/sndfile.h.in src/sndfile.c + Changed sf_open_fd(). Dropped offset parameter and added a close_desc + parameter. If close desc is TRUE, the file descritpor passed into the + library will be closed when sf_close() is called. + + * tests/utils.tpl + Modified call to sf_open_fd() to set close_desc parameter to SF_TRUE. + +2003-04-04 Erik de Castro Lopo + + * tests/write_read_test.tpl + Add a string (using sf_set_string() function) before and after data section + of all files. This will make sure that if string data can be added, it + doesn't overwrite real audio data. + +2003-04-02 Erik de Castro Lopo + + * src/sndfile.c + Started work on supporting a non-zero offset parameter for sf_open_fd (). + + * src/.c + Removed many uses of psf_fseek (SEEK_END) which to allow for future use of + sf_open_fd() with non-zero offset. + Associated refactoring. + + * src/aiff.c + Implemented functionality required to get sf_get_string() and + sf_set_string() working for AIFF files. + +2003-04-01 Erik de Castro Lopo + + * tests/utils.tpl + Modified test_open_file_or_die() to alternately use sf_open() and + sf_open_fd(). + + * src/svx.c + Fixed a bug which occurred when openning an existing file for read/write + using sf_open_fd(). In this case, the existing NAME chunk needs to be + read into psf->filename. + Fixed printing of sf_count_t types to logbuffer. + +2003-03-31 Erik de Castro Lopo + + * src/sndfile.h.in + Added prototype for new function sf_open_fd(). + + * src/sndfile.c + Moved most of the code in sf_open() to a new function psf_open_file(). + Created new function sf_open_fd() which also uses psf_open_file() but + does not currently support the offset parameter. + + * doc/api.html + Document sf_open_fd(). + +2003-03-09 Erik de Castro Lopo + + * src/sndfile.c + Fixed a memory leak reported by Evgeny Karpov. Memory leak only occurred + when an attempt was made to read and the open() call fails. + +2003-03-08 Erik de Castro Lopo + + * tests/open_fail_test.c + New test program to check for memory leaks when sf_open fails on a valid + file. Currently this must be run manually under valgrid. + + * tests/Makefile.am + Hook new test program into build. + +2003-03-03 Erik de Castro Lopo + + * Octave/sndfile_save.m Octave/sndfile_play.m + Added a -mat-binary option to the octave save command to force the output + to binary mode even if the user has set ascii data as the default. Found + by Christopher Moore. + +2003-02-27 Erik de Castro Lopo + + * doc/dither.html + New file which will document the interface which allows the addition of + audio dither when sample word sizes are being reduced. + + * src/dither.c + More work. + +2003-02-26 Erik de Castro Lopo + + * tests/misc_test.c + In update_header_test(), make HTK files a special case. + + * doc/index.html + Added HTK to the feature matrix. + +2003-02-25 Erik de Castro Lopo + + * src/htk.c + New file for reading/writing HMM Tool Kit files. + + * src/sndfile.h.in src/sndfile.c src/command.c src/Makefile.am + Hook in htk.c + + * tests/write_read_test.tpl tests/misc_test.c tests/Makefile.am + Add tests for HTK files. + +2003-02-22 Erik de Castro Lopo + + * src/wav.c + Fixed a bug where the LIST chunk length was being written incorrectly. + + * tests/string_test.c + Added call to check_log_buffer(). + Minor cleanups. + +2003-02-10 Erik de Castro Lopo + + * src/wav_w64.h + Applied patch from Antoine Mathys to add extra WAV format definitions and + a G72x_ADPCM_WAV_FMT struct definition. + + * src/wav_w64.c + Applied patch from Antoine Mathys which converts wav_w64_format_str() from + one huge inefficient switch statement to a binary search. + + * tests/string_test.c + Dump log buffer if tests fail. + +2003-02-07 Erik de Castro Lopo + + * tests/string_test.c + David Viens supplied some modifications to this file which showed up a bug + when using sf_set_string() and the sf_writef_float() functions. + + * src/sndfile.c + Fixed the above bug. + +2003-02-06 Erik de Castro Lopo + + * doc/FAQ.html + Added Q and A on how to detect libsndfile in configure.in (at the suggestion + of Davy Durham). + +2003-02-05 Erik de Castro Lopo + + * src/sndfile.h.in + Add enums and typedefs for dither. + Deprecate SFC_SET_ADD_DITHER_ON_WRITE and SFC_SET_ADD_DITHER_ON_READ, to be + replaced with SFC_SET_DITHER_ON_WRITE and SFC_SET_DITHER_ON_READ which will + allow different dither algorithms to be enabled. + Added SFC_GET_DITHER_INFO_COUNT and SFC_GET_DITHER_INFO. + + * src/sndfile.h.in src/Version_script.in Win32/libsndfile.def. + Added public sf_dither_*() functions. + + * src/sndfile.c + Implement commands above. + + * src/dither.c + More work. Framework and external hooks into dither algorithms complete. + +2003-02-03 Erik de Castro Lopo + + * doc/version-1.html libsndfile_version_convert.py + Remove redundant files. + + * doc/index.html doc/api.html + Remove links to version-1.html. + + * src/dither.c + New file to allow the addition of audio dither on input and output. + + * src/common.h + Add prototype for dither_init() function. + + * Makefile.am doc/Makefile.am + Changes for added and removed files. + +2003-02-02 Erik de Castro Lopo + + * Win32/Makefile.msvc + Changes to force example binaries to be placed in the top level directory + instead of the examples/ directory. + Add src/strings.c and src/xi.c to the build. + Add string_test to build and to tests on WAV files. + + * doc/index.html + Added XI to support matrix. + +2003-01-27 Erik de Castro Lopo + + * src/sndfile.h.in + Added prototypes for sf_get_string() and sf_set_string() and SF_STR_* + enum values. + + * src/sndfile.c + Added public interface to sf_get_string() and sf_set_string(). + + * src/wav.c + Added code for setting and getting strings in WAV files. + + * tests/string_test.c + New test program for sf_get_string() and sf_set_string() functionality. + + * tests/Makefile.am + Hook new test program into build and test framework. + +2003-01-26 Erik de Castro Lopo + + * src/common.h + Added fields to SF_PRIVATE for string data needed to implement + sf_get_string() and sf_set_string(). + + * src/strings.c + New file for storing and retrieving strings to/from files. + + * src/Makefile.am + Added strings.c to build. + +2003-01-25 Erik de Castro Lopo + + * src/xi.c + Read seems to be working so looking at write. + + * src/sndfile.h.in + Added SF_FORMAT_XI, SF_FORMAT_DPCM_8 and SF_FORMAT_DPCM_16 enum values. + + * tests/floating_point_test.c tests/lossy_comp_test.c tests/Makefile.am + Added test for 8 and 16 bit XI format files. + +2003-01-24 Erik de Castro Lopo + + * doc/index.html + Added a non-lawyer readable summary of the licensing provisions as + suggested by Steve Dekorte. + +2003-01-23 Erik de Castro Lopo + + * src/wav.c + Fixed a compiler warning found by Alexander Lerch. + +2003-01-18 Erik de Castro Lopo + + * configure.ac + Fixed the multiple linking of libm. + +2003-01-17 Erik de Castro Lopo + + * Win32/Makefile.mcvs + Added comments on the correct way to set up the MSVCDir environment + variable. + + * doc/win32.html + Add on how to set up the MSVCDir environment variable. + +2003-01-15 Erik de Castro Lopo + + * examples/sndfile-play.c examples/sndfile-info.c + When run on Win32 without any command line parameters print a message and + then sleep for 5 seconds. This means the when somebody double clicks on + these programs in explorer the user will actually see the message. + +2003-01-14 Erik de Castro Lopo + + * tests/misc_test.c + Bypass permission test if running as root because root is allowed to open + a readonly file for write. + +2003-01-08 Erik de Castro Lopo + + * Win32/Makefile.msvc + Added pvf.c and xi.c source files to project. + + * src/sndfile.h + Updated for PVF files. + +2003-01-07 Erik de Castro Lopo + + * src/sndfile.c + Modified validate_sfinfo() to force samplerate, channels and sections + to be >= 1. + In format_from_extension() replaced calls to does_extension_match() + with strcmp(). + + * src/xi.c + More work. + +2003-01-06 Erik de Castro Lopo + + * doc/Makefile.am + Added octave.html which had been left out. Found by Jan Weil. + +2003-01-05 Erik de Castro Lopo + + * src/pvf.c src/common.h src/sndfile.c + Fixed error handling for PVF files. + + * src/xi.c + New file for handling Fasttracker 2 Extended Instrument files. Not working + yet and included when configured with --enable-experimental. + + * src/sndfile.c src/common.h + Hooked in new file xi.c. + +2002-12-30 Erik de Castro Lopo + + * src/rx2.c + Added a patch from Marek Peteraj which sheds a little more light on the + slices within an RX2 file. Still need to find out data encoding. + +2002-12-20 Erik de Castro Lopo + + * src/wav.c + Started work on decoding 'acid' and 'strc' chunks. + +2002-12-14 Erik de Castro Lopo + + * tests/peak_check_test.c + Minor cleanup. + +2002-12-12 Erik de Castro Lopo + + * tests/write_read_test.tpl + Added check to make sure no error was generated when an attempt was made to + read past the end of the file. + +2002-12-11 Erik de Castro Lopo + + * doc/lists.html + Added "mailto" links for all three lists. + + * src/pvf.c + New file for Portable Voice Format files. + + * src/sndfile.h.in src/sndfile.c src/common.h src/command.c src/Makefile.am + Added hooks for SF_FORMAT_PVF format files. + + * tests/write_read_test.tpl tests/std*.c + Add tests for SF_FORMAT_PVF. + + * doc/index.html + Add PVF to the compatibility matrix. + + * src/pcm.c src/alaw.c src/ulaw.c src/float32.c src/double64.c + Previously, attempts to read beyond the end of a file would set psf->error + to SFE_SHORT_ERROR. This behaviour diverged from the behaviour of the POSIX + read() call but has now been fixed. + Attempts to read beyond the end of the file will return a short read count + but will not longer set any error. + +2002-12-09 Erik de Castro Lopo + + * src/sndfile.c + Add more sanity checking when opening a RAW file for read. When format is + not RAW, zero out all members of the SF_INFO struct. + + * tests/raw_test.c + Add bad_raw_test() to check for above problem. + + * tests/stdin_test.c examples/sndfile-info.c + Set the format field of the SF_INFO struct to zero before calling + sf_open(). + + * doc/api.html + Add information about the need to set the format field of the SF_INFO struct + to zero when opening non-RAW files for read. + + * configure.ac + Removed use of conversion script on Solaris. Not all Solaris versions + support it. + + * doc/lists.html + New file containg details of the mailing lists. + + * doc/index.html + Add a link to the above new file. + +2002-12-04 Erik de Castro Lopo + + * tests/dft_cmp.c + Fixed a SIGFPE on Alpha caused by a log10 (0.0). Thanks to Joshua Haberman + for providing the gdb traceback. + +2002-11-28 Erik de Castro Lopo + + * src/wav.c + Added more capabilities to 'smpl' chunk parser. + + * src/sndfile.c + Fixed some (not all) possible problems found with Flawfinder. + +2002-11-24 Erik de Castro Lopo + + * src/sndfile.c + Fixed a bug in sf_seek(). This bug could only occur when an attempt was + made to read beyond the end and then sf_seek() was called with a whence + parameter of SEEK_CUR. + + * src/file_io.c + Win32's _fstati64() does not work, it returns BS. Re-implemented + psf_get_filelen() in terms of psf_fseek(). + + * tests/write_read_test.tpl + Add a test to detect above bug. + + * src/float_cast.h + Modification to prevent compiler warnings on Mac OS X. + + * src/file_io.c + Fixes for windows (what a f**ked OS). + +2002-11-08 Erik de Castro Lopo + + * configure.ac + Disable use of native lrint()/lrintf() on Mac OSX. These functions exist on + Mac OSX 10.2 but not on 10.1. Forcing the use of the versions in + src/float_cast.h means that a library compiled on 10.2 will still work on + 10.1. + +2002-11-06 Erik de Castro Lopo + + * configure.in configure.ac + Renamed configure.in to configure.ac as expected by later versions of + autoconf. + Slight hacking of configure.ac to work with version 2.54 of autoconf. + Changed to using -dumpversion instead of --version for determining GCC + version numer as suggested by Anand Kumria. + + * src/G72x/Makefile.am + Slight hacking required for operation with automake 1.6.3. + +2002-11-05 Erik de Castro Lopo + + * src/common.c + In psf_binheader_readf() changed type parameter type "b" type from size_t + to int to prevent errors on IA64 CPU where sizeof (size_t) != sizeof (int). + Thanks to Enrique Robledo Arnuncio for debugging this. + +2002-11-04 Erik de Castro Lopo + + * test/command_test.tpl + Changed test value so test would pass on Solaris. + + * src/Version_script.in + Modified version numbering so that later versions of 1.0.X can replace + earlier versions without recompilation. + + * src/vox_adpcm.c + Fixed bug causing short reads. + +2002-11-03 Erik de Castro Lopo + + * test/floating_point_test.c + Code cleanup using functions from util.c. + Add test for IEEE replacement floats and doubles. + +2002-11-01 Erik de Castro Lopo + + * src/wav.c + Fixed a possible divide by zero error when read the 'smpl' chunk. Thanks to + Serg Repalov for the example file. + + * tests/pcm_test.tpl + Used sf_command (SFC_TEST_IEEE_FLOAT_REPLACE) to test IEEE replacement code. + Clean up pcm_double_test(). + + * src/float32.c src/double64.c + Force use of IEEE replacement code using psf->ieee_replace is TRUE, + Print message to log_buffer as well. + Rename all broken_read_* and broken_write* functions to replace_read_* and + replace_write_*. + + * tests/util.tpl + Added string_in_log_buffer(). + + * tests/pcm_test.tpl + Use string_in_log_buffer() to ensure that IEEE replacement code has been + used. + + * configure.in + Removed --enable-force-broken-float option. IEEE replacement code is now + always tested. + +2002-10-31 Erik de Castro Lopo + + * src/double64.c + Implement code for read/writing IEEE doubles on platforms where the native + double format is not IEEE. + + * src/float32.c src/common.h + Remove float32_read() and float32_write(). Replace with float32_le_read(), + float32_be_read(), float32_le_write() and float32_be_write() to match stuff + in src/double64.c. + + * src/common.c + Fix all usage of float32_write(). + + * src/sndfile.h.in + Added SFC_TEST_IEEE_FLOAT_REPLACE command (testing only). + + * src/common.h + Added SF_PRIVATE field ieee_replace. + + * src/sndfile.c + In sf_command() set/reset psf->ieee_replace. + +2002-10-26 Erik de Castro Lopo + + * tests/pcm_test.tpl + Fixed a problem when testing with --enable-force-broken-float. The test was + generating a value of negative zero and the broken float code is not able + to write negative zero. Removing the negative zero fixed the test. + +2002-10-25 Erik de Castro Lopo + + * src/file_io.c + Added fix for Cygwin (suggested by Maros Michalik). + +2002-10-23 Erik de Castro Lopo + + * src/file_io.c + Improved error detection and handling. + + * src/file_io.c src/common.h + Removed functions psf_ferror() and psf_clearerr() which were redundant + after above improvements. + + * src/aiff.c src/svx.c src/w64.c src/wav.c + Removed all use of psf_ferror() and psf_clearerr(). + + * src/sndfile.c + Removed #include of , , and which + are no longer needed. + + * tests/misc_test.c + Added test to make sure the correct error message is returned with an + existing read-only file is openned for write. + +2002-10-21 Erik de Castro Lopo + + * doc/index.html doc/api.html + Updated for OKI Dialogic ADPCM files. + + * src/command.c + Added VOX ADPCM to sub_fomats. + +2002-10-20 Erik de Castro Lopo + + * src/vox_adpcm.c src/Makefile.am + New file for handling OKI Dialogic ADPCM files. + + * src/sndfile.h + Add new subtype SF_FORMAT_VOX_ADPCM. + + * src/sndfile.c + Renamed function is_au_snd_file () to format_from_extenstion () and expanded + its functionality to detect headerless VOX files. + + * src/raw.c + Added hooks for SF_FORMAT_VOX_ADPCM. + + * examples/sndfile-info.c + Print out file duration (suggested by Conrad Parker). + + * libsndfile.spec.in + Force installation of sndfile.pc file (found by John Thompson). + + * tests/Makefile.am tests/lossy_comp_test.c tests/floating_point_test.c + Add tests for SF_FORMAT_VOX_ADPCM. + +2002-10-18 Erik de Castro Lopo + + * tests/misc_test.c + Add test which attempts to write to /dev/full (on Linux anyway) to check + for correct handling of writing to a full filesystem. + + * src/sndfile.c + Return correct error message if the header cannot be written because the + filesystem is full. + + * tests/util.tpl + Corrected printing of file mode in error reporting. + + * src/mat5.c + Fixed a bug where a MAT5 file written by libsndfile could not be opened by + Octave 2.1.36. + +2002-10-13 Erik de Castro Lopo + + * src/common.h src/file_io.c + All low level file I/O have been modified to be better able to report + system errors resulting from calling system level open/read/write etc. + + * src/*.c + Updated for compatibility with above changes. + + * examples/cooledit-fixer.c + New example program which fixes badly broken file created by Syntrillium's + Cooledit which are marked as containing PCM samples but actually contain + floating point data. + + * examples/Makefile.am + Hooked cooledit-fixer into the build system. + +2002-10-10 Erik de Castro Lopo + + * doc/command.html + Document SFC_GET_FORMAT_INFO. + +2002-10-09 Erik de Castro Lopo + + * examples/wav32_aiff24.c examples/sndfile2oct.c examples/sfhexdump.c + examples/sfdump.c + Removed these files because they weren't interesting. + + * examples/sfconvert.c examples/sndfile-convert.c + Renamed the first to the latter. + + * examples/Makefile.am + Added sndfile-convert to the bin_PROGRAMS, so it is installed when the lib + is installed. + Removed old programs wav32_aiff24 and sndfile2oct. + + * man/sndfile-convert.1 + New man page. + + * examples/sndfile-convert.c + Added some gloss now that sndfile-convert.c is an installed program. + + * src/sndfile.h.in src/sndfile.c src/common.h src/command.h + Added command SFC_GET_FORMAT_INFO. + + * tests/command_test.c + Added tests form SFC_GET_FORMAT_INFO. + +2002-10-08 Erik de Castro Lopo + + * src/sndfile.c + In sf_format_check() return error if samplerate < 0. + +2002-10-07 Erik de Castro Lopo + + * src/aiff.c + Fixed bug in handling of COMM chunks with a 4 byte encoding byte but no + encoding string. + +2002-10-06 Erik de Castro Lopo + + * src/sndfile.c + Fixed repeated word in an error message. + +2002-10-05 Erik de Castro Lopo + + * doc/index.html + Improved advertising in Features section. + +2002-10-04 Erik de Castro Lopo + + * src/wav.c + Added decoding of 'labl' chunks within 'LIST' chunks. + + * src/common.h + Added (experimental only) SF_FORMAT_OGG and SF_FORMAT_VORBIS and definition + of ogg_open(). This is nowhere near working yet. + + * src/sndfile.c + Added detection of 'OggS' file marker and added call to ogg_open() to + switch statement. + + * src/ogg.c + New file. Very early start of Ogg Vorbis support. + + * src/wav.c + Added handling of brain-damaged and broken Cooledit "32 bit 24.0 float + type 1" files. These files are marked as being 24 bit WAVE_FORMAT_PCM with + a block alignment of 4 times the numbers of channels but are in fact 32 bit + floating point. + +2002-10-02 Erik de Castro Lopo + + * configure.in + Modified option --enable-experimental to set ENABLE_EXPERIMENTAL_CODE in + config.h to either 0 or 1. + + * src/sndfile.c + Modify sf_command (SFC_GET_LIB_VERSION) to append "-exp" to the version + string if experimental code has been enabled. + +2002-10-01 Erik de Castro Lopo + + * src/Makefile.am + Added -lm to libsndfile_la_LIBADD. This means that -lm is not longer needed + in the link line when linking something to libsndfile. + + * tests/Makefile.am examples/Makefile.am + Removed -lm from all link lines. + + * sndfile.pc.in + Removed -lm from Libs line. + +2002-09-24 Erik de Castro Lopo + + * src/file_io.c + Removed all perror() calls. + + * src/nist.c + Removed calls to exit() function. + Added check to detect NIST files dammaged from Unix CR -> Win32 CRLF + conversion process. + +2002-09-24 Erik de Castro Lopo + + * src/sndfile.h.in src/sndfile.c + New function sf_strerror() which will eventually replace functions + sf_perror() and sf_error_str(). + Function sf_error_number() has also been changed, but this was documented + as being for testing only. + + * doc/api.html + Documented above changes. + + * tests/*.c examples/*.c + Changed to new error functions. + +2002-09-22 Erik de Castro Lopo + + * configure.in + Detect GCC version, and print a warning message about writeable strings + it GCC major version number is less than 3. + +2002-09-21 Erik de Castro Lopo + + * src/sndfile.h.in doc/api.html + Documentation fixes. + +2002-09-19 Erik de Castro Lopo + + * src/Version_script.in src/Makefile.am configure.in + Use the version script to prevent the exporting of all non public symbols. + This currently only works with Linux. Will test on Solaris as well. + + * src/float_cast.h + Added #ifndef to prevent the #warning directives killing the SGI MIPSpro + compiler. + + * src/au_g72x.c src/double64.c src/float32.c src/gsm610.c src/ima_adpcm.c + src/ms_adpcm.c + Fix benign compiler warnings arising from previously added compiler + flags. + +2002-09-18 Erik de Castro Lopo + + * src/sndfile.c + Fixed a bug in sf_error_str() where errnum was used as the index instead + of k. Found by Tim Hockin. + + * examples/sndfile-play.c + Fixed a compiler warning resulting from a variable shadowing a previously + defined local. + +2002-09-17 Erik de Castro Lopo + + * src/sndfile.h.in src/sndfile.c + Added command SFC_SET_RAW_START_OFFSET. + + * doc/command.html + Document SFC_SET_RAW_START_OFFSET. + + * tests/raw_test.c tests/Makefile.am + Add new file for for testing SF_FORMAT_RAW specific functionality. + + * tests/dwvw_test.c + Updates. + +2002-09-16 Erik de Castro Lopo + + * src/wav.c + Modified reading of 'smpl' chunk to take account of the sampler data field. + + * tests/utils.tpl tests/utils.h + Added function print_test_name(). + + * tests/misc_test.c tests/write_read_test.tpl tests/lossy_comp_test.c + tests/pcm_test.tpl tests/command_test.tpl tests/floating_point_test.c + Convert to use function print_test_name(). + +2002-09-15 Erik de Castro Lopo + + * doc/octave.html + Added a link to some other Octave scripts for reading and writing sound + files. + + * src/paf.c + Change type of dummy data field to int. This should fix a benign compiler + warning on some CPUs. + Removed superfluous casts resulting from the above change. + + * src/rx2.c + More hacking. + +2002-09-14 Erik de Castro Lopo + + * src/mat5.c src/common.c + Changed usage of snprintf() to LSF_SNPRINTF(). + + * Win32/Makefile.msvc + Updated to include new files and add new tests. + + * Win32/config.h Win32/sndfile.h + Updated. + + * doc/api.html + Added note about the possibility of "missing" features actually being + implemented as an sf_command(). + +2002-09-13 Erik de Castro Lopo + + * tests/misc_test.c + Added previously missing update_header_test and zero_data_tests for PAF, + MAT4 and MAT5 formats. + + * src/paf.c src/mat4.c src/mat5.c + Fixed bugs uncovered by new tests above. + + * src/mat5.c + Generalised parsing of name fields of MAT5 files. + + * src/mat5.c src/sndfile.c + Added support for unsigned 8 bit PCM MAT5 files. + + * tests/write_read_test.tpl + Added test for unsigned 8 bit PCM MAT5 files. + + * doc/index.html + Added unsigned 8 bit PCM MAT5 to capabilities matrix. + +2002-09-12 Erik de Castro Lopo + + * test/update_header_test.c tests/misc_test.c + Renamed update_header_test.c to misc_test.c. + Added zero_data_test() to check for case where file is opened for write and + closed immediately. The resulting file can be left in a state where + libsndfile cannot open it. Problem reported by Werner Schweer, the author + of Muse. + + * src/aiff.c + Removed superfluous cast. + + * src/wav.c src/svx.c + Fixed case of file generated with no data. + Removed superfluous cast. + + * src/sndfile.c + Fixed error on IA64 platform caused by incorrect termination of + SndfileErrors struct array. This problem was found in the Debian buildd + logs (http://buildd.debian.org/). + + * configure.in + Added Octave directory. + + * Octave/Makefile.ma + New Makfile.am for Octave directory. + + * Octave/sndfile_load.m Octave/sndfile_save.m Octave/sndfile_play.m + New files for working with Octave. + + * doc/octave.html + Document explaining the use of the above three Octave scripts. + +2002-09-10 Erik de Castro Lopo + + * src/sndfile.c + Fixed bug in RDWR mode. + +2002-09-09 Erik de Castro Lopo + + * src/common.c + Fixed psf_get_date_str() for systems which don't have gmtime_r() or + gmtime(). + + * src/file_io.c + Added #include for Win32. Reported by Koen Tanghe. + +2002-09-08 Erik de Castro Lopo + + * src/common.c + Added 'S' format specifier for psf_binheader_writef() which writes a C + string, including single null terminator to the header. + Added 'j' format specifier to allow jumping forwards or backwards in the + header. + Added function psf_get_date_str(). + + * src/mat5.c + Complete read and write support. + + * doc/index.html + Added entries for MAT4 and MAT5 in capabilities matrix. + +2002-09-06 Erik de Castro Lopo + + * src/mat4.c + Completed read and write support. + + * src/common.h src/sndfile.c + Added MAT4 and MAT5 specific error messages. + + * tests/write_read_test.tpl tests/Makefile.am + Added tests for MAT4 and MAT5 files. + + * tests/stdio_test.c tests/stdout_test.c tests/stdin_test.c + Added tests for MAT4 and MAT5 files. + +2002-09-05 Erik de Castro Lopo + + * src/command.c + Added elements for SF_FORMAT_MAT4 and SF_FORMAT_MAT5 to major_formats + array. + + * examples/sfconvert.c + Added mat4 and mat5 output targets. + +2002-09-04 Erik de Castro Lopo + + * src/sndfile.c + Added check to prevent errors openning read only formats for read/write. + + * src/interleave.c + New file for interleaving non-interleaved data. Non-interleaved data is + only supported on read. + + * src/Makefile.am + Added src/interleave.c to build. + +2002-09-03 Erik de Castro Lopo + + * src/double64.c src/common.h + Added double64_be_read(), double64_le_read(), double64_be_write() and + double64_le_write() which replace double64_read() and double64_write(). + + * src/common.c + Cleanup of psf_binheader_readf() and add ability to read big and little + endian doubles (required by mat4.c and mat5.c). + Add ability for psf_binheader_writef() to write doubles to sound file + headers. + +2002-09-01 Erik de Castro Lopo + + * src/mat5.c + New file for reading Matlab (tm) version 5 data files. This is also the + native binary file format for version 2.1.X of GNU Octave which will be + used for testing. + Not complete yet. + + * src/mat4.c + New file for reading Matlab (tm) version 4.2 data files. This is also the + native binary file format for version 2.0.X of GNU Octave which will be + used for testing. + Not complete yet. + + * src/sndfile.h.in src/sndfile.c src/common.h src/command.c src/Makefile.am + Mods to add Matlab files. + + * src/common.[ch] + Added readf_endian field to SF_PRIVATE struct allowing endianness to + remembered across calls to sf_binheader_readf(). + Fixed bug in width_specifier behaviour for printing hex values. + +2002-08-31 Erik de Castro Lopo + + * src/file_io.c + Check return value of close() call in psf_fclose(). + +2002-08-24 Erik de Castro Lopo + + * src/ms_adpcm.c + Commented out some code where 0x10000 was being subtracted from a short + and the result assigned to a short again. Andrew Zaja found this. + +2002-08-23 Erik de Castro Lopo + + * doc/command.html + Fixed typo found by Tommi Ilmonen. + + * src/ima_adpcm.c + Changed type of diff from short to int to prevent errors which can occur + during very rare circumstances. Thanks to FUWAFUWA. + +2002-08-16 Erik de Castro Lopo + + * tests/floating_point_test.c + Disable testing on machines without lrintf(). + + * Win32/Makefile.msvc + Added dwd.c and wve.c to build. + + * configure.in + Bumped version to 1.0.0. + +2002-08-15 Erik de Castro Lopo + + * src/file_io.c + Add a #include for Mac OS 9. Thanks to Stephane Letz. + + * src/wav.c + Changed an snprintf to LSF_SNPRINTF. + + * doc/Makefile.am + Added version-1.html. + +2002-08-14 Erik de Castro Lopo + + * configure.in + Bumped version to 1.0.rc6. + + * src/*.c + Modified scaling of normalised floats and doubles to integers. Until now + this has been done by multiplying by 0x8000 for short output, 0x80000000 + for 32 bit ints and so on. Unfortunately this can cause an overflow and + wrap around in the target value. All thes values have therefore been + reduced to 0x7FFF, 0x7FFFFFFF and so on. The conversion from ints to + normalised floats and doubles remains unchanged. This does mean that for + repeated conversions normalised float -> pcm16 -> normalised float would + result in a decrease in amplitude of 0x7FFF/0x8000 on every round trip. + This is undesirable but less undesireable than the wrap around I am trying + to avoid. + + * tests/floating_point_test.c + Removed file hash checking because new float scaling procedure introduced + above prevented the ability to crate a has on both x86 and PowerPC systems. + +2002-08-13 Erik de Castro Lopo + + * src/txw.c + Completed reading of TXW files. Seek doesn't work yet. + + * src/file_io.c + Added a MacOS 9 replacement for ftruncate(). + + * MacOS/sndfile.h + Added MacOS 9 header file. This should be copied into src/ to compile + libsndfile for MacOS9. + +2002-08-12 Erik de Castro Lopo + + * src/sndfile.c + Fixed commands SF_SET_NORM_DOUBLE and SFC_SET_NORM_FLOAT to return their + values after being set. Reported by Jussi Laako. + + * configure.in + If autogen is not found, touch all .c and .h files in tests/. + + * src/common.c + Added format width specifier to psf_log_printf() for %u, %d, %D and %X. + + * src/dwd.c + Completed implementation of read only access to these files. + + * src/common.h src/*.c src/pcm.c + Removed redundant field chars from SF_PRIVATE struct and modified + pcm_init() to do without it. + +2002-08-11 Erik de Castro Lopo + + * src/wve.c + New file implementing read of Psion Alaw files. This will be a read only + format. Implementation complete. + + * src/dwd/c + Started implementation of DiamondWare Digitized files. Also read only, not + complete. + + * src/wav.c + Add parsing of 'smpl' chunk. + + * src/paf.c + Fixed reading on un-normalized doubles and floats from 24 bit PAF files. + This brings it into line with the reading of 8 bit files into + un-normalized doubles which returns values in the range [-128, 127]. + + * src/common.c + Modified psf_log_printf() to accept the %% conversion specifier to allow + printing of a single '%'. + + * src/sds.c + Read only of 16 bit samples is working. Need to build a test harness for + this and other read only formats. + +2002-08-10 Erik de Castro Lopo + + * configure.in + Added --enable-experimental configure option. + Removed pkg-config message at the end of the configure process. + + * src/sds.c src/txw.c src/rx2.c src/sd2.c + Moved all the code in these files inside #if ENABLE_EXPERIMENTAL_CODE + blocks and added new *_open() function for the case where experimental is + not enabled. These new functions just return SFE_UNIMPLMENTED. + + * Win32/sndfile.h src/sndfile.h.in src/common.h + Removed un-necessary #pragma pack commands. + + * src/file_io.c + Implemented psf_ftruncate() and much other hacking for Win32. + + * Win32/Makefile.msvc + Updated. + + * doc/win32.html + Updated to include the copying of the sndfile.h file from the Win32/ + directory to the src/ directory. + + * Make.bat + Batch file to make compiling on Wi32 a little easier. Implements "make" and + "make check". + +2002-08-09 Erik de Castro Lopo + + * src/file_io.c + Add place holder for ftruncate() on Win32 which doesn't have ftruncate(). + This will need to be fixed later. + + * src/sndfile.h.in + New file (copy of sndfile.h) with sets up @TYPEOF_SF_COUNT_T@ which will be + replaced by the correct type during configure. + + * configure.in + Modified to find a good type for TYPEOF_SF_COUNT_T. + + * src/aiff.c + Fixed a bug when reading malformed headers. + + * src/common.c + Set read values to zero before performing read. + +2002-08-08 Erik de Castro Lopo + + * doc/command.html + Fixed some HTML tags which were not allowing jumps to links within the + page. + + * src/sds.c + Massive hacking on this. + + * src/wav.c + Added recognition of 'clm ' tag. + +2002-08-07 Erik de Castro Lopo + + * doc/index.html + Added beginning of a capabilities list beyond simple file formats which + can be read/written. + + * src/aiff.c + Added parsing of INST and MARK chunks of AIFF files. At the moment this + data is simply recorded in the log buffer. Later it will be possible to + read this data from an application using sf_command(). + + * src/wav.c + Added parsing of 'cue ' chunk which contains loop information in WAV files. + + * exampes/sndfile-info.c + Changed reporting of Samples to Frames. + + * src/wav.c src/w64.c src/aiff.c src/wav_w64.h + Moved from a samples to a frames nomenclature to avoid confusion. + + * doc/FAQ.html + What's the best format for storing temporary files? + + * src/sds.c + New file for reading/writing Midi Sample Dump Standard files. + + * src/Makefile.am src/sndfile.c src/common.[ch] + Added hooks for sds.c. + + * examples/sndfile-info.c + Changed from using sf_perror() to using sf_error_str(). + +2002-08-06 Erik de Castro Lopo + + * doc/api.html + Added explanation of mode parameter for sf_open(). + Added explanation of usage of SFM_* values in sf_seek(). + + * src/sndfile.[ch] src/command.c src/file_io.c src/common.h + Implemented SFC_FILE_TRUNCATE to allow a file to be truncated. File + truncation was suggested by James McCartney. + + * src/command.html + Documented SFC_FILE_TRUNCATE. + + * tests/command_test.c + Add tests for SFC_FILE_TRUNCATE. + + * src/sndfile.c + Added a thrid parameter to the VALIDATE_SNDFILE_AND_ASSIGN_PSF macro to + make resetting the error number optional. All uses of the macro other than + in error reporting functions were changed to reset the error number. + + * src/pcm.c + Fixed a bug were sf_read_* was logging an SFE_SHORT_READ even when no error + occurred. + + * tests/write_read_test.tpl + Added tests of internal error state. + +2002-08-05 Erik de Castro Lopo + + * src/GSM610/private.h src/GSM610/*.c src/GSM610/Makefile.am + Renamed private.h to gsm610_priv.h to prevent clash with other headers + named private.h in other directories. (Probably only a problem on MacOS 9). + + * src/G72x/private.h src/G72x/*.c src/G72x/Makefile.am + Renamed private.h to g72x_priv.h to prevent clash with other headers + named private.h in other directories. (Probably only a problem on MacOS 9). + + * MacOS/config.h + Changed values of HAVE_LRINT and HAVE_LRINTF to force use of code in + float_cash.h. + + * src/sndfile.h + Changes the name of samples field of the SF_INFO to frames. The old name + had caused too much confusion and it simply had to be changed. There will + be at least one more pre-release. + +2002-08-04 Erik de Castro Lopo + + * doc/index.html + Updated formats matrix to include RAW (header-less) GSM 6.10. + Fix specificaltion of table and spelling mistakes. + + * src/sndfile.c src/command.c + Fixed bug in SFC_CALC_MAX_SIGNAL family and psf_calc_signal_max (). + + * tests/command.c + Removed cruft. + Added test for SFC_CALC_MAX_SIGNAL and SFC_CALC_NORM_MAX_SIGNAL. + + * configure.in + Update version to 1.0.0rc5. + + * sfendian.h + Removed inclusion of un-necessary header. + +2002-08-03 Erik de Castro Lopo + + * src/aiff.c + Minor fixes of info written to log buffer. + + * src/float_cast.h + Add definition of HAVE_LRINT_REPLACEMENT. + + * tests/floating_point_test.c + Fix file hash check on systems without lrint/lrintf. + + * tests/dft_cmp.c + Limit SNR to less than -500.0dB. + + * examples/sndfile2oct.c + Fixed compiler warnings. + + * doc/api.html + Fixed error where last parameter of sf_error_str() was sf_count_t instead + of size_t. + +2002-08-02 Erik de Castro Lopo + + * doc/FAQ.html + Why doesn't libsndfile do interleaving/de-interleaving. + + * tests/pcm_test.tpl + On Win32 do not perform hash check on files containing doubles. + +2002-08-01 Erik de Castro Lopo + + * src/common.h + Defined SF_COUNT_MAX_POSITIVE() macro, a portable way of setting variables + of type sf_count_t to their maximum positive value. + + * src/dwvw.c src/w64.c + Used SF_COUNT_MAX_POSITIVE(). + +2002-07-31 Erik de Castro Lopo + + * src/paf.c + Fixed bug in reading/writing of 24 bit PCM PAF files on big endian systems. + + * tests/floating_point_tests.c + Fixed hash values for 24 bit PCM PAF files. + Disabled file has check if lrintf() function is not available and added + warning. + Decreased level of signal from a peak of 1.0 to a value of 0.95 to prevent + problems on platforms without lrintf() ie Solaris. + +2002-07-30 Erik de Castro Lopo + + * src/wav.c + Fixed a problem with two different kinds of mal-formed WAV file header. The + first had the 'fact' chunk before the 'fmt ' chunk, the other had an + incomplete 'INFO' chunk at the end of the file. + + * src/w64.c + Added fix to allow differentiation between W64 files and ACID files. + + * src/au_g72x.c src/common.h src/sndfile.c + Added error for G72x encoded files with more than one channel. + + * tests/pcm_test.tpl tests/utils.tpl + Moved function check_file_hash_or_die() to utils.tpl. Function was then + modified to calculate the has of the whole file. + + * src/wav.c + Fixed problem writing the 'fact' chunk on big endian systems. + + * tests/sfconvert.c + Fixed bug where .paf files were being written as Sphere NIST. + +2002-07-29 Erik de Castro Lopo + + * src/voc.c + Fix for reading headers generated using SFC_UPDATE_HEADER_NOW. + + * doc/command.html + Add docs for SFC_UPDATE_HEADER_NOW and SFC_SET_UPDATE_HEADER_AUTO. + +2002-07-28 Erik de Castro Lopo + + * man/sndfile-info.1 man/sndfile-play.1 + Added manpages supplied by Joshua Haberman the Debian maintainer for + libsndfile. Additional tweaks by me. + + * configure.in man/Makefile.am + Hooked manpages into autoconf/automake system. + + * src/sndfile.c + Added hooks for SFC_SET_UPDATE_HEADER_AUTO. + + * tests/update_header_test.c + Improved rigor of testing. + + * src/*.c + Fixed problem with *_write_header() functions. + +2002-07-27 Erik de Castro Lopo + + * doc/*.html + Updates to documentation to fix problems found by wdg-html-validator. + + * src/common.h src/command.c + Added normalize parameter to calls to psf_calc_signal_max() and + psf_calc_max_all_channels(). + + * src/sndfile.c + Added handling for commands SFC_CALC_NORM_SIGNAL_MAX and + SFC_CALC_NORM_MAX_ALL_CHANNELS. + + * doc/command.html + Added entry for SFC_CALC_NORM_SIGNAL_MAX and SFC_CALC_NORM_MAX_ALL_CHANNELS. + +2002-07-26 Erik de Castro Lopo + + * examples/sndfile-play.c Win32/Makefile.msvc + Get sndfile-play program working on Win32. The Win32 PCM sample I/O API + sucks. The sndfile-play program now works on Linux, MacOSX, Solaris and + Win32. + +2002-07-25 Erik de Castro Lopo + + * doc/FAQ.html + New file for frequently asked questsions. + +2002-07-22 Erik de Castro Lopo + + * doc/api.html + Documentation fixes. + + * src/au.[ch] src/au_g72x.c src/G72x/g72x.h + Add support of 40kbps G723 ADPCM encoding. + + * tests/lossy_comp_test.c tests/floating_point_test.c + Add tests for 40kbps G723 ADPCM encoding. + + * doc/index.html + Update support matrix. + +2002-07-21 Erik de Castro Lopo + + * doc/command.html + Documented SFC_GET_SIMPLE_FORMAT_COUNT, SFC_GET_SIMPLE_FORMAT, + SFC_GET_FORMAT_* and SFC_SET_ADD_PEAK_CHUNK. + + * src/sndfile.c src/pcm.c + Add ability to turn on and off the addition of a PEAK chunk for floating + point WAV and AIFF files. + + * src/sndfile.[ch] src/common.h src/command.c + Added sf_command SFC_CALC_MAX_ALL_CHANNELS. Implemented by Maurizio Umberto + Puxeddu. + + * doc/command.html + Docs for SFC_CALC_MAX_ALL_CHANNELS (assisted by Maurizio Umberto Puxeddu). + +2002-07-18 Erik de Castro Lopo + + * src/sndfile.c src/gsm610.c + Finalised support for GSM 6.10 AIFF files and added support for GSM 6.10 + encoded RAW (header-less) files. + + * src/wav.c + Add support for IBM_FORMAT_MULAW and IBM_FORMAT_ALAW encodings. + + * src/api.html + Fixed more documentation bugs. + +2002-07-17 Erik de Castro Lopo + + * src/sndfile.h src/common.h + Moved some yet-to-be-implelmented values for SF_FORMAT_* from the public + header file sndfile.h to the private header file common.h to avoid + confusion about the actual capabilities of libsndfile. + +2002-07-16 Erik de Castro Lopo + + * src/aiff.c src/wav.c + Fixed file parsing for WAV and AIFF files containing non-audio data after + the data chunk. + + * src/aiff.c src/sndfile.c + Add support for GSM 6.10 encoded AIFF files. + + * tests/lossy_comp_test.c tests/Makefile.am + Add tests for GSM 6.10 encoded AIFF files. + + * src/*.c + Fix compiler warnings. + +2002-07-15 Erik de Castro Lopo + + * tests/command_test.c + For SFC_SET_NORM_* tests, change the file format from SF_FORMAT_WAV to + SF_FORMAT_RAW. + + * src/sndfile.c + Added sf_command(SFC_TEST_ADD_TRAILING_DATA) to allow testing of reading + from AIFF and WAV files with non-audio data after the audio chunk. + + * src/common.h + Add test commands SFC_TEST_WAV_ADD_INFO_CHUNK and + SFC_TEST_AIFF_ADD_INST_CHUNK. When these commands are working, they will be + moved to src/sndfile.h + + * src/aiff.c src/wav.c + Begin implementation of XXXX_command() hook for sf_command(). + + * tests/write_read_test.tpl + Added sf_command (SFC_TEST_ADD_TRAILING_DATA) to ensure above new code was + working. + +2002-07-13 Erik de Castro Lopo + + * tests/update_header_test.c + Allow read sample count == write sample count - 1 to fix problems with VOC + files. + + * tests/write_read_test.tpl tests/pcm_test.tpl + Fixed some problems in the test suite discovered by using Valgrind. + +2002-07-12 Erik de Castro Lopo + + * tests/utils.[ch] tests/*.c + Renamed check_log_buffer() to check_log_buffer_or_die(). + + * src/sndfile.c + SFC_UPDATE_HEADER_NOW and SFC_SETUPDATE_HEADER_AUTO almost finished. Works + for all file formats other than VOC. + +2002-07-11 Erik de Castro Lopo + + * src/sndfile.[ch] src/common.h + Started adding functionality to allow the file header to be updated before + the file is closed on files open for SFM_WRITE. This was requested by + Maurizio Umberto Puxeddu who is using libsndfile for file I/O in iCSound. + + * tests/update_header_test.c + New test program to test that the above functionality is working correctly. + + * tests/peak_chunk_test.c tests/floating_point_test.c + Cleanups. + +2002-07-10 Erik de Castro Lopo + + * src/sfendian.[ch] + Changed length count parameters for all endswap_XXX() functions from + sf_count_t (which can be 64 bit even on 32 bit architectures) to int. These + functions are only called frin inside the library, are always called with + integer parameters and doing the actual calculation on 64 bit values is + slow in comparision to doing it on ints. + + * examples/sndfile-play.c + More playback hacking for Win32. + +2002-07-09 Erik de Castro Lopo + + * src/common.c + In psf_log_printf(), changed %D format conversion specifier to %M (marker) and + added %D specifier for printing the sf_count_t type. + + * src/*.c + Changed all usage of psf_log_printf() with %D format conversion specifiers + to use %M conversion instead. + + * tests/pcm_test.tpl tests/pcm_test.def + New files to autogen pcm_test.c. + + * src/pcm.c + Fixed bug in scaling floats and doubles to 24 bit PCM and vice versa. + +2002-07-08 Erik de Castro Lopo + + * configure.in + Fix setup of $ac_cv_sys_largefile_CFLAGS so that sndfile.pc gets valid + values for CFLAGS. + + * examples/sndfile-play.c + Start adding playback support for Win32. + +2002-07-07 Erik de Castro Lopo + + * src/*.c + Worked to removed compiler warnings. + Extensive refactoring. + + * src/common.[ch] + Added function psf_memset() which works like the standard C function memset + but takes and sf_count_t as the length parameter. + + * src/sndfile.c + Replaced calls to memset(0 with calls to psf_memset() as required. + +2002-07-06 Erik de Castro Lopo + + * src/sndfile.c + Added "libsndfile : " to the start of all error messages. This was suggested + by Conrad Parker author of Sweep ( http://sweep.sourceforge.net/ ). + + * src/sfendian.[ch] + Added endswap_XXXX_copy() functions. + + * src/pcm.c src/float32.c src/double64.c + Use endswap_XXXX_copy() functions and removed dead code. + Cleanups and optimisations. + +2002-07-05 Erik de Castro Lopo + + * src/sndfile.c src/sndfile.h + Gave values to all the SFC_* enum values to allow better control of the + interface as commands are added and removed. + Added new command SFC_SET_ADD_PEAK_CHUNK. + + * src/wav.c src/aiff.c + Modified wav_write_header and aiff_write_header to make addition of a PEAK + chunk optional, even on floating point files. + + * tests/benchmark.tpl + Added call to sf_command(SFC_SET_ADD_PEAK_CHUNK) to turn off addition of a + PEAK chunk for the benchmark where we are trying to miximize speed. + + * src.pcm.c + Changed tribyte typedef to something more sensible. + Further conversion speed ups. + +2002-07-03 Erik de Castro Lopo + + * src/command.c + In major_formats rename "Sphere NIST" to "NIST Sphere". + + * src/common.c src/sfendian.c + Moved all endswap_XXX_array() functions to sfendian.c. These functions will + be tweaked to provide maximum performance. Since maximum performance on one + platform does not guarantee maximum performance on another, a small set of + functions will be written and the optimal one chosen at compile time. + + * src/common.h src/sfendian.h + Declarations of all endswap_XXX_array() functions moved to sfendian.h. + + * src/Makefile.am + Add sfendian.c to build targets. + +2002-07-01 Erik de Castro Lopo + + * src/pcm.c src/sfendian.h + Re-coded PCM encoders and decoders to match or better the speed of + libsndfile version 0.0.28. + +2002-06-30 Erik de Castro Lopo + + * src/wav.c + Add checking for WAVPACK data in standard PCM WAV file. Return error if + found. This WAVPACK is *WAY* broken. It uses the same PCM WAV file header + and then stores non-PCM data. + + * tests/benchmark.tpl + Added more tests. + +2002-06-29 Erik de Castro Lopo + + * tests/benchmark.tpl + Added conditional definition of M_PI. + For Win32, set WRITE_PERMS to 0777. + + * Win32/Makefile.msvc + Added target to make generate program on Win32. + + * src/samplitude.c + Removed handler for Samplitude RAP file format. This file type seems rarer + than hens teeth and is completely undocumented. + + * src/common.h src/sndfile.c src/Makefile.am Win32/Makefile.msvc + Removed references to sampltiude RAP format. + + * tests/benchmark.tpl + Benchmark program now prints the libsndfile version number when run. This + program was also backported to version 0 to compare results. Version + 1.0.0rc2 is faster than version 0.0.28 on most conversions but slower on + some. The slow ones need to be fixed before final release. + +2002-06-28 Erik de Castro Lopo + + * tests/benchmark.def tests/benchmark.tpl + New files which generate tests/benchmark.c using Autogen. Added int -> + SF_FORMAT_PCM_24 test. + + * tests/benchmark.c + Now and Autogen output file. + + * tests/Makefile.am + Updated for above changes. + +2002-06-27 Erik de Castro Lopo + + * tests/benchmark.c + Basic benchmark program complete. Need to convert it to Autogen. + + * Win32/Makefile.msvc + Added benchmark.exe target. + +2002-06-26 Erik de Castro Lopo + + * examples/generate.c + New program to generate a number of different output file formats from a + single input file. This allows testing of the created files. + + * tests/benchmark.c + New test program to benchmark libsndfile. Nowhere near complete yet. + + * examples/Makefile.am tests/Makefile.am + New make rules for the two new programs. + +2002-06-25 Erik de Castro Lopo + + * Win32/libsndfile.def + Removed definition for sf_signal_max(). + + * src/sndfile.c + Removed cruft. + + * doc/index.html + A number of documentation bugs were fixed. Thanks to Anand Kumria. + + * doc/version-1.html + Minor doc updates. + + * configure.in + Bumped version to 1.0.0rc2. + + * src/sf_command.h src/Makefile.am + Removed the header file as it was no longer being used. Thanks to Anand + Kunria for spotting this. + + * doc/index.html + A number of documentation bugs were fixed. Thanks to Anand Kumria. + +2002-06-24 Erik de Castro Lopo + + * src/common.h + Test for Win32 before testing SIZEOF_OFF_T so that it works correctly + on Win32.. + + * src/file_io.c + Win32 fixes to ensure O_BINARY is used for file open. + + * doc/win32.html + New file documenting the building libsndfile on Win32. + + * doc/*.html + Updating of documentation. + +2002-06-23 Erik de Castro Lopo + + * tests/pcm_test.c + Minor changes to allow easier determination of test file name. + + * src/sndfile.[ch] + Removed function sf_signal_max(). + + * examples/sndfile-play.c + Changed call to sf_signal_max() to a call to sf_command(). + +2002-06-22 Erik de Castro Lopo + + * src/format.c src/command.c + Renamed format.c to command.c which will now include code for sf_command() + calls to perform operations other than format commands. + + * src/sndfile.c src/sndfile.h + Removed function sf_get_signal_max() which is replaced by commands passed + to sf_command(). + + * src/command.c + Implement commands SFC_CALC_SIGNAL_MAX. + + * doc/command.html + Documented SFC_CALC_SIGNAL_MAX. + +2002-06-21 Erik de Castro Lopo + + * examples/sndfile-play.c + Mods to make sndfile-play work on Solaris. The program sndfile-play now + runs on Linux, MaxOSX and Solaris. Win32 to come. + + * src/format.c + Added SF_FORMAT_DWVW_* to subtype_formats array. + + * src/nist.c + Added support for 8 bit NIST Sphere files. Example file supplied by Anand + Kumria. + +2002-06-20 Erik de Castro Lopo + + * examples/sndfile-info.c + Tidy up of output format. + + * examnples/sndfile-play.c + Mods to make sndfile-play work on MacOSX using Apple's CoreAudio API. + + * configure.in + Add new variables OS_SPECIFIC_INCLUDES and OS_SPECIFIC_LINKS which were + required to supply extra include paths and link parameters to get + sndfile-play working on MacOSX. + + * examples/Makefile.am + Use OS_SPOECIFIC_INCLUDES and OS_SPECIFIC_LINKS to build commands for + sndfile-play. + +2002-06-19 Erik de Castro Lopo + + * src/nist.c + Added ability to read/write new NIST Sphere file types (A-law, u-law). + Header parser was re-written from scratch. Example files supplied by Anand + Kumria. + + * src/sndfile.c + Support for A-law and u-law NIST files. + + * tests/Makefile.am tests/lossy_comp_test.c + Tests for A-law and u-law NIST files. + +2002-06-18 Erik de Castro Lopo + + * tests/utils.c + Fixed an error in error string. + +2002-06-17 Erik de Castro Lopo + + * acinclude.m4 + Removed exit command to allow cross-compiling. + + * Win32/unistd.h src/file_io.c + Moved contents of first file into the second file (enclosed in #ifdef). + Win32/unistd.h is now an empty file but still must be there for libsndfile + to compile on Win32. + + * src/sd2.c, src/sndfile.c: + Fixes for Sound Designer II files on big endian systems. + +2002-06-16 Erik de Castro Lopo + + * configure.in + Modified to work around problems with crappy MacOSX version of sed. + Added sanity check for proper values for CFLAGS. + +2002-06-14 Erik de Castro Lopo + + * src/sndfile.c + Code clean up in sf_open (). + + * Win32/Makefile.msvc + Michael Fink's contributed MSVC++ makefile was hacked to bits and put back + together in a new improved form. + + * src/file_io.c + Fixes for Win32; _lseeki64() returns an invalid argument for calls like + _lseeki64(fd, 0, SEEK_CUR) so need to use _telli64 (fd) instead. + + * src/common.h src/sndfile.c src/wav.c src/aiff.c + Added SFE_LOG_OVERRUN error. + Added termination for potential infinite loop when parsing file headers. + + * src/wav.c src/w64.c + Fixed bug casuing incorrect header generation when opening file read/write. + +2002-06-12 Erik de Castro Lopo + + * doc/api.html + Improved the documentation to make it clearer that the file read method + and the underlying file format are completely disconnected. Suggested + by Josh Green. + + * doc/command.html + Started correcting docs to take into account changes made to the + operations of the sf_command () function. Not complete yet. + + * src/sndfile.c + Reverted some changes which had broken the partially working SDII header + parsing. Now have access to an iBook with OS X so reading and writing SDII + files on all platforms should be a reality in the near future. On Mac this + will involve reading the resource fork via the standard MacOS API. To move + a file from Mac to another OS, the resource and data forks will need to be + combined before transfer. The combined file will be read on both Mac and + other OSes like any other file. + +2002-06-08 Erik de Castro Lopo + + * ltmain.sh + Applied a patch from http://fink.sourceforge.net/doc/porting/libtool.php + which allows libsndfile to compile on MacOSX 10.1. This patch should not + interfere with compiling on other OSes. + + * src/GSM610/private.h + Changes to fix compile problems on MacOSX (see src/GSM610/ChangeLog). + + * src/float_cast.h + Added MacOSX replacements for lrint() and lrintf(). + +2002-06-05 Erik de Castro Lopo + + * src/sndfile.c + Replaced the code to print the filename to the log buffer when a file is + opened. This code seems to have been left out during the merge of + sf_open_read() and sf_open_write() to make a single functions sf_open(). + +2002-06-01 Erik de Castro Lopo + + * src/wav.c + Fixed a bug where the WAV header parser was going into an infinite loop + on a badly formed LIST chunk. File supplied by David Viens. + +2002-05-25 Erik de Castro Lopo + + * configure.in + Added a message at the end of the configuration process to warn about the + need for the use of pkg-config when linking programs against version 1 of + libsndfile. + + * doc/pkg-config.html + New documentation file containing details of how to use pkg-config to + retrieve settings for CFLAGS and library locations for linking files + against version 1 of libsndfile. + +2002-05-17 Erik de Castro Lopo + + * src/wav.c + Fixed minor bug in handling of so-called ACIDized WAV files. + +2002-05-16 Erik de Castro Lopo + + * Win32/libsndfile.def Win32/Makefile.msvc + Two new files contributed by Michael Fink (from the winLAME project) + which allows libsndfile to be built on windows in a MSDOS box by doing + "nmake -f Makefile.msvc". Way cool! + +2002-05-15 Erik de Castro Lopo + + * configure.in + MacOSX is SSSOOOOOOO screwed up!!! I can't believe how hard it is to + generate a tarball which will configure and compile on that platform. + Joined the libtool mailing list to try and get some answers. + +2002-05-13 Erik de Castro Lopo + + * configure.in + Changed to autoconf version 2.50. MacOSX uses autoconf version 2.53 which + is incompatible with with version 2.13 which had been using until now. + The AC_SYS_LARGE_FILE macro distributed withe autoconf 2.50 is missing a + few features so AC_SYS_EXTRA_LARGE file was defined to replace it. + + * configure.in + Changed to automake version 1.5 to try and make a tarball which will + work on MacOSX. + +2002-05-12 Erik de Castro Lopo + + * src/wav_gsm610.c + Changed name to gsm610.c. Added reading/writing of headerless files. + + * src/sndfile.c src/raw.c + Added ability to read/write headerless (SF_FORMAT_RAW) GSM 6.10 files. + +2002-05-11 Erik de Castro Lopo + + * tests/lossy_comp_test.c + Clean up in preparation for Autogen-ing this file. + + * src/GSM610/*.[ch] + Code cleanup and prepartion forgetting file seek working. Details in + src/GSM610/ChangeLog. + + * sndfile.pc.in + Testing complete. Is sndfile.m4 still needed? + +2002-05-09 Erik de Castro Lopo + + * tests/write_read_test.tpl tests/rdwr_test.tpl + Merged tests from these two programs into write_read_test.tpl and deleted + rdwr_test.tpl. + +2002-05-08 Erik de Castro Lopo + + * src/w64.c src/svx.c src/paf.c + Fixed bugs in read/write mode. + +2002-05-07 Erik de Castro Lopo + + * examples/Makefile.am + Renamed sfplay.c to sndfile-play.c and sndfile_info.c to sndfile-info.c for + consistency when these programs become part of the Debian package + sndfile-programs. + + * sndfile.pc.in + New file to replace sndfile-config.in. Libsndfile now uses the pkg-config + model for providing installation parameters to dependant programs. + + * src/sndfile.c + Cleanup of code in sf_open(). + +2002-05-06 Erik de Castro Lopo + + * tests/utils.tpl tests/write_read_test.tpl + More conversion to Autogen fixes and enchancements. + + * src/*.c + Read/write mode is now working for 16, 24 and 32 bit PCM as well as 32 + bit float and 64 bit double data. More tests still required. + + * src/Makefile.am + Added DISTCLEANFILES target to remove config.status and config.last. + + * Win32/Makefile.am MacOS/Makefile.am + Added DISTCLEANFILES target to remove Makefile. + +2002-05-05 Erik de Castro Lopo + + * src/*.[ch] tests/rdwr_test.c + More verifying workings of read/write mode. Fixing bugs found. + + * tests/utils.[ch] + Made these files Autogen generated files. + + * tests/util.tpl tests/util.def + New Autogen files to generate utils.[ch]. Moved some generic test functions + into this file. Autogen is such a great tool! + +2002-05-03 Erik de Castro Lopo + + * src/pcm.c src/float_cast.h Win32/config.h + Fixed a couple of Win32 specific bugs pointed out by Michael Fink + (maintainer of WinLAME) and David Viens. + + * tests/check_log_buffer.[ch] tests/utils.[ch] + Moved check_log_buffer() to utils.[ch] and deleted old file. + +2002-05-02 Erik de Castro Lopo + + * src/common.[ch] src/sndfile.c + New function psf_default_seek() which will be the default seek function + for things like PCM and floating point data. This default is set for + both read and write in sf_open() but can be over-ridden by any codec + during it's initialisation. + +2002-05-01 Erik de Castro Lopo + + * src/au.c + AU files use a data size value of -1 to mean unknown. Fixed au_open_read() + to allow opening files like this. + + * tests/rdwr_test .c + Added more tests. + + * src/sndfile.c + Fixed bugs in read/write mode found due to improvements in the test + program. + +2002-04-30 Erik de Castro Lopo + + * tests/rdwr_test .c + New file for testing read/write mode. + +2002-04-29 Erik de Castro Lopo + + * m4/* + Removed all m4 macros from this directory as they get concatenated to form + the file aclocal.m4 anyway. + + * sndfile.m4 + Moved this from the m4 directory to the root directory asn this is part of + the distribution and is installed during "make install". + +2002-04-29 Erik de Castro Lopo + + * src/float32.c + Removed logging of peaks for all file formats other than AIFF and WAV. + + * tests/write_read_test.tpl tests/write_read_test.def + New files which autogen uses to generate write_read_test.c. Doing it this + way makes write_read_test.c far easier to maintain. Other test programs + will be converted to autogen in the near future. + + * src/*.c + Fixed a few bugs found when testing on Sparc (bug endian) Solaris. + +2002-04-28 Erik de Castro Lopo + + * doc/*.html + Fixed documention versioning. + + * configure.in + Fixed a bug in the routines which search for Large File Support on systems + which have large file support by defualt. + +2002-04-27 Erik de Castro Lopo + + * src/*.[ch] + Found and fixed an issue which can cause a bug in other software (I was + porting Conrad Parker's Sweep program from version 0 of the library to + version 1). When opening a file for write, the libsndfile code would + set the sfinfo.samples field to a maximum value. + + * tests/write_read_test.c + Added tests to detect the above problem. + +2002-04-25 Erik de Castro Lopo + + * src/*.[ch] + Finished base implementation of read/write mode. Much more testing still + needed. + + * m4/largefile.m4 + Macro for detecting Large File Standard capabilities. This macro was ripped + out of the aclocal.m4 file of GNU tar-1.13. + + * configure.in + Added detection of large file support. Files larger than 2 Gigabytes should + now be supported on 64 bit platforms and many 32 bit platforms including + Linux (2.4 kernel, glibc-2.2), *BSD, MacOS, Win32. + + * libsndfile_convert_version.py + A Python script which attempts to autoconvert code written to use version 0 + to version 1. + +2002-04-24 Erik de Castro Lopo + + * src/*.[ch] + Finished base implementation of read/write mode. Much more testing still + needed. + + * tests/write_read_test.c + Preliminary tests for read/write mode added. More needed. + +2002-04-20 Erik de Castro Lopo + + * src/sndfile.[ch] + Removed sf_open_read() and sf_open_write() functions,replacting them with + sf_open() which takes an extra mode parameter (SF_OPEN_READ, SF_OPEN_WRITE, + or SF_OPEN_RDWR). This new function sf_open can now be modified to allow + opening a file formodification (RDWR). + +2002-04-19 Erik de Castro Lopo + + * src/*.c + Completed merging of separate xxx_open_read() and xxx_open_write() + functions. All tests pass. + +2002-04-18 Erik de Castro Lopo + + * src/au.c + Massive refactoring required to merge au_open_read() with au_open_write() + to create au_open(). + +2002-04-17 Erik de Castro Lopo + + * src/*.c + Started changes required to allow a sound file to be opened in read/write + mode, with separate file pointers for read and write. This involves merging + of encoder/decoder functions like pcm_read_init() and pcm_write_init() + int a new function pcm_init() as well as doing something similar for all + the file type specific functions ie aiff_open_read() and aiff_open_write() + were merged to make the function aiff_open(). + +2002-04-15 Erik de Castro Lopo + + * src/file_io.c + New file containing psf_fopen(), psf_fread(), psf_fwrite(), psf_fseek() and + psf_ftell() functions. These function will replace use of fopen/fread/fwrite + etc and allow access to files larger than 2 gigabytes on a number of 32 bit + OSes (Linux on x86, 32 bit Solaris user space apps, Win32 and MacOS). + + * src/*.c + Replaced all instances of fopen with psf_open, fread with psd_read, fwrite + with psf_write and so on. + +2002-03-11 Erik de Castro Lopo + + * src/dwvw.c + Finally fixed all known problems with 12, 16 and 24 bit DWVW encoding. + + * tests/floating_point_test.c + Added tests for 12, 16 and 24 bit DWVW encoding. + +2002-03-03 Erik de Castro Lopo + + * m4/endian.m4 + Defines a new m4 macro AC_C_FIND_ENDIAN, for determining the endian-ness of + the target CPU. It first checks for the definition of BYTE_ORDER in + , then in and . If none of these work + and the C compiler is not a cross compiler it compiles and runs a program + to test for endian-ness. If the compiler is a cross compiler it makes a + guess based on $target_cpu. + + * configure.in + Modified to use AC_C_FIND_ENDIAN. + + * src/sfendian.h + Simplified. + +2002-02-23 Erik de Castro Lopo + + * tests/floating_point_test.c + Tests completely rewritten using the dft_cmp function. Now able to + calculate a quick guesstimate of the Signal to Noise Ratio of the encoder. + +2002-02-15 Erik de Castro Lopo + + * tests/dft_cmp.[ch] + New files containing functions for comparing pre and post lossily + compressed data using a quickly hacked DFT. + + * tests/utils.[ch] + New files containing functions for saving pre and post encoded data in a + file readable by the GNU Octave package. + +2002-02-13 Erik de Castro Lopo + + * m4/lrint.m4 m4/lrintf.m4 + Fixed m4 macros to define HAVE_LRINT and HAVE_LRINTF even when the test + is cached. + +2002-02-12 Erik de Castro Lopo + + * tests/floating_point_test.c + Fixed improper use of strncat (). + +2002-02-11 Erik de Castro Lopo + + * tests/headerless_test.c + New test program to test the ability to open and read a known file type as a + RAW header-less file. + +2002-02-07 Erik de Castro Lopo + + * tests/losy_comp_test.c + Added a test to ensure that the data read from a file is not all zeros. + + * examples/sfconvert.c + Added "-gsm610" encoding types. + +2002-01-29 Erik de Castro Lopo + + * examples/sfconvert.c + Added "-dwvw12", "-dwvw16" and "-dwvw24" encoding types. + + * tests/dwvw_test.c + New file for testing DWVW encoder/decoder. + +2002-01-28 Erik de Castro Lopo + + * src/dwvw.c + Implemented writing of DWVW. 12 bit seems to work, 16 and 24 bit still broken. + + * src/aiff.c + Improved reporting of encoding types. + + * src/voc.c + Clean up. + +2002-01-27 Erik de Castro Lopo + + * src/dwvw.c + New file implementing lossless Delta Word Variable Width (DWVW) encoding. + Reading 12 bit DWVW is now working. + + * src/aiff.c common.h sndfile.c + Added hooks for DWVW encoded AIFF and RAW files. + +2002-01-15 Erik de Castro Lopo + + * src/w64.c + Robustify header parsing. + + * src/wav_w64.h + Header file wav.h was renamed to wav_w64.h to signify sharing of + definitions across the two file types. + + * src/wav.c src/w64.c src/wav_w64.c + Refactoring. + Modified and moved functions with a high degree of similarity between + wav.c and w64.c to wav_w64.c. + +2002-01-14 Erik de Castro Lopo + + * src/w64.c + Completed work on getting read and write working. + + * examples/sfplay.c + Added code to scale floating point data so it plays at a reasonable volume. + + * tests/Makefile.am tests/write_read_test.c + Added tests for W64 files. + +2002-01-13 Erik de Castro Lopo + + * src/*.c + Modded all code in file header writing routines to use + psf_new_binheader_writef(). + Removed psf_binheader_writef() from src/common.c. + Globally replaced psf_new_binheader_writef with psf_binheader_writef. + +2002-01-12 Erik de Castro Lopo + + * src/*.c + Modded all code in file parsing routines to use psf_new_binheader_readf(). + Removed psf_binheader_readf() from src/common.c. + Globally replaced psf_new_binheader_readf with psf_binheader_readf. + + * src/common.[ch] + Added new function psf_new_binheader_writef () which will soon replace + psf_binheader_writef (). The new function has basically the same function + as the original but has a more flexible and capable interface. It also + allows the writing of 64 bit integer values for files contains 64 bit file + offsets. + +2002-01-11 Erik de Castro Lopo + + * src/formats.c src/sndfile.c src/sndfile.h + Added code allowing full enumeration of supported file formats via the + sf_command () interface. + This feature will allow applications to avoid needing recompilation when + support for new file formats are added to libsndfile. + + * tests/command_test.c + Added test code for the above feature. + + * examples/list_formats.c + New file. An example of the use of the supported file enumeration + interface. This program lists all the major formats and for each major + format the supported subformats. + +2002-01-10 Erik de Castro Lopo + + * src/*.[ch] tests/*.c + Changed command parameter of sf_command () function from a test string to + an int. The valid values for the command parameter begin with SFC_ and are + listed in src/sndfile.h. + +2001-12-20 Erik de Castro Lopo + + * src/formats.c src/sndfile.c + Added an way of enumerating a set of common file formats using the + sf_command () interface. This interface was suggested by Dominic Mazzoni, + one of the main authors of Audacity (http://audacity.sourceforge.net/). + +2001-12-26 Erik de Castro Lopo + + * src/sndfile.c + Added checking of filename parameter in sf_open_read (). Previousy, if a + NULL pointer was passed the library would segfault. + +2001-12-18 Erik de Castro Lopo + + * src/common.c src/common.h + Changed the len parameter of the endswap_*_array () functions from type + int to type long. + + * src/pcm.c + Fixed a problem which + +2001-12-15 Erik de Castro Lopo + + * src/sndfile.c + Added conditional #include for EMX/gcc on OS/2. Thanks to + Paul Hartman for pointing this out. + + * tests/lossy_comp_test.c tests/floating_point_test.c + Added definitions for M_PI for when it isn't defined in . + +2001-11-30 Erik de Castro Lopo + + * src/ircam.c + Re-implemented the header reader. Old version was making incorrect + assumptions about the endian-ness of the file from the magic number at the + start of the file. The new code looks at the integer which holds the + number of channels and determines the endian-ness from that. + +2001-11-30 Erik de Castro Lopo + + * src/aiff.c + Added support for other AIFC types ('raw ', 'in32', '23ni'). + Further work on IMA ADPCM encoding. + +2001-11-29 Erik de Castro Lopo + + * src/ima_adpcm.c + Renamed from wav_ima_adpcm.c. This file will soon handle IMA ADPCM + encodings for both WAV and AIFF files. + + * src/aiff.c + Started adding IMA ADPCM support. + +2001-11-28 Erik de Castro Lopo + + * src/double.c + New file for handling double precision floating point (SF_FORMAT_DOUBLE) + data. + + * src/wav.c src/aiff.c src/au.c src/raw.c + Added support for SF_FORMAT_DOUBLE data. + + * src/common.[ch] + Addition of endswap_long_array () for endian swapping 64 bit integers. This + function will work correctly on processors with 32 bit and 64 bit longs. + Optimised endswap_short_array () and endswap_int_array (). + + * tests/pcm_test.c + Added and extra check. After the first file of each type is written to disk + a checksum is performed of the first 64 bytes and checked against a pre- + calculated value. This will work whatever the endian-ness of the host + machine. + +2001-11-27 Erik de Castro Lopo + + * src/aiff.c + Added handling of u-law, A-law encoded AIFF files. Thanks to Tom Erbe for + supplying example files. + + * tests/lossy_comp_test.c + Added tests for above. + + * src/common.h src/*.c + Removed function typedefs from common.h and function pointer casting in all + the other files. This allows the compiler to perform proper type checking. + Hopefully this will prevernt problems like the sf_seek bug for OpenBSD, + BeOS etc. + + * src/common.[ch] + Added new function psf_new_binheader_readf () which will eventually replace + psf_binheader_readf (). The new function has basically the same function as + the original but has a more flexible and capable interface. It also allows + the reading of 64 bit integer values for files contains 64 bit file + offsets. + +2001-11-26 Erik de Castro Lopo + + * src/voc.c + Completed implementation of VOC file handling. Can now handle 8 and 16 bit + PCM, u-law and A-law files with one or two channels. + + * src/write_read_test.c tests/lossy_comp_test.c + Added tests for VOC files. + +2001-11-22 Erik de Castro Lopo + + * src/float_cast.h + Added inline asm version of lrint/lrintf for MacOS. Solution provided by + Stephane Letz. + + * src/voc.c + More work on this braindamaged format. The VOC files produced by SoX also + have a number of inconsistencies. + +2001-11-19 Erik de Castro Lopo + + * src/paf.c + Added support for 8 bit PCM PAF files. + + * tests/write_read_test.c + Added tests for 8 bit PAF files. + +2001-11-18 Erik de Castro Lopo + + * tests/pcm_test.c + New test program to test for correct scaling of integer values between + different sized integer containers (ie short -> int). + The new specs for libsndfile state that when the source and destination + containers are of a different size, the most significant bit of the source + value becomes the most significant bit of the destination container. + + * src/pcm.c src/paf.c + Modified to pass the above test program. + + * tests/write_read_test.c tests/lossy_comp_test.c + Modified to work with the new scaling rules. + +2001-11-17 Erik de Castro Lopo + + * src/raw.c tests/write_read_test.c tests/write_read_test.c + Added ability to do raw reads/writes of float, u-law and A-law files. + + * src/*.[ch] examples/*.[ch] tests/*.[ch] + Removed dependance on pcmbitwidth field of SF_INFO struct and moved to new + SF_FORMAT_* types and use of SF_ENDIAN_BIG/LITTLE/CPU. + +2001-11-12 Erik de Castro Lopo + + * src/*.[ch] + Started implmentation of major changes documented in doc/version1.html. + + Removed all usage of off_t which is not part of the ISO C standard. All + places which were using it are now using type long which is the type of + the offset parameter for the fseek function. + This should fix problems on BeOS, MacOS and *BSD like systems which were + failing "make check" because sizeof (long) != sizeof (off_t). + +-------------------------------------------------------------------------------- +This is the boundary between version 1 of the library above and version 0 below. +-------------------------------------------------------------------------------- + +2001-11-11 Erik de Castro Lopo + + * examples/sfplay_beos.cpp + Added BeOS version of sfplay.c. This needs to be compiled using a C++ + compiler so is therefore not built by default. Thanks to Marcus Overhagen + for providing this. + +2001-11-10 Erik de Castro Lopo + + * examples/sfplay.c + New example file showing how libsndfile can be used to read and play a + sound file. + At the moment on Linux is supported. Others will follow in the near future. + +2001-11-09 Erik de Castro Lopo + + * src/pcm.c + Fixed problem with normalisation code where a value of 1.0 could map to + a value greater than MAX_SHORT or MAX_INT. Thanks to Roger Dannenberg for + pointing this out. + +2001-11-08 Erik de Castro Lopo + + * src/pcm.c + Fixed scaling issue when reading/writing 8 bit files using + sf_read/sf_write_short (). + On read, values are scaled so that the most significant bit in the char + ends up in the most significant bit of the short. On write, values are + scaled so that most significant bit in the short ends up as the most + significant bit in the char. + +2001-11-07 Erik de Castro Lopo + + * src/au.c src/sndfile.c + Added support for 32 bit float data in big and little endian AU files. + + * tests/write_read_test.c + Added tests for 32 bit float data in AU files. + +2001-11-06 Erik de Castro Lopo + + * tests/lossy_comp_test.c + Finalised testing of stereo files where possible. + +2001-11-05 Erik de Castro Lopo + + * src/wav_ms_adpcm.c + Fixed bug in writing stereo MS ADPCM WAV files. Thanks to Xu Xin for + pointing out this problem. + +2001-10-24 Erik de Castro Lopo + + * src/wav_ms_adpcm.c + Modified function srate2blocksize () to handle 44k1Hz stereo files. + +2001-10-21 Erik de Castro Lopo + + * src/w64.c + Added support for Sonic Foundry 64 bit WAV format. As Linux (my main + development platform) does not yet support 64 bit file offsets by default, + current handling of this file format treats everything as 32 bit and fails + openning the file, if it finds anything that goes beyond 32 bit values. + + * src/sndfile.[hc] src/common.h src/Makefile.am + Added hooks for W64 support. + +2001-10-21 Erik de Castro Lopo + + * configure.in + Added more warnings options to CFLAGS when the gcc compiler is detected. + + * src/*.[ch] tests/*.c examples/*.c + Started fixing the warning messages due to the new CFLASG. + + * src/voc.c + More work on VOC file read/writing. + + * src/paf.c + Found that PAF files were not checking the normalisation flag when reading + or writing floats and doubles. Fixed it. + + * tests/floating_point_test.c + Added specific test for the above problem. + + * src/float_cast.h src/pcm.c + Added a section for Win32 to define lrint () and lrintf () in the header + and implement it in the pcm.c + +2001-10-20 Erik de Castro Lopo + + * sndfile-config.in m4/sndfile.m4 + These files were donated by Conrad Parker who also provided instructions + on how to install them using autoconf/automake. + + * src/float_cast.h + Fiddled around with this file some more. On Linux and other gcc supported + OSes use the C99 functions lrintf() and lrint() for casting from floating + point to int without incurring the huge perfromance penalty (particularly + on the i386 family) caused by the regular C cast from float to int. + These new C99 functions replace the FLOAT_TO_* and DOUBLE_TO_* macros which + I had been playing with. + + * configure.in m4/lrint.m4 m4/lrintf.m4 + Add detection of these functions. + +2001-10-17 Erik de Castro Lopo + + * src/voc.c + Completed code for reading VOC files containing a single audio data + segment. + Started implementing code to handle files with multiple VOC_SOUND_DATA + segments but couldn't be bothered finishing it. Multiple segment files can + have different sample rates for different sections and other nasties like + silence and repeat segments. + +2001-10-16 Erik de Castro Lopo + + * src/common.h src/*.c + Removed SF_PRIVATE struct field fdata and replaced it with extra_data. + + * src/voc.c + Further development of the read part of this woefult file format. + +2001-10-04 Erik de Castro Lopo + + * src/float_cast.h + Implemented gcc and i386 floating point to int cast macros. Standard cast + will be used when not on gcc for i385. + + * src/pcm.c + Modified all uses of FLOAT/DOUBLE_TO_INT and FLOAT/DOUBLE_TO_SHORT casts to + comply with macros in float_cast.h. + +2001-10-04 Erik de Castro Lopo + + * src/voc.c + Changed the TYPE_xxx enum names to VOC_TYPE_xxx to prevent name clashes + on MacOS with CodeWarrior 6.0. + + * MacOS/MacOS-readme.txt + Updated the compile instructions. Probably still need work as I don't have + access to a Mac. + +2001-10-01 Erik de Castro Lopo + + * src/wav.c src/aiff.c common.c + Changed all references to snprintf to LSF_SNPRINTF and all vsnprintf to + LSF_VSNPRINTF. LSF_VSNPRINTF and LSF_VSNPRINTF are defined in common.h. + + * src/common.h + Added checking of HAVE_SNPRINTF and HAVE_VSNPRINTF and defining + LSF_VSNPRINTF and LSF_VSNPRINTF to appropriate values. + + * src/missing.c + New file containing a minimal implementation of snprintf and vsnprintf + functions named missing_snprintf and missing_vsnprintf respectively. These + are only compliled into the binary if snprintf and/or vsnprintf are not + available. + +2001-09-29 Erik de Castro Lopo + + * src/ircam.c + New file to handle Berkeley/IRCAM/CARL files. + + * src/sndfile.c src/common.h + Modified for IRCAM handling. + + * tests/*.c + Added tests for IRCAM files. + +2001-09-27 Erik de Castro Lopo + + * src/wav.c + Apparently microsoft windows (tm) doesn't like ulaw and Alaw WAV files with + 20 byte format chunks (contrary to ms's own documentation). Fixed the WAV + header writing code to generate smaller ms compliant ulaw and Alaw WAV + files. + +2001-09-17 Erik de Castro Lopo + + * tests/stdio_test.sh tests/stdio_test.c + Shell script was rewritten as a C program due to incompatibilities of the + sh shell on Linux and Solaris. + +2001-09-16 Erik de Castro Lopo + + * tests/stdio_test.sh tests/stdout_test.c tests/stdin_test.c + New test programs to verify the correct operation of reading from stdin and + writing to stdout. + + * src/sndfile.c wav.c au.c nist.c paf.c + Fixed a bugs uncovered by the new test programs above. + +2001-09-15 Erik de Castro Lopo + + * src/sndfile.c wav.c + Fixed a bug preventing reading a file from stdin. Found by T. Narita. + +2001-09-12 Erik de Castro Lopo + + * src/common.h + Fixed a problem on OpenBSD 2.9 which was causing sf_seek() to fail on IMA + WAV files. Root cause was the declaration of the func_seek typedef not + matching the functions it was actually being used to point to. In OpenBSD + sizeof (off_t) != sizeof (int). Thanks to Heikki Korpela for allowing me + to log into his OpenBSD machine to debug this problem. + +2001-09-03 Erik de Castro Lopo + + * src/sndfile.c + Implemented sf_command ("norm float"). + + * src/*.c + Implemented handling of sf_command ("set-norm-float"). Float normalization + can now be turned on and off. + + * tests/double_test.c + Renamed to floating_point_test.c. Modified to include tests for all scaled + reads and writes of floats and doubles. + + * src/au_g72x.c + Fixed bug in normalization code found with improved floating_point_test + program. + + * src/wav.c + Added code for parsing 'INFO' and 'LIST' chunks. Will be used for extract + text annotations from WAV files. + + * src/aiff.c + Added code for parsing '(c) ' and 'ANNO' chunks. Will be used for extract + text annotations from WAV files. + +2001-09-02 Erik de Castro Lopo + + * examples/sf_info.c example/Makefile.am + Renamed to sndfile_info.c. The program sndfile_info will now be installed + when the library is installed. + + * src/float_cast.h + New file defining floating point to short and int casts. These casts will + eventually replace all flot and double casts to short and int. See comments + at the top of the file for the reasoning. + + * src/*.c + Changed all default float and double casts to short or int with macros + defined in floatcast.h. At the moment these casts do nothing. They will be + replaced with faster float to int cast operations in the near future. + +2001-08-31 Erik de Castro Lopo + + * tests/command_test.c + New file for testing sf_command () functionality. + + * src/sndfile.c + Revisiting of error return values of some functions. + Started implementing sf_command () a new function will allow on-the-fly + modification of library behaviour, or instance, sample value scaling. + + * src/common.h + Added hook for format specific sf_command () calls to SNDFILE struct. + + * doc/api.html + Updated and errors corrected. + + * doc/command.html + New documentation file explaining new sf_command () function. + +2001-08-11 Erik de Castro Lopo + + * src/sndfile.c + Fixed error return values from sf_read*() and sf_write*(). There were + numerous instances of -1 being returned through size_t. These now all set + error int the SF_PRIVATE struct and return 0. Thanks to David Viens for + spotting this. + +2001-08-01 Erik de Castro Lopo + + * src/common.c + Fixed use of va_arg() calls that were causing warning messages with the + latest version of gcc (thanks Maurizio Umberto Puxeddu). + +2001-07-25 Erik de Castro Lopo + + * src/*.c src/sfendian.h + Moved definition of MAKE_MARKER macro to sfendian.h + +2001-07-23 Erik de Castro Lopo + + * src/sndfile.c + Modified sf_get_lib_version () so that version string will be visible using + the Unix strings command. + + * examples/Makefile.am examples/sfinfo.c + Renamed sfinfo program and source code to sf_info. This prevents a name + clash with the program included with libaudiofile. + +2001-07-22 Erik de Castro Lopo + + * tests/read_seek_test.c tests/lossy_comp_test.c + Added tests for sf_read_float () and sf_readf_float (). + + * src/voc.c + New files for handling Creative Voice files (not complete). + + * src/samplitude.c + New files for handling Samplitude files (not complete). + +2001-07-21 Erik de Castro Lopo + + * src/aiff.c src/au.c src/paf.c src/svx.c src/wav.c + Converted these files to using psf_binheader_readf() function. Will soon be + ready to attempt to make reading writing from pipes work reliably. + + * src/*.[ch] + Added code for sf_read_float () and sf_readf_float () methods of accessing + file data. + +2001-07-20 Erik de Castro Lopo + + * src/paf.c src/wav_gsm610.c + Removed two printf()s which had escaped notice for some time (thanks + Sigbjørn Skjæret). + +2001-07-19 Erik de Castro Lopo + + * src/wav_gsm610.c + Fixed a bug which prevented GSM 6.10 encoded WAV files generated by + libsndfile from being played in Windoze (thanks klay). + +2001-07-18 Erik de Castro Lopo + + * src/common.[ch] + Implemented psf_binheader_readf() which will do for file header reading what + psf_binheader_writef() did for writing headers. Will eventually allow + libsndfile to read and write from pipes, including named pipes. + +2001-07-16 Erik de Castro Lopo + + * MacOS/config.h Win32/config.h + Attempted to bring these two files uptodate with src/config.h. As I don't + have access to either of these systems support for them may be completely + broken. + +2001-06-18 Erik de Castro Lopo + + * src/float32.c + Fixed bug for big endian processors that can't read 32 bit IEEE floats. Now + tested on Intel x86 and UltraSparc processors. + +2001-06-13 Erik de Castro Lopo + + * src/aiff.c + Modified to allow REX files (from Propellorhead's Recycle and Reason + programs) to be read. + REX files are basically an AIFF file with slightly unusual sequence of + chunks (AIFF files are supposed to allow any sequence) and some extra + application specific information. + Not yet able to write a REX file as the details of the application specific + data is unknown. + +2001-06-12 Erik de Castro Lopo + + * src/wav.c + Fixed endian bug when reading PEAK chunk on big endian machines. + + * src/common.c + Fixed endian bug when reading PEAK chunk on big endian machines with + --enable-force-broken-float configure option. + Fix psf_binheader_writef for (FORCE_BROKEN_FLOAT ||______) + +2001-06-07 Erik de Castro Lopo + + * configure.in src/config.h.in + Removed old CAN_READ_WRITE_x86_IEEE configure variable now that float + capabilities are detected at run time. + Added FORCE_BROKEN_FLOAT to allow testing of broken float code on machines + where the processor can in fact handle floats correctly. + + * src/float32.c + Rejigged code reading and writing of floats on broken processors. + + * m4/ + Removed this directory and all its files as they are no longer needed. + +2001-06-05 Erik de Castro Lopo + + * tests/peak_chunk_test.c + New test to validate reading and writing of peak chunk. + + * examples/sfconvert + Added -float32 option. + + * src/*.c + Changed all error return values to negative values (ie the negative of what + they were). + + * src/sndfile.c tests/error_test.c + Modified to take account of the previous change. + +2001-06-04 Erik de Castro Lopo + + * src/float32.c + File renamed from wav_float.c and renamed function to something more + general. + Added runtime detection of floating point capabilities. + Added recording of peaks during write for generation of PEAK chunk. + + * src/wav.c src/aiff.c + Added handing for PEAK chunk for floating point files. PEAK is read when the + file headers are read and generated when the file is closed. Logic is in + place for adding PEAK chunk to end of file when writing to a pipe (reading + and writing from/to pipe to be implemented soon). + + * src/sndfile.c + Modified sf_signal_max () to use PEAK values if present. + +2001-06-03 Erik de Castro Lopo + + * src/*.c + Added pcm_read_init () and pcm_write_init () to src/pcm.c and removed all + other calls to functions in this file from the filetype specific files. + + * src/*.c + Added alaw_read_init (), alaw_write_int (), ulaw_read_init () and + ulaw_write_init () and removed all other calls to functions in alaw.c and + ulaw.c from the filetype specific files. + + * tests/write_read_test.c + Added tests to validate sf_seek () on all file types. + + * src/raw.c + Implemented raw_seek () function to fix a bug where + sf_seek (file, 0, SEEK_SET) on a RAW file failed. + + * src/paf.c + Fixed a bug in paf24_seek () found due to added seeks tests in + tests/write_read_test.c + +2001-06-01 Erik de Castro Lopo + + * tests/read_seek_test.c + Fixed a couple of broken binary files. + + * src/aiff.c src/wav.c + Added handling of PEAK chunks on file read. + +2001-05-31 Erik de Castro Lopo + + * check_libsndfile.py + New file for the regression testing of libsndfile. + check_libsndfile.py is a Python script which reads in a file containing + filenames of audio files. Each file is checked by running the examples/sfinfo + program on them and checking for error or warning messages in the libsndfile + log buffer. + + * check_libsndfile.list + This is an example list of audio files for use with check_libsndfile.py + + * tests/lossy_comp_test.c + Changed the defined value of M_PI for math header files which don't have it. + This fixed validation test failures on MetroWerks compilers. Thanks to Lord + Praetor Satanus of Acheron for bringing this to my attention. + +2001-05-30 Erik de Castro Lopo + + * src/common.[ch] + Removed psf_header_setf () which was no longer required after refactoring + and simplification of header writing. + Added 'z' format specifier to psf_binheader_writef () for zero filling header + with N bytes. Used by paf.c and nist.c + + * tests/check_log_buffer.c + New file implementing check_log_buffer () which reads the log buffer of a + SNDFILE* object and searches for error and warning messages. Calls exit () + if any are found. + + * tests/*.c + Added calls to check_log_buffer () after each call to sf_open_XXX (). + +2001-05-29 Erik de Castro Lopo + + * src/wav.c src/wav_ms_adpcm.c src/wav_gsm610.c + Major rehack of header writing using psf_binheader_writef (). + +2001-05-28 Erik de Castro Lopo + + * src/wav.c src/wav_ima_adpcm.c + Major rehack of header writing using psf_binheader_writef (). + +2001-05-27 Erik de Castro Lopo + + * src/wav.c + Changed return type of get_encoding_str () to prevent compiler warnings on + Mac OSX. + + * src/aiff.c src/au.c + Major rehack of header writing using psf_binheader_writef (). + +2001-05-25 Erik de Castro Lopo + + * src/common.h src/common.c + Added comments. + Name of log buffer changed from strbuffer to logbuffer. + Name of log buffer index variable changed from strindex to logindex. + + * src/*.[ch] + Changed name of internal logging function from psf_sprintf () to + psf_log_printf (). + Changed name of internal header generation functions from + psf_[ab]h_printf () to psf_asciiheader_printf () and + psf_binheader_writef (). + Changed name of internal header manipulation function psf_hsetf () to + psf_header_setf (). + +2001-05-24 Erik de Castro Lopo + + * src/nist.c + Fixed reading and writing of sample_byte_format header. "01" means little + endian and "10" means big endian regardless of bit width. + + * configure.in + Detect Mac OSX and disable -Wall and -pedantic gcc options. Mac OSX is + way screwed up and spews out buckets of warning messages from the system + headers. + Added --disable-gcc-opt configure option (sets gcc optimisation to -O0 ) for + easier debugging. + Made decision to harmonise source code version number and .so library + version number. Future releases will stick to this rule. + + * doc/new_file_type.HOWTO + New file to document the addition of new file types to libsndfile. + +2001-05-23 Erik de Castro Lopo + + * src/nist.c + New file for reading/writing Sphere NIST audio file format. + Originally requested by Elis Pomales in 1999. + Retrieved from unstable (and untouched for 18 months) branch of libsndfile. + Some vital information gleaned from the source code to Bill Schottstaedt's + sndlib library : ftp://ccrma-ftp.stanford.edu/pub/Lisp/sndlib.tar.gz + Currently reading and writing 16, 24 and 32 bit, big-endian and little + endian, stereo and mono files. + + * src/common.h src/common.c + Added psf_ah_printf () function to help construction of ASCII headers (ie NIST). + + * configure.in + Added test for vsnprintf () required by psf_ah_printf (). + + * tests/write_read_test.c + Added tests for supported NIST files. + +2001-05-22 Erik de Castro Lopo + + * tests/write_read_test.c + Added tests for little endian AIFC files. + + * src/aiff.c + Minor re-working of aiff_open_write (). + Added write support for little endian PCM encoded AIFC files. + +2001-05-13 Erik de Castro Lopo + + * src/aiff.c + Minor re-working of aiff_open_read (). + Added read support for little endian PCM encoded AIFC files from the Mac + OSX CD ripper program. Guillaume Lessard provided a couple of sample files + and a working patch. + The patch was not used as is but gave a good guide as to what to do. + +2001-05-11 Erik de Castro Lopo + + * src/sndfile.h + Fixed comments about endian-ness of WAV and AIFF files. Guillaume Lessard + pointed out the error. + +2001-04-23 Erik de Castro Lopo + + * examples/make_sine.c + Re-write of this example using sample rate and required frequency in Hz. + +2001-02-11 Erik de Castro Lopo + + * src/sndfile.c + Fixed bug that prevented known file types from being read as RAW PCM data. + +2000-12-16 Erik de Castro Lopo + + * src/aiff.c + Added handing of COMT chunk. + +2000-11-16 Erik de Castro Lopo + + * examples/sfconvert.c + Fixed bug in normalisatio code. Pointed out by Johnny Wu. + +2000-11-08 Erik de Castro Lopo + + * Win32/config.h + Fixed the incorrect setting of HAVE_ENDIAN_H parameter. Win32 only issue. + +2000-10-27 Erik de Castro Lopo + + * tests/Makefile.am + Added -lm for write_read_test_LDADD. + +2000-10-16 Erik de Castro Lopo + + * src/sndfile.c src/au.c + Fixed bug which prevented writing of G723 24kbps AU files. + + * tests/lossy_comp_test.c + Corrrection to options for G723 tests. + + * configure.in + Added --disable-gcc-pipe option for DJGPP compiler (gcc on MS-DOS) which + doesn't allow gcc -pipe option. + +2000-09-03 Erik de Castro Lopo + + * src/ulaw.c src/alaw.c src/wav_imaadpcm.c src/msadpcm.c src/wav_gsm610.c + Fixed normailsation bugs shown up by new double_test program. + +2000-08-31 Erik de Castro Lopo + + * src/pcm.c + Fixed bug in normalisation code (spotted by Steve Lhomme). + + * tests/double_test.c + New file to test scaled and unscaled sf_read_double() and sf_write_double() + functions. + +2000-08-28 Erik de Castro Lopo + + * COPYING + Changed to the LGPL COPYING file (spotted by H. S. Teoh). + +2000-08-21 Erik de Castro Lopo + + * src/sndfile.h + Removed prototype of unimplemented function sf_get_info(). Added prototype + for sf_error_number() Thanks to Sigbjørn Skjæret for spotting these. + +2000-08-18 Erik de Castro Lopo + + * src/newpcm.h + New file to contain a complete rewrite of the PCM data handling. + +2000-08-15 Erik de Castro Lopo + + * src/sndfile.c + Fixed a leak of FILE* pointers in sf_open_write(). Thanks to Sigbjørn + Skjæret for spotting this one. + +2000-08-13 Erik de Castro Lopo + + * src/au_g72x.c src/G72x/g72x.c + Added G723 encoded AU file support. + + * tests/lossy_comp_test.c + Added tests for G721 and G723 encoded AU files. + +2000-08-06 Erik de Castro Lopo + + * all files + Changed the license to LGPL. Albert Faber who had copyright on + Win32/unistd.h gave his permission to change the license on that file. All + other files were either copyright erikd AT mega-nerd DOT com or copyright + under a GPL/LGPL compatible license. + +2000-08-06 Erik de Castro Lopo + + * tests/lossy_comp_test.c + Fixed incorrect error message. + + * src/au_g72x.c src/G72x/* + G721 encoded AU files now working. + + * Win32/README-Win32.txt + Replaced this file with a new one which gives a full explanation + of how to build libsndfile under Win32. Thanks to Mike Ricos. + +2000-08-05 Erik de Castro Lopo + + * src/*.[ch] + Removed double leading underscores from the start of all variable and + function names. Identifiers with a leading underscores are reserved + for use by the compiler. + + * src/au_g72x.c src/G72x/* + Continued work on G721 encoded AU files. + +2000-07-12 Erik de Castro Lopo + + * src/G72x/* + New files for reading/writing G721 and G723 ADPCM audio. These files + are from a Sun Microsystems reference implementation released under a + free software licence. + Extensive changes to this code to make it fit in with libsndfile. + See the ChangeLog in this directory for details. + + * src/au_g72x.c + New file for G721 encoded AU files. + +2000-07-08 Erik de Castro Lopo + + * libsndfile.spec.in + Added a spec file for making RPMs. Thanks to Josh Green for supplying this. + +2000-06-28 Erik de Castro Lopo + + * src/sndfile.c src/sndfile.h + Add checking for and handling of header-less u-law encoded AU/SND files. + Any file with a ".au" or ".snd" file extension and without the normal + AU file header is treated as an 8kHz, u-law encoded file. + + * src/au.h + New function for opening a headerless u-law encoded file for read. + +2000-06-04 Erik de Castro Lopo + + * src/paf.c + Add checking for files shorter than minimal PAF file header length. + +2000-06-02 Erik de Castro Lopo + + * tests/write_read_test.c + Added extra sf_perror() calls when sf_write_XXXX fails. + +2000-05-29 Erik de Castro Lopo + + * src/common.c + Modified usage of va_arg() macro to work correctly on PowerPC + Linux. Thanks to Kyle Wheeler for giving me ssh access to his + machine while I was trying to track this down. + + * configure.in src/*.[ch] + Sorted out some endian-ness issues brought up by PowerPC Linux. + + * tests/read_seek_test.c + Added extra debugging for when tests fail. + +2000-05-18 Erik de Castro Lopo + + * src/wav.c + Fixed bug in GSM 6.10 handling for big-endian machines. Thanks + to Sigbjørn Skjæret for reporting this. + +2000-04-25 Erik de Castro Lopo + + * src/sndfile.c src/wav.c src/wav_gsm610.c + Finallised writing of GSM 6.10 WAV files. + + * tests/lossy_comp_test.c + Wrote new test code for GSM 6.10 files. + + * examples/sfinfo.c + Fixed incorrect format in printf() statement. + +2000-04-06 Erik de Castro Lopo + + * src/sndfile.h.in + Fixed comments about sf_perror () and sf_error_str (). + +2000-03-14 Erik de Castro Lopo + + * configure.in + Fixed --enable-justsrc option. + +2000-03-07 Erik de Castro Lopo + + * wav.c + Fixed checking of bytespersec field of header. Still some weirdness + with some files. + +2000-03-05 Erik de Castro Lopo + + * tests/lossy_comp_test.c + Added option to test PCM WAV files (sanity check). + Fixed bug in sf_seek() tests. + +2000-02-29 Erik de Castro Lopo + + * src/sndfile.c src/wav.c + Minor changes to allow writing of GSM 6.10 WAV files. + +2000-02-28 Erik de Castro Lopo + + * configure.in Makefile.am src/Makefile.am + Finally got around to figuring out how to build a single library from + multiple source directories. + Reading GSM 6.10 files now seems to work. + +2000-01-03 Erik de Castro Lopo + + * src/wav.c + Added more error reporting in read_fmt_chunk(). + +1999-12-21 Erik de Castro Lopo + + * examples/sfinfo.c + Modified program to accept multiple filenames from the command line. + +1999-11-27 Erik de Castro Lopo + + * src/wav_ima_adpcm.c + Moved code around in preparation to adding ability to read/write IMA ADPCM + encoded AIFF files. + +1999-11-16 Erik de Castro Lopo + + * src/common.c + Fixed put_int() and put_short() macros used by _psf_hprintf() which were + causing seg. faults on Sparc Solaris. + +1999-11-15 Erik de Castro Lopo + + * src/common.c + Added string.h to includes. Thanks to Sigbjxrn Skjfret. + + * src/svx.c + Fixed __svx_close() function to ensure FORM and BODY chunks are correctly + set. + +1999-10-01 Erik de Castro Lopo + + * src/au.c + Fixed handling of incorrect size field in AU header on read. Thanks to + Christoph Lauer for finding this problem. + +1999-09-28 Erik de Castro Lopo + + * src/aiff.c + Fixed a bug with incorrect SSND chunk length being written. This also lead + to finding an minor error in AIFF header parsing. Thanks to Dan Timis for + pointing this out. + +1999-09-24 Erik de Castro Lopo + + * src/paf.c + Fixed a bug with reading and writing 24 bit stereo PAF files. This problem + came to light when implementing tests for the new functions which operate + in terms of frames rather than items. + +1999-09-23 Erik de Castro Lopo + + * src/sndfile.c + Modified file type detection to use first 12 bytes of file rather than + file name extension. Required this because NIST files use the same + filename extension as Microsoft WAV files. + + * src/sndfile.c src/sndfile.h + Added short, int and double read/write functions which work in frames + rather than items. This was originally suggested by Maurizio Umberto + Puxeddu. + +1999-09-22 Erik de Castro Lopo + + * src/svx.c + Finished off implementation of write using __psf_hprintf(). + +1999-09-21 Erik de Castro Lopo + + * src/common.h + Added a buffer to SF_PRIVATE for writing the header. This is required + to make generating headers for IFF/SVX files easier as well as making + it easier to do re-write the headers which will be required when + sf_rewrite_header() is implemented. + + * src/common.c + Implemented __psf_hprintf() function. This is an internal function + which is documented briefly just above the code. + +1999-09-05 Erik de Castro Lopo + + * src/sndfile.c + Fixed a bug in sf_write_raw() where it was returning incorrect values + (thanks to Richard Dobson for finding this one). Must put in a test + routine for sf_read_raw and sf_write_raw. + + * src/aiff.c + Fixed default FORMsize in __aiff_open_write (). + + * src/sndfile.c + Added copy of filename to internal data structure. IFF/SVX files + contain a NAME header chunk. Both sf_open_read() and sf_open_write() + copy the file name (less the leading path information) to the + filename field. + + * src/svx.c + Started implementing writing of files. + +1999-08-04 Erik de Castro Lopo + + * src/svx.c + New file for reading/writing 8SVX and 16SVX files. + + * src/sndfile.[ch] src/common.h + Changes for SVX files. + + * src/aiff.c + Fixed header parsing when unknown chunk is found. + +1999-08-01 Erik de Castro Lopo + + * src/paf.c + New file for reading/writing Ensoniq PARIS audio file format. + + * src/sndfile.[ch] src/common.h + Changes for PAF files. + + * src/sndfile.[ch] + Added stuff for sf_get_lib_version() function. + + +1999-07-31 Erik de Castro Lopo + + * src/sndfile.h MacOS/config.h + Fixed minor MacOS configuration issues. + +1999-07-30 Erik de Castro Lopo + + * MacOS/ + Added a new directory for the MacOS config.h file and the + readme file. + + * src/aiff.c + Fixed calculation of datalength when reading SSND chunk. Thanks to + Sigbjørn Skjæret for pointing out this error. + +1999-07-29 Erik de Castro Lopo + + * src/sndfile.c src/sndfile.h src/raw.c + Further fixing of #includes for MacOS. + +1999-07-25 Erik de Castro Lopo + + * src/wav.c src/aiff.c + Added call to ferror () in main header parsing loop of __XXX_open_read + functions. This should fix problems on platforms (MacOS, AmigaOS) where + fseek()ing or fread()ing beyond the end of the file puts the FILE* + stream in an error state until clearerr() is called. + + * tests/write_read_test.c + Added tests for RAW header-less PCM files. + + * src/common.h + Moved definition of struct tribyte to pcm.c which is the only place + which needs it. + + * src/pcm.c + Modified all code which assumed sizeof (struct tribyte) == 3. This code + did not work on MacOS. Thanks to Ben "Jacobs" for pointing this out. + + * src/au.c + Removed from list of #includes (not being used). + + * src/sndfile.c + Added MacOS specific #ifdef to replace . + + * src/sndfile.h + Added MacOS specific #ifdef to replace . + + * src/sndfile.h + Added MacOS specific typedef for off_t. + + * MacOS-readme.txt + New file with instructions for building libsndfile under MacOS. Thanks + to Ben "Jacobs" for supplying these instructions. + +1999-07-24 Erik de Castro Lopo + + * configure.in + Removed sndfile.h from generated file list as there were no longer + any autoconf substitutions being made. + + * src/raw.c + New file for handling raw header-less PCM files. In order to open these + for read, the user must specify format, pcmbitwidth and channels in the + SF_INFO struct when calling sf_open_read (). + + * src/sndfile.c + Added support for raw header-less PCM files. + +1999-07-22 Erik de Castro Lopo + + * examples/sfinfo.c + Removed options so the sfinfo program always prints out all the information. + +1999-07-19 Erik de Castro Lopo + + * src/alaw.c + New file for A-law encoding (similar to u-law). + + * tests/alaw_test.c + New test program to test the A-law encode/decode lookup tables. + + * tests/lossy_comp_test.c + Added tests for a-law encoded WAV, AU and AULE files. + +1999-07-18 Erik de Castro Lopo + + * src/sndfile.c src/au.c + Removed second "#include ". Thanks to Ben "Jacobs" for pointing + this out. + +1999-07-18 Erik de Castro Lopo + + * tests/ulaw_test.c + New test program to test the u-law encode/decode lookup tables. + +1999-07-16 Erik de Castro Lopo + + * src/sndfile.h + Made corrections to comments on the return values from sf_seek (). + + * src/sndfile.c + Fixed boundary condition checking bug and accounting bug in sf_read_raw (). + +1999-07-15 Erik de Castro Lopo + + * src/au.c src/ulaw.c + Finished implementation of u-law encoded AU files. + + * src/wav.c + Implemented reading and writing of u-law encoded WAV files. + + * tests/ + Changed name of adpcm_test.c to lossy_comp_test.c. This test program + will now be used to test Ulaw and Alaw encoding as well as APDCM. + Added tests for Ulaw encoded WAV files. + +1999-07-14 Erik de Castro Lopo + + * tests/adpcm_test.c + Initialised amp variable in gen_signal() to remove compiler warning. + +1999-07-12 Erik de Castro Lopo + + * src/aiff.c + In __aiff_open_read () prevented fseek()ing beyond end of file which + was causing trouble on MacOS with the MetroWerks compiler. Thanks to + Ben "Jacobs" for pointing this out. + + *src/wav.c + Fixed as above in __wav_open_read (). + +1999-07-01 Erik de Castro Lopo + + * src/wav_ms_adpcm.c + Implemented MS ADPCM encoding. Code cleanup of decoder. + + * tests/adpcm_test.c + Added tests for MS ADPCM WAV files. + + * src/wav_ima_adpcm.c + Fixed incorrect parameter in call to srate2blocksize () from + __ima_writer_init (). + +1999-06-23 Erik de Castro Lopo + + * tests/read_seek_test.c + Added test for 8 bit AIFF files. + +1999-06-18 Erik de Castro Lopo + + * tests/write_read_test.c + Removed test for IMA ADPCM WAV files which is now done in adpcm_test.c + + * configure.in + Added -Wconversion to CFLAGS. + + * src/*.c tests/*.c examples/*.c + Fixed all warnings resulting from use of -Wconversion. + +1999-06-17 Erik de Castro Lopo + + * src/wav.c + Added fact chunk handling on read and write for all non WAVE_FORMAT_PCM + WAV files. + + * src/wav_ima.c + Changed block alignment to be dependant on sample rate. This should make + WAV files created with libsndfile compatible with the MS Windows media + players. + + * tests/adpcm_test.c + Reimplemented adpcm_test_short and implemented adpcm_test_int and + adpcm_test_double. + Now have full testing of IMA ADPCM WAV file read, write and seek. + +1999-06-15 Erik de Castro Lopo + + * src/wav_float.c + Fixed function prototype for x86f2d_array () which was causing ocassional + seg. faults on Sparc Solaris machines. + +1999-06-14 Erik de Castro Lopo + + * src/aiff.c + Fixed bug in __aiff_close where the length fields in the header were + not being correctly calculated before writing. + + * tests/write_read_test.c + Modified to detect the above bug in WAV, AIFF and AU files. + +1999-06-12 Erik de Castro Lopo + + * Win32/* + Added a contribution from Albert Faber to allow libsndfile to compile + under Win32 systems. libsndfile will now be used as part of LAME the + the MPEG 1 Layer 3 encoder (http://internet.roadrunner.com/~mt/mp3/). + +1999-06-11 Erik de Castro Lopo + + * configure.in + Changed to reflect previous changes. + + * src/wav_ima_adpcm.c + Fixed incorrect calculation of bytespersec header field (IMA ADPCM only). + + Fixed bug when writing from int or double data to IMA ADPCM file. Will need + to write test code for this. + + Fixed bug in __ima_write () whereby the length of the current block was + calculated incorrectly. Thanks to Jongcheon Park for pointing this out. + +1999-03-27 Erik de Castro Lopo + + * src/*.c + Changed all read/write/lseek function calls to fread/fwrite/ + fseek/ftell and added error checking of return values from + fread and fwrite in critical areas of the code. + + * src/au.c + Fixed incorrect datasize element in AU header on write. + + * tests/error_test.c + Add new test to check all error values have an associated error + string. This will avoid embarrassing real world core dumps. + +1999-03-23 Erik de Castro Lopo + + * src/wav.c src/aiff.c + Added handling for unknown chunk markers in the file. + +1999-03-22 Erik de Castro Lopo + + * src/sndfile.c + Filled in missing error strings in SndfileErrors array. Missing entries + can cause core dumps when calling sf_error-str (). Thanks to Sam + for finding this problem. + +1999-03-21 Erik de Castro Lopo + + * src/wav_ima_adpcm.c + Work on wav_ms_adpcm.c uncovered a bug in __ima_read () when reading + stereo files. Caused by not adjusting offset into buffer of decoded + samples for 2 channels. A similar bug existed in __ima_write (). + Need a test for stereo ADPCM files. + + * src/wav_ms_adpcm.c + Decoder working correctly. + +1999-03-18 Erik de Castro Lopo + + * configure.in Makefile.am + Added --enable-justsrc configuration variable sent by Sam + . + + * src/wav_ima_adpcm.c + Fixed bug when reading beyond end of data section due to not + checking pima->blockcount. + This uncovered __ima_seek () bug due to pima->blockcount being set + before calling __ima_init_block (). + +1999-03-17 Erik de Castro Lopo + + * src/wav.c + Started implementing MS ADPCM decoder. + If file is WAVE_FORMAT_ADPCM and length of data chunk is odd, this + encoder seems to add an extra byte. Why not just give an even data + length? + +1999-03-16 Erik de Castro Lopo + + * src/wav.c + Split code out of wav.c to create wav_float.c and wav_ima_adpcm.c. + This will make it easier to add and debug other kinds of WAV files + in future. + +1999-03-14 Erik de Castro Lopo + + * tests/ + Added adpcm_test.c which implements test functions for + IMA ADPCM reading/writing/seeking etc. + + * src/wav.c + Fixed many bugs in IMA ADPCM encoder and decoder. + +1999-03-11 Erik de Castro Lopo + + * src/wav.c + Finished implementing IMA ADPCM encoder and decoder (what a bitch!). + +1999-03-03 Erik de Castro Lopo + + * src/wav.c + Started implementing IMA ADPCM decoder. + +1999-03-02 Erik de Castro Lopo + + * src/sndfile.c + Fixed bug where the sf_read_XXX functions were returning a + incorrect read count when reading past end of file. + Fixed bug in sf_seek () when seeking backwards from end of file. + + * tests/read_seek_test.c + Added multiple read test to short_test(), int_test () and + double_test (). + Added extra chunk to all test WAV files to test that reading + stops at end of 'data' chunk. + +1999-02-21 Erik de Castro Lopo + + * tests/write_read_test.c + Added tests for little DEC endian AU files. + + * src/au.c + Add handling for DEC format little endian AU files. + +1999-02-20 Erik de Castro Lopo + + * src/aiff.c src/au.c src/wav.c + Add __psf_sprintf calls during header parsing. + + * src/sndfile.c src/common.c + Implement sf_header_info (sndfile.c) function and __psf_sprintf (common.c). + + * tests/write_read_test.c + Added tests for 8 bit PCM files (WAV, AIFF and AU). + + * src/au.c src/aiff.c + Add handling of 8 bit PCM data format. + + * src/aiff.c + On write, set blocksize in SSND chunk to zero like everybody else. + +1999-02-16 Erik de Castro Lopo + + * src/pcm.c: + Fixed bug in let2s_array (cptr was not being initialised). + + * src/sndfile.c: + Fixed bug in sf_read_raw and sf_write_raw. sf_seek should + now work when using these functions. + +1999-02-15 Erik de Castro Lopo + + * tests/write_read_test.c: + Force test_buffer array to be double aligned. Sparc Solaris + requires this. + +1999-02-14 Erik de Castro Lopo + + * src/pcm.c: + Fixed a bug which was causing errors in the reading + and writing of 24 bit PCM files. + + * doc/api.html + Finished of preliminary documentaion. + +1999-02-13 Erik de Castro Lopo + + * src/aiff.c: + Changed reading of 'COMM' chunk to avoid reading an int + which overlaps an int (4 byte) boundary. + diff --git a/libs/libsndfile/Mingw-make-dist.sh b/libs/libsndfile/Mingw-make-dist.sh new file mode 100755 index 0000000000..fef4ba8cf9 --- /dev/null +++ b/libs/libsndfile/Mingw-make-dist.sh @@ -0,0 +1,113 @@ +#!/bin/sh + +# Copyright (C) 2006 Erik de Castro Lopo +# +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions are +# met: +# +# * Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# * Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in +# the documentation and/or other materials provided with the +# distribution. +# * Neither the author nor the names of any contributors may be used +# to endorse or promote products derived from this software without +# specific prior written permission. +# +# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED +# TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR +# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR +# CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, +# EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, +# PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; +# OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, +# WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR +# OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF +# ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +set -e + +if [ $# -lt 1 ] || [ $# -gt 2 ]; then + echo "Usage : Mingw-make-dist.sh ." + exit 1 + fi + +TARGZ=$1 +if [ ! -f $TARGZ ]; then + echo "Can't find source tarball." + fi + +TARGZ=$1 +if [ ! -f $TARGZ.asc ]; then + echo "Can't find source tarball signature." + fi + +UNAME=`uname -s` +if [ x$UNAME != "xMINGW32_NT-5.1" ]; then + echo "Not able to build Win32 binaries on this platform." + fi + +echo "Building MinGW binary/source zip file." + +VERSION=`pwd | sed -e "s#.*/##" | sed -e s/libsndfile-//` +BUILD=`echo $VERSION | sed -e "s/\./_/g"` +INSTALL="libsndfile-$BUILD" +ZIPNAME="$INSTALL.zip" + +if [ -z "$BUILD" ]; then + echo "Bad BUILD variable : '$BUILD'" + exit 1 + fi + +if [ ! -d $INSTALL/ ]; then + mkdir $INSTALL + fi + +if [ ! -f config.status ]; then + ./configure --prefix=`pwd`/$INSTALL/ +else + teststr=`grep "with options" config.status | grep -- --prefix=` + if [ -z "$teststr" ]; then + # --disable-static doesn't work. + ./configure --prefix=`pwd`/$INSTALL/ + fi + fi + +if [ ! -f src/.libs/libsndfile-1.dll ]; then + make all check + fi + +if [ ! -f $INSTALL/bin/libsndfile-1.dll ]; then + make install + rm -f $INSTALL/bin/sndfile-regtest.exe + strip $INSTALL/bin/*.* + mv $INSTALL/bin/*.* $INSTALL/include/*.* $INSTALL/ + rmdir $INSTALL/bin + rm -rf $INSTALL/lib + rmdir $INSTALL/include + cp src/libsndfile.def $INSTALL/ + cp Win32/README-precompiled-dll.txt $INSTALL/ + fi + +if [ ! -f $INSTALL/libsndfile-$VERSION.tar.gz ]; then + cp $TARGZ $INSTALL/ + if [ -f $TARGZ.asc ]; then + cp $TARGZ.asc $INSTALL/ + fi + fi + +if [ ! -f $ZIPNAME ]; then + zip -r $ZIPNAME $INSTALL/ + fi + + +# Do not edit or modify anything in this comment block. +# The following line is a file identity tag for the GNU Arch +# revision control system. +# +# arch-tag: 3f82cd8a-f800-48d7-9646-2cdcf03c81a0 diff --git a/libs/libsndfile/NEWS b/libs/libsndfile/NEWS new file mode 100644 index 0000000000..540a2d6413 --- /dev/null +++ b/libs/libsndfile/NEWS @@ -0,0 +1,126 @@ +Version 1.0.16 (2006-04-30) + * Add support for Broadcast (BEXT) chunks in WAV files. + * Implement new commands SFC_GET_SIGNAL_MAX and SFC_GET_MAX_ALL_CHANNELS. + * Add support for RIFX (big endian WAV variant). + * Fix configure script bugs. + * Fix bug in INST and MARK chunk writing for AIFF files. + +Version 1.0.15 (2006-03-16) + * Fix some ia64 issues. + * Fix precompiled DLL. + * Minor bug fixes. + +Version 1.0.14 (2006-02-19) + * Really fix MinGW compile problems. + * Minor bug fixes. + +Version 1.0.13 (2006-01-21) + * Fix for MinGW compiler problems. + * Allow readin/write of instrument chunks from WAV and AIFF files. + * Compile problem fix for Solaris compiler. + * Minor cleanups and bug fixes. + +Version 1.0.12 (2005-09-30) + * Add support for FLAC and Apple's Core Audio Format (CAF). + * Add virtual I/O interface (still needs docs). + * Cygwin and other Win32 fixes. + * Minor bug fixes and cleanups. + +Version 1.0.11 (2004-11-15) + * Add support for SD2 files. + * Add read support for loop info in WAV and AIFF files. + * Add more tests. + * Improve type safety. + * Minor optimisations and bug fixes. + +Version 1.0.10 (2004-06-15) + * Fix AIFF read/write mode bugs. + * Add support for compiling Win32 DLLS using MinGW. + * Fix problems resulting in failed compiles with gcc-2.95. + * Improve test suite. + * Minor bug fixes. + +Version 1.0.9 (2004-03-30) + * Add handling of AVR (Audio Visual Research) files. + * Improve handling of WAVEFORMATEXTENSIBLE WAV files. + * Fix for using pipes on Win32. + +Version 1.0.8 (2004-03-14) + * Correct peak chunk handing for files with > 16 tracks. + * Fix for WAV files with huge number of CUE chunks. + +Version 1.0.7 (2004-02-25) + * Fix clip mode detection on ia64, MIPS and other CPUs. + * Fix two MacOSX build problems. + +Version 1.0.6 (2004-02-08) + * Added support for native Win32 file access API (Ross Bencina). + * New mode to add clippling then a converting from float/double to integer + would otherwise wrap around. + * Fixed a bug in reading/writing files > 2Gig on Linux, Solaris and others. + * Many minor bug fixes. + * Other random fixes for Win32. + +Version 1.0.5 (2003-05-03) + * Added support for HTK files. + * Added new function sf_open_fd() to allow for secure opening of temporary + files as well as reading/writing sound files embedded within larger + container files. + * Added string support for AIFF files. + * Minor bug fixes and code cleanups. + +Version 1.0.4 (2003-02-02) + * Added suport of PVF and XI files. + * Added functionality for setting and retreiving strings from sound files. + * Minor code cleanups and bug fixes. + +Version 1.0.3 (2002-12-09) + * Minor bug fixes. + +Version 1.0.2 (2002-11-24) + * Added support for VOX ADPCM. + * Improved error reporting. + * Added version scripting on Linux and Solaris. + * Minor bug fixes. + +Version 1.0.1 (2002-09-14) + * Added MAT and MAT5 file formats. + * Minor bug fixes. + +Version 1.0.0 (2002-08-16) + * Final release for 1.0.0. + +Version 1.0.0rc6 (2002-08-14) + * Release candidate 6 for the 1.0.0 series. + * MacOS9 fixes. + +Version 1.0.0rc5 (2002-08-10) + * Release candidate 5 for the 1.0.0 series. + * Changed the definition of sf_count_t which was causing problems when + libsndfile was compiled with other libraries (ie WxWindows). + * Minor bug fixes. + * Documentation cleanup. + +Version 1.0.0rc4 (2002-08-03) + * Release candidate 4 for the 1.0.0 series. + * Minor bug fixes. + * Fix broken Win32 "make check". + +Version 1.0.0rc3 (2002-08-02) + * Release candidate 3 for the 1.0.0 series. + * Fix bug where libsndfile was reading beyond the end of the data chunk. + * Added on-the-fly header updates on write. + * Fix a couple of documentation issues. + +Version 1.0.0rc2 (2002-06-24) + * Release candidate 2 for the 1.0.0 series. + * Fix compile problem for Win32. + +Version 1.0.0rc1 (2002-06-24) + * Release candidate 1 for the 1.0.0 series. + +Version 0.0.28 (2002-04-27) + * Last offical release of 0.0.X series of the library. + +Version 0.0.8 (1999-02-16) + * First offical release. diff --git a/libs/libsndfile/README b/libs/libsndfile/README new file mode 100644 index 0000000000..d93edfd5bd --- /dev/null +++ b/libs/libsndfile/README @@ -0,0 +1,71 @@ +This is libsndfile, 1.0.16 + +libsndfile is a library of C routines for reading and writing +files containing sampled audio data. + +The src/ directory contains the source code for library itself. + +The doc/ directory contains the libsndfile documentation. + +The examples/ directory contains examples of how to write code using +libsndfile. 'wav32_aiff24' converts a WAV file containing 32 bit floating +point data into a 24 bit PCM AIFF file. 'sndfile2oct' dumps the audio +data of a file in a human readable format. 'sfconvert' is the beginnings +of a audio file format conversion utility. 'make_sine' generates a WAV +file containing one cycle of a sine wave with 4096 sample points in +32 bit floating point format. 'sfinfo' opens a sound file and prints +out information about that file. + +The tests/ directory contains programs which link against libsndfile +and test its functionality. + +The Win32/ directory contains files and documentation to allow libsndfile +to compile under Win32 with the Microsoft Visual C++ compiler. + +The src/GSM610 directory contains code written by Jutta Degener and Carsten +Bormann. Their original code can be found at : + http://kbs.cs.tu-berlin.de/~jutta/toast.html + +The src/G72x directory contains code written and released by Sun Microsystems +under a suitably free license. + + +Win32 +----- +There are detailed instructions for building libsndfile on Win32 in the file + + doc/win32.html + + +MacOSX +------ +Building on MacOSX should be the same as building it on any other Unix. + + +OTHER PLATFORMS +--------------- +To compile libsndfile on platforms which have a Bourne Shell compatible +shell, an ANSI C compiler and a make utility should require no more that +the following three commands : + ./configure + make + make install + +For platforms without the required shell, it is usually sufficient to +create an approriate config.h file in the src/ directory with correct +values for the following #defines (this would work for AmigaOS) : + +#define HAVE_ENDIAN_H 0 +#define GUESS_BIG_ENDIAN 1 +#define GUESS_LITTLE_ENDIAN 0 +#define FORCE_BROKEN_FLOAT 0 + + +CONTACTS +-------- + +libsndfile was written by Erik de Castro Lopo (erikd AT mega-nerd DOT com). +The libsndfile home page is at : + + http://www.mega-nerd.com/libsndfile/ + diff --git a/libs/libsndfile/SConscript b/libs/libsndfile/SConscript new file mode 100644 index 0000000000..b7d35b9337 --- /dev/null +++ b/libs/libsndfile/SConscript @@ -0,0 +1,43 @@ +# -*- python -*- + +import os +import os.path +import glob + +sndfile_files = glob.glob('src/*.c') + glob.glob('src/GSM610/*.c') + glob.glob('src/G72x/*.c') + +Import('env install_prefix') +sndfile = env.Copy() + +domain = 'libsndfile' + +sndfile.Append(CCFLAGS = "-DPACKAGE=\\\"" + domain + "\\\"") +sndfile.Append(CCFLAGS = "-DVERSION=\\\"ardour-special\\\"") +# mingw may need this +#sndfile.Append(CCFLAGS="-no-undefined") +sndfile.Append(PACKAGE = domain) +sndfile.Append(POTFILE = domain + '.pot') + +conf = Configure(sndfile) + +if conf.CheckCHeader('/System/Library/Frameworks/CoreServices.framework/Headers/CoreServices.h'): + sndfile.Append(LINKFLAGS = "-framework CoreServices") + +sndfile = conf.Finish() + +libsndfile = sndfile.SharedLibrary('sndfile', sndfile_files) + +sndfile_h = sndfile.Command('src/sndfile.h', ['src/sndfile.h.in'], 'cd libs/libsndfile && ./configure && cd -', ENV=os.environ) + +Default([sndfile_h,libsndfile]) + +env.Alias('install', env.Install(os.path.join(install_prefix, 'lib/ardour2'), libsndfile)) + +env.Alias('tarball', env.Distribute (env['DISTTREE'], + [ 'NEWS', 'README', 'AUTHORS', 'ChangeLog', + 'configure', 'SConscript',] + + sndfile_files + + glob.glob('src/*.h') + + [ 'src/sndfile.h.in', 'src/config.h.in', 'src/Symbols.linux', 'src/Symbols.darwin', 'src/libsndfile.def', 'src/cygsndfile.def' ] + )) + diff --git a/libs/libsndfile/acinclude.m4 b/libs/libsndfile/acinclude.m4 new file mode 100644 index 0000000000..37f8c0c2a1 --- /dev/null +++ b/libs/libsndfile/acinclude.m4 @@ -0,0 +1,579 @@ +dnl By default, many hosts won't let programs access large files; +dnl one must use special compiler options to get large-file access to work. +dnl For more details about this brain damage please see: +dnl http://www.sas.com/standards/large.file/x_open.20Mar96.html + +dnl Written by Paul Eggert . + +dnl Internal subroutine of AC_SYS_EXTRA_LARGEFILE. +dnl AC_SYS_EXTRA_LARGEFILE_FLAGS(FLAGSNAME) +AC_DEFUN([AC_SYS_EXTRA_LARGEFILE_FLAGS], + [AC_CACHE_CHECK([for $1 value to request large file support], + ac_cv_sys_largefile_$1, + [ac_cv_sys_largefile_$1=`($GETCONF LFS_$1) 2>/dev/null` || { + ac_cv_sys_largefile_$1=no + ifelse($1, CFLAGS, + [case "$host_os" in + # IRIX 6.2 and later require cc -n32. +changequote(, )dnl + irix6.[2-9]* | irix6.1[0-9]* | irix[7-9].* | irix[1-9][0-9]*) +changequote([, ])dnl + if test "$GCC" != yes; then + ac_cv_sys_largefile_CFLAGS=-n32 + fi + ac_save_CC="$CC" + CC="$CC $ac_cv_sys_largefile_CFLAGS" + AC_TRY_LINK(, , , ac_cv_sys_largefile_CFLAGS=no) + CC="$ac_save_CC" + esac]) + }])]) + +dnl Internal subroutine of AC_SYS_EXTRA_LARGEFILE. +dnl AC_SYS_EXTRA_LARGEFILE_SPACE_APPEND(VAR, VAL) +AC_DEFUN([AC_SYS_EXTRA_LARGEFILE_SPACE_APPEND], + [case $2 in + no) ;; + ?*) + case "[$]$1" in + '') $1=$2 ;; + *) $1=[$]$1' '$2 ;; + esac ;; + esac]) + +dnl Internal subroutine of AC_SYS_EXTRA_LARGEFILE. +dnl AC_SYS_EXTRA_LARGEFILE_MACRO_VALUE(C-MACRO, CACHE-VAR, COMMENT, CODE-TO-SET-DEFAULT) +AC_DEFUN([AC_SYS_EXTRA_LARGEFILE_MACRO_VALUE], + [AC_CACHE_CHECK([for $1], $2, + [$2=no +changequote(, )dnl + $4 + for ac_flag in $ac_cv_sys_largefile_CFLAGS no; do + case "$ac_flag" in + -D$1) + $2=1 ;; + -D$1=*) + $2=`expr " $ac_flag" : '[^=]*=\(.*\)'` ;; + esac + done +changequote([, ])dnl + ]) + if test "[$]$2" != no; then + AC_DEFINE_UNQUOTED([$1], [$]$2, [$3]) + fi]) + +AC_DEFUN([AC_SYS_EXTRA_LARGEFILE], + [AC_REQUIRE([AC_CANONICAL_HOST]) + AC_ARG_ENABLE(largefile, + [ --disable-largefile omit support for large files]) + if test "$enable_largefile" != no; then + AC_CHECK_TOOL(GETCONF, getconf) + AC_SYS_EXTRA_LARGEFILE_FLAGS(CFLAGS) + AC_SYS_EXTRA_LARGEFILE_FLAGS(LDFLAGS) + AC_SYS_EXTRA_LARGEFILE_FLAGS(LIBS) + + for ac_flag in $ac_cv_sys_largefile_CFLAGS no; do + case "$ac_flag" in + no) ;; + -D_FILE_OFFSET_BITS=*) ;; + -D_LARGEFILE_SOURCE | -D_LARGEFILE_SOURCE=*) ;; + -D_LARGE_FILES | -D_LARGE_FILES=*) ;; + -D?* | -I?*) + AC_SYS_EXTRA_LARGEFILE_SPACE_APPEND(CPPFLAGS, "$ac_flag") ;; + *) + AC_SYS_EXTRA_LARGEFILE_SPACE_APPEND(CFLAGS, "$ac_flag") ;; + esac + done + AC_SYS_EXTRA_LARGEFILE_SPACE_APPEND(LDFLAGS, "$ac_cv_sys_largefile_LDFLAGS") + AC_SYS_EXTRA_LARGEFILE_SPACE_APPEND(LIBS, "$ac_cv_sys_largefile_LIBS") + AC_SYS_EXTRA_LARGEFILE_MACRO_VALUE(_FILE_OFFSET_BITS, + ac_cv_sys_file_offset_bits, + [Number of bits in a file offset, on hosts where this is settable.]) + [case "$host_os" in + # HP-UX 10.20 and later + hpux10.[2-9][0-9]* | hpux1[1-9]* | hpux[2-9][0-9]*) + ac_cv_sys_file_offset_bits=64 ;; + esac] + AC_SYS_EXTRA_LARGEFILE_MACRO_VALUE(_LARGEFILE_SOURCE, + ac_cv_sys_largefile_source, + [Define to make fseeko etc. visible, on some hosts.], + [case "$host_os" in + # HP-UX 10.20 and later + hpux10.[2-9][0-9]* | hpux1[1-9]* | hpux[2-9][0-9]*) + ac_cv_sys_largefile_source=1 ;; + esac]) + AC_SYS_EXTRA_LARGEFILE_MACRO_VALUE(_LARGE_FILES, + ac_cv_sys_large_files, + [Define for large files, on AIX-style hosts.], + [case "$host_os" in + # AIX 4.2 and later + aix4.[2-9]* | aix4.1[0-9]* | aix[5-9].* | aix[1-9][0-9]*) + ac_cv_sys_large_files=1 ;; + esac]) + fi + ]) + + + + + + +dnl @synopsis AC_C_FIND_ENDIAN +dnl +dnl Determine endian-ness of target processor. +dnl @version 1.1 Mar 03 2002 +dnl @author Erik de Castro Lopo +dnl +dnl Majority written from scratch to replace the standard autoconf macro +dnl AC_C_BIGENDIAN. Only part remaining from the original it the invocation +dnl of the AC_TRY_RUN macro. +dnl +dnl Permission to use, copy, modify, distribute, and sell this file for any +dnl purpose is hereby granted without fee, provided that the above copyright +dnl and this permission notice appear in all copies. No representations are +dnl made about the suitability of this software for any purpose. It is +dnl provided "as is" without express or implied warranty. + +dnl Find endian-ness in the following way: +dnl 1) Look in . +dnl 2) If 1) fails, look in and . +dnl 3) If 1) and 2) fails and not cross compiling run a test program. +dnl 4) If 1) and 2) fails and cross compiling then guess based on target. + +AC_DEFUN([AC_C_FIND_ENDIAN], +[AC_CACHE_CHECK(processor byte ordering, + ac_cv_c_byte_order, + +# Initialize to unknown +ac_cv_c_byte_order=unknown + +if test x$ac_cv_header_endian_h = xyes ; then + + # First try which should set BYTE_ORDER. + + [AC_TRY_LINK([ + #include + #if BYTE_ORDER != LITTLE_ENDIAN + not big endian + #endif + ], return 0 ;, + ac_cv_c_byte_order=little + )] + + [AC_TRY_LINK([ + #include + #if BYTE_ORDER != BIG_ENDIAN + not big endian + #endif + ], return 0 ;, + ac_cv_c_byte_order=big + )] + + fi + +if test $ac_cv_c_byte_order = unknown ; then + + [AC_TRY_LINK([ + #include + #include + #if !BYTE_ORDER || !BIG_ENDIAN || !LITTLE_ENDIAN + bogus endian macros + #endif + ], return 0 ;, + + [AC_TRY_LINK([ + #include + #include + #if BYTE_ORDER != LITTLE_ENDIAN + not big endian + #endif + ], return 0 ;, + ac_cv_c_byte_order=little + )] + + [AC_TRY_LINK([ + #include + #include + #if BYTE_ORDER != LITTLE_ENDIAN + not big endian + #endif + ], return 0 ;, + ac_cv_c_byte_order=little + )] + + )] + + fi + +if test $ac_cv_c_byte_order = unknown ; then + if test $cross_compiling = yes ; then + # This is the last resort. Try to guess the target processor endian-ness + # by looking at the target CPU type. + [ + case "$target_cpu" in + alpha* | i?86* | mipsel* | ia64*) + ac_cv_c_big_endian=0 + ac_cv_c_little_endian=1 + ;; + + m68* | mips* | powerpc* | hppa* | sparc*) + ac_cv_c_big_endian=1 + ac_cv_c_little_endian=0 + ;; + + esac + ] + else + AC_TRY_RUN( + [[ + int main (void) + { /* Are we little or big endian? From Harbison&Steele. */ + union + { long l ; + char c [sizeof (long)] ; + } u ; + u.l = 1 ; + return (u.c [sizeof (long) - 1] == 1); + } + ]], , ac_cv_c_byte_order=big, + ac_cv_c_byte_order=unknown + ) + + AC_TRY_RUN( + [[int main (void) + { /* Are we little or big endian? From Harbison&Steele. */ + union + { long l ; + char c [sizeof (long)] ; + } u ; + u.l = 1 ; + return (u.c [0] == 1); + }]], , ac_cv_c_byte_order=little, + ac_cv_c_byte_order=unknown + ) + fi + fi + +) +] + +if test $ac_cv_c_byte_order = big ; then + ac_cv_c_big_endian=1 + ac_cv_c_little_endian=0 +elif test $ac_cv_c_byte_order = little ; then + ac_cv_c_big_endian=0 + ac_cv_c_little_endian=1 +else + ac_cv_c_big_endian=0 + ac_cv_c_little_endian=0 + + AC_MSG_WARN([[*****************************************************************]]) + AC_MSG_WARN([[*** Not able to determine endian-ness of target processor. ]]) + AC_MSG_WARN([[*** The constants CPU_IS_BIG_ENDIAN and CPU_IS_LITTLE_ENDIAN in ]]) + AC_MSG_WARN([[*** src/config.h may need to be hand editied. ]]) + AC_MSG_WARN([[*****************************************************************]]) + fi + +)# AC_C_FIND_ENDIAN + + + + + +dnl @synopsis AC_C99_FLEXIBLE_ARRAY +dnl +dnl Dose the compiler support the 1999 ISO C Standard "stuct hack". +dnl @version 1.1 Mar 15 2004 +dnl @author Erik de Castro Lopo +dnl +dnl Permission to use, copy, modify, distribute, and sell this file for any +dnl purpose is hereby granted without fee, provided that the above copyright +dnl and this permission notice appear in all copies. No representations are +dnl made about the suitability of this software for any purpose. It is +dnl provided "as is" without express or implied warranty. + +AC_DEFUN([AC_C99_FLEXIBLE_ARRAY], +[AC_CACHE_CHECK(C99 struct flexible array support, + ac_cv_c99_flexible_array, + +# Initialize to unknown +ac_cv_c99_flexible_array=no + +AC_TRY_LINK([[ + #include + typedef struct { + int k; + char buffer [] ; + } MY_STRUCT ; + ]], + [ MY_STRUCT *p = calloc (1, sizeof (MY_STRUCT) + 42); ], + ac_cv_c99_flexible_array=yes, + ac_cv_c99_flexible_array=no + ))] +) # AC_C99_FLEXIBLE_ARRAY + + + + + +dnl @synopsis AC_C99_FUNC_LRINT +dnl +dnl Check whether C99's lrint function is available. +dnl @version 1.3 Feb 12 2002 +dnl @author Erik de Castro Lopo +dnl +dnl Permission to use, copy, modify, distribute, and sell this file for any +dnl purpose is hereby granted without fee, provided that the above copyright +dnl and this permission notice appear in all copies. No representations are +dnl made about the suitability of this software for any purpose. It is +dnl provided "as is" without express or implied warranty. +dnl +AC_DEFUN([AC_C99_FUNC_LRINT], +[AC_CACHE_CHECK(for lrint, + ac_cv_c99_lrint, +[ +lrint_save_CFLAGS=$CFLAGS +CFLAGS="-O2 -lm" +AC_TRY_LINK([ +#define _ISOC9X_SOURCE 1 +#define _ISOC99_SOURCE 1 +#define __USE_ISOC99 1 +#define __USE_ISOC9X 1 + +#include +], if (!lrint(3.14159)) lrint(2.7183);, ac_cv_c99_lrint=yes, ac_cv_c99_lrint=no) + +CFLAGS=$lrint_save_CFLAGS + +]) + +if test "$ac_cv_c99_lrint" = yes; then + AC_DEFINE(HAVE_LRINT, 1, + [Define if you have C99's lrint function.]) +fi +])# AC_C99_FUNC_LRINT +dnl @synopsis AC_C99_FUNC_LRINTF +dnl +dnl Check whether C99's lrintf function is available. +dnl @version 1.3 Feb 12 2002 +dnl @author Erik de Castro Lopo +dnl +dnl Permission to use, copy, modify, distribute, and sell this file for any +dnl purpose is hereby granted without fee, provided that the above copyright +dnl and this permission notice appear in all copies. No representations are +dnl made about the suitability of this software for any purpose. It is +dnl provided "as is" without express or implied warranty. +dnl +AC_DEFUN([AC_C99_FUNC_LRINTF], +[AC_CACHE_CHECK(for lrintf, + ac_cv_c99_lrintf, +[ +lrintf_save_CFLAGS=$CFLAGS +CFLAGS="-O2 -lm" +AC_TRY_LINK([ +#define _ISOC9X_SOURCE 1 +#define _ISOC99_SOURCE 1 +#define __USE_ISOC99 1 +#define __USE_ISOC9X 1 + +#include +], if (!lrintf(3.14159)) lrintf(2.7183);, ac_cv_c99_lrintf=yes, ac_cv_c99_lrintf=no) + +CFLAGS=$lrintf_save_CFLAGS + +]) + +if test "$ac_cv_c99_lrintf" = yes; then + AC_DEFINE(HAVE_LRINTF, 1, + [Define if you have C99's lrintf function.]) +fi +])# AC_C99_FUNC_LRINTF + + + + +dnl @synopsis AC_C99_FUNC_LLRINT +dnl +dnl Check whether C99's llrint function is available. +dnl @version 1.1 Sep 30 2002 +dnl @author Erik de Castro Lopo +dnl +dnl Permission to use, copy, modify, distribute, and sell this file for any +dnl purpose is hereby granted without fee, provided that the above copyright +dnl and this permission notice appear in all copies. No representations are +dnl made about the suitability of this software for any purpose. It is +dnl provided "as is" without express or implied warranty. +dnl +AC_DEFUN([AC_C99_FUNC_LLRINT], +[AC_CACHE_CHECK(for llrint, + ac_cv_c99_llrint, +[ +llrint_save_CFLAGS=$CFLAGS +CFLAGS="-O2 -lm" +AC_TRY_LINK([ +#define _ISOC9X_SOURCE 1 +#define _ISOC99_SOURCE 1 +#define __USE_ISOC99 1 +#define __USE_ISOC9X 1 + +#include +#include +], int64_t x ; x = llrint(3.14159) ;, ac_cv_c99_llrint=yes, ac_cv_c99_llrint=no) + +CFLAGS=$llrint_save_CFLAGS + +]) + +if test "$ac_cv_c99_llrint" = yes; then + AC_DEFINE(HAVE_LLRINT, 1, + [Define if you have C99's llrint function.]) +fi +])# AC_C99_FUNC_LLRINT + + + +dnl @synopsis AC_C_CLIP_MODE +dnl +dnl Determine the clipping mode when converting float to int. +dnl @version 1.0 May 17 2003 +dnl @author Erik de Castro Lopo +dnl +dnl Permission to use, copy, modify, distribute, and sell this file for any +dnl purpose is hereby granted without fee, provided that the above copyright +dnl and this permission notice appear in all copies. No representations are +dnl made about the suitability of this software for any purpose. It is +dnl provided "as is" without express or implied warranty. + + + +dnl Find the clipping mode in the following way: +dnl 1) If we are not cross compiling test it. +dnl 2) IF we are cross compiling, assume that clipping isn't done correctly. + +AC_DEFUN([AC_C_CLIP_MODE], +[AC_CACHE_CHECK(processor clipping capabilities, + ac_cv_c_clip_type, + +# Initialize to unknown +ac_cv_c_clip_positive=unknown +ac_cv_c_clip_negative=unknown + +if test $ac_cv_c_clip_positive = unknown ; then + AC_TRY_RUN( + [[ + #define _ISOC9X_SOURCE 1 + #define _ISOC99_SOURCE 1 + #define __USE_ISOC99 1 + #define __USE_ISOC9X 1 + #include + int main (void) + { double fval ; + int k, ival ; + + fval = 1.0 * 0x7FFFFFFF ; + for (k = 0 ; k < 100 ; k++) + { ival = (lrint (fval)) >> 24 ; + if (ival != 127) + return 1 ; + + fval *= 1.2499999 ; + } ; + + return 0 ; + } + ]], + ac_cv_c_clip_positive=yes, + ac_cv_c_clip_positive=no, + ac_cv_c_clip_positive=unknown + ) + + AC_TRY_RUN( + [[ + #define _ISOC9X_SOURCE 1 + #define _ISOC99_SOURCE 1 + #define __USE_ISOC99 1 + #define __USE_ISOC9X 1 + #include + int main (void) + { double fval ; + int k, ival ; + + fval = -8.0 * 0x10000000 ; + for (k = 0 ; k < 100 ; k++) + { ival = (lrint (fval)) >> 24 ; + if (ival != -128) + return 1 ; + + fval *= 1.2499999 ; + } ; + + return 0 ; + } + ]], + ac_cv_c_clip_negative=yes, + ac_cv_c_clip_negative=no, + ac_cv_c_clip_negative=unknown + ) + fi + +if test $ac_cv_c_clip_positive = yes ; then + ac_cv_c_clip_positive=1 +else + ac_cv_c_clip_positive=0 + fi + +if test $ac_cv_c_clip_negative = yes ; then + ac_cv_c_clip_negative=1 +else + ac_cv_c_clip_negative=0 + fi + +[[ +case "$ac_cv_c_clip_positive$ac_cv_c_clip_negative" in + "00") + ac_cv_c_clip_type="none" + ;; + "10") + ac_cv_c_clip_type="positive" + ;; + "01") + ac_cv_c_clip_type="negative" + ;; + "11") + ac_cv_c_clip_type="both" + ;; + esac + ]] + +) +] + +)# AC_C_CLIP_MODE + + +dnl @synopsis AC_ADD_CFLAGS +dnl +dnl Add the given option to CFLAGS, if it doesn't break the compiler + +AC_DEFUN([AC_ADD_CFLAGS], +[AC_MSG_CHECKING([if $CC accepts $1]) + ac_add_cflags__old_cflags="$CFLAGS" + CFLAGS="$CFLAGS $1" + AC_TRY_LINK([#include ], + [printf("Hello, World!\n"); return 0;], + AC_MSG_RESULT([yes]), + AC_MSG_RESULT([no]) + CFLAGS="$ac_add_cflags__old_cflags") +]) + + + + +ifelse(dnl + + Do not edit or modify anything in this comment block. + The arch-tag line is a file identity tag for the GNU Arch + revision control system. + + arch-tag: bc38294d-bb5c-42ad-90b9-779def5eaab7 + +)dnl diff --git a/libs/libsndfile/aclocal.m4 b/libs/libsndfile/aclocal.m4 new file mode 100644 index 0000000000..e406d1a01b --- /dev/null +++ b/libs/libsndfile/aclocal.m4 @@ -0,0 +1,72 @@ +# generated automatically by aclocal 1.9.2 -*- Autoconf -*- + +# Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004 +# Free Software Foundation, Inc. +# This file is free software; the Free Software Foundation +# gives unlimited permission to copy and/or distribute it, +# with or without modifications, as long as this notice is preserved. + +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY, to the extent permitted by law; without +# even the implied warranty of MERCHANTABILITY or FITNESS FOR A +# PARTICULAR PURPOSE. + + +dnl PKG_CHECK_MODULES(GSTUFF, gtk+-2.0 >= 1.3 glib = 1.3.4, action-if, action-not) +dnl defines GSTUFF_LIBS, GSTUFF_CFLAGS, see pkg-config man page +dnl also defines GSTUFF_PKG_ERRORS on error +AC_DEFUN([PKG_CHECK_MODULES], [ + succeeded=no + + if test -z "$PKG_CONFIG"; then + AC_PATH_PROG(PKG_CONFIG, pkg-config, no) + fi + + if test "$PKG_CONFIG" = "no" ; then + echo "*** The pkg-config script could not be found. Make sure it is" + echo "*** in your path, or set the PKG_CONFIG environment variable" + echo "*** to the full path to pkg-config." + echo "*** Or see http://www.freedesktop.org/software/pkgconfig to get pkg-config." + else + PKG_CONFIG_MIN_VERSION=0.9.0 + if $PKG_CONFIG --atleast-pkgconfig-version $PKG_CONFIG_MIN_VERSION; then + AC_MSG_CHECKING(for $2) + + if $PKG_CONFIG --exists "$2" ; then + AC_MSG_RESULT(yes) + succeeded=yes + + AC_MSG_CHECKING($1_CFLAGS) + $1_CFLAGS=`$PKG_CONFIG --cflags "$2"` + AC_MSG_RESULT($$1_CFLAGS) + + AC_MSG_CHECKING($1_LIBS) + $1_LIBS=`$PKG_CONFIG --libs "$2"` + AC_MSG_RESULT($$1_LIBS) + else + $1_CFLAGS="" + $1_LIBS="" + ## If we have a custom action on failure, don't print errors, but + ## do set a variable so people can do so. + $1_PKG_ERRORS=`$PKG_CONFIG --errors-to-stdout --print-errors "$2"` + ifelse([$4], ,echo $$1_PKG_ERRORS,) + fi + + AC_SUBST($1_CFLAGS) + AC_SUBST($1_LIBS) + else + echo "*** Your version of pkg-config is too old. You need version $PKG_CONFIG_MIN_VERSION or newer." + echo "*** See http://www.freedesktop.org/software/pkgconfig" + fi + fi + + if test $succeeded = yes; then + ifelse([$3], , :, [$3]) + else + ifelse([$4], , AC_MSG_ERROR([Library requirements ($2) not met; consider adjusting the PKG_CONFIG_PATH environment variable if your libraries are in a nonstandard prefix so pkg-config can find them.]), [$4]) + fi +]) + + + +m4_include([acinclude.m4]) diff --git a/libs/libsndfile/compile b/libs/libsndfile/compile new file mode 100755 index 0000000000..ac07cc5414 --- /dev/null +++ b/libs/libsndfile/compile @@ -0,0 +1,107 @@ +#! /bin/sh + +# Wrapper for compilers which do not understand `-c -o'. + +# Copyright 1999, 2000 Free Software Foundation, Inc. +# Written by Tom Tromey . +# +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2, or (at your option) +# any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + +# As a special exception to the GNU General Public License, if you +# distribute this file as part of a program that contains a +# configuration script generated by Autoconf, you may include it under +# the same distribution terms that you use for the rest of that program. + +# Usage: +# compile PROGRAM [ARGS]... +# `-o FOO.o' is removed from the args passed to the actual compile. + +# Usage statement added by Billy Biggs . +if [ -z $1 ]; then + echo "Wrapper for compilers which do not understand '-c -o'." + echo "usage: compile PROGRAM [ARGS]..." + echo "'-o FOO.o' is removed from the args passed to the actual compile." + exit 1 +fi + +prog=$1 +shift + +ofile= +cfile= +args= +while test $# -gt 0; do + case "$1" in + -o) + # configure might choose to run compile as `compile cc -o foo foo.c'. + # So we do something ugly here. + ofile=$2 + shift + case "$ofile" in + *.o | *.obj) + ;; + *) + args="$args -o $ofile" + ofile= + ;; + esac + ;; + *.c) + cfile=$1 + args="$args $1" + ;; + *) + args="$args $1" + ;; + esac + shift +done + +if test -z "$ofile" || test -z "$cfile"; then + # If no `-o' option was seen then we might have been invoked from a + # pattern rule where we don't need one. That is ok -- this is a + # normal compilation that the losing compiler can handle. If no + # `.c' file was seen then we are probably linking. That is also + # ok. + exec "$prog" $args +fi + +# Name of file we expect compiler to create. +cofile=`echo $cfile | sed -e 's|^.*/||' -e 's/\.c$/.o/'` + +# Create the lock directory. +# Note: use `[/.-]' here to ensure that we don't use the same name +# that we are using for the .o file. Also, base the name on the expected +# object file name, since that is what matters with a parallel build. +lockdir=`echo $cofile | sed -e 's|[/.-]|_|g'`.d +while true; do + if mkdir $lockdir > /dev/null 2>&1; then + break + fi + sleep 1 +done +# FIXME: race condition here if user kills between mkdir and trap. +trap "rmdir $lockdir; exit 1" 1 2 15 + +# Run the compile. +"$prog" $args +status=$? + +if test -f "$cofile"; then + mv "$cofile" "$ofile" +fi + +rmdir $lockdir +exit $status diff --git a/libs/libsndfile/config.guess b/libs/libsndfile/config.guess new file mode 100755 index 0000000000..c38553dc74 --- /dev/null +++ b/libs/libsndfile/config.guess @@ -0,0 +1,1497 @@ +#! /bin/sh +# Attempt to guess a canonical system name. +# Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, +# 2000, 2001, 2002, 2003, 2004, 2005 Free Software Foundation, Inc. + +timestamp='2006-02-23' + +# This file is free software; you can redistribute it and/or modify it +# under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, but +# WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software +# Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA +# 02110-1301, USA. +# +# As a special exception to the GNU General Public License, if you +# distribute this file as part of a program that contains a +# configuration script generated by Autoconf, you may include it under +# the same distribution terms that you use for the rest of that program. + + +# Originally written by Per Bothner . +# Please send patches to . Submit a context +# diff and a properly formatted ChangeLog entry. +# +# This script attempts to guess a canonical system name similar to +# config.sub. If it succeeds, it prints the system name on stdout, and +# exits with 0. Otherwise, it exits with 1. +# +# The plan is that this can be called by configure scripts if you +# don't specify an explicit build system type. + +me=`echo "$0" | sed -e 's,.*/,,'` + +usage="\ +Usage: $0 [OPTION] + +Output the configuration name of the system \`$me' is run on. + +Operation modes: + -h, --help print this help, then exit + -t, --time-stamp print date of last modification, then exit + -v, --version print version number, then exit + +Report bugs and patches to ." + +version="\ +GNU config.guess ($timestamp) + +Originally written by Per Bothner. +Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005 +Free Software Foundation, Inc. + +This is free software; see the source for copying conditions. There is NO +warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." + +help=" +Try \`$me --help' for more information." + +# Parse command line +while test $# -gt 0 ; do + case $1 in + --time-stamp | --time* | -t ) + echo "$timestamp" ; exit ;; + --version | -v ) + echo "$version" ; exit ;; + --help | --h* | -h ) + echo "$usage"; exit ;; + -- ) # Stop option processing + shift; break ;; + - ) # Use stdin as input. + break ;; + -* ) + echo "$me: invalid option $1$help" >&2 + exit 1 ;; + * ) + break ;; + esac +done + +if test $# != 0; then + echo "$me: too many arguments$help" >&2 + exit 1 +fi + +trap 'exit 1' 1 2 15 + +# CC_FOR_BUILD -- compiler used by this script. Note that the use of a +# compiler to aid in system detection is discouraged as it requires +# temporary files to be created and, as you can see below, it is a +# headache to deal with in a portable fashion. + +# Historically, `CC_FOR_BUILD' used to be named `HOST_CC'. We still +# use `HOST_CC' if defined, but it is deprecated. + +# Portable tmp directory creation inspired by the Autoconf team. + +set_cc_for_build=' +trap "exitcode=\$?; (rm -f \$tmpfiles 2>/dev/null; rmdir \$tmp 2>/dev/null) && exit \$exitcode" 0 ; +trap "rm -f \$tmpfiles 2>/dev/null; rmdir \$tmp 2>/dev/null; exit 1" 1 2 13 15 ; +: ${TMPDIR=/tmp} ; + { tmp=`(umask 077 && mktemp -d "$TMPDIR/cgXXXXXX") 2>/dev/null` && test -n "$tmp" && test -d "$tmp" ; } || + { test -n "$RANDOM" && tmp=$TMPDIR/cg$$-$RANDOM && (umask 077 && mkdir $tmp) ; } || + { tmp=$TMPDIR/cg-$$ && (umask 077 && mkdir $tmp) && echo "Warning: creating insecure temp directory" >&2 ; } || + { echo "$me: cannot create a temporary directory in $TMPDIR" >&2 ; exit 1 ; } ; +dummy=$tmp/dummy ; +tmpfiles="$dummy.c $dummy.o $dummy.rel $dummy" ; +case $CC_FOR_BUILD,$HOST_CC,$CC in + ,,) echo "int x;" > $dummy.c ; + for c in cc gcc c89 c99 ; do + if ($c -c -o $dummy.o $dummy.c) >/dev/null 2>&1 ; then + CC_FOR_BUILD="$c"; break ; + fi ; + done ; + if test x"$CC_FOR_BUILD" = x ; then + CC_FOR_BUILD=no_compiler_found ; + fi + ;; + ,,*) CC_FOR_BUILD=$CC ;; + ,*,*) CC_FOR_BUILD=$HOST_CC ;; +esac ; set_cc_for_build= ;' + +# This is needed to find uname on a Pyramid OSx when run in the BSD universe. +# (ghazi@noc.rutgers.edu 1994-08-24) +if (test -f /.attbin/uname) >/dev/null 2>&1 ; then + PATH=$PATH:/.attbin ; export PATH +fi + +UNAME_MACHINE=`(uname -m) 2>/dev/null` || UNAME_MACHINE=unknown +UNAME_RELEASE=`(uname -r) 2>/dev/null` || UNAME_RELEASE=unknown +UNAME_SYSTEM=`(uname -s) 2>/dev/null` || UNAME_SYSTEM=unknown +UNAME_VERSION=`(uname -v) 2>/dev/null` || UNAME_VERSION=unknown + +# Note: order is significant - the case branches are not exclusive. + +case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in + *:NetBSD:*:*) + # NetBSD (nbsd) targets should (where applicable) match one or + # more of the tupples: *-*-netbsdelf*, *-*-netbsdaout*, + # *-*-netbsdecoff* and *-*-netbsd*. For targets that recently + # switched to ELF, *-*-netbsd* would select the old + # object file format. This provides both forward + # compatibility and a consistent mechanism for selecting the + # object file format. + # + # Note: NetBSD doesn't particularly care about the vendor + # portion of the name. We always set it to "unknown". + sysctl="sysctl -n hw.machine_arch" + UNAME_MACHINE_ARCH=`(/sbin/$sysctl 2>/dev/null || \ + /usr/sbin/$sysctl 2>/dev/null || echo unknown)` + case "${UNAME_MACHINE_ARCH}" in + armeb) machine=armeb-unknown ;; + arm*) machine=arm-unknown ;; + sh3el) machine=shl-unknown ;; + sh3eb) machine=sh-unknown ;; + *) machine=${UNAME_MACHINE_ARCH}-unknown ;; + esac + # The Operating System including object format, if it has switched + # to ELF recently, or will in the future. + case "${UNAME_MACHINE_ARCH}" in + arm*|i386|m68k|ns32k|sh3*|sparc|vax) + eval $set_cc_for_build + if echo __ELF__ | $CC_FOR_BUILD -E - 2>/dev/null \ + | grep __ELF__ >/dev/null + then + # Once all utilities can be ECOFF (netbsdecoff) or a.out (netbsdaout). + # Return netbsd for either. FIX? + os=netbsd + else + os=netbsdelf + fi + ;; + *) + os=netbsd + ;; + esac + # The OS release + # Debian GNU/NetBSD machines have a different userland, and + # thus, need a distinct triplet. However, they do not need + # kernel version information, so it can be replaced with a + # suitable tag, in the style of linux-gnu. + case "${UNAME_VERSION}" in + Debian*) + release='-gnu' + ;; + *) + release=`echo ${UNAME_RELEASE}|sed -e 's/[-_].*/\./'` + ;; + esac + # Since CPU_TYPE-MANUFACTURER-KERNEL-OPERATING_SYSTEM: + # contains redundant information, the shorter form: + # CPU_TYPE-MANUFACTURER-OPERATING_SYSTEM is used. + echo "${machine}-${os}${release}" + exit ;; + *:OpenBSD:*:*) + UNAME_MACHINE_ARCH=`arch | sed 's/OpenBSD.//'` + echo ${UNAME_MACHINE_ARCH}-unknown-openbsd${UNAME_RELEASE} + exit ;; + *:ekkoBSD:*:*) + echo ${UNAME_MACHINE}-unknown-ekkobsd${UNAME_RELEASE} + exit ;; + *:SolidBSD:*:*) + echo ${UNAME_MACHINE}-unknown-solidbsd${UNAME_RELEASE} + exit ;; + macppc:MirBSD:*:*) + echo powerppc-unknown-mirbsd${UNAME_RELEASE} + exit ;; + *:MirBSD:*:*) + echo ${UNAME_MACHINE}-unknown-mirbsd${UNAME_RELEASE} + exit ;; + alpha:OSF1:*:*) + case $UNAME_RELEASE in + *4.0) + UNAME_RELEASE=`/usr/sbin/sizer -v | awk '{print $3}'` + ;; + *5.*) + UNAME_RELEASE=`/usr/sbin/sizer -v | awk '{print $4}'` + ;; + esac + # According to Compaq, /usr/sbin/psrinfo has been available on + # OSF/1 and Tru64 systems produced since 1995. I hope that + # covers most systems running today. This code pipes the CPU + # types through head -n 1, so we only detect the type of CPU 0. + ALPHA_CPU_TYPE=`/usr/sbin/psrinfo -v | sed -n -e 's/^ The alpha \(.*\) processor.*$/\1/p' | head -n 1` + case "$ALPHA_CPU_TYPE" in + "EV4 (21064)") + UNAME_MACHINE="alpha" ;; + "EV4.5 (21064)") + UNAME_MACHINE="alpha" ;; + "LCA4 (21066/21068)") + UNAME_MACHINE="alpha" ;; + "EV5 (21164)") + UNAME_MACHINE="alphaev5" ;; + "EV5.6 (21164A)") + UNAME_MACHINE="alphaev56" ;; + "EV5.6 (21164PC)") + UNAME_MACHINE="alphapca56" ;; + "EV5.7 (21164PC)") + UNAME_MACHINE="alphapca57" ;; + "EV6 (21264)") + UNAME_MACHINE="alphaev6" ;; + "EV6.7 (21264A)") + UNAME_MACHINE="alphaev67" ;; + "EV6.8CB (21264C)") + UNAME_MACHINE="alphaev68" ;; + "EV6.8AL (21264B)") + UNAME_MACHINE="alphaev68" ;; + "EV6.8CX (21264D)") + UNAME_MACHINE="alphaev68" ;; + "EV6.9A (21264/EV69A)") + UNAME_MACHINE="alphaev69" ;; + "EV7 (21364)") + UNAME_MACHINE="alphaev7" ;; + "EV7.9 (21364A)") + UNAME_MACHINE="alphaev79" ;; + esac + # A Pn.n version is a patched version. + # A Vn.n version is a released version. + # A Tn.n version is a released field test version. + # A Xn.n version is an unreleased experimental baselevel. + # 1.2 uses "1.2" for uname -r. + echo ${UNAME_MACHINE}-dec-osf`echo ${UNAME_RELEASE} | sed -e 's/^[PVTX]//' | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz'` + exit ;; + Alpha\ *:Windows_NT*:*) + # How do we know it's Interix rather than the generic POSIX subsystem? + # Should we change UNAME_MACHINE based on the output of uname instead + # of the specific Alpha model? + echo alpha-pc-interix + exit ;; + 21064:Windows_NT:50:3) + echo alpha-dec-winnt3.5 + exit ;; + Amiga*:UNIX_System_V:4.0:*) + echo m68k-unknown-sysv4 + exit ;; + *:[Aa]miga[Oo][Ss]:*:*) + echo ${UNAME_MACHINE}-unknown-amigaos + exit ;; + *:[Mm]orph[Oo][Ss]:*:*) + echo ${UNAME_MACHINE}-unknown-morphos + exit ;; + *:OS/390:*:*) + echo i370-ibm-openedition + exit ;; + *:z/VM:*:*) + echo s390-ibm-zvmoe + exit ;; + *:OS400:*:*) + echo powerpc-ibm-os400 + exit ;; + arm:RISC*:1.[012]*:*|arm:riscix:1.[012]*:*) + echo arm-acorn-riscix${UNAME_RELEASE} + exit ;; + arm:riscos:*:*|arm:RISCOS:*:*) + echo arm-unknown-riscos + exit ;; + SR2?01:HI-UX/MPP:*:* | SR8000:HI-UX/MPP:*:*) + echo hppa1.1-hitachi-hiuxmpp + exit ;; + Pyramid*:OSx*:*:* | MIS*:OSx*:*:* | MIS*:SMP_DC-OSx*:*:*) + # akee@wpdis03.wpafb.af.mil (Earle F. Ake) contributed MIS and NILE. + if test "`(/bin/universe) 2>/dev/null`" = att ; then + echo pyramid-pyramid-sysv3 + else + echo pyramid-pyramid-bsd + fi + exit ;; + NILE*:*:*:dcosx) + echo pyramid-pyramid-svr4 + exit ;; + DRS?6000:unix:4.0:6*) + echo sparc-icl-nx6 + exit ;; + DRS?6000:UNIX_SV:4.2*:7* | DRS?6000:isis:4.2*:7*) + case `/usr/bin/uname -p` in + sparc) echo sparc-icl-nx7; exit ;; + esac ;; + sun4H:SunOS:5.*:*) + echo sparc-hal-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'` + exit ;; + sun4*:SunOS:5.*:* | tadpole*:SunOS:5.*:*) + echo sparc-sun-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'` + exit ;; + i86pc:SunOS:5.*:*) + echo i386-pc-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'` + exit ;; + sun4*:SunOS:6*:*) + # According to config.sub, this is the proper way to canonicalize + # SunOS6. Hard to guess exactly what SunOS6 will be like, but + # it's likely to be more like Solaris than SunOS4. + echo sparc-sun-solaris3`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'` + exit ;; + sun4*:SunOS:*:*) + case "`/usr/bin/arch -k`" in + Series*|S4*) + UNAME_RELEASE=`uname -v` + ;; + esac + # Japanese Language versions have a version number like `4.1.3-JL'. + echo sparc-sun-sunos`echo ${UNAME_RELEASE}|sed -e 's/-/_/'` + exit ;; + sun3*:SunOS:*:*) + echo m68k-sun-sunos${UNAME_RELEASE} + exit ;; + sun*:*:4.2BSD:*) + UNAME_RELEASE=`(sed 1q /etc/motd | awk '{print substr($5,1,3)}') 2>/dev/null` + test "x${UNAME_RELEASE}" = "x" && UNAME_RELEASE=3 + case "`/bin/arch`" in + sun3) + echo m68k-sun-sunos${UNAME_RELEASE} + ;; + sun4) + echo sparc-sun-sunos${UNAME_RELEASE} + ;; + esac + exit ;; + aushp:SunOS:*:*) + echo sparc-auspex-sunos${UNAME_RELEASE} + exit ;; + # The situation for MiNT is a little confusing. The machine name + # can be virtually everything (everything which is not + # "atarist" or "atariste" at least should have a processor + # > m68000). The system name ranges from "MiNT" over "FreeMiNT" + # to the lowercase version "mint" (or "freemint"). Finally + # the system name "TOS" denotes a system which is actually not + # MiNT. But MiNT is downward compatible to TOS, so this should + # be no problem. + atarist[e]:*MiNT:*:* | atarist[e]:*mint:*:* | atarist[e]:*TOS:*:*) + echo m68k-atari-mint${UNAME_RELEASE} + exit ;; + atari*:*MiNT:*:* | atari*:*mint:*:* | atarist[e]:*TOS:*:*) + echo m68k-atari-mint${UNAME_RELEASE} + exit ;; + *falcon*:*MiNT:*:* | *falcon*:*mint:*:* | *falcon*:*TOS:*:*) + echo m68k-atari-mint${UNAME_RELEASE} + exit ;; + milan*:*MiNT:*:* | milan*:*mint:*:* | *milan*:*TOS:*:*) + echo m68k-milan-mint${UNAME_RELEASE} + exit ;; + hades*:*MiNT:*:* | hades*:*mint:*:* | *hades*:*TOS:*:*) + echo m68k-hades-mint${UNAME_RELEASE} + exit ;; + *:*MiNT:*:* | *:*mint:*:* | *:*TOS:*:*) + echo m68k-unknown-mint${UNAME_RELEASE} + exit ;; + m68k:machten:*:*) + echo m68k-apple-machten${UNAME_RELEASE} + exit ;; + powerpc:machten:*:*) + echo powerpc-apple-machten${UNAME_RELEASE} + exit ;; + RISC*:Mach:*:*) + echo mips-dec-mach_bsd4.3 + exit ;; + RISC*:ULTRIX:*:*) + echo mips-dec-ultrix${UNAME_RELEASE} + exit ;; + VAX*:ULTRIX*:*:*) + echo vax-dec-ultrix${UNAME_RELEASE} + exit ;; + 2020:CLIX:*:* | 2430:CLIX:*:*) + echo clipper-intergraph-clix${UNAME_RELEASE} + exit ;; + mips:*:*:UMIPS | mips:*:*:RISCos) + eval $set_cc_for_build + sed 's/^ //' << EOF >$dummy.c +#ifdef __cplusplus +#include /* for printf() prototype */ + int main (int argc, char *argv[]) { +#else + int main (argc, argv) int argc; char *argv[]; { +#endif + #if defined (host_mips) && defined (MIPSEB) + #if defined (SYSTYPE_SYSV) + printf ("mips-mips-riscos%ssysv\n", argv[1]); exit (0); + #endif + #if defined (SYSTYPE_SVR4) + printf ("mips-mips-riscos%ssvr4\n", argv[1]); exit (0); + #endif + #if defined (SYSTYPE_BSD43) || defined(SYSTYPE_BSD) + printf ("mips-mips-riscos%sbsd\n", argv[1]); exit (0); + #endif + #endif + exit (-1); + } +EOF + $CC_FOR_BUILD -o $dummy $dummy.c && + dummyarg=`echo "${UNAME_RELEASE}" | sed -n 's/\([0-9]*\).*/\1/p'` && + SYSTEM_NAME=`$dummy $dummyarg` && + { echo "$SYSTEM_NAME"; exit; } + echo mips-mips-riscos${UNAME_RELEASE} + exit ;; + Motorola:PowerMAX_OS:*:*) + echo powerpc-motorola-powermax + exit ;; + Motorola:*:4.3:PL8-*) + echo powerpc-harris-powermax + exit ;; + Night_Hawk:*:*:PowerMAX_OS | Synergy:PowerMAX_OS:*:*) + echo powerpc-harris-powermax + exit ;; + Night_Hawk:Power_UNIX:*:*) + echo powerpc-harris-powerunix + exit ;; + m88k:CX/UX:7*:*) + echo m88k-harris-cxux7 + exit ;; + m88k:*:4*:R4*) + echo m88k-motorola-sysv4 + exit ;; + m88k:*:3*:R3*) + echo m88k-motorola-sysv3 + exit ;; + AViiON:dgux:*:*) + # DG/UX returns AViiON for all architectures + UNAME_PROCESSOR=`/usr/bin/uname -p` + if [ $UNAME_PROCESSOR = mc88100 ] || [ $UNAME_PROCESSOR = mc88110 ] + then + if [ ${TARGET_BINARY_INTERFACE}x = m88kdguxelfx ] || \ + [ ${TARGET_BINARY_INTERFACE}x = x ] + then + echo m88k-dg-dgux${UNAME_RELEASE} + else + echo m88k-dg-dguxbcs${UNAME_RELEASE} + fi + else + echo i586-dg-dgux${UNAME_RELEASE} + fi + exit ;; + M88*:DolphinOS:*:*) # DolphinOS (SVR3) + echo m88k-dolphin-sysv3 + exit ;; + M88*:*:R3*:*) + # Delta 88k system running SVR3 + echo m88k-motorola-sysv3 + exit ;; + XD88*:*:*:*) # Tektronix XD88 system running UTekV (SVR3) + echo m88k-tektronix-sysv3 + exit ;; + Tek43[0-9][0-9]:UTek:*:*) # Tektronix 4300 system running UTek (BSD) + echo m68k-tektronix-bsd + exit ;; + *:IRIX*:*:*) + echo mips-sgi-irix`echo ${UNAME_RELEASE}|sed -e 's/-/_/g'` + exit ;; + ????????:AIX?:[12].1:2) # AIX 2.2.1 or AIX 2.1.1 is RT/PC AIX. + echo romp-ibm-aix # uname -m gives an 8 hex-code CPU id + exit ;; # Note that: echo "'`uname -s`'" gives 'AIX ' + i*86:AIX:*:*) + echo i386-ibm-aix + exit ;; + ia64:AIX:*:*) + if [ -x /usr/bin/oslevel ] ; then + IBM_REV=`/usr/bin/oslevel` + else + IBM_REV=${UNAME_VERSION}.${UNAME_RELEASE} + fi + echo ${UNAME_MACHINE}-ibm-aix${IBM_REV} + exit ;; + *:AIX:2:3) + if grep bos325 /usr/include/stdio.h >/dev/null 2>&1; then + eval $set_cc_for_build + sed 's/^ //' << EOF >$dummy.c + #include + + main() + { + if (!__power_pc()) + exit(1); + puts("powerpc-ibm-aix3.2.5"); + exit(0); + } +EOF + if $CC_FOR_BUILD -o $dummy $dummy.c && SYSTEM_NAME=`$dummy` + then + echo "$SYSTEM_NAME" + else + echo rs6000-ibm-aix3.2.5 + fi + elif grep bos324 /usr/include/stdio.h >/dev/null 2>&1; then + echo rs6000-ibm-aix3.2.4 + else + echo rs6000-ibm-aix3.2 + fi + exit ;; + *:AIX:*:[45]) + IBM_CPU_ID=`/usr/sbin/lsdev -C -c processor -S available | sed 1q | awk '{ print $1 }'` + if /usr/sbin/lsattr -El ${IBM_CPU_ID} | grep ' POWER' >/dev/null 2>&1; then + IBM_ARCH=rs6000 + else + IBM_ARCH=powerpc + fi + if [ -x /usr/bin/oslevel ] ; then + IBM_REV=`/usr/bin/oslevel` + else + IBM_REV=${UNAME_VERSION}.${UNAME_RELEASE} + fi + echo ${IBM_ARCH}-ibm-aix${IBM_REV} + exit ;; + *:AIX:*:*) + echo rs6000-ibm-aix + exit ;; + ibmrt:4.4BSD:*|romp-ibm:BSD:*) + echo romp-ibm-bsd4.4 + exit ;; + ibmrt:*BSD:*|romp-ibm:BSD:*) # covers RT/PC BSD and + echo romp-ibm-bsd${UNAME_RELEASE} # 4.3 with uname added to + exit ;; # report: romp-ibm BSD 4.3 + *:BOSX:*:*) + echo rs6000-bull-bosx + exit ;; + DPX/2?00:B.O.S.:*:*) + echo m68k-bull-sysv3 + exit ;; + 9000/[34]??:4.3bsd:1.*:*) + echo m68k-hp-bsd + exit ;; + hp300:4.4BSD:*:* | 9000/[34]??:4.3bsd:2.*:*) + echo m68k-hp-bsd4.4 + exit ;; + 9000/[34678]??:HP-UX:*:*) + HPUX_REV=`echo ${UNAME_RELEASE}|sed -e 's/[^.]*.[0B]*//'` + case "${UNAME_MACHINE}" in + 9000/31? ) HP_ARCH=m68000 ;; + 9000/[34]?? ) HP_ARCH=m68k ;; + 9000/[678][0-9][0-9]) + if [ -x /usr/bin/getconf ]; then + sc_cpu_version=`/usr/bin/getconf SC_CPU_VERSION 2>/dev/null` + sc_kernel_bits=`/usr/bin/getconf SC_KERNEL_BITS 2>/dev/null` + case "${sc_cpu_version}" in + 523) HP_ARCH="hppa1.0" ;; # CPU_PA_RISC1_0 + 528) HP_ARCH="hppa1.1" ;; # CPU_PA_RISC1_1 + 532) # CPU_PA_RISC2_0 + case "${sc_kernel_bits}" in + 32) HP_ARCH="hppa2.0n" ;; + 64) HP_ARCH="hppa2.0w" ;; + '') HP_ARCH="hppa2.0" ;; # HP-UX 10.20 + esac ;; + esac + fi + if [ "${HP_ARCH}" = "" ]; then + eval $set_cc_for_build + sed 's/^ //' << EOF >$dummy.c + + #define _HPUX_SOURCE + #include + #include + + int main () + { + #if defined(_SC_KERNEL_BITS) + long bits = sysconf(_SC_KERNEL_BITS); + #endif + long cpu = sysconf (_SC_CPU_VERSION); + + switch (cpu) + { + case CPU_PA_RISC1_0: puts ("hppa1.0"); break; + case CPU_PA_RISC1_1: puts ("hppa1.1"); break; + case CPU_PA_RISC2_0: + #if defined(_SC_KERNEL_BITS) + switch (bits) + { + case 64: puts ("hppa2.0w"); break; + case 32: puts ("hppa2.0n"); break; + default: puts ("hppa2.0"); break; + } break; + #else /* !defined(_SC_KERNEL_BITS) */ + puts ("hppa2.0"); break; + #endif + default: puts ("hppa1.0"); break; + } + exit (0); + } +EOF + (CCOPTS= $CC_FOR_BUILD -o $dummy $dummy.c 2>/dev/null) && HP_ARCH=`$dummy` + test -z "$HP_ARCH" && HP_ARCH=hppa + fi ;; + esac + if [ ${HP_ARCH} = "hppa2.0w" ] + then + eval $set_cc_for_build + + # hppa2.0w-hp-hpux* has a 64-bit kernel and a compiler generating + # 32-bit code. hppa64-hp-hpux* has the same kernel and a compiler + # generating 64-bit code. GNU and HP use different nomenclature: + # + # $ CC_FOR_BUILD=cc ./config.guess + # => hppa2.0w-hp-hpux11.23 + # $ CC_FOR_BUILD="cc +DA2.0w" ./config.guess + # => hppa64-hp-hpux11.23 + + if echo __LP64__ | (CCOPTS= $CC_FOR_BUILD -E - 2>/dev/null) | + grep __LP64__ >/dev/null + then + HP_ARCH="hppa2.0w" + else + HP_ARCH="hppa64" + fi + fi + echo ${HP_ARCH}-hp-hpux${HPUX_REV} + exit ;; + ia64:HP-UX:*:*) + HPUX_REV=`echo ${UNAME_RELEASE}|sed -e 's/[^.]*.[0B]*//'` + echo ia64-hp-hpux${HPUX_REV} + exit ;; + 3050*:HI-UX:*:*) + eval $set_cc_for_build + sed 's/^ //' << EOF >$dummy.c + #include + int + main () + { + long cpu = sysconf (_SC_CPU_VERSION); + /* The order matters, because CPU_IS_HP_MC68K erroneously returns + true for CPU_PA_RISC1_0. CPU_IS_PA_RISC returns correct + results, however. */ + if (CPU_IS_PA_RISC (cpu)) + { + switch (cpu) + { + case CPU_PA_RISC1_0: puts ("hppa1.0-hitachi-hiuxwe2"); break; + case CPU_PA_RISC1_1: puts ("hppa1.1-hitachi-hiuxwe2"); break; + case CPU_PA_RISC2_0: puts ("hppa2.0-hitachi-hiuxwe2"); break; + default: puts ("hppa-hitachi-hiuxwe2"); break; + } + } + else if (CPU_IS_HP_MC68K (cpu)) + puts ("m68k-hitachi-hiuxwe2"); + else puts ("unknown-hitachi-hiuxwe2"); + exit (0); + } +EOF + $CC_FOR_BUILD -o $dummy $dummy.c && SYSTEM_NAME=`$dummy` && + { echo "$SYSTEM_NAME"; exit; } + echo unknown-hitachi-hiuxwe2 + exit ;; + 9000/7??:4.3bsd:*:* | 9000/8?[79]:4.3bsd:*:* ) + echo hppa1.1-hp-bsd + exit ;; + 9000/8??:4.3bsd:*:*) + echo hppa1.0-hp-bsd + exit ;; + *9??*:MPE/iX:*:* | *3000*:MPE/iX:*:*) + echo hppa1.0-hp-mpeix + exit ;; + hp7??:OSF1:*:* | hp8?[79]:OSF1:*:* ) + echo hppa1.1-hp-osf + exit ;; + hp8??:OSF1:*:*) + echo hppa1.0-hp-osf + exit ;; + i*86:OSF1:*:*) + if [ -x /usr/sbin/sysversion ] ; then + echo ${UNAME_MACHINE}-unknown-osf1mk + else + echo ${UNAME_MACHINE}-unknown-osf1 + fi + exit ;; + parisc*:Lites*:*:*) + echo hppa1.1-hp-lites + exit ;; + C1*:ConvexOS:*:* | convex:ConvexOS:C1*:*) + echo c1-convex-bsd + exit ;; + C2*:ConvexOS:*:* | convex:ConvexOS:C2*:*) + if getsysinfo -f scalar_acc + then echo c32-convex-bsd + else echo c2-convex-bsd + fi + exit ;; + C34*:ConvexOS:*:* | convex:ConvexOS:C34*:*) + echo c34-convex-bsd + exit ;; + C38*:ConvexOS:*:* | convex:ConvexOS:C38*:*) + echo c38-convex-bsd + exit ;; + C4*:ConvexOS:*:* | convex:ConvexOS:C4*:*) + echo c4-convex-bsd + exit ;; + CRAY*Y-MP:*:*:*) + echo ymp-cray-unicos${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/' + exit ;; + CRAY*[A-Z]90:*:*:*) + echo ${UNAME_MACHINE}-cray-unicos${UNAME_RELEASE} \ + | sed -e 's/CRAY.*\([A-Z]90\)/\1/' \ + -e y/ABCDEFGHIJKLMNOPQRSTUVWXYZ/abcdefghijklmnopqrstuvwxyz/ \ + -e 's/\.[^.]*$/.X/' + exit ;; + CRAY*TS:*:*:*) + echo t90-cray-unicos${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/' + exit ;; + CRAY*T3E:*:*:*) + echo alphaev5-cray-unicosmk${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/' + exit ;; + CRAY*SV1:*:*:*) + echo sv1-cray-unicos${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/' + exit ;; + *:UNICOS/mp:*:*) + echo craynv-cray-unicosmp${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/' + exit ;; + F30[01]:UNIX_System_V:*:* | F700:UNIX_System_V:*:*) + FUJITSU_PROC=`uname -m | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz'` + FUJITSU_SYS=`uname -p | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/\///'` + FUJITSU_REL=`echo ${UNAME_RELEASE} | sed -e 's/ /_/'` + echo "${FUJITSU_PROC}-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}" + exit ;; + 5000:UNIX_System_V:4.*:*) + FUJITSU_SYS=`uname -p | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/\///'` + FUJITSU_REL=`echo ${UNAME_RELEASE} | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/ /_/'` + echo "sparc-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}" + exit ;; + i*86:BSD/386:*:* | i*86:BSD/OS:*:* | *:Ascend\ Embedded/OS:*:*) + echo ${UNAME_MACHINE}-pc-bsdi${UNAME_RELEASE} + exit ;; + sparc*:BSD/OS:*:*) + echo sparc-unknown-bsdi${UNAME_RELEASE} + exit ;; + *:BSD/OS:*:*) + echo ${UNAME_MACHINE}-unknown-bsdi${UNAME_RELEASE} + exit ;; + *:FreeBSD:*:*) + case ${UNAME_MACHINE} in + pc98) + echo i386-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` ;; + *) + echo ${UNAME_MACHINE}-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` ;; + esac + exit ;; + i*:CYGWIN*:*) + echo ${UNAME_MACHINE}-pc-cygwin + exit ;; + i*:MINGW*:*) + echo ${UNAME_MACHINE}-pc-mingw32 + exit ;; + i*:MSYS_NT-*:*:*) + echo ${UNAME_MACHINE}-pc-mingw32 + exit ;; + i*:windows32*:*) + # uname -m includes "-pc" on this system. + echo ${UNAME_MACHINE}-mingw32 + exit ;; + i*:PW*:*) + echo ${UNAME_MACHINE}-pc-pw32 + exit ;; + x86:Interix*:[345]*) + echo i586-pc-interix${UNAME_RELEASE} + exit ;; + EM64T:Interix*:[345]*) + echo x86_64-unknown-interix${UNAME_RELEASE} + exit ;; + [345]86:Windows_95:* | [345]86:Windows_98:* | [345]86:Windows_NT:*) + echo i${UNAME_MACHINE}-pc-mks + exit ;; + i*:Windows_NT*:* | Pentium*:Windows_NT*:*) + # How do we know it's Interix rather than the generic POSIX subsystem? + # It also conflicts with pre-2.0 versions of AT&T UWIN. Should we + # UNAME_MACHINE based on the output of uname instead of i386? + echo i586-pc-interix + exit ;; + i*:UWIN*:*) + echo ${UNAME_MACHINE}-pc-uwin + exit ;; + amd64:CYGWIN*:*:* | x86_64:CYGWIN*:*:*) + echo x86_64-unknown-cygwin + exit ;; + p*:CYGWIN*:*) + echo powerpcle-unknown-cygwin + exit ;; + prep*:SunOS:5.*:*) + echo powerpcle-unknown-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'` + exit ;; + *:GNU:*:*) + # the GNU system + echo `echo ${UNAME_MACHINE}|sed -e 's,[-/].*$,,'`-unknown-gnu`echo ${UNAME_RELEASE}|sed -e 's,/.*$,,'` + exit ;; + *:GNU/*:*:*) + # other systems with GNU libc and userland + echo ${UNAME_MACHINE}-unknown-`echo ${UNAME_SYSTEM} | sed 's,^[^/]*/,,' | tr '[A-Z]' '[a-z]'``echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'`-gnu + exit ;; + i*86:Minix:*:*) + echo ${UNAME_MACHINE}-pc-minix + exit ;; + arm*:Linux:*:*) + echo ${UNAME_MACHINE}-unknown-linux-gnu + exit ;; + cris:Linux:*:*) + echo cris-axis-linux-gnu + exit ;; + crisv32:Linux:*:*) + echo crisv32-axis-linux-gnu + exit ;; + frv:Linux:*:*) + echo frv-unknown-linux-gnu + exit ;; + ia64:Linux:*:*) + echo ${UNAME_MACHINE}-unknown-linux-gnu + exit ;; + m32r*:Linux:*:*) + echo ${UNAME_MACHINE}-unknown-linux-gnu + exit ;; + m68*:Linux:*:*) + echo ${UNAME_MACHINE}-unknown-linux-gnu + exit ;; + mips:Linux:*:*) + eval $set_cc_for_build + sed 's/^ //' << EOF >$dummy.c + #undef CPU + #undef mips + #undef mipsel + #if defined(__MIPSEL__) || defined(__MIPSEL) || defined(_MIPSEL) || defined(MIPSEL) + CPU=mipsel + #else + #if defined(__MIPSEB__) || defined(__MIPSEB) || defined(_MIPSEB) || defined(MIPSEB) + CPU=mips + #else + CPU= + #endif + #endif +EOF + eval "`$CC_FOR_BUILD -E $dummy.c 2>/dev/null | sed -n ' + /^CPU/{ + s: ::g + p + }'`" + test x"${CPU}" != x && { echo "${CPU}-unknown-linux-gnu"; exit; } + ;; + mips64:Linux:*:*) + eval $set_cc_for_build + sed 's/^ //' << EOF >$dummy.c + #undef CPU + #undef mips64 + #undef mips64el + #if defined(__MIPSEL__) || defined(__MIPSEL) || defined(_MIPSEL) || defined(MIPSEL) + CPU=mips64el + #else + #if defined(__MIPSEB__) || defined(__MIPSEB) || defined(_MIPSEB) || defined(MIPSEB) + CPU=mips64 + #else + CPU= + #endif + #endif +EOF + eval "`$CC_FOR_BUILD -E $dummy.c 2>/dev/null | sed -n ' + /^CPU/{ + s: ::g + p + }'`" + test x"${CPU}" != x && { echo "${CPU}-unknown-linux-gnu"; exit; } + ;; + or32:Linux:*:*) + echo or32-unknown-linux-gnu + exit ;; + ppc:Linux:*:*) + echo powerpc-unknown-linux-gnu + exit ;; + ppc64:Linux:*:*) + echo powerpc64-unknown-linux-gnu + exit ;; + alpha:Linux:*:*) + case `sed -n '/^cpu model/s/^.*: \(.*\)/\1/p' < /proc/cpuinfo` in + EV5) UNAME_MACHINE=alphaev5 ;; + EV56) UNAME_MACHINE=alphaev56 ;; + PCA56) UNAME_MACHINE=alphapca56 ;; + PCA57) UNAME_MACHINE=alphapca56 ;; + EV6) UNAME_MACHINE=alphaev6 ;; + EV67) UNAME_MACHINE=alphaev67 ;; + EV68*) UNAME_MACHINE=alphaev68 ;; + esac + objdump --private-headers /bin/sh | grep ld.so.1 >/dev/null + if test "$?" = 0 ; then LIBC="libc1" ; else LIBC="" ; fi + echo ${UNAME_MACHINE}-unknown-linux-gnu${LIBC} + exit ;; + parisc:Linux:*:* | hppa:Linux:*:*) + # Look for CPU level + case `grep '^cpu[^a-z]*:' /proc/cpuinfo 2>/dev/null | cut -d' ' -f2` in + PA7*) echo hppa1.1-unknown-linux-gnu ;; + PA8*) echo hppa2.0-unknown-linux-gnu ;; + *) echo hppa-unknown-linux-gnu ;; + esac + exit ;; + parisc64:Linux:*:* | hppa64:Linux:*:*) + echo hppa64-unknown-linux-gnu + exit ;; + s390:Linux:*:* | s390x:Linux:*:*) + echo ${UNAME_MACHINE}-ibm-linux + exit ;; + sh64*:Linux:*:*) + echo ${UNAME_MACHINE}-unknown-linux-gnu + exit ;; + sh*:Linux:*:*) + echo ${UNAME_MACHINE}-unknown-linux-gnu + exit ;; + sparc:Linux:*:* | sparc64:Linux:*:*) + echo ${UNAME_MACHINE}-unknown-linux-gnu + exit ;; + vax:Linux:*:*) + echo ${UNAME_MACHINE}-dec-linux-gnu + exit ;; + x86_64:Linux:*:*) + echo x86_64-unknown-linux-gnu + exit ;; + i*86:Linux:*:*) + # The BFD linker knows what the default object file format is, so + # first see if it will tell us. cd to the root directory to prevent + # problems with other programs or directories called `ld' in the path. + # Set LC_ALL=C to ensure ld outputs messages in English. + ld_supported_targets=`cd /; LC_ALL=C ld --help 2>&1 \ + | sed -ne '/supported targets:/!d + s/[ ][ ]*/ /g + s/.*supported targets: *// + s/ .*// + p'` + case "$ld_supported_targets" in + elf32-i386) + TENTATIVE="${UNAME_MACHINE}-pc-linux-gnu" + ;; + a.out-i386-linux) + echo "${UNAME_MACHINE}-pc-linux-gnuaout" + exit ;; + coff-i386) + echo "${UNAME_MACHINE}-pc-linux-gnucoff" + exit ;; + "") + # Either a pre-BFD a.out linker (linux-gnuoldld) or + # one that does not give us useful --help. + echo "${UNAME_MACHINE}-pc-linux-gnuoldld" + exit ;; + esac + # Determine whether the default compiler is a.out or elf + eval $set_cc_for_build + sed 's/^ //' << EOF >$dummy.c + #include + #ifdef __ELF__ + # ifdef __GLIBC__ + # if __GLIBC__ >= 2 + LIBC=gnu + # else + LIBC=gnulibc1 + # endif + # else + LIBC=gnulibc1 + # endif + #else + #if defined(__INTEL_COMPILER) || defined(__PGI) || defined(__sun) + LIBC=gnu + #else + LIBC=gnuaout + #endif + #endif + #ifdef __dietlibc__ + LIBC=dietlibc + #endif +EOF + eval "`$CC_FOR_BUILD -E $dummy.c 2>/dev/null | sed -n ' + /^LIBC/{ + s: ::g + p + }'`" + test x"${LIBC}" != x && { + echo "${UNAME_MACHINE}-pc-linux-${LIBC}" + exit + } + test x"${TENTATIVE}" != x && { echo "${TENTATIVE}"; exit; } + ;; + i*86:DYNIX/ptx:4*:*) + # ptx 4.0 does uname -s correctly, with DYNIX/ptx in there. + # earlier versions are messed up and put the nodename in both + # sysname and nodename. + echo i386-sequent-sysv4 + exit ;; + i*86:UNIX_SV:4.2MP:2.*) + # Unixware is an offshoot of SVR4, but it has its own version + # number series starting with 2... + # I am not positive that other SVR4 systems won't match this, + # I just have to hope. -- rms. + # Use sysv4.2uw... so that sysv4* matches it. + echo ${UNAME_MACHINE}-pc-sysv4.2uw${UNAME_VERSION} + exit ;; + i*86:OS/2:*:*) + # If we were able to find `uname', then EMX Unix compatibility + # is probably installed. + echo ${UNAME_MACHINE}-pc-os2-emx + exit ;; + i*86:XTS-300:*:STOP) + echo ${UNAME_MACHINE}-unknown-stop + exit ;; + i*86:atheos:*:*) + echo ${UNAME_MACHINE}-unknown-atheos + exit ;; + i*86:syllable:*:*) + echo ${UNAME_MACHINE}-pc-syllable + exit ;; + i*86:LynxOS:2.*:* | i*86:LynxOS:3.[01]*:* | i*86:LynxOS:4.0*:*) + echo i386-unknown-lynxos${UNAME_RELEASE} + exit ;; + i*86:*DOS:*:*) + echo ${UNAME_MACHINE}-pc-msdosdjgpp + exit ;; + i*86:*:4.*:* | i*86:SYSTEM_V:4.*:*) + UNAME_REL=`echo ${UNAME_RELEASE} | sed 's/\/MP$//'` + if grep Novell /usr/include/link.h >/dev/null 2>/dev/null; then + echo ${UNAME_MACHINE}-univel-sysv${UNAME_REL} + else + echo ${UNAME_MACHINE}-pc-sysv${UNAME_REL} + fi + exit ;; + i*86:*:5:[678]*) + # UnixWare 7.x, OpenUNIX and OpenServer 6. + case `/bin/uname -X | grep "^Machine"` in + *486*) UNAME_MACHINE=i486 ;; + *Pentium) UNAME_MACHINE=i586 ;; + *Pent*|*Celeron) UNAME_MACHINE=i686 ;; + esac + echo ${UNAME_MACHINE}-unknown-sysv${UNAME_RELEASE}${UNAME_SYSTEM}${UNAME_VERSION} + exit ;; + i*86:*:3.2:*) + if test -f /usr/options/cb.name; then + UNAME_REL=`sed -n 's/.*Version //p' /dev/null >/dev/null ; then + UNAME_REL=`(/bin/uname -X|grep Release|sed -e 's/.*= //')` + (/bin/uname -X|grep i80486 >/dev/null) && UNAME_MACHINE=i486 + (/bin/uname -X|grep '^Machine.*Pentium' >/dev/null) \ + && UNAME_MACHINE=i586 + (/bin/uname -X|grep '^Machine.*Pent *II' >/dev/null) \ + && UNAME_MACHINE=i686 + (/bin/uname -X|grep '^Machine.*Pentium Pro' >/dev/null) \ + && UNAME_MACHINE=i686 + echo ${UNAME_MACHINE}-pc-sco$UNAME_REL + else + echo ${UNAME_MACHINE}-pc-sysv32 + fi + exit ;; + pc:*:*:*) + # Left here for compatibility: + # uname -m prints for DJGPP always 'pc', but it prints nothing about + # the processor, so we play safe by assuming i386. + echo i386-pc-msdosdjgpp + exit ;; + Intel:Mach:3*:*) + echo i386-pc-mach3 + exit ;; + paragon:*:*:*) + echo i860-intel-osf1 + exit ;; + i860:*:4.*:*) # i860-SVR4 + if grep Stardent /usr/include/sys/uadmin.h >/dev/null 2>&1 ; then + echo i860-stardent-sysv${UNAME_RELEASE} # Stardent Vistra i860-SVR4 + else # Add other i860-SVR4 vendors below as they are discovered. + echo i860-unknown-sysv${UNAME_RELEASE} # Unknown i860-SVR4 + fi + exit ;; + mini*:CTIX:SYS*5:*) + # "miniframe" + echo m68010-convergent-sysv + exit ;; + mc68k:UNIX:SYSTEM5:3.51m) + echo m68k-convergent-sysv + exit ;; + M680?0:D-NIX:5.3:*) + echo m68k-diab-dnix + exit ;; + M68*:*:R3V[5678]*:*) + test -r /sysV68 && { echo 'm68k-motorola-sysv'; exit; } ;; + 3[345]??:*:4.0:3.0 | 3[34]??A:*:4.0:3.0 | 3[34]??,*:*:4.0:3.0 | 3[34]??/*:*:4.0:3.0 | 4400:*:4.0:3.0 | 4850:*:4.0:3.0 | SKA40:*:4.0:3.0 | SDS2:*:4.0:3.0 | SHG2:*:4.0:3.0 | S7501*:*:4.0:3.0) + OS_REL='' + test -r /etc/.relid \ + && OS_REL=.`sed -n 's/[^ ]* [^ ]* \([0-9][0-9]\).*/\1/p' < /etc/.relid` + /bin/uname -p 2>/dev/null | grep 86 >/dev/null \ + && { echo i486-ncr-sysv4.3${OS_REL}; exit; } + /bin/uname -p 2>/dev/null | /bin/grep entium >/dev/null \ + && { echo i586-ncr-sysv4.3${OS_REL}; exit; } ;; + 3[34]??:*:4.0:* | 3[34]??,*:*:4.0:*) + /bin/uname -p 2>/dev/null | grep 86 >/dev/null \ + && { echo i486-ncr-sysv4; exit; } ;; + m68*:LynxOS:2.*:* | m68*:LynxOS:3.0*:*) + echo m68k-unknown-lynxos${UNAME_RELEASE} + exit ;; + mc68030:UNIX_System_V:4.*:*) + echo m68k-atari-sysv4 + exit ;; + TSUNAMI:LynxOS:2.*:*) + echo sparc-unknown-lynxos${UNAME_RELEASE} + exit ;; + rs6000:LynxOS:2.*:*) + echo rs6000-unknown-lynxos${UNAME_RELEASE} + exit ;; + PowerPC:LynxOS:2.*:* | PowerPC:LynxOS:3.[01]*:* | PowerPC:LynxOS:4.0*:*) + echo powerpc-unknown-lynxos${UNAME_RELEASE} + exit ;; + SM[BE]S:UNIX_SV:*:*) + echo mips-dde-sysv${UNAME_RELEASE} + exit ;; + RM*:ReliantUNIX-*:*:*) + echo mips-sni-sysv4 + exit ;; + RM*:SINIX-*:*:*) + echo mips-sni-sysv4 + exit ;; + *:SINIX-*:*:*) + if uname -p 2>/dev/null >/dev/null ; then + UNAME_MACHINE=`(uname -p) 2>/dev/null` + echo ${UNAME_MACHINE}-sni-sysv4 + else + echo ns32k-sni-sysv + fi + exit ;; + PENTIUM:*:4.0*:*) # Unisys `ClearPath HMP IX 4000' SVR4/MP effort + # says + echo i586-unisys-sysv4 + exit ;; + *:UNIX_System_V:4*:FTX*) + # From Gerald Hewes . + # How about differentiating between stratus architectures? -djm + echo hppa1.1-stratus-sysv4 + exit ;; + *:*:*:FTX*) + # From seanf@swdc.stratus.com. + echo i860-stratus-sysv4 + exit ;; + i*86:VOS:*:*) + # From Paul.Green@stratus.com. + echo ${UNAME_MACHINE}-stratus-vos + exit ;; + *:VOS:*:*) + # From Paul.Green@stratus.com. + echo hppa1.1-stratus-vos + exit ;; + mc68*:A/UX:*:*) + echo m68k-apple-aux${UNAME_RELEASE} + exit ;; + news*:NEWS-OS:6*:*) + echo mips-sony-newsos6 + exit ;; + R[34]000:*System_V*:*:* | R4000:UNIX_SYSV:*:* | R*000:UNIX_SV:*:*) + if [ -d /usr/nec ]; then + echo mips-nec-sysv${UNAME_RELEASE} + else + echo mips-unknown-sysv${UNAME_RELEASE} + fi + exit ;; + BeBox:BeOS:*:*) # BeOS running on hardware made by Be, PPC only. + echo powerpc-be-beos + exit ;; + BeMac:BeOS:*:*) # BeOS running on Mac or Mac clone, PPC only. + echo powerpc-apple-beos + exit ;; + BePC:BeOS:*:*) # BeOS running on Intel PC compatible. + echo i586-pc-beos + exit ;; + SX-4:SUPER-UX:*:*) + echo sx4-nec-superux${UNAME_RELEASE} + exit ;; + SX-5:SUPER-UX:*:*) + echo sx5-nec-superux${UNAME_RELEASE} + exit ;; + SX-6:SUPER-UX:*:*) + echo sx6-nec-superux${UNAME_RELEASE} + exit ;; + Power*:Rhapsody:*:*) + echo powerpc-apple-rhapsody${UNAME_RELEASE} + exit ;; + *:Rhapsody:*:*) + echo ${UNAME_MACHINE}-apple-rhapsody${UNAME_RELEASE} + exit ;; + *:Darwin:*:*) + UNAME_PROCESSOR=`uname -p` || UNAME_PROCESSOR=unknown + case $UNAME_PROCESSOR in + unknown) UNAME_PROCESSOR=powerpc ;; + esac + echo ${UNAME_PROCESSOR}-apple-darwin${UNAME_RELEASE} + exit ;; + *:procnto*:*:* | *:QNX:[0123456789]*:*) + UNAME_PROCESSOR=`uname -p` + if test "$UNAME_PROCESSOR" = "x86"; then + UNAME_PROCESSOR=i386 + UNAME_MACHINE=pc + fi + echo ${UNAME_PROCESSOR}-${UNAME_MACHINE}-nto-qnx${UNAME_RELEASE} + exit ;; + *:QNX:*:4*) + echo i386-pc-qnx + exit ;; + NSE-?:NONSTOP_KERNEL:*:*) + echo nse-tandem-nsk${UNAME_RELEASE} + exit ;; + NSR-?:NONSTOP_KERNEL:*:*) + echo nsr-tandem-nsk${UNAME_RELEASE} + exit ;; + *:NonStop-UX:*:*) + echo mips-compaq-nonstopux + exit ;; + BS2000:POSIX*:*:*) + echo bs2000-siemens-sysv + exit ;; + DS/*:UNIX_System_V:*:*) + echo ${UNAME_MACHINE}-${UNAME_SYSTEM}-${UNAME_RELEASE} + exit ;; + *:Plan9:*:*) + # "uname -m" is not consistent, so use $cputype instead. 386 + # is converted to i386 for consistency with other x86 + # operating systems. + if test "$cputype" = "386"; then + UNAME_MACHINE=i386 + else + UNAME_MACHINE="$cputype" + fi + echo ${UNAME_MACHINE}-unknown-plan9 + exit ;; + *:TOPS-10:*:*) + echo pdp10-unknown-tops10 + exit ;; + *:TENEX:*:*) + echo pdp10-unknown-tenex + exit ;; + KS10:TOPS-20:*:* | KL10:TOPS-20:*:* | TYPE4:TOPS-20:*:*) + echo pdp10-dec-tops20 + exit ;; + XKL-1:TOPS-20:*:* | TYPE5:TOPS-20:*:*) + echo pdp10-xkl-tops20 + exit ;; + *:TOPS-20:*:*) + echo pdp10-unknown-tops20 + exit ;; + *:ITS:*:*) + echo pdp10-unknown-its + exit ;; + SEI:*:*:SEIUX) + echo mips-sei-seiux${UNAME_RELEASE} + exit ;; + *:DragonFly:*:*) + echo ${UNAME_MACHINE}-unknown-dragonfly`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` + exit ;; + *:*VMS:*:*) + UNAME_MACHINE=`(uname -p) 2>/dev/null` + case "${UNAME_MACHINE}" in + A*) echo alpha-dec-vms ; exit ;; + I*) echo ia64-dec-vms ; exit ;; + V*) echo vax-dec-vms ; exit ;; + esac ;; + *:XENIX:*:SysV) + echo i386-pc-xenix + exit ;; + i*86:skyos:*:*) + echo ${UNAME_MACHINE}-pc-skyos`echo ${UNAME_RELEASE}` | sed -e 's/ .*$//' + exit ;; + i*86:rdos:*:*) + echo ${UNAME_MACHINE}-pc-rdos + exit ;; +esac + +#echo '(No uname command or uname output not recognized.)' 1>&2 +#echo "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" 1>&2 + +eval $set_cc_for_build +cat >$dummy.c < +# include +#endif +main () +{ +#if defined (sony) +#if defined (MIPSEB) + /* BFD wants "bsd" instead of "newsos". Perhaps BFD should be changed, + I don't know.... */ + printf ("mips-sony-bsd\n"); exit (0); +#else +#include + printf ("m68k-sony-newsos%s\n", +#ifdef NEWSOS4 + "4" +#else + "" +#endif + ); exit (0); +#endif +#endif + +#if defined (__arm) && defined (__acorn) && defined (__unix) + printf ("arm-acorn-riscix\n"); exit (0); +#endif + +#if defined (hp300) && !defined (hpux) + printf ("m68k-hp-bsd\n"); exit (0); +#endif + +#if defined (NeXT) +#if !defined (__ARCHITECTURE__) +#define __ARCHITECTURE__ "m68k" +#endif + int version; + version=`(hostinfo | sed -n 's/.*NeXT Mach \([0-9]*\).*/\1/p') 2>/dev/null`; + if (version < 4) + printf ("%s-next-nextstep%d\n", __ARCHITECTURE__, version); + else + printf ("%s-next-openstep%d\n", __ARCHITECTURE__, version); + exit (0); +#endif + +#if defined (MULTIMAX) || defined (n16) +#if defined (UMAXV) + printf ("ns32k-encore-sysv\n"); exit (0); +#else +#if defined (CMU) + printf ("ns32k-encore-mach\n"); exit (0); +#else + printf ("ns32k-encore-bsd\n"); exit (0); +#endif +#endif +#endif + +#if defined (__386BSD__) + printf ("i386-pc-bsd\n"); exit (0); +#endif + +#if defined (sequent) +#if defined (i386) + printf ("i386-sequent-dynix\n"); exit (0); +#endif +#if defined (ns32000) + printf ("ns32k-sequent-dynix\n"); exit (0); +#endif +#endif + +#if defined (_SEQUENT_) + struct utsname un; + + uname(&un); + + if (strncmp(un.version, "V2", 2) == 0) { + printf ("i386-sequent-ptx2\n"); exit (0); + } + if (strncmp(un.version, "V1", 2) == 0) { /* XXX is V1 correct? */ + printf ("i386-sequent-ptx1\n"); exit (0); + } + printf ("i386-sequent-ptx\n"); exit (0); + +#endif + +#if defined (vax) +# if !defined (ultrix) +# include +# if defined (BSD) +# if BSD == 43 + printf ("vax-dec-bsd4.3\n"); exit (0); +# else +# if BSD == 199006 + printf ("vax-dec-bsd4.3reno\n"); exit (0); +# else + printf ("vax-dec-bsd\n"); exit (0); +# endif +# endif +# else + printf ("vax-dec-bsd\n"); exit (0); +# endif +# else + printf ("vax-dec-ultrix\n"); exit (0); +# endif +#endif + +#if defined (alliant) && defined (i860) + printf ("i860-alliant-bsd\n"); exit (0); +#endif + + exit (1); +} +EOF + +$CC_FOR_BUILD -o $dummy $dummy.c 2>/dev/null && SYSTEM_NAME=`$dummy` && + { echo "$SYSTEM_NAME"; exit; } + +# Apollos put the system type in the environment. + +test -d /usr/apollo && { echo ${ISP}-apollo-${SYSTYPE}; exit; } + +# Convex versions that predate uname can use getsysinfo(1) + +if [ -x /usr/convex/getsysinfo ] +then + case `getsysinfo -f cpu_type` in + c1*) + echo c1-convex-bsd + exit ;; + c2*) + if getsysinfo -f scalar_acc + then echo c32-convex-bsd + else echo c2-convex-bsd + fi + exit ;; + c34*) + echo c34-convex-bsd + exit ;; + c38*) + echo c38-convex-bsd + exit ;; + c4*) + echo c4-convex-bsd + exit ;; + esac +fi + +cat >&2 < in order to provide the needed +information to handle your system. + +config.guess timestamp = $timestamp + +uname -m = `(uname -m) 2>/dev/null || echo unknown` +uname -r = `(uname -r) 2>/dev/null || echo unknown` +uname -s = `(uname -s) 2>/dev/null || echo unknown` +uname -v = `(uname -v) 2>/dev/null || echo unknown` + +/usr/bin/uname -p = `(/usr/bin/uname -p) 2>/dev/null` +/bin/uname -X = `(/bin/uname -X) 2>/dev/null` + +hostinfo = `(hostinfo) 2>/dev/null` +/bin/universe = `(/bin/universe) 2>/dev/null` +/usr/bin/arch -k = `(/usr/bin/arch -k) 2>/dev/null` +/bin/arch = `(/bin/arch) 2>/dev/null` +/usr/bin/oslevel = `(/usr/bin/oslevel) 2>/dev/null` +/usr/convex/getsysinfo = `(/usr/convex/getsysinfo) 2>/dev/null` + +UNAME_MACHINE = ${UNAME_MACHINE} +UNAME_RELEASE = ${UNAME_RELEASE} +UNAME_SYSTEM = ${UNAME_SYSTEM} +UNAME_VERSION = ${UNAME_VERSION} +EOF + +exit 1 + +# Local variables: +# eval: (add-hook 'write-file-hooks 'time-stamp) +# time-stamp-start: "timestamp='" +# time-stamp-format: "%:y-%02m-%02d" +# time-stamp-end: "'" +# End: diff --git a/libs/libsndfile/config.sub b/libs/libsndfile/config.sub new file mode 100755 index 0000000000..ad9f395711 --- /dev/null +++ b/libs/libsndfile/config.sub @@ -0,0 +1,1608 @@ +#! /bin/sh +# Configuration validation subroutine script. +# Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, +# 2000, 2001, 2002, 2003, 2004, 2005 Free Software Foundation, Inc. + +timestamp='2006-02-23' + +# This file is (in principle) common to ALL GNU software. +# The presence of a machine in this file suggests that SOME GNU software +# can handle that machine. It does not imply ALL GNU software can. +# +# This file is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software +# Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA +# 02110-1301, USA. +# +# As a special exception to the GNU General Public License, if you +# distribute this file as part of a program that contains a +# configuration script generated by Autoconf, you may include it under +# the same distribution terms that you use for the rest of that program. + + +# Please send patches to . Submit a context +# diff and a properly formatted ChangeLog entry. +# +# Configuration subroutine to validate and canonicalize a configuration type. +# Supply the specified configuration type as an argument. +# If it is invalid, we print an error message on stderr and exit with code 1. +# Otherwise, we print the canonical config type on stdout and succeed. + +# This file is supposed to be the same for all GNU packages +# and recognize all the CPU types, system types and aliases +# that are meaningful with *any* GNU software. +# Each package is responsible for reporting which valid configurations +# it does not support. The user should be able to distinguish +# a failure to support a valid configuration from a meaningless +# configuration. + +# The goal of this file is to map all the various variations of a given +# machine specification into a single specification in the form: +# CPU_TYPE-MANUFACTURER-OPERATING_SYSTEM +# or in some cases, the newer four-part form: +# CPU_TYPE-MANUFACTURER-KERNEL-OPERATING_SYSTEM +# It is wrong to echo any other type of specification. + +me=`echo "$0" | sed -e 's,.*/,,'` + +usage="\ +Usage: $0 [OPTION] CPU-MFR-OPSYS + $0 [OPTION] ALIAS + +Canonicalize a configuration name. + +Operation modes: + -h, --help print this help, then exit + -t, --time-stamp print date of last modification, then exit + -v, --version print version number, then exit + +Report bugs and patches to ." + +version="\ +GNU config.sub ($timestamp) + +Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005 +Free Software Foundation, Inc. + +This is free software; see the source for copying conditions. There is NO +warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." + +help=" +Try \`$me --help' for more information." + +# Parse command line +while test $# -gt 0 ; do + case $1 in + --time-stamp | --time* | -t ) + echo "$timestamp" ; exit ;; + --version | -v ) + echo "$version" ; exit ;; + --help | --h* | -h ) + echo "$usage"; exit ;; + -- ) # Stop option processing + shift; break ;; + - ) # Use stdin as input. + break ;; + -* ) + echo "$me: invalid option $1$help" + exit 1 ;; + + *local*) + # First pass through any local machine types. + echo $1 + exit ;; + + * ) + break ;; + esac +done + +case $# in + 0) echo "$me: missing argument$help" >&2 + exit 1;; + 1) ;; + *) echo "$me: too many arguments$help" >&2 + exit 1;; +esac + +# Separate what the user gave into CPU-COMPANY and OS or KERNEL-OS (if any). +# Here we must recognize all the valid KERNEL-OS combinations. +maybe_os=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\2/'` +case $maybe_os in + nto-qnx* | linux-gnu* | linux-dietlibc | linux-newlib* | linux-uclibc* | \ + uclinux-uclibc* | uclinux-gnu* | kfreebsd*-gnu* | knetbsd*-gnu* | netbsd*-gnu* | \ + storm-chaos* | os2-emx* | rtmk-nova*) + os=-$maybe_os + basic_machine=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\1/'` + ;; + *) + basic_machine=`echo $1 | sed 's/-[^-]*$//'` + if [ $basic_machine != $1 ] + then os=`echo $1 | sed 's/.*-/-/'` + else os=; fi + ;; +esac + +### Let's recognize common machines as not being operating systems so +### that things like config.sub decstation-3100 work. We also +### recognize some manufacturers as not being operating systems, so we +### can provide default operating systems below. +case $os in + -sun*os*) + # Prevent following clause from handling this invalid input. + ;; + -dec* | -mips* | -sequent* | -encore* | -pc532* | -sgi* | -sony* | \ + -att* | -7300* | -3300* | -delta* | -motorola* | -sun[234]* | \ + -unicom* | -ibm* | -next | -hp | -isi* | -apollo | -altos* | \ + -convergent* | -ncr* | -news | -32* | -3600* | -3100* | -hitachi* |\ + -c[123]* | -convex* | -sun | -crds | -omron* | -dg | -ultra | -tti* | \ + -harris | -dolphin | -highlevel | -gould | -cbm | -ns | -masscomp | \ + -apple | -axis | -knuth | -cray) + os= + basic_machine=$1 + ;; + -sim | -cisco | -oki | -wec | -winbond) + os= + basic_machine=$1 + ;; + -scout) + ;; + -wrs) + os=-vxworks + basic_machine=$1 + ;; + -chorusos*) + os=-chorusos + basic_machine=$1 + ;; + -chorusrdb) + os=-chorusrdb + basic_machine=$1 + ;; + -hiux*) + os=-hiuxwe2 + ;; + -sco6) + os=-sco5v6 + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -sco5) + os=-sco3.2v5 + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -sco4) + os=-sco3.2v4 + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -sco3.2.[4-9]*) + os=`echo $os | sed -e 's/sco3.2./sco3.2v/'` + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -sco3.2v[4-9]*) + # Don't forget version if it is 3.2v4 or newer. + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -sco5v6*) + # Don't forget version if it is 3.2v4 or newer. + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -sco*) + os=-sco3.2v2 + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -udk*) + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -isc) + os=-isc2.2 + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -clix*) + basic_machine=clipper-intergraph + ;; + -isc*) + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -lynx*) + os=-lynxos + ;; + -ptx*) + basic_machine=`echo $1 | sed -e 's/86-.*/86-sequent/'` + ;; + -windowsnt*) + os=`echo $os | sed -e 's/windowsnt/winnt/'` + ;; + -psos*) + os=-psos + ;; + -mint | -mint[0-9]*) + basic_machine=m68k-atari + os=-mint + ;; +esac + +# Decode aliases for certain CPU-COMPANY combinations. +case $basic_machine in + # Recognize the basic CPU types without company name. + # Some are omitted here because they have special meanings below. + 1750a | 580 \ + | a29k \ + | alpha | alphaev[4-8] | alphaev56 | alphaev6[78] | alphapca5[67] \ + | alpha64 | alpha64ev[4-8] | alpha64ev56 | alpha64ev6[78] | alpha64pca5[67] \ + | am33_2.0 \ + | arc | arm | arm[bl]e | arme[lb] | armv[2345] | armv[345][lb] | avr \ + | bfin \ + | c4x | clipper \ + | d10v | d30v | dlx | dsp16xx \ + | fr30 | frv \ + | h8300 | h8500 | hppa | hppa1.[01] | hppa2.0 | hppa2.0[nw] | hppa64 \ + | i370 | i860 | i960 | ia64 \ + | ip2k | iq2000 \ + | m32r | m32rle | m68000 | m68k | m88k | maxq | mb | microblaze | mcore \ + | mips | mipsbe | mipseb | mipsel | mipsle \ + | mips16 \ + | mips64 | mips64el \ + | mips64vr | mips64vrel \ + | mips64orion | mips64orionel \ + | mips64vr4100 | mips64vr4100el \ + | mips64vr4300 | mips64vr4300el \ + | mips64vr5000 | mips64vr5000el \ + | mips64vr5900 | mips64vr5900el \ + | mipsisa32 | mipsisa32el \ + | mipsisa32r2 | mipsisa32r2el \ + | mipsisa64 | mipsisa64el \ + | mipsisa64r2 | mipsisa64r2el \ + | mipsisa64sb1 | mipsisa64sb1el \ + | mipsisa64sr71k | mipsisa64sr71kel \ + | mipstx39 | mipstx39el \ + | mn10200 | mn10300 \ + | mt \ + | msp430 \ + | nios | nios2 \ + | ns16k | ns32k \ + | or32 \ + | pdp10 | pdp11 | pj | pjl \ + | powerpc | powerpc64 | powerpc64le | powerpcle | ppcbe \ + | pyramid \ + | sh | sh[1234] | sh[24]a | sh[23]e | sh[34]eb | shbe | shle | sh[1234]le | sh3ele \ + | sh64 | sh64le \ + | sparc | sparc64 | sparc64b | sparc86x | sparclet | sparclite \ + | sparcv8 | sparcv9 | sparcv9b \ + | strongarm \ + | tahoe | thumb | tic4x | tic80 | tron \ + | v850 | v850e \ + | we32k \ + | x86 | xscale | xscalee[bl] | xstormy16 | xtensa \ + | z8k) + basic_machine=$basic_machine-unknown + ;; + m32c) + basic_machine=$basic_machine-unknown + ;; + m6811 | m68hc11 | m6812 | m68hc12) + # Motorola 68HC11/12. + basic_machine=$basic_machine-unknown + os=-none + ;; + m88110 | m680[12346]0 | m683?2 | m68360 | m5200 | v70 | w65 | z8k) + ;; + ms1) + basic_machine=mt-unknown + ;; + + # We use `pc' rather than `unknown' + # because (1) that's what they normally are, and + # (2) the word "unknown" tends to confuse beginning users. + i*86 | x86_64) + basic_machine=$basic_machine-pc + ;; + # Object if more than one company name word. + *-*-*) + echo Invalid configuration \`$1\': machine \`$basic_machine\' not recognized 1>&2 + exit 1 + ;; + # Recognize the basic CPU types with company name. + 580-* \ + | a29k-* \ + | alpha-* | alphaev[4-8]-* | alphaev56-* | alphaev6[78]-* \ + | alpha64-* | alpha64ev[4-8]-* | alpha64ev56-* | alpha64ev6[78]-* \ + | alphapca5[67]-* | alpha64pca5[67]-* | arc-* \ + | arm-* | armbe-* | armle-* | armeb-* | armv*-* \ + | avr-* \ + | bfin-* | bs2000-* \ + | c[123]* | c30-* | [cjt]90-* | c4x-* | c54x-* | c55x-* | c6x-* \ + | clipper-* | craynv-* | cydra-* \ + | d10v-* | d30v-* | dlx-* \ + | elxsi-* \ + | f30[01]-* | f700-* | fr30-* | frv-* | fx80-* \ + | h8300-* | h8500-* \ + | hppa-* | hppa1.[01]-* | hppa2.0-* | hppa2.0[nw]-* | hppa64-* \ + | i*86-* | i860-* | i960-* | ia64-* \ + | ip2k-* | iq2000-* \ + | m32r-* | m32rle-* \ + | m68000-* | m680[012346]0-* | m68360-* | m683?2-* | m68k-* \ + | m88110-* | m88k-* | maxq-* | mcore-* \ + | mips-* | mipsbe-* | mipseb-* | mipsel-* | mipsle-* \ + | mips16-* \ + | mips64-* | mips64el-* \ + | mips64vr-* | mips64vrel-* \ + | mips64orion-* | mips64orionel-* \ + | mips64vr4100-* | mips64vr4100el-* \ + | mips64vr4300-* | mips64vr4300el-* \ + | mips64vr5000-* | mips64vr5000el-* \ + | mips64vr5900-* | mips64vr5900el-* \ + | mipsisa32-* | mipsisa32el-* \ + | mipsisa32r2-* | mipsisa32r2el-* \ + | mipsisa64-* | mipsisa64el-* \ + | mipsisa64r2-* | mipsisa64r2el-* \ + | mipsisa64sb1-* | mipsisa64sb1el-* \ + | mipsisa64sr71k-* | mipsisa64sr71kel-* \ + | mipstx39-* | mipstx39el-* \ + | mmix-* \ + | mt-* \ + | msp430-* \ + | nios-* | nios2-* \ + | none-* | np1-* | ns16k-* | ns32k-* \ + | orion-* \ + | pdp10-* | pdp11-* | pj-* | pjl-* | pn-* | power-* \ + | powerpc-* | powerpc64-* | powerpc64le-* | powerpcle-* | ppcbe-* \ + | pyramid-* \ + | romp-* | rs6000-* \ + | sh-* | sh[1234]-* | sh[24]a-* | sh[23]e-* | sh[34]eb-* | shbe-* \ + | shle-* | sh[1234]le-* | sh3ele-* | sh64-* | sh64le-* \ + | sparc-* | sparc64-* | sparc64b-* | sparc86x-* | sparclet-* \ + | sparclite-* \ + | sparcv8-* | sparcv9-* | sparcv9b-* | strongarm-* | sv1-* | sx?-* \ + | tahoe-* | thumb-* \ + | tic30-* | tic4x-* | tic54x-* | tic55x-* | tic6x-* | tic80-* \ + | tron-* \ + | v850-* | v850e-* | vax-* \ + | we32k-* \ + | x86-* | x86_64-* | xps100-* | xscale-* | xscalee[bl]-* \ + | xstormy16-* | xtensa-* \ + | ymp-* \ + | z8k-*) + ;; + m32c-*) + ;; + # Recognize the various machine names and aliases which stand + # for a CPU type and a company and sometimes even an OS. + 386bsd) + basic_machine=i386-unknown + os=-bsd + ;; + 3b1 | 7300 | 7300-att | att-7300 | pc7300 | safari | unixpc) + basic_machine=m68000-att + ;; + 3b*) + basic_machine=we32k-att + ;; + a29khif) + basic_machine=a29k-amd + os=-udi + ;; + abacus) + basic_machine=abacus-unknown + ;; + adobe68k) + basic_machine=m68010-adobe + os=-scout + ;; + alliant | fx80) + basic_machine=fx80-alliant + ;; + altos | altos3068) + basic_machine=m68k-altos + ;; + am29k) + basic_machine=a29k-none + os=-bsd + ;; + amd64) + basic_machine=x86_64-pc + ;; + amd64-*) + basic_machine=x86_64-`echo $basic_machine | sed 's/^[^-]*-//'` + ;; + amdahl) + basic_machine=580-amdahl + os=-sysv + ;; + amiga | amiga-*) + basic_machine=m68k-unknown + ;; + amigaos | amigados) + basic_machine=m68k-unknown + os=-amigaos + ;; + amigaunix | amix) + basic_machine=m68k-unknown + os=-sysv4 + ;; + apollo68) + basic_machine=m68k-apollo + os=-sysv + ;; + apollo68bsd) + basic_machine=m68k-apollo + os=-bsd + ;; + aux) + basic_machine=m68k-apple + os=-aux + ;; + balance) + basic_machine=ns32k-sequent + os=-dynix + ;; + c90) + basic_machine=c90-cray + os=-unicos + ;; + convex-c1) + basic_machine=c1-convex + os=-bsd + ;; + convex-c2) + basic_machine=c2-convex + os=-bsd + ;; + convex-c32) + basic_machine=c32-convex + os=-bsd + ;; + convex-c34) + basic_machine=c34-convex + os=-bsd + ;; + convex-c38) + basic_machine=c38-convex + os=-bsd + ;; + cray | j90) + basic_machine=j90-cray + os=-unicos + ;; + craynv) + basic_machine=craynv-cray + os=-unicosmp + ;; + cr16c) + basic_machine=cr16c-unknown + os=-elf + ;; + crds | unos) + basic_machine=m68k-crds + ;; + crisv32 | crisv32-* | etraxfs*) + basic_machine=crisv32-axis + ;; + cris | cris-* | etrax*) + basic_machine=cris-axis + ;; + crx) + basic_machine=crx-unknown + os=-elf + ;; + da30 | da30-*) + basic_machine=m68k-da30 + ;; + decstation | decstation-3100 | pmax | pmax-* | pmin | dec3100 | decstatn) + basic_machine=mips-dec + ;; + decsystem10* | dec10*) + basic_machine=pdp10-dec + os=-tops10 + ;; + decsystem20* | dec20*) + basic_machine=pdp10-dec + os=-tops20 + ;; + delta | 3300 | motorola-3300 | motorola-delta \ + | 3300-motorola | delta-motorola) + basic_machine=m68k-motorola + ;; + delta88) + basic_machine=m88k-motorola + os=-sysv3 + ;; + djgpp) + basic_machine=i586-pc + os=-msdosdjgpp + ;; + dpx20 | dpx20-*) + basic_machine=rs6000-bull + os=-bosx + ;; + dpx2* | dpx2*-bull) + basic_machine=m68k-bull + os=-sysv3 + ;; + ebmon29k) + basic_machine=a29k-amd + os=-ebmon + ;; + elxsi) + basic_machine=elxsi-elxsi + os=-bsd + ;; + encore | umax | mmax) + basic_machine=ns32k-encore + ;; + es1800 | OSE68k | ose68k | ose | OSE) + basic_machine=m68k-ericsson + os=-ose + ;; + fx2800) + basic_machine=i860-alliant + ;; + genix) + basic_machine=ns32k-ns + ;; + gmicro) + basic_machine=tron-gmicro + os=-sysv + ;; + go32) + basic_machine=i386-pc + os=-go32 + ;; + h3050r* | hiux*) + basic_machine=hppa1.1-hitachi + os=-hiuxwe2 + ;; + h8300hms) + basic_machine=h8300-hitachi + os=-hms + ;; + h8300xray) + basic_machine=h8300-hitachi + os=-xray + ;; + h8500hms) + basic_machine=h8500-hitachi + os=-hms + ;; + harris) + basic_machine=m88k-harris + os=-sysv3 + ;; + hp300-*) + basic_machine=m68k-hp + ;; + hp300bsd) + basic_machine=m68k-hp + os=-bsd + ;; + hp300hpux) + basic_machine=m68k-hp + os=-hpux + ;; + hp3k9[0-9][0-9] | hp9[0-9][0-9]) + basic_machine=hppa1.0-hp + ;; + hp9k2[0-9][0-9] | hp9k31[0-9]) + basic_machine=m68000-hp + ;; + hp9k3[2-9][0-9]) + basic_machine=m68k-hp + ;; + hp9k6[0-9][0-9] | hp6[0-9][0-9]) + basic_machine=hppa1.0-hp + ;; + hp9k7[0-79][0-9] | hp7[0-79][0-9]) + basic_machine=hppa1.1-hp + ;; + hp9k78[0-9] | hp78[0-9]) + # FIXME: really hppa2.0-hp + basic_machine=hppa1.1-hp + ;; + hp9k8[67]1 | hp8[67]1 | hp9k80[24] | hp80[24] | hp9k8[78]9 | hp8[78]9 | hp9k893 | hp893) + # FIXME: really hppa2.0-hp + basic_machine=hppa1.1-hp + ;; + hp9k8[0-9][13679] | hp8[0-9][13679]) + basic_machine=hppa1.1-hp + ;; + hp9k8[0-9][0-9] | hp8[0-9][0-9]) + basic_machine=hppa1.0-hp + ;; + hppa-next) + os=-nextstep3 + ;; + hppaosf) + basic_machine=hppa1.1-hp + os=-osf + ;; + hppro) + basic_machine=hppa1.1-hp + os=-proelf + ;; + i370-ibm* | ibm*) + basic_machine=i370-ibm + ;; +# I'm not sure what "Sysv32" means. Should this be sysv3.2? + i*86v32) + basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'` + os=-sysv32 + ;; + i*86v4*) + basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'` + os=-sysv4 + ;; + i*86v) + basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'` + os=-sysv + ;; + i*86sol2) + basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'` + os=-solaris2 + ;; + i386mach) + basic_machine=i386-mach + os=-mach + ;; + i386-vsta | vsta) + basic_machine=i386-unknown + os=-vsta + ;; + iris | iris4d) + basic_machine=mips-sgi + case $os in + -irix*) + ;; + *) + os=-irix4 + ;; + esac + ;; + isi68 | isi) + basic_machine=m68k-isi + os=-sysv + ;; + m88k-omron*) + basic_machine=m88k-omron + ;; + magnum | m3230) + basic_machine=mips-mips + os=-sysv + ;; + merlin) + basic_machine=ns32k-utek + os=-sysv + ;; + mingw32) + basic_machine=i386-pc + os=-mingw32 + ;; + miniframe) + basic_machine=m68000-convergent + ;; + *mint | -mint[0-9]* | *MiNT | *MiNT[0-9]*) + basic_machine=m68k-atari + os=-mint + ;; + mips3*-*) + basic_machine=`echo $basic_machine | sed -e 's/mips3/mips64/'` + ;; + mips3*) + basic_machine=`echo $basic_machine | sed -e 's/mips3/mips64/'`-unknown + ;; + monitor) + basic_machine=m68k-rom68k + os=-coff + ;; + morphos) + basic_machine=powerpc-unknown + os=-morphos + ;; + msdos) + basic_machine=i386-pc + os=-msdos + ;; + ms1-*) + basic_machine=`echo $basic_machine | sed -e 's/ms1-/mt-/'` + ;; + mvs) + basic_machine=i370-ibm + os=-mvs + ;; + ncr3000) + basic_machine=i486-ncr + os=-sysv4 + ;; + netbsd386) + basic_machine=i386-unknown + os=-netbsd + ;; + netwinder) + basic_machine=armv4l-rebel + os=-linux + ;; + news | news700 | news800 | news900) + basic_machine=m68k-sony + os=-newsos + ;; + news1000) + basic_machine=m68030-sony + os=-newsos + ;; + news-3600 | risc-news) + basic_machine=mips-sony + os=-newsos + ;; + necv70) + basic_machine=v70-nec + os=-sysv + ;; + next | m*-next ) + basic_machine=m68k-next + case $os in + -nextstep* ) + ;; + -ns2*) + os=-nextstep2 + ;; + *) + os=-nextstep3 + ;; + esac + ;; + nh3000) + basic_machine=m68k-harris + os=-cxux + ;; + nh[45]000) + basic_machine=m88k-harris + os=-cxux + ;; + nindy960) + basic_machine=i960-intel + os=-nindy + ;; + mon960) + basic_machine=i960-intel + os=-mon960 + ;; + nonstopux) + basic_machine=mips-compaq + os=-nonstopux + ;; + np1) + basic_machine=np1-gould + ;; + nsr-tandem) + basic_machine=nsr-tandem + ;; + op50n-* | op60c-*) + basic_machine=hppa1.1-oki + os=-proelf + ;; + openrisc | openrisc-*) + basic_machine=or32-unknown + ;; + os400) + basic_machine=powerpc-ibm + os=-os400 + ;; + OSE68000 | ose68000) + basic_machine=m68000-ericsson + os=-ose + ;; + os68k) + basic_machine=m68k-none + os=-os68k + ;; + pa-hitachi) + basic_machine=hppa1.1-hitachi + os=-hiuxwe2 + ;; + paragon) + basic_machine=i860-intel + os=-osf + ;; + pbd) + basic_machine=sparc-tti + ;; + pbb) + basic_machine=m68k-tti + ;; + pc532 | pc532-*) + basic_machine=ns32k-pc532 + ;; + pc98) + basic_machine=i386-pc + ;; + pc98-*) + basic_machine=i386-`echo $basic_machine | sed 's/^[^-]*-//'` + ;; + pentium | p5 | k5 | k6 | nexgen | viac3) + basic_machine=i586-pc + ;; + pentiumpro | p6 | 6x86 | athlon | athlon_*) + basic_machine=i686-pc + ;; + pentiumii | pentium2 | pentiumiii | pentium3) + basic_machine=i686-pc + ;; + pentium4) + basic_machine=i786-pc + ;; + pentium-* | p5-* | k5-* | k6-* | nexgen-* | viac3-*) + basic_machine=i586-`echo $basic_machine | sed 's/^[^-]*-//'` + ;; + pentiumpro-* | p6-* | 6x86-* | athlon-*) + basic_machine=i686-`echo $basic_machine | sed 's/^[^-]*-//'` + ;; + pentiumii-* | pentium2-* | pentiumiii-* | pentium3-*) + basic_machine=i686-`echo $basic_machine | sed 's/^[^-]*-//'` + ;; + pentium4-*) + basic_machine=i786-`echo $basic_machine | sed 's/^[^-]*-//'` + ;; + pn) + basic_machine=pn-gould + ;; + power) basic_machine=power-ibm + ;; + ppc) basic_machine=powerpc-unknown + ;; + ppc-*) basic_machine=powerpc-`echo $basic_machine | sed 's/^[^-]*-//'` + ;; + ppcle | powerpclittle | ppc-le | powerpc-little) + basic_machine=powerpcle-unknown + ;; + ppcle-* | powerpclittle-*) + basic_machine=powerpcle-`echo $basic_machine | sed 's/^[^-]*-//'` + ;; + ppc64) basic_machine=powerpc64-unknown + ;; + ppc64-*) basic_machine=powerpc64-`echo $basic_machine | sed 's/^[^-]*-//'` + ;; + ppc64le | powerpc64little | ppc64-le | powerpc64-little) + basic_machine=powerpc64le-unknown + ;; + ppc64le-* | powerpc64little-*) + basic_machine=powerpc64le-`echo $basic_machine | sed 's/^[^-]*-//'` + ;; + ps2) + basic_machine=i386-ibm + ;; + pw32) + basic_machine=i586-unknown + os=-pw32 + ;; + rdos) + basic_machine=i386-pc + os=-rdos + ;; + rom68k) + basic_machine=m68k-rom68k + os=-coff + ;; + rm[46]00) + basic_machine=mips-siemens + ;; + rtpc | rtpc-*) + basic_machine=romp-ibm + ;; + s390 | s390-*) + basic_machine=s390-ibm + ;; + s390x | s390x-*) + basic_machine=s390x-ibm + ;; + sa29200) + basic_machine=a29k-amd + os=-udi + ;; + sb1) + basic_machine=mipsisa64sb1-unknown + ;; + sb1el) + basic_machine=mipsisa64sb1el-unknown + ;; + sei) + basic_machine=mips-sei + os=-seiux + ;; + sequent) + basic_machine=i386-sequent + ;; + sh) + basic_machine=sh-hitachi + os=-hms + ;; + sh64) + basic_machine=sh64-unknown + ;; + sparclite-wrs | simso-wrs) + basic_machine=sparclite-wrs + os=-vxworks + ;; + sps7) + basic_machine=m68k-bull + os=-sysv2 + ;; + spur) + basic_machine=spur-unknown + ;; + st2000) + basic_machine=m68k-tandem + ;; + stratus) + basic_machine=i860-stratus + os=-sysv4 + ;; + sun2) + basic_machine=m68000-sun + ;; + sun2os3) + basic_machine=m68000-sun + os=-sunos3 + ;; + sun2os4) + basic_machine=m68000-sun + os=-sunos4 + ;; + sun3os3) + basic_machine=m68k-sun + os=-sunos3 + ;; + sun3os4) + basic_machine=m68k-sun + os=-sunos4 + ;; + sun4os3) + basic_machine=sparc-sun + os=-sunos3 + ;; + sun4os4) + basic_machine=sparc-sun + os=-sunos4 + ;; + sun4sol2) + basic_machine=sparc-sun + os=-solaris2 + ;; + sun3 | sun3-*) + basic_machine=m68k-sun + ;; + sun4) + basic_machine=sparc-sun + ;; + sun386 | sun386i | roadrunner) + basic_machine=i386-sun + ;; + sv1) + basic_machine=sv1-cray + os=-unicos + ;; + symmetry) + basic_machine=i386-sequent + os=-dynix + ;; + t3e) + basic_machine=alphaev5-cray + os=-unicos + ;; + t90) + basic_machine=t90-cray + os=-unicos + ;; + tic54x | c54x*) + basic_machine=tic54x-unknown + os=-coff + ;; + tic55x | c55x*) + basic_machine=tic55x-unknown + os=-coff + ;; + tic6x | c6x*) + basic_machine=tic6x-unknown + os=-coff + ;; + tx39) + basic_machine=mipstx39-unknown + ;; + tx39el) + basic_machine=mipstx39el-unknown + ;; + toad1) + basic_machine=pdp10-xkl + os=-tops20 + ;; + tower | tower-32) + basic_machine=m68k-ncr + ;; + tpf) + basic_machine=s390x-ibm + os=-tpf + ;; + udi29k) + basic_machine=a29k-amd + os=-udi + ;; + ultra3) + basic_machine=a29k-nyu + os=-sym1 + ;; + v810 | necv810) + basic_machine=v810-nec + os=-none + ;; + vaxv) + basic_machine=vax-dec + os=-sysv + ;; + vms) + basic_machine=vax-dec + os=-vms + ;; + vpp*|vx|vx-*) + basic_machine=f301-fujitsu + ;; + vxworks960) + basic_machine=i960-wrs + os=-vxworks + ;; + vxworks68) + basic_machine=m68k-wrs + os=-vxworks + ;; + vxworks29k) + basic_machine=a29k-wrs + os=-vxworks + ;; + w65*) + basic_machine=w65-wdc + os=-none + ;; + w89k-*) + basic_machine=hppa1.1-winbond + os=-proelf + ;; + xbox) + basic_machine=i686-pc + os=-mingw32 + ;; + xps | xps100) + basic_machine=xps100-honeywell + ;; + ymp) + basic_machine=ymp-cray + os=-unicos + ;; + z8k-*-coff) + basic_machine=z8k-unknown + os=-sim + ;; + none) + basic_machine=none-none + os=-none + ;; + +# Here we handle the default manufacturer of certain CPU types. It is in +# some cases the only manufacturer, in others, it is the most popular. + w89k) + basic_machine=hppa1.1-winbond + ;; + op50n) + basic_machine=hppa1.1-oki + ;; + op60c) + basic_machine=hppa1.1-oki + ;; + romp) + basic_machine=romp-ibm + ;; + mmix) + basic_machine=mmix-knuth + ;; + rs6000) + basic_machine=rs6000-ibm + ;; + vax) + basic_machine=vax-dec + ;; + pdp10) + # there are many clones, so DEC is not a safe bet + basic_machine=pdp10-unknown + ;; + pdp11) + basic_machine=pdp11-dec + ;; + we32k) + basic_machine=we32k-att + ;; + sh[1234] | sh[24]a | sh[34]eb | sh[1234]le | sh[23]ele) + basic_machine=sh-unknown + ;; + sparc | sparcv8 | sparcv9 | sparcv9b) + basic_machine=sparc-sun + ;; + cydra) + basic_machine=cydra-cydrome + ;; + orion) + basic_machine=orion-highlevel + ;; + orion105) + basic_machine=clipper-highlevel + ;; + mac | mpw | mac-mpw) + basic_machine=m68k-apple + ;; + pmac | pmac-mpw) + basic_machine=powerpc-apple + ;; + *-unknown) + # Make sure to match an already-canonicalized machine name. + ;; + *) + echo Invalid configuration \`$1\': machine \`$basic_machine\' not recognized 1>&2 + exit 1 + ;; +esac + +# Here we canonicalize certain aliases for manufacturers. +case $basic_machine in + *-digital*) + basic_machine=`echo $basic_machine | sed 's/digital.*/dec/'` + ;; + *-commodore*) + basic_machine=`echo $basic_machine | sed 's/commodore.*/cbm/'` + ;; + *) + ;; +esac + +# Decode manufacturer-specific aliases for certain operating systems. + +if [ x"$os" != x"" ] +then +case $os in + # First match some system type aliases + # that might get confused with valid system types. + # -solaris* is a basic system type, with this one exception. + -solaris1 | -solaris1.*) + os=`echo $os | sed -e 's|solaris1|sunos4|'` + ;; + -solaris) + os=-solaris2 + ;; + -svr4*) + os=-sysv4 + ;; + -unixware*) + os=-sysv4.2uw + ;; + -gnu/linux*) + os=`echo $os | sed -e 's|gnu/linux|linux-gnu|'` + ;; + # First accept the basic system types. + # The portable systems comes first. + # Each alternative MUST END IN A *, to match a version number. + # -sysv* is not here because it comes later, after sysvr4. + -gnu* | -bsd* | -mach* | -minix* | -genix* | -ultrix* | -irix* \ + | -*vms* | -sco* | -esix* | -isc* | -aix* | -sunos | -sunos[34]*\ + | -hpux* | -unos* | -osf* | -luna* | -dgux* | -solaris* | -sym* \ + | -amigaos* | -amigados* | -msdos* | -newsos* | -unicos* | -aof* \ + | -aos* \ + | -nindy* | -vxsim* | -vxworks* | -ebmon* | -hms* | -mvs* \ + | -clix* | -riscos* | -uniplus* | -iris* | -rtu* | -xenix* \ + | -hiux* | -386bsd* | -knetbsd* | -mirbsd* | -netbsd* \ + | -openbsd* | -solidbsd* \ + | -ekkobsd* | -kfreebsd* | -freebsd* | -riscix* | -lynxos* \ + | -bosx* | -nextstep* | -cxux* | -aout* | -elf* | -oabi* \ + | -ptx* | -coff* | -ecoff* | -winnt* | -domain* | -vsta* \ + | -udi* | -eabi* | -lites* | -ieee* | -go32* | -aux* \ + | -chorusos* | -chorusrdb* \ + | -cygwin* | -pe* | -psos* | -moss* | -proelf* | -rtems* \ + | -mingw32* | -linux-gnu* | -linux-newlib* | -linux-uclibc* \ + | -uxpv* | -beos* | -mpeix* | -udk* \ + | -interix* | -uwin* | -mks* | -rhapsody* | -darwin* | -opened* \ + | -openstep* | -oskit* | -conix* | -pw32* | -nonstopux* \ + | -storm-chaos* | -tops10* | -tenex* | -tops20* | -its* \ + | -os2* | -vos* | -palmos* | -uclinux* | -nucleus* \ + | -morphos* | -superux* | -rtmk* | -rtmk-nova* | -windiss* \ + | -powermax* | -dnix* | -nx6 | -nx7 | -sei* | -dragonfly* \ + | -skyos* | -haiku* | -rdos*) + # Remember, each alternative MUST END IN *, to match a version number. + ;; + -qnx*) + case $basic_machine in + x86-* | i*86-*) + ;; + *) + os=-nto$os + ;; + esac + ;; + -nto-qnx*) + ;; + -nto*) + os=`echo $os | sed -e 's|nto|nto-qnx|'` + ;; + -sim | -es1800* | -hms* | -xray | -os68k* | -none* | -v88r* \ + | -windows* | -osx | -abug | -netware* | -os9* | -beos* | -haiku* \ + | -macos* | -mpw* | -magic* | -mmixware* | -mon960* | -lnews*) + ;; + -mac*) + os=`echo $os | sed -e 's|mac|macos|'` + ;; + -linux-dietlibc) + os=-linux-dietlibc + ;; + -linux*) + os=`echo $os | sed -e 's|linux|linux-gnu|'` + ;; + -sunos5*) + os=`echo $os | sed -e 's|sunos5|solaris2|'` + ;; + -sunos6*) + os=`echo $os | sed -e 's|sunos6|solaris3|'` + ;; + -opened*) + os=-openedition + ;; + -os400*) + os=-os400 + ;; + -wince*) + os=-wince + ;; + -osfrose*) + os=-osfrose + ;; + -osf*) + os=-osf + ;; + -utek*) + os=-bsd + ;; + -dynix*) + os=-bsd + ;; + -acis*) + os=-aos + ;; + -atheos*) + os=-atheos + ;; + -syllable*) + os=-syllable + ;; + -386bsd) + os=-bsd + ;; + -ctix* | -uts*) + os=-sysv + ;; + -nova*) + os=-rtmk-nova + ;; + -ns2 ) + os=-nextstep2 + ;; + -nsk*) + os=-nsk + ;; + # Preserve the version number of sinix5. + -sinix5.*) + os=`echo $os | sed -e 's|sinix|sysv|'` + ;; + -sinix*) + os=-sysv4 + ;; + -tpf*) + os=-tpf + ;; + -triton*) + os=-sysv3 + ;; + -oss*) + os=-sysv3 + ;; + -svr4) + os=-sysv4 + ;; + -svr3) + os=-sysv3 + ;; + -sysvr4) + os=-sysv4 + ;; + # This must come after -sysvr4. + -sysv*) + ;; + -ose*) + os=-ose + ;; + -es1800*) + os=-ose + ;; + -xenix) + os=-xenix + ;; + -*mint | -mint[0-9]* | -*MiNT | -MiNT[0-9]*) + os=-mint + ;; + -aros*) + os=-aros + ;; + -kaos*) + os=-kaos + ;; + -zvmoe) + os=-zvmoe + ;; + -none) + ;; + *) + # Get rid of the `-' at the beginning of $os. + os=`echo $os | sed 's/[^-]*-//'` + echo Invalid configuration \`$1\': system \`$os\' not recognized 1>&2 + exit 1 + ;; +esac +else + +# Here we handle the default operating systems that come with various machines. +# The value should be what the vendor currently ships out the door with their +# machine or put another way, the most popular os provided with the machine. + +# Note that if you're going to try to match "-MANUFACTURER" here (say, +# "-sun"), then you have to tell the case statement up towards the top +# that MANUFACTURER isn't an operating system. Otherwise, code above +# will signal an error saying that MANUFACTURER isn't an operating +# system, and we'll never get to this point. + +case $basic_machine in + *-acorn) + os=-riscix1.2 + ;; + arm*-rebel) + os=-linux + ;; + arm*-semi) + os=-aout + ;; + c4x-* | tic4x-*) + os=-coff + ;; + # This must come before the *-dec entry. + pdp10-*) + os=-tops20 + ;; + pdp11-*) + os=-none + ;; + *-dec | vax-*) + os=-ultrix4.2 + ;; + m68*-apollo) + os=-domain + ;; + i386-sun) + os=-sunos4.0.2 + ;; + m68000-sun) + os=-sunos3 + # This also exists in the configure program, but was not the + # default. + # os=-sunos4 + ;; + m68*-cisco) + os=-aout + ;; + mips*-cisco) + os=-elf + ;; + mips*-*) + os=-elf + ;; + or32-*) + os=-coff + ;; + *-tti) # must be before sparc entry or we get the wrong os. + os=-sysv3 + ;; + sparc-* | *-sun) + os=-sunos4.1.1 + ;; + *-be) + os=-beos + ;; + *-haiku) + os=-haiku + ;; + *-ibm) + os=-aix + ;; + *-knuth) + os=-mmixware + ;; + *-wec) + os=-proelf + ;; + *-winbond) + os=-proelf + ;; + *-oki) + os=-proelf + ;; + *-hp) + os=-hpux + ;; + *-hitachi) + os=-hiux + ;; + i860-* | *-att | *-ncr | *-altos | *-motorola | *-convergent) + os=-sysv + ;; + *-cbm) + os=-amigaos + ;; + *-dg) + os=-dgux + ;; + *-dolphin) + os=-sysv3 + ;; + m68k-ccur) + os=-rtu + ;; + m88k-omron*) + os=-luna + ;; + *-next ) + os=-nextstep + ;; + *-sequent) + os=-ptx + ;; + *-crds) + os=-unos + ;; + *-ns) + os=-genix + ;; + i370-*) + os=-mvs + ;; + *-next) + os=-nextstep3 + ;; + *-gould) + os=-sysv + ;; + *-highlevel) + os=-bsd + ;; + *-encore) + os=-bsd + ;; + *-sgi) + os=-irix + ;; + *-siemens) + os=-sysv4 + ;; + *-masscomp) + os=-rtu + ;; + f30[01]-fujitsu | f700-fujitsu) + os=-uxpv + ;; + *-rom68k) + os=-coff + ;; + *-*bug) + os=-coff + ;; + *-apple) + os=-macos + ;; + *-atari*) + os=-mint + ;; + *) + os=-none + ;; +esac +fi + +# Here we handle the case where we know the os, and the CPU type, but not the +# manufacturer. We pick the logical manufacturer. +vendor=unknown +case $basic_machine in + *-unknown) + case $os in + -riscix*) + vendor=acorn + ;; + -sunos*) + vendor=sun + ;; + -aix*) + vendor=ibm + ;; + -beos*) + vendor=be + ;; + -hpux*) + vendor=hp + ;; + -mpeix*) + vendor=hp + ;; + -hiux*) + vendor=hitachi + ;; + -unos*) + vendor=crds + ;; + -dgux*) + vendor=dg + ;; + -luna*) + vendor=omron + ;; + -genix*) + vendor=ns + ;; + -mvs* | -opened*) + vendor=ibm + ;; + -os400*) + vendor=ibm + ;; + -ptx*) + vendor=sequent + ;; + -tpf*) + vendor=ibm + ;; + -vxsim* | -vxworks* | -windiss*) + vendor=wrs + ;; + -aux*) + vendor=apple + ;; + -hms*) + vendor=hitachi + ;; + -mpw* | -macos*) + vendor=apple + ;; + -*mint | -mint[0-9]* | -*MiNT | -MiNT[0-9]*) + vendor=atari + ;; + -vos*) + vendor=stratus + ;; + esac + basic_machine=`echo $basic_machine | sed "s/unknown/$vendor/"` + ;; +esac + +echo $basic_machine$os +exit + +# Local variables: +# eval: (add-hook 'write-file-hooks 'time-stamp) +# time-stamp-start: "timestamp='" +# time-stamp-format: "%:y-%02m-%02d" +# time-stamp-end: "'" +# End: diff --git a/libs/libsndfile/configure b/libs/libsndfile/configure new file mode 100755 index 0000000000..8aaca4e783 --- /dev/null +++ b/libs/libsndfile/configure @@ -0,0 +1,13925 @@ +#! /bin/sh +# Guess values for system-dependent variables and create Makefiles. +# Generated by GNU Autoconf 2.59 for libsndfile ardour-special. +# +# Report bugs to . +# +# Copyright (C) 2003 Free Software Foundation, Inc. +# This configure script is free software; the Free Software Foundation +# gives unlimited permission to copy, distribute and modify it. +## --------------------- ## +## M4sh Initialization. ## +## --------------------- ## + +# Be Bourne compatible +if test -n "${ZSH_VERSION+set}" && (emulate sh) >/dev/null 2>&1; then + emulate sh + NULLCMD=: + # Zsh 3.x and 4.x performs word splitting on ${1+"$@"}, which + # is contrary to our usage. Disable this feature. + alias -g '${1+"$@"}'='"$@"' +elif test -n "${BASH_VERSION+set}" && (set -o posix) >/dev/null 2>&1; then + set -o posix +fi +DUALCASE=1; export DUALCASE # for MKS sh + +# Support unset when possible. +if ( (MAIL=60; unset MAIL) || exit) >/dev/null 2>&1; then + as_unset=unset +else + as_unset=false +fi + + +# Work around bugs in pre-3.0 UWIN ksh. +$as_unset ENV MAIL MAILPATH +PS1='$ ' +PS2='> ' +PS4='+ ' + +# NLS nuisances. +for as_var in \ + LANG LANGUAGE LC_ADDRESS LC_ALL LC_COLLATE LC_CTYPE LC_IDENTIFICATION \ + LC_MEASUREMENT LC_MESSAGES LC_MONETARY LC_NAME LC_NUMERIC LC_PAPER \ + LC_TELEPHONE LC_TIME +do + if (set +x; test -z "`(eval $as_var=C; export $as_var) 2>&1`"); then + eval $as_var=C; export $as_var + else + $as_unset $as_var + fi +done + +# Required to use basename. +if expr a : '\(a\)' >/dev/null 2>&1; then + as_expr=expr +else + as_expr=false +fi + +if (basename /) >/dev/null 2>&1 && test "X`basename / 2>&1`" = "X/"; then + as_basename=basename +else + as_basename=false +fi + + +# Name of the executable. +as_me=`$as_basename "$0" || +$as_expr X/"$0" : '.*/\([^/][^/]*\)/*$' \| \ + X"$0" : 'X\(//\)$' \| \ + X"$0" : 'X\(/\)$' \| \ + . : '\(.\)' 2>/dev/null || +echo X/"$0" | + sed '/^.*\/\([^/][^/]*\)\/*$/{ s//\1/; q; } + /^X\/\(\/\/\)$/{ s//\1/; q; } + /^X\/\(\/\).*/{ s//\1/; q; } + s/.*/./; q'` + + +# PATH needs CR, and LINENO needs CR and PATH. +# Avoid depending upon Character Ranges. +as_cr_letters='abcdefghijklmnopqrstuvwxyz' +as_cr_LETTERS='ABCDEFGHIJKLMNOPQRSTUVWXYZ' +as_cr_Letters=$as_cr_letters$as_cr_LETTERS +as_cr_digits='0123456789' +as_cr_alnum=$as_cr_Letters$as_cr_digits + +# The user is always right. +if test "${PATH_SEPARATOR+set}" != set; then + echo "#! /bin/sh" >conf$$.sh + echo "exit 0" >>conf$$.sh + chmod +x conf$$.sh + if (PATH="/nonexistent;."; conf$$.sh) >/dev/null 2>&1; then + PATH_SEPARATOR=';' + else + PATH_SEPARATOR=: + fi + rm -f conf$$.sh +fi + + + as_lineno_1=$LINENO + as_lineno_2=$LINENO + as_lineno_3=`(expr $as_lineno_1 + 1) 2>/dev/null` + test "x$as_lineno_1" != "x$as_lineno_2" && + test "x$as_lineno_3" = "x$as_lineno_2" || { + # Find who we are. Look in the path if we contain no path at all + # relative or not. + case $0 in + *[\\/]* ) as_myself=$0 ;; + *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + test -r "$as_dir/$0" && as_myself=$as_dir/$0 && break +done + + ;; + esac + # We did not find ourselves, most probably we were run as `sh COMMAND' + # in which case we are not to be found in the path. + if test "x$as_myself" = x; then + as_myself=$0 + fi + if test ! -f "$as_myself"; then + { echo "$as_me: error: cannot find myself; rerun with an absolute path" >&2 + { (exit 1); exit 1; }; } + fi + case $CONFIG_SHELL in + '') + as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in /bin$PATH_SEPARATOR/usr/bin$PATH_SEPARATOR$PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + for as_base in sh bash ksh sh5; do + case $as_dir in + /*) + if ("$as_dir/$as_base" -c ' + as_lineno_1=$LINENO + as_lineno_2=$LINENO + as_lineno_3=`(expr $as_lineno_1 + 1) 2>/dev/null` + test "x$as_lineno_1" != "x$as_lineno_2" && + test "x$as_lineno_3" = "x$as_lineno_2" ') 2>/dev/null; then + $as_unset BASH_ENV || test "${BASH_ENV+set}" != set || { BASH_ENV=; export BASH_ENV; } + $as_unset ENV || test "${ENV+set}" != set || { ENV=; export ENV; } + CONFIG_SHELL=$as_dir/$as_base + export CONFIG_SHELL + exec "$CONFIG_SHELL" "$0" ${1+"$@"} + fi;; + esac + done +done +;; + esac + + # Create $as_me.lineno as a copy of $as_myself, but with $LINENO + # uniformly replaced by the line number. The first 'sed' inserts a + # line-number line before each line; the second 'sed' does the real + # work. The second script uses 'N' to pair each line-number line + # with the numbered line, and appends trailing '-' during + # substitution so that $LINENO is not a special case at line end. + # (Raja R Harinath suggested sed '=', and Paul Eggert wrote the + # second 'sed' script. Blame Lee E. McMahon for sed's syntax. :-) + sed '=' <$as_myself | + sed ' + N + s,$,-, + : loop + s,^\(['$as_cr_digits']*\)\(.*\)[$]LINENO\([^'$as_cr_alnum'_]\),\1\2\1\3, + t loop + s,-$,, + s,^['$as_cr_digits']*\n,, + ' >$as_me.lineno && + chmod +x $as_me.lineno || + { echo "$as_me: error: cannot create $as_me.lineno; rerun with a POSIX shell" >&2 + { (exit 1); exit 1; }; } + + # Don't try to exec as it changes $[0], causing all sort of problems + # (the dirname of $[0] is not the place where we might find the + # original and so on. Autoconf is especially sensible to this). + . ./$as_me.lineno + # Exit status is that of the last command. + exit +} + + +case `echo "testing\c"; echo 1,2,3`,`echo -n testing; echo 1,2,3` in + *c*,-n*) ECHO_N= ECHO_C=' +' ECHO_T=' ' ;; + *c*,* ) ECHO_N=-n ECHO_C= ECHO_T= ;; + *) ECHO_N= ECHO_C='\c' ECHO_T= ;; +esac + +if expr a : '\(a\)' >/dev/null 2>&1; then + as_expr=expr +else + as_expr=false +fi + +rm -f conf$$ conf$$.exe conf$$.file +echo >conf$$.file +if ln -s conf$$.file conf$$ 2>/dev/null; then + # We could just check for DJGPP; but this test a) works b) is more generic + # and c) will remain valid once DJGPP supports symlinks (DJGPP 2.04). + if test -f conf$$.exe; then + # Don't use ln at all; we don't have any links + as_ln_s='cp -p' + else + as_ln_s='ln -s' + fi +elif ln conf$$.file conf$$ 2>/dev/null; then + as_ln_s=ln +else + as_ln_s='cp -p' +fi +rm -f conf$$ conf$$.exe conf$$.file + +if mkdir -p . 2>/dev/null; then + as_mkdir_p=: +else + test -d ./-p && rmdir ./-p + as_mkdir_p=false +fi + +as_executable_p="test -f" + +# Sed expression to map a string onto a valid CPP name. +as_tr_cpp="eval sed 'y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g'" + +# Sed expression to map a string onto a valid variable name. +as_tr_sh="eval sed 'y%*+%pp%;s%[^_$as_cr_alnum]%_%g'" + + +# IFS +# We need space, tab and new line, in precisely that order. +as_nl=' +' +IFS=" $as_nl" + +# CDPATH. +$as_unset CDPATH + + +# Name of the host. +# hostname on some systems (SVR3.2, Linux) returns a bogus exit status, +# so uname gets run too. +ac_hostname=`(hostname || uname -n) 2>/dev/null | sed 1q` + +exec 6>&1 + +# +# Initializations. +# +ac_default_prefix=/usr/local +ac_config_libobj_dir=. +cross_compiling=no +subdirs= +MFLAGS= +MAKEFLAGS= +SHELL=${CONFIG_SHELL-/bin/sh} + +# Maximum number of lines to put in a shell here document. +# This variable seems obsolete. It should probably be removed, and +# only ac_max_sed_lines should be used. +: ${ac_max_here_lines=38} + +# Identity of this package. +PACKAGE_NAME='libsndfile' +PACKAGE_TARNAME='libsndfile' +PACKAGE_VERSION='ardour-special' +PACKAGE_STRING='libsndfile ardour-special' +PACKAGE_BUGREPORT='ardour@ardour.org' + +ac_unique_file="src/sndfile.c" +# Factoring default headers for most tests. +ac_includes_default="\ +#include +#if HAVE_SYS_TYPES_H +# include +#endif +#if HAVE_SYS_STAT_H +# include +#endif +#if STDC_HEADERS +# include +# include +#else +# if HAVE_STDLIB_H +# include +# endif +#endif +#if HAVE_STRING_H +# if !STDC_HEADERS && HAVE_MEMORY_H +# include +# endif +# include +#endif +#if HAVE_STRINGS_H +# include +#endif +#if HAVE_INTTYPES_H +# include +#else +# if HAVE_STDINT_H +# include +# endif +#endif +#if HAVE_UNISTD_H +# include +#endif" + +ac_subst_vars='SHELL PATH_SEPARATOR PACKAGE_NAME PACKAGE_TARNAME PACKAGE_VERSION PACKAGE_STRING PACKAGE_BUGREPORT exec_prefix prefix program_transform_name bindir sbindir libexecdir datadir sysconfdir sharedstatedir localstatedir libdir includedir oldincludedir infodir mandir build_alias host_alias target_alias DEFS ECHO_C ECHO_N ECHO_T LIBS build build_cpu build_vendor build_os host host_cpu host_vendor host_os target target_cpu target_vendor target_os CC CFLAGS LDFLAGS CPPFLAGS ac_ct_CC EXEEXT OBJEXT autogen INSTALL_PROGRAM INSTALL_SCRIPT INSTALL_DATA LN_S CPP EGREP GETCONF ac_ct_GETCONF TYPEOF_SF_COUNT_T SIZEOF_SF_COUNT_T SF_COUNT_MAX PKG_CONFIG SQLITE3_CFLAGS SQLITE3_LIBS htmldocdir HTML_BGCOLOUR HTML_FGCOLOUR SHLIB_VERSION_ARG SHARED_VERSION_INFO OS_SPECIFIC_CFLAGS OS_SPECIFIC_LINKS ALSA_LIBS FLAC_LIBS ENABLE_EXPERIMENTAL_CODE COMPILER_IS_GCC GCC_MAJOR_VERSION LIBTOOL_DEPS LIBOBJS LTLIBOBJS' +ac_subst_files='' + +# Initialize some variables set by options. +ac_init_help= +ac_init_version=false +# The variables have the same names as the options, with +# dashes changed to underlines. +cache_file=/dev/null +exec_prefix=NONE +no_create= +no_recursion= +prefix=NONE +program_prefix=NONE +program_suffix=NONE +program_transform_name=s,x,x, +silent= +site= +srcdir= +verbose= +x_includes=NONE +x_libraries=NONE + +# Installation directory options. +# These are left unexpanded so users can "make install exec_prefix=/foo" +# and all the variables that are supposed to be based on exec_prefix +# by default will actually change. +# Use braces instead of parens because sh, perl, etc. also accept them. +bindir='${exec_prefix}/bin' +sbindir='${exec_prefix}/sbin' +libexecdir='${exec_prefix}/libexec' +datadir='${prefix}/share' +sysconfdir='${prefix}/etc' +sharedstatedir='${prefix}/com' +localstatedir='${prefix}/var' +libdir='${exec_prefix}/lib' +includedir='${prefix}/include' +oldincludedir='/usr/include' +infodir='${prefix}/info' +mandir='${prefix}/man' + +ac_prev= +for ac_option +do + # If the previous option needs an argument, assign it. + if test -n "$ac_prev"; then + eval "$ac_prev=\$ac_option" + ac_prev= + continue + fi + + ac_optarg=`expr "x$ac_option" : 'x[^=]*=\(.*\)'` + + # Accept the important Cygnus configure options, so we can diagnose typos. + + case $ac_option in + + -bindir | --bindir | --bindi | --bind | --bin | --bi) + ac_prev=bindir ;; + -bindir=* | --bindir=* | --bindi=* | --bind=* | --bin=* | --bi=*) + bindir=$ac_optarg ;; + + -build | --build | --buil | --bui | --bu) + ac_prev=build_alias ;; + -build=* | --build=* | --buil=* | --bui=* | --bu=*) + build_alias=$ac_optarg ;; + + -cache-file | --cache-file | --cache-fil | --cache-fi \ + | --cache-f | --cache- | --cache | --cach | --cac | --ca | --c) + ac_prev=cache_file ;; + -cache-file=* | --cache-file=* | --cache-fil=* | --cache-fi=* \ + | --cache-f=* | --cache-=* | --cache=* | --cach=* | --cac=* | --ca=* | --c=*) + cache_file=$ac_optarg ;; + + --config-cache | -C) + cache_file=config.cache ;; + + -datadir | --datadir | --datadi | --datad | --data | --dat | --da) + ac_prev=datadir ;; + -datadir=* | --datadir=* | --datadi=* | --datad=* | --data=* | --dat=* \ + | --da=*) + datadir=$ac_optarg ;; + + -disable-* | --disable-*) + ac_feature=`expr "x$ac_option" : 'x-*disable-\(.*\)'` + # Reject names that are not valid shell variable names. + expr "x$ac_feature" : ".*[^-_$as_cr_alnum]" >/dev/null && + { echo "$as_me: error: invalid feature name: $ac_feature" >&2 + { (exit 1); exit 1; }; } + ac_feature=`echo $ac_feature | sed 's/-/_/g'` + eval "enable_$ac_feature=no" ;; + + -enable-* | --enable-*) + ac_feature=`expr "x$ac_option" : 'x-*enable-\([^=]*\)'` + # Reject names that are not valid shell variable names. + expr "x$ac_feature" : ".*[^-_$as_cr_alnum]" >/dev/null && + { echo "$as_me: error: invalid feature name: $ac_feature" >&2 + { (exit 1); exit 1; }; } + ac_feature=`echo $ac_feature | sed 's/-/_/g'` + case $ac_option in + *=*) ac_optarg=`echo "$ac_optarg" | sed "s/'/'\\\\\\\\''/g"`;; + *) ac_optarg=yes ;; + esac + eval "enable_$ac_feature='$ac_optarg'" ;; + + -exec-prefix | --exec_prefix | --exec-prefix | --exec-prefi \ + | --exec-pref | --exec-pre | --exec-pr | --exec-p | --exec- \ + | --exec | --exe | --ex) + ac_prev=exec_prefix ;; + -exec-prefix=* | --exec_prefix=* | --exec-prefix=* | --exec-prefi=* \ + | --exec-pref=* | --exec-pre=* | --exec-pr=* | --exec-p=* | --exec-=* \ + | --exec=* | --exe=* | --ex=*) + exec_prefix=$ac_optarg ;; + + -gas | --gas | --ga | --g) + # Obsolete; use --with-gas. + with_gas=yes ;; + + -help | --help | --hel | --he | -h) + ac_init_help=long ;; + -help=r* | --help=r* | --hel=r* | --he=r* | -hr*) + ac_init_help=recursive ;; + -help=s* | --help=s* | --hel=s* | --he=s* | -hs*) + ac_init_help=short ;; + + -host | --host | --hos | --ho) + ac_prev=host_alias ;; + -host=* | --host=* | --hos=* | --ho=*) + host_alias=$ac_optarg ;; + + -includedir | --includedir | --includedi | --included | --include \ + | --includ | --inclu | --incl | --inc) + ac_prev=includedir ;; + -includedir=* | --includedir=* | --includedi=* | --included=* | --include=* \ + | --includ=* | --inclu=* | --incl=* | --inc=*) + includedir=$ac_optarg ;; + + -infodir | --infodir | --infodi | --infod | --info | --inf) + ac_prev=infodir ;; + -infodir=* | --infodir=* | --infodi=* | --infod=* | --info=* | --inf=*) + infodir=$ac_optarg ;; + + -libdir | --libdir | --libdi | --libd) + ac_prev=libdir ;; + -libdir=* | --libdir=* | --libdi=* | --libd=*) + libdir=$ac_optarg ;; + + -libexecdir | --libexecdir | --libexecdi | --libexecd | --libexec \ + | --libexe | --libex | --libe) + ac_prev=libexecdir ;; + -libexecdir=* | --libexecdir=* | --libexecdi=* | --libexecd=* | --libexec=* \ + | --libexe=* | --libex=* | --libe=*) + libexecdir=$ac_optarg ;; + + -localstatedir | --localstatedir | --localstatedi | --localstated \ + | --localstate | --localstat | --localsta | --localst \ + | --locals | --local | --loca | --loc | --lo) + ac_prev=localstatedir ;; + -localstatedir=* | --localstatedir=* | --localstatedi=* | --localstated=* \ + | --localstate=* | --localstat=* | --localsta=* | --localst=* \ + | --locals=* | --local=* | --loca=* | --loc=* | --lo=*) + localstatedir=$ac_optarg ;; + + -mandir | --mandir | --mandi | --mand | --man | --ma | --m) + ac_prev=mandir ;; + -mandir=* | --mandir=* | --mandi=* | --mand=* | --man=* | --ma=* | --m=*) + mandir=$ac_optarg ;; + + -nfp | --nfp | --nf) + # Obsolete; use --without-fp. + with_fp=no ;; + + -no-create | --no-create | --no-creat | --no-crea | --no-cre \ + | --no-cr | --no-c | -n) + no_create=yes ;; + + -no-recursion | --no-recursion | --no-recursio | --no-recursi \ + | --no-recurs | --no-recur | --no-recu | --no-rec | --no-re | --no-r) + no_recursion=yes ;; + + -oldincludedir | --oldincludedir | --oldincludedi | --oldincluded \ + | --oldinclude | --oldinclud | --oldinclu | --oldincl | --oldinc \ + | --oldin | --oldi | --old | --ol | --o) + ac_prev=oldincludedir ;; + -oldincludedir=* | --oldincludedir=* | --oldincludedi=* | --oldincluded=* \ + | --oldinclude=* | --oldinclud=* | --oldinclu=* | --oldincl=* | --oldinc=* \ + | --oldin=* | --oldi=* | --old=* | --ol=* | --o=*) + oldincludedir=$ac_optarg ;; + + -prefix | --prefix | --prefi | --pref | --pre | --pr | --p) + ac_prev=prefix ;; + -prefix=* | --prefix=* | --prefi=* | --pref=* | --pre=* | --pr=* | --p=*) + prefix=$ac_optarg ;; + + -program-prefix | --program-prefix | --program-prefi | --program-pref \ + | --program-pre | --program-pr | --program-p) + ac_prev=program_prefix ;; + -program-prefix=* | --program-prefix=* | --program-prefi=* \ + | --program-pref=* | --program-pre=* | --program-pr=* | --program-p=*) + program_prefix=$ac_optarg ;; + + -program-suffix | --program-suffix | --program-suffi | --program-suff \ + | --program-suf | --program-su | --program-s) + ac_prev=program_suffix ;; + -program-suffix=* | --program-suffix=* | --program-suffi=* \ + | --program-suff=* | --program-suf=* | --program-su=* | --program-s=*) + program_suffix=$ac_optarg ;; + + -program-transform-name | --program-transform-name \ + | --program-transform-nam | --program-transform-na \ + | --program-transform-n | --program-transform- \ + | --program-transform | --program-transfor \ + | --program-transfo | --program-transf \ + | --program-trans | --program-tran \ + | --progr-tra | --program-tr | --program-t) + ac_prev=program_transform_name ;; + -program-transform-name=* | --program-transform-name=* \ + | --program-transform-nam=* | --program-transform-na=* \ + | --program-transform-n=* | --program-transform-=* \ + | --program-transform=* | --program-transfor=* \ + | --program-transfo=* | --program-transf=* \ + | --program-trans=* | --program-tran=* \ + | --progr-tra=* | --program-tr=* | --program-t=*) + program_transform_name=$ac_optarg ;; + + -q | -quiet | --quiet | --quie | --qui | --qu | --q \ + | -silent | --silent | --silen | --sile | --sil) + silent=yes ;; + + -sbindir | --sbindir | --sbindi | --sbind | --sbin | --sbi | --sb) + ac_prev=sbindir ;; + -sbindir=* | --sbindir=* | --sbindi=* | --sbind=* | --sbin=* \ + | --sbi=* | --sb=*) + sbindir=$ac_optarg ;; + + -sharedstatedir | --sharedstatedir | --sharedstatedi \ + | --sharedstated | --sharedstate | --sharedstat | --sharedsta \ + | --sharedst | --shareds | --shared | --share | --shar \ + | --sha | --sh) + ac_prev=sharedstatedir ;; + -sharedstatedir=* | --sharedstatedir=* | --sharedstatedi=* \ + | --sharedstated=* | --sharedstate=* | --sharedstat=* | --sharedsta=* \ + | --sharedst=* | --shareds=* | --shared=* | --share=* | --shar=* \ + | --sha=* | --sh=*) + sharedstatedir=$ac_optarg ;; + + -site | --site | --sit) + ac_prev=site ;; + -site=* | --site=* | --sit=*) + site=$ac_optarg ;; + + -srcdir | --srcdir | --srcdi | --srcd | --src | --sr) + ac_prev=srcdir ;; + -srcdir=* | --srcdir=* | --srcdi=* | --srcd=* | --src=* | --sr=*) + srcdir=$ac_optarg ;; + + -sysconfdir | --sysconfdir | --sysconfdi | --sysconfd | --sysconf \ + | --syscon | --sysco | --sysc | --sys | --sy) + ac_prev=sysconfdir ;; + -sysconfdir=* | --sysconfdir=* | --sysconfdi=* | --sysconfd=* | --sysconf=* \ + | --syscon=* | --sysco=* | --sysc=* | --sys=* | --sy=*) + sysconfdir=$ac_optarg ;; + + -target | --target | --targe | --targ | --tar | --ta | --t) + ac_prev=target_alias ;; + -target=* | --target=* | --targe=* | --targ=* | --tar=* | --ta=* | --t=*) + target_alias=$ac_optarg ;; + + -v | -verbose | --verbose | --verbos | --verbo | --verb) + verbose=yes ;; + + -version | --version | --versio | --versi | --vers | -V) + ac_init_version=: ;; + + -with-* | --with-*) + ac_package=`expr "x$ac_option" : 'x-*with-\([^=]*\)'` + # Reject names that are not valid shell variable names. + expr "x$ac_package" : ".*[^-_$as_cr_alnum]" >/dev/null && + { echo "$as_me: error: invalid package name: $ac_package" >&2 + { (exit 1); exit 1; }; } + ac_package=`echo $ac_package| sed 's/-/_/g'` + case $ac_option in + *=*) ac_optarg=`echo "$ac_optarg" | sed "s/'/'\\\\\\\\''/g"`;; + *) ac_optarg=yes ;; + esac + eval "with_$ac_package='$ac_optarg'" ;; + + -without-* | --without-*) + ac_package=`expr "x$ac_option" : 'x-*without-\(.*\)'` + # Reject names that are not valid shell variable names. + expr "x$ac_package" : ".*[^-_$as_cr_alnum]" >/dev/null && + { echo "$as_me: error: invalid package name: $ac_package" >&2 + { (exit 1); exit 1; }; } + ac_package=`echo $ac_package | sed 's/-/_/g'` + eval "with_$ac_package=no" ;; + + --x) + # Obsolete; use --with-x. + with_x=yes ;; + + -x-includes | --x-includes | --x-include | --x-includ | --x-inclu \ + | --x-incl | --x-inc | --x-in | --x-i) + ac_prev=x_includes ;; + -x-includes=* | --x-includes=* | --x-include=* | --x-includ=* | --x-inclu=* \ + | --x-incl=* | --x-inc=* | --x-in=* | --x-i=*) + x_includes=$ac_optarg ;; + + -x-libraries | --x-libraries | --x-librarie | --x-librari \ + | --x-librar | --x-libra | --x-libr | --x-lib | --x-li | --x-l) + ac_prev=x_libraries ;; + -x-libraries=* | --x-libraries=* | --x-librarie=* | --x-librari=* \ + | --x-librar=* | --x-libra=* | --x-libr=* | --x-lib=* | --x-li=* | --x-l=*) + x_libraries=$ac_optarg ;; + + -*) { echo "$as_me: error: unrecognized option: $ac_option +Try \`$0 --help' for more information." >&2 + { (exit 1); exit 1; }; } + ;; + + *=*) + ac_envvar=`expr "x$ac_option" : 'x\([^=]*\)='` + # Reject names that are not valid shell variable names. + expr "x$ac_envvar" : ".*[^_$as_cr_alnum]" >/dev/null && + { echo "$as_me: error: invalid variable name: $ac_envvar" >&2 + { (exit 1); exit 1; }; } + ac_optarg=`echo "$ac_optarg" | sed "s/'/'\\\\\\\\''/g"` + eval "$ac_envvar='$ac_optarg'" + export $ac_envvar ;; + + *) + # FIXME: should be removed in autoconf 3.0. + echo "$as_me: WARNING: you should use --build, --host, --target" >&2 + expr "x$ac_option" : ".*[^-._$as_cr_alnum]" >/dev/null && + echo "$as_me: WARNING: invalid host type: $ac_option" >&2 + : ${build_alias=$ac_option} ${host_alias=$ac_option} ${target_alias=$ac_option} + ;; + + esac +done + +if test -n "$ac_prev"; then + ac_option=--`echo $ac_prev | sed 's/_/-/g'` + { echo "$as_me: error: missing argument to $ac_option" >&2 + { (exit 1); exit 1; }; } +fi + +# Be sure to have absolute paths. +for ac_var in exec_prefix prefix +do + eval ac_val=$`echo $ac_var` + case $ac_val in + [\\/$]* | ?:[\\/]* | NONE | '' ) ;; + *) { echo "$as_me: error: expected an absolute directory name for --$ac_var: $ac_val" >&2 + { (exit 1); exit 1; }; };; + esac +done + +# Be sure to have absolute paths. +for ac_var in bindir sbindir libexecdir datadir sysconfdir sharedstatedir \ + localstatedir libdir includedir oldincludedir infodir mandir +do + eval ac_val=$`echo $ac_var` + case $ac_val in + [\\/$]* | ?:[\\/]* ) ;; + *) { echo "$as_me: error: expected an absolute directory name for --$ac_var: $ac_val" >&2 + { (exit 1); exit 1; }; };; + esac +done + +# There might be people who depend on the old broken behavior: `$host' +# used to hold the argument of --host etc. +# FIXME: To remove some day. +build=$build_alias +host=$host_alias +target=$target_alias + +# FIXME: To remove some day. +if test "x$host_alias" != x; then + if test "x$build_alias" = x; then + cross_compiling=maybe + echo "$as_me: WARNING: If you wanted to set the --build type, don't use --host. + If a cross compiler is detected then cross compile mode will be used." >&2 + elif test "x$build_alias" != "x$host_alias"; then + cross_compiling=yes + fi +fi + +ac_tool_prefix= +test -n "$host_alias" && ac_tool_prefix=$host_alias- + +test "$silent" = yes && exec 6>/dev/null + + +# Find the source files, if location was not specified. +if test -z "$srcdir"; then + ac_srcdir_defaulted=yes + # Try the directory containing this script, then its parent. + ac_confdir=`(dirname "$0") 2>/dev/null || +$as_expr X"$0" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ + X"$0" : 'X\(//\)[^/]' \| \ + X"$0" : 'X\(//\)$' \| \ + X"$0" : 'X\(/\)' \| \ + . : '\(.\)' 2>/dev/null || +echo X"$0" | + sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ s//\1/; q; } + /^X\(\/\/\)[^/].*/{ s//\1/; q; } + /^X\(\/\/\)$/{ s//\1/; q; } + /^X\(\/\).*/{ s//\1/; q; } + s/.*/./; q'` + srcdir=$ac_confdir + if test ! -r $srcdir/$ac_unique_file; then + srcdir=.. + fi +else + ac_srcdir_defaulted=no +fi +if test ! -r $srcdir/$ac_unique_file; then + if test "$ac_srcdir_defaulted" = yes; then + { echo "$as_me: error: cannot find sources ($ac_unique_file) in $ac_confdir or .." >&2 + { (exit 1); exit 1; }; } + else + { echo "$as_me: error: cannot find sources ($ac_unique_file) in $srcdir" >&2 + { (exit 1); exit 1; }; } + fi +fi +(cd $srcdir && test -r ./$ac_unique_file) 2>/dev/null || + { echo "$as_me: error: sources are in $srcdir, but \`cd $srcdir' does not work" >&2 + { (exit 1); exit 1; }; } +srcdir=`echo "$srcdir" | sed 's%\([^\\/]\)[\\/]*$%\1%'` +ac_env_build_alias_set=${build_alias+set} +ac_env_build_alias_value=$build_alias +ac_cv_env_build_alias_set=${build_alias+set} +ac_cv_env_build_alias_value=$build_alias +ac_env_host_alias_set=${host_alias+set} +ac_env_host_alias_value=$host_alias +ac_cv_env_host_alias_set=${host_alias+set} +ac_cv_env_host_alias_value=$host_alias +ac_env_target_alias_set=${target_alias+set} +ac_env_target_alias_value=$target_alias +ac_cv_env_target_alias_set=${target_alias+set} +ac_cv_env_target_alias_value=$target_alias +ac_env_CC_set=${CC+set} +ac_env_CC_value=$CC +ac_cv_env_CC_set=${CC+set} +ac_cv_env_CC_value=$CC +ac_env_CFLAGS_set=${CFLAGS+set} +ac_env_CFLAGS_value=$CFLAGS +ac_cv_env_CFLAGS_set=${CFLAGS+set} +ac_cv_env_CFLAGS_value=$CFLAGS +ac_env_LDFLAGS_set=${LDFLAGS+set} +ac_env_LDFLAGS_value=$LDFLAGS +ac_cv_env_LDFLAGS_set=${LDFLAGS+set} +ac_cv_env_LDFLAGS_value=$LDFLAGS +ac_env_CPPFLAGS_set=${CPPFLAGS+set} +ac_env_CPPFLAGS_value=$CPPFLAGS +ac_cv_env_CPPFLAGS_set=${CPPFLAGS+set} +ac_cv_env_CPPFLAGS_value=$CPPFLAGS +ac_env_CPP_set=${CPP+set} +ac_env_CPP_value=$CPP +ac_cv_env_CPP_set=${CPP+set} +ac_cv_env_CPP_value=$CPP + +# +# Report the --help message. +# +if test "$ac_init_help" = "long"; then + # Omit some internal or obsolete options to make the list less imposing. + # This message is too long to be a string in the A/UX 3.1 sh. + cat <<_ACEOF +\`configure' configures libsndfile ardour-special to adapt to many kinds of systems. + +Usage: $0 [OPTION]... [VAR=VALUE]... + +To assign environment variables (e.g., CC, CFLAGS...), specify them as +VAR=VALUE. See below for descriptions of some of the useful variables. + +Defaults for the options are specified in brackets. + +Configuration: + -h, --help display this help and exit + --help=short display options specific to this package + --help=recursive display the short help of all the included packages + -V, --version display version information and exit + -q, --quiet, --silent do not print \`checking...' messages + --cache-file=FILE cache test results in FILE [disabled] + -C, --config-cache alias for \`--cache-file=config.cache' + -n, --no-create do not create output files + --srcdir=DIR find the sources in DIR [configure dir or \`..'] + +_ACEOF + + cat <<_ACEOF +Installation directories: + --prefix=PREFIX install architecture-independent files in PREFIX + [$ac_default_prefix] + --exec-prefix=EPREFIX install architecture-dependent files in EPREFIX + [PREFIX] + +By default, \`make install' will install all the files in +\`$ac_default_prefix/bin', \`$ac_default_prefix/lib' etc. You can specify +an installation prefix other than \`$ac_default_prefix' using \`--prefix', +for instance \`--prefix=\$HOME'. + +For better control, use the options below. + +Fine tuning of the installation directories: + --bindir=DIR user executables [EPREFIX/bin] + --sbindir=DIR system admin executables [EPREFIX/sbin] + --libexecdir=DIR program executables [EPREFIX/libexec] + --datadir=DIR read-only architecture-independent data [PREFIX/share] + --sysconfdir=DIR read-only single-machine data [PREFIX/etc] + --sharedstatedir=DIR modifiable architecture-independent data [PREFIX/com] + --localstatedir=DIR modifiable single-machine data [PREFIX/var] + --libdir=DIR object code libraries [EPREFIX/lib] + --includedir=DIR C header files [PREFIX/include] + --oldincludedir=DIR C header files for non-gcc [/usr/include] + --infodir=DIR info documentation [PREFIX/info] + --mandir=DIR man documentation [PREFIX/man] +_ACEOF + + cat <<\_ACEOF + +System types: + --build=BUILD configure for building on BUILD [guessed] + --host=HOST cross-compile to build programs to run on HOST [BUILD] + --target=TARGET configure for building compilers for TARGET [HOST] +_ACEOF +fi + +if test -n "$ac_init_help"; then + case $ac_init_help in + short | recursive ) echo "Configuration of libsndfile ardour-special:";; + esac + cat <<\_ACEOF + +Optional Features: + --disable-FEATURE do not include FEATURE (same as --enable-FEATURE=no) + --enable-FEATURE[=ARG] include FEATURE [ARG=yes] + --enable-experimental enable experimental code + --enable-gcc-werror enable -Werror in all Makefiles + --disable-gcc-pipe disable gcc -pipe option + --disable-gcc-opt disable gcc optimisations + --disable-cpu-clip disable tricky cpu specific clipper + --enable-bow-docs enable black-on-white html docs + --disable-sqlite disable use of sqlite + --disable-flac disable use of FLAC + --disable-alsa disable use of ALSA + --disable-largefile omit support for large files + +Some influential environment variables: + CC C compiler command + CFLAGS C compiler flags + LDFLAGS linker flags, e.g. -L if you have libraries in a + nonstandard directory + CPPFLAGS C/C++ preprocessor flags, e.g. -I if you have + headers in a nonstandard directory + CPP C preprocessor + +Use these variables to override the choices made by `configure' or to help +it to find libraries and programs with nonstandard names/locations. + +Report bugs to . +_ACEOF +fi + +if test "$ac_init_help" = "recursive"; then + # If there are subdirs, report their specific --help. + ac_popdir=`pwd` + for ac_dir in : $ac_subdirs_all; do test "x$ac_dir" = x: && continue + test -d $ac_dir || continue + ac_builddir=. + +if test "$ac_dir" != .; then + ac_dir_suffix=/`echo "$ac_dir" | sed 's,^\.[\\/],,'` + # A "../" for each directory in $ac_dir_suffix. + ac_top_builddir=`echo "$ac_dir_suffix" | sed 's,/[^\\/]*,../,g'` +else + ac_dir_suffix= ac_top_builddir= +fi + +case $srcdir in + .) # No --srcdir option. We are building in place. + ac_srcdir=. + if test -z "$ac_top_builddir"; then + ac_top_srcdir=. + else + ac_top_srcdir=`echo $ac_top_builddir | sed 's,/$,,'` + fi ;; + [\\/]* | ?:[\\/]* ) # Absolute path. + ac_srcdir=$srcdir$ac_dir_suffix; + ac_top_srcdir=$srcdir ;; + *) # Relative path. + ac_srcdir=$ac_top_builddir$srcdir$ac_dir_suffix + ac_top_srcdir=$ac_top_builddir$srcdir ;; +esac + +# Do not use `cd foo && pwd` to compute absolute paths, because +# the directories may not exist. +case `pwd` in +.) ac_abs_builddir="$ac_dir";; +*) + case "$ac_dir" in + .) ac_abs_builddir=`pwd`;; + [\\/]* | ?:[\\/]* ) ac_abs_builddir="$ac_dir";; + *) ac_abs_builddir=`pwd`/"$ac_dir";; + esac;; +esac +case $ac_abs_builddir in +.) ac_abs_top_builddir=${ac_top_builddir}.;; +*) + case ${ac_top_builddir}. in + .) ac_abs_top_builddir=$ac_abs_builddir;; + [\\/]* | ?:[\\/]* ) ac_abs_top_builddir=${ac_top_builddir}.;; + *) ac_abs_top_builddir=$ac_abs_builddir/${ac_top_builddir}.;; + esac;; +esac +case $ac_abs_builddir in +.) ac_abs_srcdir=$ac_srcdir;; +*) + case $ac_srcdir in + .) ac_abs_srcdir=$ac_abs_builddir;; + [\\/]* | ?:[\\/]* ) ac_abs_srcdir=$ac_srcdir;; + *) ac_abs_srcdir=$ac_abs_builddir/$ac_srcdir;; + esac;; +esac +case $ac_abs_builddir in +.) ac_abs_top_srcdir=$ac_top_srcdir;; +*) + case $ac_top_srcdir in + .) ac_abs_top_srcdir=$ac_abs_builddir;; + [\\/]* | ?:[\\/]* ) ac_abs_top_srcdir=$ac_top_srcdir;; + *) ac_abs_top_srcdir=$ac_abs_builddir/$ac_top_srcdir;; + esac;; +esac + + cd $ac_dir + # Check for guested configure; otherwise get Cygnus style configure. + if test -f $ac_srcdir/configure.gnu; then + echo + $SHELL $ac_srcdir/configure.gnu --help=recursive + elif test -f $ac_srcdir/configure; then + echo + $SHELL $ac_srcdir/configure --help=recursive + elif test -f $ac_srcdir/configure.ac || + test -f $ac_srcdir/configure.in; then + echo + $ac_configure --help + else + echo "$as_me: WARNING: no configuration information is in $ac_dir" >&2 + fi + cd $ac_popdir + done +fi + +test -n "$ac_init_help" && exit 0 +if $ac_init_version; then + cat <<\_ACEOF +libsndfile configure ardour-special +generated by GNU Autoconf 2.59 + +Copyright (C) 2003 Free Software Foundation, Inc. +This configure script is free software; the Free Software Foundation +gives unlimited permission to copy, distribute and modify it. +_ACEOF + exit 0 +fi +exec 5>config.log +cat >&5 <<_ACEOF +This file contains any messages produced by compilers while +running configure, to aid debugging if configure makes a mistake. + +It was created by libsndfile $as_me ardour-special, which was +generated by GNU Autoconf 2.59. Invocation command line was + + $ $0 $@ + +_ACEOF +{ +cat <<_ASUNAME +## --------- ## +## Platform. ## +## --------- ## + +hostname = `(hostname || uname -n) 2>/dev/null | sed 1q` +uname -m = `(uname -m) 2>/dev/null || echo unknown` +uname -r = `(uname -r) 2>/dev/null || echo unknown` +uname -s = `(uname -s) 2>/dev/null || echo unknown` +uname -v = `(uname -v) 2>/dev/null || echo unknown` + +/usr/bin/uname -p = `(/usr/bin/uname -p) 2>/dev/null || echo unknown` +/bin/uname -X = `(/bin/uname -X) 2>/dev/null || echo unknown` + +/bin/arch = `(/bin/arch) 2>/dev/null || echo unknown` +/usr/bin/arch -k = `(/usr/bin/arch -k) 2>/dev/null || echo unknown` +/usr/convex/getsysinfo = `(/usr/convex/getsysinfo) 2>/dev/null || echo unknown` +hostinfo = `(hostinfo) 2>/dev/null || echo unknown` +/bin/machine = `(/bin/machine) 2>/dev/null || echo unknown` +/usr/bin/oslevel = `(/usr/bin/oslevel) 2>/dev/null || echo unknown` +/bin/universe = `(/bin/universe) 2>/dev/null || echo unknown` + +_ASUNAME + +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + echo "PATH: $as_dir" +done + +} >&5 + +cat >&5 <<_ACEOF + + +## ----------- ## +## Core tests. ## +## ----------- ## + +_ACEOF + + +# Keep a trace of the command line. +# Strip out --no-create and --no-recursion so they do not pile up. +# Strip out --silent because we don't want to record it for future runs. +# Also quote any args containing shell meta-characters. +# Make two passes to allow for proper duplicate-argument suppression. +ac_configure_args= +ac_configure_args0= +ac_configure_args1= +ac_sep= +ac_must_keep_next=false +for ac_pass in 1 2 +do + for ac_arg + do + case $ac_arg in + -no-create | --no-c* | -n | -no-recursion | --no-r*) continue ;; + -q | -quiet | --quiet | --quie | --qui | --qu | --q \ + | -silent | --silent | --silen | --sile | --sil) + continue ;; + *" "*|*" "*|*[\[\]\~\#\$\^\&\*\(\)\{\}\\\|\;\<\>\?\"\']*) + ac_arg=`echo "$ac_arg" | sed "s/'/'\\\\\\\\''/g"` ;; + esac + case $ac_pass in + 1) ac_configure_args0="$ac_configure_args0 '$ac_arg'" ;; + 2) + ac_configure_args1="$ac_configure_args1 '$ac_arg'" + if test $ac_must_keep_next = true; then + ac_must_keep_next=false # Got value, back to normal. + else + case $ac_arg in + *=* | --config-cache | -C | -disable-* | --disable-* \ + | -enable-* | --enable-* | -gas | --g* | -nfp | --nf* \ + | -q | -quiet | --q* | -silent | --sil* | -v | -verb* \ + | -with-* | --with-* | -without-* | --without-* | --x) + case "$ac_configure_args0 " in + "$ac_configure_args1"*" '$ac_arg' "* ) continue ;; + esac + ;; + -* ) ac_must_keep_next=true ;; + esac + fi + ac_configure_args="$ac_configure_args$ac_sep'$ac_arg'" + # Get rid of the leading space. + ac_sep=" " + ;; + esac + done +done +$as_unset ac_configure_args0 || test "${ac_configure_args0+set}" != set || { ac_configure_args0=; export ac_configure_args0; } +$as_unset ac_configure_args1 || test "${ac_configure_args1+set}" != set || { ac_configure_args1=; export ac_configure_args1; } + +# When interrupted or exit'd, cleanup temporary files, and complete +# config.log. We remove comments because anyway the quotes in there +# would cause problems or look ugly. +# WARNING: Be sure not to use single quotes in there, as some shells, +# such as our DU 5.0 friend, will then `close' the trap. +trap 'exit_status=$? + # Save into config.log some information that might help in debugging. + { + echo + + cat <<\_ASBOX +## ---------------- ## +## Cache variables. ## +## ---------------- ## +_ASBOX + echo + # The following way of writing the cache mishandles newlines in values, +{ + (set) 2>&1 | + case `(ac_space='"'"' '"'"'; set | grep ac_space) 2>&1` in + *ac_space=\ *) + sed -n \ + "s/'"'"'/'"'"'\\\\'"'"''"'"'/g; + s/^\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\)=\\(.*\\)/\\1='"'"'\\2'"'"'/p" + ;; + *) + sed -n \ + "s/^\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\)=\\(.*\\)/\\1=\\2/p" + ;; + esac; +} + echo + + cat <<\_ASBOX +## ----------------- ## +## Output variables. ## +## ----------------- ## +_ASBOX + echo + for ac_var in $ac_subst_vars + do + eval ac_val=$`echo $ac_var` + echo "$ac_var='"'"'$ac_val'"'"'" + done | sort + echo + + if test -n "$ac_subst_files"; then + cat <<\_ASBOX +## ------------- ## +## Output files. ## +## ------------- ## +_ASBOX + echo + for ac_var in $ac_subst_files + do + eval ac_val=$`echo $ac_var` + echo "$ac_var='"'"'$ac_val'"'"'" + done | sort + echo + fi + + if test -s confdefs.h; then + cat <<\_ASBOX +## ----------- ## +## confdefs.h. ## +## ----------- ## +_ASBOX + echo + sed "/^$/d" confdefs.h | sort + echo + fi + test "$ac_signal" != 0 && + echo "$as_me: caught signal $ac_signal" + echo "$as_me: exit $exit_status" + } >&5 + rm -f core *.core && + rm -rf conftest* confdefs* conf$$* $ac_clean_files && + exit $exit_status + ' 0 +for ac_signal in 1 2 13 15; do + trap 'ac_signal='$ac_signal'; { (exit 1); exit 1; }' $ac_signal +done +ac_signal=0 + +# confdefs.h avoids OS command line length limits that DEFS can exceed. +rm -rf conftest* confdefs.h +# AIX cpp loses on an empty file, so make sure it contains at least a newline. +echo >confdefs.h + +# Predefined preprocessor variables. + +cat >>confdefs.h <<_ACEOF +#define PACKAGE_NAME "$PACKAGE_NAME" +_ACEOF + + +cat >>confdefs.h <<_ACEOF +#define PACKAGE_TARNAME "$PACKAGE_TARNAME" +_ACEOF + + +cat >>confdefs.h <<_ACEOF +#define PACKAGE_VERSION "$PACKAGE_VERSION" +_ACEOF + + +cat >>confdefs.h <<_ACEOF +#define PACKAGE_STRING "$PACKAGE_STRING" +_ACEOF + + +cat >>confdefs.h <<_ACEOF +#define PACKAGE_BUGREPORT "$PACKAGE_BUGREPORT" +_ACEOF + + +# Let the site file select an alternate cache file if it wants to. +# Prefer explicitly selected file to automatically selected ones. +if test -z "$CONFIG_SITE"; then + if test "x$prefix" != xNONE; then + CONFIG_SITE="$prefix/share/config.site $prefix/etc/config.site" + else + CONFIG_SITE="$ac_default_prefix/share/config.site $ac_default_prefix/etc/config.site" + fi +fi +for ac_site_file in $CONFIG_SITE; do + if test -r "$ac_site_file"; then + { echo "$as_me:$LINENO: loading site script $ac_site_file" >&5 +echo "$as_me: loading site script $ac_site_file" >&6;} + sed 's/^/| /' "$ac_site_file" >&5 + . "$ac_site_file" + fi +done + +if test -r "$cache_file"; then + # Some versions of bash will fail to source /dev/null (special + # files actually), so we avoid doing that. + if test -f "$cache_file"; then + { echo "$as_me:$LINENO: loading cache $cache_file" >&5 +echo "$as_me: loading cache $cache_file" >&6;} + case $cache_file in + [\\/]* | ?:[\\/]* ) . $cache_file;; + *) . ./$cache_file;; + esac + fi +else + { echo "$as_me:$LINENO: creating cache $cache_file" >&5 +echo "$as_me: creating cache $cache_file" >&6;} + >$cache_file +fi + +# Check that the precious variables saved in the cache have kept the same +# value. +ac_cache_corrupted=false +for ac_var in `(set) 2>&1 | + sed -n 's/^ac_env_\([a-zA-Z_0-9]*\)_set=.*/\1/p'`; do + eval ac_old_set=\$ac_cv_env_${ac_var}_set + eval ac_new_set=\$ac_env_${ac_var}_set + eval ac_old_val="\$ac_cv_env_${ac_var}_value" + eval ac_new_val="\$ac_env_${ac_var}_value" + case $ac_old_set,$ac_new_set in + set,) + { echo "$as_me:$LINENO: error: \`$ac_var' was set to \`$ac_old_val' in the previous run" >&5 +echo "$as_me: error: \`$ac_var' was set to \`$ac_old_val' in the previous run" >&2;} + ac_cache_corrupted=: ;; + ,set) + { echo "$as_me:$LINENO: error: \`$ac_var' was not set in the previous run" >&5 +echo "$as_me: error: \`$ac_var' was not set in the previous run" >&2;} + ac_cache_corrupted=: ;; + ,);; + *) + if test "x$ac_old_val" != "x$ac_new_val"; then + { echo "$as_me:$LINENO: error: \`$ac_var' has changed since the previous run:" >&5 +echo "$as_me: error: \`$ac_var' has changed since the previous run:" >&2;} + { echo "$as_me:$LINENO: former value: $ac_old_val" >&5 +echo "$as_me: former value: $ac_old_val" >&2;} + { echo "$as_me:$LINENO: current value: $ac_new_val" >&5 +echo "$as_me: current value: $ac_new_val" >&2;} + ac_cache_corrupted=: + fi;; + esac + # Pass precious variables to config.status. + if test "$ac_new_set" = set; then + case $ac_new_val in + *" "*|*" "*|*[\[\]\~\#\$\^\&\*\(\)\{\}\\\|\;\<\>\?\"\']*) + ac_arg=$ac_var=`echo "$ac_new_val" | sed "s/'/'\\\\\\\\''/g"` ;; + *) ac_arg=$ac_var=$ac_new_val ;; + esac + case " $ac_configure_args " in + *" '$ac_arg' "*) ;; # Avoid dups. Use of quotes ensures accuracy. + *) ac_configure_args="$ac_configure_args '$ac_arg'" ;; + esac + fi +done +if $ac_cache_corrupted; then + { echo "$as_me:$LINENO: error: changes in the environment can compromise the build" >&5 +echo "$as_me: error: changes in the environment can compromise the build" >&2;} + { { echo "$as_me:$LINENO: error: run \`make distclean' and/or \`rm $cache_file' and start over" >&5 +echo "$as_me: error: run \`make distclean' and/or \`rm $cache_file' and start over" >&2;} + { (exit 1); exit 1; }; } +fi + +ac_ext=c +ac_cpp='$CPP $CPPFLAGS' +ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' +ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' +ac_compiler_gnu=$ac_cv_c_compiler_gnu + + + + + + + + + + + + + + + + + + + + + + + + + + + + +ac_aux_dir= +for ac_dir in $srcdir $srcdir/.. $srcdir/../..; do + if test -f $ac_dir/install-sh; then + ac_aux_dir=$ac_dir + ac_install_sh="$ac_aux_dir/install-sh -c" + break + elif test -f $ac_dir/install.sh; then + ac_aux_dir=$ac_dir + ac_install_sh="$ac_aux_dir/install.sh -c" + break + elif test -f $ac_dir/shtool; then + ac_aux_dir=$ac_dir + ac_install_sh="$ac_aux_dir/shtool install -c" + break + fi +done +if test -z "$ac_aux_dir"; then + { { echo "$as_me:$LINENO: error: cannot find install-sh or install.sh in $srcdir $srcdir/.. $srcdir/../.." >&5 +echo "$as_me: error: cannot find install-sh or install.sh in $srcdir $srcdir/.. $srcdir/../.." >&2;} + { (exit 1); exit 1; }; } +fi +ac_config_guess="$SHELL $ac_aux_dir/config.guess" +ac_config_sub="$SHELL $ac_aux_dir/config.sub" +ac_configure="$SHELL $ac_aux_dir/configure" # This should be Cygnus configure. + +# Make sure we can run config.sub. +$ac_config_sub sun4 >/dev/null 2>&1 || + { { echo "$as_me:$LINENO: error: cannot run $ac_config_sub" >&5 +echo "$as_me: error: cannot run $ac_config_sub" >&2;} + { (exit 1); exit 1; }; } + +echo "$as_me:$LINENO: checking build system type" >&5 +echo $ECHO_N "checking build system type... $ECHO_C" >&6 +if test "${ac_cv_build+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + ac_cv_build_alias=$build_alias +test -z "$ac_cv_build_alias" && + ac_cv_build_alias=`$ac_config_guess` +test -z "$ac_cv_build_alias" && + { { echo "$as_me:$LINENO: error: cannot guess build type; you must specify one" >&5 +echo "$as_me: error: cannot guess build type; you must specify one" >&2;} + { (exit 1); exit 1; }; } +ac_cv_build=`$ac_config_sub $ac_cv_build_alias` || + { { echo "$as_me:$LINENO: error: $ac_config_sub $ac_cv_build_alias failed" >&5 +echo "$as_me: error: $ac_config_sub $ac_cv_build_alias failed" >&2;} + { (exit 1); exit 1; }; } + +fi +echo "$as_me:$LINENO: result: $ac_cv_build" >&5 +echo "${ECHO_T}$ac_cv_build" >&6 +build=$ac_cv_build +build_cpu=`echo $ac_cv_build | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\1/'` +build_vendor=`echo $ac_cv_build | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\2/'` +build_os=`echo $ac_cv_build | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\3/'` + + +echo "$as_me:$LINENO: checking host system type" >&5 +echo $ECHO_N "checking host system type... $ECHO_C" >&6 +if test "${ac_cv_host+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + ac_cv_host_alias=$host_alias +test -z "$ac_cv_host_alias" && + ac_cv_host_alias=$ac_cv_build_alias +ac_cv_host=`$ac_config_sub $ac_cv_host_alias` || + { { echo "$as_me:$LINENO: error: $ac_config_sub $ac_cv_host_alias failed" >&5 +echo "$as_me: error: $ac_config_sub $ac_cv_host_alias failed" >&2;} + { (exit 1); exit 1; }; } + +fi +echo "$as_me:$LINENO: result: $ac_cv_host" >&5 +echo "${ECHO_T}$ac_cv_host" >&6 +host=$ac_cv_host +host_cpu=`echo $ac_cv_host | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\1/'` +host_vendor=`echo $ac_cv_host | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\2/'` +host_os=`echo $ac_cv_host | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\3/'` + + +echo "$as_me:$LINENO: checking target system type" >&5 +echo $ECHO_N "checking target system type... $ECHO_C" >&6 +if test "${ac_cv_target+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + ac_cv_target_alias=$target_alias +test "x$ac_cv_target_alias" = "x" && + ac_cv_target_alias=$ac_cv_host_alias +ac_cv_target=`$ac_config_sub $ac_cv_target_alias` || + { { echo "$as_me:$LINENO: error: $ac_config_sub $ac_cv_target_alias failed" >&5 +echo "$as_me: error: $ac_config_sub $ac_cv_target_alias failed" >&2;} + { (exit 1); exit 1; }; } + +fi +echo "$as_me:$LINENO: result: $ac_cv_target" >&5 +echo "${ECHO_T}$ac_cv_target" >&6 +target=$ac_cv_target +target_cpu=`echo $ac_cv_target | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\1/'` +target_vendor=`echo $ac_cv_target | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\2/'` +target_os=`echo $ac_cv_target | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\3/'` + + +# The aliases save the names the user supplied, while $host etc. +# will get canonicalized. +test -n "$target_alias" && + test "$program_prefix$program_suffix$program_transform_name" = \ + NONENONEs,x,x, && + program_prefix=${target_alias}- + + ac_config_headers="$ac_config_headers src/config.h" + + +ac_ext=c +ac_cpp='$CPP $CPPFLAGS' +ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' +ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' +ac_compiler_gnu=$ac_cv_c_compiler_gnu + + +#------------------------------------------------------------------------------------ +# Rules for library version information: +# +# 1. Start with version information of `0:0:0' for each libtool library. +# 2. Update the version information only immediately before a public release of +# your software. More frequent updates are unnecessary, and only guarantee +# that the current interface number gets larger faster. +# 3. If the library source code has changed at all since the last update, then +# increment revision (`c:r:a' becomes `c:r+1:a'). +# 4. If any interfaces have been added, removed, or changed since the last update, +# increment current, and set revision to 0. +# 5. If any interfaces have been added since the last public release, then increment +# age. +# 6. If any interfaces have been removed since the last public release, then set age +# to 0. + +SHARED_VERSION_INFO="1:16:0" + +ac_ext=c +ac_cpp='$CPP $CPPFLAGS' +ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' +ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' +ac_compiler_gnu=$ac_cv_c_compiler_gnu +if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}gcc", so it can be a program name with args. +set dummy ${ac_tool_prefix}gcc; ac_word=$2 +echo "$as_me:$LINENO: checking for $ac_word" >&5 +echo $ECHO_N "checking for $ac_word... $ECHO_C" >&6 +if test "${ac_cv_prog_CC+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test -n "$CC"; then + ac_cv_prog_CC="$CC" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + for ac_exec_ext in '' $ac_executable_extensions; do + if $as_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_prog_CC="${ac_tool_prefix}gcc" + echo "$as_me:$LINENO: found $as_dir/$ac_word$ac_exec_ext" >&5 + break 2 + fi +done +done + +fi +fi +CC=$ac_cv_prog_CC +if test -n "$CC"; then + echo "$as_me:$LINENO: result: $CC" >&5 +echo "${ECHO_T}$CC" >&6 +else + echo "$as_me:$LINENO: result: no" >&5 +echo "${ECHO_T}no" >&6 +fi + +fi +if test -z "$ac_cv_prog_CC"; then + ac_ct_CC=$CC + # Extract the first word of "gcc", so it can be a program name with args. +set dummy gcc; ac_word=$2 +echo "$as_me:$LINENO: checking for $ac_word" >&5 +echo $ECHO_N "checking for $ac_word... $ECHO_C" >&6 +if test "${ac_cv_prog_ac_ct_CC+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test -n "$ac_ct_CC"; then + ac_cv_prog_ac_ct_CC="$ac_ct_CC" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + for ac_exec_ext in '' $ac_executable_extensions; do + if $as_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_CC="gcc" + echo "$as_me:$LINENO: found $as_dir/$ac_word$ac_exec_ext" >&5 + break 2 + fi +done +done + +fi +fi +ac_ct_CC=$ac_cv_prog_ac_ct_CC +if test -n "$ac_ct_CC"; then + echo "$as_me:$LINENO: result: $ac_ct_CC" >&5 +echo "${ECHO_T}$ac_ct_CC" >&6 +else + echo "$as_me:$LINENO: result: no" >&5 +echo "${ECHO_T}no" >&6 +fi + + CC=$ac_ct_CC +else + CC="$ac_cv_prog_CC" +fi + +if test -z "$CC"; then + if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}cc", so it can be a program name with args. +set dummy ${ac_tool_prefix}cc; ac_word=$2 +echo "$as_me:$LINENO: checking for $ac_word" >&5 +echo $ECHO_N "checking for $ac_word... $ECHO_C" >&6 +if test "${ac_cv_prog_CC+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test -n "$CC"; then + ac_cv_prog_CC="$CC" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + for ac_exec_ext in '' $ac_executable_extensions; do + if $as_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_prog_CC="${ac_tool_prefix}cc" + echo "$as_me:$LINENO: found $as_dir/$ac_word$ac_exec_ext" >&5 + break 2 + fi +done +done + +fi +fi +CC=$ac_cv_prog_CC +if test -n "$CC"; then + echo "$as_me:$LINENO: result: $CC" >&5 +echo "${ECHO_T}$CC" >&6 +else + echo "$as_me:$LINENO: result: no" >&5 +echo "${ECHO_T}no" >&6 +fi + +fi +if test -z "$ac_cv_prog_CC"; then + ac_ct_CC=$CC + # Extract the first word of "cc", so it can be a program name with args. +set dummy cc; ac_word=$2 +echo "$as_me:$LINENO: checking for $ac_word" >&5 +echo $ECHO_N "checking for $ac_word... $ECHO_C" >&6 +if test "${ac_cv_prog_ac_ct_CC+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test -n "$ac_ct_CC"; then + ac_cv_prog_ac_ct_CC="$ac_ct_CC" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + for ac_exec_ext in '' $ac_executable_extensions; do + if $as_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_CC="cc" + echo "$as_me:$LINENO: found $as_dir/$ac_word$ac_exec_ext" >&5 + break 2 + fi +done +done + +fi +fi +ac_ct_CC=$ac_cv_prog_ac_ct_CC +if test -n "$ac_ct_CC"; then + echo "$as_me:$LINENO: result: $ac_ct_CC" >&5 +echo "${ECHO_T}$ac_ct_CC" >&6 +else + echo "$as_me:$LINENO: result: no" >&5 +echo "${ECHO_T}no" >&6 +fi + + CC=$ac_ct_CC +else + CC="$ac_cv_prog_CC" +fi + +fi +if test -z "$CC"; then + # Extract the first word of "cc", so it can be a program name with args. +set dummy cc; ac_word=$2 +echo "$as_me:$LINENO: checking for $ac_word" >&5 +echo $ECHO_N "checking for $ac_word... $ECHO_C" >&6 +if test "${ac_cv_prog_CC+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test -n "$CC"; then + ac_cv_prog_CC="$CC" # Let the user override the test. +else + ac_prog_rejected=no +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + for ac_exec_ext in '' $ac_executable_extensions; do + if $as_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + if test "$as_dir/$ac_word$ac_exec_ext" = "/usr/ucb/cc"; then + ac_prog_rejected=yes + continue + fi + ac_cv_prog_CC="cc" + echo "$as_me:$LINENO: found $as_dir/$ac_word$ac_exec_ext" >&5 + break 2 + fi +done +done + +if test $ac_prog_rejected = yes; then + # We found a bogon in the path, so make sure we never use it. + set dummy $ac_cv_prog_CC + shift + if test $# != 0; then + # We chose a different compiler from the bogus one. + # However, it has the same basename, so the bogon will be chosen + # first if we set CC to just the basename; use the full file name. + shift + ac_cv_prog_CC="$as_dir/$ac_word${1+' '}$@" + fi +fi +fi +fi +CC=$ac_cv_prog_CC +if test -n "$CC"; then + echo "$as_me:$LINENO: result: $CC" >&5 +echo "${ECHO_T}$CC" >&6 +else + echo "$as_me:$LINENO: result: no" >&5 +echo "${ECHO_T}no" >&6 +fi + +fi +if test -z "$CC"; then + if test -n "$ac_tool_prefix"; then + for ac_prog in cl + do + # Extract the first word of "$ac_tool_prefix$ac_prog", so it can be a program name with args. +set dummy $ac_tool_prefix$ac_prog; ac_word=$2 +echo "$as_me:$LINENO: checking for $ac_word" >&5 +echo $ECHO_N "checking for $ac_word... $ECHO_C" >&6 +if test "${ac_cv_prog_CC+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test -n "$CC"; then + ac_cv_prog_CC="$CC" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + for ac_exec_ext in '' $ac_executable_extensions; do + if $as_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_prog_CC="$ac_tool_prefix$ac_prog" + echo "$as_me:$LINENO: found $as_dir/$ac_word$ac_exec_ext" >&5 + break 2 + fi +done +done + +fi +fi +CC=$ac_cv_prog_CC +if test -n "$CC"; then + echo "$as_me:$LINENO: result: $CC" >&5 +echo "${ECHO_T}$CC" >&6 +else + echo "$as_me:$LINENO: result: no" >&5 +echo "${ECHO_T}no" >&6 +fi + + test -n "$CC" && break + done +fi +if test -z "$CC"; then + ac_ct_CC=$CC + for ac_prog in cl +do + # Extract the first word of "$ac_prog", so it can be a program name with args. +set dummy $ac_prog; ac_word=$2 +echo "$as_me:$LINENO: checking for $ac_word" >&5 +echo $ECHO_N "checking for $ac_word... $ECHO_C" >&6 +if test "${ac_cv_prog_ac_ct_CC+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test -n "$ac_ct_CC"; then + ac_cv_prog_ac_ct_CC="$ac_ct_CC" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + for ac_exec_ext in '' $ac_executable_extensions; do + if $as_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_CC="$ac_prog" + echo "$as_me:$LINENO: found $as_dir/$ac_word$ac_exec_ext" >&5 + break 2 + fi +done +done + +fi +fi +ac_ct_CC=$ac_cv_prog_ac_ct_CC +if test -n "$ac_ct_CC"; then + echo "$as_me:$LINENO: result: $ac_ct_CC" >&5 +echo "${ECHO_T}$ac_ct_CC" >&6 +else + echo "$as_me:$LINENO: result: no" >&5 +echo "${ECHO_T}no" >&6 +fi + + test -n "$ac_ct_CC" && break +done + + CC=$ac_ct_CC +fi + +fi + + +test -z "$CC" && { { echo "$as_me:$LINENO: error: no acceptable C compiler found in \$PATH +See \`config.log' for more details." >&5 +echo "$as_me: error: no acceptable C compiler found in \$PATH +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } + +# Provide some information about the compiler. +echo "$as_me:$LINENO:" \ + "checking for C compiler version" >&5 +ac_compiler=`set X $ac_compile; echo $2` +{ (eval echo "$as_me:$LINENO: \"$ac_compiler --version &5\"") >&5 + (eval $ac_compiler --version &5) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } +{ (eval echo "$as_me:$LINENO: \"$ac_compiler -v &5\"") >&5 + (eval $ac_compiler -v &5) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } +{ (eval echo "$as_me:$LINENO: \"$ac_compiler -V &5\"") >&5 + (eval $ac_compiler -V &5) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } + +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ + +int +main () +{ + + ; + return 0; +} +_ACEOF +ac_clean_files_save=$ac_clean_files +ac_clean_files="$ac_clean_files a.out a.exe b.out" +# Try to create an executable without -o first, disregard a.out. +# It will help us diagnose broken compilers, and finding out an intuition +# of exeext. +echo "$as_me:$LINENO: checking for C compiler default output file name" >&5 +echo $ECHO_N "checking for C compiler default output file name... $ECHO_C" >&6 +ac_link_default=`echo "$ac_link" | sed 's/ -o *conftest[^ ]*//'` +if { (eval echo "$as_me:$LINENO: \"$ac_link_default\"") >&5 + (eval $ac_link_default) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; then + # Find the output, starting from the most likely. This scheme is +# not robust to junk in `.', hence go to wildcards (a.*) only as a last +# resort. + +# Be careful to initialize this variable, since it used to be cached. +# Otherwise an old cache value of `no' led to `EXEEXT = no' in a Makefile. +ac_cv_exeext= +# b.out is created by i960 compilers. +for ac_file in a_out.exe a.exe conftest.exe a.out conftest a.* conftest.* b.out +do + test -f "$ac_file" || continue + case $ac_file in + *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.o | *.obj ) + ;; + conftest.$ac_ext ) + # This is the source file. + ;; + [ab].out ) + # We found the default executable, but exeext='' is most + # certainly right. + break;; + *.* ) + ac_cv_exeext=`expr "$ac_file" : '[^.]*\(\..*\)'` + # FIXME: I believe we export ac_cv_exeext for Libtool, + # but it would be cool to find out if it's true. Does anybody + # maintain Libtool? --akim. + export ac_cv_exeext + break;; + * ) + break;; + esac +done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +{ { echo "$as_me:$LINENO: error: C compiler cannot create executables +See \`config.log' for more details." >&5 +echo "$as_me: error: C compiler cannot create executables +See \`config.log' for more details." >&2;} + { (exit 77); exit 77; }; } +fi + +ac_exeext=$ac_cv_exeext +echo "$as_me:$LINENO: result: $ac_file" >&5 +echo "${ECHO_T}$ac_file" >&6 + +# Check the compiler produces executables we can run. If not, either +# the compiler is broken, or we cross compile. +echo "$as_me:$LINENO: checking whether the C compiler works" >&5 +echo $ECHO_N "checking whether the C compiler works... $ECHO_C" >&6 +# FIXME: These cross compiler hacks should be removed for Autoconf 3.0 +# If not cross compiling, check that we can run a simple program. +if test "$cross_compiling" != yes; then + if { ac_try='./$ac_file' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + cross_compiling=no + else + if test "$cross_compiling" = maybe; then + cross_compiling=yes + else + { { echo "$as_me:$LINENO: error: cannot run C compiled programs. +If you meant to cross compile, use \`--host'. +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot run C compiled programs. +If you meant to cross compile, use \`--host'. +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } + fi + fi +fi +echo "$as_me:$LINENO: result: yes" >&5 +echo "${ECHO_T}yes" >&6 + +rm -f a.out a.exe conftest$ac_cv_exeext b.out +ac_clean_files=$ac_clean_files_save +# Check the compiler produces executables we can run. If not, either +# the compiler is broken, or we cross compile. +echo "$as_me:$LINENO: checking whether we are cross compiling" >&5 +echo $ECHO_N "checking whether we are cross compiling... $ECHO_C" >&6 +echo "$as_me:$LINENO: result: $cross_compiling" >&5 +echo "${ECHO_T}$cross_compiling" >&6 + +echo "$as_me:$LINENO: checking for suffix of executables" >&5 +echo $ECHO_N "checking for suffix of executables... $ECHO_C" >&6 +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; then + # If both `conftest.exe' and `conftest' are `present' (well, observable) +# catch `conftest.exe'. For instance with Cygwin, `ls conftest' will +# work properly (i.e., refer to `conftest.exe'), while it won't with +# `rm'. +for ac_file in conftest.exe conftest conftest.*; do + test -f "$ac_file" || continue + case $ac_file in + *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.o | *.obj ) ;; + *.* ) ac_cv_exeext=`expr "$ac_file" : '[^.]*\(\..*\)'` + export ac_cv_exeext + break;; + * ) break;; + esac +done +else + { { echo "$as_me:$LINENO: error: cannot compute suffix of executables: cannot compile and link +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute suffix of executables: cannot compile and link +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +fi + +rm -f conftest$ac_cv_exeext +echo "$as_me:$LINENO: result: $ac_cv_exeext" >&5 +echo "${ECHO_T}$ac_cv_exeext" >&6 + +rm -f conftest.$ac_ext +EXEEXT=$ac_cv_exeext +ac_exeext=$EXEEXT +echo "$as_me:$LINENO: checking for suffix of object files" >&5 +echo $ECHO_N "checking for suffix of object files... $ECHO_C" >&6 +if test "${ac_cv_objext+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ + +int +main () +{ + + ; + return 0; +} +_ACEOF +rm -f conftest.o conftest.obj +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; then + for ac_file in `(ls conftest.o conftest.obj; ls conftest.*) 2>/dev/null`; do + case $ac_file in + *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg ) ;; + *) ac_cv_objext=`expr "$ac_file" : '.*\.\(.*\)'` + break;; + esac +done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +{ { echo "$as_me:$LINENO: error: cannot compute suffix of object files: cannot compile +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute suffix of object files: cannot compile +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +fi + +rm -f conftest.$ac_cv_objext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: $ac_cv_objext" >&5 +echo "${ECHO_T}$ac_cv_objext" >&6 +OBJEXT=$ac_cv_objext +ac_objext=$OBJEXT +echo "$as_me:$LINENO: checking whether we are using the GNU C compiler" >&5 +echo $ECHO_N "checking whether we are using the GNU C compiler... $ECHO_C" >&6 +if test "${ac_cv_c_compiler_gnu+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ + +int +main () +{ +#ifndef __GNUC__ + choke me +#endif + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_compiler_gnu=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_compiler_gnu=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +ac_cv_c_compiler_gnu=$ac_compiler_gnu + +fi +echo "$as_me:$LINENO: result: $ac_cv_c_compiler_gnu" >&5 +echo "${ECHO_T}$ac_cv_c_compiler_gnu" >&6 +GCC=`test $ac_compiler_gnu = yes && echo yes` +ac_test_CFLAGS=${CFLAGS+set} +ac_save_CFLAGS=$CFLAGS +CFLAGS="-g" +echo "$as_me:$LINENO: checking whether $CC accepts -g" >&5 +echo $ECHO_N "checking whether $CC accepts -g... $ECHO_C" >&6 +if test "${ac_cv_prog_cc_g+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ + +int +main () +{ + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_prog_cc_g=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_prog_cc_g=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: $ac_cv_prog_cc_g" >&5 +echo "${ECHO_T}$ac_cv_prog_cc_g" >&6 +if test "$ac_test_CFLAGS" = set; then + CFLAGS=$ac_save_CFLAGS +elif test $ac_cv_prog_cc_g = yes; then + if test "$GCC" = yes; then + CFLAGS="-g -O2" + else + CFLAGS="-g" + fi +else + if test "$GCC" = yes; then + CFLAGS="-O2" + else + CFLAGS= + fi +fi +echo "$as_me:$LINENO: checking for $CC option to accept ANSI C" >&5 +echo $ECHO_N "checking for $CC option to accept ANSI C... $ECHO_C" >&6 +if test "${ac_cv_prog_cc_stdc+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + ac_cv_prog_cc_stdc=no +ac_save_CC=$CC +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +#include +#include +#include +#include +/* Most of the following tests are stolen from RCS 5.7's src/conf.sh. */ +struct buf { int x; }; +FILE * (*rcsopen) (struct buf *, struct stat *, int); +static char *e (p, i) + char **p; + int i; +{ + return p[i]; +} +static char *f (char * (*g) (char **, int), char **p, ...) +{ + char *s; + va_list v; + va_start (v,p); + s = g (p, va_arg (v,int)); + va_end (v); + return s; +} + +/* OSF 4.0 Compaq cc is some sort of almost-ANSI by default. It has + function prototypes and stuff, but not '\xHH' hex character constants. + These don't provoke an error unfortunately, instead are silently treated + as 'x'. The following induces an error, until -std1 is added to get + proper ANSI mode. Curiously '\x00'!='x' always comes out true, for an + array size at least. It's necessary to write '\x00'==0 to get something + that's true only with -std1. */ +int osf4_cc_array ['\x00' == 0 ? 1 : -1]; + +int test (int i, double x); +struct s1 {int (*f) (int a);}; +struct s2 {int (*f) (double a);}; +int pairnames (int, char **, FILE *(*)(struct buf *, struct stat *, int), int, int); +int argc; +char **argv; +int +main () +{ +return f (e, argv, 0) != argv[0] || f (e, argv, 1) != argv[1]; + ; + return 0; +} +_ACEOF +# Don't try gcc -ansi; that turns off useful extensions and +# breaks some systems' header files. +# AIX -qlanglvl=ansi +# Ultrix and OSF/1 -std1 +# HP-UX 10.20 and later -Ae +# HP-UX older versions -Aa -D_HPUX_SOURCE +# SVR4 -Xc -D__EXTENSIONS__ +for ac_arg in "" -qlanglvl=ansi -std1 -Ae "-Aa -D_HPUX_SOURCE" "-Xc -D__EXTENSIONS__" +do + CC="$ac_save_CC $ac_arg" + rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_prog_cc_stdc=$ac_arg +break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +fi +rm -f conftest.err conftest.$ac_objext +done +rm -f conftest.$ac_ext conftest.$ac_objext +CC=$ac_save_CC + +fi + +case "x$ac_cv_prog_cc_stdc" in + x|xno) + echo "$as_me:$LINENO: result: none needed" >&5 +echo "${ECHO_T}none needed" >&6 ;; + *) + echo "$as_me:$LINENO: result: $ac_cv_prog_cc_stdc" >&5 +echo "${ECHO_T}$ac_cv_prog_cc_stdc" >&6 + CC="$CC $ac_cv_prog_cc_stdc" ;; +esac + +# Some people use a C++ compiler to compile C. Since we use `exit', +# in C++ we need to declare it. In case someone uses the same compiler +# for both compiling C and C++ we need to have the C++ compiler decide +# the declaration of exit, since it's the most demanding environment. +cat >conftest.$ac_ext <<_ACEOF +#ifndef __cplusplus + choke me +#endif +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + for ac_declaration in \ + '' \ + 'extern "C" void std::exit (int) throw (); using std::exit;' \ + 'extern "C" void std::exit (int); using std::exit;' \ + 'extern "C" void exit (int) throw ();' \ + 'extern "C" void exit (int);' \ + 'void exit (int);' +do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_declaration +#include +int +main () +{ +exit (42); + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + : +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +continue +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_declaration +int +main () +{ +exit (42); + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +done +rm -f conftest* +if test -n "$ac_declaration"; then + echo '#ifdef __cplusplus' >>confdefs.h + echo $ac_declaration >>confdefs.h + echo '#endif' >>confdefs.h +fi + +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +ac_ext=c +ac_cpp='$CPP $CPPFLAGS' +ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' +ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' +ac_compiler_gnu=$ac_cv_c_compiler_gnu + +#AM_PROG_LIBTOOL + +# Extract the first word of "autogen", so it can be a program name with args. +set dummy autogen; ac_word=$2 +echo "$as_me:$LINENO: checking for $ac_word" >&5 +echo $ECHO_N "checking for $ac_word... $ECHO_C" >&6 +if test "${ac_cv_prog_autogen+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test -n "$autogen"; then + ac_cv_prog_autogen="$autogen" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + for ac_exec_ext in '' $ac_executable_extensions; do + if $as_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_prog_autogen="yes" + echo "$as_me:$LINENO: found $as_dir/$ac_word$ac_exec_ext" >&5 + break 2 + fi +done +done + + test -z "$ac_cv_prog_autogen" && ac_cv_prog_autogen="no" +fi +fi +autogen=$ac_cv_prog_autogen +if test -n "$autogen"; then + echo "$as_me:$LINENO: result: $autogen" >&5 +echo "${ECHO_T}$autogen" >&6 +else + echo "$as_me:$LINENO: result: no" >&5 +echo "${ECHO_T}no" >&6 +fi + + +# Find a good install program. We prefer a C program (faster), +# so one script is as good as another. But avoid the broken or +# incompatible versions: +# SysV /etc/install, /usr/sbin/install +# SunOS /usr/etc/install +# IRIX /sbin/install +# AIX /bin/install +# AmigaOS /C/install, which installs bootblocks on floppy discs +# AIX 4 /usr/bin/installbsd, which doesn't work without a -g flag +# AFS /usr/afsws/bin/install, which mishandles nonexistent args +# SVR4 /usr/ucb/install, which tries to use the nonexistent group "staff" +# OS/2's system install, which has a completely different semantic +# ./install, which can be erroneously created by make from ./install.sh. +echo "$as_me:$LINENO: checking for a BSD-compatible install" >&5 +echo $ECHO_N "checking for a BSD-compatible install... $ECHO_C" >&6 +if test -z "$INSTALL"; then +if test "${ac_cv_path_install+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + # Account for people who put trailing slashes in PATH elements. +case $as_dir/ in + ./ | .// | /cC/* | \ + /etc/* | /usr/sbin/* | /usr/etc/* | /sbin/* | /usr/afsws/bin/* | \ + ?:\\/os2\\/install\\/* | ?:\\/OS2\\/INSTALL\\/* | \ + /usr/ucb/* ) ;; + *) + # OSF1 and SCO ODT 3.0 have their own names for install. + # Don't use installbsd from OSF since it installs stuff as root + # by default. + for ac_prog in ginstall scoinst install; do + for ac_exec_ext in '' $ac_executable_extensions; do + if $as_executable_p "$as_dir/$ac_prog$ac_exec_ext"; then + if test $ac_prog = install && + grep dspmsg "$as_dir/$ac_prog$ac_exec_ext" >/dev/null 2>&1; then + # AIX install. It has an incompatible calling convention. + : + elif test $ac_prog = install && + grep pwplus "$as_dir/$ac_prog$ac_exec_ext" >/dev/null 2>&1; then + # program-specific install script used by HP pwplus--don't use. + : + else + ac_cv_path_install="$as_dir/$ac_prog$ac_exec_ext -c" + break 3 + fi + fi + done + done + ;; +esac +done + + +fi + if test "${ac_cv_path_install+set}" = set; then + INSTALL=$ac_cv_path_install + else + # As a last resort, use the slow shell script. We don't cache a + # path for INSTALL within a source directory, because that will + # break other packages using the cache if that directory is + # removed, or if the path is relative. + INSTALL=$ac_install_sh + fi +fi +echo "$as_me:$LINENO: result: $INSTALL" >&5 +echo "${ECHO_T}$INSTALL" >&6 + +# Use test -z because SunOS4 sh mishandles braces in ${var-val}. +# It thinks the first close brace ends the variable substitution. +test -z "$INSTALL_PROGRAM" && INSTALL_PROGRAM='${INSTALL}' + +test -z "$INSTALL_SCRIPT" && INSTALL_SCRIPT='${INSTALL}' + +test -z "$INSTALL_DATA" && INSTALL_DATA='${INSTALL} -m 644' + +echo "$as_me:$LINENO: checking whether ln -s works" >&5 +echo $ECHO_N "checking whether ln -s works... $ECHO_C" >&6 +LN_S=$as_ln_s +if test "$LN_S" = "ln -s"; then + echo "$as_me:$LINENO: result: yes" >&5 +echo "${ECHO_T}yes" >&6 +else + echo "$as_me:$LINENO: result: no, using $LN_S" >&5 +echo "${ECHO_T}no, using $LN_S" >&6 +fi + + + +ac_ext=c +ac_cpp='$CPP $CPPFLAGS' +ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' +ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' +ac_compiler_gnu=$ac_cv_c_compiler_gnu +echo "$as_me:$LINENO: checking how to run the C preprocessor" >&5 +echo $ECHO_N "checking how to run the C preprocessor... $ECHO_C" >&6 +# On Suns, sometimes $CPP names a directory. +if test -n "$CPP" && test -d "$CPP"; then + CPP= +fi +if test -z "$CPP"; then + if test "${ac_cv_prog_CPP+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + # Double quotes because CPP needs to be expanded + for CPP in "$CC -E" "$CC -E -traditional-cpp" "/lib/cpp" + do + ac_preproc_ok=false +for ac_c_preproc_warn_flag in '' yes +do + # Use a header file that comes with gcc, so configuring glibc + # with a fresh cross-compiler works. + # Prefer to if __STDC__ is defined, since + # exists even on freestanding compilers. + # On the NeXT, cc -E runs the code through the compiler's parser, + # not just through cpp. "Syntax error" is here to catch this case. + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +#ifdef __STDC__ +# include +#else +# include +#endif + Syntax error +_ACEOF +if { (eval echo "$as_me:$LINENO: \"$ac_cpp conftest.$ac_ext\"") >&5 + (eval $ac_cpp conftest.$ac_ext) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } >/dev/null; then + if test -s conftest.err; then + ac_cpp_err=$ac_c_preproc_warn_flag + ac_cpp_err=$ac_cpp_err$ac_c_werror_flag + else + ac_cpp_err= + fi +else + ac_cpp_err=yes +fi +if test -z "$ac_cpp_err"; then + : +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + + # Broken: fails on valid input. +continue +fi +rm -f conftest.err conftest.$ac_ext + + # OK, works on sane cases. Now check whether non-existent headers + # can be detected and how. + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +#include +_ACEOF +if { (eval echo "$as_me:$LINENO: \"$ac_cpp conftest.$ac_ext\"") >&5 + (eval $ac_cpp conftest.$ac_ext) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } >/dev/null; then + if test -s conftest.err; then + ac_cpp_err=$ac_c_preproc_warn_flag + ac_cpp_err=$ac_cpp_err$ac_c_werror_flag + else + ac_cpp_err= + fi +else + ac_cpp_err=yes +fi +if test -z "$ac_cpp_err"; then + # Broken: success on invalid input. +continue +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + + # Passes both tests. +ac_preproc_ok=: +break +fi +rm -f conftest.err conftest.$ac_ext + +done +# Because of `break', _AC_PREPROC_IFELSE's cleaning code was skipped. +rm -f conftest.err conftest.$ac_ext +if $ac_preproc_ok; then + break +fi + + done + ac_cv_prog_CPP=$CPP + +fi + CPP=$ac_cv_prog_CPP +else + ac_cv_prog_CPP=$CPP +fi +echo "$as_me:$LINENO: result: $CPP" >&5 +echo "${ECHO_T}$CPP" >&6 +ac_preproc_ok=false +for ac_c_preproc_warn_flag in '' yes +do + # Use a header file that comes with gcc, so configuring glibc + # with a fresh cross-compiler works. + # Prefer to if __STDC__ is defined, since + # exists even on freestanding compilers. + # On the NeXT, cc -E runs the code through the compiler's parser, + # not just through cpp. "Syntax error" is here to catch this case. + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +#ifdef __STDC__ +# include +#else +# include +#endif + Syntax error +_ACEOF +if { (eval echo "$as_me:$LINENO: \"$ac_cpp conftest.$ac_ext\"") >&5 + (eval $ac_cpp conftest.$ac_ext) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } >/dev/null; then + if test -s conftest.err; then + ac_cpp_err=$ac_c_preproc_warn_flag + ac_cpp_err=$ac_cpp_err$ac_c_werror_flag + else + ac_cpp_err= + fi +else + ac_cpp_err=yes +fi +if test -z "$ac_cpp_err"; then + : +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + + # Broken: fails on valid input. +continue +fi +rm -f conftest.err conftest.$ac_ext + + # OK, works on sane cases. Now check whether non-existent headers + # can be detected and how. + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +#include +_ACEOF +if { (eval echo "$as_me:$LINENO: \"$ac_cpp conftest.$ac_ext\"") >&5 + (eval $ac_cpp conftest.$ac_ext) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } >/dev/null; then + if test -s conftest.err; then + ac_cpp_err=$ac_c_preproc_warn_flag + ac_cpp_err=$ac_cpp_err$ac_c_werror_flag + else + ac_cpp_err= + fi +else + ac_cpp_err=yes +fi +if test -z "$ac_cpp_err"; then + # Broken: success on invalid input. +continue +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + + # Passes both tests. +ac_preproc_ok=: +break +fi +rm -f conftest.err conftest.$ac_ext + +done +# Because of `break', _AC_PREPROC_IFELSE's cleaning code was skipped. +rm -f conftest.err conftest.$ac_ext +if $ac_preproc_ok; then + : +else + { { echo "$as_me:$LINENO: error: C preprocessor \"$CPP\" fails sanity check +See \`config.log' for more details." >&5 +echo "$as_me: error: C preprocessor \"$CPP\" fails sanity check +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +fi + +ac_ext=c +ac_cpp='$CPP $CPPFLAGS' +ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' +ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' +ac_compiler_gnu=$ac_cv_c_compiler_gnu + + +echo "$as_me:$LINENO: checking for egrep" >&5 +echo $ECHO_N "checking for egrep... $ECHO_C" >&6 +if test "${ac_cv_prog_egrep+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if echo a | (grep -E '(a|b)') >/dev/null 2>&1 + then ac_cv_prog_egrep='grep -E' + else ac_cv_prog_egrep='egrep' + fi +fi +echo "$as_me:$LINENO: result: $ac_cv_prog_egrep" >&5 +echo "${ECHO_T}$ac_cv_prog_egrep" >&6 + EGREP=$ac_cv_prog_egrep + + +echo "$as_me:$LINENO: checking for ANSI C header files" >&5 +echo $ECHO_N "checking for ANSI C header files... $ECHO_C" >&6 +if test "${ac_cv_header_stdc+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +#include +#include +#include +#include + +int +main () +{ + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_header_stdc=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_header_stdc=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + +if test $ac_cv_header_stdc = yes; then + # SunOS 4.x string.h does not declare mem*, contrary to ANSI. + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +#include + +_ACEOF +if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | + $EGREP "memchr" >/dev/null 2>&1; then + : +else + ac_cv_header_stdc=no +fi +rm -f conftest* + +fi + +if test $ac_cv_header_stdc = yes; then + # ISC 2.0.2 stdlib.h does not declare free, contrary to ANSI. + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +#include + +_ACEOF +if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | + $EGREP "free" >/dev/null 2>&1; then + : +else + ac_cv_header_stdc=no +fi +rm -f conftest* + +fi + +if test $ac_cv_header_stdc = yes; then + # /bin/cc in Irix-4.0.5 gets non-ANSI ctype macros unless using -ansi. + if test "$cross_compiling" = yes; then + : +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +#include +#if ((' ' & 0x0FF) == 0x020) +# define ISLOWER(c) ('a' <= (c) && (c) <= 'z') +# define TOUPPER(c) (ISLOWER(c) ? 'A' + ((c) - 'a') : (c)) +#else +# define ISLOWER(c) \ + (('a' <= (c) && (c) <= 'i') \ + || ('j' <= (c) && (c) <= 'r') \ + || ('s' <= (c) && (c) <= 'z')) +# define TOUPPER(c) (ISLOWER(c) ? ((c) | 0x40) : (c)) +#endif + +#define XOR(e, f) (((e) && !(f)) || (!(e) && (f))) +int +main () +{ + int i; + for (i = 0; i < 256; i++) + if (XOR (islower (i), ISLOWER (i)) + || toupper (i) != TOUPPER (i)) + exit(2); + exit (0); +} +_ACEOF +rm -f conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && { ac_try='./conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + : +else + echo "$as_me: program exited with status $ac_status" >&5 +echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +( exit $ac_status ) +ac_cv_header_stdc=no +fi +rm -f core *.core gmon.out bb.out conftest$ac_exeext conftest.$ac_objext conftest.$ac_ext +fi +fi +fi +echo "$as_me:$LINENO: result: $ac_cv_header_stdc" >&5 +echo "${ECHO_T}$ac_cv_header_stdc" >&6 +if test $ac_cv_header_stdc = yes; then + +cat >>confdefs.h <<\_ACEOF +#define STDC_HEADERS 1 +_ACEOF + +fi + + +# On IRIX 5.3, sys/types and inttypes.h are conflicting. + + + + + + + + + +for ac_header in sys/types.h sys/stat.h stdlib.h string.h memory.h strings.h \ + inttypes.h stdint.h unistd.h +do +as_ac_Header=`echo "ac_cv_header_$ac_header" | $as_tr_sh` +echo "$as_me:$LINENO: checking for $ac_header" >&5 +echo $ECHO_N "checking for $ac_header... $ECHO_C" >&6 +if eval "test \"\${$as_ac_Header+set}\" = set"; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default + +#include <$ac_header> +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + eval "$as_ac_Header=yes" +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +eval "$as_ac_Header=no" +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_Header'}'`" >&5 +echo "${ECHO_T}`eval echo '${'$as_ac_Header'}'`" >&6 +if test `eval echo '${'$as_ac_Header'}'` = yes; then + cat >>confdefs.h <<_ACEOF +#define `echo "HAVE_$ac_header" | $as_tr_cpp` 1 +_ACEOF + +fi + +done + + + +for ac_header in endian.h +do +as_ac_Header=`echo "ac_cv_header_$ac_header" | $as_tr_sh` +if eval "test \"\${$as_ac_Header+set}\" = set"; then + echo "$as_me:$LINENO: checking for $ac_header" >&5 +echo $ECHO_N "checking for $ac_header... $ECHO_C" >&6 +if eval "test \"\${$as_ac_Header+set}\" = set"; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +fi +echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_Header'}'`" >&5 +echo "${ECHO_T}`eval echo '${'$as_ac_Header'}'`" >&6 +else + # Is the header compilable? +echo "$as_me:$LINENO: checking $ac_header usability" >&5 +echo $ECHO_N "checking $ac_header usability... $ECHO_C" >&6 +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +#include <$ac_header> +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_header_compiler=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_header_compiler=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +echo "$as_me:$LINENO: result: $ac_header_compiler" >&5 +echo "${ECHO_T}$ac_header_compiler" >&6 + +# Is the header present? +echo "$as_me:$LINENO: checking $ac_header presence" >&5 +echo $ECHO_N "checking $ac_header presence... $ECHO_C" >&6 +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +#include <$ac_header> +_ACEOF +if { (eval echo "$as_me:$LINENO: \"$ac_cpp conftest.$ac_ext\"") >&5 + (eval $ac_cpp conftest.$ac_ext) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } >/dev/null; then + if test -s conftest.err; then + ac_cpp_err=$ac_c_preproc_warn_flag + ac_cpp_err=$ac_cpp_err$ac_c_werror_flag + else + ac_cpp_err= + fi +else + ac_cpp_err=yes +fi +if test -z "$ac_cpp_err"; then + ac_header_preproc=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + + ac_header_preproc=no +fi +rm -f conftest.err conftest.$ac_ext +echo "$as_me:$LINENO: result: $ac_header_preproc" >&5 +echo "${ECHO_T}$ac_header_preproc" >&6 + +# So? What about this header? +case $ac_header_compiler:$ac_header_preproc:$ac_c_preproc_warn_flag in + yes:no: ) + { echo "$as_me:$LINENO: WARNING: $ac_header: accepted by the compiler, rejected by the preprocessor!" >&5 +echo "$as_me: WARNING: $ac_header: accepted by the compiler, rejected by the preprocessor!" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: proceeding with the compiler's result" >&5 +echo "$as_me: WARNING: $ac_header: proceeding with the compiler's result" >&2;} + ac_header_preproc=yes + ;; + no:yes:* ) + { echo "$as_me:$LINENO: WARNING: $ac_header: present but cannot be compiled" >&5 +echo "$as_me: WARNING: $ac_header: present but cannot be compiled" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: check for missing prerequisite headers?" >&5 +echo "$as_me: WARNING: $ac_header: check for missing prerequisite headers?" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: see the Autoconf documentation" >&5 +echo "$as_me: WARNING: $ac_header: see the Autoconf documentation" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: section \"Present But Cannot Be Compiled\"" >&5 +echo "$as_me: WARNING: $ac_header: section \"Present But Cannot Be Compiled\"" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: proceeding with the preprocessor's result" >&5 +echo "$as_me: WARNING: $ac_header: proceeding with the preprocessor's result" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: in the future, the compiler will take precedence" >&5 +echo "$as_me: WARNING: $ac_header: in the future, the compiler will take precedence" >&2;} + ( + cat <<\_ASBOX +## -------------------------------- ## +## Report this to ardour@ardour.org ## +## -------------------------------- ## +_ASBOX + ) | + sed "s/^/$as_me: WARNING: /" >&2 + ;; +esac +echo "$as_me:$LINENO: checking for $ac_header" >&5 +echo $ECHO_N "checking for $ac_header... $ECHO_C" >&6 +if eval "test \"\${$as_ac_Header+set}\" = set"; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + eval "$as_ac_Header=\$ac_header_preproc" +fi +echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_Header'}'`" >&5 +echo "${ECHO_T}`eval echo '${'$as_ac_Header'}'`" >&6 + +fi +if test `eval echo '${'$as_ac_Header'}'` = yes; then + cat >>confdefs.h <<_ACEOF +#define `echo "HAVE_$ac_header" | $as_tr_cpp` 1 +_ACEOF + +fi + +done + + +for ac_header in byteswap.h +do +as_ac_Header=`echo "ac_cv_header_$ac_header" | $as_tr_sh` +if eval "test \"\${$as_ac_Header+set}\" = set"; then + echo "$as_me:$LINENO: checking for $ac_header" >&5 +echo $ECHO_N "checking for $ac_header... $ECHO_C" >&6 +if eval "test \"\${$as_ac_Header+set}\" = set"; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +fi +echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_Header'}'`" >&5 +echo "${ECHO_T}`eval echo '${'$as_ac_Header'}'`" >&6 +else + # Is the header compilable? +echo "$as_me:$LINENO: checking $ac_header usability" >&5 +echo $ECHO_N "checking $ac_header usability... $ECHO_C" >&6 +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +#include <$ac_header> +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_header_compiler=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_header_compiler=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +echo "$as_me:$LINENO: result: $ac_header_compiler" >&5 +echo "${ECHO_T}$ac_header_compiler" >&6 + +# Is the header present? +echo "$as_me:$LINENO: checking $ac_header presence" >&5 +echo $ECHO_N "checking $ac_header presence... $ECHO_C" >&6 +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +#include <$ac_header> +_ACEOF +if { (eval echo "$as_me:$LINENO: \"$ac_cpp conftest.$ac_ext\"") >&5 + (eval $ac_cpp conftest.$ac_ext) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } >/dev/null; then + if test -s conftest.err; then + ac_cpp_err=$ac_c_preproc_warn_flag + ac_cpp_err=$ac_cpp_err$ac_c_werror_flag + else + ac_cpp_err= + fi +else + ac_cpp_err=yes +fi +if test -z "$ac_cpp_err"; then + ac_header_preproc=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + + ac_header_preproc=no +fi +rm -f conftest.err conftest.$ac_ext +echo "$as_me:$LINENO: result: $ac_header_preproc" >&5 +echo "${ECHO_T}$ac_header_preproc" >&6 + +# So? What about this header? +case $ac_header_compiler:$ac_header_preproc:$ac_c_preproc_warn_flag in + yes:no: ) + { echo "$as_me:$LINENO: WARNING: $ac_header: accepted by the compiler, rejected by the preprocessor!" >&5 +echo "$as_me: WARNING: $ac_header: accepted by the compiler, rejected by the preprocessor!" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: proceeding with the compiler's result" >&5 +echo "$as_me: WARNING: $ac_header: proceeding with the compiler's result" >&2;} + ac_header_preproc=yes + ;; + no:yes:* ) + { echo "$as_me:$LINENO: WARNING: $ac_header: present but cannot be compiled" >&5 +echo "$as_me: WARNING: $ac_header: present but cannot be compiled" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: check for missing prerequisite headers?" >&5 +echo "$as_me: WARNING: $ac_header: check for missing prerequisite headers?" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: see the Autoconf documentation" >&5 +echo "$as_me: WARNING: $ac_header: see the Autoconf documentation" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: section \"Present But Cannot Be Compiled\"" >&5 +echo "$as_me: WARNING: $ac_header: section \"Present But Cannot Be Compiled\"" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: proceeding with the preprocessor's result" >&5 +echo "$as_me: WARNING: $ac_header: proceeding with the preprocessor's result" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: in the future, the compiler will take precedence" >&5 +echo "$as_me: WARNING: $ac_header: in the future, the compiler will take precedence" >&2;} + ( + cat <<\_ASBOX +## -------------------------------- ## +## Report this to ardour@ardour.org ## +## -------------------------------- ## +_ASBOX + ) | + sed "s/^/$as_me: WARNING: /" >&2 + ;; +esac +echo "$as_me:$LINENO: checking for $ac_header" >&5 +echo $ECHO_N "checking for $ac_header... $ECHO_C" >&6 +if eval "test \"\${$as_ac_Header+set}\" = set"; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + eval "$as_ac_Header=\$ac_header_preproc" +fi +echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_Header'}'`" >&5 +echo "${ECHO_T}`eval echo '${'$as_ac_Header'}'`" >&6 + +fi +if test `eval echo '${'$as_ac_Header'}'` = yes; then + cat >>confdefs.h <<_ACEOF +#define `echo "HAVE_$ac_header" | $as_tr_cpp` 1 +_ACEOF + +fi + +done + + +for ac_header in locale.h +do +as_ac_Header=`echo "ac_cv_header_$ac_header" | $as_tr_sh` +if eval "test \"\${$as_ac_Header+set}\" = set"; then + echo "$as_me:$LINENO: checking for $ac_header" >&5 +echo $ECHO_N "checking for $ac_header... $ECHO_C" >&6 +if eval "test \"\${$as_ac_Header+set}\" = set"; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +fi +echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_Header'}'`" >&5 +echo "${ECHO_T}`eval echo '${'$as_ac_Header'}'`" >&6 +else + # Is the header compilable? +echo "$as_me:$LINENO: checking $ac_header usability" >&5 +echo $ECHO_N "checking $ac_header usability... $ECHO_C" >&6 +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +#include <$ac_header> +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_header_compiler=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_header_compiler=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +echo "$as_me:$LINENO: result: $ac_header_compiler" >&5 +echo "${ECHO_T}$ac_header_compiler" >&6 + +# Is the header present? +echo "$as_me:$LINENO: checking $ac_header presence" >&5 +echo $ECHO_N "checking $ac_header presence... $ECHO_C" >&6 +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +#include <$ac_header> +_ACEOF +if { (eval echo "$as_me:$LINENO: \"$ac_cpp conftest.$ac_ext\"") >&5 + (eval $ac_cpp conftest.$ac_ext) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } >/dev/null; then + if test -s conftest.err; then + ac_cpp_err=$ac_c_preproc_warn_flag + ac_cpp_err=$ac_cpp_err$ac_c_werror_flag + else + ac_cpp_err= + fi +else + ac_cpp_err=yes +fi +if test -z "$ac_cpp_err"; then + ac_header_preproc=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + + ac_header_preproc=no +fi +rm -f conftest.err conftest.$ac_ext +echo "$as_me:$LINENO: result: $ac_header_preproc" >&5 +echo "${ECHO_T}$ac_header_preproc" >&6 + +# So? What about this header? +case $ac_header_compiler:$ac_header_preproc:$ac_c_preproc_warn_flag in + yes:no: ) + { echo "$as_me:$LINENO: WARNING: $ac_header: accepted by the compiler, rejected by the preprocessor!" >&5 +echo "$as_me: WARNING: $ac_header: accepted by the compiler, rejected by the preprocessor!" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: proceeding with the compiler's result" >&5 +echo "$as_me: WARNING: $ac_header: proceeding with the compiler's result" >&2;} + ac_header_preproc=yes + ;; + no:yes:* ) + { echo "$as_me:$LINENO: WARNING: $ac_header: present but cannot be compiled" >&5 +echo "$as_me: WARNING: $ac_header: present but cannot be compiled" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: check for missing prerequisite headers?" >&5 +echo "$as_me: WARNING: $ac_header: check for missing prerequisite headers?" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: see the Autoconf documentation" >&5 +echo "$as_me: WARNING: $ac_header: see the Autoconf documentation" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: section \"Present But Cannot Be Compiled\"" >&5 +echo "$as_me: WARNING: $ac_header: section \"Present But Cannot Be Compiled\"" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: proceeding with the preprocessor's result" >&5 +echo "$as_me: WARNING: $ac_header: proceeding with the preprocessor's result" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: in the future, the compiler will take precedence" >&5 +echo "$as_me: WARNING: $ac_header: in the future, the compiler will take precedence" >&2;} + ( + cat <<\_ASBOX +## -------------------------------- ## +## Report this to ardour@ardour.org ## +## -------------------------------- ## +_ASBOX + ) | + sed "s/^/$as_me: WARNING: /" >&2 + ;; +esac +echo "$as_me:$LINENO: checking for $ac_header" >&5 +echo $ECHO_N "checking for $ac_header... $ECHO_C" >&6 +if eval "test \"\${$as_ac_Header+set}\" = set"; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + eval "$as_ac_Header=\$ac_header_preproc" +fi +echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_Header'}'`" >&5 +echo "${ECHO_T}`eval echo '${'$as_ac_Header'}'`" >&6 + +fi +if test `eval echo '${'$as_ac_Header'}'` = yes; then + cat >>confdefs.h <<_ACEOF +#define `echo "HAVE_$ac_header" | $as_tr_cpp` 1 +_ACEOF + +fi + +done + + +for ac_header in inttypes.h +do +as_ac_Header=`echo "ac_cv_header_$ac_header" | $as_tr_sh` +if eval "test \"\${$as_ac_Header+set}\" = set"; then + echo "$as_me:$LINENO: checking for $ac_header" >&5 +echo $ECHO_N "checking for $ac_header... $ECHO_C" >&6 +if eval "test \"\${$as_ac_Header+set}\" = set"; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +fi +echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_Header'}'`" >&5 +echo "${ECHO_T}`eval echo '${'$as_ac_Header'}'`" >&6 +else + # Is the header compilable? +echo "$as_me:$LINENO: checking $ac_header usability" >&5 +echo $ECHO_N "checking $ac_header usability... $ECHO_C" >&6 +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +#include <$ac_header> +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_header_compiler=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_header_compiler=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +echo "$as_me:$LINENO: result: $ac_header_compiler" >&5 +echo "${ECHO_T}$ac_header_compiler" >&6 + +# Is the header present? +echo "$as_me:$LINENO: checking $ac_header presence" >&5 +echo $ECHO_N "checking $ac_header presence... $ECHO_C" >&6 +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +#include <$ac_header> +_ACEOF +if { (eval echo "$as_me:$LINENO: \"$ac_cpp conftest.$ac_ext\"") >&5 + (eval $ac_cpp conftest.$ac_ext) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } >/dev/null; then + if test -s conftest.err; then + ac_cpp_err=$ac_c_preproc_warn_flag + ac_cpp_err=$ac_cpp_err$ac_c_werror_flag + else + ac_cpp_err= + fi +else + ac_cpp_err=yes +fi +if test -z "$ac_cpp_err"; then + ac_header_preproc=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + + ac_header_preproc=no +fi +rm -f conftest.err conftest.$ac_ext +echo "$as_me:$LINENO: result: $ac_header_preproc" >&5 +echo "${ECHO_T}$ac_header_preproc" >&6 + +# So? What about this header? +case $ac_header_compiler:$ac_header_preproc:$ac_c_preproc_warn_flag in + yes:no: ) + { echo "$as_me:$LINENO: WARNING: $ac_header: accepted by the compiler, rejected by the preprocessor!" >&5 +echo "$as_me: WARNING: $ac_header: accepted by the compiler, rejected by the preprocessor!" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: proceeding with the compiler's result" >&5 +echo "$as_me: WARNING: $ac_header: proceeding with the compiler's result" >&2;} + ac_header_preproc=yes + ;; + no:yes:* ) + { echo "$as_me:$LINENO: WARNING: $ac_header: present but cannot be compiled" >&5 +echo "$as_me: WARNING: $ac_header: present but cannot be compiled" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: check for missing prerequisite headers?" >&5 +echo "$as_me: WARNING: $ac_header: check for missing prerequisite headers?" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: see the Autoconf documentation" >&5 +echo "$as_me: WARNING: $ac_header: see the Autoconf documentation" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: section \"Present But Cannot Be Compiled\"" >&5 +echo "$as_me: WARNING: $ac_header: section \"Present But Cannot Be Compiled\"" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: proceeding with the preprocessor's result" >&5 +echo "$as_me: WARNING: $ac_header: proceeding with the preprocessor's result" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: in the future, the compiler will take precedence" >&5 +echo "$as_me: WARNING: $ac_header: in the future, the compiler will take precedence" >&2;} + ( + cat <<\_ASBOX +## -------------------------------- ## +## Report this to ardour@ardour.org ## +## -------------------------------- ## +_ASBOX + ) | + sed "s/^/$as_me: WARNING: /" >&2 + ;; +esac +echo "$as_me:$LINENO: checking for $ac_header" >&5 +echo $ECHO_N "checking for $ac_header... $ECHO_C" >&6 +if eval "test \"\${$as_ac_Header+set}\" = set"; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + eval "$as_ac_Header=\$ac_header_preproc" +fi +echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_Header'}'`" >&5 +echo "${ECHO_T}`eval echo '${'$as_ac_Header'}'`" >&6 + +fi +if test `eval echo '${'$as_ac_Header'}'` = yes; then + cat >>confdefs.h <<_ACEOF +#define `echo "HAVE_$ac_header" | $as_tr_cpp` 1 +_ACEOF + +fi + +done + + +echo "$as_me:$LINENO: checking for sys/wait.h that is POSIX.1 compatible" >&5 +echo $ECHO_N "checking for sys/wait.h that is POSIX.1 compatible... $ECHO_C" >&6 +if test "${ac_cv_header_sys_wait_h+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +#include +#include +#ifndef WEXITSTATUS +# define WEXITSTATUS(stat_val) ((unsigned)(stat_val) >> 8) +#endif +#ifndef WIFEXITED +# define WIFEXITED(stat_val) (((stat_val) & 255) == 0) +#endif + +int +main () +{ + int s; + wait (&s); + s = WIFEXITED (s) ? WEXITSTATUS (s) : 1; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_header_sys_wait_h=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_header_sys_wait_h=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: $ac_cv_header_sys_wait_h" >&5 +echo "${ECHO_T}$ac_cv_header_sys_wait_h" >&6 +if test $ac_cv_header_sys_wait_h = yes; then + +cat >>confdefs.h <<\_ACEOF +#define HAVE_SYS_WAIT_H 1 +_ACEOF + +fi + + +echo "$as_me:$LINENO: checking whether S_IRGRP is declared" >&5 +echo $ECHO_N "checking whether S_IRGRP is declared... $ECHO_C" >&6 +if test "${ac_cv_have_decl_S_IRGRP+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +#ifndef S_IRGRP + char *p = (char *) S_IRGRP; +#endif + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_have_decl_S_IRGRP=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_have_decl_S_IRGRP=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: $ac_cv_have_decl_S_IRGRP" >&5 +echo "${ECHO_T}$ac_cv_have_decl_S_IRGRP" >&6 +if test $ac_cv_have_decl_S_IRGRP = yes; then + +cat >>confdefs.h <<_ACEOF +#define HAVE_DECL_S_IRGRP 1 +_ACEOF + + +else + cat >>confdefs.h <<_ACEOF +#define HAVE_DECL_S_IRGRP 0 +_ACEOF + + +fi + + + +cat >>confdefs.h <<_ACEOF +#define HAVE_DECL_S_IRGRP ${HAVE_DECL_S_IRGRP} +_ACEOF + + +#==================================================================================== +# Check for support of the struct hack. + +echo "$as_me:$LINENO: checking C99 struct flexible array support" >&5 +echo $ECHO_N "checking C99 struct flexible array support... $ECHO_C" >&6 +if test "${ac_cv_c99_flexible_array+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + # Initialize to unknown +ac_cv_c99_flexible_array=no + +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ + + #include + typedef struct { + int k; + char buffer [] ; + } MY_STRUCT ; + +int +main () +{ + MY_STRUCT *p = calloc (1, sizeof (MY_STRUCT) + 42); + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_c99_flexible_array=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_c99_flexible_array=no + +fi +rm -f conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: $ac_cv_c99_flexible_array" >&5 +echo "${ECHO_T}$ac_cv_c99_flexible_array" >&6 + + +if test x$ac_cv_c99_flexible_array = xyes ; then + +cat >>confdefs.h <<\_ACEOF +#define HAVE_FLEXIBLE_ARRAY 1 +_ACEOF + +else + { echo "$as_me:$LINENO: WARNING: *** This compiler does not support the 1999 ISO C Standard ***" >&5 +echo "$as_me: WARNING: *** This compiler does not support the 1999 ISO C Standard ***" >&2;} + { echo "$as_me:$LINENO: WARNING: *** feature known as the flexible array struct member. ***" >&5 +echo "$as_me: WARNING: *** feature known as the flexible array struct member. ***" >&2;} + cat >>confdefs.h <<\_ACEOF +#define HAVE_FLEXIBLE_ARRAY 0 +_ACEOF + + fi + +#==================================================================================== +# Couple of initializations here. Fill in real values later. + +SHLIB_VERSION_ARG="" + +#==================================================================================== +# Finished checking, handle options. + +# Check whether --enable-experimental or --disable-experimental was given. +if test "${enable_experimental+set}" = set; then + enableval="$enable_experimental" + +fi; + +EXPERIMENTAL_CODE=0 +if test x$enable_experimental = xyes ; then + EXPERIMENTAL_CODE=1 + fi + +cat >>confdefs.h <<_ACEOF +#define ENABLE_EXPERIMENTAL_CODE ${EXPERIMENTAL_CODE} +_ACEOF + + +# Check whether --enable-gcc-werror or --disable-gcc-werror was given. +if test "${enable_gcc_werror+set}" = set; then + enableval="$enable_gcc_werror" + +fi; + +# Check whether --enable-gcc-pipe or --disable-gcc-pipe was given. +if test "${enable_gcc_pipe+set}" = set; then + enableval="$enable_gcc_pipe" + +fi; + +# Check whether --enable-gcc-opt or --disable-gcc-opt was given. +if test "${enable_gcc_opt+set}" = set; then + enableval="$enable_gcc_opt" + +fi; + +# Check whether --enable-cpu-clip or --disable-cpu-clip was given. +if test "${enable_cpu_clip+set}" = set; then + enableval="$enable_cpu_clip" + +fi; + +# Check whether --enable-bow-docs or --disable-bow-docs was given. +if test "${enable_bow_docs+set}" = set; then + enableval="$enable_bow_docs" + +fi; + +# Check whether --enable-sqlite or --disable-sqlite was given. +if test "${enable_sqlite+set}" = set; then + enableval="$enable_sqlite" + +fi; + +# Check whether --enable-flac or --disable-flac was given. +if test "${enable_flac+set}" = set; then + enableval="$enable_flac" + +fi; + +# Check whether --enable-alsa or --disable-alsa was given. +if test "${enable_alsa+set}" = set; then + enableval="$enable_alsa" + +fi; + +#==================================================================================== +# Check types and their sizes. + +echo "$as_me:$LINENO: checking for short" >&5 +echo $ECHO_N "checking for short... $ECHO_C" >&6 +if test "${ac_cv_type_short+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +if ((short *) 0) + return 0; +if (sizeof (short)) + return 0; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_type_short=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_type_short=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: $ac_cv_type_short" >&5 +echo "${ECHO_T}$ac_cv_type_short" >&6 + +echo "$as_me:$LINENO: checking size of short" >&5 +echo $ECHO_N "checking size of short... $ECHO_C" >&6 +if test "${ac_cv_sizeof_short+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test "$ac_cv_type_short" = yes; then + # The cast to unsigned long works around a bug in the HP C Compiler + # version HP92453-01 B.11.11.23709.GP, which incorrectly rejects + # declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'. + # This bug is HP SR number 8606223364. + if test "$cross_compiling" = yes; then + # Depending upon the size, compute the lo and hi bounds. +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (short))) >= 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=0 ac_mid=0 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (short))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr $ac_mid + 1` + if test $ac_lo -le $ac_mid; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (short))) < 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=-1 ac_mid=-1 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (short))) >= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_hi=`expr '(' $ac_mid ')' - 1` + if test $ac_mid -le $ac_hi; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo= ac_hi= +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +# Binary search between lo and hi bounds. +while test "x$ac_lo" != "x$ac_hi"; do + ac_mid=`expr '(' $ac_hi - $ac_lo ')' / 2 + $ac_lo` + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (short))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr '(' $ac_mid ')' + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +done +case $ac_lo in +?*) ac_cv_sizeof_short=$ac_lo;; +'') { { echo "$as_me:$LINENO: error: cannot compute sizeof (short), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (short), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } ;; +esac +else + if test "$cross_compiling" = yes; then + { { echo "$as_me:$LINENO: error: cannot run test program while cross compiling +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot run test program while cross compiling +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +long longval () { return (long) (sizeof (short)); } +unsigned long ulongval () { return (long) (sizeof (short)); } +#include +#include +int +main () +{ + + FILE *f = fopen ("conftest.val", "w"); + if (! f) + exit (1); + if (((long) (sizeof (short))) < 0) + { + long i = longval (); + if (i != ((long) (sizeof (short)))) + exit (1); + fprintf (f, "%ld\n", i); + } + else + { + unsigned long i = ulongval (); + if (i != ((long) (sizeof (short)))) + exit (1); + fprintf (f, "%lu\n", i); + } + exit (ferror (f) || fclose (f) != 0); + + ; + return 0; +} +_ACEOF +rm -f conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && { ac_try='./conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_sizeof_short=`cat conftest.val` +else + echo "$as_me: program exited with status $ac_status" >&5 +echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +( exit $ac_status ) +{ { echo "$as_me:$LINENO: error: cannot compute sizeof (short), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (short), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +fi +rm -f core *.core gmon.out bb.out conftest$ac_exeext conftest.$ac_objext conftest.$ac_ext +fi +fi +rm -f conftest.val +else + ac_cv_sizeof_short=0 +fi +fi +echo "$as_me:$LINENO: result: $ac_cv_sizeof_short" >&5 +echo "${ECHO_T}$ac_cv_sizeof_short" >&6 +cat >>confdefs.h <<_ACEOF +#define SIZEOF_SHORT $ac_cv_sizeof_short +_ACEOF + + +echo "$as_me:$LINENO: checking for int" >&5 +echo $ECHO_N "checking for int... $ECHO_C" >&6 +if test "${ac_cv_type_int+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +if ((int *) 0) + return 0; +if (sizeof (int)) + return 0; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_type_int=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_type_int=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: $ac_cv_type_int" >&5 +echo "${ECHO_T}$ac_cv_type_int" >&6 + +echo "$as_me:$LINENO: checking size of int" >&5 +echo $ECHO_N "checking size of int... $ECHO_C" >&6 +if test "${ac_cv_sizeof_int+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test "$ac_cv_type_int" = yes; then + # The cast to unsigned long works around a bug in the HP C Compiler + # version HP92453-01 B.11.11.23709.GP, which incorrectly rejects + # declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'. + # This bug is HP SR number 8606223364. + if test "$cross_compiling" = yes; then + # Depending upon the size, compute the lo and hi bounds. +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (int))) >= 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=0 ac_mid=0 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (int))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr $ac_mid + 1` + if test $ac_lo -le $ac_mid; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (int))) < 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=-1 ac_mid=-1 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (int))) >= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_hi=`expr '(' $ac_mid ')' - 1` + if test $ac_mid -le $ac_hi; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo= ac_hi= +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +# Binary search between lo and hi bounds. +while test "x$ac_lo" != "x$ac_hi"; do + ac_mid=`expr '(' $ac_hi - $ac_lo ')' / 2 + $ac_lo` + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (int))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr '(' $ac_mid ')' + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +done +case $ac_lo in +?*) ac_cv_sizeof_int=$ac_lo;; +'') { { echo "$as_me:$LINENO: error: cannot compute sizeof (int), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (int), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } ;; +esac +else + if test "$cross_compiling" = yes; then + { { echo "$as_me:$LINENO: error: cannot run test program while cross compiling +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot run test program while cross compiling +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +long longval () { return (long) (sizeof (int)); } +unsigned long ulongval () { return (long) (sizeof (int)); } +#include +#include +int +main () +{ + + FILE *f = fopen ("conftest.val", "w"); + if (! f) + exit (1); + if (((long) (sizeof (int))) < 0) + { + long i = longval (); + if (i != ((long) (sizeof (int)))) + exit (1); + fprintf (f, "%ld\n", i); + } + else + { + unsigned long i = ulongval (); + if (i != ((long) (sizeof (int)))) + exit (1); + fprintf (f, "%lu\n", i); + } + exit (ferror (f) || fclose (f) != 0); + + ; + return 0; +} +_ACEOF +rm -f conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && { ac_try='./conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_sizeof_int=`cat conftest.val` +else + echo "$as_me: program exited with status $ac_status" >&5 +echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +( exit $ac_status ) +{ { echo "$as_me:$LINENO: error: cannot compute sizeof (int), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (int), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +fi +rm -f core *.core gmon.out bb.out conftest$ac_exeext conftest.$ac_objext conftest.$ac_ext +fi +fi +rm -f conftest.val +else + ac_cv_sizeof_int=0 +fi +fi +echo "$as_me:$LINENO: result: $ac_cv_sizeof_int" >&5 +echo "${ECHO_T}$ac_cv_sizeof_int" >&6 +cat >>confdefs.h <<_ACEOF +#define SIZEOF_INT $ac_cv_sizeof_int +_ACEOF + + +echo "$as_me:$LINENO: checking for long" >&5 +echo $ECHO_N "checking for long... $ECHO_C" >&6 +if test "${ac_cv_type_long+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +if ((long *) 0) + return 0; +if (sizeof (long)) + return 0; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_type_long=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_type_long=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: $ac_cv_type_long" >&5 +echo "${ECHO_T}$ac_cv_type_long" >&6 + +echo "$as_me:$LINENO: checking size of long" >&5 +echo $ECHO_N "checking size of long... $ECHO_C" >&6 +if test "${ac_cv_sizeof_long+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test "$ac_cv_type_long" = yes; then + # The cast to unsigned long works around a bug in the HP C Compiler + # version HP92453-01 B.11.11.23709.GP, which incorrectly rejects + # declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'. + # This bug is HP SR number 8606223364. + if test "$cross_compiling" = yes; then + # Depending upon the size, compute the lo and hi bounds. +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (long))) >= 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=0 ac_mid=0 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (long))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr $ac_mid + 1` + if test $ac_lo -le $ac_mid; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (long))) < 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=-1 ac_mid=-1 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (long))) >= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_hi=`expr '(' $ac_mid ')' - 1` + if test $ac_mid -le $ac_hi; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo= ac_hi= +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +# Binary search between lo and hi bounds. +while test "x$ac_lo" != "x$ac_hi"; do + ac_mid=`expr '(' $ac_hi - $ac_lo ')' / 2 + $ac_lo` + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (long))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr '(' $ac_mid ')' + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +done +case $ac_lo in +?*) ac_cv_sizeof_long=$ac_lo;; +'') { { echo "$as_me:$LINENO: error: cannot compute sizeof (long), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (long), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } ;; +esac +else + if test "$cross_compiling" = yes; then + { { echo "$as_me:$LINENO: error: cannot run test program while cross compiling +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot run test program while cross compiling +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +long longval () { return (long) (sizeof (long)); } +unsigned long ulongval () { return (long) (sizeof (long)); } +#include +#include +int +main () +{ + + FILE *f = fopen ("conftest.val", "w"); + if (! f) + exit (1); + if (((long) (sizeof (long))) < 0) + { + long i = longval (); + if (i != ((long) (sizeof (long)))) + exit (1); + fprintf (f, "%ld\n", i); + } + else + { + unsigned long i = ulongval (); + if (i != ((long) (sizeof (long)))) + exit (1); + fprintf (f, "%lu\n", i); + } + exit (ferror (f) || fclose (f) != 0); + + ; + return 0; +} +_ACEOF +rm -f conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && { ac_try='./conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_sizeof_long=`cat conftest.val` +else + echo "$as_me: program exited with status $ac_status" >&5 +echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +( exit $ac_status ) +{ { echo "$as_me:$LINENO: error: cannot compute sizeof (long), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (long), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +fi +rm -f core *.core gmon.out bb.out conftest$ac_exeext conftest.$ac_objext conftest.$ac_ext +fi +fi +rm -f conftest.val +else + ac_cv_sizeof_long=0 +fi +fi +echo "$as_me:$LINENO: result: $ac_cv_sizeof_long" >&5 +echo "${ECHO_T}$ac_cv_sizeof_long" >&6 +cat >>confdefs.h <<_ACEOF +#define SIZEOF_LONG $ac_cv_sizeof_long +_ACEOF + + +echo "$as_me:$LINENO: checking for float" >&5 +echo $ECHO_N "checking for float... $ECHO_C" >&6 +if test "${ac_cv_type_float+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +if ((float *) 0) + return 0; +if (sizeof (float)) + return 0; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_type_float=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_type_float=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: $ac_cv_type_float" >&5 +echo "${ECHO_T}$ac_cv_type_float" >&6 + +echo "$as_me:$LINENO: checking size of float" >&5 +echo $ECHO_N "checking size of float... $ECHO_C" >&6 +if test "${ac_cv_sizeof_float+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test "$ac_cv_type_float" = yes; then + # The cast to unsigned long works around a bug in the HP C Compiler + # version HP92453-01 B.11.11.23709.GP, which incorrectly rejects + # declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'. + # This bug is HP SR number 8606223364. + if test "$cross_compiling" = yes; then + # Depending upon the size, compute the lo and hi bounds. +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (float))) >= 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=0 ac_mid=0 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (float))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr $ac_mid + 1` + if test $ac_lo -le $ac_mid; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (float))) < 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=-1 ac_mid=-1 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (float))) >= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_hi=`expr '(' $ac_mid ')' - 1` + if test $ac_mid -le $ac_hi; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo= ac_hi= +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +# Binary search between lo and hi bounds. +while test "x$ac_lo" != "x$ac_hi"; do + ac_mid=`expr '(' $ac_hi - $ac_lo ')' / 2 + $ac_lo` + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (float))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr '(' $ac_mid ')' + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +done +case $ac_lo in +?*) ac_cv_sizeof_float=$ac_lo;; +'') { { echo "$as_me:$LINENO: error: cannot compute sizeof (float), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (float), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } ;; +esac +else + if test "$cross_compiling" = yes; then + { { echo "$as_me:$LINENO: error: cannot run test program while cross compiling +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot run test program while cross compiling +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +long longval () { return (long) (sizeof (float)); } +unsigned long ulongval () { return (long) (sizeof (float)); } +#include +#include +int +main () +{ + + FILE *f = fopen ("conftest.val", "w"); + if (! f) + exit (1); + if (((long) (sizeof (float))) < 0) + { + long i = longval (); + if (i != ((long) (sizeof (float)))) + exit (1); + fprintf (f, "%ld\n", i); + } + else + { + unsigned long i = ulongval (); + if (i != ((long) (sizeof (float)))) + exit (1); + fprintf (f, "%lu\n", i); + } + exit (ferror (f) || fclose (f) != 0); + + ; + return 0; +} +_ACEOF +rm -f conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && { ac_try='./conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_sizeof_float=`cat conftest.val` +else + echo "$as_me: program exited with status $ac_status" >&5 +echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +( exit $ac_status ) +{ { echo "$as_me:$LINENO: error: cannot compute sizeof (float), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (float), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +fi +rm -f core *.core gmon.out bb.out conftest$ac_exeext conftest.$ac_objext conftest.$ac_ext +fi +fi +rm -f conftest.val +else + ac_cv_sizeof_float=0 +fi +fi +echo "$as_me:$LINENO: result: $ac_cv_sizeof_float" >&5 +echo "${ECHO_T}$ac_cv_sizeof_float" >&6 +cat >>confdefs.h <<_ACEOF +#define SIZEOF_FLOAT $ac_cv_sizeof_float +_ACEOF + + +echo "$as_me:$LINENO: checking for double" >&5 +echo $ECHO_N "checking for double... $ECHO_C" >&6 +if test "${ac_cv_type_double+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +if ((double *) 0) + return 0; +if (sizeof (double)) + return 0; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_type_double=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_type_double=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: $ac_cv_type_double" >&5 +echo "${ECHO_T}$ac_cv_type_double" >&6 + +echo "$as_me:$LINENO: checking size of double" >&5 +echo $ECHO_N "checking size of double... $ECHO_C" >&6 +if test "${ac_cv_sizeof_double+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test "$ac_cv_type_double" = yes; then + # The cast to unsigned long works around a bug in the HP C Compiler + # version HP92453-01 B.11.11.23709.GP, which incorrectly rejects + # declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'. + # This bug is HP SR number 8606223364. + if test "$cross_compiling" = yes; then + # Depending upon the size, compute the lo and hi bounds. +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (double))) >= 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=0 ac_mid=0 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (double))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr $ac_mid + 1` + if test $ac_lo -le $ac_mid; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (double))) < 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=-1 ac_mid=-1 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (double))) >= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_hi=`expr '(' $ac_mid ')' - 1` + if test $ac_mid -le $ac_hi; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo= ac_hi= +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +# Binary search between lo and hi bounds. +while test "x$ac_lo" != "x$ac_hi"; do + ac_mid=`expr '(' $ac_hi - $ac_lo ')' / 2 + $ac_lo` + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (double))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr '(' $ac_mid ')' + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +done +case $ac_lo in +?*) ac_cv_sizeof_double=$ac_lo;; +'') { { echo "$as_me:$LINENO: error: cannot compute sizeof (double), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (double), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } ;; +esac +else + if test "$cross_compiling" = yes; then + { { echo "$as_me:$LINENO: error: cannot run test program while cross compiling +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot run test program while cross compiling +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +long longval () { return (long) (sizeof (double)); } +unsigned long ulongval () { return (long) (sizeof (double)); } +#include +#include +int +main () +{ + + FILE *f = fopen ("conftest.val", "w"); + if (! f) + exit (1); + if (((long) (sizeof (double))) < 0) + { + long i = longval (); + if (i != ((long) (sizeof (double)))) + exit (1); + fprintf (f, "%ld\n", i); + } + else + { + unsigned long i = ulongval (); + if (i != ((long) (sizeof (double)))) + exit (1); + fprintf (f, "%lu\n", i); + } + exit (ferror (f) || fclose (f) != 0); + + ; + return 0; +} +_ACEOF +rm -f conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && { ac_try='./conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_sizeof_double=`cat conftest.val` +else + echo "$as_me: program exited with status $ac_status" >&5 +echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +( exit $ac_status ) +{ { echo "$as_me:$LINENO: error: cannot compute sizeof (double), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (double), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +fi +rm -f core *.core gmon.out bb.out conftest$ac_exeext conftest.$ac_objext conftest.$ac_ext +fi +fi +rm -f conftest.val +else + ac_cv_sizeof_double=0 +fi +fi +echo "$as_me:$LINENO: result: $ac_cv_sizeof_double" >&5 +echo "${ECHO_T}$ac_cv_sizeof_double" >&6 +cat >>confdefs.h <<_ACEOF +#define SIZEOF_DOUBLE $ac_cv_sizeof_double +_ACEOF + + +echo "$as_me:$LINENO: checking for void*" >&5 +echo $ECHO_N "checking for void*... $ECHO_C" >&6 +if test "${ac_cv_type_voidp+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +if ((void* *) 0) + return 0; +if (sizeof (void*)) + return 0; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_type_voidp=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_type_voidp=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: $ac_cv_type_voidp" >&5 +echo "${ECHO_T}$ac_cv_type_voidp" >&6 + +echo "$as_me:$LINENO: checking size of void*" >&5 +echo $ECHO_N "checking size of void*... $ECHO_C" >&6 +if test "${ac_cv_sizeof_voidp+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test "$ac_cv_type_voidp" = yes; then + # The cast to unsigned long works around a bug in the HP C Compiler + # version HP92453-01 B.11.11.23709.GP, which incorrectly rejects + # declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'. + # This bug is HP SR number 8606223364. + if test "$cross_compiling" = yes; then + # Depending upon the size, compute the lo and hi bounds. +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (void*))) >= 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=0 ac_mid=0 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (void*))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr $ac_mid + 1` + if test $ac_lo -le $ac_mid; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (void*))) < 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=-1 ac_mid=-1 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (void*))) >= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_hi=`expr '(' $ac_mid ')' - 1` + if test $ac_mid -le $ac_hi; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo= ac_hi= +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +# Binary search between lo and hi bounds. +while test "x$ac_lo" != "x$ac_hi"; do + ac_mid=`expr '(' $ac_hi - $ac_lo ')' / 2 + $ac_lo` + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (void*))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr '(' $ac_mid ')' + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +done +case $ac_lo in +?*) ac_cv_sizeof_voidp=$ac_lo;; +'') { { echo "$as_me:$LINENO: error: cannot compute sizeof (void*), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (void*), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } ;; +esac +else + if test "$cross_compiling" = yes; then + { { echo "$as_me:$LINENO: error: cannot run test program while cross compiling +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot run test program while cross compiling +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +long longval () { return (long) (sizeof (void*)); } +unsigned long ulongval () { return (long) (sizeof (void*)); } +#include +#include +int +main () +{ + + FILE *f = fopen ("conftest.val", "w"); + if (! f) + exit (1); + if (((long) (sizeof (void*))) < 0) + { + long i = longval (); + if (i != ((long) (sizeof (void*)))) + exit (1); + fprintf (f, "%ld\n", i); + } + else + { + unsigned long i = ulongval (); + if (i != ((long) (sizeof (void*)))) + exit (1); + fprintf (f, "%lu\n", i); + } + exit (ferror (f) || fclose (f) != 0); + + ; + return 0; +} +_ACEOF +rm -f conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && { ac_try='./conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_sizeof_voidp=`cat conftest.val` +else + echo "$as_me: program exited with status $ac_status" >&5 +echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +( exit $ac_status ) +{ { echo "$as_me:$LINENO: error: cannot compute sizeof (void*), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (void*), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +fi +rm -f core *.core gmon.out bb.out conftest$ac_exeext conftest.$ac_objext conftest.$ac_ext +fi +fi +rm -f conftest.val +else + ac_cv_sizeof_voidp=0 +fi +fi +echo "$as_me:$LINENO: result: $ac_cv_sizeof_voidp" >&5 +echo "${ECHO_T}$ac_cv_sizeof_voidp" >&6 +cat >>confdefs.h <<_ACEOF +#define SIZEOF_VOIDP $ac_cv_sizeof_voidp +_ACEOF + + +echo "$as_me:$LINENO: checking for size_t" >&5 +echo $ECHO_N "checking for size_t... $ECHO_C" >&6 +if test "${ac_cv_type_size_t+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +if ((size_t *) 0) + return 0; +if (sizeof (size_t)) + return 0; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_type_size_t=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_type_size_t=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: $ac_cv_type_size_t" >&5 +echo "${ECHO_T}$ac_cv_type_size_t" >&6 + +echo "$as_me:$LINENO: checking size of size_t" >&5 +echo $ECHO_N "checking size of size_t... $ECHO_C" >&6 +if test "${ac_cv_sizeof_size_t+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test "$ac_cv_type_size_t" = yes; then + # The cast to unsigned long works around a bug in the HP C Compiler + # version HP92453-01 B.11.11.23709.GP, which incorrectly rejects + # declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'. + # This bug is HP SR number 8606223364. + if test "$cross_compiling" = yes; then + # Depending upon the size, compute the lo and hi bounds. +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (size_t))) >= 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=0 ac_mid=0 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (size_t))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr $ac_mid + 1` + if test $ac_lo -le $ac_mid; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (size_t))) < 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=-1 ac_mid=-1 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (size_t))) >= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_hi=`expr '(' $ac_mid ')' - 1` + if test $ac_mid -le $ac_hi; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo= ac_hi= +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +# Binary search between lo and hi bounds. +while test "x$ac_lo" != "x$ac_hi"; do + ac_mid=`expr '(' $ac_hi - $ac_lo ')' / 2 + $ac_lo` + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (size_t))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr '(' $ac_mid ')' + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +done +case $ac_lo in +?*) ac_cv_sizeof_size_t=$ac_lo;; +'') { { echo "$as_me:$LINENO: error: cannot compute sizeof (size_t), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (size_t), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } ;; +esac +else + if test "$cross_compiling" = yes; then + { { echo "$as_me:$LINENO: error: cannot run test program while cross compiling +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot run test program while cross compiling +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +long longval () { return (long) (sizeof (size_t)); } +unsigned long ulongval () { return (long) (sizeof (size_t)); } +#include +#include +int +main () +{ + + FILE *f = fopen ("conftest.val", "w"); + if (! f) + exit (1); + if (((long) (sizeof (size_t))) < 0) + { + long i = longval (); + if (i != ((long) (sizeof (size_t)))) + exit (1); + fprintf (f, "%ld\n", i); + } + else + { + unsigned long i = ulongval (); + if (i != ((long) (sizeof (size_t)))) + exit (1); + fprintf (f, "%lu\n", i); + } + exit (ferror (f) || fclose (f) != 0); + + ; + return 0; +} +_ACEOF +rm -f conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && { ac_try='./conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_sizeof_size_t=`cat conftest.val` +else + echo "$as_me: program exited with status $ac_status" >&5 +echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +( exit $ac_status ) +{ { echo "$as_me:$LINENO: error: cannot compute sizeof (size_t), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (size_t), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +fi +rm -f core *.core gmon.out bb.out conftest$ac_exeext conftest.$ac_objext conftest.$ac_ext +fi +fi +rm -f conftest.val +else + ac_cv_sizeof_size_t=0 +fi +fi +echo "$as_me:$LINENO: result: $ac_cv_sizeof_size_t" >&5 +echo "${ECHO_T}$ac_cv_sizeof_size_t" >&6 +cat >>confdefs.h <<_ACEOF +#define SIZEOF_SIZE_T $ac_cv_sizeof_size_t +_ACEOF + + +echo "$as_me:$LINENO: checking for int64_t" >&5 +echo $ECHO_N "checking for int64_t... $ECHO_C" >&6 +if test "${ac_cv_type_int64_t+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +if ((int64_t *) 0) + return 0; +if (sizeof (int64_t)) + return 0; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_type_int64_t=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_type_int64_t=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: $ac_cv_type_int64_t" >&5 +echo "${ECHO_T}$ac_cv_type_int64_t" >&6 + +echo "$as_me:$LINENO: checking size of int64_t" >&5 +echo $ECHO_N "checking size of int64_t... $ECHO_C" >&6 +if test "${ac_cv_sizeof_int64_t+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test "$ac_cv_type_int64_t" = yes; then + # The cast to unsigned long works around a bug in the HP C Compiler + # version HP92453-01 B.11.11.23709.GP, which incorrectly rejects + # declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'. + # This bug is HP SR number 8606223364. + if test "$cross_compiling" = yes; then + # Depending upon the size, compute the lo and hi bounds. +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (int64_t))) >= 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=0 ac_mid=0 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (int64_t))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr $ac_mid + 1` + if test $ac_lo -le $ac_mid; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (int64_t))) < 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=-1 ac_mid=-1 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (int64_t))) >= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_hi=`expr '(' $ac_mid ')' - 1` + if test $ac_mid -le $ac_hi; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo= ac_hi= +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +# Binary search between lo and hi bounds. +while test "x$ac_lo" != "x$ac_hi"; do + ac_mid=`expr '(' $ac_hi - $ac_lo ')' / 2 + $ac_lo` + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (int64_t))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr '(' $ac_mid ')' + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +done +case $ac_lo in +?*) ac_cv_sizeof_int64_t=$ac_lo;; +'') { { echo "$as_me:$LINENO: error: cannot compute sizeof (int64_t), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (int64_t), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } ;; +esac +else + if test "$cross_compiling" = yes; then + { { echo "$as_me:$LINENO: error: cannot run test program while cross compiling +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot run test program while cross compiling +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +long longval () { return (long) (sizeof (int64_t)); } +unsigned long ulongval () { return (long) (sizeof (int64_t)); } +#include +#include +int +main () +{ + + FILE *f = fopen ("conftest.val", "w"); + if (! f) + exit (1); + if (((long) (sizeof (int64_t))) < 0) + { + long i = longval (); + if (i != ((long) (sizeof (int64_t)))) + exit (1); + fprintf (f, "%ld\n", i); + } + else + { + unsigned long i = ulongval (); + if (i != ((long) (sizeof (int64_t)))) + exit (1); + fprintf (f, "%lu\n", i); + } + exit (ferror (f) || fclose (f) != 0); + + ; + return 0; +} +_ACEOF +rm -f conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && { ac_try='./conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_sizeof_int64_t=`cat conftest.val` +else + echo "$as_me: program exited with status $ac_status" >&5 +echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +( exit $ac_status ) +{ { echo "$as_me:$LINENO: error: cannot compute sizeof (int64_t), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (int64_t), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +fi +rm -f core *.core gmon.out bb.out conftest$ac_exeext conftest.$ac_objext conftest.$ac_ext +fi +fi +rm -f conftest.val +else + ac_cv_sizeof_int64_t=0 +fi +fi +echo "$as_me:$LINENO: result: $ac_cv_sizeof_int64_t" >&5 +echo "${ECHO_T}$ac_cv_sizeof_int64_t" >&6 +cat >>confdefs.h <<_ACEOF +#define SIZEOF_INT64_T $ac_cv_sizeof_int64_t +_ACEOF + + +echo "$as_me:$LINENO: checking for long long" >&5 +echo $ECHO_N "checking for long long... $ECHO_C" >&6 +if test "${ac_cv_type_long_long+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +if ((long long *) 0) + return 0; +if (sizeof (long long)) + return 0; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_type_long_long=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_type_long_long=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: $ac_cv_type_long_long" >&5 +echo "${ECHO_T}$ac_cv_type_long_long" >&6 + +echo "$as_me:$LINENO: checking size of long long" >&5 +echo $ECHO_N "checking size of long long... $ECHO_C" >&6 +if test "${ac_cv_sizeof_long_long+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test "$ac_cv_type_long_long" = yes; then + # The cast to unsigned long works around a bug in the HP C Compiler + # version HP92453-01 B.11.11.23709.GP, which incorrectly rejects + # declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'. + # This bug is HP SR number 8606223364. + if test "$cross_compiling" = yes; then + # Depending upon the size, compute the lo and hi bounds. +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (long long))) >= 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=0 ac_mid=0 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (long long))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr $ac_mid + 1` + if test $ac_lo -le $ac_mid; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (long long))) < 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=-1 ac_mid=-1 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (long long))) >= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_hi=`expr '(' $ac_mid ')' - 1` + if test $ac_mid -le $ac_hi; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo= ac_hi= +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +# Binary search between lo and hi bounds. +while test "x$ac_lo" != "x$ac_hi"; do + ac_mid=`expr '(' $ac_hi - $ac_lo ')' / 2 + $ac_lo` + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (long long))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr '(' $ac_mid ')' + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +done +case $ac_lo in +?*) ac_cv_sizeof_long_long=$ac_lo;; +'') { { echo "$as_me:$LINENO: error: cannot compute sizeof (long long), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (long long), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } ;; +esac +else + if test "$cross_compiling" = yes; then + { { echo "$as_me:$LINENO: error: cannot run test program while cross compiling +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot run test program while cross compiling +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +long longval () { return (long) (sizeof (long long)); } +unsigned long ulongval () { return (long) (sizeof (long long)); } +#include +#include +int +main () +{ + + FILE *f = fopen ("conftest.val", "w"); + if (! f) + exit (1); + if (((long) (sizeof (long long))) < 0) + { + long i = longval (); + if (i != ((long) (sizeof (long long)))) + exit (1); + fprintf (f, "%ld\n", i); + } + else + { + unsigned long i = ulongval (); + if (i != ((long) (sizeof (long long)))) + exit (1); + fprintf (f, "%lu\n", i); + } + exit (ferror (f) || fclose (f) != 0); + + ; + return 0; +} +_ACEOF +rm -f conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && { ac_try='./conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_sizeof_long_long=`cat conftest.val` +else + echo "$as_me: program exited with status $ac_status" >&5 +echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +( exit $ac_status ) +{ { echo "$as_me:$LINENO: error: cannot compute sizeof (long long), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (long long), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +fi +rm -f core *.core gmon.out bb.out conftest$ac_exeext conftest.$ac_objext conftest.$ac_ext +fi +fi +rm -f conftest.val +else + ac_cv_sizeof_long_long=0 +fi +fi +echo "$as_me:$LINENO: result: $ac_cv_sizeof_long_long" >&5 +echo "${ECHO_T}$ac_cv_sizeof_long_long" >&6 +cat >>confdefs.h <<_ACEOF +#define SIZEOF_LONG_LONG $ac_cv_sizeof_long_long +_ACEOF + + + +#==================================================================================== +# Find an appropriate type for sf_count_t. +# On systems supporting files larger than 2 Gig, sf_count_t must be a 64 bit value. +# Unfortunately there is more than one way of ensuring this so need to do some +# pretty rigourous testing here. + +unset ac_cv_sizeof_off_t + +echo "$as_me:$LINENO: checking for off_t" >&5 +echo $ECHO_N "checking for off_t... $ECHO_C" >&6 +if test "${ac_cv_type_off_t+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +if ((off_t *) 0) + return 0; +if (sizeof (off_t)) + return 0; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_type_off_t=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_type_off_t=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: $ac_cv_type_off_t" >&5 +echo "${ECHO_T}$ac_cv_type_off_t" >&6 + +echo "$as_me:$LINENO: checking size of off_t" >&5 +echo $ECHO_N "checking size of off_t... $ECHO_C" >&6 +if test "${ac_cv_sizeof_off_t+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test "$ac_cv_type_off_t" = yes; then + # The cast to unsigned long works around a bug in the HP C Compiler + # version HP92453-01 B.11.11.23709.GP, which incorrectly rejects + # declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'. + # This bug is HP SR number 8606223364. + if test "$cross_compiling" = yes; then + # Depending upon the size, compute the lo and hi bounds. +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (off_t))) >= 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=0 ac_mid=0 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (off_t))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr $ac_mid + 1` + if test $ac_lo -le $ac_mid; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (off_t))) < 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=-1 ac_mid=-1 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (off_t))) >= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_hi=`expr '(' $ac_mid ')' - 1` + if test $ac_mid -le $ac_hi; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo= ac_hi= +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +# Binary search between lo and hi bounds. +while test "x$ac_lo" != "x$ac_hi"; do + ac_mid=`expr '(' $ac_hi - $ac_lo ')' / 2 + $ac_lo` + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (off_t))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr '(' $ac_mid ')' + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +done +case $ac_lo in +?*) ac_cv_sizeof_off_t=$ac_lo;; +'') { { echo "$as_me:$LINENO: error: cannot compute sizeof (off_t), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (off_t), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } ;; +esac +else + if test "$cross_compiling" = yes; then + { { echo "$as_me:$LINENO: error: cannot run test program while cross compiling +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot run test program while cross compiling +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +long longval () { return (long) (sizeof (off_t)); } +unsigned long ulongval () { return (long) (sizeof (off_t)); } +#include +#include +int +main () +{ + + FILE *f = fopen ("conftest.val", "w"); + if (! f) + exit (1); + if (((long) (sizeof (off_t))) < 0) + { + long i = longval (); + if (i != ((long) (sizeof (off_t)))) + exit (1); + fprintf (f, "%ld\n", i); + } + else + { + unsigned long i = ulongval (); + if (i != ((long) (sizeof (off_t)))) + exit (1); + fprintf (f, "%lu\n", i); + } + exit (ferror (f) || fclose (f) != 0); + + ; + return 0; +} +_ACEOF +rm -f conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && { ac_try='./conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_sizeof_off_t=`cat conftest.val` +else + echo "$as_me: program exited with status $ac_status" >&5 +echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +( exit $ac_status ) +{ { echo "$as_me:$LINENO: error: cannot compute sizeof (off_t), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (off_t), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +fi +rm -f core *.core gmon.out bb.out conftest$ac_exeext conftest.$ac_objext conftest.$ac_ext +fi +fi +rm -f conftest.val +else + ac_cv_sizeof_off_t=0 +fi +fi +echo "$as_me:$LINENO: result: $ac_cv_sizeof_off_t" >&5 +echo "${ECHO_T}$ac_cv_sizeof_off_t" >&6 +cat >>confdefs.h <<_ACEOF +#define SIZEOF_OFF_T $ac_cv_sizeof_off_t +_ACEOF + + # Fake default value. + +case "$host_os" in + mingw*) + TYPEOF_SF_COUNT_T="__int64" + SF_COUNT_MAX="0x7FFFFFFFFFFFFFFFLL" + SIZEOF_SF_COUNT_T=8 + ;; + *) + if test "x$ac_cv_sizeof_off_t" = "x8" ; then + # If sizeof (off_t) is 8, no further checking is needed. + TYPEOF_SF_COUNT_T="off_t" + SF_COUNT_MAX="0x7FFFFFFFFFFFFFFFLL" + SIZEOF_SF_COUNT_T=8 + else + # Check for common 64 bit file offset types. + echo "$as_me:$LINENO: checking for loff_t" >&5 +echo $ECHO_N "checking for loff_t... $ECHO_C" >&6 +if test "${ac_cv_type_loff_t+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +if ((loff_t *) 0) + return 0; +if (sizeof (loff_t)) + return 0; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_type_loff_t=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_type_loff_t=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: $ac_cv_type_loff_t" >&5 +echo "${ECHO_T}$ac_cv_type_loff_t" >&6 + +echo "$as_me:$LINENO: checking size of loff_t" >&5 +echo $ECHO_N "checking size of loff_t... $ECHO_C" >&6 +if test "${ac_cv_sizeof_loff_t+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test "$ac_cv_type_loff_t" = yes; then + # The cast to unsigned long works around a bug in the HP C Compiler + # version HP92453-01 B.11.11.23709.GP, which incorrectly rejects + # declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'. + # This bug is HP SR number 8606223364. + if test "$cross_compiling" = yes; then + # Depending upon the size, compute the lo and hi bounds. +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (loff_t))) >= 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=0 ac_mid=0 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (loff_t))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr $ac_mid + 1` + if test $ac_lo -le $ac_mid; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (loff_t))) < 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=-1 ac_mid=-1 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (loff_t))) >= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_hi=`expr '(' $ac_mid ')' - 1` + if test $ac_mid -le $ac_hi; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo= ac_hi= +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +# Binary search between lo and hi bounds. +while test "x$ac_lo" != "x$ac_hi"; do + ac_mid=`expr '(' $ac_hi - $ac_lo ')' / 2 + $ac_lo` + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (loff_t))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr '(' $ac_mid ')' + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +done +case $ac_lo in +?*) ac_cv_sizeof_loff_t=$ac_lo;; +'') { { echo "$as_me:$LINENO: error: cannot compute sizeof (loff_t), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (loff_t), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } ;; +esac +else + if test "$cross_compiling" = yes; then + { { echo "$as_me:$LINENO: error: cannot run test program while cross compiling +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot run test program while cross compiling +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +long longval () { return (long) (sizeof (loff_t)); } +unsigned long ulongval () { return (long) (sizeof (loff_t)); } +#include +#include +int +main () +{ + + FILE *f = fopen ("conftest.val", "w"); + if (! f) + exit (1); + if (((long) (sizeof (loff_t))) < 0) + { + long i = longval (); + if (i != ((long) (sizeof (loff_t)))) + exit (1); + fprintf (f, "%ld\n", i); + } + else + { + unsigned long i = ulongval (); + if (i != ((long) (sizeof (loff_t)))) + exit (1); + fprintf (f, "%lu\n", i); + } + exit (ferror (f) || fclose (f) != 0); + + ; + return 0; +} +_ACEOF +rm -f conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && { ac_try='./conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_sizeof_loff_t=`cat conftest.val` +else + echo "$as_me: program exited with status $ac_status" >&5 +echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +( exit $ac_status ) +{ { echo "$as_me:$LINENO: error: cannot compute sizeof (loff_t), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (loff_t), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +fi +rm -f core *.core gmon.out bb.out conftest$ac_exeext conftest.$ac_objext conftest.$ac_ext +fi +fi +rm -f conftest.val +else + ac_cv_sizeof_loff_t=0 +fi +fi +echo "$as_me:$LINENO: result: $ac_cv_sizeof_loff_t" >&5 +echo "${ECHO_T}$ac_cv_sizeof_loff_t" >&6 +cat >>confdefs.h <<_ACEOF +#define SIZEOF_LOFF_T $ac_cv_sizeof_loff_t +_ACEOF + + # Fake default value. + echo "$as_me:$LINENO: checking for off64_t" >&5 +echo $ECHO_N "checking for off64_t... $ECHO_C" >&6 +if test "${ac_cv_type_off64_t+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +if ((off64_t *) 0) + return 0; +if (sizeof (off64_t)) + return 0; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_type_off64_t=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_type_off64_t=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: $ac_cv_type_off64_t" >&5 +echo "${ECHO_T}$ac_cv_type_off64_t" >&6 + +echo "$as_me:$LINENO: checking size of off64_t" >&5 +echo $ECHO_N "checking size of off64_t... $ECHO_C" >&6 +if test "${ac_cv_sizeof_off64_t+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test "$ac_cv_type_off64_t" = yes; then + # The cast to unsigned long works around a bug in the HP C Compiler + # version HP92453-01 B.11.11.23709.GP, which incorrectly rejects + # declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'. + # This bug is HP SR number 8606223364. + if test "$cross_compiling" = yes; then + # Depending upon the size, compute the lo and hi bounds. +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (off64_t))) >= 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=0 ac_mid=0 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (off64_t))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr $ac_mid + 1` + if test $ac_lo -le $ac_mid; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (off64_t))) < 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=-1 ac_mid=-1 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (off64_t))) >= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_hi=`expr '(' $ac_mid ')' - 1` + if test $ac_mid -le $ac_hi; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo= ac_hi= +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +# Binary search between lo and hi bounds. +while test "x$ac_lo" != "x$ac_hi"; do + ac_mid=`expr '(' $ac_hi - $ac_lo ')' / 2 + $ac_lo` + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (off64_t))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr '(' $ac_mid ')' + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +done +case $ac_lo in +?*) ac_cv_sizeof_off64_t=$ac_lo;; +'') { { echo "$as_me:$LINENO: error: cannot compute sizeof (off64_t), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (off64_t), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } ;; +esac +else + if test "$cross_compiling" = yes; then + { { echo "$as_me:$LINENO: error: cannot run test program while cross compiling +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot run test program while cross compiling +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +long longval () { return (long) (sizeof (off64_t)); } +unsigned long ulongval () { return (long) (sizeof (off64_t)); } +#include +#include +int +main () +{ + + FILE *f = fopen ("conftest.val", "w"); + if (! f) + exit (1); + if (((long) (sizeof (off64_t))) < 0) + { + long i = longval (); + if (i != ((long) (sizeof (off64_t)))) + exit (1); + fprintf (f, "%ld\n", i); + } + else + { + unsigned long i = ulongval (); + if (i != ((long) (sizeof (off64_t)))) + exit (1); + fprintf (f, "%lu\n", i); + } + exit (ferror (f) || fclose (f) != 0); + + ; + return 0; +} +_ACEOF +rm -f conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && { ac_try='./conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_sizeof_off64_t=`cat conftest.val` +else + echo "$as_me: program exited with status $ac_status" >&5 +echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +( exit $ac_status ) +{ { echo "$as_me:$LINENO: error: cannot compute sizeof (off64_t), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (off64_t), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +fi +rm -f core *.core gmon.out bb.out conftest$ac_exeext conftest.$ac_objext conftest.$ac_ext +fi +fi +rm -f conftest.val +else + ac_cv_sizeof_off64_t=0 +fi +fi +echo "$as_me:$LINENO: result: $ac_cv_sizeof_off64_t" >&5 +echo "${ECHO_T}$ac_cv_sizeof_off64_t" >&6 +cat >>confdefs.h <<_ACEOF +#define SIZEOF_OFF64_T $ac_cv_sizeof_off64_t +_ACEOF + + # Fake default value. + + TYPEOF_SF_COUNT_T="unknown" + if test "x$ac_cv_sizeof_loff_t" = "x8" ; then + TYPEOF_SF_COUNT_T="loff_t" + SIZEOF_SF_COUNT_T=8 + elif test "x$ac_cv_sizeof_off64_t" = "x8" ; then + TYPEOF_SF_COUNT_T="off64_t" + SIZEOF_SF_COUNT_T=8 + fi + + # Save the old sizeof (off_t) value and then unset it to see if it + # changes when Large File Support is enabled. + + pre_largefile_sizeof_off_t=$ac_cv_sizeof_off_t + unset ac_cv_sizeof_off_t + + + # Check whether --enable-largefile or --disable-largefile was given. +if test "${enable_largefile+set}" = set; then + enableval="$enable_largefile" + +fi; + if test "$enable_largefile" != no; then + if test -n "$ac_tool_prefix"; then + # Extract the first word of "${ac_tool_prefix}getconf", so it can be a program name with args. +set dummy ${ac_tool_prefix}getconf; ac_word=$2 +echo "$as_me:$LINENO: checking for $ac_word" >&5 +echo $ECHO_N "checking for $ac_word... $ECHO_C" >&6 +if test "${ac_cv_prog_GETCONF+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test -n "$GETCONF"; then + ac_cv_prog_GETCONF="$GETCONF" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + for ac_exec_ext in '' $ac_executable_extensions; do + if $as_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_prog_GETCONF="${ac_tool_prefix}getconf" + echo "$as_me:$LINENO: found $as_dir/$ac_word$ac_exec_ext" >&5 + break 2 + fi +done +done + +fi +fi +GETCONF=$ac_cv_prog_GETCONF +if test -n "$GETCONF"; then + echo "$as_me:$LINENO: result: $GETCONF" >&5 +echo "${ECHO_T}$GETCONF" >&6 +else + echo "$as_me:$LINENO: result: no" >&5 +echo "${ECHO_T}no" >&6 +fi + +fi +if test -z "$ac_cv_prog_GETCONF"; then + ac_ct_GETCONF=$GETCONF + # Extract the first word of "getconf", so it can be a program name with args. +set dummy getconf; ac_word=$2 +echo "$as_me:$LINENO: checking for $ac_word" >&5 +echo $ECHO_N "checking for $ac_word... $ECHO_C" >&6 +if test "${ac_cv_prog_ac_ct_GETCONF+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test -n "$ac_ct_GETCONF"; then + ac_cv_prog_ac_ct_GETCONF="$ac_ct_GETCONF" # Let the user override the test. +else +as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + for ac_exec_ext in '' $ac_executable_extensions; do + if $as_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_prog_ac_ct_GETCONF="getconf" + echo "$as_me:$LINENO: found $as_dir/$ac_word$ac_exec_ext" >&5 + break 2 + fi +done +done + +fi +fi +ac_ct_GETCONF=$ac_cv_prog_ac_ct_GETCONF +if test -n "$ac_ct_GETCONF"; then + echo "$as_me:$LINENO: result: $ac_ct_GETCONF" >&5 +echo "${ECHO_T}$ac_ct_GETCONF" >&6 +else + echo "$as_me:$LINENO: result: no" >&5 +echo "${ECHO_T}no" >&6 +fi + + GETCONF=$ac_ct_GETCONF +else + GETCONF="$ac_cv_prog_GETCONF" +fi + + echo "$as_me:$LINENO: checking for CFLAGS value to request large file support" >&5 +echo $ECHO_N "checking for CFLAGS value to request large file support... $ECHO_C" >&6 +if test "${ac_cv_sys_largefile_CFLAGS+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + ac_cv_sys_largefile_CFLAGS=`($GETCONF LFS_CFLAGS) 2>/dev/null` || { + ac_cv_sys_largefile_CFLAGS=no + case "$host_os" in + # IRIX 6.2 and later require cc -n32. + irix6.[2-9]* | irix6.1[0-9]* | irix[7-9].* | irix[1-9][0-9]*) + if test "$GCC" != yes; then + ac_cv_sys_largefile_CFLAGS=-n32 + fi + ac_save_CC="$CC" + CC="$CC $ac_cv_sys_largefile_CFLAGS" + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ + +int +main () +{ + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + : +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_sys_largefile_CFLAGS=no +fi +rm -f conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext + CC="$ac_save_CC" + esac + } +fi +echo "$as_me:$LINENO: result: $ac_cv_sys_largefile_CFLAGS" >&5 +echo "${ECHO_T}$ac_cv_sys_largefile_CFLAGS" >&6 + echo "$as_me:$LINENO: checking for LDFLAGS value to request large file support" >&5 +echo $ECHO_N "checking for LDFLAGS value to request large file support... $ECHO_C" >&6 +if test "${ac_cv_sys_largefile_LDFLAGS+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + ac_cv_sys_largefile_LDFLAGS=`($GETCONF LFS_LDFLAGS) 2>/dev/null` || { + ac_cv_sys_largefile_LDFLAGS=no + + } +fi +echo "$as_me:$LINENO: result: $ac_cv_sys_largefile_LDFLAGS" >&5 +echo "${ECHO_T}$ac_cv_sys_largefile_LDFLAGS" >&6 + echo "$as_me:$LINENO: checking for LIBS value to request large file support" >&5 +echo $ECHO_N "checking for LIBS value to request large file support... $ECHO_C" >&6 +if test "${ac_cv_sys_largefile_LIBS+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + ac_cv_sys_largefile_LIBS=`($GETCONF LFS_LIBS) 2>/dev/null` || { + ac_cv_sys_largefile_LIBS=no + + } +fi +echo "$as_me:$LINENO: result: $ac_cv_sys_largefile_LIBS" >&5 +echo "${ECHO_T}$ac_cv_sys_largefile_LIBS" >&6 + + for ac_flag in $ac_cv_sys_largefile_CFLAGS no; do + case "$ac_flag" in + no) ;; + -D_FILE_OFFSET_BITS=*) ;; + -D_LARGEFILE_SOURCE | -D_LARGEFILE_SOURCE=*) ;; + -D_LARGE_FILES | -D_LARGE_FILES=*) ;; + -D?* | -I?*) + case "$ac_flag" in + no) ;; + ?*) + case "$CPPFLAGS" in + '') CPPFLAGS="$ac_flag" ;; + *) CPPFLAGS=$CPPFLAGS' '"$ac_flag" ;; + esac ;; + esac ;; + *) + case "$ac_flag" in + no) ;; + ?*) + case "$CFLAGS" in + '') CFLAGS="$ac_flag" ;; + *) CFLAGS=$CFLAGS' '"$ac_flag" ;; + esac ;; + esac ;; + esac + done + case "$ac_cv_sys_largefile_LDFLAGS" in + no) ;; + ?*) + case "$LDFLAGS" in + '') LDFLAGS="$ac_cv_sys_largefile_LDFLAGS" ;; + *) LDFLAGS=$LDFLAGS' '"$ac_cv_sys_largefile_LDFLAGS" ;; + esac ;; + esac + case "$ac_cv_sys_largefile_LIBS" in + no) ;; + ?*) + case "$LIBS" in + '') LIBS="$ac_cv_sys_largefile_LIBS" ;; + *) LIBS=$LIBS' '"$ac_cv_sys_largefile_LIBS" ;; + esac ;; + esac + echo "$as_me:$LINENO: checking for _FILE_OFFSET_BITS" >&5 +echo $ECHO_N "checking for _FILE_OFFSET_BITS... $ECHO_C" >&6 +if test "${ac_cv_sys_file_offset_bits+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + ac_cv_sys_file_offset_bits=no + + for ac_flag in $ac_cv_sys_largefile_CFLAGS no; do + case "$ac_flag" in + -D_FILE_OFFSET_BITS) + ac_cv_sys_file_offset_bits=1 ;; + -D_FILE_OFFSET_BITS=*) + ac_cv_sys_file_offset_bits=`expr " $ac_flag" : '[^=]*=\(.*\)'` ;; + esac + done + +fi +echo "$as_me:$LINENO: result: $ac_cv_sys_file_offset_bits" >&5 +echo "${ECHO_T}$ac_cv_sys_file_offset_bits" >&6 + if test "$ac_cv_sys_file_offset_bits" != no; then + +cat >>confdefs.h <<_ACEOF +#define _FILE_OFFSET_BITS $ac_cv_sys_file_offset_bits +_ACEOF + + fi + case "$host_os" in + # HP-UX 10.20 and later + hpux10.[2-9][0-9]* | hpux1[1-9]* | hpux[2-9][0-9]*) + ac_cv_sys_file_offset_bits=64 ;; + esac + echo "$as_me:$LINENO: checking for _LARGEFILE_SOURCE" >&5 +echo $ECHO_N "checking for _LARGEFILE_SOURCE... $ECHO_C" >&6 +if test "${ac_cv_sys_largefile_source+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + ac_cv_sys_largefile_source=no + case "$host_os" in + # HP-UX 10.20 and later + hpux10.[2-9][0-9]* | hpux1[1-9]* | hpux[2-9][0-9]*) + ac_cv_sys_largefile_source=1 ;; + esac + for ac_flag in $ac_cv_sys_largefile_CFLAGS no; do + case "$ac_flag" in + -D_LARGEFILE_SOURCE) + ac_cv_sys_largefile_source=1 ;; + -D_LARGEFILE_SOURCE=*) + ac_cv_sys_largefile_source=`expr " $ac_flag" : '[^=]*=\(.*\)'` ;; + esac + done + +fi +echo "$as_me:$LINENO: result: $ac_cv_sys_largefile_source" >&5 +echo "${ECHO_T}$ac_cv_sys_largefile_source" >&6 + if test "$ac_cv_sys_largefile_source" != no; then + +cat >>confdefs.h <<_ACEOF +#define _LARGEFILE_SOURCE $ac_cv_sys_largefile_source +_ACEOF + + fi + echo "$as_me:$LINENO: checking for _LARGE_FILES" >&5 +echo $ECHO_N "checking for _LARGE_FILES... $ECHO_C" >&6 +if test "${ac_cv_sys_large_files+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + ac_cv_sys_large_files=no + case "$host_os" in + # AIX 4.2 and later + aix4.[2-9]* | aix4.1[0-9]* | aix[5-9].* | aix[1-9][0-9]*) + ac_cv_sys_large_files=1 ;; + esac + for ac_flag in $ac_cv_sys_largefile_CFLAGS no; do + case "$ac_flag" in + -D_LARGE_FILES) + ac_cv_sys_large_files=1 ;; + -D_LARGE_FILES=*) + ac_cv_sys_large_files=`expr " $ac_flag" : '[^=]*=\(.*\)'` ;; + esac + done + +fi +echo "$as_me:$LINENO: result: $ac_cv_sys_large_files" >&5 +echo "${ECHO_T}$ac_cv_sys_large_files" >&6 + if test "$ac_cv_sys_large_files" != no; then + +cat >>confdefs.h <<_ACEOF +#define _LARGE_FILES $ac_cv_sys_large_files +_ACEOF + + fi + fi + + + if test "x$ac_cv_sys_largefile_CFLAGS" = "xno" ; then + ac_cv_sys_largefile_CFLAGS="" + fi + if test "x$ac_cv_sys_largefile_LDFLAGS" = "xno" ; then + ac_cv_sys_largefile_LDFLAGS="" + fi + if test "x$ac_cv_sys_largefile_LIBS" = "xno" ; then + ac_cv_sys_largefile_LIBS="" + fi + + echo "$as_me:$LINENO: checking for off_t" >&5 +echo $ECHO_N "checking for off_t... $ECHO_C" >&6 +if test "${ac_cv_type_off_t+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +if ((off_t *) 0) + return 0; +if (sizeof (off_t)) + return 0; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_type_off_t=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_type_off_t=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: $ac_cv_type_off_t" >&5 +echo "${ECHO_T}$ac_cv_type_off_t" >&6 + +echo "$as_me:$LINENO: checking size of off_t" >&5 +echo $ECHO_N "checking size of off_t... $ECHO_C" >&6 +if test "${ac_cv_sizeof_off_t+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test "$ac_cv_type_off_t" = yes; then + # The cast to unsigned long works around a bug in the HP C Compiler + # version HP92453-01 B.11.11.23709.GP, which incorrectly rejects + # declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'. + # This bug is HP SR number 8606223364. + if test "$cross_compiling" = yes; then + # Depending upon the size, compute the lo and hi bounds. +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (off_t))) >= 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=0 ac_mid=0 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (off_t))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr $ac_mid + 1` + if test $ac_lo -le $ac_mid; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (off_t))) < 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=-1 ac_mid=-1 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (off_t))) >= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_hi=`expr '(' $ac_mid ')' - 1` + if test $ac_mid -le $ac_hi; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo= ac_hi= +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +# Binary search between lo and hi bounds. +while test "x$ac_lo" != "x$ac_hi"; do + ac_mid=`expr '(' $ac_hi - $ac_lo ')' / 2 + $ac_lo` + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (off_t))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr '(' $ac_mid ')' + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +done +case $ac_lo in +?*) ac_cv_sizeof_off_t=$ac_lo;; +'') { { echo "$as_me:$LINENO: error: cannot compute sizeof (off_t), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (off_t), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } ;; +esac +else + if test "$cross_compiling" = yes; then + { { echo "$as_me:$LINENO: error: cannot run test program while cross compiling +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot run test program while cross compiling +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +long longval () { return (long) (sizeof (off_t)); } +unsigned long ulongval () { return (long) (sizeof (off_t)); } +#include +#include +int +main () +{ + + FILE *f = fopen ("conftest.val", "w"); + if (! f) + exit (1); + if (((long) (sizeof (off_t))) < 0) + { + long i = longval (); + if (i != ((long) (sizeof (off_t)))) + exit (1); + fprintf (f, "%ld\n", i); + } + else + { + unsigned long i = ulongval (); + if (i != ((long) (sizeof (off_t)))) + exit (1); + fprintf (f, "%lu\n", i); + } + exit (ferror (f) || fclose (f) != 0); + + ; + return 0; +} +_ACEOF +rm -f conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && { ac_try='./conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_sizeof_off_t=`cat conftest.val` +else + echo "$as_me: program exited with status $ac_status" >&5 +echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +( exit $ac_status ) +{ { echo "$as_me:$LINENO: error: cannot compute sizeof (off_t), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (off_t), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +fi +rm -f core *.core gmon.out bb.out conftest$ac_exeext conftest.$ac_objext conftest.$ac_ext +fi +fi +rm -f conftest.val +else + ac_cv_sizeof_off_t=0 +fi +fi +echo "$as_me:$LINENO: result: $ac_cv_sizeof_off_t" >&5 +echo "${ECHO_T}$ac_cv_sizeof_off_t" >&6 +cat >>confdefs.h <<_ACEOF +#define SIZEOF_OFF_T $ac_cv_sizeof_off_t +_ACEOF + + # Fake default value. + + if test "x$ac_cv_sizeof_off_t" = "x8" ; then + SF_COUNT_MAX="0x7FFFFFFFFFFFFFFFLL" + elif test "x$ac_cv_sizeof_off_t" = "x$pre_largefile_sizeof_off_t" ; then + { echo "$as_me:$LINENO: WARNING: This machine does not seem to support 64 bit file offsets." >&5 +echo "$as_me: WARNING: This machine does not seem to support 64 bit file offsets." >&2;} + TYPEOF_SF_COUNT_T="off_t" + SIZEOF_SF_COUNT_T=$ac_cv_sizeof_off_t + elif test "x$TYPEOF_SF_COUNT_T" = "xunknown" ; then + echo + echo "*** The configure process has determined that this system is capable" + echo "*** of Large File Support but has not been able to find a type which" + echo "*** is an unambiguous 64 bit file offset." + echo "*** Please contact the author to help resolve this problem." + echo + { { echo "$as_me:$LINENO: error: Bad file offset type." >&5 +echo "$as_me: error: Bad file offset type." >&2;} + { (exit 1); exit 1; }; } + fi + fi + ;; + esac + +if test $SIZEOF_SF_COUNT_T = 4 ; then + SF_COUNT_MAX="0x7FFFFFFF" + fi + + +cat >>confdefs.h <<_ACEOF +#define TYPEOF_SF_COUNT_T ${TYPEOF_SF_COUNT_T} +_ACEOF + + + + +cat >>confdefs.h <<_ACEOF +#define SIZEOF_SF_COUNT_T ${SIZEOF_SF_COUNT_T} +_ACEOF + + + + +cat >>confdefs.h <<_ACEOF +#define SF_COUNT_MAX ${SF_COUNT_MAX} +_ACEOF + + + +echo "$as_me:$LINENO: checking for ssize_t" >&5 +echo $ECHO_N "checking for ssize_t... $ECHO_C" >&6 +if test "${ac_cv_type_ssize_t+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +if ((ssize_t *) 0) + return 0; +if (sizeof (ssize_t)) + return 0; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_type_ssize_t=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_type_ssize_t=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: $ac_cv_type_ssize_t" >&5 +echo "${ECHO_T}$ac_cv_type_ssize_t" >&6 +if test $ac_cv_type_ssize_t = yes; then + +cat >>confdefs.h <<_ACEOF +#define HAVE_SSIZE_T 1 +_ACEOF + + +fi + +echo "$as_me:$LINENO: checking for ssize_t" >&5 +echo $ECHO_N "checking for ssize_t... $ECHO_C" >&6 +if test "${ac_cv_type_ssize_t+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +if ((ssize_t *) 0) + return 0; +if (sizeof (ssize_t)) + return 0; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_type_ssize_t=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_type_ssize_t=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: $ac_cv_type_ssize_t" >&5 +echo "${ECHO_T}$ac_cv_type_ssize_t" >&6 + +echo "$as_me:$LINENO: checking size of ssize_t" >&5 +echo $ECHO_N "checking size of ssize_t... $ECHO_C" >&6 +if test "${ac_cv_sizeof_ssize_t+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + if test "$ac_cv_type_ssize_t" = yes; then + # The cast to unsigned long works around a bug in the HP C Compiler + # version HP92453-01 B.11.11.23709.GP, which incorrectly rejects + # declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'. + # This bug is HP SR number 8606223364. + if test "$cross_compiling" = yes; then + # Depending upon the size, compute the lo and hi bounds. +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (ssize_t))) >= 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=0 ac_mid=0 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (ssize_t))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr $ac_mid + 1` + if test $ac_lo -le $ac_mid; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (ssize_t))) < 0)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=-1 ac_mid=-1 + while :; do + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (ssize_t))) >= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_lo=$ac_mid; break +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_hi=`expr '(' $ac_mid ')' - 1` + if test $ac_mid -le $ac_hi; then + ac_lo= ac_hi= + break + fi + ac_mid=`expr 2 '*' $ac_mid` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext + done +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo= ac_hi= +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +# Binary search between lo and hi bounds. +while test "x$ac_lo" != "x$ac_hi"; do + ac_mid=`expr '(' $ac_hi - $ac_lo ')' / 2 + $ac_lo` + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +int +main () +{ +static int test_array [1 - 2 * !(((long) (sizeof (ssize_t))) <= $ac_mid)]; +test_array [0] = 0 + + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_hi=$ac_mid +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_lo=`expr '(' $ac_mid ')' + 1` +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +done +case $ac_lo in +?*) ac_cv_sizeof_ssize_t=$ac_lo;; +'') { { echo "$as_me:$LINENO: error: cannot compute sizeof (ssize_t), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (ssize_t), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } ;; +esac +else + if test "$cross_compiling" = yes; then + { { echo "$as_me:$LINENO: error: cannot run test program while cross compiling +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot run test program while cross compiling +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +long longval () { return (long) (sizeof (ssize_t)); } +unsigned long ulongval () { return (long) (sizeof (ssize_t)); } +#include +#include +int +main () +{ + + FILE *f = fopen ("conftest.val", "w"); + if (! f) + exit (1); + if (((long) (sizeof (ssize_t))) < 0) + { + long i = longval (); + if (i != ((long) (sizeof (ssize_t)))) + exit (1); + fprintf (f, "%ld\n", i); + } + else + { + unsigned long i = ulongval (); + if (i != ((long) (sizeof (ssize_t)))) + exit (1); + fprintf (f, "%lu\n", i); + } + exit (ferror (f) || fclose (f) != 0); + + ; + return 0; +} +_ACEOF +rm -f conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && { ac_try='./conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_sizeof_ssize_t=`cat conftest.val` +else + echo "$as_me: program exited with status $ac_status" >&5 +echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +( exit $ac_status ) +{ { echo "$as_me:$LINENO: error: cannot compute sizeof (ssize_t), 77 +See \`config.log' for more details." >&5 +echo "$as_me: error: cannot compute sizeof (ssize_t), 77 +See \`config.log' for more details." >&2;} + { (exit 1); exit 1; }; } +fi +rm -f core *.core gmon.out bb.out conftest$ac_exeext conftest.$ac_objext conftest.$ac_ext +fi +fi +rm -f conftest.val +else + ac_cv_sizeof_ssize_t=0 +fi +fi +echo "$as_me:$LINENO: result: $ac_cv_sizeof_ssize_t" >&5 +echo "${ECHO_T}$ac_cv_sizeof_ssize_t" >&6 +cat >>confdefs.h <<_ACEOF +#define SIZEOF_SSIZE_T $ac_cv_sizeof_ssize_t +_ACEOF + + + +#==================================================================================== +# Determine endian-ness of target processor. + +echo "$as_me:$LINENO: checking processor byte ordering" >&5 +echo $ECHO_N "checking processor byte ordering... $ECHO_C" >&6 +if test "${ac_cv_c_byte_order+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + # Initialize to unknown +ac_cv_c_byte_order=unknown + +if test x$ac_cv_header_endian_h = xyes ; then + + # First try which should set BYTE_ORDER. + + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ + + #include + #if BYTE_ORDER != LITTLE_ENDIAN + not big endian + #endif + +int +main () +{ +return 0 ; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_c_byte_order=little + +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +fi +rm -f conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext + + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ + + #include + #if BYTE_ORDER != BIG_ENDIAN + not big endian + #endif + +int +main () +{ +return 0 ; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_c_byte_order=big + +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +fi +rm -f conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext + + fi + +if test $ac_cv_c_byte_order = unknown ; then + + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ + + #include + #include + #if !BYTE_ORDER || !BIG_ENDIAN || !LITTLE_ENDIAN + bogus endian macros + #endif + +int +main () +{ +return 0 ; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ + + #include + #include + #if BYTE_ORDER != LITTLE_ENDIAN + not big endian + #endif + +int +main () +{ +return 0 ; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_c_byte_order=little + +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +fi +rm -f conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext + + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ + + #include + #include + #if BYTE_ORDER != LITTLE_ENDIAN + not big endian + #endif + +int +main () +{ +return 0 ; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_c_byte_order=little + +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +fi +rm -f conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext + + +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +fi +rm -f conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext + + fi + +if test $ac_cv_c_byte_order = unknown ; then + if test $cross_compiling = yes ; then + # This is the last resort. Try to guess the target processor endian-ness + # by looking at the target CPU type. + + case "$target_cpu" in + alpha* | i?86* | mipsel* | ia64*) + ac_cv_c_big_endian=0 + ac_cv_c_little_endian=1 + ;; + + m68* | mips* | powerpc* | hppa* | sparc*) + ac_cv_c_big_endian=1 + ac_cv_c_little_endian=0 + ;; + + esac + + else + if test "$cross_compiling" = yes; then + ac_cv_c_byte_order=unknown + +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ + + int main (void) + { /* Are we little or big endian? From Harbison&Steele. */ + union + { long l ; + char c [sizeof (long)] ; + } u ; + u.l = 1 ; + return (u.c [sizeof (long) - 1] == 1); + } + +_ACEOF +rm -f conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && { ac_try='./conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + : +else + echo "$as_me: program exited with status $ac_status" >&5 +echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +( exit $ac_status ) +ac_cv_c_byte_order=big +fi +rm -f core *.core gmon.out bb.out conftest$ac_exeext conftest.$ac_objext conftest.$ac_ext +fi + + if test "$cross_compiling" = yes; then + ac_cv_c_byte_order=unknown + +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +int main (void) + { /* Are we little or big endian? From Harbison&Steele. */ + union + { long l ; + char c [sizeof (long)] ; + } u ; + u.l = 1 ; + return (u.c [0] == 1); + } +_ACEOF +rm -f conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && { ac_try='./conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + : +else + echo "$as_me: program exited with status $ac_status" >&5 +echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +( exit $ac_status ) +ac_cv_c_byte_order=little +fi +rm -f core *.core gmon.out bb.out conftest$ac_exeext conftest.$ac_objext conftest.$ac_ext +fi + fi + fi + + +fi +echo "$as_me:$LINENO: result: $ac_cv_c_byte_order" >&5 +echo "${ECHO_T}$ac_cv_c_byte_order" >&6 + + +if test $ac_cv_c_byte_order = big ; then + ac_cv_c_big_endian=1 + ac_cv_c_little_endian=0 +elif test $ac_cv_c_byte_order = little ; then + ac_cv_c_big_endian=0 + ac_cv_c_little_endian=1 +else + ac_cv_c_big_endian=0 + ac_cv_c_little_endian=0 + + echo "$as_me: WARNING: *****************************************************************" >&2 + echo "$as_me: WARNING: *** Not able to determine endian-ness of target processor. " >&2 + echo "$as_me: WARNING: *** The constants CPU_IS_BIG_ENDIAN and CPU_IS_LITTLE_ENDIAN in " >&2 + echo "$as_me: WARNING: *** src/config.h may need to be hand editied. " >&2 + echo "$as_me: WARNING: *****************************************************************" >&2 + fi + + + + +cat >>confdefs.h <<_ACEOF +#define CPU_IS_BIG_ENDIAN ${ac_cv_c_big_endian} +_ACEOF + + +cat >>confdefs.h <<_ACEOF +#define CPU_IS_LITTLE_ENDIAN ${ac_cv_c_little_endian} +_ACEOF + + +#==================================================================================== +# Check for functions. + + + + + +for ac_func in malloc calloc realloc free +do +as_ac_var=`echo "ac_cv_func_$ac_func" | $as_tr_sh` +echo "$as_me:$LINENO: checking for $ac_func" >&5 +echo $ECHO_N "checking for $ac_func... $ECHO_C" >&6 +if eval "test \"\${$as_ac_var+set}\" = set"; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +/* Define $ac_func to an innocuous variant, in case declares $ac_func. + For example, HP-UX 11i declares gettimeofday. */ +#define $ac_func innocuous_$ac_func + +/* System header to define __stub macros and hopefully few prototypes, + which can conflict with char $ac_func (); below. + Prefer to if __STDC__ is defined, since + exists even on freestanding compilers. */ + +#ifdef __STDC__ +# include +#else +# include +#endif + +#undef $ac_func + +/* Override any gcc2 internal prototype to avoid an error. */ +#ifdef __cplusplus +extern "C" +{ +#endif +/* We use char because int might match the return type of a gcc2 + builtin and then its argument prototype would still apply. */ +char $ac_func (); +/* The GNU C library defines this for functions which it implements + to always fail with ENOSYS. Some functions are actually named + something starting with __ and the normal name is an alias. */ +#if defined (__stub_$ac_func) || defined (__stub___$ac_func) +choke me +#else +char (*f) () = $ac_func; +#endif +#ifdef __cplusplus +} +#endif + +int +main () +{ +return f != $ac_func; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + eval "$as_ac_var=yes" +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +eval "$as_ac_var=no" +fi +rm -f conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_var'}'`" >&5 +echo "${ECHO_T}`eval echo '${'$as_ac_var'}'`" >&6 +if test `eval echo '${'$as_ac_var'}'` = yes; then + cat >>confdefs.h <<_ACEOF +#define `echo "HAVE_$ac_func" | $as_tr_cpp` 1 +_ACEOF + +fi +done + + + + + + + +for ac_func in open read write lseek pread pwrite +do +as_ac_var=`echo "ac_cv_func_$ac_func" | $as_tr_sh` +echo "$as_me:$LINENO: checking for $ac_func" >&5 +echo $ECHO_N "checking for $ac_func... $ECHO_C" >&6 +if eval "test \"\${$as_ac_var+set}\" = set"; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +/* Define $ac_func to an innocuous variant, in case declares $ac_func. + For example, HP-UX 11i declares gettimeofday. */ +#define $ac_func innocuous_$ac_func + +/* System header to define __stub macros and hopefully few prototypes, + which can conflict with char $ac_func (); below. + Prefer to if __STDC__ is defined, since + exists even on freestanding compilers. */ + +#ifdef __STDC__ +# include +#else +# include +#endif + +#undef $ac_func + +/* Override any gcc2 internal prototype to avoid an error. */ +#ifdef __cplusplus +extern "C" +{ +#endif +/* We use char because int might match the return type of a gcc2 + builtin and then its argument prototype would still apply. */ +char $ac_func (); +/* The GNU C library defines this for functions which it implements + to always fail with ENOSYS. Some functions are actually named + something starting with __ and the normal name is an alias. */ +#if defined (__stub_$ac_func) || defined (__stub___$ac_func) +choke me +#else +char (*f) () = $ac_func; +#endif +#ifdef __cplusplus +} +#endif + +int +main () +{ +return f != $ac_func; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + eval "$as_ac_var=yes" +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +eval "$as_ac_var=no" +fi +rm -f conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_var'}'`" >&5 +echo "${ECHO_T}`eval echo '${'$as_ac_var'}'`" >&6 +if test `eval echo '${'$as_ac_var'}'` = yes; then + cat >>confdefs.h <<_ACEOF +#define `echo "HAVE_$ac_func" | $as_tr_cpp` 1 +_ACEOF + +fi +done + + + + + +for ac_func in fstat ftruncate fsync fdatasync +do +as_ac_var=`echo "ac_cv_func_$ac_func" | $as_tr_sh` +echo "$as_me:$LINENO: checking for $ac_func" >&5 +echo $ECHO_N "checking for $ac_func... $ECHO_C" >&6 +if eval "test \"\${$as_ac_var+set}\" = set"; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +/* Define $ac_func to an innocuous variant, in case declares $ac_func. + For example, HP-UX 11i declares gettimeofday. */ +#define $ac_func innocuous_$ac_func + +/* System header to define __stub macros and hopefully few prototypes, + which can conflict with char $ac_func (); below. + Prefer to if __STDC__ is defined, since + exists even on freestanding compilers. */ + +#ifdef __STDC__ +# include +#else +# include +#endif + +#undef $ac_func + +/* Override any gcc2 internal prototype to avoid an error. */ +#ifdef __cplusplus +extern "C" +{ +#endif +/* We use char because int might match the return type of a gcc2 + builtin and then its argument prototype would still apply. */ +char $ac_func (); +/* The GNU C library defines this for functions which it implements + to always fail with ENOSYS. Some functions are actually named + something starting with __ and the normal name is an alias. */ +#if defined (__stub_$ac_func) || defined (__stub___$ac_func) +choke me +#else +char (*f) () = $ac_func; +#endif +#ifdef __cplusplus +} +#endif + +int +main () +{ +return f != $ac_func; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + eval "$as_ac_var=yes" +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +eval "$as_ac_var=no" +fi +rm -f conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_var'}'`" >&5 +echo "${ECHO_T}`eval echo '${'$as_ac_var'}'`" >&6 +if test `eval echo '${'$as_ac_var'}'` = yes; then + cat >>confdefs.h <<_ACEOF +#define `echo "HAVE_$ac_func" | $as_tr_cpp` 1 +_ACEOF + +fi +done + + + +for ac_func in snprintf vsnprintf +do +as_ac_var=`echo "ac_cv_func_$ac_func" | $as_tr_sh` +echo "$as_me:$LINENO: checking for $ac_func" >&5 +echo $ECHO_N "checking for $ac_func... $ECHO_C" >&6 +if eval "test \"\${$as_ac_var+set}\" = set"; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +/* Define $ac_func to an innocuous variant, in case declares $ac_func. + For example, HP-UX 11i declares gettimeofday. */ +#define $ac_func innocuous_$ac_func + +/* System header to define __stub macros and hopefully few prototypes, + which can conflict with char $ac_func (); below. + Prefer to if __STDC__ is defined, since + exists even on freestanding compilers. */ + +#ifdef __STDC__ +# include +#else +# include +#endif + +#undef $ac_func + +/* Override any gcc2 internal prototype to avoid an error. */ +#ifdef __cplusplus +extern "C" +{ +#endif +/* We use char because int might match the return type of a gcc2 + builtin and then its argument prototype would still apply. */ +char $ac_func (); +/* The GNU C library defines this for functions which it implements + to always fail with ENOSYS. Some functions are actually named + something starting with __ and the normal name is an alias. */ +#if defined (__stub_$ac_func) || defined (__stub___$ac_func) +choke me +#else +char (*f) () = $ac_func; +#endif +#ifdef __cplusplus +} +#endif + +int +main () +{ +return f != $ac_func; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + eval "$as_ac_var=yes" +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +eval "$as_ac_var=no" +fi +rm -f conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_var'}'`" >&5 +echo "${ECHO_T}`eval echo '${'$as_ac_var'}'`" >&6 +if test `eval echo '${'$as_ac_var'}'` = yes; then + cat >>confdefs.h <<_ACEOF +#define `echo "HAVE_$ac_func" | $as_tr_cpp` 1 +_ACEOF + +fi +done + + + +for ac_func in gmtime gmtime_r +do +as_ac_var=`echo "ac_cv_func_$ac_func" | $as_tr_sh` +echo "$as_me:$LINENO: checking for $ac_func" >&5 +echo $ECHO_N "checking for $ac_func... $ECHO_C" >&6 +if eval "test \"\${$as_ac_var+set}\" = set"; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +/* Define $ac_func to an innocuous variant, in case declares $ac_func. + For example, HP-UX 11i declares gettimeofday. */ +#define $ac_func innocuous_$ac_func + +/* System header to define __stub macros and hopefully few prototypes, + which can conflict with char $ac_func (); below. + Prefer to if __STDC__ is defined, since + exists even on freestanding compilers. */ + +#ifdef __STDC__ +# include +#else +# include +#endif + +#undef $ac_func + +/* Override any gcc2 internal prototype to avoid an error. */ +#ifdef __cplusplus +extern "C" +{ +#endif +/* We use char because int might match the return type of a gcc2 + builtin and then its argument prototype would still apply. */ +char $ac_func (); +/* The GNU C library defines this for functions which it implements + to always fail with ENOSYS. Some functions are actually named + something starting with __ and the normal name is an alias. */ +#if defined (__stub_$ac_func) || defined (__stub___$ac_func) +choke me +#else +char (*f) () = $ac_func; +#endif +#ifdef __cplusplus +} +#endif + +int +main () +{ +return f != $ac_func; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + eval "$as_ac_var=yes" +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +eval "$as_ac_var=no" +fi +rm -f conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_var'}'`" >&5 +echo "${ECHO_T}`eval echo '${'$as_ac_var'}'`" >&6 +if test `eval echo '${'$as_ac_var'}'` = yes; then + cat >>confdefs.h <<_ACEOF +#define `echo "HAVE_$ac_func" | $as_tr_cpp` 1 +_ACEOF + +fi +done + + + +for ac_func in mmap getpagesize +do +as_ac_var=`echo "ac_cv_func_$ac_func" | $as_tr_sh` +echo "$as_me:$LINENO: checking for $ac_func" >&5 +echo $ECHO_N "checking for $ac_func... $ECHO_C" >&6 +if eval "test \"\${$as_ac_var+set}\" = set"; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +/* Define $ac_func to an innocuous variant, in case declares $ac_func. + For example, HP-UX 11i declares gettimeofday. */ +#define $ac_func innocuous_$ac_func + +/* System header to define __stub macros and hopefully few prototypes, + which can conflict with char $ac_func (); below. + Prefer to if __STDC__ is defined, since + exists even on freestanding compilers. */ + +#ifdef __STDC__ +# include +#else +# include +#endif + +#undef $ac_func + +/* Override any gcc2 internal prototype to avoid an error. */ +#ifdef __cplusplus +extern "C" +{ +#endif +/* We use char because int might match the return type of a gcc2 + builtin and then its argument prototype would still apply. */ +char $ac_func (); +/* The GNU C library defines this for functions which it implements + to always fail with ENOSYS. Some functions are actually named + something starting with __ and the normal name is an alias. */ +#if defined (__stub_$ac_func) || defined (__stub___$ac_func) +choke me +#else +char (*f) () = $ac_func; +#endif +#ifdef __cplusplus +} +#endif + +int +main () +{ +return f != $ac_func; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + eval "$as_ac_var=yes" +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +eval "$as_ac_var=no" +fi +rm -f conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_var'}'`" >&5 +echo "${ECHO_T}`eval echo '${'$as_ac_var'}'`" >&6 +if test `eval echo '${'$as_ac_var'}'` = yes; then + cat >>confdefs.h <<_ACEOF +#define `echo "HAVE_$ac_func" | $as_tr_cpp` 1 +_ACEOF + +fi +done + + +for ac_func in setlocale +do +as_ac_var=`echo "ac_cv_func_$ac_func" | $as_tr_sh` +echo "$as_me:$LINENO: checking for $ac_func" >&5 +echo $ECHO_N "checking for $ac_func... $ECHO_C" >&6 +if eval "test \"\${$as_ac_var+set}\" = set"; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +/* Define $ac_func to an innocuous variant, in case declares $ac_func. + For example, HP-UX 11i declares gettimeofday. */ +#define $ac_func innocuous_$ac_func + +/* System header to define __stub macros and hopefully few prototypes, + which can conflict with char $ac_func (); below. + Prefer to if __STDC__ is defined, since + exists even on freestanding compilers. */ + +#ifdef __STDC__ +# include +#else +# include +#endif + +#undef $ac_func + +/* Override any gcc2 internal prototype to avoid an error. */ +#ifdef __cplusplus +extern "C" +{ +#endif +/* We use char because int might match the return type of a gcc2 + builtin and then its argument prototype would still apply. */ +char $ac_func (); +/* The GNU C library defines this for functions which it implements + to always fail with ENOSYS. Some functions are actually named + something starting with __ and the normal name is an alias. */ +#if defined (__stub_$ac_func) || defined (__stub___$ac_func) +choke me +#else +char (*f) () = $ac_func; +#endif +#ifdef __cplusplus +} +#endif + +int +main () +{ +return f != $ac_func; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + eval "$as_ac_var=yes" +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +eval "$as_ac_var=no" +fi +rm -f conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_var'}'`" >&5 +echo "${ECHO_T}`eval echo '${'$as_ac_var'}'`" >&6 +if test `eval echo '${'$as_ac_var'}'` = yes; then + cat >>confdefs.h <<_ACEOF +#define `echo "HAVE_$ac_func" | $as_tr_cpp` 1 +_ACEOF + +fi +done + + + +echo "$as_me:$LINENO: checking for floor in -lm" >&5 +echo $ECHO_N "checking for floor in -lm... $ECHO_C" >&6 +if test "${ac_cv_lib_m_floor+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + ac_check_lib_save_LIBS=$LIBS +LIBS="-lm $LIBS" +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ + +/* Override any gcc2 internal prototype to avoid an error. */ +#ifdef __cplusplus +extern "C" +#endif +/* We use char because int might match the return type of a gcc2 + builtin and then its argument prototype would still apply. */ +char floor (); +int +main () +{ +floor (); + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_lib_m_floor=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_lib_m_floor=no +fi +rm -f conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext +LIBS=$ac_check_lib_save_LIBS +fi +echo "$as_me:$LINENO: result: $ac_cv_lib_m_floor" >&5 +echo "${ECHO_T}$ac_cv_lib_m_floor" >&6 +if test $ac_cv_lib_m_floor = yes; then + cat >>confdefs.h <<_ACEOF +#define HAVE_LIBM 1 +_ACEOF + + LIBS="-lm $LIBS" + +fi + + + + +for ac_func in floor ceil fmod +do +as_ac_var=`echo "ac_cv_func_$ac_func" | $as_tr_sh` +echo "$as_me:$LINENO: checking for $ac_func" >&5 +echo $ECHO_N "checking for $ac_func... $ECHO_C" >&6 +if eval "test \"\${$as_ac_var+set}\" = set"; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +/* Define $ac_func to an innocuous variant, in case declares $ac_func. + For example, HP-UX 11i declares gettimeofday. */ +#define $ac_func innocuous_$ac_func + +/* System header to define __stub macros and hopefully few prototypes, + which can conflict with char $ac_func (); below. + Prefer to if __STDC__ is defined, since + exists even on freestanding compilers. */ + +#ifdef __STDC__ +# include +#else +# include +#endif + +#undef $ac_func + +/* Override any gcc2 internal prototype to avoid an error. */ +#ifdef __cplusplus +extern "C" +{ +#endif +/* We use char because int might match the return type of a gcc2 + builtin and then its argument prototype would still apply. */ +char $ac_func (); +/* The GNU C library defines this for functions which it implements + to always fail with ENOSYS. Some functions are actually named + something starting with __ and the normal name is an alias. */ +#if defined (__stub_$ac_func) || defined (__stub___$ac_func) +choke me +#else +char (*f) () = $ac_func; +#endif +#ifdef __cplusplus +} +#endif + +int +main () +{ +return f != $ac_func; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + eval "$as_ac_var=yes" +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +eval "$as_ac_var=no" +fi +rm -f conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext +fi +echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_var'}'`" >&5 +echo "${ECHO_T}`eval echo '${'$as_ac_var'}'`" >&6 +if test `eval echo '${'$as_ac_var'}'` = yes; then + cat >>confdefs.h <<_ACEOF +#define `echo "HAVE_$ac_func" | $as_tr_cpp` 1 +_ACEOF + +fi +done + + +case "$host_os" in + cygwin*) + { echo "$as_me:$LINENO: WARNING: Not using built-in lrint() and lrintf() because they are broken on Cygwin." >&5 +echo "$as_me: WARNING: Not using built-in lrint() and lrintf() because they are broken on Cygwin." >&2;} + ;; + *) + echo "$as_me:$LINENO: checking for lrint" >&5 +echo $ECHO_N "checking for lrint... $ECHO_C" >&6 +if test "${ac_cv_c99_lrint+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + +lrint_save_CFLAGS=$CFLAGS +CFLAGS="-O2 -lm" +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ + +#define _ISOC9X_SOURCE 1 +#define _ISOC99_SOURCE 1 +#define __USE_ISOC99 1 +#define __USE_ISOC9X 1 + +#include + +int +main () +{ +if (!lrint(3.14159)) lrint(2.7183); + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_c99_lrint=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_c99_lrint=no +fi +rm -f conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext + +CFLAGS=$lrint_save_CFLAGS + + +fi +echo "$as_me:$LINENO: result: $ac_cv_c99_lrint" >&5 +echo "${ECHO_T}$ac_cv_c99_lrint" >&6 + +if test "$ac_cv_c99_lrint" = yes; then + +cat >>confdefs.h <<\_ACEOF +#define HAVE_LRINT 1 +_ACEOF + +fi + + echo "$as_me:$LINENO: checking for lrintf" >&5 +echo $ECHO_N "checking for lrintf... $ECHO_C" >&6 +if test "${ac_cv_c99_lrintf+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + +lrintf_save_CFLAGS=$CFLAGS +CFLAGS="-O2 -lm" +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ + +#define _ISOC9X_SOURCE 1 +#define _ISOC99_SOURCE 1 +#define __USE_ISOC99 1 +#define __USE_ISOC9X 1 + +#include + +int +main () +{ +if (!lrintf(3.14159)) lrintf(2.7183); + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_c99_lrintf=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_c99_lrintf=no +fi +rm -f conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext + +CFLAGS=$lrintf_save_CFLAGS + + +fi +echo "$as_me:$LINENO: result: $ac_cv_c99_lrintf" >&5 +echo "${ECHO_T}$ac_cv_c99_lrintf" >&6 + +if test "$ac_cv_c99_lrintf" = yes; then + +cat >>confdefs.h <<\_ACEOF +#define HAVE_LRINTF 1 +_ACEOF + +fi + + + if test "x$ac_cv_c99_lrint" = "xno" ; then + if test "x$ac_cv_c99_lrintf" = "xno" ; then + { echo "$as_me:$LINENO: WARNING: *** Missing C99 standard functions lrint() and lrintf()." >&5 +echo "$as_me: WARNING: *** Missing C99 standard functions lrint() and lrintf()." >&2;} + { echo "$as_me:$LINENO: WARNING: *** This may cause benign compiler warnings on some systems (ie Solaris)." >&5 +echo "$as_me: WARNING: *** This may cause benign compiler warnings on some systems (ie Solaris)." >&2;} + fi + fi + ;; + esac + +#==================================================================================== +# Check for libsqlite3 (only used in regtest). + +ac_cv_sqlite3=no +if test x$enable_sqlite != xno ; then + + succeeded=no + + if test -z "$PKG_CONFIG"; then + # Extract the first word of "pkg-config", so it can be a program name with args. +set dummy pkg-config; ac_word=$2 +echo "$as_me:$LINENO: checking for $ac_word" >&5 +echo $ECHO_N "checking for $ac_word... $ECHO_C" >&6 +if test "${ac_cv_path_PKG_CONFIG+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + case $PKG_CONFIG in + [\\/]* | ?:[\\/]*) + ac_cv_path_PKG_CONFIG="$PKG_CONFIG" # Let the user override the test with a path. + ;; + *) + as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + for ac_exec_ext in '' $ac_executable_extensions; do + if $as_executable_p "$as_dir/$ac_word$ac_exec_ext"; then + ac_cv_path_PKG_CONFIG="$as_dir/$ac_word$ac_exec_ext" + echo "$as_me:$LINENO: found $as_dir/$ac_word$ac_exec_ext" >&5 + break 2 + fi +done +done + + test -z "$ac_cv_path_PKG_CONFIG" && ac_cv_path_PKG_CONFIG="no" + ;; +esac +fi +PKG_CONFIG=$ac_cv_path_PKG_CONFIG + +if test -n "$PKG_CONFIG"; then + echo "$as_me:$LINENO: result: $PKG_CONFIG" >&5 +echo "${ECHO_T}$PKG_CONFIG" >&6 +else + echo "$as_me:$LINENO: result: no" >&5 +echo "${ECHO_T}no" >&6 +fi + + fi + + if test "$PKG_CONFIG" = "no" ; then + echo "*** The pkg-config script could not be found. Make sure it is" + echo "*** in your path, or set the PKG_CONFIG environment variable" + echo "*** to the full path to pkg-config." + echo "*** Or see http://www.freedesktop.org/software/pkgconfig to get pkg-config." + else + PKG_CONFIG_MIN_VERSION=0.9.0 + if $PKG_CONFIG --atleast-pkgconfig-version $PKG_CONFIG_MIN_VERSION; then + echo "$as_me:$LINENO: checking for sqlite3 >= 3.2" >&5 +echo $ECHO_N "checking for sqlite3 >= 3.2... $ECHO_C" >&6 + + if $PKG_CONFIG --exists "sqlite3 >= 3.2" ; then + echo "$as_me:$LINENO: result: yes" >&5 +echo "${ECHO_T}yes" >&6 + succeeded=yes + + echo "$as_me:$LINENO: checking SQLITE3_CFLAGS" >&5 +echo $ECHO_N "checking SQLITE3_CFLAGS... $ECHO_C" >&6 + SQLITE3_CFLAGS=`$PKG_CONFIG --cflags "sqlite3 >= 3.2"` + echo "$as_me:$LINENO: result: $SQLITE3_CFLAGS" >&5 +echo "${ECHO_T}$SQLITE3_CFLAGS" >&6 + + echo "$as_me:$LINENO: checking SQLITE3_LIBS" >&5 +echo $ECHO_N "checking SQLITE3_LIBS... $ECHO_C" >&6 + SQLITE3_LIBS=`$PKG_CONFIG --libs "sqlite3 >= 3.2"` + echo "$as_me:$LINENO: result: $SQLITE3_LIBS" >&5 +echo "${ECHO_T}$SQLITE3_LIBS" >&6 + else + SQLITE3_CFLAGS="" + SQLITE3_LIBS="" + ## If we have a custom action on failure, don't print errors, but + ## do set a variable so people can do so. + SQLITE3_PKG_ERRORS=`$PKG_CONFIG --errors-to-stdout --print-errors "sqlite3 >= 3.2"` + + fi + + + + else + echo "*** Your version of pkg-config is too old. You need version $PKG_CONFIG_MIN_VERSION or newer." + echo "*** See http://www.freedesktop.org/software/pkgconfig" + fi + fi + + if test $succeeded = yes; then + ac_cv_sqlite3=yes + else + ac_cv_sqlite3=no + fi + + fi + +if test x$ac_cv_sqlite3 = "xyes" ; then + HAVE_SQLITE3=1 +else + HAVE_SQLITE3=0 + fi + + +cat >>confdefs.h <<_ACEOF +#define HAVE_SQLITE3 $HAVE_SQLITE3 +_ACEOF + + +#==================================================================================== +# Determine if the processor can do clipping on float to int conversions. + +if test x$enable_cpu_clip != "xno" ; then + echo "$as_me:$LINENO: checking processor clipping capabilities" >&5 +echo $ECHO_N "checking processor clipping capabilities... $ECHO_C" >&6 +if test "${ac_cv_c_clip_type+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + # Initialize to unknown +ac_cv_c_clip_positive=unknown +ac_cv_c_clip_negative=unknown + +if test $ac_cv_c_clip_positive = unknown ; then + if test "$cross_compiling" = yes; then + ac_cv_c_clip_positive=unknown + +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ + + #define _ISOC9X_SOURCE 1 + #define _ISOC99_SOURCE 1 + #define __USE_ISOC99 1 + #define __USE_ISOC9X 1 + #include + int main (void) + { double fval ; + int k, ival ; + + fval = 1.0 * 0x7FFFFFFF ; + for (k = 0 ; k < 100 ; k++) + { ival = (lrint (fval)) >> 24 ; + if (ival != 127) + return 1 ; + + fval *= 1.2499999 ; + } ; + + return 0 ; + } + +_ACEOF +rm -f conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && { ac_try='./conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_c_clip_positive=yes +else + echo "$as_me: program exited with status $ac_status" >&5 +echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +( exit $ac_status ) +ac_cv_c_clip_positive=no +fi +rm -f core *.core gmon.out bb.out conftest$ac_exeext conftest.$ac_objext conftest.$ac_ext +fi + + if test "$cross_compiling" = yes; then + ac_cv_c_clip_negative=unknown + +else + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ + + #define _ISOC9X_SOURCE 1 + #define _ISOC99_SOURCE 1 + #define __USE_ISOC99 1 + #define __USE_ISOC9X 1 + #include + int main (void) + { double fval ; + int k, ival ; + + fval = -8.0 * 0x10000000 ; + for (k = 0 ; k < 100 ; k++) + { ival = (lrint (fval)) >> 24 ; + if (ival != -128) + return 1 ; + + fval *= 1.2499999 ; + } ; + + return 0 ; + } + +_ACEOF +rm -f conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && { ac_try='./conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_c_clip_negative=yes +else + echo "$as_me: program exited with status $ac_status" >&5 +echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +( exit $ac_status ) +ac_cv_c_clip_negative=no +fi +rm -f core *.core gmon.out bb.out conftest$ac_exeext conftest.$ac_objext conftest.$ac_ext +fi + fi + +if test $ac_cv_c_clip_positive = yes ; then + ac_cv_c_clip_positive=1 +else + ac_cv_c_clip_positive=0 + fi + +if test $ac_cv_c_clip_negative = yes ; then + ac_cv_c_clip_negative=1 +else + ac_cv_c_clip_negative=0 + fi + + +case "$ac_cv_c_clip_positive$ac_cv_c_clip_negative" in + "00") + ac_cv_c_clip_type="none" + ;; + "10") + ac_cv_c_clip_type="positive" + ;; + "01") + ac_cv_c_clip_type="negative" + ;; + "11") + ac_cv_c_clip_type="both" + ;; + esac + + + +fi +echo "$as_me:$LINENO: result: $ac_cv_c_clip_type" >&5 +echo "${ECHO_T}$ac_cv_c_clip_type" >&6 + + + +else + echo "checking processor clipping capabilities... disabled" + ac_cv_c_clip_positive=0 + ac_cv_c_clip_negative=0 + fi + + +cat >>confdefs.h <<_ACEOF +#define CPU_CLIPS_POSITIVE ${ac_cv_c_clip_positive} +_ACEOF + + +cat >>confdefs.h <<_ACEOF +#define CPU_CLIPS_NEGATIVE ${ac_cv_c_clip_negative} +_ACEOF + + +#==================================================================================== +# Target OS specific stuff. + +OS_SPECIFIC_CFLAGS="" +OS_SPECIFIC_LINKS="" +os_is_win32=0 +os_is_macosx=0 +use_windows_api=0 + +case "$host_os" in + darwin* | rhapsody*) + os_is_macosx=1 + OS_SPECIFIC_CFLAGS="-fpascal-strings -I/Developer/Headers/FlatCarbon" + OS_SPECIFIC_LINKS="-framework CoreAudio" + ;; + mingw*) + os_is_win32=1 + use_windows_api=1 + OS_SPECIFIC_LINKS="-lwinmm" + ;; + cygwin*) + os_is_win32=1 + OS_SPECIFIC_LINKS="-lwinmm" + ;; + esac + + +cat >>confdefs.h <<_ACEOF +#define OS_IS_WIN32 ${os_is_win32} +_ACEOF + + +cat >>confdefs.h <<_ACEOF +#define OS_IS_MACOSX ${os_is_macosx} +_ACEOF + + +cat >>confdefs.h <<_ACEOF +#define USE_WINDOWS_API ${use_windows_api} +_ACEOF + + +#==================================================================================== +# Check for ALSA. + +ALSA_LIBS="" + +if test x$enable_alsa != xno ; then + +for ac_header in alsa/asoundlib.h +do +as_ac_Header=`echo "ac_cv_header_$ac_header" | $as_tr_sh` +if eval "test \"\${$as_ac_Header+set}\" = set"; then + echo "$as_me:$LINENO: checking for $ac_header" >&5 +echo $ECHO_N "checking for $ac_header... $ECHO_C" >&6 +if eval "test \"\${$as_ac_Header+set}\" = set"; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +fi +echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_Header'}'`" >&5 +echo "${ECHO_T}`eval echo '${'$as_ac_Header'}'`" >&6 +else + # Is the header compilable? +echo "$as_me:$LINENO: checking $ac_header usability" >&5 +echo $ECHO_N "checking $ac_header usability... $ECHO_C" >&6 +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +#include <$ac_header> +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_header_compiler=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_header_compiler=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +echo "$as_me:$LINENO: result: $ac_header_compiler" >&5 +echo "${ECHO_T}$ac_header_compiler" >&6 + +# Is the header present? +echo "$as_me:$LINENO: checking $ac_header presence" >&5 +echo $ECHO_N "checking $ac_header presence... $ECHO_C" >&6 +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +#include <$ac_header> +_ACEOF +if { (eval echo "$as_me:$LINENO: \"$ac_cpp conftest.$ac_ext\"") >&5 + (eval $ac_cpp conftest.$ac_ext) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } >/dev/null; then + if test -s conftest.err; then + ac_cpp_err=$ac_c_preproc_warn_flag + ac_cpp_err=$ac_cpp_err$ac_c_werror_flag + else + ac_cpp_err= + fi +else + ac_cpp_err=yes +fi +if test -z "$ac_cpp_err"; then + ac_header_preproc=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + + ac_header_preproc=no +fi +rm -f conftest.err conftest.$ac_ext +echo "$as_me:$LINENO: result: $ac_header_preproc" >&5 +echo "${ECHO_T}$ac_header_preproc" >&6 + +# So? What about this header? +case $ac_header_compiler:$ac_header_preproc:$ac_c_preproc_warn_flag in + yes:no: ) + { echo "$as_me:$LINENO: WARNING: $ac_header: accepted by the compiler, rejected by the preprocessor!" >&5 +echo "$as_me: WARNING: $ac_header: accepted by the compiler, rejected by the preprocessor!" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: proceeding with the compiler's result" >&5 +echo "$as_me: WARNING: $ac_header: proceeding with the compiler's result" >&2;} + ac_header_preproc=yes + ;; + no:yes:* ) + { echo "$as_me:$LINENO: WARNING: $ac_header: present but cannot be compiled" >&5 +echo "$as_me: WARNING: $ac_header: present but cannot be compiled" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: check for missing prerequisite headers?" >&5 +echo "$as_me: WARNING: $ac_header: check for missing prerequisite headers?" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: see the Autoconf documentation" >&5 +echo "$as_me: WARNING: $ac_header: see the Autoconf documentation" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: section \"Present But Cannot Be Compiled\"" >&5 +echo "$as_me: WARNING: $ac_header: section \"Present But Cannot Be Compiled\"" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: proceeding with the preprocessor's result" >&5 +echo "$as_me: WARNING: $ac_header: proceeding with the preprocessor's result" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: in the future, the compiler will take precedence" >&5 +echo "$as_me: WARNING: $ac_header: in the future, the compiler will take precedence" >&2;} + ( + cat <<\_ASBOX +## -------------------------------- ## +## Report this to ardour@ardour.org ## +## -------------------------------- ## +_ASBOX + ) | + sed "s/^/$as_me: WARNING: /" >&2 + ;; +esac +echo "$as_me:$LINENO: checking for $ac_header" >&5 +echo $ECHO_N "checking for $ac_header... $ECHO_C" >&6 +if eval "test \"\${$as_ac_Header+set}\" = set"; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + eval "$as_ac_Header=\$ac_header_preproc" +fi +echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_Header'}'`" >&5 +echo "${ECHO_T}`eval echo '${'$as_ac_Header'}'`" >&6 + +fi +if test `eval echo '${'$as_ac_Header'}'` = yes; then + cat >>confdefs.h <<_ACEOF +#define `echo "HAVE_$ac_header" | $as_tr_cpp` 1 +_ACEOF + +fi + +done + + if test x$ac_cv_header_alsa_asoundlib_h = xyes ; then + ALSA_LIBS="-lasound" + fi + fi + +#==================================================================================== +# Check for FLAC + +FLAC_LIBS="" + +if test x$enable_flac != xno ; then + +for ac_header in FLAC/all.h +do +as_ac_Header=`echo "ac_cv_header_$ac_header" | $as_tr_sh` +if eval "test \"\${$as_ac_Header+set}\" = set"; then + echo "$as_me:$LINENO: checking for $ac_header" >&5 +echo $ECHO_N "checking for $ac_header... $ECHO_C" >&6 +if eval "test \"\${$as_ac_Header+set}\" = set"; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +fi +echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_Header'}'`" >&5 +echo "${ECHO_T}`eval echo '${'$as_ac_Header'}'`" >&6 +else + # Is the header compilable? +echo "$as_me:$LINENO: checking $ac_header usability" >&5 +echo $ECHO_N "checking $ac_header usability... $ECHO_C" >&6 +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +$ac_includes_default +#include <$ac_header> +_ACEOF +rm -f conftest.$ac_objext +if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 + (eval $ac_compile) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest.$ac_objext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_header_compiler=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_header_compiler=no +fi +rm -f conftest.err conftest.$ac_objext conftest.$ac_ext +echo "$as_me:$LINENO: result: $ac_header_compiler" >&5 +echo "${ECHO_T}$ac_header_compiler" >&6 + +# Is the header present? +echo "$as_me:$LINENO: checking $ac_header presence" >&5 +echo $ECHO_N "checking $ac_header presence... $ECHO_C" >&6 +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +#include <$ac_header> +_ACEOF +if { (eval echo "$as_me:$LINENO: \"$ac_cpp conftest.$ac_ext\"") >&5 + (eval $ac_cpp conftest.$ac_ext) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } >/dev/null; then + if test -s conftest.err; then + ac_cpp_err=$ac_c_preproc_warn_flag + ac_cpp_err=$ac_cpp_err$ac_c_werror_flag + else + ac_cpp_err= + fi +else + ac_cpp_err=yes +fi +if test -z "$ac_cpp_err"; then + ac_header_preproc=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + + ac_header_preproc=no +fi +rm -f conftest.err conftest.$ac_ext +echo "$as_me:$LINENO: result: $ac_header_preproc" >&5 +echo "${ECHO_T}$ac_header_preproc" >&6 + +# So? What about this header? +case $ac_header_compiler:$ac_header_preproc:$ac_c_preproc_warn_flag in + yes:no: ) + { echo "$as_me:$LINENO: WARNING: $ac_header: accepted by the compiler, rejected by the preprocessor!" >&5 +echo "$as_me: WARNING: $ac_header: accepted by the compiler, rejected by the preprocessor!" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: proceeding with the compiler's result" >&5 +echo "$as_me: WARNING: $ac_header: proceeding with the compiler's result" >&2;} + ac_header_preproc=yes + ;; + no:yes:* ) + { echo "$as_me:$LINENO: WARNING: $ac_header: present but cannot be compiled" >&5 +echo "$as_me: WARNING: $ac_header: present but cannot be compiled" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: check for missing prerequisite headers?" >&5 +echo "$as_me: WARNING: $ac_header: check for missing prerequisite headers?" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: see the Autoconf documentation" >&5 +echo "$as_me: WARNING: $ac_header: see the Autoconf documentation" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: section \"Present But Cannot Be Compiled\"" >&5 +echo "$as_me: WARNING: $ac_header: section \"Present But Cannot Be Compiled\"" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: proceeding with the preprocessor's result" >&5 +echo "$as_me: WARNING: $ac_header: proceeding with the preprocessor's result" >&2;} + { echo "$as_me:$LINENO: WARNING: $ac_header: in the future, the compiler will take precedence" >&5 +echo "$as_me: WARNING: $ac_header: in the future, the compiler will take precedence" >&2;} + ( + cat <<\_ASBOX +## -------------------------------- ## +## Report this to ardour@ardour.org ## +## -------------------------------- ## +_ASBOX + ) | + sed "s/^/$as_me: WARNING: /" >&2 + ;; +esac +echo "$as_me:$LINENO: checking for $ac_header" >&5 +echo $ECHO_N "checking for $ac_header... $ECHO_C" >&6 +if eval "test \"\${$as_ac_Header+set}\" = set"; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + eval "$as_ac_Header=\$ac_header_preproc" +fi +echo "$as_me:$LINENO: result: `eval echo '${'$as_ac_Header'}'`" >&5 +echo "${ECHO_T}`eval echo '${'$as_ac_Header'}'`" >&6 + +fi +if test `eval echo '${'$as_ac_Header'}'` = yes; then + cat >>confdefs.h <<_ACEOF +#define `echo "HAVE_$ac_header" | $as_tr_cpp` 1 +_ACEOF + +fi + +done + + if test x$ac_cv_header_FLAC_all_h = xyes ; then + echo "$as_me:$LINENO: checking for FLAC__seekable_stream_encoder_set_tell_callback in -lFLAC" >&5 +echo $ECHO_N "checking for FLAC__seekable_stream_encoder_set_tell_callback in -lFLAC... $ECHO_C" >&6 +if test "${ac_cv_lib_FLAC_FLAC__seekable_stream_encoder_set_tell_callback+set}" = set; then + echo $ECHO_N "(cached) $ECHO_C" >&6 +else + ac_check_lib_save_LIBS=$LIBS +LIBS="-lFLAC $LIBS" +cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ + +/* Override any gcc2 internal prototype to avoid an error. */ +#ifdef __cplusplus +extern "C" +#endif +/* We use char because int might match the return type of a gcc2 + builtin and then its argument prototype would still apply. */ +char FLAC__seekable_stream_encoder_set_tell_callback (); +int +main () +{ +FLAC__seekable_stream_encoder_set_tell_callback (); + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + ac_cv_lib_FLAC_FLAC__seekable_stream_encoder_set_tell_callback=yes +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +ac_cv_lib_FLAC_FLAC__seekable_stream_encoder_set_tell_callback=no +fi +rm -f conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext +LIBS=$ac_check_lib_save_LIBS +fi +echo "$as_me:$LINENO: result: $ac_cv_lib_FLAC_FLAC__seekable_stream_encoder_set_tell_callback" >&5 +echo "${ECHO_T}$ac_cv_lib_FLAC_FLAC__seekable_stream_encoder_set_tell_callback" >&6 +if test $ac_cv_lib_FLAC_FLAC__seekable_stream_encoder_set_tell_callback = yes; then + HAVE_FLAC_1_1_1="yes" +fi + + if test "x$HAVE_FLAC_1_1_1" = xyes ; then + +cat >>confdefs.h <<\_ACEOF +#define HAVE_FLAC_1_1_1 1 +_ACEOF + + fi + FLAC_LIBS="-lFLAC" + fi + fi + +#==================================================================================== +# Test for sanity when cross-compiling. + +if test x$cross_compiling = xyes ; then + { echo "$as_me:$LINENO: WARNING: ******************************************************************" >&5 +echo "$as_me: WARNING: ******************************************************************" >&2;} + { echo "$as_me:$LINENO: WARNING: *** We are cross-compiling, so have to assume sizeof (short) == 2 " >&5 +echo "$as_me: WARNING: *** We are cross-compiling, so have to assume sizeof (short) == 2 " >&2;} + { echo "$as_me:$LINENO: WARNING: *** and sizeof (int) == 4. If this is not the case there is no " >&5 +echo "$as_me: WARNING: *** and sizeof (int) == 4. If this is not the case there is no " >&2;} + { echo "$as_me:$LINENO: WARNING: *** chance of this working. Please contact the mantainer. " >&5 +echo "$as_me: WARNING: *** chance of this working. Please contact the mantainer. " >&2;} + { echo "$as_me:$LINENO: WARNING: ******************************************************************" >&5 +echo "$as_me: WARNING: ******************************************************************" >&2;} + fi + +if test $ac_cv_sizeof_short != 2 ; then + { echo "$as_me:$LINENO: WARNING: ******************************************************************" >&5 +echo "$as_me: WARNING: ******************************************************************" >&2;} + { echo "$as_me:$LINENO: WARNING: *** sizeof (short) != 2. " >&5 +echo "$as_me: WARNING: *** sizeof (short) != 2. " >&2;} + { echo "$as_me:$LINENO: WARNING: ******************************************************************" >&5 +echo "$as_me: WARNING: ******************************************************************" >&2;} + fi + +if test $ac_cv_sizeof_int != 4 ; then + { echo "$as_me:$LINENO: WARNING: ******************************************************************" >&5 +echo "$as_me: WARNING: ******************************************************************" >&2;} + { echo "$as_me:$LINENO: WARNING: *** sizeof (int) != 4 " >&5 +echo "$as_me: WARNING: *** sizeof (int) != 4 " >&2;} + { echo "$as_me:$LINENO: WARNING: ******************************************************************" >&5 +echo "$as_me: WARNING: ******************************************************************" >&2;} + fi + +if test $ac_cv_sizeof_float != 4 ; then + { echo "$as_me:$LINENO: WARNING: ******************************************************************" >&5 +echo "$as_me: WARNING: ******************************************************************" >&2;} + { echo "$as_me:$LINENO: WARNING: *** sizeof (float) != 4. " >&5 +echo "$as_me: WARNING: *** sizeof (float) != 4. " >&2;} + { echo "$as_me:$LINENO: WARNING: ******************************************************************" >&5 +echo "$as_me: WARNING: ******************************************************************" >&2;} + fi + +if test $ac_cv_sizeof_double != 8 ; then + { echo "$as_me:$LINENO: WARNING: ******************************************************************" >&5 +echo "$as_me: WARNING: ******************************************************************" >&2;} + { echo "$as_me:$LINENO: WARNING: *** sizeof (double) != 8. " >&5 +echo "$as_me: WARNING: *** sizeof (double) != 8. " >&2;} + { echo "$as_me:$LINENO: WARNING: ******************************************************************" >&5 +echo "$as_me: WARNING: ******************************************************************" >&2;} + fi + +if test x"$ac_cv_prog_autogen" = "xno" ; then + { echo "$as_me:$LINENO: WARNING: Touching files in directory tests/." >&5 +echo "$as_me: WARNING: Touching files in directory tests/." >&2;} + touch tests/*.c tests/*.h + fi + +#==================================================================================== +# Settings for the HTML documentation. + +htmldocdir=$prefix/share/doc/libsndfile1-dev/html + +if test $prefix = "NONE" ; then + htmldocdir=/usr/local/share/doc/libsndfile1-dev/html +else + htmldocdir=$prefix/share/doc/libsndfile1-dev/html + fi + +if test x$enable_bow_docs = "xyes" ; then + HTML_BGCOLOUR="white" + HTML_FGCOLOUR="black" +else + HTML_BGCOLOUR="black" + HTML_FGCOLOUR="white" + fi + +#==================================================================================== +# Now use the information from the checking stage. + +if test x$ac_cv_c_compiler_gnu = xyes ; then + echo "$as_me:$LINENO: checking if $CC accepts -std=gnu99" >&5 +echo $ECHO_N "checking if $CC accepts -std=gnu99... $ECHO_C" >&6 + ac_add_cflags__old_cflags="$CFLAGS" + CFLAGS="$CFLAGS -std=gnu99" + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +#include +int +main () +{ +printf("Hello, World!\n"); return 0; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + echo "$as_me:$LINENO: result: yes" >&5 +echo "${ECHO_T}yes" >&6 +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +echo "$as_me:$LINENO: result: no" >&5 +echo "${ECHO_T}no" >&6 + CFLAGS="$ac_add_cflags__old_cflags" +fi +rm -f conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext + + + CFLAGS="$CFLAGS -W -Wall" + + echo "$as_me:$LINENO: checking if $CC accepts -Wdeclaration-after-statement" >&5 +echo $ECHO_N "checking if $CC accepts -Wdeclaration-after-statement... $ECHO_C" >&6 + ac_add_cflags__old_cflags="$CFLAGS" + CFLAGS="$CFLAGS -Wdeclaration-after-statement" + cat >conftest.$ac_ext <<_ACEOF +/* confdefs.h. */ +_ACEOF +cat confdefs.h >>conftest.$ac_ext +cat >>conftest.$ac_ext <<_ACEOF +/* end confdefs.h. */ +#include +int +main () +{ +printf("Hello, World!\n"); return 0; + ; + return 0; +} +_ACEOF +rm -f conftest.$ac_objext conftest$ac_exeext +if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5 + (eval $ac_link) 2>conftest.er1 + ac_status=$? + grep -v '^ *+' conftest.er1 >conftest.err + rm -f conftest.er1 + cat conftest.err >&5 + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); } && + { ac_try='test -z "$ac_c_werror_flag" + || test ! -s conftest.err' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; } && + { ac_try='test -s conftest$ac_exeext' + { (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5 + (eval $ac_try) 2>&5 + ac_status=$? + echo "$as_me:$LINENO: \$? = $ac_status" >&5 + (exit $ac_status); }; }; then + echo "$as_me:$LINENO: result: yes" >&5 +echo "${ECHO_T}yes" >&6 +else + echo "$as_me: failed program was:" >&5 +sed 's/^/| /' conftest.$ac_ext >&5 + +echo "$as_me:$LINENO: result: no" >&5 +echo "${ECHO_T}no" >&6 + CFLAGS="$ac_add_cflags__old_cflags" +fi +rm -f conftest.err conftest.$ac_objext \ + conftest$ac_exeext conftest.$ac_ext + + + if test x$enable_gcc_werror = "xyes" ; then + CFLAGS="-Werror $CFLAGS" + fi + + CFLAGS="$CFLAGS -Wstrict-prototypes -Wmissing-prototypes -Waggregate-return -Wcast-align -Wcast-qual -Wnested-externs -Wshadow -Wbad-function-cast -Wwrite-strings" + # -Wpointer-arith -Wundef -Wmissing-declarations -Winline -Wconversion" + + if test "x$enable_gcc_opt" = "xno" ; then + temp_CFLAGS=`echo $CFLAGS | sed "s/O2/O0/"` + CFLAGS=$temp_CFLAGS + { echo "$as_me:$LINENO: WARNING: *** Compiler optimisations switched off. ***" >&5 +echo "$as_me: WARNING: *** Compiler optimisations switched off. ***" >&2;} + fi + + # OS specific tweaks. + case "$host_os" in + darwin* | rhapsody*) + # Disable -Wall, -pedantic and -Wshadow for Apple Darwin/Rhapsody. + # System headers on these systems are broken. + temp_CFLAGS=`echo $CFLAGS | sed "s/-Wall -pedantic//" | sed "s/-Wshadow//" | sed "s/-Waggregate-return//"` + CFLAGS=$temp_CFLAGS + SHLIB_VERSION_ARG="-Wl,-exported_symbols_list -Wl,\$(srcdir)/Symbols.darwin" + ;; + linux*) + SHLIB_VERSION_ARG="-Wl,--version-script=\$(srcdir)/Symbols.linux" + ;; + mingw*) + SHLIB_VERSION_ARG="-Wl,\$(srcdir)/libsndfile.def" + ;; + cygwin*) + SHLIB_VERSION_ARG="-Wl,\$(srcdir)/cygsndfile.def" + ;; + *) + ;; + esac + if test x$enable_gcc_pipe != "xno" ; then + CFLAGS="$CFLAGS -pipe" + fi + + +cat >>confdefs.h <<\_ACEOF +#define COMPILER_IS_GCC 1 +_ACEOF + + GCC_MAJOR_VERSION=`$CC -dumpversion | sed "s/\..*//"` + +cat >>confdefs.h <<_ACEOF +#define GCC_MAJOR_VERSION ${GCC_MAJOR_VERSION} +_ACEOF + + fi + +CFLAGS="$CFLAGS $OS_SPECIFIC_CFLAGS" + +if test x"$CFLAGS" = x ; then + echo "Error in configure script. CFLAGS has been screwed up." + exit + fi + + + + + + + + + + + + + + + + + + + ac_config_files="$ac_config_files src/sndfile.h sndfile.pc" + +cat >confcache <<\_ACEOF +# This file is a shell script that caches the results of configure +# tests run on this system so they can be shared between configure +# scripts and configure runs, see configure's option --config-cache. +# It is not useful on other systems. If it contains results you don't +# want to keep, you may remove or edit it. +# +# config.status only pays attention to the cache file if you give it +# the --recheck option to rerun configure. +# +# `ac_cv_env_foo' variables (set or unset) will be overridden when +# loading this file, other *unset* `ac_cv_foo' will be assigned the +# following values. + +_ACEOF + +# The following way of writing the cache mishandles newlines in values, +# but we know of no workaround that is simple, portable, and efficient. +# So, don't put newlines in cache variables' values. +# Ultrix sh set writes to stderr and can't be redirected directly, +# and sets the high bit in the cache file unless we assign to the vars. +{ + (set) 2>&1 | + case `(ac_space=' '; set | grep ac_space) 2>&1` in + *ac_space=\ *) + # `set' does not quote correctly, so add quotes (double-quote + # substitution turns \\\\ into \\, and sed turns \\ into \). + sed -n \ + "s/'/'\\\\''/g; + s/^\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\)=\\(.*\\)/\\1='\\2'/p" + ;; + *) + # `set' quotes correctly as required by POSIX, so do not add quotes. + sed -n \ + "s/^\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\)=\\(.*\\)/\\1=\\2/p" + ;; + esac; +} | + sed ' + t clear + : clear + s/^\([^=]*\)=\(.*[{}].*\)$/test "${\1+set}" = set || &/ + t end + /^ac_cv_env/!s/^\([^=]*\)=\(.*\)$/\1=${\1=\2}/ + : end' >>confcache +if diff $cache_file confcache >/dev/null 2>&1; then :; else + if test -w $cache_file; then + test "x$cache_file" != "x/dev/null" && echo "updating cache $cache_file" + cat confcache >$cache_file + else + echo "not updating unwritable cache $cache_file" + fi +fi +rm -f confcache + +test "x$prefix" = xNONE && prefix=$ac_default_prefix +# Let make expand exec_prefix. +test "x$exec_prefix" = xNONE && exec_prefix='${prefix}' + +# VPATH may cause trouble with some makes, so we remove $(srcdir), +# ${srcdir} and @srcdir@ from VPATH if srcdir is ".", strip leading and +# trailing colons and then remove the whole line if VPATH becomes empty +# (actually we leave an empty line to preserve line numbers). +if test "x$srcdir" = x.; then + ac_vpsub='/^[ ]*VPATH[ ]*=/{ +s/:*\$(srcdir):*/:/; +s/:*\${srcdir}:*/:/; +s/:*@srcdir@:*/:/; +s/^\([^=]*=[ ]*\):*/\1/; +s/:*$//; +s/^[^=]*=[ ]*$//; +}' +fi + +DEFS=-DHAVE_CONFIG_H + +ac_libobjs= +ac_ltlibobjs= +for ac_i in : $LIBOBJS; do test "x$ac_i" = x: && continue + # 1. Remove the extension, and $U if already installed. + ac_i=`echo "$ac_i" | + sed 's/\$U\././;s/\.o$//;s/\.obj$//'` + # 2. Add them. + ac_libobjs="$ac_libobjs $ac_i\$U.$ac_objext" + ac_ltlibobjs="$ac_ltlibobjs $ac_i"'$U.lo' +done +LIBOBJS=$ac_libobjs + +LTLIBOBJS=$ac_ltlibobjs + + + +: ${CONFIG_STATUS=./config.status} +ac_clean_files_save=$ac_clean_files +ac_clean_files="$ac_clean_files $CONFIG_STATUS" +{ echo "$as_me:$LINENO: creating $CONFIG_STATUS" >&5 +echo "$as_me: creating $CONFIG_STATUS" >&6;} +cat >$CONFIG_STATUS <<_ACEOF +#! $SHELL +# Generated by $as_me. +# Run this file to recreate the current configuration. +# Compiler output produced by configure, useful for debugging +# configure, is in config.log if it exists. + +debug=false +ac_cs_recheck=false +ac_cs_silent=false +SHELL=\${CONFIG_SHELL-$SHELL} +_ACEOF + +cat >>$CONFIG_STATUS <<\_ACEOF +## --------------------- ## +## M4sh Initialization. ## +## --------------------- ## + +# Be Bourne compatible +if test -n "${ZSH_VERSION+set}" && (emulate sh) >/dev/null 2>&1; then + emulate sh + NULLCMD=: + # Zsh 3.x and 4.x performs word splitting on ${1+"$@"}, which + # is contrary to our usage. Disable this feature. + alias -g '${1+"$@"}'='"$@"' +elif test -n "${BASH_VERSION+set}" && (set -o posix) >/dev/null 2>&1; then + set -o posix +fi +DUALCASE=1; export DUALCASE # for MKS sh + +# Support unset when possible. +if ( (MAIL=60; unset MAIL) || exit) >/dev/null 2>&1; then + as_unset=unset +else + as_unset=false +fi + + +# Work around bugs in pre-3.0 UWIN ksh. +$as_unset ENV MAIL MAILPATH +PS1='$ ' +PS2='> ' +PS4='+ ' + +# NLS nuisances. +for as_var in \ + LANG LANGUAGE LC_ADDRESS LC_ALL LC_COLLATE LC_CTYPE LC_IDENTIFICATION \ + LC_MEASUREMENT LC_MESSAGES LC_MONETARY LC_NAME LC_NUMERIC LC_PAPER \ + LC_TELEPHONE LC_TIME +do + if (set +x; test -z "`(eval $as_var=C; export $as_var) 2>&1`"); then + eval $as_var=C; export $as_var + else + $as_unset $as_var + fi +done + +# Required to use basename. +if expr a : '\(a\)' >/dev/null 2>&1; then + as_expr=expr +else + as_expr=false +fi + +if (basename /) >/dev/null 2>&1 && test "X`basename / 2>&1`" = "X/"; then + as_basename=basename +else + as_basename=false +fi + + +# Name of the executable. +as_me=`$as_basename "$0" || +$as_expr X/"$0" : '.*/\([^/][^/]*\)/*$' \| \ + X"$0" : 'X\(//\)$' \| \ + X"$0" : 'X\(/\)$' \| \ + . : '\(.\)' 2>/dev/null || +echo X/"$0" | + sed '/^.*\/\([^/][^/]*\)\/*$/{ s//\1/; q; } + /^X\/\(\/\/\)$/{ s//\1/; q; } + /^X\/\(\/\).*/{ s//\1/; q; } + s/.*/./; q'` + + +# PATH needs CR, and LINENO needs CR and PATH. +# Avoid depending upon Character Ranges. +as_cr_letters='abcdefghijklmnopqrstuvwxyz' +as_cr_LETTERS='ABCDEFGHIJKLMNOPQRSTUVWXYZ' +as_cr_Letters=$as_cr_letters$as_cr_LETTERS +as_cr_digits='0123456789' +as_cr_alnum=$as_cr_Letters$as_cr_digits + +# The user is always right. +if test "${PATH_SEPARATOR+set}" != set; then + echo "#! /bin/sh" >conf$$.sh + echo "exit 0" >>conf$$.sh + chmod +x conf$$.sh + if (PATH="/nonexistent;."; conf$$.sh) >/dev/null 2>&1; then + PATH_SEPARATOR=';' + else + PATH_SEPARATOR=: + fi + rm -f conf$$.sh +fi + + + as_lineno_1=$LINENO + as_lineno_2=$LINENO + as_lineno_3=`(expr $as_lineno_1 + 1) 2>/dev/null` + test "x$as_lineno_1" != "x$as_lineno_2" && + test "x$as_lineno_3" = "x$as_lineno_2" || { + # Find who we are. Look in the path if we contain no path at all + # relative or not. + case $0 in + *[\\/]* ) as_myself=$0 ;; + *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in $PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + test -r "$as_dir/$0" && as_myself=$as_dir/$0 && break +done + + ;; + esac + # We did not find ourselves, most probably we were run as `sh COMMAND' + # in which case we are not to be found in the path. + if test "x$as_myself" = x; then + as_myself=$0 + fi + if test ! -f "$as_myself"; then + { { echo "$as_me:$LINENO: error: cannot find myself; rerun with an absolute path" >&5 +echo "$as_me: error: cannot find myself; rerun with an absolute path" >&2;} + { (exit 1); exit 1; }; } + fi + case $CONFIG_SHELL in + '') + as_save_IFS=$IFS; IFS=$PATH_SEPARATOR +for as_dir in /bin$PATH_SEPARATOR/usr/bin$PATH_SEPARATOR$PATH +do + IFS=$as_save_IFS + test -z "$as_dir" && as_dir=. + for as_base in sh bash ksh sh5; do + case $as_dir in + /*) + if ("$as_dir/$as_base" -c ' + as_lineno_1=$LINENO + as_lineno_2=$LINENO + as_lineno_3=`(expr $as_lineno_1 + 1) 2>/dev/null` + test "x$as_lineno_1" != "x$as_lineno_2" && + test "x$as_lineno_3" = "x$as_lineno_2" ') 2>/dev/null; then + $as_unset BASH_ENV || test "${BASH_ENV+set}" != set || { BASH_ENV=; export BASH_ENV; } + $as_unset ENV || test "${ENV+set}" != set || { ENV=; export ENV; } + CONFIG_SHELL=$as_dir/$as_base + export CONFIG_SHELL + exec "$CONFIG_SHELL" "$0" ${1+"$@"} + fi;; + esac + done +done +;; + esac + + # Create $as_me.lineno as a copy of $as_myself, but with $LINENO + # uniformly replaced by the line number. The first 'sed' inserts a + # line-number line before each line; the second 'sed' does the real + # work. The second script uses 'N' to pair each line-number line + # with the numbered line, and appends trailing '-' during + # substitution so that $LINENO is not a special case at line end. + # (Raja R Harinath suggested sed '=', and Paul Eggert wrote the + # second 'sed' script. Blame Lee E. McMahon for sed's syntax. :-) + sed '=' <$as_myself | + sed ' + N + s,$,-, + : loop + s,^\(['$as_cr_digits']*\)\(.*\)[$]LINENO\([^'$as_cr_alnum'_]\),\1\2\1\3, + t loop + s,-$,, + s,^['$as_cr_digits']*\n,, + ' >$as_me.lineno && + chmod +x $as_me.lineno || + { { echo "$as_me:$LINENO: error: cannot create $as_me.lineno; rerun with a POSIX shell" >&5 +echo "$as_me: error: cannot create $as_me.lineno; rerun with a POSIX shell" >&2;} + { (exit 1); exit 1; }; } + + # Don't try to exec as it changes $[0], causing all sort of problems + # (the dirname of $[0] is not the place where we might find the + # original and so on. Autoconf is especially sensible to this). + . ./$as_me.lineno + # Exit status is that of the last command. + exit +} + + +case `echo "testing\c"; echo 1,2,3`,`echo -n testing; echo 1,2,3` in + *c*,-n*) ECHO_N= ECHO_C=' +' ECHO_T=' ' ;; + *c*,* ) ECHO_N=-n ECHO_C= ECHO_T= ;; + *) ECHO_N= ECHO_C='\c' ECHO_T= ;; +esac + +if expr a : '\(a\)' >/dev/null 2>&1; then + as_expr=expr +else + as_expr=false +fi + +rm -f conf$$ conf$$.exe conf$$.file +echo >conf$$.file +if ln -s conf$$.file conf$$ 2>/dev/null; then + # We could just check for DJGPP; but this test a) works b) is more generic + # and c) will remain valid once DJGPP supports symlinks (DJGPP 2.04). + if test -f conf$$.exe; then + # Don't use ln at all; we don't have any links + as_ln_s='cp -p' + else + as_ln_s='ln -s' + fi +elif ln conf$$.file conf$$ 2>/dev/null; then + as_ln_s=ln +else + as_ln_s='cp -p' +fi +rm -f conf$$ conf$$.exe conf$$.file + +if mkdir -p . 2>/dev/null; then + as_mkdir_p=: +else + test -d ./-p && rmdir ./-p + as_mkdir_p=false +fi + +as_executable_p="test -f" + +# Sed expression to map a string onto a valid CPP name. +as_tr_cpp="eval sed 'y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g'" + +# Sed expression to map a string onto a valid variable name. +as_tr_sh="eval sed 'y%*+%pp%;s%[^_$as_cr_alnum]%_%g'" + + +# IFS +# We need space, tab and new line, in precisely that order. +as_nl=' +' +IFS=" $as_nl" + +# CDPATH. +$as_unset CDPATH + +exec 6>&1 + +# Open the log real soon, to keep \$[0] and so on meaningful, and to +# report actual input values of CONFIG_FILES etc. instead of their +# values after options handling. Logging --version etc. is OK. +exec 5>>config.log +{ + echo + sed 'h;s/./-/g;s/^.../## /;s/...$/ ##/;p;x;p;x' <<_ASBOX +## Running $as_me. ## +_ASBOX +} >&5 +cat >&5 <<_CSEOF + +This file was extended by libsndfile $as_me ardour-special, which was +generated by GNU Autoconf 2.59. Invocation command line was + + CONFIG_FILES = $CONFIG_FILES + CONFIG_HEADERS = $CONFIG_HEADERS + CONFIG_LINKS = $CONFIG_LINKS + CONFIG_COMMANDS = $CONFIG_COMMANDS + $ $0 $@ + +_CSEOF +echo "on `(hostname || uname -n) 2>/dev/null | sed 1q`" >&5 +echo >&5 +_ACEOF + +# Files that config.status was made for. +if test -n "$ac_config_files"; then + echo "config_files=\"$ac_config_files\"" >>$CONFIG_STATUS +fi + +if test -n "$ac_config_headers"; then + echo "config_headers=\"$ac_config_headers\"" >>$CONFIG_STATUS +fi + +if test -n "$ac_config_links"; then + echo "config_links=\"$ac_config_links\"" >>$CONFIG_STATUS +fi + +if test -n "$ac_config_commands"; then + echo "config_commands=\"$ac_config_commands\"" >>$CONFIG_STATUS +fi + +cat >>$CONFIG_STATUS <<\_ACEOF + +ac_cs_usage="\ +\`$as_me' instantiates files from templates according to the +current configuration. + +Usage: $0 [OPTIONS] [FILE]... + + -h, --help print this help, then exit + -V, --version print version number, then exit + -q, --quiet do not print progress messages + -d, --debug don't remove temporary files + --recheck update $as_me by reconfiguring in the same conditions + --file=FILE[:TEMPLATE] + instantiate the configuration file FILE + --header=FILE[:TEMPLATE] + instantiate the configuration header FILE + +Configuration files: +$config_files + +Configuration headers: +$config_headers + +Report bugs to ." +_ACEOF + +cat >>$CONFIG_STATUS <<_ACEOF +ac_cs_version="\\ +libsndfile config.status ardour-special +configured by $0, generated by GNU Autoconf 2.59, + with options \\"`echo "$ac_configure_args" | sed 's/[\\""\`\$]/\\\\&/g'`\\" + +Copyright (C) 2003 Free Software Foundation, Inc. +This config.status script is free software; the Free Software Foundation +gives unlimited permission to copy, distribute and modify it." +srcdir=$srcdir +INSTALL="$INSTALL" +_ACEOF + +cat >>$CONFIG_STATUS <<\_ACEOF +# If no file are specified by the user, then we need to provide default +# value. By we need to know if files were specified by the user. +ac_need_defaults=: +while test $# != 0 +do + case $1 in + --*=*) + ac_option=`expr "x$1" : 'x\([^=]*\)='` + ac_optarg=`expr "x$1" : 'x[^=]*=\(.*\)'` + ac_shift=: + ;; + -*) + ac_option=$1 + ac_optarg=$2 + ac_shift=shift + ;; + *) # This is not an option, so the user has probably given explicit + # arguments. + ac_option=$1 + ac_need_defaults=false;; + esac + + case $ac_option in + # Handling of the options. +_ACEOF +cat >>$CONFIG_STATUS <<\_ACEOF + -recheck | --recheck | --rechec | --reche | --rech | --rec | --re | --r) + ac_cs_recheck=: ;; + --version | --vers* | -V ) + echo "$ac_cs_version"; exit 0 ;; + --he | --h) + # Conflict between --help and --header + { { echo "$as_me:$LINENO: error: ambiguous option: $1 +Try \`$0 --help' for more information." >&5 +echo "$as_me: error: ambiguous option: $1 +Try \`$0 --help' for more information." >&2;} + { (exit 1); exit 1; }; };; + --help | --hel | -h ) + echo "$ac_cs_usage"; exit 0 ;; + --debug | --d* | -d ) + debug=: ;; + --file | --fil | --fi | --f ) + $ac_shift + CONFIG_FILES="$CONFIG_FILES $ac_optarg" + ac_need_defaults=false;; + --header | --heade | --head | --hea ) + $ac_shift + CONFIG_HEADERS="$CONFIG_HEADERS $ac_optarg" + ac_need_defaults=false;; + -q | -quiet | --quiet | --quie | --qui | --qu | --q \ + | -silent | --silent | --silen | --sile | --sil | --si | --s) + ac_cs_silent=: ;; + + # This is an error. + -*) { { echo "$as_me:$LINENO: error: unrecognized option: $1 +Try \`$0 --help' for more information." >&5 +echo "$as_me: error: unrecognized option: $1 +Try \`$0 --help' for more information." >&2;} + { (exit 1); exit 1; }; } ;; + + *) ac_config_targets="$ac_config_targets $1" ;; + + esac + shift +done + +ac_configure_extra_args= + +if $ac_cs_silent; then + exec 6>/dev/null + ac_configure_extra_args="$ac_configure_extra_args --silent" +fi + +_ACEOF +cat >>$CONFIG_STATUS <<_ACEOF +if \$ac_cs_recheck; then + echo "running $SHELL $0 " $ac_configure_args \$ac_configure_extra_args " --no-create --no-recursion" >&6 + exec $SHELL $0 $ac_configure_args \$ac_configure_extra_args --no-create --no-recursion +fi + +_ACEOF + + + + + +cat >>$CONFIG_STATUS <<\_ACEOF +for ac_config_target in $ac_config_targets +do + case "$ac_config_target" in + # Handling of arguments. + "src/sndfile.h" ) CONFIG_FILES="$CONFIG_FILES src/sndfile.h" ;; + "sndfile.pc" ) CONFIG_FILES="$CONFIG_FILES sndfile.pc" ;; + "src/config.h" ) CONFIG_HEADERS="$CONFIG_HEADERS src/config.h" ;; + *) { { echo "$as_me:$LINENO: error: invalid argument: $ac_config_target" >&5 +echo "$as_me: error: invalid argument: $ac_config_target" >&2;} + { (exit 1); exit 1; }; };; + esac +done + +# If the user did not use the arguments to specify the items to instantiate, +# then the envvar interface is used. Set only those that are not. +# We use the long form for the default assignment because of an extremely +# bizarre bug on SunOS 4.1.3. +if $ac_need_defaults; then + test "${CONFIG_FILES+set}" = set || CONFIG_FILES=$config_files + test "${CONFIG_HEADERS+set}" = set || CONFIG_HEADERS=$config_headers +fi + +# Have a temporary directory for convenience. Make it in the build tree +# simply because there is no reason to put it here, and in addition, +# creating and moving files from /tmp can sometimes cause problems. +# Create a temporary directory, and hook for its removal unless debugging. +$debug || +{ + trap 'exit_status=$?; rm -rf $tmp && exit $exit_status' 0 + trap '{ (exit 1); exit 1; }' 1 2 13 15 +} + +# Create a (secure) tmp directory for tmp files. + +{ + tmp=`(umask 077 && mktemp -d -q "./confstatXXXXXX") 2>/dev/null` && + test -n "$tmp" && test -d "$tmp" +} || +{ + tmp=./confstat$$-$RANDOM + (umask 077 && mkdir $tmp) +} || +{ + echo "$me: cannot create a temporary directory in ." >&2 + { (exit 1); exit 1; } +} + +_ACEOF + +cat >>$CONFIG_STATUS <<_ACEOF + +# +# CONFIG_FILES section. +# + +# No need to generate the scripts if there are no CONFIG_FILES. +# This happens for instance when ./config.status config.h +if test -n "\$CONFIG_FILES"; then + # Protect against being on the right side of a sed subst in config.status. + sed 's/,@/@@/; s/@,/@@/; s/,;t t\$/@;t t/; /@;t t\$/s/[\\\\&,]/\\\\&/g; + s/@@/,@/; s/@@/@,/; s/@;t t\$/,;t t/' >\$tmp/subs.sed <<\\CEOF +s,@SHELL@,$SHELL,;t t +s,@PATH_SEPARATOR@,$PATH_SEPARATOR,;t t +s,@PACKAGE_NAME@,$PACKAGE_NAME,;t t +s,@PACKAGE_TARNAME@,$PACKAGE_TARNAME,;t t +s,@PACKAGE_VERSION@,$PACKAGE_VERSION,;t t +s,@PACKAGE_STRING@,$PACKAGE_STRING,;t t +s,@PACKAGE_BUGREPORT@,$PACKAGE_BUGREPORT,;t t +s,@exec_prefix@,$exec_prefix,;t t +s,@prefix@,$prefix,;t t +s,@program_transform_name@,$program_transform_name,;t t +s,@bindir@,$bindir,;t t +s,@sbindir@,$sbindir,;t t +s,@libexecdir@,$libexecdir,;t t +s,@datadir@,$datadir,;t t +s,@sysconfdir@,$sysconfdir,;t t +s,@sharedstatedir@,$sharedstatedir,;t t +s,@localstatedir@,$localstatedir,;t t +s,@libdir@,$libdir,;t t +s,@includedir@,$includedir,;t t +s,@oldincludedir@,$oldincludedir,;t t +s,@infodir@,$infodir,;t t +s,@mandir@,$mandir,;t t +s,@build_alias@,$build_alias,;t t +s,@host_alias@,$host_alias,;t t +s,@target_alias@,$target_alias,;t t +s,@DEFS@,$DEFS,;t t +s,@ECHO_C@,$ECHO_C,;t t +s,@ECHO_N@,$ECHO_N,;t t +s,@ECHO_T@,$ECHO_T,;t t +s,@LIBS@,$LIBS,;t t +s,@build@,$build,;t t +s,@build_cpu@,$build_cpu,;t t +s,@build_vendor@,$build_vendor,;t t +s,@build_os@,$build_os,;t t +s,@host@,$host,;t t +s,@host_cpu@,$host_cpu,;t t +s,@host_vendor@,$host_vendor,;t t +s,@host_os@,$host_os,;t t +s,@target@,$target,;t t +s,@target_cpu@,$target_cpu,;t t +s,@target_vendor@,$target_vendor,;t t +s,@target_os@,$target_os,;t t +s,@CC@,$CC,;t t +s,@CFLAGS@,$CFLAGS,;t t +s,@LDFLAGS@,$LDFLAGS,;t t +s,@CPPFLAGS@,$CPPFLAGS,;t t +s,@ac_ct_CC@,$ac_ct_CC,;t t +s,@EXEEXT@,$EXEEXT,;t t +s,@OBJEXT@,$OBJEXT,;t t +s,@autogen@,$autogen,;t t +s,@INSTALL_PROGRAM@,$INSTALL_PROGRAM,;t t +s,@INSTALL_SCRIPT@,$INSTALL_SCRIPT,;t t +s,@INSTALL_DATA@,$INSTALL_DATA,;t t +s,@LN_S@,$LN_S,;t t +s,@CPP@,$CPP,;t t +s,@EGREP@,$EGREP,;t t +s,@GETCONF@,$GETCONF,;t t +s,@ac_ct_GETCONF@,$ac_ct_GETCONF,;t t +s,@TYPEOF_SF_COUNT_T@,$TYPEOF_SF_COUNT_T,;t t +s,@SIZEOF_SF_COUNT_T@,$SIZEOF_SF_COUNT_T,;t t +s,@SF_COUNT_MAX@,$SF_COUNT_MAX,;t t +s,@PKG_CONFIG@,$PKG_CONFIG,;t t +s,@SQLITE3_CFLAGS@,$SQLITE3_CFLAGS,;t t +s,@SQLITE3_LIBS@,$SQLITE3_LIBS,;t t +s,@htmldocdir@,$htmldocdir,;t t +s,@HTML_BGCOLOUR@,$HTML_BGCOLOUR,;t t +s,@HTML_FGCOLOUR@,$HTML_FGCOLOUR,;t t +s,@SHLIB_VERSION_ARG@,$SHLIB_VERSION_ARG,;t t +s,@SHARED_VERSION_INFO@,$SHARED_VERSION_INFO,;t t +s,@OS_SPECIFIC_CFLAGS@,$OS_SPECIFIC_CFLAGS,;t t +s,@OS_SPECIFIC_LINKS@,$OS_SPECIFIC_LINKS,;t t +s,@ALSA_LIBS@,$ALSA_LIBS,;t t +s,@FLAC_LIBS@,$FLAC_LIBS,;t t +s,@ENABLE_EXPERIMENTAL_CODE@,$ENABLE_EXPERIMENTAL_CODE,;t t +s,@COMPILER_IS_GCC@,$COMPILER_IS_GCC,;t t +s,@GCC_MAJOR_VERSION@,$GCC_MAJOR_VERSION,;t t +s,@LIBTOOL_DEPS@,$LIBTOOL_DEPS,;t t +s,@LIBOBJS@,$LIBOBJS,;t t +s,@LTLIBOBJS@,$LTLIBOBJS,;t t +CEOF + +_ACEOF + + cat >>$CONFIG_STATUS <<\_ACEOF + # Split the substitutions into bite-sized pieces for seds with + # small command number limits, like on Digital OSF/1 and HP-UX. + ac_max_sed_lines=48 + ac_sed_frag=1 # Number of current file. + ac_beg=1 # First line for current file. + ac_end=$ac_max_sed_lines # Line after last line for current file. + ac_more_lines=: + ac_sed_cmds= + while $ac_more_lines; do + if test $ac_beg -gt 1; then + sed "1,${ac_beg}d; ${ac_end}q" $tmp/subs.sed >$tmp/subs.frag + else + sed "${ac_end}q" $tmp/subs.sed >$tmp/subs.frag + fi + if test ! -s $tmp/subs.frag; then + ac_more_lines=false + else + # The purpose of the label and of the branching condition is to + # speed up the sed processing (if there are no `@' at all, there + # is no need to browse any of the substitutions). + # These are the two extra sed commands mentioned above. + (echo ':t + /@[a-zA-Z_][a-zA-Z_0-9]*@/!b' && cat $tmp/subs.frag) >$tmp/subs-$ac_sed_frag.sed + if test -z "$ac_sed_cmds"; then + ac_sed_cmds="sed -f $tmp/subs-$ac_sed_frag.sed" + else + ac_sed_cmds="$ac_sed_cmds | sed -f $tmp/subs-$ac_sed_frag.sed" + fi + ac_sed_frag=`expr $ac_sed_frag + 1` + ac_beg=$ac_end + ac_end=`expr $ac_end + $ac_max_sed_lines` + fi + done + if test -z "$ac_sed_cmds"; then + ac_sed_cmds=cat + fi +fi # test -n "$CONFIG_FILES" + +_ACEOF +cat >>$CONFIG_STATUS <<\_ACEOF +for ac_file in : $CONFIG_FILES; do test "x$ac_file" = x: && continue + # Support "outfile[:infile[:infile...]]", defaulting infile="outfile.in". + case $ac_file in + - | *:- | *:-:* ) # input from stdin + cat >$tmp/stdin + ac_file_in=`echo "$ac_file" | sed 's,[^:]*:,,'` + ac_file=`echo "$ac_file" | sed 's,:.*,,'` ;; + *:* ) ac_file_in=`echo "$ac_file" | sed 's,[^:]*:,,'` + ac_file=`echo "$ac_file" | sed 's,:.*,,'` ;; + * ) ac_file_in=$ac_file.in ;; + esac + + # Compute @srcdir@, @top_srcdir@, and @INSTALL@ for subdirectories. + ac_dir=`(dirname "$ac_file") 2>/dev/null || +$as_expr X"$ac_file" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ + X"$ac_file" : 'X\(//\)[^/]' \| \ + X"$ac_file" : 'X\(//\)$' \| \ + X"$ac_file" : 'X\(/\)' \| \ + . : '\(.\)' 2>/dev/null || +echo X"$ac_file" | + sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ s//\1/; q; } + /^X\(\/\/\)[^/].*/{ s//\1/; q; } + /^X\(\/\/\)$/{ s//\1/; q; } + /^X\(\/\).*/{ s//\1/; q; } + s/.*/./; q'` + { if $as_mkdir_p; then + mkdir -p "$ac_dir" + else + as_dir="$ac_dir" + as_dirs= + while test ! -d "$as_dir"; do + as_dirs="$as_dir $as_dirs" + as_dir=`(dirname "$as_dir") 2>/dev/null || +$as_expr X"$as_dir" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ + X"$as_dir" : 'X\(//\)[^/]' \| \ + X"$as_dir" : 'X\(//\)$' \| \ + X"$as_dir" : 'X\(/\)' \| \ + . : '\(.\)' 2>/dev/null || +echo X"$as_dir" | + sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ s//\1/; q; } + /^X\(\/\/\)[^/].*/{ s//\1/; q; } + /^X\(\/\/\)$/{ s//\1/; q; } + /^X\(\/\).*/{ s//\1/; q; } + s/.*/./; q'` + done + test ! -n "$as_dirs" || mkdir $as_dirs + fi || { { echo "$as_me:$LINENO: error: cannot create directory \"$ac_dir\"" >&5 +echo "$as_me: error: cannot create directory \"$ac_dir\"" >&2;} + { (exit 1); exit 1; }; }; } + + ac_builddir=. + +if test "$ac_dir" != .; then + ac_dir_suffix=/`echo "$ac_dir" | sed 's,^\.[\\/],,'` + # A "../" for each directory in $ac_dir_suffix. + ac_top_builddir=`echo "$ac_dir_suffix" | sed 's,/[^\\/]*,../,g'` +else + ac_dir_suffix= ac_top_builddir= +fi + +case $srcdir in + .) # No --srcdir option. We are building in place. + ac_srcdir=. + if test -z "$ac_top_builddir"; then + ac_top_srcdir=. + else + ac_top_srcdir=`echo $ac_top_builddir | sed 's,/$,,'` + fi ;; + [\\/]* | ?:[\\/]* ) # Absolute path. + ac_srcdir=$srcdir$ac_dir_suffix; + ac_top_srcdir=$srcdir ;; + *) # Relative path. + ac_srcdir=$ac_top_builddir$srcdir$ac_dir_suffix + ac_top_srcdir=$ac_top_builddir$srcdir ;; +esac + +# Do not use `cd foo && pwd` to compute absolute paths, because +# the directories may not exist. +case `pwd` in +.) ac_abs_builddir="$ac_dir";; +*) + case "$ac_dir" in + .) ac_abs_builddir=`pwd`;; + [\\/]* | ?:[\\/]* ) ac_abs_builddir="$ac_dir";; + *) ac_abs_builddir=`pwd`/"$ac_dir";; + esac;; +esac +case $ac_abs_builddir in +.) ac_abs_top_builddir=${ac_top_builddir}.;; +*) + case ${ac_top_builddir}. in + .) ac_abs_top_builddir=$ac_abs_builddir;; + [\\/]* | ?:[\\/]* ) ac_abs_top_builddir=${ac_top_builddir}.;; + *) ac_abs_top_builddir=$ac_abs_builddir/${ac_top_builddir}.;; + esac;; +esac +case $ac_abs_builddir in +.) ac_abs_srcdir=$ac_srcdir;; +*) + case $ac_srcdir in + .) ac_abs_srcdir=$ac_abs_builddir;; + [\\/]* | ?:[\\/]* ) ac_abs_srcdir=$ac_srcdir;; + *) ac_abs_srcdir=$ac_abs_builddir/$ac_srcdir;; + esac;; +esac +case $ac_abs_builddir in +.) ac_abs_top_srcdir=$ac_top_srcdir;; +*) + case $ac_top_srcdir in + .) ac_abs_top_srcdir=$ac_abs_builddir;; + [\\/]* | ?:[\\/]* ) ac_abs_top_srcdir=$ac_top_srcdir;; + *) ac_abs_top_srcdir=$ac_abs_builddir/$ac_top_srcdir;; + esac;; +esac + + + case $INSTALL in + [\\/$]* | ?:[\\/]* ) ac_INSTALL=$INSTALL ;; + *) ac_INSTALL=$ac_top_builddir$INSTALL ;; + esac + + if test x"$ac_file" != x-; then + { echo "$as_me:$LINENO: creating $ac_file" >&5 +echo "$as_me: creating $ac_file" >&6;} + rm -f "$ac_file" + fi + # Let's still pretend it is `configure' which instantiates (i.e., don't + # use $as_me), people would be surprised to read: + # /* config.h. Generated by config.status. */ + if test x"$ac_file" = x-; then + configure_input= + else + configure_input="$ac_file. " + fi + configure_input=$configure_input"Generated from `echo $ac_file_in | + sed 's,.*/,,'` by configure." + + # First look for the input files in the build tree, otherwise in the + # src tree. + ac_file_inputs=`IFS=: + for f in $ac_file_in; do + case $f in + -) echo $tmp/stdin ;; + [\\/$]*) + # Absolute (can't be DOS-style, as IFS=:) + test -f "$f" || { { echo "$as_me:$LINENO: error: cannot find input file: $f" >&5 +echo "$as_me: error: cannot find input file: $f" >&2;} + { (exit 1); exit 1; }; } + echo "$f";; + *) # Relative + if test -f "$f"; then + # Build tree + echo "$f" + elif test -f "$srcdir/$f"; then + # Source tree + echo "$srcdir/$f" + else + # /dev/null tree + { { echo "$as_me:$LINENO: error: cannot find input file: $f" >&5 +echo "$as_me: error: cannot find input file: $f" >&2;} + { (exit 1); exit 1; }; } + fi;; + esac + done` || { (exit 1); exit 1; } +_ACEOF +cat >>$CONFIG_STATUS <<_ACEOF + sed "$ac_vpsub +$extrasub +_ACEOF +cat >>$CONFIG_STATUS <<\_ACEOF +:t +/@[a-zA-Z_][a-zA-Z_0-9]*@/!b +s,@configure_input@,$configure_input,;t t +s,@srcdir@,$ac_srcdir,;t t +s,@abs_srcdir@,$ac_abs_srcdir,;t t +s,@top_srcdir@,$ac_top_srcdir,;t t +s,@abs_top_srcdir@,$ac_abs_top_srcdir,;t t +s,@builddir@,$ac_builddir,;t t +s,@abs_builddir@,$ac_abs_builddir,;t t +s,@top_builddir@,$ac_top_builddir,;t t +s,@abs_top_builddir@,$ac_abs_top_builddir,;t t +s,@INSTALL@,$ac_INSTALL,;t t +" $ac_file_inputs | (eval "$ac_sed_cmds") >$tmp/out + rm -f $tmp/stdin + if test x"$ac_file" != x-; then + mv $tmp/out $ac_file + else + cat $tmp/out + rm -f $tmp/out + fi + +done +_ACEOF +cat >>$CONFIG_STATUS <<\_ACEOF + +# +# CONFIG_HEADER section. +# + +# These sed commands are passed to sed as "A NAME B NAME C VALUE D", where +# NAME is the cpp macro being defined and VALUE is the value it is being given. +# +# ac_d sets the value in "#define NAME VALUE" lines. +ac_dA='s,^\([ ]*\)#\([ ]*define[ ][ ]*\)' +ac_dB='[ ].*$,\1#\2' +ac_dC=' ' +ac_dD=',;t' +# ac_u turns "#undef NAME" without trailing blanks into "#define NAME VALUE". +ac_uA='s,^\([ ]*\)#\([ ]*\)undef\([ ][ ]*\)' +ac_uB='$,\1#\2define\3' +ac_uC=' ' +ac_uD=',;t' + +for ac_file in : $CONFIG_HEADERS; do test "x$ac_file" = x: && continue + # Support "outfile[:infile[:infile...]]", defaulting infile="outfile.in". + case $ac_file in + - | *:- | *:-:* ) # input from stdin + cat >$tmp/stdin + ac_file_in=`echo "$ac_file" | sed 's,[^:]*:,,'` + ac_file=`echo "$ac_file" | sed 's,:.*,,'` ;; + *:* ) ac_file_in=`echo "$ac_file" | sed 's,[^:]*:,,'` + ac_file=`echo "$ac_file" | sed 's,:.*,,'` ;; + * ) ac_file_in=$ac_file.in ;; + esac + + test x"$ac_file" != x- && { echo "$as_me:$LINENO: creating $ac_file" >&5 +echo "$as_me: creating $ac_file" >&6;} + + # First look for the input files in the build tree, otherwise in the + # src tree. + ac_file_inputs=`IFS=: + for f in $ac_file_in; do + case $f in + -) echo $tmp/stdin ;; + [\\/$]*) + # Absolute (can't be DOS-style, as IFS=:) + test -f "$f" || { { echo "$as_me:$LINENO: error: cannot find input file: $f" >&5 +echo "$as_me: error: cannot find input file: $f" >&2;} + { (exit 1); exit 1; }; } + # Do quote $f, to prevent DOS paths from being IFS'd. + echo "$f";; + *) # Relative + if test -f "$f"; then + # Build tree + echo "$f" + elif test -f "$srcdir/$f"; then + # Source tree + echo "$srcdir/$f" + else + # /dev/null tree + { { echo "$as_me:$LINENO: error: cannot find input file: $f" >&5 +echo "$as_me: error: cannot find input file: $f" >&2;} + { (exit 1); exit 1; }; } + fi;; + esac + done` || { (exit 1); exit 1; } + # Remove the trailing spaces. + sed 's/[ ]*$//' $ac_file_inputs >$tmp/in + +_ACEOF + +# Transform confdefs.h into two sed scripts, `conftest.defines' and +# `conftest.undefs', that substitutes the proper values into +# config.h.in to produce config.h. The first handles `#define' +# templates, and the second `#undef' templates. +# And first: Protect against being on the right side of a sed subst in +# config.status. Protect against being in an unquoted here document +# in config.status. +rm -f conftest.defines conftest.undefs +# Using a here document instead of a string reduces the quoting nightmare. +# Putting comments in sed scripts is not portable. +# +# `end' is used to avoid that the second main sed command (meant for +# 0-ary CPP macros) applies to n-ary macro definitions. +# See the Autoconf documentation for `clear'. +cat >confdef2sed.sed <<\_ACEOF +s/[\\&,]/\\&/g +s,[\\$`],\\&,g +t clear +: clear +s,^[ ]*#[ ]*define[ ][ ]*\([^ (][^ (]*\)\(([^)]*)\)[ ]*\(.*\)$,${ac_dA}\1${ac_dB}\1\2${ac_dC}\3${ac_dD},gp +t end +s,^[ ]*#[ ]*define[ ][ ]*\([^ ][^ ]*\)[ ]*\(.*\)$,${ac_dA}\1${ac_dB}\1${ac_dC}\2${ac_dD},gp +: end +_ACEOF +# If some macros were called several times there might be several times +# the same #defines, which is useless. Nevertheless, we may not want to +# sort them, since we want the *last* AC-DEFINE to be honored. +uniq confdefs.h | sed -n -f confdef2sed.sed >conftest.defines +sed 's/ac_d/ac_u/g' conftest.defines >conftest.undefs +rm -f confdef2sed.sed + +# This sed command replaces #undef with comments. This is necessary, for +# example, in the case of _POSIX_SOURCE, which is predefined and required +# on some systems where configure will not decide to define it. +cat >>conftest.undefs <<\_ACEOF +s,^[ ]*#[ ]*undef[ ][ ]*[a-zA-Z_][a-zA-Z_0-9]*,/* & */, +_ACEOF + +# Break up conftest.defines because some shells have a limit on the size +# of here documents, and old seds have small limits too (100 cmds). +echo ' # Handle all the #define templates only if necessary.' >>$CONFIG_STATUS +echo ' if grep "^[ ]*#[ ]*define" $tmp/in >/dev/null; then' >>$CONFIG_STATUS +echo ' # If there are no defines, we may have an empty if/fi' >>$CONFIG_STATUS +echo ' :' >>$CONFIG_STATUS +rm -f conftest.tail +while grep . conftest.defines >/dev/null +do + # Write a limited-size here document to $tmp/defines.sed. + echo ' cat >$tmp/defines.sed <>$CONFIG_STATUS + # Speed up: don't consider the non `#define' lines. + echo '/^[ ]*#[ ]*define/!b' >>$CONFIG_STATUS + # Work around the forget-to-reset-the-flag bug. + echo 't clr' >>$CONFIG_STATUS + echo ': clr' >>$CONFIG_STATUS + sed ${ac_max_here_lines}q conftest.defines >>$CONFIG_STATUS + echo 'CEOF + sed -f $tmp/defines.sed $tmp/in >$tmp/out + rm -f $tmp/in + mv $tmp/out $tmp/in +' >>$CONFIG_STATUS + sed 1,${ac_max_here_lines}d conftest.defines >conftest.tail + rm -f conftest.defines + mv conftest.tail conftest.defines +done +rm -f conftest.defines +echo ' fi # grep' >>$CONFIG_STATUS +echo >>$CONFIG_STATUS + +# Break up conftest.undefs because some shells have a limit on the size +# of here documents, and old seds have small limits too (100 cmds). +echo ' # Handle all the #undef templates' >>$CONFIG_STATUS +rm -f conftest.tail +while grep . conftest.undefs >/dev/null +do + # Write a limited-size here document to $tmp/undefs.sed. + echo ' cat >$tmp/undefs.sed <>$CONFIG_STATUS + # Speed up: don't consider the non `#undef' + echo '/^[ ]*#[ ]*undef/!b' >>$CONFIG_STATUS + # Work around the forget-to-reset-the-flag bug. + echo 't clr' >>$CONFIG_STATUS + echo ': clr' >>$CONFIG_STATUS + sed ${ac_max_here_lines}q conftest.undefs >>$CONFIG_STATUS + echo 'CEOF + sed -f $tmp/undefs.sed $tmp/in >$tmp/out + rm -f $tmp/in + mv $tmp/out $tmp/in +' >>$CONFIG_STATUS + sed 1,${ac_max_here_lines}d conftest.undefs >conftest.tail + rm -f conftest.undefs + mv conftest.tail conftest.undefs +done +rm -f conftest.undefs + +cat >>$CONFIG_STATUS <<\_ACEOF + # Let's still pretend it is `configure' which instantiates (i.e., don't + # use $as_me), people would be surprised to read: + # /* config.h. Generated by config.status. */ + if test x"$ac_file" = x-; then + echo "/* Generated by configure. */" >$tmp/config.h + else + echo "/* $ac_file. Generated by configure. */" >$tmp/config.h + fi + cat $tmp/in >>$tmp/config.h + rm -f $tmp/in + if test x"$ac_file" != x-; then + if diff $ac_file $tmp/config.h >/dev/null 2>&1; then + { echo "$as_me:$LINENO: $ac_file is unchanged" >&5 +echo "$as_me: $ac_file is unchanged" >&6;} + else + ac_dir=`(dirname "$ac_file") 2>/dev/null || +$as_expr X"$ac_file" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ + X"$ac_file" : 'X\(//\)[^/]' \| \ + X"$ac_file" : 'X\(//\)$' \| \ + X"$ac_file" : 'X\(/\)' \| \ + . : '\(.\)' 2>/dev/null || +echo X"$ac_file" | + sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ s//\1/; q; } + /^X\(\/\/\)[^/].*/{ s//\1/; q; } + /^X\(\/\/\)$/{ s//\1/; q; } + /^X\(\/\).*/{ s//\1/; q; } + s/.*/./; q'` + { if $as_mkdir_p; then + mkdir -p "$ac_dir" + else + as_dir="$ac_dir" + as_dirs= + while test ! -d "$as_dir"; do + as_dirs="$as_dir $as_dirs" + as_dir=`(dirname "$as_dir") 2>/dev/null || +$as_expr X"$as_dir" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ + X"$as_dir" : 'X\(//\)[^/]' \| \ + X"$as_dir" : 'X\(//\)$' \| \ + X"$as_dir" : 'X\(/\)' \| \ + . : '\(.\)' 2>/dev/null || +echo X"$as_dir" | + sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ s//\1/; q; } + /^X\(\/\/\)[^/].*/{ s//\1/; q; } + /^X\(\/\/\)$/{ s//\1/; q; } + /^X\(\/\).*/{ s//\1/; q; } + s/.*/./; q'` + done + test ! -n "$as_dirs" || mkdir $as_dirs + fi || { { echo "$as_me:$LINENO: error: cannot create directory \"$ac_dir\"" >&5 +echo "$as_me: error: cannot create directory \"$ac_dir\"" >&2;} + { (exit 1); exit 1; }; }; } + + rm -f $ac_file + mv $tmp/config.h $ac_file + fi + else + cat $tmp/config.h + rm -f $tmp/config.h + fi +done +_ACEOF + +cat >>$CONFIG_STATUS <<\_ACEOF + +{ (exit 0); exit 0; } +_ACEOF +chmod +x $CONFIG_STATUS +ac_clean_files=$ac_clean_files_save + + +# configure is writing to config.log, and then calls config.status. +# config.status does its own redirection, appending to config.log. +# Unfortunately, on DOS this fails, as config.log is still kept open +# by configure, so config.status won't be able to write to it; its +# output is simply discarded. So we exec the FD to /dev/null, +# effectively closing config.log, so it can be properly (re)opened and +# appended to by config.status. When coming back to configure, we +# need to make the FD available again. +if test "$no_create" != yes; then + ac_cs_success=: + ac_config_status_args= + test "$silent" = yes && + ac_config_status_args="$ac_config_status_args --quiet" + exec 5>/dev/null + $SHELL $CONFIG_STATUS $ac_config_status_args || ac_cs_success=false + exec 5>>config.log + # Use ||, not &&, to avoid exiting from the if with $? = 1, which + # would make configure fail if this is the last instruction. + $ac_cs_success || { (exit 1); exit 1; } +fi + + +#==================================================================================== + +echo "$as_me:$LINENO: result: +-=-=-=-=-=-=-=-=-=-= Configuration Complete =-=-=-=-=-=-=-=-=-=- + + Configuration summary : + + Version : ..................... ${VERSION} + Experimental code : ........... ${enable_experimental:-no} +" >&5 +echo "${ECHO_T} +-=-=-=-=-=-=-=-=-=-= Configuration Complete =-=-=-=-=-=-=-=-=-=- + + Configuration summary : + + Version : ..................... ${VERSION} + Experimental code : ........... ${enable_experimental:-no} +" >&6 + +if test x$ac_cv_c_compiler_gnu = xyes ; then + echo -e " Tools :\n" + echo " Compiler is GCC : ............. ${ac_cv_c_compiler_gnu}" + echo " GCC major version : ........... ${GCC_MAJOR_VERSION}" + if test $GCC_MAJOR_VERSION -lt 3 ; then + echo -e "\n ** This compiler version allows applications to write" + echo " ** to static strings within the library." + echo " ** Compile with GCC version 3.X to avoid this problem." + fi + fi + +if test $libdir = "\${exec_prefix}/lib" ; then + libdir="$prefix/lib" + fi + +if test $bindir = "\${exec_prefix}/bin" ; then + bindir="$prefix/bin" + fi + +echo "$as_me:$LINENO: result: + Installation directories : + + Library directory : ........... $libdir + Program directory : ........... $bindir + Pkgconfig directory : ......... $libdir/pkgconfig + HTML docs directory : ......... $htmldocdir +" >&5 +echo "${ECHO_T} + Installation directories : + + Library directory : ........... $libdir + Program directory : ........... $bindir + Pkgconfig directory : ......... $libdir/pkgconfig + HTML docs directory : ......... $htmldocdir +" >&6 + +if test x$prefix != "x/usr" ; then + echo "Compiling some other packages against libsndfile may require" + echo -e "the addition of \"$libdir/pkgconfig\" to the" + echo -e "PKG_CONFIG_PATH environment variable.\n" + fi + +#==================================================================================== + diff --git a/libs/libsndfile/configure.ac b/libs/libsndfile/configure.ac new file mode 100644 index 0000000000..c6cb55f36d --- /dev/null +++ b/libs/libsndfile/configure.ac @@ -0,0 +1,541 @@ +# Copyright (C) 1999-2006 Erik de Castro Lopo (erikd AT mega-nerd DOT com). + +dnl Require autoconf version +AC_PREREQ(2.59) + +AC_INIT([libsndfile],[ardour-special],[ardour@ardour.org]) +AC_CONFIG_SRCDIR([src/sndfile.c]) +AC_CANONICAL_TARGET([]) + +AC_CONFIG_HEADERS(src/config.h) + +AC_LANG([C]) + +#------------------------------------------------------------------------------------ +# Rules for library version information: +# +# 1. Start with version information of `0:0:0' for each libtool library. +# 2. Update the version information only immediately before a public release of +# your software. More frequent updates are unnecessary, and only guarantee +# that the current interface number gets larger faster. +# 3. If the library source code has changed at all since the last update, then +# increment revision (`c:r:a' becomes `c:r+1:a'). +# 4. If any interfaces have been added, removed, or changed since the last update, +# increment current, and set revision to 0. +# 5. If any interfaces have been added since the last public release, then increment +# age. +# 6. If any interfaces have been removed since the last public release, then set age +# to 0. + +SHARED_VERSION_INFO="1:16:0" + +AC_PROG_CC +#AM_PROG_LIBTOOL + +AC_CHECK_PROG(autogen, autogen, yes, no) + +AC_PROG_INSTALL +AC_PROG_LN_S + +AC_HEADER_STDC + +AC_CHECK_HEADERS(endian.h) +AC_CHECK_HEADERS(byteswap.h) +AC_CHECK_HEADERS(locale.h) +AC_CHECK_HEADERS(inttypes.h) + +AC_HEADER_SYS_WAIT + +AC_CHECK_DECLS(S_IRGRP) +AC_DEFINE_UNQUOTED([HAVE_DECL_S_IRGRP],${HAVE_DECL_S_IRGRP}, + [Set to 1 if S_IRGRP is defined.]) + +#==================================================================================== +# Check for support of the struct hack. + +AC_C99_FLEXIBLE_ARRAY + +if test x$ac_cv_c99_flexible_array = xyes ; then + AC_DEFINE([HAVE_FLEXIBLE_ARRAY],1, [Set to 1 if the compile supports the struct hack.]) +else + AC_MSG_WARN([[*** This compiler does not support the 1999 ISO C Standard ***]]) + AC_MSG_WARN([[*** feature known as the flexible array struct member. ***]]) + AC_DEFINE([HAVE_FLEXIBLE_ARRAY],0) + fi + +#==================================================================================== +# Couple of initializations here. Fill in real values later. + +SHLIB_VERSION_ARG="" + +#==================================================================================== +# Finished checking, handle options. + +AC_ARG_ENABLE(experimental, + AC_HELP_STRING([--enable-experimental], [enable experimental code])) + +EXPERIMENTAL_CODE=0 +if test x$enable_experimental = xyes ; then + EXPERIMENTAL_CODE=1 + fi +AC_DEFINE_UNQUOTED([ENABLE_EXPERIMENTAL_CODE],${EXPERIMENTAL_CODE}, [Set to 1 to enable experimental code.]) + +AC_ARG_ENABLE(gcc-werror, + AC_HELP_STRING([--enable-gcc-werror], [enable -Werror in all Makefiles])) + +AC_ARG_ENABLE(gcc-pipe, + AC_HELP_STRING([--disable-gcc-pipe], [disable gcc -pipe option])) + +AC_ARG_ENABLE(gcc-opt, + AC_HELP_STRING([--disable-gcc-opt], [disable gcc optimisations])) + +AC_ARG_ENABLE(cpu-clip, + AC_HELP_STRING([--disable-cpu-clip], [disable tricky cpu specific clipper])) + +AC_ARG_ENABLE(bow-docs, + AC_HELP_STRING([--enable-bow-docs], [enable black-on-white html docs])) + +AC_ARG_ENABLE(sqlite, + AC_HELP_STRING([--disable-sqlite], [disable use of sqlite])) + +AC_ARG_ENABLE(flac, + AC_HELP_STRING([--disable-flac], [disable use of FLAC])) + +AC_ARG_ENABLE(alsa, + AC_HELP_STRING([--disable-alsa], [disable use of ALSA])) + +#==================================================================================== +# Check types and their sizes. + +AC_CHECK_SIZEOF(short,2) +AC_CHECK_SIZEOF(int,4) +AC_CHECK_SIZEOF(long,4) +AC_CHECK_SIZEOF(float,4) +AC_CHECK_SIZEOF(double,4) +AC_CHECK_SIZEOF(void*,8) +AC_CHECK_SIZEOF(size_t,4) +AC_CHECK_SIZEOF(int64_t,8) +AC_CHECK_SIZEOF(long long,8) + +#==================================================================================== +# Find an appropriate type for sf_count_t. +# On systems supporting files larger than 2 Gig, sf_count_t must be a 64 bit value. +# Unfortunately there is more than one way of ensuring this so need to do some +# pretty rigourous testing here. + +unset ac_cv_sizeof_off_t + +AC_CHECK_SIZEOF(off_t,1) # Fake default value. + +case "$host_os" in + mingw*) + TYPEOF_SF_COUNT_T="__int64" + SF_COUNT_MAX="0x7FFFFFFFFFFFFFFFLL" + SIZEOF_SF_COUNT_T=8 + ;; + *) + if test "x$ac_cv_sizeof_off_t" = "x8" ; then + # If sizeof (off_t) is 8, no further checking is needed. + TYPEOF_SF_COUNT_T="off_t" + SF_COUNT_MAX="0x7FFFFFFFFFFFFFFFLL" + SIZEOF_SF_COUNT_T=8 + else + # Check for common 64 bit file offset types. + AC_CHECK_SIZEOF(loff_t,1) # Fake default value. + AC_CHECK_SIZEOF(off64_t,1) # Fake default value. + + TYPEOF_SF_COUNT_T="unknown" + if test "x$ac_cv_sizeof_loff_t" = "x8" ; then + TYPEOF_SF_COUNT_T="loff_t" + SIZEOF_SF_COUNT_T=8 + elif test "x$ac_cv_sizeof_off64_t" = "x8" ; then + TYPEOF_SF_COUNT_T="off64_t" + SIZEOF_SF_COUNT_T=8 + fi + + # Save the old sizeof (off_t) value and then unset it to see if it + # changes when Large File Support is enabled. + + pre_largefile_sizeof_off_t=$ac_cv_sizeof_off_t + unset ac_cv_sizeof_off_t + + AC_SYS_EXTRA_LARGEFILE + + if test "x$ac_cv_sys_largefile_CFLAGS" = "xno" ; then + ac_cv_sys_largefile_CFLAGS="" + fi + if test "x$ac_cv_sys_largefile_LDFLAGS" = "xno" ; then + ac_cv_sys_largefile_LDFLAGS="" + fi + if test "x$ac_cv_sys_largefile_LIBS" = "xno" ; then + ac_cv_sys_largefile_LIBS="" + fi + + AC_CHECK_SIZEOF(off_t,1) # Fake default value. + + if test "x$ac_cv_sizeof_off_t" = "x8" ; then + SF_COUNT_MAX="0x7FFFFFFFFFFFFFFFLL" + elif test "x$ac_cv_sizeof_off_t" = "x$pre_largefile_sizeof_off_t" ; then + AC_MSG_WARN([[This machine does not seem to support 64 bit file offsets.]]) + TYPEOF_SF_COUNT_T="off_t" + SIZEOF_SF_COUNT_T=$ac_cv_sizeof_off_t + elif test "x$TYPEOF_SF_COUNT_T" = "xunknown" ; then + echo + echo "*** The configure process has determined that this system is capable" + echo "*** of Large File Support but has not been able to find a type which" + echo "*** is an unambiguous 64 bit file offset." + echo "*** Please contact the author to help resolve this problem." + echo + AC_MSG_ERROR([[Bad file offset type.]]) + fi + fi + ;; + esac + +if test $SIZEOF_SF_COUNT_T = 4 ; then + SF_COUNT_MAX="0x7FFFFFFF" + fi + +AC_DEFINE_UNQUOTED([TYPEOF_SF_COUNT_T],${TYPEOF_SF_COUNT_T}, [Set to long if unknown.]) +AC_SUBST(TYPEOF_SF_COUNT_T) + +AC_DEFINE_UNQUOTED([SIZEOF_SF_COUNT_T],${SIZEOF_SF_COUNT_T}, [Set to sizeof (long) if unknown.]) +AC_SUBST(SIZEOF_SF_COUNT_T) + +AC_DEFINE_UNQUOTED([SF_COUNT_MAX],${SF_COUNT_MAX}, [Set to maximum allowed value of sf_count_t type.]) +AC_SUBST(SF_COUNT_MAX) + +AC_CHECK_TYPES(ssize_t) +AC_CHECK_SIZEOF(ssize_t,4) + +#==================================================================================== +# Determine endian-ness of target processor. + +AC_C_FIND_ENDIAN + +AC_DEFINE_UNQUOTED(CPU_IS_BIG_ENDIAN, ${ac_cv_c_big_endian}, + [Target processor is big endian.]) +AC_DEFINE_UNQUOTED(CPU_IS_LITTLE_ENDIAN, ${ac_cv_c_little_endian}, + [Target processor is little endian.]) + +#==================================================================================== +# Check for functions. + +AC_CHECK_FUNCS(malloc calloc realloc free) +AC_CHECK_FUNCS(open read write lseek pread pwrite) +AC_CHECK_FUNCS(fstat ftruncate fsync fdatasync) +AC_CHECK_FUNCS(snprintf vsnprintf) +AC_CHECK_FUNCS(gmtime gmtime_r) +AC_CHECK_FUNCS(mmap getpagesize) +AC_CHECK_FUNCS(setlocale) + +AC_CHECK_LIB([m],floor) +AC_CHECK_FUNCS(floor ceil fmod) + +case "$host_os" in + cygwin*) + AC_MSG_WARN([[Not using built-in lrint() and lrintf() because they are broken on Cygwin.]]) + ;; + *) + AC_C99_FUNC_LRINT + AC_C99_FUNC_LRINTF + + if test "x$ac_cv_c99_lrint" = "xno" ; then + if test "x$ac_cv_c99_lrintf" = "xno" ; then + AC_MSG_WARN([[*** Missing C99 standard functions lrint() and lrintf().]]) + AC_MSG_WARN([[*** This may cause benign compiler warnings on some systems (ie Solaris).]]) + fi + fi + ;; + esac + +#==================================================================================== +# Check for libsqlite3 (only used in regtest). + +ac_cv_sqlite3=no +if test x$enable_sqlite != xno ; then + PKG_CHECK_MODULES(SQLITE3, sqlite3 >= 3.2, ac_cv_sqlite3=yes, ac_cv_sqlite3=no) + fi + +if test x$ac_cv_sqlite3 = "xyes" ; then + HAVE_SQLITE3=1 +else + HAVE_SQLITE3=0 + fi + +AC_DEFINE_UNQUOTED([HAVE_SQLITE3],$HAVE_SQLITE3,[Set to 1 if you have libsqlite3.]) + +#==================================================================================== +# Determine if the processor can do clipping on float to int conversions. + +if test x$enable_cpu_clip != "xno" ; then + AC_C_CLIP_MODE +else + echo "checking processor clipping capabilities... disabled" + ac_cv_c_clip_positive=0 + ac_cv_c_clip_negative=0 + fi + +AC_DEFINE_UNQUOTED(CPU_CLIPS_POSITIVE, ${ac_cv_c_clip_positive}, + [Target processor clips on positive float to int conversion.]) +AC_DEFINE_UNQUOTED(CPU_CLIPS_NEGATIVE, ${ac_cv_c_clip_negative}, + [Target processor clips on negative float to int conversion.]) + +#==================================================================================== +# Target OS specific stuff. + +OS_SPECIFIC_CFLAGS="" +OS_SPECIFIC_LINKS="" +os_is_win32=0 +os_is_macosx=0 +use_windows_api=0 + +case "$host_os" in + darwin* | rhapsody*) + os_is_macosx=1 + OS_SPECIFIC_CFLAGS="-fpascal-strings -I/Developer/Headers/FlatCarbon" + OS_SPECIFIC_LINKS="-framework CoreAudio" + ;; + mingw*) + os_is_win32=1 + use_windows_api=1 + OS_SPECIFIC_LINKS="-lwinmm" + ;; + cygwin*) + os_is_win32=1 + OS_SPECIFIC_LINKS="-lwinmm" + ;; + esac + +AC_DEFINE_UNQUOTED(OS_IS_WIN32, ${os_is_win32}, [Set to 1 if compiling for Win32]) +AC_DEFINE_UNQUOTED(OS_IS_MACOSX, ${os_is_macosx}, [Set to 1 if compiling for MacOSX]) +AC_DEFINE_UNQUOTED(USE_WINDOWS_API, ${use_windows_api}, [Set to 1 to use the native windows API]) + +#==================================================================================== +# Check for ALSA. + +ALSA_LIBS="" + +if test x$enable_alsa != xno ; then + AC_CHECK_HEADERS(alsa/asoundlib.h) + if test x$ac_cv_header_alsa_asoundlib_h = xyes ; then + ALSA_LIBS="-lasound" + fi + fi + +#==================================================================================== +# Check for FLAC + +FLAC_LIBS="" + +if test x$enable_flac != xno ; then + AC_CHECK_HEADERS(FLAC/all.h) + if test x$ac_cv_header_FLAC_all_h = xyes ; then + AC_CHECK_LIB(FLAC, FLAC__seekable_stream_encoder_set_tell_callback, HAVE_FLAC_1_1_1="yes") + if test "x$HAVE_FLAC_1_1_1" = xyes ; then + AC_DEFINE(HAVE_FLAC_1_1_1, [1], [Define to 1 if you have libflac 1.1.1]) + fi + FLAC_LIBS="-lFLAC" + fi + fi + +#==================================================================================== +# Test for sanity when cross-compiling. + +if test x$cross_compiling = xyes ; then + AC_MSG_WARN([[******************************************************************]]) + AC_MSG_WARN([[*** We are cross-compiling, so have to assume sizeof (short) == 2 ]]) + AC_MSG_WARN([[*** and sizeof (int) == 4. If this is not the case there is no ]]) + AC_MSG_WARN([[*** chance of this working. Please contact the mantainer. ]]) + AC_MSG_WARN([[******************************************************************]]) + fi + +if test $ac_cv_sizeof_short != 2 ; then + AC_MSG_WARN([[******************************************************************]]) + AC_MSG_WARN([[*** sizeof (short) != 2. ]]) + AC_MSG_WARN([[******************************************************************]]) + fi + +if test $ac_cv_sizeof_int != 4 ; then + AC_MSG_WARN([[******************************************************************]]) + AC_MSG_WARN([[*** sizeof (int) != 4 ]]) + AC_MSG_WARN([[******************************************************************]]) + fi + +if test $ac_cv_sizeof_float != 4 ; then + AC_MSG_WARN([[******************************************************************]]) + AC_MSG_WARN([[*** sizeof (float) != 4. ]]) + AC_MSG_WARN([[******************************************************************]]) + fi + +if test $ac_cv_sizeof_double != 8 ; then + AC_MSG_WARN([[******************************************************************]]) + AC_MSG_WARN([[*** sizeof (double) != 8. ]]) + AC_MSG_WARN([[******************************************************************]]) + fi + +if test x"$ac_cv_prog_autogen" = "xno" ; then + AC_MSG_WARN([[Touching files in directory tests/.]]) + touch tests/*.c tests/*.h + fi + +#==================================================================================== +# Settings for the HTML documentation. + +htmldocdir=$prefix/share/doc/libsndfile1-dev/html + +if test $prefix = "NONE" ; then + htmldocdir=/usr/local/share/doc/libsndfile1-dev/html +else + htmldocdir=$prefix/share/doc/libsndfile1-dev/html + fi + +if test x$enable_bow_docs = "xyes" ; then + HTML_BGCOLOUR="white" + HTML_FGCOLOUR="black" +else + HTML_BGCOLOUR="black" + HTML_FGCOLOUR="white" + fi + +#==================================================================================== +# Now use the information from the checking stage. + +if test x$ac_cv_c_compiler_gnu = xyes ; then + AC_ADD_CFLAGS(-std=gnu99) + + CFLAGS="$CFLAGS -W -Wall" + + AC_ADD_CFLAGS(-Wdeclaration-after-statement) + + if test x$enable_gcc_werror = "xyes" ; then + CFLAGS="-Werror $CFLAGS" + fi + + CFLAGS="$CFLAGS -Wstrict-prototypes -Wmissing-prototypes -Waggregate-return -Wcast-align -Wcast-qual -Wnested-externs -Wshadow -Wbad-function-cast -Wwrite-strings" + # -Wpointer-arith -Wundef -Wmissing-declarations -Winline -Wconversion" + + if test "x$enable_gcc_opt" = "xno" ; then + temp_CFLAGS=`echo $CFLAGS | sed "s/O2/O0/"` + CFLAGS=$temp_CFLAGS + AC_MSG_WARN([[*** Compiler optimisations switched off. ***]]) + fi + + # OS specific tweaks. + case "$host_os" in + darwin* | rhapsody*) + # Disable -Wall, -pedantic and -Wshadow for Apple Darwin/Rhapsody. + # System headers on these systems are broken. + temp_CFLAGS=`echo $CFLAGS | sed "s/-Wall -pedantic//" | sed "s/-Wshadow//" | sed "s/-Waggregate-return//"` + CFLAGS=$temp_CFLAGS + SHLIB_VERSION_ARG="-Wl,-exported_symbols_list -Wl,\$(srcdir)/Symbols.darwin" + ;; + linux*) + SHLIB_VERSION_ARG="-Wl,--version-script=\$(srcdir)/Symbols.linux" + ;; + mingw*) + SHLIB_VERSION_ARG="-Wl,\$(srcdir)/libsndfile.def" + ;; + cygwin*) + SHLIB_VERSION_ARG="-Wl,\$(srcdir)/cygsndfile.def" + ;; + *) + ;; + esac + if test x$enable_gcc_pipe != "xno" ; then + CFLAGS="$CFLAGS -pipe" + fi + + AC_DEFINE([COMPILER_IS_GCC],1, [Set to 1 if the compile is GNU GCC.]) + GCC_MAJOR_VERSION=`$CC -dumpversion | sed "s/\..*//"` + AC_DEFINE_UNQUOTED([GCC_MAJOR_VERSION],${GCC_MAJOR_VERSION}, [Major version of GCC or 3 otherwise.]) + fi + +CFLAGS="$CFLAGS $OS_SPECIFIC_CFLAGS" + +if test x"$CFLAGS" = x ; then + echo "Error in configure script. CFLAGS has been screwed up." + exit + fi + +AC_SUBST(htmldocdir) +AC_SUBST(HTML_BGCOLOUR) +AC_SUBST(HTML_FGCOLOUR) + +AC_SUBST(SHLIB_VERSION_ARG) +AC_SUBST(SHARED_VERSION_INFO) +AC_SUBST(OS_SPECIFIC_CFLAGS) +AC_SUBST(OS_SPECIFIC_LINKS) +AC_SUBST(ALSA_LIBS) +AC_SUBST(FLAC_LIBS) +AC_SUBST(ENABLE_EXPERIMENTAL_CODE) + +AC_SUBST(COMPILER_IS_GCC) +AC_SUBST(GCC_MAJOR_VERSION) + +dnl The following line causes the libtool distributed with the source +dnl to be replaced if the build system has a more recent version. +AC_SUBST(LIBTOOL_DEPS) + +AC_CONFIG_FILES([ \ + src/sndfile.h + sndfile.pc \ + ]) +AC_OUTPUT + +#==================================================================================== + +AC_MSG_RESULT([ +-=-=-=-=-=-=-=-=-=-= Configuration Complete =-=-=-=-=-=-=-=-=-=- + + Configuration summary : + + Version : ..................... ${VERSION} + Experimental code : ........... ${enable_experimental:-no} +]) + +if test x$ac_cv_c_compiler_gnu = xyes ; then + echo -e " Tools :\n" + echo " Compiler is GCC : ............. ${ac_cv_c_compiler_gnu}" + echo " GCC major version : ........... ${GCC_MAJOR_VERSION}" + if test $GCC_MAJOR_VERSION -lt 3 ; then + echo -e "\n ** This compiler version allows applications to write" + echo " ** to static strings within the library." + echo " ** Compile with GCC version 3.X to avoid this problem." + fi + fi + +if test $libdir = "\${exec_prefix}/lib" ; then + libdir="$prefix/lib" + fi + +if test $bindir = "\${exec_prefix}/bin" ; then + bindir="$prefix/bin" + fi + +AC_MSG_RESULT([[ + Installation directories : + + Library directory : ........... $libdir + Program directory : ........... $bindir + Pkgconfig directory : ......... $libdir/pkgconfig + HTML docs directory : ......... $htmldocdir +]]) + +if test x$prefix != "x/usr" ; then + echo "Compiling some other packages against libsndfile may require" + echo -e "the addition of \"$libdir/pkgconfig\" to the" + echo -e "PKG_CONFIG_PATH environment variable.\n" + fi + +#==================================================================================== + +ifelse(dnl + + Do not edit or modify anything in this comment block. + The arch-tag line is a file identity tag for the GNU Arch + revision control system. + + arch-tag: 6391b316-6cfc-43c2-a18a-8defdc4ee359 + +)dnl diff --git a/libs/libsndfile/depcomp b/libs/libsndfile/depcomp new file mode 100755 index 0000000000..edb5d38efd --- /dev/null +++ b/libs/libsndfile/depcomp @@ -0,0 +1,479 @@ +#! /bin/sh + +# depcomp - compile a program generating dependencies as side-effects +# Copyright 1999, 2000, 2003 Free Software Foundation, Inc. + +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2, or (at your option) +# any later version. + +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. + +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA +# 02111-1307, USA. + +# As a special exception to the GNU General Public License, if you +# distribute this file as part of a program that contains a +# configuration script generated by Autoconf, you may include it under +# the same distribution terms that you use for the rest of that program. + +# Originally written by Alexandre Oliva . + +if test -z "$depmode" || test -z "$source" || test -z "$object"; then + echo "depcomp: Variables source, object and depmode must be set" 1>&2 + exit 1 +fi +# `libtool' can also be set to `yes' or `no'. + +if test -z "$depfile"; then + base=`echo "$object" | sed -e 's,^.*/,,' -e 's,\.\([^.]*\)$,.P\1,'` + dir=`echo "$object" | sed 's,/.*$,/,'` + if test "$dir" = "$object"; then + dir= + fi + # FIXME: should be _deps on DOS. + depfile="$dir.deps/$base" +fi + +tmpdepfile=${tmpdepfile-`echo "$depfile" | sed 's/\.\([^.]*\)$/.T\1/'`} + +rm -f "$tmpdepfile" + +# Some modes work just like other modes, but use different flags. We +# parameterize here, but still list the modes in the big case below, +# to make depend.m4 easier to write. Note that we *cannot* use a case +# here, because this file can only contain one case statement. +if test "$depmode" = hp; then + # HP compiler uses -M and no extra arg. + gccflag=-M + depmode=gcc +fi + +if test "$depmode" = dashXmstdout; then + # This is just like dashmstdout with a different argument. + dashmflag=-xM + depmode=dashmstdout +fi + +case "$depmode" in +gcc3) +## gcc 3 implements dependency tracking that does exactly what +## we want. Yay! Note: for some reason libtool 1.4 doesn't like +## it if -MD -MP comes after the -MF stuff. Hmm. + "$@" -MT "$object" -MD -MP -MF "$tmpdepfile" + stat=$? + if test $stat -eq 0; then : + else + rm -f "$tmpdepfile" + exit $stat + fi + mv "$tmpdepfile" "$depfile" + ;; + +gcc) +## There are various ways to get dependency output from gcc. Here's +## why we pick this rather obscure method: +## - Don't want to use -MD because we'd like the dependencies to end +## up in a subdir. Having to rename by hand is ugly. +## (We might end up doing this anyway to support other compilers.) +## - The DEPENDENCIES_OUTPUT environment variable makes gcc act like +## -MM, not -M (despite what the docs say). +## - Using -M directly means running the compiler twice (even worse +## than renaming). + if test -z "$gccflag"; then + gccflag=-MD, + fi + "$@" -Wp,"$gccflag$tmpdepfile" + stat=$? + if test $stat -eq 0; then : + else + rm -f "$tmpdepfile" + exit $stat + fi + rm -f "$depfile" + echo "$object : \\" > "$depfile" + alpha=ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz +## The second -e expression handles DOS-style file names with drive letters. + sed -e 's/^[^:]*: / /' \ + -e 's/^['$alpha']:\/[^:]*: / /' < "$tmpdepfile" >> "$depfile" +## This next piece of magic avoids the `deleted header file' problem. +## The problem is that when a header file which appears in a .P file +## is deleted, the dependency causes make to die (because there is +## typically no way to rebuild the header). We avoid this by adding +## dummy dependencies for each header file. Too bad gcc doesn't do +## this for us directly. + tr ' ' ' +' < "$tmpdepfile" | +## Some versions of gcc put a space before the `:'. On the theory +## that the space means something, we add a space to the output as +## well. +## Some versions of the HPUX 10.20 sed can't process this invocation +## correctly. Breaking it into two sed invocations is a workaround. + sed -e 's/^\\$//' -e '/^$/d' -e '/:$/d' | sed -e 's/$/ :/' >> "$depfile" + rm -f "$tmpdepfile" + ;; + +hp) + # This case exists only to let depend.m4 do its work. It works by + # looking at the text of this script. This case will never be run, + # since it is checked for above. + exit 1 + ;; + +sgi) + if test "$libtool" = yes; then + "$@" "-Wp,-MDupdate,$tmpdepfile" + else + "$@" -MDupdate "$tmpdepfile" + fi + stat=$? + if test $stat -eq 0; then : + else + rm -f "$tmpdepfile" + exit $stat + fi + rm -f "$depfile" + + if test -f "$tmpdepfile"; then # yes, the sourcefile depend on other files + echo "$object : \\" > "$depfile" + + # Clip off the initial element (the dependent). Don't try to be + # clever and replace this with sed code, as IRIX sed won't handle + # lines with more than a fixed number of characters (4096 in + # IRIX 6.2 sed, 8192 in IRIX 6.5). We also remove comment lines; + # the IRIX cc adds comments like `#:fec' to the end of the + # dependency line. + tr ' ' ' +' < "$tmpdepfile" \ + | sed -e 's/^.*\.o://' -e 's/#.*$//' -e '/^$/ d' | \ + tr ' +' ' ' >> $depfile + echo >> $depfile + + # The second pass generates a dummy entry for each header file. + tr ' ' ' +' < "$tmpdepfile" \ + | sed -e 's/^.*\.o://' -e 's/#.*$//' -e '/^$/ d' -e 's/$/:/' \ + >> $depfile + else + # The sourcefile does not contain any dependencies, so just + # store a dummy comment line, to avoid errors with the Makefile + # "include basename.Plo" scheme. + echo "#dummy" > "$depfile" + fi + rm -f "$tmpdepfile" + ;; + +aix) + # The C for AIX Compiler uses -M and outputs the dependencies + # in a .u file. In older versions, this file always lives in the + # current directory. Also, the AIX compiler puts `$object:' at the + # start of each line; $object doesn't have directory information. + # Version 6 uses the directory in both cases. + stripped=`echo "$object" | sed 's/\(.*\)\..*$/\1/'` + tmpdepfile="$stripped.u" + if test "$libtool" = yes; then + "$@" -Wc,-M + else + "$@" -M + fi + stat=$? + + if test -f "$tmpdepfile"; then : + else + stripped=`echo "$stripped" | sed 's,^.*/,,'` + tmpdepfile="$stripped.u" + fi + + if test $stat -eq 0; then : + else + rm -f "$tmpdepfile" + exit $stat + fi + + if test -f "$tmpdepfile"; then + outname="$stripped.o" + # Each line is of the form `foo.o: dependent.h'. + # Do two passes, one to just change these to + # `$object: dependent.h' and one to simply `dependent.h:'. + sed -e "s,^$outname:,$object :," < "$tmpdepfile" > "$depfile" + sed -e "s,^$outname: \(.*\)$,\1:," < "$tmpdepfile" >> "$depfile" + else + # The sourcefile does not contain any dependencies, so just + # store a dummy comment line, to avoid errors with the Makefile + # "include basename.Plo" scheme. + echo "#dummy" > "$depfile" + fi + rm -f "$tmpdepfile" + ;; + +icc) + # Intel's C compiler understands `-MD -MF file'. However on + # icc -MD -MF foo.d -c -o sub/foo.o sub/foo.c + # ICC 7.0 will fill foo.d with something like + # foo.o: sub/foo.c + # foo.o: sub/foo.h + # which is wrong. We want: + # sub/foo.o: sub/foo.c + # sub/foo.o: sub/foo.h + # sub/foo.c: + # sub/foo.h: + # ICC 7.1 will output + # foo.o: sub/foo.c sub/foo.h + # and will wrap long lines using \ : + # foo.o: sub/foo.c ... \ + # sub/foo.h ... \ + # ... + + "$@" -MD -MF "$tmpdepfile" + stat=$? + if test $stat -eq 0; then : + else + rm -f "$tmpdepfile" + exit $stat + fi + rm -f "$depfile" + # Each line is of the form `foo.o: dependent.h', + # or `foo.o: dep1.h dep2.h \', or ` dep3.h dep4.h \'. + # Do two passes, one to just change these to + # `$object: dependent.h' and one to simply `dependent.h:'. + sed "s,^[^:]*:,$object :," < "$tmpdepfile" > "$depfile" + # Some versions of the HPUX 10.20 sed can't process this invocation + # correctly. Breaking it into two sed invocations is a workaround. + sed 's,^[^:]*: \(.*\)$,\1,;s/^\\$//;/^$/d;/:$/d' < "$tmpdepfile" | + sed -e 's/$/ :/' >> "$depfile" + rm -f "$tmpdepfile" + ;; + +tru64) + # The Tru64 compiler uses -MD to generate dependencies as a side + # effect. `cc -MD -o foo.o ...' puts the dependencies into `foo.o.d'. + # At least on Alpha/Redhat 6.1, Compaq CCC V6.2-504 seems to put + # dependencies in `foo.d' instead, so we check for that too. + # Subdirectories are respected. + dir=`echo "$object" | sed -e 's|/[^/]*$|/|'` + test "x$dir" = "x$object" && dir= + base=`echo "$object" | sed -e 's|^.*/||' -e 's/\.o$//' -e 's/\.lo$//'` + + if test "$libtool" = yes; then + tmpdepfile1="$dir.libs/$base.lo.d" + tmpdepfile2="$dir.libs/$base.d" + "$@" -Wc,-MD + else + tmpdepfile1="$dir$base.o.d" + tmpdepfile2="$dir$base.d" + "$@" -MD + fi + + stat=$? + if test $stat -eq 0; then : + else + rm -f "$tmpdepfile1" "$tmpdepfile2" + exit $stat + fi + + if test -f "$tmpdepfile1"; then + tmpdepfile="$tmpdepfile1" + else + tmpdepfile="$tmpdepfile2" + fi + if test -f "$tmpdepfile"; then + sed -e "s,^.*\.[a-z]*:,$object:," < "$tmpdepfile" > "$depfile" + # That's a tab and a space in the []. + sed -e 's,^.*\.[a-z]*:[ ]*,,' -e 's,$,:,' < "$tmpdepfile" >> "$depfile" + else + echo "#dummy" > "$depfile" + fi + rm -f "$tmpdepfile" + ;; + +#nosideeffect) + # This comment above is used by automake to tell side-effect + # dependency tracking mechanisms from slower ones. + +dashmstdout) + # Important note: in order to support this mode, a compiler *must* + # always write the preprocessed file to stdout, regardless of -o. + "$@" || exit $? + + # Remove the call to Libtool. + if test "$libtool" = yes; then + while test $1 != '--mode=compile'; do + shift + done + shift + fi + + # Remove `-o $object'. + IFS=" " + for arg + do + case $arg in + -o) + shift + ;; + $object) + shift + ;; + *) + set fnord "$@" "$arg" + shift # fnord + shift # $arg + ;; + esac + done + + test -z "$dashmflag" && dashmflag=-M + # Require at least two characters before searching for `:' + # in the target name. This is to cope with DOS-style filenames: + # a dependency such as `c:/foo/bar' could be seen as target `c' otherwise. + "$@" $dashmflag | + sed 's:^[ ]*[^: ][^:][^:]*\:[ ]*:'"$object"'\: :' > "$tmpdepfile" + rm -f "$depfile" + cat < "$tmpdepfile" > "$depfile" + tr ' ' ' +' < "$tmpdepfile" | \ +## Some versions of the HPUX 10.20 sed can't process this invocation +## correctly. Breaking it into two sed invocations is a workaround. + sed -e 's/^\\$//' -e '/^$/d' -e '/:$/d' | sed -e 's/$/ :/' >> "$depfile" + rm -f "$tmpdepfile" + ;; + +dashXmstdout) + # This case only exists to satisfy depend.m4. It is never actually + # run, as this mode is specially recognized in the preamble. + exit 1 + ;; + +makedepend) + "$@" || exit $? + # Remove any Libtool call + if test "$libtool" = yes; then + while test $1 != '--mode=compile'; do + shift + done + shift + fi + # X makedepend + shift + cleared=no + for arg in "$@"; do + case $cleared in + no) + set ""; shift + cleared=yes ;; + esac + case "$arg" in + -D*|-I*) + set fnord "$@" "$arg"; shift ;; + # Strip any option that makedepend may not understand. Remove + # the object too, otherwise makedepend will parse it as a source file. + -*|$object) + ;; + *) + set fnord "$@" "$arg"; shift ;; + esac + done + obj_suffix="`echo $object | sed 's/^.*\././'`" + touch "$tmpdepfile" + ${MAKEDEPEND-makedepend} -o"$obj_suffix" -f"$tmpdepfile" "$@" + rm -f "$depfile" + cat < "$tmpdepfile" > "$depfile" + sed '1,2d' "$tmpdepfile" | tr ' ' ' +' | \ +## Some versions of the HPUX 10.20 sed can't process this invocation +## correctly. Breaking it into two sed invocations is a workaround. + sed -e 's/^\\$//' -e '/^$/d' -e '/:$/d' | sed -e 's/$/ :/' >> "$depfile" + rm -f "$tmpdepfile" "$tmpdepfile".bak + ;; + +cpp) + # Important note: in order to support this mode, a compiler *must* + # always write the preprocessed file to stdout. + "$@" || exit $? + + # Remove the call to Libtool. + if test "$libtool" = yes; then + while test $1 != '--mode=compile'; do + shift + done + shift + fi + + # Remove `-o $object'. + IFS=" " + for arg + do + case $arg in + -o) + shift + ;; + $object) + shift + ;; + *) + set fnord "$@" "$arg" + shift # fnord + shift # $arg + ;; + esac + done + + "$@" -E | + sed -n '/^# [0-9][0-9]* "\([^"]*\)".*/ s:: \1 \\:p' | + sed '$ s: \\$::' > "$tmpdepfile" + rm -f "$depfile" + echo "$object : \\" > "$depfile" + cat < "$tmpdepfile" >> "$depfile" + sed < "$tmpdepfile" '/^$/d;s/^ //;s/ \\$//;s/$/ :/' >> "$depfile" + rm -f "$tmpdepfile" + ;; + +msvisualcpp) + # Important note: in order to support this mode, a compiler *must* + # always write the preprocessed file to stdout, regardless of -o, + # because we must use -o when running libtool. + "$@" || exit $? + IFS=" " + for arg + do + case "$arg" in + "-Gm"|"/Gm"|"-Gi"|"/Gi"|"-ZI"|"/ZI") + set fnord "$@" + shift + shift + ;; + *) + set fnord "$@" "$arg" + shift + shift + ;; + esac + done + "$@" -E | + sed -n '/^#line [0-9][0-9]* "\([^"]*\)"/ s::echo "`cygpath -u \\"\1\\"`":p' | sort | uniq > "$tmpdepfile" + rm -f "$depfile" + echo "$object : \\" > "$depfile" + . "$tmpdepfile" | sed 's% %\\ %g' | sed -n '/^\(.*\)$/ s:: \1 \\:p' >> "$depfile" + echo " " >> "$depfile" + . "$tmpdepfile" | sed 's% %\\ %g' | sed -n '/^\(.*\)$/ s::\1\::p' >> "$depfile" + rm -f "$tmpdepfile" + ;; + +none) + exec "$@" + ;; + +*) + echo "Unknown depmode $depmode" 1>&2 + exit 1 + ;; +esac + +exit 0 diff --git a/libs/libsndfile/install-sh b/libs/libsndfile/install-sh new file mode 100755 index 0000000000..6ce63b9f76 --- /dev/null +++ b/libs/libsndfile/install-sh @@ -0,0 +1,294 @@ +#!/bin/sh +# +# install - install a program, script, or datafile +# +# This originates from X11R5 (mit/util/scripts/install.sh), which was +# later released in X11R6 (xc/config/util/install.sh) with the +# following copyright and license. +# +# Copyright (C) 1994 X Consortium +# +# Permission is hereby granted, free of charge, to any person obtaining a copy +# of this software and associated documentation files (the "Software"), to +# deal in the Software without restriction, including without limitation the +# rights to use, copy, modify, merge, publish, distribute, sublicense, and/or +# sell copies of the Software, and to permit persons to whom the Software is +# furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +# X CONSORTIUM BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN +# AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNEC- +# TION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +# +# Except as contained in this notice, the name of the X Consortium shall not +# be used in advertising or otherwise to promote the sale, use or other deal- +# ings in this Software without prior written authorization from the X Consor- +# tium. +# +# +# FSF changes to this file are in the public domain. +# +# Calling this script install-sh is preferred over install.sh, to prevent +# `make' implicit rules from creating a file called install from it +# when there is no Makefile. +# +# This script is compatible with the BSD install script, but was written +# from scratch. It can only install one file at a time, a restriction +# shared with many OS's install programs. + + +# set DOITPROG to echo to test this script + +# Don't use :- since 4.3BSD and earlier shells don't like it. +doit="${DOITPROG-}" + + +# put in absolute paths if you don't have them in your path; or use env. vars. + +mvprog="${MVPROG-mv}" +cpprog="${CPPROG-cp}" +chmodprog="${CHMODPROG-chmod}" +chownprog="${CHOWNPROG-chown}" +chgrpprog="${CHGRPPROG-chgrp}" +stripprog="${STRIPPROG-strip}" +rmprog="${RMPROG-rm}" +mkdirprog="${MKDIRPROG-mkdir}" + +transformbasename="" +transform_arg="" +instcmd="$mvprog" +chmodcmd="$chmodprog 0755" +chowncmd="" +chgrpcmd="" +stripcmd="" +rmcmd="$rmprog -f" +mvcmd="$mvprog" +src="" +dst="" +dir_arg="" + +while [ x"$1" != x ]; do + case $1 in + -c) instcmd=$cpprog + shift + continue;; + + -d) dir_arg=true + shift + continue;; + + -m) chmodcmd="$chmodprog $2" + shift + shift + continue;; + + -o) chowncmd="$chownprog $2" + shift + shift + continue;; + + -g) chgrpcmd="$chgrpprog $2" + shift + shift + continue;; + + -s) stripcmd=$stripprog + shift + continue;; + + -t=*) transformarg=`echo $1 | sed 's/-t=//'` + shift + continue;; + + -b=*) transformbasename=`echo $1 | sed 's/-b=//'` + shift + continue;; + + *) if [ x"$src" = x ] + then + src=$1 + else + # this colon is to work around a 386BSD /bin/sh bug + : + dst=$1 + fi + shift + continue;; + esac +done + +if [ x"$src" = x ] +then + echo "$0: no input file specified" >&2 + exit 1 +else + : +fi + +if [ x"$dir_arg" != x ]; then + dst=$src + src="" + + if [ -d "$dst" ]; then + instcmd=: + chmodcmd="" + else + instcmd=$mkdirprog + fi +else + +# Waiting for this to be detected by the "$instcmd $src $dsttmp" command +# might cause directories to be created, which would be especially bad +# if $src (and thus $dsttmp) contains '*'. + + if [ -f "$src" ] || [ -d "$src" ] + then + : + else + echo "$0: $src does not exist" >&2 + exit 1 + fi + + if [ x"$dst" = x ] + then + echo "$0: no destination specified" >&2 + exit 1 + else + : + fi + +# If destination is a directory, append the input filename; if your system +# does not like double slashes in filenames, you may need to add some logic + + if [ -d "$dst" ] + then + dst=$dst/`basename "$src"` + else + : + fi +fi + +## this sed command emulates the dirname command +dstdir=`echo "$dst" | sed -e 's,[^/]*$,,;s,/$,,;s,^$,.,'` + +# Make sure that the destination directory exists. +# this part is taken from Noah Friedman's mkinstalldirs script + +# Skip lots of stat calls in the usual case. +if [ ! -d "$dstdir" ]; then +defaultIFS=' + ' +IFS="${IFS-$defaultIFS}" + +oIFS=$IFS +# Some sh's can't handle IFS=/ for some reason. +IFS='%' +set - `echo "$dstdir" | sed -e 's@/@%@g' -e 's@^%@/@'` +IFS=$oIFS + +pathcomp='' + +while [ $# -ne 0 ] ; do + pathcomp=$pathcomp$1 + shift + + if [ ! -d "$pathcomp" ] ; + then + $mkdirprog "$pathcomp" + else + : + fi + + pathcomp=$pathcomp/ +done +fi + +if [ x"$dir_arg" != x ] +then + $doit $instcmd "$dst" && + + if [ x"$chowncmd" != x ]; then $doit $chowncmd "$dst"; else : ; fi && + if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd "$dst"; else : ; fi && + if [ x"$stripcmd" != x ]; then $doit $stripcmd "$dst"; else : ; fi && + if [ x"$chmodcmd" != x ]; then $doit $chmodcmd "$dst"; else : ; fi +else + +# If we're going to rename the final executable, determine the name now. + + if [ x"$transformarg" = x ] + then + dstfile=`basename "$dst"` + else + dstfile=`basename "$dst" $transformbasename | + sed $transformarg`$transformbasename + fi + +# don't allow the sed command to completely eliminate the filename + + if [ x"$dstfile" = x ] + then + dstfile=`basename "$dst"` + else + : + fi + +# Make a couple of temp file names in the proper directory. + + dsttmp=$dstdir/_inst.$$_ + rmtmp=$dstdir/_rm.$$_ + +# Trap to clean up temp files at exit. + + trap 'status=$?; rm -f "$dsttmp" "$rmtmp" && exit $status' 0 + trap '(exit $?); exit' 1 2 13 15 + +# Move or copy the file name to the temp name + + $doit $instcmd "$src" "$dsttmp" && + +# and set any options; do chmod last to preserve setuid bits + +# If any of these fail, we abort the whole thing. If we want to +# ignore errors from any of these, just make sure not to ignore +# errors from the above "$doit $instcmd $src $dsttmp" command. + + if [ x"$chowncmd" != x ]; then $doit $chowncmd "$dsttmp"; else :;fi && + if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd "$dsttmp"; else :;fi && + if [ x"$stripcmd" != x ]; then $doit $stripcmd "$dsttmp"; else :;fi && + if [ x"$chmodcmd" != x ]; then $doit $chmodcmd "$dsttmp"; else :;fi && + +# Now remove or move aside any old file at destination location. We try this +# two ways since rm can't unlink itself on some systems and the destination +# file might be busy for other reasons. In this case, the final cleanup +# might fail but the new file should still install successfully. + +{ + if [ -f "$dstdir/$dstfile" ] + then + $doit $rmcmd -f "$dstdir/$dstfile" 2>/dev/null || + $doit $mvcmd -f "$dstdir/$dstfile" "$rmtmp" 2>/dev/null || + { + echo "$0: cannot unlink or rename $dstdir/$dstfile" >&2 + (exit 1); exit + } + else + : + fi +} && + +# Now rename the file to the real destination. + + $doit $mvcmd "$dsttmp" "$dstdir/$dstfile" + +fi && + +# The final little trick to "correctly" pass the exit status to the exit trap. + +{ + (exit 0); exit +} diff --git a/libs/libsndfile/libsndfile.spec.in b/libs/libsndfile/libsndfile.spec.in new file mode 100644 index 0000000000..ad47a5f3f8 --- /dev/null +++ b/libs/libsndfile/libsndfile.spec.in @@ -0,0 +1,69 @@ + +%define name @PACKAGE@ +%define version @VERSION@ +%define release 1 + +Summary: A library to handle various audio file formats. +Name: %{name} +Version: %{version} +Release: %{release} +Copyright: LGPL +Group: Libraries/Sound +Source: http://www.mega-nerd.com/libsndfile/libsndfile-%{version}.tar.gz +URL: http://www.mega-nerd.com/libsndfile/ +BuildRoot: /var/tmp/%{name}-%{version} + +%description +libsndfile is a C library for reading and writing sound files such as +AIFF, AU and WAV files through one standard interface. It can currently +read/write 8, 16, 24 and 32-bit PCM files as well as 32-bit floating +point WAV files and a number of compressed formats. + +%package devel +Summary: Libraries, includes, etc to develop libsndfile applications +Group: Libraries + +%description devel +Libraries, include files, etc you can use to develop libsndfile applications. + +%prep +%setup + +%build +%configure +make + +%install +if [ -d $RPM_BUILD_ROOT ]; then rm -rf $RPM_BUILD_ROOT; fi +mkdir -p $RPM_BUILD_ROOT +make DESTDIR=$RPM_BUILD_ROOT install +%clean +if [ -d $RPM_BUILD_ROOT ]; then rm -rf $RPM_BUILD_ROOT; fi + +%files +%defattr(-,root,root) +%doc AUTHORS COPYING ChangeLog INSTALL NEWS README TODO doc +%{_libdir}/libsndfile.so.* +%{_bindir}/* +%{_mandir}/man1/* +%{_datadir}/octave/site/m/* +%{_defaultdocdir}/libsndfile1-dev/html/* + +%files devel +%defattr(-,root,root) +%{_libdir}/libsndfile.a +%{_libdir}/libsndfile.la +%{_libdir}/libsndfile.so +%{_includedir}/sndfile.h +%{_libdir}/pkgconfig/sndfile.pc + +%changelog +* Sun May 15 2005 Erik de Castro Lopo +- Add html files to the files section. +* Tue Sep 16 2003 Erik de Castro Lopo +- Apply corrections from Andrew Schultz. +* Mon Oct 21 2002 Erik de Castro Lopo +- Force installation of sndfile.pc file. +* Thu Jul 6 2000 Josh Green +- Created libsndfile.spec.in + diff --git a/libs/libsndfile/missing b/libs/libsndfile/missing new file mode 100755 index 0000000000..fc54c64ec9 --- /dev/null +++ b/libs/libsndfile/missing @@ -0,0 +1,336 @@ +#! /bin/sh +# Common stub for a few missing GNU programs while installing. +# Copyright (C) 1996, 1997, 1999, 2000, 2002, 2003 Free Software Foundation, Inc. +# Originally by Fran,cois Pinard , 1996. + +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2, or (at your option) +# any later version. + +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. + +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA +# 02111-1307, USA. + +# As a special exception to the GNU General Public License, if you +# distribute this file as part of a program that contains a +# configuration script generated by Autoconf, you may include it under +# the same distribution terms that you use for the rest of that program. + +if test $# -eq 0; then + echo 1>&2 "Try \`$0 --help' for more information" + exit 1 +fi + +run=: + +# In the cases where this matters, `missing' is being run in the +# srcdir already. +if test -f configure.ac; then + configure_ac=configure.ac +else + configure_ac=configure.in +fi + +case "$1" in +--run) + # Try to run requested program, and just exit if it succeeds. + run= + shift + "$@" && exit 0 + ;; +esac + +# If it does not exist, or fails to run (possibly an outdated version), +# try to emulate it. +case "$1" in + + -h|--h|--he|--hel|--help) + echo "\ +$0 [OPTION]... PROGRAM [ARGUMENT]... + +Handle \`PROGRAM [ARGUMENT]...' for when PROGRAM is missing, or return an +error status if there is no known handling for PROGRAM. + +Options: + -h, --help display this help and exit + -v, --version output version information and exit + --run try to run the given command, and emulate it if it fails + +Supported PROGRAM values: + aclocal touch file \`aclocal.m4' + autoconf touch file \`configure' + autoheader touch file \`config.h.in' + automake touch all \`Makefile.in' files + bison create \`y.tab.[ch]', if possible, from existing .[ch] + flex create \`lex.yy.c', if possible, from existing .c + help2man touch the output file + lex create \`lex.yy.c', if possible, from existing .c + makeinfo touch the output file + tar try tar, gnutar, gtar, then tar without non-portable flags + yacc create \`y.tab.[ch]', if possible, from existing .[ch]" + ;; + + -v|--v|--ve|--ver|--vers|--versi|--versio|--version) + echo "missing 0.4 - GNU automake" + ;; + + -*) + echo 1>&2 "$0: Unknown \`$1' option" + echo 1>&2 "Try \`$0 --help' for more information" + exit 1 + ;; + + aclocal*) + if test -z "$run" && ($1 --version) > /dev/null 2>&1; then + # We have it, but it failed. + exit 1 + fi + + echo 1>&2 "\ +WARNING: \`$1' is missing on your system. You should only need it if + you modified \`acinclude.m4' or \`${configure_ac}'. You might want + to install the \`Automake' and \`Perl' packages. Grab them from + any GNU archive site." + touch aclocal.m4 + ;; + + autoconf) + if test -z "$run" && ($1 --version) > /dev/null 2>&1; then + # We have it, but it failed. + exit 1 + fi + + echo 1>&2 "\ +WARNING: \`$1' is missing on your system. You should only need it if + you modified \`${configure_ac}'. You might want to install the + \`Autoconf' and \`GNU m4' packages. Grab them from any GNU + archive site." + touch configure + ;; + + autoheader) + if test -z "$run" && ($1 --version) > /dev/null 2>&1; then + # We have it, but it failed. + exit 1 + fi + + echo 1>&2 "\ +WARNING: \`$1' is missing on your system. You should only need it if + you modified \`acconfig.h' or \`${configure_ac}'. You might want + to install the \`Autoconf' and \`GNU m4' packages. Grab them + from any GNU archive site." + files=`sed -n 's/^[ ]*A[CM]_CONFIG_HEADER(\([^)]*\)).*/\1/p' ${configure_ac}` + test -z "$files" && files="config.h" + touch_files= + for f in $files; do + case "$f" in + *:*) touch_files="$touch_files "`echo "$f" | + sed -e 's/^[^:]*://' -e 's/:.*//'`;; + *) touch_files="$touch_files $f.in";; + esac + done + touch $touch_files + ;; + + automake*) + if test -z "$run" && ($1 --version) > /dev/null 2>&1; then + # We have it, but it failed. + exit 1 + fi + + echo 1>&2 "\ +WARNING: \`$1' is missing on your system. You should only need it if + you modified \`Makefile.am', \`acinclude.m4' or \`${configure_ac}'. + You might want to install the \`Automake' and \`Perl' packages. + Grab them from any GNU archive site." + find . -type f -name Makefile.am -print | + sed 's/\.am$/.in/' | + while read f; do touch "$f"; done + ;; + + autom4te) + if test -z "$run" && ($1 --version) > /dev/null 2>&1; then + # We have it, but it failed. + exit 1 + fi + + echo 1>&2 "\ +WARNING: \`$1' is needed, and you do not seem to have it handy on your + system. You might have modified some files without having the + proper tools for further handling them. + You can get \`$1' as part of \`Autoconf' from any GNU + archive site." + + file=`echo "$*" | sed -n 's/.*--output[ =]*\([^ ]*\).*/\1/p'` + test -z "$file" && file=`echo "$*" | sed -n 's/.*-o[ ]*\([^ ]*\).*/\1/p'` + if test -f "$file"; then + touch $file + else + test -z "$file" || exec >$file + echo "#! /bin/sh" + echo "# Created by GNU Automake missing as a replacement of" + echo "# $ $@" + echo "exit 0" + chmod +x $file + exit 1 + fi + ;; + + bison|yacc) + echo 1>&2 "\ +WARNING: \`$1' is missing on your system. You should only need it if + you modified a \`.y' file. You may need the \`Bison' package + in order for those modifications to take effect. You can get + \`Bison' from any GNU archive site." + rm -f y.tab.c y.tab.h + if [ $# -ne 1 ]; then + eval LASTARG="\${$#}" + case "$LASTARG" in + *.y) + SRCFILE=`echo "$LASTARG" | sed 's/y$/c/'` + if [ -f "$SRCFILE" ]; then + cp "$SRCFILE" y.tab.c + fi + SRCFILE=`echo "$LASTARG" | sed 's/y$/h/'` + if [ -f "$SRCFILE" ]; then + cp "$SRCFILE" y.tab.h + fi + ;; + esac + fi + if [ ! -f y.tab.h ]; then + echo >y.tab.h + fi + if [ ! -f y.tab.c ]; then + echo 'main() { return 0; }' >y.tab.c + fi + ;; + + lex|flex) + echo 1>&2 "\ +WARNING: \`$1' is missing on your system. You should only need it if + you modified a \`.l' file. You may need the \`Flex' package + in order for those modifications to take effect. You can get + \`Flex' from any GNU archive site." + rm -f lex.yy.c + if [ $# -ne 1 ]; then + eval LASTARG="\${$#}" + case "$LASTARG" in + *.l) + SRCFILE=`echo "$LASTARG" | sed 's/l$/c/'` + if [ -f "$SRCFILE" ]; then + cp "$SRCFILE" lex.yy.c + fi + ;; + esac + fi + if [ ! -f lex.yy.c ]; then + echo 'main() { return 0; }' >lex.yy.c + fi + ;; + + help2man) + if test -z "$run" && ($1 --version) > /dev/null 2>&1; then + # We have it, but it failed. + exit 1 + fi + + echo 1>&2 "\ +WARNING: \`$1' is missing on your system. You should only need it if + you modified a dependency of a manual page. You may need the + \`Help2man' package in order for those modifications to take + effect. You can get \`Help2man' from any GNU archive site." + + file=`echo "$*" | sed -n 's/.*-o \([^ ]*\).*/\1/p'` + if test -z "$file"; then + file=`echo "$*" | sed -n 's/.*--output=\([^ ]*\).*/\1/p'` + fi + if [ -f "$file" ]; then + touch $file + else + test -z "$file" || exec >$file + echo ".ab help2man is required to generate this page" + exit 1 + fi + ;; + + makeinfo) + if test -z "$run" && (makeinfo --version) > /dev/null 2>&1; then + # We have makeinfo, but it failed. + exit 1 + fi + + echo 1>&2 "\ +WARNING: \`$1' is missing on your system. You should only need it if + you modified a \`.texi' or \`.texinfo' file, or any other file + indirectly affecting the aspect of the manual. The spurious + call might also be the consequence of using a buggy \`make' (AIX, + DU, IRIX). You might want to install the \`Texinfo' package or + the \`GNU make' package. Grab either from any GNU archive site." + file=`echo "$*" | sed -n 's/.*-o \([^ ]*\).*/\1/p'` + if test -z "$file"; then + file=`echo "$*" | sed 's/.* \([^ ]*\) *$/\1/'` + file=`sed -n '/^@setfilename/ { s/.* \([^ ]*\) *$/\1/; p; q; }' $file` + fi + touch $file + ;; + + tar) + shift + if test -n "$run"; then + echo 1>&2 "ERROR: \`tar' requires --run" + exit 1 + fi + + # We have already tried tar in the generic part. + # Look for gnutar/gtar before invocation to avoid ugly error + # messages. + if (gnutar --version > /dev/null 2>&1); then + gnutar "$@" && exit 0 + fi + if (gtar --version > /dev/null 2>&1); then + gtar "$@" && exit 0 + fi + firstarg="$1" + if shift; then + case "$firstarg" in + *o*) + firstarg=`echo "$firstarg" | sed s/o//` + tar "$firstarg" "$@" && exit 0 + ;; + esac + case "$firstarg" in + *h*) + firstarg=`echo "$firstarg" | sed s/h//` + tar "$firstarg" "$@" && exit 0 + ;; + esac + fi + + echo 1>&2 "\ +WARNING: I can't seem to be able to run \`tar' with the given arguments. + You may want to install GNU tar or Free paxutils, or check the + command line arguments." + exit 1 + ;; + + *) + echo 1>&2 "\ +WARNING: \`$1' is needed, and you do not seem to have it handy on your + system. You might have modified some files without having the + proper tools for further handling them. Check the \`README' file, + it often tells you about the needed prerequisites for installing + this package. You may also peek at any GNU archive site, in case + some other package would contain this missing \`$1' program." + exit 1 + ;; +esac + +exit 0 diff --git a/libs/libsndfile/mkinstalldirs b/libs/libsndfile/mkinstalldirs new file mode 100755 index 0000000000..d2d5f21b61 --- /dev/null +++ b/libs/libsndfile/mkinstalldirs @@ -0,0 +1,111 @@ +#! /bin/sh +# mkinstalldirs --- make directory hierarchy +# Author: Noah Friedman +# Created: 1993-05-16 +# Public domain + +errstatus=0 +dirmode="" + +usage="\ +Usage: mkinstalldirs [-h] [--help] [-m mode] dir ..." + +# process command line arguments +while test $# -gt 0 ; do + case $1 in + -h | --help | --h*) # -h for help + echo "$usage" 1>&2 + exit 0 + ;; + -m) # -m PERM arg + shift + test $# -eq 0 && { echo "$usage" 1>&2; exit 1; } + dirmode=$1 + shift + ;; + --) # stop option processing + shift + break + ;; + -*) # unknown option + echo "$usage" 1>&2 + exit 1 + ;; + *) # first non-opt arg + break + ;; + esac +done + +for file +do + if test -d "$file"; then + shift + else + break + fi +done + +case $# in + 0) exit 0 ;; +esac + +case $dirmode in + '') + if mkdir -p -- . 2>/dev/null; then + echo "mkdir -p -- $*" + exec mkdir -p -- "$@" + fi + ;; + *) + if mkdir -m "$dirmode" -p -- . 2>/dev/null; then + echo "mkdir -m $dirmode -p -- $*" + exec mkdir -m "$dirmode" -p -- "$@" + fi + ;; +esac + +for file +do + set fnord `echo ":$file" | sed -ne 's/^:\//#/;s/^://;s/\// /g;s/^#/\//;p'` + shift + + pathcomp= + for d + do + pathcomp="$pathcomp$d" + case $pathcomp in + -*) pathcomp=./$pathcomp ;; + esac + + if test ! -d "$pathcomp"; then + echo "mkdir $pathcomp" + + mkdir "$pathcomp" || lasterr=$? + + if test ! -d "$pathcomp"; then + errstatus=$lasterr + else + if test ! -z "$dirmode"; then + echo "chmod $dirmode $pathcomp" + lasterr="" + chmod "$dirmode" "$pathcomp" || lasterr=$? + + if test ! -z "$lasterr"; then + errstatus=$lasterr + fi + fi + fi + fi + + pathcomp="$pathcomp/" + done +done + +exit $errstatus + +# Local Variables: +# mode: shell-script +# sh-indentation: 2 +# End: +# mkinstalldirs ends here diff --git a/libs/libsndfile/sndfile.pc.in b/libs/libsndfile/sndfile.pc.in new file mode 100644 index 0000000000..f2a833bddb --- /dev/null +++ b/libs/libsndfile/sndfile.pc.in @@ -0,0 +1,11 @@ +prefix=@prefix@ +exec_prefix=@exec_prefix@ +libdir=@libdir@ +includedir=@includedir@ + +Name: sndfile +Description: A library for reading and writing audio files +Requires: +Version: @VERSION@ +Libs: -L${libdir} -lsndfile +Cflags: -I${includedir} diff --git a/libs/libsndfile/src/G72x/ChangeLog b/libs/libsndfile/src/G72x/ChangeLog new file mode 100644 index 0000000000..aa108dff7f --- /dev/null +++ b/libs/libsndfile/src/G72x/ChangeLog @@ -0,0 +1,50 @@ +2001-06-05 Erik de Castro Lopo + + * g72x.c + Added {} in function update () to prevent 'ambiguous else' warning messages. + +2000-07-14 Erik de Castro Lopo + + * g72x.c + Modified g72x_init_state () to fit in with the new structure of the code. + Implemented g72x_encode_block () and g72x_decode_block (). + +2000-07-12 Erik de Castro Lopo + + * g72x.h + Moved nearly all definitions and function prototypes from this file have been + moved to private.h. + Added an enum defining the 4 different G72x ADPCM codecs. + Added new function prototypes to define a cleaner interface to the encoder + and decoder. This new interface also allows samples to be processed in blocks + rather than on a sample by sample basis like the original code. + + * private.h + Added prototypes moved from g72x.h. + Changed struct g72x_state to a typedef struct { .. } G72x_PRIVATE. + Added fields to G72x_PRIVATE required for working on blocks of samples. + +2000-06-07 Erik de Castro Lopo + + * g72x.c + Fixed all compiler warnings. + Removed functions tandem_adjust() which is not required by libsndfile. + + * g721.c + Fixed all compiler warnings. + Removed functions tandem_adjust_alaw() and tandem_adjust_ulaw () which are not + required by libsndfile. + Removed second parameter to g721_encoder () which is not required. + + * g72x.h + Removed in_coding and out_coding parameters from all functions. These allowed + g72x encoding/decoding to/from A-law or u-law and are not required by libsndfile. + Removed unneeded defines for A-law, u-law and linear encoding. + + * g723_16.c + Removed second parameter (in_coding) for g723_16_encoder(). + Removed second parameter (out_coding) for g723_16_decoder(). + + * private.h + New file containing prototypes and tyepdefs private to G72x code. + diff --git a/libs/libsndfile/src/G72x/README b/libs/libsndfile/src/G72x/README new file mode 100644 index 0000000000..e69de29bb2 diff --git a/libs/libsndfile/src/G72x/README.original b/libs/libsndfile/src/G72x/README.original new file mode 100644 index 0000000000..23b0e7dd50 --- /dev/null +++ b/libs/libsndfile/src/G72x/README.original @@ -0,0 +1,94 @@ +The files in this directory comprise ANSI-C language reference implementations +of the CCITT (International Telegraph and Telephone Consultative Committee) +G.711, G.721 and G.723 voice compressions. They have been tested on Sun +SPARCstations and passed 82 out of 84 test vectors published by CCITT +(Dec. 20, 1988) for G.721 and G.723. [The two remaining test vectors, +which the G.721 decoder implementation for u-law samples did not pass, +may be in error because they are identical to two other vectors for G.723_40.] + +This source code is released by Sun Microsystems, Inc. to the public domain. +Please give your acknowledgement in product literature if this code is used +in your product implementation. + +Sun Microsystems supports some CCITT audio formats in Solaris 2.0 system +software. However, Sun's implementations have been optimized for higher +performance on SPARCstations. + + +The source files for CCITT conversion routines in this directory are: + + g72x.h header file for g721.c, g723_24.c and g723_40.c + g711.c CCITT G.711 u-law and A-law compression + g72x.c common denominator of G.721 and G.723 ADPCM codes + g721.c CCITT G.721 32Kbps ADPCM coder (with g72x.c) + g723_24.c CCITT G.723 24Kbps ADPCM coder (with g72x.c) + g723_40.c CCITT G.723 40Kbps ADPCM coder (with g72x.c) + + +Simple conversions between u-law, A-law, and 16-bit linear PCM are invoked +as follows: + + unsigned char ucode, acode; + short pcm_val; + + ucode = linear2ulaw(pcm_val); + ucode = alaw2ulaw(acode); + + acode = linear2alaw(pcm_val); + acode = ulaw2alaw(ucode); + + pcm_val = ulaw2linear(ucode); + pcm_val = alaw2linear(acode); + + +The other CCITT compression routines are invoked as follows: + + #include "g72x.h" + + struct g72x_state state; + int sample, code; + + g72x_init_state(&state); + code = {g721,g723_24,g723_40}_encoder(sample, coding, &state); + sample = {g721,g723_24,g723_40}_decoder(code, coding, &state); + +where + coding = AUDIO_ENCODING_ULAW for 8-bit u-law samples + AUDIO_ENCODING_ALAW for 8-bit A-law samples + AUDIO_ENCODING_LINEAR for 16-bit linear PCM samples + + + +This directory also includes the following sample programs: + + encode.c CCITT ADPCM encoder + decode.c CCITT ADPCM decoder + Makefile makefile for the sample programs + + +The sample programs contain examples of how to call the various compression +routines and pack/unpack the bits. The sample programs read byte streams from +stdin and write to stdout. The input/output data is raw data (no file header +or other identifying information is embedded). The sample programs are +invoked as follows: + + encode [-3|4|5] [-a|u|l] outfile + decode [-3|4|5] [-a|u|l] outfile +where: + -3 encode to (decode from) G.723 24kbps (3-bit) data + -4 encode to (decode from) G.721 32kbps (4-bit) data [the default] + -5 encode to (decode from) G.723 40kbps (5-bit) data + -a encode from (decode to) A-law data + -u encode from (decode to) u-law data [the default] + -l encode from (decode to) 16-bit linear data + +Examples: + # Read 16-bit linear and output G.721 + encode -4 -l g721file + + # Read 40Kbps G.723 and output A-law + decode -5 -a alawfile + + # Compress and then decompress u-law data using 24Kbps G.723 + encode -3 ulawout + diff --git a/libs/libsndfile/src/G72x/g721.c b/libs/libsndfile/src/G72x/g721.c new file mode 100644 index 0000000000..4f51bb1977 --- /dev/null +++ b/libs/libsndfile/src/G72x/g721.c @@ -0,0 +1,162 @@ +/* + * This source code is a product of Sun Microsystems, Inc. and is provided + * for unrestricted use. Users may copy or modify this source code without + * charge. + * + * SUN SOURCE CODE IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING + * THE WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR + * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE. + * + * Sun source code is provided with no support and without any obligation on + * the part of Sun Microsystems, Inc. to assist in its use, correction, + * modification or enhancement. + * + * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE + * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY THIS SOFTWARE + * OR ANY PART THEREOF. + * + * In no event will Sun Microsystems, Inc. be liable for any lost revenue + * or profits or other special, indirect and consequential damages, even if + * Sun has been advised of the possibility of such damages. + * + * Sun Microsystems, Inc. + * 2550 Garcia Avenue + * Mountain View, California 94043 + */ + +/* + * g721.c + * + * Description: + * + * g721_encoder(), g721_decoder() + * + * These routines comprise an implementation of the CCITT G.721 ADPCM + * coding algorithm. Essentially, this implementation is identical to + * the bit level description except for a few deviations which + * take advantage of work station attributes, such as hardware 2's + * complement arithmetic and large memory. Specifically, certain time + * consuming operations such as multiplications are replaced + * with lookup tables and software 2's complement operations are + * replaced with hardware 2's complement. + * + * The deviation from the bit level specification (lookup tables) + * preserves the bit level performance specifications. + * + * As outlined in the G.721 Recommendation, the algorithm is broken + * down into modules. Each section of code below is preceded by + * the name of the module which it is implementing. + * + */ + +#include "g72x.h" +#include "g72x_priv.h" + +static short qtab_721[7] = {-124, 80, 178, 246, 300, 349, 400}; +/* + * Maps G.721 code word to reconstructed scale factor normalized log + * magnitude values. + */ +static short _dqlntab[16] = {-2048, 4, 135, 213, 273, 323, 373, 425, + 425, 373, 323, 273, 213, 135, 4, -2048}; + +/* Maps G.721 code word to log of scale factor multiplier. */ +static short _witab[16] = {-12, 18, 41, 64, 112, 198, 355, 1122, + 1122, 355, 198, 112, 64, 41, 18, -12}; +/* + * Maps G.721 code words to a set of values whose long and short + * term averages are computed and then compared to give an indication + * how stationary (steady state) the signal is. + */ +static short _fitab[16] = {0, 0, 0, 0x200, 0x200, 0x200, 0x600, 0xE00, + 0xE00, 0x600, 0x200, 0x200, 0x200, 0, 0, 0}; + +/* + * g721_encoder() + * + * Encodes the input vale of linear PCM, A-law or u-law data sl and returns + * the resulting code. -1 is returned for unknown input coding value. + */ +int +g721_encoder( + int sl, + G72x_STATE *state_ptr) +{ + short sezi, se, sez; /* ACCUM */ + short d; /* SUBTA */ + short sr; /* ADDB */ + short y; /* MIX */ + short dqsez; /* ADDC */ + short dq, i; + + /* linearize input sample to 14-bit PCM */ + sl >>= 2; /* 14-bit dynamic range */ + + sezi = predictor_zero(state_ptr); + sez = sezi >> 1; + se = (sezi + predictor_pole(state_ptr)) >> 1; /* estimated signal */ + + d = sl - se; /* estimation difference */ + + /* quantize the prediction difference */ + y = step_size(state_ptr); /* quantizer step size */ + i = quantize(d, y, qtab_721, 7); /* i = ADPCM code */ + + dq = reconstruct(i & 8, _dqlntab[i], y); /* quantized est diff */ + + sr = (dq < 0) ? se - (dq & 0x3FFF) : se + dq; /* reconst. signal */ + + dqsez = sr + sez - se; /* pole prediction diff. */ + + update(4, y, _witab[i] << 5, _fitab[i], dq, sr, dqsez, state_ptr); + + return (i); +} + +/* + * g721_decoder() + * + * Description: + * + * Decodes a 4-bit code of G.721 encoded data of i and + * returns the resulting linear PCM, A-law or u-law value. + * return -1 for unknown out_coding value. + */ +int +g721_decoder( + int i, + G72x_STATE *state_ptr) +{ + short sezi, sei, sez, se; /* ACCUM */ + short y; /* MIX */ + short sr; /* ADDB */ + short dq; + short dqsez; + + i &= 0x0f; /* mask to get proper bits */ + sezi = predictor_zero(state_ptr); + sez = sezi >> 1; + sei = sezi + predictor_pole(state_ptr); + se = sei >> 1; /* se = estimated signal */ + + y = step_size(state_ptr); /* dynamic quantizer step size */ + + dq = reconstruct(i & 0x08, _dqlntab[i], y); /* quantized diff. */ + + sr = (dq < 0) ? (se - (dq & 0x3FFF)) : se + dq; /* reconst. signal */ + + dqsez = sr - se + sez; /* pole prediction diff. */ + + update(4, y, _witab[i] << 5, _fitab[i], dq, sr, dqsez, state_ptr); + + /* sr was 14-bit dynamic range */ + return (sr << 2); +} +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 101b6e25-457d-490a-99ae-e2e74a26ea24 +*/ + diff --git a/libs/libsndfile/src/G72x/g723_16.c b/libs/libsndfile/src/G72x/g723_16.c new file mode 100644 index 0000000000..0c3174501c --- /dev/null +++ b/libs/libsndfile/src/G72x/g723_16.c @@ -0,0 +1,169 @@ +/* + * This source code is a product of Sun Microsystems, Inc. and is provided + * for unrestricted use. Users may copy or modify this source code without + * charge. + * + * SUN SOURCE CODE IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING + * THE WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR + * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE. + * + * Sun source code is provided with no support and without any obligation on + * the part of Sun Microsystems, Inc. to assist in its use, correction, + * modification or enhancement. + * + * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE + * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY THIS SOFTWARE + * OR ANY PART THEREOF. + * + * In no event will Sun Microsystems, Inc. be liable for any lost revenue + * or profits or other special, indirect and consequential damages, even if + * Sun has been advised of the possibility of such damages. + * + * Sun Microsystems, Inc. + * 2550 Garcia Avenue + * Mountain View, California 94043 + */ +/* 16kbps version created, used 24kbps code and changing as little as possible. + * G.726 specs are available from ITU's gopher or WWW site (http://www.itu.ch) + * If any errors are found, please contact me at mrand@tamu.edu + * -Marc Randolph + */ + +/* + * g723_16.c + * + * Description: + * + * g723_16_encoder(), g723_16_decoder() + * + * These routines comprise an implementation of the CCITT G.726 16 Kbps + * ADPCM coding algorithm. Essentially, this implementation is identical to + * the bit level description except for a few deviations which take advantage + * of workstation attributes, such as hardware 2's complement arithmetic. + * + */ + +#include "g72x.h" +#include "g72x_priv.h" + +/* + * Maps G.723_16 code word to reconstructed scale factor normalized log + * magnitude values. Comes from Table 11/G.726 + */ +static short _dqlntab[4] = { 116, 365, 365, 116}; + +/* Maps G.723_16 code word to log of scale factor multiplier. + * + * _witab[4] is actually {-22 , 439, 439, -22}, but FILTD wants it + * as WI << 5 (multiplied by 32), so we'll do that here + */ +static short _witab[4] = {-704, 14048, 14048, -704}; + +/* + * Maps G.723_16 code words to a set of values whose long and short + * term averages are computed and then compared to give an indication + * how stationary (steady state) the signal is. + */ + +/* Comes from FUNCTF */ +static short _fitab[4] = {0, 0xE00, 0xE00, 0}; + +/* Comes from quantizer decision level tables (Table 7/G.726) + */ +static short qtab_723_16[1] = {261}; + + +/* + * g723_16_encoder() + * + * Encodes a linear PCM, A-law or u-law input sample and returns its 2-bit code. + * Returns -1 if invalid input coding value. + */ +int +g723_16_encoder( + int sl, + G72x_STATE *state_ptr) +{ + short sei, sezi, se, sez; /* ACCUM */ + short d; /* SUBTA */ + short y; /* MIX */ + short sr; /* ADDB */ + short dqsez; /* ADDC */ + short dq, i; + + /* linearize input sample to 14-bit PCM */ + sl >>= 2; /* sl of 14-bit dynamic range */ + + sezi = predictor_zero(state_ptr); + sez = sezi >> 1; + sei = sezi + predictor_pole(state_ptr); + se = sei >> 1; /* se = estimated signal */ + + d = sl - se; /* d = estimation diff. */ + + /* quantize prediction difference d */ + y = step_size(state_ptr); /* quantizer step size */ + i = quantize(d, y, qtab_723_16, 1); /* i = ADPCM code */ + + /* Since quantize() only produces a three level output + * (1, 2, or 3), we must create the fourth one on our own + */ + if (i == 3) /* i code for the zero region */ + if ((d & 0x8000) == 0) /* If d > 0, i=3 isn't right... */ + i = 0; + + dq = reconstruct(i & 2, _dqlntab[i], y); /* quantized diff. */ + + sr = (dq < 0) ? se - (dq & 0x3FFF) : se + dq; /* reconstructed signal */ + + dqsez = sr + sez - se; /* pole prediction diff. */ + + update(2, y, _witab[i], _fitab[i], dq, sr, dqsez, state_ptr); + + return (i); +} + +/* + * g723_16_decoder() + * + * Decodes a 2-bit CCITT G.723_16 ADPCM code and returns + * the resulting 16-bit linear PCM, A-law or u-law sample value. + * -1 is returned if the output coding is unknown. + */ +int +g723_16_decoder( + int i, + G72x_STATE *state_ptr) +{ + short sezi, sei, sez, se; /* ACCUM */ + short y; /* MIX */ + short sr; /* ADDB */ + short dq; + short dqsez; + + i &= 0x03; /* mask to get proper bits */ + sezi = predictor_zero(state_ptr); + sez = sezi >> 1; + sei = sezi + predictor_pole(state_ptr); + se = sei >> 1; /* se = estimated signal */ + + y = step_size(state_ptr); /* adaptive quantizer step size */ + dq = reconstruct(i & 0x02, _dqlntab[i], y); /* unquantize pred diff */ + + sr = (dq < 0) ? (se - (dq & 0x3FFF)) : (se + dq); /* reconst. signal */ + + dqsez = sr - se + sez; /* pole prediction diff. */ + + update(2, y, _witab[i], _fitab[i], dq, sr, dqsez, state_ptr); + + /* sr was of 14-bit dynamic range */ + return (sr << 2); +} +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: ae265466-c3fc-4f83-bb32-edae488a5ca5 +*/ + diff --git a/libs/libsndfile/src/G72x/g723_24.c b/libs/libsndfile/src/G72x/g723_24.c new file mode 100644 index 0000000000..8748459ac4 --- /dev/null +++ b/libs/libsndfile/src/G72x/g723_24.c @@ -0,0 +1,146 @@ +/* + * This source code is a product of Sun Microsystems, Inc. and is provided + * for unrestricted use. Users may copy or modify this source code without + * charge. + * + * SUN SOURCE CODE IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING + * THE WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR + * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE. + * + * Sun source code is provided with no support and without any obligation on + * the part of Sun Microsystems, Inc. to assist in its use, correction, + * modification or enhancement. + * + * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE + * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY THIS SOFTWARE + * OR ANY PART THEREOF. + * + * In no event will Sun Microsystems, Inc. be liable for any lost revenue + * or profits or other special, indirect and consequential damages, even if + * Sun has been advised of the possibility of such damages. + * + * Sun Microsystems, Inc. + * 2550 Garcia Avenue + * Mountain View, California 94043 + */ + +/* + * g723_24.c + * + * Description: + * + * g723_24_encoder(), g723_24_decoder() + * + * These routines comprise an implementation of the CCITT G.723 24 Kbps + * ADPCM coding algorithm. Essentially, this implementation is identical to + * the bit level description except for a few deviations which take advantage + * of workstation attributes, such as hardware 2's complement arithmetic. + * + */ + +#include "g72x.h" +#include "g72x_priv.h" + +/* + * Maps G.723_24 code word to reconstructed scale factor normalized log + * magnitude values. + */ +static short _dqlntab[8] = {-2048, 135, 273, 373, 373, 273, 135, -2048}; + +/* Maps G.723_24 code word to log of scale factor multiplier. */ +static short _witab[8] = {-128, 960, 4384, 18624, 18624, 4384, 960, -128}; + +/* + * Maps G.723_24 code words to a set of values whose long and short + * term averages are computed and then compared to give an indication + * how stationary (steady state) the signal is. + */ +static short _fitab[8] = {0, 0x200, 0x400, 0xE00, 0xE00, 0x400, 0x200, 0}; + +static short qtab_723_24[3] = {8, 218, 331}; + +/* + * g723_24_encoder() + * + * Encodes a linear PCM, A-law or u-law input sample and returns its 3-bit code. + * Returns -1 if invalid input coding value. + */ +int +g723_24_encoder( + int sl, + G72x_STATE *state_ptr) +{ + short sei, sezi, se, sez; /* ACCUM */ + short d; /* SUBTA */ + short y; /* MIX */ + short sr; /* ADDB */ + short dqsez; /* ADDC */ + short dq, i; + + /* linearize input sample to 14-bit PCM */ + sl >>= 2; /* sl of 14-bit dynamic range */ + + sezi = predictor_zero(state_ptr); + sez = sezi >> 1; + sei = sezi + predictor_pole(state_ptr); + se = sei >> 1; /* se = estimated signal */ + + d = sl - se; /* d = estimation diff. */ + + /* quantize prediction difference d */ + y = step_size(state_ptr); /* quantizer step size */ + i = quantize(d, y, qtab_723_24, 3); /* i = ADPCM code */ + dq = reconstruct(i & 4, _dqlntab[i], y); /* quantized diff. */ + + sr = (dq < 0) ? se - (dq & 0x3FFF) : se + dq; /* reconstructed signal */ + + dqsez = sr + sez - se; /* pole prediction diff. */ + + update(3, y, _witab[i], _fitab[i], dq, sr, dqsez, state_ptr); + + return (i); +} + +/* + * g723_24_decoder() + * + * Decodes a 3-bit CCITT G.723_24 ADPCM code and returns + * the resulting 16-bit linear PCM, A-law or u-law sample value. + * -1 is returned if the output coding is unknown. + */ +int +g723_24_decoder( + int i, + G72x_STATE *state_ptr) +{ + short sezi, sei, sez, se; /* ACCUM */ + short y; /* MIX */ + short sr; /* ADDB */ + short dq; + short dqsez; + + i &= 0x07; /* mask to get proper bits */ + sezi = predictor_zero(state_ptr); + sez = sezi >> 1; + sei = sezi + predictor_pole(state_ptr); + se = sei >> 1; /* se = estimated signal */ + + y = step_size(state_ptr); /* adaptive quantizer step size */ + dq = reconstruct(i & 0x04, _dqlntab[i], y); /* unquantize pred diff */ + + sr = (dq < 0) ? (se - (dq & 0x3FFF)) : (se + dq); /* reconst. signal */ + + dqsez = sr - se + sez; /* pole prediction diff. */ + + update(3, y, _witab[i], _fitab[i], dq, sr, dqsez, state_ptr); + + return (sr << 2); /* sr was of 14-bit dynamic range */ +} +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 75389236-650b-4427-98f3-0df6e8fb24bc +*/ + diff --git a/libs/libsndfile/src/G72x/g723_40.c b/libs/libsndfile/src/G72x/g723_40.c new file mode 100644 index 0000000000..6ddb577dfb --- /dev/null +++ b/libs/libsndfile/src/G72x/g723_40.c @@ -0,0 +1,160 @@ +/* + * This source code is a product of Sun Microsystems, Inc. and is provided + * for unrestricted use. Users may copy or modify this source code without + * charge. + * + * SUN SOURCE CODE IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING + * THE WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR + * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE. + * + * Sun source code is provided with no support and without any obligation on + * the part of Sun Microsystems, Inc. to assist in its use, correction, + * modification or enhancement. + * + * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE + * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY THIS SOFTWARE + * OR ANY PART THEREOF. + * + * In no event will Sun Microsystems, Inc. be liable for any lost revenue + * or profits or other special, indirect and consequential damages, even if + * Sun has been advised of the possibility of such damages. + * + * Sun Microsystems, Inc. + * 2550 Garcia Avenue + * Mountain View, California 94043 + */ + +/* + * g723_40.c + * + * Description: + * + * g723_40_encoder(), g723_40_decoder() + * + * These routines comprise an implementation of the CCITT G.723 40Kbps + * ADPCM coding algorithm. Essentially, this implementation is identical to + * the bit level description except for a few deviations which + * take advantage of workstation attributes, such as hardware 2's + * complement arithmetic. + * + * The deviation from the bit level specification (lookup tables), + * preserves the bit level performance specifications. + * + * As outlined in the G.723 Recommendation, the algorithm is broken + * down into modules. Each section of code below is preceded by + * the name of the module which it is implementing. + * + */ + +#include "g72x.h" +#include "g72x_priv.h" + +/* + * Maps G.723_40 code word to ructeconstructed scale factor normalized log + * magnitude values. + */ +static short _dqlntab[32] = {-2048, -66, 28, 104, 169, 224, 274, 318, + 358, 395, 429, 459, 488, 514, 539, 566, + 566, 539, 514, 488, 459, 429, 395, 358, + 318, 274, 224, 169, 104, 28, -66, -2048}; + +/* Maps G.723_40 code word to log of scale factor multiplier. */ +static short _witab[32] = {448, 448, 768, 1248, 1280, 1312, 1856, 3200, + 4512, 5728, 7008, 8960, 11456, 14080, 16928, 22272, + 22272, 16928, 14080, 11456, 8960, 7008, 5728, 4512, + 3200, 1856, 1312, 1280, 1248, 768, 448, 448}; + +/* + * Maps G.723_40 code words to a set of values whose long and short + * term averages are computed and then compared to give an indication + * how stationary (steady state) the signal is. + */ +static short _fitab[32] = {0, 0, 0, 0, 0, 0x200, 0x200, 0x200, + 0x200, 0x200, 0x400, 0x600, 0x800, 0xA00, 0xC00, 0xC00, + 0xC00, 0xC00, 0xA00, 0x800, 0x600, 0x400, 0x200, 0x200, + 0x200, 0x200, 0x200, 0, 0, 0, 0, 0}; + +static short qtab_723_40[15] = {-122, -16, 68, 139, 198, 250, 298, 339, + 378, 413, 445, 475, 502, 528, 553}; + +/* + * g723_40_encoder() + * + * Encodes a 16-bit linear PCM, A-law or u-law input sample and retuens + * the resulting 5-bit CCITT G.723 40Kbps code. + * Returns -1 if the input coding value is invalid. + */ +int g723_40_encoder (int sl, G72x_STATE *state_ptr) +{ + short sei, sezi, se, sez; /* ACCUM */ + short d; /* SUBTA */ + short y; /* MIX */ + short sr; /* ADDB */ + short dqsez; /* ADDC */ + short dq, i; + + /* linearize input sample to 14-bit PCM */ + sl >>= 2; /* sl of 14-bit dynamic range */ + + sezi = predictor_zero(state_ptr); + sez = sezi >> 1; + sei = sezi + predictor_pole(state_ptr); + se = sei >> 1; /* se = estimated signal */ + + d = sl - se; /* d = estimation difference */ + + /* quantize prediction difference */ + y = step_size(state_ptr); /* adaptive quantizer step size */ + i = quantize(d, y, qtab_723_40, 15); /* i = ADPCM code */ + + dq = reconstruct(i & 0x10, _dqlntab[i], y); /* quantized diff */ + + sr = (dq < 0) ? se - (dq & 0x7FFF) : se + dq; /* reconstructed signal */ + + dqsez = sr + sez - se; /* dqsez = pole prediction diff. */ + + update(5, y, _witab[i], _fitab[i], dq, sr, dqsez, state_ptr); + + return (i); +} + +/* + * g723_40_decoder() + * + * Decodes a 5-bit CCITT G.723 40Kbps code and returns + * the resulting 16-bit linear PCM, A-law or u-law sample value. + * -1 is returned if the output coding is unknown. + */ +int g723_40_decoder (int i, G72x_STATE *state_ptr) +{ + short sezi, sei, sez, se; /* ACCUM */ + short y ; /* MIX */ + short sr; /* ADDB */ + short dq; + short dqsez; + + i &= 0x1f; /* mask to get proper bits */ + sezi = predictor_zero(state_ptr); + sez = sezi >> 1; + sei = sezi + predictor_pole(state_ptr); + se = sei >> 1; /* se = estimated signal */ + + y = step_size(state_ptr); /* adaptive quantizer step size */ + dq = reconstruct(i & 0x10, _dqlntab[i], y); /* estimation diff. */ + + sr = (dq < 0) ? (se - (dq & 0x7FFF)) : (se + dq); /* reconst. signal */ + + dqsez = sr - se + sez; /* pole prediction diff. */ + + update(5, y, _witab[i], _fitab[i], dq, sr, dqsez, state_ptr); + + return (sr << 2); /* sr was of 14-bit dynamic range */ +} +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: eb8d9a00-32bf-4dd2-b287-01b0336d72bf +*/ + diff --git a/libs/libsndfile/src/G72x/g72x.c b/libs/libsndfile/src/G72x/g72x.c new file mode 100644 index 0000000000..ea01d793d0 --- /dev/null +++ b/libs/libsndfile/src/G72x/g72x.c @@ -0,0 +1,652 @@ +/* + * This source code is a product of Sun Microsystems, Inc. and is provided + * for unrestricted use. Users may copy or modify this source code without + * charge. + * + * SUN SOURCE CODE IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING + * THE WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR + * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE. + * + * Sun source code is provided with no support and without any obligation on + * the part of Sun Microsystems, Inc. to assist in its use, correction, + * modification or enhancement. + * + * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE + * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY THIS SOFTWARE + * OR ANY PART THEREOF. + * + * In no event will Sun Microsystems, Inc. be liable for any lost revenue + * or profits or other special, indirect and consequential damages, even if + * Sun has been advised of the possibility of such damages. + * + * Sun Microsystems, Inc. + * 2550 Garcia Avenue + * Mountain View, California 94043 + */ + +/* + * g72x.c + * + * Common routines for G.721 and G.723 conversions. + */ + +#include +#include +#include + +#include "g72x.h" +#include "g72x_priv.h" + +static G72x_STATE * g72x_state_new (void) ; +static int unpack_bytes (int bits, int blocksize, const unsigned char * block, short * samples) ; +static int pack_bytes (int bits, const short * samples, unsigned char * block) ; + +static +short power2 [15] = +{ 1, 2, 4, 8, 0x10, 0x20, 0x40, 0x80, + 0x100, 0x200, 0x400, 0x800, 0x1000, 0x2000, 0x4000 +} ; + +/* + * quan() + * + * quantizes the input val against the table of size short integers. + * It returns i if table[i - 1] <= val < table[i]. + * + * Using linear search for simple coding. + */ +static +int quan (int val, short *table, int size) +{ + int i; + + for (i = 0; i < size; i++) + if (val < *table++) + break; + return (i); +} + +/* + * fmult() + * + * returns the integer product of the 14-bit integer "an" and + * "floating point" representation (4-bit exponent, 6-bit mantessa) "srn". + */ +static +int fmult (int an, int srn) +{ + short anmag, anexp, anmant; + short wanexp, wanmant; + short retval; + + anmag = (an > 0) ? an : ((-an) & 0x1FFF); + anexp = quan(anmag, power2, 15) - 6; + anmant = (anmag == 0) ? 32 : + (anexp >= 0) ? anmag >> anexp : anmag << -anexp; + wanexp = anexp + ((srn >> 6) & 0xF) - 13; + + /* + ** The original was : + ** wanmant = (anmant * (srn & 0x37) + 0x30) >> 4 ; + ** but could see no valid reason for the + 0x30. + ** Removed it and it improved the SNR of the codec. + */ + + wanmant = (anmant * (srn & 0x37)) >> 4 ; + + retval = (wanexp >= 0) ? ((wanmant << wanexp) & 0x7FFF) : + (wanmant >> -wanexp); + + return (((an ^ srn) < 0) ? -retval : retval); +} + +static G72x_STATE * g72x_state_new (void) +{ return calloc (1, sizeof (G72x_STATE)) ; +} + +/* + * private_init_state() + * + * This routine initializes and/or resets the G72x_PRIVATE structure + * pointed to by 'state_ptr'. + * All the initial state values are specified in the CCITT G.721 document. + */ +void private_init_state (G72x_STATE *state_ptr) +{ + int cnta; + + state_ptr->yl = 34816; + state_ptr->yu = 544; + state_ptr->dms = 0; + state_ptr->dml = 0; + state_ptr->ap = 0; + for (cnta = 0; cnta < 2; cnta++) { + state_ptr->a[cnta] = 0; + state_ptr->pk[cnta] = 0; + state_ptr->sr[cnta] = 32; + } + for (cnta = 0; cnta < 6; cnta++) { + state_ptr->b[cnta] = 0; + state_ptr->dq[cnta] = 32; + } + state_ptr->td = 0; +} /* private_init_state */ + +struct g72x_state * g72x_reader_init (int codec, int *blocksize, int *samplesperblock) +{ G72x_STATE *pstate ; + + if ((pstate = g72x_state_new ()) == NULL) + return NULL ; + + private_init_state (pstate) ; + + pstate->encoder = NULL ; + + switch (codec) + { case G723_16_BITS_PER_SAMPLE : /* 2 bits per sample. */ + pstate->decoder = g723_16_decoder ; + *blocksize = G723_16_BYTES_PER_BLOCK ; + *samplesperblock = G723_16_SAMPLES_PER_BLOCK ; + pstate->codec_bits = 2 ; + pstate->blocksize = G723_16_BYTES_PER_BLOCK ; + pstate->samplesperblock = G723_16_SAMPLES_PER_BLOCK ; + break ; + + case G723_24_BITS_PER_SAMPLE : /* 3 bits per sample. */ + pstate->decoder = g723_24_decoder ; + *blocksize = G723_24_BYTES_PER_BLOCK ; + *samplesperblock = G723_24_SAMPLES_PER_BLOCK ; + pstate->codec_bits = 3 ; + pstate->blocksize = G723_24_BYTES_PER_BLOCK ; + pstate->samplesperblock = G723_24_SAMPLES_PER_BLOCK ; + break ; + + case G721_32_BITS_PER_SAMPLE : /* 4 bits per sample. */ + pstate->decoder = g721_decoder ; + *blocksize = G721_32_BYTES_PER_BLOCK ; + *samplesperblock = G721_32_SAMPLES_PER_BLOCK ; + pstate->codec_bits = 4 ; + pstate->blocksize = G721_32_BYTES_PER_BLOCK ; + pstate->samplesperblock = G721_32_SAMPLES_PER_BLOCK ; + break ; + + case G721_40_BITS_PER_SAMPLE : /* 5 bits per sample. */ + pstate->decoder = g723_40_decoder ; + *blocksize = G721_40_BYTES_PER_BLOCK ; + *samplesperblock = G721_40_SAMPLES_PER_BLOCK ; + pstate->codec_bits = 5 ; + pstate->blocksize = G721_40_BYTES_PER_BLOCK ; + pstate->samplesperblock = G721_40_SAMPLES_PER_BLOCK ; + break ; + + default : + free (pstate) ; + return NULL ; + } ; + + return pstate ; +} /* g72x_reader_init */ + +struct g72x_state * g72x_writer_init (int codec, int *blocksize, int *samplesperblock) +{ G72x_STATE *pstate ; + + if ((pstate = g72x_state_new ()) == NULL) + return NULL ; + + private_init_state (pstate) ; + pstate->decoder = NULL ; + + switch (codec) + { case G723_16_BITS_PER_SAMPLE : /* 2 bits per sample. */ + pstate->encoder = g723_16_encoder ; + *blocksize = G723_16_BYTES_PER_BLOCK ; + *samplesperblock = G723_16_SAMPLES_PER_BLOCK ; + pstate->codec_bits = 2 ; + pstate->blocksize = G723_16_BYTES_PER_BLOCK ; + pstate->samplesperblock = G723_16_SAMPLES_PER_BLOCK ; + break ; + + case G723_24_BITS_PER_SAMPLE : /* 3 bits per sample. */ + pstate->encoder = g723_24_encoder ; + *blocksize = G723_24_BYTES_PER_BLOCK ; + *samplesperblock = G723_24_SAMPLES_PER_BLOCK ; + pstate->codec_bits = 3 ; + pstate->blocksize = G723_24_BYTES_PER_BLOCK ; + pstate->samplesperblock = G723_24_SAMPLES_PER_BLOCK ; + break ; + + case G721_32_BITS_PER_SAMPLE : /* 4 bits per sample. */ + pstate->encoder = g721_encoder ; + *blocksize = G721_32_BYTES_PER_BLOCK ; + *samplesperblock = G721_32_SAMPLES_PER_BLOCK ; + pstate->codec_bits = 4 ; + pstate->blocksize = G721_32_BYTES_PER_BLOCK ; + pstate->samplesperblock = G721_32_SAMPLES_PER_BLOCK ; + break ; + + case G721_40_BITS_PER_SAMPLE : /* 5 bits per sample. */ + pstate->encoder = g723_40_encoder ; + *blocksize = G721_40_BYTES_PER_BLOCK ; + *samplesperblock = G721_40_SAMPLES_PER_BLOCK ; + pstate->codec_bits = 5 ; + pstate->blocksize = G721_40_BYTES_PER_BLOCK ; + pstate->samplesperblock = G721_40_SAMPLES_PER_BLOCK ; + break ; + + default : + free (pstate) ; + return NULL ; + } ; + + return pstate ; +} /* g72x_writer_init */ + +int g72x_decode_block (G72x_STATE *pstate, const unsigned char *block, short *samples) +{ int k, count ; + + count = unpack_bytes (pstate->codec_bits, pstate->blocksize, block, samples) ; + + for (k = 0 ; k < count ; k++) + samples [k] = pstate->decoder (samples [k], pstate) ; + + return 0 ; +} /* g72x_decode_block */ + +int g72x_encode_block (G72x_STATE *pstate, short *samples, unsigned char *block) +{ int k, count ; + + for (k = 0 ; k < pstate->samplesperblock ; k++) + samples [k] = pstate->encoder (samples [k], pstate) ; + + count = pack_bytes (pstate->codec_bits, samples, block) ; + + return count ; +} /* g72x_encode_block */ + +/* + * predictor_zero() + * + * computes the estimated signal from 6-zero predictor. + * + */ +int predictor_zero (G72x_STATE *state_ptr) +{ + int i; + int sezi; + + sezi = fmult(state_ptr->b[0] >> 2, state_ptr->dq[0]); + for (i = 1; i < 6; i++) /* ACCUM */ + sezi += fmult(state_ptr->b[i] >> 2, state_ptr->dq[i]); + return (sezi); +} +/* + * predictor_pole() + * + * computes the estimated signal from 2-pole predictor. + * + */ +int predictor_pole(G72x_STATE *state_ptr) +{ + return (fmult(state_ptr->a[1] >> 2, state_ptr->sr[1]) + + fmult(state_ptr->a[0] >> 2, state_ptr->sr[0])); +} +/* + * step_size() + * + * computes the quantization step size of the adaptive quantizer. + * + */ +int step_size (G72x_STATE *state_ptr) +{ + int y; + int dif; + int al; + + if (state_ptr->ap >= 256) + return (state_ptr->yu); + else { + y = state_ptr->yl >> 6; + dif = state_ptr->yu - y; + al = state_ptr->ap >> 2; + if (dif > 0) + y += (dif * al) >> 6; + else if (dif < 0) + y += (dif * al + 0x3F) >> 6; + return (y); + } +} + +/* + * quantize() + * + * Given a raw sample, 'd', of the difference signal and a + * quantization step size scale factor, 'y', this routine returns the + * ADPCM codeword to which that sample gets quantized. The step + * size scale factor division operation is done in the log base 2 domain + * as a subtraction. + */ +int quantize( + int d, /* Raw difference signal sample */ + int y, /* Step size multiplier */ + short *table, /* quantization table */ + int size) /* table size of short integers */ +{ + short dqm; /* Magnitude of 'd' */ + short expon; /* Integer part of base 2 log of 'd' */ + short mant; /* Fractional part of base 2 log */ + short dl; /* Log of magnitude of 'd' */ + short dln; /* Step size scale factor normalized log */ + int i; + + /* + * LOG + * + * Compute base 2 log of 'd', and store in 'dl'. + */ + dqm = abs(d); + expon = quan(dqm >> 1, power2, 15); + mant = ((dqm << 7) >> expon) & 0x7F; /* Fractional portion. */ + dl = (expon << 7) + mant; + + /* + * SUBTB + * + * "Divide" by step size multiplier. + */ + dln = dl - (y >> 2); + + /* + * QUAN + * + * Obtain codword i for 'd'. + */ + i = quan(dln, table, size); + if (d < 0) /* take 1's complement of i */ + return ((size << 1) + 1 - i); + else if (i == 0) /* take 1's complement of 0 */ + return ((size << 1) + 1); /* new in 1988 */ + else + return (i); +} +/* + * reconstruct() + * + * Returns reconstructed difference signal 'dq' obtained from + * codeword 'i' and quantization step size scale factor 'y'. + * Multiplication is performed in log base 2 domain as addition. + */ +int +reconstruct( + int sign, /* 0 for non-negative value */ + int dqln, /* G.72x codeword */ + int y) /* Step size multiplier */ +{ + short dql; /* Log of 'dq' magnitude */ + short dex; /* Integer part of log */ + short dqt; + short dq; /* Reconstructed difference signal sample */ + + dql = dqln + (y >> 2); /* ADDA */ + + if (dql < 0) { + return ((sign) ? -0x8000 : 0); + } else { /* ANTILOG */ + dex = (dql >> 7) & 15; + dqt = 128 + (dql & 127); + dq = (dqt << 7) >> (14 - dex); + return ((sign) ? (dq - 0x8000) : dq); + } +} + + +/* + * update() + * + * updates the state variables for each output code + */ +void +update( + int code_size, /* distinguish 723_40 with others */ + int y, /* quantizer step size */ + int wi, /* scale factor multiplier */ + int fi, /* for long/short term energies */ + int dq, /* quantized prediction difference */ + int sr, /* reconstructed signal */ + int dqsez, /* difference from 2-pole predictor */ + G72x_STATE *state_ptr) /* coder state pointer */ +{ + int cnt; + short mag, expon; /* Adaptive predictor, FLOAT A */ + short a2p = 0; /* LIMC */ + short a1ul; /* UPA1 */ + short pks1; /* UPA2 */ + short fa1; + char tr; /* tone/transition detector */ + short ylint, thr2, dqthr; + short ylfrac, thr1; + short pk0; + + pk0 = (dqsez < 0) ? 1 : 0; /* needed in updating predictor poles */ + + mag = dq & 0x7FFF; /* prediction difference magnitude */ + /* TRANS */ + ylint = state_ptr->yl >> 15; /* exponent part of yl */ + ylfrac = (state_ptr->yl >> 10) & 0x1F; /* fractional part of yl */ + thr1 = (32 + ylfrac) << ylint; /* threshold */ + thr2 = (ylint > 9) ? 31 << 10 : thr1; /* limit thr2 to 31 << 10 */ + dqthr = (thr2 + (thr2 >> 1)) >> 1; /* dqthr = 0.75 * thr2 */ + if (state_ptr->td == 0) /* signal supposed voice */ + tr = 0; + else if (mag <= dqthr) /* supposed data, but small mag */ + tr = 0; /* treated as voice */ + else /* signal is data (modem) */ + tr = 1; + + /* + * Quantizer scale factor adaptation. + */ + + /* FUNCTW & FILTD & DELAY */ + /* update non-steady state step size multiplier */ + state_ptr->yu = y + ((wi - y) >> 5); + + /* LIMB */ + if (state_ptr->yu < 544) /* 544 <= yu <= 5120 */ + state_ptr->yu = 544; + else if (state_ptr->yu > 5120) + state_ptr->yu = 5120; + + /* FILTE & DELAY */ + /* update steady state step size multiplier */ + state_ptr->yl += state_ptr->yu + ((-state_ptr->yl) >> 6); + + /* + * Adaptive predictor coefficients. + */ + if (tr == 1) { /* reset a's and b's for modem signal */ + state_ptr->a[0] = 0; + state_ptr->a[1] = 0; + state_ptr->b[0] = 0; + state_ptr->b[1] = 0; + state_ptr->b[2] = 0; + state_ptr->b[3] = 0; + state_ptr->b[4] = 0; + state_ptr->b[5] = 0; + } else { /* update a's and b's */ + pks1 = pk0 ^ state_ptr->pk[0]; /* UPA2 */ + + /* update predictor pole a[1] */ + a2p = state_ptr->a[1] - (state_ptr->a[1] >> 7); + if (dqsez != 0) { + fa1 = (pks1) ? state_ptr->a[0] : -state_ptr->a[0]; + if (fa1 < -8191) /* a2p = function of fa1 */ + a2p -= 0x100; + else if (fa1 > 8191) + a2p += 0xFF; + else + a2p += fa1 >> 5; + + if (pk0 ^ state_ptr->pk[1]) + { /* LIMC */ + if (a2p <= -12160) + a2p = -12288; + else if (a2p >= 12416) + a2p = 12288; + else + a2p -= 0x80; + } + else if (a2p <= -12416) + a2p = -12288; + else if (a2p >= 12160) + a2p = 12288; + else + a2p += 0x80; + } + + /* TRIGB & DELAY */ + state_ptr->a[1] = a2p; + + /* UPA1 */ + /* update predictor pole a[0] */ + state_ptr->a[0] -= state_ptr->a[0] >> 8; + if (dqsez != 0) + { if (pks1 == 0) + state_ptr->a[0] += 192; + else + state_ptr->a[0] -= 192; + } ; + + /* LIMD */ + a1ul = 15360 - a2p; + if (state_ptr->a[0] < -a1ul) + state_ptr->a[0] = -a1ul; + else if (state_ptr->a[0] > a1ul) + state_ptr->a[0] = a1ul; + + /* UPB : update predictor zeros b[6] */ + for (cnt = 0; cnt < 6; cnt++) { + if (code_size == 5) /* for 40Kbps G.723 */ + state_ptr->b[cnt] -= state_ptr->b[cnt] >> 9; + else /* for G.721 and 24Kbps G.723 */ + state_ptr->b[cnt] -= state_ptr->b[cnt] >> 8; + if (dq & 0x7FFF) { /* XOR */ + if ((dq ^ state_ptr->dq[cnt]) >= 0) + state_ptr->b[cnt] += 128; + else + state_ptr->b[cnt] -= 128; + } + } + } + + for (cnt = 5; cnt > 0; cnt--) + state_ptr->dq[cnt] = state_ptr->dq[cnt-1]; + /* FLOAT A : convert dq[0] to 4-bit exp, 6-bit mantissa f.p. */ + if (mag == 0) { + state_ptr->dq[0] = (dq >= 0) ? 0x20 : 0xFC20; + } else { + expon = quan(mag, power2, 15); + state_ptr->dq[0] = (dq >= 0) ? + (expon << 6) + ((mag << 6) >> expon) : + (expon << 6) + ((mag << 6) >> expon) - 0x400; + } + + state_ptr->sr[1] = state_ptr->sr[0]; + /* FLOAT B : convert sr to 4-bit exp., 6-bit mantissa f.p. */ + if (sr == 0) { + state_ptr->sr[0] = 0x20; + } else if (sr > 0) { + expon = quan(sr, power2, 15); + state_ptr->sr[0] = (expon << 6) + ((sr << 6) >> expon); + } else if (sr > -32768) { + mag = -sr; + expon = quan(mag, power2, 15); + state_ptr->sr[0] = (expon << 6) + ((mag << 6) >> expon) - 0x400; + } else + state_ptr->sr[0] = (short) 0xFC20; + + /* DELAY A */ + state_ptr->pk[1] = state_ptr->pk[0]; + state_ptr->pk[0] = pk0; + + /* TONE */ + if (tr == 1) /* this sample has been treated as data */ + state_ptr->td = 0; /* next one will be treated as voice */ + else if (a2p < -11776) /* small sample-to-sample correlation */ + state_ptr->td = 1; /* signal may be data */ + else /* signal is voice */ + state_ptr->td = 0; + + /* + * Adaptation speed control. + */ + state_ptr->dms += (fi - state_ptr->dms) >> 5; /* FILTA */ + state_ptr->dml += (((fi << 2) - state_ptr->dml) >> 7); /* FILTB */ + + if (tr == 1) + state_ptr->ap = 256; + else if (y < 1536) /* SUBTC */ + state_ptr->ap += (0x200 - state_ptr->ap) >> 4; + else if (state_ptr->td == 1) + state_ptr->ap += (0x200 - state_ptr->ap) >> 4; + else if (abs((state_ptr->dms << 2) - state_ptr->dml) >= + (state_ptr->dml >> 3)) + state_ptr->ap += (0x200 - state_ptr->ap) >> 4; + else + state_ptr->ap += (-state_ptr->ap) >> 4; + + return ; +} /* update */ + +/*------------------------------------------------------------------------------ +*/ + +static int +unpack_bytes (int bits, int blocksize, const unsigned char * block, short * samples) +{ unsigned int in_buffer = 0 ; + unsigned char in_byte ; + int k, in_bits = 0, bindex = 0 ; + + for (k = 0 ; bindex <= blocksize && k < G72x_BLOCK_SIZE ; k++) + { if (in_bits < bits) + { in_byte = block [bindex++] ; + + in_buffer |= (in_byte << in_bits); + in_bits += 8; + } + samples [k] = in_buffer & ((1 << bits) - 1); + in_buffer >>= bits; + in_bits -= bits; + } ; + + return k ; +} /* unpack_bytes */ + +static int +pack_bytes (int bits, const short * samples, unsigned char * block) +{ + unsigned int out_buffer = 0 ; + int k, bindex = 0, out_bits = 0 ; + unsigned char out_byte ; + + for (k = 0 ; k < G72x_BLOCK_SIZE ; k++) + { out_buffer |= (samples [k] << out_bits) ; + out_bits += bits ; + if (out_bits >= 8) + { out_byte = out_buffer & 0xFF ; + out_bits -= 8 ; + out_buffer >>= 8 ; + block [bindex++] = out_byte ; + } + } ; + + return bindex ; +} /* pack_bytes */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 6298dc75-fd0f-4062-9b90-f73ed69f22d4 +*/ + diff --git a/libs/libsndfile/src/G72x/g72x.h b/libs/libsndfile/src/G72x/g72x.h new file mode 100644 index 0000000000..e6319e6248 --- /dev/null +++ b/libs/libsndfile/src/G72x/g72x.h @@ -0,0 +1,99 @@ +/* +** Copyright (C) 1999-2005 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +/* +** This file is not the same as the original file from Sun Microsystems. Nearly +** all the original definitions and function prototypes that were in the file +** of this name have been moved to g72x_priv.h. +*/ + +#ifndef G72X_HEADER_FILE +#define G72X_HEADER_FILE + +/* +** Number of samples per block to process. +** Must be a common multiple of possible bits per sample : 2, 3, 4, 5 and 8. +*/ +#define G72x_BLOCK_SIZE (3 * 5 * 8) + +/* +** Identifiers for the differing kinds of G72x ADPCM codecs. +** The identifiers also define the number of encoded bits per sample. +*/ + +enum +{ G723_16_BITS_PER_SAMPLE = 2, + G723_24_BITS_PER_SAMPLE = 3, + G723_40_BITS_PER_SAMPLE = 5, + + G721_32_BITS_PER_SAMPLE = 4, + G721_40_BITS_PER_SAMPLE = 5, + + G723_16_SAMPLES_PER_BLOCK = G72x_BLOCK_SIZE, + G723_24_SAMPLES_PER_BLOCK = G723_24_BITS_PER_SAMPLE * (G72x_BLOCK_SIZE / G723_24_BITS_PER_SAMPLE), + G723_40_SAMPLES_PER_BLOCK = G723_40_BITS_PER_SAMPLE * (G72x_BLOCK_SIZE / G723_40_BITS_PER_SAMPLE), + + G721_32_SAMPLES_PER_BLOCK = G72x_BLOCK_SIZE, + G721_40_SAMPLES_PER_BLOCK = G721_40_BITS_PER_SAMPLE * (G72x_BLOCK_SIZE / G721_40_BITS_PER_SAMPLE), + + G723_16_BYTES_PER_BLOCK = (G723_16_BITS_PER_SAMPLE * G72x_BLOCK_SIZE) / 8, + G723_24_BYTES_PER_BLOCK = (G723_24_BITS_PER_SAMPLE * G72x_BLOCK_SIZE) / 8, + G723_40_BYTES_PER_BLOCK = (G723_40_BITS_PER_SAMPLE * G72x_BLOCK_SIZE) / 8, + + G721_32_BYTES_PER_BLOCK = (G721_32_BITS_PER_SAMPLE * G72x_BLOCK_SIZE) / 8, + G721_40_BYTES_PER_BLOCK = (G721_40_BITS_PER_SAMPLE * G72x_BLOCK_SIZE) / 8 +} ; + +/* Forward declaration of of g72x_state. */ + +struct g72x_state ; + +/* External function definitions. */ + +struct g72x_state * g72x_reader_init (int codec, int *blocksize, int *samplesperblock) ; +struct g72x_state * g72x_writer_init (int codec, int *blocksize, int *samplesperblock) ; +/* +** Initialize the ADPCM state table for the given codec. +** Return 0 on success, 1 on fail. +*/ + +int g72x_decode_block (struct g72x_state *pstate, const unsigned char *block, short *samples) ; +/* +** The caller fills data->block with data->bytes bytes before calling the +** function. The value data->bytes must be an integer multiple of +** data->blocksize and be <= data->max_bytes. +** When it returns, the caller can read out data->samples samples. +*/ + +int g72x_encode_block (struct g72x_state *pstate, short *samples, unsigned char *block) ; +/* +** The caller fills state->samples some integer multiple data->samples_per_block +** (up to G72x_BLOCK_SIZE) samples before calling the function. +** When it returns, the caller can read out bytes encoded bytes. +*/ + +#endif /* !G72X_HEADER_FILE */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 6ca84e5f-f932-4ba1-87ee-37056d921621 +*/ + diff --git a/libs/libsndfile/src/G72x/g72x_priv.h b/libs/libsndfile/src/G72x/g72x_priv.h new file mode 100644 index 0000000000..a88e96d0da --- /dev/null +++ b/libs/libsndfile/src/G72x/g72x_priv.h @@ -0,0 +1,118 @@ +/* + * This source code is a product of Sun Microsystems, Inc. and is provided + * for unrestricted use. Users may copy or modify this source code without + * charge. + * + * SUN SOURCE CODE IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING + * THE WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR + * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE. + * + * Sun source code is provided with no support and without any obligation on + * the part of Sun Microsystems, Inc. to assist in its use, correction, + * modification or enhancement. + * + * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE + * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY THIS SOFTWARE + * OR ANY PART THEREOF. + * + * In no event will Sun Microsystems, Inc. be liable for any lost revenue + * or profits or other special, indirect and consequential damages, even if + * Sun has been advised of the possibility of such damages. + * + * Sun Microsystems, Inc. + * 2550 Garcia Avenue + * Mountain View, California 94043 + */ + +#ifndef G72X_PRIVATE_H +#define G72X_PRIVATE_H + +#ifdef __cplusplus +#error "This code is not designed to be compiled with a C++ compiler." +#endif + +/* +** The following is the definition of the state structure used by the +** G.721/G.723 encoder and decoder to preserve their internal state +** between successive calls. The meanings of the majority of the state +** structure fields are explained in detail in the CCITT Recommendation +** G.721. The field names are essentially identical to variable names +** in the bit level description of the coding algorithm included in this +** Recommendation. +*/ + +struct g72x_state +{ long yl; /* Locked or steady state step size multiplier. */ + short yu; /* Unlocked or non-steady state step size multiplier. */ + short dms; /* Short term energy estimate. */ + short dml; /* Long term energy estimate. */ + short ap; /* Linear weighting coefficient of 'yl' and 'yu'. */ + + short a[2]; /* Coefficients of pole portion of prediction filter. */ + short b[6]; /* Coefficients of zero portion of prediction filter. */ + short pk[2]; /* + ** Signs of previous two samples of a partially + ** reconstructed signal. + **/ + short dq[6]; /* + ** Previous 6 samples of the quantized difference + ** signal represented in an internal floating point + ** format. + **/ + short sr[2]; /* + ** Previous 2 samples of the quantized difference + ** signal represented in an internal floating point + ** format. + */ + char td; /* delayed tone detect, new in 1988 version */ + + /* The following struct members were added for libsndfile. The original + ** code worked by calling a set of functions on a sample by sample basis + ** which is slow on architectures like Intel x86. For libsndfile, this + ** was changed so that the encoding and decoding routines could work on + ** a block of samples at a time to reduce the function call overhead. + */ + int (*encoder) (int, struct g72x_state* state) ; + int (*decoder) (int, struct g72x_state* state) ; + + int codec_bits, blocksize, samplesperblock ; +} ; + +typedef struct g72x_state G72x_STATE ; + +int predictor_zero (G72x_STATE *state_ptr); + +int predictor_pole (G72x_STATE *state_ptr); + +int step_size (G72x_STATE *state_ptr); + +int quantize (int d, int y, short *table, int size); + +int reconstruct (int sign, int dqln, int y); + +void update (int code_size, int y, int wi, int fi, int dq, int sr, int dqsez, G72x_STATE *state_ptr); + +int g721_encoder (int sample, G72x_STATE *state_ptr); +int g721_decoder (int code, G72x_STATE *state_ptr); + +int g723_16_encoder (int sample, G72x_STATE *state_ptr); +int g723_16_decoder (int code, G72x_STATE *state_ptr); + +int g723_24_encoder (int sample, G72x_STATE *state_ptr); +int g723_24_decoder (int code, G72x_STATE *state_ptr); + +int g723_40_encoder (int sample, G72x_STATE *state_ptr); +int g723_40_decoder (int code, G72x_STATE *state_ptr); + +void private_init_state (G72x_STATE *state_ptr) ; + +#endif /* G72X_PRIVATE_H */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: d9ad4da7-0fa3-471d-8020-720b5cfb5e5b +*/ + diff --git a/libs/libsndfile/src/G72x/g72x_test.c b/libs/libsndfile/src/G72x/g72x_test.c new file mode 100644 index 0000000000..caf58467b7 --- /dev/null +++ b/libs/libsndfile/src/G72x/g72x_test.c @@ -0,0 +1,222 @@ +/* +** Copyright (C) 1999-2004 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU General Public License as published by +** the Free Software Foundation; either version 2 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU General Public License for more details. +** +** You should have received a copy of the GNU General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include +#include +#include +#include +#include + +#include "g72x.h" +#include "g72x_priv.h" + +#ifndef M_PI +#define M_PI 3.14159265358979323846264338 +#endif + +#define BUFFER_SIZE (1<<14) /* Should be (1<<14) */ +#define SAMPLE_RATE 11025 + + +static void g721_test (void) ; +static void g723_test (double margin) ; + +static void gen_signal_double (double *data, double scale, int datalen) ; +static int error_function (double data, double orig, double margin) ; + +static int oct_save_short (short *a, short *b, int len) ; + +int +main (int argc, char *argv []) +{ int bDoAll = 0 ; + int nTests = 0 ; + + if (argc != 2) + { printf ("Usage : %s \n", argv [0]) ; + printf (" Where is one of the following:\n") ; + printf (" g721 - test G721 encoder and decoder\n") ; + printf (" g723 - test G721 encoder and decoder\n") ; + printf (" all - perform all tests\n") ; + exit (1) ; + } ; + + bDoAll=!strcmp (argv [1], "all"); + + if (bDoAll || ! strcmp (argv [1], "g721")) + { g721_test () ; + nTests++ ; + } ; + + if (bDoAll || ! strcmp (argv [1], "g723")) + { g723_test (0.53) ; + nTests++ ; + } ; + + if (nTests == 0) + { printf ("Mono : ************************************\n") ; + printf ("Mono : * No '%s' test defined.\n", argv [1]) ; + printf ("Mono : ************************************\n") ; + return 1 ; + } ; + + return 0 ; +} /* main */ + +static void +g721_test (void) +{ + return ; +} /* g721_test */ + +static void +g723_test (double margin) +{ static double orig_buffer [BUFFER_SIZE] ; + static short orig [BUFFER_SIZE] ; + static short data [BUFFER_SIZE] ; + + G72x_STATE encoder_state, decoder_state ; + + long k ; + int code, position, max_err ; + + private_init_state (&encoder_state) ; + encoder_state.encoder = g723_24_encoder ; + encoder_state.codec_bits = 3 ; + + private_init_state (&decoder_state) ; + decoder_state.decoder = g723_24_decoder ; + decoder_state.codec_bits = 3 ; + + memset (data, 0, BUFFER_SIZE * sizeof (short)) ; + memset (orig, 0, BUFFER_SIZE * sizeof (short)) ; + + printf (" g723_test : ") ; + fflush (stdout) ; + + gen_signal_double (orig_buffer, 32000.0, BUFFER_SIZE) ; + for (k = 0 ; k < BUFFER_SIZE ; k++) + orig [k] = (short) orig_buffer [k] ; + + /* Write and read data here. */ + position = 0 ; + max_err = 0 ; + for (k = 0 ; k < BUFFER_SIZE ; k++) + { code = encoder_state.encoder (orig [k], &encoder_state) ; + data [k] = decoder_state.decoder (code, &decoder_state) ; + if (abs (orig [k] - data [k]) > max_err) + { position = k ; + max_err = abs (orig [k] - data [k]) ; + } ; + } ; + + printf ("\n\nMax error of %d at postion %d.\n", max_err, position) ; + + for (k = 0 ; k < BUFFER_SIZE ; k++) + { if (error_function (data [k], orig [k], margin)) + { printf ("Line %d: Incorrect sample A (#%ld : %d should be %d).\n", __LINE__, k, data [k], orig [k]) ; + oct_save_short (orig, data, BUFFER_SIZE) ; + exit (1) ; + } ; + } ; + + + printf ("ok\n") ; + + return ; +} /* g723_test */ + + +#define SIGNAL_MAXVAL 30000.0 +#define DECAY_COUNT 1000 + +static void +gen_signal_double (double *gendata, double scale, int gendatalen) +{ int k, ramplen ; + double amp = 0.0 ; + + ramplen = DECAY_COUNT ; + + for (k = 0 ; k < gendatalen ; k++) + { if (k <= ramplen) + amp = scale * k / ((double) ramplen) ; + else if (k > gendatalen - ramplen) + amp = scale * (gendatalen - k) / ((double) ramplen) ; + + gendata [k] = amp * (0.4 * sin (33.3 * 2.0 * M_PI * ((double) (k+1)) / ((double) SAMPLE_RATE)) + + 0.3 * cos (201.1 * 2.0 * M_PI * ((double) (k+1)) / ((double) SAMPLE_RATE))) ; + } ; + + return ; +} /* gen_signal_double */ + +static int +error_function (double data, double orig, double margin) +{ double error ; + + if (fabs (orig) <= 500.0) + error = fabs (fabs (data) - fabs(orig)) / 2000.0 ; + else if (fabs (orig) <= 1000.0) + error = fabs (data - orig) / 3000.0 ; + else + error = fabs (data - orig) / fabs (orig) ; + + if (error > margin) + { printf ("\n\n*******************\nError : %f\n", error) ; + return 1 ; + } ; + return 0 ; +} /* error_function */ + +static int +oct_save_short (short *a, short *b, int len) +{ FILE *file ; + int k ; + + if (! (file = fopen ("error.dat", "w"))) + return 1 ; + + fprintf (file, "# Not created by Octave\n") ; + + fprintf (file, "# name: a\n") ; + fprintf (file, "# type: matrix\n") ; + fprintf (file, "# rows: %d\n", len) ; + fprintf (file, "# columns: 1\n") ; + + for (k = 0 ; k < len ; k++) + fprintf (file, "% d\n", a [k]) ; + + fprintf (file, "# name: b\n") ; + fprintf (file, "# type: matrix\n") ; + fprintf (file, "# rows: %d\n", len) ; + fprintf (file, "# columns: 1\n") ; + + for (k = 0 ; k < len ; k++) + fprintf (file, "% d\n", b [k]) ; + + fclose (file) ; + return 0 ; +} /* oct_save_short */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 0597b442-a5b0-4abf-92a4-92f6c24e85a6 +*/ + diff --git a/libs/libsndfile/src/GSM610/COPYRIGHT b/libs/libsndfile/src/GSM610/COPYRIGHT new file mode 100644 index 0000000000..eba0e523bb --- /dev/null +++ b/libs/libsndfile/src/GSM610/COPYRIGHT @@ -0,0 +1,16 @@ +Copyright 1992, 1993, 1994 by Jutta Degener and Carsten Bormann, +Technische Universitaet Berlin + +Any use of this software is permitted provided that this notice is not +removed and that neither the authors nor the Technische Universitaet Berlin +are deemed to have made any representations as to the suitability of this +software for any purpose nor are held responsible for any defects of +this software. THERE IS ABSOLUTELY NO WARRANTY FOR THIS SOFTWARE. + +As a matter of courtesy, the authors request to be informed about uses +this software has found, about bugs in this software, and about any +improvements that may be of general interest. + +Berlin, 28.11.1994 +Jutta Degener +Carsten Bormann diff --git a/libs/libsndfile/src/GSM610/ChangeLog b/libs/libsndfile/src/GSM610/ChangeLog new file mode 100644 index 0000000000..24f524882d --- /dev/null +++ b/libs/libsndfile/src/GSM610/ChangeLog @@ -0,0 +1,56 @@ +2004-05-12 Erik de Castro Lopo + + * gsm610_priv.h + Replace ugly macros with inline functions. + + * *.c + Remove temporary variables used by macros and other minor fixes required by + above change. + +2003-06-02 Erik de Castro Lopo + + * rpe.c + Renamed variables "exp" to "expon" to avoid shadowed parameter warnigns. + +2002-06-08 Erik de Castro Lopo + + * long_term.c + Changes tp removed compiler warnings about shadowed parameters. + +2002-06-08 Erik de Castro Lopo + + * private.h + Made declarations of gsm_A, gsm_B, gsm_MIC etc extern. This fixed a compile + problem on MacOSX. + +2002-05-10 Erik de Castro Lopo + + * *.[ch] + Removed all pre-ANSI prototype kludges. Removed proto.h and unproto.h. + Started work on making GSM 6.10 files seekable. Currently they are not. + + * code.c private.h + Function Gsm_Coder () used a statically defined array. This was obviously + not re-entrant so moved it to struct gsm_state. + +2001-09-16 Erik de Castro Lopo + + * code.c + Added #includes for string.h and stdlib.h. + +2000-10-27 Erik de Castro Lopo + + * config.h + Removed some commented out #defines (ie //*efine) which were causing problems on + the Sun cc compiler. + +2000-02-29 Erik de Castro Lopo + + * private.h + Added #defines to emulate normal compile time options. + +2000-02-28 Erik de Castro Lopo + + * everthing + Created this directory and copied files from libgsm. + http://kbs.cs.tu-berlin.de/~jutta/toast.html diff --git a/libs/libsndfile/src/GSM610/README b/libs/libsndfile/src/GSM610/README new file mode 100644 index 0000000000..b57132b051 --- /dev/null +++ b/libs/libsndfile/src/GSM610/README @@ -0,0 +1,36 @@ +GSM 06.10 13 kbit/s RPE/LTP speech codec +---------------------------------------- + +All the file in this directory were written by Jutta Degener +and Carsten Borman for The Communications and Operating Systems +Research Group (KBS) at the Technische Universitaet Berlin. + +Their work was released under the following license which is +assumed to be compatible with The GNU Lesser General Public License. + +---------------------------------------------------------------------------- + +Copyright 1992, 1993, 1994 by Jutta Degener and Carsten Bormann, +Technische Universitaet Berlin + +Any use of this software is permitted provided that this notice is not +removed and that neither the authors nor the Technische Universitaet Berlin +are deemed to have made any representations as to the suitability of this +software for any purpose nor are held responsible for any defects of +this software. THERE IS ABSOLUTELY NO WARRANTY FOR THIS SOFTWARE. + +As a matter of courtesy, the authors request to be informed about uses +this software has found, about bugs in this software, and about any +improvements that may be of general interest. + +Berlin, 28.11.1994 +Jutta Degener (jutta@cs.tu-berlin.de) +Carsten Bormann (cabo@cs.tu-berlin.de) + +---------------------------------------------------------------------------- + +Jutta Degener and Carsten Bormann's work can be found on their homepage +at: + + http://kbs.cs.tu-berlin.de/~jutta/toast.html + diff --git a/libs/libsndfile/src/GSM610/add.c b/libs/libsndfile/src/GSM610/add.c new file mode 100644 index 0000000000..fbf7cf147d --- /dev/null +++ b/libs/libsndfile/src/GSM610/add.c @@ -0,0 +1,248 @@ +/* + * Copyright 1992 by Jutta Degener and Carsten Bormann, Technische + * Universitaet Berlin. See the accompanying file "COPYRIGHT" for + * details. THERE IS ABSOLUTELY NO WARRANTY FOR THIS SOFTWARE. + */ + +/* + * See private.h for the more commonly used macro versions. + */ + +#include +#include + +#include "gsm610_priv.h" +#include "gsm.h" + +#define saturate(x) \ + ((x) < MIN_WORD ? MIN_WORD : (x) > MAX_WORD ? MAX_WORD: (x)) + +word gsm_add ( word a, word b) +{ + longword sum = (longword)a + (longword)b; + return saturate(sum); +} + +word gsm_sub ( word a, word b) +{ + longword diff = (longword)a - (longword)b; + return saturate(diff); +} + +word gsm_mult ( word a, word b) +{ + if (a == MIN_WORD && b == MIN_WORD) + return MAX_WORD; + + return SASR_L( (longword)a * (longword)b, 15 ); +} + +word gsm_mult_r ( word a, word b) +{ + if (b == MIN_WORD && a == MIN_WORD) return MAX_WORD; + else { + longword prod = (longword)a * (longword)b + 16384; + prod >>= 15; + return prod & 0xFFFF; + } +} + +word gsm_abs (word a) +{ + return a < 0 ? (a == MIN_WORD ? MAX_WORD : -a) : a; +} + +longword gsm_L_mult (word a, word b) +{ + assert( a != MIN_WORD || b != MIN_WORD ); + return ((longword)a * (longword)b) << 1; +} + +longword gsm_L_add ( longword a, longword b) +{ + if (a < 0) { + if (b >= 0) return a + b; + else { + ulongword A = (ulongword)-(a + 1) + (ulongword)-(b + 1); + return A >= MAX_LONGWORD ? MIN_LONGWORD :-(longword)A-2; + } + } + else if (b <= 0) return a + b; + else { + ulongword A = (ulongword)a + (ulongword)b; + return A > MAX_LONGWORD ? MAX_LONGWORD : A; + } +} + +longword gsm_L_sub ( longword a, longword b) +{ + if (a >= 0) { + if (b >= 0) return a - b; + else { + /* a>=0, b<0 */ + + ulongword A = (ulongword)a + -(b + 1); + return A >= MAX_LONGWORD ? MAX_LONGWORD : (A + 1); + } + } + else if (b <= 0) return a - b; + else { + /* a<0, b>0 */ + + ulongword A = (ulongword)-(a + 1) + b; + return A >= MAX_LONGWORD ? MIN_LONGWORD : -(longword)A - 1; + } +} + +static unsigned char const bitoff[ 256 ] = { + 8, 7, 6, 6, 5, 5, 5, 5, 4, 4, 4, 4, 4, 4, 4, 4, + 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, + 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, + 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, + 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, + 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, + 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, + 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 +}; + +word gsm_norm (longword a ) +/* + * the number of left shifts needed to normalize the 32 bit + * variable L_var1 for positive values on the interval + * + * with minimum of + * minimum of 1073741824 (01000000000000000000000000000000) and + * maximum of 2147483647 (01111111111111111111111111111111) + * + * + * and for negative values on the interval with + * minimum of -2147483648 (-10000000000000000000000000000000) and + * maximum of -1073741824 ( -1000000000000000000000000000000). + * + * in order to normalize the result, the following + * operation must be done: L_norm_var1 = L_var1 << norm( L_var1 ); + * + * (That's 'ffs', only from the left, not the right..) + */ +{ + assert(a != 0); + + if (a < 0) { + if (a <= -1073741824) return 0; + a = ~a; + } + + return a & 0xffff0000 + ? ( a & 0xff000000 + ? -1 + bitoff[ 0xFF & (a >> 24) ] + : 7 + bitoff[ 0xFF & (a >> 16) ] ) + : ( a & 0xff00 + ? 15 + bitoff[ 0xFF & (a >> 8) ] + : 23 + bitoff[ 0xFF & a ] ); +} + +longword gsm_L_asl (longword a, int n) +{ + if (n >= 32) return 0; + if (n <= -32) return -(a < 0); + if (n < 0) return gsm_L_asr(a, -n); + return a << n; +} + +word gsm_asr (word a, int n) +{ + if (n >= 16) return -(a < 0); + if (n <= -16) return 0; + if (n < 0) return a << -n; + + return SASR_W (a, (word) n); +} + +word gsm_asl (word a, int n) +{ + if (n >= 16) return 0; + if (n <= -16) return -(a < 0); + if (n < 0) return gsm_asr(a, -n); + return a << n; +} + +longword gsm_L_asr (longword a, int n) +{ + if (n >= 32) return -(a < 0); + if (n <= -32) return 0; + if (n < 0) return a << -n; + + return SASR_L (a, (word) n); +} + +/* +** word gsm_asr (word a, int n) +** { +** if (n >= 16) return -(a < 0); +** if (n <= -16) return 0; +** if (n < 0) return a << -n; +** +** # ifdef SASR_W +** return a >> n; +** # else +** if (a >= 0) return a >> n; +** else return -(word)( -(uword)a >> n ); +** # endif +** } +** +*/ +/* + * (From p. 46, end of section 4.2.5) + * + * NOTE: The following lines gives [sic] one correct implementation + * of the div(num, denum) arithmetic operation. Compute div + * which is the integer division of num by denum: with denum + * >= num > 0 + */ + +word gsm_div (word num, word denum) +{ + longword L_num = num; + longword L_denum = denum; + word div = 0; + int k = 15; + + /* The parameter num sometimes becomes zero. + * Although this is explicitly guarded against in 4.2.5, + * we assume that the result should then be zero as well. + */ + + /* assert(num != 0); */ + + assert(num >= 0 && denum >= num); + if (num == 0) + return 0; + + while (k--) { + div <<= 1; + L_num <<= 1; + + if (L_num >= L_denum) { + L_num -= L_denum; + div++; + } + } + + return div; +} +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: a7398579-e2e1-4733-aa2d-4c6efc0c58ff +*/ + diff --git a/libs/libsndfile/src/GSM610/code.c b/libs/libsndfile/src/GSM610/code.c new file mode 100644 index 0000000000..02ec75bf12 --- /dev/null +++ b/libs/libsndfile/src/GSM610/code.c @@ -0,0 +1,97 @@ +/* + * Copyright 1992 by Jutta Degener and Carsten Bormann, Technische + * Universitaet Berlin. See the accompanying file "COPYRIGHT" for + * details. THERE IS ABSOLUTELY NO WARRANTY FOR THIS SOFTWARE. + */ + + +#include +#include + +#include "config.h" + +#include "gsm610_priv.h" +#include "gsm.h" + +/* + * 4.2 FIXED POINT IMPLEMENTATION OF THE RPE-LTP CODER + */ + +void Gsm_Coder ( + + struct gsm_state * State, + + word * s, /* [0..159] samples IN */ + +/* + * The RPE-LTD coder works on a frame by frame basis. The length of + * the frame is equal to 160 samples. Some computations are done + * once per frame to produce at the output of the coder the + * LARc[1..8] parameters which are the coded LAR coefficients and + * also to realize the inverse filtering operation for the entire + * frame (160 samples of signal d[0..159]). These parts produce at + * the output of the coder: + */ + + word * LARc, /* [0..7] LAR coefficients OUT */ + +/* + * Procedure 4.2.11 to 4.2.18 are to be executed four times per + * frame. That means once for each sub-segment RPE-LTP analysis of + * 40 samples. These parts produce at the output of the coder: + */ + + word * Nc, /* [0..3] LTP lag OUT */ + word * bc, /* [0..3] coded LTP gain OUT */ + word * Mc, /* [0..3] RPE grid selection OUT */ + word * xmaxc,/* [0..3] Coded maximum amplitude OUT */ + word * xMc /* [13*4] normalized RPE samples OUT */ +) +{ + int k; + word * dp = State->dp0 + 120; /* [ -120...-1 ] */ + word * dpp = dp; /* [ 0...39 ] */ + + word so[160]; + + Gsm_Preprocess (State, s, so); + Gsm_LPC_Analysis (State, so, LARc); + Gsm_Short_Term_Analysis_Filter (State, LARc, so); + + for (k = 0; k <= 3; k++, xMc += 13) { + + Gsm_Long_Term_Predictor ( State, + so+k*40, /* d [0..39] IN */ + dp, /* dp [-120..-1] IN */ + State->e + 5, /* e [0..39] OUT */ + dpp, /* dpp [0..39] OUT */ + Nc++, + bc++); + + Gsm_RPE_Encoding ( /*-S,-*/ + State->e + 5, /* e ][0..39][ IN/OUT */ + xmaxc++, Mc++, xMc ); + /* + * Gsm_Update_of_reconstructed_short_time_residual_signal + * ( dpp, e + 5, dp ); + */ + + { register int i; + for (i = 0; i <= 39; i++) + dp[ i ] = GSM_ADD( State->e[5 + i], dpp[i] ); + } + dp += 40; + dpp += 40; + + } + (void)memcpy( (char *)State->dp0, (char *)(State->dp0 + 160), + 120 * sizeof(*State->dp0) ); +} +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: ae8ef1b2-5a1e-4263-94cd-42b15dca81a3 +*/ + diff --git a/libs/libsndfile/src/GSM610/config.h b/libs/libsndfile/src/GSM610/config.h new file mode 100644 index 0000000000..23ac5ad08d --- /dev/null +++ b/libs/libsndfile/src/GSM610/config.h @@ -0,0 +1,33 @@ +/* + * Copyright 1992 by Jutta Degener and Carsten Bormann, Technische + * Universitaet Berlin. See the accompanying file "COPYRIGHT" for + * details. THERE IS ABSOLUTELY NO WARRANTY FOR THIS SOFTWARE. + */ + +#ifndef CONFIG_H +#define CONFIG_H + +#define HAS_STDLIB_H 1 /* /usr/include/stdlib.h */ +#define HAS_FCNTL_H 1 /* /usr/include/fcntl.h */ + +#define HAS_FSTAT 1 /* fstat syscall */ +#define HAS_FCHMOD 1 /* fchmod syscall */ +#define HAS_CHMOD 1 /* chmod syscall */ +#define HAS_FCHOWN 1 /* fchown syscall */ +#define HAS_CHOWN 1 /* chown syscall */ + +#define HAS_STRING_H 1 /* /usr/include/string.h */ + +#define HAS_UNISTD_H 1 /* /usr/include/unistd.h */ +#define HAS_UTIME 1 /* POSIX utime(path, times) */ +#define HAS_UTIME_H 1 /* UTIME header file */ + +#endif /* CONFIG_H */ +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 5338dfef-8e59-4f51-af47-627c9ea85353 +*/ + diff --git a/libs/libsndfile/src/GSM610/decode.c b/libs/libsndfile/src/GSM610/decode.c new file mode 100644 index 0000000000..46db31825b --- /dev/null +++ b/libs/libsndfile/src/GSM610/decode.c @@ -0,0 +1,67 @@ +/* + * Copyright 1992 by Jutta Degener and Carsten Bormann, Technische + * Universitaet Berlin. See the accompanying file "COPYRIGHT" for + * details. THERE IS ABSOLUTELY NO WARRANTY FOR THIS SOFTWARE. + */ + +#include + +#include "gsm610_priv.h" +#include "gsm.h" + +/* + * 4.3 FIXED POINT IMPLEMENTATION OF THE RPE-LTP DECODER + */ + +static void Postprocessing ( + struct gsm_state * S, + register word * s) +{ + register int k; + register word msr = S->msr; + register word tmp; + + for (k = 160; k--; s++) { + tmp = GSM_MULT_R( msr, 28180 ); + msr = GSM_ADD(*s, tmp); /* Deemphasis */ + *s = GSM_ADD(msr, msr) & 0xFFF8; /* Truncation & Upscaling */ + } + S->msr = msr; +} + +void Gsm_Decoder ( + struct gsm_state * S, + + word * LARcr, /* [0..7] IN */ + + word * Ncr, /* [0..3] IN */ + word * bcr, /* [0..3] IN */ + word * Mcr, /* [0..3] IN */ + word * xmaxcr, /* [0..3] IN */ + word * xMcr, /* [0..13*4] IN */ + + word * s) /* [0..159] OUT */ +{ + int j, k; + word erp[40], wt[160]; + word * drp = S->dp0 + 120; + + for (j=0; j <= 3; j++, xmaxcr++, bcr++, Ncr++, Mcr++, xMcr += 13) { + + Gsm_RPE_Decoding( /*-S,-*/ *xmaxcr, *Mcr, xMcr, erp ); + Gsm_Long_Term_Synthesis_Filtering( S, *Ncr, *bcr, erp, drp ); + + for (k = 0; k <= 39; k++) wt[ j * 40 + k ] = drp[ k ]; + } + + Gsm_Short_Term_Synthesis_Filter( S, LARcr, wt, s ); + Postprocessing(S, s); +} +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 11ae5b90-2e8b-400b-ac64-a69a1fc6cc41 +*/ + diff --git a/libs/libsndfile/src/GSM610/gsm.h b/libs/libsndfile/src/GSM610/gsm.h new file mode 100644 index 0000000000..a13a606147 --- /dev/null +++ b/libs/libsndfile/src/GSM610/gsm.h @@ -0,0 +1,58 @@ +/* + * Copyright 1992 by Jutta Degener and Carsten Bormann, Technische + * Universitaet Berlin. See the accompanying file "COPYRIGHT" for + * details. THERE IS ABSOLUTELY NO WARRANTY FOR THIS SOFTWARE. + */ + +#ifndef GSM_H +#define GSM_H + +#include /* for FILE * */ + +/* + * Interface + */ + +typedef struct gsm_state * gsm; +typedef short gsm_signal; /* signed 16 bit */ +typedef unsigned char gsm_byte; +typedef gsm_byte gsm_frame[33]; /* 33 * 8 bits */ + +#define GSM_MAGIC 0xD /* 13 kbit/s RPE-LTP */ + +#define GSM_PATCHLEVEL 10 +#define GSM_MINOR 0 +#define GSM_MAJOR 1 + +#define GSM_OPT_VERBOSE 1 +#define GSM_OPT_FAST 2 +#define GSM_OPT_LTP_CUT 3 +#define GSM_OPT_WAV49 4 +#define GSM_OPT_FRAME_INDEX 5 +#define GSM_OPT_FRAME_CHAIN 6 + +gsm gsm_create (void); + +/* Added for libsndfile : May 6, 2002 */ +void gsm_init (gsm); + +void gsm_destroy (gsm); + +int gsm_print (FILE *, gsm, gsm_byte *); +int gsm_option (gsm, int, int *); + +void gsm_encode (gsm, gsm_signal *, gsm_byte *); +int gsm_decode (gsm, gsm_byte *, gsm_signal *); + +int gsm_explode (gsm, gsm_byte *, gsm_signal *); +void gsm_implode (gsm, gsm_signal *, gsm_byte *); + +#endif /* GSM_H */ +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 8cfc7698-5433-4b6f-aeca-967c6fda4dec +*/ + diff --git a/libs/libsndfile/src/GSM610/gsm610_priv.h b/libs/libsndfile/src/GSM610/gsm610_priv.h new file mode 100644 index 0000000000..c9ab3f25eb --- /dev/null +++ b/libs/libsndfile/src/GSM610/gsm610_priv.h @@ -0,0 +1,308 @@ +/* + * Copyright 1992 by Jutta Degener and Carsten Bormann, Technische + * Universitaet Berlin. See the accompanying file "COPYRIGHT" for + * details. THERE IS ABSOLUTELY NO WARRANTY FOR THIS SOFTWARE. + */ + +#ifndef PRIVATE_H +#define PRIVATE_H + +/* Added by Erik de Castro Lopo */ +#define USE_FLOAT_MUL +#define FAST +#define WAV49 + +#ifdef __cplusplus +#error "This code is not designed to be compiled with a C++ compiler." +#endif +/* Added by Erik de Castro Lopo */ + + + +typedef short word; /* 16 bit signed int */ +typedef int longword; /* 32 bit signed int */ + +typedef unsigned short uword; /* unsigned word */ +typedef unsigned int ulongword; /* unsigned longword */ + +struct gsm_state +{ word dp0[ 280 ] ; + + word z1; /* preprocessing.c, Offset_com. */ + longword L_z2; /* Offset_com. */ + int mp; /* Preemphasis */ + + word u[8] ; /* short_term_aly_filter.c */ + word LARpp[2][8] ; /* */ + word j; /* */ + + word ltp_cut; /* long_term.c, LTP crosscorr. */ + word nrp; /* 40 */ /* long_term.c, synthesis */ + word v[9] ; /* short_term.c, synthesis */ + word msr; /* decoder.c, Postprocessing */ + + char verbose; /* only used if !NDEBUG */ + char fast; /* only used if FAST */ + + char wav_fmt; /* only used if WAV49 defined */ + unsigned char frame_index; /* odd/even chaining */ + unsigned char frame_chain; /* half-byte to carry forward */ + + /* Moved here from code.c where it was defined as static */ + word e[50] ; +} ; + +typedef struct gsm_state GSM_STATE ; + +#define MIN_WORD (-32767 - 1) +#define MAX_WORD 32767 + +#define MIN_LONGWORD (-2147483647 - 1) +#define MAX_LONGWORD 2147483647 + +/* Signed arithmetic shift right. */ +static inline word +SASR_W (word x, word by) +{ return (x >> by) ; +} /* SASR */ + +static inline longword +SASR_L (longword x, word by) +{ return (x >> by) ; +} /* SASR */ + +/* + * Prototypes from add.c + */ +word gsm_mult (word a, word b) ; +longword gsm_L_mult (word a, word b) ; +word gsm_mult_r (word a, word b) ; + +word gsm_div (word num, word denum) ; + +word gsm_add (word a, word b ) ; +longword gsm_L_add (longword a, longword b ) ; + +word gsm_sub (word a, word b) ; +longword gsm_L_sub (longword a, longword b) ; + +word gsm_abs (word a) ; + +word gsm_norm (longword a ) ; + +longword gsm_L_asl (longword a, int n) ; +word gsm_asl (word a, int n) ; + +longword gsm_L_asr (longword a, int n) ; +word gsm_asr (word a, int n) ; + +/* + * Inlined functions from add.h + */ + +static inline longword +GSM_MULT_R (word a, word b) +{ return (((longword) (a)) * ((longword) (b)) + 16384) >> 15 ; +} /* GSM_MULT_R */ + +static inline longword +GSM_MULT (word a, word b) +{ return (((longword) (a)) * ((longword) (b))) >> 15 ; +} /* GSM_MULT */ + +static inline longword +GSM_L_MULT (word a, word b) +{ return ((longword) (a)) * ((longword) (b)) << 1 ; +} /* GSM_L_MULT */ + +static inline longword +GSM_L_ADD (longword a, longword b) +{ ulongword utmp ; + + if (a < 0 && b < 0) + { utmp = (ulongword)-((a) + 1) + (ulongword)-((b) + 1) ; + return (utmp >= (ulongword) MAX_LONGWORD) ? MIN_LONGWORD : -(longword)utmp-2 ; + } ; + + if (a > 0 && b > 0) + { utmp = (ulongword) a + (ulongword) b ; + return (utmp >= (ulongword) MAX_LONGWORD) ? MAX_LONGWORD : utmp ; + } ; + + return a + b ; +} /* GSM_L_ADD */ + +static inline longword +GSM_ADD (word a, word b) +{ longword ltmp ; + + ltmp = ((longword) a) + ((longword) b) ; + + if (ltmp >= MAX_WORD) + return MAX_WORD ; + if (ltmp <= MIN_WORD) + return MIN_WORD ; + + return ltmp ; +} /* GSM_ADD */ + +static inline longword +GSM_SUB (word a, word b) +{ longword ltmp ; + + ltmp = ((longword) a) - ((longword) b) ; + + if (ltmp >= MAX_WORD) + ltmp = MAX_WORD ; + else if (ltmp <= MIN_WORD) + ltmp = MIN_WORD ; + + return ltmp ; +} /* GSM_SUB */ + +static inline word +GSM_ABS (word a) +{ + if (a > 0) + return a ; + if (a == MIN_WORD) + return MAX_WORD ; + return -a ; +} /* GSM_ADD */ + + +/* + * More prototypes from implementations.. + */ +void Gsm_Coder ( + struct gsm_state * S, + word * s, /* [0..159] samples IN */ + word * LARc, /* [0..7] LAR coefficients OUT */ + word * Nc, /* [0..3] LTP lag OUT */ + word * bc, /* [0..3] coded LTP gain OUT */ + word * Mc, /* [0..3] RPE grid selection OUT */ + word * xmaxc,/* [0..3] Coded maximum amplitude OUT */ + word * xMc) ;/* [13*4] normalized RPE samples OUT */ + +void Gsm_Long_Term_Predictor ( /* 4x for 160 samples */ + struct gsm_state * S, + word * d, /* [0..39] residual signal IN */ + word * dp, /* [-120..-1] d' IN */ + word * e, /* [0..40] OUT */ + word * dpp, /* [0..40] OUT */ + word * Nc, /* correlation lag OUT */ + word * bc) ; /* gain factor OUT */ + +void Gsm_LPC_Analysis ( + struct gsm_state * S, + word * s, /* 0..159 signals IN/OUT */ + word * LARc) ; /* 0..7 LARc's OUT */ + +void Gsm_Preprocess ( + struct gsm_state * S, + word * s, word * so) ; + +void Gsm_Encoding ( + struct gsm_state * S, + word * e, + word * ep, + word * xmaxc, + word * Mc, + word * xMc) ; + +void Gsm_Short_Term_Analysis_Filter ( + struct gsm_state * S, + word * LARc, /* coded log area ratio [0..7] IN */ + word * d) ; /* st res. signal [0..159] IN/OUT */ + +void Gsm_Decoder ( + struct gsm_state * S, + word * LARcr, /* [0..7] IN */ + word * Ncr, /* [0..3] IN */ + word * bcr, /* [0..3] IN */ + word * Mcr, /* [0..3] IN */ + word * xmaxcr, /* [0..3] IN */ + word * xMcr, /* [0..13*4] IN */ + word * s) ; /* [0..159] OUT */ + +void Gsm_Decoding ( + struct gsm_state * S, + word xmaxcr, + word Mcr, + word * xMcr, /* [0..12] IN */ + word * erp) ; /* [0..39] OUT */ + +void Gsm_Long_Term_Synthesis_Filtering ( + struct gsm_state* S, + word Ncr, + word bcr, + word * erp, /* [0..39] IN */ + word * drp) ; /* [-120..-1] IN, [0..40] OUT */ + +void Gsm_RPE_Decoding ( + /*-struct gsm_state *S,-*/ + word xmaxcr, + word Mcr, + word * xMcr, /* [0..12], 3 bits IN */ + word * erp) ; /* [0..39] OUT */ + +void Gsm_RPE_Encoding ( + /*-struct gsm_state * S,-*/ + word * e, /* -5..-1][0..39][40..44 IN/OUT */ + word * xmaxc, /* OUT */ + word * Mc, /* OUT */ + word * xMc) ; /* [0..12] OUT */ + +void Gsm_Short_Term_Synthesis_Filter ( + struct gsm_state * S, + word * LARcr, /* log area ratios [0..7] IN */ + word * drp, /* received d [0...39] IN */ + word * s) ; /* signal s [0..159] OUT */ + +void Gsm_Update_of_reconstructed_short_time_residual_signal ( + word * dpp, /* [0...39] IN */ + word * ep, /* [0...39] IN */ + word * dp) ; /* [-120...-1] IN/OUT */ + +/* + * Tables from table.c + */ +#ifndef GSM_TABLE_C + +extern word gsm_A [8], gsm_B [8], gsm_MIC [8], gsm_MAC [8] ; +extern word gsm_INVA [8] ; +extern word gsm_DLB [4], gsm_QLB [4] ; +extern word gsm_H [11] ; +extern word gsm_NRFAC [8] ; +extern word gsm_FAC [8] ; + +#endif /* GSM_TABLE_C */ + +/* + * Debugging + */ +#ifdef NDEBUG + +# define gsm_debug_words(a, b, c, d) /* nil */ +# define gsm_debug_longwords(a, b, c, d) /* nil */ +# define gsm_debug_word(a, b) /* nil */ +# define gsm_debug_longword(a, b) /* nil */ + +#else /* !NDEBUG => DEBUG */ + + void gsm_debug_words (char * name, int, int, word *) ; + void gsm_debug_longwords (char * name, int, int, longword *) ; + void gsm_debug_longword (char * name, longword) ; + void gsm_debug_word (char * name, word) ; + +#endif /* !NDEBUG */ + +#endif /* PRIVATE_H */ +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 8bc5fdf2-e8c8-4686-9bd7-a30b512bef0c +*/ + diff --git a/libs/libsndfile/src/GSM610/gsm_create.c b/libs/libsndfile/src/GSM610/gsm_create.c new file mode 100644 index 0000000000..94e8d7d70c --- /dev/null +++ b/libs/libsndfile/src/GSM610/gsm_create.c @@ -0,0 +1,44 @@ +/* + * Copyright 1992 by Jutta Degener and Carsten Bormann, Technische + * Universitaet Berlin. See the accompanying file "COPYRIGHT" for + * details. THERE IS ABSOLUTELY NO WARRANTY FOR THIS SOFTWARE. + */ + +#include "config.h" + +#include +#include +#include + + + +#include "gsm.h" +#include "gsm610_priv.h" + +gsm gsm_create (void) +{ + gsm r; + + r = malloc (sizeof(struct gsm_state)); + if (!r) return r; + + memset((char *)r, 0, sizeof (struct gsm_state)); + r->nrp = 40; + + return r; +} + +/* Added for libsndfile : May 6, 2002. Not sure if it works. */ +void gsm_init (gsm state) +{ + memset (state, 0, sizeof (struct gsm_state)) ; + state->nrp = 40 ; +} +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 9fedb6b3-ed99-40c2-aac1-484c536261fe +*/ + diff --git a/libs/libsndfile/src/GSM610/gsm_decode.c b/libs/libsndfile/src/GSM610/gsm_decode.c new file mode 100644 index 0000000000..e6425587ce --- /dev/null +++ b/libs/libsndfile/src/GSM610/gsm_decode.c @@ -0,0 +1,366 @@ +/* + * Copyright 1992 by Jutta Degener and Carsten Bormann, Technische + * Universitaet Berlin. See the accompanying file "COPYRIGHT" for + * details. THERE IS ABSOLUTELY NO WARRANTY FOR THIS SOFTWARE. + */ + +#include "gsm610_priv.h" + +#include "gsm.h" + +int gsm_decode (gsm s, gsm_byte * c, gsm_signal * target) +{ + word LARc[8], Nc[4], Mc[4], bc[4], xmaxc[4], xmc[13*4]; + +#ifdef WAV49 + if (s->wav_fmt) { + + uword sr = 0; + + s->frame_index = !s->frame_index; + if (s->frame_index) { + + sr = *c++; + LARc[0] = sr & 0x3f; sr >>= 6; + sr |= (uword)*c++ << 2; + LARc[1] = sr & 0x3f; sr >>= 6; + sr |= (uword)*c++ << 4; + LARc[2] = sr & 0x1f; sr >>= 5; + LARc[3] = sr & 0x1f; sr >>= 5; + sr |= (uword)*c++ << 2; + LARc[4] = sr & 0xf; sr >>= 4; + LARc[5] = sr & 0xf; sr >>= 4; + sr |= (uword)*c++ << 2; /* 5 */ + LARc[6] = sr & 0x7; sr >>= 3; + LARc[7] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 4; + Nc[0] = sr & 0x7f; sr >>= 7; + bc[0] = sr & 0x3; sr >>= 2; + Mc[0] = sr & 0x3; sr >>= 2; + sr |= (uword)*c++ << 1; + xmaxc[0] = sr & 0x3f; sr >>= 6; + xmc[0] = sr & 0x7; sr >>= 3; + sr = *c++; + xmc[1] = sr & 0x7; sr >>= 3; + xmc[2] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 2; + xmc[3] = sr & 0x7; sr >>= 3; + xmc[4] = sr & 0x7; sr >>= 3; + xmc[5] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 1; /* 10 */ + xmc[6] = sr & 0x7; sr >>= 3; + xmc[7] = sr & 0x7; sr >>= 3; + xmc[8] = sr & 0x7; sr >>= 3; + sr = *c++; + xmc[9] = sr & 0x7; sr >>= 3; + xmc[10] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 2; + xmc[11] = sr & 0x7; sr >>= 3; + xmc[12] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 4; + Nc[1] = sr & 0x7f; sr >>= 7; + bc[1] = sr & 0x3; sr >>= 2; + Mc[1] = sr & 0x3; sr >>= 2; + sr |= (uword)*c++ << 1; + xmaxc[1] = sr & 0x3f; sr >>= 6; + xmc[13] = sr & 0x7; sr >>= 3; + sr = *c++; /* 15 */ + xmc[14] = sr & 0x7; sr >>= 3; + xmc[15] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 2; + xmc[16] = sr & 0x7; sr >>= 3; + xmc[17] = sr & 0x7; sr >>= 3; + xmc[18] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 1; + xmc[19] = sr & 0x7; sr >>= 3; + xmc[20] = sr & 0x7; sr >>= 3; + xmc[21] = sr & 0x7; sr >>= 3; + sr = *c++; + xmc[22] = sr & 0x7; sr >>= 3; + xmc[23] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 2; + xmc[24] = sr & 0x7; sr >>= 3; + xmc[25] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 4; /* 20 */ + Nc[2] = sr & 0x7f; sr >>= 7; + bc[2] = sr & 0x3; sr >>= 2; + Mc[2] = sr & 0x3; sr >>= 2; + sr |= (uword)*c++ << 1; + xmaxc[2] = sr & 0x3f; sr >>= 6; + xmc[26] = sr & 0x7; sr >>= 3; + sr = *c++; + xmc[27] = sr & 0x7; sr >>= 3; + xmc[28] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 2; + xmc[29] = sr & 0x7; sr >>= 3; + xmc[30] = sr & 0x7; sr >>= 3; + xmc[31] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 1; + xmc[32] = sr & 0x7; sr >>= 3; + xmc[33] = sr & 0x7; sr >>= 3; + xmc[34] = sr & 0x7; sr >>= 3; + sr = *c++; /* 25 */ + xmc[35] = sr & 0x7; sr >>= 3; + xmc[36] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 2; + xmc[37] = sr & 0x7; sr >>= 3; + xmc[38] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 4; + Nc[3] = sr & 0x7f; sr >>= 7; + bc[3] = sr & 0x3; sr >>= 2; + Mc[3] = sr & 0x3; sr >>= 2; + sr |= (uword)*c++ << 1; + xmaxc[3] = sr & 0x3f; sr >>= 6; + xmc[39] = sr & 0x7; sr >>= 3; + sr = *c++; + xmc[40] = sr & 0x7; sr >>= 3; + xmc[41] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 2; /* 30 */ + xmc[42] = sr & 0x7; sr >>= 3; + xmc[43] = sr & 0x7; sr >>= 3; + xmc[44] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 1; + xmc[45] = sr & 0x7; sr >>= 3; + xmc[46] = sr & 0x7; sr >>= 3; + xmc[47] = sr & 0x7; sr >>= 3; + sr = *c++; + xmc[48] = sr & 0x7; sr >>= 3; + xmc[49] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 2; + xmc[50] = sr & 0x7; sr >>= 3; + xmc[51] = sr & 0x7; sr >>= 3; + + s->frame_chain = sr & 0xf; + } + else { + sr = s->frame_chain; + sr |= (uword)*c++ << 4; /* 1 */ + LARc[0] = sr & 0x3f; sr >>= 6; + LARc[1] = sr & 0x3f; sr >>= 6; + sr = *c++; + LARc[2] = sr & 0x1f; sr >>= 5; + sr |= (uword)*c++ << 3; + LARc[3] = sr & 0x1f; sr >>= 5; + LARc[4] = sr & 0xf; sr >>= 4; + sr |= (uword)*c++ << 2; + LARc[5] = sr & 0xf; sr >>= 4; + LARc[6] = sr & 0x7; sr >>= 3; + LARc[7] = sr & 0x7; sr >>= 3; + sr = *c++; /* 5 */ + Nc[0] = sr & 0x7f; sr >>= 7; + sr |= (uword)*c++ << 1; + bc[0] = sr & 0x3; sr >>= 2; + Mc[0] = sr & 0x3; sr >>= 2; + sr |= (uword)*c++ << 5; + xmaxc[0] = sr & 0x3f; sr >>= 6; + xmc[0] = sr & 0x7; sr >>= 3; + xmc[1] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 1; + xmc[2] = sr & 0x7; sr >>= 3; + xmc[3] = sr & 0x7; sr >>= 3; + xmc[4] = sr & 0x7; sr >>= 3; + sr = *c++; + xmc[5] = sr & 0x7; sr >>= 3; + xmc[6] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 2; /* 10 */ + xmc[7] = sr & 0x7; sr >>= 3; + xmc[8] = sr & 0x7; sr >>= 3; + xmc[9] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 1; + xmc[10] = sr & 0x7; sr >>= 3; + xmc[11] = sr & 0x7; sr >>= 3; + xmc[12] = sr & 0x7; sr >>= 3; + sr = *c++; + Nc[1] = sr & 0x7f; sr >>= 7; + sr |= (uword)*c++ << 1; + bc[1] = sr & 0x3; sr >>= 2; + Mc[1] = sr & 0x3; sr >>= 2; + sr |= (uword)*c++ << 5; + xmaxc[1] = sr & 0x3f; sr >>= 6; + xmc[13] = sr & 0x7; sr >>= 3; + xmc[14] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 1; /* 15 */ + xmc[15] = sr & 0x7; sr >>= 3; + xmc[16] = sr & 0x7; sr >>= 3; + xmc[17] = sr & 0x7; sr >>= 3; + sr = *c++; + xmc[18] = sr & 0x7; sr >>= 3; + xmc[19] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 2; + xmc[20] = sr & 0x7; sr >>= 3; + xmc[21] = sr & 0x7; sr >>= 3; + xmc[22] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 1; + xmc[23] = sr & 0x7; sr >>= 3; + xmc[24] = sr & 0x7; sr >>= 3; + xmc[25] = sr & 0x7; sr >>= 3; + sr = *c++; + Nc[2] = sr & 0x7f; sr >>= 7; + sr |= (uword)*c++ << 1; /* 20 */ + bc[2] = sr & 0x3; sr >>= 2; + Mc[2] = sr & 0x3; sr >>= 2; + sr |= (uword)*c++ << 5; + xmaxc[2] = sr & 0x3f; sr >>= 6; + xmc[26] = sr & 0x7; sr >>= 3; + xmc[27] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 1; + xmc[28] = sr & 0x7; sr >>= 3; + xmc[29] = sr & 0x7; sr >>= 3; + xmc[30] = sr & 0x7; sr >>= 3; + sr = *c++; + xmc[31] = sr & 0x7; sr >>= 3; + xmc[32] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 2; + xmc[33] = sr & 0x7; sr >>= 3; + xmc[34] = sr & 0x7; sr >>= 3; + xmc[35] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 1; /* 25 */ + xmc[36] = sr & 0x7; sr >>= 3; + xmc[37] = sr & 0x7; sr >>= 3; + xmc[38] = sr & 0x7; sr >>= 3; + sr = *c++; + Nc[3] = sr & 0x7f; sr >>= 7; + sr |= (uword)*c++ << 1; + bc[3] = sr & 0x3; sr >>= 2; + Mc[3] = sr & 0x3; sr >>= 2; + sr |= (uword)*c++ << 5; + xmaxc[3] = sr & 0x3f; sr >>= 6; + xmc[39] = sr & 0x7; sr >>= 3; + xmc[40] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 1; + xmc[41] = sr & 0x7; sr >>= 3; + xmc[42] = sr & 0x7; sr >>= 3; + xmc[43] = sr & 0x7; sr >>= 3; + sr = *c++; /* 30 */ + xmc[44] = sr & 0x7; sr >>= 3; + xmc[45] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 2; + xmc[46] = sr & 0x7; sr >>= 3; + xmc[47] = sr & 0x7; sr >>= 3; + xmc[48] = sr & 0x7; sr >>= 3; + sr |= (uword)*c++ << 1; + xmc[49] = sr & 0x7; sr >>= 3; + xmc[50] = sr & 0x7; sr >>= 3; + xmc[51] = sr & 0x7; sr >>= 3; + } + } + else +#endif + { + /* GSM_MAGIC = (*c >> 4) & 0xF; */ + + if (((*c >> 4) & 0x0F) != GSM_MAGIC) return -1; + + LARc[0] = (*c++ & 0xF) << 2; /* 1 */ + LARc[0] |= (*c >> 6) & 0x3; + LARc[1] = *c++ & 0x3F; + LARc[2] = (*c >> 3) & 0x1F; + LARc[3] = (*c++ & 0x7) << 2; + LARc[3] |= (*c >> 6) & 0x3; + LARc[4] = (*c >> 2) & 0xF; + LARc[5] = (*c++ & 0x3) << 2; + LARc[5] |= (*c >> 6) & 0x3; + LARc[6] = (*c >> 3) & 0x7; + LARc[7] = *c++ & 0x7; + Nc[0] = (*c >> 1) & 0x7F; + bc[0] = (*c++ & 0x1) << 1; + bc[0] |= (*c >> 7) & 0x1; + Mc[0] = (*c >> 5) & 0x3; + xmaxc[0] = (*c++ & 0x1F) << 1; + xmaxc[0] |= (*c >> 7) & 0x1; + xmc[0] = (*c >> 4) & 0x7; + xmc[1] = (*c >> 1) & 0x7; + xmc[2] = (*c++ & 0x1) << 2; + xmc[2] |= (*c >> 6) & 0x3; + xmc[3] = (*c >> 3) & 0x7; + xmc[4] = *c++ & 0x7; + xmc[5] = (*c >> 5) & 0x7; + xmc[6] = (*c >> 2) & 0x7; + xmc[7] = (*c++ & 0x3) << 1; /* 10 */ + xmc[7] |= (*c >> 7) & 0x1; + xmc[8] = (*c >> 4) & 0x7; + xmc[9] = (*c >> 1) & 0x7; + xmc[10] = (*c++ & 0x1) << 2; + xmc[10] |= (*c >> 6) & 0x3; + xmc[11] = (*c >> 3) & 0x7; + xmc[12] = *c++ & 0x7; + Nc[1] = (*c >> 1) & 0x7F; + bc[1] = (*c++ & 0x1) << 1; + bc[1] |= (*c >> 7) & 0x1; + Mc[1] = (*c >> 5) & 0x3; + xmaxc[1] = (*c++ & 0x1F) << 1; + xmaxc[1] |= (*c >> 7) & 0x1; + xmc[13] = (*c >> 4) & 0x7; + xmc[14] = (*c >> 1) & 0x7; + xmc[15] = (*c++ & 0x1) << 2; + xmc[15] |= (*c >> 6) & 0x3; + xmc[16] = (*c >> 3) & 0x7; + xmc[17] = *c++ & 0x7; + xmc[18] = (*c >> 5) & 0x7; + xmc[19] = (*c >> 2) & 0x7; + xmc[20] = (*c++ & 0x3) << 1; + xmc[20] |= (*c >> 7) & 0x1; + xmc[21] = (*c >> 4) & 0x7; + xmc[22] = (*c >> 1) & 0x7; + xmc[23] = (*c++ & 0x1) << 2; + xmc[23] |= (*c >> 6) & 0x3; + xmc[24] = (*c >> 3) & 0x7; + xmc[25] = *c++ & 0x7; + Nc[2] = (*c >> 1) & 0x7F; + bc[2] = (*c++ & 0x1) << 1; /* 20 */ + bc[2] |= (*c >> 7) & 0x1; + Mc[2] = (*c >> 5) & 0x3; + xmaxc[2] = (*c++ & 0x1F) << 1; + xmaxc[2] |= (*c >> 7) & 0x1; + xmc[26] = (*c >> 4) & 0x7; + xmc[27] = (*c >> 1) & 0x7; + xmc[28] = (*c++ & 0x1) << 2; + xmc[28] |= (*c >> 6) & 0x3; + xmc[29] = (*c >> 3) & 0x7; + xmc[30] = *c++ & 0x7; + xmc[31] = (*c >> 5) & 0x7; + xmc[32] = (*c >> 2) & 0x7; + xmc[33] = (*c++ & 0x3) << 1; + xmc[33] |= (*c >> 7) & 0x1; + xmc[34] = (*c >> 4) & 0x7; + xmc[35] = (*c >> 1) & 0x7; + xmc[36] = (*c++ & 0x1) << 2; + xmc[36] |= (*c >> 6) & 0x3; + xmc[37] = (*c >> 3) & 0x7; + xmc[38] = *c++ & 0x7; + Nc[3] = (*c >> 1) & 0x7F; + bc[3] = (*c++ & 0x1) << 1; + bc[3] |= (*c >> 7) & 0x1; + Mc[3] = (*c >> 5) & 0x3; + xmaxc[3] = (*c++ & 0x1F) << 1; + xmaxc[3] |= (*c >> 7) & 0x1; + xmc[39] = (*c >> 4) & 0x7; + xmc[40] = (*c >> 1) & 0x7; + xmc[41] = (*c++ & 0x1) << 2; + xmc[41] |= (*c >> 6) & 0x3; + xmc[42] = (*c >> 3) & 0x7; + xmc[43] = *c++ & 0x7; /* 30 */ + xmc[44] = (*c >> 5) & 0x7; + xmc[45] = (*c >> 2) & 0x7; + xmc[46] = (*c++ & 0x3) << 1; + xmc[46] |= (*c >> 7) & 0x1; + xmc[47] = (*c >> 4) & 0x7; + xmc[48] = (*c >> 1) & 0x7; + xmc[49] = (*c++ & 0x1) << 2; + xmc[49] |= (*c >> 6) & 0x3; + xmc[50] = (*c >> 3) & 0x7; + xmc[51] = *c & 0x7; /* 33 */ + } + + Gsm_Decoder(s, LARc, Nc, bc, Mc, xmaxc, xmc, target); + + return 0; +} +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 6a9b6628-821c-4a96-84c1-485ebd35f170 +*/ + diff --git a/libs/libsndfile/src/GSM610/gsm_destroy.c b/libs/libsndfile/src/GSM610/gsm_destroy.c new file mode 100644 index 0000000000..9e2d6a49b7 --- /dev/null +++ b/libs/libsndfile/src/GSM610/gsm_destroy.c @@ -0,0 +1,31 @@ +/* + * Copyright 1992 by Jutta Degener and Carsten Bormann, Technische + * Universitaet Berlin. See the accompanying file "COPYRIGHT" for + * details. THERE IS ABSOLUTELY NO WARRANTY FOR THIS SOFTWARE. + */ + +#include "gsm.h" +#include "config.h" + +#ifdef HAS_STDLIB_H +# include +#else +# ifdef HAS_MALLOC_H +# include +# else + extern void free(); +# endif +#endif + +void gsm_destroy (gsm S) +{ + if (S) free((char *)S); +} +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: f423d09b-6ccc-47e0-9b18-ee1cf7a8e473 +*/ + diff --git a/libs/libsndfile/src/GSM610/gsm_encode.c b/libs/libsndfile/src/GSM610/gsm_encode.c new file mode 100644 index 0000000000..02af4ba282 --- /dev/null +++ b/libs/libsndfile/src/GSM610/gsm_encode.c @@ -0,0 +1,456 @@ +/* + * Copyright 1992 by Jutta Degener and Carsten Bormann, Technische + * Universitaet Berlin. See the accompanying file "COPYRIGHT" for + * details. THERE IS ABSOLUTELY NO WARRANTY FOR THIS SOFTWARE. + */ + +#include "gsm610_priv.h" +#include "gsm.h" + +void gsm_encode (gsm s, gsm_signal * source, gsm_byte * c) +{ + word LARc[8], Nc[4], Mc[4], bc[4], xmaxc[4], xmc[13*4]; + + Gsm_Coder(s, source, LARc, Nc, bc, Mc, xmaxc, xmc); + + + /* variable size + + GSM_MAGIC 4 + + LARc[0] 6 + LARc[1] 6 + LARc[2] 5 + LARc[3] 5 + LARc[4] 4 + LARc[5] 4 + LARc[6] 3 + LARc[7] 3 + + Nc[0] 7 + bc[0] 2 + Mc[0] 2 + xmaxc[0] 6 + xmc[0] 3 + xmc[1] 3 + xmc[2] 3 + xmc[3] 3 + xmc[4] 3 + xmc[5] 3 + xmc[6] 3 + xmc[7] 3 + xmc[8] 3 + xmc[9] 3 + xmc[10] 3 + xmc[11] 3 + xmc[12] 3 + + Nc[1] 7 + bc[1] 2 + Mc[1] 2 + xmaxc[1] 6 + xmc[13] 3 + xmc[14] 3 + xmc[15] 3 + xmc[16] 3 + xmc[17] 3 + xmc[18] 3 + xmc[19] 3 + xmc[20] 3 + xmc[21] 3 + xmc[22] 3 + xmc[23] 3 + xmc[24] 3 + xmc[25] 3 + + Nc[2] 7 + bc[2] 2 + Mc[2] 2 + xmaxc[2] 6 + xmc[26] 3 + xmc[27] 3 + xmc[28] 3 + xmc[29] 3 + xmc[30] 3 + xmc[31] 3 + xmc[32] 3 + xmc[33] 3 + xmc[34] 3 + xmc[35] 3 + xmc[36] 3 + xmc[37] 3 + xmc[38] 3 + + Nc[3] 7 + bc[3] 2 + Mc[3] 2 + xmaxc[3] 6 + xmc[39] 3 + xmc[40] 3 + xmc[41] 3 + xmc[42] 3 + xmc[43] 3 + xmc[44] 3 + xmc[45] 3 + xmc[46] 3 + xmc[47] 3 + xmc[48] 3 + xmc[49] 3 + xmc[50] 3 + xmc[51] 3 + */ + +#ifdef WAV49 + + if (s->wav_fmt) { + s->frame_index = !s->frame_index; + if (s->frame_index) { + + uword sr; + + sr = 0; + sr = sr >> 6 | LARc[0] << 10; + sr = sr >> 6 | LARc[1] << 10; + *c++ = sr >> 4; + sr = sr >> 5 | LARc[2] << 11; + *c++ = sr >> 7; + sr = sr >> 5 | LARc[3] << 11; + sr = sr >> 4 | LARc[4] << 12; + *c++ = sr >> 6; + sr = sr >> 4 | LARc[5] << 12; + sr = sr >> 3 | LARc[6] << 13; + *c++ = sr >> 7; + sr = sr >> 3 | LARc[7] << 13; + sr = sr >> 7 | Nc[0] << 9; + *c++ = sr >> 5; + sr = sr >> 2 | bc[0] << 14; + sr = sr >> 2 | Mc[0] << 14; + sr = sr >> 6 | xmaxc[0] << 10; + *c++ = sr >> 3; + sr = sr >> 3 | xmc[0] << 13; + *c++ = sr >> 8; + sr = sr >> 3 | xmc[1] << 13; + sr = sr >> 3 | xmc[2] << 13; + sr = sr >> 3 | xmc[3] << 13; + *c++ = sr >> 7; + sr = sr >> 3 | xmc[4] << 13; + sr = sr >> 3 | xmc[5] << 13; + sr = sr >> 3 | xmc[6] << 13; + *c++ = sr >> 6; + sr = sr >> 3 | xmc[7] << 13; + sr = sr >> 3 | xmc[8] << 13; + *c++ = sr >> 8; + sr = sr >> 3 | xmc[9] << 13; + sr = sr >> 3 | xmc[10] << 13; + sr = sr >> 3 | xmc[11] << 13; + *c++ = sr >> 7; + sr = sr >> 3 | xmc[12] << 13; + sr = sr >> 7 | Nc[1] << 9; + *c++ = sr >> 5; + sr = sr >> 2 | bc[1] << 14; + sr = sr >> 2 | Mc[1] << 14; + sr = sr >> 6 | xmaxc[1] << 10; + *c++ = sr >> 3; + sr = sr >> 3 | xmc[13] << 13; + *c++ = sr >> 8; + sr = sr >> 3 | xmc[14] << 13; + sr = sr >> 3 | xmc[15] << 13; + sr = sr >> 3 | xmc[16] << 13; + *c++ = sr >> 7; + sr = sr >> 3 | xmc[17] << 13; + sr = sr >> 3 | xmc[18] << 13; + sr = sr >> 3 | xmc[19] << 13; + *c++ = sr >> 6; + sr = sr >> 3 | xmc[20] << 13; + sr = sr >> 3 | xmc[21] << 13; + *c++ = sr >> 8; + sr = sr >> 3 | xmc[22] << 13; + sr = sr >> 3 | xmc[23] << 13; + sr = sr >> 3 | xmc[24] << 13; + *c++ = sr >> 7; + sr = sr >> 3 | xmc[25] << 13; + sr = sr >> 7 | Nc[2] << 9; + *c++ = sr >> 5; + sr = sr >> 2 | bc[2] << 14; + sr = sr >> 2 | Mc[2] << 14; + sr = sr >> 6 | xmaxc[2] << 10; + *c++ = sr >> 3; + sr = sr >> 3 | xmc[26] << 13; + *c++ = sr >> 8; + sr = sr >> 3 | xmc[27] << 13; + sr = sr >> 3 | xmc[28] << 13; + sr = sr >> 3 | xmc[29] << 13; + *c++ = sr >> 7; + sr = sr >> 3 | xmc[30] << 13; + sr = sr >> 3 | xmc[31] << 13; + sr = sr >> 3 | xmc[32] << 13; + *c++ = sr >> 6; + sr = sr >> 3 | xmc[33] << 13; + sr = sr >> 3 | xmc[34] << 13; + *c++ = sr >> 8; + sr = sr >> 3 | xmc[35] << 13; + sr = sr >> 3 | xmc[36] << 13; + sr = sr >> 3 | xmc[37] << 13; + *c++ = sr >> 7; + sr = sr >> 3 | xmc[38] << 13; + sr = sr >> 7 | Nc[3] << 9; + *c++ = sr >> 5; + sr = sr >> 2 | bc[3] << 14; + sr = sr >> 2 | Mc[3] << 14; + sr = sr >> 6 | xmaxc[3] << 10; + *c++ = sr >> 3; + sr = sr >> 3 | xmc[39] << 13; + *c++ = sr >> 8; + sr = sr >> 3 | xmc[40] << 13; + sr = sr >> 3 | xmc[41] << 13; + sr = sr >> 3 | xmc[42] << 13; + *c++ = sr >> 7; + sr = sr >> 3 | xmc[43] << 13; + sr = sr >> 3 | xmc[44] << 13; + sr = sr >> 3 | xmc[45] << 13; + *c++ = sr >> 6; + sr = sr >> 3 | xmc[46] << 13; + sr = sr >> 3 | xmc[47] << 13; + *c++ = sr >> 8; + sr = sr >> 3 | xmc[48] << 13; + sr = sr >> 3 | xmc[49] << 13; + sr = sr >> 3 | xmc[50] << 13; + *c++ = sr >> 7; + sr = sr >> 3 | xmc[51] << 13; + sr = sr >> 4; + *c = sr >> 8; + s->frame_chain = *c; + } + else { + uword sr; + + sr = 0; + sr = sr >> 4 | s->frame_chain << 12; + sr = sr >> 6 | LARc[0] << 10; + *c++ = sr >> 6; + sr = sr >> 6 | LARc[1] << 10; + *c++ = sr >> 8; + sr = sr >> 5 | LARc[2] << 11; + sr = sr >> 5 | LARc[3] << 11; + *c++ = sr >> 6; + sr = sr >> 4 | LARc[4] << 12; + sr = sr >> 4 | LARc[5] << 12; + *c++ = sr >> 6; + sr = sr >> 3 | LARc[6] << 13; + sr = sr >> 3 | LARc[7] << 13; + *c++ = sr >> 8; + sr = sr >> 7 | Nc[0] << 9; + sr = sr >> 2 | bc[0] << 14; + *c++ = sr >> 7; + sr = sr >> 2 | Mc[0] << 14; + sr = sr >> 6 | xmaxc[0] << 10; + *c++ = sr >> 7; + sr = sr >> 3 | xmc[0] << 13; + sr = sr >> 3 | xmc[1] << 13; + sr = sr >> 3 | xmc[2] << 13; + *c++ = sr >> 6; + sr = sr >> 3 | xmc[3] << 13; + sr = sr >> 3 | xmc[4] << 13; + *c++ = sr >> 8; + sr = sr >> 3 | xmc[5] << 13; + sr = sr >> 3 | xmc[6] << 13; + sr = sr >> 3 | xmc[7] << 13; + *c++ = sr >> 7; + sr = sr >> 3 | xmc[8] << 13; + sr = sr >> 3 | xmc[9] << 13; + sr = sr >> 3 | xmc[10] << 13; + *c++ = sr >> 6; + sr = sr >> 3 | xmc[11] << 13; + sr = sr >> 3 | xmc[12] << 13; + *c++ = sr >> 8; + sr = sr >> 7 | Nc[1] << 9; + sr = sr >> 2 | bc[1] << 14; + *c++ = sr >> 7; + sr = sr >> 2 | Mc[1] << 14; + sr = sr >> 6 | xmaxc[1] << 10; + *c++ = sr >> 7; + sr = sr >> 3 | xmc[13] << 13; + sr = sr >> 3 | xmc[14] << 13; + sr = sr >> 3 | xmc[15] << 13; + *c++ = sr >> 6; + sr = sr >> 3 | xmc[16] << 13; + sr = sr >> 3 | xmc[17] << 13; + *c++ = sr >> 8; + sr = sr >> 3 | xmc[18] << 13; + sr = sr >> 3 | xmc[19] << 13; + sr = sr >> 3 | xmc[20] << 13; + *c++ = sr >> 7; + sr = sr >> 3 | xmc[21] << 13; + sr = sr >> 3 | xmc[22] << 13; + sr = sr >> 3 | xmc[23] << 13; + *c++ = sr >> 6; + sr = sr >> 3 | xmc[24] << 13; + sr = sr >> 3 | xmc[25] << 13; + *c++ = sr >> 8; + sr = sr >> 7 | Nc[2] << 9; + sr = sr >> 2 | bc[2] << 14; + *c++ = sr >> 7; + sr = sr >> 2 | Mc[2] << 14; + sr = sr >> 6 | xmaxc[2] << 10; + *c++ = sr >> 7; + sr = sr >> 3 | xmc[26] << 13; + sr = sr >> 3 | xmc[27] << 13; + sr = sr >> 3 | xmc[28] << 13; + *c++ = sr >> 6; + sr = sr >> 3 | xmc[29] << 13; + sr = sr >> 3 | xmc[30] << 13; + *c++ = sr >> 8; + sr = sr >> 3 | xmc[31] << 13; + sr = sr >> 3 | xmc[32] << 13; + sr = sr >> 3 | xmc[33] << 13; + *c++ = sr >> 7; + sr = sr >> 3 | xmc[34] << 13; + sr = sr >> 3 | xmc[35] << 13; + sr = sr >> 3 | xmc[36] << 13; + *c++ = sr >> 6; + sr = sr >> 3 | xmc[37] << 13; + sr = sr >> 3 | xmc[38] << 13; + *c++ = sr >> 8; + sr = sr >> 7 | Nc[3] << 9; + sr = sr >> 2 | bc[3] << 14; + *c++ = sr >> 7; + sr = sr >> 2 | Mc[3] << 14; + sr = sr >> 6 | xmaxc[3] << 10; + *c++ = sr >> 7; + sr = sr >> 3 | xmc[39] << 13; + sr = sr >> 3 | xmc[40] << 13; + sr = sr >> 3 | xmc[41] << 13; + *c++ = sr >> 6; + sr = sr >> 3 | xmc[42] << 13; + sr = sr >> 3 | xmc[43] << 13; + *c++ = sr >> 8; + sr = sr >> 3 | xmc[44] << 13; + sr = sr >> 3 | xmc[45] << 13; + sr = sr >> 3 | xmc[46] << 13; + *c++ = sr >> 7; + sr = sr >> 3 | xmc[47] << 13; + sr = sr >> 3 | xmc[48] << 13; + sr = sr >> 3 | xmc[49] << 13; + *c++ = sr >> 6; + sr = sr >> 3 | xmc[50] << 13; + sr = sr >> 3 | xmc[51] << 13; + *c++ = sr >> 8; + } + } + + else + +#endif /* WAV49 */ + { + + *c++ = ((GSM_MAGIC & 0xF) << 4) /* 1 */ + | ((LARc[0] >> 2) & 0xF); + *c++ = ((LARc[0] & 0x3) << 6) + | (LARc[1] & 0x3F); + *c++ = ((LARc[2] & 0x1F) << 3) + | ((LARc[3] >> 2) & 0x7); + *c++ = ((LARc[3] & 0x3) << 6) + | ((LARc[4] & 0xF) << 2) + | ((LARc[5] >> 2) & 0x3); + *c++ = ((LARc[5] & 0x3) << 6) + | ((LARc[6] & 0x7) << 3) + | (LARc[7] & 0x7); + *c++ = ((Nc[0] & 0x7F) << 1) + | ((bc[0] >> 1) & 0x1); + *c++ = ((bc[0] & 0x1) << 7) + | ((Mc[0] & 0x3) << 5) + | ((xmaxc[0] >> 1) & 0x1F); + *c++ = ((xmaxc[0] & 0x1) << 7) + | ((xmc[0] & 0x7) << 4) + | ((xmc[1] & 0x7) << 1) + | ((xmc[2] >> 2) & 0x1); + *c++ = ((xmc[2] & 0x3) << 6) + | ((xmc[3] & 0x7) << 3) + | (xmc[4] & 0x7); + *c++ = ((xmc[5] & 0x7) << 5) /* 10 */ + | ((xmc[6] & 0x7) << 2) + | ((xmc[7] >> 1) & 0x3); + *c++ = ((xmc[7] & 0x1) << 7) + | ((xmc[8] & 0x7) << 4) + | ((xmc[9] & 0x7) << 1) + | ((xmc[10] >> 2) & 0x1); + *c++ = ((xmc[10] & 0x3) << 6) + | ((xmc[11] & 0x7) << 3) + | (xmc[12] & 0x7); + *c++ = ((Nc[1] & 0x7F) << 1) + | ((bc[1] >> 1) & 0x1); + *c++ = ((bc[1] & 0x1) << 7) + | ((Mc[1] & 0x3) << 5) + | ((xmaxc[1] >> 1) & 0x1F); + *c++ = ((xmaxc[1] & 0x1) << 7) + | ((xmc[13] & 0x7) << 4) + | ((xmc[14] & 0x7) << 1) + | ((xmc[15] >> 2) & 0x1); + *c++ = ((xmc[15] & 0x3) << 6) + | ((xmc[16] & 0x7) << 3) + | (xmc[17] & 0x7); + *c++ = ((xmc[18] & 0x7) << 5) + | ((xmc[19] & 0x7) << 2) + | ((xmc[20] >> 1) & 0x3); + *c++ = ((xmc[20] & 0x1) << 7) + | ((xmc[21] & 0x7) << 4) + | ((xmc[22] & 0x7) << 1) + | ((xmc[23] >> 2) & 0x1); + *c++ = ((xmc[23] & 0x3) << 6) + | ((xmc[24] & 0x7) << 3) + | (xmc[25] & 0x7); + *c++ = ((Nc[2] & 0x7F) << 1) /* 20 */ + | ((bc[2] >> 1) & 0x1); + *c++ = ((bc[2] & 0x1) << 7) + | ((Mc[2] & 0x3) << 5) + | ((xmaxc[2] >> 1) & 0x1F); + *c++ = ((xmaxc[2] & 0x1) << 7) + | ((xmc[26] & 0x7) << 4) + | ((xmc[27] & 0x7) << 1) + | ((xmc[28] >> 2) & 0x1); + *c++ = ((xmc[28] & 0x3) << 6) + | ((xmc[29] & 0x7) << 3) + | (xmc[30] & 0x7); + *c++ = ((xmc[31] & 0x7) << 5) + | ((xmc[32] & 0x7) << 2) + | ((xmc[33] >> 1) & 0x3); + *c++ = ((xmc[33] & 0x1) << 7) + | ((xmc[34] & 0x7) << 4) + | ((xmc[35] & 0x7) << 1) + | ((xmc[36] >> 2) & 0x1); + *c++ = ((xmc[36] & 0x3) << 6) + | ((xmc[37] & 0x7) << 3) + | (xmc[38] & 0x7); + *c++ = ((Nc[3] & 0x7F) << 1) + | ((bc[3] >> 1) & 0x1); + *c++ = ((bc[3] & 0x1) << 7) + | ((Mc[3] & 0x3) << 5) + | ((xmaxc[3] >> 1) & 0x1F); + *c++ = ((xmaxc[3] & 0x1) << 7) + | ((xmc[39] & 0x7) << 4) + | ((xmc[40] & 0x7) << 1) + | ((xmc[41] >> 2) & 0x1); + *c++ = ((xmc[41] & 0x3) << 6) /* 30 */ + | ((xmc[42] & 0x7) << 3) + | (xmc[43] & 0x7); + *c++ = ((xmc[44] & 0x7) << 5) + | ((xmc[45] & 0x7) << 2) + | ((xmc[46] >> 1) & 0x3); + *c++ = ((xmc[46] & 0x1) << 7) + | ((xmc[47] & 0x7) << 4) + | ((xmc[48] & 0x7) << 1) + | ((xmc[49] >> 2) & 0x1); + *c++ = ((xmc[49] & 0x3) << 6) + | ((xmc[50] & 0x7) << 3) + | (xmc[51] & 0x7); + + } +} +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: cfe9c43d-d97c-4216-b5e5-ccd6a25b582b +*/ + diff --git a/libs/libsndfile/src/GSM610/gsm_option.c b/libs/libsndfile/src/GSM610/gsm_option.c new file mode 100644 index 0000000000..5c56d78df2 --- /dev/null +++ b/libs/libsndfile/src/GSM610/gsm_option.c @@ -0,0 +1,74 @@ +/* + * Copyright 1992 by Jutta Degener and Carsten Bormann, Technische + * Universitaet Berlin. See the accompanying file "COPYRIGHT" for + * details. THERE IS ABSOLUTELY NO WARRANTY FOR THIS SOFTWARE. + */ + +#include "gsm610_priv.h" + +#include "gsm.h" + +int gsm_option (gsm r, int opt, int * val) +{ + int result = -1; + + switch (opt) { + case GSM_OPT_LTP_CUT: +#ifdef LTP_CUT + result = r->ltp_cut; + if (val) r->ltp_cut = *val; +#endif + break; + + case GSM_OPT_VERBOSE: +#ifndef NDEBUG + result = r->verbose; + if (val) r->verbose = *val; +#endif + break; + + case GSM_OPT_FAST: + +#if defined(FAST) && defined(USE_FLOAT_MUL) + result = r->fast; + if (val) r->fast = !!*val; +#endif + break; + + case GSM_OPT_FRAME_CHAIN: + +#ifdef WAV49 + result = r->frame_chain; + if (val) r->frame_chain = *val; +#endif + break; + + case GSM_OPT_FRAME_INDEX: + +#ifdef WAV49 + result = r->frame_index; + if (val) r->frame_index = *val; +#endif + break; + + case GSM_OPT_WAV49: + +#ifdef WAV49 + result = r->wav_fmt; + if (val) r->wav_fmt = !!*val; +#endif + break; + + default: + break; + } + return result; +} +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 963ff156-506f-4359-9145-371e9060b030 +*/ + diff --git a/libs/libsndfile/src/GSM610/long_term.c b/libs/libsndfile/src/GSM610/long_term.c new file mode 100644 index 0000000000..5179d1d09b --- /dev/null +++ b/libs/libsndfile/src/GSM610/long_term.c @@ -0,0 +1,951 @@ +/* + * Copyright 1992 by Jutta Degener and Carsten Bormann, Technische + * Universitaet Berlin. See the accompanying file "COPYRIGHT" for + * details. THERE IS ABSOLUTELY NO WARRANTY FOR THIS SOFTWARE. + */ + +#include +#include + +#include "gsm610_priv.h" + +#include "gsm.h" + +/* + * 4.2.11 .. 4.2.12 LONG TERM PREDICTOR (LTP) SECTION + */ + + +/* + * This module computes the LTP gain (bc) and the LTP lag (Nc) + * for the long term analysis filter. This is done by calculating a + * maximum of the cross-correlation function between the current + * sub-segment short term residual signal d[0..39] (output of + * the short term analysis filter; for simplification the index + * of this array begins at 0 and ends at 39 for each sub-segment of the + * RPE-LTP analysis) and the previous reconstructed short term + * residual signal dp[ -120 .. -1 ]. A dynamic scaling must be + * performed to avoid overflow. + */ + + /* The next procedure exists in six versions. First two integer + * version (if USE_FLOAT_MUL is not defined); then four floating + * point versions, twice with proper scaling (USE_FLOAT_MUL defined), + * once without (USE_FLOAT_MUL and FAST defined, and fast run-time + * option used). Every pair has first a Cut version (see the -C + * option to toast or the LTP_CUT option to gsm_option()), then the + * uncut one. (For a detailed explanation of why this is altogether + * a bad idea, see Henry Spencer and Geoff Collyer, ``#ifdef Considered + * Harmful''.) + */ + +#ifndef USE_FLOAT_MUL + +#ifdef LTP_CUT + +static void Cut_Calculation_of_the_LTP_parameters ( + + struct gsm_state * st, + + register word * d, /* [0..39] IN */ + register word * dp, /* [-120..-1] IN */ + word * bc_out, /* OUT */ + word * Nc_out /* OUT */ +) +{ + register int k, lambda; + word Nc, bc; + word wt[40]; + + longword L_result; + longword L_max, L_power; + word R, S, dmax, scal, best_k; + word ltp_cut; + + register word temp, wt_k; + + /* Search of the optimum scaling of d[0..39]. + */ + dmax = 0; + for (k = 0; k <= 39; k++) { + temp = d[k]; + temp = GSM_ABS( temp ); + if (temp > dmax) { + dmax = temp; + best_k = k; + } + } + temp = 0; + if (dmax == 0) scal = 0; + else { + assert(dmax > 0); + temp = gsm_norm( (longword)dmax << 16 ); + } + if (temp > 6) scal = 0; + else scal = 6 - temp; + assert(scal >= 0); + + /* Search for the maximum cross-correlation and coding of the LTP lag + */ + L_max = 0; + Nc = 40; /* index for the maximum cross-correlation */ + wt_k = SASR_W(d[best_k], scal); + + for (lambda = 40; lambda <= 120; lambda++) { + L_result = (longword)wt_k * dp[best_k - lambda]; + if (L_result > L_max) { + Nc = lambda; + L_max = L_result; + } + } + *Nc_out = Nc; + L_max <<= 1; + + /* Rescaling of L_max + */ + assert(scal <= 100 && scal >= -100); + L_max = L_max >> (6 - scal); /* sub(6, scal) */ + + assert( Nc <= 120 && Nc >= 40); + + /* Compute the power of the reconstructed short term residual + * signal dp[..] + */ + L_power = 0; + for (k = 0; k <= 39; k++) { + + register longword L_temp; + + L_temp = SASR_W( dp[k - Nc], 3 ); + L_power += L_temp * L_temp; + } + L_power <<= 1; /* from L_MULT */ + + /* Normalization of L_max and L_power + */ + + if (L_max <= 0) { + *bc_out = 0; + return; + } + if (L_max >= L_power) { + *bc_out = 3; + return; + } + + temp = gsm_norm( L_power ); + + R = SASR( L_max << temp, 16 ); + S = SASR( L_power << temp, 16 ); + + /* Coding of the LTP gain + */ + + /* Table 4.3a must be used to obtain the level DLB[i] for the + * quantization of the LTP gain b to get the coded version bc. + */ + for (bc = 0; bc <= 2; bc++) if (R <= gsm_mult(S, gsm_DLB[bc])) break; + *bc_out = bc; +} + +#endif /* LTP_CUT */ + +static void Calculation_of_the_LTP_parameters ( + register word * d, /* [0..39] IN */ + register word * dp, /* [-120..-1] IN */ + word * bc_out, /* OUT */ + word * Nc_out /* OUT */ +) +{ + register int k, lambda; + word Nc, bc; + word wt[40]; + + longword L_max, L_power; + word R, S, dmax, scal; + register word temp; + + /* Search of the optimum scaling of d[0..39]. + */ + dmax = 0; + + for (k = 0; k <= 39; k++) { + temp = d[k]; + temp = GSM_ABS( temp ); + if (temp > dmax) dmax = temp; + } + + temp = 0; + if (dmax == 0) scal = 0; + else { + assert(dmax > 0); + temp = gsm_norm( (longword)dmax << 16 ); + } + + if (temp > 6) scal = 0; + else scal = 6 - temp; + + assert(scal >= 0); + + /* Initialization of a working array wt + */ + + for (k = 0; k <= 39; k++) wt[k] = SASR_W( d[k], scal ); + + /* Search for the maximum cross-correlation and coding of the LTP lag + */ + L_max = 0; + Nc = 40; /* index for the maximum cross-correlation */ + + for (lambda = 40; lambda <= 120; lambda++) { + +# undef STEP +# define STEP(k) (longword)wt[k] * dp[k - lambda] + + register longword L_result; + + L_result = STEP(0) ; L_result += STEP(1) ; + L_result += STEP(2) ; L_result += STEP(3) ; + L_result += STEP(4) ; L_result += STEP(5) ; + L_result += STEP(6) ; L_result += STEP(7) ; + L_result += STEP(8) ; L_result += STEP(9) ; + L_result += STEP(10) ; L_result += STEP(11) ; + L_result += STEP(12) ; L_result += STEP(13) ; + L_result += STEP(14) ; L_result += STEP(15) ; + L_result += STEP(16) ; L_result += STEP(17) ; + L_result += STEP(18) ; L_result += STEP(19) ; + L_result += STEP(20) ; L_result += STEP(21) ; + L_result += STEP(22) ; L_result += STEP(23) ; + L_result += STEP(24) ; L_result += STEP(25) ; + L_result += STEP(26) ; L_result += STEP(27) ; + L_result += STEP(28) ; L_result += STEP(29) ; + L_result += STEP(30) ; L_result += STEP(31) ; + L_result += STEP(32) ; L_result += STEP(33) ; + L_result += STEP(34) ; L_result += STEP(35) ; + L_result += STEP(36) ; L_result += STEP(37) ; + L_result += STEP(38) ; L_result += STEP(39) ; + + if (L_result > L_max) { + + Nc = lambda; + L_max = L_result; + } + } + + *Nc_out = Nc; + + L_max <<= 1; + + /* Rescaling of L_max + */ + assert(scal <= 100 && scal >= -100); + L_max = L_max >> (6 - scal); /* sub(6, scal) */ + + assert( Nc <= 120 && Nc >= 40); + + /* Compute the power of the reconstructed short term residual + * signal dp[..] + */ + L_power = 0; + for (k = 0; k <= 39; k++) { + + register longword L_temp; + + L_temp = SASR_W( dp[k - Nc], 3 ); + L_power += L_temp * L_temp; + } + L_power <<= 1; /* from L_MULT */ + + /* Normalization of L_max and L_power + */ + + if (L_max <= 0) { + *bc_out = 0; + return; + } + if (L_max >= L_power) { + *bc_out = 3; + return; + } + + temp = gsm_norm( L_power ); + + R = SASR_L( L_max << temp, 16 ); + S = SASR_L( L_power << temp, 16 ); + + /* Coding of the LTP gain + */ + + /* Table 4.3a must be used to obtain the level DLB[i] for the + * quantization of the LTP gain b to get the coded version bc. + */ + for (bc = 0; bc <= 2; bc++) if (R <= gsm_mult(S, gsm_DLB[bc])) break; + *bc_out = bc; +} + +#else /* USE_FLOAT_MUL */ + +#ifdef LTP_CUT + +static void Cut_Calculation_of_the_LTP_parameters ( + struct gsm_state * st, /* IN */ + register word * d, /* [0..39] IN */ + register word * dp, /* [-120..-1] IN */ + word * bc_out, /* OUT */ + word * Nc_out /* OUT */ +) +{ + register int k, lambda; + word Nc, bc; + word ltp_cut; + + float wt_float[40]; + float dp_float_base[120], * dp_float = dp_float_base + 120; + + longword L_max, L_power; + word R, S, dmax, scal; + register word temp; + + /* Search of the optimum scaling of d[0..39]. + */ + dmax = 0; + + for (k = 0; k <= 39; k++) { + temp = d[k]; + temp = GSM_ABS( temp ); + if (temp > dmax) dmax = temp; + } + + temp = 0; + if (dmax == 0) scal = 0; + else { + assert(dmax > 0); + temp = gsm_norm( (longword)dmax << 16 ); + } + + if (temp > 6) scal = 0; + else scal = 6 - temp; + + assert(scal >= 0); + ltp_cut = (longword)SASR_W(dmax, scal) * st->ltp_cut / 100; + + + /* Initialization of a working array wt + */ + + for (k = 0; k < 40; k++) { + register word w = SASR_W( d[k], scal ); + if (w < 0 ? w > -ltp_cut : w < ltp_cut) { + wt_float[k] = 0.0; + } + else { + wt_float[k] = w; + } + } + for (k = -120; k < 0; k++) dp_float[k] = dp[k]; + + /* Search for the maximum cross-correlation and coding of the LTP lag + */ + L_max = 0; + Nc = 40; /* index for the maximum cross-correlation */ + + for (lambda = 40; lambda <= 120; lambda += 9) { + + /* Calculate L_result for l = lambda .. lambda + 9. + */ + register float *lp = dp_float - lambda; + + register float W; + register float a = lp[-8], b = lp[-7], c = lp[-6], + d = lp[-5], e = lp[-4], f = lp[-3], + g = lp[-2], h = lp[-1]; + register float E; + register float S0 = 0, S1 = 0, S2 = 0, S3 = 0, S4 = 0, + S5 = 0, S6 = 0, S7 = 0, S8 = 0; + +# undef STEP +# define STEP(K, a, b, c, d, e, f, g, h) \ + if ((W = wt_float[K]) != 0.0) { \ + E = W * a; S8 += E; \ + E = W * b; S7 += E; \ + E = W * c; S6 += E; \ + E = W * d; S5 += E; \ + E = W * e; S4 += E; \ + E = W * f; S3 += E; \ + E = W * g; S2 += E; \ + E = W * h; S1 += E; \ + a = lp[K]; \ + E = W * a; S0 += E; } else (a = lp[K]) + +# define STEP_A(K) STEP(K, a, b, c, d, e, f, g, h) +# define STEP_B(K) STEP(K, b, c, d, e, f, g, h, a) +# define STEP_C(K) STEP(K, c, d, e, f, g, h, a, b) +# define STEP_D(K) STEP(K, d, e, f, g, h, a, b, c) +# define STEP_E(K) STEP(K, e, f, g, h, a, b, c, d) +# define STEP_F(K) STEP(K, f, g, h, a, b, c, d, e) +# define STEP_G(K) STEP(K, g, h, a, b, c, d, e, f) +# define STEP_H(K) STEP(K, h, a, b, c, d, e, f, g) + + STEP_A( 0); STEP_B( 1); STEP_C( 2); STEP_D( 3); + STEP_E( 4); STEP_F( 5); STEP_G( 6); STEP_H( 7); + + STEP_A( 8); STEP_B( 9); STEP_C(10); STEP_D(11); + STEP_E(12); STEP_F(13); STEP_G(14); STEP_H(15); + + STEP_A(16); STEP_B(17); STEP_C(18); STEP_D(19); + STEP_E(20); STEP_F(21); STEP_G(22); STEP_H(23); + + STEP_A(24); STEP_B(25); STEP_C(26); STEP_D(27); + STEP_E(28); STEP_F(29); STEP_G(30); STEP_H(31); + + STEP_A(32); STEP_B(33); STEP_C(34); STEP_D(35); + STEP_E(36); STEP_F(37); STEP_G(38); STEP_H(39); + + if (S0 > L_max) { L_max = S0; Nc = lambda; } + if (S1 > L_max) { L_max = S1; Nc = lambda + 1; } + if (S2 > L_max) { L_max = S2; Nc = lambda + 2; } + if (S3 > L_max) { L_max = S3; Nc = lambda + 3; } + if (S4 > L_max) { L_max = S4; Nc = lambda + 4; } + if (S5 > L_max) { L_max = S5; Nc = lambda + 5; } + if (S6 > L_max) { L_max = S6; Nc = lambda + 6; } + if (S7 > L_max) { L_max = S7; Nc = lambda + 7; } + if (S8 > L_max) { L_max = S8; Nc = lambda + 8; } + + } + *Nc_out = Nc; + + L_max <<= 1; + + /* Rescaling of L_max + */ + assert(scal <= 100 && scal >= -100); + L_max = L_max >> (6 - scal); /* sub(6, scal) */ + + assert( Nc <= 120 && Nc >= 40); + + /* Compute the power of the reconstructed short term residual + * signal dp[..] + */ + L_power = 0; + for (k = 0; k <= 39; k++) { + + register longword L_temp; + + L_temp = SASR_W( dp[k - Nc], 3 ); + L_power += L_temp * L_temp; + } + L_power <<= 1; /* from L_MULT */ + + /* Normalization of L_max and L_power + */ + + if (L_max <= 0) { + *bc_out = 0; + return; + } + if (L_max >= L_power) { + *bc_out = 3; + return; + } + + temp = gsm_norm( L_power ); + + R = SASR( L_max << temp, 16 ); + S = SASR( L_power << temp, 16 ); + + /* Coding of the LTP gain + */ + + /* Table 4.3a must be used to obtain the level DLB[i] for the + * quantization of the LTP gain b to get the coded version bc. + */ + for (bc = 0; bc <= 2; bc++) if (R <= gsm_mult(S, gsm_DLB[bc])) break; + *bc_out = bc; +} + +#endif /* LTP_CUT */ + +static void Calculation_of_the_LTP_parameters ( + register word * din, /* [0..39] IN */ + register word * dp, /* [-120..-1] IN */ + word * bc_out, /* OUT */ + word * Nc_out /* OUT */ +) +{ + register int k, lambda; + word Nc, bc; + + float wt_float[40]; + float dp_float_base[120], * dp_float = dp_float_base + 120; + + longword L_max, L_power; + word R, S, dmax, scal; + register word temp; + + /* Search of the optimum scaling of d[0..39]. + */ + dmax = 0; + + for (k = 0; k <= 39; k++) { + temp = din [k] ; + temp = GSM_ABS (temp) ; + if (temp > dmax) dmax = temp; + } + + temp = 0; + if (dmax == 0) scal = 0; + else { + assert(dmax > 0); + temp = gsm_norm( (longword)dmax << 16 ); + } + + if (temp > 6) scal = 0; + else scal = 6 - temp; + + assert(scal >= 0); + + /* Initialization of a working array wt + */ + + for (k = 0; k < 40; k++) wt_float[k] = SASR_W (din [k], scal) ; + for (k = -120; k < 0; k++) dp_float[k] = dp[k]; + + /* Search for the maximum cross-correlation and coding of the LTP lag + */ + L_max = 0; + Nc = 40; /* index for the maximum cross-correlation */ + + for (lambda = 40; lambda <= 120; lambda += 9) { + + /* Calculate L_result for l = lambda .. lambda + 9. + */ + register float *lp = dp_float - lambda; + + register float W; + register float a = lp[-8], b = lp[-7], c = lp[-6], + d = lp[-5], e = lp[-4], f = lp[-3], + g = lp[-2], h = lp[-1]; + register float E; + register float S0 = 0, S1 = 0, S2 = 0, S3 = 0, S4 = 0, + S5 = 0, S6 = 0, S7 = 0, S8 = 0; + +# undef STEP +# define STEP(K, a, b, c, d, e, f, g, h) \ + W = wt_float[K]; \ + E = W * a; S8 += E; \ + E = W * b; S7 += E; \ + E = W * c; S6 += E; \ + E = W * d; S5 += E; \ + E = W * e; S4 += E; \ + E = W * f; S3 += E; \ + E = W * g; S2 += E; \ + E = W * h; S1 += E; \ + a = lp[K]; \ + E = W * a; S0 += E + +# define STEP_A(K) STEP(K, a, b, c, d, e, f, g, h) +# define STEP_B(K) STEP(K, b, c, d, e, f, g, h, a) +# define STEP_C(K) STEP(K, c, d, e, f, g, h, a, b) +# define STEP_D(K) STEP(K, d, e, f, g, h, a, b, c) +# define STEP_E(K) STEP(K, e, f, g, h, a, b, c, d) +# define STEP_F(K) STEP(K, f, g, h, a, b, c, d, e) +# define STEP_G(K) STEP(K, g, h, a, b, c, d, e, f) +# define STEP_H(K) STEP(K, h, a, b, c, d, e, f, g) + + STEP_A( 0); STEP_B( 1); STEP_C( 2); STEP_D( 3); + STEP_E( 4); STEP_F( 5); STEP_G( 6); STEP_H( 7); + + STEP_A( 8); STEP_B( 9); STEP_C(10); STEP_D(11); + STEP_E(12); STEP_F(13); STEP_G(14); STEP_H(15); + + STEP_A(16); STEP_B(17); STEP_C(18); STEP_D(19); + STEP_E(20); STEP_F(21); STEP_G(22); STEP_H(23); + + STEP_A(24); STEP_B(25); STEP_C(26); STEP_D(27); + STEP_E(28); STEP_F(29); STEP_G(30); STEP_H(31); + + STEP_A(32); STEP_B(33); STEP_C(34); STEP_D(35); + STEP_E(36); STEP_F(37); STEP_G(38); STEP_H(39); + + if (S0 > L_max) { L_max = S0; Nc = lambda; } + if (S1 > L_max) { L_max = S1; Nc = lambda + 1; } + if (S2 > L_max) { L_max = S2; Nc = lambda + 2; } + if (S3 > L_max) { L_max = S3; Nc = lambda + 3; } + if (S4 > L_max) { L_max = S4; Nc = lambda + 4; } + if (S5 > L_max) { L_max = S5; Nc = lambda + 5; } + if (S6 > L_max) { L_max = S6; Nc = lambda + 6; } + if (S7 > L_max) { L_max = S7; Nc = lambda + 7; } + if (S8 > L_max) { L_max = S8; Nc = lambda + 8; } + } + *Nc_out = Nc; + + L_max <<= 1; + + /* Rescaling of L_max + */ + assert(scal <= 100 && scal >= -100); + L_max = L_max >> (6 - scal); /* sub(6, scal) */ + + assert( Nc <= 120 && Nc >= 40); + + /* Compute the power of the reconstructed short term residual + * signal dp[..] + */ + L_power = 0; + for (k = 0; k <= 39; k++) { + + register longword L_temp; + + L_temp = SASR_W( dp[k - Nc], 3 ); + L_power += L_temp * L_temp; + } + L_power <<= 1; /* from L_MULT */ + + /* Normalization of L_max and L_power + */ + + if (L_max <= 0) { + *bc_out = 0; + return; + } + if (L_max >= L_power) { + *bc_out = 3; + return; + } + + temp = gsm_norm( L_power ); + + R = SASR_L ( L_max << temp, 16 ); + S = SASR_L ( L_power << temp, 16 ); + + /* Coding of the LTP gain + */ + + /* Table 4.3a must be used to obtain the level DLB[i] for the + * quantization of the LTP gain b to get the coded version bc. + */ + for (bc = 0; bc <= 2; bc++) if (R <= gsm_mult(S, gsm_DLB[bc])) break; + *bc_out = bc; +} + +#ifdef FAST +#ifdef LTP_CUT + +static void Cut_Fast_Calculation_of_the_LTP_parameters ( + struct gsm_state * st, /* IN */ + register word * d, /* [0..39] IN */ + register word * dp, /* [-120..-1] IN */ + word * bc_out, /* OUT */ + word * Nc_out /* OUT */ +) +{ + register int k, lambda; + register float wt_float; + word Nc, bc; + word wt_max, best_k, ltp_cut; + + float dp_float_base[120], * dp_float = dp_float_base + 120; + + register float L_result, L_max, L_power; + + wt_max = 0; + + for (k = 0; k < 40; ++k) { + if ( d[k] > wt_max) wt_max = d[best_k = k]; + else if (-d[k] > wt_max) wt_max = -d[best_k = k]; + } + + assert(wt_max >= 0); + wt_float = (float)wt_max; + + for (k = -120; k < 0; ++k) dp_float[k] = (float)dp[k]; + + /* Search for the maximum cross-correlation and coding of the LTP lag + */ + L_max = 0; + Nc = 40; /* index for the maximum cross-correlation */ + + for (lambda = 40; lambda <= 120; lambda++) { + L_result = wt_float * dp_float[best_k - lambda]; + if (L_result > L_max) { + Nc = lambda; + L_max = L_result; + } + } + + *Nc_out = Nc; + if (L_max <= 0.) { + *bc_out = 0; + return; + } + + /* Compute the power of the reconstructed short term residual + * signal dp[..] + */ + dp_float -= Nc; + L_power = 0; + for (k = 0; k < 40; ++k) { + register float f = dp_float[k]; + L_power += f * f; + } + + if (L_max >= L_power) { + *bc_out = 3; + return; + } + + /* Coding of the LTP gain + * Table 4.3a must be used to obtain the level DLB[i] for the + * quantization of the LTP gain b to get the coded version bc. + */ + lambda = L_max / L_power * 32768.; + for (bc = 0; bc <= 2; ++bc) if (lambda <= gsm_DLB[bc]) break; + *bc_out = bc; +} + +#endif /* LTP_CUT */ + +static void Fast_Calculation_of_the_LTP_parameters ( + register word * din, /* [0..39] IN */ + register word * dp, /* [-120..-1] IN */ + word * bc_out, /* OUT */ + word * Nc_out /* OUT */ +) +{ + register int k, lambda; + word Nc, bc; + + float wt_float[40]; + float dp_float_base[120], * dp_float = dp_float_base + 120; + + register float L_max, L_power; + + for (k = 0; k < 40; ++k) wt_float[k] = (float) din [k] ; + for (k = -120; k < 0; ++k) dp_float[k] = (float) dp [k] ; + + /* Search for the maximum cross-correlation and coding of the LTP lag + */ + L_max = 0; + Nc = 40; /* index for the maximum cross-correlation */ + + for (lambda = 40; lambda <= 120; lambda += 9) { + + /* Calculate L_result for l = lambda .. lambda + 9. + */ + register float *lp = dp_float - lambda; + + register float W; + register float a = lp[-8], b = lp[-7], c = lp[-6], + d = lp[-5], e = lp[-4], f = lp[-3], + g = lp[-2], h = lp[-1]; + register float E; + register float S0 = 0, S1 = 0, S2 = 0, S3 = 0, S4 = 0, + S5 = 0, S6 = 0, S7 = 0, S8 = 0; + +# undef STEP +# define STEP(K, a, b, c, d, e, f, g, h) \ + W = wt_float[K]; \ + E = W * a; S8 += E; \ + E = W * b; S7 += E; \ + E = W * c; S6 += E; \ + E = W * d; S5 += E; \ + E = W * e; S4 += E; \ + E = W * f; S3 += E; \ + E = W * g; S2 += E; \ + E = W * h; S1 += E; \ + a = lp[K]; \ + E = W * a; S0 += E + +# define STEP_A(K) STEP(K, a, b, c, d, e, f, g, h) +# define STEP_B(K) STEP(K, b, c, d, e, f, g, h, a) +# define STEP_C(K) STEP(K, c, d, e, f, g, h, a, b) +# define STEP_D(K) STEP(K, d, e, f, g, h, a, b, c) +# define STEP_E(K) STEP(K, e, f, g, h, a, b, c, d) +# define STEP_F(K) STEP(K, f, g, h, a, b, c, d, e) +# define STEP_G(K) STEP(K, g, h, a, b, c, d, e, f) +# define STEP_H(K) STEP(K, h, a, b, c, d, e, f, g) + + STEP_A( 0); STEP_B( 1); STEP_C( 2); STEP_D( 3); + STEP_E( 4); STEP_F( 5); STEP_G( 6); STEP_H( 7); + + STEP_A( 8); STEP_B( 9); STEP_C(10); STEP_D(11); + STEP_E(12); STEP_F(13); STEP_G(14); STEP_H(15); + + STEP_A(16); STEP_B(17); STEP_C(18); STEP_D(19); + STEP_E(20); STEP_F(21); STEP_G(22); STEP_H(23); + + STEP_A(24); STEP_B(25); STEP_C(26); STEP_D(27); + STEP_E(28); STEP_F(29); STEP_G(30); STEP_H(31); + + STEP_A(32); STEP_B(33); STEP_C(34); STEP_D(35); + STEP_E(36); STEP_F(37); STEP_G(38); STEP_H(39); + + if (S0 > L_max) { L_max = S0; Nc = lambda; } + if (S1 > L_max) { L_max = S1; Nc = lambda + 1; } + if (S2 > L_max) { L_max = S2; Nc = lambda + 2; } + if (S3 > L_max) { L_max = S3; Nc = lambda + 3; } + if (S4 > L_max) { L_max = S4; Nc = lambda + 4; } + if (S5 > L_max) { L_max = S5; Nc = lambda + 5; } + if (S6 > L_max) { L_max = S6; Nc = lambda + 6; } + if (S7 > L_max) { L_max = S7; Nc = lambda + 7; } + if (S8 > L_max) { L_max = S8; Nc = lambda + 8; } + } + *Nc_out = Nc; + + if (L_max <= 0.) { + *bc_out = 0; + return; + } + + /* Compute the power of the reconstructed short term residual + * signal dp[..] + */ + dp_float -= Nc; + L_power = 0; + for (k = 0; k < 40; ++k) { + register float f = dp_float[k]; + L_power += f * f; + } + + if (L_max >= L_power) { + *bc_out = 3; + return; + } + + /* Coding of the LTP gain + * Table 4.3a must be used to obtain the level DLB[i] for the + * quantization of the LTP gain b to get the coded version bc. + */ + lambda = L_max / L_power * 32768.; + for (bc = 0; bc <= 2; ++bc) if (lambda <= gsm_DLB[bc]) break; + *bc_out = bc; +} + +#endif /* FAST */ +#endif /* USE_FLOAT_MUL */ + + +/* 4.2.12 */ + +static void Long_term_analysis_filtering ( + word bc, /* IN */ + word Nc, /* IN */ + register word * dp, /* previous d [-120..-1] IN */ + register word * d, /* d [0..39] IN */ + register word * dpp, /* estimate [0..39] OUT */ + register word * e /* long term res. signal [0..39] OUT */ +) +/* + * In this part, we have to decode the bc parameter to compute + * the samples of the estimate dpp[0..39]. The decoding of bc needs the + * use of table 4.3b. The long term residual signal e[0..39] + * is then calculated to be fed to the RPE encoding section. + */ +{ + register int k; + +# undef STEP +# define STEP(BP) \ + for (k = 0; k <= 39; k++) { \ + dpp[k] = GSM_MULT_R( BP, dp[k - Nc]); \ + e[k] = GSM_SUB( d[k], dpp[k] ); \ + } + + switch (bc) { + case 0: STEP( 3277 ); break; + case 1: STEP( 11469 ); break; + case 2: STEP( 21299 ); break; + case 3: STEP( 32767 ); break; + } +} + +void Gsm_Long_Term_Predictor ( /* 4x for 160 samples */ + + struct gsm_state * S, + + word * d, /* [0..39] residual signal IN */ + word * dp, /* [-120..-1] d' IN */ + + word * e, /* [0..39] OUT */ + word * dpp, /* [0..39] OUT */ + word * Nc, /* correlation lag OUT */ + word * bc /* gain factor OUT */ +) +{ + assert( d ); assert( dp ); assert( e ); + assert( dpp); assert( Nc ); assert( bc ); + +#if defined(FAST) && defined(USE_FLOAT_MUL) + if (S->fast) +#if defined (LTP_CUT) + if (S->ltp_cut) + Cut_Fast_Calculation_of_the_LTP_parameters(S, + d, dp, bc, Nc); + else +#endif /* LTP_CUT */ + Fast_Calculation_of_the_LTP_parameters(d, dp, bc, Nc ); + else +#endif /* FAST & USE_FLOAT_MUL */ +#ifdef LTP_CUT + if (S->ltp_cut) + Cut_Calculation_of_the_LTP_parameters(S, d, dp, bc, Nc); + else +#endif + Calculation_of_the_LTP_parameters(d, dp, bc, Nc); + + Long_term_analysis_filtering( *bc, *Nc, dp, d, dpp, e ); +} + +/* 4.3.2 */ +void Gsm_Long_Term_Synthesis_Filtering ( + struct gsm_state * S, + + word Ncr, + word bcr, + register word * erp, /* [0..39] IN */ + register word * drp /* [-120..-1] IN, [-120..40] OUT */ +) +/* + * This procedure uses the bcr and Ncr parameter to realize the + * long term synthesis filtering. The decoding of bcr needs + * table 4.3b. + */ +{ + register int k; + word brp, drpp, Nr; + + /* Check the limits of Nr. + */ + Nr = Ncr < 40 || Ncr > 120 ? S->nrp : Ncr; + S->nrp = Nr; + assert(Nr >= 40 && Nr <= 120); + + /* Decoding of the LTP gain bcr + */ + brp = gsm_QLB[ bcr ]; + + /* Computation of the reconstructed short term residual + * signal drp[0..39] + */ + assert(brp != MIN_WORD); + + for (k = 0; k <= 39; k++) { + drpp = GSM_MULT_R( brp, drp[ k - Nr ] ); + drp[k] = GSM_ADD( erp[k], drpp ); + } + + /* + * Update of the reconstructed short term residual signal + * drp[ -1..-120 ] + */ + + for (k = 0; k <= 119; k++) drp[ -120 + k ] = drp[ -80 + k ]; +} +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: b369b90d-0284-42a0-87b0-99a25bbd93ac +*/ + diff --git a/libs/libsndfile/src/GSM610/lpc.c b/libs/libsndfile/src/GSM610/lpc.c new file mode 100644 index 0000000000..0a879f354a --- /dev/null +++ b/libs/libsndfile/src/GSM610/lpc.c @@ -0,0 +1,341 @@ +/* + * Copyright 1992 by Jutta Degener and Carsten Bormann, Technische + * Universitaet Berlin. See the accompanying file "COPYRIGHT" for + * details. THERE IS ABSOLUTELY NO WARRANTY FOR THIS SOFTWARE. + */ + +#include +#include + +#include "gsm610_priv.h" + +#include "gsm.h" + +/* + * 4.2.4 .. 4.2.7 LPC ANALYSIS SECTION + */ + +/* 4.2.4 */ + + +static void Autocorrelation ( + word * s, /* [0..159] IN/OUT */ + longword * L_ACF) /* [0..8] OUT */ +/* + * The goal is to compute the array L_ACF[k]. The signal s[i] must + * be scaled in order to avoid an overflow situation. + */ +{ + register int k, i; + + word temp, smax, scalauto; + +#ifdef USE_FLOAT_MUL + float float_s[160]; +#endif + + /* Dynamic scaling of the array s[0..159] + */ + + /* Search for the maximum. + */ + smax = 0; + for (k = 0; k <= 159; k++) { + temp = GSM_ABS( s[k] ); + if (temp > smax) smax = temp; + } + + /* Computation of the scaling factor. + */ + if (smax == 0) scalauto = 0; + else { + assert(smax > 0); + scalauto = 4 - gsm_norm( (longword)smax << 16 );/* sub(4,..) */ + } + + /* Scaling of the array s[0...159] + */ + + if (scalauto > 0) { + +# ifdef USE_FLOAT_MUL +# define SCALE(n) \ + case n: for (k = 0; k <= 159; k++) \ + float_s[k] = (float) \ + (s[k] = GSM_MULT_R(s[k], 16384 >> (n-1)));\ + break; +# else +# define SCALE(n) \ + case n: for (k = 0; k <= 159; k++) \ + s[k] = GSM_MULT_R( s[k], 16384 >> (n-1) );\ + break; +# endif /* USE_FLOAT_MUL */ + + switch (scalauto) { + SCALE(1) + SCALE(2) + SCALE(3) + SCALE(4) + } +# undef SCALE + } +# ifdef USE_FLOAT_MUL + else for (k = 0; k <= 159; k++) float_s[k] = (float) s[k]; +# endif + + /* Compute the L_ACF[..]. + */ + { +# ifdef USE_FLOAT_MUL + register float * sp = float_s; + register float sl = *sp; + +# define STEP(k) L_ACF[k] += (longword)(sl * sp[ -(k) ]); +# else + word * sp = s; + word sl = *sp; + +# define STEP(k) L_ACF[k] += ((longword)sl * sp[ -(k) ]); +# endif + +# define NEXTI sl = *++sp + + + for (k = 9; k--; L_ACF[k] = 0) ; + + STEP (0); + NEXTI; + STEP(0); STEP(1); + NEXTI; + STEP(0); STEP(1); STEP(2); + NEXTI; + STEP(0); STEP(1); STEP(2); STEP(3); + NEXTI; + STEP(0); STEP(1); STEP(2); STEP(3); STEP(4); + NEXTI; + STEP(0); STEP(1); STEP(2); STEP(3); STEP(4); STEP(5); + NEXTI; + STEP(0); STEP(1); STEP(2); STEP(3); STEP(4); STEP(5); STEP(6); + NEXTI; + STEP(0); STEP(1); STEP(2); STEP(3); STEP(4); STEP(5); STEP(6); STEP(7); + + for (i = 8; i <= 159; i++) { + + NEXTI; + + STEP(0); + STEP(1); STEP(2); STEP(3); STEP(4); + STEP(5); STEP(6); STEP(7); STEP(8); + } + + for (k = 9; k--; L_ACF[k] <<= 1) ; + + } + /* Rescaling of the array s[0..159] + */ + if (scalauto > 0) { + assert(scalauto <= 4); + for (k = 160; k--; *s++ <<= scalauto) ; + } +} + +#if defined(USE_FLOAT_MUL) && defined(FAST) + +static void Fast_Autocorrelation ( + word * s, /* [0..159] IN/OUT */ + longword * L_ACF) /* [0..8] OUT */ +{ + register int k, i; + float f_L_ACF[9]; + float scale; + + float s_f[160]; + register float *sf = s_f; + + for (i = 0; i < 160; ++i) sf[i] = s[i]; + for (k = 0; k <= 8; k++) { + register float L_temp2 = 0; + register float *sfl = sf - k; + for (i = k; i < 160; ++i) L_temp2 += sf[i] * sfl[i]; + f_L_ACF[k] = L_temp2; + } + scale = MAX_LONGWORD / f_L_ACF[0]; + + for (k = 0; k <= 8; k++) { + L_ACF[k] = f_L_ACF[k] * scale; + } +} +#endif /* defined (USE_FLOAT_MUL) && defined (FAST) */ + +/* 4.2.5 */ + +static void Reflection_coefficients ( + longword * L_ACF, /* 0...8 IN */ + register word * r /* 0...7 OUT */ +) +{ + register int i, m, n; + register word temp; + word ACF[9]; /* 0..8 */ + word P[ 9]; /* 0..8 */ + word K[ 9]; /* 2..8 */ + + /* Schur recursion with 16 bits arithmetic. + */ + + if (L_ACF[0] == 0) { + for (i = 8; i--; *r++ = 0) ; + return; + } + + assert( L_ACF[0] != 0 ); + temp = gsm_norm( L_ACF[0] ); + + assert(temp >= 0 && temp < 32); + + /* ? overflow ? */ + for (i = 0; i <= 8; i++) ACF[i] = SASR_L( L_ACF[i] << temp, 16 ); + + /* Initialize array P[..] and K[..] for the recursion. + */ + + for (i = 1; i <= 7; i++) K[ i ] = ACF[ i ]; + for (i = 0; i <= 8; i++) P[ i ] = ACF[ i ]; + + /* Compute reflection coefficients + */ + for (n = 1; n <= 8; n++, r++) { + + temp = P[1]; + temp = GSM_ABS(temp); + if (P[0] < temp) { + for (i = n; i <= 8; i++) *r++ = 0; + return; + } + + *r = gsm_div( temp, P[0] ); + + assert(*r >= 0); + if (P[1] > 0) *r = -*r; /* r[n] = sub(0, r[n]) */ + assert (*r != MIN_WORD); + if (n == 8) return; + + /* Schur recursion + */ + temp = GSM_MULT_R( P[1], *r ); + P[0] = GSM_ADD( P[0], temp ); + + for (m = 1; m <= 8 - n; m++) { + temp = GSM_MULT_R( K[ m ], *r ); + P[m] = GSM_ADD( P[ m+1 ], temp ); + + temp = GSM_MULT_R( P[ m+1 ], *r ); + K[m] = GSM_ADD( K[ m ], temp ); + } + } +} + +/* 4.2.6 */ + +static void Transformation_to_Log_Area_Ratios ( + register word * r /* 0..7 IN/OUT */ +) +/* + * The following scaling for r[..] and LAR[..] has been used: + * + * r[..] = integer( real_r[..]*32768. ); -1 <= real_r < 1. + * LAR[..] = integer( real_LAR[..] * 16384 ); + * with -1.625 <= real_LAR <= 1.625 + */ +{ + register word temp; + register int i; + + + /* Computation of the LAR[0..7] from the r[0..7] + */ + for (i = 1; i <= 8; i++, r++) { + + temp = *r; + temp = GSM_ABS(temp); + assert(temp >= 0); + + if (temp < 22118) { + temp >>= 1; + } else if (temp < 31130) { + assert( temp >= 11059 ); + temp -= 11059; + } else { + assert( temp >= 26112 ); + temp -= 26112; + temp <<= 2; + } + + *r = *r < 0 ? -temp : temp; + assert( *r != MIN_WORD ); + } +} + +/* 4.2.7 */ + +static void Quantization_and_coding ( + register word * LAR /* [0..7] IN/OUT */ +) +{ + register word temp; + + /* This procedure needs four tables; the following equations + * give the optimum scaling for the constants: + * + * A[0..7] = integer( real_A[0..7] * 1024 ) + * B[0..7] = integer( real_B[0..7] * 512 ) + * MAC[0..7] = maximum of the LARc[0..7] + * MIC[0..7] = minimum of the LARc[0..7] + */ + +# undef STEP +# define STEP( A, B, MAC, MIC ) \ + temp = GSM_MULT( A, *LAR ); \ + temp = GSM_ADD( temp, B ); \ + temp = GSM_ADD( temp, 256 ); \ + temp = SASR_W( temp, 9 ); \ + *LAR = temp>MAC ? MAC - MIC : (tempfast) Fast_Autocorrelation (s, L_ACF ); + else +#endif + Autocorrelation (s, L_ACF ); + Reflection_coefficients (L_ACF, LARc ); + Transformation_to_Log_Area_Ratios (LARc); + Quantization_and_coding (LARc); +} +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 63146664-a002-4e1e-8b7b-f0cc8a6a53da +*/ + diff --git a/libs/libsndfile/src/GSM610/preprocess.c b/libs/libsndfile/src/GSM610/preprocess.c new file mode 100644 index 0000000000..d1b473d693 --- /dev/null +++ b/libs/libsndfile/src/GSM610/preprocess.c @@ -0,0 +1,115 @@ +/* + * Copyright 1992 by Jutta Degener and Carsten Bormann, Technische + * Universitaet Berlin. See the accompanying file "COPYRIGHT" for + * details. THERE IS ABSOLUTELY NO WARRANTY FOR THIS SOFTWARE. + */ + +#include +#include + +#include "gsm610_priv.h" + +#include "gsm.h" + +/* 4.2.0 .. 4.2.3 PREPROCESSING SECTION + * + * After A-law to linear conversion (or directly from the + * Ato D converter) the following scaling is assumed for + * input to the RPE-LTP algorithm: + * + * in: 0.1.....................12 + * S.v.v.v.v.v.v.v.v.v.v.v.v.*.*.* + * + * Where S is the sign bit, v a valid bit, and * a "don't care" bit. + * The original signal is called sop[..] + * + * out: 0.1................... 12 + * S.S.v.v.v.v.v.v.v.v.v.v.v.v.0.0 + */ + + +void Gsm_Preprocess ( + struct gsm_state * S, + word * s, + word * so ) /* [0..159] IN/OUT */ +{ + + word z1 = S->z1; + longword L_z2 = S->L_z2; + word mp = S->mp; + + word s1; + longword L_s2; + + longword L_temp; + + word msp, lsp; + word SO; + + register int k = 160; + + while (k--) { + + /* 4.2.1 Downscaling of the input signal + */ + SO = SASR_W( *s, 3 ) << 2; + s++; + + assert (SO >= -0x4000); /* downscaled by */ + assert (SO <= 0x3FFC); /* previous routine. */ + + + /* 4.2.2 Offset compensation + * + * This part implements a high-pass filter and requires extended + * arithmetic precision for the recursive part of this filter. + * The input of this procedure is the array so[0...159] and the + * output the array sof[ 0...159 ]. + */ + /* Compute the non-recursive part + */ + + s1 = SO - z1; /* s1 = gsm_sub( *so, z1 ); */ + z1 = SO; + + assert(s1 != MIN_WORD); + + /* Compute the recursive part + */ + L_s2 = s1; + L_s2 <<= 15; + + /* Execution of a 31 bv 16 bits multiplication + */ + + msp = SASR_L( L_z2, 15 ); + lsp = L_z2-((longword)msp<<15); /* gsm_L_sub(L_z2,(msp<<15)); */ + + L_s2 += GSM_MULT_R( lsp, 32735 ); + L_temp = (longword)msp * 32735; /* GSM_L_MULT(msp,32735) >> 1;*/ + L_z2 = GSM_L_ADD( L_temp, L_s2 ); + + /* Compute sof[k] with rounding + */ + L_temp = GSM_L_ADD( L_z2, 16384 ); + + /* 4.2.3 Preemphasis + */ + + msp = GSM_MULT_R( mp, -28180 ); + mp = SASR_L( L_temp, 15 ); + *so++ = GSM_ADD( mp, msp ); + } + + S->z1 = z1; + S->L_z2 = L_z2; + S->mp = mp; +} +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: b760b0d9-3a05-4da3-9dc9-441ffb905d87 +*/ + diff --git a/libs/libsndfile/src/GSM610/rpe.c b/libs/libsndfile/src/GSM610/rpe.c new file mode 100644 index 0000000000..1d91f38be0 --- /dev/null +++ b/libs/libsndfile/src/GSM610/rpe.c @@ -0,0 +1,490 @@ +/* + * Copyright 1992 by Jutta Degener and Carsten Bormann, Technische + * Universitaet Berlin. See the accompanying file "COPYRIGHT" for + * details. THERE IS ABSOLUTELY NO WARRANTY FOR THIS SOFTWARE. + */ + +#include +#include + +#include "gsm610_priv.h" + +#include "gsm.h" + +/* 4.2.13 .. 4.2.17 RPE ENCODING SECTION + */ + +/* 4.2.13 */ + +static void Weighting_filter ( + register word * e, /* signal [-5..0.39.44] IN */ + word * x /* signal [0..39] OUT */ +) +/* + * The coefficients of the weighting filter are stored in a table + * (see table 4.4). The following scaling is used: + * + * H[0..10] = integer( real_H[ 0..10] * 8192 ); + */ +{ + /* word wt[ 50 ]; */ + + register longword L_result; + register int k /* , i */ ; + + /* Initialization of a temporary working array wt[0...49] + */ + + /* for (k = 0; k <= 4; k++) wt[k] = 0; + * for (k = 5; k <= 44; k++) wt[k] = *e++; + * for (k = 45; k <= 49; k++) wt[k] = 0; + * + * (e[-5..-1] and e[40..44] are allocated by the caller, + * are initially zero and are not written anywhere.) + */ + e -= 5; + + /* Compute the signal x[0..39] + */ + for (k = 0; k <= 39; k++) { + + L_result = 8192 >> 1; + + /* for (i = 0; i <= 10; i++) { + * L_temp = GSM_L_MULT( wt[k+i], gsm_H[i] ); + * L_result = GSM_L_ADD( L_result, L_temp ); + * } + */ + +#undef STEP +#define STEP( i, H ) (e[ k + i ] * (longword)H) + + /* Every one of these multiplications is done twice -- + * but I don't see an elegant way to optimize this. + * Do you? + */ + +#ifdef STUPID_COMPILER + L_result += STEP( 0, -134 ) ; + L_result += STEP( 1, -374 ) ; + /* + STEP( 2, 0 ) */ + L_result += STEP( 3, 2054 ) ; + L_result += STEP( 4, 5741 ) ; + L_result += STEP( 5, 8192 ) ; + L_result += STEP( 6, 5741 ) ; + L_result += STEP( 7, 2054 ) ; + /* + STEP( 8, 0 ) */ + L_result += STEP( 9, -374 ) ; + L_result += STEP( 10, -134 ) ; +#else + L_result += + STEP( 0, -134 ) + + STEP( 1, -374 ) + /* + STEP( 2, 0 ) */ + + STEP( 3, 2054 ) + + STEP( 4, 5741 ) + + STEP( 5, 8192 ) + + STEP( 6, 5741 ) + + STEP( 7, 2054 ) + /* + STEP( 8, 0 ) */ + + STEP( 9, -374 ) + + STEP(10, -134 ) + ; +#endif + + /* L_result = GSM_L_ADD( L_result, L_result ); (* scaling(x2) *) + * L_result = GSM_L_ADD( L_result, L_result ); (* scaling(x4) *) + * + * x[k] = SASR( L_result, 16 ); + */ + + /* 2 adds vs. >>16 => 14, minus one shift to compensate for + * those we lost when replacing L_MULT by '*'. + */ + + L_result = SASR_L( L_result, 13 ); + x[k] = ( L_result < MIN_WORD ? MIN_WORD + : (L_result > MAX_WORD ? MAX_WORD : L_result )); + } +} + +/* 4.2.14 */ + +static void RPE_grid_selection ( + word * x, /* [0..39] IN */ + word * xM, /* [0..12] OUT */ + word * Mc_out /* OUT */ +) +/* + * The signal x[0..39] is used to select the RPE grid which is + * represented by Mc. + */ +{ + /* register word temp1; */ + register int /* m, */ i; + register longword L_result, L_temp; + longword EM; /* xxx should be L_EM? */ + word Mc; + + longword L_common_0_3; + + EM = 0; + Mc = 0; + + /* for (m = 0; m <= 3; m++) { + * L_result = 0; + * + * + * for (i = 0; i <= 12; i++) { + * + * temp1 = SASR_W( x[m + 3*i], 2 ); + * + * assert(temp1 != MIN_WORD); + * + * L_temp = GSM_L_MULT( temp1, temp1 ); + * L_result = GSM_L_ADD( L_temp, L_result ); + * } + * + * if (L_result > EM) { + * Mc = m; + * EM = L_result; + * } + * } + */ + +#undef STEP +#define STEP( m, i ) L_temp = SASR_W( x[m + 3 * i], 2 ); \ + L_result += L_temp * L_temp; + + /* common part of 0 and 3 */ + + L_result = 0; + STEP( 0, 1 ); STEP( 0, 2 ); STEP( 0, 3 ); STEP( 0, 4 ); + STEP( 0, 5 ); STEP( 0, 6 ); STEP( 0, 7 ); STEP( 0, 8 ); + STEP( 0, 9 ); STEP( 0, 10); STEP( 0, 11); STEP( 0, 12); + L_common_0_3 = L_result; + + /* i = 0 */ + + STEP( 0, 0 ); + L_result <<= 1; /* implicit in L_MULT */ + EM = L_result; + + /* i = 1 */ + + L_result = 0; + STEP( 1, 0 ); + STEP( 1, 1 ); STEP( 1, 2 ); STEP( 1, 3 ); STEP( 1, 4 ); + STEP( 1, 5 ); STEP( 1, 6 ); STEP( 1, 7 ); STEP( 1, 8 ); + STEP( 1, 9 ); STEP( 1, 10); STEP( 1, 11); STEP( 1, 12); + L_result <<= 1; + if (L_result > EM) { + Mc = 1; + EM = L_result; + } + + /* i = 2 */ + + L_result = 0; + STEP( 2, 0 ); + STEP( 2, 1 ); STEP( 2, 2 ); STEP( 2, 3 ); STEP( 2, 4 ); + STEP( 2, 5 ); STEP( 2, 6 ); STEP( 2, 7 ); STEP( 2, 8 ); + STEP( 2, 9 ); STEP( 2, 10); STEP( 2, 11); STEP( 2, 12); + L_result <<= 1; + if (L_result > EM) { + Mc = 2; + EM = L_result; + } + + /* i = 3 */ + + L_result = L_common_0_3; + STEP( 3, 12 ); + L_result <<= 1; + if (L_result > EM) { + Mc = 3; + EM = L_result; + } + + /**/ + + /* Down-sampling by a factor 3 to get the selected xM[0..12] + * RPE sequence. + */ + for (i = 0; i <= 12; i ++) xM[i] = x[Mc + 3*i]; + *Mc_out = Mc; +} + +/* 4.12.15 */ + +static void APCM_quantization_xmaxc_to_exp_mant ( + word xmaxc, /* IN */ + word * expon_out, /* OUT */ + word * mant_out ) /* OUT */ +{ + word expon, mant; + + /* Compute expononent and mantissa of the decoded version of xmaxc + */ + + expon = 0; + if (xmaxc > 15) expon = SASR_W(xmaxc, 3) - 1; + mant = xmaxc - (expon << 3); + + if (mant == 0) { + expon = -4; + mant = 7; + } + else { + while (mant <= 7) { + mant = mant << 1 | 1; + expon--; + } + mant -= 8; + } + + assert( expon >= -4 && expon <= 6 ); + assert( mant >= 0 && mant <= 7 ); + + *expon_out = expon; + *mant_out = mant; +} + +static void APCM_quantization ( + word * xM, /* [0..12] IN */ + word * xMc, /* [0..12] OUT */ + word * mant_out, /* OUT */ + word * expon_out, /* OUT */ + word * xmaxc_out /* OUT */ +) +{ + int i, itest; + + word xmax, xmaxc, temp, temp1, temp2; + word expon, mant; + + + /* Find the maximum absolute value xmax of xM[0..12]. + */ + + xmax = 0; + for (i = 0; i <= 12; i++) { + temp = xM[i]; + temp = GSM_ABS(temp); + if (temp > xmax) xmax = temp; + } + + /* Qantizing and coding of xmax to get xmaxc. + */ + + expon = 0; + temp = SASR_W( xmax, 9 ); + itest = 0; + + for (i = 0; i <= 5; i++) { + + itest |= (temp <= 0); + temp = SASR_W( temp, 1 ); + + assert(expon <= 5); + if (itest == 0) expon++; /* expon = add (expon, 1) */ + } + + assert(expon <= 6 && expon >= 0); + temp = expon + 5; + + assert(temp <= 11 && temp >= 0); + xmaxc = gsm_add( SASR_W(xmax, temp), (word) (expon << 3) ); + + /* Quantizing and coding of the xM[0..12] RPE sequence + * to get the xMc[0..12] + */ + + APCM_quantization_xmaxc_to_exp_mant( xmaxc, &expon, &mant ); + + /* This computation uses the fact that the decoded version of xmaxc + * can be calculated by using the expononent and the mantissa part of + * xmaxc (logarithmic table). + * So, this method avoids any division and uses only a scaling + * of the RPE samples by a function of the expononent. A direct + * multiplication by the inverse of the mantissa (NRFAC[0..7] + * found in table 4.5) gives the 3 bit coded version xMc[0..12] + * of the RPE samples. + */ + + + /* Direct computation of xMc[0..12] using table 4.5 + */ + + assert( expon <= 4096 && expon >= -4096); + assert( mant >= 0 && mant <= 7 ); + + temp1 = 6 - expon; /* normalization by the expononent */ + temp2 = gsm_NRFAC[ mant ]; /* inverse mantissa */ + + for (i = 0; i <= 12; i++) { + + assert(temp1 >= 0 && temp1 < 16); + + temp = xM[i] << temp1; + temp = GSM_MULT( temp, temp2 ); + temp = SASR_W(temp, 12); + xMc[i] = temp + 4; /* see note below */ + } + + /* NOTE: This equation is used to make all the xMc[i] positive. + */ + + *mant_out = mant; + *expon_out = expon; + *xmaxc_out = xmaxc; +} + +/* 4.2.16 */ + +static void APCM_inverse_quantization ( + register word * xMc, /* [0..12] IN */ + word mant, + word expon, + register word * xMp) /* [0..12] OUT */ +/* + * This part is for decoding the RPE sequence of coded xMc[0..12] + * samples to obtain the xMp[0..12] array. Table 4.6 is used to get + * the mantissa of xmaxc (FAC[0..7]). + */ +{ + int i; + word temp, temp1, temp2, temp3; + + assert( mant >= 0 && mant <= 7 ); + + temp1 = gsm_FAC[ mant ]; /* see 4.2-15 for mant */ + temp2 = gsm_sub( 6, expon ); /* see 4.2-15 for exp */ + temp3 = gsm_asl( 1, gsm_sub( temp2, 1 )); + + for (i = 13; i--;) { + + assert( *xMc <= 7 && *xMc >= 0 ); /* 3 bit unsigned */ + + /* temp = gsm_sub( *xMc++ << 1, 7 ); */ + temp = (*xMc++ << 1) - 7; /* restore sign */ + assert( temp <= 7 && temp >= -7 ); /* 4 bit signed */ + + temp <<= 12; /* 16 bit signed */ + temp = GSM_MULT_R( temp1, temp ); + temp = GSM_ADD( temp, temp3 ); + *xMp++ = gsm_asr( temp, temp2 ); + } +} + +/* 4.2.17 */ + +static void RPE_grid_positioning ( + word Mc, /* grid position IN */ + register word * xMp, /* [0..12] IN */ + register word * ep /* [0..39] OUT */ +) +/* + * This procedure computes the reconstructed long term residual signal + * ep[0..39] for the LTP analysis filter. The inputs are the Mc + * which is the grid position selection and the xMp[0..12] decoded + * RPE samples which are upsampled by a factor of 3 by inserting zero + * values. + */ +{ + int i = 13; + + assert(0 <= Mc && Mc <= 3); + + switch (Mc) { + case 3: *ep++ = 0; + case 2: do { + *ep++ = 0; + case 1: *ep++ = 0; + case 0: *ep++ = *xMp++; + } while (--i); + } + while (++Mc < 4) *ep++ = 0; + + /* + + int i, k; + for (k = 0; k <= 39; k++) ep[k] = 0; + for (i = 0; i <= 12; i++) { + ep[ Mc + (3*i) ] = xMp[i]; + } + */ +} + +/* 4.2.18 */ + +/* This procedure adds the reconstructed long term residual signal + * ep[0..39] to the estimated signal dpp[0..39] from the long term + * analysis filter to compute the reconstructed short term residual + * signal dp[-40..-1]; also the reconstructed short term residual + * array dp[-120..-41] is updated. + */ + +#if 0 /* Has been inlined in code.c */ +void Gsm_Update_of_reconstructed_short_time_residual_signal ( + word * dpp, /* [0...39] IN */ + word * ep, /* [0...39] IN */ + word * dp) /* [-120...-1] IN/OUT */ +{ + int k; + + for (k = 0; k <= 79; k++) + dp[ -120 + k ] = dp[ -80 + k ]; + + for (k = 0; k <= 39; k++) + dp[ -40 + k ] = gsm_add( ep[k], dpp[k] ); +} +#endif /* Has been inlined in code.c */ + +void Gsm_RPE_Encoding ( + /*-struct gsm_state * S,-*/ + + word * e, /* -5..-1][0..39][40..44 IN/OUT */ + word * xmaxc, /* OUT */ + word * Mc, /* OUT */ + word * xMc) /* [0..12] OUT */ +{ + word x[40]; + word xM[13], xMp[13]; + word mant, expon; + + Weighting_filter(e, x); + RPE_grid_selection(x, xM, Mc); + + APCM_quantization( xM, xMc, &mant, &expon, xmaxc); + APCM_inverse_quantization( xMc, mant, expon, xMp); + + RPE_grid_positioning( *Mc, xMp, e ); + +} + +void Gsm_RPE_Decoding ( + /*-struct gsm_state * S,-*/ + + word xmaxcr, + word Mcr, + word * xMcr, /* [0..12], 3 bits IN */ + word * erp /* [0..39] OUT */ +) +{ + word expon, mant; + word xMp[ 13 ]; + + APCM_quantization_xmaxc_to_exp_mant( xmaxcr, &expon, &mant ); + APCM_inverse_quantization( xMcr, mant, expon, xMp ); + RPE_grid_positioning( Mcr, xMp, erp ); + +} +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 82005b9e-1560-4e94-9ddb-00cb14867295 +*/ + diff --git a/libs/libsndfile/src/GSM610/short_term.c b/libs/libsndfile/src/GSM610/short_term.c new file mode 100644 index 0000000000..0174b05232 --- /dev/null +++ b/libs/libsndfile/src/GSM610/short_term.c @@ -0,0 +1,427 @@ +/* + * Copyright 1992 by Jutta Degener and Carsten Bormann, Technische + * Universitaet Berlin. See the accompanying file "COPYRIGHT" for + * details. THERE IS ABSOLUTELY NO WARRANTY FOR THIS SOFTWARE. + */ + +#include +#include + +#include "gsm610_priv.h" + +#include "gsm.h" + +/* + * SHORT TERM ANALYSIS FILTERING SECTION + */ + +/* 4.2.8 */ + +static void Decoding_of_the_coded_Log_Area_Ratios ( + word * LARc, /* coded log area ratio [0..7] IN */ + word * LARpp) /* out: decoded .. */ +{ + register word temp1 /* , temp2 */; + + /* This procedure requires for efficient implementation + * two tables. + * + * INVA[1..8] = integer( (32768 * 8) / real_A[1..8]) + * MIC[1..8] = minimum value of the LARc[1..8] + */ + + /* Compute the LARpp[1..8] + */ + + /* for (i = 1; i <= 8; i++, B++, MIC++, INVA++, LARc++, LARpp++) { + * + * temp1 = GSM_ADD( *LARc, *MIC ) << 10; + * temp2 = *B << 1; + * temp1 = GSM_SUB( temp1, temp2 ); + * + * assert(*INVA != MIN_WORD); + * + * temp1 = GSM_MULT_R( *INVA, temp1 ); + * *LARpp = GSM_ADD( temp1, temp1 ); + * } + */ + +#undef STEP +#define STEP( B, MIC, INVA ) \ + temp1 = GSM_ADD( *LARc++, MIC ) << 10; \ + temp1 = GSM_SUB( temp1, B << 1 ); \ + temp1 = GSM_MULT_R( INVA, temp1 ); \ + *LARpp++ = GSM_ADD( temp1, temp1 ); + + STEP( 0, -32, 13107 ); + STEP( 0, -32, 13107 ); + STEP( 2048, -16, 13107 ); + STEP( -2560, -16, 13107 ); + + STEP( 94, -8, 19223 ); + STEP( -1792, -8, 17476 ); + STEP( -341, -4, 31454 ); + STEP( -1144, -4, 29708 ); + + /* NOTE: the addition of *MIC is used to restore + * the sign of *LARc. + */ +} + +/* 4.2.9 */ +/* Computation of the quantized reflection coefficients + */ + +/* 4.2.9.1 Interpolation of the LARpp[1..8] to get the LARp[1..8] + */ + +/* + * Within each frame of 160 analyzed speech samples the short term + * analysis and synthesis filters operate with four different sets of + * coefficients, derived from the previous set of decoded LARs(LARpp(j-1)) + * and the actual set of decoded LARs (LARpp(j)) + * + * (Initial value: LARpp(j-1)[1..8] = 0.) + */ + +static void Coefficients_0_12 ( + register word * LARpp_j_1, + register word * LARpp_j, + register word * LARp) +{ + register int i; + + for (i = 1; i <= 8; i++, LARp++, LARpp_j_1++, LARpp_j++) { + *LARp = GSM_ADD( SASR_W( *LARpp_j_1, 2 ), SASR_W( *LARpp_j, 2 )); + *LARp = GSM_ADD( *LARp, SASR_W( *LARpp_j_1, 1)); + } +} + +static void Coefficients_13_26 ( + register word * LARpp_j_1, + register word * LARpp_j, + register word * LARp) +{ + register int i; + for (i = 1; i <= 8; i++, LARpp_j_1++, LARpp_j++, LARp++) { + *LARp = GSM_ADD( SASR_W( *LARpp_j_1, 1), SASR_W( *LARpp_j, 1 )); + } +} + +static void Coefficients_27_39 ( + register word * LARpp_j_1, + register word * LARpp_j, + register word * LARp) +{ + register int i; + + for (i = 1; i <= 8; i++, LARpp_j_1++, LARpp_j++, LARp++) { + *LARp = GSM_ADD( SASR_W( *LARpp_j_1, 2 ), SASR_W( *LARpp_j, 2 )); + *LARp = GSM_ADD( *LARp, SASR_W( *LARpp_j, 1 )); + } +} + + +static void Coefficients_40_159 ( + register word * LARpp_j, + register word * LARp) +{ + register int i; + + for (i = 1; i <= 8; i++, LARp++, LARpp_j++) + *LARp = *LARpp_j; +} + +/* 4.2.9.2 */ + +static void LARp_to_rp ( + register word * LARp) /* [0..7] IN/OUT */ +/* + * The input of this procedure is the interpolated LARp[0..7] array. + * The reflection coefficients, rp[i], are used in the analysis + * filter and in the synthesis filter. + */ +{ + register int i; + register word temp; + + for (i = 1; i <= 8; i++, LARp++) { + + /* temp = GSM_ABS( *LARp ); + * + * if (temp < 11059) temp <<= 1; + * else if (temp < 20070) temp += 11059; + * else temp = GSM_ADD( temp >> 2, 26112 ); + * + * *LARp = *LARp < 0 ? -temp : temp; + */ + + if (*LARp < 0) { + temp = *LARp == MIN_WORD ? MAX_WORD : -(*LARp); + *LARp = - ((temp < 11059) ? temp << 1 + : ((temp < 20070) ? temp + 11059 + : GSM_ADD( (word) (temp >> 2), (word) 26112 ))); + } else { + temp = *LARp; + *LARp = (temp < 11059) ? temp << 1 + : ((temp < 20070) ? temp + 11059 + : GSM_ADD( (word) (temp >> 2), (word) 26112 )); + } + } +} + + +/* 4.2.10 */ +static void Short_term_analysis_filtering ( + struct gsm_state * S, + register word * rp, /* [0..7] IN */ + register int k_n, /* k_end - k_start */ + register word * s /* [0..n-1] IN/OUT */ +) +/* + * This procedure computes the short term residual signal d[..] to be fed + * to the RPE-LTP loop from the s[..] signal and from the local rp[..] + * array (quantized reflection coefficients). As the call of this + * procedure can be done in many ways (see the interpolation of the LAR + * coefficient), it is assumed that the computation begins with index + * k_start (for arrays d[..] and s[..]) and stops with index k_end + * (k_start and k_end are defined in 4.2.9.1). This procedure also + * needs to keep the array u[0..7] in memory for each call. + */ +{ + register word * u = S->u; + register int i; + register word di, zzz, ui, sav, rpi; + + for (; k_n--; s++) { + + di = sav = *s; + + for (i = 0; i < 8; i++) { /* YYY */ + + ui = u[i]; + rpi = rp[i]; + u[i] = sav; + + zzz = GSM_MULT_R(rpi, di); + sav = GSM_ADD( ui, zzz); + + zzz = GSM_MULT_R(rpi, ui); + di = GSM_ADD( di, zzz ); + } + + *s = di; + } +} + +#if defined(USE_FLOAT_MUL) && defined(FAST) + +static void Fast_Short_term_analysis_filtering ( + struct gsm_state * S, + register word * rp, /* [0..7] IN */ + register int k_n, /* k_end - k_start */ + register word * s /* [0..n-1] IN/OUT */ +) +{ + register word * u = S->u; + register int i; + + float uf[8], + rpf[8]; + + register float scalef = 3.0517578125e-5; + register float sav, di, temp; + + for (i = 0; i < 8; ++i) { + uf[i] = u[i]; + rpf[i] = rp[i] * scalef; + } + for (; k_n--; s++) { + sav = di = *s; + for (i = 0; i < 8; ++i) { + register float rpfi = rpf[i]; + register float ufi = uf[i]; + + uf[i] = sav; + temp = rpfi * di + ufi; + di += rpfi * ufi; + sav = temp; + } + *s = di; + } + for (i = 0; i < 8; ++i) u[i] = uf[i]; +} +#endif /* ! (defined (USE_FLOAT_MUL) && defined (FAST)) */ + +static void Short_term_synthesis_filtering ( + struct gsm_state * S, + register word * rrp, /* [0..7] IN */ + register int k, /* k_end - k_start */ + register word * wt, /* [0..k-1] IN */ + register word * sr /* [0..k-1] OUT */ +) +{ + register word * v = S->v; + register int i; + register word sri, tmp1, tmp2; + + while (k--) { + sri = *wt++; + for (i = 8; i--;) { + + /* sri = GSM_SUB( sri, gsm_mult_r( rrp[i], v[i] ) ); + */ + tmp1 = rrp[i]; + tmp2 = v[i]; + tmp2 = ( tmp1 == MIN_WORD && tmp2 == MIN_WORD + ? MAX_WORD + : 0x0FFFF & (( (longword)tmp1 * (longword)tmp2 + + 16384) >> 15)) ; + + sri = GSM_SUB( sri, tmp2 ); + + /* v[i+1] = GSM_ADD( v[i], gsm_mult_r( rrp[i], sri ) ); + */ + tmp1 = ( tmp1 == MIN_WORD && sri == MIN_WORD + ? MAX_WORD + : 0x0FFFF & (( (longword)tmp1 * (longword)sri + + 16384) >> 15)) ; + + v[i+1] = GSM_ADD( v[i], tmp1); + } + *sr++ = v[0] = sri; + } +} + + +#if defined(FAST) && defined(USE_FLOAT_MUL) + +static void Fast_Short_term_synthesis_filtering ( + struct gsm_state * S, + register word * rrp, /* [0..7] IN */ + register int k, /* k_end - k_start */ + register word * wt, /* [0..k-1] IN */ + register word * sr /* [0..k-1] OUT */ +) +{ + register word * v = S->v; + register int i; + + float va[9], rrpa[8]; + register float scalef = 3.0517578125e-5, temp; + + for (i = 0; i < 8; ++i) { + va[i] = v[i]; + rrpa[i] = (float)rrp[i] * scalef; + } + while (k--) { + register float sri = *wt++; + for (i = 8; i--;) { + sri -= rrpa[i] * va[i]; + if (sri < -32768.) sri = -32768.; + else if (sri > 32767.) sri = 32767.; + + temp = va[i] + rrpa[i] * sri; + if (temp < -32768.) temp = -32768.; + else if (temp > 32767.) temp = 32767.; + va[i+1] = temp; + } + *sr++ = va[0] = sri; + } + for (i = 0; i < 9; ++i) v[i] = va[i]; +} + +#endif /* defined(FAST) && defined(USE_FLOAT_MUL) */ + +void Gsm_Short_Term_Analysis_Filter ( + + struct gsm_state * S, + + word * LARc, /* coded log area ratio [0..7] IN */ + word * s /* signal [0..159] IN/OUT */ +) +{ + word * LARpp_j = S->LARpp[ S->j ]; + word * LARpp_j_1 = S->LARpp[ S->j ^= 1 ]; + + word LARp[8]; + +#undef FILTER +#if defined(FAST) && defined(USE_FLOAT_MUL) +# define FILTER (* (S->fast \ + ? Fast_Short_term_analysis_filtering \ + : Short_term_analysis_filtering )) + +#else +# define FILTER Short_term_analysis_filtering +#endif + + Decoding_of_the_coded_Log_Area_Ratios( LARc, LARpp_j ); + + Coefficients_0_12( LARpp_j_1, LARpp_j, LARp ); + LARp_to_rp( LARp ); + FILTER( S, LARp, 13, s); + + Coefficients_13_26( LARpp_j_1, LARpp_j, LARp); + LARp_to_rp( LARp ); + FILTER( S, LARp, 14, s + 13); + + Coefficients_27_39( LARpp_j_1, LARpp_j, LARp); + LARp_to_rp( LARp ); + FILTER( S, LARp, 13, s + 27); + + Coefficients_40_159( LARpp_j, LARp); + LARp_to_rp( LARp ); + FILTER( S, LARp, 120, s + 40); +} + +void Gsm_Short_Term_Synthesis_Filter ( + struct gsm_state * S, + + word * LARcr, /* received log area ratios [0..7] IN */ + word * wt, /* received d [0..159] IN */ + + word * s /* signal s [0..159] OUT */ +) +{ + word * LARpp_j = S->LARpp[ S->j ]; + word * LARpp_j_1 = S->LARpp[ S->j ^=1 ]; + + word LARp[8]; + +#undef FILTER +#if defined(FAST) && defined(USE_FLOAT_MUL) + +# define FILTER (* (S->fast \ + ? Fast_Short_term_synthesis_filtering \ + : Short_term_synthesis_filtering )) +#else +# define FILTER Short_term_synthesis_filtering +#endif + + Decoding_of_the_coded_Log_Area_Ratios( LARcr, LARpp_j ); + + Coefficients_0_12( LARpp_j_1, LARpp_j, LARp ); + LARp_to_rp( LARp ); + FILTER( S, LARp, 13, wt, s ); + + Coefficients_13_26( LARpp_j_1, LARpp_j, LARp); + LARp_to_rp( LARp ); + FILTER( S, LARp, 14, wt + 13, s + 13 ); + + Coefficients_27_39( LARpp_j_1, LARpp_j, LARp); + LARp_to_rp( LARp ); + FILTER( S, LARp, 13, wt + 27, s + 27 ); + + Coefficients_40_159( LARpp_j, LARp ); + LARp_to_rp( LARp ); + FILTER(S, LARp, 120, wt + 40, s + 40); +} +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 019ac7ba-c6dd-4540-abf0-8644b6c4a633 +*/ + diff --git a/libs/libsndfile/src/GSM610/table.c b/libs/libsndfile/src/GSM610/table.c new file mode 100644 index 0000000000..b5aa881eac --- /dev/null +++ b/libs/libsndfile/src/GSM610/table.c @@ -0,0 +1,69 @@ +/* + * Copyright 1992 by Jutta Degener and Carsten Bormann, Technische + * Universitaet Berlin. See the accompanying file "COPYRIGHT" for + * details. THERE IS ABSOLUTELY NO WARRANTY FOR THIS SOFTWARE. + */ + +/* Most of these tables are inlined at their point of use. + */ + +/* 4.4 TABLES USED IN THE FIXED POINT IMPLEMENTATION OF THE RPE-LTP + * CODER AND DECODER + * + * (Most of them inlined, so watch out.) + */ + +#define GSM_TABLE_C +#include "gsm610_priv.h" +#include "gsm.h" + +/* Table 4.1 Quantization of the Log.-Area Ratios + */ +/* i 1 2 3 4 5 6 7 8 */ +word gsm_A[8] = {20480, 20480, 20480, 20480, 13964, 15360, 8534, 9036}; +word gsm_B[8] = { 0, 0, 2048, -2560, 94, -1792, -341, -1144}; +word gsm_MIC[8] = { -32, -32, -16, -16, -8, -8, -4, -4 }; +word gsm_MAC[8] = { 31, 31, 15, 15, 7, 7, 3, 3 }; + + +/* Table 4.2 Tabulation of 1/A[1..8] + */ +word gsm_INVA[8]={ 13107, 13107, 13107, 13107, 19223, 17476, 31454, 29708 }; + + +/* Table 4.3a Decision level of the LTP gain quantizer + */ +/* bc 0 1 2 3 */ +word gsm_DLB[4] = { 6554, 16384, 26214, 32767 }; + + +/* Table 4.3b Quantization levels of the LTP gain quantizer + */ +/* bc 0 1 2 3 */ +word gsm_QLB[4] = { 3277, 11469, 21299, 32767 }; + + +/* Table 4.4 Coefficients of the weighting filter + */ +/* i 0 1 2 3 4 5 6 7 8 9 10 */ +word gsm_H[11] = {-134, -374, 0, 2054, 5741, 8192, 5741, 2054, 0, -374, -134 }; + + +/* Table 4.5 Normalized inverse mantissa used to compute xM/xmax + */ +/* i 0 1 2 3 4 5 6 7 */ +word gsm_NRFAC[8] = { 29128, 26215, 23832, 21846, 20165, 18725, 17476, 16384 }; + + +/* Table 4.6 Normalized direct mantissa used to compute xM/xmax + */ +/* i 0 1 2 3 4 5 6 7 */ +word gsm_FAC[8] = { 18431, 20479, 22527, 24575, 26623, 28671, 30719, 32767 }; +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 8957c531-e6b0-4097-9202-da7ca42729ca +*/ + diff --git a/libs/libsndfile/src/Symbols.darwin b/libs/libsndfile/src/Symbols.darwin new file mode 100644 index 0000000000..271e0b0c87 --- /dev/null +++ b/libs/libsndfile/src/Symbols.darwin @@ -0,0 +1,36 @@ +# Auto-generated by create_symbols_file.py + +_sf_command +_sf_open +_sf_close +_sf_seek +_sf_error +_sf_perror +_sf_error_str +_sf_error_number +_sf_format_check +_sf_read_raw +_sf_readf_short +_sf_readf_int +_sf_readf_float +_sf_readf_double +_sf_read_short +_sf_read_int +_sf_read_float +_sf_read_double +_sf_write_raw +_sf_writef_short +_sf_writef_int +_sf_writef_float +_sf_writef_double +_sf_write_short +_sf_write_int +_sf_write_float +_sf_write_double +_sf_strerror +_sf_get_string +_sf_set_string +_sf_open_fd +_sf_open_virtual +_sf_write_sync + diff --git a/libs/libsndfile/src/Symbols.linux b/libs/libsndfile/src/Symbols.linux new file mode 100644 index 0000000000..163346f700 --- /dev/null +++ b/libs/libsndfile/src/Symbols.linux @@ -0,0 +1,42 @@ +# Auto-generated by create_symbols_file.py + +libsndfile.so.1.0 +{ + global: + sf_command ; + sf_open ; + sf_close ; + sf_seek ; + sf_error ; + sf_perror ; + sf_error_str ; + sf_error_number ; + sf_format_check ; + sf_read_raw ; + sf_readf_short ; + sf_readf_int ; + sf_readf_float ; + sf_readf_double ; + sf_read_short ; + sf_read_int ; + sf_read_float ; + sf_read_double ; + sf_write_raw ; + sf_writef_short ; + sf_writef_int ; + sf_writef_float ; + sf_writef_double ; + sf_write_short ; + sf_write_int ; + sf_write_float ; + sf_write_double ; + sf_strerror ; + sf_get_string ; + sf_set_string ; + sf_open_fd ; + sf_open_virtual ; + sf_write_sync ; + local: + * ; +} ; + diff --git a/libs/libsndfile/src/aiff.c b/libs/libsndfile/src/aiff.c new file mode 100644 index 0000000000..129d79ca6d --- /dev/null +++ b/libs/libsndfile/src/aiff.c @@ -0,0 +1,1482 @@ +/* +** Copyright (C) 1999-2006 Erik de Castro Lopo +** Copyright (C) 2005 David Viens +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" + +/*------------------------------------------------------------------------------ + * Macros to handle big/little endian issues. + */ + +#define FORM_MARKER (MAKE_MARKER ('F', 'O', 'R', 'M')) +#define AIFF_MARKER (MAKE_MARKER ('A', 'I', 'F', 'F')) +#define AIFC_MARKER (MAKE_MARKER ('A', 'I', 'F', 'C')) +#define COMM_MARKER (MAKE_MARKER ('C', 'O', 'M', 'M')) +#define SSND_MARKER (MAKE_MARKER ('S', 'S', 'N', 'D')) +#define MARK_MARKER (MAKE_MARKER ('M', 'A', 'R', 'K')) +#define INST_MARKER (MAKE_MARKER ('I', 'N', 'S', 'T')) +#define APPL_MARKER (MAKE_MARKER ('A', 'P', 'P', 'L')) + +#define c_MARKER (MAKE_MARKER ('(', 'c', ')', ' ')) +#define NAME_MARKER (MAKE_MARKER ('N', 'A', 'M', 'E')) +#define AUTH_MARKER (MAKE_MARKER ('A', 'U', 'T', 'H')) +#define ANNO_MARKER (MAKE_MARKER ('A', 'N', 'N', 'O')) +#define COMT_MARKER (MAKE_MARKER ('C', 'O', 'M', 'T')) +#define FVER_MARKER (MAKE_MARKER ('F', 'V', 'E', 'R')) +#define SFX_MARKER (MAKE_MARKER ('S', 'F', 'X', '!')) + +#define PEAK_MARKER (MAKE_MARKER ('P', 'E', 'A', 'K')) +#define basc_MARKER (MAKE_MARKER ('b', 'a', 's', 'c')) + +/* Supported AIFC encodings.*/ +#define NONE_MARKER (MAKE_MARKER ('N', 'O', 'N', 'E')) +#define sowt_MARKER (MAKE_MARKER ('s', 'o', 'w', 't')) +#define twos_MARKER (MAKE_MARKER ('t', 'w', 'o', 's')) +#define raw_MARKER (MAKE_MARKER ('r', 'a', 'w', ' ')) +#define in32_MARKER (MAKE_MARKER ('i', 'n', '3', '2')) +#define ni32_MARKER (MAKE_MARKER ('2', '3', 'n', 'i')) + +#define fl32_MARKER (MAKE_MARKER ('f', 'l', '3', '2')) +#define FL32_MARKER (MAKE_MARKER ('F', 'L', '3', '2')) +#define fl64_MARKER (MAKE_MARKER ('f', 'l', '6', '4')) +#define FL64_MARKER (MAKE_MARKER ('F', 'L', '6', '4')) + +#define ulaw_MARKER (MAKE_MARKER ('u', 'l', 'a', 'w')) +#define ULAW_MARKER (MAKE_MARKER ('U', 'L', 'A', 'W')) +#define alaw_MARKER (MAKE_MARKER ('a', 'l', 'a', 'w')) +#define ALAW_MARKER (MAKE_MARKER ('A', 'L', 'A', 'W')) + +#define DWVW_MARKER (MAKE_MARKER ('D', 'W', 'V', 'W')) +#define GSM_MARKER (MAKE_MARKER ('G', 'S', 'M', ' ')) +#define ima4_MARKER (MAKE_MARKER ('i', 'm', 'a', '4')) + +/* Unsupported AIFC encodings.*/ + +#define MAC3_MARKER (MAKE_MARKER ('M', 'A', 'C', '3')) +#define MAC6_MARKER (MAKE_MARKER ('M', 'A', 'C', '6')) +#define ADP4_MARKER (MAKE_MARKER ('A', 'D', 'P', '4')) + +/* Predfined chunk sizes. */ +#define SIZEOF_AIFF_COMM 18 +#define SIZEOF_AIFC_COMM_MIN 22 +#define SIZEOF_AIFC_COMM 24 +#define SIZEOF_SSND_CHUNK 8 +#define SIZEOF_INST_CHUNK 20 + +/* Is it constant? */ + +/* AIFC/IMA4 defines. */ +#define AIFC_IMA4_BLOCK_LEN 34 +#define AIFC_IMA4_SAMPLES_PER_BLOCK 64 + +#define AIFF_PEAK_CHUNK_SIZE(ch) (2 * sizeof (int) + ch * (sizeof (float) + sizeof (int))) + +/*------------------------------------------------------------------------------ + * Typedefs for file chunks. + */ + +enum +{ HAVE_FORM = 0x01, + HAVE_AIFF = 0x02, + HAVE_COMM = 0x04, + HAVE_SSND = 0x08 +} ; + +typedef struct +{ unsigned int size ; + short numChannels ; + unsigned int numSampleFrames ; + short sampleSize ; + unsigned char sampleRate [10] ; + unsigned int encoding ; + char zero_bytes [2] ; +} COMM_CHUNK ; + +typedef struct +{ unsigned int offset ; + unsigned int blocksize ; +} SSND_CHUNK ; + +typedef struct +{ short playMode ; + unsigned short beginLoop ; + unsigned short endLoop ; +} INST_LOOP ; + +typedef struct +{ char baseNote ; /* all notes are MIDI note numbers */ + char detune ; /* cents off, only -50 to +50 are significant */ + char lowNote ; + char highNote ; + char lowVelocity ; /* 1 to 127 */ + char highVelocity ; /* 1 to 127 */ + short gain ; /* in dB, 0 is normal */ + INST_LOOP sustain_loop ; + INST_LOOP release_loop ; +} INST_CHUNK ; + + +enum +{ basc_SCALE_MINOR = 1, + basc_SCALE_MAJOR, + basc_SCALE_NEITHER, + basc_SCALE_BOTH +} ; + +enum +{ basc_TYPE_LOOP = 0, + basc_TYPE_ONE_SHOT +} ; + + +typedef struct +{ unsigned int version ; + unsigned int numBeats ; + unsigned short rootNote ; + unsigned short scaleType ; + unsigned short sigNumerator ; + unsigned short sigDenominator ; + unsigned short loopType ; +} basc_CHUNK ; + +typedef struct +{ unsigned short markerID ; + unsigned int position ; +} MARK_ID_POS ; + +/*------------------------------------------------------------------------------ + * Private static functions. + */ + +static int aiff_close (SF_PRIVATE *psf) ; + +static int tenbytefloat2int (unsigned char *bytes) ; +static void uint2tenbytefloat (unsigned int num, unsigned char *bytes) ; + +static int aiff_read_comm_chunk (SF_PRIVATE *psf, COMM_CHUNK *comm_fmt) ; + +static int aiff_read_header (SF_PRIVATE *psf, COMM_CHUNK *comm_fmt) ; + +static int aiff_write_header (SF_PRIVATE *psf, int calc_length) ; +static int aiff_write_tailer (SF_PRIVATE *psf) ; +static void aiff_write_strings (SF_PRIVATE *psf, int location) ; + +static int aiff_command (SF_PRIVATE *psf, int command, void *data, int datasize) ; + +static const char *get_loop_mode_str (short mode) ; + +static short get_loop_mode (short mode) ; + +static int aiff_read_basc_chunk (SF_PRIVATE * psf, int) ; + +static unsigned int marker_to_position (const MARK_ID_POS *m, unsigned short n, int marksize) ; + +/*------------------------------------------------------------------------------ +** Public function. +*/ + +int +aiff_open (SF_PRIVATE *psf) +{ COMM_CHUNK comm_fmt ; + int error, subformat ; + + memset (&comm_fmt, 0, sizeof (comm_fmt)) ; + + subformat = psf->sf.format & SF_FORMAT_SUBMASK ; + + if (psf->mode == SFM_READ || (psf->mode == SFM_RDWR && psf->filelength > 0)) + { if ((error = aiff_read_header (psf, &comm_fmt))) + return error ; + + psf_fseek (psf, psf->dataoffset, SEEK_SET) ; + } ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { if (psf->is_pipe) + return SFE_NO_PIPE_WRITE ; + + if ((psf->sf.format & SF_FORMAT_TYPEMASK) != SF_FORMAT_AIFF) + return SFE_BAD_OPEN_FORMAT ; + + if (psf->mode == SFM_WRITE && (subformat == SF_FORMAT_FLOAT || subformat == SF_FORMAT_DOUBLE)) + { if ((psf->peak_info = peak_info_calloc (psf->sf.channels)) == NULL) + return SFE_MALLOC_FAILED ; + psf->peak_info->peak_loc = SF_PEAK_START ; + } ; + + if (psf->mode != SFM_RDWR || psf->filelength < 40) + { psf->filelength = 0 ; + psf->datalength = 0 ; + psf->dataoffset = 0 ; + psf->sf.frames = 0 ; + } ; + + psf->str_flags = SF_STR_ALLOW_START | SF_STR_ALLOW_END ; + + if ((error = aiff_write_header (psf, SF_FALSE))) + return error ; + + psf->write_header = aiff_write_header ; + } ; + + psf->container_close = aiff_close ; + psf->command = aiff_command ; + + switch (psf->sf.format & SF_FORMAT_SUBMASK) + { case SF_FORMAT_PCM_U8 : + error = pcm_init (psf) ; + break ; + + case SF_FORMAT_PCM_S8 : + error = pcm_init (psf) ; + break ; + + case SF_FORMAT_PCM_16 : + case SF_FORMAT_PCM_24 : + case SF_FORMAT_PCM_32 : + error = pcm_init (psf) ; + break ; + + case SF_FORMAT_ULAW : + error = ulaw_init (psf) ; + break ; + + case SF_FORMAT_ALAW : + error = alaw_init (psf) ; + break ; + + /* Lite remove start */ + case SF_FORMAT_FLOAT : + error = float32_init (psf) ; + break ; + + case SF_FORMAT_DOUBLE : + error = double64_init (psf) ; + break ; + + case SF_FORMAT_DWVW_12 : + error = dwvw_init (psf, 12) ; + break ; + + case SF_FORMAT_DWVW_16 : + error = dwvw_init (psf, 16) ; + break ; + + case SF_FORMAT_DWVW_24 : + error = dwvw_init (psf, 24) ; + break ; + + case SF_FORMAT_DWVW_N : + if (psf->mode != SFM_READ) + { error = SFE_DWVW_BAD_BITWIDTH ; + break ; + } ; + if (comm_fmt.sampleSize >= 8 && comm_fmt.sampleSize < 24) + { error = dwvw_init (psf, comm_fmt.sampleSize) ; + psf->sf.frames = comm_fmt.numSampleFrames ; + break ; + } ; + psf_log_printf (psf, "AIFC/DWVW : Bad bitwidth %d\n", comm_fmt.sampleSize) ; + error = SFE_DWVW_BAD_BITWIDTH ; + break ; + + case SF_FORMAT_IMA_ADPCM : + /* + ** IMA ADPCM encoded AIFF files always have a block length + ** of 34 which decodes to 64 samples. + */ + error = aiff_ima_init (psf, AIFC_IMA4_BLOCK_LEN, AIFC_IMA4_SAMPLES_PER_BLOCK) ; + break ; + /* Lite remove end */ + + case SF_FORMAT_GSM610 : + error = gsm610_init (psf) ; + break ; + + default : return SFE_UNIMPLEMENTED ; + } ; + + + return error ; +} /* aiff_open */ + +/*========================================================================================== +** Private functions. +*/ + +/* This function ought to check size */ +static unsigned int +marker_to_position (const MARK_ID_POS *m, unsigned short n, int marksize) +{ int i ; + + for (i = 0 ; i < marksize ; i++) + if (m [i].markerID == n) + return m [i].position ; + return 0 ; +} /* marker_to_position */ + +static int +aiff_read_header (SF_PRIVATE *psf, COMM_CHUNK *comm_fmt) +{ SSND_CHUNK ssnd_fmt ; + MARK_ID_POS *markstr = NULL ; + unsigned marker, dword, FORMsize, SSNDsize, bytesread ; + int k, found_chunk = 0, done = 0, error = 0 ; + char *cptr, byte ; + int instr_found = 0, mark_found = 0, mark_count = 0 ; + + /* Set position to start of file to begin reading header. */ + psf_binheader_readf (psf, "p", 0) ; + + memset (comm_fmt, 0, sizeof (COMM_CHUNK)) ; + + /* Until recently AIF* file were all BIG endian. */ + psf->endian = SF_ENDIAN_BIG ; + + /* AIFF files can apparently have their chunks in any order. However, they + ** must have a FORM chunk. Approach here is to read all the chunks one by + ** one and then check for the mandatory chunks at the end. + */ + while (! done) + { psf_binheader_readf (psf, "m", &marker) ; + + if (psf->mode == SFM_RDWR && (found_chunk & HAVE_SSND)) + return SFE_AIFF_RW_SSND_NOT_LAST ; + + switch (marker) + { case FORM_MARKER : + if (found_chunk) + return SFE_AIFF_NO_FORM ; + + psf_binheader_readf (psf, "E4", &FORMsize) ; + + if (psf->fileoffset > 0 && psf->filelength > FORMsize + 8) + { /* Set file length. */ + psf->filelength = FORMsize + 8 ; + psf_log_printf (psf, "FORM : %u\n", FORMsize) ; + } + else if (FORMsize != psf->filelength - 2 * SIGNED_SIZEOF (dword)) + { dword = psf->filelength - 2 * sizeof (dword) ; + psf_log_printf (psf, "FORM : %u (should be %u)\n", FORMsize, dword) ; + FORMsize = dword ; + } + else + psf_log_printf (psf, "FORM : %u\n", FORMsize) ; + found_chunk |= HAVE_FORM ; + break ; + + case AIFC_MARKER : + case AIFF_MARKER : + if ((found_chunk & HAVE_FORM) == 0) + return SFE_AIFF_AIFF_NO_FORM ; + psf_log_printf (psf, " %M\n", marker) ; + found_chunk |= HAVE_AIFF ; + break ; + + case COMM_MARKER : + error = aiff_read_comm_chunk (psf, comm_fmt) ; + + psf->sf.samplerate = tenbytefloat2int (comm_fmt->sampleRate) ; + psf->sf.frames = comm_fmt->numSampleFrames ; + psf->sf.channels = comm_fmt->numChannels ; + psf->bytewidth = BITWIDTH2BYTES (comm_fmt->sampleSize) ; + + if (error) + return error ; + + found_chunk |= HAVE_COMM ; + break ; + + case PEAK_MARKER : + /* Must have COMM chunk before PEAK chunk. */ + if ((found_chunk & (HAVE_FORM | HAVE_AIFF | HAVE_COMM)) != (HAVE_FORM | HAVE_AIFF | HAVE_COMM)) + return SFE_AIFF_PEAK_B4_COMM ; + + psf_binheader_readf (psf, "E4", &dword) ; + + psf_log_printf (psf, "%M : %d\n", marker, dword) ; + if (dword != AIFF_PEAK_CHUNK_SIZE (psf->sf.channels)) + { psf_binheader_readf (psf, "j", dword) ; + psf_log_printf (psf, "*** File PEAK chunk too big.\n") ; + return SFE_WAV_BAD_PEAK ; + } ; + + if ((psf->peak_info = peak_info_calloc (psf->sf.channels)) == NULL) + return SFE_MALLOC_FAILED ; + + /* read in rest of PEAK chunk. */ + psf_binheader_readf (psf, "E44", &(psf->peak_info->version), &(psf->peak_info->timestamp)) ; + + if (psf->peak_info->version != 1) + psf_log_printf (psf, " version : %d *** (should be version 1)\n", psf->peak_info->version) ; + else + psf_log_printf (psf, " version : %d\n", psf->peak_info->version) ; + + psf_log_printf (psf, " time stamp : %d\n", psf->peak_info->timestamp) ; + psf_log_printf (psf, " Ch Position Value\n") ; + + cptr = psf->u.cbuf ; + for (dword = 0 ; dword < (unsigned) psf->sf.channels ; dword++) + { float value ; + unsigned int position ; + + psf_binheader_readf (psf, "Ef4", &value, &position) ; + psf->peak_info->peaks [dword].value = value ; + psf->peak_info->peaks [dword].position = position ; + + LSF_SNPRINTF (cptr, sizeof (psf->u.scbuf), " %2d %-12ld %g\n", + dword, (long) psf->peak_info->peaks [dword].position, psf->peak_info->peaks [dword].value) ; + cptr [sizeof (psf->u.scbuf) - 1] = 0 ; + psf_log_printf (psf, cptr) ; + } ; + + break ; + + case SSND_MARKER : + psf_binheader_readf (psf, "E444", &SSNDsize, &(ssnd_fmt.offset), &(ssnd_fmt.blocksize)) ; + + psf->datalength = SSNDsize - sizeof (ssnd_fmt) ; + psf->dataoffset = psf_ftell (psf) ; + + if (psf->datalength > psf->filelength - psf->dataoffset || psf->datalength < 0) + { psf_log_printf (psf, " SSND : %u (should be %D)\n", SSNDsize, psf->filelength - psf->dataoffset + sizeof (SSND_CHUNK)) ; + psf->datalength = psf->filelength - psf->dataoffset ; + } + else + psf_log_printf (psf, " SSND : %u\n", SSNDsize) ; + + /* Only set dataend if there really is data at the end. */ + if (psf->datalength + psf->dataoffset < psf->filelength) + psf->dataend = psf->datalength + psf->dataoffset ; + + psf_log_printf (psf, " Offset : %u\n", ssnd_fmt.offset) ; + psf_log_printf (psf, " Block Size : %u\n", ssnd_fmt.blocksize) ; + + found_chunk |= HAVE_SSND ; + + if (! psf->sf.seekable) + break ; + + /* Seek to end of SSND chunk. */ + psf_fseek (psf, psf->dataoffset + psf->datalength + (SSNDsize & 1), SEEK_SET) ; + break ; + + case c_MARKER : + psf_binheader_readf (psf, "E4", &dword) ; + if (dword == 0) + break ; + if (dword > SIGNED_SIZEOF (psf->u.scbuf) - 1) + { psf_log_printf (psf, " %M : %d (too big)\n", marker, dword) ; + return SFE_INTERNAL ; + } ; + + cptr = psf->u.cbuf ; + psf_binheader_readf (psf, "b", cptr, dword + (dword & 1)) ; + cptr [dword] = 0 ; + psf_log_printf (psf, " %M : %s\n", marker, cptr) ; + psf_store_string (psf, SF_STR_COPYRIGHT, cptr) ; + break ; + + case AUTH_MARKER : + psf_binheader_readf (psf, "E4", &dword) ; + if (dword == 0) + break ; + if (dword > SIGNED_SIZEOF (psf->u.scbuf) - 1) + { psf_log_printf (psf, " %M : %d (too big)\n", marker, dword) ; + return SFE_INTERNAL ; + } ; + + cptr = psf->u.cbuf ; + psf_binheader_readf (psf, "b", cptr, dword + (dword & 1)) ; + cptr [dword] = 0 ; + psf_log_printf (psf, " %M : %s\n", marker, cptr) ; + psf_store_string (psf, SF_STR_ARTIST, cptr) ; + break ; + + case COMT_MARKER : + { unsigned short count, id, len ; + unsigned int timestamp ; + + psf_binheader_readf (psf, "E42", &dword, &count) ; + psf_log_printf (psf, " %M : %d\n count : %d\n", marker, dword, count) ; + dword += (dword & 1) ; + if (dword == 0) + break ; + dword -= 2 ; + + for (k = 0 ; k < count ; k++) + { dword -= psf_binheader_readf (psf, "E422", ×tamp, &id, &len) ; + psf_log_printf (psf, " time : 0x%x\n marker : %x\n length : %d\n", timestamp, id, len) ; + + if (len + 1 > SIGNED_SIZEOF (psf->u.scbuf)) + { psf_log_printf (psf, "\nError : string length (%d) too big.\n", len) ; + return SFE_INTERNAL ; + } ; + + cptr = psf->u.cbuf ; + dword -= psf_binheader_readf (psf, "b", cptr, len) ; + cptr [len] = 0 ; + psf_log_printf (psf, " string : %s\n", cptr) ; + } ; + + if (dword > 0) + psf_binheader_readf (psf, "j", dword) ; + } ; + break ; + + case APPL_MARKER : + psf_binheader_readf (psf, "E4", &dword) ; + if (dword == 0) + break ; + if (dword >= SIGNED_SIZEOF (psf->u.scbuf) - 1) + { psf_log_printf (psf, " %M : %d (too big, skipping)\n", marker, dword) ; + psf_binheader_readf (psf, "j", dword + (dword & 1)) ; + break ; + } ; + + cptr = psf->u.cbuf ; + psf_binheader_readf (psf, "b", cptr, dword + (dword & 1)) ; + cptr [dword] = 0 ; + + for (k = 0 ; k < (int) dword ; k++) + if (! isprint (cptr [k])) + { cptr [k] = 0 ; + break ; + } ; + + psf_log_printf (psf, " %M : %s\n", marker, cptr) ; + psf_store_string (psf, SF_STR_SOFTWARE, cptr) ; + break ; + + case NAME_MARKER : + psf_binheader_readf (psf, "E4", &dword) ; + if (dword == 0) + break ; + if (dword > SIGNED_SIZEOF (psf->u.scbuf) - 2) + { psf_log_printf (psf, " %M : %d (too big)\n", marker, dword) ; + return SFE_INTERNAL ; + } ; + + cptr = psf->u.cbuf ; + psf_binheader_readf (psf, "b", cptr, dword + (dword & 1)) ; + cptr [dword] = 0 ; + psf_log_printf (psf, " %M : %s\n", marker, cptr) ; + psf_store_string (psf, SF_STR_TITLE, cptr) ; + break ; + + case ANNO_MARKER : + psf_binheader_readf (psf, "E4", &dword) ; + if (dword == 0) + break ; + if (dword > SIGNED_SIZEOF (psf->u.scbuf) - 2) + { psf_log_printf (psf, " %M : %d (too big)\n", marker, dword) ; + return SFE_INTERNAL ; + } ; + + cptr = psf->u.cbuf ; + psf_binheader_readf (psf, "b", cptr, dword + (dword & 1)) ; + cptr [dword] = 0 ; + psf_log_printf (psf, " %M : %s\n", marker, cptr) ; + psf_store_string (psf, SF_STR_COMMENT, cptr) ; + break ; + + case INST_MARKER : + psf_binheader_readf (psf, "E4", &dword) ; + if (dword != SIZEOF_INST_CHUNK) + { psf_log_printf (psf, " %M : %d (should be %d)\n", marker, dword, SIZEOF_INST_CHUNK) ; + psf_binheader_readf (psf, "j", dword) ; + break ; + } ; + psf_log_printf (psf, " %M : %d\n", marker, dword) ; + { unsigned char bytes [6] ; + short gain ; + + if (psf->instrument == NULL && (psf->instrument = psf_instrument_alloc ()) == NULL) + return SFE_MALLOC_FAILED ; + + psf_binheader_readf (psf, "b", bytes, 6) ; + psf_log_printf (psf, " Base Note : %u\n Detune : %u\n" + " Low Note : %u\n High Note : %u\n" + " Low Vel. : %u\n High Vel. : %u\n", + bytes [0], bytes [1], bytes [2], bytes [3], bytes [4], bytes [5]) ; + psf->instrument->basenote = bytes [0] ; + psf->instrument->detune = bytes [1] ; + psf->instrument->key_lo = bytes [2] ; + psf->instrument->key_hi = bytes [3] ; + psf->instrument->velocity_lo = bytes [4] ; + psf->instrument->velocity_hi = bytes [5] ; + psf_binheader_readf (psf, "E2", &gain) ; + psf->instrument->gain = gain ; + psf_log_printf (psf, " Gain (dB) : %d\n", gain) ; + } ; + { short mode ; /* 0 - no loop, 1 - forward looping, 2 - backward looping */ + const char *loop_mode ; + unsigned short begin, end ; + + psf_binheader_readf (psf, "E222", &mode, &begin, &end) ; + loop_mode = get_loop_mode_str (mode) ; + mode = get_loop_mode (mode) ; + if (mode == SF_LOOP_NONE) + { psf->instrument->loop_count = 0 ; + psf->instrument->loops [0].mode = SF_LOOP_NONE ; + } + else + { psf->instrument->loop_count = 1 ; + psf->instrument->loops [0].mode = SF_LOOP_FORWARD ; + psf->instrument->loops [0].start = begin ; + psf->instrument->loops [0].end = end ; + psf->instrument->loops [0].count = 0 ; + } ; + psf_log_printf (psf, " Sustain\n mode : %d => %s\n begin : %u\n end : %u\n", + mode, loop_mode, begin, end) ; + psf_binheader_readf (psf, "E222", &mode, &begin, &end) ; + loop_mode = get_loop_mode_str (mode) ; + mode = get_loop_mode (mode) ; + if (mode == SF_LOOP_NONE) + psf->instrument->loops [0].mode = SF_LOOP_NONE ; + else + { psf->instrument->loop_count += 1 ; + psf->instrument->loops [1].mode = SF_LOOP_FORWARD ; + psf->instrument->loops [1].start = begin ; + psf->instrument->loops [1].end = end ; + psf->instrument->loops [1].count = 0 ; + } ; + psf_log_printf (psf, " Release\n mode : %d => %s\n begin : %u\n end : %u\n", + mode, loop_mode, begin, end) ; + } ; + instr_found++ ; + break ; + + case basc_MARKER : + psf_binheader_readf (psf, "E4", &dword) ; + psf_log_printf (psf, " basc : %u\n", dword) ; + + if ((error = aiff_read_basc_chunk (psf, dword))) + return error ; + break ; + + case MARK_MARKER : + psf_binheader_readf (psf, "E4", &dword) ; + psf_log_printf (psf, " %M : %d\n", marker, dword) ; + { unsigned short mark_id, n = 0 ; + unsigned char pstr_len ; + unsigned int position ; + + bytesread = psf_binheader_readf (psf, "E2", &n) ; + mark_count = n ; + markstr = calloc (mark_count, sizeof (MARK_ID_POS)) ; + psf_log_printf (psf, " Count : %d\n", mark_count) ; + + for (n = 0 ; n < mark_count && bytesread < dword ; n++) + { bytesread += psf_binheader_readf (psf, "E241", &mark_id, &position, &pstr_len) ; + psf_log_printf (psf, " Mark ID : %u\n Position : %u\n", mark_id, position) ; + + pstr_len += (pstr_len & 1) + 1 ; /* fudgy, fudgy, hack, hack */ + + bytesread += psf_binheader_readf (psf, "b", psf->u.scbuf, pstr_len) ; + psf_log_printf (psf, " Name : %s\n", psf->u.scbuf) ; + + markstr [n].markerID = mark_id ; + markstr [n].position = position ; + /* + ** TODO if psf->u.scbuf is equal to + ** either Beg_loop, Beg loop or beg loop and spam + ** if (psf->instrument == NULL && (psf->instrument = psf_instrument_alloc ()) == NULL) + ** return SFE_MALLOC_FAILED ; + */ + } ; + } ; + mark_found++ ; + psf_binheader_readf (psf, "j", dword - bytesread) ; + break ; + + case FVER_MARKER : + case SFX_MARKER : + psf_binheader_readf (psf, "E4", &dword) ; + psf_log_printf (psf, " %M : %d\n", marker, dword) ; + + psf_binheader_readf (psf, "j", dword) ; + break ; + + case NONE_MARKER : + /* Fix for broken AIFC files with incorrect COMM chunk length. */ + psf_binheader_readf (psf, "1", &byte) ; + dword = byte ; + psf_binheader_readf (psf, "j", dword) ; + break ; + + default : + if (isprint ((marker >> 24) & 0xFF) && isprint ((marker >> 16) & 0xFF) + && isprint ((marker >> 8) & 0xFF) && isprint (marker & 0xFF)) + { psf_binheader_readf (psf, "E4", &dword) ; + psf_log_printf (psf, " %M : %d (unknown marker)\n", marker, dword) ; + + psf_binheader_readf (psf, "j", dword) ; + break ; + } ; + if ((dword = psf_ftell (psf)) & 0x03) + { psf_log_printf (psf, " Unknown chunk marker %X at position %d. Resyncing.\n", marker, dword - 4) ; + + psf_binheader_readf (psf, "j", -3) ; + break ; + } ; + psf_log_printf (psf, "*** Unknown chunk marker %X at position %D. Exiting parser.\n", marker, psf_ftell (psf)) ; + done = 1 ; + break ; + } ; /* switch (marker) */ + + if ((! psf->sf.seekable) && (found_chunk & HAVE_SSND)) + break ; + + if (psf_ftell (psf) >= psf->filelength - (2 * SIGNED_SIZEOF (dword))) + break ; + } ; /* while (1) */ + + if (instr_found && mark_found) + { int j ; + + for (j = 0 ; jinstrument->loop_count ; j ++) + { if (j < ARRAY_LEN (psf->instrument->loops)) + { psf->instrument->loops [j].start = marker_to_position (markstr, psf->instrument->loops [j].start, mark_count) ; + psf->instrument->loops [j].end = marker_to_position (markstr, psf->instrument->loops [j].end, mark_count) ; + psf->instrument->loops [j].mode = SF_LOOP_FORWARD ; + } ; + } ; + } ; + + if (markstr) + free (markstr) ; + + if (! (found_chunk & HAVE_FORM)) + return SFE_AIFF_NO_FORM ; + + if (! (found_chunk & HAVE_AIFF)) + return SFE_AIFF_COMM_NO_FORM ; + + if (! (found_chunk & HAVE_COMM)) + return SFE_AIFF_SSND_NO_COMM ; + + if (! psf->dataoffset) + return SFE_AIFF_NO_DATA ; + + return 0 ; +} /* aiff_read_header */ + +static int +aiff_close (SF_PRIVATE *psf) +{ + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { aiff_write_tailer (psf) ; + + aiff_write_header (psf, SF_TRUE) ; + } ; + + return 0 ; +} /* aiff_close */ + +static int +aiff_read_comm_chunk (SF_PRIVATE *psf, COMM_CHUNK *comm_fmt) +{ int error = 0, bytesread, subformat ; + + psf->u.scbuf [0] = 0 ; + + bytesread = psf_binheader_readf (psf, "E4", &(comm_fmt->size)) ; + + /* The COMM chunk has an int aligned to an odd word boundary. Some + ** procesors are not able to deal with this (ie bus fault) so we have + ** to take special care. + */ + comm_fmt->size += comm_fmt->size & 1 ; + + bytesread += + psf_binheader_readf (psf, "E242b", &(comm_fmt->numChannels), &(comm_fmt->numSampleFrames), + &(comm_fmt->sampleSize), &(comm_fmt->sampleRate), SIGNED_SIZEOF (comm_fmt->sampleRate)) ; + + if (comm_fmt->size == SIZEOF_AIFF_COMM) + comm_fmt->encoding = NONE_MARKER ; + else if (comm_fmt->size == SIZEOF_AIFC_COMM_MIN) + bytesread += psf_binheader_readf (psf, "Em", &(comm_fmt->encoding)) ; + else if (comm_fmt->size >= SIZEOF_AIFC_COMM) + { unsigned char encoding_len ; + + bytesread += psf_binheader_readf (psf, "Em1", &(comm_fmt->encoding), &encoding_len) ; + + memset (psf->u.scbuf, 0, comm_fmt->size) ; + + bytesread += psf_binheader_readf (psf, "b", psf->u.scbuf, + comm_fmt->size - SIZEOF_AIFC_COMM + 1) ; + psf->u.scbuf [encoding_len] = 0 ; + } ; + + psf_log_printf (psf, " COMM : %d\n", comm_fmt->size) ; + psf_log_printf (psf, " Sample Rate : %d\n", tenbytefloat2int (comm_fmt->sampleRate)) ; + psf_log_printf (psf, " Frames : %u%s\n", comm_fmt->numSampleFrames, (comm_fmt->numSampleFrames == 0 && psf->filelength > 100) ? " (Should not be 0)" : "") ; + psf_log_printf (psf, " Channels : %d\n", comm_fmt->numChannels) ; + + /* Found some broken 'fl32' files with comm.samplesize == 16. Fix it here. */ + + if ((comm_fmt->encoding == fl32_MARKER || comm_fmt->encoding == FL32_MARKER) && comm_fmt->sampleSize != 32) + { psf_log_printf (psf, " Sample Size : %d (should be 32)\n", comm_fmt->sampleSize) ; + comm_fmt->sampleSize = 32 ; + } + else if ((comm_fmt->encoding == fl64_MARKER || comm_fmt->encoding == FL64_MARKER) && comm_fmt->sampleSize != 64) + { psf_log_printf (psf, " Sample Size : %d (should be 64)\n", comm_fmt->sampleSize) ; + comm_fmt->sampleSize = 64 ; + } + else + psf_log_printf (psf, " Sample Size : %d\n", comm_fmt->sampleSize) ; + + subformat = s_bitwidth_to_subformat (comm_fmt->sampleSize) ; + + psf->endian = SF_ENDIAN_BIG ; + + switch (comm_fmt->encoding) + { case NONE_MARKER : + psf->sf.format = (SF_FORMAT_AIFF | subformat) ; + break ; + + case twos_MARKER : + case in32_MARKER : + psf->sf.format = (SF_ENDIAN_BIG | SF_FORMAT_AIFF | subformat) ; + break ; + + case sowt_MARKER : + case ni32_MARKER : + psf->endian = SF_ENDIAN_LITTLE ; + psf->sf.format = (SF_ENDIAN_LITTLE | SF_FORMAT_AIFF | subformat) ; + break ; + + case fl32_MARKER : + case FL32_MARKER : + psf->sf.format = (SF_FORMAT_AIFF | SF_FORMAT_FLOAT) ; + break ; + + case ulaw_MARKER : + case ULAW_MARKER : + psf->sf.format = (SF_FORMAT_AIFF | SF_FORMAT_ULAW) ; + break ; + + case alaw_MARKER : + case ALAW_MARKER : + psf->sf.format = (SF_FORMAT_AIFF | SF_FORMAT_ALAW) ; + break ; + + case fl64_MARKER : + case FL64_MARKER : + psf->sf.format = (SF_FORMAT_AIFF | SF_FORMAT_DOUBLE) ; + break ; + + case raw_MARKER : + psf->sf.format = (SF_FORMAT_AIFF | SF_FORMAT_PCM_U8) ; + break ; + + case DWVW_MARKER : + psf->sf.format = SF_FORMAT_AIFF ; + switch (comm_fmt->sampleSize) + { case 12 : + psf->sf.format |= SF_FORMAT_DWVW_12 ; + break ; + case 16 : + psf->sf.format |= SF_FORMAT_DWVW_16 ; + break ; + case 24 : + psf->sf.format |= SF_FORMAT_DWVW_24 ; + break ; + + default : + psf->sf.format |= SF_FORMAT_DWVW_N ; + break ; + } ; + break ; + + case GSM_MARKER : + psf->sf.format = SF_FORMAT_AIFF ; + psf->sf.format = (SF_FORMAT_AIFF | SF_FORMAT_GSM610) ; + break ; + + + case ima4_MARKER : + psf->endian = SF_ENDIAN_BIG ; + psf->sf.format = (SF_FORMAT_AIFF | SF_FORMAT_IMA_ADPCM) ; + break ; + + default : + psf_log_printf (psf, "AIFC : Unimplemented format : %M\n", comm_fmt->encoding) ; + error = SFE_UNIMPLEMENTED ; + } ; + + if (! psf->u.scbuf [0]) + psf_log_printf (psf, " Encoding : %M\n", comm_fmt->encoding) ; + else + psf_log_printf (psf, " Encoding : %M => %s\n", comm_fmt->encoding, psf->u.scbuf) ; + + return error ; +} /* aiff_read_comm_chunk */ + + +static int +aiff_write_header (SF_PRIVATE *psf, int calc_length) +{ sf_count_t current ; + unsigned char comm_sample_rate [10], comm_zero_bytes [2] = { 0, 0 } ; + unsigned int comm_type, comm_size, comm_encoding, comm_frames ; + int k, endian ; + short bit_width ; + + current = psf_ftell (psf) ; + + if (calc_length) + { psf->filelength = psf_get_filelen (psf) ; + + psf->datalength = psf->filelength - psf->dataoffset ; + if (psf->dataend) + psf->datalength -= psf->filelength - psf->dataend ; + + if (psf->bytewidth > 0) + psf->sf.frames = psf->datalength / (psf->bytewidth * psf->sf.channels) ; + } ; + + if (psf->mode == SFM_RDWR && psf->dataoffset > 0) + { /* Assuming here that the header has already been written and just + ** needs to be corrected for new data length. That means that we + ** only change the length fields of the FORM and SSND chunks ; + ** everything else can be skipped over. + */ + + /* First write new FORM chunk. */ + psf->headindex = 0 ; + psf_fseek (psf, 0, SEEK_SET) ; + + psf_binheader_writef (psf, "Etm8", FORM_MARKER, psf->filelength - 8) ; + psf_fwrite (psf->header, psf->headindex, 1, psf) ; + + /* Now write frame count field of COMM chunk header. */ + psf->headindex = 0 ; + psf_fseek (psf, 22, SEEK_SET) ; + + psf_binheader_writef (psf, "Et8", psf->sf.frames) ; + psf_fwrite (psf->header, psf->headindex, 1, psf) ; + + /* Now write new SSND chunk header. */ + psf->headindex = 0 ; + psf_fseek (psf, psf->dataoffset - 16, SEEK_SET) ; + + psf_binheader_writef (psf, "Etm8", SSND_MARKER, psf->datalength + SIZEOF_SSND_CHUNK) ; + psf_fwrite (psf->header, psf->headindex, 1, psf) ; + + if (current < psf->dataoffset) + psf_fseek (psf, psf->dataoffset, SEEK_SET) ; + else if (current > 0) + psf_fseek (psf, current, SEEK_SET) ; + + return 0 ; + } ; + + endian = psf->sf.format & SF_FORMAT_ENDMASK ; + if (CPU_IS_LITTLE_ENDIAN && endian == SF_ENDIAN_CPU) + endian = SF_ENDIAN_LITTLE ; + + /* Standard value here. */ + bit_width = psf->bytewidth * 8 ; + comm_frames = (psf->sf.frames > 0xFFFFFFFF) ? 0xFFFFFFFF : psf->sf.frames ; + + switch (psf->sf.format & SF_FORMAT_SUBMASK) + { case SF_FORMAT_PCM_S8 : + case SF_FORMAT_PCM_16 : + case SF_FORMAT_PCM_24 : + case SF_FORMAT_PCM_32 : + switch (endian) + { case SF_ENDIAN_BIG : + psf->endian = SF_ENDIAN_BIG ; + comm_type = AIFC_MARKER ; + comm_size = SIZEOF_AIFC_COMM ; + comm_encoding = twos_MARKER ; + break ; + + case SF_ENDIAN_LITTLE : + psf->endian = SF_ENDIAN_LITTLE ; + comm_type = AIFC_MARKER ; + comm_size = SIZEOF_AIFC_COMM ; + comm_encoding = sowt_MARKER ; + break ; + + default : /* SF_ENDIAN_FILE */ + psf->endian = SF_ENDIAN_BIG ; + comm_type = AIFF_MARKER ; + comm_size = SIZEOF_AIFF_COMM ; + comm_encoding = 0 ; + break ; + } ; + break ; + + case SF_FORMAT_FLOAT : /* Big endian floating point. */ + psf->endian = SF_ENDIAN_BIG ; + comm_type = AIFC_MARKER ; + comm_size = SIZEOF_AIFC_COMM ; + comm_encoding = FL32_MARKER ; /* Use 'FL32' because its easier to read. */ + break ; + + case SF_FORMAT_DOUBLE : /* Big endian double precision floating point. */ + psf->endian = SF_ENDIAN_BIG ; + comm_type = AIFC_MARKER ; + comm_size = SIZEOF_AIFC_COMM ; + comm_encoding = FL64_MARKER ; /* Use 'FL64' because its easier to read. */ + break ; + + case SF_FORMAT_ULAW : + psf->endian = SF_ENDIAN_BIG ; + comm_type = AIFC_MARKER ; + comm_size = SIZEOF_AIFC_COMM ; + comm_encoding = ulaw_MARKER ; + break ; + + case SF_FORMAT_ALAW : + psf->endian = SF_ENDIAN_BIG ; + comm_type = AIFC_MARKER ; + comm_size = SIZEOF_AIFC_COMM ; + comm_encoding = alaw_MARKER ; + break ; + + case SF_FORMAT_PCM_U8 : + psf->endian = SF_ENDIAN_BIG ; + comm_type = AIFC_MARKER ; + comm_size = SIZEOF_AIFC_COMM ; + comm_encoding = raw_MARKER ; + break ; + + case SF_FORMAT_DWVW_12 : + psf->endian = SF_ENDIAN_BIG ; + comm_type = AIFC_MARKER ; + comm_size = SIZEOF_AIFC_COMM ; + comm_encoding = DWVW_MARKER ; + + /* Override standard value here.*/ + bit_width = 12 ; + break ; + + case SF_FORMAT_DWVW_16 : + psf->endian = SF_ENDIAN_BIG ; + comm_type = AIFC_MARKER ; + comm_size = SIZEOF_AIFC_COMM ; + comm_encoding = DWVW_MARKER ; + + /* Override standard value here.*/ + bit_width = 16 ; + break ; + + case SF_FORMAT_DWVW_24 : + psf->endian = SF_ENDIAN_BIG ; + comm_type = AIFC_MARKER ; + comm_size = SIZEOF_AIFC_COMM ; + comm_encoding = DWVW_MARKER ; + + /* Override standard value here.*/ + bit_width = 24 ; + break ; + + case SF_FORMAT_GSM610 : + psf->endian = SF_ENDIAN_BIG ; + comm_type = AIFC_MARKER ; + comm_size = SIZEOF_AIFC_COMM ; + comm_encoding = GSM_MARKER ; + + /* Override standard value here.*/ + bit_width = 16 ; + break ; + + case SF_FORMAT_IMA_ADPCM : + psf->endian = SF_ENDIAN_BIG ; + comm_type = AIFC_MARKER ; + comm_size = SIZEOF_AIFC_COMM ; + comm_encoding = ima4_MARKER ; + + /* Override standard value here.*/ + bit_width = 16 ; + comm_frames = psf->sf.frames / AIFC_IMA4_SAMPLES_PER_BLOCK ; + break ; + + default : return SFE_BAD_OPEN_FORMAT ; + } ; + + /* Reset the current header length to zero. */ + psf->header [0] = 0 ; + psf->headindex = 0 ; + psf_fseek (psf, 0, SEEK_SET) ; + + psf_binheader_writef (psf, "Etm8", FORM_MARKER, psf->filelength - 8) ; + + /* Write COMM chunk. */ + psf_binheader_writef (psf, "Emm4", comm_type, COMM_MARKER, comm_size) ; + + memset (comm_sample_rate, 0, sizeof (comm_sample_rate)) ; + uint2tenbytefloat (psf->sf.samplerate, comm_sample_rate) ; + + psf_binheader_writef (psf, "Et242", psf->sf.channels, comm_frames, bit_width) ; + psf_binheader_writef (psf, "b", comm_sample_rate, sizeof (comm_sample_rate)) ; + + /* AIFC chunks have some extra data. */ + if (comm_type == AIFC_MARKER) + psf_binheader_writef (psf, "mb", comm_encoding, comm_zero_bytes, sizeof (comm_zero_bytes)) ; + + if (psf->instrument != NULL) + { MARK_ID_POS m [4] ; + INST_CHUNK ch ; + unsigned short ct = 0 ; + + memset (m, 0, sizeof (m)) ; + memset (&ch, 0, sizeof (ch)) ; + + ch.baseNote = psf->instrument->basenote ; + ch.detune = psf->instrument->detune ; + ch.lowNote = psf->instrument->key_lo ; + ch.highNote = psf->instrument->key_hi ; + ch.lowVelocity = psf->instrument->velocity_lo ; + ch.highVelocity = psf->instrument->velocity_hi ; + ch.gain = psf->instrument->gain ; + if (psf->instrument->loops [0].mode != SF_LOOP_NONE) + { ch.sustain_loop.playMode = 1 ; + ch.sustain_loop.beginLoop = ct ; + m [0].markerID = ct++ ; + m [0].position = psf->instrument->loops [0].start ; + ch.sustain_loop.endLoop = ct ; + m [1].markerID = ct++ ; + m [1].position = psf->instrument->loops [0].end ; + } ; + if (psf->instrument->loops [1].mode != SF_LOOP_NONE) + { ch.release_loop.playMode = 1 ; + ch.release_loop.beginLoop = ct ; + m [2].markerID = ct++ ; + m [2].position = psf->instrument->loops [1].start ; + ch.release_loop.endLoop = ct ; + m [3].markerID = ct++ ; + m [3].position = psf->instrument->loops [1].end ; + } + else + { ch.release_loop.playMode = 0 ; + ch.release_loop.beginLoop = 0 ; + ch.release_loop.endLoop = 0 ; + } ; + + psf_binheader_writef (psf, "Em4111111", INST_MARKER, SIZEOF_INST_CHUNK, ch.baseNote, ch.detune, + ch.lowNote, ch.highNote, ch.lowVelocity, ch.highVelocity) ; + psf_binheader_writef (psf, "2222222", ch.gain, ch.sustain_loop.playMode, + ch.sustain_loop.beginLoop, ch.sustain_loop.endLoop, ch.release_loop.playMode, + ch.release_loop.beginLoop, ch.release_loop.endLoop) ; + + if (ct == 2) + psf_binheader_writef (psf, "Em42241b241b", + MARK_MARKER, 2 + 2 * (2 + 4 + 1 + 9), 2, + m [0].markerID, m [0].position, 8, "beg loop", make_size_t (9), + m [1].markerID, m [1].position, 8, "end loop", make_size_t (9)) ; + else if (ct == 4) + psf_binheader_writef (psf, "Em42 241b 241b 241b 241b", + MARK_MARKER, 2 + 4 * (2 + 4 + 1 + 9), 4, + m [0].markerID, m [0].position, 8, "beg loop", make_size_t (9), + m [1].markerID, m [1].position, 8, "end loop", make_size_t (9), + m [2].markerID, m [2].position, 8, "beg loop", make_size_t (9), + m [3].markerID, m [3].position, 8, "end loop", make_size_t (9)) ; + } ; + + if (psf->str_flags & SF_STR_LOCATE_START) + aiff_write_strings (psf, SF_STR_LOCATE_START) ; + + if (psf->peak_info != NULL && psf->peak_info->peak_loc == SF_PEAK_START) + { psf_binheader_writef (psf, "Em4", PEAK_MARKER, AIFF_PEAK_CHUNK_SIZE (psf->sf.channels)) ; + psf_binheader_writef (psf, "E44", 1, time (NULL)) ; + for (k = 0 ; k < psf->sf.channels ; k++) + psf_binheader_writef (psf, "Eft8", (float) psf->peak_info->peaks [k].value, psf->peak_info->peaks [k].position) ; + } ; + + /* Write SSND chunk. */ + psf_binheader_writef (psf, "Etm844", SSND_MARKER, psf->datalength + SIZEOF_SSND_CHUNK, 0, 0) ; + + /* Header construction complete so write it out. */ + psf_fwrite (psf->header, psf->headindex, 1, psf) ; + + if (psf->error) + return psf->error ; + + psf->dataoffset = psf->headindex ; + + if (current < psf->dataoffset) + psf_fseek (psf, psf->dataoffset, SEEK_SET) ; + else if (current > 0) + psf_fseek (psf, current, SEEK_SET) ; + + return psf->error ; +} /* aiff_write_header */ + +static int +aiff_write_tailer (SF_PRIVATE *psf) +{ int k ; + + /* Reset the current header length to zero. */ + psf->header [0] = 0 ; + psf->headindex = 0 ; + + psf->dataend = psf_fseek (psf, 0, SEEK_END) ; + + /* Make sure tailer data starts at even byte offset. Pad if necessary. */ + if (psf->dataend % 2 == 1) + { psf_fwrite (psf->header, 1, 1, psf) ; + psf->dataend ++ ; + } ; + + if (psf->peak_info != NULL && psf->peak_info->peak_loc == SF_PEAK_END) + { psf_binheader_writef (psf, "Em4", PEAK_MARKER, AIFF_PEAK_CHUNK_SIZE (psf->sf.channels)) ; + psf_binheader_writef (psf, "E44", 1, time (NULL)) ; + for (k = 0 ; k < psf->sf.channels ; k++) + psf_binheader_writef (psf, "Eft8", (float) psf->peak_info->peaks [k].value, psf->peak_info->peaks [k].position) ; + } ; + + if (psf->str_flags & SF_STR_LOCATE_END) + aiff_write_strings (psf, SF_STR_LOCATE_END) ; + + /* Write the tailer. */ + if (psf->headindex > 0) + psf_fwrite (psf->header, psf->headindex, 1, psf) ; + + return 0 ; +} /* aiff_write_tailer */ + +static void +aiff_write_strings (SF_PRIVATE *psf, int location) +{ int k ; + + for (k = 0 ; k < SF_MAX_STRINGS ; k++) + { if (psf->strings [k].type == 0) + break ; + + if (psf->strings [k].flags != location) + continue ; + + switch (psf->strings [k].type) + { case SF_STR_SOFTWARE : + psf_binheader_writef (psf, "EmS", APPL_MARKER, psf->strings [k].str) ; + break ; + + case SF_STR_TITLE : + psf_binheader_writef (psf, "EmS", NAME_MARKER, psf->strings [k].str) ; + break ; + + case SF_STR_COPYRIGHT : + psf_binheader_writef (psf, "EmS", c_MARKER, psf->strings [k].str) ; + break ; + + case SF_STR_ARTIST : + psf_binheader_writef (psf, "EmS", AUTH_MARKER, psf->strings [k].str) ; + break ; + + case SF_STR_COMMENT : + psf_binheader_writef (psf, "EmS", ANNO_MARKER, psf->strings [k].str) ; + break ; + + /* + case SF_STR_DATE : + psf_binheader_writef (psf, "Ems", ICRD_MARKER, psf->strings [k].str) ; + break ; + */ + } ; + } ; + + return ; +} /* aiff_write_strings */ + +static int +aiff_command (SF_PRIVATE *psf, int command, void *data, int datasize) +{ + /* Avoid compiler warnings. */ + psf = psf ; + data = data ; + datasize = datasize ; + + switch (command) + { default : break ; + } ; + + return 0 ; +} /* aiff_command */ + +static const char* +get_loop_mode_str (short mode) +{ switch (mode) + { case 0 : return "none" ; + case 1 : return "forward" ; + case 2 : return "backward" ; + } ; + + return "*** unknown" ; +} /* get_loop_mode_str */ + +static short +get_loop_mode (short mode) +{ switch (mode) + { case 0 : return SF_LOOP_NONE ; + case 1 : return SF_LOOP_FORWARD ; + case 2 : return SF_LOOP_BACKWARD ; + } ; + + return SF_LOOP_NONE ; +} /* get_loop_mode */ + +/*========================================================================================== +** Rough hack at converting from 80 bit IEEE float in AIFF header to an int and +** back again. It assumes that all sample rates are between 1 and 800MHz, which +** should be OK as other sound file formats use a 32 bit integer to store sample +** rate. +** There is another (probably better) version in the source code to the SoX but it +** has a copyright which probably prevents it from being allowable as GPL/LGPL. +*/ + +static int +tenbytefloat2int (unsigned char *bytes) +{ int val = 3 ; + + if (bytes [0] & 0x80) /* Negative number. */ + return 0 ; + + if (bytes [0] <= 0x3F) /* Less than 1. */ + return 1 ; + + if (bytes [0] > 0x40) /* Way too big. */ + return 0x4000000 ; + + if (bytes [0] == 0x40 && bytes [1] > 0x1C) /* Too big. */ + return 800000000 ; + + /* Ok, can handle it. */ + + val = (bytes [2] << 23) | (bytes [3] << 15) | (bytes [4] << 7) | (bytes [5] >> 1) ; + + val >>= (29 - bytes [1]) ; + + return val ; +} /* tenbytefloat2int */ + +static void +uint2tenbytefloat (unsigned int num, unsigned char *bytes) +{ unsigned int mask = 0x40000000 ; + int count ; + + if (num <= 1) + { bytes [0] = 0x3F ; + bytes [1] = 0xFF ; + bytes [2] = 0x80 ; + return ; + } ; + + bytes [0] = 0x40 ; + + if (num >= mask) + { bytes [1] = 0x1D ; + return ; + } ; + + for (count = 0 ; count <= 32 ; count ++) + { if (num & mask) + break ; + mask >>= 1 ; + } ; + + num <<= count + 1 ; + bytes [1] = 29 - count ; + bytes [2] = (num >> 24) & 0xFF ; + bytes [3] = (num >> 16) & 0xFF ; + bytes [4] = (num >> 8) & 0xFF ; + bytes [5] = num & 0xFF ; + +} /* uint2tenbytefloat */ + +static int +aiff_read_basc_chunk (SF_PRIVATE * psf, int datasize) +{ const char * type_str ; + basc_CHUNK bc ; + + psf_binheader_readf (psf, "E442", &bc.version, &bc.numBeats, &bc.rootNote) ; + psf_binheader_readf (psf, "E222", &bc.scaleType, &bc.sigNumerator, &bc.sigDenominator) ; + psf_binheader_readf (psf, "E2j", &bc.loopType, datasize - sizeof (bc)) ; + + psf_log_printf (psf, " Version ? : %u\n Num Beats : %u\n Root Note : 0x%x\n", + bc.version, bc.numBeats, bc.rootNote) ; + + switch (bc.scaleType) + { case basc_SCALE_MINOR : + type_str = "MINOR" ; + break ; + case basc_SCALE_MAJOR : + type_str = "MAJOR" ; + break ; + case basc_SCALE_NEITHER : + type_str = "NEITHER" ; + break ; + case basc_SCALE_BOTH : + type_str = "BOTH" ; + break ; + default : + type_str = "!!WRONG!!" ; + break ; + } ; + + psf_log_printf (psf, " ScaleType : 0x%x (%s)\n", bc.scaleType, type_str) ; + psf_log_printf (psf, " Time Sig : %d/%d\n", bc.sigNumerator, bc.sigDenominator) ; + + switch (bc.loopType) + { case basc_TYPE_ONE_SHOT : + type_str = "One Shot" ; + break ; + case basc_TYPE_LOOP : + type_str = "Loop" ; + break ; + default: + type_str = "!!WRONG!!" ; + break ; + } ; + + psf_log_printf (psf, " Loop Type : 0x%x (%s)\n", bc.loopType, type_str) ; + + if ((psf->loop_info = calloc (1, sizeof (SF_LOOP_INFO))) == NULL) + return SFE_MALLOC_FAILED ; + + psf->loop_info->time_sig_num = bc.sigNumerator ; + psf->loop_info->time_sig_den = bc.sigDenominator ; + psf->loop_info->loop_mode = (bc.loopType == basc_TYPE_ONE_SHOT) ? SF_LOOP_NONE : SF_LOOP_FORWARD ; + psf->loop_info->num_beats = bc.numBeats ; + + /* Can always be recalculated from other known fields. */ + psf->loop_info->bpm = (1.0 / psf->sf.frames) * psf->sf.samplerate + * ((bc.numBeats * 4.0) / bc.sigDenominator) * 60.0 ; + psf->loop_info->root_key = bc.rootNote ; + + return 0 ; +} /* aiff_read_basc_chunk */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 7dec56ca-d6f2-48cf-863b-a72e7e17a5d9 +*/ diff --git a/libs/libsndfile/src/alaw.c b/libs/libsndfile/src/alaw.c new file mode 100644 index 0000000000..a2d27cb58c --- /dev/null +++ b/libs/libsndfile/src/alaw.c @@ -0,0 +1,544 @@ +/* +** Copyright (C) 1999-2005 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sndfile.h" +#include "float_cast.h" +#include "common.h" + +static sf_count_t alaw_read_alaw2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t alaw_read_alaw2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t alaw_read_alaw2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t alaw_read_alaw2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; + +static sf_count_t alaw_write_s2alaw (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t alaw_write_i2alaw (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t alaw_write_f2alaw (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t alaw_write_d2alaw (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; + +static void alaw2s_array (unsigned char *buffer, int count, short *ptr) ; +static void alaw2i_array (unsigned char *buffer, int count, int *ptr) ; +static void alaw2f_array (unsigned char *buffer, int count, float *ptr, float normfact) ; +static void alaw2d_array (unsigned char *buffer, int count, double *ptr, double normfact) ; + +static void s2alaw_array (const short *buffer, int count, unsigned char *ptr) ; +static void i2alaw_array (const int *buffer, int count, unsigned char *ptr) ; +static void f2alaw_array (const float *buffer, int count, unsigned char *ptr, float normfact) ; +static void d2alaw_array (const double *buffer, int count, unsigned char *ptr, double normfact) ; + + +int +alaw_init (SF_PRIVATE *psf) +{ + if (psf->mode == SFM_READ || psf->mode == SFM_RDWR) + { psf->read_short = alaw_read_alaw2s ; + psf->read_int = alaw_read_alaw2i ; + psf->read_float = alaw_read_alaw2f ; + psf->read_double = alaw_read_alaw2d ; + } ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { psf->write_short = alaw_write_s2alaw ; + psf->write_int = alaw_write_i2alaw ; + psf->write_float = alaw_write_f2alaw ; + psf->write_double = alaw_write_d2alaw ; + } ; + + psf->bytewidth = 1 ; + psf->blockwidth = psf->sf.channels ; + + if (psf->filelength > psf->dataoffset) + psf->datalength = (psf->dataend) ? psf->dataend - psf->dataoffset : psf->filelength - psf->dataoffset ; + else + psf->datalength = 0 ; + + psf->sf.frames = psf->datalength / psf->blockwidth ; + + return 0 ; +} /* alaw_init */ + +/*============================================================================== + * Private static functions and data. + */ + +static +short alaw_decode [256] = +{ -5504, -5248, -6016, -5760, -4480, -4224, -4992, -4736, + -7552, -7296, -8064, -7808, -6528, -6272, -7040, -6784, + -2752, -2624, -3008, -2880, -2240, -2112, -2496, -2368, + -3776, -3648, -4032, -3904, -3264, -3136, -3520, -3392, + -22016, -20992, -24064, -23040, -17920, -16896, -19968, -18944, + -30208, -29184, -32256, -31232, -26112, -25088, -28160, -27136, + -11008, -10496, -12032, -11520, -8960, -8448, -9984, -9472, + -15104, -14592, -16128, -15616, -13056, -12544, -14080, -13568, + -344, -328, -376, -360, -280, -264, -312, -296, + -472, -456, -504, -488, -408, -392, -440, -424, + -88, -72, -120, -104, -24, -8, -56, -40, + -216, -200, -248, -232, -152, -136, -184, -168, + -1376, -1312, -1504, -1440, -1120, -1056, -1248, -1184, + -1888, -1824, -2016, -1952, -1632, -1568, -1760, -1696, + -688, -656, -752, -720, -560, -528, -624, -592, + -944, -912, -1008, -976, -816, -784, -880, -848, + 5504, 5248, 6016, 5760, 4480, 4224, 4992, 4736, + 7552, 7296, 8064, 7808, 6528, 6272, 7040, 6784, + 2752, 2624, 3008, 2880, 2240, 2112, 2496, 2368, + 3776, 3648, 4032, 3904, 3264, 3136, 3520, 3392, + 22016, 20992, 24064, 23040, 17920, 16896, 19968, 18944, + 30208, 29184, 32256, 31232, 26112, 25088, 28160, 27136, + 11008, 10496, 12032, 11520, 8960, 8448, 9984, 9472, + 15104, 14592, 16128, 15616, 13056, 12544, 14080, 13568, + 344, 328, 376, 360, 280, 264, 312, 296, + 472, 456, 504, 488, 408, 392, 440, 424, + 88, 72, 120, 104, 24, 8, 56, 40, + 216, 200, 248, 232, 152, 136, 184, 168, + 1376, 1312, 1504, 1440, 1120, 1056, 1248, 1184, + 1888, 1824, 2016, 1952, 1632, 1568, 1760, 1696, + 688, 656, 752, 720, 560, 528, 624, 592, + 944, 912, 1008, 976, 816, 784, 880, 848 +} ; /* alaw_decode */ + +static +unsigned char alaw_encode [2048 + 1] = +{ 0xd5, 0xd4, 0xd7, 0xd6, 0xd1, 0xd0, 0xd3, 0xd2, 0xdd, 0xdc, 0xdf, 0xde, + 0xd9, 0xd8, 0xdb, 0xda, 0xc5, 0xc4, 0xc7, 0xc6, 0xc1, 0xc0, 0xc3, 0xc2, + 0xcd, 0xcc, 0xcf, 0xce, 0xc9, 0xc8, 0xcb, 0xca, 0xf5, 0xf5, 0xf4, 0xf4, + 0xf7, 0xf7, 0xf6, 0xf6, 0xf1, 0xf1, 0xf0, 0xf0, 0xf3, 0xf3, 0xf2, 0xf2, + 0xfd, 0xfd, 0xfc, 0xfc, 0xff, 0xff, 0xfe, 0xfe, 0xf9, 0xf9, 0xf8, 0xf8, + 0xfb, 0xfb, 0xfa, 0xfa, 0xe5, 0xe5, 0xe5, 0xe5, 0xe4, 0xe4, 0xe4, 0xe4, + 0xe7, 0xe7, 0xe7, 0xe7, 0xe6, 0xe6, 0xe6, 0xe6, 0xe1, 0xe1, 0xe1, 0xe1, + 0xe0, 0xe0, 0xe0, 0xe0, 0xe3, 0xe3, 0xe3, 0xe3, 0xe2, 0xe2, 0xe2, 0xe2, + 0xed, 0xed, 0xed, 0xed, 0xec, 0xec, 0xec, 0xec, 0xef, 0xef, 0xef, 0xef, + 0xee, 0xee, 0xee, 0xee, 0xe9, 0xe9, 0xe9, 0xe9, 0xe8, 0xe8, 0xe8, 0xe8, + 0xeb, 0xeb, 0xeb, 0xeb, 0xea, 0xea, 0xea, 0xea, 0x95, 0x95, 0x95, 0x95, + 0x95, 0x95, 0x95, 0x95, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, + 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x96, 0x96, 0x96, 0x96, + 0x96, 0x96, 0x96, 0x96, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, + 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x93, 0x93, 0x93, 0x93, + 0x93, 0x93, 0x93, 0x93, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, + 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9c, 0x9c, 0x9c, 0x9c, + 0x9c, 0x9c, 0x9c, 0x9c, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, + 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x99, 0x99, 0x99, 0x99, + 0x99, 0x99, 0x99, 0x99, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, + 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9a, 0x9a, 0x9a, 0x9a, + 0x9a, 0x9a, 0x9a, 0x9a, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, + 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x84, 0x84, 0x84, 0x84, + 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, + 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, + 0x87, 0x87, 0x87, 0x87, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, + 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, + 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x82, 0x82, 0x82, 0x82, + 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, + 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, + 0x8d, 0x8d, 0x8d, 0x8d, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, + 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8f, 0x8f, 0x8f, 0x8f, + 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, + 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, + 0x8e, 0x8e, 0x8e, 0x8e, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, + 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, + 0x8b, 0x8b, 0x8b, 0x8b, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, + 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0xb5, 0xb5, 0xb5, 0xb5, + 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, + 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, + 0xb5, 0xb5, 0xb5, 0xb5, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, + 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, + 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, + 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, + 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, + 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb6, 0xb6, 0xb6, 0xb6, + 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, + 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, + 0xb6, 0xb6, 0xb6, 0xb6, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, + 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, + 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, + 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, + 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, + 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb3, 0xb3, 0xb3, 0xb3, + 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, + 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, + 0xb3, 0xb3, 0xb3, 0xb3, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, + 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, + 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, + 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, + 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, + 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbc, 0xbc, 0xbc, 0xbc, + 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, + 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, + 0xbc, 0xbc, 0xbc, 0xbc, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, + 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, + 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, + 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, + 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, + 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xb9, 0xb9, 0xb9, 0xb9, + 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, + 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, + 0xb9, 0xb9, 0xb9, 0xb9, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, + 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, + 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, + 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, + 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, + 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xba, 0xba, 0xba, 0xba, + 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, + 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, + 0xba, 0xba, 0xba, 0xba, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, + 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, + 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, + 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, + 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, + 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa4, 0xa4, 0xa4, 0xa4, + 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, + 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, + 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, + 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, + 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, + 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, + 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, + 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, + 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, + 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, + 0xa7, 0xa7, 0xa7, 0xa7, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, + 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, + 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, + 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, + 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, + 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa1, 0xa1, 0xa1, 0xa1, + 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, + 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, + 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, + 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, + 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, + 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, + 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, + 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, + 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, + 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, + 0xa0, 0xa0, 0xa0, 0xa0, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, + 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, + 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, + 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, + 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, + 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa2, 0xa2, 0xa2, 0xa2, + 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, + 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, + 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, + 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, + 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, + 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, + 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, + 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, + 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, + 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, + 0xad, 0xad, 0xad, 0xad, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, + 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, + 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, + 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, + 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, + 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xaf, 0xaf, 0xaf, 0xaf, + 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, + 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, + 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, + 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, + 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, + 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, + 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, + 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, + 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, + 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, + 0xae, 0xae, 0xae, 0xae, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, + 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, + 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, + 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, + 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, + 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa8, 0xa8, 0xa8, 0xa8, + 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, + 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, + 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, + 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, + 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, + 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, + 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, + 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, + 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, + 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, + 0xab, 0xab, 0xab, 0xab, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, + 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, + 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, + 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, + 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, + 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0x2a +} ; /* alaw_encode */ + +static inline void +alaw2s_array (unsigned char *buffer, int count, short *ptr) +{ while (--count >= 0) + ptr [count] = alaw_decode [(int) buffer [count]] ; +} /* alaw2s_array */ + +static inline void +alaw2i_array (unsigned char *buffer, int count, int *ptr) +{ while (--count >= 0) + ptr [count] = alaw_decode [(int) buffer [count]] << 16 ; +} /* alaw2i_array */ + +static inline void +alaw2f_array (unsigned char *buffer, int count, float *ptr, float normfact) +{ while (--count >= 0) + ptr [count] = normfact * alaw_decode [(int) buffer [count]] ; +} /* alaw2f_array */ + +static inline void +alaw2d_array (unsigned char *buffer, int count, double *ptr, double normfact) +{ while (--count >= 0) + ptr [count] = normfact * alaw_decode [(int) buffer [count]] ; +} /* alaw2d_array */ + +static inline void +s2alaw_array (const short *ptr, int count, unsigned char *buffer) +{ while (--count >= 0) + { if (ptr [count] >= 0) + buffer [count] = alaw_encode [ptr [count] / 16] ; + else + buffer [count] = 0x7F & alaw_encode [ptr [count] / -16] ; + } ; +} /* s2alaw_array */ + +static inline void +i2alaw_array (const int *ptr, int count, unsigned char *buffer) +{ while (--count >= 0) + { if (ptr [count] >= 0) + buffer [count] = alaw_encode [ptr [count] >> (16 + 4)] ; + else + buffer [count] = 0x7F & alaw_encode [- ptr [count] >> (16 + 4)] ; + } ; +} /* i2alaw_array */ + +static inline void +f2alaw_array (const float *ptr, int count, unsigned char *buffer, float normfact) +{ while (--count >= 0) + { if (ptr [count] >= 0) + buffer [count] = alaw_encode [lrintf (normfact * ptr [count])] ; + else + buffer [count] = 0x7F & alaw_encode [- lrintf (normfact * ptr [count])] ; + } ; +} /* f2alaw_array */ + +static inline void +d2alaw_array (const double *ptr, int count, unsigned char *buffer, double normfact) +{ while (--count >= 0) + { if (ptr [count] >= 0) + buffer [count] = alaw_encode [lrint (normfact * ptr [count])] ; + else + buffer [count] = 0x7F & alaw_encode [- lrint (normfact * ptr [count])] ; + } ; +} /* d2alaw_array */ + +/*============================================================================== +*/ + +static sf_count_t +alaw_read_alaw2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ucbuf, 1, bufferlen, psf) ; + alaw2s_array (psf->u.ucbuf, readcount, ptr + total) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* alaw_read_alaw2s */ + +static sf_count_t +alaw_read_alaw2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ucbuf, 1, bufferlen, psf) ; + alaw2i_array (psf->u.ucbuf, readcount, ptr + total) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* alaw_read_alaw2i */ + +static sf_count_t +alaw_read_alaw2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + float normfact ; + + normfact = (psf->norm_float == SF_TRUE) ? 1.0 / ((float) 0x8000) : 1.0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ucbuf, 1, bufferlen, psf) ; + alaw2f_array (psf->u.ucbuf, readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* alaw_read_alaw2f */ + +static sf_count_t +alaw_read_alaw2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + double normfact ; + + normfact = (psf->norm_double) ? 1.0 / ((double) 0x8000) : 1.0 ; + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ucbuf, 1, bufferlen, psf) ; + alaw2d_array (psf->u.ucbuf, readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* alaw_read_alaw2d */ + +/*============================================================================================= +*/ + +static sf_count_t +alaw_write_s2alaw (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + s2alaw_array (ptr + total, bufferlen, psf->u.ucbuf) ; + writecount = psf_fwrite (psf->u.ucbuf, 1, bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* alaw_write_s2alaw */ + +static sf_count_t +alaw_write_i2alaw (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + i2alaw_array (ptr + total, bufferlen, psf->u.ucbuf) ; + writecount = psf_fwrite (psf->u.ucbuf, 1, bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* alaw_write_i2alaw */ + +static sf_count_t +alaw_write_f2alaw (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + float normfact ; + + normfact = (psf->norm_float == SF_TRUE) ? (1.0 * 0x7FFF) / 16.0 : 1.0 / 16 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + f2alaw_array (ptr + total, bufferlen, psf->u.ucbuf, normfact) ; + writecount = psf_fwrite (psf->u.ucbuf, 1, bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* alaw_write_f2alaw */ + +static sf_count_t +alaw_write_d2alaw (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + double normfact ; + + normfact = (psf->norm_double) ? (1.0 * 0x7FFF) / 16.0 : 1.0 / 16.0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + d2alaw_array (ptr + total, bufferlen, psf->u.ucbuf, normfact) ; + writecount = psf_fwrite (psf->u.ucbuf, 1, bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* alaw_write_d2alaw */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 289ccfc2-42a6-4f1f-a29f-4dcc9bfa8752 +*/ diff --git a/libs/libsndfile/src/au.c b/libs/libsndfile/src/au.c new file mode 100644 index 0000000000..3a5f93bd90 --- /dev/null +++ b/libs/libsndfile/src/au.c @@ -0,0 +1,453 @@ +/* +** Copyright (C) 1999-2004 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" + +/*------------------------------------------------------------------------------ +** Macros to handle big/little endian issues. +*/ + +#define DOTSND_MARKER (MAKE_MARKER ('.', 's', 'n', 'd')) +#define DNSDOT_MARKER (MAKE_MARKER ('d', 'n', 's', '.')) + +#define AU_DATA_OFFSET 24 + +/*------------------------------------------------------------------------------ +** Known AU file encoding types. +*/ + +enum +{ AU_ENCODING_ULAW_8 = 1, /* 8-bit u-law samples */ + AU_ENCODING_PCM_8 = 2, /* 8-bit linear samples */ + AU_ENCODING_PCM_16 = 3, /* 16-bit linear samples */ + AU_ENCODING_PCM_24 = 4, /* 24-bit linear samples */ + AU_ENCODING_PCM_32 = 5, /* 32-bit linear samples */ + + AU_ENCODING_FLOAT = 6, /* floating-point samples */ + AU_ENCODING_DOUBLE = 7, /* double-precision float samples */ + AU_ENCODING_INDIRECT = 8, /* fragmented sampled data */ + AU_ENCODING_NESTED = 9, /* ? */ + AU_ENCODING_DSP_CORE = 10, /* DSP program */ + AU_ENCODING_DSP_DATA_8 = 11, /* 8-bit fixed-point samples */ + AU_ENCODING_DSP_DATA_16 = 12, /* 16-bit fixed-point samples */ + AU_ENCODING_DSP_DATA_24 = 13, /* 24-bit fixed-point samples */ + AU_ENCODING_DSP_DATA_32 = 14, /* 32-bit fixed-point samples */ + + AU_ENCODING_DISPLAY = 16, /* non-audio display data */ + AU_ENCODING_MULAW_SQUELCH = 17, /* ? */ + AU_ENCODING_EMPHASIZED = 18, /* 16-bit linear with emphasis */ + AU_ENCODING_NEXT = 19, /* 16-bit linear with compression (NEXT) */ + AU_ENCODING_COMPRESSED_EMPHASIZED = 20, /* A combination of the two above */ + AU_ENCODING_DSP_COMMANDS = 21, /* Music Kit DSP commands */ + AU_ENCODING_DSP_COMMANDS_SAMPLES = 22, /* ? */ + + AU_ENCODING_ADPCM_G721_32 = 23, /* G721 32 kbs ADPCM - 4 bits per sample. */ + AU_ENCODING_ADPCM_G722 = 24, /* G722 64 kbs ADPCM */ + AU_ENCODING_ADPCM_G723_24 = 25, /* G723 24 kbs ADPCM - 3 bits per sample. */ + AU_ENCODING_ADPCM_G723_40 = 26, /* G723 40 kbs ADPCM - 5 bits per sample. */ + + AU_ENCODING_ALAW_8 = 27 +} ; + +/*------------------------------------------------------------------------------ +** Typedefs. +*/ + +typedef struct +{ int dataoffset ; + int datasize ; + int encoding ; + int samplerate ; + int channels ; +} AU_FMT ; + + +/*------------------------------------------------------------------------------ +** Private static functions. +*/ + +static int au_close (SF_PRIVATE *psf) ; + +static int au_format_to_encoding (int format) ; + +static int au_write_header (SF_PRIVATE *psf, int calc_length) ; +static int au_read_header (SF_PRIVATE *psf) ; + +/*------------------------------------------------------------------------------ +** Public function. +*/ + +int +au_open (SF_PRIVATE *psf) +{ int subformat ; + int error = 0 ; + + if (psf->mode == SFM_READ || (psf->mode == SFM_RDWR && psf->filelength > 0)) + { if ((error = au_read_header (psf))) + return error ; + } ; + + if ((psf->sf.format & SF_FORMAT_TYPEMASK) != SF_FORMAT_AU) + return SFE_BAD_OPEN_FORMAT ; + + subformat = psf->sf.format & SF_FORMAT_SUBMASK ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { psf->endian = psf->sf.format & SF_FORMAT_ENDMASK ; + if (CPU_IS_LITTLE_ENDIAN && psf->endian == SF_ENDIAN_CPU) + psf->endian = SF_ENDIAN_LITTLE ; + else if (psf->endian != SF_ENDIAN_LITTLE) + psf->endian = SF_ENDIAN_BIG ; + + if (au_write_header (psf, SF_FALSE)) + return psf->error ; + + psf->write_header = au_write_header ; + } ; + + psf->container_close = au_close ; + + psf->blockwidth = psf->bytewidth * psf->sf.channels ; + + switch (subformat) + { case SF_FORMAT_ULAW : /* 8-bit Ulaw encoding. */ + ulaw_init (psf) ; + break ; + + case SF_FORMAT_PCM_S8 : /* 8-bit linear PCM. */ + error = pcm_init (psf) ; + break ; + + case SF_FORMAT_PCM_16 : /* 16-bit linear PCM. */ + case SF_FORMAT_PCM_24 : /* 24-bit linear PCM */ + case SF_FORMAT_PCM_32 : /* 32-bit linear PCM. */ + error = pcm_init (psf) ; + break ; + + case SF_FORMAT_ALAW : /* 8-bit Alaw encoding. */ + alaw_init (psf) ; + break ; + + /* Lite remove start */ + case SF_FORMAT_FLOAT : /* 32-bit floats. */ + error = float32_init (psf) ; + break ; + + case SF_FORMAT_DOUBLE : /* 64-bit double precision floats. */ + error = double64_init (psf) ; + break ; + + case SF_FORMAT_G721_32 : + error = g72x_init (psf) ; + psf->sf.seekable = SF_FALSE ; + break ; + + case SF_FORMAT_G723_24 : + error = g72x_init (psf) ; + psf->sf.seekable = SF_FALSE ; + break ; + + case SF_FORMAT_G723_40 : + error = g72x_init (psf) ; + psf->sf.seekable = SF_FALSE ; + break ; + /* Lite remove end */ + + default : break ; + } ; + + return error ; +} /* au_open */ + +/*------------------------------------------------------------------------------ +*/ + +static int +au_close (SF_PRIVATE *psf) +{ + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + au_write_header (psf, SF_TRUE) ; + + return 0 ; +} /* au_close */ + +static int +au_write_header (SF_PRIVATE *psf, int calc_length) +{ sf_count_t current ; + int encoding, datalength ; + + if (psf->pipeoffset > 0) + return 0 ; + + current = psf_ftell (psf) ; + + if (calc_length) + { psf->filelength = psf_get_filelen (psf) ; + + psf->datalength = psf->filelength - psf->dataoffset ; + if (psf->dataend) + psf->datalength -= psf->filelength - psf->dataend ; + + psf->sf.frames = psf->datalength / (psf->bytewidth * psf->sf.channels) ; + } ; + + encoding = au_format_to_encoding (psf->sf.format & SF_FORMAT_SUBMASK) ; + if (! encoding) + return (psf->error = SFE_BAD_OPEN_FORMAT) ; + + /* Reset the current header length to zero. */ + psf->header [0] = 0 ; + psf->headindex = 0 ; + + /* + ** Only attempt to seek if we are not writng to a pipe. If we are + ** writing to a pipe we shouldn't be here anyway. + */ + if (psf->is_pipe == SF_FALSE) + psf_fseek (psf, 0, SEEK_SET) ; + + /* + ** AU format files allow a datalength value of -1 if the datalength + ** is not know at the time the header is written. + ** Also use this value of -1 if the datalength > 2 gigabytes. + */ + if (psf->datalength < 0 || psf->datalength > 0x7FFFFFFF) + datalength = -1 ; + else + datalength = (int) (psf->datalength & 0x7FFFFFFF) ; + + if (psf->endian == SF_ENDIAN_BIG) + { psf_binheader_writef (psf, "Em4", DOTSND_MARKER, AU_DATA_OFFSET) ; + psf_binheader_writef (psf, "E4444", datalength, encoding, psf->sf.samplerate, psf->sf.channels) ; + } + else if (psf->endian == SF_ENDIAN_LITTLE) + { psf_binheader_writef (psf, "em4", DNSDOT_MARKER, AU_DATA_OFFSET) ; + psf_binheader_writef (psf, "e4444", datalength, encoding, psf->sf.samplerate, psf->sf.channels) ; + } + else + return (psf->error = SFE_BAD_OPEN_FORMAT) ; + + /* Header construction complete so write it out. */ + psf_fwrite (psf->header, psf->headindex, 1, psf) ; + + if (psf->error) + return psf->error ; + + psf->dataoffset = psf->headindex ; + + if (current > 0) + psf_fseek (psf, current, SEEK_SET) ; + + return psf->error ; +} /* au_write_header */ + +static int +au_format_to_encoding (int format) +{ + switch (format) + { case SF_FORMAT_PCM_S8 : return AU_ENCODING_PCM_8 ; + case SF_FORMAT_PCM_16 : return AU_ENCODING_PCM_16 ; + case SF_FORMAT_PCM_24 : return AU_ENCODING_PCM_24 ; + case SF_FORMAT_PCM_32 : return AU_ENCODING_PCM_32 ; + + case SF_FORMAT_FLOAT : return AU_ENCODING_FLOAT ; + case SF_FORMAT_DOUBLE : return AU_ENCODING_DOUBLE ; + + case SF_FORMAT_ULAW : return AU_ENCODING_ULAW_8 ; + case SF_FORMAT_ALAW : return AU_ENCODING_ALAW_8 ; + + case SF_FORMAT_G721_32 : return AU_ENCODING_ADPCM_G721_32 ; + case SF_FORMAT_G723_24 : return AU_ENCODING_ADPCM_G723_24 ; + case SF_FORMAT_G723_40 : return AU_ENCODING_ADPCM_G723_40 ; + + default : break ; + } ; + return 0 ; +} /* au_format_to_encoding */ + +static int +au_read_header (SF_PRIVATE *psf) +{ AU_FMT au_fmt ; + int marker, dword ; + + memset (&au_fmt, 0, sizeof (au_fmt)) ; + psf_binheader_readf (psf, "pm", 0, &marker) ; + psf_log_printf (psf, "%M\n", marker) ; + + if (marker == DOTSND_MARKER) + { psf->endian = SF_ENDIAN_BIG ; + + psf_binheader_readf (psf, "E44444", &(au_fmt.dataoffset), &(au_fmt.datasize), + &(au_fmt.encoding), &(au_fmt.samplerate), &(au_fmt.channels)) ; + } + else if (marker == DNSDOT_MARKER) + { psf->endian = SF_ENDIAN_LITTLE ; + psf_binheader_readf (psf, "e44444", &(au_fmt.dataoffset), &(au_fmt.datasize), + &(au_fmt.encoding), &(au_fmt.samplerate), &(au_fmt.channels)) ; + } + else + return SFE_AU_NO_DOTSND ; + + psf_log_printf (psf, " Data Offset : %d\n", au_fmt.dataoffset) ; + + if (psf->fileoffset > 0 && au_fmt.datasize == -1) + { psf_log_printf (psf, " Data Size : -1\n") ; + return SFE_AU_EMBED_BAD_LEN ; + } ; + + if (psf->fileoffset > 0) + { psf->filelength = au_fmt.dataoffset + au_fmt.datasize ; + psf_log_printf (psf, " Data Size : %d\n", au_fmt.datasize) ; + } + else if (au_fmt.datasize == -1 || au_fmt.dataoffset + au_fmt.datasize == psf->filelength) + psf_log_printf (psf, " Data Size : %d\n", au_fmt.datasize) ; + else if (au_fmt.dataoffset + au_fmt.datasize < psf->filelength) + { psf->filelength = au_fmt.dataoffset + au_fmt.datasize ; + psf_log_printf (psf, " Data Size : %d\n", au_fmt.datasize) ; + } + else + { dword = psf->filelength - au_fmt.dataoffset ; + psf_log_printf (psf, " Data Size : %d (should be %d)\n", au_fmt.datasize, dword) ; + au_fmt.datasize = dword ; + } ; + + psf->dataoffset = au_fmt.dataoffset ; + psf->datalength = psf->filelength - psf->dataoffset ; + + if (psf_ftell (psf) < psf->dataoffset) + psf_binheader_readf (psf, "j", psf->dataoffset - psf_ftell (psf)) ; + + psf->sf.samplerate = au_fmt.samplerate ; + psf->sf.channels = au_fmt.channels ; + + /* Only fill in type major. */ + if (psf->endian == SF_ENDIAN_BIG) + psf->sf.format = SF_FORMAT_AU ; + else if (psf->endian == SF_ENDIAN_LITTLE) + psf->sf.format = SF_ENDIAN_LITTLE | SF_FORMAT_AU ; + + psf_log_printf (psf, " Encoding : %d => ", au_fmt.encoding) ; + + psf->sf.format = psf->sf.format & SF_FORMAT_ENDMASK ; + + switch (au_fmt.encoding) + { case AU_ENCODING_ULAW_8 : + psf->sf.format |= SF_FORMAT_AU | SF_FORMAT_ULAW ; + psf->bytewidth = 1 ; /* Before decoding */ + psf_log_printf (psf, "8-bit ISDN u-law\n") ; + break ; + + case AU_ENCODING_PCM_8 : + psf->sf.format |= SF_FORMAT_AU | SF_FORMAT_PCM_S8 ; + psf->bytewidth = 1 ; + psf_log_printf (psf, "8-bit linear PCM\n") ; + break ; + + case AU_ENCODING_PCM_16 : + psf->sf.format |= SF_FORMAT_AU | SF_FORMAT_PCM_16 ; + psf->bytewidth = 2 ; + psf_log_printf (psf, "16-bit linear PCM\n") ; + break ; + + case AU_ENCODING_PCM_24 : + psf->sf.format |= SF_FORMAT_AU | SF_FORMAT_PCM_24 ; + psf->bytewidth = 3 ; + psf_log_printf (psf, "24-bit linear PCM\n") ; + break ; + + case AU_ENCODING_PCM_32 : + psf->sf.format |= SF_FORMAT_AU | SF_FORMAT_PCM_32 ; + psf->bytewidth = 4 ; + psf_log_printf (psf, "32-bit linear PCM\n") ; + break ; + + case AU_ENCODING_FLOAT : + psf->sf.format |= SF_FORMAT_AU | SF_FORMAT_FLOAT ; + psf->bytewidth = 4 ; + psf_log_printf (psf, "32-bit float\n") ; + break ; + + case AU_ENCODING_DOUBLE : + psf->sf.format |= SF_FORMAT_AU | SF_FORMAT_DOUBLE ; + psf->bytewidth = 8 ; + psf_log_printf (psf, "64-bit double precision float\n") ; + break ; + + case AU_ENCODING_ALAW_8 : + psf->sf.format |= SF_FORMAT_AU | SF_FORMAT_ALAW ; + psf->bytewidth = 1 ; /* Before decoding */ + psf_log_printf (psf, "8-bit ISDN A-law\n") ; + break ; + + case AU_ENCODING_ADPCM_G721_32 : + psf->sf.format |= SF_FORMAT_AU | SF_FORMAT_G721_32 ; + psf->bytewidth = 0 ; + psf_log_printf (psf, "G721 32kbs ADPCM\n") ; + break ; + + case AU_ENCODING_ADPCM_G723_24 : + psf->sf.format |= SF_FORMAT_AU | SF_FORMAT_G723_24 ; + psf->bytewidth = 0 ; + psf_log_printf (psf, "G723 24kbs ADPCM\n") ; + break ; + + case AU_ENCODING_ADPCM_G723_40 : + psf->sf.format |= SF_FORMAT_AU | SF_FORMAT_G723_40 ; + psf->bytewidth = 0 ; + psf_log_printf (psf, "G723 40kbs ADPCM\n") ; + break ; + + case AU_ENCODING_ADPCM_G722 : + psf_log_printf (psf, "G722 64 kbs ADPCM (unsupported)\n") ; + break ; + + case AU_ENCODING_NEXT : + psf_log_printf (psf, "Weird NeXT encoding format (unsupported)\n") ; + break ; + + default : + psf_log_printf (psf, "Unknown!!\n") ; + break ; + } ; + + psf_log_printf (psf, " Sample Rate : %d\n", au_fmt.samplerate) ; + psf_log_printf (psf, " Channels : %d\n", au_fmt.channels) ; + + psf->blockwidth = psf->sf.channels * psf->bytewidth ; + + if (! psf->sf.frames && psf->blockwidth) + psf->sf.frames = (psf->filelength - psf->dataoffset) / psf->blockwidth ; + + return 0 ; +} /* au_read_header */ +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 31f691b1-cde9-4ed2-9469-6bca60fb9cd0 +*/ diff --git a/libs/libsndfile/src/avr.c b/libs/libsndfile/src/avr.c new file mode 100644 index 0000000000..ad02c048ac --- /dev/null +++ b/libs/libsndfile/src/avr.c @@ -0,0 +1,254 @@ +/* +** Copyright (C) 2004-2006 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" + +#define TWOBIT_MARKER (MAKE_MARKER ('2', 'B', 'I', 'T')) +#define AVR_HDR_SIZE 128 + +#define SFE_AVR_X 666 + +/* +** From: hyc@hanauma.Jpl.Nasa.Gov (Howard Chu) +** +** A lot of PD software exists to play Mac .snd files on the ST. One other +** format that seems pretty popular (used by a number of commercial packages) +** is the AVR format (from Audio Visual Research). This format has a 128 byte +** header that looks like this (its actually packed, but thats not portable): +*/ + +typedef struct +{ int marker ; /* 2BIT */ + char name [8] ; /* null-padded sample name */ + short mono ; /* 0 = mono, 0xffff = stereo */ + short rez ; /* 8 = 8 bit, 16 = 16 bit */ + short sign ; /* 0 = unsigned, 0xffff = signed */ + + short loop ; /* 0 = no loop, 0xffff = looping sample */ + short midi ; /* 0xffff = no MIDI note assigned, */ + /* 0xffXX = single key note assignment */ + /* 0xLLHH = key split, low/hi note */ + int srate ; /* sample frequency in hertz */ + int frames ; /* sample length in bytes or words (see rez) */ + int lbeg ; /* offset to start of loop in bytes or words. */ + /* set to zero if unused */ + int lend ; /* offset to end of loop in bytes or words. */ + /* set to sample length if unused */ + short res1 ; /* Reserved, MIDI keyboard split */ + short res2 ; /* Reserved, sample compression */ + short res3 ; /* Reserved */ + char ext [20] ; /* Additional filename space, used if (name[7] != 0) */ + char user [64] ; /* User defined. Typically ASCII message */ +} AVR_HEADER ; + +/*------------------------------------------------------------------------------ +** Private static functions. +*/ + +static int avr_close (SF_PRIVATE *psf) ; + +static int avr_read_header (SF_PRIVATE *psf) ; +static int avr_write_header (SF_PRIVATE *psf, int calc_length) ; + +/*------------------------------------------------------------------------------ +** Public function. +*/ + +int +avr_open (SF_PRIVATE *psf) +{ int error = 0 ; + + if (psf->mode == SFM_READ || (psf->mode == SFM_RDWR && psf->filelength > 0)) + { if ((error = avr_read_header (psf))) + return error ; + } ; + + if ((psf->sf.format & SF_FORMAT_TYPEMASK) != SF_FORMAT_AVR) + return SFE_BAD_OPEN_FORMAT ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { psf->endian = psf->sf.format & SF_FORMAT_ENDMASK ; + psf->endian = SF_ENDIAN_BIG ; + + if (avr_write_header (psf, SF_FALSE)) + return psf->error ; + + psf->write_header = avr_write_header ; + } ; + + psf->container_close = avr_close ; + + psf->blockwidth = psf->bytewidth * psf->sf.channels ; + + error = pcm_init (psf) ; + + return error ; +} /* avr_open */ + +static int +avr_read_header (SF_PRIVATE *psf) +{ AVR_HEADER hdr ; + + memset (&hdr, 0, sizeof (hdr)) ; + + psf_binheader_readf (psf, "pmb", 0, &hdr.marker, &hdr.name, sizeof (hdr.name)) ; + psf_log_printf (psf, "%M\n", hdr.marker) ; + + if (hdr.marker != TWOBIT_MARKER) + return SFE_AVR_X ; + + psf_log_printf (psf, " Name : %s\n", hdr.name) ; + + psf_binheader_readf (psf, "E22222", &hdr.mono, &hdr.rez, &hdr.sign, &hdr.loop, &hdr.midi) ; + + psf->sf.channels = (hdr.mono & 1) + 1 ; + + psf_log_printf (psf, " Channels : %d\n Bit width : %d\n Signed : %s\n", + (hdr.mono & 1) + 1, hdr.rez, hdr.sign ? "yes" : "no") ; + + switch ((hdr.rez << 16) + (hdr.sign & 1)) + { case ((8 << 16) + 0) : + psf->sf.format = SF_FORMAT_AVR | SF_FORMAT_PCM_U8 ; + psf->bytewidth = 1 ; + break ; + + case ((8 << 16) + 1) : + psf->sf.format = SF_FORMAT_AVR | SF_FORMAT_PCM_S8 ; + psf->bytewidth = 1 ; + break ; + + case ((16 << 16) + 1) : + psf->sf.format = SF_FORMAT_AVR | SF_FORMAT_PCM_16 ; + psf->bytewidth = 2 ; + break ; + + default : + psf_log_printf (psf, "Error : bad rez/sign combination.\n") ; + return SFE_AVR_X ; + } ; + + psf_binheader_readf (psf, "E4444", &hdr.srate, &hdr.frames, &hdr.lbeg, &hdr.lend) ; + + psf->sf.frames = hdr.frames ; + psf->sf.samplerate = hdr.srate ; + + psf_log_printf (psf, " Frames : %D\n", psf->sf.frames) ; + psf_log_printf (psf, " Sample rate : %d\n", psf->sf.samplerate) ; + + psf_binheader_readf (psf, "E222", &hdr.res1, &hdr.res2, &hdr.res3) ; + psf_binheader_readf (psf, "bb", hdr.ext, sizeof (hdr.ext), hdr.user, sizeof (hdr.user)) ; + + psf_log_printf (psf, " Ext : %s\n User : %s\n", hdr.ext, hdr.user) ; + + psf->endian = SF_ENDIAN_BIG ; + + psf->dataoffset = AVR_HDR_SIZE ; + psf->datalength = hdr.frames * (hdr.rez / 8) ; + + if (psf->fileoffset > 0) + psf->filelength = AVR_HDR_SIZE + psf->datalength ; + + if (psf_ftell (psf) != psf->dataoffset) + psf_binheader_readf (psf, "j", psf->dataoffset - psf_ftell (psf)) ; + + psf->blockwidth = psf->sf.channels * psf->bytewidth ; + + if (psf->sf.frames == 0 && psf->blockwidth) + psf->sf.frames = (psf->filelength - psf->dataoffset) / psf->blockwidth ; + + return 0 ; +} /* avr_read_header */ + +static int +avr_write_header (SF_PRIVATE *psf, int calc_length) +{ sf_count_t current ; + int sign ; + + if (psf->pipeoffset > 0) + return 0 ; + + current = psf_ftell (psf) ; + + if (calc_length) + { psf->filelength = psf_get_filelen (psf) ; + + psf->datalength = psf->filelength - psf->dataoffset ; + if (psf->dataend) + psf->datalength -= psf->filelength - psf->dataend ; + + psf->sf.frames = psf->datalength / (psf->bytewidth * psf->sf.channels) ; + } ; + + /* Reset the current header length to zero. */ + psf->header [0] = 0 ; + psf->headindex = 0 ; + + /* + ** Only attempt to seek if we are not writng to a pipe. If we are + ** writing to a pipe we shouldn't be here anyway. + */ + if (psf->is_pipe == SF_FALSE) + psf_fseek (psf, 0, SEEK_SET) ; + + psf_binheader_writef (psf, "Emz22", TWOBIT_MARKER, make_size_t (8), + psf->sf.channels == 2 ? 0xFFFF : 0, psf->bytewidth * 8) ; + + sign = ((psf->sf.format & SF_FORMAT_SUBMASK) == SF_FORMAT_PCM_U8) ? 0 : 0xFFFF ; + + psf_binheader_writef (psf, "E222", sign, 0, 0xFFFF) ; + psf_binheader_writef (psf, "E4444", psf->sf.samplerate, psf->sf.frames, 0, 0) ; + + psf_binheader_writef (psf, "E222zz", 0, 0, 0, make_size_t (20), make_size_t (64)) ; + + /* Header construction complete so write it out. */ + psf_fwrite (psf->header, psf->headindex, 1, psf) ; + + if (psf->error) + return psf->error ; + + psf->dataoffset = psf->headindex ; + + if (current > 0) + psf_fseek (psf, current, SEEK_SET) ; + + return psf->error ; +} /* avr_write_header */ + +static int +avr_close (SF_PRIVATE *psf) +{ + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + avr_write_header (psf, SF_TRUE) ; + + return 0 ; +} /* avr_close */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 0823d454-f39a-4a28-a776-607f1ef33b52 +*/ diff --git a/libs/libsndfile/src/broadcast.c b/libs/libsndfile/src/broadcast.c new file mode 100644 index 0000000000..e33227778d --- /dev/null +++ b/libs/libsndfile/src/broadcast.c @@ -0,0 +1,89 @@ +/* +** Copyright (C) 2006 Paul Davis +** Copyright (C) 2006 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include +#include + +#include "common.h" + +/* +** Allocate and initialize a broadcast info structure. +*/ + +SF_BROADCAST_INFO* +broadcast_info_alloc (void) +{ SF_BROADCAST_INFO* bext ; + + if ((bext = calloc (1, sizeof (SF_BROADCAST_INFO))) == NULL) + return NULL ; + + return bext ; +} /* broadcast_info_alloc */ + +int +broadcast_info_copy (SF_BROADCAST_INFO* dst, SF_BROADCAST_INFO* src) +{ memcpy (dst, src, sizeof (SF_BROADCAST_INFO)) ; + + /* Currently writing this version. */ + dst->version = 1 ; + + return SF_TRUE ; +} /* broadcast_info_copy */ + +int +broadcast_add_coding_history (SF_BROADCAST_INFO* bext, unsigned int channels, unsigned int samplerate) +{ char chnstr [16] ; + int count ; + + switch (channels) + { case 0 : + return SF_FALSE ; + + case 1 : + strncpy (chnstr, "mono", sizeof (chnstr)) ; + break ; + + case 2 : + strncpy (chnstr, "stereo", sizeof (chnstr)) ; + break ; + + default : + LSF_SNPRINTF (chnstr, sizeof (chnstr), "%uchn", channels) ; + break ; + } + + count = LSF_SNPRINTF (bext->coding_history, sizeof (bext->coding_history), "F=%u,A=PCM,M=%s,W=24,T=%s-%s", samplerate, chnstr, PACKAGE, VERSION) ; + + if (count >= SIGNED_SIZEOF (bext->coding_history)) + bext->coding_history_size = sizeof (bext->coding_history) ; + else + { count += count & 1 ; + bext->coding_history_size = count ; + } ; + + return SF_TRUE ; +} /* broadcast_add_coding_history */ + +/* +** Do not edit or modify anything in this comment block. +** The following line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 4b3b69c7-d710-4424-9da0-5048534a0beb +*/ diff --git a/libs/libsndfile/src/caf.c b/libs/libsndfile/src/caf.c new file mode 100644 index 0000000000..01f3719897 --- /dev/null +++ b/libs/libsndfile/src/caf.c @@ -0,0 +1,538 @@ +/* +** Copyright (C) 2005 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "float_cast.h" +#include "common.h" + +/*------------------------------------------------------------------------------ +** Macros to handle big/little endian issues. +*/ + +#define aac_MARKER MAKE_MARKER ('a', 'a', 'c', ' ') +#define alac_MARKER MAKE_MARKER ('a', 'l', 'a', 'c') +#define alaw_MARKER MAKE_MARKER ('a', 'l', 'a', 'w') +#define caff_MARKER MAKE_MARKER ('c', 'a', 'f', 'f') +#define chan_MARKER MAKE_MARKER ('c', 'h', 'a', 'n') +#define data_MARKER MAKE_MARKER ('d', 'a', 't', 'a') +#define desc_MARKER MAKE_MARKER ('d', 'e', 's', 'c') +#define edct_MARKER MAKE_MARKER ('e', 'd', 'c', 't') +#define free_MARKER MAKE_MARKER ('f', 'r', 'e', 'e') +#define ima4_MARKER MAKE_MARKER ('i', 'm', 'a', '4') +#define info_MARKER MAKE_MARKER ('i', 'n', 'f', 'o') +#define inst_MARKER MAKE_MARKER ('i', 'n', 's', 't') +#define kuki_MARKER MAKE_MARKER ('k', 'u', 'k', 'i') +#define lpcm_MARKER MAKE_MARKER ('l', 'p', 'c', 'm') +#define mark_MARKER MAKE_MARKER ('m', 'a', 'r', 'k') +#define midi_MARKER MAKE_MARKER ('m', 'i', 'd', 'i') +#define mp1_MARKER MAKE_MARKER ('.', 'm', 'p', '1') +#define mp2_MARKER MAKE_MARKER ('.', 'm', 'p', '2') +#define mp3_MARKER MAKE_MARKER ('.', 'm', 'p', '3') +#define ovvw_MARKER MAKE_MARKER ('o', 'v', 'v', 'w') +#define pakt_MARKER MAKE_MARKER ('p', 'a', 'k', 't') +#define peak_MARKER MAKE_MARKER ('p', 'e', 'a', 'k') +#define regn_MARKER MAKE_MARKER ('r', 'e', 'g', 'n') +#define strg_MARKER MAKE_MARKER ('s', 't', 'r', 'g') +#define umid_MARKER MAKE_MARKER ('u', 'm', 'i', 'd') +#define uuid_MARKER MAKE_MARKER ('u', 'u', 'i', 'd') +#define ulaw_MARKER MAKE_MARKER ('u', 'l', 'a', 'w') +#define MAC3_MARKER MAKE_MARKER ('M', 'A', 'C', '3') +#define MAC6_MARKER MAKE_MARKER ('M', 'A', 'C', '6') + +#define CAF_PEAK_CHUNK_SIZE(ch) (sizeof (int) + ch * (sizeof (float) + 8)) + +#define SFE_CAF_NOT_CAF 666 +#define SFE_CAF_NO_DESC 667 +#define SFE_CAF_BAD_PEAK 668 + +/*------------------------------------------------------------------------------ +** Typedefs. +*/ + +typedef struct +{ unsigned char srate [8] ; + unsigned int fmt_id ; + unsigned int fmt_flags ; + unsigned int pkt_bytes ; + unsigned int pkt_frames ; + unsigned int channels_per_frame ; + unsigned int bits_per_chan ; +} DESC_CHUNK ; + +/*------------------------------------------------------------------------------ +** Private static functions. +*/ + +static int caf_close (SF_PRIVATE *psf) ; +static int caf_read_header (SF_PRIVATE *psf) ; +static int caf_write_header (SF_PRIVATE *psf, int calc_length) ; + +/*------------------------------------------------------------------------------ +** Public function. +*/ + +int +caf_open (SF_PRIVATE *psf) +{ int subformat, format, error = 0 ; + + if (psf->mode == SFM_READ || (psf->mode == SFM_RDWR && psf->filelength > 0)) + { if ((error = caf_read_header (psf))) + return error ; + } ; + + subformat = psf->sf.format & SF_FORMAT_SUBMASK ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { if (psf->is_pipe) + return SFE_NO_PIPE_WRITE ; + + format = psf->sf.format & SF_FORMAT_TYPEMASK ; + if (format != SF_FORMAT_CAF) + return SFE_BAD_OPEN_FORMAT ; + + psf->blockwidth = psf->bytewidth * psf->sf.channels ; + + if (psf->mode != SFM_RDWR || psf->filelength < 44) + { psf->filelength = 0 ; + psf->datalength = 0 ; + psf->dataoffset = 0 ; + psf->sf.frames = 0 ; + } ; + + psf->str_flags = SF_STR_ALLOW_START ; + + /* + ** By default, add the peak chunk to floating point files. Default behaviour + ** can be switched off using sf_command (SFC_SET_PEAK_CHUNK, SF_FALSE). + */ + if (psf->mode == SFM_WRITE && (subformat == SF_FORMAT_FLOAT || subformat == SF_FORMAT_DOUBLE)) + { if ((psf->peak_info = peak_info_calloc (psf->sf.channels)) == NULL) + return SFE_MALLOC_FAILED ; + psf->peak_info->peak_loc = SF_PEAK_START ; + } ; + + if ((error = caf_write_header (psf, SF_FALSE)) != 0) + return error ; + + psf->write_header = caf_write_header ; + } ; + + psf->container_close = caf_close ; + /*psf->command = caf_command ;*/ + + switch (subformat) + { case SF_FORMAT_PCM_S8 : + case SF_FORMAT_PCM_16 : + case SF_FORMAT_PCM_24 : + case SF_FORMAT_PCM_32 : + error = pcm_init (psf) ; + break ; + + case SF_FORMAT_ULAW : + error = ulaw_init (psf) ; + break ; + + case SF_FORMAT_ALAW : + error = alaw_init (psf) ; + break ; + + /* Lite remove start */ + case SF_FORMAT_FLOAT : + error = float32_init (psf) ; + break ; + + case SF_FORMAT_DOUBLE : + error = double64_init (psf) ; + break ; + /* Lite remove end */ + + default : + return SFE_UNSUPPORTED_ENCODING ; + } ; + + return error ; +} /* caf_open */ + +static int +caf_close (SF_PRIVATE *psf) +{ + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + caf_write_header (psf, SF_TRUE) ; + + return 0 ; +} /* caf_close */ + +/*------------------------------------------------------------------------------ +*/ + +static int +decode_desc_chunk (SF_PRIVATE *psf, const DESC_CHUNK *desc) +{ int format ; + + psf->sf.channels = desc->channels_per_frame ; + + format = SF_FORMAT_CAF | (psf->endian == SF_ENDIAN_LITTLE ? SF_ENDIAN_LITTLE : 0) ; + + if (desc->fmt_id == lpcm_MARKER && desc->fmt_flags & 1) + { /* Floating point data. */ + if (desc->bits_per_chan == 32 && desc->pkt_bytes == 4 * desc->channels_per_frame) + { psf->bytewidth = 4 ; + return format | SF_FORMAT_FLOAT ; + } ; + if (desc->bits_per_chan == 64 && desc->pkt_bytes == 8 * desc->channels_per_frame) + { psf->bytewidth = 8 ; + return format | SF_FORMAT_DOUBLE ; + } ; + } ; + + if ((desc->fmt_flags & 1) != 0) + { psf_log_printf (psf, "**** Ooops, 'desc' chunk suggests float data, but other info invalid.\n") ; + return 0 ; + } ; + + if (desc->fmt_id == lpcm_MARKER) + { /* Integer data. */ + if (desc->bits_per_chan == 32 && desc->pkt_bytes == 4 * desc->channels_per_frame) + { psf->bytewidth = 4 ; + return format | SF_FORMAT_PCM_32 ; + } ; + if (desc->bits_per_chan == 24 && desc->pkt_bytes == 3 * desc->channels_per_frame) + { psf->bytewidth = 3 ; + return format | SF_FORMAT_PCM_24 ; + } ; + if (desc->bits_per_chan == 16 && desc->pkt_bytes == 2 * desc->channels_per_frame) + { psf->bytewidth = 2 ; + return format | SF_FORMAT_PCM_16 ; + } ; + if (desc->bits_per_chan == 8 && desc->pkt_bytes == 1 * desc->channels_per_frame) + { psf->bytewidth = 1 ; + return format | SF_FORMAT_PCM_S8 ; + } ; + } ; + + if (desc->fmt_id == alaw_MARKER && desc->bits_per_chan == 8) + { psf->bytewidth = 1 ; + return format | SF_FORMAT_ALAW ; + } ; + + if (desc->fmt_id == ulaw_MARKER && desc->bits_per_chan == 8) + { psf->bytewidth = 1 ; + return format | SF_FORMAT_ULAW ; + } ; + + return 0 ; +} /* decode_desc_chunk */ + +static int +caf_read_header (SF_PRIVATE *psf) +{ DESC_CHUNK desc ; + sf_count_t chunk_size ; + double srate ; + short version, flags ; + int marker, k, have_data = 0 ; + + memset (&desc, 0, sizeof (desc)) ; + + /* Set position to start of file to begin reading header. */ + psf_binheader_readf (psf, "pmE2E2", 0, &marker, &version, &flags) ; + psf_log_printf (psf, "%M\n Version : %d\n Flags : %x\n", marker, version, flags) ; + if (marker != caff_MARKER) + return SFE_CAF_NOT_CAF ; + + psf_binheader_readf (psf, "mE8b", &marker, &chunk_size, psf->u.ucbuf, 8) ; + srate = double64_be_read (psf->u.ucbuf) ; + LSF_SNPRINTF (psf->u.cbuf, sizeof (psf->u.cbuf), "%5.3f", srate) ; + psf_log_printf (psf, "%M : %D\n Sample rate : %s\n", marker, chunk_size, psf->u.cbuf) ; + if (marker != desc_MARKER) + return SFE_CAF_NO_DESC ; + + if (chunk_size < sizeof (DESC_CHUNK)) + { psf_log_printf (psf, "**** Chunk size too small. Should be > 32 bytes.\n") ; + return SFE_MALFORMED_FILE ; + } ; + + psf->sf.samplerate = lrint (srate) ; + + psf_binheader_readf (psf, "mE44444", &desc.fmt_id, &desc.fmt_flags, &desc.pkt_bytes, &desc.pkt_frames, + &desc.channels_per_frame, &desc.bits_per_chan) ; + psf_log_printf (psf, " Format id : %M\n Format flags : %x\n Bytes / packet : %u\n" + " Frames / packet : %u\n Channels / frame : %u\n Bits / channel : %u\n", + desc.fmt_id, desc.fmt_flags, desc.pkt_bytes, desc.pkt_frames, desc.channels_per_frame, desc.bits_per_chan) ; + + if (chunk_size > sizeof (DESC_CHUNK)) + psf_binheader_readf (psf, "j", (int) (chunk_size - sizeof (DESC_CHUNK))) ; + + psf->sf.channels = desc.channels_per_frame ; + + while (have_data == 0 && psf_ftell (psf) < psf->filelength - SIGNED_SIZEOF (marker)) + { psf_binheader_readf (psf, "mE8", &marker, &chunk_size) ; + + switch (marker) + { case peak_MARKER : + psf_log_printf (psf, "%M : %D\n", marker, chunk_size) ; + if (chunk_size != CAF_PEAK_CHUNK_SIZE (psf->sf.channels)) + { psf_binheader_readf (psf, "j", (int) chunk_size) ; + psf_log_printf (psf, "*** File PEAK chunk %D should be %d.\n", chunk_size, CAF_PEAK_CHUNK_SIZE (psf->sf.channels)) ; + return SFE_CAF_BAD_PEAK ; + } ; + + if ((psf->peak_info = peak_info_calloc (psf->sf.channels)) == NULL) + return SFE_MALLOC_FAILED ; + + /* read in rest of PEAK chunk. */ + psf_binheader_readf (psf, "E4", & (psf->peak_info->edit_number)) ; + psf_log_printf (psf, " edit count : %d\n", psf->peak_info->edit_number) ; + + psf_log_printf (psf, " Ch Position Value\n") ; + for (k = 0 ; k < psf->sf.channels ; k++) + { sf_count_t position ; + float value ; + + psf_binheader_readf (psf, "Ef8", &value, &position) ; + psf->peak_info->peaks [k].value = value ; + psf->peak_info->peaks [k].position = position ; + + LSF_SNPRINTF (psf->u.cbuf, sizeof (psf->u.cbuf), " %2d %-12ld %g\n", k, (long) position, value) ; + psf_log_printf (psf, psf->u.cbuf) ; + } ; + + psf->peak_info->peak_loc = SF_PEAK_START ; + break ; + + case free_MARKER : + psf_log_printf (psf, "%M : %D\n", marker, chunk_size) ; + psf_binheader_readf (psf, "j", (int) chunk_size) ; + break ; + + case data_MARKER : + psf_log_printf (psf, "%M : %D\n", marker, chunk_size) ; + psf_binheader_readf (psf, "E4", &k) ; + psf_log_printf (psf, " edit : %u\n", k) ; + have_data = 1 ; + break ; + + default : + psf_log_printf (psf, " %M : %D (skipped)\n", marker, chunk_size) ; + psf_binheader_readf (psf, "j", (int) chunk_size) ; + break ; + } ; + } ; + + if (have_data == 0) + { psf_log_printf (psf, "**** Error, could not find 'data' chunk.\n") ; + return SFE_MALFORMED_FILE ; + } ; + + psf_log_printf (psf, "End\n") ; + + psf->dataoffset = psf_ftell (psf) ; + psf->datalength = psf->filelength - psf->dataoffset ; + psf->endian = (desc.fmt_flags & 2) ? SF_ENDIAN_LITTLE : SF_ENDIAN_BIG ; + + if ((psf->sf.format = decode_desc_chunk (psf, &desc)) == 0) + return SFE_UNSUPPORTED_ENCODING ; + + if (psf->bytewidth > 0) + psf->sf.frames = psf->datalength / psf->bytewidth ; + + return 0 ; +} /* caf_read_header */ + +/*------------------------------------------------------------------------------ +*/ + +static int +caf_write_header (SF_PRIVATE *psf, int calc_length) +{ DESC_CHUNK desc ; + sf_count_t current, free_len ; + int subformat ; + + memset (&desc, 0, sizeof (desc)) ; + + current = psf_ftell (psf) ; + + if (calc_length) + { psf->filelength = psf_get_filelen (psf) ; + + psf->datalength = psf->filelength - psf->dataoffset ; + + if (psf->dataend) + psf->datalength -= psf->filelength - psf->dataend ; + + if (psf->bytewidth > 0) + psf->sf.frames = psf->datalength / (psf->bytewidth * psf->sf.channels) ; + } ; + + /* Reset the current header length to zero. */ + psf->header [0] = 0 ; + psf->headindex = 0 ; + psf_fseek (psf, 0, SEEK_SET) ; + + /* 'caff' marker, version and flags. */ + psf_binheader_writef (psf, "Em22", caff_MARKER, 1, 0) ; + + /* 'desc' marker and chunk size. */ + psf_binheader_writef (psf, "Em8", desc_MARKER, (sf_count_t) (sizeof (DESC_CHUNK))) ; + + double64_be_write (1.0 * psf->sf.samplerate, psf->u.ucbuf) ; + psf_binheader_writef (psf, "b", psf->u.ucbuf, 8) ; + + subformat = psf->sf.format & SF_FORMAT_SUBMASK ; + + psf->endian = psf->sf.format & SF_FORMAT_ENDMASK ; + + if (CPU_IS_BIG_ENDIAN && (psf->endian == 0 || psf->endian == SF_ENDIAN_CPU)) + psf->endian = SF_ENDIAN_BIG ; + else if (CPU_IS_LITTLE_ENDIAN && (psf->endian == SF_ENDIAN_LITTLE || psf->endian == SF_ENDIAN_CPU)) + psf->endian = SF_ENDIAN_LITTLE ; + + if (psf->endian == SF_ENDIAN_LITTLE) + desc.fmt_flags = 2 ; + else + psf->endian = SF_ENDIAN_BIG ; + + /* initial section (same for all, it appears) */ + switch (subformat) + { case SF_FORMAT_PCM_S8 : + desc.fmt_id = lpcm_MARKER ; + psf->bytewidth = 1 ; + desc.pkt_bytes = psf->bytewidth * psf->sf.channels ; + desc.pkt_frames = 1 ; + desc.channels_per_frame = psf->sf.channels ; + desc.bits_per_chan = 8 ; + break ; + + case SF_FORMAT_PCM_16 : + desc.fmt_id = lpcm_MARKER ; + psf->bytewidth = 2 ; + desc.pkt_bytes = psf->bytewidth * psf->sf.channels ; + desc.pkt_frames = 1 ; + desc.channels_per_frame = psf->sf.channels ; + desc.bits_per_chan = 16 ; + break ; + + case SF_FORMAT_PCM_24 : + psf->bytewidth = 3 ; + desc.pkt_bytes = psf->bytewidth * psf->sf.channels ; + desc.pkt_frames = 1 ; + desc.channels_per_frame = psf->sf.channels ; + desc.bits_per_chan = 24 ; + desc.fmt_id = lpcm_MARKER ; + break ; + + case SF_FORMAT_PCM_32 : + desc.fmt_id = lpcm_MARKER ; + psf->bytewidth = 4 ; + desc.pkt_bytes = psf->bytewidth * psf->sf.channels ; + desc.pkt_frames = 1 ; + desc.channels_per_frame = psf->sf.channels ; + desc.bits_per_chan = 32 ; + break ; + + case SF_FORMAT_FLOAT : + desc.fmt_id = lpcm_MARKER ; + desc.fmt_flags |= 1 ; + psf->bytewidth = 4 ; + desc.pkt_bytes = psf->bytewidth * psf->sf.channels ; + desc.pkt_frames = 1 ; + desc.channels_per_frame = psf->sf.channels ; + desc.bits_per_chan = 32 ; + break ; + + case SF_FORMAT_DOUBLE : + desc.fmt_id = lpcm_MARKER ; + desc.fmt_flags |= 1 ; + psf->bytewidth = 8 ; + desc.pkt_bytes = psf->bytewidth * psf->sf.channels ; + desc.pkt_frames = 1 ; + desc.channels_per_frame = psf->sf.channels ; + desc.bits_per_chan = 64 ; + break ; + + case SF_FORMAT_ALAW : + desc.fmt_id = alaw_MARKER ; + psf->bytewidth = 1 ; + desc.pkt_bytes = psf->bytewidth * psf->sf.channels ; + desc.pkt_frames = 1 ; + desc.channels_per_frame = psf->sf.channels ; + desc.bits_per_chan = 8 ; + break ; + + case SF_FORMAT_ULAW : + desc.fmt_id = ulaw_MARKER ; + psf->bytewidth = 1 ; + desc.pkt_bytes = psf->bytewidth * psf->sf.channels ; + desc.pkt_frames = 1 ; + desc.channels_per_frame = psf->sf.channels ; + desc.bits_per_chan = 8 ; + break ; + + default : + return SFE_UNIMPLEMENTED ; + } ; + + psf_binheader_writef (psf, "mE44444", desc.fmt_id, desc.fmt_flags, desc.pkt_bytes, desc.pkt_frames, desc.channels_per_frame, desc.bits_per_chan) ; + +#if 0 + if (psf->str_flags & SF_STR_LOCATE_START) + caf_write_strings (psf, SF_STR_LOCATE_START) ; +#endif + + if (psf->peak_info != NULL) + { int k ; + psf_binheader_writef (psf, "Em84", peak_MARKER, (sf_count_t) CAF_PEAK_CHUNK_SIZE (psf->sf.channels), psf->peak_info->edit_number) ; + for (k = 0 ; k < psf->sf.channels ; k++) + psf_binheader_writef (psf, "Ef8", (float) psf->peak_info->peaks [k].value, psf->peak_info->peaks [k].position) ; + } ; + + /* Add free chunk so that the actual audio data starts at a multiple 0x1000. */ + free_len = 0x1000 - psf->headindex - 16 - 12 ; + while (free_len < 0) + free_len += 0x1000 ; + psf_binheader_writef (psf, "Em8z", free_MARKER, free_len, (int) free_len) ; + + psf_binheader_writef (psf, "Em84", data_MARKER, psf->datalength, 0) ; + + psf_fwrite (psf->header, psf->headindex, 1, psf) ; + if (psf->error) + return psf->error ; + + psf->dataoffset = psf->headindex ; + if (current < psf->dataoffset) + psf_fseek (psf, psf->dataoffset, SEEK_SET) ; + else if (current > 0) + psf_fseek (psf, current, SEEK_SET) ; + + return psf->error ; +} /* caf_write_header */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 65883e65-bd3c-4618-9241-d3c02fd630bd +*/ diff --git a/libs/libsndfile/src/command.c b/libs/libsndfile/src/command.c new file mode 100644 index 0000000000..edb793f215 --- /dev/null +++ b/libs/libsndfile/src/command.c @@ -0,0 +1,367 @@ +/* +** Copyright (C) 2001-2004 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include + +#include "sndfile.h" +#include "common.h" + +static SF_FORMAT_INFO const simple_formats [] = +{ + { SF_FORMAT_AIFF | SF_FORMAT_PCM_16, + "AIFF (Apple/SGI 16 bit PCM)", "aiff" + }, + + { SF_FORMAT_AIFF | SF_FORMAT_FLOAT, + "AIFF (Apple/SGI 32 bit float)", "aifc" + }, + + { SF_FORMAT_AIFF | SF_FORMAT_PCM_S8, + "AIFF (Apple/SGI 8 bit PCM)", "aiff" + }, + + { SF_FORMAT_AU | SF_FORMAT_PCM_16, + "AU (Sun/Next 16 bit PCM)", "au" + }, + + { SF_FORMAT_AU | SF_FORMAT_ULAW, + "AU (Sun/Next 8-bit u-law)", "au" + }, + + { SF_FORMAT_CAF | SF_FORMAT_PCM_16, + "CAF (Apple 16 bit PCM)", "caf" + }, + +#ifdef HAVE_FLAC_ALL_H + { SF_FORMAT_FLAC | SF_FORMAT_PCM_16, + "FLAC 16 bit", "flac" + }, +#endif + + { SF_FORMAT_RAW | SF_FORMAT_VOX_ADPCM, + "OKI Dialogic VOX ADPCM", "vox" + }, + + { SF_FORMAT_WAV | SF_FORMAT_PCM_16, + "WAV (Microsoft 16 bit PCM)", "wav" + }, + + { SF_FORMAT_WAV | SF_FORMAT_FLOAT, + "WAV (Microsoft 32 bit float)", "wav" + }, + + { SF_FORMAT_WAV | SF_FORMAT_IMA_ADPCM, + "WAV (Microsoft 4 bit IMA ADPCM)", "wav" + }, + + { SF_FORMAT_WAV | SF_FORMAT_MS_ADPCM, + "WAV (Microsoft 4 bit MS ADPCM)", "wav" + }, + + { SF_FORMAT_WAV | SF_FORMAT_PCM_U8, + "WAV (Microsoft 8 bit PCM)", "wav" + }, + +} ; /* simple_formats */ + +int +psf_get_format_simple_count (void) +{ return (sizeof (simple_formats) / sizeof (SF_FORMAT_INFO)) ; +} /* psf_get_format_simple_count */ + +int +psf_get_format_simple (SF_FORMAT_INFO *data) +{ int indx ; + + if (data->format < 0 || data->format >= (SIGNED_SIZEOF (simple_formats) / SIGNED_SIZEOF (SF_FORMAT_INFO))) + return SFE_BAD_CONTROL_CMD ; + + indx = data->format ; + memcpy (data, &(simple_formats [indx]), SIGNED_SIZEOF (SF_FORMAT_INFO)) ; + + return 0 ; +} /* psf_get_format_simple */ + +/*============================================================================ +** Major format info. +*/ + +static SF_FORMAT_INFO const major_formats [] = +{ + { SF_FORMAT_AIFF, "AIFF (Apple/SGI)", "aiff" }, + { SF_FORMAT_AU, "AU (Sun/NeXT)", "au" }, + { SF_FORMAT_AVR, "AVR (Audio Visual Research)", "avr" }, + { SF_FORMAT_CAF, "CAF (Apple Core Audio File)", "caf" }, +#ifdef HAVE_FLAC_ALL_H + { SF_FORMAT_FLAC, "FLAC (FLAC Lossless Audio Codec)", "flac" }, +#endif + { SF_FORMAT_HTK, "HTK (HMM Tool Kit)", "htk" }, + { SF_FORMAT_SVX, "IFF (Amiga IFF/SVX8/SV16)", "iff" }, + { SF_FORMAT_MAT4, "MAT4 (GNU Octave 2.0 / Matlab 4.2)", "mat" }, + { SF_FORMAT_MAT5, "MAT5 (GNU Octave 2.1 / Matlab 5.0)", "mat" }, + { SF_FORMAT_PAF, "PAF (Ensoniq PARIS)", "paf" }, + { SF_FORMAT_PVF, "PVF (Portable Voice Format)", "pvf" }, + { SF_FORMAT_RAW, "RAW (header-less)", "raw" }, + { SF_FORMAT_SD2, "SD2 (Sound Designer II)", "sd2" }, + { SF_FORMAT_SDS, "SDS (Midi Sample Dump Standard)", "sds" }, + { SF_FORMAT_IRCAM, "SF (Berkeley/IRCAM/CARL)", "sf" }, + { SF_FORMAT_VOC, "VOC (Creative Labs)", "voc" }, + { SF_FORMAT_W64, "W64 (SoundFoundry WAVE 64)", "w64" }, + { SF_FORMAT_WAV, "WAV (Microsoft)", "wav" }, + { SF_FORMAT_NIST, "WAV (NIST Sphere)", "wav" }, + { SF_FORMAT_WAVEX, "WAVEX (Microsoft)", "wav" }, + { SF_FORMAT_XI, "XI (FastTracker 2)", "xi" }, + +} ; /* major_formats */ + +int +psf_get_format_major_count (void) +{ return (sizeof (major_formats) / sizeof (SF_FORMAT_INFO)) ; +} /* psf_get_format_major_count */ + +int +psf_get_format_major (SF_FORMAT_INFO *data) +{ int indx ; + + if (data->format < 0 || data->format >= (SIGNED_SIZEOF (major_formats) / SIGNED_SIZEOF (SF_FORMAT_INFO))) + return SFE_BAD_CONTROL_CMD ; + + indx = data->format ; + memcpy (data, &(major_formats [indx]), SIGNED_SIZEOF (SF_FORMAT_INFO)) ; + + return 0 ; +} /* psf_get_format_major */ + +/*============================================================================ +** Subtype format info. +*/ + +static SF_FORMAT_INFO subtype_formats [] = +{ + { SF_FORMAT_PCM_S8, "Signed 8 bit PCM", NULL }, + { SF_FORMAT_PCM_16, "Signed 16 bit PCM", NULL }, + { SF_FORMAT_PCM_24, "Signed 24 bit PCM", NULL }, + { SF_FORMAT_PCM_32, "Signed 32 bit PCM", NULL }, + + { SF_FORMAT_PCM_U8, "Unsigned 8 bit PCM", NULL }, + + { SF_FORMAT_FLOAT, "32 bit float", NULL }, + { SF_FORMAT_DOUBLE, "64 bit float", NULL }, + + { SF_FORMAT_ULAW, "U-Law", NULL }, + { SF_FORMAT_ALAW, "A-Law", NULL }, + { SF_FORMAT_IMA_ADPCM, "IMA ADPCM", NULL }, + { SF_FORMAT_MS_ADPCM, "Microsoft ADPCM", NULL }, + + { SF_FORMAT_GSM610, "GSM 6.10", NULL }, + + { SF_FORMAT_G721_32, "32kbs G721 ADPCM", NULL }, + { SF_FORMAT_G723_24, "24kbs G723 ADPCM", NULL }, + + { SF_FORMAT_DWVW_12, "12 bit DWVW", NULL }, + { SF_FORMAT_DWVW_16, "16 bit DWVW", NULL }, + { SF_FORMAT_DWVW_24, "24 bit DWVW", NULL }, + { SF_FORMAT_VOX_ADPCM, "VOX ADPCM", "vox" }, + + { SF_FORMAT_DPCM_16, "16 bit DPCM", NULL }, + { SF_FORMAT_DPCM_8, "8 bit DPCM", NULL } +} ; /* subtype_formats */ + +int +psf_get_format_subtype_count (void) +{ return (sizeof (subtype_formats) / sizeof (SF_FORMAT_INFO)) ; +} /* psf_get_format_subtype_count */ + +int +psf_get_format_subtype (SF_FORMAT_INFO *data) +{ int indx ; + + if (data->format < 0 || data->format >= (SIGNED_SIZEOF (subtype_formats) / SIGNED_SIZEOF (SF_FORMAT_INFO))) + return SFE_BAD_CONTROL_CMD ; + + indx = data->format ; + memcpy (data, &(subtype_formats [indx]), sizeof (SF_FORMAT_INFO)) ; + + return 0 ; +} /* psf_get_format_subtype */ + +/*============================================================================== +*/ + +int +psf_get_format_info (SF_FORMAT_INFO *data) +{ int k, format ; + + if (data->format & SF_FORMAT_TYPEMASK) + { format = data->format & SF_FORMAT_TYPEMASK ; + + for (k = 0 ; k < (SIGNED_SIZEOF (major_formats) / SIGNED_SIZEOF (SF_FORMAT_INFO)) ; k++) + { if (format == major_formats [k].format) + { memcpy (data, &(major_formats [k]), sizeof (SF_FORMAT_INFO)) ; + return 0 ; + } ; + } ; + } + else if (data->format & SF_FORMAT_SUBMASK) + { format = data->format & SF_FORMAT_SUBMASK ; + + for (k = 0 ; k < (SIGNED_SIZEOF (subtype_formats) / SIGNED_SIZEOF (SF_FORMAT_INFO)) ; k++) + { if (format == subtype_formats [k].format) + { memcpy (data, &(subtype_formats [k]), sizeof (SF_FORMAT_INFO)) ; + return 0 ; + } ; + } ; + } ; + + memset (data, 0, sizeof (SF_FORMAT_INFO)) ; + + return SFE_BAD_CONTROL_CMD ; +} /* psf_get_format_info */ + +/*============================================================================== +*/ + +double +psf_calc_signal_max (SF_PRIVATE *psf, int normalize) +{ sf_count_t position ; + double max_val, temp, *data ; + int k, len, readcount, save_state ; + + /* If the file is not seekable, there is nothing we can do. */ + if (! psf->sf.seekable) + { psf->error = SFE_NOT_SEEKABLE ; + return 0.0 ; + } ; + + if (! psf->read_double) + { psf->error = SFE_UNIMPLEMENTED ; + return 0.0 ; + } ; + + save_state = sf_command ((SNDFILE*) psf, SFC_GET_NORM_DOUBLE, NULL, 0) ; + sf_command ((SNDFILE*) psf, SFC_SET_NORM_DOUBLE, NULL, normalize) ; + + /* Brute force. Read the whole file and find the biggest sample. */ + /* Get current position in file */ + position = sf_seek ((SNDFILE*) psf, 0, SEEK_CUR) ; + /* Go to start of file. */ + sf_seek ((SNDFILE*) psf, 0, SEEK_SET) ; + + data = psf->u.dbuf ; + len = ARRAY_LEN (psf->u.dbuf) ; + + for (readcount = 1, max_val = 0.0 ; readcount > 0 ; /* nothing */) + { readcount = sf_read_double ((SNDFILE*) psf, data, len) ; + for (k = 0 ; k < readcount ; k++) + { temp = fabs (data [k]) ; + max_val = temp > max_val ? temp : max_val ; + } ; + } ; + + /* Return to SNDFILE to original state. */ + sf_seek ((SNDFILE*) psf, position, SEEK_SET) ; + sf_command ((SNDFILE*) psf, SFC_SET_NORM_DOUBLE, NULL, save_state) ; + + return max_val ; +} /* psf_calc_signal_max */ + +int +psf_calc_max_all_channels (SF_PRIVATE *psf, double *peaks, int normalize) +{ sf_count_t position ; + double temp, *data ; + int k, len, readcount, save_state ; + int chan ; + + /* If the file is not seekable, there is nothing we can do. */ + if (! psf->sf.seekable) + return (psf->error = SFE_NOT_SEEKABLE) ; + + if (! psf->read_double) + return (psf->error = SFE_UNIMPLEMENTED) ; + + save_state = sf_command ((SNDFILE*) psf, SFC_GET_NORM_DOUBLE, NULL, 0) ; + sf_command ((SNDFILE*) psf, SFC_SET_NORM_DOUBLE, NULL, normalize) ; + + memset (peaks, 0, sizeof (double) * psf->sf.channels) ; + + /* Brute force. Read the whole file and find the biggest sample for each channel. */ + position = sf_seek ((SNDFILE*) psf, 0, SEEK_CUR) ; /* Get current position in file */ + sf_seek ((SNDFILE*) psf, 0, SEEK_SET) ; /* Go to start of file. */ + + len = ARRAY_LEN (psf->u.dbuf) ; + + data = psf->u.dbuf ; + + chan = 0 ; + readcount = len ; + while (readcount > 0) + { readcount = sf_read_double ((SNDFILE*) psf, data, len) ; + for (k = 0 ; k < readcount ; k++) + { temp = fabs (data [k]) ; + peaks [chan] = temp > peaks [chan] ? temp : peaks [chan] ; + chan = (chan + 1) % psf->sf.channels ; + } ; + } ; + + sf_seek ((SNDFILE*) psf, position, SEEK_SET) ; /* Return to original position. */ + + sf_command ((SNDFILE*) psf, SFC_SET_NORM_DOUBLE, NULL, save_state) ; + + return 0 ; +} /* psf_calc_max_all_channels */ + +int +psf_get_signal_max (SF_PRIVATE *psf, double *peak) +{ int k ; + + if (psf->peak_info == NULL) + return SF_FALSE ; + + peak [0] = psf->peak_info->peaks [0].value ; + + for (k = 1 ; k < psf->sf.channels ; k++) + peak [0] = SF_MAX (peak [0], psf->peak_info->peaks [k].value) ; + + return SF_TRUE ; +} /* psf_get_signal_max */ + +int +psf_get_max_all_channels (SF_PRIVATE *psf, double *peaks) +{ int k ; + + if (psf->peak_info == NULL) + return SF_FALSE ; + + for (k = 0 ; k < psf->sf.channels ; k++) + peaks [k] = psf->peak_info->peaks [k].value ; + + return SF_TRUE ; +} /* psf_get_max_all_channels */ + + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 0aae0d9d-ab2b-4d70-ade3-47a534666f8e +*/ diff --git a/libs/libsndfile/src/common.c b/libs/libsndfile/src/common.c new file mode 100644 index 0000000000..fa0f4f7b62 --- /dev/null +++ b/libs/libsndfile/src/common.c @@ -0,0 +1,1290 @@ +/* +** Copyright (C) 1999-2006 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include +#include +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" + +/*----------------------------------------------------------------------------------------------- +** psf_log_printf allows libsndfile internal functions to print to an internal logbuffer which +** can later be displayed. +** The format specifiers are as for printf but without the field width and other modifiers. +** Printing is performed to the logbuffer char array of the SF_PRIVATE struct. +** Printing is done in such a way as to guarantee that the log never overflows the end of the +** logbuffer array. +*/ + +static inline void +log_putchar (SF_PRIVATE *psf, char ch) +{ if (psf->logindex < SIGNED_SIZEOF (psf->logbuffer) - 1) + { psf->logbuffer [psf->logindex++] = ch ; + psf->logbuffer [psf->logindex] = 0 ; + } ; + return ; +} /* log_putchar */ + +void +psf_log_printf (SF_PRIVATE *psf, const char *format, ...) +{ va_list ap ; + unsigned int u ; + int d, tens, shift, width, width_specifier, left_align ; + char c, *strptr, istr [5], lead_char, sign_char ; + + va_start (ap, format) ; + + while ((c = *format++)) + { if (c != '%') + { log_putchar (psf, c) ; + continue ; + } ; + + if (format [0] == '%') /* Handle %% */ + { log_putchar (psf, '%') ; + format ++ ; + continue ; + } ; + + sign_char = 0 ; + left_align = SF_FALSE ; + while (1) + { switch (format [0]) + { case ' ' : + case '+' : + sign_char = format [0] ; + format ++ ; + continue ; + + case '-' : + left_align = SF_TRUE ; + format ++ ; + continue ; + + default : break ; + } ; + + break ; + } ; + + if (format [0] == 0) + break ; + + lead_char = ' ' ; + if (format [0] == '0') + lead_char = '0' ; + + width_specifier = 0 ; + while ((c = *format++) && isdigit (c)) + width_specifier = width_specifier * 10 + (c - '0') ; + + switch (c) + { case 0 : /* NULL character. */ + va_end (ap) ; + return ; + + case 's': /* string */ + strptr = va_arg (ap, char *) ; + if (strptr == NULL) + break ; + width_specifier -= strlen (strptr) ; + if (left_align == SF_FALSE) + while (width_specifier -- > 0) + log_putchar (psf, ' ') ; + while (*strptr) + log_putchar (psf, *strptr++) ; + while (width_specifier -- > 0) + log_putchar (psf, ' ') ; + break ; + + case 'd': /* int */ + d = va_arg (ap, int) ; + + if (d < 0) + { d = -d ; + sign_char = '-' ; + if (lead_char != '0' && left_align == SF_FALSE) + width_specifier -- ; + } ; + + tens = 1 ; + width = 1 ; + while (d / tens >= 10) + { tens *= 10 ; + width ++ ; + } ; + + width_specifier -= width ; + + if (sign_char == ' ') + { log_putchar (psf, ' ') ; + width_specifier -- ; + } ; + + if (left_align == SF_FALSE && lead_char != '0') + { if (sign_char == '+') + width_specifier -- ; + + while (width_specifier -- > 0) + log_putchar (psf, lead_char) ; + } ; + + if (sign_char == '+' || sign_char == '-') + { log_putchar (psf, sign_char) ; + width_specifier -- ; + } ; + + if (left_align == SF_FALSE) + while (width_specifier -- > 0) + log_putchar (psf, lead_char) ; + + while (tens > 0) + { log_putchar (psf, '0' + d / tens) ; + d %= tens ; + tens /= 10 ; + } ; + + while (width_specifier -- > 0) + log_putchar (psf, lead_char) ; + break ; + + case 'D': /* sf_count_t */ + { sf_count_t D, Tens ; + + D = va_arg (ap, sf_count_t) ; + + if (D == 0) + { while (-- width_specifier > 0) + log_putchar (psf, lead_char) ; + log_putchar (psf, '0') ; + break ; + } + if (D < 0) + { log_putchar (psf, '-') ; + D = -D ; + } ; + Tens = 1 ; + width = 1 ; + while (D / Tens >= 10) + { Tens *= 10 ; + width ++ ; + } ; + + while (width_specifier > width) + { log_putchar (psf, lead_char) ; + width_specifier-- ; + } ; + + while (Tens > 0) + { log_putchar (psf, '0' + D / Tens) ; + D %= Tens ; + Tens /= 10 ; + } ; + } ; + break ; + + case 'u': /* unsigned int */ + u = va_arg (ap, unsigned int) ; + + tens = 1 ; + width = 1 ; + while (u / tens >= 10) + { tens *= 10 ; + width ++ ; + } ; + + width_specifier -= width ; + + if (sign_char == ' ') + { log_putchar (psf, ' ') ; + width_specifier -- ; + } ; + + if (left_align == SF_FALSE && lead_char != '0') + { if (sign_char == '+') + width_specifier -- ; + + while (width_specifier -- > 0) + log_putchar (psf, lead_char) ; + } ; + + if (sign_char == '+' || sign_char == '-') + { log_putchar (psf, sign_char) ; + width_specifier -- ; + } ; + + if (left_align == SF_FALSE) + while (width_specifier -- > 0) + log_putchar (psf, lead_char) ; + + while (tens > 0) + { log_putchar (psf, '0' + u / tens) ; + u %= tens ; + tens /= 10 ; + } ; + + while (width_specifier -- > 0) + log_putchar (psf, lead_char) ; + break ; + + case 'c': /* char */ + c = va_arg (ap, int) & 0xFF ; + log_putchar (psf, c) ; + break ; + + case 'x': /* hex */ + case 'X': /* hex */ + d = va_arg (ap, int) ; + + if (d == 0) + { while (--width_specifier > 0) + log_putchar (psf, lead_char) ; + log_putchar (psf, '0') ; + break ; + } ; + shift = 28 ; + width = (width_specifier < 8) ? 8 : width_specifier ; + while (! ((0xF << shift) & d)) + { shift -= 4 ; + width -- ; + } ; + + while (width > 0 && width_specifier > width) + { log_putchar (psf, lead_char) ; + width_specifier-- ; + } ; + + while (shift >= 0) + { c = (d >> shift) & 0xF ; + log_putchar (psf, (c > 9) ? c + 'A' - 10 : c + '0') ; + shift -= 4 ; + } ; + break ; + + case 'M': /* int2str */ + d = va_arg (ap, int) ; + if (CPU_IS_LITTLE_ENDIAN) + { istr [0] = d & 0xFF ; + istr [1] = (d >> 8) & 0xFF ; + istr [2] = (d >> 16) & 0xFF ; + istr [3] = (d >> 24) & 0xFF ; + } + else + { istr [3] = d & 0xFF ; + istr [2] = (d >> 8) & 0xFF ; + istr [1] = (d >> 16) & 0xFF ; + istr [0] = (d >> 24) & 0xFF ; + } ; + istr [4] = 0 ; + strptr = istr ; + while (*strptr) + { c = *strptr++ ; + log_putchar (psf, c) ; + } ; + break ; + + default : + log_putchar (psf, '*') ; + log_putchar (psf, c) ; + log_putchar (psf, '*') ; + break ; + } /* switch */ + } /* while */ + + va_end (ap) ; + return ; +} /* psf_log_printf */ + +#ifndef PSF_LOG_PRINTF_ONLY +/*----------------------------------------------------------------------------------------------- +** ASCII header printf functions. +** Some formats (ie NIST) use ascii text in their headers. +** Format specifiers are the same as the standard printf specifiers (uses vsnprintf). +** If this generates a compile error on any system, the author should be notified +** so an alternative vsnprintf can be provided. +*/ + +void +psf_asciiheader_printf (SF_PRIVATE *psf, const char *format, ...) +{ va_list argptr ; + int maxlen ; + char *start ; + + maxlen = strlen ((char*) psf->header) ; + start = ((char*) psf->header) + maxlen ; + maxlen = sizeof (psf->header) - maxlen ; + + va_start (argptr, format) ; + LSF_VSNPRINTF (start, maxlen, format, argptr) ; + va_end (argptr) ; + + /* Make sure the string is properly terminated. */ + start [maxlen - 1] = 0 ; + + psf->headindex = strlen ((char*) psf->header) ; + + return ; +} /* psf_asciiheader_printf */ + +/*----------------------------------------------------------------------------------------------- +** Binary header writing functions. Returns number of bytes written. +** +** Format specifiers for psf_binheader_writef are as follows +** m - marker - four bytes - no endian manipulation +** +** e - all following numerical values will be little endian +** E - all following numerical values will be big endian +** +** t - all following O types will be truncated to 4 bytes +** T - switch off truncation of all following O types +** +** 1 - single byte value +** 2 - two byte value +** 3 - three byte value +** 4 - four byte value +** 8 - eight byte value (sometimes written as 4 bytes) +** +** s - string preceded by a four byte length +** S - string including null terminator +** f - floating point data +** d - double precision floating point data +** h - 16 binary bytes value +** +** b - binary data (see below) +** z - zero bytes (ses below) +** j - jump forwards or backwards +** +** To write a word followed by an int (both little endian) use: +** psf_binheader_writef ("e24", wordval, longval) ; +** +** To write binary data use: +** psf_binheader_writef ("b", &bindata, sizeof (bindata)) ; +** +** To write N zero bytes use: +** NOTE: due to platform issues (ie x86-64) you should cast the +** argument to size_t or ensure the variable type is size_t. +** psf_binheader_writef ("z", N) ; +*/ + +/* These macros may seem a bit messy but do prevent problems with processors which +** seg. fault when asked to write an int or short to a non-int/short aligned address. +*/ + +static inline void +header_put_byte (SF_PRIVATE *psf, char x) +{ if (psf->headindex < SIGNED_SIZEOF (psf->header) - 1) + psf->header [psf->headindex++] = x ; +} /* header_put_byte */ + +#if (CPU_IS_BIG_ENDIAN == 1) +static inline void +header_put_marker (SF_PRIVATE *psf, int x) +{ if (psf->headindex < SIGNED_SIZEOF (psf->header) - 4) + { psf->header [psf->headindex++] = (x >> 24) ; + psf->header [psf->headindex++] = (x >> 16) ; + psf->header [psf->headindex++] = (x >> 8) ; + psf->header [psf->headindex++] = x ; + } ; +} /* header_put_marker */ + +#elif (CPU_IS_LITTLE_ENDIAN == 1) +static inline void +header_put_marker (SF_PRIVATE *psf, int x) +{ if (psf->headindex < SIGNED_SIZEOF (psf->header) - 4) + { psf->header [psf->headindex++] = x ; + psf->header [psf->headindex++] = (x >> 8) ; + psf->header [psf->headindex++] = (x >> 16) ; + psf->header [psf->headindex++] = (x >> 24) ; + } ; +} /* header_put_marker */ + +#else +# error "Cannot determine endian-ness of processor." +#endif + + +static inline void +header_put_be_short (SF_PRIVATE *psf, int x) +{ if (psf->headindex < SIGNED_SIZEOF (psf->header) - 2) + { psf->header [psf->headindex++] = (x >> 8) ; + psf->header [psf->headindex++] = x ; + } ; +} /* header_put_be_short */ + +static inline void +header_put_le_short (SF_PRIVATE *psf, int x) +{ if (psf->headindex < SIGNED_SIZEOF (psf->header) - 2) + { psf->header [psf->headindex++] = x ; + psf->header [psf->headindex++] = (x >> 8) ; + } ; +} /* header_put_le_short */ + +static inline void +header_put_be_3byte (SF_PRIVATE *psf, int x) +{ if (psf->headindex < SIGNED_SIZEOF (psf->header) - 3) + { psf->header [psf->headindex++] = (x >> 16) ; + psf->header [psf->headindex++] = (x >> 8) ; + psf->header [psf->headindex++] = x ; + } ; +} /* header_put_be_3byte */ + +static inline void +header_put_le_3byte (SF_PRIVATE *psf, int x) +{ if (psf->headindex < SIGNED_SIZEOF (psf->header) - 3) + { psf->header [psf->headindex++] = x ; + psf->header [psf->headindex++] = (x >> 8) ; + psf->header [psf->headindex++] = (x >> 16) ; + } ; +} /* header_put_le_3byte */ + +static inline void +header_put_be_int (SF_PRIVATE *psf, int x) +{ if (psf->headindex < SIGNED_SIZEOF (psf->header) - 4) + { psf->header [psf->headindex++] = (x >> 24) ; + psf->header [psf->headindex++] = (x >> 16) ; + psf->header [psf->headindex++] = (x >> 8) ; + psf->header [psf->headindex++] = x ; + } ; +} /* header_put_be_int */ + +static inline void +header_put_le_int (SF_PRIVATE *psf, int x) +{ if (psf->headindex < SIGNED_SIZEOF (psf->header) - 4) + { psf->header [psf->headindex++] = x ; + psf->header [psf->headindex++] = (x >> 8) ; + psf->header [psf->headindex++] = (x >> 16) ; + psf->header [psf->headindex++] = (x >> 24) ; + } ; +} /* header_put_le_int */ + +#if (SIZEOF_SF_COUNT_T == 4) + +static inline void +header_put_be_8byte (SF_PRIVATE *psf, sf_count_t x) +{ if (psf->headindex < SIGNED_SIZEOF (psf->header) - 8) + { psf->header [psf->headindex++] = 0 ; + psf->header [psf->headindex++] = 0 ; + psf->header [psf->headindex++] = 0 ; + psf->header [psf->headindex++] = 0 ; + psf->header [psf->headindex++] = (x >> 24) ; + psf->header [psf->headindex++] = (x >> 16) ; + psf->header [psf->headindex++] = (x >> 8) ; + psf->header [psf->headindex++] = x ; + } ; +} /* header_put_be_8byte */ + +static inline void +header_put_le_8byte (SF_PRIVATE *psf, sf_count_t x) +{ if (psf->headindex < SIGNED_SIZEOF (psf->header) - 8) + { psf->header [psf->headindex++] = x ; + psf->header [psf->headindex++] = (x >> 8) ; + psf->header [psf->headindex++] = (x >> 16) ; + psf->header [psf->headindex++] = (x >> 24) ; + psf->header [psf->headindex++] = 0 ; + psf->header [psf->headindex++] = 0 ; + psf->header [psf->headindex++] = 0 ; + psf->header [psf->headindex++] = 0 ; + } ; +} /* header_put_le_8byte */ + +#elif (SIZEOF_SF_COUNT_T == 8) + +static inline void +header_put_be_8byte (SF_PRIVATE *psf, sf_count_t x) +{ if (psf->headindex < SIGNED_SIZEOF (psf->header) - 8) + { psf->header [psf->headindex++] = (x >> 56) ; + psf->header [psf->headindex++] = (x >> 48) ; + psf->header [psf->headindex++] = (x >> 40) ; + psf->header [psf->headindex++] = (x >> 32) ; + psf->header [psf->headindex++] = (x >> 24) ; + psf->header [psf->headindex++] = (x >> 16) ; + psf->header [psf->headindex++] = (x >> 8) ; + psf->header [psf->headindex++] = x ; + } ; +} /* header_put_be_8byte */ + +static inline void +header_put_le_8byte (SF_PRIVATE *psf, sf_count_t x) +{ if (psf->headindex < SIGNED_SIZEOF (psf->header) - 8) + { psf->header [psf->headindex++] = x ; + psf->header [psf->headindex++] = (x >> 8) ; + psf->header [psf->headindex++] = (x >> 16) ; + psf->header [psf->headindex++] = (x >> 24) ; + psf->header [psf->headindex++] = (x >> 32) ; + psf->header [psf->headindex++] = (x >> 40) ; + psf->header [psf->headindex++] = (x >> 48) ; + psf->header [psf->headindex++] = (x >> 56) ; + } ; +} /* header_put_le_8byte */ + +#else +#error "SIZEOF_SF_COUNT_T is not defined." +#endif + +int +psf_binheader_writef (SF_PRIVATE *psf, const char *format, ...) +{ va_list argptr ; + sf_count_t countdata ; + unsigned long longdata ; + unsigned int data ; + float floatdata ; + double doubledata ; + void *bindata ; + size_t size ; + char c, *strptr ; + int count = 0, trunc_8to4 ; + + trunc_8to4 = SF_FALSE ; + + va_start (argptr, format) ; + + while ((c = *format++)) + { switch (c) + { case ' ' : /* Do nothing. Just used to space out format string. */ + break ; + + case 'e' : /* All conversions are now from LE to host. */ + psf->rwf_endian = SF_ENDIAN_LITTLE ; + break ; + + case 'E' : /* All conversions are now from BE to host. */ + psf->rwf_endian = SF_ENDIAN_BIG ; + break ; + + case 't' : /* All 8 byte values now get written as 4 bytes. */ + trunc_8to4 = SF_TRUE ; + break ; + + case 'T' : /* All 8 byte values now get written as 8 bytes. */ + trunc_8to4 = SF_FALSE ; + break ; + + case 'm' : + data = va_arg (argptr, unsigned int) ; + header_put_marker (psf, data) ; + count += 4 ; + break ; + + case '1' : + data = va_arg (argptr, unsigned int) ; + header_put_byte (psf, data) ; + count += 1 ; + break ; + + case '2' : + data = va_arg (argptr, unsigned int) ; + if (psf->rwf_endian == SF_ENDIAN_BIG) + { header_put_be_short (psf, data) ; + } + else + { header_put_le_short (psf, data) ; + } ; + count += 2 ; + break ; + + case '3' : /* tribyte */ + data = va_arg (argptr, unsigned int) ; + if (psf->rwf_endian == SF_ENDIAN_BIG) + { header_put_be_3byte (psf, data) ; + } + else + { header_put_le_3byte (psf, data) ; + } ; + count += 3 ; + break ; + + case '4' : + data = va_arg (argptr, unsigned int) ; + if (psf->rwf_endian == SF_ENDIAN_BIG) + { header_put_be_int (psf, data) ; + } + else + { header_put_le_int (psf, data) ; + } ; + count += 4 ; + break ; + + case '8' : + countdata = va_arg (argptr, sf_count_t) ; + if (psf->rwf_endian == SF_ENDIAN_BIG && trunc_8to4 == SF_FALSE) + { header_put_be_8byte (psf, countdata) ; + count += 8 ; + } + else if (psf->rwf_endian == SF_ENDIAN_LITTLE && trunc_8to4 == SF_FALSE) + { header_put_le_8byte (psf, countdata) ; + count += 8 ; + } + else if (psf->rwf_endian == SF_ENDIAN_BIG && trunc_8to4 == SF_TRUE) + { longdata = countdata & 0xFFFFFFFF ; + header_put_be_int (psf, longdata) ; + count += 4 ; + } + else if (psf->rwf_endian == SF_ENDIAN_LITTLE && trunc_8to4 == SF_TRUE) + { longdata = countdata & 0xFFFFFFFF ; + header_put_le_int (psf, longdata) ; + count += 4 ; + } + break ; + + case 'f' : + /* Floats are passed as doubles. Is this always true? */ + floatdata = (float) va_arg (argptr, double) ; + if (psf->rwf_endian == SF_ENDIAN_BIG) + float32_be_write (floatdata, psf->header + psf->headindex) ; + else + float32_le_write (floatdata, psf->header + psf->headindex) ; + psf->headindex += 4 ; + count += 4 ; + break ; + + case 'd' : + doubledata = va_arg (argptr, double) ; + if (psf->rwf_endian == SF_ENDIAN_BIG) + double64_be_write (doubledata, psf->header + psf->headindex) ; + else + double64_le_write (doubledata, psf->header + psf->headindex) ; + psf->headindex += 8 ; + count += 8 ; + break ; + + case 's' : + /* Write a C string (guaranteed to have a zero terminator). */ + strptr = va_arg (argptr, char *) ; + size = strlen (strptr) + 1 ; + size += (size & 1) ; + if (psf->rwf_endian == SF_ENDIAN_BIG) + header_put_be_int (psf, size) ; + else + header_put_le_int (psf, size) ; + memcpy (&(psf->header [psf->headindex]), strptr, size) ; + psf->headindex += size ; + psf->header [psf->headindex - 1] = 0 ; + count += 4 + size ; + break ; + + case 'S' : + /* + ** Write an AIFF style string (no zero terminator but possibly + ** an extra pad byte if the string length is odd). + */ + strptr = va_arg (argptr, char *) ; + size = strlen (strptr) ; + if (psf->rwf_endian == SF_ENDIAN_BIG) + header_put_be_int (psf, size) ; + else + header_put_le_int (psf, size) ; + memcpy (&(psf->header [psf->headindex]), strptr, size + 1) ; + size += (size & 1) ; + psf->headindex += size ; + psf->header [psf->headindex] = 0 ; + count += 4 + size ; + break ; + + case 'b' : + bindata = va_arg (argptr, void *) ; + size = va_arg (argptr, size_t) ; + memcpy (&(psf->header [psf->headindex]), bindata, size) ; + psf->headindex += size ; + count += size ; + break ; + + case 'z' : + size = va_arg (argptr, size_t) ; + count += size ; + while (size) + { psf->header [psf->headindex] = 0 ; + psf->headindex ++ ; + size -- ; + } ; + break ; + + case 'h' : + bindata = va_arg (argptr, void *) ; + memcpy (&(psf->header [psf->headindex]), bindata, 16) ; + psf->headindex += 16 ; + count += 16 ; + break ; + + case 'j' : + size = va_arg (argptr, size_t) ; + psf->headindex += size ; + count = size ; + break ; + + default : + psf_log_printf (psf, "*** Invalid format specifier `%c'\n", c) ; + psf->error = SFE_INTERNAL ; + break ; + } ; + } ; + + va_end (argptr) ; + return count ; +} /* psf_binheader_writef */ + +/*----------------------------------------------------------------------------------------------- +** Binary header reading functions. Returns number of bytes read. +** +** Format specifiers are the same as for header write function above with the following +** additions: +** +** p - jump a given number of position from start of file. +** +** If format is NULL, psf_binheader_readf returns the current offset. +*/ + +#if (CPU_IS_BIG_ENDIAN == 1) +#define GET_MARKER(ptr) ( ((ptr) [0] << 24) | ((ptr) [1] << 16) | \ + ((ptr) [2] << 8) | ((ptr) [3]) ) + +#elif (CPU_IS_LITTLE_ENDIAN == 1) +#define GET_MARKER(ptr) ( ((ptr) [0]) | ((ptr) [1] << 8) | \ + ((ptr) [2] << 16) | ((ptr) [3] << 24) ) + +#else +# error "Cannot determine endian-ness of processor." +#endif + +#define GET_LE_SHORT(ptr) ( ((ptr) [1] << 8) | ((ptr) [0]) ) +#define GET_BE_SHORT(ptr) ( ((ptr) [0] << 8) | ((ptr) [1]) ) + +#define GET_LE_3BYTE(ptr) ( ((ptr) [2] << 16) | ((ptr) [1] << 8) | ((ptr) [0]) ) +#define GET_BE_3BYTE(ptr) ( ((ptr) [0] << 16) | ((ptr) [1] << 8) | ((ptr) [2]) ) + +#define GET_LE_INT(ptr) ( ((ptr) [3] << 24) | ((ptr) [2] << 16) | \ + ((ptr) [1] << 8) | ((ptr) [0]) ) + +#define GET_BE_INT(ptr) ( ((ptr) [0] << 24) | ((ptr) [1] << 16) | \ + ((ptr) [2] << 8) | ((ptr) [3]) ) + +#if (SIZEOF_LONG == 4) +#define GET_LE_8BYTE(ptr) ( ((ptr) [3] << 24) | ((ptr) [2] << 16) | \ + ((ptr) [1] << 8) | ((ptr) [0]) ) + +#define GET_BE_8BYTE(ptr) ( ((ptr) [4] << 24) | ((ptr) [5] << 16) | \ + ((ptr) [6] << 8) | ((ptr) [7]) ) +#else +#define GET_LE_8BYTE(ptr) ( (((ptr) [7] * 1L) << 56) | (((ptr) [6] * 1L) << 48) | \ + (((ptr) [5] * 1L) << 40) | (((ptr) [4] * 1L) << 32) | \ + (((ptr) [3] * 1L) << 24) | (((ptr) [2] * 1L) << 16) | \ + (((ptr) [1] * 1L) << 8 ) | ((ptr) [0])) + +#define GET_BE_8BYTE(ptr) ( (((ptr) [0] * 1L) << 56) | (((ptr) [1] * 1L) << 48) | \ + (((ptr) [2] * 1L) << 40) | (((ptr) [3] * 1L) << 32) | \ + (((ptr) [4] * 1L) << 24) | (((ptr) [5] * 1L) << 16) | \ + (((ptr) [6] * 1L) << 8 ) | ((ptr) [7])) + +#endif + +static int +header_read (SF_PRIVATE *psf, void *ptr, int bytes) +{ int count = 0 ; + + if (psf->headindex >= SIGNED_SIZEOF (psf->header)) + { memset (ptr, 0, SIGNED_SIZEOF (psf->header) - psf->headindex) ; + + /* This is the best that we can do. */ + psf_fseek (psf, bytes, SEEK_CUR) ; + return bytes ; + } ; + + if (psf->headindex + bytes > SIGNED_SIZEOF (psf->header)) + { int most ; + + most = SIGNED_SIZEOF (psf->header) - psf->headindex ; + psf_fread (psf->header + psf->headend, 1, most, psf) ; + memset (ptr + most, 0, bytes - most) ; + + psf_fseek (psf, bytes - most, SEEK_CUR) ; + return bytes ; + } ; + + if (psf->headindex + bytes > psf->headend) + { count = psf_fread (psf->header + psf->headend, 1, bytes - (psf->headend - psf->headindex), psf) ; + if (count != bytes - (int) (psf->headend - psf->headindex)) + { psf_log_printf (psf, "Error : psf_fread returned short count.\n") ; + return 0 ; + } ; + psf->headend += count ; + } ; + + memcpy (ptr, psf->header + psf->headindex, bytes) ; + psf->headindex += bytes ; + + return bytes ; +} /* header_read */ + +static void +header_seek (SF_PRIVATE *psf, sf_count_t position, int whence) +{ + + switch (whence) + { case SEEK_SET : + if (position > SIGNED_SIZEOF (psf->header)) + { /* Too much header to cache so just seek instead. */ + psf_fseek (psf, position, whence) ; + return ; + } ; + if (position > psf->headend) + psf->headend += psf_fread (psf->header + psf->headend, 1, position - psf->headend, psf) ; + psf->headindex = position ; + break ; + + case SEEK_CUR : + if (psf->headindex + position < 0) + break ; + + if (psf->headindex >= SIGNED_SIZEOF (psf->header)) + { psf_fseek (psf, position, whence) ; + return ; + } ; + + if (psf->headindex + position <= psf->headend) + { psf->headindex += position ; + break ; + } ; + + if (psf->headindex + position > SIGNED_SIZEOF (psf->header)) + { /* Need to jump this without caching it. */ + psf->headindex = psf->headend ; + psf_fseek (psf, position, SEEK_CUR) ; + break ; + } ; + + psf->headend += psf_fread (psf->header + psf->headend, 1, position - (psf->headend - psf->headindex), psf) ; + psf->headindex = psf->headend ; + break ; + + case SEEK_END : + default : + psf_log_printf (psf, "Bad whence param in header_seek().\n") ; + break ; + } ; + + return ; +} /* header_seek */ + +static int +header_gets (SF_PRIVATE *psf, char *ptr, int bufsize) +{ + int k ; + + for (k = 0 ; k < bufsize - 1 ; k++) + { if (psf->headindex < psf->headend) + { ptr [k] = psf->header [psf->headindex] ; + psf->headindex ++ ; + } + else + { psf->headend += psf_fread (psf->header + psf->headend, 1, 1, psf) ; + ptr [k] = psf->header [psf->headindex] ; + psf->headindex = psf->headend ; + } ; + + if (ptr [k] == '\n') + break ; + } ; + + ptr [k] = 0 ; + + return k ; +} /* header_gets */ + +int +psf_binheader_readf (SF_PRIVATE *psf, char const *format, ...) +{ va_list argptr ; + sf_count_t *countptr, countdata ; + unsigned char *ucptr, sixteen_bytes [16] ; + unsigned int *intptr, intdata ; + unsigned short *shortptr ; + char *charptr ; + float *floatptr ; + double *doubleptr ; + char c ; + int byte_count = 0, count ; + + if (! format) + return psf_ftell (psf) ; + + va_start (argptr, format) ; + + while ((c = *format++)) + { switch (c) + { case 'e' : /* All conversions are now from LE to host. */ + psf->rwf_endian = SF_ENDIAN_LITTLE ; + break ; + + case 'E' : /* All conversions are now from BE to host. */ + psf->rwf_endian = SF_ENDIAN_BIG ; + break ; + + case 'm' : + intptr = va_arg (argptr, unsigned int*) ; + ucptr = (unsigned char*) intptr ; + byte_count += header_read (psf, ucptr, sizeof (int)) ; + *intptr = GET_MARKER (ucptr) ; + break ; + + case 'h' : + intptr = va_arg (argptr, unsigned int*) ; + ucptr = (unsigned char*) intptr ; + byte_count += header_read (psf, sixteen_bytes, sizeof (sixteen_bytes)) ; + { int k ; + intdata = 0 ; + for (k = 0 ; k < 16 ; k++) + intdata ^= sixteen_bytes [k] << k ; + } + *intptr = intdata ; + break ; + + case '1' : + charptr = va_arg (argptr, char*) ; + *charptr = 0 ; + byte_count += header_read (psf, charptr, sizeof (char)) ; + break ; + + case '2' : + shortptr = va_arg (argptr, unsigned short*) ; + *shortptr = 0 ; + ucptr = (unsigned char*) shortptr ; + byte_count += header_read (psf, ucptr, sizeof (short)) ; + if (psf->rwf_endian == SF_ENDIAN_BIG) + *shortptr = GET_BE_SHORT (ucptr) ; + else + *shortptr = GET_LE_SHORT (ucptr) ; + break ; + + case '3' : + intptr = va_arg (argptr, unsigned int*) ; + *intptr = 0 ; + byte_count += header_read (psf, sixteen_bytes, 3) ; + if (psf->rwf_endian == SF_ENDIAN_BIG) + *intptr = GET_BE_3BYTE (sixteen_bytes) ; + else + *intptr = GET_LE_3BYTE (sixteen_bytes) ; + break ; + + case '4' : + intptr = va_arg (argptr, unsigned int*) ; + *intptr = 0 ; + ucptr = (unsigned char*) intptr ; + byte_count += header_read (psf, ucptr, sizeof (int)) ; + if (psf->rwf_endian == SF_ENDIAN_BIG) + *intptr = GET_BE_INT (ucptr) ; + else + *intptr = GET_LE_INT (ucptr) ; + break ; + + case '8' : + countptr = va_arg (argptr, sf_count_t *) ; + *countptr = 0 ; + byte_count += header_read (psf, sixteen_bytes, 8) ; + if (psf->rwf_endian == SF_ENDIAN_BIG) + countdata = GET_BE_8BYTE (sixteen_bytes) ; + else + countdata = GET_LE_8BYTE (sixteen_bytes) ; + *countptr = countdata ; + break ; + + case 'f' : /* Float conversion */ + floatptr = va_arg (argptr, float *) ; + *floatptr = 0.0 ; + byte_count += header_read (psf, floatptr, sizeof (float)) ; + if (psf->rwf_endian == SF_ENDIAN_BIG) + *floatptr = float32_be_read ((unsigned char*) floatptr) ; + else + *floatptr = float32_le_read ((unsigned char*) floatptr) ; + break ; + + case 'd' : /* double conversion */ + doubleptr = va_arg (argptr, double *) ; + *doubleptr = 0.0 ; + byte_count += header_read (psf, doubleptr, sizeof (double)) ; + if (psf->rwf_endian == SF_ENDIAN_BIG) + *doubleptr = double64_be_read ((unsigned char*) doubleptr) ; + else + *doubleptr = double64_le_read ((unsigned char*) doubleptr) ; + break ; + + case 's' : + psf_log_printf (psf, "Format conversion 's' not implemented yet.\n") ; + /* + strptr = va_arg (argptr, char *) ; + size = strlen (strptr) + 1 ; + size += (size & 1) ; + longdata = H2LE_INT (size) ; + get_int (psf, longdata) ; + memcpy (&(psf->header [psf->headindex]), strptr, size) ; + psf->headindex += size ; + */ + break ; + + case 'b' : + charptr = va_arg (argptr, char*) ; + count = va_arg (argptr, int) ; + if (count > 0) + byte_count += header_read (psf, charptr, count) ; + break ; + + case 'G' : + charptr = va_arg (argptr, char*) ; + count = va_arg (argptr, int) ; + if (count > 0) + byte_count += header_gets (psf, charptr, count) ; + break ; + + case 'z' : + psf_log_printf (psf, "Format conversion 'z' not implemented yet.\n") ; + /* + size = va_arg (argptr, size_t) ; + while (size) + { psf->header [psf->headindex] = 0 ; + psf->headindex ++ ; + size -- ; + } ; + */ + break ; + + case 'p' : + /* Get the seek position first. */ + count = va_arg (argptr, int) ; + header_seek (psf, count, SEEK_SET) ; + byte_count = count ; + break ; + + case 'j' : + /* Get the seek position first. */ + count = va_arg (argptr, int) ; + header_seek (psf, count, SEEK_CUR) ; + byte_count += count ; + break ; + + default : + psf_log_printf (psf, "*** Invalid format specifier `%c'\n", c) ; + psf->error = SFE_INTERNAL ; + break ; + } ; + } ; + + va_end (argptr) ; + + return byte_count ; +} /* psf_binheader_readf */ + +/*----------------------------------------------------------------------------------------------- +*/ + +sf_count_t +psf_default_seek (SF_PRIVATE *psf, int mode, sf_count_t samples_from_start) +{ sf_count_t position, retval ; + + if (! (psf->blockwidth && psf->dataoffset >= 0)) + { psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; + } ; + + if (! psf->sf.seekable) + { psf->error = SFE_NOT_SEEKABLE ; + return PSF_SEEK_ERROR ; + } ; + + position = psf->dataoffset + psf->blockwidth * samples_from_start ; + + if ((retval = psf_fseek (psf, position, SEEK_SET)) != position) + { psf->error = SFE_SEEK_FAILED ; + return PSF_SEEK_ERROR ; + } ; + + mode = mode ; + + return samples_from_start ; +} /* psf_default_seek */ + +/*----------------------------------------------------------------------------------------------- +*/ + +void +psf_hexdump (void *ptr, int len) +{ char ascii [17], *data ; + int k, m ; + + if ((data = ptr) == NULL) + return ; + if (len <= 0) + return ; + + puts ("") ; + for (k = 0 ; k < len ; k += 16) + { memset (ascii, ' ', sizeof (ascii)) ; + + printf ("%08X: ", k) ; + for (m = 0 ; m < 16 && k + m < len ; m++) + { printf (m == 8 ? " %02X " : "%02X ", data [k + m] & 0xFF) ; + ascii [m] = isprint (data [k + m]) ? data [k + m] : '.' ; + } ; + + if (m <= 8) printf (" ") ; + for ( ; m < 16 ; m++) printf (" ") ; + + ascii [16] = 0 ; + printf (" %s\n", ascii) ; + } ; + + puts ("") ; +} /* psf_hexdump */ + +void +psf_log_SF_INFO (SF_PRIVATE *psf) +{ psf_log_printf (psf, "---------------------------------\n") ; + + psf_log_printf (psf, " Sample rate : %d\n", psf->sf.samplerate) ; + psf_log_printf (psf, " Frames : %D\n", psf->sf.frames) ; + psf_log_printf (psf, " Channels : %d\n", psf->sf.channels) ; + + psf_log_printf (psf, " Format : 0x%X\n", psf->sf.format) ; + psf_log_printf (psf, " Sections : %d\n", psf->sf.sections) ; + psf_log_printf (psf, " Seekable : %s\n", psf->sf.seekable ? "TRUE" : "FALSE") ; + + psf_log_printf (psf, "---------------------------------\n") ; +} /* psf_dump_SFINFO */ + +/*======================================================================================== +*/ + +SF_INSTRUMENT * +psf_instrument_alloc (void) +{ SF_INSTRUMENT *instr ; + + instr = calloc (1, sizeof (SF_INSTRUMENT)) ; + + if (instr == NULL) + return NULL ; + + /* Set non-zero default values. */ + instr->basenote = -1 ; + instr->velocity_lo = -1 ; + instr->velocity_hi = -1 ; + instr->key_lo = -1 ; + instr->key_hi = -1 ; + + return instr ; +} /* psf_instrument_alloc */ + +void* +psf_memset (void *s, int c, sf_count_t len) +{ char *ptr ; + int setcount ; + + ptr = (char *) s ; + + while (len > 0) + { setcount = (len > 0x10000000) ? 0x10000000 : (int) len ; + + memset (ptr, c, setcount) ; + + ptr += setcount ; + len -= setcount ; + } ; + + return s ; +} /* psf_memset */ + +void psf_get_date_str (char *str, int maxlen) +{ time_t current ; + struct tm timedata, *tmptr ; + + time (¤t) ; + +#if defined (HAVE_GMTIME_R) + /* If the re-entrant version is available, use it. */ + tmptr = gmtime_r (¤t, &timedata) ; +#elif defined (HAVE_GMTIME) + /* Otherwise use the standard one and copy the data to local storage. */ + tmptr = gmtime (¤t) ; + memcpy (&timedata, tmptr, sizeof (timedata)) ; +#else + tmptr = NULL ; +#endif + + if (tmptr) + LSF_SNPRINTF (str, maxlen, "%4d-%02d-%02d %02d:%02d:%02d UTC", + 1900 + timedata.tm_year, timedata.tm_mon, timedata.tm_mday, + timedata.tm_hour, timedata.tm_min, timedata.tm_sec) ; + else + LSF_SNPRINTF (str, maxlen, "Unknown date") ; + + return ; +} /* psf_get_date_str */ + +int +subformat_to_bytewidth (int format) +{ + switch (format) + { case SF_FORMAT_PCM_U8 : + case SF_FORMAT_PCM_S8 : + return 1 ; + case SF_FORMAT_PCM_16 : + return 2 ; + case SF_FORMAT_PCM_24 : + return 3 ; + case SF_FORMAT_PCM_32 : + case SF_FORMAT_FLOAT : + return 4 ; + case SF_FORMAT_DOUBLE : + return 8 ; + } ; + + return 0 ; +} /* subformat_to_bytewidth */ + +int +s_bitwidth_to_subformat (int bits) +{ static int array [] = + { SF_FORMAT_PCM_S8, SF_FORMAT_PCM_16, SF_FORMAT_PCM_24, SF_FORMAT_PCM_32 + } ; + + if (bits < 8 || bits > 32) + return 0 ; + + return array [((bits + 7) / 8) - 1] ; +} /* bitwidth_to_subformat */ + +int +u_bitwidth_to_subformat (int bits) +{ static int array [] = + { SF_FORMAT_PCM_U8, SF_FORMAT_PCM_16, SF_FORMAT_PCM_24, SF_FORMAT_PCM_32 + } ; + + if (bits < 8 || bits > 32) + return 0 ; + + return array [((bits + 7) / 8) - 1] ; +} /* bitwidth_to_subformat */ + +#endif /* PSF_LOG_PRINTF_ONLY */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 33e9795e-f717-461a-9feb-65d083a56395 +*/ diff --git a/libs/libsndfile/src/common.h b/libs/libsndfile/src/common.h new file mode 100644 index 0000000000..c08ff67e96 --- /dev/null +++ b/libs/libsndfile/src/common.h @@ -0,0 +1,766 @@ +/* +** Copyright (C) 1999-2006 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#ifndef SNDFILE_COMMON_H +#define SNDFILE_COMMON_H + +#include "sfconfig.h" + +#include + +#if HAVE_STDINT_H +#include +#endif + +#ifndef SNDFILE_H +#include "sndfile.h" +#elif HAVE_INTTYPES_H +#include +#endif + +#ifdef __cplusplus +#error "This code is not designed to be compiled with a C++ compiler." +#endif + +#ifdef UNUSED +#elif defined (__GNUC__) +# define UNUSED(x) UNUSED_ ## x __attribute__ ((unused)) +#elif defined (__LCLINT__) +# define UNUSED(x) /*@unused@*/ x +#else +# define UNUSED(x) x +#endif + +#ifdef __GNUC__ +# define WARN_UNUSED __attribute__ ((warn_unused_result)) +#else +# define WARN_UNUSED +#endif + +#define SF_BUFFER_LEN (8192*2) +#define SF_FILENAME_LEN (512) +#define SF_SYSERR_LEN (256) +#define SF_MAX_STRINGS (16) +#define SF_STR_BUFFER_LEN (8192) +#define SF_HEADER_LEN (4100 + SF_STR_BUFFER_LEN) + +#define PSF_SEEK_ERROR ((sf_count_t) -1) + + +#define BITWIDTH2BYTES(x) (((x) + 7) / 8) + +/* For some reason sizeof returns an unsigned value which causes +** a warning when that value is added or subtracted from a signed +** value. Use SIGNED_SIZEOF instead. +*/ +#define SIGNED_SIZEOF(x) ((int) sizeof (x)) + +#define ARRAY_LEN(x) ((int) (sizeof (x) / sizeof ((x) [0]))) + +#define SF_MAX(a,b) ((a) > (b) ? (a) : (b)) +#define SF_MIN(a,b) ((a) < (b) ? (a) : (b)) + +enum +{ /* PEAK chunk location. */ + SF_PEAK_START = 42, + SF_PEAK_END = 43, + + /* PEAK chunk location. */ + SF_SCALE_MAX = 52, + SF_SCALE_MIN = 53, + + /* str_flags values. */ + SF_STR_ALLOW_START = 0x0100, + SF_STR_ALLOW_END = 0x0200, + + /* Location of strings. */ + SF_STR_LOCATE_START = 0x0400, + SF_STR_LOCATE_END = 0x0800, + + SFD_TYPEMASK = 0x0FFFFFFF +} ; + +#define SFM_MASK (SFM_READ | SFM_WRITE | SFM_RDWR) +#define SFM_UNMASK (~SFM_MASK) + +/*--------------------------------------------------------------------------------------- +** Formats that may be supported at some time in the future. +** When support is finalised, these values move to src/sndfile.h. +*/ + +enum +{ /* Work in progress. */ + + /* Formats supported read only. */ + SF_FORMAT_WVE = 0x4020000, /* Psion ALaw Sound File */ + SF_FORMAT_TXW = 0x4030000, /* Yamaha TX16 sampler file */ + SF_FORMAT_DWD = 0x4040000, /* DiamondWare Digirized */ + + /* Following are detected but not supported. */ + SF_FORMAT_OGG = 0x4090000, + + SF_FORMAT_REX = 0x40A0000, /* Propellorheads Rex/Rcy */ + SF_FORMAT_REX2 = 0x40D0000, /* Propellorheads Rex2 */ + SF_FORMAT_KRZ = 0x40E0000, /* Kurzweil sampler file */ + SF_FORMAT_WMA = 0x4100000, /* Windows Media Audio. */ + SF_FORMAT_SHN = 0x4110000, /* Shorten. */ + + /* Unsupported encodings. */ + SF_FORMAT_VORBIS = 0x1001, + + SF_FORMAT_SVX_FIB = 0x1020, /* SVX Fibonacci Delta encoding. */ + SF_FORMAT_SVX_EXP = 0x1021, /* SVX Exponential Delta encoding. */ + + SF_FORMAT_PCM_N = 0x1030 +} ; + +/*--------------------------------------------------------------------------------------- +** PEAK_CHUNK - This chunk type is common to both AIFF and WAVE files although their +** endian encodings are different. +*/ + +typedef struct +{ double value ; /* signed value of peak */ + sf_count_t position ; /* the sample frame for the peak */ +} PEAK_POS ; + +typedef struct +{ /* libsndfile internal : write a PEAK chunk at the start or end of the file? */ + int peak_loc ; + + /* WAV/AIFF */ + unsigned int version ; /* version of the PEAK chunk */ + unsigned int timestamp ; /* secs since 1/1/1970 */ + + /* CAF */ + unsigned int edit_number ; + +#if HAVE_FLEXIBLE_ARRAY + /* the per channel peak info */ + PEAK_POS peaks [] ; +#else + /* + ** This is not ISO compliant C. It works on some compilers which + ** don't support the ISO standard flexible struct array which is + ** used above. If your compiler doesn't like this I suggest you find + ** youself a 1999 ISO C standards compilant compiler. GCC-3.X is + ** highly recommended. + */ + PEAK_POS peaks [0] ; +#endif +} PEAK_INFO ; + +static inline PEAK_INFO * +peak_info_calloc (int channels) +{ return calloc (1, sizeof (PEAK_INFO) + channels * sizeof (PEAK_POS)) ; +} /* peak_info_calloc */ + +typedef struct +{ int type ; + int flags ; + char *str ; +} STR_DATA ; + +static inline size_t +make_size_t (int x) +{ return (size_t) x ; +} /* size_t_of_int */ + +/*======================================================================================= +** SF_PRIVATE stuct - a pointer to this struct is passed back to the caller of the +** sf_open_XXXX functions. The caller however has no knowledge of the struct's +** contents. +*/ + +typedef struct sf_private_tag +{ /* Force the compiler to double align the start of buffer. */ + union + { double dbuf [SF_BUFFER_LEN / sizeof (double)] ; +#if (defined (SIZEOF_INT64_T) && (SIZEOF_INT64_T == 8)) + int64_t lbuf [SF_BUFFER_LEN / sizeof (int64_t)] ; +#else + long lbuf [SF_BUFFER_LEN / sizeof (double)] ; +#endif + float fbuf [SF_BUFFER_LEN / sizeof (float)] ; + int ibuf [SF_BUFFER_LEN / sizeof (int)] ; + short sbuf [SF_BUFFER_LEN / sizeof (short)] ; + char cbuf [SF_BUFFER_LEN / sizeof (char)] ; + signed char scbuf [SF_BUFFER_LEN / sizeof (signed char)] ; + unsigned char ucbuf [SF_BUFFER_LEN / sizeof (signed char)] ; + } u ; + + char filepath [SF_FILENAME_LEN] ; + char rsrcpath [SF_FILENAME_LEN] ; + char directory [SF_FILENAME_LEN] ; + char filename [SF_FILENAME_LEN / 4] ; + + char syserr [SF_SYSERR_LEN] ; + + /* logbuffer and logindex should only be changed within the logging functions + ** of common.c + */ + char logbuffer [SF_BUFFER_LEN] ; + unsigned char header [SF_HEADER_LEN] ; /* Must be unsigned */ + int rwf_endian ; /* Header endian-ness flag. */ + + /* Storage and housekeeping data for adding/reading strings from + ** sound files. + */ + STR_DATA strings [SF_MAX_STRINGS] ; + char str_storage [SF_STR_BUFFER_LEN] ; + char *str_end ; + int str_flags ; + + /* Guard value. If this changes the buffers above have overflowed. */ + int Magick ; + + /* Index variables for maintaining logbuffer and header above. */ + int logindex ; + int headindex, headend ; + int has_text ; + int do_not_close_descriptor ; + +#if USE_WINDOWS_API + /* + ** These fields can only be used in src/file_io.c. + ** They are basically the same as a windows file HANDLE. + */ + void *hfile, *hrsrc, *hsaved ; +#else + /* These fields can only be used in src/file_io.c. */ + int filedes, rsrcdes, savedes ; +#endif + + int error ; + + int mode ; /* Open mode : SFM_READ, SFM_WRITE or SFM_RDWR. */ + int endian ; /* File endianness : SF_ENDIAN_LITTLE or SF_ENDIAN_BIG. */ + int float_endswap ; /* Need to endswap float32s? */ + + /* + ** Maximum float value for calculating the multiplier for + ** float/double to short/int conversions. + */ + int float_int_mult ; + float float_max ; + + /* Vairables for handling pipes. */ + int is_pipe ; /* True if file is a pipe. */ + sf_count_t pipeoffset ; /* Number of bytes read from a pipe. */ + + /* True if clipping must be performed on float->int conversions. */ + int add_clipping ; + + SF_INFO sf ; + + int have_written ; /* Has a single write been done to the file? */ + PEAK_INFO *peak_info ; + + /* Loop Info */ + SF_LOOP_INFO *loop_info ; + SF_INSTRUMENT *instrument ; + + /* Broadcast (EBU) Info */ + SF_BROADCAST_INFO *broadcast_info ; + + sf_count_t filelength ; /* Overall length of (embedded) file. */ + sf_count_t fileoffset ; /* Offset in number of bytes from beginning of file. */ + + sf_count_t rsrclength ; /* Length of the resource fork (if it exists). */ + + sf_count_t dataoffset ; /* Offset in number of bytes from beginning of file. */ + sf_count_t datalength ; /* Length in bytes of the audio data. */ + sf_count_t dataend ; /* Offset to file tailer. */ + + int blockwidth ; /* Size in bytes of one set of interleaved samples. */ + int bytewidth ; /* Size in bytes of one sample (one channel). */ + + void *dither ; + void *interleave ; + + int last_op ; /* Last operation; either SFM_READ or SFM_WRITE */ + sf_count_t read_current ; + sf_count_t write_current ; + + void *fdata ; /* This is a pointer to dynamically allocated file format + ** specific data. + */ + + SF_DITHER_INFO write_dither ; + SF_DITHER_INFO read_dither ; + + int norm_double ; + int norm_float ; + + int auto_header ; + + int ieee_replace ; + /* A set of file specific function pointers */ + + sf_count_t (*read_short) (struct sf_private_tag*, short *ptr, sf_count_t len) ; + sf_count_t (*read_int) (struct sf_private_tag*, int *ptr, sf_count_t len) ; + sf_count_t (*read_float) (struct sf_private_tag*, float *ptr, sf_count_t len) ; + sf_count_t (*read_double) (struct sf_private_tag*, double *ptr, sf_count_t len) ; + + sf_count_t (*write_short) (struct sf_private_tag*, const short *ptr, sf_count_t len) ; + sf_count_t (*write_int) (struct sf_private_tag*, const int *ptr, sf_count_t len) ; + sf_count_t (*write_float) (struct sf_private_tag*, const float *ptr, sf_count_t len) ; + sf_count_t (*write_double) (struct sf_private_tag*, const double *ptr, sf_count_t len) ; + + sf_count_t (*seek) (struct sf_private_tag*, int mode, sf_count_t samples_from_start) ; + int (*write_header) (struct sf_private_tag*, int calc_length) ; + int (*command) (struct sf_private_tag*, int command, void *data, int datasize) ; + + /* + ** Separate close functions for the codec and the container. + ** The codec close function is always called first. + */ + int (*codec_close) (struct sf_private_tag*) ; + int (*container_close) (struct sf_private_tag*) ; + + char *format_desc ; + + /* Virtual I/O functions. */ + int virtual_io ; + SF_VIRTUAL_IO vio ; + void *vio_user_data ; +} SF_PRIVATE ; + + + +enum +{ SFE_NO_ERROR = SF_ERR_NO_ERROR, + SFE_BAD_OPEN_FORMAT = SF_ERR_UNRECOGNISED_FORMAT, + SFE_SYSTEM = SF_ERR_SYSTEM, + SFE_MALFORMED_FILE = SF_ERR_MALFORMED_FILE, + SFE_UNSUPPORTED_ENCODING = SF_ERR_UNSUPPORTED_ENCODING, + + SFE_BAD_FILE, + SFE_BAD_FILE_READ, + SFE_OPEN_FAILED, + SFE_BAD_SNDFILE_PTR, + SFE_BAD_SF_INFO_PTR, + SFE_BAD_SF_INCOMPLETE, + SFE_BAD_FILE_PTR, + SFE_BAD_INT_PTR, + SFE_BAD_STAT_SIZE, + SFE_MALLOC_FAILED, + SFE_UNIMPLEMENTED, + SFE_BAD_READ_ALIGN, + SFE_BAD_WRITE_ALIGN, + SFE_UNKNOWN_FORMAT, + SFE_NOT_READMODE, + SFE_NOT_WRITEMODE, + SFE_BAD_MODE_RW, + SFE_BAD_SF_INFO, + SFE_BAD_OFFSET, + SFE_NO_EMBED_SUPPORT, + SFE_NO_EMBEDDED_RDWR, + SFE_NO_PIPE_WRITE, + + SFE_INTERNAL, + SFE_BAD_CONTROL_CMD, + SFE_BAD_ENDIAN, + SFE_CHANNEL_COUNT, + SFE_BAD_RDWR_FORMAT, + + SFE_BAD_VIRTUAL_IO, + + SFE_INTERLEAVE_MODE, + SFE_INTERLEAVE_SEEK, + SFE_INTERLEAVE_READ, + + SFE_BAD_SEEK, + SFE_NOT_SEEKABLE, + SFE_AMBIGUOUS_SEEK, + SFE_WRONG_SEEK, + SFE_SEEK_FAILED, + + SFE_BAD_OPEN_MODE, + SFE_OPEN_PIPE_RDWR, + SFE_RDWR_POSITION, + SFE_RDWR_BAD_HEADER, + + SFE_STR_NO_SUPPORT, + SFE_STR_NOT_WRITE, + SFE_STR_MAX_DATA, + SFE_STR_MAX_COUNT, + SFE_STR_BAD_TYPE, + SFE_STR_NO_ADD_END, + SFE_STR_BAD_STRING, + SFE_STR_WEIRD, + + SFE_WAV_NO_RIFF, + SFE_WAV_NO_WAVE, + SFE_WAV_NO_FMT, + SFE_WAV_FMT_SHORT, + SFE_WAV_BAD_FACT, + SFE_WAV_BAD_PEAK, + SFE_WAV_PEAK_B4_FMT, + SFE_WAV_BAD_FORMAT, + SFE_WAV_BAD_BLOCKALIGN, + SFE_WAV_NO_DATA, + SFE_WAV_BAD_LIST, + SFE_WAV_ADPCM_NOT4BIT, + SFE_WAV_ADPCM_CHANNELS, + SFE_WAV_GSM610_FORMAT, + SFE_WAV_UNKNOWN_CHUNK, + SFE_WAV_WVPK_DATA, + + SFE_AIFF_NO_FORM, + SFE_AIFF_AIFF_NO_FORM, + SFE_AIFF_COMM_NO_FORM, + SFE_AIFF_SSND_NO_COMM, + SFE_AIFF_UNKNOWN_CHUNK, + SFE_AIFF_COMM_CHUNK_SIZE, + SFE_AIFF_BAD_COMM_CHUNK, + SFE_AIFF_PEAK_B4_COMM, + SFE_AIFF_BAD_PEAK, + SFE_AIFF_NO_SSND, + SFE_AIFF_NO_DATA, + SFE_AIFF_RW_SSND_NOT_LAST, + + SFE_AU_UNKNOWN_FORMAT, + SFE_AU_NO_DOTSND, + SFE_AU_EMBED_BAD_LEN, + + SFE_RAW_READ_BAD_SPEC, + SFE_RAW_BAD_BITWIDTH, + SFE_RAW_BAD_FORMAT, + + SFE_PAF_NO_MARKER, + SFE_PAF_VERSION, + SFE_PAF_UNKNOWN_FORMAT, + SFE_PAF_SHORT_HEADER, + + SFE_SVX_NO_FORM, + SFE_SVX_NO_BODY, + SFE_SVX_NO_DATA, + SFE_SVX_BAD_COMP, + SFE_SVX_BAD_NAME_LENGTH, + + SFE_NIST_BAD_HEADER, + SFE_NIST_CRLF_CONVERISON, + SFE_NIST_BAD_ENCODING, + + SFE_VOC_NO_CREATIVE, + SFE_VOC_BAD_FORMAT, + SFE_VOC_BAD_VERSION, + SFE_VOC_BAD_MARKER, + SFE_VOC_BAD_SECTIONS, + SFE_VOC_MULTI_SAMPLERATE, + SFE_VOC_MULTI_SECTION, + SFE_VOC_MULTI_PARAM, + SFE_VOC_SECTION_COUNT, + SFE_VOC_NO_PIPE, + + SFE_IRCAM_NO_MARKER, + SFE_IRCAM_BAD_CHANNELS, + SFE_IRCAM_UNKNOWN_FORMAT, + + SFE_W64_64_BIT, + SFE_W64_NO_RIFF, + SFE_W64_NO_WAVE, + SFE_W64_NO_FMT, + SFE_W64_NO_DATA, + SFE_W64_FMT_SHORT, + SFE_W64_FMT_TOO_BIG, + SFE_W64_ADPCM_NOT4BIT, + SFE_W64_ADPCM_CHANNELS, + SFE_W64_GSM610_FORMAT, + + SFE_MAT4_BAD_NAME, + SFE_MAT4_NO_SAMPLERATE, + SFE_MAT4_ZERO_CHANNELS, + + SFE_MAT5_BAD_ENDIAN, + SFE_MAT5_NO_BLOCK, + SFE_MAT5_SAMPLE_RATE, + SFE_MAT5_ZERO_CHANNELS, + + SFE_PVF_NO_PVF1, + SFE_PVF_BAD_HEADER, + SFE_PVF_BAD_BITWIDTH, + + SFE_DWVW_BAD_BITWIDTH, + SFE_G72X_NOT_MONO, + + SFE_XI_BAD_HEADER, + SFE_XI_EXCESS_SAMPLES, + SFE_XI_NO_PIPE, + + SFE_HTK_NO_PIPE, + + SFE_SDS_NOT_SDS, + SFE_SDS_BAD_BIT_WIDTH, + + SFE_SD2_FD_DISALLOWED, + SFE_SD2_BAD_DATA_OFFSET, + SFE_SD2_BAD_MAP_OFFSET, + SFE_SD2_BAD_DATA_LENGTH, + SFE_SD2_BAD_MAP_LENGTH, + SFE_SD2_BAD_RSRC, + SFE_SD2_BAD_SAMPLE_SIZE, + + SFE_FLAC_BAD_HEADER, + SFE_FLAC_NEW_DECODER, + SFE_FLAC_INIT_DECODER, + SFE_FLAC_LOST_SYNC, + SFE_FLAC_BAD_SAMPLE_RATE, + SFE_FLAC_UNKOWN_ERROR, + + SFE_MAX_ERROR /* This must be last in list. */ +} ; + +int subformat_to_bytewidth (int format) ; +int s_bitwidth_to_subformat (int bits) ; +int u_bitwidth_to_subformat (int bits) ; + +/* Functions for reading and writing floats and doubles on processors +** with non-IEEE floats/doubles. +*/ +float float32_be_read (unsigned char *cptr) ; +float float32_le_read (unsigned char *cptr) ; +void float32_be_write (float in, unsigned char *out) ; +void float32_le_write (float in, unsigned char *out) ; + +double double64_be_read (unsigned char *cptr) ; +double double64_le_read (unsigned char *cptr) ; +void double64_be_write (double in, unsigned char *out) ; +void double64_le_write (double in, unsigned char *out) ; + +/* Functions for writing to the internal logging buffer. */ + +void psf_log_printf (SF_PRIVATE *psf, const char *format, ...) ; +void psf_log_SF_INFO (SF_PRIVATE *psf) ; + +void psf_hexdump (void *ptr, int len) ; + +/* Functions used when writing file headers. */ + +int psf_binheader_writef (SF_PRIVATE *psf, const char *format, ...) ; +void psf_asciiheader_printf (SF_PRIVATE *psf, const char *format, ...) ; + +/* Functions used when reading file headers. */ + +int psf_binheader_readf (SF_PRIVATE *psf, char const *format, ...) ; + +/* Functions used in the write function for updating the peak chunk. */ + +void peak_update_short (SF_PRIVATE *psf, short *ptr, size_t items) ; +void peak_update_int (SF_PRIVATE *psf, int *ptr, size_t items) ; +void peak_update_double (SF_PRIVATE *psf, double *ptr, size_t items) ; + +/* Functions defined in command.c. */ + +int psf_get_format_simple_count (void) ; +int psf_get_format_simple (SF_FORMAT_INFO *data) ; + +int psf_get_format_info (SF_FORMAT_INFO *data) ; + +int psf_get_format_major_count (void) ; +int psf_get_format_major (SF_FORMAT_INFO *data) ; + +int psf_get_format_subtype_count (void) ; +int psf_get_format_subtype (SF_FORMAT_INFO *data) ; + +void psf_generate_format_desc (SF_PRIVATE *psf) ; + +double psf_calc_signal_max (SF_PRIVATE *psf, int normalize) ; +int psf_calc_max_all_channels (SF_PRIVATE *psf, double *peaks, int normalize) ; + +int psf_get_signal_max (SF_PRIVATE *psf, double *peak) ; +int psf_get_max_all_channels (SF_PRIVATE *psf, double *peaks) ; + +/* Functions in strings.c. */ + +const char* psf_get_string (SF_PRIVATE *psf, int str_type) ; +int psf_set_string (SF_PRIVATE *psf, int str_type, const char *str) ; +int psf_store_string (SF_PRIVATE *psf, int str_type, const char *str) ; + +/* Default seek function. Use for PCM and float encoded data. */ +sf_count_t psf_default_seek (SF_PRIVATE *psf, int mode, sf_count_t samples_from_start) ; + +/* Generate the currebt date as a string. */ +void psf_get_date_str (char *str, int maxlen) ; + +int macos_guess_file_type (SF_PRIVATE *psf, const char *filename) ; + +/*------------------------------------------------------------------------------------ +** File I/O functions which will allow access to large files (> 2 Gig) on +** some 32 bit OSes. Implementation in file_io.c. +*/ + +int psf_fopen (SF_PRIVATE *psf, const char *pathname, int flags) ; +int psf_set_stdio (SF_PRIVATE *psf, int mode) ; +int psf_file_valid (SF_PRIVATE *psf) ; +void psf_set_file (SF_PRIVATE *psf, int fd) ; +void psf_init_files (SF_PRIVATE *psf) ; +void psf_use_rsrc (SF_PRIVATE *psf, int on_off) ; + +sf_count_t psf_fseek (SF_PRIVATE *psf, sf_count_t offset, int whence) ; +sf_count_t psf_fread (void *ptr, sf_count_t bytes, sf_count_t count, SF_PRIVATE *psf) ; +sf_count_t psf_fwrite (const void *ptr, sf_count_t bytes, sf_count_t count, SF_PRIVATE *psf) ; +sf_count_t psf_fgets (char *buffer, sf_count_t bufsize, SF_PRIVATE *psf) ; +sf_count_t psf_ftell (SF_PRIVATE *psf) ; +sf_count_t psf_get_filelen (SF_PRIVATE *psf) ; + +void psf_fsync (SF_PRIVATE *psf) ; + +int psf_is_pipe (SF_PRIVATE *psf) ; + +int psf_ftruncate (SF_PRIVATE *psf, sf_count_t len) ; +int psf_fclose (SF_PRIVATE *psf) ; + +/* Open and close the resource fork of a file. */ +int psf_open_rsrc (SF_PRIVATE *psf, int mode) ; +int psf_close_rsrc (SF_PRIVATE *psf) ; + +/* +void psf_fclearerr (SF_PRIVATE *psf) ; +int psf_ferror (SF_PRIVATE *psf) ; +*/ + +/*------------------------------------------------------------------------------------ +** Functions for reading and writing different file formats. +*/ + +int aiff_open (SF_PRIVATE *psf) ; +int au_open (SF_PRIVATE *psf) ; +int avr_open (SF_PRIVATE *psf) ; +int htk_open (SF_PRIVATE *psf) ; +int ircam_open (SF_PRIVATE *psf) ; +int mat4_open (SF_PRIVATE *psf) ; +int mat5_open (SF_PRIVATE *psf) ; +int nist_open (SF_PRIVATE *psf) ; +int paf_open (SF_PRIVATE *psf) ; +int pvf_open (SF_PRIVATE *psf) ; +int raw_open (SF_PRIVATE *psf) ; +int sd2_open (SF_PRIVATE *psf) ; +int sds_open (SF_PRIVATE *psf) ; +int svx_open (SF_PRIVATE *psf) ; +int voc_open (SF_PRIVATE *psf) ; +int w64_open (SF_PRIVATE *psf) ; +int wav_open (SF_PRIVATE *psf) ; +int xi_open (SF_PRIVATE *psf) ; +int flac_open (SF_PRIVATE *psf) ; +int caf_open (SF_PRIVATE *psf) ; + +/* In progress. Do not currently work. */ + +int mpeg_open (SF_PRIVATE *psf) ; +int ogg_open (SF_PRIVATE *psf) ; +int rx2_open (SF_PRIVATE *psf) ; +int txw_open (SF_PRIVATE *psf) ; +int wve_open (SF_PRIVATE *psf) ; +int dwd_open (SF_PRIVATE *psf) ; + +int macbinary3_open (SF_PRIVATE *psf) ; + +/*------------------------------------------------------------------------------------ +** Init functions for a number of common data encodings. +*/ + +int pcm_init (SF_PRIVATE *psf) ; +int ulaw_init (SF_PRIVATE *psf) ; +int alaw_init (SF_PRIVATE *psf) ; +int float32_init (SF_PRIVATE *psf) ; +int double64_init (SF_PRIVATE *psf) ; +int dwvw_init (SF_PRIVATE *psf, int bitwidth) ; +int gsm610_init (SF_PRIVATE *psf) ; +int vox_adpcm_init (SF_PRIVATE *psf) ; +int flac_init (SF_PRIVATE *psf) ; +int g72x_init (SF_PRIVATE * psf) ; + +int dither_init (SF_PRIVATE *psf, int mode) ; + +int wav_w64_ima_init (SF_PRIVATE *psf, int blockalign, int samplesperblock) ; +int wav_w64_msadpcm_init (SF_PRIVATE *psf, int blockalign, int samplesperblock) ; + +int aiff_ima_init (SF_PRIVATE *psf, int blockalign, int samplesperblock) ; + +int interleave_init (SF_PRIVATE *psf) ; + +/*------------------------------------------------------------------------------------ +** Other helper functions. +*/ + +void *psf_memset (void *s, int c, sf_count_t n) ; + +SF_INSTRUMENT * psf_instrument_alloc (void) ; + + +SF_BROADCAST_INFO* broadcast_info_alloc (void) ; +int broadcast_info_copy (SF_BROADCAST_INFO* dst, SF_BROADCAST_INFO* src) ; +int broadcast_add_coding_history (SF_BROADCAST_INFO* bext, unsigned int channels, unsigned int samplerate) ; + +/*------------------------------------------------------------------------------------ +** Here's how we fix systems which don't snprintf / vsnprintf. +** Systems without these functions should use the +*/ + +#if USE_WINDOWS_API +#define LSF_SNPRINTF _snprintf +#elif (HAVE_SNPRINTF && ! FORCE_MISSING_SNPRINTF) +#define LSF_SNPRINTF snprintf +#else +int missing_snprintf (char *str, size_t n, char const *fmt, ...) ; +#define LSF_SNPRINTF missing_snprintf +#endif + +#if USE_WINDOWS_API +#define LSF_VSNPRINTF _vsnprintf +#elif (HAVE_VSNPRINTF && ! FORCE_MISSING_SNPRINTF) +#define LSF_VSNPRINTF vsnprintf +#else +int missing_vsnprintf (char *str, size_t n, const char *fmt, ...) ; +#define LSF_VSNPRINTF missing_vsnprintf +#endif + +/*------------------------------------------------------------------------------------ +** Extra commands for sf_command(). Not for public use yet. +*/ + +enum +{ SFC_TEST_AIFF_ADD_INST_CHUNK = 0x2000, + SFC_TEST_WAV_ADD_INFO_CHUNK = 0x2010 +} ; + +/* +** Maybe, one day, make these functions or something like them, public. +** +** Buffer to buffer dithering. Pointer in and out are allowed to point +** to the same buffer for in-place dithering. +*/ + +#if 0 +int sf_dither_short (const SF_DITHER_INFO *dither, const short *in, short *out, int count) ; +int sf_dither_int (const SF_DITHER_INFO *dither, const int *in, int *out, int count) ; +int sf_dither_float (const SF_DITHER_INFO *dither, const float *in, float *out, int count) ; +int sf_dither_double (const SF_DITHER_INFO *dither, const double *in, double *out, int count) ; +#endif + +#endif /* SNDFILE_COMMON_H */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 7b45c0ee-5835-4a18-a4ef-994e4cd95b67 +*/ diff --git a/libs/libsndfile/src/config.h.in b/libs/libsndfile/src/config.h.in new file mode 100644 index 0000000000..4b3d8440a2 --- /dev/null +++ b/libs/libsndfile/src/config.h.in @@ -0,0 +1,247 @@ +/* src/config.h.in. Generated from configure.ac by autoheader. */ + +/* Set to 1 if the compile is GNU GCC. */ +#undef COMPILER_IS_GCC + +/* Target processor clips on negative float to int conversion. */ +#undef CPU_CLIPS_NEGATIVE + +/* Target processor clips on positive float to int conversion. */ +#undef CPU_CLIPS_POSITIVE + +/* Target processor is big endian. */ +#undef CPU_IS_BIG_ENDIAN + +/* Target processor is little endian. */ +#undef CPU_IS_LITTLE_ENDIAN + +/* Set to 1 to enable experimental code. */ +#undef ENABLE_EXPERIMENTAL_CODE + +/* Major version of GCC or 3 otherwise. */ +#undef GCC_MAJOR_VERSION + +/* Define to 1 if you have the header file. */ +#undef HAVE_ALSA_ASOUNDLIB_H + +/* Define to 1 if you have the header file. */ +#undef HAVE_BYTESWAP_H + +/* Define to 1 if you have the `calloc' function. */ +#undef HAVE_CALLOC + +/* Define to 1 if you have the `ceil' function. */ +#undef HAVE_CEIL + +/* Set to 1 if S_IRGRP is defined. */ +#undef HAVE_DECL_S_IRGRP + +/* Define to 1 if you have the header file. */ +#undef HAVE_ENDIAN_H + +/* Define to 1 if you have the `fdatasync' function. */ +#undef HAVE_FDATASYNC + +/* Define to 1 if you have libflac 1.1.1 */ +#undef HAVE_FLAC_1_1_1 + +/* Define to 1 if you have the header file. */ +#undef HAVE_FLAC_ALL_H + +/* Set to 1 if the compile supports the struct hack. */ +#undef HAVE_FLEXIBLE_ARRAY + +/* Define to 1 if you have the `floor' function. */ +#undef HAVE_FLOOR + +/* Define to 1 if you have the `fmod' function. */ +#undef HAVE_FMOD + +/* Define to 1 if you have the `free' function. */ +#undef HAVE_FREE + +/* Define to 1 if you have the `fstat' function. */ +#undef HAVE_FSTAT + +/* Define to 1 if you have the `fsync' function. */ +#undef HAVE_FSYNC + +/* Define to 1 if you have the `ftruncate' function. */ +#undef HAVE_FTRUNCATE + +/* Define to 1 if you have the `getpagesize' function. */ +#undef HAVE_GETPAGESIZE + +/* Define to 1 if you have the `gmtime' function. */ +#undef HAVE_GMTIME + +/* Define to 1 if you have the `gmtime_r' function. */ +#undef HAVE_GMTIME_R + +/* Define to 1 if you have the header file. */ +#undef HAVE_INTTYPES_H + +/* Define to 1 if you have the `m' library (-lm). */ +#undef HAVE_LIBM + +/* Define to 1 if you have the header file. */ +#undef HAVE_LOCALE_H + +/* Define if you have C99's lrint function. */ +#undef HAVE_LRINT + +/* Define if you have C99's lrintf function. */ +#undef HAVE_LRINTF + +/* Define to 1 if you have the `lseek' function. */ +#undef HAVE_LSEEK + +/* Define to 1 if you have the `malloc' function. */ +#undef HAVE_MALLOC + +/* Define to 1 if you have the header file. */ +#undef HAVE_MEMORY_H + +/* Define to 1 if you have the `mmap' function. */ +#undef HAVE_MMAP + +/* Define to 1 if you have the `open' function. */ +#undef HAVE_OPEN + +/* Define to 1 if you have the `pread' function. */ +#undef HAVE_PREAD + +/* Define to 1 if you have the `pwrite' function. */ +#undef HAVE_PWRITE + +/* Define to 1 if you have the `read' function. */ +#undef HAVE_READ + +/* Define to 1 if you have the `realloc' function. */ +#undef HAVE_REALLOC + +/* Define to 1 if you have the `setlocale' function. */ +#undef HAVE_SETLOCALE + +/* Define to 1 if you have the `snprintf' function. */ +#undef HAVE_SNPRINTF + +/* Set to 1 if you have libsqlite3. */ +#undef HAVE_SQLITE3 + +/* Define to 1 if the system has the type `ssize_t'. */ +#undef HAVE_SSIZE_T + +/* Define to 1 if you have the header file. */ +#undef HAVE_STDINT_H + +/* Define to 1 if you have the header file. */ +#undef HAVE_STDLIB_H + +/* Define to 1 if you have the header file. */ +#undef HAVE_STRINGS_H + +/* Define to 1 if you have the header file. */ +#undef HAVE_STRING_H + +/* Define to 1 if you have the header file. */ +#undef HAVE_SYS_STAT_H + +/* Define to 1 if you have the header file. */ +#undef HAVE_SYS_TYPES_H + +/* Define to 1 if you have that is POSIX.1 compatible. */ +#undef HAVE_SYS_WAIT_H + +/* Define to 1 if you have the header file. */ +#undef HAVE_UNISTD_H + +/* Define to 1 if you have the `vsnprintf' function. */ +#undef HAVE_VSNPRINTF + +/* Define to 1 if you have the `write' function. */ +#undef HAVE_WRITE + +/* Set to 1 if compiling for MacOSX */ +#undef OS_IS_MACOSX + +/* Set to 1 if compiling for Win32 */ +#undef OS_IS_WIN32 + +/* Define to the address where bug reports for this package should be sent. */ +#undef PACKAGE_BUGREPORT + +/* Define to the full name of this package. */ +#undef PACKAGE_NAME + +/* Define to the full name and version of this package. */ +#undef PACKAGE_STRING + +/* Define to the one symbol short name of this package. */ +#undef PACKAGE_TARNAME + +/* Define to the version of this package. */ +#undef PACKAGE_VERSION + +/* Set to maximum allowed value of sf_count_t type. */ +#undef SF_COUNT_MAX + +/* The size of a `double', as computed by sizeof. */ +#undef SIZEOF_DOUBLE + +/* The size of a `float', as computed by sizeof. */ +#undef SIZEOF_FLOAT + +/* The size of a `int', as computed by sizeof. */ +#undef SIZEOF_INT + +/* The size of a `int64_t', as computed by sizeof. */ +#undef SIZEOF_INT64_T + +/* The size of a `loff_t', as computed by sizeof. */ +#undef SIZEOF_LOFF_T + +/* The size of a `long', as computed by sizeof. */ +#undef SIZEOF_LONG + +/* The size of a `long long', as computed by sizeof. */ +#undef SIZEOF_LONG_LONG + +/* The size of a `off64_t', as computed by sizeof. */ +#undef SIZEOF_OFF64_T + +/* The size of a `off_t', as computed by sizeof. */ +#undef SIZEOF_OFF_T + +/* Set to sizeof (long) if unknown. */ +#undef SIZEOF_SF_COUNT_T + +/* The size of a `short', as computed by sizeof. */ +#undef SIZEOF_SHORT + +/* The size of a `size_t', as computed by sizeof. */ +#undef SIZEOF_SIZE_T + +/* The size of a `ssize_t', as computed by sizeof. */ +#undef SIZEOF_SSIZE_T + +/* The size of a `void*', as computed by sizeof. */ +#undef SIZEOF_VOIDP + +/* Define to 1 if you have the ANSI C header files. */ +#undef STDC_HEADERS + +/* Set to long if unknown. */ +#undef TYPEOF_SF_COUNT_T + +/* Set to 1 to use the native windows API */ +#undef USE_WINDOWS_API + +/* Number of bits in a file offset, on hosts where this is settable. */ +#undef _FILE_OFFSET_BITS + +/* Define to make fseeko etc. visible, on some hosts. */ +#undef _LARGEFILE_SOURCE + +/* Define for large files, on AIX-style hosts. */ +#undef _LARGE_FILES diff --git a/libs/libsndfile/src/cygsndfile.def b/libs/libsndfile/src/cygsndfile.def new file mode 100644 index 0000000000..510aa8e229 --- /dev/null +++ b/libs/libsndfile/src/cygsndfile.def @@ -0,0 +1,39 @@ +; Auto-generated by create_symbols_file.py + +LIBRARY cygsndfile-1.dll +EXPORTS + +sf_command @1 +sf_open @2 +sf_close @3 +sf_seek @4 +sf_error @7 +sf_perror @8 +sf_error_str @9 +sf_error_number @10 +sf_format_check @11 +sf_read_raw @16 +sf_readf_short @17 +sf_readf_int @18 +sf_readf_float @19 +sf_readf_double @20 +sf_read_short @21 +sf_read_int @22 +sf_read_float @23 +sf_read_double @24 +sf_write_raw @32 +sf_writef_short @33 +sf_writef_int @34 +sf_writef_float @35 +sf_writef_double @36 +sf_write_short @37 +sf_write_int @38 +sf_write_float @39 +sf_write_double @40 +sf_strerror @50 +sf_get_string @60 +sf_set_string @61 +sf_open_fd @70 +sf_open_virtual @80 +sf_write_sync @90 + diff --git a/libs/libsndfile/src/dither.c b/libs/libsndfile/src/dither.c new file mode 100644 index 0000000000..873f1bbc10 --- /dev/null +++ b/libs/libsndfile/src/dither.c @@ -0,0 +1,535 @@ +/* +** Copyright (C) 2003,2005 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" + +/*============================================================================ +** Rule number 1 is to only apply dither when going from a larger bitwidth +** to a smaller bitwidth. This can happen on both read and write. +** +** Need to apply dither on all conversions marked X below. +** +** Dither on write: +** +** Input +** | short int float double +** --------+----------------------------------------------- +** O 8 bit | X X X X +** u 16 bit | none X X X +** t 24 bit | none X X X +** p 32 bit | none none X X +** u float | none none none none +** t double | none none none none +** +** Dither on read: +** +** Input +** O | 8 bit 16 bit 24 bit 32 bit float double +** u --------+------------------------------------------------- +** t short | none none X X X X +** p int | none none none X X X +** u float | none none none none none none +** t double | none none none none none none +*/ + +#define SFE_DITHER_BAD_PTR 666 +#define SFE_DITHER_BAD_TYPE 667 + +typedef struct +{ int read_short_dither_bits, read_int_dither_bits ; + int write_short_dither_bits, write_int_dither_bits ; + double read_float_dither_scale, read_double_dither_bits ; + double write_float_dither_scale, write_double_dither_bits ; + + sf_count_t (*read_short) (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; + sf_count_t (*read_int) (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; + sf_count_t (*read_float) (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; + sf_count_t (*read_double) (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; + + sf_count_t (*write_short) (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; + sf_count_t (*write_int) (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; + sf_count_t (*write_float) (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; + sf_count_t (*write_double) (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; + + double buffer [SF_BUFFER_LEN / sizeof (double)] ; +} DITHER_DATA ; + +static sf_count_t dither_read_short (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t dither_read_int (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; + +static sf_count_t dither_write_short (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t dither_write_int (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t dither_write_float (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t dither_write_double (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; + +int +dither_init (SF_PRIVATE *psf, int mode) +{ DITHER_DATA *pdither ; + + pdither = psf->dither ; /* This may be NULL. */ + + /* Turn off dither on read. */ + if (mode == SFM_READ && psf->read_dither.type == SFD_NO_DITHER) + { if (pdither == NULL) + return 0 ; /* Dither is already off, so just return. */ + + if (pdither->read_short) + psf->read_short = pdither->read_short ; + if (pdither->read_int) + psf->read_int = pdither->read_int ; + if (pdither->read_float) + psf->read_float = pdither->read_float ; + if (pdither->read_double) + psf->read_double = pdither->read_double ; + return 0 ; + } ; + + /* Turn off dither on write. */ + if (mode == SFM_WRITE && psf->write_dither.type == SFD_NO_DITHER) + { if (pdither == NULL) + return 0 ; /* Dither is already off, so just return. */ + + if (pdither->write_short) + psf->write_short = pdither->write_short ; + if (pdither->write_int) + psf->write_int = pdither->write_int ; + if (pdither->write_float) + psf->write_float = pdither->write_float ; + if (pdither->write_double) + psf->write_double = pdither->write_double ; + return 0 ; + } ; + + /* Turn on dither on read if asked. */ + if (mode == SFM_READ && psf->read_dither.type != 0) + { if (pdither == NULL) + pdither = psf->dither = calloc (1, sizeof (DITHER_DATA)) ; + if (pdither == NULL) + return SFE_MALLOC_FAILED ; + + switch (psf->sf.format & SF_FORMAT_SUBMASK) + { case SF_FORMAT_DOUBLE : + case SF_FORMAT_FLOAT : + pdither->read_int = psf->read_int ; + psf->read_int = dither_read_int ; + + case SF_FORMAT_PCM_32 : + case SF_FORMAT_PCM_24 : + case SF_FORMAT_PCM_16 : + case SF_FORMAT_PCM_S8 : + case SF_FORMAT_PCM_U8 : + pdither->read_short = psf->read_short ; + psf->read_short = dither_read_short ; + + default : break ; + } ; + } ; + + /* Turn on dither on write if asked. */ + if (mode == SFM_WRITE && psf->write_dither.type != 0) + { if (pdither == NULL) + pdither = psf->dither = calloc (1, sizeof (DITHER_DATA)) ; + if (pdither == NULL) + return SFE_MALLOC_FAILED ; + + switch (psf->sf.format & SF_FORMAT_SUBMASK) + { case SF_FORMAT_DOUBLE : + case SF_FORMAT_FLOAT : + pdither->write_int = psf->write_int ; + psf->write_int = dither_write_int ; + + case SF_FORMAT_PCM_32 : + case SF_FORMAT_PCM_24 : + case SF_FORMAT_PCM_16 : + case SF_FORMAT_PCM_S8 : + case SF_FORMAT_PCM_U8 : + + default : break ; + } ; + + pdither->write_short = psf->write_short ; + psf->write_short = dither_write_short ; + + pdither->write_int = psf->write_int ; + psf->write_int = dither_write_int ; + + pdither->write_float = psf->write_float ; + psf->write_float = dither_write_float ; + + pdither->write_double = psf->write_double ; + psf->write_double = dither_write_double ; + } ; + + return 0 ; +} /* dither_init */ + +/*============================================================================== +*/ + +static void dither_short (const short *in, short *out, int frames, int channels) ; +static void dither_int (const int *in, int *out, int frames, int channels) ; + +static void dither_float (const float *in, float *out, int frames, int channels) ; +static void dither_double (const double *in, double *out, int frames, int channels) ; + +static sf_count_t +dither_read_short (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ psf = psf ; + ptr = ptr ; + return len ; +} /* dither_read_short */ + +static sf_count_t +dither_read_int (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ psf = psf ; + ptr = ptr ; + return len ; +} /* dither_read_int */ + +/*------------------------------------------------------------------------------ +*/ + +static sf_count_t +dither_write_short (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ DITHER_DATA *pdither ; + int bufferlen, writecount, thiswrite ; + sf_count_t total = 0 ; + + if ((pdither = psf->dither) == NULL) + { psf->error = SFE_DITHER_BAD_PTR ; + return 0 ; + } ; + + switch (psf->sf.format & SF_FORMAT_SUBMASK) + { case SF_FORMAT_PCM_S8 : + case SF_FORMAT_PCM_U8 : + case SF_FORMAT_DPCM_8 : + break ; + + default : + return pdither->write_short (psf, ptr, len) ; + } ; + + bufferlen = sizeof (pdither->buffer) / sizeof (short) ; + + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : (int) len ; + writecount /= psf->sf.channels ; + writecount *= psf->sf.channels ; + + dither_short (ptr, (short*) pdither->buffer, writecount / psf->sf.channels, psf->sf.channels) ; + + thiswrite = pdither->write_short (psf, (short*) pdither->buffer, writecount) ; + total += thiswrite ; + len -= thiswrite ; + if (thiswrite < writecount) + break ; + } ; + + return total ; +} /* dither_write_short */ + +static sf_count_t +dither_write_int (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ DITHER_DATA *pdither ; + int bufferlen, writecount, thiswrite ; + sf_count_t total = 0 ; + + if ((pdither = psf->dither) == NULL) + { psf->error = SFE_DITHER_BAD_PTR ; + return 0 ; + } ; + + switch (psf->sf.format & SF_FORMAT_SUBMASK) + { case SF_FORMAT_PCM_S8 : + case SF_FORMAT_PCM_U8 : + case SF_FORMAT_PCM_16 : + case SF_FORMAT_PCM_24 : + + case SF_FORMAT_DPCM_8 : + case SF_FORMAT_DPCM_16 : + break ; + + default : + return pdither->write_int (psf, ptr, len) ; + } ; + + + bufferlen = sizeof (pdither->buffer) / sizeof (int) ; + + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : (int) len ; + writecount /= psf->sf.channels ; + writecount *= psf->sf.channels ; + + dither_int (ptr, (int*) pdither->buffer, writecount / psf->sf.channels, psf->sf.channels) ; + + thiswrite = pdither->write_int (psf, (int*) pdither->buffer, writecount) ; + total += thiswrite ; + len -= thiswrite ; + if (thiswrite < writecount) + break ; + } ; + + return total ; +} /* dither_write_int */ + +static sf_count_t +dither_write_float (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ DITHER_DATA *pdither ; + int bufferlen, writecount, thiswrite ; + sf_count_t total = 0 ; + + if ((pdither = psf->dither) == NULL) + { psf->error = SFE_DITHER_BAD_PTR ; + return 0 ; + } ; + + switch (psf->sf.format & SF_FORMAT_SUBMASK) + { case SF_FORMAT_PCM_S8 : + case SF_FORMAT_PCM_U8 : + case SF_FORMAT_PCM_16 : + case SF_FORMAT_PCM_24 : + + case SF_FORMAT_DPCM_8 : + case SF_FORMAT_DPCM_16 : + break ; + + default : + return pdither->write_float (psf, ptr, len) ; + } ; + + bufferlen = sizeof (pdither->buffer) / sizeof (float) ; + + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : (float) len ; + writecount /= psf->sf.channels ; + writecount *= psf->sf.channels ; + + dither_float (ptr, (float*) pdither->buffer, writecount / psf->sf.channels, psf->sf.channels) ; + + thiswrite = pdither->write_float (psf, (float*) pdither->buffer, writecount) ; + total += thiswrite ; + len -= thiswrite ; + if (thiswrite < writecount) + break ; + } ; + + return total ; +} /* dither_write_float */ + +static sf_count_t +dither_write_double (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ DITHER_DATA *pdither ; + int bufferlen, writecount, thiswrite ; + sf_count_t total = 0 ; + + if ((pdither = psf->dither) == NULL) + { psf->error = SFE_DITHER_BAD_PTR ; + return 0 ; + } ; + + switch (psf->sf.format & SF_FORMAT_SUBMASK) + { case SF_FORMAT_PCM_S8 : + case SF_FORMAT_PCM_U8 : + case SF_FORMAT_PCM_16 : + case SF_FORMAT_PCM_24 : + + case SF_FORMAT_DPCM_8 : + case SF_FORMAT_DPCM_16 : + break ; + + default : + return pdither->write_double (psf, ptr, len) ; + } ; + + + bufferlen = sizeof (pdither->buffer) / sizeof (double) ; + + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : (double) len ; + writecount /= psf->sf.channels ; + writecount *= psf->sf.channels ; + + dither_double (ptr, (double*) pdither->buffer, writecount / psf->sf.channels, psf->sf.channels) ; + + thiswrite = pdither->write_double (psf, (double*) pdither->buffer, writecount) ; + total += thiswrite ; + len -= thiswrite ; + if (thiswrite < writecount) + break ; + } ; + + return total ; +} /* dither_write_double */ + +/*============================================================================== +*/ + +static void +dither_short (const short *in, short *out, int frames, int channels) +{ int ch, k ; + + for (ch = 0 ; ch < channels ; ch++) + for (k = ch ; k < channels * frames ; k += channels) + out [k] = in [k] ; + +} /* dither_short */ + +static void +dither_int (const int *in, int *out, int frames, int channels) +{ int ch, k ; + + for (ch = 0 ; ch < channels ; ch++) + for (k = ch ; k < channels * frames ; k += channels) + out [k] = in [k] ; + +} /* dither_int */ + +static void +dither_float (const float *in, float *out, int frames, int channels) +{ int ch, k ; + + for (ch = 0 ; ch < channels ; ch++) + for (k = ch ; k < channels * frames ; k += channels) + out [k] = in [k] ; + +} /* dither_float */ + +static void +dither_double (const double *in, double *out, int frames, int channels) +{ int ch, k ; + + for (ch = 0 ; ch < channels ; ch++) + for (k = ch ; k < channels * frames ; k += channels) + out [k] = in [k] ; + +} /* dither_double */ + +/*============================================================================== +*/ +#if 0 + +/* +** Not made public because this (maybe) requires storage of state information. +** +** Also maybe need separate state info for each channel!!!! +*/ + +int +DO_NOT_USE_sf_dither_short (const SF_DITHER_INFO *dither, const short *in, short *out, int frames, int channels) +{ int ch, k ; + + if (! dither) + return SFE_DITHER_BAD_PTR ; + + switch (dither->type & SFD_TYPEMASK) + { case SFD_WHITE : + case SFD_TRIANGULAR_PDF : + for (ch = 0 ; ch < channels ; ch++) + for (k = ch ; k < channels * frames ; k += channels) + out [k] = in [k] ; + break ; + + default : + return SFE_DITHER_BAD_TYPE ; + } ; + + return 0 ; +} /* DO_NOT_USE_sf_dither_short */ + +int +DO_NOT_USE_sf_dither_int (const SF_DITHER_INFO *dither, const int *in, int *out, int frames, int channels) +{ int ch, k ; + + if (! dither) + return SFE_DITHER_BAD_PTR ; + + switch (dither->type & SFD_TYPEMASK) + { case SFD_WHITE : + case SFD_TRIANGULAR_PDF : + for (ch = 0 ; ch < channels ; ch++) + for (k = ch ; k < channels * frames ; k += channels) + out [k] = in [k] ; + break ; + + default : + return SFE_DITHER_BAD_TYPE ; + } ; + + return 0 ; +} /* DO_NOT_USE_sf_dither_int */ + +int +DO_NOT_USE_sf_dither_float (const SF_DITHER_INFO *dither, const float *in, float *out, int frames, int channels) +{ int ch, k ; + + if (! dither) + return SFE_DITHER_BAD_PTR ; + + switch (dither->type & SFD_TYPEMASK) + { case SFD_WHITE : + case SFD_TRIANGULAR_PDF : + for (ch = 0 ; ch < channels ; ch++) + for (k = ch ; k < channels * frames ; k += channels) + out [k] = in [k] ; + break ; + + default : + return SFE_DITHER_BAD_TYPE ; + } ; + + return 0 ; +} /* DO_NOT_USE_sf_dither_float */ + +int +DO_NOT_USE_sf_dither_double (const SF_DITHER_INFO *dither, const double *in, double *out, int frames, int channels) +{ int ch, k ; + + if (! dither) + return SFE_DITHER_BAD_PTR ; + + switch (dither->type & SFD_TYPEMASK) + { case SFD_WHITE : + case SFD_TRIANGULAR_PDF : + for (ch = 0 ; ch < channels ; ch++) + for (k = ch ; k < channels * frames ; k += channels) + out [k] = in [k] ; + break ; + + default : + return SFE_DITHER_BAD_TYPE ; + } ; + + return 0 ; +} /* DO_NOT_USE_sf_dither_double */ + +#endif +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 673fad58-5314-421c-9144-9d54bfdf104c +*/ diff --git a/libs/libsndfile/src/double64.c b/libs/libsndfile/src/double64.c new file mode 100644 index 0000000000..9a6f8f1196 --- /dev/null +++ b/libs/libsndfile/src/double64.c @@ -0,0 +1,1009 @@ +/* +** Copyright (C) 1999-2005 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" +#include "float_cast.h" + +#if CPU_IS_LITTLE_ENDIAN + #define DOUBLE64_READ double64_le_read + #define DOUBLE64_WRITE double64_le_write +#elif CPU_IS_BIG_ENDIAN + #define DOUBLE64_READ double64_be_read + #define DOUBLE64_WRITE double64_be_write +#endif + +/* A 32 number which will not overflow when multiplied by sizeof (double). */ +#define SENSIBLE_LEN (0x8000000) + +/*-------------------------------------------------------------------------------------------- +** Processor floating point capabilities. double64_get_capability () returns one of the +** latter three values. +*/ + +enum +{ DOUBLE_UNKNOWN = 0x00, + DOUBLE_CAN_RW_LE = 0x23, + DOUBLE_CAN_RW_BE = 0x34, + DOUBLE_BROKEN_LE = 0x45, + DOUBLE_BROKEN_BE = 0x56 +} ; + +/*-------------------------------------------------------------------------------------------- +** Prototypes for private functions. +*/ + +static sf_count_t host_read_d2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t host_read_d2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t host_read_d2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t host_read_d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; + +static sf_count_t host_write_s2d (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t host_write_i2d (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t host_write_f2d (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t host_write_d (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; + +static void double64_peak_update (SF_PRIVATE *psf, const double *buffer, int count, sf_count_t indx) ; + +static int double64_get_capability (SF_PRIVATE *psf) ; + +static sf_count_t replace_read_d2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t replace_read_d2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t replace_read_d2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t replace_read_d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; + +static sf_count_t replace_write_s2d (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t replace_write_i2d (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t replace_write_f2d (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t replace_write_d (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; + +static void d2bd_read (double *buffer, int count) ; +static void bd2d_write (double *buffer, int count) ; + +/*-------------------------------------------------------------------------------------------- +** Exported functions. +*/ + +int +double64_init (SF_PRIVATE *psf) +{ static int double64_caps ; + + double64_caps = double64_get_capability (psf) ; + + psf->blockwidth = sizeof (double) * psf->sf.channels ; + + if (psf->mode == SFM_READ || psf->mode == SFM_RDWR) + { switch (psf->endian + double64_caps) + { case (SF_ENDIAN_BIG + DOUBLE_CAN_RW_BE) : + psf->float_endswap = SF_FALSE ; + psf->read_short = host_read_d2s ; + psf->read_int = host_read_d2i ; + psf->read_float = host_read_d2f ; + psf->read_double = host_read_d ; + break ; + + case (SF_ENDIAN_LITTLE + DOUBLE_CAN_RW_LE) : + psf->float_endswap = SF_FALSE ; + psf->read_short = host_read_d2s ; + psf->read_int = host_read_d2i ; + psf->read_float = host_read_d2f ; + psf->read_double = host_read_d ; + break ; + + case (SF_ENDIAN_BIG + DOUBLE_CAN_RW_LE) : + psf->float_endswap = SF_TRUE ; + psf->read_short = host_read_d2s ; + psf->read_int = host_read_d2i ; + psf->read_float = host_read_d2f ; + psf->read_double = host_read_d ; + break ; + + case (SF_ENDIAN_LITTLE + DOUBLE_CAN_RW_BE) : + psf->float_endswap = SF_TRUE ; + psf->read_short = host_read_d2s ; + psf->read_int = host_read_d2i ; + psf->read_float = host_read_d2f ; + psf->read_double = host_read_d ; + break ; + + /* When the CPU is not IEEE compatible. */ + case (SF_ENDIAN_BIG + DOUBLE_BROKEN_BE) : + psf->float_endswap = SF_FALSE ; + psf->read_short = replace_read_d2s ; + psf->read_int = replace_read_d2i ; + psf->read_float = replace_read_d2f ; + psf->read_double = replace_read_d ; + break ; + + case (SF_ENDIAN_LITTLE + DOUBLE_BROKEN_LE) : + psf->float_endswap = SF_FALSE ; + psf->read_short = replace_read_d2s ; + psf->read_int = replace_read_d2i ; + psf->read_float = replace_read_d2f ; + psf->read_double = replace_read_d ; + break ; + + case (SF_ENDIAN_BIG + DOUBLE_BROKEN_LE) : + psf->float_endswap = SF_TRUE ; + psf->read_short = replace_read_d2s ; + psf->read_int = replace_read_d2i ; + psf->read_float = replace_read_d2f ; + psf->read_double = replace_read_d ; + break ; + + case (SF_ENDIAN_LITTLE + DOUBLE_BROKEN_BE) : + psf->float_endswap = SF_TRUE ; + psf->read_short = replace_read_d2s ; + psf->read_int = replace_read_d2i ; + psf->read_float = replace_read_d2f ; + psf->read_double = replace_read_d ; + break ; + + default : break ; + } ; + } ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { switch (psf->endian + double64_caps) + { case (SF_ENDIAN_LITTLE + DOUBLE_CAN_RW_LE) : + psf->float_endswap = SF_FALSE ; + psf->write_short = host_write_s2d ; + psf->write_int = host_write_i2d ; + psf->write_float = host_write_f2d ; + psf->write_double = host_write_d ; + break ; + + case (SF_ENDIAN_BIG + DOUBLE_CAN_RW_BE) : + psf->float_endswap = SF_FALSE ; + psf->write_short = host_write_s2d ; + psf->write_int = host_write_i2d ; + psf->write_float = host_write_f2d ; + psf->write_double = host_write_d ; + break ; + + case (SF_ENDIAN_BIG + DOUBLE_CAN_RW_LE) : + psf->float_endswap = SF_TRUE ; + psf->write_short = host_write_s2d ; + psf->write_int = host_write_i2d ; + psf->write_float = host_write_f2d ; + psf->write_double = host_write_d ; + break ; + + case (SF_ENDIAN_LITTLE + DOUBLE_CAN_RW_BE) : + psf->float_endswap = SF_TRUE ; + psf->write_short = host_write_s2d ; + psf->write_int = host_write_i2d ; + psf->write_float = host_write_f2d ; + psf->write_double = host_write_d ; + break ; + + /* When the CPU is not IEEE compatible. */ + case (SF_ENDIAN_LITTLE + DOUBLE_BROKEN_LE) : + psf->float_endswap = SF_FALSE ; + psf->write_short = replace_write_s2d ; + psf->write_int = replace_write_i2d ; + psf->write_float = replace_write_f2d ; + psf->write_double = replace_write_d ; + break ; + + case (SF_ENDIAN_BIG + DOUBLE_BROKEN_BE) : + psf->float_endswap = SF_FALSE ; + psf->write_short = replace_write_s2d ; + psf->write_int = replace_write_i2d ; + psf->write_float = replace_write_f2d ; + psf->write_double = replace_write_d ; + break ; + + case (SF_ENDIAN_BIG + DOUBLE_BROKEN_LE) : + psf->float_endswap = SF_TRUE ; + psf->write_short = replace_write_s2d ; + psf->write_int = replace_write_i2d ; + psf->write_float = replace_write_f2d ; + psf->write_double = replace_write_d ; + break ; + + case (SF_ENDIAN_LITTLE + DOUBLE_BROKEN_BE) : + psf->float_endswap = SF_TRUE ; + psf->write_short = replace_write_s2d ; + psf->write_int = replace_write_i2d ; + psf->write_float = replace_write_f2d ; + psf->write_double = replace_write_d ; + break ; + + default : break ; + } ; + } ; + + if (psf->filelength > psf->dataoffset) + { psf->datalength = (psf->dataend > 0) ? psf->dataend - psf->dataoffset : + psf->filelength - psf->dataoffset ; + } + else + psf->datalength = 0 ; + + psf->sf.frames = psf->datalength / psf->blockwidth ; + + return 0 ; +} /* double64_init */ + +/*---------------------------------------------------------------------------- +** From : http://www.hpcf.cam.ac.uk/fp_formats.html +** +** 64 bit double precision layout (big endian) +** Sign bit 0 +** Exponent bits 1-11 +** Mantissa bits 12-63 +** Exponent Offset 1023 +** +** double single +** +** +INF 7FF0000000000000 7F800000 +** -INF FFF0000000000000 FF800000 +** NaN 7FF0000000000001 7F800001 +** to to +** 7FFFFFFFFFFFFFFF 7FFFFFFF +** and and +** FFF0000000000001 FF800001 +** to to +** FFFFFFFFFFFFFFFF FFFFFFFF +** +OVER 7FEFFFFFFFFFFFFF 7F7FFFFF +** -OVER FFEFFFFFFFFFFFFF FF7FFFFF +** +UNDER 0010000000000000 00800000 +** -UNDER 8010000000000000 80800000 +*/ + +double +double64_be_read (unsigned char *cptr) +{ int exponent, negative, upper, lower ; + double dvalue ; + + negative = (cptr [0] & 0x80) ? 1 : 0 ; + exponent = ((cptr [0] & 0x7F) << 4) | ((cptr [1] >> 4) & 0xF) ; + + /* Might not have a 64 bit long, so load the mantissa into a double. */ + upper = (((cptr [1] & 0xF) << 24) | (cptr [2] << 16) | (cptr [3] << 8) | cptr [4]) ; + lower = (cptr [5] << 16) | (cptr [6] << 8) | cptr [7] ; + + if (exponent == 0 && upper == 0 && lower == 0) + return 0.0 ; + + dvalue = upper + lower / ((double) 0x1000000) ; + dvalue += 0x10000000 ; + + exponent = exponent - 0x3FF ; + + dvalue = dvalue / ((double) 0x10000000) ; + + if (negative) + dvalue *= -1 ; + + if (exponent > 0) + dvalue *= (1 << exponent) ; + else if (exponent < 0) + dvalue /= (1 << abs (exponent)) ; + + return dvalue ; +} /* double64_be_read */ + +double +double64_le_read (unsigned char *cptr) +{ int exponent, negative, upper, lower ; + double dvalue ; + + negative = (cptr [7] & 0x80) ? 1 : 0 ; + exponent = ((cptr [7] & 0x7F) << 4) | ((cptr [6] >> 4) & 0xF) ; + + /* Might not have a 64 bit long, so load the mantissa into a double. */ + upper = ((cptr [6] & 0xF) << 24) | (cptr [5] << 16) | (cptr [4] << 8) | cptr [3] ; + lower = (cptr [2] << 16) | (cptr [1] << 8) | cptr [0] ; + + if (exponent == 0 && upper == 0 && lower == 0) + return 0.0 ; + + dvalue = upper + lower / ((double) 0x1000000) ; + dvalue += 0x10000000 ; + + exponent = exponent - 0x3FF ; + + dvalue = dvalue / ((double) 0x10000000) ; + + if (negative) + dvalue *= -1 ; + + if (exponent > 0) + dvalue *= (1 << exponent) ; + else if (exponent < 0) + dvalue /= (1 << abs (exponent)) ; + + return dvalue ; +} /* double64_le_read */ + +void +double64_be_write (double in, unsigned char *out) +{ int exponent, mantissa ; + + memset (out, 0, sizeof (double)) ; + + if (fabs (in) < 1e-30) + return ; + + if (in < 0.0) + { in *= -1.0 ; + out [0] |= 0x80 ; + } ; + + in = frexp (in, &exponent) ; + + exponent += 1022 ; + + out [0] |= (exponent >> 4) & 0x7F ; + out [1] |= (exponent << 4) & 0xF0 ; + + in *= 0x20000000 ; + mantissa = lrint (floor (in)) ; + + out [1] |= (mantissa >> 24) & 0xF ; + out [2] = (mantissa >> 16) & 0xFF ; + out [3] = (mantissa >> 8) & 0xFF ; + out [4] = mantissa & 0xFF ; + + in = fmod (in, 1.0) ; + in *= 0x1000000 ; + mantissa = lrint (floor (in)) ; + + out [5] = (mantissa >> 16) & 0xFF ; + out [6] = (mantissa >> 8) & 0xFF ; + out [7] = mantissa & 0xFF ; + + return ; +} /* double64_be_write */ + +void +double64_le_write (double in, unsigned char *out) +{ int exponent, mantissa ; + + memset (out, 0, sizeof (double)) ; + + if (fabs (in) < 1e-30) + return ; + + if (in < 0.0) + { in *= -1.0 ; + out [7] |= 0x80 ; + } ; + + in = frexp (in, &exponent) ; + + exponent += 1022 ; + + out [7] |= (exponent >> 4) & 0x7F ; + out [6] |= (exponent << 4) & 0xF0 ; + + in *= 0x20000000 ; + mantissa = lrint (floor (in)) ; + + out [6] |= (mantissa >> 24) & 0xF ; + out [5] = (mantissa >> 16) & 0xFF ; + out [4] = (mantissa >> 8) & 0xFF ; + out [3] = mantissa & 0xFF ; + + in = fmod (in, 1.0) ; + in *= 0x1000000 ; + mantissa = lrint (floor (in)) ; + + out [2] = (mantissa >> 16) & 0xFF ; + out [1] = (mantissa >> 8) & 0xFF ; + out [0] = mantissa & 0xFF ; + + return ; +} /* double64_le_write */ + +/*============================================================================================== +** Private functions. +*/ + +static void +double64_peak_update (SF_PRIVATE *psf, const double *buffer, int count, sf_count_t indx) +{ int chan ; + int k, position ; + float fmaxval ; + + for (chan = 0 ; chan < psf->sf.channels ; chan++) + { fmaxval = fabs (buffer [chan]) ; + position = 0 ; + for (k = chan ; k < count ; k += psf->sf.channels) + if (fmaxval < fabs (buffer [k])) + { fmaxval = fabs (buffer [k]) ; + position = k ; + } ; + + if (fmaxval > psf->peak_info->peaks [chan].value) + { psf->peak_info->peaks [chan].value = fmaxval ; + psf->peak_info->peaks [chan].position = psf->write_current + indx + (position / psf->sf.channels) ; + } ; + } ; + + return ; +} /* double64_peak_update */ + +static int +double64_get_capability (SF_PRIVATE *psf) +{ union + { double d ; + int i [2] ; + unsigned char c [8] ; + } data ; + + data.d = 1.234567890123456789 ; /* Some abitrary value. */ + + if (! psf->ieee_replace) + { /* If this test is true ints and floats are compatible and little endian. */ + if (data.i [0] == 0x428c59fb && data.i [1] == 0x3ff3c0ca && + data.c [0] == 0xfb && data.c [2] == 0x8c && data.c [4] == 0xca && data.c [6] == 0xf3) + return DOUBLE_CAN_RW_LE ; + + /* If this test is true ints and floats are compatible and big endian. */ + if ((data.i [0] == 0x3ff3c0ca && data.i [1] == 0x428c59fb) && + (data.c [0] == 0x3f && data.c [2] == 0xc0 && data.c [4] == 0x42 && data.c [6] == 0x59)) + return DOUBLE_CAN_RW_BE ; + } ; + + /* Doubles are broken. Don't expect reading or writing to be fast. */ + psf_log_printf (psf, "Using IEEE replacement code for double.\n") ; + + return (CPU_IS_LITTLE_ENDIAN) ? DOUBLE_BROKEN_LE : DOUBLE_BROKEN_BE ; +} /* double64_get_capability */ + +/*======================================================================================= +*/ + +static inline void +d2s_array (const double *src, int count, short *dest, double scale) +{ while (--count >= 0) + { dest [count] = lrint (scale * src [count]) ; + } ; +} /* d2s_array */ + +static inline void +d2i_array (const double *src, int count, int *dest, double scale) +{ while (--count >= 0) + { dest [count] = lrint (scale * src [count]) ; + } ; +} /* d2i_array */ + +static inline void +d2f_array (const double *src, int count, float *dest) +{ while (--count >= 0) + { dest [count] = src [count] ; + } ; +} /* d2f_array */ + +static inline void +s2d_array (const short *src, double *dest, int count) +{ while (--count >= 0) + { dest [count] = src [count] ; + } ; +} /* s2d_array */ + +static inline void +i2d_array (const int *src, double *dest, int count) +{ while (--count >= 0) + { dest [count] = src [count] ; + } ; +} /* i2d_array */ + +static inline void +f2d_array (const float *src, double *dest, int count) +{ while (--count >= 0) + { dest [count] = src [count] ; + } ; +} /* f2d_array */ + +/*---------------------------------------------------------------------------------------------- +*/ + +static sf_count_t +host_read_d2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + double scale ; + + bufferlen = ARRAY_LEN (psf->u.dbuf) ; + scale = (psf->float_int_mult == 0) ? 1.0 : 0x7FFF / psf->float_max ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.dbuf, sizeof (double), bufferlen, psf) ; + + if (psf->float_endswap == SF_TRUE) + endswap_double_array (psf->u.dbuf, readcount) ; + + d2s_array (psf->u.dbuf, readcount, ptr + total, scale) ; + total += readcount ; + len -= readcount ; + if (readcount < bufferlen) + break ; + } ; + + return total ; +} /* host_read_d2s */ + +static sf_count_t +host_read_d2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + double scale ; + bufferlen = ARRAY_LEN (psf->u.dbuf) ; + scale = (psf->float_int_mult == 0) ? 1.0 : 0x7FFFFFFF / psf->float_max ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.dbuf, sizeof (double), bufferlen, psf) ; + + if (psf->float_endswap == SF_TRUE) + endswap_double_array (psf->u.dbuf, bufferlen) ; + + d2i_array (psf->u.dbuf, readcount, ptr + total, scale) ; + total += readcount ; + len -= readcount ; + if (readcount < bufferlen) + break ; + } ; + + return total ; +} /* host_read_d2i */ + +static sf_count_t +host_read_d2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.dbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.dbuf, sizeof (double), bufferlen, psf) ; + + if (psf->float_endswap == SF_TRUE) + endswap_double_array (psf->u.dbuf, bufferlen) ; + + d2f_array (psf->u.dbuf, readcount, ptr + total) ; + total += readcount ; + len -= readcount ; + if (readcount < bufferlen) + break ; + } ; + + return total ; +} /* host_read_d2f */ + +static sf_count_t +host_read_d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ int bufferlen ; + sf_count_t readcount, total = 0 ; + + readcount = psf_fread (ptr, sizeof (double), len, psf) ; + + if (psf->float_endswap != SF_TRUE) + return readcount ; + + /* If the read length was sensible, endswap output in one go. */ + if (readcount < SENSIBLE_LEN) + { endswap_double_array (ptr, readcount) ; + return readcount ; + } ; + + bufferlen = SENSIBLE_LEN ; + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + + endswap_double_array (ptr + total, bufferlen) ; + + total += bufferlen ; + len -= bufferlen ; + } ; + + return total ; +} /* host_read_d */ + +static sf_count_t +host_write_s2d (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.dbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + + s2d_array (ptr + total, psf->u.dbuf, bufferlen) ; + + if (psf->peak_info) + double64_peak_update (psf, psf->u.dbuf, bufferlen, total / psf->sf.channels) ; + + if (psf->float_endswap == SF_TRUE) + endswap_double_array (psf->u.dbuf, bufferlen) ; + + writecount = psf_fwrite (psf->u.dbuf, sizeof (double), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* host_write_s2d */ + +static sf_count_t +host_write_i2d (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.dbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + i2d_array (ptr + total, psf->u.dbuf, bufferlen) ; + + if (psf->peak_info) + double64_peak_update (psf, psf->u.dbuf, bufferlen, total / psf->sf.channels) ; + + if (psf->float_endswap == SF_TRUE) + endswap_double_array (psf->u.dbuf, bufferlen) ; + + writecount = psf_fwrite (psf->u.dbuf, sizeof (double), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* host_write_i2d */ + +static sf_count_t +host_write_f2d (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.dbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + f2d_array (ptr + total, psf->u.dbuf, bufferlen) ; + + if (psf->peak_info) + double64_peak_update (psf, psf->u.dbuf, bufferlen, total / psf->sf.channels) ; + + if (psf->float_endswap == SF_TRUE) + endswap_double_array (psf->u.dbuf, bufferlen) ; + + writecount = psf_fwrite (psf->u.dbuf, sizeof (double), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* host_write_f2d */ + +static sf_count_t +host_write_d (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + if (psf->peak_info) + double64_peak_update (psf, ptr, len, 0) ; + + if (psf->float_endswap != SF_TRUE) + return psf_fwrite (ptr, sizeof (double), len, psf) ; + + bufferlen = ARRAY_LEN (psf->u.dbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + + endswap_double_copy (psf->u.dbuf, ptr + total, bufferlen) ; + + writecount = psf_fwrite (psf->u.dbuf, sizeof (double), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* host_write_d */ + +/*======================================================================================= +*/ + +static sf_count_t +replace_read_d2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + double scale ; + + bufferlen = ARRAY_LEN (psf->u.dbuf) ; + scale = (psf->float_int_mult == 0) ? 1.0 : 0x7FFF / psf->float_max ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.dbuf, sizeof (double), bufferlen, psf) ; + + if (psf->float_endswap == SF_TRUE) + endswap_double_array (psf->u.dbuf, bufferlen) ; + + d2bd_read (psf->u.dbuf, bufferlen) ; + + d2s_array (psf->u.dbuf, readcount, ptr + total, scale) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* replace_read_d2s */ + +static sf_count_t +replace_read_d2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + double scale ; + + bufferlen = ARRAY_LEN (psf->u.dbuf) ; + scale = (psf->float_int_mult == 0) ? 1.0 : 0x7FFFFFFF / psf->float_max ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.dbuf, sizeof (double), bufferlen, psf) ; + + if (psf->float_endswap == SF_TRUE) + endswap_double_array (psf->u.dbuf, bufferlen) ; + + d2bd_read (psf->u.dbuf, bufferlen) ; + + d2i_array (psf->u.dbuf, readcount, ptr + total, scale) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* replace_read_d2i */ + +static sf_count_t +replace_read_d2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.dbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.dbuf, sizeof (double), bufferlen, psf) ; + + if (psf->float_endswap == SF_TRUE) + endswap_double_array (psf->u.dbuf, bufferlen) ; + + d2bd_read (psf->u.dbuf, bufferlen) ; + + memcpy (ptr + total, psf->u.dbuf, bufferlen * sizeof (double)) ; + + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* replace_read_d2f */ + +static sf_count_t +replace_read_d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + + /* FIXME : This is probably nowhere near optimal. */ + bufferlen = ARRAY_LEN (psf->u.dbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.dbuf, sizeof (double), bufferlen, psf) ; + + if (psf->float_endswap == SF_TRUE) + endswap_double_array (psf->u.dbuf, readcount) ; + + d2bd_read (psf->u.dbuf, readcount) ; + + memcpy (ptr + total, psf->u.dbuf, readcount * sizeof (double)) ; + + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* replace_read_d */ + +static sf_count_t +replace_write_s2d (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.dbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + s2d_array (ptr + total, psf->u.dbuf, bufferlen) ; + + if (psf->peak_info) + double64_peak_update (psf, psf->u.dbuf, bufferlen, total / psf->sf.channels) ; + + bd2d_write (psf->u.dbuf, bufferlen) ; + + if (psf->float_endswap == SF_TRUE) + endswap_double_array (psf->u.dbuf, bufferlen) ; + + writecount = psf_fwrite (psf->u.dbuf, sizeof (double), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* replace_write_s2d */ + +static sf_count_t +replace_write_i2d (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.dbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + i2d_array (ptr + total, psf->u.dbuf, bufferlen) ; + + if (psf->peak_info) + double64_peak_update (psf, psf->u.dbuf, bufferlen, total / psf->sf.channels) ; + + bd2d_write (psf->u.dbuf, bufferlen) ; + + if (psf->float_endswap == SF_TRUE) + endswap_double_array (psf->u.dbuf, bufferlen) ; + + writecount = psf_fwrite (psf->u.dbuf, sizeof (double), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* replace_write_i2d */ + +static sf_count_t +replace_write_f2d (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.dbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + f2d_array (ptr + total, psf->u.dbuf, bufferlen) ; + + bd2d_write (psf->u.dbuf, bufferlen) ; + + if (psf->float_endswap == SF_TRUE) + endswap_double_array (psf->u.dbuf, bufferlen) ; + + writecount = psf_fwrite (psf->u.dbuf, sizeof (double), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* replace_write_f2d */ + +static sf_count_t +replace_write_d (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + /* FIXME : This is probably nowhere near optimal. */ + if (psf->peak_info) + double64_peak_update (psf, ptr, len, 0) ; + + bufferlen = ARRAY_LEN (psf->u.dbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + + memcpy (psf->u.dbuf, ptr + total, bufferlen * sizeof (double)) ; + + bd2d_write (psf->u.dbuf, bufferlen) ; + + if (psf->float_endswap == SF_TRUE) + endswap_double_array (psf->u.dbuf, bufferlen) ; + + writecount = psf_fwrite (psf->u.dbuf, sizeof (double), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* replace_write_d */ + +/*---------------------------------------------------------------------------------------------- +*/ + +static void +d2bd_read (double *buffer, int count) +{ while (--count >= 0) + { buffer [count] = DOUBLE64_READ ((unsigned char *) (buffer + count)) ; + } ; +} /* d2bd_read */ + +static void +bd2d_write (double *buffer, int count) +{ while (--count >= 0) + { DOUBLE64_WRITE (buffer [count], (unsigned char*) (buffer + count)) ; + } ; +} /* bd2d_write */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 4ee243b7-8c7a-469b-869c-e9aa0ee3b77f +*/ diff --git a/libs/libsndfile/src/dwd.c b/libs/libsndfile/src/dwd.c new file mode 100644 index 0000000000..a33bae0c8e --- /dev/null +++ b/libs/libsndfile/src/dwd.c @@ -0,0 +1,210 @@ +/* +** Copyright (C) 2002-2004 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" + +#if (ENABLE_EXPERIMENTAL_CODE == 0) + +int +dwd_open (SF_PRIVATE *psf) +{ if (psf) + return SFE_UNIMPLEMENTED ; + return (psf && 0) ; +} /* dwd_open */ + +#else + +/*------------------------------------------------------------------------------ +** Macros to handle big/little endian issues. +*/ + +#define SFE_DWD_NO_DWD 1666 +#define SFE_DWD_BAND_BIT_WIDTH 1667 +#define SFE_DWD_COMPRESSION 1668 + +#define DWD_IDENTIFIER "DiamondWare Digitized\n\0\x1a" +#define DWD_IDENTIFIER_LEN 24 + +#define DWD_HEADER_LEN 57 + +/*------------------------------------------------------------------------------ +** Typedefs. +*/ + +/*------------------------------------------------------------------------------ +** Private static functions. +*/ + +static int dwd_read_header (SF_PRIVATE *psf) ; + +static int dwd_close (SF_PRIVATE *psf) ; + +/*------------------------------------------------------------------------------ +** Public function. +*/ + +int +dwd_open (SF_PRIVATE *psf) +{ int subformat, error = 0 ; + + if (psf->mode == SFM_READ || (psf->mode == SFM_RDWR && psf->filelength > 0)) + { if ((error = dwd_read_header (psf))) + return error ; + } ; + + if ((psf->sf.format & SF_FORMAT_TYPEMASK) != SF_FORMAT_DWD) + return SFE_BAD_OPEN_FORMAT ; + + subformat = psf->sf.format & SF_FORMAT_SUBMASK ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { + /*-psf->endian = psf->sf.format & SF_FORMAT_ENDMASK ; + if (CPU_IS_LITTLE_ENDIAN && psf->endian == SF_ENDIAN_CPU) + psf->endian = SF_ENDIAN_LITTLE ; + else if (psf->endian != SF_ENDIAN_LITTLE) + psf->endian = SF_ENDIAN_BIG ; + + if (! (encoding = dwd_write_header (psf, SF_FALSE))) + return psf->error ; + + psf->write_header = dwd_write_header ; + -*/ + } ; + + psf->container_close = dwd_close ; + + /*-psf->blockwidth = psf->bytewidth * psf->sf.channels ;-*/ + + return error ; +} /* dwd_open */ + +/*------------------------------------------------------------------------------ +*/ + +static int +dwd_close (SF_PRIVATE *psf) +{ + psf = psf ; + + return 0 ; +} /* dwd_close */ + +/* This struct contains all the fields of interest om the DWD header, but does not +** do so in the same order and layout as the actual file, header. +** No assumptions are made about the packing of this struct. +*/ +typedef struct +{ unsigned char major, minor, compression, channels, bitwidth ; + unsigned short srate, maxval ; + unsigned int id, datalen, frames, offset ; +} DWD_HEADER ; + +static int +dwd_read_header (SF_PRIVATE *psf) +{ DWD_HEADER dwdh ; + + memset (psf->u.cbuf, 0, sizeof (psf->u.cbuf)) ; + /* Set position to start of file to begin reading header. */ + psf_binheader_readf (psf, "pb", 0, psf->u.cbuf, DWD_IDENTIFIER_LEN) ; + + if (memcmp (psf->u.cbuf, DWD_IDENTIFIER, DWD_IDENTIFIER_LEN) != 0) + return SFE_DWD_NO_DWD ; + + psf_log_printf (psf, "Read only : DiamondWare Digitized (.dwd)\n", psf->u.cbuf) ; + + psf_binheader_readf (psf, "11", &dwdh.major, &dwdh.minor) ; + psf_binheader_readf (psf, "e4j1", &dwdh.id, 1, &dwdh.compression) ; + psf_binheader_readf (psf, "e211", &dwdh.srate, &dwdh.channels, &dwdh.bitwidth) ; + psf_binheader_readf (psf, "e24", &dwdh.maxval, &dwdh.datalen) ; + psf_binheader_readf (psf, "e44", &dwdh.frames, &dwdh.offset) ; + + psf_log_printf (psf, " Version Major : %d\n Version Minor : %d\n Unique ID : %08X\n", + dwdh.major, dwdh.minor, dwdh.id) ; + psf_log_printf (psf, " Compression : %d => ", dwdh.compression) ; + + if (dwdh.compression != 0) + { psf_log_printf (psf, "Unsupported compression\n") ; + return SFE_DWD_COMPRESSION ; + } + else + psf_log_printf (psf, "None\n") ; + + psf_log_printf (psf, " Sample Rate : %d\n Channels : %d\n" + " Bit Width : %d\n", + dwdh.srate, dwdh.channels, dwdh.bitwidth) ; + + switch (dwdh.bitwidth) + { case 8 : + psf->sf.format = SF_FORMAT_DWD | SF_FORMAT_PCM_S8 ; + psf->bytewidth = 1 ; + break ; + + case 16 : + psf->sf.format = SF_FORMAT_DWD | SF_FORMAT_PCM_16 ; + psf->bytewidth = 2 ; + break ; + + default : + psf_log_printf (psf, "*** Bad bit width %d\n", dwdh.bitwidth) ; + return SFE_DWD_BAND_BIT_WIDTH ; + } ; + + if (psf->filelength != dwdh.offset + dwdh.datalen) + { psf_log_printf (psf, " Data Length : %d (should be %D)\n", dwdh.datalen, psf->filelength - dwdh.offset) ; + dwdh.datalen = (unsigned int) (psf->filelength - dwdh.offset) ; + } + else + psf_log_printf (psf, " Data Length : %d\n", dwdh.datalen) ; + + psf_log_printf (psf, " Max Value : %d\n", dwdh.maxval) ; + psf_log_printf (psf, " Frames : %d\n", dwdh.frames) ; + psf_log_printf (psf, " Data Offset : %d\n", dwdh.offset) ; + + psf->datalength = dwdh.datalen ; + psf->dataoffset = dwdh.offset ; + + psf->endian = SF_ENDIAN_LITTLE ; + + psf->sf.samplerate = dwdh.srate ; + psf->sf.channels = dwdh.channels ; + psf->sf.sections = 1 ; + + return pcm_init (psf) ; +} /* dwd_read_header */ + +/*------------------------------------------------------------------------------ +*/ + +#endif +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: a5e1d2a6-a840-4039-a0e7-e1a43eb05a4f +*/ diff --git a/libs/libsndfile/src/dwvw.c b/libs/libsndfile/src/dwvw.c new file mode 100644 index 0000000000..dc9ae774bb --- /dev/null +++ b/libs/libsndfile/src/dwvw.c @@ -0,0 +1,671 @@ +/* +** Copyright (C) 2002-2005 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +/*=========================================================================== +** Delta Word Variable Width +** +** This decoder and encoder were implemented using information found in this +** document : http://home.swbell.net/rubywand/R011SNDFMTS.TXT +** +** According to the document, the algorithm "was invented 1991 by Magnus +** Lidstrom and is copyright 1993 by NuEdge Development". +*/ + +#include "sfconfig.h" + +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "float_cast.h" +#include "common.h" + +typedef struct +{ int dwm_maxsize, bit_width, max_delta, span ; + int samplecount ; + int bit_count, bits, last_delta_width, last_sample ; + struct + { int index, end ; + unsigned char buffer [256] ; + } b ; +} DWVW_PRIVATE ; + +/*============================================================================================ +*/ + +static sf_count_t dwvw_read_s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t dwvw_read_i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t dwvw_read_f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t dwvw_read_d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; + +static sf_count_t dwvw_write_s (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t dwvw_write_i (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t dwvw_write_f (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t dwvw_write_d (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; + +static sf_count_t dwvw_seek (SF_PRIVATE *psf, int mode, sf_count_t offset) ; +static int dwvw_close (SF_PRIVATE *psf) ; + +static int dwvw_decode_data (SF_PRIVATE *psf, DWVW_PRIVATE *pdwvw, int *ptr, int len) ; +static int dwvw_decode_load_bits (SF_PRIVATE *psf, DWVW_PRIVATE *pdwvw, int bit_count) ; + +static int dwvw_encode_data (SF_PRIVATE *psf, DWVW_PRIVATE *pdwvw, const int *ptr, int len) ; +static void dwvw_encode_store_bits (SF_PRIVATE *psf, DWVW_PRIVATE *pdwvw, int data, int new_bits) ; +static void dwvw_read_reset (DWVW_PRIVATE *pdwvw) ; + +/*============================================================================================ +** DWVW initialisation function. +*/ + +int +dwvw_init (SF_PRIVATE *psf, int bitwidth) +{ DWVW_PRIVATE *pdwvw ; + + if (psf->fdata != NULL) + { psf_log_printf (psf, "*** psf->fdata is not NULL.\n") ; + return SFE_INTERNAL ; + } ; + + if (bitwidth > 24) + return SFE_DWVW_BAD_BITWIDTH ; + + if (psf->mode == SFM_RDWR) + return SFE_BAD_MODE_RW ; + + if ((pdwvw = calloc (1, sizeof (DWVW_PRIVATE))) == NULL) + return SFE_MALLOC_FAILED ; + + psf->fdata = (void*) pdwvw ; + + pdwvw->bit_width = bitwidth ; + pdwvw->dwm_maxsize = bitwidth / 2 ; + pdwvw->max_delta = 1 << (bitwidth - 1) ; + pdwvw->span = 1 << bitwidth ; + + dwvw_read_reset (pdwvw) ; + + if (psf->mode == SFM_READ) + { psf->read_short = dwvw_read_s ; + psf->read_int = dwvw_read_i ; + psf->read_float = dwvw_read_f ; + psf->read_double = dwvw_read_d ; + } ; + + if (psf->mode == SFM_WRITE) + { psf->write_short = dwvw_write_s ; + psf->write_int = dwvw_write_i ; + psf->write_float = dwvw_write_f ; + psf->write_double = dwvw_write_d ; + } ; + + psf->codec_close = dwvw_close ; + psf->seek = dwvw_seek ; + + /* FIXME : This is bogus. */ + psf->sf.frames = SF_COUNT_MAX ; + psf->datalength = psf->sf.frames ; + /* EMXIF : This is bogus. */ + + return 0 ; +} /* dwvw_init */ + +/*-------------------------------------------------------------------------------------------- +*/ + +static int +dwvw_close (SF_PRIVATE *psf) +{ DWVW_PRIVATE *pdwvw ; + + if (psf->fdata == NULL) + return 0 ; + pdwvw = (DWVW_PRIVATE*) psf->fdata ; + + if (psf->mode == SFM_WRITE) + { static int last_values [12] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 } ; + + /* Write 8 zero samples to fully flush output. */ + dwvw_encode_data (psf, pdwvw, last_values, 12) ; + + /* Write the last buffer worth of data to disk. */ + psf_fwrite (pdwvw->b.buffer, 1, pdwvw->b.index, psf) ; + + if (psf->write_header) + psf->write_header (psf, SF_TRUE) ; + } ; + + return 0 ; +} /* dwvw_close */ + +static sf_count_t +dwvw_seek (SF_PRIVATE *psf, int mode, sf_count_t offset) +{ DWVW_PRIVATE *pdwvw ; + + mode = mode ; + + if (! psf->fdata) + { psf->error = SFE_INTERNAL ; + return PSF_SEEK_ERROR ; + } ; + + pdwvw = (DWVW_PRIVATE*) psf->fdata ; + + if (offset == 0) + { psf_fseek (psf, psf->dataoffset, SEEK_SET) ; + dwvw_read_reset (pdwvw) ; + return 0 ; + } ; + + psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; +} /* dwvw_seek */ + + +/*============================================================================== +*/ + +static sf_count_t +dwvw_read_s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ DWVW_PRIVATE *pdwvw ; + int *iptr ; + int k, bufferlen, readcount = 0, count ; + sf_count_t total = 0 ; + + if (! psf->fdata) + return 0 ; + pdwvw = (DWVW_PRIVATE*) psf->fdata ; + + iptr = psf->u.ibuf ; + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : len ; + count = dwvw_decode_data (psf, pdwvw, iptr, readcount) ; + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = iptr [k] >> 16 ; + + total += count ; + len -= readcount ; + if (count != readcount) + break ; + } ; + + return total ; +} /* dwvw_read_s */ + +static sf_count_t +dwvw_read_i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ DWVW_PRIVATE *pdwvw ; + int readcount, count ; + sf_count_t total = 0 ; + + if (! psf->fdata) + return 0 ; + pdwvw = (DWVW_PRIVATE*) psf->fdata ; + + while (len > 0) + { readcount = (len > 0x10000000) ? 0x10000000 : (int) len ; + + count = dwvw_decode_data (psf, pdwvw, ptr, readcount) ; + + total += count ; + len -= count ; + + if (count != readcount) + break ; + } ; + + return total ; +} /* dwvw_read_i */ + +static sf_count_t +dwvw_read_f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ DWVW_PRIVATE *pdwvw ; + int *iptr ; + int k, bufferlen, readcount = 0, count ; + sf_count_t total = 0 ; + float normfact ; + + if (! psf->fdata) + return 0 ; + pdwvw = (DWVW_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_float == SF_TRUE) ? 1.0 / ((float) 0x80000000) : 1.0 ; + + iptr = psf->u.ibuf ; + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : len ; + count = dwvw_decode_data (psf, pdwvw, iptr, readcount) ; + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = normfact * (float) (iptr [k]) ; + + total += count ; + len -= readcount ; + if (count != readcount) + break ; + } ; + + return total ; +} /* dwvw_read_f */ + +static sf_count_t +dwvw_read_d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ DWVW_PRIVATE *pdwvw ; + int *iptr ; + int k, bufferlen, readcount = 0, count ; + sf_count_t total = 0 ; + double normfact ; + + if (! psf->fdata) + return 0 ; + pdwvw = (DWVW_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_double == SF_TRUE) ? 1.0 / ((double) 0x80000000) : 1.0 ; + + iptr = psf->u.ibuf ; + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : len ; + count = dwvw_decode_data (psf, pdwvw, iptr, readcount) ; + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = normfact * (double) (iptr [k]) ; + + total += count ; + len -= readcount ; + if (count != readcount) + break ; + } ; + + return total ; +} /* dwvw_read_d */ + +static int +dwvw_decode_data (SF_PRIVATE *psf, DWVW_PRIVATE *pdwvw, int *ptr, int len) +{ int count ; + int delta_width_modifier, delta_width, delta_negative, delta, sample ; + + /* Restore state from last decode call. */ + delta_width = pdwvw->last_delta_width ; + sample = pdwvw->last_sample ; + + for (count = 0 ; count < len ; count++) + { /* If bit_count parameter is zero get the delta_width_modifier. */ + delta_width_modifier = dwvw_decode_load_bits (psf, pdwvw, -1) ; + + /* Check for end of input bit stream. Break loop if end. */ + if (delta_width_modifier < 0) + break ; + + if (delta_width_modifier && dwvw_decode_load_bits (psf, pdwvw, 1)) + delta_width_modifier = - delta_width_modifier ; + + /* Calculate the current word width. */ + delta_width = (delta_width + delta_width_modifier + pdwvw->bit_width) % pdwvw->bit_width ; + + /* Load the delta. */ + delta = 0 ; + if (delta_width) + { delta = dwvw_decode_load_bits (psf, pdwvw, delta_width - 1) | (1 << (delta_width - 1)) ; + delta_negative = dwvw_decode_load_bits (psf, pdwvw, 1) ; + if (delta == pdwvw->max_delta - 1) + delta += dwvw_decode_load_bits (psf, pdwvw, 1) ; + if (delta_negative) + delta = -delta ; + } ; + + /* Calculate the sample */ + sample += delta ; + + if (sample >= pdwvw->max_delta) + sample -= pdwvw->span ; + else if (sample < - pdwvw->max_delta) + sample += pdwvw->span ; + + /* Store the sample justifying to the most significant bit. */ + ptr [count] = sample << (32 - pdwvw->bit_width) ; + + if (pdwvw->b.end == 0 && pdwvw->bit_count == 0) + break ; + } ; + + pdwvw->last_delta_width = delta_width ; + pdwvw->last_sample = sample ; + + pdwvw->samplecount += count ; + + return count ; +} /* dwvw_decode_data */ + +static int +dwvw_decode_load_bits (SF_PRIVATE *psf, DWVW_PRIVATE *pdwvw, int bit_count) +{ int output = 0, get_dwm = SF_FALSE ; + + /* + ** Depending on the value of parameter bit_count, either get the + ** required number of bits (ie bit_count > 0) or the + ** delta_width_modifier (otherwise). + */ + + if (bit_count < 0) + { get_dwm = SF_TRUE ; + /* modify bit_count to ensure we have enought bits for finding dwm. */ + bit_count = pdwvw->dwm_maxsize ; + } ; + + /* Load bits in bit reseviour. */ + while (pdwvw->bit_count < bit_count) + { if (pdwvw->b.index >= pdwvw->b.end) + { pdwvw->b.end = psf_fread (pdwvw->b.buffer, 1, sizeof (pdwvw->b.buffer), psf) ; + pdwvw->b.index = 0 ; + } ; + + /* Check for end of input stream. */ + if (bit_count < 8 && pdwvw->b.end == 0) + return -1 ; + + pdwvw->bits = (pdwvw->bits << 8) ; + + if (pdwvw->b.index < pdwvw->b.end) + { pdwvw->bits |= pdwvw->b.buffer [pdwvw->b.index] ; + pdwvw->b.index ++ ; + } ; + pdwvw->bit_count += 8 ; + } ; + + /* If asked to get bits do so. */ + if (! get_dwm) + { output = (pdwvw->bits >> (pdwvw->bit_count - bit_count)) & ((1 << bit_count) - 1) ; + pdwvw->bit_count -= bit_count ; + return output ; + } ; + + /* Otherwise must have been asked to get delta_width_modifier. */ + while (output < (pdwvw->dwm_maxsize)) + { pdwvw->bit_count -= 1 ; + if (pdwvw->bits & (1 << pdwvw->bit_count)) + break ; + output += 1 ; + } ; + + return output ; +} /* dwvw_decode_load_bits */ + +static void +dwvw_read_reset (DWVW_PRIVATE *pdwvw) +{ pdwvw->samplecount = 0 ; + pdwvw->b.index = 0 ; + pdwvw->b.end = 0 ; + pdwvw->bit_count = 0 ; + pdwvw->bits = 0 ; + pdwvw->last_delta_width = 0 ; + pdwvw->last_sample = 0 ; +} /* dwvw_read_reset */ + +static void +dwvw_encode_store_bits (SF_PRIVATE *psf, DWVW_PRIVATE *pdwvw, int data, int new_bits) +{ int byte ; + + /* Shift the bits into the resevoir. */ + pdwvw->bits = (pdwvw->bits << new_bits) | (data & ((1 << new_bits) - 1)) ; + pdwvw->bit_count += new_bits ; + + /* Transfer bit to buffer. */ + while (pdwvw->bit_count >= 8) + { byte = pdwvw->bits >> (pdwvw->bit_count - 8) ; + pdwvw->bit_count -= 8 ; + pdwvw->b.buffer [pdwvw->b.index] = byte & 0xFF ; + pdwvw->b.index ++ ; + } ; + + if (pdwvw->b.index > SIGNED_SIZEOF (pdwvw->b.buffer) - 4) + { psf_fwrite (pdwvw->b.buffer, 1, pdwvw->b.index, psf) ; + pdwvw->b.index = 0 ; + } ; + + return ; +} /* dwvw_encode_store_bits */ + +#if 0 +/* Debigging routine. */ +static void +dump_bits (DWVW_PRIVATE *pdwvw) +{ int k, mask ; + + for (k = 0 ; k < 10 && k < pdwvw->b.index ; k++) + { mask = 0x80 ; + while (mask) + { putchar (mask & pdwvw->b.buffer [k] ? '1' : '0') ; + mask >>= 1 ; + } ; + putchar (' ') ; + } + + for (k = pdwvw->bit_count - 1 ; k >= 0 ; k --) + putchar (pdwvw->bits & (1 << k) ? '1' : '0') ; + + putchar ('\n') ; +} /* dump_bits */ +#endif + +#define HIGHEST_BIT(x,count) \ + { int y = x ; \ + (count) = 0 ; \ + while (y) \ + { (count) ++ ; \ + y >>= 1 ; \ + } ; \ + } ; + +static int +dwvw_encode_data (SF_PRIVATE *psf, DWVW_PRIVATE *pdwvw, const int *ptr, int len) +{ int count ; + int delta_width_modifier, delta, delta_negative, delta_width, extra_bit ; + + for (count = 0 ; count < len ; count++) + { delta = (ptr [count] >> (32 - pdwvw->bit_width)) - pdwvw->last_sample ; + + /* Calculate extra_bit if needed. */ + extra_bit = -1 ; + delta_negative = 0 ; + if (delta < -pdwvw->max_delta) + delta = pdwvw->max_delta + (delta % pdwvw->max_delta) ; + else if (delta == -pdwvw->max_delta) + { extra_bit = 1 ; + delta_negative = 1 ; + delta = pdwvw->max_delta - 1 ; + } + else if (delta > pdwvw->max_delta) + { delta_negative = 1 ; + delta = pdwvw->span - delta ; + delta = abs (delta) ; + } + else if (delta == pdwvw->max_delta) + { extra_bit = 1 ; + delta = pdwvw->max_delta - 1 ; + } + else if (delta < 0) + { delta_negative = 1 ; + delta = abs (delta) ; + } ; + + if (delta == pdwvw->max_delta - 1 && extra_bit == -1) + extra_bit = 0 ; + + /* Find width in bits of delta */ + HIGHEST_BIT (delta, delta_width) ; + + /* Calculate the delta_width_modifier */ + delta_width_modifier = (delta_width - pdwvw->last_delta_width) % pdwvw->bit_width ; + if (delta_width_modifier > pdwvw->dwm_maxsize) + delta_width_modifier -= pdwvw->bit_width ; + if (delta_width_modifier < -pdwvw->dwm_maxsize) + delta_width_modifier += pdwvw->bit_width ; + + /* Write delta_width_modifier zeros, followed by terminating '1'. */ + dwvw_encode_store_bits (psf, pdwvw, 0, abs (delta_width_modifier)) ; + if (abs (delta_width_modifier) != pdwvw->dwm_maxsize) + dwvw_encode_store_bits (psf, pdwvw, 1, 1) ; + + /* Write delta_width_modifier sign. */ + if (delta_width_modifier < 0) + dwvw_encode_store_bits (psf, pdwvw, 1, 1) ; + if (delta_width_modifier > 0) + dwvw_encode_store_bits (psf, pdwvw, 0, 1) ; + + /* Write delta and delta sign bit. */ + if (delta_width) + { dwvw_encode_store_bits (psf, pdwvw, delta, abs (delta_width) - 1) ; + dwvw_encode_store_bits (psf, pdwvw, (delta_negative ? 1 : 0), 1) ; + } ; + + /* Write extra bit!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! */ + if (extra_bit >= 0) + dwvw_encode_store_bits (psf, pdwvw, extra_bit, 1) ; + + pdwvw->last_sample = ptr [count] >> (32 - pdwvw->bit_width) ; + pdwvw->last_delta_width = delta_width ; + } ; + + pdwvw->samplecount += count ; + + return count ; +} /* dwvw_encode_data */ + +static sf_count_t +dwvw_write_s (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ DWVW_PRIVATE *pdwvw ; + int *iptr ; + int k, bufferlen, writecount = 0, count ; + sf_count_t total = 0 ; + + if (! psf->fdata) + return 0 ; + pdwvw = (DWVW_PRIVATE*) psf->fdata ; + + iptr = psf->u.ibuf ; + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : len ; + for (k = 0 ; k < writecount ; k++) + iptr [k] = ptr [total + k] << 16 ; + count = dwvw_encode_data (psf, pdwvw, iptr, writecount) ; + + total += count ; + len -= writecount ; + if (count != writecount) + break ; + } ; + + return total ; +} /* dwvw_write_s */ + +static sf_count_t +dwvw_write_i (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ DWVW_PRIVATE *pdwvw ; + int writecount, count ; + sf_count_t total = 0 ; + + if (! psf->fdata) + return 0 ; + pdwvw = (DWVW_PRIVATE*) psf->fdata ; + + while (len > 0) + { writecount = (len > 0x10000000) ? 0x10000000 : (int) len ; + + count = dwvw_encode_data (psf, pdwvw, ptr, writecount) ; + + total += count ; + len -= count ; + + if (count != writecount) + break ; + } ; + + return total ; +} /* dwvw_write_i */ + +static sf_count_t +dwvw_write_f (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ DWVW_PRIVATE *pdwvw ; + int *iptr ; + int k, bufferlen, writecount = 0, count ; + sf_count_t total = 0 ; + float normfact ; + + if (! psf->fdata) + return 0 ; + pdwvw = (DWVW_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_float == SF_TRUE) ? (1.0 * 0x7FFFFFFF) : 1.0 ; + + iptr = psf->u.ibuf ; + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : len ; + for (k = 0 ; k < writecount ; k++) + iptr [k] = lrintf (normfact * ptr [total + k]) ; + count = dwvw_encode_data (psf, pdwvw, iptr, writecount) ; + + total += count ; + len -= writecount ; + if (count != writecount) + break ; + } ; + + return total ; +} /* dwvw_write_f */ + +static sf_count_t +dwvw_write_d (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ DWVW_PRIVATE *pdwvw ; + int *iptr ; + int k, bufferlen, writecount = 0, count ; + sf_count_t total = 0 ; + double normfact ; + + if (! psf->fdata) + return 0 ; + pdwvw = (DWVW_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_double == SF_TRUE) ? (1.0 * 0x7FFFFFFF) : 1.0 ; + + iptr = psf->u.ibuf ; + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : len ; + for (k = 0 ; k < writecount ; k++) + iptr [k] = lrint (normfact * ptr [total + k]) ; + count = dwvw_encode_data (psf, pdwvw, iptr, writecount) ; + + total += count ; + len -= writecount ; + if (count != writecount) + break ; + } ; + + return total ; +} /* dwvw_write_d */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 1ca09552-b01f-4d7f-9bcf-612f834fe41d +*/ diff --git a/libs/libsndfile/src/file_io.c b/libs/libsndfile/src/file_io.c new file mode 100644 index 0000000000..d80e17d307 --- /dev/null +++ b/libs/libsndfile/src/file_io.c @@ -0,0 +1,1537 @@ +/* +** Copyright (C) 2002-2005 Erik de Castro Lopo +** Copyright (C) 2003 Ross Bencina +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +/* +** The file is split into three sections as follows: +** - The top section (USE_WINDOWS_API == 0) for Linux, Unix and MacOSX +** systems (including Cygwin). +** - The middle section (USE_WINDOWS_API == 1) for microsoft windows +** (including MinGW) using the native windows API. +** - A legacy windows section which attempted to work around grevious +** bugs in microsoft's POSIX implementation. +*/ + +/* +** The header file sfconfig.h MUST be included before the others to ensure +** that large file support is enabled correctly on Unix systems. +*/ + +#include "sfconfig.h" + +#include +#include + +#if HAVE_UNISTD_H +#include +#endif + +#if (HAVE_DECL_S_IRGRP == 0) +#include +#endif + +#include +#include +#include +#include + +#include "sndfile.h" +#include "common.h" + +#define SENSIBLE_SIZE (0x40000000) + +static void psf_log_syserr (SF_PRIVATE *psf, int error) ; + +#if (USE_WINDOWS_API == 0) + +/*------------------------------------------------------------------------------ +** Win32 stuff at the bottom of the file. Unix and other sensible OSes here. +*/ + +static int psf_close_fd (int fd) ; +static int psf_open_fd (const char * path, int mode) ; +static sf_count_t psf_get_filelen_fd (int fd) ; + +int +psf_fopen (SF_PRIVATE *psf, const char *pathname, int open_mode) +{ + psf->error = 0 ; + psf->filedes = psf_open_fd (pathname, open_mode) ; + + if (psf->filedes == - SFE_BAD_OPEN_MODE) + { psf->error = SFE_BAD_OPEN_MODE ; + psf->filedes = -1 ; + return psf->error ; + } ; + + if (psf->filedes == -1) + psf_log_syserr (psf, errno) ; + + psf->mode = open_mode ; + + return psf->error ; +} /* psf_fopen */ + +int +psf_fclose (SF_PRIVATE *psf) +{ int retval ; + + if (psf->virtual_io) + return 0 ; + + if (psf->do_not_close_descriptor) + { psf->filedes = -1 ; + return 0 ; + } ; + + if ((retval = psf_close_fd (psf->filedes)) == -1) + psf_log_syserr (psf, errno) ; + + psf->filedes = -1 ; + + return retval ; +} /* psf_fclose */ + +int +psf_open_rsrc (SF_PRIVATE *psf, int open_mode) +{ + if (psf->rsrcdes > 0) + return 0 ; + + /* Test for MacOSX style resource fork on HPFS or HPFS+ filesystems. */ + LSF_SNPRINTF (psf->rsrcpath, sizeof (psf->rsrcpath), "%s/rsrc", psf->filepath) ; + psf->error = SFE_NO_ERROR ; + if ((psf->rsrcdes = psf_open_fd (psf->rsrcpath, open_mode)) >= 0) + { psf->rsrclength = psf_get_filelen_fd (psf->rsrcdes) ; + if (psf->rsrclength > 0 || (open_mode & SFM_WRITE)) + return SFE_NO_ERROR ; + psf_close_fd (psf->rsrcdes) ; + psf->rsrcdes = -1 ; + } ; + + if (psf->rsrcdes == - SFE_BAD_OPEN_MODE) + { psf->error = SFE_BAD_OPEN_MODE ; + return psf->error ; + } ; + + /* + ** Now try for a resource fork stored as a separate file in the same + ** directory, but preceded with a dot underscore. + */ + LSF_SNPRINTF (psf->rsrcpath, sizeof (psf->rsrcpath), "%s._%s", psf->directory, psf->filename) ; + psf->error = SFE_NO_ERROR ; + if ((psf->rsrcdes = psf_open_fd (psf->rsrcpath, open_mode)) >= 0) + { psf->rsrclength = psf_get_filelen_fd (psf->rsrcdes) ; + return SFE_NO_ERROR ; + } ; + + /* + ** Now try for a resource fork stored in a separate file in the + ** .AppleDouble/ directory. + */ + LSF_SNPRINTF (psf->rsrcpath, sizeof (psf->rsrcpath), "%s.AppleDouble/%s", psf->directory, psf->filename) ; + psf->error = SFE_NO_ERROR ; + if ((psf->rsrcdes = psf_open_fd (psf->rsrcpath, open_mode)) >= 0) + { psf->rsrclength = psf_get_filelen_fd (psf->rsrcdes) ; + return SFE_NO_ERROR ; + } ; + + /* No resource file found. */ + if (psf->rsrcdes == -1) + psf_log_syserr (psf, errno) ; + + psf->rsrcdes = -1 ; + + return psf->error ; +} /* psf_open_rsrc */ + +sf_count_t +psf_get_filelen (SF_PRIVATE *psf) +{ sf_count_t filelen ; + + if (psf->virtual_io) + return psf->vio.get_filelen (psf->vio_user_data) ; + + filelen = psf_get_filelen_fd (psf->filedes) ; + + if (filelen == -1) + { psf_log_syserr (psf, errno) ; + return (sf_count_t) -1 ; + } ; + + if (filelen == -SFE_BAD_STAT_SIZE) + { psf->error = SFE_BAD_STAT_SIZE ; + return (sf_count_t) -1 ; + } ; + + switch (psf->mode) + { case SFM_WRITE : + filelen = filelen - psf->fileoffset ; + break ; + + case SFM_READ : + if (psf->fileoffset > 0 && psf->filelength > 0) + filelen = psf->filelength ; + break ; + + case SFM_RDWR : + /* + ** Cannot open embedded files SFM_RDWR so we don't need to + ** subtract psf->fileoffset. We already have the answer we + ** need. + */ + break ; + + default : + /* Shouldn't be here, so return error. */ + filelen = -1 ; + } ; + + return filelen ; +} /* psf_get_filelen */ + +int +psf_close_rsrc (SF_PRIVATE *psf) +{ + if (psf->rsrcdes >= 0) + psf_close_fd (psf->rsrcdes) ; + psf->rsrcdes = -1 ; + return 0 ; +} /* psf_close_rsrc */ + +int +psf_set_stdio (SF_PRIVATE *psf, int mode) +{ int error = 0 ; + + switch (mode) + { case SFM_RDWR : + error = SFE_OPEN_PIPE_RDWR ; + break ; + + case SFM_READ : + psf->filedes = 0 ; + break ; + + case SFM_WRITE : + psf->filedes = 1 ; + break ; + + default : + error = SFE_BAD_OPEN_MODE ; + break ; + } ; + psf->filelength = 0 ; + + return error ; +} /* psf_set_stdio */ + +void +psf_set_file (SF_PRIVATE *psf, int fd) +{ psf->filedes = fd ; +} /* psf_set_file */ + +int +psf_file_valid (SF_PRIVATE *psf) +{ return (psf->filedes >= 0) ? SF_TRUE : SF_FALSE ; +} /* psf_set_file */ + +sf_count_t +psf_fseek (SF_PRIVATE *psf, sf_count_t offset, int whence) +{ sf_count_t new_position ; + + if (psf->virtual_io) + return psf->vio.seek (offset, whence, psf->vio_user_data) ; + + switch (whence) + { case SEEK_SET : + offset += psf->fileoffset ; + break ; + + case SEEK_END : + if (psf->mode == SFM_WRITE) + { new_position = lseek (psf->filedes, offset, whence) ; + + if (new_position < 0) + psf_log_syserr (psf, errno) ; + + return new_position - psf->fileoffset ; + } ; + + /* Transform SEEK_END into a SEEK_SET, ie find the file + ** length add the requested offset (should be <= 0) to + ** get the offset wrt the start of file. + */ + whence = SEEK_SET ; + offset = lseek (psf->filedes, 0, SEEK_END) + offset ; + break ; + + default : + /* No need to do anything about SEEK_CUR. */ + break ; + } ; + + new_position = lseek (psf->filedes, offset, whence) ; + + if (new_position < 0) + psf_log_syserr (psf, errno) ; + + new_position -= psf->fileoffset ; + + return new_position ; +} /* psf_fseek */ + +sf_count_t +psf_fread (void *ptr, sf_count_t bytes, sf_count_t items, SF_PRIVATE *psf) +{ sf_count_t total = 0 ; + ssize_t count ; + + if (psf->virtual_io) + return psf->vio.read (ptr, bytes*items, psf->vio_user_data) / bytes ; + + items *= bytes ; + + /* Do this check after the multiplication above. */ + if (items <= 0) + return 0 ; + + while (items > 0) + { /* Break the read down to a sensible size. */ + count = (items > SENSIBLE_SIZE) ? SENSIBLE_SIZE : (ssize_t) items ; + + count = read (psf->filedes, ((char*) ptr) + total, (size_t) count) ; + + if (count == -1) + { if (errno == EINTR) + continue ; + + psf_log_syserr (psf, errno) ; + break ; + } ; + + if (count == 0) + break ; + + total += count ; + items -= count ; + } ; + + if (psf->is_pipe) + psf->pipeoffset += total ; + + return total / bytes ; +} /* psf_fread */ + +sf_count_t +psf_fwrite (const void *ptr, sf_count_t bytes, sf_count_t items, SF_PRIVATE *psf) +{ sf_count_t total = 0 ; + ssize_t count ; + + if (psf->virtual_io) + return psf->vio.write (ptr, bytes*items, psf->vio_user_data) / bytes ; + + items *= bytes ; + + /* Do this check after the multiplication above. */ + if (items <= 0) + return 0 ; + + while (items > 0) + { /* Break the writes down to a sensible size. */ + count = (items > SENSIBLE_SIZE) ? SENSIBLE_SIZE : items ; + + count = write (psf->filedes, ((const char*) ptr) + total, count) ; + + if (count == -1) + { if (errno == EINTR) + continue ; + + psf_log_syserr (psf, errno) ; + break ; + } ; + + if (count == 0) + break ; + + total += count ; + items -= count ; + } ; + + if (psf->is_pipe) + psf->pipeoffset += total ; + + return total / bytes ; +} /* psf_fwrite */ + +sf_count_t +psf_ftell (SF_PRIVATE *psf) +{ sf_count_t pos ; + + if (psf->virtual_io) + return psf->vio.tell (psf->vio_user_data) ; + + if (psf->is_pipe) + return psf->pipeoffset ; + + pos = lseek (psf->filedes, 0, SEEK_CUR) ; + + if (pos == ((sf_count_t) -1)) + { psf_log_syserr (psf, errno) ; + return -1 ; + } ; + + return pos - psf->fileoffset ; +} /* psf_ftell */ + +static int +psf_close_fd (int fd) +{ int retval ; + + while ((retval = close (fd)) == -1 && errno == EINTR) + /* Do nothing. */ ; + + return retval ; +} /* psf_close_fd */ + +sf_count_t +psf_fgets (char *buffer, sf_count_t bufsize, SF_PRIVATE *psf) +{ sf_count_t k = 0 ; + sf_count_t count ; + + while (k < bufsize - 1) + { count = read (psf->filedes, &(buffer [k]), 1) ; + + if (count == -1) + { if (errno == EINTR) + continue ; + + psf_log_syserr (psf, errno) ; + break ; + } ; + + if (count == 0 || buffer [k++] == '\n') + break ; + } ; + + buffer [k] = 0 ; + + return k ; +} /* psf_fgets */ + +int +psf_is_pipe (SF_PRIVATE *psf) +{ struct stat statbuf ; + + if (psf->virtual_io) + return SF_FALSE ; + + if (fstat (psf->filedes, &statbuf) == -1) + { psf_log_syserr (psf, errno) ; + /* Default to maximum safety. */ + return SF_TRUE ; + } ; + + if (S_ISFIFO (statbuf.st_mode) || S_ISSOCK (statbuf.st_mode)) + return SF_TRUE ; + + return SF_FALSE ; +} /* psf_is_pipe */ + +static sf_count_t +psf_get_filelen_fd (int fd) +{ struct stat statbuf ; + + /* + ** Sanity check. + ** If everything is OK, this will be optimised out. + */ + if (sizeof (statbuf.st_size) == 4 && sizeof (sf_count_t) == 8) + return (sf_count_t) -SFE_BAD_STAT_SIZE ; + + if (fstat (fd, &statbuf) == -1) + return (sf_count_t) -1 ; + + return statbuf.st_size ; +} /* psf_get_filelen_fd */ + +int +psf_ftruncate (SF_PRIVATE *psf, sf_count_t len) +{ int retval ; + + /* Returns 0 on success, non-zero on failure. */ + if (len < 0) + return -1 ; + + if ((sizeof (off_t) < sizeof (sf_count_t)) && len > 0x7FFFFFFF) + return -1 ; + + retval = ftruncate (psf->filedes, len) ; + + if (retval == -1) + psf_log_syserr (psf, errno) ; + + return retval ; +} /* psf_ftruncate */ + +void +psf_init_files (SF_PRIVATE *psf) +{ psf->filedes = -1 ; + psf->rsrcdes = -1 ; + psf->savedes = -1 ; +} /* psf_init_files */ + +void +psf_use_rsrc (SF_PRIVATE *psf, int on_off) +{ + if (on_off) + { if (psf->filedes != psf->rsrcdes) + { psf->savedes = psf->filedes ; + psf->filedes = psf->rsrcdes ; + } ; + } + else if (psf->filedes == psf->rsrcdes) + psf->filedes = psf->savedes ; + + return ; +} /* psf_use_rsrc */ + +static int +psf_open_fd (const char * pathname, int open_mode) +{ int fd, oflag, mode ; + + /* + ** Sanity check. If everything is OK, this test and the printfs will + ** be optimised out. This is meant to catch the problems caused by + ** "sfconfig.h" being included after . + */ + if (sizeof (off_t) != sizeof (sf_count_t)) + { puts ("\n\n*** Fatal error : sizeof (off_t) != sizeof (sf_count_t)") ; + puts ("*** This means that libsndfile was not configured correctly.\n") ; + exit (1) ; + } ; + + switch (open_mode) + { case SFM_READ : + oflag = O_RDONLY ; + mode = 0 ; + break ; + + case SFM_WRITE : + oflag = O_WRONLY | O_CREAT | O_TRUNC ; + mode = S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH ; + break ; + + case SFM_RDWR : + oflag = O_RDWR | O_CREAT ; + mode = S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH ; + break ; + + default : + return - SFE_BAD_OPEN_MODE ; + break ; + } ; + +#if OS_IS_WIN32 + /* For Cygwin. */ + oflag |= O_BINARY ; +#endif + + if (mode == 0) + fd = open (pathname, oflag) ; + else + fd = open (pathname, oflag, mode) ; + + return fd ; +} /* psf_open_fd */ + +static void +psf_log_syserr (SF_PRIVATE *psf, int error) +{ + /* Only log an error if no error has been set yet. */ + if (psf->error == 0) + { psf->error = SFE_SYSTEM ; + LSF_SNPRINTF (psf->syserr, sizeof (psf->syserr), "System error : %s.", strerror (error)) ; + } ; + + return ; +} /* psf_log_syserr */ + +void +psf_fsync (SF_PRIVATE *psf) +{ +#if HAVE_FSYNC + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + fsync (psf->filedes) ; +#else + psf = NULL ; +#endif +} /* psf_fsync */ + +#elif USE_WINDOWS_API + +/* Win32 file i/o functions implemented using native Win32 API */ + +#include +#include + +#ifndef HAVE_SSIZE_T +typedef long ssize_t ; +#endif + +static int psf_close_handle (HANDLE handle) ; +static HANDLE psf_open_handle (const char * path, int mode) ; +static sf_count_t psf_get_filelen_handle (HANDLE handle) ; + +/* USE_WINDOWS_API */ int +psf_fopen (SF_PRIVATE *psf, const char *pathname, int open_mode) +{ + psf->error = 0 ; + psf->hfile = psf_open_handle (pathname, open_mode) ; + + if (psf->hfile == NULL) + psf_log_syserr (psf, errno) ; + + psf->mode = open_mode ; + + return psf->error ; +} /* psf_fopen */ + +/* USE_WINDOWS_API */ int +psf_fclose (SF_PRIVATE *psf) +{ int retval ; + + if (psf->virtual_io) + return 0 ; + + if (psf->do_not_close_descriptor) + { psf->hfile = NULL ; + return 0 ; + } ; + + if ((retval = psf_close_handle (psf->hfile)) == -1) + psf_log_syserr (psf, errno) ; + + psf->hfile = NULL ; + + return retval ; +} /* psf_fclose */ + +/* USE_WINDOWS_API */ int +psf_open_rsrc (SF_PRIVATE *psf, int open_mode) +{ + if (psf->hrsrc != NULL) + return 0 ; + + /* Test for MacOSX style resource fork on HPFS or HPFS+ filesystems. */ + LSF_SNPRINTF (psf->rsrcpath, sizeof (psf->rsrcpath), "%s/rsrc", psf->filepath) ; + psf->error = SFE_NO_ERROR ; + if ((psf->hrsrc = psf_open_handle (psf->rsrcpath, open_mode)) != NULL) + { psf->rsrclength = psf_get_filelen_handle (psf->hrsrc) ; + return SFE_NO_ERROR ; + } ; + + /* + ** Now try for a resource fork stored as a separate file in the same + ** directory, but preceded with a dot underscore. + */ + LSF_SNPRINTF (psf->rsrcpath, sizeof (psf->rsrcpath), "%s._%s", psf->directory, psf->filename) ; + psf->error = SFE_NO_ERROR ; + if ((psf->hrsrc = psf_open_handle (psf->rsrcpath, open_mode)) != NULL) + { psf->rsrclength = psf_get_filelen_handle (psf->hrsrc) ; + return SFE_NO_ERROR ; + } ; + + /* + ** Now try for a resource fork stored in a separate file in the + ** .AppleDouble/ directory. + */ + LSF_SNPRINTF (psf->rsrcpath, sizeof (psf->rsrcpath), "%s.AppleDouble/%s", psf->directory, psf->filename) ; + psf->error = SFE_NO_ERROR ; + if ((psf->hrsrc = psf_open_handle (psf->rsrcpath, open_mode)) != NULL) + { psf->rsrclength = psf_get_filelen_handle (psf->hrsrc) ; + return SFE_NO_ERROR ; + } ; + + /* No resource file found. */ + if (psf->hrsrc == NULL) + psf_log_syserr (psf, errno) ; + + psf->hrsrc = NULL ; + + return psf->error ; +} /* psf_open_rsrc */ + +/* USE_WINDOWS_API */ sf_count_t +psf_get_filelen (SF_PRIVATE *psf) +{ sf_count_t filelen ; + + if (psf->virtual_io) + return psf->vio.get_filelen (psf->vio_user_data) ; + + filelen = psf_get_filelen_handle (psf->hfile) ; + + if (filelen == -1) + { psf_log_syserr (psf, errno) ; + return (sf_count_t) -1 ; + } ; + + if (filelen == -SFE_BAD_STAT_SIZE) + { psf->error = SFE_BAD_STAT_SIZE ; + return (sf_count_t) -1 ; + } ; + + switch (psf->mode) + { case SFM_WRITE : + filelen = filelen - psf->fileoffset ; + break ; + + case SFM_READ : + if (psf->fileoffset > 0 && psf->filelength > 0) + filelen = psf->filelength ; + break ; + + case SFM_RDWR : + /* + ** Cannot open embedded files SFM_RDWR so we don't need to + ** subtract psf->fileoffset. We already have the answer we + ** need. + */ + break ; + + default : + /* Shouldn't be here, so return error. */ + filelen = -1 ; + } ; + + return filelen ; +} /* psf_get_filelen */ + +/* USE_WINDOWS_API */ void +psf_init_files (SF_PRIVATE *psf) +{ psf->hfile = NULL ; + psf->hrsrc = NULL ; + psf->hsaved = NULL ; +} /* psf_init_files */ + +/* USE_WINDOWS_API */ void +psf_use_rsrc (SF_PRIVATE *psf, int on_off) +{ + if (on_off) + { if (psf->hfile != psf->hrsrc) + { psf->hsaved = psf->hfile ; + psf->hfile = psf->hrsrc ; + } ; + } + else if (psf->hfile == psf->hrsrc) + psf->hfile = psf->hsaved ; + + return ; +} /* psf_use_rsrc */ + +/* USE_WINDOWS_API */ static HANDLE +psf_open_handle (const char * pathname, int open_mode) +{ DWORD dwDesiredAccess ; + DWORD dwShareMode ; + DWORD dwCreationDistribution ; + HANDLE handle ; + + switch (open_mode) + { case SFM_READ : + dwDesiredAccess = GENERIC_READ ; + dwShareMode = FILE_SHARE_READ | FILE_SHARE_WRITE ; + dwCreationDistribution = OPEN_EXISTING ; + break ; + + case SFM_WRITE : + dwDesiredAccess = GENERIC_WRITE ; + dwShareMode = FILE_SHARE_READ | FILE_SHARE_WRITE ; + dwCreationDistribution = CREATE_ALWAYS ; + break ; + + case SFM_RDWR : + dwDesiredAccess = GENERIC_READ | GENERIC_WRITE ; + dwShareMode = FILE_SHARE_READ | FILE_SHARE_WRITE ; + dwCreationDistribution = OPEN_ALWAYS ; + break ; + + default : + return NULL ; + } ; + + handle = CreateFile ( + pathname, /* pointer to name of the file */ + dwDesiredAccess, /* access (read-write) mode */ + dwShareMode, /* share mode */ + 0, /* pointer to security attributes */ + dwCreationDistribution, /* how to create */ + FILE_ATTRIBUTE_NORMAL, /* file attributes (could use FILE_FLAG_SEQUENTIAL_SCAN) */ + NULL /* handle to file with attributes to copy */ + ) ; + + if (handle == INVALID_HANDLE_VALUE) + return NULL ; + + return handle ; +} /* psf_open_handle */ + +/* USE_WINDOWS_API */ static void +psf_log_syserr (SF_PRIVATE *psf, int error) +{ LPVOID lpMsgBuf ; + + /* Only log an error if no error has been set yet. */ + if (psf->error == 0) + { psf->error = SFE_SYSTEM ; + + FormatMessage ( + FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM, + NULL, + error, + MAKELANGID (LANG_NEUTRAL, SUBLANG_DEFAULT), + (LPTSTR) &lpMsgBuf, + 0, + NULL + ) ; + + LSF_SNPRINTF (psf->syserr, sizeof (psf->syserr), "System error : %s", lpMsgBuf) ; + LocalFree (lpMsgBuf) ; + } ; + + return ; +} /* psf_log_syserr */ + + +/* USE_WINDOWS_API */ int +psf_close_rsrc (SF_PRIVATE *psf) +{ + if (psf->hrsrc != NULL) + psf_close_handle (psf->hrsrc) ; + psf->hrsrc = NULL ; + return 0 ; +} /* psf_close_rsrc */ + + +/* USE_WINDOWS_API */ int +psf_set_stdio (SF_PRIVATE *psf, int mode) +{ HANDLE handle = NULL ; + int error = 0 ; + + switch (mode) + { case SFM_RDWR : + error = SFE_OPEN_PIPE_RDWR ; + break ; + + case SFM_READ : + handle = GetStdHandle (STD_INPUT_HANDLE) ; + psf->do_not_close_descriptor = 1 ; + break ; + + case SFM_WRITE : + handle = GetStdHandle (STD_OUTPUT_HANDLE) ; + psf->do_not_close_descriptor = 1 ; + break ; + + default : + error = SFE_BAD_OPEN_MODE ; + break ; + } ; + + psf->hfile = handle ; + psf->filelength = 0 ; + + return error ; +} /* psf_set_stdio */ + +/* USE_WINDOWS_API */ void +psf_set_file (SF_PRIVATE *psf, int fd) +{ HANDLE handle ; + long osfhandle ; + + osfhandle = _get_osfhandle (fd) ; + handle = (HANDLE) osfhandle ; + + psf->hfile = handle ; +} /* psf_set_file */ + +/* USE_WINDOWS_API */ int +psf_file_valid (SF_PRIVATE *psf) +{ if (psf->hfile == NULL) + return SF_FALSE ; + if (psf->hfile == INVALID_HANDLE_VALUE) + return SF_FALSE ; + return SF_TRUE ; +} /* psf_set_file */ + +/* USE_WINDOWS_API */ sf_count_t +psf_fseek (SF_PRIVATE *psf, sf_count_t offset, int whence) +{ sf_count_t new_position ; + LONG lDistanceToMove, lDistanceToMoveHigh ; + DWORD dwMoveMethod ; + DWORD dwResult, dwError ; + + if (psf->virtual_io) + return psf->vio.seek (offset, whence, psf->vio_user_data) ; + + switch (whence) + { case SEEK_SET : + offset += psf->fileoffset ; + dwMoveMethod = FILE_BEGIN ; + break ; + + case SEEK_END : + dwMoveMethod = FILE_END ; + break ; + + default : + dwMoveMethod = FILE_CURRENT ; + break ; + } ; + + lDistanceToMove = (DWORD) (offset & 0xFFFFFFFF) ; + lDistanceToMoveHigh = (DWORD) ((offset >> 32) & 0xFFFFFFFF) ; + + dwResult = SetFilePointer (psf->hfile, lDistanceToMove, &lDistanceToMoveHigh, dwMoveMethod) ; + + if (dwResult == 0xFFFFFFFF) + dwError = GetLastError () ; + else + dwError = NO_ERROR ; + + if (dwError != NO_ERROR) + { psf_log_syserr (psf, dwError) ; + return -1 ; + } ; + + new_position = (dwResult + ((__int64) lDistanceToMoveHigh << 32)) - psf->fileoffset ; + + return new_position ; +} /* psf_fseek */ + +/* USE_WINDOWS_API */ sf_count_t +psf_fread (void *ptr, sf_count_t bytes, sf_count_t items, SF_PRIVATE *psf) +{ sf_count_t total = 0 ; + ssize_t count ; + DWORD dwNumberOfBytesRead ; + + if (psf->virtual_io) + return psf->vio.read (ptr, bytes*items, psf->vio_user_data) / bytes ; + + items *= bytes ; + + /* Do this check after the multiplication above. */ + if (items <= 0) + return 0 ; + + while (items > 0) + { /* Break the writes down to a sensible size. */ + count = (items > SENSIBLE_SIZE) ? SENSIBLE_SIZE : (ssize_t) items ; + + if (ReadFile (psf->hfile, ((char*) ptr) + total, count, &dwNumberOfBytesRead, 0) == 0) + { psf_log_syserr (psf, GetLastError ()) ; + break ; + } + else + count = dwNumberOfBytesRead ; + + if (count == 0) + break ; + + total += count ; + items -= count ; + } ; + + if (psf->is_pipe) + psf->pipeoffset += total ; + + return total / bytes ; +} /* psf_fread */ + +/* USE_WINDOWS_API */ sf_count_t +psf_fwrite (const void *ptr, sf_count_t bytes, sf_count_t items, SF_PRIVATE *psf) +{ sf_count_t total = 0 ; + ssize_t count ; + DWORD dwNumberOfBytesWritten ; + + if (psf->virtual_io) + return psf->vio.write (ptr, bytes * items, psf->vio_user_data) / bytes ; + + items *= bytes ; + + /* Do this check after the multiplication above. */ + if (items <= 0) + return 0 ; + + while (items > 0) + { /* Break the writes down to a sensible size. */ + count = (items > SENSIBLE_SIZE) ? SENSIBLE_SIZE : (ssize_t) items ; + + if (WriteFile (psf->hfile, ((const char*) ptr) + total, count, &dwNumberOfBytesWritten, 0) == 0) + { psf_log_syserr (psf, GetLastError ()) ; + break ; + } + else + count = dwNumberOfBytesWritten ; + + if (count == 0) + break ; + + total += count ; + items -= count ; + } ; + + if (psf->is_pipe) + psf->pipeoffset += total ; + + return total / bytes ; +} /* psf_fwrite */ + +/* USE_WINDOWS_API */ sf_count_t +psf_ftell (SF_PRIVATE *psf) +{ sf_count_t pos ; + LONG lDistanceToMoveLow, lDistanceToMoveHigh ; + DWORD dwResult, dwError ; + + if (psf->virtual_io) + return psf->vio.tell (psf->vio_user_data) ; + + if (psf->is_pipe) + return psf->pipeoffset ; + + lDistanceToMoveLow = 0 ; + lDistanceToMoveHigh = 0 ; + + dwResult = SetFilePointer (psf->hfile, lDistanceToMoveLow, &lDistanceToMoveHigh, FILE_CURRENT) ; + + if (dwResult == 0xFFFFFFFF) + dwError = GetLastError () ; + else + dwError = NO_ERROR ; + + if (dwError != NO_ERROR) + { psf_log_syserr (psf, dwError) ; + return -1 ; + } ; + + pos = (dwResult + ((__int64) lDistanceToMoveHigh << 32)) ; + + return pos - psf->fileoffset ; +} /* psf_ftell */ + +/* USE_WINDOWS_API */ static int +psf_close_handle (HANDLE handle) +{ if (CloseHandle (handle) == 0) + return -1 ; + + return 0 ; +} /* psf_close_handle */ + +/* USE_WINDOWS_API */ sf_count_t +psf_fgets (char *buffer, sf_count_t bufsize, SF_PRIVATE *psf) +{ sf_count_t k = 0 ; + sf_count_t count ; + DWORD dwNumberOfBytesRead ; + + while (k < bufsize - 1) + { if (ReadFile (psf->hfile, &(buffer [k]), 1, &dwNumberOfBytesRead, 0) == 0) + { psf_log_syserr (psf, GetLastError ()) ; + break ; + } + else + { count = dwNumberOfBytesRead ; + /* note that we only check for '\n' not other line endings such as CRLF */ + if (count == 0 || buffer [k++] == '\n') + break ; + } ; + } ; + + buffer [k] = 0 ; + + return k ; +} /* psf_fgets */ + +/* USE_WINDOWS_API */ int +psf_is_pipe (SF_PRIVATE *psf) +{ + if (psf->virtual_io) + return SF_FALSE ; + + if (GetFileType (psf->hfile) == FILE_TYPE_DISK) + return SF_FALSE ; + + /* Default to maximum safety. */ + return SF_TRUE ; +} /* psf_is_pipe */ + +/* USE_WINDOWS_API */ sf_count_t +psf_get_filelen_handle (HANDLE handle) +{ sf_count_t filelen ; + DWORD dwFileSizeLow, dwFileSizeHigh, dwError = NO_ERROR ; + + dwFileSizeLow = GetFileSize (handle, &dwFileSizeHigh) ; + + if (dwFileSizeLow == 0xFFFFFFFF) + dwError = GetLastError () ; + + if (dwError != NO_ERROR) + return (sf_count_t) -1 ; + + filelen = dwFileSizeLow + ((__int64) dwFileSizeHigh << 32) ; + + return filelen ; +} /* psf_get_filelen_handle */ + +/* USE_WINDOWS_API */ void +psf_fsync (SF_PRIVATE *psf) +{ FlushFileBuffers (psf->hfile) ; +} /* psf_fsync */ + + +/* USE_WINDOWS_API */ int +psf_ftruncate (SF_PRIVATE *psf, sf_count_t len) +{ int retval = 0 ; + LONG lDistanceToMoveLow, lDistanceToMoveHigh ; + DWORD dwResult, dwError = NO_ERROR ; + + /* This implementation trashes the current file position. + ** should it save and restore it? what if the current position is past + ** the new end of file? + */ + + /* Returns 0 on success, non-zero on failure. */ + if (len < 0) + return 1 ; + + lDistanceToMoveLow = (DWORD) (len & 0xFFFFFFFF) ; + lDistanceToMoveHigh = (DWORD) ((len >> 32) & 0xFFFFFFFF) ; + + dwResult = SetFilePointer (psf->hfile, lDistanceToMoveLow, &lDistanceToMoveHigh, FILE_BEGIN) ; + + if (dwResult == 0xFFFFFFFF) + dwError = GetLastError () ; + + if (dwError != NO_ERROR) + { retval = -1 ; + psf_log_syserr (psf, dwError) ; + } + else + { /* Note: when SetEndOfFile is used to extend a file, the contents of the + ** new portion of the file is undefined. This is unlike chsize(), + ** which guarantees that the new portion of the file will be zeroed. + ** Not sure if this is important or not. + */ + if (SetEndOfFile (psf->hfile) == 0) + { retval = -1 ; + psf_log_syserr (psf, GetLastError ()) ; + } ; + } ; + + return retval ; +} /* psf_ftruncate */ + + +#else +/* Win32 file i/o functions implemented using Unix-style file i/o API */ + +/* Win32 has a 64 file offset seek function: +** +** __int64 _lseeki64 (int handle, __int64 offset, int origin) ; +** +** It also has a 64 bit fstat function: +** +** int fstati64 (int, struct _stati64) ; +** +** but the fscking thing doesn't work!!!!! The file size parameter returned +** by this function is only valid up until more data is written at the end of +** the file. That makes this function completely 100% useless. +*/ + +#include +#include + +#ifndef HAVE_SSIZE_T +typedef long ssize_t ; +#endif + +/* Win32 */ int +psf_fopen (SF_PRIVATE *psf, const char *pathname, int open_mode) +{ int oflag, mode ; + + switch (open_mode) + { case SFM_READ : + oflag = O_RDONLY | O_BINARY ; + mode = 0 ; + break ; + + case SFM_WRITE : + oflag = O_WRONLY | O_CREAT | O_TRUNC | O_BINARY ; + mode = S_IRUSR | S_IWUSR | S_IRGRP ; + break ; + + case SFM_RDWR : + oflag = O_RDWR | O_CREAT | O_BINARY ; + mode = S_IRUSR | S_IWUSR | S_IRGRP ; + break ; + + default : + psf->error = SFE_BAD_OPEN_MODE ; + return -1 ; + break ; + } ; + + if (mode == 0) + psf->filedes = open (pathname, oflag) ; + else + psf->filedes = open (pathname, oflag, mode) ; + + if (psf->filedes == -1) + psf_log_syserr (psf, errno) ; + + return psf->filedes ; +} /* psf_fopen */ + +/* Win32 */ sf_count_t +psf_fseek (SF_PRIVATE *psf, sf_count_t offset, int whence) +{ sf_count_t new_position ; + + if (psf->virtual_io) + return psf->vio.seek (offset, whence, psf->vio_user_data) ; + + switch (whence) + { case SEEK_SET : + offset += psf->fileoffset ; + break ; + + case SEEK_END : + if (psf->mode == SFM_WRITE) + { new_position = _lseeki64 (psf->filedes, offset, whence) ; + + if (new_position < 0) + psf_log_syserr (psf, errno) ; + + return new_position - psf->fileoffset ; + } ; + + /* Transform SEEK_END into a SEEK_SET, ie find the file + ** length add the requested offset (should be <= 0) to + ** get the offset wrt the start of file. + */ + whence = SEEK_SET ; + offset = _lseeki64 (psf->filedes, 0, SEEK_END) + offset ; + break ; + + default : + /* No need to do anything about SEEK_CUR. */ + break ; + } ; + + /* + ** Bypass weird Win32-ism if necessary. + ** _lseeki64() returns an "invalid parameter" error if called with the + ** offset == 0 and whence == SEEK_CUR. + *** Use the _telli64() function instead. + */ + if (offset == 0 && whence == SEEK_CUR) + new_position = _telli64 (psf->filedes) ; + else + new_position = _lseeki64 (psf->filedes, offset, whence) ; + + if (new_position < 0) + psf_log_syserr (psf, errno) ; + + new_position -= psf->fileoffset ; + + return new_position ; +} /* psf_fseek */ + +/* Win32 */ sf_count_t +psf_fread (void *ptr, sf_count_t bytes, sf_count_t items, SF_PRIVATE *psf) +{ sf_count_t total = 0 ; + ssize_t count ; + + if (psf->virtual_io) + return psf->vio.read (ptr, bytes*items, psf->vio_user_data) / bytes ; + + items *= bytes ; + + /* Do this check after the multiplication above. */ + if (items <= 0) + return 0 ; + + while (items > 0) + { /* Break the writes down to a sensible size. */ + count = (items > SENSIBLE_SIZE) ? SENSIBLE_SIZE : (ssize_t) items ; + + count = read (psf->filedes, ((char*) ptr) + total, (size_t) count) ; + + if (count == -1) + { if (errno == EINTR) + continue ; + + psf_log_syserr (psf, errno) ; + break ; + } ; + + if (count == 0) + break ; + + total += count ; + items -= count ; + } ; + + return total / bytes ; +} /* psf_fread */ + +/* Win32 */ sf_count_t +psf_fwrite (const void *ptr, sf_count_t bytes, sf_count_t items, SF_PRIVATE *psf) +{ sf_count_t total = 0 ; + ssize_t count ; + + if (psf->virtual_io) + return psf->vio.write (ptr, bytes*items, psf->vio_user_data) / bytes ; + + items *= bytes ; + + /* Do this check after the multiplication above. */ + if (items <= 0) + return 0 ; + + while (items > 0) + { /* Break the writes down to a sensible size. */ + count = (items > SENSIBLE_SIZE) ? SENSIBLE_SIZE : items ; + + count = write (psf->filedes, ((const char*) ptr) + total, count) ; + + if (count == -1) + { if (errno == EINTR) + continue ; + + psf_log_syserr (psf, errno) ; + break ; + } ; + + if (count == 0) + break ; + + total += count ; + items -= count ; + } ; + + return total / bytes ; +} /* psf_fwrite */ + +/* Win32 */ sf_count_t +psf_ftell (SF_PRIVATE *psf) +{ sf_count_t pos ; + + if (psf->virtual_io) + return psf->vio.tell (psf->vio_user_data) ; + + pos = _telli64 (psf->filedes) ; + + if (pos == ((sf_count_t) -1)) + { psf_log_syserr (psf, errno) ; + return -1 ; + } ; + + return pos - psf->fileoffset ; +} /* psf_ftell */ + +/* Win32 */ int +psf_fclose (SF_PRIVATE *psf) +{ int retval ; + + while ((retval = close (psf->filedes)) == -1 && errno == EINTR) + /* Do nothing. */ ; + + if (retval == -1) + psf_log_syserr (psf, errno) ; + + psf->filedes = -1 ; + + return retval ; +} /* psf_fclose */ + +/* Win32 */ sf_count_t +psf_fgets (char *buffer, sf_count_t bufsize, SF_PRIVATE *psf) +{ sf_count_t k = 0 ; + sf_count_t count ; + + while (k < bufsize - 1) + { count = read (psf->filedes, &(buffer [k]), 1) ; + + if (count == -1) + { if (errno == EINTR) + continue ; + + psf_log_syserr (psf, errno) ; + break ; + } ; + + if (count == 0 || buffer [k++] == '\n') + break ; + } ; + + buffer [k] = 0 ; + + return k ; +} /* psf_fgets */ + +/* Win32 */ int +psf_is_pipe (SF_PRIVATE *psf) +{ struct stat statbuf ; + + if (psf->virtual_io) + return SF_FALSE ; + + /* Not sure if this works. */ + if (fstat (psf->filedes, &statbuf) == -1) + { psf_log_syserr (psf, errno) ; + /* Default to maximum safety. */ + return SF_TRUE ; + } ; + + /* These macros are defined in Win32/unistd.h. */ + if (S_ISFIFO (statbuf.st_mode) || S_ISSOCK (statbuf.st_mode)) + return SF_TRUE ; + + return SF_FALSE ; +} /* psf_checkpipe */ + +/* Win32 */ sf_count_t +psf_get_filelen (SF_PRIVATE *psf) +{ +#if 0 + /* + ** Windoze is SOOOOO FUCKED!!!!!!! + ** This code should work but doesn't. Why? + ** Code below does work. + */ + struct _stati64 statbuf ; + + if (_fstati64 (psf->filedes, &statbuf)) + { psf_log_syserr (psf, errno) ; + return (sf_count_t) -1 ; + } ; + + return statbuf.st_size ; +#else + sf_count_t current, filelen ; + + if (psf->virtual_io) + return psf->vio.get_filelen (psf->vio_user_data) ; + + if ((current = _telli64 (psf->filedes)) < 0) + { psf_log_syserr (psf, errno) ; + return (sf_count_t) -1 ; + } ; + + /* + ** Lets face it, windoze if FUBAR!!! + ** + ** For some reason, I have to call _lseeki64() TWICE to get to the + ** end of the file. + ** + ** This might have been avoided if windows had implemented the POSIX + ** standard function fsync() but NO, that would have been too easy. + ** + ** I am VERY close to saying that windoze will no longer be supported + ** by libsndfile and changing the license to GPL at the same time. + */ + + _lseeki64 (psf->filedes, 0, SEEK_END) ; + + if ((filelen = _lseeki64 (psf->filedes, 0, SEEK_END)) < 0) + { psf_log_syserr (psf, errno) ; + return (sf_count_t) -1 ; + } ; + + if (filelen > current) + _lseeki64 (psf->filedes, current, SEEK_SET) ; + + switch (psf->mode) + { case SFM_WRITE : + filelen = filelen - psf->fileoffset ; + break ; + + case SFM_READ : + if (psf->fileoffset > 0 && psf->filelength > 0) + filelen = psf->filelength ; + break ; + + case SFM_RDWR : + /* + ** Cannot open embedded files SFM_RDWR so we don't need to + ** subtract psf->fileoffset. We already have the answer we + ** need. + */ + break ; + + default : + filelen = 0 ; + } ; + + return filelen ; +#endif +} /* psf_get_filelen */ + +/* Win32 */ int +psf_ftruncate (SF_PRIVATE *psf, sf_count_t len) +{ int retval ; + + /* Returns 0 on success, non-zero on failure. */ + if (len < 0) + return 1 ; + + /* The global village idiots at micorsoft decided to implement + ** nearly all the required 64 bit file offset functions except + ** for one, truncate. The fscking morons! + ** + ** This is not 64 bit file offset clean. Somone needs to clean + ** this up. + */ + if (len > 0x7FFFFFFF) + return -1 ; + + retval = chsize (psf->filedes, len) ; + + if (retval == -1) + psf_log_syserr (psf, errno) ; + + return retval ; +} /* psf_ftruncate */ + + +static void +psf_log_syserr (SF_PRIVATE *psf, int error) +{ + /* Only log an error if no error has been set yet. */ + if (psf->error == 0) + { psf->error = SFE_SYSTEM ; + LSF_SNPRINTF (psf->syserr, sizeof (psf->syserr), "System error : %s", strerror (error)) ; + } ; + + return ; +} /* psf_log_syserr */ + +#endif + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 749740d7-ecc7-47bd-8cf7-600f31d32e6d +*/ diff --git a/libs/libsndfile/src/flac.c b/libs/libsndfile/src/flac.c new file mode 100644 index 0000000000..1f0872f0bd --- /dev/null +++ b/libs/libsndfile/src/flac.c @@ -0,0 +1,1156 @@ +/* +** Copyright (C) 2004, 2005 Erik de Castro Lopo +** Copyright (C) 2004 Tobias Gehrig +** +** This program is free software ; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation ; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY ; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program ; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include +#include +#include + +#include "sndfile.h" +#include "common.h" + + +#ifndef HAVE_FLAC_ALL_H + +int +flac_open (SF_PRIVATE *psf) +{ if (psf) + return SFE_UNIMPLEMENTED ; + return (psf && 0) ; +} /* flac_open */ + + +#else + +#include + +#include "sfendian.h" +#include "float_cast.h" + +/*------------------------------------------------------------------------------ +** Private static functions. +*/ + +#define ENC_BUFFER_SIZE 4096 + +typedef enum +{ PFLAC_PCM_SHORT = 0, + PFLAC_PCM_INT = 1, + PFLAC_PCM_FLOAT = 2, + PFLAC_PCM_DOUBLE = 3 +} PFLAC_PCM ; + +typedef struct +{ FLAC__SeekableStreamDecoder *fsd ; + FLAC__SeekableStreamEncoder *fse ; + PFLAC_PCM pcmtype ; + void* ptr ; + unsigned pos, len, remain ; + + const FLAC__int32 * const * wbuffer ; + FLAC__int32 * rbuffer [FLAC__MAX_CHANNELS] ; + + FLAC__int32* encbuffer ; + unsigned bufferpos ; + + const FLAC__Frame *frame ; + FLAC__bool bufferbackup ; +} FLAC_PRIVATE ; + +static sf_count_t flac_seek (SF_PRIVATE *psf, int mode, sf_count_t offset) ; +static int flac_close (SF_PRIVATE *psf) ; + +static int flac_enc_init (SF_PRIVATE *psf) ; +static int flac_read_header (SF_PRIVATE *psf) ; + +static sf_count_t flac_read_flac2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t flac_read_flac2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t flac_read_flac2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t flac_read_flac2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; + +static sf_count_t flac_write_s2flac (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t flac_write_i2flac (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t flac_write_f2flac (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t flac_write_d2flac (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; + +static void f2flac8_array (const float *src, FLAC__int32 *dest, int count, int normalize) ; +static void f2flac16_array (const float *src, FLAC__int32 *dest, int count, int normalize) ; +static void f2flac24_array (const float *src, FLAC__int32 *dest, int count, int normalize) ; +static void f2flac8_clip_array (const float *src, FLAC__int32 *dest, int count, int normalize) ; +static void f2flac16_clip_array (const float *src, FLAC__int32 *dest, int count, int normalize) ; +static void f2flac24_clip_array (const float *src, FLAC__int32 *dest, int count, int normalize) ; +static void d2flac8_array (const double *src, FLAC__int32 *dest, int count, int normalize) ; +static void d2flac16_array (const double *src, FLAC__int32 *dest, int count, int normalize) ; +static void d2flac24_array (const double *src, FLAC__int32 *dest, int count, int normalize) ; +static void d2flac8_clip_array (const double *src, FLAC__int32 *dest, int count, int normalize) ; +static void d2flac16_clip_array (const double *src, FLAC__int32 *dest, int count, int normalize) ; +static void d2flac24_clip_array (const double *src, FLAC__int32 *dest, int count, int normalize) ; + +static int flac_command (SF_PRIVATE *psf, int command, void *data, int datasize) ; + +/* Decoder Callbacks */ +static FLAC__SeekableStreamDecoderReadStatus sf_flac_read_callback (const FLAC__SeekableStreamDecoder *decoder, FLAC__byte buffer [], unsigned *bytes, void *client_data) ; +static FLAC__SeekableStreamDecoderSeekStatus sf_flac_seek_callback (const FLAC__SeekableStreamDecoder *decoder, FLAC__uint64 absolute_byte_offset, void *client_data) ; +static FLAC__SeekableStreamDecoderTellStatus sf_flac_tell_callback (const FLAC__SeekableStreamDecoder *decoder, FLAC__uint64 *absolute_byte_offset, void *client_data) ; +static FLAC__SeekableStreamDecoderLengthStatus sf_flac_length_callback (const FLAC__SeekableStreamDecoder *decoder, FLAC__uint64 *stream_length, void *client_data) ; +static FLAC__bool sf_flac_eof_callback (const FLAC__SeekableStreamDecoder *decoder, void *client_data) ; +static FLAC__StreamDecoderWriteStatus sf_flac_write_callback (const FLAC__SeekableStreamDecoder *decoder, const FLAC__Frame *frame, const FLAC__int32 * const buffer [], void *client_data) ; +static void sf_flac_meta_callback (const FLAC__SeekableStreamDecoder *decoder, const FLAC__StreamMetadata *metadata, void *client_data) ; +static void sf_flac_error_callback (const FLAC__SeekableStreamDecoder *decoder, FLAC__StreamDecoderErrorStatus status, void *client_data) ; + +/* Encoder Callbacks */ +static FLAC__SeekableStreamEncoderSeekStatus sf_flac_enc_seek_callback (const FLAC__SeekableStreamEncoder *encoder, FLAC__uint64 absolute_byte_offset, void *client_data) ; +#ifdef HAVE_FLAC_1_1_1 +static FLAC__SeekableStreamEncoderTellStatus sf_flac_enc_tell_callback (const FLAC__SeekableStreamEncoder *encoder, FLAC__uint64 *absolute_byte_offset, void *client_data) ; +#endif +static FLAC__StreamEncoderWriteStatus sf_flac_enc_write_callback (const FLAC__SeekableStreamEncoder *encoder, const FLAC__byte buffer [], unsigned bytes, unsigned samples, unsigned current_frame, void *client_data) ; + +static const int legal_sample_rates [] = +{ 8000, 16000, 22050, 24000, 32000, 44100, 48000, 96000 +} ; + +static inline void +s2flac8_array (const short *src, FLAC__int32 *dest, int count) +{ while (--count >= 0) + dest [count] = src [count] >> 8 ; +} /* s2flac8_array */ + +static inline void +s2flac16_array (const short *src, FLAC__int32 *dest, int count) +{ while (--count >= 0) + dest [count] = src [count] ; +} /* s2flac16_array */ + +static inline void +s2flac24_array (const short *src, FLAC__int32 *dest, int count) +{ while (--count >= 0) + dest [count] = src [count] << 8 ; +} /* s2flac24_array */ + +static inline void +i2flac8_array (const int *src, FLAC__int32 *dest, int count) +{ while (--count >= 0) + dest [count] = src [count] >> 24 ; +} /* i2flac8_array */ + +static inline void +i2flac16_array (const int *src, FLAC__int32 *dest, int count) +{ + while (--count >= 0) + dest [count] = src [count] >> 16 ; +} /* i2flac16_array */ + +static inline void +i2flac24_array (const int *src, FLAC__int32 *dest, int count) +{ while (--count >= 0) + dest [count] = src [count] >> 8 ; +} /* i2flac24_array */ + +static sf_count_t +flac_buffer_copy (SF_PRIVATE *psf) +{ FLAC_PRIVATE* pflac = (FLAC_PRIVATE*) psf->fdata ; + const FLAC__Frame *frame = pflac->frame ; + const FLAC__int32* const *buffer = pflac->wbuffer ; + unsigned i = 0, j, offset ; + + if (pflac->ptr == NULL) + { /* + ** Not sure why this code is here and not elsewhere. + ** Removing it causes valgrind errors. + */ + pflac->bufferbackup = SF_TRUE ; + for (i = 0 ; i < frame->header.channels ; i++) + { if (pflac->rbuffer [i] == NULL) + pflac->rbuffer [i] = calloc (frame->header.blocksize, sizeof (FLAC__int32)) ; + memcpy (pflac->rbuffer [i], buffer [i], frame->header.blocksize * sizeof (FLAC__int32)) ; + } ; + pflac->wbuffer = (const FLAC__int32* const*) pflac->rbuffer ; + + return 0 ; + } ; + + switch (pflac->pcmtype) + { case PFLAC_PCM_SHORT : + { short *retpcm = ((short*) pflac->ptr) ; + int shift = 16 - frame->header.bits_per_sample ; + if (shift < 0) + { shift = abs (shift) ; + for (i = 0 ; i < frame->header.blocksize && pflac->remain > 0 ; i++) + { offset = pflac->pos + i * frame->header.channels ; + for (j = 0 ; j < frame->header.channels ; j++) + retpcm [offset + j] = buffer [j][pflac->bufferpos] >> shift ; + pflac->remain -= frame->header.channels ; + pflac->bufferpos++ ; + } + } + else + { for (i = 0 ; i < frame->header.blocksize && pflac->remain > 0 ; i++) + { offset = pflac->pos + i * frame->header.channels ; + + if (pflac->bufferpos >= frame->header.blocksize) + break ; + + for (j = 0 ; j < frame->header.channels ; j++) + retpcm [offset + j] = (buffer [j][pflac->bufferpos]) << shift ; + + pflac->remain -= frame->header.channels ; + pflac->bufferpos++ ; + } ; + } ; + } ; + break ; + + case PFLAC_PCM_INT : + { int *retpcm = ((int*) pflac->ptr) ; + int shift = 32 - frame->header.bits_per_sample ; + for (i = 0 ; i < frame->header.blocksize && pflac->remain > 0 ; i++) + { offset = pflac->pos + i * frame->header.channels ; + + if (pflac->bufferpos >= frame->header.blocksize) + break ; + + for (j = 0 ; j < frame->header.channels ; j++) + retpcm [offset + j] = buffer [j][pflac->bufferpos] << shift ; + pflac->remain -= frame->header.channels ; + pflac->bufferpos++ ; + } ; + } ; + break ; + + case PFLAC_PCM_FLOAT : + { float *retpcm = ((float*) pflac->ptr) ; + float norm = (psf->norm_float == SF_TRUE) ? 1.0 / (1 << (frame->header.bits_per_sample - 1)) : 1.0 ; + + for (i = 0 ; i < frame->header.blocksize && pflac->remain > 0 ; i++) + { offset = pflac->pos + i * frame->header.channels ; + + if (pflac->bufferpos >= frame->header.blocksize) + break ; + + for (j = 0 ; j < frame->header.channels ; j++) + retpcm [offset + j] = buffer [j][pflac->bufferpos] * norm ; + pflac->remain -= frame->header.channels ; + pflac->bufferpos++ ; + } ; + } ; + break ; + + case PFLAC_PCM_DOUBLE : + { double *retpcm = ((double*) pflac->ptr) ; + double norm = (psf->norm_double == SF_TRUE) ? 1.0 / (1 << (frame->header.bits_per_sample - 1)) : 1.0 ; + + for (i = 0 ; i < frame->header.blocksize && pflac->remain > 0 ; i++) + { offset = pflac->pos + i * frame->header.channels ; + + if (pflac->bufferpos >= frame->header.blocksize) + break ; + + for (j = 0 ; j < frame->header.channels ; j++) + retpcm [offset + j] = buffer [j][pflac->bufferpos] * norm ; + pflac->remain -= frame->header.channels ; + pflac->bufferpos++ ; + } ; + } ; + break ; + + default : + return 0 ; + } ; + + offset = i * frame->header.channels ; + pflac->pos += i * frame->header.channels ; + + return offset ; +} /* flac_buffer_copy */ + + +static FLAC__SeekableStreamDecoderReadStatus +sf_flac_read_callback (const FLAC__SeekableStreamDecoder * UNUSED (decoder), FLAC__byte buffer [], unsigned *bytes, void *client_data) +{ SF_PRIVATE *psf = (SF_PRIVATE*) client_data ; + + *bytes = psf_fread (buffer, 1, *bytes, psf) ; + if (*bytes > 0 && psf->error == 0) + return FLAC__SEEKABLE_STREAM_DECODER_READ_STATUS_OK ; + + return FLAC__SEEKABLE_STREAM_DECODER_READ_STATUS_ERROR ; +} /* sf_flac_read_callback */ + +static FLAC__SeekableStreamDecoderSeekStatus +sf_flac_seek_callback (const FLAC__SeekableStreamDecoder * UNUSED (decoder), FLAC__uint64 absolute_byte_offset, void *client_data) +{ SF_PRIVATE *psf = (SF_PRIVATE*) client_data ; + + psf_fseek (psf, absolute_byte_offset, SEEK_SET) ; + if (psf->error) + return FLAC__SEEKABLE_STREAM_DECODER_SEEK_STATUS_ERROR ; + + return FLAC__SEEKABLE_STREAM_DECODER_SEEK_STATUS_OK ; +} /* sf_flac_seek_callback */ + +static FLAC__SeekableStreamDecoderTellStatus +sf_flac_tell_callback (const FLAC__SeekableStreamDecoder * UNUSED (decoder), FLAC__uint64 *absolute_byte_offset, void *client_data) +{ SF_PRIVATE *psf = (SF_PRIVATE*) client_data ; + + *absolute_byte_offset = psf_ftell (psf) ; + if (psf->error) + return FLAC__SEEKABLE_STREAM_DECODER_TELL_STATUS_ERROR ; + + return FLAC__SEEKABLE_STREAM_DECODER_TELL_STATUS_OK ; +} /* sf_flac_tell_callback */ + +static FLAC__SeekableStreamDecoderLengthStatus +sf_flac_length_callback (const FLAC__SeekableStreamDecoder * UNUSED (decoder), FLAC__uint64 *stream_length, void *client_data) +{ SF_PRIVATE *psf = (SF_PRIVATE*) client_data ; + + if ((*stream_length = psf->filelength) == 0) + return FLAC__SEEKABLE_STREAM_DECODER_LENGTH_STATUS_ERROR ; + + return FLAC__SEEKABLE_STREAM_DECODER_LENGTH_STATUS_OK ; +} /* sf_flac_length_callback */ + +static FLAC__bool +sf_flac_eof_callback (const FLAC__SeekableStreamDecoder *UNUSED (decoder), void *client_data) +{ SF_PRIVATE *psf = (SF_PRIVATE*) client_data ; + + if (psf_ftell (psf) == psf->filelength) + return SF_TRUE ; + + return SF_FALSE ; +} /* sf_flac_eof_callback */ + +static FLAC__StreamDecoderWriteStatus +sf_flac_write_callback (const FLAC__SeekableStreamDecoder * UNUSED (decoder), const FLAC__Frame *frame, const FLAC__int32 * const buffer [], void *client_data) +{ SF_PRIVATE *psf = (SF_PRIVATE*) client_data ; + FLAC_PRIVATE* pflac = (FLAC_PRIVATE*) psf->fdata ; + + pflac->frame = frame ; + pflac->bufferpos = 0 ; + + pflac->bufferbackup = SF_FALSE ; + pflac->wbuffer = buffer ; + + flac_buffer_copy (psf) ; + + return FLAC__STREAM_DECODER_WRITE_STATUS_CONTINUE ; +} /* sf_flac_write_callback */ + +static void +sf_flac_meta_callback (const FLAC__SeekableStreamDecoder * UNUSED (decoder), const FLAC__StreamMetadata *metadata, void *client_data) +{ SF_PRIVATE *psf = (SF_PRIVATE*) client_data ; + + switch (metadata->type) + { case FLAC__METADATA_TYPE_STREAMINFO : + psf->sf.channels = metadata->data.stream_info.channels ; + psf->sf.samplerate = metadata->data.stream_info.sample_rate ; + psf->sf.frames = metadata->data.stream_info.total_samples ; + + switch (metadata->data.stream_info.bits_per_sample) + { case 8 : + psf->sf.format |= SF_FORMAT_PCM_S8 ; + break ; + case 16 : + psf->sf.format |= SF_FORMAT_PCM_16 ; + break ; + case 24 : + psf->sf.format |= SF_FORMAT_PCM_24 ; + break ; + default : + psf_log_printf (psf, "sf_flac_meta_callback : bits_per_sample %d not yet implemented.\n", metadata->data.stream_info.bits_per_sample) ; + break ; + } ; + break ; + + default : + psf_log_printf (psf, "sf_flac_meta_callback : metadata-type %d not yet implemented.\n", metadata->type) ; + break ; + } ; + + return ; +} /* sf_flac_meta_callback */ + +static void +sf_flac_error_callback (const FLAC__SeekableStreamDecoder * UNUSED (decoder), FLAC__StreamDecoderErrorStatus status, void *client_data) +{ SF_PRIVATE *psf = (SF_PRIVATE*) client_data ; + + psf_log_printf (psf, "ERROR : %s\n", FLAC__StreamDecoderErrorStatusString [status]) ; + + switch (status) + { case FLAC__STREAM_DECODER_ERROR_STATUS_LOST_SYNC : + psf->error = SFE_FLAC_LOST_SYNC ; + break ; + case FLAC__STREAM_DECODER_ERROR_STATUS_BAD_HEADER : + psf->error = SFE_FLAC_BAD_HEADER ; + break ; + default : + psf->error = SFE_FLAC_UNKOWN_ERROR ; + break ; + } ; + + return ; +} /* sf_flac_error_callback */ + +static FLAC__SeekableStreamEncoderSeekStatus +sf_flac_enc_seek_callback (const FLAC__SeekableStreamEncoder * UNUSED (encoder), FLAC__uint64 absolute_byte_offset, void *client_data) +{ SF_PRIVATE *psf = (SF_PRIVATE*) client_data ; + + psf_fseek (psf, absolute_byte_offset, SEEK_SET) ; + if (psf->error) + return FLAC__SEEKABLE_STREAM_ENCODER_SEEK_STATUS_ERROR ; + + return FLAC__SEEKABLE_STREAM_ENCODER_SEEK_STATUS_OK ; +} /* sf_flac_enc_seek_callback */ + +#ifdef HAVE_FLAC_1_1_1 +static FLAC__SeekableStreamEncoderTellStatus +sf_flac_enc_tell_callback (const FLAC__SeekableStreamEncoder *UNUSED (encoder), FLAC__uint64 *absolute_byte_offset, void *client_data) +{ SF_PRIVATE *psf = (SF_PRIVATE*) client_data ; + + *absolute_byte_offset = psf_ftell (psf) ; + if (psf->error) + return FLAC__SEEKABLE_STREAM_ENCODER_TELL_STATUS_ERROR ; + + return FLAC__SEEKABLE_STREAM_ENCODER_TELL_STATUS_OK ; +} /* sf_flac_enc_tell_callback */ +#endif + +static FLAC__StreamEncoderWriteStatus +sf_flac_enc_write_callback (const FLAC__SeekableStreamEncoder * UNUSED (encoder), const FLAC__byte buffer [], unsigned bytes, unsigned UNUSED (samples), unsigned UNUSED (current_frame), void *client_data) +{ SF_PRIVATE *psf = (SF_PRIVATE*) client_data ; + + if (psf_fwrite (buffer, 1, bytes, psf) == bytes && psf->error == 0) + return FLAC__STREAM_ENCODER_WRITE_STATUS_OK ; + + return FLAC__STREAM_ENCODER_WRITE_STATUS_FATAL_ERROR ; +} /* sf_flac_enc_write_callback */ + +/*------------------------------------------------------------------------------ +** Public function. +*/ + +int +flac_open (SF_PRIVATE *psf) +{ int subformat ; + int error = 0 ; + + FLAC_PRIVATE* pflac = calloc (1, sizeof (FLAC_PRIVATE)) ; + psf->fdata = pflac ; + + if (psf->mode == SFM_RDWR) + return SFE_UNIMPLEMENTED ; + + if (psf->mode == SFM_READ) + { if ((error = flac_read_header (psf))) + return error ; + } ; + + subformat = psf->sf.format & SF_FORMAT_SUBMASK ; + + if (psf->mode == SFM_WRITE) + { if ((psf->sf.format & SF_FORMAT_TYPEMASK) != SF_FORMAT_FLAC) + return SFE_BAD_OPEN_FORMAT ; + + psf->endian = SF_ENDIAN_BIG ; + + if ((error = flac_enc_init (psf))) + return error ; + } ; + + psf->datalength = psf->filelength ; + psf->dataoffset = 0 ; + psf->blockwidth = 0 ; + psf->bytewidth = 1 ; + + psf->container_close = flac_close ; + psf->seek = flac_seek ; + psf->command = flac_command ; + + psf->blockwidth = psf->bytewidth * psf->sf.channels ; + + switch (subformat) + { case SF_FORMAT_PCM_S8 : /* 8-bit FLAC. */ + case SF_FORMAT_PCM_16 : /* 16-bit FLAC. */ + case SF_FORMAT_PCM_24 : /* 24-bit FLAC. */ + error = flac_init (psf) ; + break ; + + default : return SFE_UNIMPLEMENTED ; + } ; + + return error ; +} /* flac_open */ + +/*------------------------------------------------------------------------------ +*/ + +static int +flac_close (SF_PRIVATE *psf) +{ FLAC_PRIVATE* pflac ; + int k ; + + if ((pflac = (FLAC_PRIVATE*) psf->fdata) == NULL) + return 0 ; + + if (psf->mode == SFM_WRITE) + { FLAC__seekable_stream_encoder_finish (pflac->fse) ; + FLAC__seekable_stream_encoder_delete (pflac->fse) ; + if (pflac->encbuffer) + free (pflac->encbuffer) ; + } ; + + if (psf->mode == SFM_READ) + { FLAC__seekable_stream_decoder_finish (pflac->fsd) ; + FLAC__seekable_stream_decoder_delete (pflac->fsd) ; + } ; + + for (k = 0 ; k < ARRAY_LEN (pflac->rbuffer) ; k++) + free (pflac->rbuffer [k]) ; + + free (pflac) ; + psf->fdata = NULL ; + + return 0 ; +} /* flac_close */ + +static int +flac_enc_init (SF_PRIVATE *psf) +{ FLAC_PRIVATE* pflac = (FLAC_PRIVATE*) psf->fdata ; + unsigned bps ; + int k, found ; + + found = 0 ; + for (k = 0 ; k < ARRAY_LEN (legal_sample_rates) ; k++) + if (psf->sf.samplerate == legal_sample_rates [k]) + { found = 1 ; + break ; + } ; + + if (found == 0) + return SFE_FLAC_BAD_SAMPLE_RATE ; + + psf_fseek (psf, 0, SEEK_SET) ; + if ((pflac->fse = FLAC__seekable_stream_encoder_new ()) == NULL) + return SFE_FLAC_NEW_DECODER ; + FLAC__seekable_stream_encoder_set_write_callback (pflac->fse, sf_flac_enc_write_callback) ; + FLAC__seekable_stream_encoder_set_seek_callback (pflac->fse, sf_flac_enc_seek_callback) ; + +#ifdef HAVE_FLAC_1_1_1 + FLAC__seekable_stream_encoder_set_tell_callback (pflac->fse, sf_flac_enc_tell_callback) ; +#endif + FLAC__seekable_stream_encoder_set_client_data (pflac->fse, psf) ; + FLAC__seekable_stream_encoder_set_channels (pflac->fse, psf->sf.channels) ; + FLAC__seekable_stream_encoder_set_sample_rate (pflac->fse, psf->sf.samplerate) ; + + switch (psf->sf.format & SF_FORMAT_SUBMASK) + { case SF_FORMAT_PCM_S8 : + bps = 8 ; + break ; + case SF_FORMAT_PCM_16 : + bps = 16 ; + break ; + case SF_FORMAT_PCM_24 : + bps = 24 ; + break ; + + default : + bps = 0 ; + break ; + } ; + + FLAC__seekable_stream_encoder_set_bits_per_sample (pflac->fse, bps) ; + + if ((bps = FLAC__seekable_stream_encoder_init (pflac->fse)) != FLAC__SEEKABLE_STREAM_DECODER_OK) + { psf_log_printf (psf, "Error : FLAC encoder init returned error : %s\n", FLAC__seekable_stream_encoder_get_resolved_state_string (pflac->fse)) ; + return SFE_FLAC_INIT_DECODER ; + } ; + + if (psf->error == 0) + psf->dataoffset = psf_ftell (psf) ; + pflac->encbuffer = calloc (ENC_BUFFER_SIZE, sizeof (FLAC__int32)) ; + + return psf->error ; +} /* flac_enc_init */ + +static int +flac_read_header (SF_PRIVATE *psf) +{ FLAC_PRIVATE* pflac = (FLAC_PRIVATE*) psf->fdata ; + + psf_fseek (psf, 0, SEEK_SET) ; + if ((pflac->fsd = FLAC__seekable_stream_decoder_new ()) == NULL) + return SFE_FLAC_NEW_DECODER ; + + FLAC__seekable_stream_decoder_set_read_callback (pflac->fsd, sf_flac_read_callback) ; + FLAC__seekable_stream_decoder_set_seek_callback (pflac->fsd, sf_flac_seek_callback) ; + FLAC__seekable_stream_decoder_set_tell_callback (pflac->fsd, sf_flac_tell_callback) ; + FLAC__seekable_stream_decoder_set_length_callback (pflac->fsd, sf_flac_length_callback) ; + FLAC__seekable_stream_decoder_set_eof_callback (pflac->fsd, sf_flac_eof_callback) ; + FLAC__seekable_stream_decoder_set_write_callback (pflac->fsd, sf_flac_write_callback) ; + FLAC__seekable_stream_decoder_set_metadata_callback (pflac->fsd, sf_flac_meta_callback) ; + FLAC__seekable_stream_decoder_set_error_callback (pflac->fsd, sf_flac_error_callback) ; + FLAC__seekable_stream_decoder_set_client_data (pflac->fsd, psf) ; + + if (FLAC__seekable_stream_decoder_init (pflac->fsd) != FLAC__SEEKABLE_STREAM_DECODER_OK) + return SFE_FLAC_INIT_DECODER ; + + FLAC__seekable_stream_decoder_process_until_end_of_metadata (pflac->fsd) ; + if (psf->error == 0) + { FLAC__uint64 position ; + FLAC__seekable_stream_decoder_get_decode_position (pflac->fsd, &position) ; + psf->dataoffset = position ; + } ; + + return psf->error ; +} /* flac_read_header */ + +static int +flac_command (SF_PRIVATE *psf, int command, void *data, int datasize) +{ + /* Avoid compiler warnings. */ + psf = psf ; + data = data ; + datasize = datasize ; + + switch (command) + { default : break ; + } ; + + return 0 ; +} /* flac_command */ + +int +flac_init (SF_PRIVATE *psf) +{ + if (psf->mode == SFM_RDWR) + return SFE_BAD_MODE_RW ; + + if (psf->mode == SFM_READ) + { psf->read_short = flac_read_flac2s ; + psf->read_int = flac_read_flac2i ; + psf->read_float = flac_read_flac2f ; + psf->read_double = flac_read_flac2d ; + } ; + + if (psf->mode == SFM_WRITE) + { psf->write_short = flac_write_s2flac ; + psf->write_int = flac_write_i2flac ; + psf->write_float = flac_write_f2flac ; + psf->write_double = flac_write_d2flac ; + } ; + + psf->bytewidth = 1 ; + psf->blockwidth = psf->sf.channels ; + + if (psf->filelength > psf->dataoffset) + psf->datalength = (psf->dataend) ? psf->dataend - psf->dataoffset : psf->filelength - psf->dataoffset ; + else + psf->datalength = 0 ; + + return 0 ; +} /* flac_init */ + +static unsigned +flac_read_loop (SF_PRIVATE *psf, unsigned len) +{ FLAC_PRIVATE* pflac = (FLAC_PRIVATE*) psf->fdata ; + + pflac->pos = 0 ; + pflac->len = len ; + pflac->remain = len ; + if (pflac->frame != NULL && pflac->bufferpos < pflac->frame->header.blocksize) + flac_buffer_copy (psf) ; + + while (pflac->pos < pflac->len) + { if (FLAC__seekable_stream_decoder_process_single (pflac->fsd) == 0) + break ; + if (FLAC__seekable_stream_decoder_get_state (pflac->fsd) != FLAC__SEEKABLE_STREAM_DECODER_OK) + break ; + } ; + + pflac->ptr = NULL ; + + return pflac->pos ; +} /* flac_read_loop */ + +static sf_count_t +flac_read_flac2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ FLAC_PRIVATE* pflac = (FLAC_PRIVATE*) psf->fdata ; + sf_count_t total = 0, current ; + unsigned readlen ; + + pflac->pcmtype = PFLAC_PCM_SHORT ; + + while (total < len) + { pflac->ptr = ptr + total ; + readlen = (len - total > 0x1000000) ? 0x1000000 : (unsigned) (len - total) ; + current = flac_read_loop (psf, readlen) ; + if (current == 0) + break ; + total += current ; + } ; + + return total ; +} /* flac_read_flac2s */ + +static sf_count_t +flac_read_flac2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ FLAC_PRIVATE* pflac = (FLAC_PRIVATE*) psf->fdata ; + sf_count_t total = 0, current ; + unsigned readlen ; + + pflac->pcmtype = PFLAC_PCM_INT ; + + while (total < len) + { pflac->ptr = ptr + total ; + readlen = (len - total > 0x1000000) ? 0x1000000 : (unsigned) (len - total) ; + current = flac_read_loop (psf, readlen) ; + if (current == 0) + break ; + total += current ; + } ; + + return total ; +} /* flac_read_flac2i */ + +static sf_count_t +flac_read_flac2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ FLAC_PRIVATE* pflac = (FLAC_PRIVATE*) psf->fdata ; + sf_count_t total = 0, current ; + unsigned readlen ; + + pflac->pcmtype = PFLAC_PCM_FLOAT ; + + while (total < len) + { pflac->ptr = ptr + total ; + readlen = (len - total > 0x1000000) ? 0x1000000 : (unsigned) (len - total) ; + current = flac_read_loop (psf, readlen) ; + if (current == 0) + break ; + total += current ; + } ; + + return total ; +} /* flac_read_flac2f */ + +static sf_count_t +flac_read_flac2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ FLAC_PRIVATE* pflac = (FLAC_PRIVATE*) psf->fdata ; + sf_count_t total = 0, current ; + unsigned readlen ; + + pflac->pcmtype = PFLAC_PCM_DOUBLE ; + + while (total < len) + { pflac->ptr = ptr + total ; + readlen = (len - total > 0x1000000) ? 0x1000000 : (unsigned) (len - total) ; + current = flac_read_loop (psf, readlen) ; + if (current == 0) + break ; + total += current ; + } ; + + return total ; +} /* flac_read_flac2d */ + +static sf_count_t +flac_write_s2flac (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ FLAC_PRIVATE* pflac = (FLAC_PRIVATE*) psf->fdata ; + void (*convert) (const short *, FLAC__int32 *, int) ; + int bufferlen, writecount, thiswrite ; + sf_count_t total = 0 ; + FLAC__int32* buffer = pflac->encbuffer ; + + switch (psf->sf.format & SF_FORMAT_SUBMASK) + { case SF_FORMAT_PCM_S8 : + convert = s2flac8_array ; + break ; + case SF_FORMAT_PCM_16 : + convert = s2flac16_array ; + break ; + case SF_FORMAT_PCM_24 : + convert = s2flac24_array ; + break ; + default : + return -1 ; + } ; + + bufferlen = ENC_BUFFER_SIZE / (sizeof (FLAC__int32) * psf->sf.channels) ; + bufferlen *= psf->sf.channels ; + + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : (int) len ; + convert (ptr + total, buffer, writecount) ; + if (FLAC__seekable_stream_encoder_process_interleaved (pflac->fse, buffer, writecount/psf->sf.channels)) + thiswrite = writecount ; + else + break ; + total += thiswrite ; + if (thiswrite < writecount) + break ; + + len -= thiswrite ; + } ; + + return total ; +} /* flac_write_s2flac */ + +static sf_count_t +flac_write_i2flac (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ FLAC_PRIVATE* pflac = (FLAC_PRIVATE*) psf->fdata ; + void (*convert) (const int *, FLAC__int32 *, int) ; + int bufferlen, writecount, thiswrite ; + sf_count_t total = 0 ; + FLAC__int32* buffer = pflac->encbuffer ; + + switch (psf->sf.format & SF_FORMAT_SUBMASK) + { case SF_FORMAT_PCM_S8 : + convert = i2flac8_array ; + break ; + case SF_FORMAT_PCM_16 : + convert = i2flac16_array ; + break ; + case SF_FORMAT_PCM_24 : + convert = i2flac24_array ; + break ; + default : + return -1 ; + } ; + + bufferlen = ENC_BUFFER_SIZE / (sizeof (FLAC__int32) * psf->sf.channels) ; + bufferlen *= psf->sf.channels ; + + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : (int) len ; + convert (ptr + total, buffer, writecount) ; + if (FLAC__seekable_stream_encoder_process_interleaved (pflac->fse, buffer, writecount/psf->sf.channels)) + thiswrite = writecount ; + else + break ; + total += thiswrite ; + if (thiswrite < writecount) + break ; + + len -= thiswrite ; + } ; + + return total ; +} /* flac_write_i2flac */ + +static sf_count_t +flac_write_f2flac (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ FLAC_PRIVATE* pflac = (FLAC_PRIVATE*) psf->fdata ; + void (*convert) (const float *, FLAC__int32 *, int, int) ; + int bufferlen, writecount, thiswrite ; + sf_count_t total = 0 ; + FLAC__int32* buffer = pflac->encbuffer ; + + switch (psf->sf.format & SF_FORMAT_SUBMASK) + { case SF_FORMAT_PCM_S8 : + convert = (psf->add_clipping) ? f2flac8_clip_array : f2flac8_array ; + break ; + case SF_FORMAT_PCM_16 : + convert = (psf->add_clipping) ? f2flac16_clip_array : f2flac16_array ; + break ; + case SF_FORMAT_PCM_24 : + convert = (psf->add_clipping) ? f2flac24_clip_array : f2flac24_array ; + break ; + default : + return -1 ; + } ; + + bufferlen = ENC_BUFFER_SIZE / (sizeof (FLAC__int32) * psf->sf.channels) ; + bufferlen *= psf->sf.channels ; + + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : (int) len ; + convert (ptr + total, buffer, writecount, psf->norm_float) ; + if (FLAC__seekable_stream_encoder_process_interleaved (pflac->fse, buffer, writecount/psf->sf.channels)) + thiswrite = writecount ; + else + break ; + total += thiswrite ; + if (thiswrite < writecount) + break ; + + len -= thiswrite ; + } ; + + return total ; +} /* flac_write_f2flac */ + +static void +f2flac8_clip_array (const float *src, FLAC__int32 *dest, int count, int normalize) +{ float normfact, scaled_value ; + + normfact = normalize ? (8.0 * 0x10) : 1.0 ; + + while (--count >= 0) + { scaled_value = src [count] * normfact ; + if (CPU_CLIPS_POSITIVE == 0 && scaled_value >= (1.0 * 0x7F)) + { dest [count] = 0x7F ; + continue ; + } ; + if (CPU_CLIPS_NEGATIVE == 0 && scaled_value <= (-8.0 * 0x10)) + { dest [count] = 0x80 ; + continue ; + } ; + dest [count] = lrintf (scaled_value) ; + } ; + + return ; +} /* f2flac8_clip_array */ + +static void +f2flac16_clip_array (const float *src, FLAC__int32 *dest, int count, int normalize) +{ + float normfact, scaled_value ; + + normfact = normalize ? (8.0 * 0x1000) : 1.0 ; + + while (--count >= 0) { + scaled_value = src [count] * normfact ; + if (CPU_CLIPS_POSITIVE == 0 && scaled_value >= (1.0 * 0x7FFF)) { + dest [count] = 0x7FFF ; + continue ; + } + if (CPU_CLIPS_NEGATIVE == 0 && scaled_value <= (-8.0 * 0x1000)) { + dest [count] = 0x8000 ; + continue ; + } + dest [count] = lrintf (scaled_value) ; + } +} /* f2flac16_clip_array */ + +static void +f2flac24_clip_array (const float *src, FLAC__int32 *dest, int count, int normalize) +{ float normfact, scaled_value ; + + normfact = normalize ? (8.0 * 0x100000) : 1.0 ; + + while (--count >= 0) + { scaled_value = src [count] * normfact ; + if (CPU_CLIPS_POSITIVE == 0 && scaled_value >= (1.0 * 0x7FFFFF)) + { dest [count] = 0x7FFFFF ; + continue ; + } ; + + if (CPU_CLIPS_NEGATIVE == 0 && scaled_value <= (-8.0 * 0x100000)) + { dest [count] = 0x800000 ; + continue ; + } + dest [count] = lrintf (scaled_value) ; + } ; + + return ; +} /* f2flac24_clip_array */ + +static void +f2flac8_array (const float *src, FLAC__int32 *dest, int count, int normalize) +{ float normfact = normalize ? (1.0 * 0x7F) : 1.0 ; + + while (--count >= 0) + dest [count] = lrintf (src [count] * normfact) ; +} /* f2flac8_array */ + +static void +f2flac16_array (const float *src, FLAC__int32 *dest, int count, int normalize) +{ float normfact = normalize ? (1.0 * 0x7FFF) : 1.0 ; + + while (--count >= 0) + dest [count] = lrintf (src [count] * normfact) ; +} /* f2flac16_array */ + +static void +f2flac24_array (const float *src, FLAC__int32 *dest, int count, int normalize) +{ float normfact = normalize ? (1.0 * 0x7FFFFF) : 1.0 ; + + while (--count >= 0) + dest [count] = lrintf (src [count] * normfact) ; +} /* f2flac24_array */ + +static sf_count_t +flac_write_d2flac (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ FLAC_PRIVATE* pflac = (FLAC_PRIVATE*) psf->fdata ; + void (*convert) (const double *, FLAC__int32 *, int, int) ; + int bufferlen, writecount, thiswrite ; + sf_count_t total = 0 ; + FLAC__int32* buffer = pflac->encbuffer ; + + switch (psf->sf.format & SF_FORMAT_SUBMASK) + { case SF_FORMAT_PCM_S8 : + convert = (psf->add_clipping) ? d2flac8_clip_array : d2flac8_array ; + break ; + case SF_FORMAT_PCM_16 : + convert = (psf->add_clipping) ? d2flac16_clip_array : d2flac16_array ; + break ; + case SF_FORMAT_PCM_24 : + convert = (psf->add_clipping) ? d2flac24_clip_array : d2flac24_array ; + break ; + default : + return -1 ; + } ; + + bufferlen = ENC_BUFFER_SIZE / (sizeof (FLAC__int32) * psf->sf.channels) ; + bufferlen *= psf->sf.channels ; + + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : (int) len ; + convert (ptr + total, buffer, writecount, psf->norm_double) ; + if (FLAC__seekable_stream_encoder_process_interleaved (pflac->fse, buffer, writecount/psf->sf.channels)) + thiswrite = writecount ; + else + break ; + total += thiswrite ; + if (thiswrite < writecount) + break ; + + len -= thiswrite ; + } ; + + return total ; +} /* flac_write_d2flac */ + +static void +d2flac8_clip_array (const double *src, FLAC__int32 *dest, int count, int normalize) +{ double normfact, scaled_value ; + + normfact = normalize ? (8.0 * 0x10) : 1.0 ; + + while (--count >= 0) + { scaled_value = src [count] * normfact ; + if (CPU_CLIPS_POSITIVE == 0 && scaled_value >= (1.0 * 0x7F)) + { dest [count] = 0x7F ; + continue ; + } ; + if (CPU_CLIPS_NEGATIVE == 0 && scaled_value <= (-8.0 * 0x10)) + { dest [count] = 0x80 ; + continue ; + } ; + dest [count] = lrint (scaled_value) ; + } ; + + return ; +} /* d2flac8_clip_array */ + +static void +d2flac16_clip_array (const double *src, FLAC__int32 *dest, int count, int normalize) +{ double normfact, scaled_value ; + + normfact = normalize ? (8.0 * 0x1000) : 1.0 ; + + while (--count >= 0) + { scaled_value = src [count] * normfact ; + if (CPU_CLIPS_POSITIVE == 0 && scaled_value >= (1.0 * 0x7FFF)) + { dest [count] = 0x7FFF ; + continue ; + } ; + if (CPU_CLIPS_NEGATIVE == 0 && scaled_value <= (-8.0 * 0x1000)) + { dest [count] = 0x8000 ; + continue ; + } ; + dest [count] = lrint (scaled_value) ; + } ; + + return ; +} /* d2flac16_clip_array */ + +static void +d2flac24_clip_array (const double *src, FLAC__int32 *dest, int count, int normalize) +{ double normfact, scaled_value ; + + normfact = normalize ? (8.0 * 0x100000) : 1.0 ; + + while (--count >= 0) + { scaled_value = src [count] * normfact ; + if (CPU_CLIPS_POSITIVE == 0 && scaled_value >= (1.0 * 0x7FFFFF)) + { dest [count] = 0x7FFFFF ; + continue ; + } ; + if (CPU_CLIPS_NEGATIVE == 0 && scaled_value <= (-8.0 * 0x100000)) + { dest [count] = 0x800000 ; + continue ; + } ; + dest [count] = lrint (scaled_value) ; + } ; + + return ; +} /* d2flac24_clip_array */ + +static void +d2flac8_array (const double *src, FLAC__int32 *dest, int count, int normalize) +{ double normfact = normalize ? (1.0 * 0x7F) : 1.0 ; + + while (--count >= 0) + dest [count] = lrint (src [count] * normfact) ; +} /* d2flac8_array */ + +static void +d2flac16_array (const double *src, FLAC__int32 *dest, int count, int normalize) +{ double normfact = normalize ? (1.0 * 0x7FFF) : 1.0 ; + + while (--count >= 0) + dest [count] = lrint (src [count] * normfact) ; +} /* d2flac16_array */ + +static void +d2flac24_array (const double *src, FLAC__int32 *dest, int count, int normalize) +{ double normfact = normalize ? (1.0 * 0x7FFFFF) : 1.0 ; + + while (--count >= 0) + dest [count] = lrint (src [count] * normfact) ; +} /* d2flac24_array */ + +static sf_count_t +flac_seek (SF_PRIVATE *psf, int UNUSED (mode), sf_count_t offset) +{ FLAC_PRIVATE* pflac = (FLAC_PRIVATE*) psf->fdata ; + + if (pflac == NULL) + return 0 ; + + if (psf->dataoffset < 0) + { psf->error = SFE_BAD_SEEK ; + return ((sf_count_t) -1) ; + } ; + + pflac->frame = NULL ; + + if (psf->mode == SFM_READ) + { FLAC__uint64 position ; + if (FLAC__seekable_stream_decoder_seek_absolute (pflac->fsd, offset)) + { FLAC__seekable_stream_decoder_get_decode_position (pflac->fsd, &position) ; + return offset ; + } ; + + return ((sf_count_t) -1) ; + } ; + + /* Seeking in write mode not yet supported. */ + psf->error = SFE_BAD_SEEK ; + + return ((sf_count_t) -1) ; +} /* flac_seek */ + +#endif + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 46d49617-ebff-42b4-8f66-a0e428147360 +*/ diff --git a/libs/libsndfile/src/float32.c b/libs/libsndfile/src/float32.c new file mode 100644 index 0000000000..b376e60f7d --- /dev/null +++ b/libs/libsndfile/src/float32.c @@ -0,0 +1,961 @@ +/* +** Copyright (C) 1999-2005 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" +#include "float_cast.h" + +#if CPU_IS_LITTLE_ENDIAN + #define FLOAT32_READ float32_le_read + #define FLOAT32_WRITE float32_le_write +#elif CPU_IS_BIG_ENDIAN + #define FLOAT32_READ float32_be_read + #define FLOAT32_WRITE float32_be_write +#endif + +/*-------------------------------------------------------------------------------------------- +** Processor floating point capabilities. float32_get_capability () returns one of the +** latter four values. +*/ + +enum +{ FLOAT_UNKNOWN = 0x00, + FLOAT_CAN_RW_LE = 0x12, + FLOAT_CAN_RW_BE = 0x23, + FLOAT_BROKEN_LE = 0x34, + FLOAT_BROKEN_BE = 0x45 +} ; + +/*-------------------------------------------------------------------------------------------- +** Prototypes for private functions. +*/ + +static sf_count_t host_read_f2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t host_read_f2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t host_read_f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t host_read_f2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; + +static sf_count_t host_write_s2f (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t host_write_i2f (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t host_write_f (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t host_write_d2f (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; + +static void float32_peak_update (SF_PRIVATE *psf, const float *buffer, int count, sf_count_t indx) ; + +static sf_count_t replace_read_f2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t replace_read_f2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t replace_read_f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t replace_read_f2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; + +static sf_count_t replace_write_s2f (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t replace_write_i2f (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t replace_write_f (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t replace_write_d2f (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; + +static void bf2f_array (float *buffer, int count) ; +static void f2bf_array (float *buffer, int count) ; + +static int float32_get_capability (SF_PRIVATE *psf) ; + +/*-------------------------------------------------------------------------------------------- +** Exported functions. +*/ + +int +float32_init (SF_PRIVATE *psf) +{ static int float_caps ; + + float_caps = float32_get_capability (psf) ; + + psf->blockwidth = sizeof (float) * psf->sf.channels ; + + if (psf->mode == SFM_READ || psf->mode == SFM_RDWR) + { switch (psf->endian + float_caps) + { case (SF_ENDIAN_BIG + FLOAT_CAN_RW_BE) : + psf->float_endswap = SF_FALSE ; + psf->read_short = host_read_f2s ; + psf->read_int = host_read_f2i ; + psf->read_float = host_read_f ; + psf->read_double = host_read_f2d ; + break ; + + case (SF_ENDIAN_LITTLE + FLOAT_CAN_RW_LE) : + psf->float_endswap = SF_FALSE ; + psf->read_short = host_read_f2s ; + psf->read_int = host_read_f2i ; + psf->read_float = host_read_f ; + psf->read_double = host_read_f2d ; + break ; + + case (SF_ENDIAN_BIG + FLOAT_CAN_RW_LE) : + psf->float_endswap = SF_TRUE ; + psf->read_short = host_read_f2s ; + psf->read_int = host_read_f2i ; + psf->read_float = host_read_f ; + psf->read_double = host_read_f2d ; + break ; + + case (SF_ENDIAN_LITTLE + FLOAT_CAN_RW_BE) : + psf->float_endswap = SF_TRUE ; + psf->read_short = host_read_f2s ; + psf->read_int = host_read_f2i ; + psf->read_float = host_read_f ; + psf->read_double = host_read_f2d ; + break ; + + /* When the CPU is not IEEE compatible. */ + case (SF_ENDIAN_BIG + FLOAT_BROKEN_LE) : + psf->float_endswap = SF_TRUE ; + psf->read_short = replace_read_f2s ; + psf->read_int = replace_read_f2i ; + psf->read_float = replace_read_f ; + psf->read_double = replace_read_f2d ; + break ; + + case (SF_ENDIAN_LITTLE + FLOAT_BROKEN_LE) : + psf->float_endswap = SF_FALSE ; + psf->read_short = replace_read_f2s ; + psf->read_int = replace_read_f2i ; + psf->read_float = replace_read_f ; + psf->read_double = replace_read_f2d ; + break ; + + case (SF_ENDIAN_BIG + FLOAT_BROKEN_BE) : + psf->float_endswap = SF_FALSE ; + psf->read_short = replace_read_f2s ; + psf->read_int = replace_read_f2i ; + psf->read_float = replace_read_f ; + psf->read_double = replace_read_f2d ; + break ; + + case (SF_ENDIAN_LITTLE + FLOAT_BROKEN_BE) : + psf->float_endswap = SF_TRUE ; + psf->read_short = replace_read_f2s ; + psf->read_int = replace_read_f2i ; + psf->read_float = replace_read_f ; + psf->read_double = replace_read_f2d ; + break ; + + default : break ; + } ; + } ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { switch (psf->endian + float_caps) + { case (SF_ENDIAN_LITTLE + FLOAT_CAN_RW_LE) : + psf->float_endswap = SF_FALSE ; + psf->write_short = host_write_s2f ; + psf->write_int = host_write_i2f ; + psf->write_float = host_write_f ; + psf->write_double = host_write_d2f ; + break ; + + case (SF_ENDIAN_BIG + FLOAT_CAN_RW_BE) : + psf->float_endswap = SF_FALSE ; + psf->write_short = host_write_s2f ; + psf->write_int = host_write_i2f ; + psf->write_float = host_write_f ; + psf->write_double = host_write_d2f ; + break ; + + case (SF_ENDIAN_BIG + FLOAT_CAN_RW_LE) : + psf->float_endswap = SF_TRUE ; + psf->write_short = host_write_s2f ; + psf->write_int = host_write_i2f ; + psf->write_float = host_write_f ; + psf->write_double = host_write_d2f ; + break ; + + case (SF_ENDIAN_LITTLE + FLOAT_CAN_RW_BE) : + psf->float_endswap = SF_TRUE ; + psf->write_short = host_write_s2f ; + psf->write_int = host_write_i2f ; + psf->write_float = host_write_f ; + psf->write_double = host_write_d2f ; + break ; + + /* When the CPU is not IEEE compatible. */ + case (SF_ENDIAN_BIG + FLOAT_BROKEN_LE) : + psf->float_endswap = SF_TRUE ; + psf->write_short = replace_write_s2f ; + psf->write_int = replace_write_i2f ; + psf->write_float = replace_write_f ; + psf->write_double = replace_write_d2f ; + break ; + + case (SF_ENDIAN_LITTLE + FLOAT_BROKEN_LE) : + psf->float_endswap = SF_FALSE ; + psf->write_short = replace_write_s2f ; + psf->write_int = replace_write_i2f ; + psf->write_float = replace_write_f ; + psf->write_double = replace_write_d2f ; + break ; + + case (SF_ENDIAN_BIG + FLOAT_BROKEN_BE) : + psf->float_endswap = SF_FALSE ; + psf->write_short = replace_write_s2f ; + psf->write_int = replace_write_i2f ; + psf->write_float = replace_write_f ; + psf->write_double = replace_write_d2f ; + break ; + + case (SF_ENDIAN_LITTLE + FLOAT_BROKEN_BE) : + psf->float_endswap = SF_TRUE ; + psf->write_short = replace_write_s2f ; + psf->write_int = replace_write_i2f ; + psf->write_float = replace_write_f ; + psf->write_double = replace_write_d2f ; + break ; + + default : break ; + } ; + } ; + + if (psf->filelength > psf->dataoffset) + { psf->datalength = (psf->dataend > 0) ? psf->dataend - psf->dataoffset : + psf->filelength - psf->dataoffset ; + } + else + psf->datalength = 0 ; + + psf->sf.frames = psf->datalength / psf->blockwidth ; + + return 0 ; +} /* float32_init */ + +float +float32_be_read (unsigned char *cptr) +{ int exponent, mantissa, negative ; + float fvalue ; + + negative = cptr [0] & 0x80 ; + exponent = ((cptr [0] & 0x7F) << 1) | ((cptr [1] & 0x80) ? 1 : 0) ; + mantissa = ((cptr [1] & 0x7F) << 16) | (cptr [2] << 8) | (cptr [3]) ; + + if (! (exponent || mantissa)) + return 0.0 ; + + mantissa |= 0x800000 ; + exponent = exponent ? exponent - 127 : 0 ; + + fvalue = mantissa ? ((float) mantissa) / ((float) 0x800000) : 0.0 ; + + if (negative) + fvalue *= -1 ; + + if (exponent > 0) + fvalue *= (1 << exponent) ; + else if (exponent < 0) + fvalue /= (1 << abs (exponent)) ; + + return fvalue ; +} /* float32_be_read */ + +float +float32_le_read (unsigned char *cptr) +{ int exponent, mantissa, negative ; + float fvalue ; + + negative = cptr [3] & 0x80 ; + exponent = ((cptr [3] & 0x7F) << 1) | ((cptr [2] & 0x80) ? 1 : 0) ; + mantissa = ((cptr [2] & 0x7F) << 16) | (cptr [1] << 8) | (cptr [0]) ; + + if (! (exponent || mantissa)) + return 0.0 ; + + mantissa |= 0x800000 ; + exponent = exponent ? exponent - 127 : 0 ; + + fvalue = mantissa ? ((float) mantissa) / ((float) 0x800000) : 0.0 ; + + if (negative) + fvalue *= -1 ; + + if (exponent > 0) + fvalue *= (1 << exponent) ; + else if (exponent < 0) + fvalue /= (1 << abs (exponent)) ; + + return fvalue ; +} /* float32_le_read */ + +void +float32_le_write (float in, unsigned char *out) +{ int exponent, mantissa, negative = 0 ; + + memset (out, 0, sizeof (int)) ; + + if (fabs (in) < 1e-30) + return ; + + if (in < 0.0) + { in *= -1.0 ; + negative = 1 ; + } ; + + in = frexp (in, &exponent) ; + + exponent += 126 ; + + in *= (float) 0x1000000 ; + mantissa = (((int) in) & 0x7FFFFF) ; + + if (negative) + out [3] |= 0x80 ; + + if (exponent & 0x01) + out [2] |= 0x80 ; + + out [0] = mantissa & 0xFF ; + out [1] = (mantissa >> 8) & 0xFF ; + out [2] |= (mantissa >> 16) & 0x7F ; + out [3] |= (exponent >> 1) & 0x7F ; + + return ; +} /* float32_le_write */ + +void +float32_be_write (float in, unsigned char *out) +{ int exponent, mantissa, negative = 0 ; + + memset (out, 0, sizeof (int)) ; + + if (fabs (in) < 1e-30) + return ; + + if (in < 0.0) + { in *= -1.0 ; + negative = 1 ; + } ; + + in = frexp (in, &exponent) ; + + exponent += 126 ; + + in *= (float) 0x1000000 ; + mantissa = (((int) in) & 0x7FFFFF) ; + + if (negative) + out [0] |= 0x80 ; + + if (exponent & 0x01) + out [1] |= 0x80 ; + + out [3] = mantissa & 0xFF ; + out [2] = (mantissa >> 8) & 0xFF ; + out [1] |= (mantissa >> 16) & 0x7F ; + out [0] |= (exponent >> 1) & 0x7F ; + + return ; +} /* float32_be_write */ + +/*============================================================================================== +** Private functions. +*/ + +static void +float32_peak_update (SF_PRIVATE *psf, const float *buffer, int count, sf_count_t indx) +{ int chan ; + int k, position ; + float fmaxval ; + + for (chan = 0 ; chan < psf->sf.channels ; chan++) + { fmaxval = fabs (buffer [chan]) ; + position = 0 ; + for (k = chan ; k < count ; k += psf->sf.channels) + if (fmaxval < fabs (buffer [k])) + { fmaxval = fabs (buffer [k]) ; + position = k ; + } ; + + if (fmaxval > psf->peak_info->peaks [chan].value) + { psf->peak_info->peaks [chan].value = fmaxval ; + psf->peak_info->peaks [chan].position = psf->write_current + indx + (position / psf->sf.channels) ; + } ; + } ; + + return ; +} /* float32_peak_update */ + +static int +float32_get_capability (SF_PRIVATE *psf) +{ union + { float f ; + int i ; + unsigned char c [4] ; + } data ; + + data.f = (float) 1.23456789 ; /* Some abitrary value. */ + + if (! psf->ieee_replace) + { /* If this test is true ints and floats are compatible and little endian. */ + if (data.c [0] == 0x52 && data.c [1] == 0x06 && data.c [2] == 0x9e && data.c [3] == 0x3f) + return FLOAT_CAN_RW_LE ; + + /* If this test is true ints and floats are compatible and big endian. */ + if (data.c [3] == 0x52 && data.c [2] == 0x06 && data.c [1] == 0x9e && data.c [0] == 0x3f) + return FLOAT_CAN_RW_BE ; + } ; + + /* Floats are broken. Don't expect reading or writing to be fast. */ + psf_log_printf (psf, "Using IEEE replacement code for float.\n") ; + + return (CPU_IS_LITTLE_ENDIAN) ? FLOAT_BROKEN_LE : FLOAT_BROKEN_BE ; +} /* float32_get_capability */ + +/*======================================================================================= +*/ + +static inline void +f2s_array (const float *src, int count, short *dest, float scale) +{ while (--count >= 0) + { dest [count] = lrintf (scale * src [count]) ; + } ; +} /* f2s_array */ + +static inline void +f2i_array (const float *src, int count, int *dest, float scale) +{ while (--count >= 0) + { dest [count] = lrintf (scale * src [count]) ; + } ; +} /* f2i_array */ + +static inline void +f2d_array (const float *src, int count, double *dest) +{ while (--count >= 0) + { dest [count] = src [count] ; + } ; +} /* f2d_array */ + +static inline void +s2f_array (const short *src, float *dest, int count) +{ while (--count >= 0) + { dest [count] = src [count] ; + } ; + +} /* s2f_array */ + +static inline void +i2f_array (const int *src, float *dest, int count) +{ while (--count >= 0) + { dest [count] = src [count] ; + } ; +} /* i2f_array */ + +static inline void +d2f_array (const double *src, float *dest, int count) +{ while (--count >= 0) + { dest [count] = src [count] ; + } ; +} /* d2f_array */ + +/*---------------------------------------------------------------------------------------------- +*/ + +static sf_count_t +host_read_f2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + float scale ; + + bufferlen = ARRAY_LEN (psf->u.fbuf) ; + scale = (psf->float_int_mult == 0) ? 1.0 : 0x7FFF / psf->float_max ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.fbuf, sizeof (float), bufferlen, psf) ; + +/* Fix me : Need lef2s_array */ + if (psf->float_endswap == SF_TRUE) + endswap_int_array (psf->u.ibuf, bufferlen) ; + + f2s_array (psf->u.fbuf, readcount, ptr + total, scale) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* host_read_f2s */ + +static sf_count_t +host_read_f2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + float scale ; + + bufferlen = ARRAY_LEN (psf->u.fbuf) ; + scale = (psf->float_int_mult == 0) ? 1.0 : 0x7FFFFFFF / psf->float_max ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.fbuf, sizeof (float), bufferlen, psf) ; + + if (psf->float_endswap == SF_TRUE) + endswap_int_array (psf->u.ibuf, bufferlen) ; + + f2i_array (psf->u.fbuf, readcount, ptr + total, scale) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* host_read_f2i */ + +static sf_count_t +host_read_f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + + if (psf->float_endswap != SF_TRUE) + return psf_fread (ptr, sizeof (float), len, psf) ; + + bufferlen = ARRAY_LEN (psf->u.fbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.fbuf, sizeof (float), bufferlen, psf) ; + + endswap_int_copy ((int*) (ptr + total), psf->u.ibuf, readcount) ; + + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* host_read_f */ + +static sf_count_t +host_read_f2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.fbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.fbuf, sizeof (float), bufferlen, psf) ; + + if (psf->float_endswap == SF_TRUE) + endswap_int_array (psf->u.ibuf, bufferlen) ; + +/* Fix me : Need lef2d_array */ + f2d_array (psf->u.fbuf, readcount, ptr + total) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* host_read_f2d */ + +static sf_count_t +host_write_s2f (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.fbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + s2f_array (ptr + total, psf->u.fbuf, bufferlen) ; + + if (psf->peak_info) + float32_peak_update (psf, psf->u.fbuf, bufferlen, total / psf->sf.channels) ; + + if (psf->float_endswap == SF_TRUE) + endswap_int_array (psf->u.ibuf, bufferlen) ; + + writecount = psf_fwrite (psf->u.fbuf, sizeof (float), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* host_write_s2f */ + +static sf_count_t +host_write_i2f (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.fbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + i2f_array (ptr + total, psf->u.fbuf, bufferlen) ; + + if (psf->peak_info) + float32_peak_update (psf, psf->u.fbuf, bufferlen, total / psf->sf.channels) ; + + if (psf->float_endswap == SF_TRUE) + endswap_int_array (psf->u.ibuf, bufferlen) ; + + writecount = psf_fwrite (psf->u.fbuf, sizeof (float) , bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* host_write_i2f */ + +static sf_count_t +host_write_f (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + if (psf->peak_info) + float32_peak_update (psf, ptr, len, 0) ; + + if (psf->float_endswap != SF_TRUE) + return psf_fwrite (ptr, sizeof (float), len, psf) ; + + bufferlen = ARRAY_LEN (psf->u.fbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + + endswap_int_copy (psf->u.ibuf, (const int*) (ptr + total), bufferlen) ; + + writecount = psf_fwrite (psf->u.fbuf, sizeof (float), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* host_write_f */ + +static sf_count_t +host_write_d2f (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.fbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + + d2f_array (ptr + total, psf->u.fbuf, bufferlen) ; + + if (psf->peak_info) + float32_peak_update (psf, psf->u.fbuf, bufferlen, total / psf->sf.channels) ; + + if (psf->float_endswap == SF_TRUE) + endswap_int_array (psf->u.ibuf, bufferlen) ; + + writecount = psf_fwrite (psf->u.fbuf, sizeof (float), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* host_write_d2f */ + +/*======================================================================================= +*/ + +static sf_count_t +replace_read_f2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + float scale ; + + bufferlen = ARRAY_LEN (psf->u.fbuf) ; + scale = (psf->float_int_mult == 0) ? 1.0 : 0x7FFF / psf->float_max ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.fbuf, sizeof (float), bufferlen, psf) ; + + if (psf->float_endswap == SF_TRUE) + endswap_int_array (psf->u.ibuf, bufferlen) ; + + bf2f_array (psf->u.fbuf, bufferlen) ; + + f2s_array (psf->u.fbuf, readcount, ptr + total, scale) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* replace_read_f2s */ + +static sf_count_t +replace_read_f2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + float scale ; + + bufferlen = ARRAY_LEN (psf->u.fbuf) ; + scale = (psf->float_int_mult == 0) ? 1.0 : 0x7FFF / psf->float_max ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.fbuf, sizeof (float), bufferlen, psf) ; + + if (psf->float_endswap == SF_TRUE) + endswap_int_array (psf->u.ibuf, bufferlen) ; + + bf2f_array (psf->u.fbuf, bufferlen) ; + + f2i_array (psf->u.fbuf, readcount, ptr + total, scale) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* replace_read_f2i */ + +static sf_count_t +replace_read_f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + + /* FIX THIS */ + + bufferlen = ARRAY_LEN (psf->u.fbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.fbuf, sizeof (float), bufferlen, psf) ; + + if (psf->float_endswap == SF_TRUE) + endswap_int_array (psf->u.ibuf, bufferlen) ; + + bf2f_array (psf->u.fbuf, bufferlen) ; + + memcpy (ptr + total, psf->u.fbuf, bufferlen * sizeof (float)) ; + + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* replace_read_f */ + +static sf_count_t +replace_read_f2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.fbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.fbuf, sizeof (float), bufferlen, psf) ; + + if (psf->float_endswap == SF_TRUE) + endswap_int_array (psf->u.ibuf, bufferlen) ; + + bf2f_array (psf->u.fbuf, bufferlen) ; + + f2d_array (psf->u.fbuf, readcount, ptr + total) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* replace_read_f2d */ + +static sf_count_t +replace_write_s2f (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.fbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + s2f_array (ptr + total, psf->u.fbuf, bufferlen) ; + + if (psf->peak_info) + float32_peak_update (psf, psf->u.fbuf, bufferlen, total / psf->sf.channels) ; + + f2bf_array (psf->u.fbuf, bufferlen) ; + + if (psf->float_endswap == SF_TRUE) + endswap_int_array (psf->u.ibuf, bufferlen) ; + + writecount = psf_fwrite (psf->u.fbuf, sizeof (float), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* replace_write_s2f */ + +static sf_count_t +replace_write_i2f (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.fbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + i2f_array (ptr + total, psf->u.fbuf, bufferlen) ; + + if (psf->peak_info) + float32_peak_update (psf, psf->u.fbuf, bufferlen, total / psf->sf.channels) ; + + f2bf_array (psf->u.fbuf, bufferlen) ; + + if (psf->float_endswap == SF_TRUE) + endswap_int_array (psf->u.ibuf, bufferlen) ; + + writecount = psf_fwrite (psf->u.fbuf, sizeof (float), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* replace_write_i2f */ + +static sf_count_t +replace_write_f (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + /* FIX THIS */ + if (psf->peak_info) + float32_peak_update (psf, ptr, len, 0) ; + + bufferlen = ARRAY_LEN (psf->u.fbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + + memcpy (psf->u.fbuf, ptr + total, bufferlen * sizeof (float)) ; + + f2bf_array (psf->u.fbuf, bufferlen) ; + + if (psf->float_endswap == SF_TRUE) + endswap_int_array (psf->u.ibuf, bufferlen) ; + + writecount = psf_fwrite (psf->u.fbuf, sizeof (float) , bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* replace_write_f */ + +static sf_count_t +replace_write_d2f (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.fbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + d2f_array (ptr + total, psf->u.fbuf, bufferlen) ; + + if (psf->peak_info) + float32_peak_update (psf, psf->u.fbuf, bufferlen, total / psf->sf.channels) ; + + f2bf_array (psf->u.fbuf, bufferlen) ; + + if (psf->float_endswap == SF_TRUE) + endswap_int_array (psf->u.ibuf, bufferlen) ; + + writecount = psf_fwrite (psf->u.fbuf, sizeof (float), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* replace_write_d2f */ + +/*---------------------------------------------------------------------------------------------- +*/ + +static void +bf2f_array (float *buffer, int count) +{ while (--count >= 0) + { buffer [count] = FLOAT32_READ ((unsigned char *) (buffer + count)) ; + } ; +} /* bf2f_array */ + +static void +f2bf_array (float *buffer, int count) +{ while (--count >= 0) + { FLOAT32_WRITE (buffer [count], (unsigned char*) (buffer + count)) ; + } ; +} /* f2bf_array */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: b6c34917-488c-4145-9648-f4371fc4c889 +*/ diff --git a/libs/libsndfile/src/float_cast.h b/libs/libsndfile/src/float_cast.h new file mode 100644 index 0000000000..099670a365 --- /dev/null +++ b/libs/libsndfile/src/float_cast.h @@ -0,0 +1,262 @@ +/* +** Copyright (C) 2001-2004 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +/* Version 1.4 */ + +#ifndef FLOAT_CAST_HEADER +#define FLOAT_CAST_HEADER + +/*============================================================================ +** On Intel Pentium processors (especially PIII and probably P4), converting +** from float to int is very slow. To meet the C specs, the code produced by +** most C compilers targeting Pentium needs to change the FPU rounding mode +** before the float to int conversion is performed. +** +** Changing the FPU rounding mode causes the FPU pipeline to be flushed. It +** is this flushing of the pipeline which is so slow. +** +** Fortunately the ISO C99 specifications define the functions lrint, lrintf, +** llrint and llrintf which fix this problem as a side effect. +** +** On Unix-like systems, the configure process should have detected the +** presence of these functions. If they weren't found we have to replace them +** here with a standard C cast. +*/ + +/* +** The C99 prototypes for lrint and lrintf are as follows: +** +** long int lrintf (float x) ; +** long int lrint (double x) ; +*/ + +#include "sfconfig.h" + +/* +** The presence of the required functions are detected during the configure +** process and the values HAVE_LRINT and HAVE_LRINTF are set accordingly in +** the sfconfig.h file. +*/ + +#define HAVE_LRINT_REPLACEMENT 0 + +#if (HAVE_LRINT && HAVE_LRINTF) + + /* + ** These defines enable functionality introduced with the 1999 ISO C + ** standard. They must be defined before the inclusion of math.h to + ** engage them. If optimisation is enabled, these functions will be + ** inlined. With optimisation switched off, you have to link in the + ** maths library using -lm. + */ + + #define _ISOC9X_SOURCE 1 + #define _ISOC99_SOURCE 1 + + #define __USE_ISOC9X 1 + #define __USE_ISOC99 1 + + #include + +#elif (defined (__CYGWIN__)) + + #include + + #undef HAVE_LRINT_REPLACEMENT + #define HAVE_LRINT_REPLACEMENT 1 + + #undef lrint + #undef lrintf + + #define lrint double2int + #define lrintf float2int + + /* + ** The native CYGWIN lrint and lrintf functions are buggy: + ** http://sourceware.org/ml/cygwin/2005-06/msg00153.html + ** http://sourceware.org/ml/cygwin/2005-09/msg00047.html + ** and slow. + ** These functions (pulled from the Public Domain MinGW math.h header) + ** replace the native versions. + */ + + static inline long double2int (double in) + { long retval ; + + __asm__ __volatile__ + ( "fistpl %0" + : "=m" (retval) + : "t" (in) + : "st" + ) ; + + return retval ; + } /* double2int */ + + static inline long float2int (float in) + { long retval ; + + __asm__ __volatile__ + ( "fistpl %0" + : "=m" (retval) + : "t" (in) + : "st" + ) ; + + return retval ; + } /* float2int */ + +#elif (defined (WIN32) || defined (_WIN32)) + + #undef HAVE_LRINT_REPLACEMENT + #define HAVE_LRINT_REPLACEMENT 1 + + #include + + /* + ** Win32 doesn't seem to have these functions. + ** Therefore implement inline versions of these functions here. + */ + + __inline long int + lrint (double flt) + { int intgr ; + + _asm + { fld flt + fistp intgr + } ; + + return intgr ; + } + + __inline long int + lrintf (float flt) + { int intgr ; + + _asm + { fld flt + fistp intgr + } ; + + return intgr ; + } + +#elif (defined (__MWERKS__) && defined (macintosh)) + + /* This MacOS 9 solution was provided by Stephane Letz */ + + #undef HAVE_LRINT_REPLACEMENT + #define HAVE_LRINT_REPLACEMENT 1 + #include + + #undef lrint + #undef lrintf + + #define lrint double2int + #define lrintf float2int + + inline int + float2int (register float in) + { long res [2] ; + + asm + { fctiw in, in + stfd in, res + } + return res [1] ; + } /* float2int */ + + inline int + double2int (register double in) + { long res [2] ; + + asm + { fctiw in, in + stfd in, res + } + return res [1] ; + } /* double2int */ + +#elif (defined (__MACH__) && defined (__APPLE__)) + + /* For Apple MacOSX. */ + + #undef HAVE_LRINT_REPLACEMENT + #define HAVE_LRINT_REPLACEMENT 1 + #include + + #undef lrint + #undef lrintf + + #define lrint double2int + #define lrintf float2int + + inline static long + float2int (register float in) + { int res [2] ; + + __asm__ __volatile__ + ( "fctiw %1, %1\n\t" + "stfd %1, %0" + : "=m" (res) /* Output */ + : "f" (in) /* Input */ + : "memory" + ) ; + + return res [1] ; + } /* lrintf */ + + inline static long + double2int (register double in) + { int res [2] ; + + __asm__ __volatile__ + ( "fctiw %1, %1\n\t" + "stfd %1, %0" + : "=m" (res) /* Output */ + : "f" (in) /* Input */ + : "memory" + ) ; + + return res [1] ; + } /* lrint */ + +#else + #ifndef __sgi + #warning "Don't have the functions lrint() and lrintf()." + #warning "Replacing these functions with a standard C cast." + #endif + + #include + + #define lrint(dbl) ((long) (dbl)) + #define lrintf(flt) ((long) (flt)) + +#endif + + +#endif /* FLOAT_CAST_HEADER */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 42db1693-ff61-4051-bac1-e4d24c4e30b7 +*/ diff --git a/libs/libsndfile/src/g72x.c b/libs/libsndfile/src/g72x.c new file mode 100644 index 0000000000..dbbf9dae52 --- /dev/null +++ b/libs/libsndfile/src/g72x.c @@ -0,0 +1,615 @@ +/* +** Copyright (C) 1999-2005 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "float_cast.h" +#include "common.h" +#include "G72x/g72x.h" + +/* This struct is private to the G72x code. */ +struct g72x_state ; +typedef struct g72x_state G72x_STATE ; + +typedef struct +{ /* Private data. Don't mess with it. */ + struct g72x_state * private ; + + /* Public data. Read only. */ + int blocksize, samplesperblock, bytesperblock ; + + /* Public data. Read and write. */ + int blocks_total, block_curr, sample_curr ; + unsigned char block [G72x_BLOCK_SIZE] ; + short samples [G72x_BLOCK_SIZE] ; +} G72x_PRIVATE ; + +static int psf_g72x_decode_block (SF_PRIVATE *psf, G72x_PRIVATE *pg72x) ; +static int psf_g72x_encode_block (SF_PRIVATE *psf, G72x_PRIVATE *pg72x) ; + +static sf_count_t g72x_read_s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t g72x_read_i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t g72x_read_f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t g72x_read_d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; + +static sf_count_t g72x_write_s (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t g72x_write_i (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t g72x_write_f (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t g72x_write_d (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; + +static sf_count_t g72x_seek (SF_PRIVATE *psf, int mode, sf_count_t offset) ; + +static int g72x_close (SF_PRIVATE *psf) ; + + +/*============================================================================================ +** WAV G721 Reader initialisation function. +*/ + +int +g72x_init (SF_PRIVATE * psf) +{ G72x_PRIVATE *pg72x ; + int bitspersample, bytesperblock, codec ; + + if (psf->fdata != NULL) + { psf_log_printf (psf, "*** psf->fdata is not NULL.\n") ; + return SFE_INTERNAL ; + } ; + + psf->sf.seekable = SF_FALSE ; + + if (psf->sf.channels != 1) + return SFE_G72X_NOT_MONO ; + + if ((pg72x = calloc (1, sizeof (G72x_PRIVATE))) == NULL) + return SFE_MALLOC_FAILED ; + + psf->fdata = (void*) pg72x ; + + pg72x->block_curr = 0 ; + pg72x->sample_curr = 0 ; + + switch (psf->sf.format & SF_FORMAT_SUBMASK) + { case SF_FORMAT_G721_32 : + codec = G721_32_BITS_PER_SAMPLE ; + bytesperblock = G721_32_BYTES_PER_BLOCK ; + bitspersample = G721_32_BITS_PER_SAMPLE ; + break ; + + case SF_FORMAT_G723_24: + codec = G723_24_BITS_PER_SAMPLE ; + bytesperblock = G723_24_BYTES_PER_BLOCK ; + bitspersample = G723_24_BITS_PER_SAMPLE ; + break ; + + case SF_FORMAT_G723_40: + codec = G723_40_BITS_PER_SAMPLE ; + bytesperblock = G723_40_BYTES_PER_BLOCK ; + bitspersample = G723_40_BITS_PER_SAMPLE ; + break ; + + default : return SFE_UNIMPLEMENTED ; + } ; + + psf->blockwidth = psf->bytewidth = 1 ; + + psf->filelength = psf_get_filelen (psf) ; + if (psf->filelength < psf->dataoffset) + psf->filelength = psf->dataoffset ; + + psf->datalength = psf->filelength - psf->dataoffset ; + if (psf->dataend > 0) + psf->datalength -= psf->filelength - psf->dataend ; + + if (psf->mode == SFM_READ) + { pg72x->private = g72x_reader_init (codec, &(pg72x->blocksize), &(pg72x->samplesperblock)) ; + if (pg72x->private == NULL) + return SFE_MALLOC_FAILED ; + + pg72x->bytesperblock = bytesperblock ; + + psf->read_short = g72x_read_s ; + psf->read_int = g72x_read_i ; + psf->read_float = g72x_read_f ; + psf->read_double = g72x_read_d ; + + psf->seek = g72x_seek ; + + if (psf->datalength % pg72x->blocksize) + { psf_log_printf (psf, "*** Odd psf->datalength (%D) should be a multiple of %d\n", psf->datalength, pg72x->blocksize) ; + pg72x->blocks_total = (psf->datalength / pg72x->blocksize) + 1 ; + } + else + pg72x->blocks_total = psf->datalength / pg72x->blocksize ; + + psf->sf.frames = pg72x->blocks_total * pg72x->samplesperblock ; + + psf_g72x_decode_block (psf, pg72x) ; + } + else if (psf->mode == SFM_WRITE) + { pg72x->private = g72x_writer_init (codec, &(pg72x->blocksize), &(pg72x->samplesperblock)) ; + if (pg72x->private == NULL) + return SFE_MALLOC_FAILED ; + + pg72x->bytesperblock = bytesperblock ; + + psf->write_short = g72x_write_s ; + psf->write_int = g72x_write_i ; + psf->write_float = g72x_write_f ; + psf->write_double = g72x_write_d ; + + if (psf->datalength % pg72x->blocksize) + pg72x->blocks_total = (psf->datalength / pg72x->blocksize) + 1 ; + else + pg72x->blocks_total = psf->datalength / pg72x->blocksize ; + + if (psf->datalength > 0) + psf->sf.frames = (8 * psf->datalength) / bitspersample ; + + if ((psf->sf.frames * bitspersample) / 8 != psf->datalength) + psf_log_printf (psf, "*** Warning : weird psf->datalength.\n") ; + } ; + + psf->codec_close = g72x_close ; + + return 0 ; +} /* g72x_init */ + +/*============================================================================================ +** G721 Read Functions. +*/ + +static int +psf_g72x_decode_block (SF_PRIVATE *psf, G72x_PRIVATE *pg72x) +{ int k ; + + pg72x->block_curr ++ ; + pg72x->sample_curr = 0 ; + + if (pg72x->block_curr > pg72x->blocks_total) + { memset (pg72x->samples, 0, G72x_BLOCK_SIZE * sizeof (short)) ; + return 1 ; + } ; + + if ((k = psf_fread (pg72x->block, 1, pg72x->bytesperblock, psf)) != pg72x->bytesperblock) + psf_log_printf (psf, "*** Warning : short read (%d != %d).\n", k, pg72x->bytesperblock) ; + + pg72x->blocksize = k ; + g72x_decode_block (pg72x->private, pg72x->block, pg72x->samples) ; + + return 1 ; +} /* psf_g72x_decode_block */ + +static int +g72x_read_block (SF_PRIVATE *psf, G72x_PRIVATE *pg72x, short *ptr, int len) +{ int count, total = 0, indx = 0 ; + + while (indx < len) + { if (pg72x->block_curr > pg72x->blocks_total) + { memset (&(ptr [indx]), 0, (len - indx) * sizeof (short)) ; + return total ; + } ; + + if (pg72x->sample_curr >= pg72x->samplesperblock) + psf_g72x_decode_block (psf, pg72x) ; + + count = pg72x->samplesperblock - pg72x->sample_curr ; + count = (len - indx > count) ? count : len - indx ; + + memcpy (&(ptr [indx]), &(pg72x->samples [pg72x->sample_curr]), count * sizeof (short)) ; + indx += count ; + pg72x->sample_curr += count ; + total = indx ; + } ; + + return total ; +} /* g72x_read_block */ + +static sf_count_t +g72x_read_s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ G72x_PRIVATE *pg72x ; + int readcount, count ; + sf_count_t total = 0 ; + + if (psf->fdata == NULL) + return 0 ; + pg72x = (G72x_PRIVATE*) psf->fdata ; + + while (len > 0) + { readcount = (len > 0x10000000) ? 0x10000000 : (int) len ; + + count = g72x_read_block (psf, pg72x, ptr, readcount) ; + + total += count ; + len -= count ; + + if (count != readcount) + break ; + } ; + + return total ; +} /* g72x_read_s */ + +static sf_count_t +g72x_read_i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ G72x_PRIVATE *pg72x ; + short *sptr ; + int k, bufferlen, readcount = 0, count ; + sf_count_t total = 0 ; + + if (psf->fdata == NULL) + return 0 ; + pg72x = (G72x_PRIVATE*) psf->fdata ; + + sptr = psf->u.sbuf ; + bufferlen = SF_BUFFER_LEN / sizeof (short) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : len ; + count = g72x_read_block (psf, pg72x, sptr, readcount) ; + + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = sptr [k] << 16 ; + + total += count ; + len -= readcount ; + if (count != readcount) + break ; + } ; + + return total ; +} /* g72x_read_i */ + +static sf_count_t +g72x_read_f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ G72x_PRIVATE *pg72x ; + short *sptr ; + int k, bufferlen, readcount = 0, count ; + sf_count_t total = 0 ; + float normfact ; + + if (psf->fdata == NULL) + return 0 ; + pg72x = (G72x_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_float == SF_TRUE) ? 1.0 / ((float) 0x8000) : 1.0 ; + + sptr = psf->u.sbuf ; + bufferlen = SF_BUFFER_LEN / sizeof (short) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : len ; + count = g72x_read_block (psf, pg72x, sptr, readcount) ; + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = normfact * sptr [k] ; + + total += count ; + len -= readcount ; + if (count != readcount) + break ; + } ; + + return total ; +} /* g72x_read_f */ + +static sf_count_t +g72x_read_d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ G72x_PRIVATE *pg72x ; + short *sptr ; + int k, bufferlen, readcount = 0, count ; + sf_count_t total = 0 ; + double normfact ; + + if (psf->fdata == NULL) + return 0 ; + pg72x = (G72x_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_double == SF_TRUE) ? 1.0 / ((double) 0x8000) : 1.0 ; + + sptr = psf->u.sbuf ; + bufferlen = SF_BUFFER_LEN / sizeof (short) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : len ; + count = g72x_read_block (psf, pg72x, sptr, readcount) ; + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = normfact * (double) (sptr [k]) ; + + total += count ; + len -= readcount ; + if (count != readcount) + break ; + } ; + + return total ; +} /* g72x_read_d */ + +static sf_count_t +g72x_seek (SF_PRIVATE *psf, int mode, sf_count_t offset) +{ + /* Prevent compiler warnings. */ + mode ++ ; + offset ++ ; + + psf_log_printf (psf, "seek unsupported\n") ; + + /* No simple solution. To do properly, would need to seek + ** to start of file and decode everything up to seek position. + ** Maybe implement SEEK_SET to 0 only? + */ + return 0 ; + +/* +** G72x_PRIVATE *pg72x ; +** int newblock, newsample, sample_curr ; +** +** if (psf->fdata == NULL) +** return 0 ; +** pg72x = (G72x_PRIVATE*) psf->fdata ; +** +** if (! (psf->datalength && psf->dataoffset)) +** { psf->error = SFE_BAD_SEEK ; +** return PSF_SEEK_ERROR ; +** } ; +** +** sample_curr = (8 * psf->datalength) / G721_32_BITS_PER_SAMPLE ; +** +** switch (whence) +** { case SEEK_SET : +** if (offset < 0 || offset > sample_curr) +** { psf->error = SFE_BAD_SEEK ; +** return PSF_SEEK_ERROR ; +** } ; +** newblock = offset / pg72x->samplesperblock ; +** newsample = offset % pg72x->samplesperblock ; +** break ; +** +** case SEEK_CUR : +** if (psf->current + offset < 0 || psf->current + offset > sample_curr) +** { psf->error = SFE_BAD_SEEK ; +** return PSF_SEEK_ERROR ; +** } ; +** newblock = (8 * (psf->current + offset)) / pg72x->samplesperblock ; +** newsample = (8 * (psf->current + offset)) % pg72x->samplesperblock ; +** break ; +** +** case SEEK_END : +** if (offset > 0 || sample_curr + offset < 0) +** { psf->error = SFE_BAD_SEEK ; +** return PSF_SEEK_ERROR ; +** } ; +** newblock = (sample_curr + offset) / pg72x->samplesperblock ; +** newsample = (sample_curr + offset) % pg72x->samplesperblock ; +** break ; +** +** default : +** psf->error = SFE_BAD_SEEK ; +** return PSF_SEEK_ERROR ; +** } ; +** +** if (psf->mode == SFM_READ) +** { psf_fseek (psf, psf->dataoffset + newblock * pg72x->blocksize, SEEK_SET) ; +** pg72x->block_curr = newblock ; +** psf_g72x_decode_block (psf, pg72x) ; +** pg72x->sample_curr = newsample ; +** } +** else +** { /+* What to do about write??? *+/ +** psf->error = SFE_BAD_SEEK ; +** return PSF_SEEK_ERROR ; +** } ; +** +** psf->current = newblock * pg72x->samplesperblock + newsample ; +** return psf->current ; +** +*/ +} /* g72x_seek */ + +/*========================================================================================== +** G72x Write Functions. +*/ + +static int +psf_g72x_encode_block (SF_PRIVATE *psf, G72x_PRIVATE *pg72x) +{ int k ; + + /* Encode the samples. */ + g72x_encode_block (pg72x->private, pg72x->samples, pg72x->block) ; + + /* Write the block to disk. */ + if ((k = psf_fwrite (pg72x->block, 1, pg72x->blocksize, psf)) != pg72x->blocksize) + psf_log_printf (psf, "*** Warning : short write (%d != %d).\n", k, pg72x->blocksize) ; + + pg72x->sample_curr = 0 ; + pg72x->block_curr ++ ; + + /* Set samples to zero for next block. */ + memset (pg72x->samples, 0, G72x_BLOCK_SIZE * sizeof (short)) ; + + return 1 ; +} /* psf_g72x_encode_block */ + +static int +g72x_write_block (SF_PRIVATE *psf, G72x_PRIVATE *pg72x, const short *ptr, int len) +{ int count, total = 0, indx = 0 ; + + while (indx < len) + { count = pg72x->samplesperblock - pg72x->sample_curr ; + + if (count > len - indx) + count = len - indx ; + + memcpy (&(pg72x->samples [pg72x->sample_curr]), &(ptr [indx]), count * sizeof (short)) ; + indx += count ; + pg72x->sample_curr += count ; + total = indx ; + + if (pg72x->sample_curr >= pg72x->samplesperblock) + psf_g72x_encode_block (psf, pg72x) ; + } ; + + return total ; +} /* g72x_write_block */ + +static sf_count_t +g72x_write_s (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ G72x_PRIVATE *pg72x ; + int writecount, count ; + sf_count_t total = 0 ; + + if (psf->fdata == NULL) + return 0 ; + pg72x = (G72x_PRIVATE*) psf->fdata ; + + while (len > 0) + { writecount = (len > 0x10000000) ? 0x10000000 : (int) len ; + + count = g72x_write_block (psf, pg72x, ptr, writecount) ; + + total += count ; + len -= count ; + if (count != writecount) + break ; + } ; + + return total ; +} /* g72x_write_s */ + +static sf_count_t +g72x_write_i (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ G72x_PRIVATE *pg72x ; + short *sptr ; + int k, bufferlen, writecount = 0, count ; + sf_count_t total = 0 ; + + if (psf->fdata == NULL) + return 0 ; + pg72x = (G72x_PRIVATE*) psf->fdata ; + + sptr = psf->u.sbuf ; + bufferlen = ((SF_BUFFER_LEN / psf->blockwidth) * psf->blockwidth) / sizeof (short) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : len ; + for (k = 0 ; k < writecount ; k++) + sptr [k] = ptr [total + k] >> 16 ; + count = g72x_write_block (psf, pg72x, sptr, writecount) ; + + total += count ; + len -= writecount ; + if (count != writecount) + break ; + } ; + return total ; +} /* g72x_write_i */ + +static sf_count_t +g72x_write_f (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ G72x_PRIVATE *pg72x ; + short *sptr ; + int k, bufferlen, writecount = 0, count ; + sf_count_t total = 0 ; + float normfact ; + + if (psf->fdata == NULL) + return 0 ; + pg72x = (G72x_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_float == SF_TRUE) ? (1.0 * 0x8000) : 1.0 ; + + sptr = psf->u.sbuf ; + bufferlen = ((SF_BUFFER_LEN / psf->blockwidth) * psf->blockwidth) / sizeof (short) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : len ; + for (k = 0 ; k < writecount ; k++) + sptr [k] = lrintf (normfact * ptr [total + k]) ; + count = g72x_write_block (psf, pg72x, sptr, writecount) ; + + total += count ; + len -= writecount ; + if (count != writecount) + break ; + } ; + + return total ; +} /* g72x_write_f */ + +static sf_count_t +g72x_write_d (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ G72x_PRIVATE *pg72x ; + short *sptr ; + int k, bufferlen, writecount = 0, count ; + sf_count_t total = 0 ; + double normfact ; + + if (psf->fdata == NULL) + return 0 ; + pg72x = (G72x_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_double == SF_TRUE) ? (1.0 * 0x8000) : 1.0 ; + + sptr = psf->u.sbuf ; + bufferlen = ((SF_BUFFER_LEN / psf->blockwidth) * psf->blockwidth) / sizeof (short) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : len ; + for (k = 0 ; k < writecount ; k++) + sptr [k] = lrint (normfact * ptr [total + k]) ; + count = g72x_write_block (psf, pg72x, sptr, writecount) ; + + total += count ; + len -= writecount ; + if (count != writecount) + break ; + } ; + + return total ; +} /* g72x_write_d */ + +static int +g72x_close (SF_PRIVATE *psf) +{ G72x_PRIVATE *pg72x ; + + pg72x = (G72x_PRIVATE*) psf->fdata ; + + if (psf->mode == SFM_WRITE) + { /* If a block has been partially assembled, write it out + ** as the final block. + */ + + if (pg72x->sample_curr && pg72x->sample_curr < G72x_BLOCK_SIZE) + psf_g72x_encode_block (psf, pg72x) ; + + if (psf->write_header) + psf->write_header (psf, SF_FALSE) ; + } ; + + /* Only free the pointer allocated by g72x_(reader|writer)_init. */ + free (pg72x->private) ; + + return 0 ; +} /* g72x_close */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 3cc5439e-7247-486b-b2e6-11a4affa5744 +*/ diff --git a/libs/libsndfile/src/gsm610.c b/libs/libsndfile/src/gsm610.c new file mode 100644 index 0000000000..db954ccb18 --- /dev/null +++ b/libs/libsndfile/src/gsm610.c @@ -0,0 +1,628 @@ +/* +** Copyright (C) 1999-2006 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "float_cast.h" +#include "common.h" +#include "wav_w64.h" +#include "GSM610/gsm.h" + +#define GSM610_BLOCKSIZE 33 +#define GSM610_SAMPLES 160 + +typedef struct gsm610_tag +{ int blocks ; + int blockcount, samplecount ; + int samplesperblock, blocksize ; + + int (*decode_block) (SF_PRIVATE *psf, struct gsm610_tag *pgsm610) ; + int (*encode_block) (SF_PRIVATE *psf, struct gsm610_tag *pgsm610) ; + + short samples [WAV_W64_GSM610_SAMPLES] ; + unsigned char block [WAV_W64_GSM610_BLOCKSIZE] ; + + /* Damn I hate typedef-ed pointers; yes, gsm is a pointer type. */ + gsm gsm_data ; +} GSM610_PRIVATE ; + +static sf_count_t gsm610_read_s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t gsm610_read_i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t gsm610_read_f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t gsm610_read_d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; + +static sf_count_t gsm610_write_s (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t gsm610_write_i (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t gsm610_write_f (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t gsm610_write_d (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; + +static int gsm610_read_block (SF_PRIVATE *psf, GSM610_PRIVATE *pgsm610, short *ptr, int len) ; +static int gsm610_write_block (SF_PRIVATE *psf, GSM610_PRIVATE *pgsm610, const short *ptr, int len) ; + +static int gsm610_decode_block (SF_PRIVATE *psf, GSM610_PRIVATE *pgsm610) ; +static int gsm610_encode_block (SF_PRIVATE *psf, GSM610_PRIVATE *pgsm610) ; + +static int gsm610_wav_decode_block (SF_PRIVATE *psf, GSM610_PRIVATE *pgsm610) ; +static int gsm610_wav_encode_block (SF_PRIVATE *psf, GSM610_PRIVATE *pgsm610) ; + +static sf_count_t gsm610_seek (SF_PRIVATE *psf, int mode, sf_count_t offset) ; + +static int gsm610_close (SF_PRIVATE *psf) ; + +/*============================================================================================ +** WAV GSM610 initialisation function. +*/ + +int +gsm610_init (SF_PRIVATE *psf) +{ GSM610_PRIVATE *pgsm610 ; + int true_flag = 1 ; + + if (psf->fdata != NULL) + { psf_log_printf (psf, "*** psf->fdata is not NULL.\n") ; + return SFE_INTERNAL ; + } ; + + if (psf->mode == SFM_RDWR) + return SFE_BAD_MODE_RW ; + + psf->sf.seekable = SF_FALSE ; + + if ((pgsm610 = calloc (1, sizeof (GSM610_PRIVATE))) == NULL) + return SFE_MALLOC_FAILED ; + + psf->fdata = (void*) pgsm610 ; + + memset (pgsm610, 0, sizeof (GSM610_PRIVATE)) ; + +/*============================================================ + +Need separate gsm_data structs for encode and decode. + +============================================================*/ + + if ((pgsm610->gsm_data = gsm_create ()) == NULL) + return SFE_MALLOC_FAILED ; + + switch (psf->sf.format & SF_FORMAT_TYPEMASK) + { case SF_FORMAT_WAV : + case SF_FORMAT_WAVEX : + case SF_FORMAT_W64 : + gsm_option (pgsm610->gsm_data, GSM_OPT_WAV49, &true_flag) ; + + pgsm610->encode_block = gsm610_wav_encode_block ; + pgsm610->decode_block = gsm610_wav_decode_block ; + + pgsm610->samplesperblock = WAV_W64_GSM610_SAMPLES ; + pgsm610->blocksize = WAV_W64_GSM610_BLOCKSIZE ; + break ; + + case SF_FORMAT_AIFF : + case SF_FORMAT_RAW : + pgsm610->encode_block = gsm610_encode_block ; + pgsm610->decode_block = gsm610_decode_block ; + + pgsm610->samplesperblock = GSM610_SAMPLES ; + pgsm610->blocksize = GSM610_BLOCKSIZE ; + break ; + + default : + return SFE_INTERNAL ; + break ; + } ; + + if (psf->mode == SFM_READ) + { if (psf->datalength % pgsm610->blocksize == 0) + pgsm610->blocks = psf->datalength / pgsm610->blocksize ; + else if (psf->datalength % pgsm610->blocksize == 1 && pgsm610->blocksize == GSM610_BLOCKSIZE) + { /* + ** Weird AIFF specific case. + ** AIFF chunks must be at an odd offset from the start of file and + ** GSM610_BLOCKSIZE is odd which can result in an odd length SSND + ** chunk. The SSND chunk then gets padded on write which means that + ** when it is read the datalength is too big by 1. + */ + pgsm610->blocks = psf->datalength / pgsm610->blocksize ; + } + else + { psf_log_printf (psf, "*** Warning : data chunk seems to be truncated.\n") ; + pgsm610->blocks = psf->datalength / pgsm610->blocksize + 1 ; + } ; + + psf->sf.frames = pgsm610->samplesperblock * pgsm610->blocks ; + + pgsm610->decode_block (psf, pgsm610) ; /* Read first block. */ + + psf->read_short = gsm610_read_s ; + psf->read_int = gsm610_read_i ; + psf->read_float = gsm610_read_f ; + psf->read_double = gsm610_read_d ; + } ; + + if (psf->mode == SFM_WRITE) + { pgsm610->blockcount = 0 ; + pgsm610->samplecount = 0 ; + + psf->write_short = gsm610_write_s ; + psf->write_int = gsm610_write_i ; + psf->write_float = gsm610_write_f ; + psf->write_double = gsm610_write_d ; + } ; + + psf->codec_close = gsm610_close ; + + psf->seek = gsm610_seek ; + + psf->filelength = psf_get_filelen (psf) ; + psf->datalength = psf->filelength - psf->dataoffset ; + + return 0 ; +} /* gsm610_init */ + +/*============================================================================================ +** GSM 6.10 Read Functions. +*/ + +static int +gsm610_wav_decode_block (SF_PRIVATE *psf, GSM610_PRIVATE *pgsm610) +{ int k ; + + pgsm610->blockcount ++ ; + pgsm610->samplecount = 0 ; + + if (pgsm610->blockcount > pgsm610->blocks) + { memset (pgsm610->samples, 0, WAV_W64_GSM610_SAMPLES * sizeof (short)) ; + return 1 ; + } ; + + if ((k = psf_fread (pgsm610->block, 1, WAV_W64_GSM610_BLOCKSIZE, psf)) != WAV_W64_GSM610_BLOCKSIZE) + psf_log_printf (psf, "*** Warning : short read (%d != %d).\n", k, WAV_W64_GSM610_BLOCKSIZE) ; + + if (gsm_decode (pgsm610->gsm_data, pgsm610->block, pgsm610->samples) < 0) + { psf_log_printf (psf, "Error from gsm_decode() on frame : %d\n", pgsm610->blockcount) ; + return 0 ; + } ; + + if (gsm_decode (pgsm610->gsm_data, pgsm610->block + (WAV_W64_GSM610_BLOCKSIZE + 1) / 2, pgsm610->samples + WAV_W64_GSM610_SAMPLES / 2) < 0) + { psf_log_printf (psf, "Error from gsm_decode() on frame : %d.5\n", pgsm610->blockcount) ; + return 0 ; + } ; + + return 1 ; +} /* gsm610_wav_decode_block */ + +static int +gsm610_decode_block (SF_PRIVATE *psf, GSM610_PRIVATE *pgsm610) +{ int k ; + + pgsm610->blockcount ++ ; + pgsm610->samplecount = 0 ; + + if (pgsm610->blockcount > pgsm610->blocks) + { memset (pgsm610->samples, 0, GSM610_SAMPLES * sizeof (short)) ; + return 1 ; + } ; + + if ((k = psf_fread (pgsm610->block, 1, GSM610_BLOCKSIZE, psf)) != GSM610_BLOCKSIZE) + psf_log_printf (psf, "*** Warning : short read (%d != %d).\n", k, GSM610_BLOCKSIZE) ; + + if (gsm_decode (pgsm610->gsm_data, pgsm610->block, pgsm610->samples) < 0) + { psf_log_printf (psf, "Error from gsm_decode() on frame : %d\n", pgsm610->blockcount) ; + return 0 ; + } ; + + return 1 ; +} /* gsm610_decode_block */ + +static int +gsm610_read_block (SF_PRIVATE *psf, GSM610_PRIVATE *pgsm610, short *ptr, int len) +{ int count, total = 0, indx = 0 ; + + while (indx < len) + { if (pgsm610->blockcount >= pgsm610->blocks && pgsm610->samplecount >= pgsm610->samplesperblock) + { memset (&(ptr [indx]), 0, (len - indx) * sizeof (short)) ; + return total ; + } ; + + if (pgsm610->samplecount >= pgsm610->samplesperblock) + pgsm610->decode_block (psf, pgsm610) ; + + count = pgsm610->samplesperblock - pgsm610->samplecount ; + count = (len - indx > count) ? count : len - indx ; + + memcpy (&(ptr [indx]), &(pgsm610->samples [pgsm610->samplecount]), count * sizeof (short)) ; + indx += count ; + pgsm610->samplecount += count ; + total = indx ; + } ; + + return total ; +} /* gsm610_read_block */ + +static sf_count_t +gsm610_read_s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ GSM610_PRIVATE *pgsm610 ; + int readcount, count ; + sf_count_t total = 0 ; + + if (psf->fdata == NULL) + return 0 ; + pgsm610 = (GSM610_PRIVATE*) psf->fdata ; + + while (len > 0) + { readcount = (len > 0x10000000) ? 0x1000000 : (int) len ; + + count = gsm610_read_block (psf, pgsm610, ptr, readcount) ; + + total += count ; + len -= count ; + + if (count != readcount) + break ; + } ; + + return total ; +} /* gsm610_read_s */ + +static sf_count_t +gsm610_read_i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ GSM610_PRIVATE *pgsm610 ; + short *sptr ; + int k, bufferlen, readcount = 0, count ; + sf_count_t total = 0 ; + + if (psf->fdata == NULL) + return 0 ; + pgsm610 = (GSM610_PRIVATE*) psf->fdata ; + + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : len ; + count = gsm610_read_block (psf, pgsm610, sptr, readcount) ; + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = sptr [k] << 16 ; + + total += count ; + len -= readcount ; + } ; + return total ; +} /* gsm610_read_i */ + +static sf_count_t +gsm610_read_f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ GSM610_PRIVATE *pgsm610 ; + short *sptr ; + int k, bufferlen, readcount = 0, count ; + sf_count_t total = 0 ; + float normfact ; + + if (psf->fdata == NULL) + return 0 ; + pgsm610 = (GSM610_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_float == SF_TRUE) ? 1.0 / ((float) 0x8000) : 1.0 ; + + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : len ; + count = gsm610_read_block (psf, pgsm610, sptr, readcount) ; + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = normfact * sptr [k] ; + + total += count ; + len -= readcount ; + } ; + return total ; +} /* gsm610_read_f */ + +static sf_count_t +gsm610_read_d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ GSM610_PRIVATE *pgsm610 ; + short *sptr ; + int k, bufferlen, readcount = 0, count ; + sf_count_t total = 0 ; + double normfact ; + + normfact = (psf->norm_double == SF_TRUE) ? 1.0 / ((double) 0x8000) : 1.0 ; + + if (psf->fdata == NULL) + return 0 ; + pgsm610 = (GSM610_PRIVATE*) psf->fdata ; + + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : len ; + count = gsm610_read_block (psf, pgsm610, sptr, readcount) ; + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = normfact * sptr [k] ; + + total += count ; + len -= readcount ; + } ; + return total ; +} /* gsm610_read_d */ + +static sf_count_t +gsm610_seek (SF_PRIVATE *psf, int mode, sf_count_t offset) +{ GSM610_PRIVATE *pgsm610 ; + int newblock, newsample ; + + mode = mode ; + + if (psf->fdata == NULL) + return 0 ; + pgsm610 = (GSM610_PRIVATE*) psf->fdata ; + + if (psf->dataoffset < 0) + { psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; + } ; + + if (offset == 0) + { int true_flag = 1 ; + + psf_fseek (psf, psf->dataoffset, SEEK_SET) ; + pgsm610->blockcount = 0 ; + + gsm_init (pgsm610->gsm_data) ; + if ((psf->sf.format & SF_FORMAT_TYPEMASK) == SF_FORMAT_WAV || + (psf->sf.format & SF_FORMAT_TYPEMASK) == SF_FORMAT_W64) + gsm_option (pgsm610->gsm_data, GSM_OPT_WAV49, &true_flag) ; + + pgsm610->decode_block (psf, pgsm610) ; + pgsm610->samplecount = 0 ; + return 0 ; + } ; + + if (offset < 0 || offset > pgsm610->blocks * pgsm610->samplesperblock) + { psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; + } ; + + newblock = offset / pgsm610->samplesperblock ; + newsample = offset % pgsm610->samplesperblock ; + + if (psf->mode == SFM_READ) + { if (psf->read_current != newblock * pgsm610->samplesperblock + newsample) + { psf_fseek (psf, psf->dataoffset + newblock * pgsm610->samplesperblock, SEEK_SET) ; + pgsm610->blockcount = newblock ; + pgsm610->decode_block (psf, pgsm610) ; + pgsm610->samplecount = newsample ; + } ; + + return newblock * pgsm610->samplesperblock + newsample ; + } ; + + /* What to do about write??? */ + psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; +} /* gsm610_seek */ + +/*========================================================================================== +** GSM 6.10 Write Functions. +*/ + +static int +gsm610_encode_block (SF_PRIVATE *psf, GSM610_PRIVATE *pgsm610) +{ int k ; + + /* Encode the samples. */ + gsm_encode (pgsm610->gsm_data, pgsm610->samples, pgsm610->block) ; + + /* Write the block to disk. */ + if ((k = psf_fwrite (pgsm610->block, 1, GSM610_BLOCKSIZE, psf)) != GSM610_BLOCKSIZE) + psf_log_printf (psf, "*** Warning : short write (%d != %d).\n", k, GSM610_BLOCKSIZE) ; + + pgsm610->samplecount = 0 ; + pgsm610->blockcount ++ ; + + /* Set samples to zero for next block. */ + memset (pgsm610->samples, 0, WAV_W64_GSM610_SAMPLES * sizeof (short)) ; + + return 1 ; +} /* gsm610_encode_block */ + +static int +gsm610_wav_encode_block (SF_PRIVATE *psf, GSM610_PRIVATE *pgsm610) +{ int k ; + + /* Encode the samples. */ + gsm_encode (pgsm610->gsm_data, pgsm610->samples, pgsm610->block) ; + gsm_encode (pgsm610->gsm_data, pgsm610->samples+WAV_W64_GSM610_SAMPLES/2, pgsm610->block+WAV_W64_GSM610_BLOCKSIZE/2) ; + + /* Write the block to disk. */ + if ((k = psf_fwrite (pgsm610->block, 1, WAV_W64_GSM610_BLOCKSIZE, psf)) != WAV_W64_GSM610_BLOCKSIZE) + psf_log_printf (psf, "*** Warning : short write (%d != %d).\n", k, WAV_W64_GSM610_BLOCKSIZE) ; + + pgsm610->samplecount = 0 ; + pgsm610->blockcount ++ ; + + /* Set samples to zero for next block. */ + memset (pgsm610->samples, 0, WAV_W64_GSM610_SAMPLES * sizeof (short)) ; + + return 1 ; +} /* gsm610_wav_encode_block */ + +static int +gsm610_write_block (SF_PRIVATE *psf, GSM610_PRIVATE *pgsm610, const short *ptr, int len) +{ int count, total = 0, indx = 0 ; + + while (indx < len) + { count = pgsm610->samplesperblock - pgsm610->samplecount ; + + if (count > len - indx) + count = len - indx ; + + memcpy (&(pgsm610->samples [pgsm610->samplecount]), &(ptr [indx]), count * sizeof (short)) ; + indx += count ; + pgsm610->samplecount += count ; + total = indx ; + + if (pgsm610->samplecount >= pgsm610->samplesperblock) + pgsm610->encode_block (psf, pgsm610) ; + } ; + + return total ; +} /* gsm610_write_block */ + +static sf_count_t +gsm610_write_s (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ GSM610_PRIVATE *pgsm610 ; + int writecount, count ; + sf_count_t total = 0 ; + + if (psf->fdata == NULL) + return 0 ; + pgsm610 = (GSM610_PRIVATE*) psf->fdata ; + + while (len > 0) + { writecount = (len > 0x10000000) ? 0x10000000 : (int) len ; + + count = gsm610_write_block (psf, pgsm610, ptr, writecount) ; + + total += count ; + len -= count ; + + if (count != writecount) + break ; + } ; + + return total ; +} /* gsm610_write_s */ + +static sf_count_t +gsm610_write_i (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ GSM610_PRIVATE *pgsm610 ; + short *sptr ; + int k, bufferlen, writecount = 0, count ; + sf_count_t total = 0 ; + + if (psf->fdata == NULL) + return 0 ; + pgsm610 = (GSM610_PRIVATE*) psf->fdata ; + + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : len ; + for (k = 0 ; k < writecount ; k++) + sptr [k] = ptr [total + k] >> 16 ; + count = gsm610_write_block (psf, pgsm610, sptr, writecount) ; + + total += count ; + len -= writecount ; + } ; + return total ; +} /* gsm610_write_i */ + +static sf_count_t +gsm610_write_f (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ GSM610_PRIVATE *pgsm610 ; + short *sptr ; + int k, bufferlen, writecount = 0, count ; + sf_count_t total = 0 ; + float normfact ; + + if (psf->fdata == NULL) + return 0 ; + pgsm610 = (GSM610_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_float == SF_TRUE) ? (1.0 * 0x7FFF) : 1.0 ; + + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : len ; + for (k = 0 ; k < writecount ; k++) + sptr [k] = lrintf (normfact * ptr [total + k]) ; + count = gsm610_write_block (psf, pgsm610, sptr, writecount) ; + + total += count ; + len -= writecount ; + } ; + return total ; +} /* gsm610_write_f */ + +static sf_count_t +gsm610_write_d (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ GSM610_PRIVATE *pgsm610 ; + short *sptr ; + int k, bufferlen, writecount = 0, count ; + sf_count_t total = 0 ; + double normfact ; + + if (psf->fdata == NULL) + return 0 ; + pgsm610 = (GSM610_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_double == SF_TRUE) ? (1.0 * 0x7FFF) : 1.0 ; + + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : len ; + for (k = 0 ; k < writecount ; k++) + sptr [k] = lrint (normfact * ptr [total + k]) ; + count = gsm610_write_block (psf, pgsm610, sptr, writecount) ; + + total += count ; + len -= writecount ; + } ; + return total ; +} /* gsm610_write_d */ + +static int +gsm610_close (SF_PRIVATE *psf) +{ GSM610_PRIVATE *pgsm610 ; + + if (psf->fdata == NULL) + return 0 ; + + pgsm610 = (GSM610_PRIVATE*) psf->fdata ; + + if (psf->mode == SFM_WRITE) + { /* If a block has been partially assembled, write it out + ** as the final block. + */ + + if (pgsm610->samplecount && pgsm610->samplecount < pgsm610->samplesperblock) + pgsm610->encode_block (psf, pgsm610) ; + } ; + + if (pgsm610->gsm_data) + gsm_destroy (pgsm610->gsm_data) ; + + return 0 ; +} /* gsm610_close */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 8575187d-af4f-4acf-b9dd-6ff705628345 +*/ diff --git a/libs/libsndfile/src/htk.c b/libs/libsndfile/src/htk.c new file mode 100644 index 0000000000..716868b5b8 --- /dev/null +++ b/libs/libsndfile/src/htk.c @@ -0,0 +1,225 @@ +/* +** Copyright (C) 2002-2004 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" + +/*------------------------------------------------------------------------------ +** Macros to handle big/little endian issues. +*/ + +#define SFE_HTK_BAD_FILE_LEN 1666 +#define SFE_HTK_NOT_WAVEFORM 1667 + +/*------------------------------------------------------------------------------ +** Private static functions. +*/ + +static int htk_close (SF_PRIVATE *psf) ; + +static int htk_write_header (SF_PRIVATE *psf, int calc_length) ; +static int htk_read_header (SF_PRIVATE *psf) ; + +/*------------------------------------------------------------------------------ +** Public function. +*/ + +int +htk_open (SF_PRIVATE *psf) +{ int subformat ; + int error = 0 ; + + if (psf->is_pipe) + return SFE_HTK_NO_PIPE ; + + if (psf->mode == SFM_READ || (psf->mode == SFM_RDWR && psf->filelength > 0)) + { if ((error = htk_read_header (psf))) + return error ; + } ; + + subformat = psf->sf.format & SF_FORMAT_SUBMASK ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { if ((psf->sf.format & SF_FORMAT_TYPEMASK) != SF_FORMAT_HTK) + return SFE_BAD_OPEN_FORMAT ; + + psf->endian = SF_ENDIAN_BIG ; + + if (htk_write_header (psf, SF_FALSE)) + return psf->error ; + + psf->write_header = htk_write_header ; + } ; + + psf->container_close = htk_close ; + + psf->blockwidth = psf->bytewidth * psf->sf.channels ; + + switch (subformat) + { case SF_FORMAT_PCM_16 : /* 16-bit linear PCM. */ + error = pcm_init (psf) ; + break ; + + default : break ; + } ; + + return error ; +} /* htk_open */ + +/*------------------------------------------------------------------------------ +*/ + +static int +htk_close (SF_PRIVATE *psf) +{ + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + htk_write_header (psf, SF_TRUE) ; + + return 0 ; +} /* htk_close */ + +static int +htk_write_header (SF_PRIVATE *psf, int calc_length) +{ sf_count_t current ; + int sample_count, sample_period ; + + current = psf_ftell (psf) ; + + if (calc_length) + psf->filelength = psf_get_filelen (psf) ; + + /* Reset the current header length to zero. */ + psf->header [0] = 0 ; + psf->headindex = 0 ; + psf_fseek (psf, 0, SEEK_SET) ; + + if (psf->filelength > 12) + sample_count = (psf->filelength - 12) / 2 ; + else + sample_count = 0 ; + + sample_period = 10000000 / psf->sf.samplerate ; + + psf_binheader_writef (psf, "E444", sample_count, sample_period, 0x20000) ; + + /* Header construction complete so write it out. */ + psf_fwrite (psf->header, psf->headindex, 1, psf) ; + + if (psf->error) + return psf->error ; + + psf->dataoffset = psf->headindex ; + + if (current > 0) + psf_fseek (psf, current, SEEK_SET) ; + + return psf->error ; +} /* htk_write_header */ + +/* +** Found the following info in a comment block within Bill Schottstaedt's +** sndlib library. +** +** HTK format files consist of a contiguous sequence of samples preceded by a +** header. Each sample is a vector of either 2-byte integers or 4-byte floats. +** 2-byte integers are used for compressed forms as described below and for +** vector quantised data as described later in section 5.11. HTK format data +** files can also be used to store speech waveforms as described in section 5.8. +** +** The HTK file format header is 12 bytes long and contains the following data +** nSamples -- number of samples in file (4-byte integer) +** sampPeriod -- sample period in 100ns units (4-byte integer) +** sampSize -- number of bytes per sample (2-byte integer) +** parmKind -- a code indicating the sample kind (2-byte integer) +** +** The parameter kind consists of a 6 bit code representing the basic +** parameter kind plus additional bits for each of the possible qualifiers. +** The basic parameter kind codes are +** +** 0 WAVEFORM sampled waveform +** 1 LPC linear prediction filter coefficients +** 2 LPREFC linear prediction reflection coefficients +** 3 LPCEPSTRA LPC cepstral coefficients +** 4 LPDELCEP LPC cepstra plus delta coefficients +** 5 IREFC LPC reflection coef in 16 bit integer format +** 6 MFCC mel-frequency cepstral coefficients +** 7 FBANK log mel-filter bank channel outputs +** 8 MELSPEC linear mel-filter bank channel outputs +** 9 USER user defined sample kind +** 10 DISCRETE vector quantised data +** +** and the bit-encoding for the qualifiers (in octal) is +** _E 000100 has energy +** _N 000200 absolute energy suppressed +** _D 000400 has delta coefficients +** _A 001000 has acceleration coefficients +** _C 002000 is compressed +** _Z 004000 has zero mean static coef. +** _K 010000 has CRC checksum +** _O 020000 has 0'th cepstral coef. +*/ + +static int +htk_read_header (SF_PRIVATE *psf) +{ int sample_count, sample_period, marker ; + + psf_binheader_readf (psf, "pE444", 0, &sample_count, &sample_period, &marker) ; + + if (2 * sample_count + 12 != psf->filelength) + return SFE_HTK_BAD_FILE_LEN ; + + if (marker != 0x20000) + return SFE_HTK_NOT_WAVEFORM ; + + psf->sf.channels = 1 ; + psf->sf.samplerate = 10000000 / sample_period ; + + psf_log_printf (psf, "HTK Waveform file\n Sample Count : %d\n Sample Period : %d => %d Hz\n", + sample_count, sample_period, psf->sf.samplerate) ; + + psf->sf.format = SF_FORMAT_HTK | SF_FORMAT_PCM_16 ; + psf->bytewidth = 2 ; + + /* HTK always has a 12 byte header. */ + psf->dataoffset = 12 ; + psf->endian = SF_ENDIAN_BIG ; + + psf->datalength = psf->filelength - psf->dataoffset ; + + psf->blockwidth = psf->sf.channels * psf->bytewidth ; + + if (! psf->sf.frames && psf->blockwidth) + psf->sf.frames = (psf->filelength - psf->dataoffset) / psf->blockwidth ; + + return 0 ; +} /* htk_read_header */ +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: c350e972-082e-4c20-8934-03391a723560 +*/ diff --git a/libs/libsndfile/src/ima_adpcm.c b/libs/libsndfile/src/ima_adpcm.c new file mode 100644 index 0000000000..abc49e5774 --- /dev/null +++ b/libs/libsndfile/src/ima_adpcm.c @@ -0,0 +1,976 @@ +/* +** Copyright (C) 1999-2005 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "float_cast.h" +#include "common.h" + +typedef struct IMA_ADPCM_PRIVATE_tag +{ int (*decode_block) (SF_PRIVATE *psf, struct IMA_ADPCM_PRIVATE_tag *pima) ; + int (*encode_block) (SF_PRIVATE *psf, struct IMA_ADPCM_PRIVATE_tag *pima) ; + + int channels, blocksize, samplesperblock, blocks ; + int blockcount, samplecount ; + int previous [2] ; + int stepindx [2] ; + unsigned char *block ; + short *samples ; +#if HAVE_FLEXIBLE_ARRAY + short data [] ; /* ISO C99 struct flexible array. */ +#else + short data [0] ; /* This is a hack and might not work. */ +#endif +} IMA_ADPCM_PRIVATE ; + +/*============================================================================================ +** Predefined IMA ADPCM data. +*/ + +static int ima_indx_adjust [16] = +{ -1, -1, -1, -1, /* +0 - +3, decrease the step size */ + 2, 4, 6, 8, /* +4 - +7, increase the step size */ + -1, -1, -1, -1, /* -0 - -3, decrease the step size */ + 2, 4, 6, 8, /* -4 - -7, increase the step size */ +} ; + +static int ima_step_size [89] = +{ 7, 8, 9, 10, 11, 12, 13, 14, 16, 17, 19, 21, 23, 25, 28, 31, 34, 37, 41, 45, + 50, 55, 60, 66, 73, 80, 88, 97, 107, 118, 130, 143, 157, 173, 190, 209, 230, + 253, 279, 307, 337, 371, 408, 449, 494, 544, 598, 658, 724, 796, 876, 963, + 1060, 1166, 1282, 1411, 1552, 1707, 1878, 2066, 2272, 2499, 2749, 3024, 3327, + 3660, 4026, 4428, 4871, 5358, 5894, 6484, 7132, 7845, 8630, 9493, 10442, + 11487, 12635, 13899, 15289, 16818, 18500, 20350, 22385, 24623, 27086, 29794, + 32767 +} ; + +static int ima_reader_init (SF_PRIVATE *psf, int blockalign, int samplesperblock) ; +static int ima_writer_init (SF_PRIVATE *psf, int blockalign) ; + +static int ima_read_block (SF_PRIVATE *psf, IMA_ADPCM_PRIVATE *pima, short *ptr, int len) ; +static int ima_write_block (SF_PRIVATE *psf, IMA_ADPCM_PRIVATE *pima, const short *ptr, int len) ; + +static sf_count_t ima_read_s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t ima_read_i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t ima_read_f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t ima_read_d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; + +static sf_count_t ima_write_s (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t ima_write_i (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t ima_write_f (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t ima_write_d (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; + +static sf_count_t ima_seek (SF_PRIVATE *psf, int mode, sf_count_t offset) ; + +static int ima_close (SF_PRIVATE *psf) ; + +static int wav_w64_ima_decode_block (SF_PRIVATE *psf, IMA_ADPCM_PRIVATE *pima) ; +static int wav_w64_ima_encode_block (SF_PRIVATE *psf, IMA_ADPCM_PRIVATE *pima) ; + +/*-static int aiff_ima_reader_init (SF_PRIVATE *psf, int blockalign, int samplesperblock) ;-*/ +static int aiff_ima_decode_block (SF_PRIVATE *psf, IMA_ADPCM_PRIVATE *pima) ; +static int aiff_ima_encode_block (SF_PRIVATE *psf, IMA_ADPCM_PRIVATE *pima) ; + + +/*============================================================================================ +** IMA ADPCM Reader initialisation function. +*/ + +int +wav_w64_ima_init (SF_PRIVATE *psf, int blockalign, int samplesperblock) +{ int error ; + + if (psf->fdata != NULL) + { psf_log_printf (psf, "*** psf->fdata is not NULL.\n") ; + return SFE_INTERNAL ; + } ; + + if (psf->mode == SFM_RDWR) + return SFE_BAD_MODE_RW ; + + if (psf->mode == SFM_READ) + if ((error = ima_reader_init (psf, blockalign, samplesperblock))) + return error ; + + if (psf->mode == SFM_WRITE) + if ((error = ima_writer_init (psf, blockalign))) + return error ; + + psf->codec_close = ima_close ; + psf->seek = ima_seek ; + + return 0 ; +} /* wav_w64_ima_init */ + +int +aiff_ima_init (SF_PRIVATE *psf, int blockalign, int samplesperblock) +{ int error ; + + if (psf->mode == SFM_RDWR) + return SFE_BAD_MODE_RW ; + + if (psf->mode == SFM_READ) + if ((error = ima_reader_init (psf, blockalign, samplesperblock))) + return error ; + + if (psf->mode == SFM_WRITE) + if ((error = ima_writer_init (psf, blockalign))) + return error ; + + psf->codec_close = ima_close ; + + return 0 ; +} /* aiff_ima_init */ + +static int +ima_close (SF_PRIVATE *psf) +{ IMA_ADPCM_PRIVATE *pima ; + + pima = (IMA_ADPCM_PRIVATE*) psf->fdata ; + + if (psf->mode == SFM_WRITE) + { /* If a block has been partially assembled, write it out + ** as the final block. + */ + if (pima->samplecount && pima->samplecount < pima->samplesperblock) + pima->encode_block (psf, pima) ; + + psf->sf.frames = pima->samplesperblock * pima->blockcount / psf->sf.channels ; + } ; + + return 0 ; +} /* ima_close */ + +/*============================================================================================ +** IMA ADPCM Read Functions. +*/ + +static int +ima_reader_init (SF_PRIVATE *psf, int blockalign, int samplesperblock) +{ IMA_ADPCM_PRIVATE *pima ; + int pimasize, count ; + + if (psf->mode != SFM_READ) + return SFE_BAD_MODE_RW ; + + pimasize = sizeof (IMA_ADPCM_PRIVATE) + blockalign * psf->sf.channels + 3 * psf->sf.channels * samplesperblock ; + + if (! (pima = malloc (pimasize))) + return SFE_MALLOC_FAILED ; + + psf->fdata = (void*) pima ; + + memset (pima, 0, pimasize) ; + + pima->samples = pima->data ; + pima->block = (unsigned char*) (pima->data + samplesperblock * psf->sf.channels) ; + + pima->channels = psf->sf.channels ; + pima->blocksize = blockalign ; + pima->samplesperblock = samplesperblock ; + + psf->filelength = psf_get_filelen (psf) ; + psf->datalength = (psf->dataend) ? psf->dataend - psf->dataoffset : + psf->filelength - psf->dataoffset ; + + if (psf->datalength % pima->blocksize) + pima->blocks = psf->datalength / pima->blocksize + 1 ; + else + pima->blocks = psf->datalength / pima->blocksize ; + + switch (psf->sf.format & SF_FORMAT_TYPEMASK) + { case SF_FORMAT_WAV : + case SF_FORMAT_W64 : + count = 2 * (pima->blocksize - 4 * pima->channels) / pima->channels + 1 ; + + if (pima->samplesperblock != count) + psf_log_printf (psf, "*** Warning : samplesperblock should be %d.\n", count) ; + + pima->decode_block = wav_w64_ima_decode_block ; + + psf->sf.frames = pima->samplesperblock * pima->blocks ; + break ; + + case SF_FORMAT_AIFF : + psf_log_printf (psf, "still need to check block count\n") ; + pima->decode_block = aiff_ima_decode_block ; + psf->sf.frames = pima->samplesperblock * pima->blocks / pima->channels ; + break ; + + default : + psf_log_printf (psf, "ima_reader_init: bad psf->sf.format\n") ; + return SFE_INTERNAL ; + break ; + } ; + + pima->decode_block (psf, pima) ; /* Read first block. */ + + psf->read_short = ima_read_s ; + psf->read_int = ima_read_i ; + psf->read_float = ima_read_f ; + psf->read_double = ima_read_d ; + + return 0 ; +} /* ima_reader_init */ + +static int +aiff_ima_decode_block (SF_PRIVATE *psf, IMA_ADPCM_PRIVATE *pima) +{ unsigned char *blockdata ; + int chan, k, diff, bytecode ; + short step, stepindx, predictor, *sampledata ; + +static int count = 0 ; +count ++ ; + + pima->blockcount += pima->channels ; + pima->samplecount = 0 ; + + if (pima->blockcount > pima->blocks) + { memset (pima->samples, 0, pima->samplesperblock * pima->channels * sizeof (short)) ; + return 1 ; + } ; + + if ((k = psf_fread (pima->block, 1, pima->blocksize * pima->channels, psf)) != pima->blocksize * pima->channels) + psf_log_printf (psf, "*** Warning : short read (%d != %d).\n", k, pima->blocksize) ; + + /* Read and check the block header. */ + for (chan = 0 ; chan < pima->channels ; chan++) + { blockdata = pima->block + chan * 34 ; + sampledata = pima->samples + chan ; + + predictor = (blockdata [0] << 8) | (blockdata [1] & 0x80) ; + stepindx = blockdata [1] & 0x7F ; + +{ +if (count < 5) +printf ("\nchan: %d predictor: %d stepindx: %d (%d)\n", + chan, predictor, stepindx, ima_step_size [stepindx]) ; +} + /* FIXME : Do this a better way. */ + if (stepindx < 0) stepindx = 0 ; + else if (stepindx > 88) stepindx = 88 ; + + /* + ** Pull apart the packed 4 bit samples and store them in their + ** correct sample positions. + */ + for (k = 0 ; k < pima->blocksize - 2 ; k++) + { bytecode = blockdata [k + 2] ; + sampledata [pima->channels * (2 * k + 0)] = bytecode & 0xF ; + sampledata [pima->channels * (2 * k + 1)] = (bytecode >> 4) & 0xF ; + } ; + + /* Decode the encoded 4 bit samples. */ + for (k = 0 ; k < pima->samplesperblock ; k ++) + { step = ima_step_size [stepindx] ; + + bytecode = pima->samples [pima->channels * k + chan] ; + + stepindx += ima_indx_adjust [bytecode] ; + + if (stepindx < 0) stepindx = 0 ; + else if (stepindx > 88) stepindx = 88 ; + + diff = step >> 3 ; + if (bytecode & 1) diff += step >> 2 ; + if (bytecode & 2) diff += step >> 1 ; + if (bytecode & 4) diff += step ; + if (bytecode & 8) diff = -diff ; + + predictor += diff ; + + pima->samples [pima->channels * k + chan] = predictor ; + } ; + } ; + +if (count < 5) +{ + for (k = 0 ; k < 10 ; k++) + printf ("% 7d,", pima->samples [k]) ; + puts ("") ; +} + + return 1 ; +} /* aiff_ima_decode_block */ + +static int +aiff_ima_encode_block (SF_PRIVATE *psf, IMA_ADPCM_PRIVATE *pima) +{ int chan, k, step, diff, vpdiff, blockindx, indx ; + short bytecode, mask ; + +static int count = 0 ; +if (0 && count == 0) +{ pima->samples [0] = 0 ; + printf ("blocksize : %d\n", pima->blocksize) ; + printf ("pima->stepindx [0] : %d\n", pima->stepindx [0]) ; + } +count ++ ; + + /* Encode the block header. */ + for (chan = 0 ; chan < pima->channels ; chan ++) + { blockindx = chan * pima->blocksize ; + + pima->block [blockindx] = (pima->samples [chan] >> 8) & 0xFF ; + pima->block [blockindx + 1] = (pima->samples [chan] & 0x80) + (pima->stepindx [chan] & 0x7F) ; + + pima->previous [chan] = pima->samples [chan] ; + } ; + + /* Encode second and later samples for every block as a 4 bit value. */ + for (k = pima->channels ; k < (pima->samplesperblock * pima->channels) ; k ++) + { chan = (pima->channels > 1) ? (k % 2) : 0 ; + + diff = pima->samples [k] - pima->previous [chan] ; + + bytecode = 0 ; + step = ima_step_size [pima->stepindx [chan]] ; + vpdiff = step >> 3 ; + if (diff < 0) + { bytecode = 8 ; + diff = -diff ; + } ; + mask = 4 ; + while (mask) + { if (diff >= step) + { bytecode |= mask ; + diff -= step ; + vpdiff += step ; + } ; + step >>= 1 ; + mask >>= 1 ; + } ; + + if (bytecode & 8) + pima->previous [chan] -= vpdiff ; + else + pima->previous [chan] += vpdiff ; + + if (pima->previous [chan] > 32767) + pima->previous [chan] = 32767 ; + else if (pima->previous [chan] < -32768) + pima->previous [chan] = -32768 ; + + pima->stepindx [chan] += ima_indx_adjust [bytecode] ; + if (pima->stepindx [chan] < 0) + pima->stepindx [chan] = 0 ; + else if (pima->stepindx [chan] > 88) + pima->stepindx [chan] = 88 ; + + pima->samples [k] = bytecode ; + } ; + + /* Pack the 4 bit encoded samples. */ + + for (chan = 0 ; chan < pima->channels ; chan ++) + { for (indx = pima->channels ; indx < pima->channels * pima->samplesperblock ; indx += 2 * pima->channels) + { blockindx = chan * pima->blocksize + 2 + indx / 2 ; + +if (0 && count ++ < 5) + printf ("chan: %d blockindx: %3d indx: %3d\n", chan, blockindx, indx) ; + + pima->block [blockindx] = pima->samples [indx] & 0x0F ; + pima->block [blockindx] |= (pima->samples [indx + pima->channels] << 4) & 0xF0 ; + } ; + } ; + + /* Write the block to disk. */ + + if ((k = psf_fwrite (pima->block, 1, pima->channels * pima->blocksize, psf)) != pima->channels * pima->blocksize) + psf_log_printf (psf, "*** Warning : short write (%d != %d).\n", k, pima->channels * pima->blocksize) ; + + memset (pima->samples, 0, pima->channels * pima->samplesperblock * sizeof (short)) ; + pima->samplecount = 0 ; + pima->blockcount ++ ; + + return 1 ; +} /* aiff_ima_encode_block */ + +static int +wav_w64_ima_decode_block (SF_PRIVATE *psf, IMA_ADPCM_PRIVATE *pima) +{ int chan, k, current, blockindx, indx, indxstart, diff ; + short step, bytecode, stepindx [2] ; + + pima->blockcount ++ ; + pima->samplecount = 0 ; + + if (pima->blockcount > pima->blocks) + { memset (pima->samples, 0, pima->samplesperblock * pima->channels * sizeof (short)) ; + return 1 ; + } ; + + if ((k = psf_fread (pima->block, 1, pima->blocksize, psf)) != pima->blocksize) + psf_log_printf (psf, "*** Warning : short read (%d != %d).\n", k, pima->blocksize) ; + + /* Read and check the block header. */ + + for (chan = 0 ; chan < pima->channels ; chan++) + { current = pima->block [chan*4] | (pima->block [chan*4+1] << 8) ; + if (current & 0x8000) + current -= 0x10000 ; + + stepindx [chan] = pima->block [chan*4+2] ; + if (stepindx [chan] < 0) + stepindx [chan] = 0 ; + else if (stepindx [chan] > 88) + stepindx [chan] = 88 ; + + if (pima->block [chan*4+3] != 0) + psf_log_printf (psf, "IMA ADPCM synchronisation error.\n") ; + + pima->samples [chan] = current ; + } ; + + /* + ** Pull apart the packed 4 bit samples and store them in their + ** correct sample positions. + */ + + blockindx = 4 * pima->channels ; + + indxstart = pima->channels ; + while (blockindx < pima->blocksize) + { for (chan = 0 ; chan < pima->channels ; chan++) + { indx = indxstart + chan ; + for (k = 0 ; k < 4 ; k++) + { bytecode = pima->block [blockindx++] ; + pima->samples [indx] = bytecode & 0x0F ; + indx += pima->channels ; + pima->samples [indx] = (bytecode >> 4) & 0x0F ; + indx += pima->channels ; + } ; + } ; + indxstart += 8 * pima->channels ; + } ; + + /* Decode the encoded 4 bit samples. */ + + for (k = pima->channels ; k < (pima->samplesperblock * pima->channels) ; k ++) + { chan = (pima->channels > 1) ? (k % 2) : 0 ; + + bytecode = pima->samples [k] & 0xF ; + + step = ima_step_size [stepindx [chan]] ; + current = pima->samples [k - pima->channels] ; + + diff = step >> 3 ; + if (bytecode & 1) + diff += step >> 2 ; + if (bytecode & 2) + diff += step >> 1 ; + if (bytecode & 4) + diff += step ; + if (bytecode & 8) + diff = -diff ; + + current += diff ; + + if (current > 32767) + current = 32767 ; + else if (current < -32768) + current = -32768 ; + + stepindx [chan] += ima_indx_adjust [bytecode] ; + + if (stepindx [chan] < 0) + stepindx [chan] = 0 ; + else if (stepindx [chan] > 88) + stepindx [chan] = 88 ; + + pima->samples [k] = current ; + } ; + + return 1 ; +} /* wav_w64_ima_decode_block */ + +static int +wav_w64_ima_encode_block (SF_PRIVATE *psf, IMA_ADPCM_PRIVATE *pima) +{ int chan, k, step, diff, vpdiff, blockindx, indx, indxstart ; + short bytecode, mask ; + + /* Encode the block header. */ + for (chan = 0 ; chan < pima->channels ; chan++) + { pima->block [chan*4] = pima->samples [chan] & 0xFF ; + pima->block [chan*4+1] = (pima->samples [chan] >> 8) & 0xFF ; + + pima->block [chan*4+2] = pima->stepindx [chan] ; + pima->block [chan*4+3] = 0 ; + + pima->previous [chan] = pima->samples [chan] ; + } ; + + /* Encode the samples as 4 bit. */ + + for (k = pima->channels ; k < (pima->samplesperblock * pima->channels) ; k ++) + { chan = (pima->channels > 1) ? (k % 2) : 0 ; + + diff = pima->samples [k] - pima->previous [chan] ; + + bytecode = 0 ; + step = ima_step_size [pima->stepindx [chan]] ; + vpdiff = step >> 3 ; + if (diff < 0) + { bytecode = 8 ; + diff = -diff ; + } ; + mask = 4 ; + while (mask) + { if (diff >= step) + { bytecode |= mask ; + diff -= step ; + vpdiff += step ; + } ; + step >>= 1 ; + mask >>= 1 ; + } ; + + if (bytecode & 8) + pima->previous [chan] -= vpdiff ; + else + pima->previous [chan] += vpdiff ; + + if (pima->previous [chan] > 32767) + pima->previous [chan] = 32767 ; + else if (pima->previous [chan] < -32768) + pima->previous [chan] = -32768 ; + + pima->stepindx [chan] += ima_indx_adjust [bytecode] ; + if (pima->stepindx [chan] < 0) + pima->stepindx [chan] = 0 ; + else if (pima->stepindx [chan] > 88) + pima->stepindx [chan] = 88 ; + + pima->samples [k] = bytecode ; + } ; + + /* Pack the 4 bit encoded samples. */ + + blockindx = 4 * pima->channels ; + + indxstart = pima->channels ; + while (blockindx < pima->blocksize) + { for (chan = 0 ; chan < pima->channels ; chan++) + { indx = indxstart + chan ; + for (k = 0 ; k < 4 ; k++) + { pima->block [blockindx] = pima->samples [indx] & 0x0F ; + indx += pima->channels ; + pima->block [blockindx] |= (pima->samples [indx] << 4) & 0xF0 ; + indx += pima->channels ; + blockindx ++ ; + } ; + } ; + indxstart += 8 * pima->channels ; + } ; + + /* Write the block to disk. */ + + if ((k = psf_fwrite (pima->block, 1, pima->blocksize, psf)) != pima->blocksize) + psf_log_printf (psf, "*** Warning : short write (%d != %d).\n", k, pima->blocksize) ; + + memset (pima->samples, 0, pima->samplesperblock * sizeof (short)) ; + pima->samplecount = 0 ; + pima->blockcount ++ ; + + return 1 ; +} /* wav_w64_ima_encode_block */ + +static int +ima_read_block (SF_PRIVATE *psf, IMA_ADPCM_PRIVATE *pima, short *ptr, int len) +{ int count, total = 0, indx = 0 ; + + while (indx < len) + { if (pima->blockcount >= pima->blocks && pima->samplecount >= pima->samplesperblock) + { memset (&(ptr [indx]), 0, (size_t) ((len - indx) * sizeof (short))) ; + return total ; + } ; + + if (pima->samplecount >= pima->samplesperblock) + pima->decode_block (psf, pima) ; + + count = (pima->samplesperblock - pima->samplecount) * pima->channels ; + count = (len - indx > count) ? count : len - indx ; + + memcpy (&(ptr [indx]), &(pima->samples [pima->samplecount * pima->channels]), count * sizeof (short)) ; + indx += count ; + pima->samplecount += count / pima->channels ; + total = indx ; + } ; + + return total ; +} /* ima_read_block */ + +static sf_count_t +ima_read_s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ IMA_ADPCM_PRIVATE *pima ; + int readcount, count ; + sf_count_t total = 0 ; + + if (! psf->fdata) + return 0 ; + pima = (IMA_ADPCM_PRIVATE*) psf->fdata ; + + while (len > 0) + { readcount = (len > 0x10000000) ? 0x10000000 : (int) len ; + + count = ima_read_block (psf, pima, ptr, readcount) ; + + total += count ; + len -= count ; + if (count != readcount) + break ; + } ; + + return total ; +} /* ima_read_s */ + +static sf_count_t +ima_read_i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ IMA_ADPCM_PRIVATE *pima ; + short *sptr ; + int k, bufferlen, readcount, count ; + sf_count_t total = 0 ; + + if (! psf->fdata) + return 0 ; + pima = (IMA_ADPCM_PRIVATE*) psf->fdata ; + + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : (int) len ; + count = ima_read_block (psf, pima, sptr, readcount) ; + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = ((int) sptr [k]) << 16 ; + total += count ; + len -= readcount ; + if (count != readcount) + break ; + } ; + + return total ; +} /* ima_read_i */ + +static sf_count_t +ima_read_f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ IMA_ADPCM_PRIVATE *pima ; + short *sptr ; + int k, bufferlen, readcount, count ; + sf_count_t total = 0 ; + float normfact ; + + if (! psf->fdata) + return 0 ; + pima = (IMA_ADPCM_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_float == SF_TRUE) ? 1.0 / ((float) 0x8000) : 1.0 ; + + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : (int) len ; + count = ima_read_block (psf, pima, sptr, readcount) ; + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = normfact * (float) (sptr [k]) ; + total += count ; + len -= readcount ; + if (count != readcount) + break ; + } ; + + return total ; +} /* ima_read_f */ + +static sf_count_t +ima_read_d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ IMA_ADPCM_PRIVATE *pima ; + short *sptr ; + int k, bufferlen, readcount, count ; + sf_count_t total = 0 ; + double normfact ; + + if (! psf->fdata) + return 0 ; + pima = (IMA_ADPCM_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_double == SF_TRUE) ? 1.0 / ((double) 0x8000) : 1.0 ; + + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : (int) len ; + count = ima_read_block (psf, pima, sptr, readcount) ; + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = normfact * (double) (sptr [k]) ; + total += count ; + len -= readcount ; + if (count != readcount) + break ; + } ; + + return total ; +} /* ima_read_d */ + +static sf_count_t +ima_seek (SF_PRIVATE *psf, int mode, sf_count_t offset) +{ IMA_ADPCM_PRIVATE *pima ; + int newblock, newsample ; + + if (! psf->fdata) + return 0 ; + pima = (IMA_ADPCM_PRIVATE*) psf->fdata ; + + if (psf->datalength < 0 || psf->dataoffset < 0) + { psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; + } ; + + if (offset == 0) + { psf_fseek (psf, psf->dataoffset, SEEK_SET) ; + pima->blockcount = 0 ; + pima->decode_block (psf, pima) ; + pima->samplecount = 0 ; + return 0 ; + } ; + + if (offset < 0 || offset > pima->blocks * pima->samplesperblock) + { psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; + } ; + + newblock = offset / pima->samplesperblock ; + newsample = offset % pima->samplesperblock ; + + if (mode == SFM_READ) + { psf_fseek (psf, psf->dataoffset + newblock * pima->blocksize, SEEK_SET) ; + pima->blockcount = newblock ; + pima->decode_block (psf, pima) ; + pima->samplecount = newsample ; + } + else + { /* What to do about write??? */ + psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; + } ; + + return newblock * pima->samplesperblock + newsample ; +} /* ima_seek */ + +/*========================================================================================== +** IMA ADPCM Write Functions. +*/ + +static int +ima_writer_init (SF_PRIVATE *psf, int blockalign) +{ IMA_ADPCM_PRIVATE *pima ; + int samplesperblock ; + unsigned int pimasize ; + + if (psf->mode != SFM_WRITE) + return SFE_BAD_MODE_RW ; + + samplesperblock = 2 * (blockalign - 4 * psf->sf.channels) / psf->sf.channels + 1 ; + + pimasize = sizeof (IMA_ADPCM_PRIVATE) + blockalign + 3 * psf->sf.channels * samplesperblock ; + + if ((pima = calloc (1, pimasize)) == NULL) + return SFE_MALLOC_FAILED ; + + psf->fdata = (void*) pima ; + + pima->channels = psf->sf.channels ; + pima->blocksize = blockalign ; + pima->samplesperblock = samplesperblock ; + + pima->block = (unsigned char*) pima->data ; + pima->samples = (short*) (pima->data + blockalign) ; + + pima->samplecount = 0 ; + + switch (psf->sf.format & SF_FORMAT_TYPEMASK) + { case SF_FORMAT_WAV : + case SF_FORMAT_W64 : + pima->encode_block = wav_w64_ima_encode_block ; + break ; + + case SF_FORMAT_AIFF : + pima->encode_block = aiff_ima_encode_block ; + break ; + + default : + psf_log_printf (psf, "ima_reader_init: bad psf->sf.format\n") ; + return SFE_INTERNAL ; + break ; + } ; + + psf->write_short = ima_write_s ; + psf->write_int = ima_write_i ; + psf->write_float = ima_write_f ; + psf->write_double = ima_write_d ; + + return 0 ; +} /* ima_writer_init */ + +/*========================================================================================== +*/ + +static int +ima_write_block (SF_PRIVATE *psf, IMA_ADPCM_PRIVATE *pima, const short *ptr, int len) +{ int count, total = 0, indx = 0 ; + + while (indx < len) + { count = (pima->samplesperblock - pima->samplecount) * pima->channels ; + + if (count > len - indx) + count = len - indx ; + + memcpy (&(pima->samples [pima->samplecount * pima->channels]), &(ptr [total]), count * sizeof (short)) ; + indx += count ; + pima->samplecount += count / pima->channels ; + total = indx ; + + if (pima->samplecount >= pima->samplesperblock) + pima->encode_block (psf, pima) ; + } ; + + return total ; +} /* ima_write_block */ + +static sf_count_t +ima_write_s (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ IMA_ADPCM_PRIVATE *pima ; + int writecount, count ; + sf_count_t total = 0 ; + + if (! psf->fdata) + return 0 ; + pima = (IMA_ADPCM_PRIVATE*) psf->fdata ; + + while (len) + { writecount = (len > 0x10000000) ? 0x10000000 : (int) len ; + + count = ima_write_block (psf, pima, ptr, writecount) ; + + total += count ; + len -= count ; + if (count != writecount) + break ; + } ; + + return total ; +} /* ima_write_s */ + +static sf_count_t +ima_write_i (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ IMA_ADPCM_PRIVATE *pima ; + short *sptr ; + int k, bufferlen, writecount, count ; + sf_count_t total = 0 ; + + if (! psf->fdata) + return 0 ; + pima = (IMA_ADPCM_PRIVATE*) psf->fdata ; + + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : (int) len ; + for (k = 0 ; k < writecount ; k++) + sptr [k] = ptr [total + k] >> 16 ; + count = ima_write_block (psf, pima, sptr, writecount) ; + total += count ; + len -= writecount ; + if (count != writecount) + break ; + } ; + + return total ; +} /* ima_write_i */ + +static sf_count_t +ima_write_f (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ IMA_ADPCM_PRIVATE *pima ; + short *sptr ; + int k, bufferlen, writecount, count ; + sf_count_t total = 0 ; + float normfact ; + + if (! psf->fdata) + return 0 ; + pima = (IMA_ADPCM_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_float == SF_TRUE) ? (1.0 * 0x7FFF) : 1.0 ; + + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : (int) len ; + for (k = 0 ; k < writecount ; k++) + sptr [k] = lrintf (normfact * ptr [total + k]) ; + count = ima_write_block (psf, pima, sptr, writecount) ; + total += count ; + len -= writecount ; + if (count != writecount) + break ; + } ; + + return total ; +} /* ima_write_f */ + +static sf_count_t +ima_write_d (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ IMA_ADPCM_PRIVATE *pima ; + short *sptr ; + int k, bufferlen, writecount, count ; + sf_count_t total = 0 ; + double normfact ; + + if (! psf->fdata) + return 0 ; + pima = (IMA_ADPCM_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_double == SF_TRUE) ? (1.0 * 0x7FFF) : 1.0 ; + + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : (int) len ; + for (k = 0 ; k < writecount ; k++) + sptr [k] = lrint (normfact * ptr [total + k]) ; + count = ima_write_block (psf, pima, sptr, writecount) ; + total += count ; + len -= writecount ; + if (count != writecount) + break ; + } ; + + return total ; +} /* ima_write_d */ + + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 75a54b82-ad18-4758-9933-64e00a7f24e0 +*/ diff --git a/libs/libsndfile/src/interleave.c b/libs/libsndfile/src/interleave.c new file mode 100644 index 0000000000..7c18bd46c2 --- /dev/null +++ b/libs/libsndfile/src/interleave.c @@ -0,0 +1,306 @@ +/* +** Copyright (C) 2002-2004 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfendian.h" + +#include + +#include "sndfile.h" +#include "common.h" + +#define INTERLEAVE_CHANNELS 6 + +typedef struct +{ double buffer [SF_BUFFER_LEN / sizeof (double)] ; + + sf_count_t channel_len ; + + sf_count_t (*read_short) (SF_PRIVATE*, short *ptr, sf_count_t len) ; + sf_count_t (*read_int) (SF_PRIVATE*, int *ptr, sf_count_t len) ; + sf_count_t (*read_float) (SF_PRIVATE*, float *ptr, sf_count_t len) ; + sf_count_t (*read_double) (SF_PRIVATE*, double *ptr, sf_count_t len) ; + +} INTERLEAVE_DATA ; + + + +static sf_count_t interleave_read_short (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t interleave_read_int (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t interleave_read_float (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t interleave_read_double (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; + +static sf_count_t interleave_seek (SF_PRIVATE*, int mode, sf_count_t samples_from_start) ; + + + + +int +interleave_init (SF_PRIVATE *psf) +{ INTERLEAVE_DATA *pdata ; + + if (psf->mode != SFM_READ) + return SFE_INTERLEAVE_MODE ; + + if (psf->interleave) + { psf_log_printf (psf, "*** Weird, already have interleave.\n") ; + return 666 ; + } ; + + /* Free this in sf_close() function. */ + if (! (pdata = malloc (sizeof (INTERLEAVE_DATA)))) + return SFE_MALLOC_FAILED ; + +puts ("interleave_init") ; + + psf->interleave = pdata ; + + /* Save the existing methods. */ + pdata->read_short = psf->read_short ; + pdata->read_int = psf->read_int ; + pdata->read_float = psf->read_float ; + pdata->read_double = psf->read_double ; + + pdata->channel_len = psf->sf.frames * psf->bytewidth ; + + /* Insert our new methods. */ + psf->read_short = interleave_read_short ; + psf->read_int = interleave_read_int ; + psf->read_float = interleave_read_float ; + psf->read_double = interleave_read_double ; + + psf->seek = interleave_seek ; + + return 0 ; +} /* pcm_interleave_init */ + +/*------------------------------------------------------------------------------ +*/ + +static sf_count_t +interleave_read_short (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ INTERLEAVE_DATA *pdata ; + sf_count_t offset, templen ; + int chan, count, k ; + short *inptr, *outptr ; + + if (! (pdata = psf->interleave)) + return 0 ; + + inptr = (short*) pdata->buffer ; + + for (chan = 0 ; chan < psf->sf.channels ; chan++) + { outptr = ptr + chan ; + + offset = psf->dataoffset + chan * psf->bytewidth * psf->read_current ; + + if (psf_fseek (psf, offset, SEEK_SET) != offset) + { psf->error = SFE_INTERLEAVE_SEEK ; + return 0 ; + } ; + + templen = len / psf->sf.channels ; + + while (templen > 0) + { if (templen > SIGNED_SIZEOF (pdata->buffer) / SIGNED_SIZEOF (short)) + count = SIGNED_SIZEOF (pdata->buffer) / SIGNED_SIZEOF (short) ; + else + count = (int) templen ; + + if (pdata->read_short (psf, inptr, count) != count) + { psf->error = SFE_INTERLEAVE_READ ; + return 0 ; + } ; + + for (k = 0 ; k < count ; k++) + { *outptr = inptr [k] ; + outptr += psf->sf.channels ; + } ; + + templen -= count ; + } ; + } ; + + return len ; +} /* interleave_read_short */ + +static sf_count_t +interleave_read_int (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ INTERLEAVE_DATA *pdata ; + sf_count_t offset, templen ; + int chan, count, k ; + int *inptr, *outptr ; + + if (! (pdata = psf->interleave)) + return 0 ; + + inptr = (int*) pdata->buffer ; + + for (chan = 0 ; chan < psf->sf.channels ; chan++) + { outptr = ptr + chan ; + + offset = psf->dataoffset + chan * psf->bytewidth * psf->read_current ; + + if (psf_fseek (psf, offset, SEEK_SET) != offset) + { psf->error = SFE_INTERLEAVE_SEEK ; + return 0 ; + } ; + + templen = len / psf->sf.channels ; + + while (templen > 0) + { if (templen > SIGNED_SIZEOF (pdata->buffer) / SIGNED_SIZEOF (int)) + count = SIGNED_SIZEOF (pdata->buffer) / SIGNED_SIZEOF (int) ; + else + count = (int) templen ; + + if (pdata->read_int (psf, inptr, count) != count) + { psf->error = SFE_INTERLEAVE_READ ; + return 0 ; + } ; + + for (k = 0 ; k < count ; k++) + { *outptr = inptr [k] ; + outptr += psf->sf.channels ; + } ; + + templen -= count ; + } ; + } ; + + return len ; +} /* interleave_read_int */ + +static sf_count_t +interleave_read_float (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ INTERLEAVE_DATA *pdata ; + sf_count_t offset, templen ; + int chan, count, k ; + float *inptr, *outptr ; + + if (! (pdata = psf->interleave)) + return 0 ; + + inptr = (float*) pdata->buffer ; + + for (chan = 0 ; chan < psf->sf.channels ; chan++) + { outptr = ptr + chan ; + + offset = psf->dataoffset + pdata->channel_len * chan + psf->read_current * psf->bytewidth ; + +/*-printf ("chan : %d read_current : %6lld offset : %6lld\n", chan, psf->read_current, offset) ;-*/ + + if (psf_fseek (psf, offset, SEEK_SET) != offset) + { psf->error = SFE_INTERLEAVE_SEEK ; +/*-puts ("interleave_seek error") ; exit (1) ;-*/ + return 0 ; + } ; + + templen = len / psf->sf.channels ; + + while (templen > 0) + { if (templen > SIGNED_SIZEOF (pdata->buffer) / SIGNED_SIZEOF (float)) + count = SIGNED_SIZEOF (pdata->buffer) / SIGNED_SIZEOF (float) ; + else + count = (int) templen ; + + if (pdata->read_float (psf, inptr, count) != count) + { psf->error = SFE_INTERLEAVE_READ ; +/*-puts ("interleave_read error") ; exit (1) ;-*/ + return 0 ; + } ; + + for (k = 0 ; k < count ; k++) + { *outptr = inptr [k] ; + outptr += psf->sf.channels ; + } ; + + templen -= count ; + } ; + } ; + + return len ; +} /* interleave_read_float */ + +static sf_count_t +interleave_read_double (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ INTERLEAVE_DATA *pdata ; + sf_count_t offset, templen ; + int chan, count, k ; + double *inptr, *outptr ; + + if (! (pdata = psf->interleave)) + return 0 ; + + inptr = (double*) pdata->buffer ; + + for (chan = 0 ; chan < psf->sf.channels ; chan++) + { outptr = ptr + chan ; + + offset = psf->dataoffset + chan * psf->bytewidth * psf->read_current ; + + if (psf_fseek (psf, offset, SEEK_SET) != offset) + { psf->error = SFE_INTERLEAVE_SEEK ; + return 0 ; + } ; + + templen = len / psf->sf.channels ; + + while (templen > 0) + { if (templen > SIGNED_SIZEOF (pdata->buffer) / SIGNED_SIZEOF (double)) + count = SIGNED_SIZEOF (pdata->buffer) / SIGNED_SIZEOF (double) ; + else + count = (int) templen ; + + if (pdata->read_double (psf, inptr, count) != count) + { psf->error = SFE_INTERLEAVE_READ ; + return 0 ; + } ; + + for (k = 0 ; k < count ; k++) + { *outptr = inptr [k] ; + outptr += psf->sf.channels ; + } ; + + templen -= count ; + } ; + } ; + + return len ; +} /* interleave_read_double */ + +/*------------------------------------------------------------------------------ +*/ + +static sf_count_t +interleave_seek (SF_PRIVATE *psf, int mode, sf_count_t samples_from_start) +{ psf = psf ; mode = mode ; + + /* + ** Do nothing here. This is a place holder to prevent the default + ** seek function from being called. + */ + + return samples_from_start ; +} /* interleave_seek */ +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 82314e13-0225-4408-a2f2-e6dab3f38904 +*/ diff --git a/libs/libsndfile/src/ircam.c b/libs/libsndfile/src/ircam.c new file mode 100644 index 0000000000..003809f3fa --- /dev/null +++ b/libs/libsndfile/src/ircam.c @@ -0,0 +1,331 @@ +/* +** Copyright (C) 2001-2004 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" + +/*------------------------------------------------------------------------------ +** Macros to handle big/little endian issues. +*/ + +/* The IRCAM magic number is weird in that one byte in the number can have +** values of 0x1, 0x2, 0x03 or 0x04. Hence the need for a marker and a mask. +*/ + +#define IRCAM_BE_MASK (MAKE_MARKER (0xFF, 0xFF, 0x00, 0xFF)) +#define IRCAM_BE_MARKER (MAKE_MARKER (0x64, 0xA3, 0x00, 0x00)) + +#define IRCAM_LE_MASK (MAKE_MARKER (0xFF, 0x00, 0xFF, 0xFF)) +#define IRCAM_LE_MARKER (MAKE_MARKER (0x00, 0x00, 0xA3, 0x64)) + +#define IRCAM_02B_MARKER (MAKE_MARKER (0x64, 0xA3, 0x02, 0x00)) +#define IRCAM_03L_MARKER (MAKE_MARKER (0x64, 0xA3, 0x03, 0x00)) + +#define IRCAM_DATA_OFFSET (1024) + +/*------------------------------------------------------------------------------ +** Typedefs. +*/ + +enum +{ IRCAM_PCM_16 = 0x00002, + IRCAM_FLOAT = 0x00004, + IRCAM_ALAW = 0x10001, + IRCAM_ULAW = 0x20001, + IRCAM_PCM_32 = 0x40004 +} ; + + +/*------------------------------------------------------------------------------ +** Private static functions. +*/ + +static int ircam_close (SF_PRIVATE *psf) ; +static int ircam_write_header (SF_PRIVATE *psf, int calc_length) ; +static int ircam_read_header (SF_PRIVATE *psf) ; + +static int get_encoding (int subformat) ; + +static const char* get_encoding_str (int encoding) ; + +/*------------------------------------------------------------------------------ +** Public function. +*/ + +int +ircam_open (SF_PRIVATE *psf) +{ int subformat ; + int error = SFE_NO_ERROR ; + + if (psf->mode == SFM_READ || (psf->mode == SFM_RDWR && psf->filelength > 0)) + { if ((error = ircam_read_header (psf))) + return error ; + } ; + + subformat = psf->sf.format & SF_FORMAT_SUBMASK ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { if ((psf->sf.format & SF_FORMAT_TYPEMASK) != SF_FORMAT_IRCAM) + return SFE_BAD_OPEN_FORMAT ; + + psf->endian = psf->sf.format & SF_FORMAT_ENDMASK ; + if (psf->endian == 0 || psf->endian == SF_ENDIAN_CPU) + psf->endian = (CPU_IS_BIG_ENDIAN) ? SF_ENDIAN_BIG : SF_ENDIAN_LITTLE ; + + psf->dataoffset = IRCAM_DATA_OFFSET ; + + if ((error = ircam_write_header (psf, SF_FALSE))) + return error ; + + psf->write_header = ircam_write_header ; + } ; + + psf->container_close = ircam_close ; + + switch (subformat) + { case SF_FORMAT_ULAW : /* 8-bit Ulaw encoding. */ + error = ulaw_init (psf) ; + break ; + + case SF_FORMAT_ALAW : /* 8-bit Alaw encoding. */ + error = alaw_init (psf) ; + break ; + + case SF_FORMAT_PCM_16 : /* 16-bit linear PCM. */ + case SF_FORMAT_PCM_32 : /* 32-bit linear PCM. */ + error = pcm_init (psf) ; + break ; + + case SF_FORMAT_FLOAT : /* 32-bit linear PCM. */ + error = float32_init (psf) ; + break ; + + default : break ; + } ; + + return error ; +} /* ircam_open */ + +/*------------------------------------------------------------------------------ +*/ + +static int +ircam_read_header (SF_PRIVATE *psf) +{ unsigned int marker, encoding ; + float samplerate ; + int error = SFE_NO_ERROR ; + + psf_binheader_readf (psf, "epmf44", 0, &marker, &samplerate, &(psf->sf.channels), &encoding) ; + + if (((marker & IRCAM_BE_MASK) != IRCAM_BE_MARKER) && ((marker & IRCAM_LE_MASK) != IRCAM_LE_MARKER)) + { psf_log_printf (psf, "marker: 0x%X\n", marker) ; + return SFE_IRCAM_NO_MARKER ; + } ; + + psf->endian = SF_ENDIAN_LITTLE ; + + if (psf->sf.channels > 256) + { psf_binheader_readf (psf, "Epmf44", 0, &marker, &samplerate, &(psf->sf.channels), &encoding) ; + + /* Sanity checking for endian-ness detection. */ + if (psf->sf.channels > 256) + { psf_log_printf (psf, "marker: 0x%X\n", marker) ; + return SFE_IRCAM_BAD_CHANNELS ; + } ; + + psf->endian = SF_ENDIAN_BIG ; + } ; + + psf_log_printf (psf, "marker: 0x%X\n", marker) ; + + psf->sf.samplerate = (int) samplerate ; + + psf_log_printf (psf, " Sample Rate : %d\n" + " Channels : %d\n" + " Encoding : %X => %s\n", psf->sf.samplerate, psf->sf.channels, encoding, get_encoding_str (encoding)) ; + + switch (encoding) + { case IRCAM_PCM_16 : + psf->bytewidth = 2 ; + psf->blockwidth = psf->sf.channels * psf->bytewidth ; + + psf->sf.format = SF_FORMAT_IRCAM | SF_FORMAT_PCM_16 ; + break ; + + case IRCAM_PCM_32 : + psf->bytewidth = 4 ; + psf->blockwidth = psf->sf.channels * psf->bytewidth ; + + psf->sf.format = SF_FORMAT_IRCAM | SF_FORMAT_PCM_32 ; + break ; + + case IRCAM_FLOAT : + psf->bytewidth = 4 ; + psf->blockwidth = psf->sf.channels * psf->bytewidth ; + + psf->sf.format = SF_FORMAT_IRCAM | SF_FORMAT_FLOAT ; + break ; + + case IRCAM_ALAW : + psf->bytewidth = 1 ; + psf->blockwidth = psf->sf.channels * psf->bytewidth ; + + psf->sf.format = SF_FORMAT_IRCAM | SF_FORMAT_ALAW ; + break ; + + case IRCAM_ULAW : + psf->bytewidth = 1 ; + psf->blockwidth = psf->sf.channels * psf->bytewidth ; + + psf->sf.format = SF_FORMAT_IRCAM | SF_FORMAT_ULAW ; + break ; + + default : + error = SFE_IRCAM_UNKNOWN_FORMAT ; + break ; + } ; + + if (psf->endian == SF_ENDIAN_BIG) + psf->sf.format |= SF_ENDIAN_BIG ; + else + psf->sf.format |= SF_ENDIAN_LITTLE ; + + if (error) + return error ; + + psf->dataoffset = IRCAM_DATA_OFFSET ; + psf->datalength = psf->filelength - psf->dataoffset ; + + if (psf->sf.frames == 0 && psf->blockwidth) + psf->sf.frames = psf->datalength / psf->blockwidth ; + + psf_log_printf (psf, " Samples : %d\n", psf->sf.frames) ; + + psf_binheader_readf (psf, "p", IRCAM_DATA_OFFSET) ; + + return 0 ; +} /* ircam_read_header */ + +static int +ircam_close (SF_PRIVATE *psf) +{ + psf_log_printf (psf, "close\n") ; + + return 0 ; +} /* ircam_close */ + +static int +ircam_write_header (SF_PRIVATE *psf, int calc_length) +{ int encoding ; + float samplerate ; + sf_count_t current ; + + if (psf->pipeoffset > 0) + return 0 ; + + current = psf_ftell (psf) ; + + calc_length = calc_length ; + + /* This also sets psf->endian. */ + encoding = get_encoding (psf->sf.format & SF_FORMAT_SUBMASK) ; + + if (encoding == 0) + return SFE_BAD_OPEN_FORMAT ; + + /* Reset the current header length to zero. */ + psf->header [0] = 0 ; + psf->headindex = 0 ; + + if (psf->is_pipe == SF_FALSE) + psf_fseek (psf, 0, SEEK_SET) ; + + samplerate = psf->sf.samplerate ; + + switch (psf->endian) + { case SF_ENDIAN_BIG : + psf_binheader_writef (psf, "Emf", IRCAM_02B_MARKER, samplerate) ; + psf_binheader_writef (psf, "E44", psf->sf.channels, encoding) ; + break ; + + case SF_ENDIAN_LITTLE : + psf_binheader_writef (psf, "emf", IRCAM_03L_MARKER, samplerate) ; + psf_binheader_writef (psf, "e44", psf->sf.channels, encoding) ; + break ; + + default : return SFE_BAD_OPEN_FORMAT ; + } ; + + psf_binheader_writef (psf, "z", (size_t) (IRCAM_DATA_OFFSET - psf->headindex)) ; + + /* Header construction complete so write it out. */ + psf_fwrite (psf->header, psf->headindex, 1, psf) ; + + if (psf->error) + return psf->error ; + + if (current > 0) + psf_fseek (psf, current, SEEK_SET) ; + + return psf->error ; +} /* ircam_write_header */ + +static int +get_encoding (int subformat) +{ switch (subformat) + { case SF_FORMAT_PCM_16 : return IRCAM_PCM_16 ; + case SF_FORMAT_PCM_32 : return IRCAM_PCM_32 ; + + case SF_FORMAT_FLOAT : return IRCAM_FLOAT ; + + case SF_FORMAT_ULAW : return IRCAM_ULAW ; + case SF_FORMAT_ALAW : return IRCAM_ALAW ; + + default : break ; + } ; + + return 0 ; +} /* get_encoding */ + +static const char* +get_encoding_str (int encoding) +{ switch (encoding) + { case IRCAM_PCM_16 : return "16 bit PCM" ; + case IRCAM_FLOAT : return "32 bit float" ; + case IRCAM_ALAW : return "A law" ; + case IRCAM_ULAW : return "u law" ; + case IRCAM_PCM_32 : return "32 bit PCM" ; + } ; + return "Unknown encoding" ; +} /* get_encoding_str */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: f2714ab8-f286-4c94-9740-edaf673a1c71 +*/ diff --git a/libs/libsndfile/src/libsndfile.def b/libs/libsndfile/src/libsndfile.def new file mode 100644 index 0000000000..7b144538fc --- /dev/null +++ b/libs/libsndfile/src/libsndfile.def @@ -0,0 +1,39 @@ +; Auto-generated by create_symbols_file.py + +LIBRARY libsndfile-1.dll +EXPORTS + +sf_command @1 +sf_open @2 +sf_close @3 +sf_seek @4 +sf_error @7 +sf_perror @8 +sf_error_str @9 +sf_error_number @10 +sf_format_check @11 +sf_read_raw @16 +sf_readf_short @17 +sf_readf_int @18 +sf_readf_float @19 +sf_readf_double @20 +sf_read_short @21 +sf_read_int @22 +sf_read_float @23 +sf_read_double @24 +sf_write_raw @32 +sf_writef_short @33 +sf_writef_int @34 +sf_writef_float @35 +sf_writef_double @36 +sf_write_short @37 +sf_write_int @38 +sf_write_float @39 +sf_write_double @40 +sf_strerror @50 +sf_get_string @60 +sf_set_string @61 +sf_open_fd @70 +sf_open_virtual @80 +sf_write_sync @90 + diff --git a/libs/libsndfile/src/macbinary3.c b/libs/libsndfile/src/macbinary3.c new file mode 100644 index 0000000000..32a10593a4 --- /dev/null +++ b/libs/libsndfile/src/macbinary3.c @@ -0,0 +1,58 @@ +/* +** Copyright (C) 2003-2005 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" + +#if (OS_IS_MACOSX == 1) + +#include + +int +macbinary3_open (SF_PRIVATE *psf) +{ + if (psf) + return 0 ; + + return 0 ; +} /* macbinary3_open */ + +#else + +int +macbinary3_open (SF_PRIVATE *psf) +{ + psf = psf ; + return 0 ; +} /* macbinary3_open */ + +#endif /* OS_IS_MACOSX */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: c397a7d7-1a31-4349-9684-bd29ef06211e +*/ diff --git a/libs/libsndfile/src/macos.c b/libs/libsndfile/src/macos.c new file mode 100644 index 0000000000..bb5543aa0c --- /dev/null +++ b/libs/libsndfile/src/macos.c @@ -0,0 +1,63 @@ +/* +** Copyright (C) 2003-2005 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" + +#define STR_MARKER MAKE_MARKER ('S', 'T', 'R', ' ') + +int +macos_guess_file_type (SF_PRIVATE *psf, const char *filename) +{ static char rsrc_name [1024] ; + struct stat statbuf ; + int format ; + + psf = psf ; + + snprintf (rsrc_name, sizeof (rsrc_name), "%s/rsrc", filename) ; + + /* If there is no resource fork, just return. */ + if (stat (rsrc_name, &statbuf) != 0) + { psf_log_printf (psf, "No resource fork.\n") ; + return 0 ; + } ; + + if (statbuf.st_size == 0) + { psf_log_printf (psf, "Have zero size resource fork.\n") ; + return 0 ; + } ; + + format = 0 ; + + return format ; +} /* macos_guess_file_type */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 5fbf66d7-9547-442a-9c73-92fd164f3a95 +*/ diff --git a/libs/libsndfile/src/mat4.c b/libs/libsndfile/src/mat4.c new file mode 100644 index 0000000000..fcc6111506 --- /dev/null +++ b/libs/libsndfile/src/mat4.c @@ -0,0 +1,394 @@ +/* +** Copyright (C) 2002-2004 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" +#include "float_cast.h" + +/*------------------------------------------------------------------------------ +** Information on how to decode and encode this file was obtained in a PDF +** file which I found on http://www.wotsit.org/. +** Also did a lot of testing with GNU Octave but do not have access to +** Matlab (tm) and so could not test it there. +*/ + +/*------------------------------------------------------------------------------ +** Macros to handle big/little endian issues. +*/ + +#define MAT4_BE_DOUBLE (MAKE_MARKER (0, 0, 0x03, 0xE8)) +#define MAT4_LE_DOUBLE (MAKE_MARKER (0, 0, 0, 0)) + +#define MAT4_BE_FLOAT (MAKE_MARKER (0, 0, 0x03, 0xF2)) +#define MAT4_LE_FLOAT (MAKE_MARKER (0x0A, 0, 0, 0)) + +#define MAT4_BE_PCM_32 (MAKE_MARKER (0, 0, 0x03, 0xFC)) +#define MAT4_LE_PCM_32 (MAKE_MARKER (0x14, 0, 0, 0)) + +#define MAT4_BE_PCM_16 (MAKE_MARKER (0, 0, 0x04, 0x06)) +#define MAT4_LE_PCM_16 (MAKE_MARKER (0x1E, 0, 0, 0)) + +/* Can't see any reason to ever implement this. */ +#define MAT4_BE_PCM_U8 (MAKE_MARKER (0, 0, 0x04, 0x1A)) +#define MAT4_LE_PCM_U8 (MAKE_MARKER (0x32, 0, 0, 0)) + +/*------------------------------------------------------------------------------ +** Private static functions. +*/ + +static int mat4_close (SF_PRIVATE *psf) ; + +static int mat4_format_to_encoding (int format, int endian) ; + +static int mat4_write_header (SF_PRIVATE *psf, int calc_length) ; +static int mat4_read_header (SF_PRIVATE *psf) ; + +static const char * mat4_marker_to_str (int marker) ; + +/*------------------------------------------------------------------------------ +** Public function. +*/ + +int +mat4_open (SF_PRIVATE *psf) +{ int subformat, error = 0 ; + + if (psf->mode == SFM_READ || (psf->mode == SFM_RDWR && psf->filelength > 0)) + { if ((error = mat4_read_header (psf))) + return error ; + } ; + + if ((psf->sf.format & SF_FORMAT_TYPEMASK) != SF_FORMAT_MAT4) + return SFE_BAD_OPEN_FORMAT ; + + subformat = psf->sf.format & SF_FORMAT_SUBMASK ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { if (psf->is_pipe) + return SFE_NO_PIPE_WRITE ; + + psf->endian = psf->sf.format & SF_FORMAT_ENDMASK ; + if (CPU_IS_LITTLE_ENDIAN && (psf->endian == SF_ENDIAN_CPU || psf->endian == 0)) + psf->endian = SF_ENDIAN_LITTLE ; + else if (CPU_IS_BIG_ENDIAN && (psf->endian == SF_ENDIAN_CPU || psf->endian == 0)) + psf->endian = SF_ENDIAN_BIG ; + + if ((error = mat4_write_header (psf, SF_FALSE))) + return error ; + + psf->write_header = mat4_write_header ; + } ; + + psf->container_close = mat4_close ; + + psf->blockwidth = psf->bytewidth * psf->sf.channels ; + + switch (subformat) + { case SF_FORMAT_PCM_16 : + case SF_FORMAT_PCM_32 : + error = pcm_init (psf) ; + break ; + + case SF_FORMAT_FLOAT : + error = float32_init (psf) ; + break ; + + case SF_FORMAT_DOUBLE : + error = double64_init (psf) ; + break ; + + default : break ; + } ; + + if (error) + return error ; + + return error ; +} /* mat4_open */ + +/*------------------------------------------------------------------------------ +*/ + +static int +mat4_close (SF_PRIVATE *psf) +{ + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + mat4_write_header (psf, SF_TRUE) ; + + return 0 ; +} /* mat4_close */ + +/*------------------------------------------------------------------------------ +*/ + +static int +mat4_write_header (SF_PRIVATE *psf, int calc_length) +{ sf_count_t current ; + int encoding ; + double samplerate ; + + current = psf_ftell (psf) ; + + if (calc_length) + { psf->filelength = psf_get_filelen (psf) ; + + psf->datalength = psf->filelength - psf->dataoffset ; + if (psf->dataend) + psf->datalength -= psf->filelength - psf->dataend ; + + psf->sf.frames = psf->datalength / (psf->bytewidth * psf->sf.channels) ; + } ; + + encoding = mat4_format_to_encoding (psf->sf.format & SF_FORMAT_SUBMASK, psf->endian) ; + + if (encoding == -1) + return SFE_BAD_OPEN_FORMAT ; + + /* Reset the current header length to zero. */ + psf->header [0] = 0 ; + psf->headindex = 0 ; + psf_fseek (psf, 0, SEEK_SET) ; + + /* Need sample rate as a double for writing to the header. */ + samplerate = psf->sf.samplerate ; + + if (psf->endian == SF_ENDIAN_BIG) + { psf_binheader_writef (psf, "Em444", MAT4_BE_DOUBLE, 1, 1, 0) ; + psf_binheader_writef (psf, "E4bd", 11, "samplerate", 11, samplerate) ; + psf_binheader_writef (psf, "tEm484", encoding, psf->sf.channels, psf->sf.frames, 0) ; + psf_binheader_writef (psf, "E4b", 9, "wavedata", 9) ; + } + else if (psf->endian == SF_ENDIAN_LITTLE) + { psf_binheader_writef (psf, "em444", MAT4_LE_DOUBLE, 1, 1, 0) ; + psf_binheader_writef (psf, "e4bd", 11, "samplerate", 11, samplerate) ; + psf_binheader_writef (psf, "tem484", encoding, psf->sf.channels, psf->sf.frames, 0) ; + psf_binheader_writef (psf, "e4b", 9, "wavedata", 9) ; + } + else + return SFE_BAD_OPEN_FORMAT ; + + /* Header construction complete so write it out. */ + psf_fwrite (psf->header, psf->headindex, 1, psf) ; + + if (psf->error) + return psf->error ; + + psf->dataoffset = psf->headindex ; + + if (current > 0) + psf_fseek (psf, current, SEEK_SET) ; + + return psf->error ; +} /* mat4_write_header */ + +static int +mat4_read_header (SF_PRIVATE *psf) +{ int marker, namesize, rows, cols, imag ; + double value ; + const char *marker_str ; + char name [64] ; + + psf_binheader_readf (psf, "pm", 0, &marker) ; + + /* MAT4 file must start with a double for the samplerate. */ + if (marker == MAT4_BE_DOUBLE) + { psf->endian = psf->rwf_endian = SF_ENDIAN_BIG ; + marker_str = "big endian double" ; + } + else if (marker == MAT4_LE_DOUBLE) + { psf->endian = psf->rwf_endian = SF_ENDIAN_LITTLE ; + marker_str = "little endian double" ; + } + else + return SFE_UNIMPLEMENTED ; + + psf_log_printf (psf, "GNU Octave 2.0 / MATLAB v4.2 format\nMarker : %s\n", marker_str) ; + + psf_binheader_readf (psf, "444", &rows, &cols, &imag) ; + + psf_log_printf (psf, " Rows : %d\n Cols : %d\n Imag : %s\n", rows, cols, imag ? "True" : "False") ; + + psf_binheader_readf (psf, "4", &namesize) ; + + if (namesize >= SIGNED_SIZEOF (name)) + return SFE_MAT4_BAD_NAME ; + + psf_binheader_readf (psf, "b", name, namesize) ; + name [namesize] = 0 ; + + psf_log_printf (psf, " Name : %s\n", name) ; + + psf_binheader_readf (psf, "d", &value) ; + + LSF_SNPRINTF (psf->u.cbuf, sizeof (psf->u.cbuf), " Value : %f\n", value) ; + psf_log_printf (psf, psf->u.cbuf) ; + + if ((rows != 1) || (cols != 1)) + return SFE_MAT4_NO_SAMPLERATE ; + + psf->sf.samplerate = lrint (value) ; + + /* Now write out the audio data. */ + + psf_binheader_readf (psf, "m", &marker) ; + + psf_log_printf (psf, "Marker : %s\n", mat4_marker_to_str (marker)) ; + + psf_binheader_readf (psf, "444", &rows, &cols, &imag) ; + + psf_log_printf (psf, " Rows : %d\n Cols : %d\n Imag : %s\n", rows, cols, imag ? "True" : "False") ; + + psf_binheader_readf (psf, "4", &namesize) ; + + if (namesize >= SIGNED_SIZEOF (name)) + return SFE_MAT4_BAD_NAME ; + + psf_binheader_readf (psf, "b", name, namesize) ; + name [namesize] = 0 ; + + psf_log_printf (psf, " Name : %s\n", name) ; + + psf->dataoffset = psf_ftell (psf) ; + + if (rows == 0 && cols == 0) + { psf_log_printf (psf, "*** Error : zero channel count.\n") ; + return SFE_MAT4_ZERO_CHANNELS ; + } ; + + psf->sf.channels = rows ; + psf->sf.frames = cols ; + + psf->sf.format = psf->endian | SF_FORMAT_MAT4 ; + switch (marker) + { case MAT4_BE_DOUBLE : + case MAT4_LE_DOUBLE : + psf->sf.format |= SF_FORMAT_DOUBLE ; + psf->bytewidth = 8 ; + break ; + + case MAT4_BE_FLOAT : + case MAT4_LE_FLOAT : + psf->sf.format |= SF_FORMAT_FLOAT ; + psf->bytewidth = 4 ; + break ; + + case MAT4_BE_PCM_32 : + case MAT4_LE_PCM_32 : + psf->sf.format |= SF_FORMAT_PCM_32 ; + psf->bytewidth = 4 ; + break ; + + case MAT4_BE_PCM_16 : + case MAT4_LE_PCM_16 : + psf->sf.format |= SF_FORMAT_PCM_16 ; + psf->bytewidth = 2 ; + break ; + + default : + psf_log_printf (psf, "*** Error : Bad marker %08X\n", marker) ; + return SFE_UNIMPLEMENTED ; + } ; + + if ((psf->filelength - psf->dataoffset) < psf->sf.channels * psf->sf.frames * psf->bytewidth) + { psf_log_printf (psf, "*** File seems to be truncated. %D <--> %D\n", + psf->filelength - psf->dataoffset, psf->sf.channels * psf->sf.frames * psf->bytewidth) ; + } + else if ((psf->filelength - psf->dataoffset) > psf->sf.channels * psf->sf.frames * psf->bytewidth) + psf->dataend = psf->dataoffset + rows * cols * psf->bytewidth ; + + psf->datalength = psf->filelength - psf->dataoffset - psf->dataend ; + + psf->sf.sections = 1 ; + + return 0 ; +} /* mat4_read_header */ + +static int +mat4_format_to_encoding (int format, int endian) +{ + switch (format | endian) + { case (SF_FORMAT_PCM_16 | SF_ENDIAN_BIG) : + return MAT4_BE_PCM_16 ; + + case (SF_FORMAT_PCM_16 | SF_ENDIAN_LITTLE) : + return MAT4_LE_PCM_16 ; + + case (SF_FORMAT_PCM_32 | SF_ENDIAN_BIG) : + return MAT4_BE_PCM_32 ; + + case (SF_FORMAT_PCM_32 | SF_ENDIAN_LITTLE) : + return MAT4_LE_PCM_32 ; + + case (SF_FORMAT_FLOAT | SF_ENDIAN_BIG) : + return MAT4_BE_FLOAT ; + + case (SF_FORMAT_FLOAT | SF_ENDIAN_LITTLE) : + return MAT4_LE_FLOAT ; + + case (SF_FORMAT_DOUBLE | SF_ENDIAN_BIG) : + return MAT4_BE_DOUBLE ; + + case (SF_FORMAT_DOUBLE | SF_ENDIAN_LITTLE) : + return MAT4_LE_DOUBLE ; + + default : break ; + } ; + + return -1 ; +} /* mat4_format_to_encoding */ + +static const char * +mat4_marker_to_str (int marker) +{ static char str [32] ; + + switch (marker) + { + case MAT4_BE_PCM_16 : return "big endian 16 bit PCM" ; + case MAT4_LE_PCM_16 : return "little endian 16 bit PCM" ; + + case MAT4_BE_PCM_32 : return "big endian 32 bit PCM" ; + case MAT4_LE_PCM_32 : return "little endian 32 bit PCM" ; + + + case MAT4_BE_FLOAT : return "big endian float" ; + case MAT4_LE_FLOAT : return "big endian float" ; + + case MAT4_BE_DOUBLE : return "big endian double" ; + case MAT4_LE_DOUBLE : return "little endian double" ; + } ; + + /* This is a little unsafe but is really only for debugging. */ + str [sizeof (str) - 1] = 0 ; + LSF_SNPRINTF (str, sizeof (str) - 1, "%08X", marker) ; + return str ; +} /* mat4_marker_to_str */ +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: f7e5f5d6-fc39-452e-bc4a-59627116ff59 +*/ diff --git a/libs/libsndfile/src/mat5.c b/libs/libsndfile/src/mat5.c new file mode 100644 index 0000000000..dfef7b517a --- /dev/null +++ b/libs/libsndfile/src/mat5.c @@ -0,0 +1,507 @@ +/* +** Copyright (C) 2002-2004 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" +#include "float_cast.h" + +/*------------------------------------------------------------------------------ +** Information on how to decode and encode this file was obtained in a PDF +** file which I found on http://www.wotsit.org/. +** Also did a lot of testing with GNU Octave but do not have access to +** Matlab (tm) and so could not test it there. +*/ + +/*------------------------------------------------------------------------------ +** Macros to handle big/little endian issues. +*/ + +#define MATL_MARKER (MAKE_MARKER ('M', 'A', 'T', 'L')) + +#define IM_MARKER (('I' << 8) + 'M') +#define MI_MARKER (('M' << 8) + 'I') + +/*------------------------------------------------------------------------------ +** Enums and typedefs. +*/ + +enum +{ MAT5_TYPE_SCHAR = 0x1, + MAT5_TYPE_UCHAR = 0x2, + MAT5_TYPE_INT16 = 0x3, + MAT5_TYPE_UINT16 = 0x4, + MAT5_TYPE_INT32 = 0x5, + MAT5_TYPE_UINT32 = 0x6, + MAT5_TYPE_FLOAT = 0x7, + MAT5_TYPE_DOUBLE = 0x9, + MAT5_TYPE_ARRAY = 0xE, + + MAT5_TYPE_COMP_USHORT = 0x00020004, + MAT5_TYPE_COMP_UINT = 0x00040006 +} ; + +typedef struct +{ sf_count_t size ; + int rows, cols ; + char name [32] ; +} MAT5_MATRIX ; + +/*------------------------------------------------------------------------------ +** Private static functions. +*/ + +static int mat5_close (SF_PRIVATE *psf) ; + +static int mat5_write_header (SF_PRIVATE *psf, int calc_length) ; +static int mat5_read_header (SF_PRIVATE *psf) ; + +/*------------------------------------------------------------------------------ +** Public function. +*/ + +int +mat5_open (SF_PRIVATE *psf) +{ int subformat, error = 0 ; + + if (psf->mode == SFM_READ || (psf->mode == SFM_RDWR && psf->filelength > 0)) + { if ((error = mat5_read_header (psf))) + return error ; + } ; + + if ((psf->sf.format & SF_FORMAT_TYPEMASK) != SF_FORMAT_MAT5) + return SFE_BAD_OPEN_FORMAT ; + + subformat = psf->sf.format & SF_FORMAT_SUBMASK ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { if (psf->is_pipe) + return SFE_NO_PIPE_WRITE ; + + psf->endian = psf->sf.format & SF_FORMAT_ENDMASK ; + if (CPU_IS_LITTLE_ENDIAN && (psf->endian == SF_ENDIAN_CPU || psf->endian == 0)) + psf->endian = SF_ENDIAN_LITTLE ; + else if (CPU_IS_BIG_ENDIAN && (psf->endian == SF_ENDIAN_CPU || psf->endian == 0)) + psf->endian = SF_ENDIAN_BIG ; + + if ((error = mat5_write_header (psf, SF_FALSE))) + return error ; + + psf->write_header = mat5_write_header ; + } ; + + psf->container_close = mat5_close ; + + psf->blockwidth = psf->bytewidth * psf->sf.channels ; + + switch (subformat) + { case SF_FORMAT_PCM_U8 : + case SF_FORMAT_PCM_16 : + case SF_FORMAT_PCM_32 : + error = pcm_init (psf) ; + break ; + + case SF_FORMAT_FLOAT : + error = float32_init (psf) ; + break ; + + case SF_FORMAT_DOUBLE : + error = double64_init (psf) ; + break ; + + default : break ; + } ; + + return error ; +} /* mat5_open */ + +/*------------------------------------------------------------------------------ +*/ + +static int +mat5_close (SF_PRIVATE *psf) +{ + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + mat5_write_header (psf, SF_TRUE) ; + + return 0 ; +} /* mat5_close */ + +/*------------------------------------------------------------------------------ +*/ + +static int +mat5_write_header (SF_PRIVATE *psf, int calc_length) +{ static const char *filename = "MATLAB 5.0 MAT-file, written by " PACKAGE "-" VERSION ", " ; + static const char *sr_name = "samplerate\0\0\0\0\0\0\0\0\0\0\0" ; + static const char *wd_name = "wavedata\0" ; + sf_count_t current, datasize ; + int encoding ; + + current = psf_ftell (psf) ; + + if (calc_length) + { psf_fseek (psf, 0, SEEK_END) ; + psf->filelength = psf_ftell (psf) ; + psf_fseek (psf, 0, SEEK_SET) ; + + psf->datalength = psf->filelength - psf->dataoffset ; + if (psf->dataend) + psf->datalength -= psf->filelength - psf->dataend ; + + psf->sf.frames = psf->datalength / (psf->bytewidth * psf->sf.channels) ; + } ; + + switch (psf->sf.format & SF_FORMAT_SUBMASK) + { case SF_FORMAT_PCM_U8 : + encoding = MAT5_TYPE_UCHAR ; + break ; + + case SF_FORMAT_PCM_16 : + encoding = MAT5_TYPE_INT16 ; + break ; + + case SF_FORMAT_PCM_32 : + encoding = MAT5_TYPE_INT32 ; + break ; + + case SF_FORMAT_FLOAT : + encoding = MAT5_TYPE_FLOAT ; + break ; + + case SF_FORMAT_DOUBLE : + encoding = MAT5_TYPE_DOUBLE ; + break ; + + default : + return SFE_BAD_OPEN_FORMAT ; + } ; + + /* Reset the current header length to zero. */ + psf->header [0] = 0 ; + psf->headindex = 0 ; + psf_fseek (psf, 0, SEEK_SET) ; + + psf_get_date_str (psf->u.cbuf, sizeof (psf->u.scbuf)) ; + psf_binheader_writef (psf, "bb", filename, strlen (filename), psf->u.cbuf, strlen (psf->u.cbuf) + 1) ; + + memset (psf->u.scbuf, ' ', 124 - psf->headindex) ; + psf_binheader_writef (psf, "b", psf->u.scbuf, 124 - psf->headindex) ; + + psf->rwf_endian = psf->endian ; + + if (psf->rwf_endian == SF_ENDIAN_BIG) + psf_binheader_writef (psf, "2b", 0x0100, "MI", 2) ; + else + psf_binheader_writef (psf, "2b", 0x0100, "IM", 2) ; + + psf_binheader_writef (psf, "444444", MAT5_TYPE_ARRAY, 64, MAT5_TYPE_UINT32, 8, 6, 0) ; + psf_binheader_writef (psf, "4444", MAT5_TYPE_INT32, 8, 1, 1) ; + psf_binheader_writef (psf, "44b", MAT5_TYPE_SCHAR, strlen (sr_name), sr_name, 16) ; + + if (psf->sf.samplerate > 0xFFFF) + psf_binheader_writef (psf, "44", MAT5_TYPE_COMP_UINT, psf->sf.samplerate) ; + else + { unsigned short samplerate = psf->sf.samplerate ; + + psf_binheader_writef (psf, "422", MAT5_TYPE_COMP_USHORT, samplerate, 0) ; + } ; + + datasize = psf->sf.frames * psf->sf.channels * psf->bytewidth ; + + psf_binheader_writef (psf, "t484444", MAT5_TYPE_ARRAY, datasize + 64, MAT5_TYPE_UINT32, 8, 6, 0) ; + psf_binheader_writef (psf, "t4448", MAT5_TYPE_INT32, 8, psf->sf.channels, psf->sf.frames) ; + psf_binheader_writef (psf, "44b", MAT5_TYPE_SCHAR, strlen (wd_name), wd_name, strlen (wd_name)) ; + + datasize = psf->sf.frames * psf->sf.channels * psf->bytewidth ; + if (datasize > 0x7FFFFFFF) + datasize = 0x7FFFFFFF ; + + psf_binheader_writef (psf, "t48", encoding, datasize) ; + + /* Header construction complete so write it out. */ + psf_fwrite (psf->header, psf->headindex, 1, psf) ; + + if (psf->error) + return psf->error ; + + psf->dataoffset = psf->headindex ; + + if (current > 0) + psf_fseek (psf, current, SEEK_SET) ; + + return psf->error ; +} /* mat5_write_header */ + +static int +mat5_read_header (SF_PRIVATE *psf) +{ char name [32] ; + short version, endian ; + int type, size, flags1, flags2, rows, cols ; + + psf_binheader_readf (psf, "pb", 0, psf->u.cbuf, 124) ; + + psf->u.scbuf [125] = 0 ; + + if (strlen (psf->u.cbuf) >= 124) + return SFE_UNIMPLEMENTED ; + + if (strstr (psf->u.cbuf, "MATLAB 5.0 MAT-file") == psf->u.cbuf) + psf_log_printf (psf, "%s\n", psf->u.scbuf) ; + + + psf_binheader_readf (psf, "E22", &version, &endian) ; + + if (endian == MI_MARKER) + { psf->endian = psf->rwf_endian = SF_ENDIAN_BIG ; + if (CPU_IS_LITTLE_ENDIAN) version = ENDSWAP_SHORT (version) ; + } + else if (endian == IM_MARKER) + { psf->endian = psf->rwf_endian = SF_ENDIAN_LITTLE ; + if (CPU_IS_BIG_ENDIAN) version = ENDSWAP_SHORT (version) ; + } + else + return SFE_MAT5_BAD_ENDIAN ; + + if ((CPU_IS_LITTLE_ENDIAN && endian == IM_MARKER) || + (CPU_IS_BIG_ENDIAN && endian == MI_MARKER)) + version = ENDSWAP_SHORT (version) ; + + psf_log_printf (psf, "Version : 0x%04X\n", version) ; + psf_log_printf (psf, "Endian : 0x%04X => %s\n", endian, + (psf->endian == SF_ENDIAN_LITTLE) ? "Little" : "Big") ; + + /*========================================================*/ + psf_binheader_readf (psf, "44", &type, &size) ; + psf_log_printf (psf, "Block\n Type : %X Size : %d\n", type, size) ; + + if (type != MAT5_TYPE_ARRAY) + return SFE_MAT5_NO_BLOCK ; + + psf_binheader_readf (psf, "44", &type, &size) ; + psf_log_printf (psf, " Type : %X Size : %d\n", type, size) ; + + if (type != MAT5_TYPE_UINT32) + return SFE_MAT5_NO_BLOCK ; + + psf_binheader_readf (psf, "44", &flags1, &flags2) ; + psf_log_printf (psf, " Flg1 : %X Flg2 : %d\n", flags1, flags2) ; + + psf_binheader_readf (psf, "44", &type, &size) ; + psf_log_printf (psf, " Type : %X Size : %d\n", type, size) ; + + if (type != MAT5_TYPE_INT32) + return SFE_MAT5_NO_BLOCK ; + + psf_binheader_readf (psf, "44", &rows, &cols) ; + psf_log_printf (psf, " Rows : %X Cols : %d\n", rows, cols) ; + + if (rows != 1 || cols != 1) + return SFE_MAT5_SAMPLE_RATE ; + + psf_binheader_readf (psf, "4", &type) ; + + if (type == MAT5_TYPE_SCHAR) + { psf_binheader_readf (psf, "4", &size) ; + psf_log_printf (psf, " Type : %X Size : %d\n", type, size) ; + if (size > SIGNED_SIZEOF (name) - 1) + { psf_log_printf (psf, "Error : Bad name length.\n") ; + return SFE_MAT5_NO_BLOCK ; + } ; + + psf_binheader_readf (psf, "bj", name, size, (8 - (size % 8)) % 8) ; + name [size] = 0 ; + } + else if ((type & 0xFFFF) == MAT5_TYPE_SCHAR) + { size = type >> 16 ; + if (size > 4) + { psf_log_printf (psf, "Error : Bad name length.\n") ; + return SFE_MAT5_NO_BLOCK ; + } ; + + psf_log_printf (psf, " Type : %X\n", type) ; + psf_binheader_readf (psf, "4", &name) ; + name [size] = 0 ; + } + else + return SFE_MAT5_NO_BLOCK ; + + psf_log_printf (psf, " Name : %s\n", name) ; + + /*-----------------------------------------*/ + + psf_binheader_readf (psf, "44", &type, &size) ; + + switch (type) + { case MAT5_TYPE_DOUBLE : + { double samplerate ; + + psf_binheader_readf (psf, "d", &samplerate) ; + LSF_SNPRINTF (name, sizeof (name), "%f\n", samplerate) ; + psf_log_printf (psf, " Val : %s\n", name) ; + + psf->sf.samplerate = lrint (samplerate) ; + } ; + break ; + + case MAT5_TYPE_COMP_USHORT : + { unsigned short samplerate ; + + psf_binheader_readf (psf, "j2j", -4, &samplerate, 2) ; + psf_log_printf (psf, " Val : %u\n", samplerate) ; + psf->sf.samplerate = samplerate ; + } + break ; + + case MAT5_TYPE_COMP_UINT : + psf_log_printf (psf, " Val : %u\n", size) ; + psf->sf.samplerate = size ; + break ; + + default : + psf_log_printf (psf, " Type : %X Size : %d ***\n", type, size) ; + return SFE_MAT5_SAMPLE_RATE ; + } ; + + /*-----------------------------------------*/ + + + psf_binheader_readf (psf, "44", &type, &size) ; + psf_log_printf (psf, " Type : %X Size : %d\n", type, size) ; + + if (type != MAT5_TYPE_ARRAY) + return SFE_MAT5_NO_BLOCK ; + + psf_binheader_readf (psf, "44", &type, &size) ; + psf_log_printf (psf, " Type : %X Size : %d\n", type, size) ; + + if (type != MAT5_TYPE_UINT32) + return SFE_MAT5_NO_BLOCK ; + + psf_binheader_readf (psf, "44", &flags1, &flags2) ; + psf_log_printf (psf, " Flg1 : %X Flg2 : %d\n", flags1, flags2) ; + + psf_binheader_readf (psf, "44", &type, &size) ; + psf_log_printf (psf, " Type : %X Size : %d\n", type, size) ; + + if (type != MAT5_TYPE_INT32) + return SFE_MAT5_NO_BLOCK ; + + psf_binheader_readf (psf, "44", &rows, &cols) ; + psf_log_printf (psf, " Rows : %X Cols : %d\n", rows, cols) ; + + psf_binheader_readf (psf, "4", &type) ; + + if (type == MAT5_TYPE_SCHAR) + { psf_binheader_readf (psf, "4", &size) ; + psf_log_printf (psf, " Type : %X Size : %d\n", type, size) ; + if (size > SIGNED_SIZEOF (name) - 1) + { psf_log_printf (psf, "Error : Bad name length.\n") ; + return SFE_MAT5_NO_BLOCK ; + } ; + + psf_binheader_readf (psf, "bj", name, size, (8 - (size % 8)) % 8) ; + name [size] = 0 ; + } + else if ((type & 0xFFFF) == MAT5_TYPE_SCHAR) + { size = type >> 16 ; + if (size > 4) + { psf_log_printf (psf, "Error : Bad name length.\n") ; + return SFE_MAT5_NO_BLOCK ; + } ; + + psf_log_printf (psf, " Type : %X\n", type) ; + psf_binheader_readf (psf, "4", &name) ; + name [size] = 0 ; + } + else + return SFE_MAT5_NO_BLOCK ; + + psf_log_printf (psf, " Name : %s\n", name) ; + + psf_binheader_readf (psf, "44", &type, &size) ; + psf_log_printf (psf, " Type : %X Size : %d\n", type, size) ; + + /*++++++++++++++++++++++++++++++++++++++++++++++++++*/ + + if (rows == 0 && cols == 0) + { psf_log_printf (psf, "*** Error : zero channel count.\n") ; + return SFE_MAT5_ZERO_CHANNELS ; + } ; + + psf->sf.channels = rows ; + psf->sf.frames = cols ; + + psf->sf.format = psf->endian | SF_FORMAT_MAT5 ; + + switch (type) + { case MAT5_TYPE_DOUBLE : + psf_log_printf (psf, "Data type : double\n") ; + psf->sf.format |= SF_FORMAT_DOUBLE ; + psf->bytewidth = 8 ; + break ; + + case MAT5_TYPE_FLOAT : + psf_log_printf (psf, "Data type : float\n") ; + psf->sf.format |= SF_FORMAT_FLOAT ; + psf->bytewidth = 4 ; + break ; + + case MAT5_TYPE_INT32 : + psf_log_printf (psf, "Data type : 32 bit PCM\n") ; + psf->sf.format |= SF_FORMAT_PCM_32 ; + psf->bytewidth = 4 ; + break ; + + case MAT5_TYPE_INT16 : + psf_log_printf (psf, "Data type : 16 bit PCM\n") ; + psf->sf.format |= SF_FORMAT_PCM_16 ; + psf->bytewidth = 2 ; + break ; + + case MAT5_TYPE_UCHAR : + psf_log_printf (psf, "Data type : unsigned 8 bit PCM\n") ; + psf->sf.format |= SF_FORMAT_PCM_U8 ; + psf->bytewidth = 1 ; + break ; + + default : + psf_log_printf (psf, "*** Error : Bad marker %08X\n", type) ; + return SFE_UNIMPLEMENTED ; + } ; + + psf->dataoffset = psf_ftell (psf) ; + psf->datalength = psf->filelength - psf->dataoffset ; + + return 0 ; +} /* mat5_read_header */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: dfdb6742-b2be-4be8-b390-d0c674e8bc8e +*/ diff --git a/libs/libsndfile/src/ms_adpcm.c b/libs/libsndfile/src/ms_adpcm.c new file mode 100644 index 0000000000..bb774fa1b2 --- /dev/null +++ b/libs/libsndfile/src/ms_adpcm.c @@ -0,0 +1,834 @@ +/* +** Copyright (C) 1999-2005 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "float_cast.h" +#include "common.h" +#include "wav_w64.h" + +/* These required here because we write the header in this file. */ + +#define RIFF_MARKER (MAKE_MARKER ('R', 'I', 'F', 'F')) +#define WAVE_MARKER (MAKE_MARKER ('W', 'A', 'V', 'E')) +#define fmt_MARKER (MAKE_MARKER ('f', 'm', 't', ' ')) +#define fact_MARKER (MAKE_MARKER ('f', 'a', 'c', 't')) +#define data_MARKER (MAKE_MARKER ('d', 'a', 't', 'a')) + +#define WAVE_FORMAT_MS_ADPCM 0x0002 + +typedef struct +{ int channels, blocksize, samplesperblock, blocks, dataremaining ; + int blockcount ; + sf_count_t samplecount ; + short *samples ; + unsigned char *block ; +#if HAVE_FLEXIBLE_ARRAY + short dummydata [] ; /* ISO C99 struct flexible array. */ +#else + short dummydata [0] ; /* This is a hack an might not work. */ +#endif +} MSADPCM_PRIVATE ; + +/*============================================================================================ +** MS ADPCM static data and functions. +*/ + +static int AdaptationTable [] = +{ 230, 230, 230, 230, 307, 409, 512, 614, + 768, 614, 512, 409, 307, 230, 230, 230 +} ; + +/* TODO : The first 7 coef's are are always hardcode and must + appear in the actual WAVE file. They should be read in + in case a sound program added extras to the list. */ + +static int AdaptCoeff1 [MSADPCM_ADAPT_COEFF_COUNT] = +{ 256, 512, 0, 192, 240, 460, 392 +} ; + +static int AdaptCoeff2 [MSADPCM_ADAPT_COEFF_COUNT] = +{ 0, -256, 0, 64, 0, -208, -232 +} ; + +/*============================================================================================ +** MS ADPCM Block Layout. +** ====================== +** Block is usually 256, 512 or 1024 bytes depending on sample rate. +** For a mono file, the block is laid out as follows: +** byte purpose +** 0 block predictor [0..6] +** 1,2 initial idelta (positive) +** 3,4 sample 1 +** 5,6 sample 0 +** 7..n packed bytecodes +** +** For a stereo file, the block is laid out as follows: +** byte purpose +** 0 block predictor [0..6] for left channel +** 1 block predictor [0..6] for right channel +** 2,3 initial idelta (positive) for left channel +** 4,5 initial idelta (positive) for right channel +** 6,7 sample 1 for left channel +** 8,9 sample 1 for right channel +** 10,11 sample 0 for left channel +** 12,13 sample 0 for right channel +** 14..n packed bytecodes +*/ + +/*============================================================================================ +** Static functions. +*/ + +static int msadpcm_decode_block (SF_PRIVATE *psf, MSADPCM_PRIVATE *pms) ; +static sf_count_t msadpcm_read_block (SF_PRIVATE *psf, MSADPCM_PRIVATE *pms, short *ptr, int len) ; + +static int msadpcm_encode_block (SF_PRIVATE *psf, MSADPCM_PRIVATE *pms) ; +static sf_count_t msadpcm_write_block (SF_PRIVATE *psf, MSADPCM_PRIVATE *pms, const short *ptr, int len) ; + +static sf_count_t msadpcm_read_s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t msadpcm_read_i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t msadpcm_read_f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t msadpcm_read_d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; + +static sf_count_t msadpcm_write_s (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t msadpcm_write_i (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t msadpcm_write_f (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t msadpcm_write_d (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; + +static sf_count_t msadpcm_seek (SF_PRIVATE *psf, int mode, sf_count_t offset) ; +static int msadpcm_close (SF_PRIVATE *psf) ; + +static void choose_predictor (unsigned int channels, short *data, int *bpred, int *idelta) ; + +/*============================================================================================ +** MS ADPCM Read Functions. +*/ + +int +wav_w64_msadpcm_init (SF_PRIVATE *psf, int blockalign, int samplesperblock) +{ MSADPCM_PRIVATE *pms ; + unsigned int pmssize ; + int count ; + + if (psf->fdata != NULL) + { psf_log_printf (psf, "*** psf->fdata is not NULL.\n") ; + return SFE_INTERNAL ; + } ; + + if (psf->mode == SFM_WRITE) + samplesperblock = 2 + 2 * (blockalign - 7 * psf->sf.channels) / psf->sf.channels ; + + pmssize = sizeof (MSADPCM_PRIVATE) + blockalign + 3 * psf->sf.channels * samplesperblock ; + + if (! (psf->fdata = malloc (pmssize))) + return SFE_MALLOC_FAILED ; + pms = (MSADPCM_PRIVATE*) psf->fdata ; + memset (pms, 0, pmssize) ; + + pms->samples = pms->dummydata ; + pms->block = (unsigned char*) (pms->dummydata + psf->sf.channels * samplesperblock) ; + + pms->channels = psf->sf.channels ; + pms->blocksize = blockalign ; + pms->samplesperblock = samplesperblock ; + + if (psf->mode == SFM_READ) + { pms->dataremaining = psf->datalength ; + + if (psf->datalength % pms->blocksize) + pms->blocks = psf->datalength / pms->blocksize + 1 ; + else + pms->blocks = psf->datalength / pms->blocksize ; + + count = 2 * (pms->blocksize - 6 * pms->channels) / pms->channels ; + if (pms->samplesperblock != count) + psf_log_printf (psf, "*** Warning : samplesperblock shoud be %d.\n", count) ; + + psf->sf.frames = (psf->datalength / pms->blocksize) * pms->samplesperblock ; + + psf_log_printf (psf, " bpred idelta\n") ; + + msadpcm_decode_block (psf, pms) ; + + psf->read_short = msadpcm_read_s ; + psf->read_int = msadpcm_read_i ; + psf->read_float = msadpcm_read_f ; + psf->read_double = msadpcm_read_d ; + } ; + + if (psf->mode == SFM_WRITE) + { pms->samples = pms->dummydata ; + + pms->samplecount = 0 ; + + psf->write_short = msadpcm_write_s ; + psf->write_int = msadpcm_write_i ; + psf->write_float = msadpcm_write_f ; + psf->write_double = msadpcm_write_d ; + } ; + + psf->codec_close = msadpcm_close ; + psf->seek = msadpcm_seek ; + + return 0 ; +} /* wav_w64_msadpcm_init */ + +static int +msadpcm_decode_block (SF_PRIVATE *psf, MSADPCM_PRIVATE *pms) +{ int chan, k, blockindx, sampleindx ; + short bytecode, bpred [2], chan_idelta [2] ; + + int predict ; + int current ; + int idelta ; + + pms->blockcount ++ ; + pms->samplecount = 0 ; + + if (pms->blockcount > pms->blocks) + { memset (pms->samples, 0, pms->samplesperblock * pms->channels) ; + return 1 ; + } ; + + if ((k = psf_fread (pms->block, 1, pms->blocksize, psf)) != pms->blocksize) + psf_log_printf (psf, "*** Warning : short read (%d != %d).\n", k, pms->blocksize) ; + + /* Read and check the block header. */ + + if (pms->channels == 1) + { bpred [0] = pms->block [0] ; + + if (bpred [0] >= 7) + psf_log_printf (psf, "MS ADPCM synchronisation error (%d).\n", bpred [0]) ; + + chan_idelta [0] = pms->block [1] | (pms->block [2] << 8) ; + chan_idelta [1] = 0 ; + + psf_log_printf (psf, "(%d) (%d)\n", bpred [0], chan_idelta [0]) ; + + pms->samples [1] = pms->block [3] | (pms->block [4] << 8) ; + pms->samples [0] = pms->block [5] | (pms->block [6] << 8) ; + blockindx = 7 ; + } + else + { bpred [0] = pms->block [0] ; + bpred [1] = pms->block [1] ; + + if (bpred [0] >= 7 || bpred [1] >= 7) + psf_log_printf (psf, "MS ADPCM synchronisation error (%d %d).\n", bpred [0], bpred [1]) ; + + chan_idelta [0] = pms->block [2] | (pms->block [3] << 8) ; + chan_idelta [1] = pms->block [4] | (pms->block [5] << 8) ; + + psf_log_printf (psf, "(%d, %d) (%d, %d)\n", bpred [0], bpred [1], chan_idelta [0], chan_idelta [1]) ; + + pms->samples [2] = pms->block [6] | (pms->block [7] << 8) ; + pms->samples [3] = pms->block [8] | (pms->block [9] << 8) ; + + pms->samples [0] = pms->block [10] | (pms->block [11] << 8) ; + pms->samples [1] = pms->block [12] | (pms->block [13] << 8) ; + + blockindx = 14 ; + } ; + + /*-------------------------------------------------------- + This was left over from a time when calculations were done + as ints rather than shorts. Keep this around as a reminder + in case I ever find a file which decodes incorrectly. + + if (chan_idelta [0] & 0x8000) + chan_idelta [0] -= 0x10000 ; + if (chan_idelta [1] & 0x8000) + chan_idelta [1] -= 0x10000 ; + --------------------------------------------------------*/ + + /* Pull apart the packed 4 bit samples and store them in their + ** correct sample positions. + */ + + sampleindx = 2 * pms->channels ; + while (blockindx < pms->blocksize) + { bytecode = pms->block [blockindx++] ; + pms->samples [sampleindx++] = (bytecode >> 4) & 0x0F ; + pms->samples [sampleindx++] = bytecode & 0x0F ; + } ; + + /* Decode the encoded 4 bit samples. */ + + for (k = 2 * pms->channels ; k < (pms->samplesperblock * pms->channels) ; k ++) + { chan = (pms->channels > 1) ? (k % 2) : 0 ; + + bytecode = pms->samples [k] & 0xF ; + + /* Compute next Adaptive Scale Factor (ASF) */ + idelta = chan_idelta [chan] ; + chan_idelta [chan] = (AdaptationTable [bytecode] * idelta) >> 8 ; /* => / 256 => FIXED_POINT_ADAPTATION_BASE == 256 */ + if (chan_idelta [chan] < 16) + chan_idelta [chan] = 16 ; + if (bytecode & 0x8) + bytecode -= 0x10 ; + + predict = ((pms->samples [k - pms->channels] * AdaptCoeff1 [bpred [chan]]) + + (pms->samples [k - 2 * pms->channels] * AdaptCoeff2 [bpred [chan]])) >> 8 ; /* => / 256 => FIXED_POINT_COEFF_BASE == 256 */ + current = (bytecode * idelta) + predict ; + + if (current > 32767) + current = 32767 ; + else if (current < -32768) + current = -32768 ; + + pms->samples [k] = current ; + } ; + + return 1 ; +} /* msadpcm_decode_block */ + +static sf_count_t +msadpcm_read_block (SF_PRIVATE *psf, MSADPCM_PRIVATE *pms, short *ptr, int len) +{ int count, total = 0, indx = 0 ; + + while (indx < len) + { if (pms->blockcount >= pms->blocks && pms->samplecount >= pms->samplesperblock) + { memset (&(ptr [indx]), 0, (size_t) ((len - indx) * sizeof (short))) ; + return total ; + } ; + + if (pms->samplecount >= pms->samplesperblock) + msadpcm_decode_block (psf, pms) ; + + count = (pms->samplesperblock - pms->samplecount) * pms->channels ; + count = (len - indx > count) ? count : len - indx ; + + memcpy (&(ptr [indx]), &(pms->samples [pms->samplecount * pms->channels]), count * sizeof (short)) ; + indx += count ; + pms->samplecount += count / pms->channels ; + total = indx ; + } ; + + return total ; +} /* msadpcm_read_block */ + +static sf_count_t +msadpcm_read_s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ MSADPCM_PRIVATE *pms ; + int readcount, count ; + sf_count_t total = 0 ; + + if (! psf->fdata) + return 0 ; + pms = (MSADPCM_PRIVATE*) psf->fdata ; + + while (len > 0) + { readcount = (len > 0x10000000) ? 0x10000000 : (int) len ; + + count = msadpcm_read_block (psf, pms, ptr, readcount) ; + + total += count ; + len -= count ; + if (count != readcount) + break ; + } ; + + return total ; +} /* msadpcm_read_s */ + +static sf_count_t +msadpcm_read_i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ MSADPCM_PRIVATE *pms ; + short *sptr ; + int k, bufferlen, readcount = 0, count ; + sf_count_t total = 0 ; + + if (! psf->fdata) + return 0 ; + pms = (MSADPCM_PRIVATE*) psf->fdata ; + + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : len ; + count = msadpcm_read_block (psf, pms, sptr, readcount) ; + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = sptr [k] << 16 ; + total += count ; + len -= readcount ; + if (count != readcount) + break ; + } ; + return total ; +} /* msadpcm_read_i */ + +static sf_count_t +msadpcm_read_f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ MSADPCM_PRIVATE *pms ; + short *sptr ; + int k, bufferlen, readcount = 0, count ; + sf_count_t total = 0 ; + float normfact ; + + if (! psf->fdata) + return 0 ; + pms = (MSADPCM_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_float == SF_TRUE) ? 1.0 / ((float) 0x8000) : 1.0 ; + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : len ; + count = msadpcm_read_block (psf, pms, sptr, readcount) ; + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = normfact * (float) (sptr [k]) ; + total += count ; + len -= readcount ; + if (count != readcount) + break ; + } ; + return total ; +} /* msadpcm_read_f */ + +static sf_count_t +msadpcm_read_d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ MSADPCM_PRIVATE *pms ; + short *sptr ; + int k, bufferlen, readcount = 0, count ; + sf_count_t total = 0 ; + double normfact ; + + normfact = (psf->norm_double == SF_TRUE) ? 1.0 / ((double) 0x8000) : 1.0 ; + + if (! psf->fdata) + return 0 ; + pms = (MSADPCM_PRIVATE*) psf->fdata ; + + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : len ; + count = msadpcm_read_block (psf, pms, sptr, readcount) ; + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = normfact * (double) (sptr [k]) ; + total += count ; + len -= readcount ; + if (count != readcount) + break ; + } ; + return total ; +} /* msadpcm_read_d */ + +static sf_count_t +msadpcm_seek (SF_PRIVATE *psf, int mode, sf_count_t offset) +{ MSADPCM_PRIVATE *pms ; + int newblock, newsample ; + + if (! psf->fdata) + return 0 ; + pms = (MSADPCM_PRIVATE*) psf->fdata ; + + if (psf->datalength < 0 || psf->dataoffset < 0) + { psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; + } ; + + if (offset == 0) + { psf_fseek (psf, psf->dataoffset, SEEK_SET) ; + pms->blockcount = 0 ; + msadpcm_decode_block (psf, pms) ; + pms->samplecount = 0 ; + return 0 ; + } ; + + if (offset < 0 || offset > pms->blocks * pms->samplesperblock) + { psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; + } ; + + newblock = offset / pms->samplesperblock ; + newsample = offset % pms->samplesperblock ; + + if (mode == SFM_READ) + { psf_fseek (psf, psf->dataoffset + newblock * pms->blocksize, SEEK_SET) ; + pms->blockcount = newblock ; + msadpcm_decode_block (psf, pms) ; + pms->samplecount = newsample ; + } + else + { /* What to do about write??? */ + psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; + } ; + + return newblock * pms->samplesperblock + newsample ; +} /* msadpcm_seek */ + +/*========================================================================================== +** MS ADPCM Write Functions. +*/ + +void +msadpcm_write_adapt_coeffs (SF_PRIVATE *psf) +{ int k ; + + for (k = 0 ; k < MSADPCM_ADAPT_COEFF_COUNT ; k++) + psf_binheader_writef (psf, "22", AdaptCoeff1 [k], AdaptCoeff2 [k]) ; +} /* msadpcm_write_adapt_coeffs */ + +/*========================================================================================== +*/ + +static int +msadpcm_encode_block (SF_PRIVATE *psf, MSADPCM_PRIVATE *pms) +{ unsigned int blockindx ; + unsigned char byte ; + int chan, k, predict, bpred [2], idelta [2], errordelta, newsamp ; + + choose_predictor (pms->channels, pms->samples, bpred, idelta) ; + + /* Write the block header. */ + + if (pms->channels == 1) + { pms->block [0] = bpred [0] ; + pms->block [1] = idelta [0] & 0xFF ; + pms->block [2] = idelta [0] >> 8 ; + pms->block [3] = pms->samples [1] & 0xFF ; + pms->block [4] = pms->samples [1] >> 8 ; + pms->block [5] = pms->samples [0] & 0xFF ; + pms->block [6] = pms->samples [0] >> 8 ; + + blockindx = 7 ; + byte = 0 ; + + /* Encode the samples as 4 bit. */ + + for (k = 2 ; k < pms->samplesperblock ; k++) + { predict = (pms->samples [k-1] * AdaptCoeff1 [bpred [0]] + pms->samples [k-2] * AdaptCoeff2 [bpred [0]]) >> 8 ; + errordelta = (pms->samples [k] - predict) / idelta [0] ; + if (errordelta < -8) + errordelta = -8 ; + else if (errordelta > 7) + errordelta = 7 ; + newsamp = predict + (idelta [0] * errordelta) ; + if (newsamp > 32767) + newsamp = 32767 ; + else if (newsamp < -32768) + newsamp = -32768 ; + if (errordelta < 0) + errordelta += 0x10 ; + + byte = (byte << 4) | (errordelta & 0xF) ; + if (k % 2) + { pms->block [blockindx++] = byte ; + byte = 0 ; + } ; + + idelta [0] = (idelta [0] * AdaptationTable [errordelta]) >> 8 ; + if (idelta [0] < 16) + idelta [0] = 16 ; + pms->samples [k] = newsamp ; + } ; + } + else + { /* Stereo file. */ + pms->block [0] = bpred [0] ; + pms->block [1] = bpred [1] ; + + pms->block [2] = idelta [0] & 0xFF ; + pms->block [3] = idelta [0] >> 8 ; + pms->block [4] = idelta [1] & 0xFF ; + pms->block [5] = idelta [1] >> 8 ; + + pms->block [6] = pms->samples [2] & 0xFF ; + pms->block [7] = pms->samples [2] >> 8 ; + pms->block [8] = pms->samples [3] & 0xFF ; + pms->block [9] = pms->samples [3] >> 8 ; + + pms->block [10] = pms->samples [0] & 0xFF ; + pms->block [11] = pms->samples [0] >> 8 ; + pms->block [12] = pms->samples [1] & 0xFF ; + pms->block [13] = pms->samples [1] >> 8 ; + + blockindx = 14 ; + byte = 0 ; + chan = 1 ; + + for (k = 4 ; k < 2 * pms->samplesperblock ; k++) + { chan = k & 1 ; + + predict = (pms->samples [k-2] * AdaptCoeff1 [bpred [chan]] + pms->samples [k-4] * AdaptCoeff2 [bpred [chan]]) >> 8 ; + errordelta = (pms->samples [k] - predict) / idelta [chan] ; + + + if (errordelta < -8) + errordelta = -8 ; + else if (errordelta > 7) + errordelta = 7 ; + newsamp = predict + (idelta [chan] * errordelta) ; + if (newsamp > 32767) + newsamp = 32767 ; + else if (newsamp < -32768) + newsamp = -32768 ; + if (errordelta < 0) + errordelta += 0x10 ; + + byte = (byte << 4) | (errordelta & 0xF) ; + + if (chan) + { pms->block [blockindx++] = byte ; + byte = 0 ; + } ; + + idelta [chan] = (idelta [chan] * AdaptationTable [errordelta]) >> 8 ; + if (idelta [chan] < 16) + idelta [chan] = 16 ; + pms->samples [k] = newsamp ; + } ; + } ; + + /* Write the block to disk. */ + + if ((k = psf_fwrite (pms->block, 1, pms->blocksize, psf)) != pms->blocksize) + psf_log_printf (psf, "*** Warning : short write (%d != %d).\n", k, pms->blocksize) ; + + memset (pms->samples, 0, pms->samplesperblock * sizeof (short)) ; + + pms->blockcount ++ ; + pms->samplecount = 0 ; + + return 1 ; +} /* msadpcm_encode_block */ + +static sf_count_t +msadpcm_write_block (SF_PRIVATE *psf, MSADPCM_PRIVATE *pms, const short *ptr, int len) +{ int count, total = 0, indx = 0 ; + + while (indx < len) + { count = (pms->samplesperblock - pms->samplecount) * pms->channels ; + + if (count > len - indx) + count = len - indx ; + + memcpy (&(pms->samples [pms->samplecount * pms->channels]), &(ptr [total]), count * sizeof (short)) ; + indx += count ; + pms->samplecount += count / pms->channels ; + total = indx ; + + if (pms->samplecount >= pms->samplesperblock) + msadpcm_encode_block (psf, pms) ; + } ; + + return total ; +} /* msadpcm_write_block */ + +static sf_count_t +msadpcm_write_s (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ MSADPCM_PRIVATE *pms ; + int writecount, count ; + sf_count_t total = 0 ; + + if (! psf->fdata) + return 0 ; + pms = (MSADPCM_PRIVATE*) psf->fdata ; + + while (len > 0) + { writecount = (len > 0x10000000) ? 0x10000000 : (int) len ; + + count = msadpcm_write_block (psf, pms, ptr, writecount) ; + + total += count ; + len -= count ; + if (count != writecount) + break ; + } ; + + return total ; +} /* msadpcm_write_s */ + +static sf_count_t +msadpcm_write_i (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ MSADPCM_PRIVATE *pms ; + short *sptr ; + int k, bufferlen, writecount, count ; + sf_count_t total = 0 ; + + if (! psf->fdata) + return 0 ; + pms = (MSADPCM_PRIVATE*) psf->fdata ; + + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : len ; + for (k = 0 ; k < writecount ; k++) + sptr [k] = ptr [total + k] >> 16 ; + count = msadpcm_write_block (psf, pms, sptr, writecount) ; + total += count ; + len -= writecount ; + if (count != writecount) + break ; + } ; + return total ; +} /* msadpcm_write_i */ + +static sf_count_t +msadpcm_write_f (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ MSADPCM_PRIVATE *pms ; + short *sptr ; + int k, bufferlen, writecount, count ; + sf_count_t total = 0 ; + float normfact ; + + if (! psf->fdata) + return 0 ; + pms = (MSADPCM_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_float == SF_TRUE) ? (1.0 * 0x7FFF) : 1.0 ; + + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : len ; + for (k = 0 ; k < writecount ; k++) + sptr [k] = lrintf (normfact * ptr [total + k]) ; + count = msadpcm_write_block (psf, pms, sptr, writecount) ; + total += count ; + len -= writecount ; + if (count != writecount) + break ; + } ; + return total ; +} /* msadpcm_write_f */ + +static sf_count_t +msadpcm_write_d (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ MSADPCM_PRIVATE *pms ; + short *sptr ; + int k, bufferlen, writecount, count ; + sf_count_t total = 0 ; + double normfact ; + + normfact = (psf->norm_double == SF_TRUE) ? (1.0 * 0x7FFF) : 1.0 ; + + if (! psf->fdata) + return 0 ; + pms = (MSADPCM_PRIVATE*) psf->fdata ; + + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : len ; + for (k = 0 ; k < writecount ; k++) + sptr [k] = lrint (normfact * ptr [total + k]) ; + count = msadpcm_write_block (psf, pms, sptr, writecount) ; + total += count ; + len -= writecount ; + if (count != writecount) + break ; + } ; + return total ; +} /* msadpcm_write_d */ + +/*======================================================================================== +*/ + +static int +msadpcm_close (SF_PRIVATE *psf) +{ MSADPCM_PRIVATE *pms ; + + pms = (MSADPCM_PRIVATE*) psf->fdata ; + + if (psf->mode == SFM_WRITE) + { /* Now we know static int for certain the length of the file we can + ** re-write the header. + */ + + if (pms->samplecount && pms->samplecount < pms->samplesperblock) + msadpcm_encode_block (psf, pms) ; + } ; + + return 0 ; +} /* msadpcm_close */ + +/*======================================================================================== +** Static functions. +*/ + +/*---------------------------------------------------------------------------------------- +** Choosing the block predictor. +** Each block requires a predictor and an idelta for each channel. +** The predictor is in the range [0..6] which is an indx into the two AdaptCoeff tables. +** The predictor is chosen by trying all of the possible predictors on a small set of +** samples at the beginning of the block. The predictor with the smallest average +** abs (idelta) is chosen as the best predictor for this block. +** The value of idelta is chosen to to give a 4 bit code value of +/- 4 (approx. half the +** max. code value). If the average abs (idelta) is zero, the sixth predictor is chosen. +** If the value of idelta is less then 16 it is set to 16. +** +** Microsoft uses an IDELTA_COUNT (number of sample pairs used to choose best predictor) +** value of 3. The best possible results would be obtained by using all the samples to +** choose the predictor. +*/ + +#define IDELTA_COUNT 3 + +static void +choose_predictor (unsigned int channels, short *data, int *block_pred, int *idelta) +{ unsigned int chan, k, bpred, idelta_sum, best_bpred, best_idelta ; + + for (chan = 0 ; chan < channels ; chan++) + { best_bpred = best_idelta = 0 ; + + for (bpred = 0 ; bpred < 7 ; bpred++) + { idelta_sum = 0 ; + for (k = 2 ; k < 2 + IDELTA_COUNT ; k++) + idelta_sum += abs (data [k * channels] - ((data [(k - 1) * channels] * AdaptCoeff1 [bpred] + data [(k - 2) * channels] * AdaptCoeff2 [bpred]) >> 8)) ; + idelta_sum /= (4 * IDELTA_COUNT) ; + + if (bpred == 0 || idelta_sum < best_idelta) + { best_bpred = bpred ; + best_idelta = idelta_sum ; + } ; + + if (! idelta_sum) + { best_bpred = bpred ; + best_idelta = 16 ; + break ; + } ; + + } ; /* for bpred ... */ + if (best_idelta < 16) + best_idelta = 16 ; + + block_pred [chan] = best_bpred ; + idelta [chan] = best_idelta ; + } ; + + return ; +} /* choose_predictor */ +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: a98908a3-5305-4935-872b-77d6a86c330f +*/ diff --git a/libs/libsndfile/src/nist.c b/libs/libsndfile/src/nist.c new file mode 100644 index 0000000000..2ab20dbf96 --- /dev/null +++ b/libs/libsndfile/src/nist.c @@ -0,0 +1,367 @@ +/* +** Copyright (C) 1999-2004 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +/* +** Some of the information used to read NIST files was gleaned from +** reading the code of Bill Schottstaedt's sndlib library +** ftp://ccrma-ftp.stanford.edu/pub/Lisp/sndlib.tar.gz +** However, no code from that package was used. +*/ + +#include "sfconfig.h" + +#include +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" + +/*------------------------------------------------------------------------------ +*/ + +#define NIST_HEADER_LENGTH 1024 + +/*------------------------------------------------------------------------------ +** Private static functions. +*/ + +static int nist_close (SF_PRIVATE *psf) ; +static int nist_write_header (SF_PRIVATE *psf, int calc_length) ; +static int nist_read_header (SF_PRIVATE *psf) ; + +/*------------------------------------------------------------------------------ +*/ + +int +nist_open (SF_PRIVATE *psf) +{ int error ; + + if (psf->mode == SFM_READ || (psf->mode == SFM_RDWR && psf->filelength > 0)) + { if ((error = nist_read_header (psf))) + return error ; + } ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { if (psf->is_pipe) + return SFE_NO_PIPE_WRITE ; + + if ((psf->sf.format & SF_FORMAT_TYPEMASK) != SF_FORMAT_NIST) + return SFE_BAD_OPEN_FORMAT ; + + psf->endian = psf->sf.format & SF_FORMAT_ENDMASK ; + if (psf->endian == 0 || psf->endian == SF_ENDIAN_CPU) + psf->endian = (CPU_IS_BIG_ENDIAN) ? SF_ENDIAN_BIG : SF_ENDIAN_LITTLE ; + + psf->blockwidth = psf->bytewidth * psf->sf.channels ; + psf->sf.frames = 0 ; + + if ((error = nist_write_header (psf, SF_FALSE))) + return error ; + + psf->write_header = nist_write_header ; + } ; + + psf->container_close = nist_close ; + + switch (psf->sf.format & SF_FORMAT_SUBMASK) + { case SF_FORMAT_PCM_S8 : + error = pcm_init (psf) ; + break ; + + case SF_FORMAT_PCM_16 : + case SF_FORMAT_PCM_24 : + case SF_FORMAT_PCM_32 : + error = pcm_init (psf) ; + break ; + + case SF_FORMAT_ULAW : + error = ulaw_init (psf) ; + break ; + + case SF_FORMAT_ALAW : + error = alaw_init (psf) ; + break ; + + default : error = SFE_UNIMPLEMENTED ; + break ; + } ; + + return error ; +} /* nist_open */ + +/*------------------------------------------------------------------------------ +*/ + +static char bad_header [] = +{ 'N', 'I', 'S', 'T', '_', '1', 'A', 0x0d, 0x0a, + ' ', ' ', ' ', '1', '0', '2', '4', 0x0d, 0x0a, + 0 +} ; + + static int +nist_read_header (SF_PRIVATE *psf) +{ char *psf_header ; + int bitwidth = 0, bytes = 0, count, encoding ; + char str [64], *cptr ; + long samples ; + + psf->sf.format = SF_FORMAT_NIST ; + + psf_header = psf->u.cbuf ; + + if (sizeof (psf->header) <= NIST_HEADER_LENGTH) + return SFE_INTERNAL ; + + /* Go to start of file and read in the whole header. */ + psf_binheader_readf (psf, "pb", 0, psf_header, NIST_HEADER_LENGTH) ; + + /* Header is a string, so make sure it is null terminated. */ + psf_header [NIST_HEADER_LENGTH] = 0 ; + + /* Now trim the header after the end marker. */ + if ((cptr = strstr (psf_header, "end_head"))) + { cptr += strlen ("end_head") + 1 ; + cptr [0] = 0 ; + } ; + + if (strstr (psf_header, bad_header) == psf_header) + return SFE_NIST_CRLF_CONVERISON ; + + /* Make sure its a NIST file. */ + if (strstr (psf_header, "NIST_1A\n") != psf_header) + { psf_log_printf (psf, "Not a NIST file.\n") ; + return SFE_NIST_BAD_HEADER ; + } ; + + if (sscanf (psf_header, "NIST_1A\n%d\n", &count) == 1) + psf->dataoffset = count ; + else + { psf_log_printf (psf, "*** Suspicious header length.\n") ; + psf->dataoffset = NIST_HEADER_LENGTH ; + } ; + + /* Determine sample encoding, start by assuming PCM. */ + encoding = SF_FORMAT_PCM_U8 ; + if ((cptr = strstr (psf_header, "sample_coding -s"))) + { sscanf (cptr, "sample_coding -s%d %63s", &count, str) ; + + if (strcmp (str, "pcm") == 0) + encoding = SF_FORMAT_PCM_U8 ; + else if (strcmp (str, "alaw") == 0) + encoding = SF_FORMAT_ALAW ; + else if ((strcmp (str, "ulaw") == 0) || (strcmp (str, "mu-law") == 0)) + encoding = SF_FORMAT_ULAW ; + else + { psf_log_printf (psf, "*** Unknown encoding : %s\n", str) ; + encoding = 0 ; + } ; + } ; + + if ((cptr = strstr (psf_header, "channel_count -i "))) + sscanf (cptr, "channel_count -i %d", &(psf->sf.channels)) ; + + if ((cptr = strstr (psf_header, "sample_rate -i "))) + sscanf (cptr, "sample_rate -i %d", &(psf->sf.samplerate)) ; + + if ((cptr = strstr (psf_header, "sample_count -i "))) + { sscanf (psf_header, "sample_count -i %ld", &samples) ; + psf->sf.frames = samples ; + } ; + + if ((cptr = strstr (psf_header, "sample_n_bytes -i "))) + sscanf (cptr, "sample_n_bytes -i %d", &(psf->bytewidth)) ; + + /* Default endian-ness (for 8 bit, u-law, A-law. */ + psf->endian = (CPU_IS_BIG_ENDIAN) ? SF_ENDIAN_BIG : SF_ENDIAN_LITTLE ; + + /* This is where we figure out endian-ness. */ + if ((cptr = strstr (psf_header, "sample_byte_format -s"))) + { sscanf (cptr, "sample_byte_format -s%d %8s", &bytes, str) ; + if (bytes > 1) + { if (psf->bytewidth == 0) + psf->bytewidth = bytes ; + else if (psf->bytewidth != bytes) + { psf_log_printf (psf, "psf->bytewidth (%d) != bytes (%d)\n", psf->bytewidth, bytes) ; + return SFE_NIST_BAD_ENCODING ; + } ; + + if (strstr (str, "01") == str) + psf->endian = SF_ENDIAN_LITTLE ; + else if (strstr (str, "10")) + psf->endian = SF_ENDIAN_BIG ; + else + { psf_log_printf (psf, "Weird endian-ness : %s\n", str) ; + return SFE_NIST_BAD_ENCODING ; + } ; + } ; + + psf->sf.format |= psf->endian ; + } ; + + if ((cptr = strstr (psf_header, "sample_sig_bits -i "))) + sscanf (cptr, "sample_sig_bits -i %d", &bitwidth) ; + + if (strstr (psf_header, "channels_interleaved -s5 FALSE")) + { psf_log_printf (psf, "Non-interleaved data unsupported.\n", str) ; + return SFE_NIST_BAD_ENCODING ; + } ; + + psf->blockwidth = psf->sf.channels * psf->bytewidth ; + psf->datalength = psf->filelength - psf->dataoffset ; + + psf_fseek (psf, psf->dataoffset, SEEK_SET) ; + + if (encoding == SF_FORMAT_PCM_U8) + { switch (psf->bytewidth) + { case 1 : + psf->sf.format |= SF_FORMAT_PCM_S8 ; + break ; + + case 2 : + psf->sf.format |= SF_FORMAT_PCM_16 ; + break ; + + case 3 : + psf->sf.format |= SF_FORMAT_PCM_24 ; + break ; + + case 4 : + psf->sf.format |= SF_FORMAT_PCM_32 ; + break ; + + default : break ; + } ; + } + else if (encoding != 0) + psf->sf.format |= encoding ; + else + return SFE_UNIMPLEMENTED ; + + return 0 ; +} /* nist_read_header */ + +static int +nist_close (SF_PRIVATE *psf) +{ + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + nist_write_header (psf, SF_TRUE) ; + + return 0 ; +} /* nist_close */ + +/*========================================================================= +*/ + +static int +nist_write_header (SF_PRIVATE *psf, int calc_length) +{ const char *end_str ; + long samples ; + sf_count_t current ; + + current = psf_ftell (psf) ; + + if (calc_length) + { psf->filelength = psf_get_filelen (psf) ; + + psf->datalength = psf->filelength - psf->dataoffset ; + + if (psf->dataend) + psf->datalength -= psf->filelength - psf->dataend ; + + if (psf->bytewidth > 0) + psf->sf.frames = psf->datalength / (psf->bytewidth * psf->sf.channels) ; + } ; + + if (psf->endian == SF_ENDIAN_BIG) + end_str = "10" ; + else if (psf->endian == SF_ENDIAN_LITTLE) + end_str = "01" ; + else + end_str = "error" ; + + /* Clear the whole header. */ + memset (psf->header, 0, sizeof (psf->header)) ; + psf->headindex = 0 ; + + psf_fseek (psf, 0, SEEK_SET) ; + + psf_asciiheader_printf (psf, "NIST_1A\n 1024\n") ; + psf_asciiheader_printf (psf, "channel_count -i %d\n", psf->sf.channels) ; + psf_asciiheader_printf (psf, "sample_rate -i %d\n", psf->sf.samplerate) ; + + switch (psf->sf.format & SF_FORMAT_SUBMASK) + { case SF_FORMAT_PCM_S8 : + psf_asciiheader_printf (psf, "sample_coding -s3 pcm\n") ; + psf_asciiheader_printf (psf, "sample_n_bytes -i 1\n" + "sample_sig_bits -i 8\n") ; + break ; + + case SF_FORMAT_PCM_16 : + case SF_FORMAT_PCM_24 : + case SF_FORMAT_PCM_32 : + psf_asciiheader_printf (psf, "sample_n_bytes -i %d\n", psf->bytewidth) ; + psf_asciiheader_printf (psf, "sample_sig_bits -i %d\n", psf->bytewidth * 8) ; + psf_asciiheader_printf (psf, "sample_coding -s3 pcm\n" + "sample_byte_format -s%d %s\n", psf->bytewidth, end_str) ; + break ; + + case SF_FORMAT_ALAW : + psf_asciiheader_printf (psf, "sample_coding -s4 alaw\n") ; + psf_asciiheader_printf (psf, "sample_n_bytes -s1 1\n") ; + break ; + + case SF_FORMAT_ULAW : + psf_asciiheader_printf (psf, "sample_coding -s4 ulaw\n") ; + psf_asciiheader_printf (psf, "sample_n_bytes -s1 1\n") ; + break ; + + default : return SFE_UNIMPLEMENTED ; + } ; + + psf->dataoffset = NIST_HEADER_LENGTH ; + + /* Fix this */ + samples = psf->sf.frames ; + psf_asciiheader_printf (psf, "sample_count -i %ld\n", samples) ; + psf_asciiheader_printf (psf, "end_head\n") ; + + /* Zero fill to dataoffset. */ + psf_binheader_writef (psf, "z", (size_t) (NIST_HEADER_LENGTH - psf->headindex)) ; + + psf_fwrite (psf->header, psf->headindex, 1, psf) ; + + if (psf->error) + return psf->error ; + + if (current > 0) + psf_fseek (psf, current, SEEK_SET) ; + + return psf->error ; +} /* nist_write_header */ + + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: b45ed85d-9e22-4ad9-b78c-4b58b67152a8 +*/ diff --git a/libs/libsndfile/src/ogg.c b/libs/libsndfile/src/ogg.c new file mode 100644 index 0000000000..869baa9500 --- /dev/null +++ b/libs/libsndfile/src/ogg.c @@ -0,0 +1,44 @@ +/* +** Copyright (C) 2002-2004 Erik de Castro Lopo +** +** This program is free software ; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation ; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY ; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program ; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" + +int +ogg_open (SF_PRIVATE *psf) +{ if (psf) + return SFE_UNIMPLEMENTED ; + return (psf && 0) ; +} /* ogg_open */ + + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 9ff1fe9c-629e-4e9c-9ef5-3d0eb1e427a0 +*/ diff --git a/libs/libsndfile/src/paf.c b/libs/libsndfile/src/paf.c new file mode 100644 index 0000000000..6114dac838 --- /dev/null +++ b/libs/libsndfile/src/paf.c @@ -0,0 +1,843 @@ +/* +** Copyright (C) 1999-2005 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "float_cast.h" +#include "common.h" + +/*------------------------------------------------------------------------------ +** Macros to handle big/little endian issues. +*/ + +#define FAP_MARKER (MAKE_MARKER ('f', 'a', 'p', ' ')) +#define PAF_MARKER (MAKE_MARKER (' ', 'p', 'a', 'f')) + +/*------------------------------------------------------------------------------ +** Other defines. +*/ + +#define PAF_HEADER_LENGTH 2048 + +#define PAF24_SAMPLES_PER_BLOCK 10 +#define PAF24_BLOCK_SIZE 32 + +/*------------------------------------------------------------------------------ +** Typedefs. +*/ + +typedef struct +{ int version ; + int endianness ; + int samplerate ; + int format ; + int channels ; + int source ; +} PAF_FMT ; + +typedef struct +{ int max_blocks, channels, samplesperblock, blocksize ; + int read_block, write_block, read_count, write_count ; + sf_count_t sample_count ; + int *samples ; + unsigned char *block ; +#if HAVE_FLEXIBLE_ARRAY + int data [] ; /* ISO C99 struct flexible array. */ +#else + int data [1] ; /* This is a hack and may not work. */ +#endif +} PAF24_PRIVATE ; + +/*------------------------------------------------------------------------------ +** Private static functions. +*/ + +static int paf24_init (SF_PRIVATE *psf) ; + +static int paf_read_header (SF_PRIVATE *psf) ; +static int paf_write_header (SF_PRIVATE *psf, int calc_length) ; + +static sf_count_t paf24_read_s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t paf24_read_i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t paf24_read_f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t paf24_read_d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; + +static sf_count_t paf24_write_s (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t paf24_write_i (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t paf24_write_f (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t paf24_write_d (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; + +static sf_count_t paf24_seek (SF_PRIVATE *psf, int mode, sf_count_t offset) ; + +enum +{ PAF_PCM_16 = 0, + PAF_PCM_24 = 1, + PAF_PCM_S8 = 2 +} ; + +/*------------------------------------------------------------------------------ +** Public function. +*/ + +int +paf_open (SF_PRIVATE *psf) +{ int subformat, error, endian ; + + psf->dataoffset = PAF_HEADER_LENGTH ; + + if (psf->mode == SFM_READ || (psf->mode == SFM_RDWR && psf->filelength > 0)) + { if ((error = paf_read_header (psf))) + return error ; + } ; + + subformat = psf->sf.format & SF_FORMAT_SUBMASK ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { if ((psf->sf.format & SF_FORMAT_TYPEMASK) != SF_FORMAT_PAF) + return SFE_BAD_OPEN_FORMAT ; + + endian = psf->sf.format & SF_FORMAT_ENDMASK ; + + /* PAF is by default big endian. */ + psf->endian = SF_ENDIAN_BIG ; + + if (endian == SF_ENDIAN_LITTLE || (CPU_IS_LITTLE_ENDIAN && (endian == SF_ENDIAN_CPU))) + psf->endian = SF_ENDIAN_LITTLE ; + + if ((error = paf_write_header (psf, SF_FALSE))) + return error ; + + psf->write_header = paf_write_header ; + } ; + + switch (subformat) + { case SF_FORMAT_PCM_S8 : + psf->bytewidth = 1 ; + error = pcm_init (psf) ; + break ; + + case SF_FORMAT_PCM_16 : + psf->bytewidth = 2 ; + error = pcm_init (psf) ; + break ; + + case SF_FORMAT_PCM_24 : + /* No bytewidth because of whacky 24 bit encoding. */ + error = paf24_init (psf) ; + break ; + + default : return SFE_PAF_UNKNOWN_FORMAT ; + } ; + + return error ; +} /* paf_open */ + +/*------------------------------------------------------------------------------ +*/ + +static int +paf_read_header (SF_PRIVATE *psf) +{ PAF_FMT paf_fmt ; + int marker ; + + memset (&paf_fmt, 0, sizeof (paf_fmt)) ; + psf_binheader_readf (psf, "pm", 0, &marker) ; + + psf_log_printf (psf, "Signature : '%M'\n", marker) ; + + if (marker == PAF_MARKER) + { psf_binheader_readf (psf, "E444444", &(paf_fmt.version), &(paf_fmt.endianness), + &(paf_fmt.samplerate), &(paf_fmt.format), &(paf_fmt.channels), &(paf_fmt.source)) ; + } + else if (marker == FAP_MARKER) + { psf_binheader_readf (psf, "e444444", &(paf_fmt.version), &(paf_fmt.endianness), + &(paf_fmt.samplerate), &(paf_fmt.format), &(paf_fmt.channels), &(paf_fmt.source)) ; + } + else + return SFE_PAF_NO_MARKER ; + + psf_log_printf (psf, "Version : %d\n", paf_fmt.version) ; + + if (paf_fmt.version != 0) + { psf_log_printf (psf, "*** Bad version number. should be zero.\n") ; + return SFE_PAF_VERSION ; + } ; + + psf_log_printf (psf, "Sample Rate : %d\n", paf_fmt.samplerate) ; + psf_log_printf (psf, "Channels : %d\n", paf_fmt.channels) ; + + psf_log_printf (psf, "Endianness : %d => ", paf_fmt.endianness) ; + if (paf_fmt.endianness) + { psf_log_printf (psf, "Little\n", paf_fmt.endianness) ; + psf->endian = SF_ENDIAN_LITTLE ; + } + else + { psf_log_printf (psf, "Big\n", paf_fmt.endianness) ; + psf->endian = SF_ENDIAN_BIG ; + } ; + + if (psf->filelength < PAF_HEADER_LENGTH) + return SFE_PAF_SHORT_HEADER ; + + psf->datalength = psf->filelength - psf->dataoffset ; + + psf_binheader_readf (psf, "p", (int) psf->dataoffset) ; + + psf->sf.samplerate = paf_fmt.samplerate ; + psf->sf.channels = paf_fmt.channels ; + + /* Only fill in type major. */ + psf->sf.format = SF_FORMAT_PAF ; + + psf_log_printf (psf, "Format : %d => ", paf_fmt.format) ; + + /* PAF is by default big endian. */ + psf->sf.format |= paf_fmt.endianness ? SF_ENDIAN_LITTLE : SF_ENDIAN_BIG ; + + switch (paf_fmt.format) + { case PAF_PCM_S8 : + psf_log_printf (psf, "8 bit linear PCM\n") ; + psf->bytewidth = 1 ; + + psf->sf.format |= SF_FORMAT_PCM_S8 ; + + psf->blockwidth = psf->bytewidth * psf->sf.channels ; + psf->sf.frames = psf->datalength / psf->blockwidth ; + break ; + + case PAF_PCM_16 : + psf_log_printf (psf, "16 bit linear PCM\n") ; + psf->bytewidth = 2 ; + + psf->sf.format |= SF_FORMAT_PCM_16 ; + + psf->blockwidth = psf->bytewidth * psf->sf.channels ; + psf->sf.frames = psf->datalength / psf->blockwidth ; + break ; + + case PAF_PCM_24 : + psf_log_printf (psf, "24 bit linear PCM\n") ; + psf->bytewidth = 3 ; + + psf->sf.format |= SF_FORMAT_PCM_24 ; + + psf->blockwidth = 0 ; + psf->sf.frames = PAF24_SAMPLES_PER_BLOCK * psf->datalength / + (PAF24_BLOCK_SIZE * psf->sf.channels) ; + break ; + + default : psf_log_printf (psf, "Unknown\n") ; + return SFE_PAF_UNKNOWN_FORMAT ; + break ; + } ; + + psf_log_printf (psf, "Source : %d => ", paf_fmt.source) ; + + switch (paf_fmt.source) + { case 1 : psf_log_printf (psf, "Analog Recording\n") ; + break ; + case 2 : psf_log_printf (psf, "Digital Transfer\n") ; + break ; + case 3 : psf_log_printf (psf, "Multi-track Mixdown\n") ; + break ; + case 5 : psf_log_printf (psf, "Audio Resulting From DSP Processing\n") ; + break ; + default : psf_log_printf (psf, "Unknown\n") ; + break ; + } ; + + return 0 ; +} /* paf_read_header */ + +static int +paf_write_header (SF_PRIVATE *psf, int calc_length) +{ int paf_format ; + + /* PAF header already written so no need to re-write. */ + if (psf_ftell (psf) >= PAF_HEADER_LENGTH) + return 0 ; + + psf->dataoffset = PAF_HEADER_LENGTH ; + + psf->dataoffset = PAF_HEADER_LENGTH ; + + /* Prevent compiler warning. */ + calc_length = calc_length ; + + switch (psf->sf.format & SF_FORMAT_SUBMASK) + { case SF_FORMAT_PCM_S8 : + paf_format = PAF_PCM_S8 ; + break ; + + case SF_FORMAT_PCM_16 : + paf_format = PAF_PCM_16 ; + break ; + + case SF_FORMAT_PCM_24 : + paf_format = PAF_PCM_24 ; + break ; + + default : return SFE_PAF_UNKNOWN_FORMAT ; + } ; + + /* Reset the current header length to zero. */ + psf->header [0] = 0 ; + psf->headindex = 0 ; + + if (psf->endian == SF_ENDIAN_BIG) + { /* Marker, version, endianness, samplerate */ + psf_binheader_writef (psf, "Em444", PAF_MARKER, 0, 0, psf->sf.samplerate) ; + /* format, channels, source */ + psf_binheader_writef (psf, "E444", paf_format, psf->sf.channels, 0) ; + } + else if (psf->endian == SF_ENDIAN_LITTLE) + { /* Marker, version, endianness, samplerate */ + psf_binheader_writef (psf, "em444", FAP_MARKER, 0, 1, psf->sf.samplerate) ; + /* format, channels, source */ + psf_binheader_writef (psf, "e444", paf_format, psf->sf.channels, 0) ; + } ; + + /* Zero fill to dataoffset. */ + psf_binheader_writef (psf, "z", (size_t) (psf->dataoffset - psf->headindex)) ; + + psf_fwrite (psf->header, psf->headindex, 1, psf) ; + + return psf->error ; +} /* paf_write_header */ + +/*=============================================================================== +** 24 bit PAF files have a really weird encoding. +** For a mono file, 10 samples (each being 3 bytes) are packed into a 32 byte +** block. The 8 ints in this 32 byte block are then endian swapped (as ints) +** if necessary before being written to disk. +** For a stereo file, blocks of 10 samples from the same channel are encoded +** into 32 bytes as for the mono case. The 32 byte blocks are then interleaved +** on disk. +** Reading has to reverse the above process :-). +** Weird!!! +** +** The code below attempts to gain efficiency while maintaining readability. +*/ + +static int paf24_read_block (SF_PRIVATE *psf, PAF24_PRIVATE *ppaf24) ; +static int paf24_write_block (SF_PRIVATE *psf, PAF24_PRIVATE *ppaf24) ; +static int paf24_close (SF_PRIVATE *psf) ; + + +static int +paf24_init (SF_PRIVATE *psf) +{ PAF24_PRIVATE *ppaf24 ; + int paf24size ; + + paf24size = sizeof (PAF24_PRIVATE) + psf->sf.channels * + (PAF24_BLOCK_SIZE + PAF24_SAMPLES_PER_BLOCK * sizeof (int)) ; + + /* + ** Not exatly sure why this needs to be here but the tests + ** fail without it. + */ + psf->last_op = 0 ; + + if (! (psf->fdata = malloc (paf24size))) + return SFE_MALLOC_FAILED ; + + ppaf24 = (PAF24_PRIVATE*) psf->fdata ; + memset (ppaf24, 0, paf24size) ; + + ppaf24->channels = psf->sf.channels ; + ppaf24->samples = ppaf24->data ; + ppaf24->block = (unsigned char*) (ppaf24->data + PAF24_SAMPLES_PER_BLOCK * ppaf24->channels) ; + + ppaf24->blocksize = PAF24_BLOCK_SIZE * ppaf24->channels ; + ppaf24->samplesperblock = PAF24_SAMPLES_PER_BLOCK ; + + if (psf->mode == SFM_READ || psf->mode == SFM_RDWR) + { paf24_read_block (psf, ppaf24) ; /* Read first block. */ + + psf->read_short = paf24_read_s ; + psf->read_int = paf24_read_i ; + psf->read_float = paf24_read_f ; + psf->read_double = paf24_read_d ; + } ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { psf->write_short = paf24_write_s ; + psf->write_int = paf24_write_i ; + psf->write_float = paf24_write_f ; + psf->write_double = paf24_write_d ; + } ; + + psf->seek = paf24_seek ; + psf->container_close = paf24_close ; + + psf->filelength = psf_get_filelen (psf) ; + psf->datalength = psf->filelength - psf->dataoffset ; + + if (psf->datalength % PAF24_BLOCK_SIZE) + { if (psf->mode == SFM_READ) + psf_log_printf (psf, "*** Warning : file seems to be truncated.\n") ; + ppaf24->max_blocks = psf->datalength / ppaf24->blocksize + 1 ; + } + else + ppaf24->max_blocks = psf->datalength / ppaf24->blocksize ; + + ppaf24->read_block = 0 ; + if (psf->mode == SFM_RDWR) + ppaf24->write_block = ppaf24->max_blocks ; + else + ppaf24->write_block = 0 ; + + psf->sf.frames = ppaf24->samplesperblock * ppaf24->max_blocks ; + ppaf24->sample_count = psf->sf.frames ; + + return 0 ; +} /* paf24_init */ + +static sf_count_t +paf24_seek (SF_PRIVATE *psf, int mode, sf_count_t offset) +{ PAF24_PRIVATE *ppaf24 ; + int newblock, newsample ; + + if (psf->fdata == NULL) + { psf->error = SFE_INTERNAL ; + return PSF_SEEK_ERROR ; + } ; + + ppaf24 = (PAF24_PRIVATE*) psf->fdata ; + + if (mode == SFM_READ && ppaf24->write_count > 0) + paf24_write_block (psf, ppaf24) ; + + newblock = offset / ppaf24->samplesperblock ; + newsample = offset % ppaf24->samplesperblock ; + + switch (mode) + { case SFM_READ : + if (psf->last_op == SFM_WRITE && ppaf24->write_count) + paf24_write_block (psf, ppaf24) ; + + psf_fseek (psf, psf->dataoffset + newblock * ppaf24->blocksize, SEEK_SET) ; + ppaf24->read_block = newblock ; + paf24_read_block (psf, ppaf24) ; + ppaf24->read_count = newsample ; + break ; + + case SFM_WRITE : + if (offset > ppaf24->sample_count) + { psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; + } ; + + if (psf->last_op == SFM_WRITE && ppaf24->write_count) + paf24_write_block (psf, ppaf24) ; + + psf_fseek (psf, psf->dataoffset + newblock * ppaf24->blocksize, SEEK_SET) ; + ppaf24->write_block = newblock ; + paf24_read_block (psf, ppaf24) ; + ppaf24->write_count = newsample ; + break ; + + default : + psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; + } ; + + return newblock * ppaf24->samplesperblock + newsample ; +} /* paf24_seek */ + +static int +paf24_close (SF_PRIVATE *psf) +{ PAF24_PRIVATE *ppaf24 ; + + if (psf->fdata == NULL) + return 0 ; + + ppaf24 = (PAF24_PRIVATE*) psf->fdata ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { if (ppaf24->write_count > 0) + paf24_write_block (psf, ppaf24) ; + } ; + + return 0 ; +} /* paf24_close */ + +/*--------------------------------------------------------------------------- +*/ +static int +paf24_read_block (SF_PRIVATE *psf, PAF24_PRIVATE *ppaf24) +{ int k, channel ; + unsigned char *cptr ; + + ppaf24->read_block ++ ; + ppaf24->read_count = 0 ; + + if (ppaf24->read_block * ppaf24->samplesperblock > ppaf24->sample_count) + { memset (ppaf24->samples, 0, ppaf24->samplesperblock * ppaf24->channels) ; + return 1 ; + } ; + + /* Read the block. */ + if ((k = psf_fread (ppaf24->block, 1, ppaf24->blocksize, psf)) != ppaf24->blocksize) + psf_log_printf (psf, "*** Warning : short read (%d != %d).\n", k, ppaf24->blocksize) ; + + + if (CPU_IS_LITTLE_ENDIAN) + { /* Do endian swapping if necessary. */ + if (psf->endian == SF_ENDIAN_BIG) + endswap_int_array (ppaf24->data, 8 * ppaf24->channels) ; + + /* Unpack block. */ + for (k = 0 ; k < PAF24_SAMPLES_PER_BLOCK * ppaf24->channels ; k++) + { channel = k % ppaf24->channels ; + cptr = ppaf24->block + PAF24_BLOCK_SIZE * channel + 3 * (k / ppaf24->channels) ; + ppaf24->samples [k] = (cptr [0] << 8) | (cptr [1] << 16) | (cptr [2] << 24) ; + } ; + } + else + { /* Do endian swapping if necessary. */ + if (psf->endian == SF_ENDIAN_BIG) + endswap_int_array (ppaf24->data, 8 * ppaf24->channels) ; + + /* Unpack block. */ + for (k = 0 ; k < PAF24_SAMPLES_PER_BLOCK * ppaf24->channels ; k++) + { channel = k % ppaf24->channels ; + cptr = ppaf24->block + PAF24_BLOCK_SIZE * channel + 3 * (k / ppaf24->channels) ; + ppaf24->samples [k] = (cptr [0] << 8) | (cptr [1] << 16) | (cptr [2] << 24) ; + } ; + } ; + + return 1 ; +} /* paf24_read_block */ + +static int +paf24_read (SF_PRIVATE *psf, PAF24_PRIVATE *ppaf24, int *ptr, int len) +{ int count, total = 0 ; + + while (total < len) + { if (ppaf24->read_block * ppaf24->samplesperblock >= ppaf24->sample_count) + { memset (&(ptr [total]), 0, (len - total) * sizeof (int)) ; + return total ; + } ; + + if (ppaf24->read_count >= ppaf24->samplesperblock) + paf24_read_block (psf, ppaf24) ; + + count = (ppaf24->samplesperblock - ppaf24->read_count) * ppaf24->channels ; + count = (len - total > count) ? count : len - total ; + + memcpy (&(ptr [total]), &(ppaf24->samples [ppaf24->read_count * ppaf24->channels]), count * sizeof (int)) ; + total += count ; + ppaf24->read_count += count / ppaf24->channels ; + } ; + + return total ; +} /* paf24_read */ + +static sf_count_t +paf24_read_s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ PAF24_PRIVATE *ppaf24 ; + int *iptr ; + int k, bufferlen, readcount, count ; + sf_count_t total = 0 ; + + if (psf->fdata == NULL) + return 0 ; + ppaf24 = (PAF24_PRIVATE*) psf->fdata ; + + iptr = psf->u.ibuf ; + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : len ; + count = paf24_read (psf, ppaf24, iptr, readcount) ; + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = iptr [k] >> 16 ; + total += count ; + len -= readcount ; + } ; + return total ; +} /* paf24_read_s */ + +static sf_count_t +paf24_read_i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ PAF24_PRIVATE *ppaf24 ; + int total ; + + if (psf->fdata == NULL) + return 0 ; + ppaf24 = (PAF24_PRIVATE*) psf->fdata ; + + total = paf24_read (psf, ppaf24, ptr, len) ; + + return total ; +} /* paf24_read_i */ + +static sf_count_t +paf24_read_f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ PAF24_PRIVATE *ppaf24 ; + int *iptr ; + int k, bufferlen, readcount, count ; + sf_count_t total = 0 ; + float normfact ; + + if (psf->fdata == NULL) + return 0 ; + ppaf24 = (PAF24_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_float == SF_TRUE) ? (1.0 / 0x80000000) : (1.0 / 0x100) ; + + iptr = psf->u.ibuf ; + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : len ; + count = paf24_read (psf, ppaf24, iptr, readcount) ; + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = normfact * iptr [k] ; + total += count ; + len -= readcount ; + } ; + return total ; +} /* paf24_read_f */ + +static sf_count_t +paf24_read_d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ PAF24_PRIVATE *ppaf24 ; + int *iptr ; + int k, bufferlen, readcount, count ; + sf_count_t total = 0 ; + double normfact ; + + if (psf->fdata == NULL) + return 0 ; + ppaf24 = (PAF24_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_double == SF_TRUE) ? (1.0 / 0x80000000) : (1.0 / 0x100) ; + + iptr = psf->u.ibuf ; + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : len ; + count = paf24_read (psf, ppaf24, iptr, readcount) ; + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = normfact * iptr [k] ; + total += count ; + len -= readcount ; + } ; + return total ; +} /* paf24_read_d */ + +/*--------------------------------------------------------------------------- +*/ + +static int +paf24_write_block (SF_PRIVATE *psf, PAF24_PRIVATE *ppaf24) +{ int k, nextsample, channel ; + unsigned char *cptr ; + + /* First pack block. */ + + if (CPU_IS_LITTLE_ENDIAN) + { for (k = 0 ; k < PAF24_SAMPLES_PER_BLOCK * ppaf24->channels ; k++) + { channel = k % ppaf24->channels ; + cptr = ppaf24->block + PAF24_BLOCK_SIZE * channel + 3 * (k / ppaf24->channels) ; + nextsample = ppaf24->samples [k] >> 8 ; + cptr [0] = nextsample ; + cptr [1] = nextsample >> 8 ; + cptr [2] = nextsample >> 16 ; + } ; + + /* Do endian swapping if necessary. */ + if (psf->endian == SF_ENDIAN_BIG) + endswap_int_array (ppaf24->data, 8 * ppaf24->channels) ; + } + else if (CPU_IS_BIG_ENDIAN) + { /* This is correct. */ + for (k = 0 ; k < PAF24_SAMPLES_PER_BLOCK * ppaf24->channels ; k++) + { channel = k % ppaf24->channels ; + cptr = ppaf24->block + PAF24_BLOCK_SIZE * channel + 3 * (k / ppaf24->channels) ; + nextsample = ppaf24->samples [k] >> 8 ; + cptr [0] = nextsample ; + cptr [1] = nextsample >> 8 ; + cptr [2] = nextsample >> 16 ; + } ; + if (psf->endian == SF_ENDIAN_BIG) + endswap_int_array (ppaf24->data, 8 * ppaf24->channels) ; + } ; + + /* Write block to disk. */ + if ((k = psf_fwrite (ppaf24->block, 1, ppaf24->blocksize, psf)) != ppaf24->blocksize) + psf_log_printf (psf, "*** Warning : short write (%d != %d).\n", k, ppaf24->blocksize) ; + + if (ppaf24->sample_count < ppaf24->write_block * ppaf24->samplesperblock + ppaf24->write_count) + ppaf24->sample_count = ppaf24->write_block * ppaf24->samplesperblock + ppaf24->write_count ; + + if (ppaf24->write_count == ppaf24->samplesperblock) + { ppaf24->write_block ++ ; + ppaf24->write_count = 0 ; + } ; + + return 1 ; +} /* paf24_write_block */ + +static int +paf24_write (SF_PRIVATE *psf, PAF24_PRIVATE *ppaf24, const int *ptr, int len) +{ int count, total = 0 ; + + while (total < len) + { count = (ppaf24->samplesperblock - ppaf24->write_count) * ppaf24->channels ; + + if (count > len - total) + count = len - total ; + + memcpy (&(ppaf24->samples [ppaf24->write_count * ppaf24->channels]), &(ptr [total]), count * sizeof (int)) ; + total += count ; + ppaf24->write_count += count / ppaf24->channels ; + + if (ppaf24->write_count >= ppaf24->samplesperblock) + paf24_write_block (psf, ppaf24) ; + } ; + + return total ; +} /* paf24_write */ + +static sf_count_t +paf24_write_s (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ PAF24_PRIVATE *ppaf24 ; + int *iptr ; + int k, bufferlen, writecount = 0, count ; + sf_count_t total = 0 ; + + if (psf->fdata == NULL) + return 0 ; + ppaf24 = (PAF24_PRIVATE*) psf->fdata ; + + iptr = psf->u.ibuf ; + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : len ; + for (k = 0 ; k < writecount ; k++) + iptr [k] = ptr [total + k] << 16 ; + count = paf24_write (psf, ppaf24, iptr, writecount) ; + total += count ; + len -= writecount ; + if (count != writecount) + break ; + } ; + return total ; +} /* paf24_write_s */ + +static sf_count_t +paf24_write_i (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ PAF24_PRIVATE *ppaf24 ; + int writecount, count ; + sf_count_t total = 0 ; + + if (psf->fdata == NULL) + return 0 ; + ppaf24 = (PAF24_PRIVATE*) psf->fdata ; + + while (len > 0) + { writecount = (len > 0x10000000) ? 0x10000000 : (int) len ; + + count = paf24_write (psf, ppaf24, ptr, writecount) ; + + total += count ; + len -= count ; + if (count != writecount) + break ; + } ; + + return total ; +} /* paf24_write_i */ + +static sf_count_t +paf24_write_f (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ PAF24_PRIVATE *ppaf24 ; + int *iptr ; + int k, bufferlen, writecount = 0, count ; + sf_count_t total = 0 ; + float normfact ; + + if (psf->fdata == NULL) + return 0 ; + ppaf24 = (PAF24_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_float == SF_TRUE) ? (1.0 * 0x7FFFFFFF) : (1.0 / 0x100) ; + + iptr = psf->u.ibuf ; + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : len ; + for (k = 0 ; k < writecount ; k++) + iptr [k] = lrintf (normfact * ptr [total + k]) ; + count = paf24_write (psf, ppaf24, iptr, writecount) ; + total += count ; + len -= writecount ; + if (count != writecount) + break ; + } ; + + return total ; +} /* paf24_write_f */ + +static sf_count_t +paf24_write_d (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ PAF24_PRIVATE *ppaf24 ; + int *iptr ; + int k, bufferlen, writecount = 0, count ; + sf_count_t total = 0 ; + double normfact ; + + if (psf->fdata == NULL) + return 0 ; + ppaf24 = (PAF24_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_double == SF_TRUE) ? (1.0 * 0x7FFFFFFF) : (1.0 / 0x100) ; + + iptr = psf->u.ibuf ; + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : len ; + for (k = 0 ; k < writecount ; k++) + iptr [k] = lrint (normfact * ptr [total+k]) ; + count = paf24_write (psf, ppaf24, iptr, writecount) ; + total += count ; + len -= writecount ; + if (count != writecount) + break ; + } ; + + return total ; +} /* paf24_write_d */ + + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 477a5308-451e-4bbd-bab4-fab6caa4e884 +*/ diff --git a/libs/libsndfile/src/pcm.c b/libs/libsndfile/src/pcm.c new file mode 100644 index 0000000000..bad607c165 --- /dev/null +++ b/libs/libsndfile/src/pcm.c @@ -0,0 +1,2899 @@ +/* +** Copyright (C) 1999-2005 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include "sndfile.h" +#include "sfendian.h" +#include "float_cast.h" +#include "common.h" + +/* Need to be able to handle 3 byte (24 bit) integers. So defined a +** type and use SIZEOF_TRIBYTE instead of (tribyte). +*/ + +typedef void tribyte ; + +#define SIZEOF_TRIBYTE 3 + +static sf_count_t pcm_read_sc2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t pcm_read_uc2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t pcm_read_bes2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t pcm_read_les2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t pcm_read_bet2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t pcm_read_let2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t pcm_read_bei2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t pcm_read_lei2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; + +static sf_count_t pcm_read_sc2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t pcm_read_uc2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t pcm_read_bes2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t pcm_read_les2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t pcm_read_bet2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t pcm_read_let2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t pcm_read_bei2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t pcm_read_lei2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; + +static sf_count_t pcm_read_sc2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t pcm_read_uc2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t pcm_read_bes2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t pcm_read_les2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t pcm_read_bet2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t pcm_read_let2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t pcm_read_bei2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t pcm_read_lei2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; + +static sf_count_t pcm_read_sc2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; +static sf_count_t pcm_read_uc2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; +static sf_count_t pcm_read_bes2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; +static sf_count_t pcm_read_les2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; +static sf_count_t pcm_read_bet2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; +static sf_count_t pcm_read_let2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; +static sf_count_t pcm_read_bei2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; +static sf_count_t pcm_read_lei2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; + +static sf_count_t pcm_write_s2sc (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t pcm_write_s2uc (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t pcm_write_s2bes (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t pcm_write_s2les (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t pcm_write_s2bet (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t pcm_write_s2let (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t pcm_write_s2bei (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t pcm_write_s2lei (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; + +static sf_count_t pcm_write_i2sc (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t pcm_write_i2uc (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t pcm_write_i2bes (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t pcm_write_i2les (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t pcm_write_i2bet (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t pcm_write_i2let (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t pcm_write_i2bei (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t pcm_write_i2lei (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; + +static sf_count_t pcm_write_f2sc (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t pcm_write_f2uc (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t pcm_write_f2bes (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t pcm_write_f2les (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t pcm_write_f2bet (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t pcm_write_f2let (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t pcm_write_f2bei (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t pcm_write_f2lei (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; + +static sf_count_t pcm_write_d2sc (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; +static sf_count_t pcm_write_d2uc (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; +static sf_count_t pcm_write_d2bes (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; +static sf_count_t pcm_write_d2les (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; +static sf_count_t pcm_write_d2bet (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; +static sf_count_t pcm_write_d2let (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; +static sf_count_t pcm_write_d2bei (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; +static sf_count_t pcm_write_d2lei (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; + +/*----------------------------------------------------------------------------------------------- +*/ + +enum +{ /* Char type for 8 bit files. */ + SF_CHARS_SIGNED = 200, + SF_CHARS_UNSIGNED = 201 +} ; + +/*----------------------------------------------------------------------------------------------- +*/ + +int +pcm_init (SF_PRIVATE *psf) +{ int chars = 0 ; + + if (psf->bytewidth == 0 || psf->sf.channels == 0) + return SFE_INTERNAL ; + + psf->blockwidth = psf->bytewidth * psf->sf.channels ; + + if ((psf->sf.format & SF_FORMAT_SUBMASK) == SF_FORMAT_PCM_S8) + chars = SF_CHARS_SIGNED ; + else if ((psf->sf.format & SF_FORMAT_SUBMASK) == SF_FORMAT_PCM_U8) + chars = SF_CHARS_UNSIGNED ; + + if (psf->mode == SFM_READ || psf->mode == SFM_RDWR) + { switch (psf->bytewidth * 0x10000 + psf->endian + chars) + { case (0x10000 + SF_ENDIAN_BIG + SF_CHARS_SIGNED) : + case (0x10000 + SF_ENDIAN_LITTLE + SF_CHARS_SIGNED) : + psf->read_short = pcm_read_sc2s ; + psf->read_int = pcm_read_sc2i ; + psf->read_float = pcm_read_sc2f ; + psf->read_double = pcm_read_sc2d ; + break ; + case (0x10000 + SF_ENDIAN_BIG + SF_CHARS_UNSIGNED) : + case (0x10000 + SF_ENDIAN_LITTLE + SF_CHARS_UNSIGNED) : + psf->read_short = pcm_read_uc2s ; + psf->read_int = pcm_read_uc2i ; + psf->read_float = pcm_read_uc2f ; + psf->read_double = pcm_read_uc2d ; + break ; + + case (2 * 0x10000 + SF_ENDIAN_BIG) : + psf->read_short = pcm_read_bes2s ; + psf->read_int = pcm_read_bes2i ; + psf->read_float = pcm_read_bes2f ; + psf->read_double = pcm_read_bes2d ; + break ; + case (3 * 0x10000 + SF_ENDIAN_BIG) : + psf->read_short = pcm_read_bet2s ; + psf->read_int = pcm_read_bet2i ; + psf->read_float = pcm_read_bet2f ; + psf->read_double = pcm_read_bet2d ; + break ; + case (4 * 0x10000 + SF_ENDIAN_BIG) : + psf->read_short = pcm_read_bei2s ; + psf->read_int = pcm_read_bei2i ; + psf->read_float = pcm_read_bei2f ; + psf->read_double = pcm_read_bei2d ; + break ; + + case (2 * 0x10000 + SF_ENDIAN_LITTLE) : + psf->read_short = pcm_read_les2s ; + psf->read_int = pcm_read_les2i ; + psf->read_float = pcm_read_les2f ; + psf->read_double = pcm_read_les2d ; + break ; + case (3 * 0x10000 + SF_ENDIAN_LITTLE) : + psf->read_short = pcm_read_let2s ; + psf->read_int = pcm_read_let2i ; + psf->read_float = pcm_read_let2f ; + psf->read_double = pcm_read_let2d ; + break ; + case (4 * 0x10000 + SF_ENDIAN_LITTLE) : + psf->read_short = pcm_read_lei2s ; + psf->read_int = pcm_read_lei2i ; + psf->read_float = pcm_read_lei2f ; + psf->read_double = pcm_read_lei2d ; + break ; + default : + psf_log_printf (psf, "pcm.c returning SFE_UNIMPLEMENTED\n") ; + return SFE_UNIMPLEMENTED ; + } ; + } ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { switch (psf->bytewidth * 0x10000 + psf->endian + chars) + { case (0x10000 + SF_ENDIAN_BIG + SF_CHARS_SIGNED) : + case (0x10000 + SF_ENDIAN_LITTLE + SF_CHARS_SIGNED) : + psf->write_short = pcm_write_s2sc ; + psf->write_int = pcm_write_i2sc ; + psf->write_float = pcm_write_f2sc ; + psf->write_double = pcm_write_d2sc ; + break ; + case (0x10000 + SF_ENDIAN_BIG + SF_CHARS_UNSIGNED) : + case (0x10000 + SF_ENDIAN_LITTLE + SF_CHARS_UNSIGNED) : + psf->write_short = pcm_write_s2uc ; + psf->write_int = pcm_write_i2uc ; + psf->write_float = pcm_write_f2uc ; + psf->write_double = pcm_write_d2uc ; + break ; + + case (2 * 0x10000 + SF_ENDIAN_BIG) : + psf->write_short = pcm_write_s2bes ; + psf->write_int = pcm_write_i2bes ; + psf->write_float = pcm_write_f2bes ; + psf->write_double = pcm_write_d2bes ; + break ; + + case (3 * 0x10000 + SF_ENDIAN_BIG) : + psf->write_short = pcm_write_s2bet ; + psf->write_int = pcm_write_i2bet ; + psf->write_float = pcm_write_f2bet ; + psf->write_double = pcm_write_d2bet ; + break ; + + case (4 * 0x10000 + SF_ENDIAN_BIG) : + psf->write_short = pcm_write_s2bei ; + psf->write_int = pcm_write_i2bei ; + psf->write_float = pcm_write_f2bei ; + psf->write_double = pcm_write_d2bei ; + break ; + + case (2 * 0x10000 + SF_ENDIAN_LITTLE) : + psf->write_short = pcm_write_s2les ; + psf->write_int = pcm_write_i2les ; + psf->write_float = pcm_write_f2les ; + psf->write_double = pcm_write_d2les ; + break ; + + case (3 * 0x10000 + SF_ENDIAN_LITTLE) : + psf->write_short = pcm_write_s2let ; + psf->write_int = pcm_write_i2let ; + psf->write_float = pcm_write_f2let ; + psf->write_double = pcm_write_d2let ; + break ; + + case (4 * 0x10000 + SF_ENDIAN_LITTLE) : + psf->write_short = pcm_write_s2lei ; + psf->write_int = pcm_write_i2lei ; + psf->write_float = pcm_write_f2lei ; + psf->write_double = pcm_write_d2lei ; + break ; + + default : + psf_log_printf (psf, "pcm.c returning SFE_UNIMPLEMENTED\n") ; + return SFE_UNIMPLEMENTED ; + } ; + + } ; + + if (psf->filelength > psf->dataoffset) + { psf->datalength = (psf->dataend > 0) ? psf->dataend - psf->dataoffset : + psf->filelength - psf->dataoffset ; + } + else + psf->datalength = 0 ; + + psf->sf.frames = psf->datalength / psf->blockwidth ; + + return 0 ; +} /* pcm_init */ + +/*============================================================================== +*/ + +static inline void +sc2s_array (signed char *src, int count, short *dest) +{ while (--count >= 0) + { dest [count] = src [count] << 8 ; + } ; +} /* sc2s_array */ + +static inline void +uc2s_array (unsigned char *src, int count, short *dest) +{ while (--count >= 0) + { dest [count] = (((short) src [count]) - 0x80) << 8 ; + } ; +} /* uc2s_array */ + +static inline void +let2s_array (tribyte *src, int count, short *dest) +{ unsigned char *ucptr ; + + ucptr = ((unsigned char*) src) + 3 * count ; + while (--count >= 0) + { ucptr -= 3 ; + dest [count] = LET2H_SHORT_PTR (ucptr) ; + } ; +} /* let2s_array */ + +static inline void +bet2s_array (tribyte *src, int count, short *dest) +{ unsigned char *ucptr ; + + ucptr = ((unsigned char*) src) + 3 * count ; + while (--count >= 0) + { ucptr -= 3 ; + dest [count] = BET2H_SHORT_PTR (ucptr) ; + } ; +} /* bet2s_array */ + +static inline void +lei2s_array (int *src, int count, short *dest) +{ int value ; + + while (--count >= 0) + { value = LEI2H_INT (src [count]) ; + dest [count] = value >> 16 ; + } ; +} /* lei2s_array */ + +static inline void +bei2s_array (int *src, int count, short *dest) +{ int value ; + + while (--count >= 0) + { value = BEI2H_INT (src [count]) ; + dest [count] = value >> 16 ; + } ; +} /* bei2s_array */ + +/*-------------------------------------------------------------------------- +*/ + +static inline void +sc2i_array (signed char *src, int count, int *dest) +{ while (--count >= 0) + { dest [count] = ((int) src [count]) << 24 ; + } ; +} /* sc2i_array */ + +static inline void +uc2i_array (unsigned char *src, int count, int *dest) +{ while (--count >= 0) + { dest [count] = (((int) src [count]) - 128) << 24 ; + } ; +} /* uc2i_array */ + +static inline void +bes2i_array (short *src, int count, int *dest) +{ short value ; + + while (--count >= 0) + { value = BES2H_SHORT (src [count]) ; + dest [count] = value << 16 ; + } ; +} /* bes2i_array */ + +static inline void +les2i_array (short *src, int count, int *dest) +{ short value ; + + while (--count >= 0) + { value = LES2H_SHORT (src [count]) ; + dest [count] = value << 16 ; + } ; +} /* les2i_array */ + +static inline void +bet2i_array (tribyte *src, int count, int *dest) +{ unsigned char *ucptr ; + + ucptr = ((unsigned char*) src) + 3 * count ; + while (--count >= 0) + { ucptr -= 3 ; + dest [count] = BET2H_INT_PTR (ucptr) ; + } ; +} /* bet2i_array */ + +static inline void +let2i_array (tribyte *src, int count, int *dest) +{ unsigned char *ucptr ; + + ucptr = ((unsigned char*) src) + 3 * count ; + while (--count >= 0) + { ucptr -= 3 ; + dest [count] = LET2H_INT_PTR (ucptr) ; + } ; +} /* let2i_array */ + +/*-------------------------------------------------------------------------- +*/ + +static inline void +sc2f_array (signed char *src, int count, float *dest, float normfact) +{ while (--count >= 0) + dest [count] = ((float) src [count]) * normfact ; +} /* sc2f_array */ + +static inline void +uc2f_array (unsigned char *src, int count, float *dest, float normfact) +{ while (--count >= 0) + dest [count] = (((int) src [count]) - 128) * normfact ; +} /* uc2f_array */ + +static inline void +les2f_array (short *src, int count, float *dest, float normfact) +{ short value ; + + while (--count >= 0) + { value = src [count] ; + value = LES2H_SHORT (value) ; + dest [count] = ((float) value) * normfact ; + } ; +} /* les2f_array */ + +static inline void +bes2f_array (short *src, int count, float *dest, float normfact) +{ short value ; + + while (--count >= 0) + { value = src [count] ; + value = BES2H_SHORT (value) ; + dest [count] = ((float) value) * normfact ; + } ; +} /* bes2f_array */ + +static inline void +let2f_array (tribyte *src, int count, float *dest, float normfact) +{ unsigned char *ucptr ; + int value ; + + ucptr = ((unsigned char*) src) + 3 * count ; + while (--count >= 0) + { ucptr -= 3 ; + value = LET2H_INT_PTR (ucptr) ; + dest [count] = ((float) value) * normfact ; + } ; +} /* let2f_array */ + +static inline void +bet2f_array (tribyte *src, int count, float *dest, float normfact) +{ unsigned char *ucptr ; + int value ; + + ucptr = ((unsigned char*) src) + 3 * count ; + while (--count >= 0) + { ucptr -= 3 ; + value = BET2H_INT_PTR (ucptr) ; + dest [count] = ((float) value) * normfact ; + } ; +} /* bet2f_array */ + +static inline void +lei2f_array (int *src, int count, float *dest, float normfact) +{ int value ; + + while (--count >= 0) + { value = src [count] ; + value = LEI2H_INT (value) ; + dest [count] = ((float) value) * normfact ; + } ; +} /* lei2f_array */ + +static inline void +bei2f_array (int *src, int count, float *dest, float normfact) +{ int value ; + + while (--count >= 0) + { value = src [count] ; + value = BEI2H_INT (value) ; + dest [count] = ((float) value) * normfact ; + } ; +} /* bei2f_array */ + +/*-------------------------------------------------------------------------- +*/ + +static inline void +sc2d_array (signed char *src, int count, double *dest, double normfact) +{ while (--count >= 0) + dest [count] = ((double) src [count]) * normfact ; +} /* sc2d_array */ + +static inline void +uc2d_array (unsigned char *src, int count, double *dest, double normfact) +{ while (--count >= 0) + dest [count] = (((int) src [count]) - 128) * normfact ; +} /* uc2d_array */ + +static inline void +les2d_array (short *src, int count, double *dest, double normfact) +{ short value ; + + while (--count >= 0) + { value = src [count] ; + value = LES2H_SHORT (value) ; + dest [count] = ((double) value) * normfact ; + } ; +} /* les2d_array */ + +static inline void +bes2d_array (short *src, int count, double *dest, double normfact) +{ short value ; + + while (--count >= 0) + { value = src [count] ; + value = BES2H_SHORT (value) ; + dest [count] = ((double) value) * normfact ; + } ; +} /* bes2d_array */ + +static inline void +let2d_array (tribyte *src, int count, double *dest, double normfact) +{ unsigned char *ucptr ; + int value ; + + ucptr = ((unsigned char*) src) + 3 * count ; + while (--count >= 0) + { ucptr -= 3 ; + value = LET2H_INT_PTR (ucptr) ; + dest [count] = ((double) value) * normfact ; + } ; +} /* let2d_array */ + +static inline void +bet2d_array (tribyte *src, int count, double *dest, double normfact) +{ unsigned char *ucptr ; + int value ; + + ucptr = ((unsigned char*) src) + 3 * count ; + while (--count >= 0) + { ucptr -= 3 ; + value = (ucptr [0] << 24) | (ucptr [1] << 16) | (ucptr [2] << 8) ; + dest [count] = ((double) value) * normfact ; + } ; +} /* bet2d_array */ + +static inline void +lei2d_array (int *src, int count, double *dest, double normfact) +{ int value ; + + while (--count >= 0) + { value = src [count] ; + value = LEI2H_INT (value) ; + dest [count] = ((double) value) * normfact ; + } ; +} /* lei2d_array */ + +static inline void +bei2d_array (int *src, int count, double *dest, double normfact) +{ int value ; + + while (--count >= 0) + { value = src [count] ; + value = BEI2H_INT (value) ; + dest [count] = ((double) value) * normfact ; + } ; +} /* bei2d_array */ + +/*-------------------------------------------------------------------------- +*/ + +static inline void +s2sc_array (const short *src, signed char *dest, int count) +{ while (--count >= 0) + dest [count] = src [count] >> 8 ; +} /* s2sc_array */ + +static inline void +s2uc_array (const short *src, unsigned char *dest, int count) +{ while (--count >= 0) + dest [count] = (src [count] >> 8) + 0x80 ; +} /* s2uc_array */ + +static inline void +s2let_array (const short *src, tribyte *dest, int count) +{ unsigned char *ucptr ; + + ucptr = ((unsigned char*) dest) + 3 * count ; + while (--count >= 0) + { ucptr -= 3 ; + ucptr [0] = 0 ; + ucptr [1] = src [count] ; + ucptr [2] = src [count] >> 8 ; + } ; +} /* s2let_array */ + +static inline void +s2bet_array (const short *src, tribyte *dest, int count) +{ unsigned char *ucptr ; + + ucptr = ((unsigned char*) dest) + 3 * count ; + while (--count >= 0) + { ucptr -= 3 ; + ucptr [2] = 0 ; + ucptr [1] = src [count] ; + ucptr [0] = src [count] >> 8 ; + } ; +} /* s2bet_array */ + +static inline void +s2lei_array (const short *src, int *dest, int count) +{ unsigned char *ucptr ; + + ucptr = ((unsigned char*) dest) + 4 * count ; + while (--count >= 0) + { ucptr -= 4 ; + ucptr [0] = 0 ; + ucptr [1] = 0 ; + ucptr [2] = src [count] ; + ucptr [3] = src [count] >> 8 ; + } ; +} /* s2lei_array */ + +static inline void +s2bei_array (const short *src, int *dest, int count) +{ unsigned char *ucptr ; + + ucptr = ((unsigned char*) dest) + 4 * count ; + while (--count >= 0) + { ucptr -= 4 ; + ucptr [0] = src [count] >> 8 ; + ucptr [1] = src [count] ; + ucptr [2] = 0 ; + ucptr [3] = 0 ; + } ; +} /* s2bei_array */ + +/*-------------------------------------------------------------------------- +*/ + +static inline void +i2sc_array (const int *src, signed char *dest, int count) +{ while (--count >= 0) + dest [count] = (src [count] >> 24) ; +} /* i2sc_array */ + +static inline void +i2uc_array (const int *src, unsigned char *dest, int count) +{ while (--count >= 0) + dest [count] = ((src [count] >> 24) + 128) ; +} /* i2uc_array */ + +static inline void +i2bes_array (const int *src, short *dest, int count) +{ unsigned char *ucptr ; + + ucptr = ((unsigned char*) dest) + 2 * count ; + while (--count >= 0) + { ucptr -= 2 ; + ucptr [0] = src [count] >> 24 ; + ucptr [1] = src [count] >> 16 ; + } ; +} /* i2bes_array */ + +static inline void +i2les_array (const int *src, short *dest, int count) +{ unsigned char *ucptr ; + + ucptr = ((unsigned char*) dest) + 2 * count ; + while (--count >= 0) + { ucptr -= 2 ; + ucptr [0] = src [count] >> 16 ; + ucptr [1] = src [count] >> 24 ; + } ; +} /* i2les_array */ + +static inline void +i2let_array (const int *src, tribyte *dest, int count) +{ unsigned char *ucptr ; + int value ; + + ucptr = ((unsigned char*) dest) + 3 * count ; + while (--count >= 0) + { ucptr -= 3 ; + value = src [count] >> 8 ; + ucptr [0] = value ; + ucptr [1] = value >> 8 ; + ucptr [2] = value >> 16 ; + } ; +} /* i2let_array */ + +static inline void +i2bet_array (const int *src, tribyte *dest, int count) +{ unsigned char *ucptr ; + int value ; + + ucptr = ((unsigned char*) dest) + 3 * count ; + while (--count >= 0) + { ucptr -= 3 ; + value = src [count] >> 8 ; + ucptr [2] = value ; + ucptr [1] = value >> 8 ; + ucptr [0] = value >> 16 ; + } ; +} /* i2bet_array */ + +/*=============================================================================================== +*/ + +static sf_count_t +pcm_read_sc2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.scbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.scbuf, sizeof (signed char), bufferlen, psf) ; + sc2s_array (psf->u.scbuf, readcount, ptr + total) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_sc2s */ + +static sf_count_t +pcm_read_uc2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ucbuf, sizeof (unsigned char), bufferlen, psf) ; + uc2s_array (psf->u.ucbuf, readcount, ptr + total) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_uc2s */ + +static sf_count_t +pcm_read_bes2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ int total ; + + total = psf_fread (ptr, sizeof (short), len, psf) ; + if (CPU_IS_LITTLE_ENDIAN) + endswap_short_array (ptr, len) ; + + return total ; +} /* pcm_read_bes2s */ + +static sf_count_t +pcm_read_les2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ int total ; + + total = psf_fread (ptr, sizeof (short), len, psf) ; + if (CPU_IS_BIG_ENDIAN) + endswap_short_array (ptr, len) ; + + return total ; +} /* pcm_read_les2s */ + +static sf_count_t +pcm_read_bet2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + + bufferlen = sizeof (psf->u.ucbuf) / SIZEOF_TRIBYTE ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ucbuf, SIZEOF_TRIBYTE, bufferlen, psf) ; + bet2s_array ((tribyte*) (psf->u.ucbuf), readcount, ptr + total) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_bet2s */ + +static sf_count_t +pcm_read_let2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + + bufferlen = sizeof (psf->u.ucbuf) / SIZEOF_TRIBYTE ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ucbuf, SIZEOF_TRIBYTE, bufferlen, psf) ; + let2s_array ((tribyte*) (psf->u.ucbuf), readcount, ptr + total) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_let2s */ + +static sf_count_t +pcm_read_bei2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ibuf, sizeof (int), bufferlen, psf) ; + bei2s_array (psf->u.ibuf, readcount, ptr + total) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_bei2s */ + +static sf_count_t +pcm_read_lei2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ibuf, sizeof (int), bufferlen, psf) ; + lei2s_array (psf->u.ibuf, readcount, ptr + total) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_lei2s */ + +/*----------------------------------------------------------------------------------------------- +*/ + +static sf_count_t +pcm_read_sc2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.scbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.scbuf, sizeof (signed char), bufferlen, psf) ; + sc2i_array (psf->u.scbuf, readcount, ptr + total) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_sc2i */ + +static sf_count_t +pcm_read_uc2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ucbuf, sizeof (unsigned char), bufferlen, psf) ; + uc2i_array (psf->u.ucbuf, readcount, ptr + total) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_uc2i */ + +static sf_count_t +pcm_read_bes2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.sbuf, sizeof (short), bufferlen, psf) ; + bes2i_array (psf->u.sbuf, readcount, ptr + total) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_bes2i */ + +static sf_count_t +pcm_read_les2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.sbuf, sizeof (short), bufferlen, psf) ; + les2i_array (psf->u.sbuf, readcount, ptr + total) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_les2i */ + +static sf_count_t +pcm_read_bet2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + + bufferlen = sizeof (psf->u.ucbuf) / SIZEOF_TRIBYTE ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ucbuf, SIZEOF_TRIBYTE, bufferlen, psf) ; + bet2i_array ((tribyte*) (psf->u.ucbuf), readcount, ptr + total) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_bet2i */ + +static sf_count_t +pcm_read_let2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + + bufferlen = sizeof (psf->u.ucbuf) / SIZEOF_TRIBYTE ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ucbuf, SIZEOF_TRIBYTE, bufferlen, psf) ; + let2i_array ((tribyte*) (psf->u.ucbuf), readcount, ptr + total) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_let2i */ + +static sf_count_t +pcm_read_bei2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ int total ; + + total = psf_fread (ptr, sizeof (int), len, psf) ; + if (CPU_IS_LITTLE_ENDIAN) + endswap_int_array (ptr, len) ; + + return total ; +} /* pcm_read_bei2i */ + +static sf_count_t +pcm_read_lei2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ int total ; + + total = psf_fread (ptr, sizeof (int), len, psf) ; + if (CPU_IS_BIG_ENDIAN) + endswap_int_array (ptr, len) ; + + return total ; +} /* pcm_read_lei2i */ + +/*----------------------------------------------------------------------------------------------- +*/ + +static sf_count_t +pcm_read_sc2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + float normfact ; + + normfact = (psf->norm_float == SF_TRUE) ? 1.0 / ((float) 0x80) : 1.0 ; + + bufferlen = ARRAY_LEN (psf->u.scbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.scbuf, sizeof (signed char), bufferlen, psf) ; + sc2f_array (psf->u.scbuf, readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_sc2f */ + +static sf_count_t +pcm_read_uc2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + float normfact ; + + normfact = (psf->norm_float == SF_TRUE) ? 1.0 / ((float) 0x80) : 1.0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ucbuf, sizeof (unsigned char), bufferlen, psf) ; + uc2f_array (psf->u.ucbuf, readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_uc2f */ + +static sf_count_t +pcm_read_bes2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + float normfact ; + + normfact = (psf->norm_float == SF_TRUE) ? 1.0 / ((float) 0x8000) : 1.0 ; + + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.sbuf, sizeof (short), bufferlen, psf) ; + bes2f_array (psf->u.sbuf, readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_bes2f */ + +static sf_count_t +pcm_read_les2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + float normfact ; + + normfact = (psf->norm_float == SF_TRUE) ? 1.0 / ((float) 0x8000) : 1.0 ; + + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.sbuf, sizeof (short), bufferlen, psf) ; + les2f_array (psf->u.sbuf, readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_les2f */ + +static sf_count_t +pcm_read_bet2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + float normfact ; + + /* Special normfactor because tribyte value is read into an int. */ + normfact = (psf->norm_float == SF_TRUE) ? 1.0 / ((float) 0x80000000) : 1.0 / 256.0 ; + + bufferlen = sizeof (psf->u.ucbuf) / SIZEOF_TRIBYTE ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ucbuf, SIZEOF_TRIBYTE, bufferlen, psf) ; + bet2f_array ((tribyte*) (psf->u.ucbuf), readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_bet2f */ + +static sf_count_t +pcm_read_let2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + float normfact ; + + /* Special normfactor because tribyte value is read into an int. */ + normfact = (psf->norm_float == SF_TRUE) ? 1.0 / ((float) 0x80000000) : 1.0 / 256.0 ; + + bufferlen = sizeof (psf->u.ucbuf) / SIZEOF_TRIBYTE ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ucbuf, SIZEOF_TRIBYTE, bufferlen, psf) ; + let2f_array ((tribyte*) (psf->u.ucbuf), readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_let2f */ + +static sf_count_t +pcm_read_bei2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + float normfact ; + + normfact = (psf->norm_float == SF_TRUE) ? 1.0 / ((float) 0x80000000) : 1.0 ; + + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ibuf, sizeof (int), bufferlen, psf) ; + bei2f_array (psf->u.ibuf, readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_bei2f */ + +static sf_count_t +pcm_read_lei2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + float normfact ; + + normfact = (psf->norm_float == SF_TRUE) ? 1.0 / ((float) 0x80000000) : 1.0 ; + + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ibuf, sizeof (int), bufferlen, psf) ; + lei2f_array (psf->u.ibuf, readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_lei2f */ + +/*----------------------------------------------------------------------------------------------- +*/ + +static sf_count_t +pcm_read_sc2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + double normfact ; + + normfact = (psf->norm_double == SF_TRUE) ? 1.0 / ((double) 0x80) : 1.0 ; + + bufferlen = ARRAY_LEN (psf->u.scbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.scbuf, sizeof (signed char), bufferlen, psf) ; + sc2d_array (psf->u.scbuf, readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_sc2d */ + +static sf_count_t +pcm_read_uc2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + double normfact ; + + normfact = (psf->norm_double == SF_TRUE) ? 1.0 / ((double) 0x80) : 1.0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ucbuf, sizeof (unsigned char), bufferlen, psf) ; + uc2d_array (psf->u.ucbuf, readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_uc2d */ + +static sf_count_t +pcm_read_bes2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + double normfact ; + + normfact = (psf->norm_double == SF_TRUE) ? 1.0 / ((double) 0x8000) : 1.0 ; + + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.sbuf, sizeof (short), bufferlen, psf) ; + bes2d_array (psf->u.sbuf, readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_bes2d */ + +static sf_count_t +pcm_read_les2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + double normfact ; + + normfact = (psf->norm_double == SF_TRUE) ? 1.0 / ((double) 0x8000) : 1.0 ; + + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.sbuf, sizeof (short), bufferlen, psf) ; + les2d_array (psf->u.sbuf, readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_les2d */ + +static sf_count_t +pcm_read_bet2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + double normfact ; + + normfact = (psf->norm_double == SF_TRUE) ? 1.0 / ((double) 0x80000000) : 1.0 / 256.0 ; + + bufferlen = sizeof (psf->u.ucbuf) / SIZEOF_TRIBYTE ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ucbuf, SIZEOF_TRIBYTE, bufferlen, psf) ; + bet2d_array ((tribyte*) (psf->u.ucbuf), readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_bet2d */ + +static sf_count_t +pcm_read_let2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + double normfact ; + + /* Special normfactor because tribyte value is read into an int. */ + normfact = (psf->norm_double == SF_TRUE) ? 1.0 / ((double) 0x80000000) : 1.0 / 256.0 ; + + bufferlen = sizeof (psf->u.ucbuf) / SIZEOF_TRIBYTE ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ucbuf, SIZEOF_TRIBYTE, bufferlen, psf) ; + let2d_array ((tribyte*) (psf->u.ucbuf), readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_let2d */ + +static sf_count_t +pcm_read_bei2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + double normfact ; + + normfact = (psf->norm_double == SF_TRUE) ? 1.0 / ((double) 0x80000000) : 1.0 ; + + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ibuf, sizeof (int), bufferlen, psf) ; + bei2d_array (psf->u.ibuf, readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_bei2d */ + +static sf_count_t +pcm_read_lei2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + double normfact ; + + normfact = (psf->norm_double == SF_TRUE) ? 1.0 / ((double) 0x80000000) : 1.0 ; + + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ibuf, sizeof (int), bufferlen, psf) ; + lei2d_array (psf->u.ibuf, readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* pcm_read_lei2d */ + +/*=============================================================================================== +**----------------------------------------------------------------------------------------------- +**=============================================================================================== +*/ + +static sf_count_t +pcm_write_s2sc (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.scbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + s2sc_array (ptr + total, psf->u.scbuf, bufferlen) ; + writecount = psf_fwrite (psf->u.scbuf, sizeof (signed char), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_s2sc */ + +static sf_count_t +pcm_write_s2uc (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + s2uc_array (ptr + total, psf->u.ucbuf, bufferlen) ; + writecount = psf_fwrite (psf->u.ucbuf, sizeof (unsigned char), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_s2uc */ + +static sf_count_t +pcm_write_s2bes (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + if (CPU_IS_BIG_ENDIAN) + return psf_fwrite (ptr, sizeof (short), len, psf) ; + else + + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + endswap_short_copy (psf->u.sbuf, ptr + total, bufferlen) ; + writecount = psf_fwrite (psf->u.sbuf, sizeof (short), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_s2bes */ + +static sf_count_t +pcm_write_s2les (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + if (CPU_IS_LITTLE_ENDIAN) + return psf_fwrite (ptr, sizeof (short), len, psf) ; + + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + endswap_short_copy (psf->u.sbuf, ptr + total, bufferlen) ; + writecount = psf_fwrite (psf->u.sbuf, sizeof (short), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_s2les */ + +static sf_count_t +pcm_write_s2bet (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = sizeof (psf->u.ucbuf) / SIZEOF_TRIBYTE ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + s2bet_array (ptr + total, (tribyte*) (psf->u.ucbuf), bufferlen) ; + writecount = psf_fwrite (psf->u.ucbuf, SIZEOF_TRIBYTE, bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_s2bet */ + +static sf_count_t +pcm_write_s2let (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = sizeof (psf->u.ucbuf) / SIZEOF_TRIBYTE ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + s2let_array (ptr + total, (tribyte*) (psf->u.ucbuf), bufferlen) ; + writecount = psf_fwrite (psf->u.ucbuf, SIZEOF_TRIBYTE, bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_s2let */ + +static sf_count_t +pcm_write_s2bei (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + s2bei_array (ptr + total, psf->u.ibuf, bufferlen) ; + writecount = psf_fwrite (psf->u.ibuf, sizeof (int), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_s2bei */ + +static sf_count_t +pcm_write_s2lei (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + s2lei_array (ptr + total, psf->u.ibuf, bufferlen) ; + writecount = psf_fwrite (psf->u.ibuf, sizeof (int), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_s2lei */ + +/*----------------------------------------------------------------------------------------------- +*/ + +static sf_count_t +pcm_write_i2sc (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.scbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + i2sc_array (ptr + total, psf->u.scbuf, bufferlen) ; + writecount = psf_fwrite (psf->u.scbuf, sizeof (signed char), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_i2sc */ + +static sf_count_t +pcm_write_i2uc (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + i2uc_array (ptr + total, psf->u.ucbuf, bufferlen) ; + writecount = psf_fwrite (psf->u.ucbuf, sizeof (signed char), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_i2uc */ + +static sf_count_t +pcm_write_i2bes (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + i2bes_array (ptr + total, psf->u.sbuf, bufferlen) ; + writecount = psf_fwrite (psf->u.sbuf, sizeof (short), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_i2bes */ + +static sf_count_t +pcm_write_i2les (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + i2les_array (ptr + total, psf->u.sbuf, bufferlen) ; + writecount = psf_fwrite (psf->u.sbuf, sizeof (short), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_i2les */ + +static sf_count_t +pcm_write_i2bet (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = sizeof (psf->u.ucbuf) / SIZEOF_TRIBYTE ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + i2bet_array (ptr + total, (tribyte*) (psf->u.ucbuf), bufferlen) ; + writecount = psf_fwrite (psf->u.ucbuf, SIZEOF_TRIBYTE, bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_i2bet */ + +static sf_count_t +pcm_write_i2let (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = sizeof (psf->u.ucbuf) / SIZEOF_TRIBYTE ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + i2let_array (ptr + total, (tribyte*) (psf->u.ucbuf), bufferlen) ; + writecount = psf_fwrite (psf->u.ucbuf, SIZEOF_TRIBYTE, bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_i2les */ + +static sf_count_t +pcm_write_i2bei (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + if (CPU_IS_BIG_ENDIAN) + return psf_fwrite (ptr, sizeof (int), len, psf) ; + + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + endswap_int_copy (psf->u.ibuf, ptr + total, bufferlen) ; + writecount = psf_fwrite (psf->u.ibuf, sizeof (int), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_i2bei */ + +static sf_count_t +pcm_write_i2lei (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + if (CPU_IS_LITTLE_ENDIAN) + return psf_fwrite (ptr, sizeof (int), len, psf) ; + + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + endswap_int_copy (psf->u.ibuf, ptr + total, bufferlen) ; + writecount = psf_fwrite (psf->u.ibuf, sizeof (int), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_i2lei */ + +/*------------------------------------------------------------------------------ +**============================================================================== +**------------------------------------------------------------------------------ +*/ + +static void +f2sc_array (const float *src, signed char *dest, int count, int normalize) +{ float normfact ; + + normfact = normalize ? (1.0 * 0x7F) : 1.0 ; + + while (--count >= 0) + { dest [count] = lrintf (src [count] * normfact) ; + } ; +} /* f2sc_array */ + +static void +f2sc_clip_array (const float *src, signed char *dest, int count, int normalize) +{ float normfact, scaled_value ; + + normfact = normalize ? (8.0 * 0x10000000) : (1.0 * 0x1000000) ; + + while (--count >= 0) + { scaled_value = src [count] * normfact ; + if (CPU_CLIPS_POSITIVE == 0 && scaled_value >= (1.0 * 0x7FFFFFFF)) + { dest [count] = 127 ; + continue ; + } ; + if (CPU_CLIPS_NEGATIVE == 0 && scaled_value <= (-8.0 * 0x10000000)) + { dest [count] = -128 ; + continue ; + } ; + + dest [count] = lrintf (scaled_value) >> 24 ; + } ; +} /* f2sc_clip_array */ + +static sf_count_t +pcm_write_f2sc (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ void (*convert) (const float *, signed char *, int, int) ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + + convert = (psf->add_clipping) ? f2sc_clip_array : f2sc_array ; + bufferlen = ARRAY_LEN (psf->u.scbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + convert (ptr + total, psf->u.scbuf, bufferlen, psf->norm_float) ; + writecount = psf_fwrite (psf->u.scbuf, sizeof (signed char), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_f2sc */ + +/*============================================================================== +*/ + +static void +f2uc_array (const float *src, unsigned char *dest, int count, int normalize) +{ float normfact ; + + normfact = normalize ? (1.0 * 0x7F) : 1.0 ; + + while (--count >= 0) + { dest [count] = lrintf (src [count] * normfact) + 128 ; + } ; +} /* f2uc_array */ + +static void +f2uc_clip_array (const float *src, unsigned char *dest, int count, int normalize) +{ float normfact, scaled_value ; + + normfact = normalize ? (8.0 * 0x10000000) : (1.0 * 0x1000000) ; + + while (--count >= 0) + { scaled_value = src [count] * normfact ; + if (CPU_CLIPS_POSITIVE == 0 && scaled_value >= (1.0 * 0x7FFFFFFF)) + { dest [count] = 0xFF ; + continue ; + } ; + if (CPU_CLIPS_NEGATIVE == 0 && scaled_value <= (-8.0 * 0x10000000)) + { dest [count] = 0 ; + continue ; + } ; + + dest [count] = (lrintf (scaled_value) >> 24) + 128 ; + } ; +} /* f2uc_clip_array */ + +static sf_count_t +pcm_write_f2uc (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ void (*convert) (const float *, unsigned char *, int, int) ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + + convert = (psf->add_clipping) ? f2uc_clip_array : f2uc_array ; + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + convert (ptr + total, psf->u.ucbuf, bufferlen, psf->norm_float) ; + writecount = psf_fwrite (psf->u.ucbuf, sizeof (unsigned char), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_f2uc */ + +/*============================================================================== +*/ + +static void +f2bes_array (const float *src, short *dest, int count, int normalize) +{ unsigned char *ucptr ; + float normfact ; + short value ; + + normfact = normalize ? (1.0 * 0x7FFF) : 1.0 ; + ucptr = ((unsigned char*) dest) + 2 * count ; + + while (--count >= 0) + { ucptr -= 2 ; + value = lrintf (src [count] * normfact) ; + ucptr [1] = value ; + ucptr [0] = value >> 8 ; + } ; +} /* f2bes_array */ + +static void +f2bes_clip_array (const float *src, short *dest, int count, int normalize) +{ unsigned char *ucptr ; + float normfact, scaled_value ; + int value ; + + normfact = normalize ? (8.0 * 0x10000000) : (1.0 * 0x10000) ; + ucptr = ((unsigned char*) dest) + 2 * count ; + + while (--count >= 0) + { ucptr -= 2 ; + scaled_value = src [count] * normfact ; + if (CPU_CLIPS_POSITIVE == 0 && scaled_value >= (1.0 * 0x7FFFFFFF)) + { ucptr [1] = 0xFF ; + ucptr [0] = 0x7F ; + continue ; + } ; + if (CPU_CLIPS_NEGATIVE == 0 && scaled_value <= (-8.0 * 0x10000000)) + { ucptr [1] = 0x00 ; + ucptr [0] = 0x80 ; + continue ; + } ; + + value = lrintf (scaled_value) ; + ucptr [1] = value >> 16 ; + ucptr [0] = value >> 24 ; + } ; +} /* f2bes_clip_array */ + +static sf_count_t +pcm_write_f2bes (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ void (*convert) (const float *, short *t, int, int) ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + + convert = (psf->add_clipping) ? f2bes_clip_array : f2bes_array ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + convert (ptr + total, psf->u.sbuf, bufferlen, psf->norm_float) ; + writecount = psf_fwrite (psf->u.sbuf, sizeof (short), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_f2bes */ + +/*============================================================================== +*/ + +static void +f2les_array (const float *src, short *dest, int count, int normalize) +{ unsigned char *ucptr ; + float normfact ; + int value ; + + normfact = normalize ? (1.0 * 0x7FFF) : 1.0 ; + ucptr = ((unsigned char*) dest) + 2 * count ; + + while (--count >= 0) + { ucptr -= 2 ; + value = lrintf (src [count] * normfact) ; + ucptr [0] = value ; + ucptr [1] = value >> 8 ; + } ; +} /* f2les_array */ + +static void +f2les_clip_array (const float *src, short *dest, int count, int normalize) +{ unsigned char *ucptr ; + float normfact, scaled_value ; + int value ; + + normfact = normalize ? (8.0 * 0x10000000) : (1.0 * 0x10000) ; + ucptr = ((unsigned char*) dest) + 2 * count ; + + while (--count >= 0) + { ucptr -= 2 ; + scaled_value = src [count] * normfact ; + if (CPU_CLIPS_POSITIVE == 0 && scaled_value >= (1.0 * 0x7FFFFFFF)) + { ucptr [0] = 0xFF ; + ucptr [1] = 0x7F ; + continue ; + } ; + if (CPU_CLIPS_NEGATIVE == 0 && scaled_value <= (-8.0 * 0x10000000)) + { ucptr [0] = 0x00 ; + ucptr [1] = 0x80 ; + continue ; + } ; + + value = lrintf (scaled_value) ; + ucptr [0] = value >> 16 ; + ucptr [1] = value >> 24 ; + } ; +} /* f2les_clip_array */ + +static sf_count_t +pcm_write_f2les (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ void (*convert) (const float *, short *t, int, int) ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + + convert = (psf->add_clipping) ? f2les_clip_array : f2les_array ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + convert (ptr + total, psf->u.sbuf, bufferlen, psf->norm_float) ; + writecount = psf_fwrite (psf->u.sbuf, sizeof (short), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_f2les */ + +/*============================================================================== +*/ + +static void +f2let_array (const float *src, tribyte *dest, int count, int normalize) +{ unsigned char *ucptr ; + float normfact ; + int value ; + + normfact = normalize ? (1.0 * 0x7FFFFF) : 1.0 ; + ucptr = ((unsigned char*) dest) + 3 * count ; + + while (--count >= 0) + { ucptr -= 3 ; + value = lrintf (src [count] * normfact) ; + ucptr [0] = value ; + ucptr [1] = value >> 8 ; + ucptr [2] = value >> 16 ; + } ; +} /* f2let_array */ + +static void +f2let_clip_array (const float *src, tribyte *dest, int count, int normalize) +{ unsigned char *ucptr ; + float normfact, scaled_value ; + int value ; + + normfact = normalize ? (8.0 * 0x10000000) : (1.0 * 0x100) ; + ucptr = ((unsigned char*) dest) + 3 * count ; + + while (--count >= 0) + { ucptr -= 3 ; + scaled_value = src [count] * normfact ; + if (CPU_CLIPS_POSITIVE == 0 && scaled_value >= (1.0 * 0x7FFFFFFF)) + { ucptr [0] = 0xFF ; + ucptr [1] = 0xFF ; + ucptr [2] = 0x7F ; + continue ; + } ; + if (CPU_CLIPS_NEGATIVE == 0 && scaled_value <= (-8.0 * 0x10000000)) + { ucptr [0] = 0x00 ; + ucptr [1] = 0x00 ; + ucptr [2] = 0x80 ; + continue ; + } ; + + value = lrintf (scaled_value) ; + ucptr [0] = value >> 8 ; + ucptr [1] = value >> 16 ; + ucptr [2] = value >> 24 ; + } ; +} /* f2let_clip_array */ + +static sf_count_t +pcm_write_f2let (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ void (*convert) (const float *, tribyte *, int, int) ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + + convert = (psf->add_clipping) ? f2let_clip_array : f2let_array ; + bufferlen = sizeof (psf->u.ucbuf) / SIZEOF_TRIBYTE ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + convert (ptr + total, (tribyte*) (psf->u.ucbuf), bufferlen, psf->norm_float) ; + writecount = psf_fwrite (psf->u.ucbuf, SIZEOF_TRIBYTE, bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_f2let */ + +/*============================================================================== +*/ + +static void +f2bet_array (const float *src, tribyte *dest, int count, int normalize) +{ unsigned char *ucptr ; + float normfact ; + int value ; + + normfact = normalize ? (1.0 * 0x7FFFFF) : 1.0 ; + ucptr = ((unsigned char*) dest) + 3 * count ; + + while (--count >= 0) + { ucptr -= 3 ; + value = lrintf (src [count] * normfact) ; + ucptr [0] = value >> 16 ; + ucptr [1] = value >> 8 ; + ucptr [2] = value ; + } ; +} /* f2bet_array */ + +static void +f2bet_clip_array (const float *src, tribyte *dest, int count, int normalize) +{ unsigned char *ucptr ; + float normfact, scaled_value ; + int value ; + + normfact = normalize ? (8.0 * 0x10000000) : (1.0 * 0x100) ; + ucptr = ((unsigned char*) dest) + 3 * count ; + + while (--count >= 0) + { ucptr -= 3 ; + scaled_value = src [count] * normfact ; + if (CPU_CLIPS_POSITIVE == 0 && scaled_value >= (1.0 * 0x7FFFFFFF)) + { ucptr [0] = 0x7F ; + ucptr [1] = 0xFF ; + ucptr [2] = 0xFF ; + continue ; + } ; + if (CPU_CLIPS_NEGATIVE == 0 && scaled_value <= (-8.0 * 0x10000000)) + { ucptr [0] = 0x80 ; + ucptr [1] = 0x00 ; + ucptr [2] = 0x00 ; + continue ; + } ; + + value = lrint (scaled_value) ; + ucptr [0] = value >> 24 ; + ucptr [1] = value >> 16 ; + ucptr [2] = value >> 8 ; + } ; +} /* f2bet_clip_array */ + +static sf_count_t +pcm_write_f2bet (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ void (*convert) (const float *, tribyte *, int, int) ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + + convert = (psf->add_clipping) ? f2bet_clip_array : f2bet_array ; + bufferlen = sizeof (psf->u.ucbuf) / SIZEOF_TRIBYTE ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + convert (ptr + total, (tribyte*) (psf->u.ucbuf), bufferlen, psf->norm_float) ; + writecount = psf_fwrite (psf->u.ucbuf, SIZEOF_TRIBYTE, bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_f2bet */ + +/*============================================================================== +*/ + +static void +f2bei_array (const float *src, int *dest, int count, int normalize) +{ unsigned char *ucptr ; + float normfact ; + int value ; + + normfact = normalize ? (1.0 * 0x7FFFFFFF) : 1.0 ; + ucptr = ((unsigned char*) dest) + 4 * count ; + while (--count >= 0) + { ucptr -= 4 ; + value = lrintf (src [count] * normfact) ; + ucptr [0] = value >> 24 ; + ucptr [1] = value >> 16 ; + ucptr [2] = value >> 8 ; + ucptr [3] = value ; + } ; +} /* f2bei_array */ + +static void +f2bei_clip_array (const float *src, int *dest, int count, int normalize) +{ unsigned char *ucptr ; + float normfact, scaled_value ; + int value ; + + normfact = normalize ? (8.0 * 0x10000000) : 1.0 ; + ucptr = ((unsigned char*) dest) + 4 * count ; + + while (--count >= 0) + { ucptr -= 4 ; + scaled_value = src [count] * normfact ; + if (CPU_CLIPS_POSITIVE == 0 && scaled_value >= 1.0 * 0x7FFFFFFF) + { ucptr [0] = 0x7F ; + ucptr [1] = 0xFF ; + ucptr [2] = 0xFF ; + ucptr [3] = 0xFF ; + continue ; + } ; + if (CPU_CLIPS_NEGATIVE == 0 && scaled_value <= (-8.0 * 0x10000000)) + { ucptr [0] = 0x80 ; + ucptr [1] = 0x00 ; + ucptr [2] = 0x00 ; + ucptr [3] = 0x00 ; + continue ; + } ; + + value = lrintf (scaled_value) ; + ucptr [0] = value >> 24 ; + ucptr [1] = value >> 16 ; + ucptr [2] = value >> 8 ; + ucptr [3] = value ; + } ; +} /* f2bei_clip_array */ + +static sf_count_t +pcm_write_f2bei (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ void (*convert) (const float *, int *, int, int) ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + + convert = (psf->add_clipping) ? f2bei_clip_array : f2bei_array ; + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + convert (ptr + total, psf->u.ibuf, bufferlen, psf->norm_float) ; + writecount = psf_fwrite (psf->u.ibuf, sizeof (int), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_f2bei */ + +/*============================================================================== +*/ + +static void +f2lei_array (const float *src, int *dest, int count, int normalize) +{ unsigned char *ucptr ; + float normfact ; + int value ; + + normfact = normalize ? (1.0 * 0x7FFFFFFF) : 1.0 ; + ucptr = ((unsigned char*) dest) + 4 * count ; + + while (--count >= 0) + { ucptr -= 4 ; + value = lrintf (src [count] * normfact) ; + ucptr [0] = value ; + ucptr [1] = value >> 8 ; + ucptr [2] = value >> 16 ; + ucptr [3] = value >> 24 ; + } ; +} /* f2lei_array */ + +static void +f2lei_clip_array (const float *src, int *dest, int count, int normalize) +{ unsigned char *ucptr ; + float normfact, scaled_value ; + int value ; + + normfact = normalize ? (8.0 * 0x10000000) : 1.0 ; + ucptr = ((unsigned char*) dest) + 4 * count ; + + while (--count >= 0) + { ucptr -= 4 ; + scaled_value = src [count] * normfact ; + if (CPU_CLIPS_POSITIVE == 0 && scaled_value >= (1.0 * 0x7FFFFFFF)) + { ucptr [0] = 0xFF ; + ucptr [1] = 0xFF ; + ucptr [2] = 0xFF ; + ucptr [3] = 0x7F ; + continue ; + } ; + if (CPU_CLIPS_NEGATIVE == 0 && scaled_value <= (-8.0 * 0x10000000)) + { ucptr [0] = 0x00 ; + ucptr [1] = 0x00 ; + ucptr [2] = 0x00 ; + ucptr [3] = 0x80 ; + continue ; + } ; + + value = lrintf (scaled_value) ; + ucptr [0] = value ; + ucptr [1] = value >> 8 ; + ucptr [2] = value >> 16 ; + ucptr [3] = value >> 24 ; + } ; +} /* f2lei_clip_array */ + +static sf_count_t +pcm_write_f2lei (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ void (*convert) (const float *, int *, int, int) ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + + convert = (psf->add_clipping) ? f2lei_clip_array : f2lei_array ; + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + convert (ptr + total, psf->u.ibuf, bufferlen, psf->norm_float) ; + writecount = psf_fwrite (psf->u.ibuf, sizeof (int), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_f2lei */ + +/*============================================================================== +*/ + +static void +d2sc_array (const double *src, signed char *dest, int count, int normalize) +{ double normfact ; + + normfact = normalize ? (1.0 * 0x7F) : 1.0 ; + + while (--count >= 0) + { dest [count] = lrint (src [count] * normfact) ; + } ; +} /* d2sc_array */ + +static void +d2sc_clip_array (const double *src, signed char *dest, int count, int normalize) +{ double normfact, scaled_value ; + + normfact = normalize ? (8.0 * 0x10000000) : (1.0 * 0x1000000) ; + + while (--count >= 0) + { scaled_value = src [count] * normfact ; + if (CPU_CLIPS_POSITIVE == 0 && scaled_value >= (1.0 * 0x7FFFFFFF)) + { dest [count] = 127 ; + continue ; + } ; + if (CPU_CLIPS_NEGATIVE == 0 && scaled_value <= (-8.0 * 0x10000000)) + { dest [count] = -128 ; + continue ; + } ; + + dest [count] = lrintf (scaled_value) >> 24 ; + } ; +} /* d2sc_clip_array */ + +static sf_count_t +pcm_write_d2sc (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ void (*convert) (const double *, signed char *, int, int) ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + + convert = (psf->add_clipping) ? d2sc_clip_array : d2sc_array ; + bufferlen = ARRAY_LEN (psf->u.scbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + convert (ptr + total, psf->u.scbuf, bufferlen, psf->norm_double) ; + writecount = psf_fwrite (psf->u.scbuf, sizeof (signed char), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_d2sc */ + +/*============================================================================== +*/ + +static void +d2uc_array (const double *src, unsigned char *dest, int count, int normalize) +{ double normfact ; + + normfact = normalize ? (1.0 * 0x7F) : 1.0 ; + + while (--count >= 0) + { dest [count] = lrint (src [count] * normfact) + 128 ; + } ; +} /* d2uc_array */ + +static void +d2uc_clip_array (const double *src, unsigned char *dest, int count, int normalize) +{ double normfact, scaled_value ; + + normfact = normalize ? (8.0 * 0x10000000) : (1.0 * 0x1000000) ; + + while (--count >= 0) + { scaled_value = src [count] * normfact ; + if (CPU_CLIPS_POSITIVE == 0 && scaled_value >= (1.0 * 0x7FFFFFFF)) + { dest [count] = 255 ; + continue ; + } ; + if (CPU_CLIPS_NEGATIVE == 0 && scaled_value <= (-8.0 * 0x10000000)) + { dest [count] = 0 ; + continue ; + } ; + + dest [count] = (lrint (src [count] * normfact) >> 24) + 128 ; + } ; +} /* d2uc_clip_array */ + +static sf_count_t +pcm_write_d2uc (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ void (*convert) (const double *, unsigned char *, int, int) ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + + convert = (psf->add_clipping) ? d2uc_clip_array : d2uc_array ; + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + convert (ptr + total, psf->u.ucbuf, bufferlen, psf->norm_double) ; + writecount = psf_fwrite (psf->u.ucbuf, sizeof (unsigned char), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_d2uc */ + +/*============================================================================== +*/ + +static void +d2bes_array (const double *src, short *dest, int count, int normalize) +{ unsigned char *ucptr ; + short value ; + double normfact ; + + normfact = normalize ? (1.0 * 0x7FFF) : 1.0 ; + ucptr = ((unsigned char*) dest) + 2 * count ; + + while (--count >= 0) + { ucptr -= 2 ; + value = lrint (src [count] * normfact) ; + ucptr [1] = value ; + ucptr [0] = value >> 8 ; + } ; +} /* d2bes_array */ + +static void +d2bes_clip_array (const double *src, short *dest, int count, int normalize) +{ unsigned char *ucptr ; + double normfact, scaled_value ; + int value ; + + normfact = normalize ? (8.0 * 0x10000000) : (1.0 * 0x10000) ; + ucptr = ((unsigned char*) dest) + 2 * count ; + + while (--count >= 0) + { ucptr -= 2 ; + scaled_value = src [count] * normfact ; + if (CPU_CLIPS_POSITIVE == 0 && scaled_value >= (1.0 * 0x7FFFFFFF)) + { ucptr [1] = 0xFF ; + ucptr [0] = 0x7F ; + continue ; + } ; + if (CPU_CLIPS_NEGATIVE == 0 && scaled_value <= (-8.0 * 0x10000000)) + { ucptr [1] = 0x00 ; + ucptr [0] = 0x80 ; + continue ; + } ; + + value = lrint (scaled_value) ; + ucptr [1] = value >> 16 ; + ucptr [0] = value >> 24 ; + } ; +} /* d2bes_clip_array */ + +static sf_count_t +pcm_write_d2bes (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ void (*convert) (const double *, short *, int, int) ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + + convert = (psf->add_clipping) ? d2bes_clip_array : d2bes_array ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + convert (ptr + total, psf->u.sbuf, bufferlen, psf->norm_double) ; + writecount = psf_fwrite (psf->u.sbuf, sizeof (short), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_d2bes */ + +/*============================================================================== +*/ + +static void +d2les_array (const double *src, short *dest, int count, int normalize) +{ unsigned char *ucptr ; + short value ; + double normfact ; + + normfact = normalize ? (1.0 * 0x7FFF) : 1.0 ; + ucptr = ((unsigned char*) dest) + 2 * count ; + + while (--count >= 0) + { ucptr -= 2 ; + value = lrint (src [count] * normfact) ; + ucptr [0] = value ; + ucptr [1] = value >> 8 ; + } ; +} /* d2les_array */ + +static void +d2les_clip_array (const double *src, short *dest, int count, int normalize) +{ unsigned char *ucptr ; + int value ; + double normfact, scaled_value ; + + normfact = normalize ? (8.0 * 0x10000000) : (1.0 * 0x10000) ; + ucptr = ((unsigned char*) dest) + 2 * count ; + + while (--count >= 0) + { ucptr -= 2 ; + scaled_value = src [count] * normfact ; + if (CPU_CLIPS_POSITIVE == 0 && scaled_value >= (1.0 * 0x7FFFFFFF)) + { ucptr [0] = 0xFF ; + ucptr [1] = 0x7F ; + continue ; + } ; + if (CPU_CLIPS_NEGATIVE == 0 && scaled_value <= (-8.0 * 0x10000000)) + { ucptr [0] = 0x00 ; + ucptr [1] = 0x80 ; + continue ; + } ; + + value = lrint (scaled_value) ; + ucptr [0] = value >> 16 ; + ucptr [1] = value >> 24 ; + } ; +} /* d2les_clip_array */ + +static sf_count_t +pcm_write_d2les (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ void (*convert) (const double *, short *, int, int) ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + + convert = (psf->add_clipping) ? d2les_clip_array : d2les_array ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + convert (ptr + total, psf->u.sbuf, bufferlen, psf->norm_double) ; + writecount = psf_fwrite (psf->u.sbuf, sizeof (short), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_d2les */ + +/*============================================================================== +*/ + +static void +d2let_array (const double *src, tribyte *dest, int count, int normalize) +{ unsigned char *ucptr ; + int value ; + double normfact ; + + normfact = normalize ? (1.0 * 0x7FFFFF) : 1.0 ; + ucptr = ((unsigned char*) dest) + 3 * count ; + + while (--count >= 0) + { ucptr -= 3 ; + value = lrint (src [count] * normfact) ; + ucptr [0] = value ; + ucptr [1] = value >> 8 ; + ucptr [2] = value >> 16 ; + } ; +} /* d2let_array */ + +static void +d2let_clip_array (const double *src, tribyte *dest, int count, int normalize) +{ unsigned char *ucptr ; + int value ; + double normfact, scaled_value ; + + normfact = normalize ? (8.0 * 0x10000000) : (1.0 * 0x100) ; + ucptr = ((unsigned char*) dest) + 3 * count ; + + while (--count >= 0) + { ucptr -= 3 ; + scaled_value = src [count] * normfact ; + if (CPU_CLIPS_POSITIVE == 0 && scaled_value >= (1.0 * 0x7FFFFFFF)) + { ucptr [0] = 0xFF ; + ucptr [1] = 0xFF ; + ucptr [2] = 0x7F ; + continue ; + } ; + if (CPU_CLIPS_NEGATIVE == 0 && scaled_value <= (-8.0 * 0x10000000)) + { ucptr [0] = 0x00 ; + ucptr [1] = 0x00 ; + ucptr [2] = 0x80 ; + continue ; + } ; + + value = lrint (scaled_value) ; + ucptr [0] = value >> 8 ; + ucptr [1] = value >> 16 ; + ucptr [2] = value >> 24 ; + } ; +} /* d2let_clip_array */ + +static sf_count_t +pcm_write_d2let (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ void (*convert) (const double *, tribyte *, int, int) ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + + convert = (psf->add_clipping) ? d2let_clip_array : d2let_array ; + bufferlen = sizeof (psf->u.ucbuf) / SIZEOF_TRIBYTE ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + convert (ptr + total, (tribyte*) (psf->u.ucbuf), bufferlen, psf->norm_double) ; + writecount = psf_fwrite (psf->u.ucbuf, SIZEOF_TRIBYTE, bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_d2let */ + +/*============================================================================== +*/ + +static void +d2bet_array (const double *src, tribyte *dest, int count, int normalize) +{ unsigned char *ucptr ; + int value ; + double normfact ; + + normfact = normalize ? (1.0 * 0x7FFFFF) : 1.0 ; + ucptr = ((unsigned char*) dest) + 3 * count ; + + while (--count >= 0) + { ucptr -= 3 ; + value = lrint (src [count] * normfact) ; + ucptr [2] = value ; + ucptr [1] = value >> 8 ; + ucptr [0] = value >> 16 ; + } ; +} /* d2bet_array */ + +static void +d2bet_clip_array (const double *src, tribyte *dest, int count, int normalize) +{ unsigned char *ucptr ; + int value ; + double normfact, scaled_value ; + + normfact = normalize ? (8.0 * 0x10000000) : (1.0 * 0x100) ; + ucptr = ((unsigned char*) dest) + 3 * count ; + + while (--count >= 0) + { ucptr -= 3 ; + scaled_value = src [count] * normfact ; + if (CPU_CLIPS_POSITIVE == 0 && scaled_value >= (1.0 * 0x7FFFFFFF)) + { ucptr [2] = 0xFF ; + ucptr [1] = 0xFF ; + ucptr [0] = 0x7F ; + continue ; + } ; + if (CPU_CLIPS_NEGATIVE == 0 && scaled_value <= (-8.0 * 0x10000000)) + { ucptr [2] = 0x00 ; + ucptr [1] = 0x00 ; + ucptr [0] = 0x80 ; + continue ; + } ; + + value = lrint (scaled_value) ; + ucptr [2] = value >> 8 ; + ucptr [1] = value >> 16 ; + ucptr [0] = value >> 24 ; + } ; +} /* d2bet_clip_array */ + +static sf_count_t +pcm_write_d2bet (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ void (*convert) (const double *, tribyte *, int, int) ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + + convert = (psf->add_clipping) ? d2bet_clip_array : d2bet_array ; + bufferlen = sizeof (psf->u.ucbuf) / SIZEOF_TRIBYTE ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + convert (ptr + total, (tribyte*) (psf->u.ucbuf), bufferlen, psf->norm_double) ; + writecount = psf_fwrite (psf->u.ucbuf, SIZEOF_TRIBYTE, bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_d2bet */ + +/*============================================================================== +*/ + +static void +d2bei_array (const double *src, int *dest, int count, int normalize) +{ unsigned char *ucptr ; + int value ; + double normfact ; + + normfact = normalize ? (1.0 * 0x7FFFFFFF) : 1.0 ; + ucptr = ((unsigned char*) dest) + 4 * count ; + + while (--count >= 0) + { ucptr -= 4 ; + value = lrint (src [count] * normfact) ; + ucptr [0] = value >> 24 ; + ucptr [1] = value >> 16 ; + ucptr [2] = value >> 8 ; + ucptr [3] = value ; + } ; +} /* d2bei_array */ + +static void +d2bei_clip_array (const double *src, int *dest, int count, int normalize) +{ unsigned char *ucptr ; + int value ; + double normfact, scaled_value ; + + normfact = normalize ? (8.0 * 0x10000000) : 1.0 ; + ucptr = ((unsigned char*) dest) + 4 * count ; + + while (--count >= 0) + { ucptr -= 4 ; + scaled_value = src [count] * normfact ; + if (CPU_CLIPS_POSITIVE == 0 && scaled_value >= (1.0 * 0x7FFFFFFF)) + { ucptr [3] = 0xFF ; + ucptr [2] = 0xFF ; + ucptr [1] = 0xFF ; + ucptr [0] = 0x7F ; + continue ; + } ; + if (CPU_CLIPS_NEGATIVE == 0 && scaled_value <= (-8.0 * 0x10000000)) + { ucptr [3] = 0x00 ; + ucptr [2] = 0x00 ; + ucptr [1] = 0x00 ; + ucptr [0] = 0x80 ; + continue ; + } ; + + value = lrint (scaled_value) ; + ucptr [0] = value >> 24 ; + ucptr [1] = value >> 16 ; + ucptr [2] = value >> 8 ; + ucptr [3] = value ; + } ; +} /* d2bei_clip_array */ + +static sf_count_t +pcm_write_d2bei (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ void (*convert) (const double *, int *, int, int) ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + + convert = (psf->add_clipping) ? d2bei_clip_array : d2bei_array ; + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + convert (ptr + total, psf->u.ibuf, bufferlen, psf->norm_double) ; + writecount = psf_fwrite (psf->u.ibuf, sizeof (int), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_d2bei */ + +/*============================================================================== +*/ + +static void +d2lei_array (const double *src, int *dest, int count, int normalize) +{ unsigned char *ucptr ; + int value ; + double normfact ; + + normfact = normalize ? (1.0 * 0x7FFFFFFF) : 1.0 ; + ucptr = ((unsigned char*) dest) + 4 * count ; + + while (--count >= 0) + { ucptr -= 4 ; + value = lrint (src [count] * normfact) ; + ucptr [0] = value ; + ucptr [1] = value >> 8 ; + ucptr [2] = value >> 16 ; + ucptr [3] = value >> 24 ; + } ; +} /* d2lei_array */ + +static void +d2lei_clip_array (const double *src, int *dest, int count, int normalize) +{ unsigned char *ucptr ; + int value ; + double normfact, scaled_value ; + + normfact = normalize ? (8.0 * 0x10000000) : 1.0 ; + ucptr = ((unsigned char*) dest) + 4 * count ; + + while (--count >= 0) + { ucptr -= 4 ; + scaled_value = src [count] * normfact ; + if (CPU_CLIPS_POSITIVE == 0 && scaled_value >= (1.0 * 0x7FFFFFFF)) + { ucptr [0] = 0xFF ; + ucptr [1] = 0xFF ; + ucptr [2] = 0xFF ; + ucptr [3] = 0x7F ; + continue ; + } ; + if (CPU_CLIPS_NEGATIVE == 0 && scaled_value <= (-8.0 * 0x10000000)) + { ucptr [0] = 0x00 ; + ucptr [1] = 0x00 ; + ucptr [2] = 0x00 ; + ucptr [3] = 0x80 ; + continue ; + } ; + + value = lrint (scaled_value) ; + ucptr [0] = value ; + ucptr [1] = value >> 8 ; + ucptr [2] = value >> 16 ; + ucptr [3] = value >> 24 ; + } ; +} /* d2lei_clip_array */ + +static sf_count_t +pcm_write_d2lei (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ void (*convert) (const double *, int *, int, int) ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + + convert = (psf->add_clipping) ? d2lei_clip_array : d2lei_array ; + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + convert (ptr + total, psf->u.ibuf, bufferlen, psf->norm_double) ; + writecount = psf_fwrite (psf->u.ibuf, sizeof (int), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* pcm_write_d2lei */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: d8bc7c0e-1e2f-4ff3-a28f-10ce1fbade3b +*/ diff --git a/libs/libsndfile/src/pvf.c b/libs/libsndfile/src/pvf.c new file mode 100644 index 0000000000..1dab17ccb1 --- /dev/null +++ b/libs/libsndfile/src/pvf.c @@ -0,0 +1,199 @@ +/* +** Copyright (C) 2002-2004 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" + +/*------------------------------------------------------------------------------ +** Macros to handle big/little endian issues. +*/ + +#define PVF1_MARKER (MAKE_MARKER ('P', 'V', 'F', '1')) + +/*------------------------------------------------------------------------------ +** Private static functions. +*/ + +static int pvf_close (SF_PRIVATE *psf) ; + +static int pvf_write_header (SF_PRIVATE *psf, int calc_length) ; +static int pvf_read_header (SF_PRIVATE *psf) ; + +/*------------------------------------------------------------------------------ +** Public function. +*/ + +int +pvf_open (SF_PRIVATE *psf) +{ int subformat ; + int error = 0 ; + + if (psf->mode == SFM_READ || (psf->mode == SFM_RDWR && psf->filelength > 0)) + { if ((error = pvf_read_header (psf))) + return error ; + } ; + + subformat = psf->sf.format & SF_FORMAT_SUBMASK ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { if ((psf->sf.format & SF_FORMAT_TYPEMASK) != SF_FORMAT_PVF) + return SFE_BAD_OPEN_FORMAT ; + + psf->endian = SF_ENDIAN_BIG ; + + if (pvf_write_header (psf, SF_FALSE)) + return psf->error ; + + psf->write_header = pvf_write_header ; + } ; + + psf->container_close = pvf_close ; + + psf->blockwidth = psf->bytewidth * psf->sf.channels ; + + switch (subformat) + { case SF_FORMAT_PCM_S8 : /* 8-bit linear PCM. */ + case SF_FORMAT_PCM_16 : /* 16-bit linear PCM. */ + case SF_FORMAT_PCM_32 : /* 32-bit linear PCM. */ + error = pcm_init (psf) ; + break ; + + default : break ; + } ; + + return error ; +} /* pvf_open */ + +/*------------------------------------------------------------------------------ +*/ + +static int +pvf_close (SF_PRIVATE *psf) +{ + psf = psf ; + + return 0 ; +} /* pvf_close */ + +static int +pvf_write_header (SF_PRIVATE *psf, int calc_length) +{ sf_count_t current ; + + if (psf->pipeoffset > 0) + return 0 ; + + calc_length = calc_length ; /* Avoid a compiler warning. */ + + current = psf_ftell (psf) ; + + /* Reset the current header length to zero. */ + psf->header [0] = 0 ; + psf->headindex = 0 ; + + if (psf->is_pipe == SF_FALSE) + psf_fseek (psf, 0, SEEK_SET) ; + + LSF_SNPRINTF ((char*) psf->header, sizeof (psf->header), "PVF1\n%d %d %d\n", + psf->sf.channels, psf->sf.samplerate, psf->bytewidth * 8) ; + + psf->headindex = strlen ((char*) psf->header) ; + + /* Header construction complete so write it out. */ + psf_fwrite (psf->header, psf->headindex, 1, psf) ; + + if (psf->error) + return psf->error ; + + psf->dataoffset = psf->headindex ; + + if (current > 0) + psf_fseek (psf, current, SEEK_SET) ; + + return psf->error ; +} /* pvf_write_header */ + +static int +pvf_read_header (SF_PRIVATE *psf) +{ char buffer [32] ; + int marker, channels, samplerate, bitwidth ; + + psf_binheader_readf (psf, "pmj", 0, &marker, 1) ; + psf_log_printf (psf, "%M\n", marker) ; + + if (marker != PVF1_MARKER) + return SFE_PVF_NO_PVF1 ; + + /* Grab characters up until a newline which is replaced by an EOS. */ + psf_binheader_readf (psf, "G", buffer, sizeof (buffer)) ; + + if (sscanf (buffer, "%d %d %d", &channels, &samplerate, &bitwidth) != 3) + return SFE_PVF_BAD_HEADER ; + + psf_log_printf (psf, " Channels : %d\n Sample rate : %d\n Bit width : %d\n", + channels, samplerate, bitwidth) ; + + psf->sf.channels = channels ; + psf->sf.samplerate = samplerate ; + + switch (bitwidth) + { case 8 : + psf->sf.format = SF_FORMAT_PVF | SF_FORMAT_PCM_S8 ; + psf->bytewidth = 1 ; + break ; + + case 16 : + psf->sf.format = SF_FORMAT_PVF | SF_FORMAT_PCM_16 ; + psf->bytewidth = 2 ; + break ; + case 32 : + psf->sf.format = SF_FORMAT_PVF | SF_FORMAT_PCM_32 ; + psf->bytewidth = 4 ; + break ; + + default : + return SFE_PVF_BAD_BITWIDTH ; + } ; + + psf->dataoffset = psf_ftell (psf) ; + psf_log_printf (psf, " Data Offset : %D\n", psf->dataoffset) ; + + psf->endian = SF_ENDIAN_BIG ; + + psf->datalength = psf->filelength - psf->dataoffset ; + psf->blockwidth = psf->sf.channels * psf->bytewidth ; + + if (! psf->sf.frames && psf->blockwidth) + psf->sf.frames = (psf->filelength - psf->dataoffset) / psf->blockwidth ; + + return 0 ; +} /* pvf_read_header */ +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 20a26761-8bc1-41d7-b1f3-9793bf3d9864 +*/ diff --git a/libs/libsndfile/src/raw.c b/libs/libsndfile/src/raw.c new file mode 100644 index 0000000000..65be491feb --- /dev/null +++ b/libs/libsndfile/src/raw.c @@ -0,0 +1,111 @@ +/* +** Copyright (C) 1999-2004 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include + +#include "sndfile.h" +#include "common.h" + +/*------------------------------------------------------------------------------ +** Public function. +*/ + +int +raw_open (SF_PRIVATE *psf) +{ int subformat, error = SFE_NO_ERROR ; + + subformat = psf->sf.format & SF_FORMAT_SUBMASK ; + + psf->endian = psf->sf.format & SF_FORMAT_ENDMASK ; + + if (CPU_IS_BIG_ENDIAN && (psf->endian == 0 || psf->endian == SF_ENDIAN_CPU)) + psf->endian = SF_ENDIAN_BIG ; + else if (CPU_IS_LITTLE_ENDIAN && (psf->endian == 0 || psf->endian == SF_ENDIAN_CPU)) + psf->endian = SF_ENDIAN_LITTLE ; + + psf->blockwidth = psf->bytewidth * psf->sf.channels ; + psf->dataoffset = 0 ; + psf->datalength = psf->filelength ; + + switch (subformat) + { case SF_FORMAT_PCM_S8 : + error = pcm_init (psf) ; + break ; + + case SF_FORMAT_PCM_U8 : + error = pcm_init (psf) ; + break ; + + case SF_FORMAT_PCM_16 : + case SF_FORMAT_PCM_24 : + case SF_FORMAT_PCM_32 : + error = pcm_init (psf) ; + break ; + + case SF_FORMAT_ULAW : + error = ulaw_init (psf) ; + break ; + + case SF_FORMAT_ALAW : + error = alaw_init (psf) ; + break ; + + case SF_FORMAT_GSM610 : + error = gsm610_init (psf) ; + break ; + + /* Lite remove start */ + case SF_FORMAT_FLOAT : + error = float32_init (psf) ; + break ; + + case SF_FORMAT_DOUBLE : + error = double64_init (psf) ; + break ; + + case SF_FORMAT_DWVW_12 : + error = dwvw_init (psf, 12) ; + break ; + + case SF_FORMAT_DWVW_16 : + error = dwvw_init (psf, 16) ; + break ; + + case SF_FORMAT_DWVW_24 : + error = dwvw_init (psf, 24) ; + break ; + + case SF_FORMAT_VOX_ADPCM : + error = vox_adpcm_init (psf) ; + break ; + /* Lite remove end */ + + default : return SFE_BAD_OPEN_FORMAT ; + } ; + + return error ; +} /* raw_open */ +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: f0066de7-d6ce-4f36-a1e0-e475c07d4e1a +*/ diff --git a/libs/libsndfile/src/rx2.c b/libs/libsndfile/src/rx2.c new file mode 100644 index 0000000000..d95f11fe78 --- /dev/null +++ b/libs/libsndfile/src/rx2.c @@ -0,0 +1,326 @@ +/* +** Copyright (C) 2001-2004 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" + +#if (ENABLE_EXPERIMENTAL_CODE == 0) + +int +rx2_open (SF_PRIVATE *psf) +{ if (psf) + return SFE_UNIMPLEMENTED ; + return (psf && 0) ; +} /* rx2_open */ + +#else + +/*------------------------------------------------------------------------------ + * Macros to handle big/little endian issues. +*/ + +#define CAT_MARKER (MAKE_MARKER ('C', 'A', 'T', ' ')) +#define GLOB_MARKER (MAKE_MARKER ('G', 'L', 'O', 'B')) + +#define RECY_MARKER (MAKE_MARKER ('R', 'E', 'C', 'Y')) + +#define SLCL_MARKER (MAKE_MARKER ('S', 'L', 'C', 'L')) +#define SLCE_MARKER (MAKE_MARKER ('S', 'L', 'C', 'E')) + +#define DEVL_MARKER (MAKE_MARKER ('D', 'E', 'V', 'L')) +#define TRSH_MARKER (MAKE_MARKER ('T', 'R', 'S', 'H')) + +#define EQ_MARKER (MAKE_MARKER ('E', 'Q', ' ', ' ')) +#define COMP_MARKER (MAKE_MARKER ('C', 'O', 'M', 'P')) + +#define SINF_MARKER (MAKE_MARKER ('S', 'I', 'N', 'F')) +#define SDAT_MARKER (MAKE_MARKER ('S', 'D', 'A', 'T')) + +/*------------------------------------------------------------------------------ + * Typedefs for file chunks. +*/ + + +/*------------------------------------------------------------------------------ + * Private static functions. +*/ +static int rx2_close (SF_PRIVATE *psf) ; + +/*------------------------------------------------------------------------------ +** Public functions. +*/ + +int +rx2_open (SF_PRIVATE *psf) +{ static const char *marker_type [4] = + { "Original Enabled", "Enabled Hidden", + "Additional/PencilTool", "Disabled" + } ; + + int error, marker, length, glob_offset, slce_count, frames ; + + int sdat_length = 0, slce_total = 0 ; + + int n_channels ; + + + /* So far only doing read. */ + + psf_binheader_readf (psf, "Epm4", 0, &marker, &length) ; + + if (marker != CAT_MARKER) + { psf_log_printf (psf, "length : %d\n", length) ; + return -1000 ; + } ; + + if (length != psf->filelength - 8) + psf_log_printf (psf, "%M : %d (should be %d)\n", marker, length, psf->filelength - 8) ; + else + psf_log_printf (psf, "%M : %d\n", marker, length) ; + + /* 'REX2' marker */ + psf_binheader_readf (psf, "m", &marker) ; + psf_log_printf (psf, "%M", marker) ; + + /* 'HEAD' marker */ + psf_binheader_readf (psf, "m", &marker) ; + psf_log_printf (psf, "%M\n", marker) ; + + /* Grab 'GLOB' offset. */ + psf_binheader_readf (psf, "E4", &glob_offset) ; + glob_offset += 0x14 ; /* Add the current file offset. */ + + /* Jump to offset 0x30 */ + psf_binheader_readf (psf, "p", 0x30) ; + + /* Get name length */ + length = 0 ; + psf_binheader_readf (psf, "1", &length) ; + if (length >= SIGNED_SIZEOF (psf->u.cbuf)) + { psf_log_printf (psf, " Text : %d *** Error : Too sf_count_t!\n") ; + return -1001 ; + } + + memset (psf->u.cbuf, 0, sizeof (psf->u.cbuf)) ; + psf_binheader_readf (psf, "b", psf->u.cbuf, length) ; + psf_log_printf (psf, " Text : \"%s\"\n", psf->u.cbuf) ; + + /* Jump to GLOB offset position. */ + if (glob_offset & 1) + glob_offset ++ ; + + psf_binheader_readf (psf, "p", glob_offset) ; + + slce_count = 0 ; + /* GLOB */ + while (1) + { psf_binheader_readf (psf, "m", &marker) ; + + if (marker != SLCE_MARKER && slce_count > 0) + { psf_log_printf (psf, " SLCE count : %d\n", slce_count) ; + slce_count = 0 ; + } + switch (marker) + { case GLOB_MARKER: + psf_binheader_readf (psf, "E4", &length) ; + psf_log_printf (psf, " %M : %d\n", marker, length) ; + psf_binheader_readf (psf, "j", length) ; + break ; + + case RECY_MARKER: + psf_binheader_readf (psf, "E4", &length) ; + psf_log_printf (psf, " %M : %d\n", marker, length) ; + psf_binheader_readf (psf, "j", (length+1) & 0xFFFFFFFE) ; /* ?????? */ + break ; + + case CAT_MARKER: + psf_binheader_readf (psf, "E4", &length) ; + psf_log_printf (psf, " %M : %d\n", marker, length) ; + /*-psf_binheader_readf (psf, "j", length) ;-*/ + break ; + + case DEVL_MARKER: + psf_binheader_readf (psf, "mE4", &marker, &length) ; + psf_log_printf (psf, " DEVL%M : %d\n", marker, length) ; + if (length & 1) + length ++ ; + psf_binheader_readf (psf, "j", length) ; + break ; + + case EQ_MARKER: + case COMP_MARKER: + psf_binheader_readf (psf, "E4", &length) ; + psf_log_printf (psf, " %M : %d\n", marker, length) ; + /* This is weird!!!! why make this (length - 1) */ + if (length & 1) + length ++ ; + psf_binheader_readf (psf, "j", length) ; + break ; + + case SLCL_MARKER: + psf_log_printf (psf, " %M\n (Offset, Next Offset, Type)\n", marker) ; + slce_count = 0 ; + break ; + + case SLCE_MARKER: + { int len [4], indx ; + + psf_binheader_readf (psf, "E4444", &len [0], &len [1], &len [2], &len [3]) ; + + indx = ((len [3] & 0x0000FFFF) >> 8) & 3 ; + + if (len [2] == 1) + { if (indx != 1) + indx = 3 ; /* 2 cases, where next slice offset = 1 -> disabled & enabled/hidden */ + + psf_log_printf (psf, " %M : (%6d, ?: 0x%X, %s)\n", marker, len [1], (len [3] & 0xFFFF0000) >> 16, marker_type [indx]) ; + } + else + { slce_total += len [2] ; + + psf_log_printf (psf, " %M : (%6d, SLCE_next_ofs:%d, ?: 0x%X, %s)\n", marker, len [1], len [2], (len [3] & 0xFFFF0000) >> 16, marker_type [indx]) ; + } ; + + slce_count ++ ; + } ; + break ; + + case SINF_MARKER: + psf_binheader_readf (psf, "E4", &length) ; + psf_log_printf (psf, " %M : %d\n", marker, length) ; + + psf_binheader_readf (psf, "E2", &n_channels) ; + n_channels = (n_channels & 0x0000FF00) >> 8 ; + psf_log_printf (psf, " Channels : %d\n", n_channels) ; + + psf_binheader_readf (psf, "E44", &psf->sf.samplerate, &frames) ; + psf->sf.frames = frames ; + psf_log_printf (psf, " Sample Rate : %d\n", psf->sf.samplerate) ; + psf_log_printf (psf, " Frames : %D\n", psf->sf.frames) ; + + psf_binheader_readf (psf, "E4", &length) ; + psf_log_printf (psf, " ??????????? : %d\n", length) ; + + psf_binheader_readf (psf, "E4", &length) ; + psf_log_printf (psf, " ??????????? : %d\n", length) ; + break ; + + case SDAT_MARKER: + psf_binheader_readf (psf, "E4", &length) ; + + sdat_length = length ; + + /* Get the current offset. */ + psf->dataoffset = psf_binheader_readf (psf, NULL) ; + + if (psf->dataoffset + length != psf->filelength) + psf_log_printf (psf, " %M : %d (should be %d)\n", marker, length, psf->dataoffset + psf->filelength) ; + else + psf_log_printf (psf, " %M : %d\n", marker, length) ; + break ; + + default : + psf_log_printf (psf, "Unknown marker : 0x%X %M", marker, marker) ; + return -1003 ; + break ; + } ; + + /* SDAT always last marker in file. */ + if (marker == SDAT_MARKER) + break ; + } ; + + puts (psf->logbuffer) ; + puts ("-----------------------------------") ; + + printf ("SDAT length : %d\n", sdat_length) ; + printf ("SLCE count : %d\n", slce_count) ; + + /* Hack for zero slice count. */ + if (slce_count == 0 && slce_total == 1) + slce_total = frames ; + + printf ("SLCE samples : %d\n", slce_total) ; + + /* Two bytes per sample. */ + printf ("Comp Ratio : %f:1\n", (2.0 * slce_total * n_channels) / sdat_length) ; + + puts (" ") ; + + psf->logbuffer [0] = 0 ; + + /* OK, have the header although not too sure what it all means. */ + + psf->endian = SF_ENDIAN_BIG ; + + psf->datalength = psf->filelength - psf->dataoffset ; + + if (psf_fseek (psf, psf->dataoffset, SEEK_SET)) + return SFE_BAD_SEEK ; + + psf->sf.format = (SF_FORMAT_REX2 | SF_FORMAT_DWVW_12) ; + + psf->sf.channels = 1 ; + psf->bytewidth = 2 ; + psf->blockwidth = psf->sf.channels * psf->bytewidth ; + + if ((error = dwvw_init (psf, 16))) + return error ; + + psf->container_close = rx2_close ; + + if (! psf->sf.frames && psf->blockwidth) + psf->sf.frames = psf->datalength / psf->blockwidth ; + + /* All done. */ + + return 0 ; +} /* rx2_open */ + +/*------------------------------------------------------------------------------ +*/ + +static int +rx2_close (SF_PRIVATE *psf) +{ + if (psf->mode == SFM_WRITE) + { /* Now we know for certain the length of the file we can re-write + ** correct values for the FORM, 8SVX and BODY chunks. + */ + + } ; + + return 0 ; +} /* rx2_close */ + +#endif +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 7366e813-9fee-4d1f-881e-e4a691469370 +*/ diff --git a/libs/libsndfile/src/sd2.c b/libs/libsndfile/src/sd2.c new file mode 100644 index 0000000000..7ef4814290 --- /dev/null +++ b/libs/libsndfile/src/sd2.c @@ -0,0 +1,613 @@ +/* +** Copyright (C) 2001-2006 Erik de Castro Lopo +** Copyright (C) 2004 Paavo Jumppanen +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +/* +** The sd2 support implemented in this file was partially sponsored +** (financially) by Paavo Jumppanen. +*/ + +/* +** Documentation on the Mac resource fork was obtained here : +** http://developer.apple.com/documentation/mac/MoreToolbox/MoreToolbox-99.html +*/ + +#include "sfconfig.h" + +#include +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" + +/*------------------------------------------------------------------------------ + * Markers. +*/ + +#define Sd2f_MARKER MAKE_MARKER ('S', 'd', '2', 'f') +#define Sd2a_MARKER MAKE_MARKER ('S', 'd', '2', 'a') +#define ALCH_MARKER MAKE_MARKER ('A', 'L', 'C', 'H') +#define lsf1_MARKER MAKE_MARKER ('l', 's', 'f', '1') + +#define STR_MARKER MAKE_MARKER ('S', 'T', 'R', ' ') +#define sdML_MARKER MAKE_MARKER ('s', 'd', 'M', 'L') + +enum +{ RSRC_STR = 111, + RSRC_BIN +} ; + +typedef struct +{ unsigned char * rsrc_data ; + int rsrc_len ; + + int data_offset, data_length ; + int map_offset, map_length ; + + int type_count, type_offset ; + int item_offset ; + + int str_index, str_count ; + + int string_offset ; + + /* All the above just to get these three. */ + int sample_size, sample_rate, channels ; +} SD2_RSRC ; + +typedef struct +{ int type ; + int id ; + char name [32] ; + char value [32] ; + int value_len ; +} STR_RSRC ; + +/*------------------------------------------------------------------------------ + * Private static functions. +*/ + +static int sd2_close (SF_PRIVATE *psf) ; + +static int sd2_parse_rsrc_fork (SF_PRIVATE *psf) ; +static int parse_str_rsrc (SF_PRIVATE *psf, SD2_RSRC * rsrc) ; + +static int sd2_write_rsrc_fork (SF_PRIVATE *psf, int calc_length) ; + +/*------------------------------------------------------------------------------ +** Public functions. +*/ + +int +sd2_open (SF_PRIVATE *psf) +{ int subformat, error = 0, valid ; + + /* SD2 is always big endian. */ + psf->endian = SF_ENDIAN_BIG ; + + if (psf->mode == SFM_READ || (psf->mode == SFM_RDWR && psf->rsrclength > 0)) + { psf_use_rsrc (psf, SF_TRUE) ; + valid = psf_file_valid (psf) ; + psf_use_rsrc (psf, SF_FALSE) ; + if (! valid) + { psf_log_printf (psf, "sd2_open : psf->rsrcdes < 0\n") ; + return SFE_SD2_BAD_RSRC ; + } ; + + error = sd2_parse_rsrc_fork (psf) ; + + if (error) + goto error_cleanup ; + } ; + + if ((psf->sf.format & SF_FORMAT_TYPEMASK) != SF_FORMAT_SD2) + { error = SFE_BAD_OPEN_FORMAT ; + goto error_cleanup ; + } ; + + subformat = psf->sf.format & SF_FORMAT_SUBMASK ; + psf->dataoffset = 0 ; + + /* Only open and write the resource in RDWR mode is its current length is zero. */ + if (psf->mode == SFM_WRITE || (psf->mode == SFM_RDWR && psf->rsrclength == 0)) + { psf_open_rsrc (psf, psf->mode) ; + + error = sd2_write_rsrc_fork (psf, SF_FALSE) ; + + if (error) + goto error_cleanup ; + + /* Not needed. */ + psf->write_header = NULL ; + } ; + + psf->container_close = sd2_close ; + + psf->blockwidth = psf->bytewidth * psf->sf.channels ; + + switch (subformat) + { case SF_FORMAT_PCM_S8 : /* 8-bit linear PCM. */ + case SF_FORMAT_PCM_16 : /* 16-bit linear PCM. */ + case SF_FORMAT_PCM_24 : /* 24-bit linear PCM */ + error = pcm_init (psf) ; + break ; + + default : + error = SFE_UNIMPLEMENTED ; + break ; + } ; + + psf_fseek (psf, psf->dataoffset, SEEK_SET) ; + +error_cleanup: + + /* Close the resource fork regardless. We won't need it again. */ + psf_close_rsrc (psf) ; + + return error ; +} /* sd2_open */ + +/*------------------------------------------------------------------------------ +*/ + +static int +sd2_close (SF_PRIVATE *psf) +{ + if (psf->mode == SFM_WRITE) + { /* Now we know for certain the audio_length of the file we can re-write + ** correct values for the FORM, 8SVX and BODY chunks. + */ + + } ; + + return 0 ; +} /* sd2_close */ + +/*------------------------------------------------------------------------------ +*/ + +static inline void +write_char (unsigned char * data, int offset, char value) +{ data [offset] = value ; +} /* write_char */ + +static inline void +write_short (unsigned char * data, int offset, short value) +{ data [offset] = value >> 8 ; + data [offset + 1] = value ; +} /* write_char */ + +static inline void +write_int (unsigned char * data, int offset, int value) +{ data [offset] = value >> 24 ; + data [offset + 1] = value >> 16 ; + data [offset + 2] = value >> 8 ; + data [offset + 3] = value ; +} /* write_int */ + +static inline void +write_marker (unsigned char * data, int offset, int value) +{ + if (CPU_IS_BIG_ENDIAN) + { data [offset] = value >> 24 ; + data [offset + 1] = value >> 16 ; + data [offset + 2] = value >> 8 ; + data [offset + 3] = value ; + } + else + { data [offset] = value ; + data [offset + 1] = value >> 8 ; + data [offset + 2] = value >> 16 ; + data [offset + 3] = value >> 24 ; + } ; +} /* write_marker */ + +static void +write_str (unsigned char * data, int offset, char * buffer, int buffer_len) +{ memcpy (data + offset, buffer, buffer_len) ; +} /* write_str */ + +static int +sd2_write_rsrc_fork (SF_PRIVATE *psf, int UNUSED (calc_length)) +{ SD2_RSRC rsrc ; + STR_RSRC str_rsrc [] = + { { RSRC_STR, 1000, "_sample-size", "", 0 }, + { RSRC_STR, 1001, "_sample-rate", "", 0 }, + { RSRC_STR, 1002, "_channels", "", 0 }, + { RSRC_BIN, 1000, "_Markers", "", 8 } + } ; + + int k, str_offset, data_offset, next_str ; + + psf_use_rsrc (psf, SF_TRUE) ; + + memset (&rsrc, 0, sizeof (rsrc)) ; + + rsrc.sample_rate = psf->sf.samplerate ; + rsrc.sample_size = psf->bytewidth ; + rsrc.channels = psf->sf.channels ; + + rsrc.rsrc_data = psf->header ; + rsrc.rsrc_len = sizeof (psf->header) ; + memset (rsrc.rsrc_data, 0xea, rsrc.rsrc_len) ; + + LSF_SNPRINTF (str_rsrc [0].value, sizeof (str_rsrc [0].value), "_%d", rsrc.sample_size) ; + LSF_SNPRINTF (str_rsrc [1].value, sizeof (str_rsrc [1].value), "_%d.000000", rsrc.sample_rate) ; + LSF_SNPRINTF (str_rsrc [2].value, sizeof (str_rsrc [2].value), "_%d", rsrc.channels) ; + + for (k = 0 ; k < ARRAY_LEN (str_rsrc) ; k++) + { if (str_rsrc [k].value_len == 0) + { str_rsrc [k].value_len = strlen (str_rsrc [k].value) ; + str_rsrc [k].value [0] = str_rsrc [k].value_len - 1 ; + } ; + + /* Turn name string into a pascal string. */ + str_rsrc [k].name [0] = strlen (str_rsrc [k].name) - 1 ; + } ; + + rsrc.data_offset = 0x100 ; + + /* + ** Calculate data length : + ** length of strings, plus the length of the sdML chunk. + */ + rsrc.data_length = 0 ; + for (k = 0 ; k < ARRAY_LEN (str_rsrc) ; k++) + rsrc.data_length += str_rsrc [k].value_len + 4 ; + + rsrc.map_offset = rsrc.data_offset + rsrc.data_length ; + + /* Very start of resource fork. */ + write_int (rsrc.rsrc_data, 0, rsrc.data_offset) ; + write_int (rsrc.rsrc_data, 4, rsrc.map_offset) ; + write_int (rsrc.rsrc_data, 8, rsrc.data_length) ; + + write_char (rsrc.rsrc_data, 0x30, strlen (psf->filename)) ; + write_str (rsrc.rsrc_data, 0x31, psf->filename, strlen (psf->filename)) ; + + write_short (rsrc.rsrc_data, 0x50, 0) ; + write_marker (rsrc.rsrc_data, 0x52, Sd2f_MARKER) ; + write_marker (rsrc.rsrc_data, 0x56, lsf1_MARKER) ; + + /* Very start of resource map. */ + write_int (rsrc.rsrc_data, rsrc.map_offset + 0, rsrc.data_offset) ; + write_int (rsrc.rsrc_data, rsrc.map_offset + 4, rsrc.map_offset) ; + write_int (rsrc.rsrc_data, rsrc.map_offset + 8, rsrc.data_length) ; + + /* These I don't currently understand. */ + if (1) + { write_char (rsrc.rsrc_data, rsrc.map_offset+ 16, 1) ; + /* Next resource map. */ + write_int (rsrc.rsrc_data, rsrc.map_offset + 17, 0x12345678) ; + /* File ref number. */ + write_short (rsrc.rsrc_data, rsrc.map_offset + 21, 0xabcd) ; + /* Fork attributes. */ + write_short (rsrc.rsrc_data, rsrc.map_offset + 23, 0) ; + } ; + + /* Resource type offset. */ + rsrc.type_offset = rsrc.map_offset + 30 ; + write_short (rsrc.rsrc_data, rsrc.map_offset + 24, rsrc.type_offset - rsrc.map_offset - 2) ; + + /* Type index max. */ + rsrc.type_count = 2 ; + write_short (rsrc.rsrc_data, rsrc.map_offset + 28, rsrc.type_count - 1) ; + + rsrc.item_offset = rsrc.type_offset + rsrc.type_count * 8 ; + + rsrc.str_count = ARRAY_LEN (str_rsrc) ; + rsrc.string_offset = rsrc.item_offset + (rsrc.str_count + 1) * 12 - rsrc.map_offset ; + write_short (rsrc.rsrc_data, rsrc.map_offset + 26, rsrc.string_offset) ; + + /* Write 'STR ' resource type. */ + rsrc.str_count = 3 ; + write_marker (rsrc.rsrc_data, rsrc.type_offset, STR_MARKER) ; + write_short (rsrc.rsrc_data, rsrc.type_offset + 4, rsrc.str_count - 1) ; + write_short (rsrc.rsrc_data, rsrc.type_offset + 6, 0x12) ; + + /* Write 'sdML' resource type. */ + write_marker (rsrc.rsrc_data, rsrc.type_offset + 8, sdML_MARKER) ; + write_short (rsrc.rsrc_data, rsrc.type_offset + 12, 0) ; + write_short (rsrc.rsrc_data, rsrc.type_offset + 14, 0x36) ; + + str_offset = rsrc.map_offset + rsrc.string_offset ; + next_str = 0 ; + data_offset = rsrc.data_offset ; + for (k = 0 ; k < ARRAY_LEN (str_rsrc) ; k++) + { write_str (rsrc.rsrc_data, str_offset, str_rsrc [k].name, strlen (str_rsrc [k].name)) ; + + write_short (rsrc.rsrc_data, rsrc.item_offset + k * 12, str_rsrc [k].id) ; + write_short (rsrc.rsrc_data, rsrc.item_offset + k * 12 + 2, next_str) ; + + str_offset += strlen (str_rsrc [k].name) ; + next_str += strlen (str_rsrc [k].name) ; + + write_int (rsrc.rsrc_data, rsrc.item_offset + k * 12 + 4, data_offset - rsrc.data_offset) ; + + write_int (rsrc.rsrc_data, data_offset, str_rsrc [k].value_len) ; + write_str (rsrc.rsrc_data, data_offset + 4, str_rsrc [k].value, str_rsrc [k].value_len) ; + data_offset += 4 + str_rsrc [k].value_len ; + } ; + + /* Finally, calculate and set map length. */ + rsrc.map_length = str_offset - rsrc.map_offset ; + write_int (rsrc.rsrc_data, 12, rsrc.map_length) ; + write_int (rsrc.rsrc_data, rsrc.map_offset + 12, rsrc.map_length) ; + + rsrc.rsrc_len = rsrc.map_offset + rsrc.map_length ; + + psf_fwrite (rsrc.rsrc_data, rsrc.rsrc_len, 1, psf) ; + + psf_use_rsrc (psf, SF_FALSE) ; + + if (psf->error) + return psf->error ; + + return 0 ; +} /* sd2_write_rsrc_fork */ + +/*------------------------------------------------------------------------------ +*/ + +static inline int +read_char (const unsigned char * data, int offset) +{ return data [offset] ; +} /* read_char */ + +static inline int +read_short (const unsigned char * data, int offset) +{ return (data [offset] << 8) + data [offset + 1] ; +} /* read_short */ + +static inline int +read_int (const unsigned char * data, int offset) +{ return (data [offset] << 24) + (data [offset + 1] << 16) + (data [offset + 2] << 8) + data [offset + 3] ; +} /* read_int */ + +static inline int +read_marker (const unsigned char * data, int offset) +{ + if (CPU_IS_BIG_ENDIAN) + return (data [offset] << 24) + (data [offset + 1] << 16) + (data [offset + 2] << 8) + data [offset + 3] ; + else if (CPU_IS_LITTLE_ENDIAN) + return data [offset] + (data [offset + 1] << 8) + (data [offset + 2] << 16) + (data [offset + 3] << 24) ; + else + return 0x666 ; +} /* read_marker */ + +static void +read_str (const unsigned char * data, int offset, char * buffer, int buffer_len) +{ int k ; + + memset (buffer, 0, buffer_len) ; + + for (k = 0 ; k < buffer_len - 1 ; k++) + { if (isprint (data [offset + k]) == 0) + return ; + buffer [k] = data [offset + k] ; + } ; + return ; +} /* read_str */ + +static int +sd2_parse_rsrc_fork (SF_PRIVATE *psf) +{ SD2_RSRC rsrc ; + int k, marker, error = 0 ; + + psf_use_rsrc (psf, SF_TRUE) ; + + memset (&rsrc, 0, sizeof (rsrc)) ; + + rsrc.rsrc_len = psf_get_filelen (psf) ; + psf_log_printf (psf, "Resource length : %d (0x%04X)\n", rsrc.rsrc_len, rsrc.rsrc_len) ; + + if (rsrc.rsrc_len > SIGNED_SIZEOF (psf->header)) + rsrc.rsrc_data = calloc (1, rsrc.rsrc_len) ; + else + rsrc.rsrc_data = psf->header ; + + /* Read in the whole lot. */ + psf_fread (rsrc.rsrc_data, rsrc.rsrc_len, 1, psf) ; + + /* Reset the header storage because we have changed to the rsrcdes. */ + psf->headindex = psf->headend = rsrc.rsrc_len ; + + rsrc.data_offset = read_int (rsrc.rsrc_data, 0) ; + rsrc.map_offset = read_int (rsrc.rsrc_data, 4) ; + rsrc.data_length = read_int (rsrc.rsrc_data, 8) ; + rsrc.map_length = read_int (rsrc.rsrc_data, 12) ; + + if (rsrc.data_offset == 0x51607 && rsrc.map_offset == 0x20000) + { psf_log_printf (psf, "Trying offset of 0x52 bytes.\n") ; + rsrc.data_offset = read_int (rsrc.rsrc_data, 0x52 + 0) + 0x52 ; + rsrc.map_offset = read_int (rsrc.rsrc_data, 0x52 + 4) + 0x52 ; + rsrc.data_length = read_int (rsrc.rsrc_data, 0x52 + 8) ; + rsrc.map_length = read_int (rsrc.rsrc_data, 0x52 + 12) ; + } ; + + psf_log_printf (psf, " data offset : 0x%04X\n map offset : 0x%04X\n" + " data length : 0x%04X\n map length : 0x%04X\n", + rsrc.data_offset, rsrc.map_offset, rsrc.data_length, rsrc.map_length) ; + + if (rsrc.data_offset > rsrc.rsrc_len) + { psf_log_printf (psf, "Error : rsrc.data_offset (%d, 0x%x) > len\n", rsrc.data_offset, rsrc.data_offset) ; + error = SFE_SD2_BAD_DATA_OFFSET ; + goto parse_rsrc_fork_cleanup ; + } ; + + if (rsrc.map_offset > rsrc.rsrc_len) + { psf_log_printf (psf, "Error : rsrc.map_offset > len\n") ; + error = SFE_SD2_BAD_MAP_OFFSET ; + goto parse_rsrc_fork_cleanup ; + } ; + + if (rsrc.data_length > rsrc.rsrc_len) + { psf_log_printf (psf, "Error : rsrc.data_length > len\n") ; + error = SFE_SD2_BAD_DATA_LENGTH ; + goto parse_rsrc_fork_cleanup ; + } ; + + if (rsrc.map_length > rsrc.rsrc_len) + { psf_log_printf (psf, "Error : rsrc.map_length > len\n") ; + error = SFE_SD2_BAD_MAP_LENGTH ; + goto parse_rsrc_fork_cleanup ; + } ; + + if (rsrc.data_offset + rsrc.data_length != rsrc.map_offset || rsrc.map_offset + rsrc.map_length != rsrc.rsrc_len) + { psf_log_printf (psf, "Error : This does not look like a MacOSX resource fork.\n") ; + error = SFE_SD2_BAD_RSRC ; + goto parse_rsrc_fork_cleanup ; + } ; + + rsrc.string_offset = rsrc.map_offset + read_short (rsrc.rsrc_data, rsrc.map_offset + 26) ; + if (rsrc.string_offset > rsrc.rsrc_len) + { psf_log_printf (psf, "Bad string offset (%d).\n", rsrc.string_offset) ; + error = SFE_SD2_BAD_RSRC ; + goto parse_rsrc_fork_cleanup ; + } ; + + rsrc.type_offset = rsrc.map_offset + 30 ; + + rsrc.type_count = read_short (rsrc.rsrc_data, rsrc.map_offset + 28) + 1 ; + if (rsrc.type_count < 1) + { psf_log_printf (psf, "Bad type count.\n") ; + error = SFE_SD2_BAD_RSRC ; + goto parse_rsrc_fork_cleanup ; + } ; + + rsrc.item_offset = rsrc.type_offset + rsrc.type_count * 8 ; + if (rsrc.item_offset < 0 || rsrc.item_offset > rsrc.rsrc_len) + { psf_log_printf (psf, "Bad item offset (%d).\n", rsrc.item_offset) ; + error = SFE_SD2_BAD_RSRC ; + goto parse_rsrc_fork_cleanup ; + } ; + + rsrc.str_index = -1 ; + for (k = 0 ; k < rsrc.type_count ; k ++) + { marker = read_marker (rsrc.rsrc_data, rsrc.type_offset + k * 8) ; + + if (marker == STR_MARKER) + { rsrc.str_index = k ; + rsrc.str_count = read_short (rsrc.rsrc_data, rsrc.type_offset + k * 8 + 4) + 1 ; + error = parse_str_rsrc (psf, &rsrc) ; + goto parse_rsrc_fork_cleanup ; + } ; + } ; + + psf_log_printf (psf, "No 'STR ' resource.\n") ; + error = SFE_SD2_BAD_RSRC ; + +parse_rsrc_fork_cleanup : + + psf_use_rsrc (psf, SF_FALSE) ; + + if ((void *) rsrc.rsrc_data < (void *) psf || (void *) rsrc.rsrc_data > (void *) (psf + 1)) + free (rsrc.rsrc_data) ; + + return error ; +} /* sd2_parse_rsrc_fork */ + +static int +parse_str_rsrc (SF_PRIVATE *psf, SD2_RSRC * rsrc) +{ char name [32], value [32] ; + int k, str_offset, data_offset, data_len, rsrc_id ; + + psf_log_printf (psf, "Finding parameters :\n") ; + + str_offset = rsrc->string_offset ; + for (k = 0 ; k < rsrc->str_count ; k++) + { int slen ; + + slen = read_char (rsrc->rsrc_data, str_offset) ; + read_str (rsrc->rsrc_data, str_offset + 1, name, SF_MIN (SIGNED_SIZEOF (name), slen + 1)) ; + str_offset += slen + 1 ; + + rsrc_id = read_short (rsrc->rsrc_data, rsrc->item_offset + k * 12) ; + + data_offset = rsrc->data_offset + read_int (rsrc->rsrc_data, rsrc->item_offset + k * 12 + 4) ; + if (data_offset < 0 || data_offset > rsrc->rsrc_len) + { psf_log_printf (psf, "Bad data offset (%d)\n", data_offset) ; + return SFE_SD2_BAD_DATA_OFFSET ; + } ; + + data_len = read_int (rsrc->rsrc_data, data_offset) ; + if (data_len < 0 || data_len > rsrc->rsrc_len) + { psf_log_printf (psf, "Bad data length (%d).\n", data_len) ; + return SFE_SD2_BAD_RSRC ; + } ; + + slen = read_char (rsrc->rsrc_data, data_offset + 4) ; + read_str (rsrc->rsrc_data, data_offset + 5, value, SF_MIN (SIGNED_SIZEOF (value), slen + 1)) ; + + psf_log_printf (psf, " %-12s 0x%04x %4d %2d %2d '%s'\n", name, data_offset, rsrc_id, data_len, slen, value) ; + + if (strcmp (name, "sample-size") == 0 && rsrc->sample_size == 0) + rsrc->sample_size = strtol (value, NULL, 10) ; + else if (strcmp (name, "sample-rate") == 0 && rsrc->sample_rate == 0) + rsrc->sample_rate = strtol (value, NULL, 10) ; + else if (strcmp (name, "channels") == 0 && rsrc->channels == 0) + rsrc->channels = strtol (value, NULL, 10) ; + } ; + + if (rsrc->sample_rate < 0) + { psf_log_printf (psf, "Bad sample rate (%d)\n", rsrc->sample_rate) ; + return SFE_SD2_BAD_RSRC ; + } ; + + if (rsrc->channels < 0) + { psf_log_printf (psf, "Bad channel count (%d)\n", rsrc->channels) ; + return SFE_SD2_BAD_RSRC ; + } ; + + psf->sf.samplerate = rsrc->sample_rate ; + psf->sf.channels = rsrc->channels ; + psf->bytewidth = rsrc->sample_size ; + + switch (rsrc->sample_size) + { case 1 : + psf->sf.format = SF_FORMAT_SD2 | SF_FORMAT_PCM_S8 ; + break ; + + case 2 : + psf->sf.format = SF_FORMAT_SD2 | SF_FORMAT_PCM_16 ; + break ; + + case 3 : + psf->sf.format = SF_FORMAT_SD2 | SF_FORMAT_PCM_24 ; + break ; + + default : + psf_log_printf (psf, "Bad sample size (%d)\n", rsrc->sample_size) ; + return SFE_SD2_BAD_SAMPLE_SIZE ; + } ; + + psf_log_printf (psf, "ok\n") ; + + return 0 ; +} /* parse_str_rsrc */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 1ee183e5-6b9f-4c2c-bd0a-24f35595cefc +*/ diff --git a/libs/libsndfile/src/sds.c b/libs/libsndfile/src/sds.c new file mode 100644 index 0000000000..3769bf021c --- /dev/null +++ b/libs/libsndfile/src/sds.c @@ -0,0 +1,993 @@ +/* +** Copyright (C) 2002-2005 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" +#include "float_cast.h" + +/*------------------------------------------------------------------------------ +*/ + +#define SDS_DATA_OFFSET 0x15 +#define SDS_BLOCK_SIZE 127 + +#define SDS_AUDIO_BYTES_PER_BLOCK 120 + +#define SDS_3BYTE_TO_INT_DECODE(x) (((x) & 0x7F) | (((x) & 0x7F00) >> 1) | (((x) & 0x7F0000) >> 2)) +#define SDS_INT_TO_3BYTE_ENCODE(x) (((x) & 0x7F) | (((x) << 1) & 0x7F00) | (((x) << 2) & 0x7F0000)) + +/*------------------------------------------------------------------------------ +** Typedefs. +*/ + +typedef struct tag_SDS_PRIVATE +{ int bitwidth, frames ; + int samplesperblock, total_blocks ; + + int (*reader) (SF_PRIVATE *psf, struct tag_SDS_PRIVATE *psds) ; + int (*writer) (SF_PRIVATE *psf, struct tag_SDS_PRIVATE *psds) ; + + int read_block, read_count ; + unsigned char read_data [SDS_BLOCK_SIZE] ; + int read_samples [SDS_BLOCK_SIZE / 2] ; /* Maximum samples per block */ + + int write_block, write_count ; + unsigned char write_data [SDS_BLOCK_SIZE] ; + int write_samples [SDS_BLOCK_SIZE / 2] ; /* Maximum samples per block */ +} SDS_PRIVATE ; + +/*------------------------------------------------------------------------------ +** Private static functions. +*/ + +static int sds_close (SF_PRIVATE *psf) ; + +static int sds_write_header (SF_PRIVATE *psf, int calc_length) ; +static int sds_read_header (SF_PRIVATE *psf, SDS_PRIVATE *psds) ; + +static int sds_init (SF_PRIVATE *psf, SDS_PRIVATE *psds) ; + +static sf_count_t sds_read_s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t sds_read_i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t sds_read_f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t sds_read_d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; + +static sf_count_t sds_write_s (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t sds_write_i (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t sds_write_f (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t sds_write_d (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; + +static sf_count_t sds_seek (SF_PRIVATE *psf, int mode, sf_count_t offset) ; + +static int sds_2byte_read (SF_PRIVATE *psf, SDS_PRIVATE *psds) ; +static int sds_3byte_read (SF_PRIVATE *psf, SDS_PRIVATE *psds) ; +static int sds_4byte_read (SF_PRIVATE *psf, SDS_PRIVATE *psds) ; + +static int sds_read (SF_PRIVATE *psf, SDS_PRIVATE *psds, int *iptr, int readcount) ; + +static int sds_2byte_write (SF_PRIVATE *psf, SDS_PRIVATE *psds) ; +static int sds_3byte_write (SF_PRIVATE *psf, SDS_PRIVATE *psds) ; +static int sds_4byte_write (SF_PRIVATE *psf, SDS_PRIVATE *psds) ; + +static int sds_write (SF_PRIVATE *psf, SDS_PRIVATE *psds, const int *iptr, int writecount) ; + +/*------------------------------------------------------------------------------ +** Public function. +*/ + +int +sds_open (SF_PRIVATE *psf) +{ SDS_PRIVATE *psds ; + int error = 0 ; + + /* Hmmmm, need this here to pass update_header_test. */ + psf->sf.frames = 0 ; + + if (! (psds = calloc (1, sizeof (SDS_PRIVATE)))) + return SFE_MALLOC_FAILED ; + psf->fdata = psds ; + + if (psf->mode == SFM_READ || (psf->mode == SFM_RDWR && psf->filelength > 0)) + { if ((error = sds_read_header (psf, psds))) + return error ; + } ; + + if ((psf->sf.format & SF_FORMAT_TYPEMASK) != SF_FORMAT_SDS) + return SFE_BAD_OPEN_FORMAT ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { if (sds_write_header (psf, SF_FALSE)) + return psf->error ; + + psf->write_header = sds_write_header ; + + psf_fseek (psf, SDS_DATA_OFFSET, SEEK_SET) ; + } ; + + if ((error = sds_init (psf, psds)) != 0) + return error ; + + psf->seek = sds_seek ; + psf->container_close = sds_close ; + + psf->blockwidth = 0 ; + + return error ; +} /* sds_open */ + +/*------------------------------------------------------------------------------ +*/ + +static int +sds_close (SF_PRIVATE *psf) +{ + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { SDS_PRIVATE *psds ; + + if ((psds = (SDS_PRIVATE *) psf->fdata) == NULL) + { psf_log_printf (psf, "*** Bad psf->fdata ptr.\n") ; + return SFE_INTERNAL ; + } ; + + if (psds->write_count > 0) + { memset (&(psds->write_data [psds->write_count]), 0, (psds->samplesperblock - psds->write_count) * sizeof (int)) ; + psds->writer (psf, psds) ; + } ; + + sds_write_header (psf, SF_TRUE) ; + } ; + + return 0 ; +} /* sds_close */ + +static int +sds_init (SF_PRIVATE *psf, SDS_PRIVATE *psds) +{ + if (psds->bitwidth < 8 || psds->bitwidth > 28) + return (psf->error = SFE_SDS_BAD_BIT_WIDTH) ; + + if (psds->bitwidth < 14) + { psds->reader = sds_2byte_read ; + psds->writer = sds_2byte_write ; + psds->samplesperblock = SDS_AUDIO_BYTES_PER_BLOCK / 2 ; + } + else if (psds->bitwidth < 21) + { psds->reader = sds_3byte_read ; + psds->writer = sds_3byte_write ; + psds->samplesperblock = SDS_AUDIO_BYTES_PER_BLOCK / 3 ; + } + else + { psds->reader = sds_4byte_read ; + psds->writer = sds_4byte_write ; + psds->samplesperblock = SDS_AUDIO_BYTES_PER_BLOCK / 4 ; + } ; + + if (psf->mode == SFM_READ || psf->mode == SFM_RDWR) + { psf->read_short = sds_read_s ; + psf->read_int = sds_read_i ; + psf->read_float = sds_read_f ; + psf->read_double = sds_read_d ; + + /* Read first block. */ + psds->reader (psf, psds) ; + } ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { psf->write_short = sds_write_s ; + psf->write_int = sds_write_i ; + psf->write_float = sds_write_f ; + psf->write_double = sds_write_d ; + } ; + + return 0 ; +} /* sds_init */ + +static int +sds_read_header (SF_PRIVATE *psf, SDS_PRIVATE *psds) +{ unsigned char channel, bitwidth, loop_type, byte ; + unsigned short sample_no, marker ; + unsigned int samp_period, data_length, sustain_loop_start, sustain_loop_end ; + int bytesread, blockcount ; + + /* Set position to start of file to begin reading header. */ + bytesread = psf_binheader_readf (psf, "pE211", 0, &marker, &channel, &byte) ; + + if (marker != 0xF07E || byte != 0x01) + return SFE_SDS_NOT_SDS ; + + psf_log_printf (psf, "Midi Sample Dump Standard (.sds)\nF07E\n Midi Channel : %d\n", channel) ; + + bytesread += psf_binheader_readf (psf, "e213", &sample_no, &bitwidth, &samp_period) ; + + sample_no = SDS_3BYTE_TO_INT_DECODE (sample_no) ; + samp_period = SDS_3BYTE_TO_INT_DECODE (samp_period) ; + + psds->bitwidth = bitwidth ; + + psf->sf.samplerate = 1000000000 / samp_period ; + + psf_log_printf (psf, " Sample Number : %d\n" + " Bit Width : %d\n" + " Sample Rate : %d\n", + sample_no, psds->bitwidth, psf->sf.samplerate) ; + + bytesread += psf_binheader_readf (psf, "e3331", &data_length, &sustain_loop_start, &sustain_loop_end, &loop_type) ; + + data_length = SDS_3BYTE_TO_INT_DECODE (data_length) ; + + sustain_loop_start = SDS_3BYTE_TO_INT_DECODE (sustain_loop_start) ; + sustain_loop_end = SDS_3BYTE_TO_INT_DECODE (sustain_loop_end) ; + + psf_log_printf (psf, " Sustain Loop\n" + " Start : %d\n" + " End : %d\n" + " Loop Type : %d\n", + sustain_loop_start, sustain_loop_end, loop_type) ; + + psf->dataoffset = SDS_DATA_OFFSET ; + psf->datalength = psf->filelength - psf->dataoffset ; + + if (data_length != psf->filelength - psf->dataoffset) + { psf_log_printf (psf, " Datalength : %d (truncated data??? %d)\n", data_length, psf->filelength - psf->dataoffset) ; + data_length = psf->filelength - psf->dataoffset ; + } + else + psf_log_printf (psf, " Datalength : %d\n", data_length) ; + + bytesread += psf_binheader_readf (psf, "1", &byte) ; + if (byte != 0xF7) + psf_log_printf (psf, "bad end : %X\n", byte & 0xFF) ; + + for (blockcount = 0 ; bytesread < psf->filelength ; blockcount++) + { + bytesread += psf_fread (&marker, 1, 2, psf) ; + + if (marker == 0) + break ; + + psf_fseek (psf, SDS_BLOCK_SIZE - 2, SEEK_CUR) ; + bytesread += SDS_BLOCK_SIZE - 2 ; + } ; + + psf_log_printf (psf, "\nBlocks : %d\n", blockcount) ; + psds->total_blocks = blockcount ; + + psds->samplesperblock = SDS_AUDIO_BYTES_PER_BLOCK / ((psds->bitwidth + 6) / 7) ; + psf_log_printf (psf, "Samples/Block : %d\n", psds->samplesperblock) ; + + psf_log_printf (psf, "Frames : %d\n", blockcount * psds->samplesperblock) ; + + psf->sf.frames = blockcount * psds->samplesperblock ; + psds->frames = blockcount * psds->samplesperblock ; + + /* Always Mono */ + psf->sf.channels = 1 ; + psf->sf.sections = 1 ; + + /* + ** Lie to the user about PCM bit width. Always round up to + ** the next multiple of 8. + */ + switch ((psds->bitwidth + 7) / 8) + { case 1 : + psf->sf.format = SF_FORMAT_SDS | SF_FORMAT_PCM_S8 ; + break ; + + case 2 : + psf->sf.format = SF_FORMAT_SDS | SF_FORMAT_PCM_16 ; + break ; + + case 3 : + psf->sf.format = SF_FORMAT_SDS | SF_FORMAT_PCM_24 ; + break ; + + case 4 : + psf->sf.format = SF_FORMAT_SDS | SF_FORMAT_PCM_32 ; + break ; + + default : + psf_log_printf (psf, "*** Weird byte width (%d)\n", (psds->bitwidth + 7) / 8) ; + return SFE_SDS_BAD_BIT_WIDTH ; + } ; + + psf_fseek (psf, SDS_DATA_OFFSET, SEEK_SET) ; + + return 0 ; +} /* sds_read_header */ + +static int +sds_write_header (SF_PRIVATE *psf, int calc_length) +{ SDS_PRIVATE *psds ; + sf_count_t current ; + int samp_period, data_length, sustain_loop_start, sustain_loop_end ; + unsigned char loop_type = 0 ; + + if ((psds = (SDS_PRIVATE *) psf->fdata) == NULL) + { psf_log_printf (psf, "*** Bad psf->fdata ptr.\n") ; + return SFE_INTERNAL ; + } ; + + if (psf->pipeoffset > 0) + return 0 ; + + current = psf_ftell (psf) ; + + if (calc_length) + psf->sf.frames = psds->total_blocks * psds->samplesperblock + psds->write_count ; + + if (psds->write_count > 0) + { int current_count = psds->write_count ; + int current_block = psds->write_block ; + + psds->writer (psf, psds) ; + + psf_fseek (psf, -1 * SDS_BLOCK_SIZE, SEEK_CUR) ; + + psds->write_count = current_count ; + psds->write_block = current_block ; + } ; + + /* Reset the current header length to zero. */ + psf->header [0] = 0 ; + psf->headindex = 0 ; + + if (psf->is_pipe == SF_FALSE) + psf_fseek (psf, 0, SEEK_SET) ; + + psf_binheader_writef (psf, "E211", 0xF07E, 0, 1) ; + + switch (psf->sf.format & SF_FORMAT_SUBMASK) + { case SF_FORMAT_PCM_S8 : + psds->bitwidth = 8 ; + break ; + case SF_FORMAT_PCM_16 : + psds->bitwidth = 16 ; + break ; + case SF_FORMAT_PCM_24 : + psds->bitwidth = 24 ; + break ; + default: + return SFE_SDS_BAD_BIT_WIDTH ; + } ; + + samp_period = SDS_INT_TO_3BYTE_ENCODE (1000000000 / psf->sf.samplerate) ; + + psf_binheader_writef (psf, "e213", 0, psds->bitwidth, samp_period) ; + + data_length = SDS_INT_TO_3BYTE_ENCODE (psds->total_blocks * SDS_BLOCK_SIZE) ; + sustain_loop_start = SDS_INT_TO_3BYTE_ENCODE (0) ; + sustain_loop_end = SDS_INT_TO_3BYTE_ENCODE (psf->sf.frames) ; + + psf_binheader_writef (psf, "e33311", data_length, sustain_loop_start, sustain_loop_end, loop_type, 0xF7) ; + + /* Header construction complete so write it out. */ + psf_fwrite (psf->header, psf->headindex, 1, psf) ; + + if (psf->error) + return psf->error ; + + psf->dataoffset = psf->headindex ; + psf->datalength = psds->write_block * SDS_BLOCK_SIZE ; + + if (current > 0) + psf_fseek (psf, current, SEEK_SET) ; + + return psf->error ; +} /* sds_write_header */ + + +/*------------------------------------------------------------------------------ +*/ + +static int +sds_2byte_read (SF_PRIVATE *psf, SDS_PRIVATE *psds) +{ unsigned char *ucptr, checksum ; + unsigned int sample ; + int k ; + + psds->read_block ++ ; + psds->read_count = 0 ; + + if (psds->read_block * psds->samplesperblock > psds->frames) + { memset (psds->read_samples, 0, psds->samplesperblock * sizeof (int)) ; + return 1 ; + } ; + + if ((k = psf_fread (psds->read_data, 1, SDS_BLOCK_SIZE, psf)) != SDS_BLOCK_SIZE) + psf_log_printf (psf, "*** Warning : short read (%d != %d).\n", k, SDS_BLOCK_SIZE) ; + + if (psds->read_data [0] != 0xF0) + { printf ("Error A : %02X\n", psds->read_data [0] & 0xFF) ; + } ; + + checksum = psds->read_data [1] ; + if (checksum != 0x7E) + { printf ("Error 1 : %02X\n", checksum & 0xFF) ; + } + + for (k = 2 ; k < SDS_BLOCK_SIZE - 3 ; k ++) + checksum ^= psds->read_data [k] ; + + checksum &= 0x7F ; + + if (checksum != psds->read_data [SDS_BLOCK_SIZE - 2]) + { psf_log_printf (psf, "Block %d : checksum is %02X should be %02X\n", psds->read_data [4], checksum, psds->read_data [SDS_BLOCK_SIZE - 2]) ; + } ; + + ucptr = psds->read_data + 5 ; + for (k = 0 ; k < 120 ; k += 2) + { sample = (ucptr [k] << 25) + (ucptr [k + 1] << 18) ; + psds->read_samples [k / 2] = (int) (sample - 0x80000000) ; + } ; + + return 1 ; +} /* sds_2byte_read */ + +static int +sds_3byte_read (SF_PRIVATE *psf, SDS_PRIVATE *psds) +{ unsigned char *ucptr, checksum ; + unsigned int sample ; + int k ; + + psds->read_block ++ ; + psds->read_count = 0 ; + + if (psds->read_block * psds->samplesperblock > psds->frames) + { memset (psds->read_samples, 0, psds->samplesperblock * sizeof (int)) ; + return 1 ; + } ; + + if ((k = psf_fread (psds->read_data, 1, SDS_BLOCK_SIZE, psf)) != SDS_BLOCK_SIZE) + psf_log_printf (psf, "*** Warning : short read (%d != %d).\n", k, SDS_BLOCK_SIZE) ; + + if (psds->read_data [0] != 0xF0) + { printf ("Error A : %02X\n", psds->read_data [0] & 0xFF) ; + } ; + + checksum = psds->read_data [1] ; + if (checksum != 0x7E) + { printf ("Error 1 : %02X\n", checksum & 0xFF) ; + } + + for (k = 2 ; k < SDS_BLOCK_SIZE - 3 ; k ++) + checksum ^= psds->read_data [k] ; + + checksum &= 0x7F ; + + if (checksum != psds->read_data [SDS_BLOCK_SIZE - 2]) + { psf_log_printf (psf, "Block %d : checksum is %02X should be %02X\n", psds->read_data [4], checksum, psds->read_data [SDS_BLOCK_SIZE - 2]) ; + } ; + + ucptr = psds->read_data + 5 ; + for (k = 0 ; k < 120 ; k += 3) + { sample = (ucptr [k] << 25) + (ucptr [k + 1] << 18) + (ucptr [k + 2] << 11) ; + psds->read_samples [k / 3] = (int) (sample - 0x80000000) ; + } ; + + return 1 ; +} /* sds_3byte_read */ + +static int +sds_4byte_read (SF_PRIVATE *psf, SDS_PRIVATE *psds) +{ unsigned char *ucptr, checksum ; + unsigned int sample ; + int k ; + + psds->read_block ++ ; + psds->read_count = 0 ; + + if (psds->read_block * psds->samplesperblock > psds->frames) + { memset (psds->read_samples, 0, psds->samplesperblock * sizeof (int)) ; + return 1 ; + } ; + + if ((k = psf_fread (psds->read_data, 1, SDS_BLOCK_SIZE, psf)) != SDS_BLOCK_SIZE) + psf_log_printf (psf, "*** Warning : short read (%d != %d).\n", k, SDS_BLOCK_SIZE) ; + + if (psds->read_data [0] != 0xF0) + { printf ("Error A : %02X\n", psds->read_data [0] & 0xFF) ; + } ; + + checksum = psds->read_data [1] ; + if (checksum != 0x7E) + { printf ("Error 1 : %02X\n", checksum & 0xFF) ; + } + + for (k = 2 ; k < SDS_BLOCK_SIZE - 3 ; k ++) + checksum ^= psds->read_data [k] ; + + checksum &= 0x7F ; + + if (checksum != psds->read_data [SDS_BLOCK_SIZE - 2]) + { psf_log_printf (psf, "Block %d : checksum is %02X should be %02X\n", psds->read_data [4], checksum, psds->read_data [SDS_BLOCK_SIZE - 2]) ; + } ; + + ucptr = psds->read_data + 5 ; + for (k = 0 ; k < 120 ; k += 4) + { sample = (ucptr [k] << 25) + (ucptr [k + 1] << 18) + (ucptr [k + 2] << 11) + (ucptr [k + 3] << 4) ; + psds->read_samples [k / 4] = (int) (sample - 0x80000000) ; + } ; + + return 1 ; +} /* sds_4byte_read */ + + +static sf_count_t +sds_read_s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ SDS_PRIVATE *psds ; + int *iptr ; + int k, bufferlen, readcount, count ; + sf_count_t total = 0 ; + + if (psf->fdata == NULL) + return 0 ; + psds = (SDS_PRIVATE*) psf->fdata ; + + iptr = psf->u.ibuf ; + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : len ; + count = sds_read (psf, psds, iptr, readcount) ; + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = iptr [k] >> 16 ; + total += count ; + len -= readcount ; + } ; + + return total ; +} /* sds_read_s */ + +static sf_count_t +sds_read_i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ SDS_PRIVATE *psds ; + int total ; + + if (psf->fdata == NULL) + return 0 ; + psds = (SDS_PRIVATE*) psf->fdata ; + + total = sds_read (psf, psds, ptr, len) ; + + return total ; +} /* sds_read_i */ + +static sf_count_t +sds_read_f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ SDS_PRIVATE *psds ; + int *iptr ; + int k, bufferlen, readcount, count ; + sf_count_t total = 0 ; + float normfact ; + + if (psf->fdata == NULL) + return 0 ; + psds = (SDS_PRIVATE*) psf->fdata ; + + if (psf->norm_float == SF_TRUE) + normfact = 1.0 / 0x80000000 ; + else + normfact = 1.0 / (1 << psds->bitwidth) ; + + iptr = psf->u.ibuf ; + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : len ; + count = sds_read (psf, psds, iptr, readcount) ; + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = normfact * iptr [k] ; + total += count ; + len -= readcount ; + } ; + + return total ; +} /* sds_read_f */ + +static sf_count_t +sds_read_d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ SDS_PRIVATE *psds ; + int *iptr ; + int k, bufferlen, readcount, count ; + sf_count_t total = 0 ; + double normfact ; + + if (psf->fdata == NULL) + return 0 ; + psds = (SDS_PRIVATE*) psf->fdata ; + + if (psf->norm_double == SF_TRUE) + normfact = 1.0 / 0x80000000 ; + else + normfact = 1.0 / (1 << psds->bitwidth) ; + + iptr = psf->u.ibuf ; + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : len ; + count = sds_read (psf, psds, iptr, readcount) ; + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = normfact * iptr [k] ; + total += count ; + len -= readcount ; + } ; + + return total ; +} /* sds_read_d */ + +static int +sds_read (SF_PRIVATE *psf, SDS_PRIVATE *psds, int *ptr, int len) +{ int count, total = 0 ; + + while (total < len) + { if (psds->read_block * psds->samplesperblock >= psds->frames) + { memset (&(ptr [total]), 0, (len - total) * sizeof (int)) ; + return total ; + } ; + + if (psds->read_count >= psds->samplesperblock) + psds->reader (psf, psds) ; + + count = (psds->samplesperblock - psds->read_count) ; + count = (len - total > count) ? count : len - total ; + + memcpy (&(ptr [total]), &(psds->read_samples [psds->read_count]), count * sizeof (int)) ; + total += count ; + psds->read_count += count ; + } ; + + return total ; +} /* sds_read */ + +/*============================================================================== +*/ + +static sf_count_t +sds_seek (SF_PRIVATE *psf, int mode, sf_count_t seek_from_start) +{ SDS_PRIVATE *psds ; + sf_count_t file_offset ; + int newblock, newsample ; + + if ((psds = psf->fdata) == NULL) + { psf->error = SFE_INTERNAL ; + return PSF_SEEK_ERROR ; + } ; + + if (psf->datalength < 0 || psf->dataoffset < 0) + { psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; + } ; + + if (seek_from_start < 0 || seek_from_start > psf->sf.frames) + { psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; + } ; + + if (mode == SFM_READ && psds->write_count > 0) + psds->writer (psf, psds) ; + + newblock = seek_from_start / psds->samplesperblock ; + newsample = seek_from_start % psds->samplesperblock ; + + switch (mode) + { case SFM_READ : + if (newblock > psds->total_blocks) + { psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; + } ; + + file_offset = psf->dataoffset + newblock * SDS_BLOCK_SIZE ; + + if (psf_fseek (psf, file_offset, SEEK_SET) != file_offset) + { psf->error = SFE_SEEK_FAILED ; + return PSF_SEEK_ERROR ; + } ; + + psds->read_block = newblock ; + psds->reader (psf, psds) ; + psds->read_count = newsample ; + break ; + + case SFM_WRITE : + if (newblock > psds->total_blocks) + { psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; + } ; + + file_offset = psf->dataoffset + newblock * SDS_BLOCK_SIZE ; + + if (psf_fseek (psf, file_offset, SEEK_SET) != file_offset) + { psf->error = SFE_SEEK_FAILED ; + return PSF_SEEK_ERROR ; + } ; + + psds->write_block = newblock ; + psds->reader (psf, psds) ; + psds->write_count = newsample ; + break ; + + default : + psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; + break ; + } ; + + return seek_from_start ; +} /* sds_seek */ + +/*============================================================================== +*/ + +static int +sds_2byte_write (SF_PRIVATE *psf, SDS_PRIVATE *psds) +{ unsigned char *ucptr, checksum ; + unsigned int sample ; + int k ; + + psds->write_data [0] = 0xF0 ; + psds->write_data [1] = 0x7E ; + psds->write_data [2] = 0 ; /* Channel number */ + psds->write_data [3] = psds->write_block & 0x7F ; /* Packet number */ + + ucptr = psds->write_data + 5 ; + for (k = 0 ; k < 120 ; k += 2) + { sample = psds->write_samples [k / 2] ; + sample += 0x80000000 ; + ucptr [k] = (sample >> 25) & 0x7F ; + ucptr [k + 1] = (sample >> 18) & 0x7F ; + } ; + + checksum = psds->write_data [1] ; + for (k = 2 ; k < SDS_BLOCK_SIZE - 3 ; k ++) + checksum ^= psds->write_data [k] ; + checksum &= 0x7F ; + + psds->write_data [SDS_BLOCK_SIZE - 2] = checksum ; + psds->write_data [SDS_BLOCK_SIZE - 1] = 0xF7 ; + + if ((k = psf_fwrite (psds->write_data, 1, SDS_BLOCK_SIZE, psf)) != SDS_BLOCK_SIZE) + psf_log_printf (psf, "*** Warning : psf_fwrite (%d != %d).\n", k, SDS_BLOCK_SIZE) ; + + psds->write_block ++ ; + psds->write_count = 0 ; + + if (psds->write_block > psds->total_blocks) + psds->total_blocks = psds->write_block ; + psds->frames = psds->total_blocks * psds->samplesperblock ; + + return 1 ; +} /* sds_2byte_write */ + +static int +sds_3byte_write (SF_PRIVATE *psf, SDS_PRIVATE *psds) +{ unsigned char *ucptr, checksum ; + unsigned int sample ; + int k ; + + psds->write_data [0] = 0xF0 ; + psds->write_data [1] = 0x7E ; + psds->write_data [2] = 0 ; /* Channel number */ + psds->write_data [3] = psds->write_block & 0x7F ; /* Packet number */ + + ucptr = psds->write_data + 5 ; + for (k = 0 ; k < 120 ; k += 3) + { sample = psds->write_samples [k / 3] ; + sample += 0x80000000 ; + ucptr [k] = (sample >> 25) & 0x7F ; + ucptr [k + 1] = (sample >> 18) & 0x7F ; + ucptr [k + 2] = (sample >> 11) & 0x7F ; + } ; + + checksum = psds->write_data [1] ; + for (k = 2 ; k < SDS_BLOCK_SIZE - 3 ; k ++) + checksum ^= psds->write_data [k] ; + checksum &= 0x7F ; + + psds->write_data [SDS_BLOCK_SIZE - 2] = checksum ; + psds->write_data [SDS_BLOCK_SIZE - 1] = 0xF7 ; + + if ((k = psf_fwrite (psds->write_data, 1, SDS_BLOCK_SIZE, psf)) != SDS_BLOCK_SIZE) + psf_log_printf (psf, "*** Warning : psf_fwrite (%d != %d).\n", k, SDS_BLOCK_SIZE) ; + + psds->write_block ++ ; + psds->write_count = 0 ; + + if (psds->write_block > psds->total_blocks) + psds->total_blocks = psds->write_block ; + psds->frames = psds->total_blocks * psds->samplesperblock ; + + return 1 ; +} /* sds_3byte_write */ + +static int +sds_4byte_write (SF_PRIVATE *psf, SDS_PRIVATE *psds) +{ unsigned char *ucptr, checksum ; + unsigned int sample ; + int k ; + + psds->write_data [0] = 0xF0 ; + psds->write_data [1] = 0x7E ; + psds->write_data [2] = 0 ; /* Channel number */ + psds->write_data [3] = psds->write_block & 0x7F ; /* Packet number */ + + ucptr = psds->write_data + 5 ; + for (k = 0 ; k < 120 ; k += 4) + { sample = psds->write_samples [k / 4] ; + sample += 0x80000000 ; + ucptr [k] = (sample >> 25) & 0x7F ; + ucptr [k + 1] = (sample >> 18) & 0x7F ; + ucptr [k + 2] = (sample >> 11) & 0x7F ; + ucptr [k + 3] = (sample >> 4) & 0x7F ; + } ; + + checksum = psds->write_data [1] ; + for (k = 2 ; k < SDS_BLOCK_SIZE - 3 ; k ++) + checksum ^= psds->write_data [k] ; + checksum &= 0x7F ; + + psds->write_data [SDS_BLOCK_SIZE - 2] = checksum ; + psds->write_data [SDS_BLOCK_SIZE - 1] = 0xF7 ; + + if ((k = psf_fwrite (psds->write_data, 1, SDS_BLOCK_SIZE, psf)) != SDS_BLOCK_SIZE) + psf_log_printf (psf, "*** Warning : psf_fwrite (%d != %d).\n", k, SDS_BLOCK_SIZE) ; + + psds->write_block ++ ; + psds->write_count = 0 ; + + if (psds->write_block > psds->total_blocks) + psds->total_blocks = psds->write_block ; + psds->frames = psds->total_blocks * psds->samplesperblock ; + + return 1 ; +} /* sds_4byte_write */ + +static sf_count_t +sds_write_s (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ SDS_PRIVATE *psds ; + int *iptr ; + int k, bufferlen, writecount, count ; + sf_count_t total = 0 ; + + if (psf->fdata == NULL) + return 0 ; + psds = (SDS_PRIVATE*) psf->fdata ; + + iptr = psf->u.ibuf ; + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : len ; + for (k = 0 ; k < writecount ; k++) + iptr [k] = ptr [total + k] << 16 ; + count = sds_write (psf, psds, iptr, writecount) ; + total += count ; + len -= writecount ; + } ; + + return total ; +} /* sds_write_s */ + +static sf_count_t +sds_write_i (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ SDS_PRIVATE *psds ; + int total ; + + if (psf->fdata == NULL) + return 0 ; + psds = (SDS_PRIVATE*) psf->fdata ; + + total = sds_write (psf, psds, ptr, len) ; + + return total ; +} /* sds_write_i */ + +static sf_count_t +sds_write_f (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ SDS_PRIVATE *psds ; + int *iptr ; + int k, bufferlen, writecount, count ; + sf_count_t total = 0 ; + float normfact ; + + if (psf->fdata == NULL) + return 0 ; + psds = (SDS_PRIVATE*) psf->fdata ; + + if (psf->norm_float == SF_TRUE) + normfact = 1.0 * 0x80000000 ; + else + normfact = 1.0 * (1 << psds->bitwidth) ; + + iptr = psf->u.ibuf ; + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : len ; + for (k = 0 ; k < writecount ; k++) + iptr [k] = normfact * ptr [total + k] ; + count = sds_write (psf, psds, iptr, writecount) ; + total += count ; + len -= writecount ; + } ; + + return total ; +} /* sds_write_f */ + +static sf_count_t +sds_write_d (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ SDS_PRIVATE *psds ; + int *iptr ; + int k, bufferlen, writecount, count ; + sf_count_t total = 0 ; + double normfact ; + + if (psf->fdata == NULL) + return 0 ; + psds = (SDS_PRIVATE*) psf->fdata ; + + if (psf->norm_double == SF_TRUE) + normfact = 1.0 * 0x80000000 ; + else + normfact = 1.0 * (1 << psds->bitwidth) ; + + iptr = psf->u.ibuf ; + bufferlen = ARRAY_LEN (psf->u.ibuf) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : len ; + for (k = 0 ; k < writecount ; k++) + iptr [k] = normfact * ptr [total + k] ; + count = sds_write (psf, psds, iptr, writecount) ; + total += count ; + len -= writecount ; + } ; + + return total ; +} /* sds_write_d */ + +static int +sds_write (SF_PRIVATE *psf, SDS_PRIVATE *psds, const int *ptr, int len) +{ int count, total = 0 ; + + while (total < len) + { count = psds->samplesperblock - psds->write_count ; + if (count > len - total) + count = len - total ; + + memcpy (&(psds->write_samples [psds->write_count]), &(ptr [total]), count * sizeof (int)) ; + total += count ; + psds->write_count += count ; + + if (psds->write_count >= psds->samplesperblock) + psds->writer (psf, psds) ; + } ; + + return total ; +} /* sds_write */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: d5d26aa3-368c-4ca6-bb85-377e5a2578cc +*/ diff --git a/libs/libsndfile/src/sf_unistd.h b/libs/libsndfile/src/sf_unistd.h new file mode 100644 index 0000000000..f24ae67e98 --- /dev/null +++ b/libs/libsndfile/src/sf_unistd.h @@ -0,0 +1,67 @@ +/* +** Copyright (C) 2002-2004 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +/* Some defines that microsoft 'forgot' to implement. */ + +#ifndef S_IRWXU +#define S_IRWXU 0000700 /* rwx, owner */ +#endif + +#ifndef S_IRUSR +#define S_IRUSR 0000400 /* read permission, owner */ +#endif + +#ifndef S_IWUSR +#define S_IWUSR 0000200 /* write permission, owner */ +#endif + +#ifndef S_IXUSR +#define S_IXUSR 0000100 /* execute/search permission, owner */ +#endif + +#define S_IRWXG 0000070 /* rwx, group */ +#define S_IRGRP 0000040 /* read permission, group */ +#define S_IWGRP 0000020 /* write permission, grougroup */ +#define S_IXGRP 0000010 /* execute/search permission, group */ + +#define S_IRWXO 0000007 /* rwx, other */ +#define S_IROTH 0000004 /* read permission, other */ +#define S_IWOTH 0000002 /* write permission, other */ +#define S_IXOTH 0000001 /* execute/search permission, other */ + +#ifndef S_ISFIFO +#define S_ISFIFO(mode) (((mode) & _S_IFMT) == _S_IFIFO) +#endif + +#ifndef S_ISREG +#define S_ISREG(mode) (((mode) & _S_IFREG) == _S_IFREG) +#endif + +/* +** Don't know if these are still needed. +** +** #define _IFMT _S_IFMT +** #define _IFREG _S_IFREG +*/ +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 253aea6d-6299-46fd-8d06-bc5f6224c8fe +*/ diff --git a/libs/libsndfile/src/sfconfig.h b/libs/libsndfile/src/sfconfig.h new file mode 100644 index 0000000000..f12df6d787 --- /dev/null +++ b/libs/libsndfile/src/sfconfig.h @@ -0,0 +1,108 @@ +/* +** Copyright (C) 2005 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +/* +** Autoconf leaves many config parameters undefined. +** Here we change then from being undefined to defining them to 0. +** This allows things like: +** +** #if HAVE_CONFIG_PARAM +** +** and +** +** if (HAVE_CONFIG_PARAM) +** do_something () ; +*/ + +#ifndef SFCONFIG_H +#define SFCONFIG_H + +/* Include the Autoconf generated file. */ +#include "config.h" + +/* Now fiddle the values. */ + +#ifndef HAVE_ALSA_ASOUNDLIB_H +#define HAVE_ALSA_ASOUNDLIB_H 0 +#endif + +#ifndef HAVE_BYTESWAP_H +#define HAVE_BYTESWAP_H 0 +#endif + +#ifndef HAVE_DECL_S_IRGRP +#define HAVE_DECL_S_IRGRP 0 +#endif + +#ifndef HAVE_ENDIAN_H +#define HAVE_ENDIAN_H 0 +#endif + +#ifndef HAVE_FSYNC +#define HAVE_FSYNC 0 +#endif + +#ifndef HAVE_LOCALE_H +#define HAVE_LOCALE_H 0 +#endif + +#ifndef HAVE_LRINT +#define HAVE_LRINT 0 +#endif + +#ifndef HAVE_LRINTF +#define HAVE_LRINTF 0 +#endif + +#ifndef HAVE_MMAP +#define HAVE_MMAP 0 +#endif + +#ifndef HAVE_PREAD +#define HAVE_PREAD 0 +#endif + +#ifndef HAVE_PWRITE +#define HAVE_PWRITE 0 +#endif + +#ifndef HAVE_SETLOCALE +#define HAVE_SETLOCALE 0 +#endif + +#ifndef HAVE_SQLITE3 +#define HAVE_SQLITE3 0 +#endif + +#ifndef HAVE_STDINT_H +#define HAVE_STDINT_H 0 +#endif + +#ifndef HAVE_UNISTD_H +#define HAVE_UNISTD_H 0 +#endif + +#endif + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 2df2316e-8f9d-4860-bba7-f3c16c63eed3 +*/ diff --git a/libs/libsndfile/src/sfendian.h b/libs/libsndfile/src/sfendian.h new file mode 100644 index 0000000000..efc1c1060a --- /dev/null +++ b/libs/libsndfile/src/sfendian.h @@ -0,0 +1,256 @@ +/* +** Copyright (C) 1999-2006 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#if HAVE_STDINT_H +#include +#elif HAVE_INTTYPES_H +#include +#endif + +#if (defined (SIZEOF_INT64_T) && (SIZEOF_INT64_T == 8)) +/* Good, we have int64_t. */ +#elif (defined (SIZEOF_LONG_LONG) && (SIZEOF_LONG_LONG == 8)) +typedef long long int64_t ; +#elif (defined (SIZEOF_LONG) && (SIZEOF_LONG == 8)) +typedef long int64_t ; +#elif (defined (WIN32) || defined (_WIN32)) +typedef __int64 int64_t ; +#else +#error "No 64 bit integer type." +#endif + +#if HAVE_BYTESWAP_H + +#include + +#define ENDSWAP_SHORT(x) ((short) bswap_16 (x)) +#define ENDSWAP_INT(x) ((int) bswap_32 (x)) + +#else + +#define ENDSWAP_SHORT(x) ((((x) >> 8) & 0xFF) + (((x) & 0xFF) << 8)) +#define ENDSWAP_INT(x) ((((x) >> 24) & 0xFF) + (((x) >> 8) & 0xFF00) + (((x) & 0xFF00) << 8) + (((x) & 0xFF) << 24)) + +#endif + +/* +** Many file types (ie WAV, AIFF) use sets of four consecutive bytes as a +** marker indicating different sections of the file. +** The following MAKE_MARKER macro allows th creation of integer constants +** for these markers. +*/ + +#if (CPU_IS_LITTLE_ENDIAN == 1) + #define MAKE_MARKER(a,b,c,d) ((a) | ((b) << 8) | ((c) << 16) | ((d) << 24)) +#elif (CPU_IS_BIG_ENDIAN == 1) + #define MAKE_MARKER(a,b,c,d) (((a) << 24) | ((b) << 16) | ((c) << 8) | (d)) +#else + #error "Target CPU endian-ness unknown. May need to hand edit src/sfconfig.h" +#endif + +/* +** Macros to handle reading of data of a specific endian-ness into host endian +** shorts and ints. The single input is an unsigned char* pointer to the start +** of the object. There are two versions of each macro as we need to deal with +** both big and little endian CPUs. +*/ + +#if (CPU_IS_LITTLE_ENDIAN == 1) + #define LES2H_SHORT(x) (x) + #define LEI2H_INT(x) (x) + + #define BES2H_SHORT(x) ENDSWAP_SHORT (x) + #define BEI2H_INT(x) ENDSWAP_INT (x) + + #define H2BE_SHORT(x) ENDSWAP_SHORT (x) + #define H2BE_INT(x) ENDSWAP_INT (x) + +#elif (CPU_IS_BIG_ENDIAN == 1) + #define LES2H_SHORT(x) ENDSWAP_SHORT (x) + #define LEI2H_INT(x) ENDSWAP_INT (x) + + #define BES2H_SHORT(x) (x) + #define BEI2H_INT(x) (x) + + #define H2LE_SHORT(x) ENDSWAP_SHORT (x) + #define H2LE_INT(x) ENDSWAP_INT (x) + +#else + #error "Target CPU endian-ness unknown. May need to hand edit src/sfconfig.h" +#endif + +#define LET2H_SHORT_PTR(x) ((x) [1] + ((x) [2] << 8)) +#define LET2H_INT_PTR(x) (((x) [0] << 8) + ((x) [1] << 16) + ((x) [2] << 24)) + +#define BET2H_SHORT_PTR(x) (((x) [0] << 8) + (x) [1]) +#define BET2H_INT_PTR(x) (((x) [0] << 24) + ((x) [1] << 16) + ((x) [2] << 8)) + +/*----------------------------------------------------------------------------------------------- +** Generic functions for performing endian swapping on integer arrays. +*/ + +static inline void +endswap_short_array (short *ptr, int len) +{ short temp ; + + while (--len >= 0) + { temp = ptr [len] ; + ptr [len] = ENDSWAP_SHORT (temp) ; + } ; +} /* endswap_short_array */ + +static inline void +endswap_short_copy (short *dest, const short *src, int len) +{ + while (--len >= 0) + { dest [len] = ENDSWAP_SHORT (src [len]) ; + } ; +} /* endswap_short_copy */ + +static inline void +endswap_int_array (int *ptr, int len) +{ int temp ; + + while (--len >= 0) + { temp = ptr [len] ; + ptr [len] = ENDSWAP_INT (temp) ; + } ; +} /* endswap_int_array */ + +static inline void +endswap_int_copy (int *dest, const int *src, int len) +{ + while (--len >= 0) + { dest [len] = ENDSWAP_INT (src [len]) ; + } ; +} /* endswap_int_copy */ + +/*======================================================================================== +*/ + +#if (HAVE_BYTESWAP_H && defined (SIZEOF_INT64_T) && (SIZEOF_INT64_T == 8)) + +static inline void +endswap_int64_t_array (int64_t *ptr, int len) +{ int64_t value ; + + while (--len >= 0) + { value = ptr [len] ; + ptr [len] = bswap_64 (value) ; + } ; +} /* endswap_int64_t_array */ + +static inline void +endswap_int64_t_copy (int64_t *dest, const int64_t *src, int len) +{ int64_t value ; + + while (--len >= 0) + { value = src [len] ; + dest [len] = bswap_64 (value) ; + } ; +} /* endswap_int64_t_copy */ + +#else + +static inline void +endswap_int64_t_array (int64_t *ptr, int len) +{ unsigned char *ucptr, temp ; + + ucptr = (unsigned char *) ptr ; + ucptr += 8 * len ; + while (--len >= 0) + { ucptr -= 8 ; + + temp = ucptr [0] ; + ucptr [0] = ucptr [7] ; + ucptr [7] = temp ; + + temp = ucptr [1] ; + ucptr [1] = ucptr [6] ; + ucptr [6] = temp ; + + temp = ucptr [2] ; + ucptr [2] = ucptr [5] ; + ucptr [5] = temp ; + + temp = ucptr [3] ; + ucptr [3] = ucptr [4] ; + ucptr [4] = temp ; + } ; +} /* endswap_int64_t_array */ + +static inline void +endswap_int64_t_copy (int64_t *dest, const int64_t *src, int len) +{ const unsigned char *psrc ; + unsigned char *pdest ; + + if (dest == src) + { endswap_int64_t_array (dest, len) ; + return ; + } ; + + psrc = ((const unsigned char *) src) + 8 * len ; + pdest = ((unsigned char *) dest) + 8 * len ; + while (--len >= 0) + { psrc -= 8 ; + pdest -= 8 ; + + pdest [0] = psrc [7] ; + pdest [2] = psrc [5] ; + pdest [4] = psrc [3] ; + pdest [6] = psrc [1] ; + pdest [7] = psrc [0] ; + pdest [1] = psrc [6] ; + pdest [3] = psrc [4] ; + pdest [5] = psrc [2] ; + } ; +} /* endswap_int64_t_copy */ + +#endif + +/* A couple of wrapper functions. */ + +static inline void +endswap_float_array (float *ptr, int len) +{ endswap_int_array ((void *) ptr, len) ; +} /* endswap_float_array */ + +static inline void +endswap_double_array (double *ptr, int len) +{ endswap_int64_t_array ((void *) ptr, len) ; +} /* endswap_double_array */ + +static inline void +endswap_float_copy (float *dest, const float *src, int len) +{ endswap_int_copy ((int *) dest, (const int *) src, len) ; +} /* endswap_float_copy */ + +static inline void +endswap_double_copy (double *dest, const double *src, int len) +{ endswap_int64_t_copy ((int64_t *) dest, (const int64_t *) src, len) ; +} /* endswap_double_copy */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: f0c5cd54-42d3-4237-90ec-11fe24995de7 +*/ diff --git a/libs/libsndfile/src/sndfile.c b/libs/libsndfile/src/sndfile.c new file mode 100644 index 0000000000..c30d7b61b4 --- /dev/null +++ b/libs/libsndfile/src/sndfile.c @@ -0,0 +1,2694 @@ +/* +** Copyright (C) 1999-2005 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" + +#define SNDFILE_MAGICK 0x1234C0DE + +typedef struct +{ int error ; + const char *str ; +} ErrorStruct ; + +static +ErrorStruct SndfileErrors [] = +{ + /* Public error values and their associated strings. */ + { SF_ERR_NO_ERROR , "No Error." }, + { SF_ERR_UNRECOGNISED_FORMAT , "File opened for read. Format not recognised." }, + { SF_ERR_SYSTEM , "System error." /* Often replaced. */ }, + { SF_ERR_MALFORMED_FILE , "Supported file format but file is malformed." }, + { SF_ERR_UNSUPPORTED_ENCODING , "Supported file format but unsupported encoding." }, + + /* Private error values and their associated strings. */ + { SFE_BAD_FILE , "File does not exist or is not a regular file (possibly a pipe?)." }, + { SFE_BAD_FILE_READ , "File exists but no data could be read." }, + { SFE_OPEN_FAILED , "Could not open file." }, + { SFE_BAD_SNDFILE_PTR , "Not a valid SNDFILE* pointer." }, + { SFE_BAD_SF_INFO_PTR , "NULL SF_INFO pointer passed to libsndfile." }, + { SFE_BAD_SF_INCOMPLETE , "SF_PRIVATE struct incomplete and end of header parsing." }, + { SFE_BAD_FILE_PTR , "Bad FILE pointer." }, + { SFE_BAD_INT_PTR , "Internal error, Bad pointer." }, + { SFE_BAD_STAT_SIZE , "Error : software was misconfigured at compile time (sizeof statbuf.st_size)." }, + + { SFE_MALLOC_FAILED , "Internal malloc () failed." }, + { SFE_UNIMPLEMENTED , "File contains data in an unimplemented format." }, + { SFE_BAD_READ_ALIGN , "Attempt to read a non-integer number of channels." }, + { SFE_BAD_WRITE_ALIGN , "Attempt to write a non-integer number of channels." }, + { SFE_UNKNOWN_FORMAT , "File contains data in an unknown format." }, + { SFE_NOT_READMODE , "Read attempted on file currently open for write." }, + { SFE_NOT_WRITEMODE , "Write attempted on file currently open for read." }, + { SFE_BAD_MODE_RW , "This file format does not support read/write mode." }, + { SFE_BAD_SF_INFO , "Internal error : SF_INFO struct incomplete." }, + { SFE_BAD_OFFSET , "Error : supplied offset beyond end of file." }, + { SFE_NO_EMBED_SUPPORT , "Error : embedding not supported for this file format." }, + { SFE_NO_EMBEDDED_RDWR , "Error : cannot open embedded file read/write." }, + { SFE_NO_PIPE_WRITE , "Error : this file format does not support pipe write." }, + { SFE_BAD_RDWR_FORMAT , "Attempted to open read only format for RDWR." }, + { SFE_BAD_VIRTUAL_IO , "Error : bad pointer on SF_VIRTUAL_IO struct." }, + + { SFE_INTERLEAVE_MODE , "Attempt to write to file with non-interleaved data." }, + { SFE_INTERLEAVE_SEEK , "Bad karma in seek during interleave read operation." }, + { SFE_INTERLEAVE_READ , "Bad karma in read during interleave read operation." }, + + { SFE_INTERNAL , "Unspecified internal error." }, + { SFE_BAD_CONTROL_CMD , "Bad command passed to function sf_command()." }, + { SFE_BAD_ENDIAN , "Bad endian-ness. Try default endian-ness" }, + { SFE_CHANNEL_COUNT , "Too many channels specified." }, + + { SFE_BAD_SEEK , "Internal psf_fseek() failed." }, + { SFE_NOT_SEEKABLE , "Seek attempted on unseekable file type." }, + { SFE_AMBIGUOUS_SEEK , "Error : combination of file open mode and seek command is ambiguous." }, + { SFE_WRONG_SEEK , "Error : invalid seek parameters." }, + { SFE_SEEK_FAILED , "Error : parameters OK, but psf_seek() failed." }, + + { SFE_BAD_OPEN_MODE , "Error : bad mode parameter for file open." }, + { SFE_OPEN_PIPE_RDWR , "Error : attempt toopen a pipe in read/write mode." }, + { SFE_RDWR_POSITION , "Error on RDWR position (cryptic)." }, + { SFE_RDWR_BAD_HEADER , "Error : Cannot open file in read/write mode due to string data in header." }, + + { SFE_STR_NO_SUPPORT , "Error : File type does not support string data." }, + { SFE_STR_NOT_WRITE , "Error : Trying to set a string when file is not in write mode." }, + { SFE_STR_MAX_DATA , "Error : Maximum string data storage reached." }, + { SFE_STR_MAX_COUNT , "Error : Maximum string data count reached." }, + { SFE_STR_BAD_TYPE , "Error : Bad string data type." }, + { SFE_STR_NO_ADD_END , "Error : file type does not support strings added at end of file." }, + { SFE_STR_BAD_STRING , "Error : bad string." }, + { SFE_STR_WEIRD , "Error : Weird string error." }, + + { SFE_WAV_NO_RIFF , "Error in WAV file. No 'RIFF' chunk marker." }, + { SFE_WAV_NO_WAVE , "Error in WAV file. No 'WAVE' chunk marker." }, + { SFE_WAV_NO_FMT , "Error in WAV file. No 'fmt ' chunk marker." }, + { SFE_WAV_FMT_SHORT , "Error in WAV file. Short 'fmt ' chunk." }, + + { SFE_WAV_BAD_FACT , "Error in WAV file. 'fact' chunk out of place." }, + { SFE_WAV_BAD_PEAK , "Error in WAV file. Bad 'PEAK' chunk." }, + { SFE_WAV_PEAK_B4_FMT , "Error in WAV file. 'PEAK' chunk found before 'fmt ' chunk." }, + + { SFE_WAV_BAD_FORMAT , "Error in WAV file. Errors in 'fmt ' chunk." }, + { SFE_WAV_BAD_BLOCKALIGN , "Error in WAV file. Block alignment in 'fmt ' chunk is incorrect." }, + { SFE_WAV_NO_DATA , "Error in WAV file. No 'data' chunk marker." }, + { SFE_WAV_BAD_LIST , "Error in WAV file. Malformed LIST chunk." }, + { SFE_WAV_UNKNOWN_CHUNK , "Error in WAV file. File contains an unknown chunk marker." }, + { SFE_WAV_WVPK_DATA , "Error in WAV file. Data is in WAVPACK format." }, + + { SFE_WAV_ADPCM_NOT4BIT , "Error in ADPCM WAV file. Invalid bit width." }, + { SFE_WAV_ADPCM_CHANNELS , "Error in ADPCM WAV file. Invalid number of channels." }, + { SFE_WAV_GSM610_FORMAT , "Error in GSM610 WAV file. Invalid format chunk." }, + + { SFE_AIFF_NO_FORM , "Error in AIFF file, bad 'FORM' marker." }, + { SFE_AIFF_AIFF_NO_FORM , "Error in AIFF file, 'AIFF' marker without 'FORM'." }, + { SFE_AIFF_COMM_NO_FORM , "Error in AIFF file, 'COMM' marker without 'FORM'." }, + { SFE_AIFF_SSND_NO_COMM , "Error in AIFF file, 'SSND' marker without 'COMM'." }, + { SFE_AIFF_UNKNOWN_CHUNK , "Error in AIFF file, unknown chunk." }, + { SFE_AIFF_COMM_CHUNK_SIZE, "Error in AIFF file, bad 'COMM' chunk size." }, + { SFE_AIFF_BAD_COMM_CHUNK , "Error in AIFF file, bad 'COMM' chunk." }, + { SFE_AIFF_PEAK_B4_COMM , "Error in AIFF file. 'PEAK' chunk found before 'COMM' chunk." }, + { SFE_AIFF_BAD_PEAK , "Error in AIFF file. Bad 'PEAK' chunk." }, + { SFE_AIFF_NO_SSND , "Error in AIFF file, bad 'SSND' chunk." }, + { SFE_AIFF_NO_DATA , "Error in AIFF file, no sound data." }, + { SFE_AIFF_RW_SSND_NOT_LAST, "Error in AIFF file, RDWR only possible if SSND chunk at end of file." }, + + { SFE_AU_UNKNOWN_FORMAT , "Error in AU file, unknown format." }, + { SFE_AU_NO_DOTSND , "Error in AU file, missing '.snd' or 'dns.' marker." }, + { SFE_AU_EMBED_BAD_LEN , "Embedded AU file with unknown length." }, + + { SFE_RAW_READ_BAD_SPEC , "Error while opening RAW file for read. Must specify format and channels.\n" + "Possibly trying to open unsupported format." + }, + { SFE_RAW_BAD_BITWIDTH , "Error. RAW file bitwidth must be a multiple of 8." }, + { SFE_RAW_BAD_FORMAT , "Error. Bad format field in SF_INFO struct when openning a RAW file for read." }, + + { SFE_PAF_NO_MARKER , "Error in PAF file, no marker." }, + { SFE_PAF_VERSION , "Error in PAF file, bad version." }, + { SFE_PAF_UNKNOWN_FORMAT , "Error in PAF file, unknown format." }, + { SFE_PAF_SHORT_HEADER , "Error in PAF file. File shorter than minimal header." }, + + { SFE_SVX_NO_FORM , "Error in 8SVX / 16SV file, no 'FORM' marker." }, + { SFE_SVX_NO_BODY , "Error in 8SVX / 16SV file, no 'BODY' marker." }, + { SFE_SVX_NO_DATA , "Error in 8SVX / 16SV file, no sound data." }, + { SFE_SVX_BAD_COMP , "Error in 8SVX / 16SV file, unsupported compression format." }, + { SFE_SVX_BAD_NAME_LENGTH , "Error in 8SVX / 16SV file, NAME chunk too long." }, + + { SFE_NIST_BAD_HEADER , "Error in NIST file, bad header." }, + { SFE_NIST_CRLF_CONVERISON, "Error : NIST file damaged by Windows CR -> CRLF conversion process." }, + { SFE_NIST_BAD_ENCODING , "Error in NIST file, unsupported compression format." }, + + { SFE_VOC_NO_CREATIVE , "Error in VOC file, no 'Creative Voice File' marker." }, + { SFE_VOC_BAD_FORMAT , "Error in VOC file, bad format." }, + { SFE_VOC_BAD_VERSION , "Error in VOC file, bad version number." }, + { SFE_VOC_BAD_MARKER , "Error in VOC file, bad marker in file." }, + { SFE_VOC_BAD_SECTIONS , "Error in VOC file, incompatible VOC sections." }, + { SFE_VOC_MULTI_SAMPLERATE, "Error in VOC file, more than one sample rate defined." }, + { SFE_VOC_MULTI_SECTION , "Unimplemented VOC file feature, file contains multiple sound sections." }, + { SFE_VOC_MULTI_PARAM , "Error in VOC file, file contains multiple bit or channel widths." }, + { SFE_VOC_SECTION_COUNT , "Error in VOC file, too many sections." }, + { SFE_VOC_NO_PIPE , "Error : not able to operate on VOC files over a pipe." }, + + { SFE_IRCAM_NO_MARKER , "Error in IRCAM file, bad IRCAM marker." }, + { SFE_IRCAM_BAD_CHANNELS , "Error in IRCAM file, bad channel count." }, + { SFE_IRCAM_UNKNOWN_FORMAT, "Error in IRCAM file, unknow encoding format." }, + + { SFE_W64_64_BIT , "Error in W64 file, file contains 64 bit offset." }, + + { SFE_W64_NO_RIFF , "Error in W64 file. No 'riff' chunk marker." }, + { SFE_W64_NO_WAVE , "Error in W64 file. No 'wave' chunk marker." }, + { SFE_W64_NO_FMT , "Error in W64 file. No 'fmt ' chunk marker." }, + { SFE_W64_NO_DATA , "Error in W64 file. No 'data' chunk marker." }, + + { SFE_W64_FMT_SHORT , "Error in W64 file. Short 'fmt ' chunk." }, + { SFE_W64_FMT_TOO_BIG , "Error in W64 file. 'fmt ' chunk too large." }, + + { SFE_W64_ADPCM_NOT4BIT , "Error in ADPCM W64 file. Invalid bit width." }, + { SFE_W64_ADPCM_CHANNELS , "Error in ADPCM W64 file. Invalid number of channels." }, + { SFE_W64_GSM610_FORMAT , "Error in GSM610 W64 file. Invalid format chunk." }, + + { SFE_MAT4_BAD_NAME , "Error in MAT4 file. No variable name." }, + { SFE_MAT4_NO_SAMPLERATE , "Error in MAT4 file. No sample rate." }, + { SFE_MAT4_ZERO_CHANNELS , "Error in MAT4 file. Channel count is zero." }, + + { SFE_MAT5_BAD_ENDIAN , "Error in MAT5 file. Not able to determine endian-ness." }, + { SFE_MAT5_NO_BLOCK , "Error in MAT5 file. Bad block structure." }, + { SFE_MAT5_SAMPLE_RATE , "Error in MAT5 file. Not able to determine sample rate." }, + { SFE_MAT5_ZERO_CHANNELS , "Error in MAT5 file. Channel count is zero." }, + + { SFE_PVF_NO_PVF1 , "Error in PVF file. No PVF1 marker." }, + { SFE_PVF_BAD_HEADER , "Error in PVF file. Bad header." }, + { SFE_PVF_BAD_BITWIDTH , "Error in PVF file. Bad bit width." }, + + { SFE_XI_BAD_HEADER , "Error in XI file. Bad header." }, + { SFE_XI_EXCESS_SAMPLES , "Error in XI file. Excess samples in file." }, + { SFE_XI_NO_PIPE , "Error : not able to operate on XI files over a pipe." }, + + { SFE_HTK_NO_PIPE , "Error : not able to operate on HTK files over a pipe." }, + + { SFE_SDS_NOT_SDS , "Error : not an SDS file." }, + { SFE_SDS_BAD_BIT_WIDTH , "Error : bad bit width for SDS file." }, + + { SFE_SD2_FD_DISALLOWED , "Error : cannot open SD2 file without a file name." }, + { SFE_SD2_BAD_DATA_OFFSET , "Error : bad data offset." }, + { SFE_SD2_BAD_MAP_OFFSET , "Error : bad map offset." }, + { SFE_SD2_BAD_DATA_LENGTH , "Error : bad data length." }, + { SFE_SD2_BAD_MAP_LENGTH , "Error : bad map length." }, + { SFE_SD2_BAD_RSRC , "Error : bad resource fork." }, + { SFE_SD2_BAD_SAMPLE_SIZE , "Error : bad sample size." }, + + { SFE_FLAC_BAD_HEADER , "Error : bad flac header." }, + { SFE_FLAC_NEW_DECODER , "Error : problem while creating flac decoder." }, + { SFE_FLAC_INIT_DECODER , "Error : problem while initialization of the flac decoder." }, + { SFE_FLAC_LOST_SYNC , "Error : flac decoder lost sync." }, + { SFE_FLAC_BAD_SAMPLE_RATE, "Error : flac does not support this sample rate." }, + { SFE_FLAC_UNKOWN_ERROR , "Error : unkown error in flac decoder." }, + + { SFE_DWVW_BAD_BITWIDTH , "Error : Bad bit width for DWVW encoding. Must be 12, 16 or 24." }, + { SFE_G72X_NOT_MONO , "Error : G72x encoding does not support more than 1 channel." }, + + { SFE_MAX_ERROR , "Maximum error number." }, + { SFE_MAX_ERROR + 1 , NULL } +} ; + +/*------------------------------------------------------------------------------ +*/ + +static int format_from_extension (SF_PRIVATE *psf) ; +static int guess_file_type (SF_PRIVATE *psf) ; +static int validate_sfinfo (SF_INFO *sfinfo) ; +static int validate_psf (SF_PRIVATE *psf) ; +static void save_header_info (SF_PRIVATE *psf) ; +static void copy_filename (SF_PRIVATE *psf, const char *path) ; +static int psf_close (SF_PRIVATE *psf) ; +static int psf_open_file (SF_PRIVATE *psf, int mode, SF_INFO *sfinfo) ; + +static int try_resource_fork (SF_PRIVATE * psf, int mode) ; + +/*------------------------------------------------------------------------------ +** Private (static) variables. +*/ + +static int sf_errno = 0 ; +static char sf_logbuffer [SF_BUFFER_LEN] = { 0 } ; +static char sf_syserr [SF_SYSERR_LEN] = { 0 } ; + +/*------------------------------------------------------------------------------ +*/ + +#define VALIDATE_SNDFILE_AND_ASSIGN_PSF(a,b,c) \ + { if (! (a)) \ + { sf_errno = SFE_BAD_SNDFILE_PTR ; \ + return 0 ; \ + } ; \ + (b) = (SF_PRIVATE*) (a) ; \ + if ((b)->virtual_io == SF_FALSE && \ + psf_file_valid (b) == 0) \ + { (b)->error = SFE_BAD_FILE_PTR ; \ + return 0 ; \ + } ; \ + if ((b)->Magick != SNDFILE_MAGICK) \ + { (b)->error = SFE_BAD_SNDFILE_PTR ; \ + return 0 ; \ + } ; \ + if (c) (b)->error = 0 ; \ + } + +/*------------------------------------------------------------------------------ +** Public functions. +*/ + +SNDFILE* +sf_open (const char *path, int mode, SF_INFO *sfinfo) +{ SF_PRIVATE *psf ; + int error = 0 ; + + if ((psf = calloc (1, sizeof (SF_PRIVATE))) == NULL) + { sf_errno = SFE_MALLOC_FAILED ; + return NULL ; + } ; + + memset (psf, 0, sizeof (SF_PRIVATE)) ; + psf_init_files (psf) ; + + psf_log_printf (psf, "File : %s\n", path) ; + + copy_filename (psf, path) ; + + if (strcmp (path, "-") == 0) + error = psf_set_stdio (psf, mode) ; + else + error = psf_fopen (psf, path, mode) ; + + if (error == 0) + error = psf_open_file (psf, mode, sfinfo) ; + + if (error) + { sf_errno = error ; + if (error == SFE_SYSTEM) + LSF_SNPRINTF (sf_syserr, sizeof (sf_syserr), "%s", psf->syserr) ; + LSF_SNPRINTF (sf_logbuffer, sizeof (sf_logbuffer), "%s", psf->logbuffer) ; + psf_close (psf) ; + return NULL ; + } ; + + memcpy (sfinfo, &(psf->sf), sizeof (SF_INFO)) ; + + return (SNDFILE*) psf ; +} /* sf_open */ + +SNDFILE* +sf_open_fd (int fd, int mode, SF_INFO *sfinfo, int close_desc) +{ SF_PRIVATE *psf ; + int error ; + + if ((sfinfo->format & SF_FORMAT_TYPEMASK) == SF_FORMAT_SD2) + { sf_errno = SFE_SD2_FD_DISALLOWED ; + return NULL ; + } ; + + if ((psf = calloc (1, sizeof (SF_PRIVATE))) == NULL) + { sf_errno = SFE_MALLOC_FAILED ; + return NULL ; + } ; + + psf_init_files (psf) ; + + psf_set_file (psf, fd) ; + psf->is_pipe = psf_is_pipe (psf) ; + psf->fileoffset = psf_ftell (psf) ; + + if (! close_desc) + psf->do_not_close_descriptor = SF_TRUE ; + + error = psf_open_file (psf, mode, sfinfo) ; + + if (error) + { sf_errno = error ; + if (error == SFE_SYSTEM) + LSF_SNPRINTF (sf_syserr, sizeof (sf_syserr), "%s", psf->syserr) ; + LSF_SNPRINTF (sf_logbuffer, sizeof (sf_logbuffer), "%s", psf->logbuffer) ; + psf_close (psf) ; + return NULL ; + } ; + + memcpy (sfinfo, &(psf->sf), sizeof (SF_INFO)) ; + + return (SNDFILE*) psf ; +} /* sf_open_fd */ + +SNDFILE* +sf_open_virtual (SF_VIRTUAL_IO *sfvirtual, int mode, SF_INFO *sfinfo, void *user_data) +{ SF_PRIVATE *psf ; + int error = 0 ; + + /* Make sure we have a valid set ot virtual pointers. */ + if (sfvirtual->get_filelen == NULL || sfvirtual->seek == NULL || sfvirtual->tell == NULL) + { sf_errno = SFE_BAD_VIRTUAL_IO ; + LSF_SNPRINTF (sf_logbuffer, sizeof (sf_logbuffer), "Bad vio_get_filelen / vio_seek / vio_tell in SF_VIRTUAL_IO struct.\n") ; + return NULL ; + } ; + + if ((mode == SFM_READ || mode == SFM_RDWR) && sfvirtual->read == NULL) + { sf_errno = SFE_BAD_VIRTUAL_IO ; + LSF_SNPRINTF (sf_logbuffer, sizeof (sf_logbuffer), "Bad vio_read in SF_VIRTUAL_IO struct.\n") ; + return NULL ; + } ; + + if ((mode == SFM_WRITE || mode == SFM_RDWR) && sfvirtual->write == NULL) + { sf_errno = SFE_BAD_VIRTUAL_IO ; + LSF_SNPRINTF (sf_logbuffer, sizeof (sf_logbuffer), "Bad vio_write in SF_VIRTUAL_IO struct.\n") ; + return NULL ; + } ; + + if ((psf = calloc (1, sizeof (SF_PRIVATE))) == NULL) + { sf_errno = SFE_MALLOC_FAILED ; + return NULL ; + } ; + + psf_init_files (psf) ; + + psf->virtual_io = SF_TRUE ; + psf->vio = *sfvirtual ; + psf->vio_user_data = user_data ; + + psf->mode = mode ; + + error = psf_open_file (psf, mode, sfinfo) ; + + if (error) + { sf_errno = error ; + if (error == SFE_SYSTEM) + LSF_SNPRINTF (sf_syserr, sizeof (sf_syserr), "%s", psf->syserr) ; + LSF_SNPRINTF (sf_logbuffer, sizeof (sf_logbuffer), "%s", psf->logbuffer) ; + psf_close (psf) ; + return NULL ; + } ; + + memcpy (sfinfo, &(psf->sf), sizeof (SF_INFO)) ; + + return (SNDFILE*) psf ; +} /* sf_open_virtual */ + +int +sf_close (SNDFILE *sndfile) +{ SF_PRIVATE *psf ; + + VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 1) ; + + return psf_close (psf) ; +} /* sf_close */ + +void +sf_write_sync (SNDFILE *sndfile) +{ SF_PRIVATE *psf ; + + if ((psf = (SF_PRIVATE *) sndfile) == NULL) + return ; + + psf_fsync (psf) ; + + return ; +} /* sf_write_sync */ + +/*============================================================================== +*/ + +const char* +sf_error_number (int errnum) +{ static const char *bad_errnum = + "No error defined for this error number. This is a bug in libsndfile." ; + int k ; + + if (errnum == SFE_MAX_ERROR) + return SndfileErrors [0].str ; + + if (errnum < 0 || errnum > SFE_MAX_ERROR) + { /* This really shouldn't happen in release versions. */ + printf ("Not a valid error number (%d).\n", errnum) ; + return bad_errnum ; + } ; + + for (k = 0 ; SndfileErrors [k].str ; k++) + if (errnum == SndfileErrors [k].error) + return SndfileErrors [k].str ; + + return bad_errnum ; +} /* sf_error_number */ + +const char* +sf_strerror (SNDFILE *sndfile) +{ SF_PRIVATE *psf = NULL ; + int errnum ; + + if (! sndfile) + { errnum = sf_errno ; + if (errnum == SFE_SYSTEM && sf_syserr [0]) + return sf_syserr ; + } + else + { psf = (SF_PRIVATE *) sndfile ; + + if (psf->Magick != SNDFILE_MAGICK) + return "sf_strerror : Bad magic number." ; + + errnum = psf->error ; + + if (errnum == SFE_SYSTEM && psf->syserr [0]) + return psf->syserr ; + } ; + + return sf_error_number (errnum) ; +} /* sf_strerror */ + +/*------------------------------------------------------------------------------ +*/ + +int +sf_error (SNDFILE *sndfile) +{ SF_PRIVATE *psf ; + + if (! sndfile) + { if (sf_error != 0) + return sf_errno ; + return 0 ; + } ; + + VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 0) ; + + if (psf->error) + return psf->error ; + + return 0 ; +} /* sf_error */ + +/*------------------------------------------------------------------------------ +*/ + +int +sf_perror (SNDFILE *sndfile) +{ SF_PRIVATE *psf ; + int errnum ; + + if (! sndfile) + { errnum = sf_errno ; + } + else + { VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 0) ; + errnum = psf->error ; + } ; + + fprintf (stderr, "%s\n", sf_error_number (errnum)) ; + return SFE_NO_ERROR ; +} /* sf_perror */ + + +/*------------------------------------------------------------------------------ +*/ + +int +sf_error_str (SNDFILE *sndfile, char *str, size_t maxlen) +{ SF_PRIVATE *psf ; + int errnum ; + + if (! str) + return SFE_INTERNAL ; + + if (! sndfile) + errnum = sf_errno ; + else + { VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 0) ; + errnum = psf->error ; + } ; + + LSF_SNPRINTF (str, maxlen, "%s", sf_error_number (errnum)) ; + + return SFE_NO_ERROR ; +} /* sf_error_str */ + +/*============================================================================== +*/ + +int +sf_format_check (const SF_INFO *info) +{ int subformat, endian ; + + subformat = info->format & SF_FORMAT_SUBMASK ; + endian = info->format & SF_FORMAT_ENDMASK ; + + /* This is the place where each file format can check if the suppiled + ** SF_INFO struct is valid. + ** Return 0 on failure, 1 ons success. + */ + + if (info->channels < 1 || info->channels > 256) + return 0 ; + + if (info->samplerate < 0) + return 0 ; + + switch (info->format & SF_FORMAT_TYPEMASK) + { case SF_FORMAT_WAV : + case SF_FORMAT_WAVEX : + /* WAV now allows both endian, RIFF or RIFX (little or big respectively) */ + if (subformat == SF_FORMAT_PCM_U8 || subformat == SF_FORMAT_PCM_16) + return 1 ; + if (subformat == SF_FORMAT_PCM_24 || subformat == SF_FORMAT_PCM_32) + return 1 ; + if ((subformat == SF_FORMAT_IMA_ADPCM || subformat == SF_FORMAT_MS_ADPCM) && info->channels <= 2) + return 1 ; + if (subformat == SF_FORMAT_GSM610 && info->channels == 1) + return 1 ; + if (subformat == SF_FORMAT_G721_32 && info->channels == 1) + return 1 ; + if (subformat == SF_FORMAT_ULAW || subformat == SF_FORMAT_ALAW) + return 1 ; + if (subformat == SF_FORMAT_FLOAT || subformat == SF_FORMAT_DOUBLE) + return 1 ; + break ; + + case SF_FORMAT_AIFF : + /* AIFF does allow both endian-nesses for PCM data.*/ + if (subformat == SF_FORMAT_PCM_16 || subformat == SF_FORMAT_PCM_24 || subformat == SF_FORMAT_PCM_32) + return 1 ; + /* Other encodings. Check for endian-ness. */ + if (endian == SF_ENDIAN_LITTLE || endian == SF_ENDIAN_CPU) + return 0 ; + if (subformat == SF_FORMAT_PCM_U8 || subformat == SF_FORMAT_PCM_S8) + return 1 ; + if (subformat == SF_FORMAT_FLOAT || subformat == SF_FORMAT_DOUBLE) + return 1 ; + if (subformat == SF_FORMAT_ULAW || subformat == SF_FORMAT_ALAW) + return 1 ; + if ((subformat == SF_FORMAT_DWVW_12 || subformat == SF_FORMAT_DWVW_16 || + subformat == SF_FORMAT_DWVW_24) && info-> channels == 1) + return 1 ; + if (subformat == SF_FORMAT_GSM610 && info->channels == 1) + return 1 ; + if (subformat == SF_FORMAT_IMA_ADPCM && (info->channels == 1 || info->channels == 2)) + return 1 ; + break ; + + case SF_FORMAT_AU : + if (subformat == SF_FORMAT_PCM_S8 || subformat == SF_FORMAT_PCM_16) + return 1 ; + if (subformat == SF_FORMAT_PCM_24 || subformat == SF_FORMAT_PCM_32) + return 1 ; + if (subformat == SF_FORMAT_ULAW || subformat == SF_FORMAT_ALAW) + return 1 ; + if (subformat == SF_FORMAT_FLOAT || subformat == SF_FORMAT_DOUBLE) + return 1 ; + if (subformat == SF_FORMAT_G721_32 && info->channels == 1) + return 1 ; + if (subformat == SF_FORMAT_G723_24 && info->channels == 1) + return 1 ; + if (subformat == SF_FORMAT_G723_40 && info->channels == 1) + return 1 ; + break ; + + case SF_FORMAT_CAF : + if (subformat == SF_FORMAT_PCM_S8 || subformat == SF_FORMAT_PCM_16) + return 1 ; + if (subformat == SF_FORMAT_PCM_24 || subformat == SF_FORMAT_PCM_32) + return 1 ; + if (subformat == SF_FORMAT_ULAW || subformat == SF_FORMAT_ALAW) + return 1 ; + if (subformat == SF_FORMAT_FLOAT || subformat == SF_FORMAT_DOUBLE) + return 1 ; + break ; + + case SF_FORMAT_RAW : + if (subformat == SF_FORMAT_PCM_U8 || subformat == SF_FORMAT_PCM_S8 || subformat == SF_FORMAT_PCM_16) + return 1 ; + if (subformat == SF_FORMAT_PCM_24 || subformat == SF_FORMAT_PCM_32) + return 1 ; + if (subformat == SF_FORMAT_FLOAT || subformat == SF_FORMAT_DOUBLE) + return 1 ; + if (subformat == SF_FORMAT_ALAW || subformat == SF_FORMAT_ULAW) + return 1 ; + if ((subformat == SF_FORMAT_DWVW_12 || subformat == SF_FORMAT_DWVW_16 || + subformat == SF_FORMAT_DWVW_24) && info-> channels == 1) + return 1 ; + if (subformat == SF_FORMAT_GSM610 && info->channels == 1) + return 1 ; + if (subformat == SF_FORMAT_VOX_ADPCM && info->channels == 1) + return 1 ; + break ; + + case SF_FORMAT_PAF : + if (subformat == SF_FORMAT_PCM_S8 || subformat == SF_FORMAT_PCM_16) + return 1 ; + if (subformat == SF_FORMAT_PCM_24 || subformat == SF_FORMAT_PCM_32) + return 1 ; + break ; + + case SF_FORMAT_SVX : + /* SVX currently does not support more than one channel for write. + ** Read will allow more than one channel but only allow one here. + */ + if (info->channels != 1) + return 0 ; + /* Always big endian. */ + if (endian == SF_ENDIAN_LITTLE || endian == SF_ENDIAN_CPU) + return 0 ; + + if ((subformat == SF_FORMAT_PCM_S8 || subformat == SF_FORMAT_PCM_16) && info->channels == 1) + return 1 ; + break ; + + case SF_FORMAT_NIST : + if (subformat == SF_FORMAT_PCM_S8 || subformat == SF_FORMAT_PCM_16) + return 1 ; + if (subformat == SF_FORMAT_PCM_24 || subformat == SF_FORMAT_PCM_32) + return 1 ; + if (subformat == SF_FORMAT_ULAW || subformat == SF_FORMAT_ALAW) + return 1 ; + break ; + + case SF_FORMAT_IRCAM : + if (subformat == SF_FORMAT_PCM_16 || subformat == SF_FORMAT_PCM_24 || subformat == SF_FORMAT_PCM_32) + return 1 ; + if (subformat == SF_FORMAT_ULAW || subformat == SF_FORMAT_ALAW || subformat == SF_FORMAT_FLOAT) + return 1 ; + break ; + + case SF_FORMAT_VOC : + /* VOC is strictly little endian. */ + if (endian == SF_ENDIAN_BIG || endian == SF_ENDIAN_CPU) + return 0 ; + if (subformat == SF_FORMAT_PCM_U8 || subformat == SF_FORMAT_PCM_16) + return 1 ; + if (subformat == SF_FORMAT_ULAW || subformat == SF_FORMAT_ALAW) + return 1 ; + break ; + + case SF_FORMAT_W64 : + /* W64 is strictly little endian. */ + if (endian == SF_ENDIAN_BIG || endian == SF_ENDIAN_CPU) + return 0 ; + if (subformat == SF_FORMAT_PCM_U8 || subformat == SF_FORMAT_PCM_16) + return 1 ; + if (subformat == SF_FORMAT_PCM_24 || subformat == SF_FORMAT_PCM_32) + return 1 ; + if ((subformat == SF_FORMAT_IMA_ADPCM || subformat == SF_FORMAT_MS_ADPCM) && info->channels <= 2) + return 1 ; + if (subformat == SF_FORMAT_GSM610 && info->channels == 1) + return 1 ; + if (subformat == SF_FORMAT_ULAW || subformat == SF_FORMAT_ALAW) + return 1 ; + if (subformat == SF_FORMAT_FLOAT || subformat == SF_FORMAT_DOUBLE) + return 1 ; + break ; + + case SF_FORMAT_MAT4 : + if (subformat == SF_FORMAT_PCM_16 || subformat == SF_FORMAT_PCM_32) + return 1 ; + if (subformat == SF_FORMAT_FLOAT || subformat == SF_FORMAT_DOUBLE) + return 1 ; + break ; + + case SF_FORMAT_MAT5 : + if (subformat == SF_FORMAT_PCM_U8 || subformat == SF_FORMAT_PCM_16 || subformat == SF_FORMAT_PCM_32) + return 1 ; + if (subformat == SF_FORMAT_FLOAT || subformat == SF_FORMAT_DOUBLE) + return 1 ; + break ; + + case SF_FORMAT_PVF : + if (subformat == SF_FORMAT_PCM_S8 || subformat == SF_FORMAT_PCM_16 || subformat == SF_FORMAT_PCM_32) + return 1 ; + break ; + + case SF_FORMAT_XI : + if (info->channels != 1) + return 0 ; + if (subformat == SF_FORMAT_DPCM_8 || subformat == SF_FORMAT_DPCM_16) + return 1 ; + break ; + + case SF_FORMAT_HTK : + /* HTK is strictly big endian. */ + if (endian == SF_ENDIAN_LITTLE || endian == SF_ENDIAN_CPU) + return 0 ; + if (info->channels != 1) + return 0 ; + if (subformat == SF_FORMAT_PCM_16) + return 1 ; + break ; + + case SF_FORMAT_SDS : + /* SDS is strictly big endian. */ + if (endian == SF_ENDIAN_LITTLE || endian == SF_ENDIAN_CPU) + return 0 ; + if (info->channels != 1) + return 0 ; + if (subformat == SF_FORMAT_PCM_S8 || subformat == SF_FORMAT_PCM_16 || subformat == SF_FORMAT_PCM_24) + return 1 ; + break ; + + case SF_FORMAT_AVR : + /* SDS is strictly big endian. */ + if (endian == SF_ENDIAN_LITTLE || endian == SF_ENDIAN_CPU) + return 0 ; + if (info->channels > 2) + return 0 ; + if (subformat == SF_FORMAT_PCM_U8 || subformat == SF_FORMAT_PCM_S8 || subformat == SF_FORMAT_PCM_16) + return 1 ; + break ; + + case SF_FORMAT_FLAC : + /* FLAC can't do more than 8 channels. */ + if (info->channels > 8) + return 0 ; + if (subformat == SF_FORMAT_PCM_S8 || subformat == SF_FORMAT_PCM_16 || subformat == SF_FORMAT_PCM_24) + return 1 ; + break ; + + case SF_FORMAT_SD2 : + /* SD2 is strictly big endian. */ + if (endian == SF_ENDIAN_LITTLE || endian == SF_ENDIAN_CPU) + return 0 ; + if (subformat == SF_FORMAT_PCM_S8 || subformat == SF_FORMAT_PCM_16 || subformat == SF_FORMAT_PCM_24) + return 1 ; + break ; + + default : break ; + } ; + + return 0 ; +} /* sf_format_check */ + +/*------------------------------------------------------------------------------ +*/ + +int +sf_command (SNDFILE *sndfile, int command, void *data, int datasize) +{ SF_PRIVATE *psf = NULL ; + int old_value ; + + /* This set of commands do not need the sndfile parameter. */ + switch (command) + { case SFC_GET_LIB_VERSION : + if (data == NULL) + return (psf->error = SFE_BAD_CONTROL_CMD) ; + if (ENABLE_EXPERIMENTAL_CODE) + LSF_SNPRINTF (data, datasize, "%s-%s-exp", PACKAGE_NAME, PACKAGE_VERSION) ; + else + LSF_SNPRINTF (data, datasize, "%s-%s", PACKAGE_NAME, PACKAGE_VERSION) ; + return strlen (data) ; + + case SFC_GET_SIMPLE_FORMAT_COUNT : + if (data == NULL || datasize != SIGNED_SIZEOF (int)) + return (sf_errno = SFE_BAD_CONTROL_CMD) ; + *((int*) data) = psf_get_format_simple_count () ; + return 0 ; + + case SFC_GET_SIMPLE_FORMAT : + if (data == NULL || datasize != SIGNED_SIZEOF (SF_FORMAT_INFO)) + return (sf_errno = SFE_BAD_CONTROL_CMD) ; + return psf_get_format_simple (data) ; + + case SFC_GET_FORMAT_MAJOR_COUNT : + if (data == NULL || datasize != SIGNED_SIZEOF (int)) + return (sf_errno = SFE_BAD_CONTROL_CMD) ; + *((int*) data) = psf_get_format_major_count () ; + return 0 ; + + case SFC_GET_FORMAT_MAJOR : + if (data == NULL || datasize != SIGNED_SIZEOF (SF_FORMAT_INFO)) + return (sf_errno = SFE_BAD_CONTROL_CMD) ; + return psf_get_format_major (data) ; + + case SFC_GET_FORMAT_SUBTYPE_COUNT : + if (data == NULL || datasize != SIGNED_SIZEOF (int)) + return (sf_errno = SFE_BAD_CONTROL_CMD) ; + *((int*) data) = psf_get_format_subtype_count () ; + return 0 ; + + case SFC_GET_FORMAT_SUBTYPE : + if (data == NULL || datasize != SIGNED_SIZEOF (SF_FORMAT_INFO)) + return (sf_errno = SFE_BAD_CONTROL_CMD) ; + return psf_get_format_subtype (data) ; + + case SFC_GET_FORMAT_INFO : + if (data == NULL || datasize != SIGNED_SIZEOF (SF_FORMAT_INFO)) + return (sf_errno = SFE_BAD_CONTROL_CMD) ; + return psf_get_format_info (data) ; + } ; + + if (sndfile == NULL && command == SFC_GET_LOG_INFO) + { if (data == NULL) + return (psf->error = SFE_BAD_CONTROL_CMD) ; + LSF_SNPRINTF (data, datasize, "%s", sf_logbuffer) ; + return strlen (data) ; + } ; + + VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 1) ; + + switch (command) + { case SFC_SET_NORM_FLOAT : + old_value = psf->norm_float ; + psf->norm_float = (datasize) ? SF_TRUE : SF_FALSE ; + return old_value ; + + case SFC_SET_NORM_DOUBLE : + old_value = psf->norm_double ; + psf->norm_double = (datasize) ? SF_TRUE : SF_FALSE ; + return old_value ; + + case SFC_GET_NORM_FLOAT : + return psf->norm_float ; + + case SFC_GET_NORM_DOUBLE : + return psf->norm_double ; + + case SFC_SET_SCALE_FLOAT_INT_READ : + old_value = psf->float_int_mult ; + + psf->float_int_mult = (datasize != 0) ? SF_TRUE : SF_FALSE ; + if (psf->float_int_mult && psf->float_max < 0.0) + psf->float_max = psf_calc_signal_max (psf, SF_FALSE) ; + return old_value ; + + case SFC_SET_ADD_PEAK_CHUNK : + { int format = psf->sf.format & SF_FORMAT_TYPEMASK ; + + /* Only WAV and AIFF support the PEAK chunk. */ + if (format != SF_FORMAT_WAV && format != SF_FORMAT_WAVEX && format != SF_FORMAT_AIFF) + return SF_FALSE ; + + format = psf->sf.format & SF_FORMAT_SUBMASK ; + + /* Only files containg the following data types support the PEAK chunk. */ + if (format != SF_FORMAT_FLOAT && format != SF_FORMAT_DOUBLE) + return SF_FALSE ; + + } ; + /* Can only do this is in SFM_WRITE mode. */ + if (psf->mode != SFM_WRITE) + return SF_FALSE ; + /* If data has already been written this must fail. */ + if (psf->have_written) + return SF_FALSE ; + /* Everything seems OK, so set psf->has_peak and re-write header. */ + if (datasize == SF_FALSE && psf->peak_info != NULL) + { free (psf->peak_info) ; + psf->peak_info = NULL ; + } + else if (psf->peak_info == NULL) + { psf->peak_info = peak_info_calloc (psf->sf.channels) ; + psf->peak_info->peak_loc = SF_PEAK_START ; + } ; + + if (psf->write_header) + psf->write_header (psf, SF_TRUE) ; + return datasize ; + + case SFC_GET_LOG_INFO : + if (data == NULL) + return (psf->error = SFE_BAD_CONTROL_CMD) ; + LSF_SNPRINTF (data, datasize, "%s", psf->logbuffer) ; + break ; + + case SFC_CALC_SIGNAL_MAX : + if (data == NULL || datasize != sizeof (double)) + return (psf->error = SFE_BAD_CONTROL_CMD) ; + *((double*) data) = psf_calc_signal_max (psf, SF_FALSE) ; + break ; + + case SFC_CALC_NORM_SIGNAL_MAX : + if (data == NULL || datasize != sizeof (double)) + return (psf->error = SFE_BAD_CONTROL_CMD) ; + *((double*) data) = psf_calc_signal_max (psf, SF_TRUE) ; + break ; + + case SFC_CALC_MAX_ALL_CHANNELS : + if (data == NULL || datasize != SIGNED_SIZEOF (double) * psf->sf.channels) + return (psf->error = SFE_BAD_CONTROL_CMD) ; + return psf_calc_max_all_channels (psf, (double*) data, SF_FALSE) ; + + case SFC_CALC_NORM_MAX_ALL_CHANNELS : + if (data == NULL || datasize != SIGNED_SIZEOF (double) * psf->sf.channels) + return (psf->error = SFE_BAD_CONTROL_CMD) ; + return psf_calc_max_all_channels (psf, (double*) data, SF_TRUE) ; + + case SFC_GET_SIGNAL_MAX : + if (data == NULL || datasize != sizeof (double)) + { psf->error = SFE_BAD_CONTROL_CMD ; + return SF_FALSE ; + } ; + return psf_get_signal_max (psf, (double *) data) ; + + case SFC_GET_MAX_ALL_CHANNELS : + if (data == NULL || datasize != SIGNED_SIZEOF (double) * psf->sf.channels) + { psf->error = SFE_BAD_CONTROL_CMD ; + return SF_FALSE ; + } ; + return psf_get_max_all_channels (psf, (double*) data) ; + + case SFC_UPDATE_HEADER_NOW : + if (psf->write_header) + psf->write_header (psf, SF_TRUE) ; + break ; + + case SFC_SET_UPDATE_HEADER_AUTO : + psf->auto_header = datasize ? SF_TRUE : SF_FALSE ; + return psf->auto_header ; + break ; + + case SFC_SET_ADD_DITHER_ON_WRITE : + case SFC_SET_ADD_DITHER_ON_READ : + /* + ** FIXME ! + ** These are obsolete. Just return. + ** Remove some time after version 1.0.8. + */ + break ; + + case SFC_SET_DITHER_ON_WRITE : + if (data == NULL || datasize != SIGNED_SIZEOF (SF_DITHER_INFO)) + return (psf->error = SFE_BAD_CONTROL_CMD) ; + memcpy (&psf->write_dither, data, sizeof (psf->write_dither)) ; + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + dither_init (psf, SFM_WRITE) ; + break ; + + case SFC_SET_DITHER_ON_READ : + if (data == NULL || datasize != SIGNED_SIZEOF (SF_DITHER_INFO)) + return (psf->error = SFE_BAD_CONTROL_CMD) ; + memcpy (&psf->read_dither, data, sizeof (psf->read_dither)) ; + if (psf->mode == SFM_READ || psf->mode == SFM_RDWR) + dither_init (psf, SFM_READ) ; + break ; + + case SFC_FILE_TRUNCATE : + if (psf->mode != SFM_WRITE && psf->mode != SFM_RDWR) + return SF_TRUE ; + if (datasize != sizeof (sf_count_t)) + return SF_TRUE ; + { sf_count_t position ; + + position = *((sf_count_t*) data) ; + + if (sf_seek (sndfile, position, SEEK_SET) != position) + return SF_TRUE ; + + psf->sf.frames = position ; + + position = psf_fseek (psf, 0, SEEK_CUR) ; + + return psf_ftruncate (psf, position) ; + } ; + break ; + + case SFC_SET_RAW_START_OFFSET : + if (data == NULL || datasize != sizeof (sf_count_t)) + return (psf->error = SFE_BAD_CONTROL_CMD) ; + if ((psf->sf.format & SF_FORMAT_TYPEMASK) != SF_FORMAT_RAW) + return (psf->error = SFE_BAD_CONTROL_CMD) ; + + psf->dataoffset = *((sf_count_t*) data) ; + sf_seek (sndfile, 0, SEEK_CUR) ; + break ; + + case SFC_GET_EMBED_FILE_INFO : + if (data == NULL || datasize != sizeof (SF_EMBED_FILE_INFO)) + return (psf->error = SFE_BAD_CONTROL_CMD) ; + + ((SF_EMBED_FILE_INFO*) data)->offset = psf->fileoffset ; + ((SF_EMBED_FILE_INFO*) data)->length = psf->filelength ; + break ; + + /* Lite remove start */ + case SFC_TEST_IEEE_FLOAT_REPLACE : + psf->ieee_replace = (datasize) ? SF_TRUE : SF_FALSE ; + if ((psf->sf.format & SF_FORMAT_SUBMASK) == SF_FORMAT_FLOAT) + float32_init (psf) ; + else if ((psf->sf.format & SF_FORMAT_SUBMASK) == SF_FORMAT_DOUBLE) + double64_init (psf) ; + else + return (psf->error = SFE_BAD_CONTROL_CMD) ; + break ; + /* Lite remove end */ + + case SFC_SET_CLIPPING : + psf->add_clipping = (datasize) ? SF_TRUE : SF_FALSE ; + return psf->add_clipping ; + + case SFC_GET_CLIPPING : + return psf->add_clipping ; + + case SFC_GET_LOOP_INFO : + if (datasize != sizeof (SF_LOOP_INFO) || data == NULL) + return SF_FALSE ; + if (psf->loop_info == NULL) + return SF_FALSE ; + memcpy (data, psf->loop_info, sizeof (SF_LOOP_INFO)) ; + return SF_TRUE ; + + case SFC_SET_BROADCAST_INFO : + { int format = psf->sf.format & SF_FORMAT_TYPEMASK ; + + /* Only WAV supports the BEXT (Broadcast) chunk. */ + if (format != SF_FORMAT_WAV && format != SF_FORMAT_WAVEX) + return SF_FALSE ; + } ; + + /* Can only do this is in SFM_RDWR or SFM_WRITE modes. */ + if (psf->mode == SFM_READ) + return SF_FALSE ; + + /* If data has already been written this must fail. */ + if (psf->broadcast_info == NULL && psf->have_written) + return SF_FALSE ; + + if (psf->broadcast_info == NULL) + psf->broadcast_info = broadcast_info_alloc () ; + + broadcast_info_copy (psf->broadcast_info, data) ; + broadcast_add_coding_history (psf->broadcast_info, psf->sf.channels, psf->sf.samplerate) ; + + if (psf->write_header) + psf->write_header (psf, SF_TRUE) ; + return SF_TRUE ; + + case SFC_GET_BROADCAST_INFO : + if (datasize != sizeof (SF_BROADCAST_INFO) || data == NULL) + return SF_FALSE ; + if (psf->broadcast_info == NULL) + return SF_FALSE ; + return broadcast_info_copy (data, psf->broadcast_info) ; + + case SFC_GET_INSTRUMENT : + if (datasize != sizeof (SF_INSTRUMENT) || data == NULL) + return SF_FALSE ; + if (psf->instrument == NULL) + return SF_FALSE ; + memcpy (data, psf->instrument, sizeof (SF_INSTRUMENT)) ; + return SF_TRUE ; + + case SFC_SET_INSTRUMENT : + /* If data has already been written this must fail. */ + if (psf->have_written) + return SF_FALSE ; + if (datasize != sizeof (SF_INSTRUMENT) || data == NULL) + return SF_FALSE ; + if (psf->instrument == NULL && (psf->instrument = psf_instrument_alloc ()) == NULL) + { psf->error = SFE_MALLOC_FAILED ; + return SF_FALSE ; + } ; + memcpy (psf->instrument, data, sizeof (SF_INSTRUMENT)) ; + return SF_TRUE ; + + default : + /* Must be a file specific command. Pass it on. */ + if (psf->command) + return psf->command (psf, command, data, datasize) ; + + psf_log_printf (psf, "*** sf_command : cmd = 0x%X\n", command) ; + return (psf->error = SFE_BAD_CONTROL_CMD) ; + } ; + + return 0 ; +} /* sf_command */ + +/*------------------------------------------------------------------------------ +*/ + +sf_count_t +sf_seek (SNDFILE *sndfile, sf_count_t offset, int whence) +{ SF_PRIVATE *psf ; + sf_count_t seek_from_start = 0, retval ; + + VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 1) ; + + if (! psf->sf.seekable) + { psf->error = SFE_NOT_SEEKABLE ; + return PSF_SEEK_ERROR ; + } ; + + /* If the whence parameter has a mode ORed in, check to see that + ** it makes sense. + */ + if (((whence & SFM_MASK) == SFM_WRITE && psf->mode == SFM_READ) || + ((whence & SFM_MASK) == SFM_WRITE && psf->mode == SFM_WRITE)) + { psf->error = SFE_WRONG_SEEK ; + return PSF_SEEK_ERROR ; + } ; + + /* Convert all SEEK_CUR and SEEK_END into seek_from_start to be + ** used with SEEK_SET. + */ + switch (whence) + { /* The SEEK_SET behaviour is independant of mode. */ + case SEEK_SET : + case SEEK_SET | SFM_READ : + case SEEK_SET | SFM_WRITE : + case SEEK_SET | SFM_RDWR : + seek_from_start = offset ; + break ; + + /* The SEEK_CUR is a little more tricky. */ + case SEEK_CUR : + if (offset == 0) + { if (psf->mode == SFM_READ) + return psf->read_current ; + if (psf->mode == SFM_WRITE) + return psf->write_current ; + } ; + if (psf->mode == SFM_READ) + seek_from_start = psf->read_current + offset ; + else if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + seek_from_start = psf->write_current + offset ; + else + psf->error = SFE_AMBIGUOUS_SEEK ; + break ; + + case SEEK_CUR | SFM_READ : + if (offset == 0) + return psf->read_current ; + seek_from_start = psf->read_current + offset ; + break ; + + case SEEK_CUR | SFM_WRITE : + if (offset == 0) + return psf->write_current ; + seek_from_start = psf->write_current + offset ; + break ; + + /* The SEEK_END */ + case SEEK_END : + case SEEK_END | SFM_READ : + case SEEK_END | SFM_WRITE : + seek_from_start = psf->sf.frames + offset ; + break ; + + default : + psf->error = SFE_BAD_SEEK ; + break ; + } ; + + if (psf->error) + return PSF_SEEK_ERROR ; + + if (seek_from_start < 0 || seek_from_start > psf->sf.frames) + { psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; + } ; + + if (psf->seek) + { int new_mode = (whence & SFM_MASK) ? (whence & SFM_MASK) : psf->mode ; + + retval = psf->seek (psf, new_mode, seek_from_start) ; + + switch (new_mode) + { case SFM_READ : + psf->read_current = retval ; + break ; + case SFM_WRITE : + psf->write_current = retval ; + break ; + case SFM_RDWR : + psf->read_current = retval ; + psf->write_current = retval ; + new_mode = SFM_READ ; + break ; + } ; + + psf->last_op = new_mode ; + + return retval ; + } ; + + psf->error = SFE_AMBIGUOUS_SEEK ; + return PSF_SEEK_ERROR ; +} /* sf_seek */ + +/*------------------------------------------------------------------------------ +*/ + +const char* +sf_get_string (SNDFILE *sndfile, int str_type) +{ SF_PRIVATE *psf ; + + if ((psf = (SF_PRIVATE*) sndfile) == NULL) + return NULL ; + if (psf->Magick != SNDFILE_MAGICK) + return NULL ; + + return psf_get_string (psf, str_type) ; +} /* sf_get_string */ + +int +sf_set_string (SNDFILE *sndfile, int str_type, const char* str) +{ SF_PRIVATE *psf ; + + VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 1) ; + + return psf_set_string (psf, str_type, str) ; +} /* sf_get_string */ + +/*============================================================================== +*/ + +sf_count_t +sf_read_raw (SNDFILE *sndfile, void *ptr, sf_count_t bytes) +{ SF_PRIVATE *psf ; + sf_count_t count ; + int bytewidth, blockwidth ; + + VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 1) ; + + bytewidth = (psf->bytewidth > 0) ? psf->bytewidth : 1 ; + blockwidth = (psf->blockwidth > 0) ? psf->blockwidth : 1 ; + + if (psf->mode == SFM_WRITE) + { psf->error = SFE_NOT_READMODE ; + return 0 ; + } ; + + if (bytes < 0 || psf->read_current >= psf->datalength) + { psf_memset (ptr, 0, bytes) ; + return 0 ; + } ; + + if (bytes % (psf->sf.channels * bytewidth)) + { psf->error = SFE_BAD_READ_ALIGN ; + return 0 ; + } ; + + count = psf_fread (ptr, 1, bytes, psf) ; + + if (count < bytes) + psf_memset (((char*) ptr) + count, 0, bytes - count) ; + + psf->read_current += count / blockwidth ; + + psf->last_op = SFM_READ ; + + return count ; +} /* sf_read_raw */ + +/*------------------------------------------------------------------------------ +*/ + +sf_count_t +sf_read_short (SNDFILE *sndfile, short *ptr, sf_count_t len) +{ SF_PRIVATE *psf ; + sf_count_t count, extra ; + + VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 1) ; + + if (psf->mode == SFM_WRITE) + { psf->error = SFE_NOT_READMODE ; + return 0 ; + } ; + + if (len % psf->sf.channels) + { psf->error = SFE_BAD_READ_ALIGN ; + return 0 ; + } ; + + if (len <= 0 || psf->read_current >= psf->sf.frames) + { psf_memset (ptr, 0, len * sizeof (short)) ; + return 0 ; /* End of file. */ + } ; + + if (! psf->read_short || psf->seek == NULL) + { psf->error = SFE_UNIMPLEMENTED ; + return 0 ; + } ; + + if (psf->last_op != SFM_READ) + if (psf->seek (psf, SFM_READ, psf->read_current) < 0) + return 0 ; + + count = psf->read_short (psf, ptr, len) ; + + if (psf->read_current + count / psf->sf.channels > psf->sf.frames) + { count = (psf->sf.frames - psf->read_current) * psf->sf.channels ; + extra = len - count ; + psf_memset (ptr + count, 0, extra * sizeof (short)) ; + psf->read_current = psf->sf.frames ; + } ; + + psf->read_current += count / psf->sf.channels ; + + psf->last_op = SFM_READ ; + + if (psf->read_current > psf->sf.frames) + { count = psf->sf.channels * (psf->read_current - psf->sf.frames) ; + psf->read_current = psf->sf.frames ; + } ; + + return count ; +} /* sf_read_short */ + +sf_count_t +sf_readf_short (SNDFILE *sndfile, short *ptr, sf_count_t frames) +{ SF_PRIVATE *psf ; + sf_count_t count, extra ; + + VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 1) ; + + if (psf->mode == SFM_WRITE) + { psf->error = SFE_NOT_READMODE ; + return 0 ; + } ; + + if (frames <= 0 || psf->read_current >= psf->sf.frames) + { psf_memset (ptr, 0, frames * psf->sf.channels * sizeof (short)) ; + return 0 ; /* End of file. */ + } ; + + if (! psf->read_short || psf->seek == NULL) + { psf->error = SFE_UNIMPLEMENTED ; + return 0 ; + } ; + + if (psf->last_op != SFM_READ) + if (psf->seek (psf, SFM_READ, psf->read_current) < 0) + return 0 ; + + count = psf->read_short (psf, ptr, frames * psf->sf.channels) ; + + if (psf->read_current + count / psf->sf.channels > psf->sf.frames) + { count = (psf->sf.frames - psf->read_current) * psf->sf.channels ; + extra = frames * psf->sf.channels - count ; + psf_memset (ptr + count, 0, extra * sizeof (short)) ; + psf->read_current = psf->sf.frames ; + } ; + + psf->read_current += count / psf->sf.channels ; + + psf->last_op = SFM_READ ; + + if (psf->read_current > psf->sf.frames) + { count = psf->sf.channels * (psf->read_current - psf->sf.frames) ; + psf->read_current = psf->sf.frames ; + } ; + + return count / psf->sf.channels ; +} /* sf_readf_short */ + +/*------------------------------------------------------------------------------ +*/ + +sf_count_t +sf_read_int (SNDFILE *sndfile, int *ptr, sf_count_t len) +{ SF_PRIVATE *psf ; + sf_count_t count, extra ; + + VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 1) ; + + if (psf->mode == SFM_WRITE) + { psf->error = SFE_NOT_READMODE ; + return 0 ; + } ; + + if (len % psf->sf.channels) + { psf->error = SFE_BAD_READ_ALIGN ; + return 0 ; + } ; + + if (len <= 0 || psf->read_current >= psf->sf.frames) + { psf_memset (ptr, 0, len * sizeof (int)) ; + return 0 ; + } ; + + if (! psf->read_int || psf->seek == NULL) + { psf->error = SFE_UNIMPLEMENTED ; + return 0 ; + } ; + + if (psf->last_op != SFM_READ) + if (psf->seek (psf, SFM_READ, psf->read_current) < 0) + return 0 ; + + count = psf->read_int (psf, ptr, len) ; + + if (psf->read_current + count / psf->sf.channels > psf->sf.frames) + { count = (psf->sf.frames - psf->read_current) * psf->sf.channels ; + extra = len - count ; + psf_memset (ptr + count, 0, extra * sizeof (int)) ; + psf->read_current = psf->sf.frames ; + } ; + + psf->read_current += count / psf->sf.channels ; + + psf->last_op = SFM_READ ; + + if (psf->read_current > psf->sf.frames) + { count = psf->sf.channels * (psf->read_current - psf->sf.frames) ; + psf->read_current = psf->sf.frames ; + } ; + + return count ; +} /* sf_read_int */ + +sf_count_t +sf_readf_int (SNDFILE *sndfile, int *ptr, sf_count_t frames) +{ SF_PRIVATE *psf ; + sf_count_t count, extra ; + + VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 1) ; + + if (psf->mode == SFM_WRITE) + { psf->error = SFE_NOT_READMODE ; + return 0 ; + } ; + + if (frames <= 0 || psf->read_current >= psf->sf.frames) + { psf_memset (ptr, 0, frames * psf->sf.channels * sizeof (int)) ; + return 0 ; + } ; + + if (! psf->read_int || psf->seek == NULL) + { psf->error = SFE_UNIMPLEMENTED ; + return 0 ; + } ; + + if (psf->last_op != SFM_READ) + if (psf->seek (psf, SFM_READ, psf->read_current) < 0) + return 0 ; + + count = psf->read_int (psf, ptr, frames * psf->sf.channels) ; + + if (psf->read_current + count / psf->sf.channels > psf->sf.frames) + { count = (psf->sf.frames - psf->read_current) * psf->sf.channels ; + extra = frames * psf->sf.channels - count ; + psf_memset (ptr + count, 0, extra * sizeof (int)) ; + psf->read_current = psf->sf.frames ; + } ; + + psf->read_current += count / psf->sf.channels ; + + psf->last_op = SFM_READ ; + + if (psf->read_current > psf->sf.frames) + { count = psf->sf.channels * (psf->read_current - psf->sf.frames) ; + psf->read_current = psf->sf.frames ; + } ; + + return count / psf->sf.channels ; +} /* sf_readf_int */ + +/*------------------------------------------------------------------------------ +*/ + +sf_count_t +sf_read_float (SNDFILE *sndfile, float *ptr, sf_count_t len) +{ SF_PRIVATE *psf ; + sf_count_t count, extra ; + + VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 1) ; + + if (psf->mode == SFM_WRITE) + { psf->error = SFE_NOT_READMODE ; + return 0 ; + } ; + + if (len % psf->sf.channels) + { psf->error = SFE_BAD_READ_ALIGN ; + return 0 ; + } ; + + if (len <= 0 || psf->read_current >= psf->sf.frames) + { psf_memset (ptr, 0, len * sizeof (float)) ; + return 0 ; + } ; + + if (! psf->read_float || psf->seek == NULL) + { psf->error = SFE_UNIMPLEMENTED ; + return 0 ; + } ; + + if (psf->last_op != SFM_READ) + if (psf->seek (psf, SFM_READ, psf->read_current) < 0) + return 0 ; + + count = psf->read_float (psf, ptr, len) ; + + if (psf->read_current + count / psf->sf.channels > psf->sf.frames) + { count = (psf->sf.frames - psf->read_current) * psf->sf.channels ; + extra = len - count ; + psf_memset (ptr + count, 0, extra * sizeof (float)) ; + psf->read_current = psf->sf.frames ; + } ; + + psf->read_current += count / psf->sf.channels ; + + psf->last_op = SFM_READ ; + + if (psf->read_current > psf->sf.frames) + { count = psf->sf.channels * (psf->read_current - psf->sf.frames) ; + psf->read_current = psf->sf.frames ; + } ; + + return count ; +} /* sf_read_float */ + +sf_count_t +sf_readf_float (SNDFILE *sndfile, float *ptr, sf_count_t frames) +{ SF_PRIVATE *psf ; + sf_count_t count, extra ; + + VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 1) ; + + if (psf->mode == SFM_WRITE) + { psf->error = SFE_NOT_READMODE ; + return 0 ; + } ; + + if (frames <= 0 || psf->read_current >= psf->sf.frames) + { psf_memset (ptr, 0, frames * psf->sf.channels * sizeof (float)) ; + return 0 ; + } ; + + if (! psf->read_float || psf->seek == NULL) + { psf->error = SFE_UNIMPLEMENTED ; + return 0 ; + } ; + + if (psf->last_op != SFM_READ) + if (psf->seek (psf, SFM_READ, psf->read_current) < 0) + return 0 ; + + count = psf->read_float (psf, ptr, frames * psf->sf.channels) ; + + if (psf->read_current + count / psf->sf.channels > psf->sf.frames) + { count = (psf->sf.frames - psf->read_current) * psf->sf.channels ; + extra = frames * psf->sf.channels - count ; + psf_memset (ptr + count, 0, extra * sizeof (float)) ; + psf->read_current = psf->sf.frames ; + } ; + + psf->read_current += count / psf->sf.channels ; + + psf->last_op = SFM_READ ; + + if (psf->read_current > psf->sf.frames) + { count = psf->sf.channels * (psf->read_current - psf->sf.frames) ; + psf->read_current = psf->sf.frames ; + } ; + + return count / psf->sf.channels ; +} /* sf_readf_float */ + +/*------------------------------------------------------------------------------ +*/ + +sf_count_t +sf_read_double (SNDFILE *sndfile, double *ptr, sf_count_t len) +{ SF_PRIVATE *psf ; + sf_count_t count, extra ; + + VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 1) ; + + if (psf->mode == SFM_WRITE) + { psf->error = SFE_NOT_READMODE ; + return 0 ; + } ; + + if (len % psf->sf.channels) + { psf->error = SFE_BAD_READ_ALIGN ; + return 0 ; + } ; + + if (len <= 0 || psf->read_current >= psf->sf.frames) + { psf_memset (ptr, 0, len * sizeof (double)) ; + return 0 ; + } ; + + if (! psf->read_double || psf->seek == NULL) + { psf->error = SFE_UNIMPLEMENTED ; + return 0 ; + } ; + + if (psf->last_op != SFM_READ) + if (psf->seek (psf, SFM_READ, psf->read_current) < 0) + return 0 ; + + count = psf->read_double (psf, ptr, len) ; + + if (psf->read_current + count / psf->sf.channels > psf->sf.frames) + { count = (psf->sf.frames - psf->read_current) * psf->sf.channels ; + extra = len - count ; + psf_memset (ptr + count, 0, extra * sizeof (double)) ; + psf->read_current = psf->sf.frames ; + } ; + + psf->read_current += count / psf->sf.channels ; + + psf->last_op = SFM_READ ; + + if (psf->read_current > psf->sf.frames) + { count = psf->sf.channels * (psf->read_current - psf->sf.frames) ; + psf->read_current = psf->sf.frames ; + } ; + + return count ; +} /* sf_read_double */ + +sf_count_t +sf_readf_double (SNDFILE *sndfile, double *ptr, sf_count_t frames) +{ SF_PRIVATE *psf ; + sf_count_t count, extra ; + + VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 1) ; + + if (psf->mode == SFM_WRITE) + { psf->error = SFE_NOT_READMODE ; + return 0 ; + } ; + + if (frames <= 0 || psf->read_current >= psf->sf.frames) + { psf_memset (ptr, 0, frames * psf->sf.channels * sizeof (double)) ; + return 0 ; + } ; + + if (! psf->read_double || psf->seek == NULL) + { psf->error = SFE_UNIMPLEMENTED ; + return 0 ; + } ; + + if (psf->last_op != SFM_READ) + if (psf->seek (psf, SFM_READ, psf->read_current) < 0) + return 0 ; + + count = psf->read_double (psf, ptr, frames * psf->sf.channels) ; + + if (psf->read_current + count / psf->sf.channels > psf->sf.frames) + { count = (psf->sf.frames - psf->read_current) * psf->sf.channels ; + extra = frames * psf->sf.channels - count ; + psf_memset (ptr + count, 0, extra * sizeof (double)) ; + psf->read_current = psf->sf.frames ; + } ; + + psf->read_current += count / psf->sf.channels ; + + psf->last_op = SFM_READ ; + + if (psf->read_current > psf->sf.frames) + { count = psf->sf.channels * (psf->read_current - psf->sf.frames) ; + psf->read_current = psf->sf.frames ; + } ; + + return count / psf->sf.channels ; +} /* sf_readf_double */ + +/*------------------------------------------------------------------------------ +*/ + +sf_count_t +sf_write_raw (SNDFILE *sndfile, const void *ptr, sf_count_t len) +{ SF_PRIVATE *psf ; + sf_count_t count ; + int bytewidth, blockwidth ; + + VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 1) ; + + bytewidth = (psf->bytewidth > 0) ? psf->bytewidth : 1 ; + blockwidth = (psf->blockwidth > 0) ? psf->blockwidth : 1 ; + + if (psf->mode == SFM_READ) + { psf->error = SFE_NOT_WRITEMODE ; + return 0 ; + } ; + + if (len % (psf->sf.channels * bytewidth)) + { psf->error = SFE_BAD_WRITE_ALIGN ; + return 0 ; + } ; + + if (psf->have_written == SF_FALSE && psf->write_header != NULL) + psf->write_header (psf, SF_FALSE) ; + psf->have_written = SF_TRUE ; + + count = psf_fwrite (ptr, 1, len, psf) ; + + psf->write_current += count / blockwidth ; + + if (psf->write_current > psf->sf.frames) + psf->sf.frames = psf->write_current ; + + psf->last_op = SFM_WRITE ; + + return count ; +} /* sf_write_raw */ + +/*------------------------------------------------------------------------------ +*/ + +sf_count_t +sf_write_short (SNDFILE *sndfile, const short *ptr, sf_count_t len) +{ SF_PRIVATE *psf ; + sf_count_t count ; + + VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 1) ; + + if (psf->mode == SFM_READ) + { psf->error = SFE_NOT_WRITEMODE ; + return 0 ; + } ; + + if (len % psf->sf.channels) + { psf->error = SFE_BAD_WRITE_ALIGN ; + return 0 ; + } ; + + if (! psf->write_short || psf->seek == NULL) + { psf->error = SFE_UNIMPLEMENTED ; + return 0 ; + } ; + + if (psf->last_op != SFM_WRITE) + if (psf->seek (psf, SFM_WRITE, psf->write_current) < 0) + return 0 ; + + if (psf->have_written == SF_FALSE && psf->write_header != NULL) + psf->write_header (psf, SF_FALSE) ; + psf->have_written = SF_TRUE ; + + count = psf->write_short (psf, ptr, len) ; + + psf->write_current += count / psf->sf.channels ; + + psf->last_op = SFM_WRITE ; + + if (psf->auto_header && psf->write_header != NULL) + psf->write_header (psf, SF_TRUE) ; + + if (psf->write_current > psf->sf.frames) + psf->sf.frames = psf->write_current ; + + return count ; +} /* sf_write_short */ + +sf_count_t +sf_writef_short (SNDFILE *sndfile, const short *ptr, sf_count_t frames) +{ SF_PRIVATE *psf ; + sf_count_t count ; + + VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 1) ; + + if (psf->mode == SFM_READ) + { psf->error = SFE_NOT_WRITEMODE ; + return 0 ; + } ; + + if (! psf->write_short || psf->seek == NULL) + { psf->error = SFE_UNIMPLEMENTED ; + return 0 ; + } ; + + if (psf->last_op != SFM_WRITE) + if (psf->seek (psf, SFM_WRITE, psf->write_current) < 0) + return 0 ; + + if (psf->have_written == SF_FALSE && psf->write_header != NULL) + psf->write_header (psf, SF_FALSE) ; + psf->have_written = SF_TRUE ; + + count = psf->write_short (psf, ptr, frames * psf->sf.channels) ; + + psf->write_current += count / psf->sf.channels ; + + psf->last_op = SFM_WRITE ; + + if (psf->auto_header && psf->write_header != NULL) + psf->write_header (psf, SF_TRUE) ; + + if (psf->write_current > psf->sf.frames) + psf->sf.frames = psf->write_current ; + + return count / psf->sf.channels ; +} /* sf_writef_short */ + +/*------------------------------------------------------------------------------ +*/ + +sf_count_t +sf_write_int (SNDFILE *sndfile, const int *ptr, sf_count_t len) +{ SF_PRIVATE *psf ; + sf_count_t count ; + + VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 1) ; + + if (psf->mode == SFM_READ) + { psf->error = SFE_NOT_WRITEMODE ; + return 0 ; + } ; + + if (len % psf->sf.channels) + { psf->error = SFE_BAD_WRITE_ALIGN ; + return 0 ; + } ; + + if (! psf->write_int || psf->seek == NULL) + { psf->error = SFE_UNIMPLEMENTED ; + return 0 ; + } ; + + if (psf->last_op != SFM_WRITE) + if (psf->seek (psf, SFM_WRITE, psf->write_current) < 0) + return 0 ; + + if (psf->have_written == SF_FALSE && psf->write_header != NULL) + psf->write_header (psf, SF_FALSE) ; + psf->have_written = SF_TRUE ; + + count = psf->write_int (psf, ptr, len) ; + + psf->write_current += count / psf->sf.channels ; + + psf->last_op = SFM_WRITE ; + + if (psf->auto_header && psf->write_header != NULL) + psf->write_header (psf, SF_TRUE) ; + + if (psf->write_current > psf->sf.frames) + psf->sf.frames = psf->write_current ; + + return count ; +} /* sf_write_int */ + +sf_count_t +sf_writef_int (SNDFILE *sndfile, const int *ptr, sf_count_t frames) +{ SF_PRIVATE *psf ; + sf_count_t count ; + + VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 1) ; + + if (psf->mode == SFM_READ) + { psf->error = SFE_NOT_WRITEMODE ; + return 0 ; + } ; + + if (! psf->write_int || psf->seek == NULL) + { psf->error = SFE_UNIMPLEMENTED ; + return 0 ; + } ; + + if (psf->last_op != SFM_WRITE) + if (psf->seek (psf, SFM_WRITE, psf->write_current) < 0) + return 0 ; + + if (psf->have_written == SF_FALSE && psf->write_header != NULL) + psf->write_header (psf, SF_FALSE) ; + psf->have_written = SF_TRUE ; + + count = psf->write_int (psf, ptr, frames * psf->sf.channels) ; + + psf->write_current += count / psf->sf.channels ; + + psf->last_op = SFM_WRITE ; + + if (psf->auto_header && psf->write_header != NULL) + psf->write_header (psf, SF_TRUE) ; + + if (psf->write_current > psf->sf.frames) + psf->sf.frames = psf->write_current ; + + return count / psf->sf.channels ; +} /* sf_writef_int */ + +/*------------------------------------------------------------------------------ +*/ + +sf_count_t +sf_write_float (SNDFILE *sndfile, const float *ptr, sf_count_t len) +{ SF_PRIVATE *psf ; + sf_count_t count ; + + VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 1) ; + + if (psf->mode == SFM_READ) + { psf->error = SFE_NOT_WRITEMODE ; + return 0 ; + } ; + + if (len % psf->sf.channels) + { psf->error = SFE_BAD_WRITE_ALIGN ; + return 0 ; + } ; + + if (! psf->write_float || psf->seek == NULL) + { psf->error = SFE_UNIMPLEMENTED ; + return 0 ; + } ; + + if (psf->last_op != SFM_WRITE) + if (psf->seek (psf, SFM_WRITE, psf->write_current) < 0) + return 0 ; + + if (psf->have_written == SF_FALSE && psf->write_header != NULL) + psf->write_header (psf, SF_FALSE) ; + psf->have_written = SF_TRUE ; + + count = psf->write_float (psf, ptr, len) ; + + psf->write_current += count / psf->sf.channels ; + + psf->last_op = SFM_WRITE ; + + if (psf->auto_header && psf->write_header != NULL) + psf->write_header (psf, SF_TRUE) ; + + if (psf->write_current > psf->sf.frames) + psf->sf.frames = psf->write_current ; + + return count ; +} /* sf_write_float */ + +sf_count_t +sf_writef_float (SNDFILE *sndfile, const float *ptr, sf_count_t frames) +{ SF_PRIVATE *psf ; + sf_count_t count ; + + VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 1) ; + + if (psf->mode == SFM_READ) + { psf->error = SFE_NOT_WRITEMODE ; + return 0 ; + } ; + + if (! psf->write_float || psf->seek == NULL) + { psf->error = SFE_UNIMPLEMENTED ; + return 0 ; + } ; + + if (psf->last_op != SFM_WRITE) + if (psf->seek (psf, SFM_WRITE, psf->write_current) < 0) + return 0 ; + + if (psf->have_written == SF_FALSE && psf->write_header != NULL) + psf->write_header (psf, SF_FALSE) ; + psf->have_written = SF_TRUE ; + + count = psf->write_float (psf, ptr, frames * psf->sf.channels) ; + + psf->write_current += count / psf->sf.channels ; + + psf->last_op = SFM_WRITE ; + + if (psf->auto_header && psf->write_header != NULL) + psf->write_header (psf, SF_TRUE) ; + + if (psf->write_current > psf->sf.frames) + psf->sf.frames = psf->write_current ; + + return count / psf->sf.channels ; +} /* sf_writef_float */ + +/*------------------------------------------------------------------------------ +*/ + +sf_count_t +sf_write_double (SNDFILE *sndfile, const double *ptr, sf_count_t len) +{ SF_PRIVATE *psf ; + sf_count_t count ; + + VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 1) ; + + if (psf->mode == SFM_READ) + { psf->error = SFE_NOT_WRITEMODE ; + return 0 ; + } ; + + if (len % psf->sf.channels) + { psf->error = SFE_BAD_WRITE_ALIGN ; + return 0 ; + } ; + + if (! psf->write_double || psf->seek == NULL) + { psf->error = SFE_UNIMPLEMENTED ; + return 0 ; + } ; + + if (psf->last_op != SFM_WRITE) + if (psf->seek (psf, SFM_WRITE, psf->write_current) < 0) + return 0 ; + + if (psf->have_written == SF_FALSE && psf->write_header != NULL) + psf->write_header (psf, SF_FALSE) ; + psf->have_written = SF_TRUE ; + + count = psf->write_double (psf, ptr, len) ; + + psf->write_current += count / psf->sf.channels ; + + psf->last_op = SFM_WRITE ; + + if (psf->auto_header && psf->write_header != NULL) + psf->write_header (psf, SF_TRUE) ; + + if (psf->write_current > psf->sf.frames) + psf->sf.frames = psf->write_current ; + + return count ; +} /* sf_write_double */ + +sf_count_t +sf_writef_double (SNDFILE *sndfile, const double *ptr, sf_count_t frames) +{ SF_PRIVATE *psf ; + sf_count_t count ; + + VALIDATE_SNDFILE_AND_ASSIGN_PSF (sndfile, psf, 1) ; + + if (psf->mode == SFM_READ) + { psf->error = SFE_NOT_WRITEMODE ; + return 0 ; + } ; + + if (! psf->write_double || psf->seek == NULL) + { psf->error = SFE_UNIMPLEMENTED ; + return 0 ; + } ; + + if (psf->last_op != SFM_WRITE) + if (psf->seek (psf, SFM_WRITE, psf->write_current) < 0) + return 0 ; + + if (psf->have_written == SF_FALSE && psf->write_header != NULL) + psf->write_header (psf, SF_FALSE) ; + psf->have_written = SF_TRUE ; + + count = psf->write_double (psf, ptr, frames * psf->sf.channels) ; + + psf->write_current += count / psf->sf.channels ; + + psf->last_op = SFM_WRITE ; + + if (psf->auto_header && psf->write_header != NULL) + psf->write_header (psf, SF_TRUE) ; + + if (psf->write_current > psf->sf.frames) + psf->sf.frames = psf->write_current ; + + return count / psf->sf.channels ; +} /* sf_writef_double */ + +/*========================================================================= +** Private functions. +*/ + +static int +try_resource_fork (SF_PRIVATE * psf, int mode) +{ + if (psf_open_rsrc (psf, mode) != 0) + return 0 ; + + /* More checking here. */ + psf_log_printf (psf, "Resource fork : %s\n", psf->rsrcpath) ; + + return SF_FORMAT_SD2 ; +} /* try_resource_fork */ + +static int +format_from_extension (SF_PRIVATE *psf) +{ char *cptr ; + char buffer [16] ; + + if (psf->filename == NULL) + return 0 ; + + if ((cptr = strrchr (psf->filename, '.')) == NULL) + return 0 ; + + cptr ++ ; + if (strlen (cptr) > sizeof (buffer) - 1) + return 0 ; + + strncpy (buffer, cptr, sizeof (buffer)) ; + buffer [sizeof (buffer) - 1] = 0 ; + + /* Convert everything in the buffer to lower case. */ + cptr = buffer ; + while (*cptr) + { *cptr = tolower (*cptr) ; + cptr ++ ; + } ; + + cptr = buffer ; + + if (strcmp (cptr, "au") == 0) + { psf->sf.channels = 1 ; + psf->sf.samplerate = 8000 ; + return SF_FORMAT_RAW | SF_FORMAT_ULAW ; + } ; + + if (strcmp (cptr, "snd") == 0) + { psf->sf.channels = 1 ; + psf->sf.samplerate = 8000 ; + return SF_FORMAT_RAW | SF_FORMAT_ULAW ; + } ; + + if (strcmp (cptr, "vox") == 0) + { psf->sf.channels = 1 ; + psf->sf.samplerate = 8000 ; + return SF_FORMAT_RAW | SF_FORMAT_VOX_ADPCM ; + } ; + + if (strcmp (cptr, "gsm") == 0) + { psf->sf.channels = 1 ; + psf->sf.samplerate = 8000 ; + return SF_FORMAT_RAW | SF_FORMAT_GSM610 ; + } ; + + return 0 ; +} /* format_from_extension */ + +static int +guess_file_type (SF_PRIVATE *psf) +{ int buffer [3], format ; + + if (psf_binheader_readf (psf, "b", &buffer, SIGNED_SIZEOF (buffer)) != SIGNED_SIZEOF (buffer)) + { psf->error = SFE_BAD_FILE_READ ; + return 0 ; + } ; + + if ((buffer [0] == MAKE_MARKER ('R', 'I', 'F', 'F') || buffer [0] == MAKE_MARKER ('R', 'I', 'F', 'X')) + && buffer [2] == MAKE_MARKER ('W', 'A', 'V', 'E')) + return SF_FORMAT_WAV ; + + if (buffer [0] == MAKE_MARKER ('F', 'O', 'R', 'M')) + { if (buffer [2] == MAKE_MARKER ('A', 'I', 'F', 'F') || buffer [2] == MAKE_MARKER ('A', 'I', 'F', 'C')) + return SF_FORMAT_AIFF ; + if (buffer [2] == MAKE_MARKER ('8', 'S', 'V', 'X') || buffer [2] == MAKE_MARKER ('1', '6', 'S', 'V')) + return SF_FORMAT_SVX ; + return 0 ; + } ; + + if (buffer [0] == MAKE_MARKER ('.', 's', 'n', 'd') || buffer [0] == MAKE_MARKER ('d', 'n', 's', '.')) + return SF_FORMAT_AU ; + + if ((buffer [0] == MAKE_MARKER ('f', 'a', 'p', ' ') || buffer [0] == MAKE_MARKER (' ', 'p', 'a', 'f'))) + return SF_FORMAT_PAF ; + + if (buffer [0] == MAKE_MARKER ('N', 'I', 'S', 'T')) + return SF_FORMAT_NIST ; + + if (buffer [0] == MAKE_MARKER ('C', 'r', 'e', 'a') && buffer [1] == MAKE_MARKER ('t', 'i', 'v', 'e')) + return SF_FORMAT_VOC ; + + if ((buffer [0] & MAKE_MARKER (0xFF, 0xFF, 0xF8, 0xFF)) == MAKE_MARKER (0x64, 0xA3, 0x00, 0x00) || + (buffer [0] & MAKE_MARKER (0xFF, 0xF8, 0xFF, 0xFF)) == MAKE_MARKER (0x00, 0x00, 0xA3, 0x64)) + return SF_FORMAT_IRCAM ; + + if (buffer [0] == MAKE_MARKER ('r', 'i', 'f', 'f')) + return SF_FORMAT_W64 ; + + if (buffer [0] == MAKE_MARKER (0, 0, 0x03, 0xE8) && buffer [1] == MAKE_MARKER (0, 0, 0, 1) && + buffer [2] == MAKE_MARKER (0, 0, 0, 1)) + return SF_FORMAT_MAT4 ; + + if (buffer [0] == MAKE_MARKER (0, 0, 0, 0) && buffer [1] == MAKE_MARKER (1, 0, 0, 0) && + buffer [2] == MAKE_MARKER (1, 0, 0, 0)) + return SF_FORMAT_MAT4 ; + + if (buffer [0] == MAKE_MARKER ('M', 'A', 'T', 'L') && buffer [1] == MAKE_MARKER ('A', 'B', ' ', '5')) + return SF_FORMAT_MAT5 ; + + if (buffer [0] == MAKE_MARKER ('P', 'V', 'F', '1')) + return SF_FORMAT_PVF ; + + if (buffer [0] == MAKE_MARKER ('E', 'x', 't', 'e') && buffer [1] == MAKE_MARKER ('n', 'd', 'e', 'd') && + buffer [2] == MAKE_MARKER (' ', 'I', 'n', 's')) + return SF_FORMAT_XI ; + + if (buffer [0] == MAKE_MARKER ('c', 'a', 'f', 'f') && buffer [2] == MAKE_MARKER ('d', 'e', 's', 'c')) + return SF_FORMAT_CAF ; + + if (ENABLE_EXPERIMENTAL_CODE && buffer [0] == MAKE_MARKER ('O', 'g', 'g', 'S')) + return SF_FORMAT_OGG ; + + if (buffer [0] == MAKE_MARKER ('A', 'L', 'a', 'w') && buffer [1] == MAKE_MARKER ('S', 'o', 'u', 'n') + && buffer [2] == MAKE_MARKER ('d', 'F', 'i', 'l')) + return SF_FORMAT_WVE ; + + if (buffer [0] == MAKE_MARKER ('D', 'i', 'a', 'm') && buffer [1] == MAKE_MARKER ('o', 'n', 'd', 'W') + && buffer [2] == MAKE_MARKER ('a', 'r', 'e', ' ')) + return SF_FORMAT_DWD ; + + if (buffer [0] == MAKE_MARKER ('L', 'M', '8', '9') || buffer [0] == MAKE_MARKER ('5', '3', 0, 0)) + return SF_FORMAT_TXW ; + + if ((buffer [0] & MAKE_MARKER (0xFF, 0xFF, 0x80, 0xFF)) == MAKE_MARKER (0xF0, 0x7E, 0, 0x01)) + return SF_FORMAT_SDS ; + + if (buffer [0] == MAKE_MARKER ('C', 'A', 'T', ' ') && buffer [2] == MAKE_MARKER ('R', 'E', 'X', '2')) + return SF_FORMAT_REX2 ; + + if (buffer [0] == MAKE_MARKER (0x30, 0x26, 0xB2, 0x75) && buffer [1] == MAKE_MARKER (0x8E, 0x66, 0xCF, 0x11)) + return 0 /*-SF_FORMAT_WMA-*/ ; + + /* HMM (Hidden Markov Model) Tool Kit. */ + if (2 * BEI2H_INT (buffer [0]) + 12 == psf->filelength && buffer [2] == MAKE_MARKER (0, 2, 0, 0)) + return SF_FORMAT_HTK ; + + if (buffer [0] == MAKE_MARKER ('f', 'L', 'a', 'C')) + return SF_FORMAT_FLAC ; + + /* Turtle Beach SMP 16-bit */ + if (buffer [0] == MAKE_MARKER ('S', 'O', 'U', 'N') && buffer [1] == MAKE_MARKER ('D', ' ', 'S', 'A')) + return 0 ; + + if (buffer [0] == MAKE_MARKER ('S', 'Y', '8', '0') || buffer [0] == MAKE_MARKER ('S', 'Y', '8', '5')) + return 0 ; + + if (buffer [0] == MAKE_MARKER ('a', 'j', 'k', 'g')) + return 0 /*-SF_FORMAT_SHN-*/ ; + + if (buffer [0] == MAKE_MARKER ('2', 'B', 'I', 'T')) + return SF_FORMAT_AVR ; + + /* This must be the second last one. */ + if (psf->filelength > 0 && (format = try_resource_fork (psf, SFM_READ)) != 0) + return format ; + + return 0 ; +} /* guess_file_type */ + + +static int +validate_sfinfo (SF_INFO *sfinfo) +{ if (sfinfo->samplerate < 1) + return 0 ; + if (sfinfo->frames < 0) + return 0 ; + if (sfinfo->channels < 1) + return 0 ; + if ((sfinfo->format & SF_FORMAT_TYPEMASK) == 0) + return 0 ; + if ((sfinfo->format & SF_FORMAT_SUBMASK) == 0) + return 0 ; + if (sfinfo->sections < 1) + return 0 ; + return 1 ; +} /* validate_sfinfo */ + +static int +validate_psf (SF_PRIVATE *psf) +{ + if (psf->datalength < 0) + { psf_log_printf (psf, "Invalid SF_PRIVATE field : datalength == %D.\n", psf->datalength) ; + return 0 ; + } ; + if (psf->dataoffset < 0) + { psf_log_printf (psf, "Invalid SF_PRIVATE field : dataoffset == %D.\n", psf->dataoffset) ; + return 0 ; + } ; + if (psf->blockwidth && psf->blockwidth != psf->sf.channels * psf->bytewidth) + { psf_log_printf (psf, "Invalid SF_PRIVATE field : channels * bytewidth == %d.\n", + psf->sf.channels * psf->bytewidth) ; + return 0 ; + } ; + return 1 ; +} /* validate_psf */ + +static void +save_header_info (SF_PRIVATE *psf) +{ LSF_SNPRINTF (sf_logbuffer, sizeof (sf_logbuffer), "%s", psf->logbuffer) ; +} /* save_header_info */ + +static void +copy_filename (SF_PRIVATE *psf, const char *path) +{ const char *ccptr ; + char *cptr ; + + LSF_SNPRINTF (psf->filepath, sizeof (psf->filepath), "%s", path) ; + if ((ccptr = strrchr (path, '/')) || (ccptr = strrchr (path, '\\'))) + ccptr ++ ; + else + ccptr = path ; + + LSF_SNPRINTF (psf->filename, sizeof (psf->filename), "%s", ccptr) ; + + /* Now grab the directory. */ + LSF_SNPRINTF (psf->directory, sizeof (psf->directory), "%s", path) ; + if ((cptr = strrchr (psf->directory, '/')) || (cptr = strrchr (psf->directory, '\\'))) + cptr [1] = 0 ; + else + psf->directory [0] = 0 ; + + return ; +} /* copy_filename */ + +/*============================================================================== +*/ + +static int +psf_close (SF_PRIVATE *psf) +{ int error ; + + if (psf->codec_close) + error = psf->codec_close (psf) ; + if (psf->container_close) + error = psf->container_close (psf) ; + + psf_fclose (psf) ; + psf_close_rsrc (psf) ; + + if (psf->fdata) + free (psf->fdata) ; + + if (psf->interleave) + free (psf->interleave) ; + + if (psf->dither) + free (psf->dither) ; + + if (psf->peak_info) + free (psf->peak_info) ; + + if (psf->broadcast_info) + free (psf->broadcast_info) ; + + if (psf->loop_info) + free (psf->loop_info) ; + + if (psf->instrument) + free (psf->instrument) ; + + if (psf->format_desc) + { memset (psf->format_desc, 0, strlen (psf->format_desc)) ; + free (psf->format_desc) ; + } ; + + memset (psf, 0, sizeof (SF_PRIVATE)) ; + free (psf) ; + + return 0 ; +} /* psf_close */ + +static int +psf_open_file (SF_PRIVATE *psf, int mode, SF_INFO *sfinfo) +{ int error, format ; + + if (mode != SFM_READ && mode != SFM_WRITE && mode != SFM_RDWR) + return SFE_BAD_OPEN_MODE ; + + if (sfinfo == NULL) + return SFE_BAD_SF_INFO_PTR ; + + /* Zero out these fields. */ + sfinfo->frames = 0 ; + sfinfo->sections = 0 ; + sfinfo->seekable = 0 ; + + if (mode == SFM_READ) + { if ((sfinfo->format & SF_FORMAT_TYPEMASK) == SF_FORMAT_RAW) + { if (sf_format_check (sfinfo) == 0) + return SFE_RAW_BAD_FORMAT ; + } + else + memset (sfinfo, 0, sizeof (SF_INFO)) ; + } ; + + sf_errno = error = 0 ; + sf_logbuffer [0] = 0 ; + + memcpy (&(psf->sf), sfinfo, sizeof (SF_INFO)) ; + + psf->Magick = SNDFILE_MAGICK ; + psf->norm_float = SF_TRUE ; + psf->norm_double = SF_TRUE ; + psf->mode = mode ; + psf->dataoffset = -1 ; + psf->datalength = -1 ; + psf->read_current = -1 ; + psf->write_current = -1 ; + psf->auto_header = SF_FALSE ; + psf->rwf_endian = SF_ENDIAN_LITTLE ; + psf->seek = psf_default_seek ; + psf->float_int_mult = 0 ; + psf->float_max = -1.0 ; + + psf->sf.sections = 1 ; + + psf->is_pipe = psf_is_pipe (psf) ; + + if (psf->is_pipe) + { psf->sf.seekable = SF_FALSE ; + psf->filelength = SF_COUNT_MAX ; + } + else + { psf->sf.seekable = SF_TRUE ; + + /* File is open, so get the length. */ + psf->filelength = psf_get_filelen (psf) ; + } ; + + if (psf->fileoffset > 0) + { switch (psf->mode) + { case SFM_READ : + if (psf->filelength < 44) + { psf_log_printf (psf, "Short filelength: %D (fileoffset: %D)\n", psf->filelength, psf->fileoffset) ; + return SFE_BAD_OFFSET ; + } ; + break ; + + case SFM_WRITE : + psf->fileoffset = 0 ; + psf_fseek (psf, 0, SEEK_END) ; + psf->fileoffset = psf_ftell (psf) ; + break ; + + case SFM_RDWR : + return SFE_NO_EMBEDDED_RDWR ; + } ; + + psf_log_printf (psf, "Embedded file offset : %D\n", psf->fileoffset) ; + } ; + + if (psf->filelength == SF_COUNT_MAX) + psf_log_printf (psf, "Length : unknown\n") ; + else + psf_log_printf (psf, "Length : %D\n", psf->filelength) ; + + if (mode == SFM_WRITE || (mode == SFM_RDWR && psf->filelength == 0)) + { /* If the file is being opened for write or RDWR and the file is currently + ** empty, then the SF_INFO struct must contain valid data. + */ + if (sf_format_check (&(psf->sf)) == 0) + return SFE_BAD_OPEN_FORMAT ; + } + else if ((psf->sf.format & SF_FORMAT_TYPEMASK) != SF_FORMAT_RAW) + { /* If type RAW has not been specified then need to figure out file type. */ + psf->sf.format = guess_file_type (psf) ; + + if (psf->sf.format == 0) + psf->sf.format = format_from_extension (psf) ; + } ; + + /* Prevent unnecessary seeks */ + psf->last_op = psf->mode ; + + /* Set bytewidth if known. */ + switch (psf->sf.format & SF_FORMAT_SUBMASK) + { case SF_FORMAT_PCM_S8 : + case SF_FORMAT_PCM_U8 : + case SF_FORMAT_ULAW : + case SF_FORMAT_ALAW : + case SF_FORMAT_DPCM_8 : + psf->bytewidth = 1 ; + break ; + + case SF_FORMAT_PCM_16 : + case SF_FORMAT_DPCM_16 : + psf->bytewidth = 2 ; + break ; + + case SF_FORMAT_PCM_24 : + psf->bytewidth = 3 ; + break ; + + case SF_FORMAT_PCM_32 : + case SF_FORMAT_FLOAT : + psf->bytewidth = 4 ; + break ; + + case SF_FORMAT_DOUBLE : + psf->bytewidth = 8 ; + break ; + } ; + + /* Call the initialisation function for the relevant file type. */ + switch (psf->sf.format & SF_FORMAT_TYPEMASK) + { case SF_FORMAT_WAV : + case SF_FORMAT_WAVEX : + error = wav_open (psf) ; + break ; + + case SF_FORMAT_AIFF : + error = aiff_open (psf) ; + break ; + + case SF_FORMAT_AU : + error = au_open (psf) ; + break ; + + case SF_FORMAT_RAW : + error = raw_open (psf) ; + break ; + + case SF_FORMAT_W64 : + error = w64_open (psf) ; + break ; + + /* Lite remove start */ + case SF_FORMAT_PAF : + error = paf_open (psf) ; + break ; + + case SF_FORMAT_SVX : + error = svx_open (psf) ; + break ; + + case SF_FORMAT_NIST : + error = nist_open (psf) ; + break ; + + case SF_FORMAT_IRCAM : + error = ircam_open (psf) ; + break ; + + case SF_FORMAT_VOC : + error = voc_open (psf) ; + break ; + + case SF_FORMAT_SDS : + error = sds_open (psf) ; + break ; + + case SF_FORMAT_OGG : + error = ogg_open (psf) ; + break ; + + case SF_FORMAT_TXW : + error = txw_open (psf) ; + break ; + + case SF_FORMAT_WVE : + error = wve_open (psf) ; + break ; + + case SF_FORMAT_DWD : + error = dwd_open (psf) ; + break ; + + case SF_FORMAT_MAT4 : + error = mat4_open (psf) ; + break ; + + case SF_FORMAT_MAT5 : + error = mat5_open (psf) ; + break ; + + case SF_FORMAT_PVF : + error = pvf_open (psf) ; + break ; + + case SF_FORMAT_XI : + error = xi_open (psf) ; + break ; + + case SF_FORMAT_HTK : + error = htk_open (psf) ; + break ; + + case SF_FORMAT_SD2 : + error = sd2_open (psf) ; + break ; + + case SF_FORMAT_REX2 : + error = rx2_open (psf) ; + break ; + + case SF_FORMAT_AVR : + error = avr_open (psf) ; + break ; + + case SF_FORMAT_FLAC : + error = flac_open (psf) ; + break ; + + case SF_FORMAT_CAF : + error = caf_open (psf) ; + break ; + + /* Lite remove end */ + + default : + error = SFE_UNKNOWN_FORMAT ; + } ; + + if (error) + { if (error != SF_ERR_SYSTEM && error != SF_ERR_UNSUPPORTED_ENCODING) + { psf_log_printf (psf, "Parse error : %s\n", sf_error_number (error)) ; + error = SF_ERR_MALFORMED_FILE ; + } ; + + return error ; + } ; + + /* For now, check whether embedding is supported. */ + format = psf->sf.format & SF_FORMAT_TYPEMASK ; + if (psf->fileoffset > 0 && + (format != SF_FORMAT_WAV) && (format != SF_FORMAT_WAVEX) && + (format != SF_FORMAT_AIFF) && (format != SF_FORMAT_AU) + ) + return SFE_NO_EMBED_SUPPORT ; + + if (psf->fileoffset > 0) + psf_log_printf (psf, "Embedded file length : %D\n", psf->filelength) ; + + if (mode == SFM_RDWR && sf_format_check (&(psf->sf)) == 0) + return SFE_BAD_RDWR_FORMAT ; + + if (validate_sfinfo (&(psf->sf)) == 0) + { psf_log_SF_INFO (psf) ; + save_header_info (psf) ; + return SFE_BAD_SF_INFO ; + } ; + + if (validate_psf (psf) == 0) + { save_header_info (psf) ; + return SFE_INTERNAL ; + } ; + + psf->read_current = 0 ; + psf->write_current = (psf->mode == SFM_RDWR) ? psf->sf.frames : 0 ; + + memcpy (sfinfo, &(psf->sf), sizeof (SF_INFO)) ; + + return 0 ; +} /* psf_open_file */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: cd4f9e91-a8ec-4154-9bf6-fe4b8c69a615 +*/ diff --git a/libs/libsndfile/src/sndfile.h.in b/libs/libsndfile/src/sndfile.h.in new file mode 100644 index 0000000000..93f1d61e2b --- /dev/null +++ b/libs/libsndfile/src/sndfile.h.in @@ -0,0 +1,554 @@ +/* +** Copyright (C) 1999-2006 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +/* +** sndfile.h -- system-wide definitions +** +** API documentation is in the doc/ directory of the source code tarball +** and at http://www.mega-nerd.com/libsndfile/api.html. +*/ + +#ifndef SNDFILE_H +#define SNDFILE_H + +/* This is the version 1.0.X header file. */ +#define SNDFILE_1 + +#include + +/* For the Metrowerks CodeWarrior Pro Compiler (mainly MacOS) */ + +#if (defined (__MWERKS__)) +#include +#else +#include +#endif + +#ifdef __cplusplus +extern "C" { +#endif /* __cplusplus */ + +/* The following file types can be read and written. +** A file type would consist of a major type (ie SF_FORMAT_WAV) bitwise +** ORed with a minor type (ie SF_FORMAT_PCM). SF_FORMAT_TYPEMASK and +** SF_FORMAT_SUBMASK can be used to separate the major and minor file +** types. +*/ + +enum +{ /* Major formats. */ + SF_FORMAT_WAV = 0x010000, /* Microsoft WAV format (little endian default). */ + SF_FORMAT_AIFF = 0x020000, /* Apple/SGI AIFF format (big endian). */ + SF_FORMAT_AU = 0x030000, /* Sun/NeXT AU format (big endian). */ + SF_FORMAT_RAW = 0x040000, /* RAW PCM data. */ + SF_FORMAT_PAF = 0x050000, /* Ensoniq PARIS file format. */ + SF_FORMAT_SVX = 0x060000, /* Amiga IFF / SVX8 / SV16 format. */ + SF_FORMAT_NIST = 0x070000, /* Sphere NIST format. */ + SF_FORMAT_VOC = 0x080000, /* VOC files. */ + SF_FORMAT_IRCAM = 0x0A0000, /* Berkeley/IRCAM/CARL */ + SF_FORMAT_W64 = 0x0B0000, /* Sonic Foundry's 64 bit RIFF/WAV */ + SF_FORMAT_MAT4 = 0x0C0000, /* Matlab (tm) V4.2 / GNU Octave 2.0 */ + SF_FORMAT_MAT5 = 0x0D0000, /* Matlab (tm) V5.0 / GNU Octave 2.1 */ + SF_FORMAT_PVF = 0x0E0000, /* Portable Voice Format */ + SF_FORMAT_XI = 0x0F0000, /* Fasttracker 2 Extended Instrument */ + SF_FORMAT_HTK = 0x100000, /* HMM Tool Kit format */ + SF_FORMAT_SDS = 0x110000, /* Midi Sample Dump Standard */ + SF_FORMAT_AVR = 0x120000, /* Audio Visual Research */ + SF_FORMAT_WAVEX = 0x130000, /* MS WAVE with WAVEFORMATEX */ + SF_FORMAT_SD2 = 0x160000, /* Sound Designer 2 */ + SF_FORMAT_FLAC = 0x170000, /* FLAC lossless file format */ + SF_FORMAT_CAF = 0x180000, /* Core Audio File format */ + + /* Subtypes from here on. */ + + SF_FORMAT_PCM_S8 = 0x0001, /* Signed 8 bit data */ + SF_FORMAT_PCM_16 = 0x0002, /* Signed 16 bit data */ + SF_FORMAT_PCM_24 = 0x0003, /* Signed 24 bit data */ + SF_FORMAT_PCM_32 = 0x0004, /* Signed 32 bit data */ + + SF_FORMAT_PCM_U8 = 0x0005, /* Unsigned 8 bit data (WAV and RAW only) */ + + SF_FORMAT_FLOAT = 0x0006, /* 32 bit float data */ + SF_FORMAT_DOUBLE = 0x0007, /* 64 bit float data */ + + SF_FORMAT_ULAW = 0x0010, /* U-Law encoded. */ + SF_FORMAT_ALAW = 0x0011, /* A-Law encoded. */ + SF_FORMAT_IMA_ADPCM = 0x0012, /* IMA ADPCM. */ + SF_FORMAT_MS_ADPCM = 0x0013, /* Microsoft ADPCM. */ + + SF_FORMAT_GSM610 = 0x0020, /* GSM 6.10 encoding. */ + SF_FORMAT_VOX_ADPCM = 0x0021, /* OKI / Dialogix ADPCM */ + + SF_FORMAT_G721_32 = 0x0030, /* 32kbs G721 ADPCM encoding. */ + SF_FORMAT_G723_24 = 0x0031, /* 24kbs G723 ADPCM encoding. */ + SF_FORMAT_G723_40 = 0x0032, /* 40kbs G723 ADPCM encoding. */ + + SF_FORMAT_DWVW_12 = 0x0040, /* 12 bit Delta Width Variable Word encoding. */ + SF_FORMAT_DWVW_16 = 0x0041, /* 16 bit Delta Width Variable Word encoding. */ + SF_FORMAT_DWVW_24 = 0x0042, /* 24 bit Delta Width Variable Word encoding. */ + SF_FORMAT_DWVW_N = 0x0043, /* N bit Delta Width Variable Word encoding. */ + + SF_FORMAT_DPCM_8 = 0x0050, /* 8 bit differential PCM (XI only) */ + SF_FORMAT_DPCM_16 = 0x0051, /* 16 bit differential PCM (XI only) */ + + /* Endian-ness options. */ + + SF_ENDIAN_FILE = 0x00000000, /* Default file endian-ness. */ + SF_ENDIAN_LITTLE = 0x10000000, /* Force little endian-ness. */ + SF_ENDIAN_BIG = 0x20000000, /* Force big endian-ness. */ + SF_ENDIAN_CPU = 0x30000000, /* Force CPU endian-ness. */ + + SF_FORMAT_SUBMASK = 0x0000FFFF, + SF_FORMAT_TYPEMASK = 0x0FFF0000, + SF_FORMAT_ENDMASK = 0x30000000 +} ; + +/* +** The following are the valid command numbers for the sf_command() +** interface. The use of these commands is documented in the file +** command.html in the doc directory of the source code distribution. +*/ + +enum +{ SFC_GET_LIB_VERSION = 0x1000, + SFC_GET_LOG_INFO = 0x1001, + + SFC_GET_NORM_DOUBLE = 0x1010, + SFC_GET_NORM_FLOAT = 0x1011, + SFC_SET_NORM_DOUBLE = 0x1012, + SFC_SET_NORM_FLOAT = 0x1013, + SFC_SET_SCALE_FLOAT_INT_READ = 0x1014, + + SFC_GET_SIMPLE_FORMAT_COUNT = 0x1020, + SFC_GET_SIMPLE_FORMAT = 0x1021, + + SFC_GET_FORMAT_INFO = 0x1028, + + SFC_GET_FORMAT_MAJOR_COUNT = 0x1030, + SFC_GET_FORMAT_MAJOR = 0x1031, + SFC_GET_FORMAT_SUBTYPE_COUNT = 0x1032, + SFC_GET_FORMAT_SUBTYPE = 0x1033, + + SFC_CALC_SIGNAL_MAX = 0x1040, + SFC_CALC_NORM_SIGNAL_MAX = 0x1041, + SFC_CALC_MAX_ALL_CHANNELS = 0x1042, + SFC_CALC_NORM_MAX_ALL_CHANNELS = 0x1043, + SFC_GET_SIGNAL_MAX = 0x1044, + SFC_GET_MAX_ALL_CHANNELS = 0x1045, + + SFC_SET_ADD_PEAK_CHUNK = 0x1050, + + SFC_UPDATE_HEADER_NOW = 0x1060, + SFC_SET_UPDATE_HEADER_AUTO = 0x1061, + + SFC_FILE_TRUNCATE = 0x1080, + + SFC_SET_RAW_START_OFFSET = 0x1090, + + SFC_SET_DITHER_ON_WRITE = 0x10A0, + SFC_SET_DITHER_ON_READ = 0x10A1, + + SFC_GET_DITHER_INFO_COUNT = 0x10A2, + SFC_GET_DITHER_INFO = 0x10A3, + + SFC_GET_EMBED_FILE_INFO = 0x10B0, + + SFC_SET_CLIPPING = 0x10C0, + SFC_GET_CLIPPING = 0x10C1, + + SFC_GET_INSTRUMENT = 0x10D0, + SFC_SET_INSTRUMENT = 0x10D1, + + SFC_GET_LOOP_INFO = 0x10E0, + + SFC_GET_BROADCAST_INFO = 0x10F0, + SFC_SET_BROADCAST_INFO = 0x10F1, + + /* Following commands for testing only. */ + SFC_TEST_IEEE_FLOAT_REPLACE = 0x6001, + + /* + ** SFC_SET_ADD_* values are deprecated and will disappear at some + ** time in the future. They are guaranteed to be here up to and + ** including version 1.0.8 to avoid breakage of existng software. + ** They currently do nothing and will continue to do nothing. + */ + SFC_SET_ADD_DITHER_ON_WRITE = 0x1070, + SFC_SET_ADD_DITHER_ON_READ = 0x1071 +} ; + + +/* +** String types that can be set and read from files. Not all file types +** support this and even the file types which support one, may not support +** all string types. +*/ + +enum +{ SF_STR_TITLE = 0x01, + SF_STR_COPYRIGHT = 0x02, + SF_STR_SOFTWARE = 0x03, + SF_STR_ARTIST = 0x04, + SF_STR_COMMENT = 0x05, + SF_STR_DATE = 0x06 +} ; + +/* +** Use the following as the start and end index when doing metadata +** transcoding. +*/ + +#define SF_STR_FIRST SF_STR_TITLE +#define SF_STR_LAST SF_STR_DATE + +enum +{ /* True and false */ + SF_FALSE = 0, + SF_TRUE = 1, + + /* Modes for opening files. */ + SFM_READ = 0x10, + SFM_WRITE = 0x20, + SFM_RDWR = 0x30 +} ; + +/* Public error values. These are guaranteed to remain unchanged for the duration +** of the library major version number. +** There are also a large number of private error numbers which are internal to +** the library which can change at any time. +*/ + +enum +{ SF_ERR_NO_ERROR = 0, + SF_ERR_UNRECOGNISED_FORMAT = 1, + SF_ERR_SYSTEM = 2, + SF_ERR_MALFORMED_FILE = 3, + SF_ERR_UNSUPPORTED_ENCODING = 4 +} ; + +/* A SNDFILE* pointer can be passed around much like stdio.h's FILE* pointer. */ + +typedef struct SNDFILE_tag SNDFILE ; + +/* The following typedef is system specific and is defined when libsndfile is. +** compiled. sf_count_t can be one of loff_t (Linux), off_t (*BSD), +** off64_t (Solaris), __int64_t (Win32) etc. +*/ + +typedef @TYPEOF_SF_COUNT_T@ sf_count_t ; + +#define SF_COUNT_MAX @SF_COUNT_MAX@ + +/* A pointer to a SF_INFO structure is passed to sf_open_read () and filled in. +** On write, the SF_INFO structure is filled in by the user and passed into +** sf_open_write (). +*/ + +struct SF_INFO +{ sf_count_t frames ; /* Used to be called samples. Changed to avoid confusion. */ + int samplerate ; + int channels ; + int format ; + int sections ; + int seekable ; +} ; + +typedef struct SF_INFO SF_INFO ; + +/* The SF_FORMAT_INFO struct is used to retrieve information about the sound +** file formats libsndfile supports using the sf_command () interface. +** +** Using this interface will allow applications to support new file formats +** and encoding types when libsndfile is upgraded, without requiring +** re-compilation of the application. +** +** Please consult the libsndfile documentation (particularly the information +** on the sf_command () interface) for examples of its use. +*/ + +typedef struct +{ int format ; + const char *name ; + const char *extension ; +} SF_FORMAT_INFO ; + +/* +** Enums and typedefs for adding dither on read and write. +** See the html documentation for sf_command(), SFC_SET_DITHER_ON_WRITE +** and SFC_SET_DITHER_ON_READ. +*/ + +enum +{ SFD_DEFAULT_LEVEL = 0, + SFD_CUSTOM_LEVEL = 0x40000000, + + SFD_NO_DITHER = 500, + SFD_WHITE = 501, + SFD_TRIANGULAR_PDF = 502 +} ; + +typedef struct +{ int type ; + double level ; + const char *name ; +} SF_DITHER_INFO ; + +/* Struct used to retrieve information about a file embedded within a +** larger file. See SFC_GET_EMBED_FILE_INFO. +*/ + +typedef struct +{ sf_count_t offset ; + sf_count_t length ; +} SF_EMBED_FILE_INFO ; + +/* +** Structs used to retrieve music sample information from a file. +*/ + +enum +{ /* + ** The loop mode field in SF_INSTRUMENT will be one of the following. + */ + SF_LOOP_NONE = 800, + SF_LOOP_FORWARD, + SF_LOOP_BACKWARD, + SF_LOOP_ALTERNATING +} ; + +typedef struct +{ int gain ; + char basenote, detune ; + char velocity_lo, velocity_hi ; + char key_lo, key_hi ; + int loop_count ; + + struct + { int mode ; + unsigned int start ; + unsigned int end ; + unsigned int count ; + } loops [16] ; /* make variable in a sensible way */ +} SF_INSTRUMENT ; + + + +/* Struct used to retrieve loop information from a file.*/ +typedef struct +{ + short time_sig_num ; /* any positive integer > 0 */ + short time_sig_den ; /* any positive power of 2 > 0 */ + int loop_mode ; /* see SF_LOOP enum */ + + int num_beats ; /* this is NOT the amount of quarter notes !!!*/ + /* a full bar of 4/4 is 4 beats */ + /* a full bar of 7/8 is 7 beats */ + + float bpm ; /* suggestion, as it can be calculated using other fields:*/ + /* file's lenght, file's sampleRate and our time_sig_den*/ + /* -> bpms are always the amount of _quarter notes_ per minute */ + + int root_key ; /* MIDI note, or -1 for None */ + int future [6] ; +} SF_LOOP_INFO ; + + +/* Struct used to retrieve broadcast (EBU) information from a file. +** Strongly (!) based on EBU "bext" chunk format used in Broadcast WAVE. +*/ +typedef struct +{ char description [256] ; + char originator [32] ; + char originator_reference [32] ; + char origination_date [10] ; + char origination_time [8] ; + int time_reference_low ; + int time_reference_high ; + short version ; + char umid [64] ; + char reserved [190] ; + unsigned int coding_history_size ; + char coding_history [256] ; +} SF_BROADCAST_INFO ; + +typedef sf_count_t (*sf_vio_get_filelen) (void *user_data) ; +typedef sf_count_t (*sf_vio_seek) (sf_count_t offset, int whence, void *user_data) ; +typedef sf_count_t (*sf_vio_read) (void *ptr, sf_count_t count, void *user_data) ; +typedef sf_count_t (*sf_vio_write) (const void *ptr, sf_count_t count, void *user_data) ; +typedef sf_count_t (*sf_vio_tell) (void *user_data) ; + +struct SF_VIRTUAL_IO +{ sf_vio_get_filelen get_filelen ; + sf_vio_seek seek ; + sf_vio_read read ; + sf_vio_write write ; + sf_vio_tell tell ; +} ; + +typedef struct SF_VIRTUAL_IO SF_VIRTUAL_IO ; + +/* Open the specified file for read, write or both. On error, this will +** return a NULL pointer. To find the error number, pass a NULL SNDFILE +** to sf_perror () or sf_error_str (). +** All calls to sf_open() should be matched with a call to sf_close(). +*/ + +SNDFILE* sf_open (const char *path, int mode, SF_INFO *sfinfo) ; + +/* Use the existing file descriptor to create a SNDFILE object. If close_desc +** is TRUE, the file descriptor will be closed when sf_close() is called. If +** it is FALSE, the descritor will not be closed. +** When passed a descriptor like this, the library will assume that the start +** of file header is at the current file offset. This allows sound files within +** larger container files to be read and/or written. +** On error, this will return a NULL pointer. To find the error number, pass a +** NULL SNDFILE to sf_perror () or sf_error_str (). +** All calls to sf_open_fd() should be matched with a call to sf_close(). + +*/ + +SNDFILE* sf_open_fd (int fd, int mode, SF_INFO *sfinfo, int close_desc) ; + +SNDFILE* sf_open_virtual (SF_VIRTUAL_IO *sfvirtual, int mode, SF_INFO *sfinfo, void *user_data) ; + +/* sf_error () returns a error number which can be translated to a text +** string using sf_error_number(). +*/ + +int sf_error (SNDFILE *sndfile) ; + +/* sf_strerror () returns to the caller a pointer to the current error message for +** the given SNDFILE. +*/ + +const char* sf_strerror (SNDFILE *sndfile) ; + +/* sf_error_number () allows the retrieval of the error string for each internal +** error number. +** +*/ + +const char* sf_error_number (int errnum) ; + +/* The following three error functions are deprecated but they will remain in the +** library for the forseeable future. The function sf_strerror() should be used +** in their place. +*/ + +int sf_perror (SNDFILE *sndfile) ; +int sf_error_str (SNDFILE *sndfile, char* str, size_t len) ; + + +/* Return TRUE if fields of the SF_INFO struct are a valid combination of values. */ + +int sf_command (SNDFILE *sndfile, int command, void *data, int datasize) ; + +/* Return TRUE if fields of the SF_INFO struct are a valid combination of values. */ + +int sf_format_check (const SF_INFO *info) ; + +/* Seek within the waveform data chunk of the SNDFILE. sf_seek () uses +** the same values for whence (SEEK_SET, SEEK_CUR and SEEK_END) as +** stdio.h function fseek (). +** An offset of zero with whence set to SEEK_SET will position the +** read / write pointer to the first data sample. +** On success sf_seek returns the current position in (multi-channel) +** samples from the start of the file. +** Please see the libsndfile documentation for moving the read pointer +** separately from the write pointer on files open in mode SFM_RDWR. +** On error all of these functions return -1. +*/ + +sf_count_t sf_seek (SNDFILE *sndfile, sf_count_t frames, int whence) ; + +/* Functions for retrieving and setting string data within sound files. +** Not all file types support this features; AIFF and WAV do. For both +** functions, the str_type parameter must be one of the SF_STR_* values +** defined above. +** On error, sf_set_string() returns non-zero while sf_get_string() +** returns NULL. +*/ + +int sf_set_string (SNDFILE *sndfile, int str_type, const char* str) ; + +const char* sf_get_string (SNDFILE *sndfile, int str_type) ; + +/* Functions for reading/writing the waveform data of a sound file. +*/ + +sf_count_t sf_read_raw (SNDFILE *sndfile, void *ptr, sf_count_t bytes) ; +sf_count_t sf_write_raw (SNDFILE *sndfile, const void *ptr, sf_count_t bytes) ; + +/* Functions for reading and writing the data chunk in terms of frames. +** The number of items actually read/written = frames * number of channels. +** sf_xxxx_raw read/writes the raw data bytes from/to the file +** sf_xxxx_short passes data in the native short format +** sf_xxxx_int passes data in the native int format +** sf_xxxx_float passes data in the native float format +** sf_xxxx_double passes data in the native double format +** All of these read/write function return number of frames read/written. +*/ + +sf_count_t sf_readf_short (SNDFILE *sndfile, short *ptr, sf_count_t frames) ; +sf_count_t sf_writef_short (SNDFILE *sndfile, const short *ptr, sf_count_t frames) ; + +sf_count_t sf_readf_int (SNDFILE *sndfile, int *ptr, sf_count_t frames) ; +sf_count_t sf_writef_int (SNDFILE *sndfile, const int *ptr, sf_count_t frames) ; + +sf_count_t sf_readf_float (SNDFILE *sndfile, float *ptr, sf_count_t frames) ; +sf_count_t sf_writef_float (SNDFILE *sndfile, const float *ptr, sf_count_t frames) ; + +sf_count_t sf_readf_double (SNDFILE *sndfile, double *ptr, sf_count_t frames) ; +sf_count_t sf_writef_double (SNDFILE *sndfile, const double *ptr, sf_count_t frames) ; + +/* Functions for reading and writing the data chunk in terms of items. +** Otherwise similar to above. +** All of these read/write function return number of items read/written. +*/ + +sf_count_t sf_read_short (SNDFILE *sndfile, short *ptr, sf_count_t items) ; +sf_count_t sf_write_short (SNDFILE *sndfile, const short *ptr, sf_count_t items) ; + +sf_count_t sf_read_int (SNDFILE *sndfile, int *ptr, sf_count_t items) ; +sf_count_t sf_write_int (SNDFILE *sndfile, const int *ptr, sf_count_t items) ; + +sf_count_t sf_read_float (SNDFILE *sndfile, float *ptr, sf_count_t items) ; +sf_count_t sf_write_float (SNDFILE *sndfile, const float *ptr, sf_count_t items) ; + +sf_count_t sf_read_double (SNDFILE *sndfile, double *ptr, sf_count_t items) ; +sf_count_t sf_write_double (SNDFILE *sndfile, const double *ptr, sf_count_t items) ; + +/* Close the SNDFILE and clean up all memory allocations associated with this +** file. +** Returns 0 on success, or an error number. +*/ + +int sf_close (SNDFILE *sndfile) ; + +/* If the file is opened SFM_WRITE or SFM_RDWR, call fsync() on the file +** to force the writing of data to disk. If the file is opened SFM_READ +** no action is taken. +*/ + +void sf_write_sync (SNDFILE *sndfile) ; + +#ifdef __cplusplus +} /* extern "C" */ +#endif /* __cplusplus */ + +#endif /* SNDFILE_H */ diff --git a/libs/libsndfile/src/stamp-h1 b/libs/libsndfile/src/stamp-h1 new file mode 100644 index 0000000000..57ea58e405 --- /dev/null +++ b/libs/libsndfile/src/stamp-h1 @@ -0,0 +1 @@ +timestamp for src/config.h diff --git a/libs/libsndfile/src/strings.c b/libs/libsndfile/src/strings.c new file mode 100644 index 0000000000..2433f9b069 --- /dev/null +++ b/libs/libsndfile/src/strings.c @@ -0,0 +1,204 @@ +/* +** Copyright (C) 2001-2004 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include + +#include "sndfile.h" +#include "common.h" + +#define STRINGS_DEBUG 0 +#if STRINGS_DEBUG +static void hexdump (void *data, int len) ; +#endif + +int +psf_store_string (SF_PRIVATE *psf, int str_type, const char *str) +{ static char lsf_name [] = PACKAGE "-" VERSION ; + static char bracket_name [] = " (" PACKAGE "-" VERSION ")" ; + int k, str_len, len_remaining, str_flags ; + + if (str == NULL) + return SFE_STR_BAD_STRING ; + + str_len = strlen (str) ; + + /* A few extra checks for write mode. */ + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { if ((psf->str_flags & SF_STR_ALLOW_START) == 0) + return SFE_STR_NO_SUPPORT ; + if ((psf->str_flags & SF_STR_ALLOW_END) == 0) + return SFE_STR_NO_SUPPORT ; + /* Only allow zero length strings for software. */ + if (str_type != SF_STR_SOFTWARE && str_len == 0) + return SFE_STR_BAD_STRING ; + } ; + + /* Determine flags */ + str_flags = SF_STR_LOCATE_START ; + if (psf->have_written) + { if ((psf->str_flags & SF_STR_ALLOW_END) == 0) + return SFE_STR_NO_ADD_END ; + str_flags = SF_STR_LOCATE_END ; + } ; + + /* Find next free slot in table. */ + for (k = 0 ; k < SF_MAX_STRINGS ; k++) + if (psf->strings [k].type == 0) + break ; + + /* More sanity checking. */ + if (k >= SF_MAX_STRINGS) + return SFE_STR_MAX_COUNT ; + + if (k == 0 && psf->str_end != NULL) + { psf_log_printf (psf, "SFE_STR_WEIRD : k == 0 && psf->str_end != NULL\n") ; + return SFE_STR_WEIRD ; + } ; + + if (k != 0 && psf->str_end == NULL) + { psf_log_printf (psf, "SFE_STR_WEIRD : k != 0 && psf->str_end == NULL\n") ; + return SFE_STR_WEIRD ; + } ; + + /* Special case for the first string. */ + if (k == 0) + psf->str_end = psf->str_storage ; + + +#if STRINGS_DEBUG + psf_log_printf (psf, "str_storage : %X\n", (int) psf->str_storage) ; + psf_log_printf (psf, "str_end : %X\n", (int) psf->str_end) ; + psf_log_printf (psf, "sizeof (str_storage) : %d\n", SIGNED_SIZEOF (psf->str_storage)) ; +#endif + + len_remaining = SIGNED_SIZEOF (psf->str_storage) - (psf->str_end - psf->str_storage) ; + + if (len_remaining < str_len + 2) + return SFE_STR_MAX_DATA ; + + switch (str_type) + { case SF_STR_SOFTWARE : + /* In write mode, want to append libsndfile-version to string. */ + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { psf->strings [k].type = str_type ; + psf->strings [k].str = psf->str_end ; + psf->strings [k].flags = str_flags ; + + memcpy (psf->str_end, str, str_len + 1) ; + psf->str_end += str_len ; + + /* + ** If the supplied string does not already contain a + ** libsndfile-X.Y.Z component, then add it. + */ + if (strstr (str, PACKAGE) == NULL && len_remaining > (int) (strlen (bracket_name) + str_len + 2)) + { if (strlen (str) == 0) + strncat (psf->str_end, lsf_name, len_remaining) ; + else + strncat (psf->str_end, bracket_name, len_remaining) ; + psf->str_end += strlen (psf->str_end) ; + } ; + + /* Plus one to catch string terminator. */ + psf->str_end += 1 ; + break ; + } ; + + /* Fall though if not write mode. */ + + case SF_STR_TITLE : + case SF_STR_COPYRIGHT : + case SF_STR_ARTIST : + case SF_STR_COMMENT : + case SF_STR_DATE : + psf->strings [k].type = str_type ; + psf->strings [k].str = psf->str_end ; + psf->strings [k].flags = str_flags ; + + /* Plus one to catch string terminator. */ + memcpy (psf->str_end, str, str_len + 1) ; + psf->str_end += str_len + 1 ; + break ; + + default : + return SFE_STR_BAD_TYPE ; + } ; + + psf->str_flags |= (psf->have_written) ? SF_STR_LOCATE_END : SF_STR_LOCATE_START ; + +#if STRINGS_DEBUG + hexdump (psf->str_storage, 300) ; +#endif + + return 0 ; +} /* psf_store_string */ + +int +psf_set_string (SF_PRIVATE *psf, int str_type, const char *str) +{ if (psf->mode == SFM_READ) + return SFE_STR_NOT_WRITE ; + + return psf_store_string (psf, str_type, str) ; +} /* psf_set_string */ + +const char* +psf_get_string (SF_PRIVATE *psf, int str_type) +{ int k ; + + for (k = 0 ; k < SF_MAX_STRINGS ; k++) + if (str_type == psf->strings [k].type) + return psf->strings [k].str ; + + return NULL ; +} /* psf_get_string */ + +#if STRINGS_DEBUG + +#include +static void +hexdump (void *data, int len) +{ unsigned char *ptr ; + int k ; + + ptr = data ; + + puts ("---------------------------------------------------------") ; + while (len >= 16) + { for (k = 0 ; k < 16 ; k++) + printf ("%02X ", ptr [k] & 0xFF) ; + printf (" ") ; + for (k = 0 ; k < 16 ; k++) + printf ("%c", isprint (ptr [k]) ? ptr [k] : '.') ; + puts ("") ; + ptr += 16 ; + len -= 16 ; + } ; +} /* hexdump */ + +#endif +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 04393aa1-9389-46fe-baf2-58a7bd544fd6 +*/ diff --git a/libs/libsndfile/src/svx.c b/libs/libsndfile/src/svx.c new file mode 100644 index 0000000000..3ef461ddec --- /dev/null +++ b/libs/libsndfile/src/svx.c @@ -0,0 +1,410 @@ +/* +** Copyright (C) 1999-2004 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" + + +/*------------------------------------------------------------------------------ + * Macros to handle big/little endian issues. +*/ + +#define FORM_MARKER (MAKE_MARKER ('F', 'O', 'R', 'M')) +#define SVX8_MARKER (MAKE_MARKER ('8', 'S', 'V', 'X')) +#define SV16_MARKER (MAKE_MARKER ('1', '6', 'S', 'V')) +#define VHDR_MARKER (MAKE_MARKER ('V', 'H', 'D', 'R')) +#define BODY_MARKER (MAKE_MARKER ('B', 'O', 'D', 'Y')) + +#define ATAK_MARKER (MAKE_MARKER ('A', 'T', 'A', 'K')) +#define RLSE_MARKER (MAKE_MARKER ('R', 'L', 'S', 'E')) + +#define c_MARKER (MAKE_MARKER ('(', 'c', ')', ' ')) +#define NAME_MARKER (MAKE_MARKER ('N', 'A', 'M', 'E')) +#define AUTH_MARKER (MAKE_MARKER ('A', 'U', 'T', 'H')) +#define ANNO_MARKER (MAKE_MARKER ('A', 'N', 'N', 'O')) +#define CHAN_MARKER (MAKE_MARKER ('C', 'H', 'A', 'N')) + +/*------------------------------------------------------------------------------ + * Typedefs for file chunks. +*/ + +typedef struct +{ unsigned int oneShotHiSamples, repeatHiSamples, samplesPerHiCycle ; + unsigned short samplesPerSec ; + unsigned char octave, compression ; + unsigned int volume ; +} VHDR_CHUNK ; + +enum { + HAVE_FORM = 0x01, + + HAVE_SVX = 0x02, + HAVE_VHDR = 0x04, + HAVE_BODY = 0x08 +} ; + +/*------------------------------------------------------------------------------ + * Private static functions. +*/ + +static int svx_close (SF_PRIVATE *psf) ; +static int svx_write_header (SF_PRIVATE *psf, int calc_length) ; +static int svx_read_header (SF_PRIVATE *psf) ; + +/*------------------------------------------------------------------------------ +** Public function. +*/ + +int +svx_open (SF_PRIVATE *psf) +{ int error ; + + if (psf->mode == SFM_READ || (psf->mode == SFM_RDWR && psf->filelength > 0)) + { if ((error = svx_read_header (psf))) + return error ; + + psf->endian = SF_ENDIAN_BIG ; /* All SVX files are big endian. */ + + psf->blockwidth = psf->sf.channels * psf->bytewidth ; + if (psf->blockwidth) + psf->sf.frames = psf->datalength / psf->blockwidth ; + + psf_fseek (psf, psf->dataoffset, SEEK_SET) ; + } ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { if (psf->is_pipe) + return SFE_NO_PIPE_WRITE ; + + if ((psf->sf.format & SF_FORMAT_TYPEMASK) != SF_FORMAT_SVX) + return SFE_BAD_OPEN_FORMAT ; + + psf->endian = psf->sf.format & SF_FORMAT_ENDMASK ; + + if (psf->endian == SF_ENDIAN_LITTLE || (CPU_IS_LITTLE_ENDIAN && psf->endian == SF_ENDIAN_CPU)) + return SFE_BAD_ENDIAN ; + + psf->endian = SF_ENDIAN_BIG ; /* All SVX files are big endian. */ + + error = svx_write_header (psf, SF_FALSE) ; + if (error) + return error ; + + psf->write_header = svx_write_header ; + } ; + + psf->container_close = svx_close ; + + if ((error = pcm_init (psf))) + return error ; + + return 0 ; +} /* svx_open */ + +/*------------------------------------------------------------------------------ +*/ + +static int +svx_read_header (SF_PRIVATE *psf) +{ VHDR_CHUNK vhdr ; + unsigned int FORMsize, vhdrsize, dword, marker ; + int filetype = 0, parsestage = 0, done = 0 ; + int bytecount = 0, channels ; + + memset (&vhdr, 0, sizeof (vhdr)) ; + psf_binheader_readf (psf, "p", 0) ; + + /* Set default number of channels. Currently can't handle stereo SVX files. */ + psf->sf.channels = 1 ; + + psf->sf.format = SF_FORMAT_SVX ; + + while (! done) + { psf_binheader_readf (psf, "m", &marker) ; + switch (marker) + { case FORM_MARKER : + if (parsestage) + return SFE_SVX_NO_FORM ; + + psf_binheader_readf (psf, "E4", &FORMsize) ; + + if (FORMsize != psf->filelength - 2 * sizeof (dword)) + { dword = psf->filelength - 2 * sizeof (dword) ; + psf_log_printf (psf, "FORM : %d (should be %d)\n", FORMsize, dword) ; + FORMsize = dword ; + } + else + psf_log_printf (psf, "FORM : %d\n", FORMsize) ; + parsestage |= HAVE_FORM ; + break ; + + case SVX8_MARKER : + case SV16_MARKER : + if (! (parsestage & HAVE_FORM)) + return SFE_SVX_NO_FORM ; + filetype = marker ; + psf_log_printf (psf, " %M\n", marker) ; + parsestage |= HAVE_SVX ; + break ; + + case VHDR_MARKER : + if (! (parsestage & (HAVE_FORM | HAVE_SVX))) + return SFE_SVX_NO_FORM ; + + psf_binheader_readf (psf, "E4", &vhdrsize) ; + + psf_log_printf (psf, " VHDR : %d\n", vhdrsize) ; + + psf_binheader_readf (psf, "E4442114", &(vhdr.oneShotHiSamples), &(vhdr.repeatHiSamples), + &(vhdr.samplesPerHiCycle), &(vhdr.samplesPerSec), &(vhdr.octave), &(vhdr.compression), + &(vhdr.volume)) ; + + psf_log_printf (psf, " OneShotHiSamples : %d\n", vhdr.oneShotHiSamples) ; + psf_log_printf (psf, " RepeatHiSamples : %d\n", vhdr.repeatHiSamples) ; + psf_log_printf (psf, " samplesPerHiCycle : %d\n", vhdr.samplesPerHiCycle) ; + psf_log_printf (psf, " Sample Rate : %d\n", vhdr.samplesPerSec) ; + psf_log_printf (psf, " Octave : %d\n", vhdr.octave) ; + + psf_log_printf (psf, " Compression : %d => ", vhdr.compression) ; + + switch (vhdr.compression) + { case 0 : psf_log_printf (psf, "None.\n") ; + break ; + case 1 : psf_log_printf (psf, "Fibonacci delta\n") ; + break ; + case 2 : psf_log_printf (psf, "Exponential delta\n") ; + break ; + } ; + + psf_log_printf (psf, " Volume : %d\n", vhdr.volume) ; + + psf->sf.samplerate = vhdr.samplesPerSec ; + + if (filetype == SVX8_MARKER) + { psf->sf.format |= SF_FORMAT_PCM_S8 ; + psf->bytewidth = 1 ; + } + else if (filetype == SV16_MARKER) + { psf->sf.format |= SF_FORMAT_PCM_16 ; + psf->bytewidth = 2 ; + } ; + + parsestage |= HAVE_VHDR ; + break ; + + case BODY_MARKER : + if (! (parsestage & HAVE_VHDR)) + return SFE_SVX_NO_BODY ; + + psf_binheader_readf (psf, "E4", &dword) ; + psf->datalength = dword ; + + psf->dataoffset = psf_ftell (psf) ; + + if (psf->datalength > psf->filelength - psf->dataoffset) + { psf_log_printf (psf, " BODY : %D (should be %D)\n", psf->datalength, psf->filelength - psf->dataoffset) ; + psf->datalength = psf->filelength - psf->dataoffset ; + } + else + psf_log_printf (psf, " BODY : %D\n", psf->datalength) ; + + parsestage |= HAVE_BODY ; + + if (! psf->sf.seekable) + break ; + + psf_fseek (psf, psf->datalength, SEEK_CUR) ; + break ; + + case NAME_MARKER : + if (! (parsestage & HAVE_SVX)) + return SFE_SVX_NO_FORM ; + + psf_binheader_readf (psf, "E4", &dword) ; + + psf_log_printf (psf, " %M : %d\n", marker, dword) ; + + if (strlen (psf->filename) != dword) + { if (dword > sizeof (psf->filename) - 1) + return SFE_SVX_BAD_NAME_LENGTH ; + + psf_binheader_readf (psf, "b", psf->filename, dword) ; + psf->filename [dword] = 0 ; + } + else + psf_binheader_readf (psf, "j", dword) ; + break ; + + case ANNO_MARKER : + if (! (parsestage & HAVE_SVX)) + return SFE_SVX_NO_FORM ; + + psf_binheader_readf (psf, "E4", &dword) ; + + psf_log_printf (psf, " %M : %d\n", marker, dword) ; + + psf_binheader_readf (psf, "j", dword) ; + break ; + + case CHAN_MARKER : + if (! (parsestage & HAVE_SVX)) + return SFE_SVX_NO_FORM ; + + psf_binheader_readf (psf, "E4", &dword) ; + + psf_log_printf (psf, " %M : %d\n", marker, dword) ; + + bytecount += psf_binheader_readf (psf, "E4", &channels) ; + psf->sf.channels = channels ; + + psf_log_printf (psf, " Channels : %d\n", channels) ; + + psf_binheader_readf (psf, "j", dword - bytecount) ; + break ; + + + case AUTH_MARKER : + case c_MARKER : + if (! (parsestage & HAVE_SVX)) + return SFE_SVX_NO_FORM ; + + psf_binheader_readf (psf, "E4", &dword) ; + + psf_log_printf (psf, " %M : %d\n", marker, dword) ; + + psf_binheader_readf (psf, "j", dword) ; + break ; + + default : + if (isprint ((marker >> 24) & 0xFF) && isprint ((marker >> 16) & 0xFF) + && isprint ((marker >> 8) & 0xFF) && isprint (marker & 0xFF)) + { psf_binheader_readf (psf, "E4", &dword) ; + + psf_log_printf (psf, "%M : %d (unknown marker)\n", marker, dword) ; + + psf_binheader_readf (psf, "j", dword) ; + break ; + } ; + if ((dword = psf_ftell (psf)) & 0x03) + { psf_log_printf (psf, " Unknown chunk marker at position %d. Resynching.\n", dword - 4) ; + + psf_binheader_readf (psf, "j", -3) ; + break ; + } ; + psf_log_printf (psf, "*** Unknown chunk marker : %X. Exiting parser.\n", marker) ; + done = 1 ; + } ; /* switch (marker) */ + + if (! psf->sf.seekable && (parsestage & HAVE_BODY)) + break ; + + if (psf_ftell (psf) >= psf->filelength - SIGNED_SIZEOF (dword)) + break ; + } ; /* while (1) */ + + if (vhdr.compression) + return SFE_SVX_BAD_COMP ; + + if (psf->dataoffset <= 0) + return SFE_SVX_NO_DATA ; + + return 0 ; +} /* svx_read_header */ + +static int +svx_close (SF_PRIVATE *psf) +{ + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + svx_write_header (psf, SF_TRUE) ; + + return 0 ; +} /* svx_close */ + +static int +svx_write_header (SF_PRIVATE *psf, int calc_length) +{ static char annotation [] = "libsndfile by Erik de Castro Lopo\0\0\0" ; + sf_count_t current ; + + current = psf_ftell (psf) ; + + if (calc_length) + { psf->filelength = psf_get_filelen (psf) ; + + psf->datalength = psf->filelength - psf->dataoffset ; + + if (psf->dataend) + psf->datalength -= psf->filelength - psf->dataend ; + + psf->sf.frames = psf->datalength / (psf->bytewidth * psf->sf.channels) ; + } ; + + psf->header [0] = 0 ; + psf->headindex = 0 ; + psf_fseek (psf, 0, SEEK_SET) ; + + /* FORM marker and FORM size. */ + psf_binheader_writef (psf, "Etm8", FORM_MARKER, (psf->filelength < 8) ? + psf->filelength * 0 : psf->filelength - 8) ; + + psf_binheader_writef (psf, "m", (psf->bytewidth == 1) ? SVX8_MARKER : SV16_MARKER) ; + + /* VHDR chunk. */ + psf_binheader_writef (psf, "Em4", VHDR_MARKER, sizeof (VHDR_CHUNK)) ; + /* VHDR : oneShotHiSamples, repeatHiSamples, samplesPerHiCycle */ + psf_binheader_writef (psf, "E444", psf->sf.frames, 0, 0) ; + /* VHDR : samplesPerSec, octave, compression */ + psf_binheader_writef (psf, "E211", psf->sf.samplerate, 1, 0) ; + /* VHDR : volume */ + psf_binheader_writef (psf, "E4", (psf->bytewidth == 1) ? 0xFF : 0xFFFF) ; + + /* Filename and annotation strings. */ + psf_binheader_writef (psf, "Emsms", NAME_MARKER, psf->filename, ANNO_MARKER, annotation) ; + + /* BODY marker and size. */ + psf_binheader_writef (psf, "Etm8", BODY_MARKER, (psf->datalength < 0) ? + psf->datalength * 0 : psf->datalength) ; + + psf_fwrite (psf->header, psf->headindex, 1, psf) ; + + if (psf->error) + return psf->error ; + + psf->dataoffset = psf->headindex ; + + if (current > 0) + psf_fseek (psf, current, SEEK_SET) ; + + return psf->error ; +} /* svx_write_header */ + + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: a80ab6fb-7d75-4d32-a6b0-0061a3f05d95 +*/ diff --git a/libs/libsndfile/src/txw.c b/libs/libsndfile/src/txw.c new file mode 100644 index 0000000000..0f0add673d --- /dev/null +++ b/libs/libsndfile/src/txw.c @@ -0,0 +1,379 @@ +/* +** Copyright (C) 2002-2004 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +/*=========================================================================== +** Yamaha TX16 Sampler Files. +** +** This header parser was written using information from the SoX source code +** and trial and error experimentation. The code here however is all original. +*/ + +#include "sfconfig.h" + +#include +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" + +#if (ENABLE_EXPERIMENTAL_CODE == 0) + +int +txw_open (SF_PRIVATE *psf) +{ if (psf) + return SFE_UNIMPLEMENTED ; + return (psf && 0) ; +} /* txw_open */ + +#else + +/*------------------------------------------------------------------------------ +** Markers. +*/ + +#define TXW_DATA_OFFSET 32 + +#define TXW_LOOPED 0x49 +#define TXW_NO_LOOP 0xC9 + +/*------------------------------------------------------------------------------ +** Private static functions. +*/ + +static int txw_read_header (SF_PRIVATE *psf) ; + +static sf_count_t txw_read_s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t txw_read_i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t txw_read_f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t txw_read_d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; + +static sf_count_t txw_seek (SF_PRIVATE *psf, int mode, sf_count_t offset) ; + +/*------------------------------------------------------------------------------ +** Public functions. +*/ + +/* + * ftp://ftp.t0.or.at/pub/sound/tx16w/samples.yamaha + * ftp://ftp.t0.or.at/pub/sound/tx16w/faq/tx16w.tec + * http://www.t0.or.at/~mpakesch/tx16w/ + * + * from tx16w.c sox 12.15: (7-Oct-98) (Mark Lakata and Leigh Smith) + * char filetype[6] "LM8953" + * nulls[10], + * dummy_aeg[6] + * format 0x49 = looped, 0xC9 = non-looped + * sample_rate 1 = 33 kHz, 2 = 50 kHz, 3 = 16 kHz + * atc_length[3] if sample rate 0, [2]&0xfe = 6: 33kHz, 0x10:50, 0xf6: 16, + * depending on [5] but to heck with it + * rpt_length[3] (these are for looped samples, attack and loop lengths) + * unused[2] + */ + +typedef struct +{ unsigned char format, srate, sr2, sr3 ; + unsigned short srhash ; + unsigned int attacklen, repeatlen ; +} TXW_HEADER ; + +#define ERROR_666 666 + +int +txw_open (SF_PRIVATE *psf) +{ int error ; + + if (psf->mode != SFM_READ) + return SFE_UNIMPLEMENTED ; + + if ((error = txw_read_header (psf))) + return error ; + + if (psf_fseek (psf, psf->dataoffset, SEEK_SET) != psf->dataoffset) + return SFE_BAD_SEEK ; + + psf->read_short = txw_read_s ; + psf->read_int = txw_read_i ; + psf->read_float = txw_read_f ; + psf->read_double = txw_read_d ; + + psf->seek = txw_seek ; + + return 0 ; +} /* txw_open */ + +/*------------------------------------------------------------------------------ +*/ + +static int +txw_read_header (SF_PRIVATE *psf) +{ TXW_HEADER txwh ; + char *strptr ; + + memset (&txwh, 0, sizeof (txwh)) ; + memset (psf->u.cbuf, 0, sizeof (psf->u.cbuf)) ; + psf_binheader_readf (psf, "pb", 0, psf->u.cbuf, 16) ; + + if (memcmp (psf->u.cbuf, "LM8953\0\0\0\0\0\0\0\0\0\0", 16) != 0) + return ERROR_666 ; + + psf_log_printf (psf, "Read only : Yamaha TX-16 Sampler (.txw)\nLM8953\n") ; + + /* Jump 6 bytes (dummp_aeg), read format, read sample rate. */ + psf_binheader_readf (psf, "j11", 6, &txwh.format, &txwh.srate) ; + + /* 8 bytes (atc_length[3], rpt_length[3], unused[2]). */ + psf_binheader_readf (psf, "e33j", &txwh.attacklen, &txwh.repeatlen, 2) ; + txwh.sr2 = (txwh.attacklen >> 16) & 0xFE ; + txwh.sr3 = (txwh.repeatlen >> 16) & 0xFE ; + txwh.attacklen &= 0x1FFFF ; + txwh.repeatlen &= 0x1FFFF ; + + switch (txwh.format) + { case TXW_LOOPED : + strptr = "looped" ; + break ; + + case TXW_NO_LOOP : + strptr = "non-looped" ; + break ; + + default : + psf_log_printf (psf, " Format : 0x%02x => ?????\n", txwh.format) ; + return ERROR_666 ; + } ; + + psf_log_printf (psf, " Format : 0x%02X => %s\n", txwh.format, strptr) ; + + strptr = NULL ; + + switch (txwh.srate) + { case 1 : + psf->sf.samplerate = 33333 ; + break ; + + case 2 : + psf->sf.samplerate = 50000 ; + break ; + + case 3 : + psf->sf.samplerate = 16667 ; + break ; + + default : + /* This is ugly and braindead. */ + txwh.srhash = ((txwh.sr2 & 0xFE) << 8) | (txwh.sr3 & 0xFE) ; + switch (txwh.srhash) + { case ((0x6 << 8) | 0x52) : + psf->sf.samplerate = 33333 ; + break ; + + case ((0x10 << 8) | 0x52) : + psf->sf.samplerate = 50000 ; + break ; + + case ((0xF6 << 8) | 0x52) : + psf->sf.samplerate = 166667 ; + break ; + + default : + strptr = " Sample Rate : Unknown : forcing to 33333\n" ; + psf->sf.samplerate = 33333 ; + break ; + } ; + } ; + + + if (strptr) + psf_log_printf (psf, strptr) ; + else if (txwh.srhash) + psf_log_printf (psf, " Sample Rate : %d (0x%X) => %d\n", txwh.srate, txwh.srhash, psf->sf.samplerate) ; + else + psf_log_printf (psf, " Sample Rate : %d => %d\n", txwh.srate, psf->sf.samplerate) ; + + if (txwh.format == TXW_LOOPED) + { psf_log_printf (psf, " Attack Len : %d\n", txwh.attacklen) ; + psf_log_printf (psf, " Repeat Len : %d\n", txwh.repeatlen) ; + } ; + + psf->dataoffset = TXW_DATA_OFFSET ; + psf->datalength = psf->filelength - TXW_DATA_OFFSET ; + psf->sf.frames = 2 * psf->datalength / 3 ; + + + if (psf->datalength % 3 == 1) + psf_log_printf (psf, "*** File seems to be truncated, %d extra bytes.\n", + (int) (psf->datalength % 3)) ; + + if (txwh.attacklen + txwh.repeatlen > psf->sf.frames) + psf_log_printf (psf, "*** File has been truncated.\n") ; + + psf->sf.format = SF_FORMAT_TXW | SF_FORMAT_PCM_16 ; + psf->sf.channels = 1 ; + psf->sf.sections = 1 ; + psf->sf.seekable = SF_TRUE ; + + return 0 ; +} /* txw_read_header */ + +static sf_count_t +txw_read_s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ unsigned char *ucptr ; + short sample ; + int k, bufferlen, readcount, count ; + sf_count_t total = 0 ; + + bufferlen = sizeof (psf->u.cbuf) / 3 ; + bufferlen -= (bufferlen & 1) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : len ; + count = psf_fread (psf->u.cbuf, 3, readcount, psf) ; + + ucptr = psf->u.ucbuf ; + for (k = 0 ; k < readcount ; k += 2) + { sample = (ucptr [0] << 8) | (ucptr [1] & 0xF0) ; + ptr [total + k] = sample ; + sample = (ucptr [2] << 8) | ((ucptr [1] & 0xF) << 4) ; + ptr [total + k + 1] = sample ; + ucptr += 3 ; + } ; + + total += count ; + len -= readcount ; + } ; + + return total ; +} /* txw_read_s */ + +static sf_count_t +txw_read_i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ unsigned char *ucptr ; + short sample ; + int k, bufferlen, readcount, count ; + sf_count_t total = 0 ; + + bufferlen = sizeof (psf->u.cbuf) / 3 ; + bufferlen -= (bufferlen & 1) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : len ; + count = psf_fread (psf->u.cbuf, 3, readcount, psf) ; + + ucptr = psf->u.ucbuf ; + for (k = 0 ; k < readcount ; k += 2) + { sample = (ucptr [0] << 8) | (ucptr [1] & 0xF0) ; + ptr [total + k] = sample << 16 ; + sample = (ucptr [2] << 8) | ((ucptr [1] & 0xF) << 4) ; + ptr [total + k + 1] = sample << 16 ; + ucptr += 3 ; + } ; + + total += count ; + len -= readcount ; + } ; + + return total ; +} /* txw_read_i */ + +static sf_count_t +txw_read_f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ unsigned char *ucptr ; + short sample ; + int k, bufferlen, readcount, count ; + sf_count_t total = 0 ; + float normfact ; + + if (psf->norm_float == SF_TRUE) + normfact = 1.0 / 0x8000 ; + else + normfact = 1.0 / 0x10 ; + + bufferlen = sizeof (psf->u.cbuf) / 3 ; + bufferlen -= (bufferlen & 1) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : len ; + count = psf_fread (psf->u.cbuf, 3, readcount, psf) ; + + ucptr = psf->u.ucbuf ; + for (k = 0 ; k < readcount ; k += 2) + { sample = (ucptr [0] << 8) | (ucptr [1] & 0xF0) ; + ptr [total + k] = normfact * sample ; + sample = (ucptr [2] << 8) | ((ucptr [1] & 0xF) << 4) ; + ptr [total + k + 1] = normfact * sample ; + ucptr += 3 ; + } ; + + total += count ; + len -= readcount ; + } ; + + return total ; +} /* txw_read_f */ + +static sf_count_t +txw_read_d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ unsigned char *ucptr ; + short sample ; + int k, bufferlen, readcount, count ; + sf_count_t total = 0 ; + double normfact ; + + if (psf->norm_double == SF_TRUE) + normfact = 1.0 / 0x8000 ; + else + normfact = 1.0 / 0x10 ; + + bufferlen = sizeof (psf->u.cbuf) / 3 ; + bufferlen -= (bufferlen & 1) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : len ; + count = psf_fread (psf->u.cbuf, 3, readcount, psf) ; + + ucptr = psf->u.ucbuf ; + for (k = 0 ; k < readcount ; k += 2) + { sample = (ucptr [0] << 8) | (ucptr [1] & 0xF0) ; + ptr [total + k] = normfact * sample ; + sample = (ucptr [2] << 8) | ((ucptr [1] & 0xF) << 4) ; + ptr [total + k + 1] = normfact * sample ; + ucptr += 3 ; + } ; + + total += count ; + len -= readcount ; + } ; + + return total ; +} /* txw_read_d */ + +static sf_count_t +txw_seek (SF_PRIVATE *psf, int mode, sf_count_t offset) +{ if (psf && mode) + return offset ; + + return 0 ; +} /* txw_seek */ + +#endif +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 4d0ba7af-b1c5-46b4-a900-7c6f59fd9a89 +*/ diff --git a/libs/libsndfile/src/ulaw.c b/libs/libsndfile/src/ulaw.c new file mode 100644 index 0000000000..e476c0a781 --- /dev/null +++ b/libs/libsndfile/src/ulaw.c @@ -0,0 +1,1047 @@ +/* +** Copyright (C) 1999-2005 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sndfile.h" +#include "float_cast.h" +#include "common.h" + +static sf_count_t ulaw_read_ulaw2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t ulaw_read_ulaw2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t ulaw_read_ulaw2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t ulaw_read_ulaw2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; + +static sf_count_t ulaw_write_s2ulaw (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t ulaw_write_i2ulaw (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t ulaw_write_f2ulaw (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t ulaw_write_d2ulaw (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; + +int +ulaw_init (SF_PRIVATE *psf) +{ + if (psf->mode == SFM_READ || psf->mode == SFM_RDWR) + { psf->read_short = ulaw_read_ulaw2s ; + psf->read_int = ulaw_read_ulaw2i ; + psf->read_float = ulaw_read_ulaw2f ; + psf->read_double = ulaw_read_ulaw2d ; + } ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { psf->write_short = ulaw_write_s2ulaw ; + psf->write_int = ulaw_write_i2ulaw ; + psf->write_float = ulaw_write_f2ulaw ; + psf->write_double = ulaw_write_d2ulaw ; + } ; + + psf->bytewidth = 1 ; + psf->blockwidth = psf->sf.channels ; + + if (psf->filelength > psf->dataoffset) + psf->datalength = (psf->dataend) ? psf->dataend - psf->dataoffset : + psf->filelength - psf->dataoffset ; + else + psf->datalength = 0 ; + + psf->sf.frames = psf->datalength / psf->blockwidth ; + + return 0 ; +} /* ulaw_init */ + +/*============================================================================== +*/ + +static short ulaw_decode [256] = +{ -32124, -31100, -30076, -29052, -28028, -27004, -25980, -24956, + -23932, -22908, -21884, -20860, -19836, -18812, -17788, -16764, + -15996, -15484, -14972, -14460, -13948, -13436, -12924, -12412, + -11900, -11388, -10876, -10364, -9852, -9340, -8828, -8316, + -7932, -7676, -7420, -7164, -6908, -6652, -6396, -6140, + -5884, -5628, -5372, -5116, -4860, -4604, -4348, -4092, + -3900, -3772, -3644, -3516, -3388, -3260, -3132, -3004, + -2876, -2748, -2620, -2492, -2364, -2236, -2108, -1980, + -1884, -1820, -1756, -1692, -1628, -1564, -1500, -1436, + -1372, -1308, -1244, -1180, -1116, -1052, -988, -924, + -876, -844, -812, -780, -748, -716, -684, -652, + -620, -588, -556, -524, -492, -460, -428, -396, + -372, -356, -340, -324, -308, -292, -276, -260, + -244, -228, -212, -196, -180, -164, -148, -132, + -120, -112, -104, -96, -88, -80, -72, -64, + -56, -48, -40, -32, -24, -16, -8, 0, + + 32124, 31100, 30076, 29052, 28028, 27004, 25980, 24956, + 23932, 22908, 21884, 20860, 19836, 18812, 17788, 16764, + 15996, 15484, 14972, 14460, 13948, 13436, 12924, 12412, + 11900, 11388, 10876, 10364, 9852, 9340, 8828, 8316, + 7932, 7676, 7420, 7164, 6908, 6652, 6396, 6140, + 5884, 5628, 5372, 5116, 4860, 4604, 4348, 4092, + 3900, 3772, 3644, 3516, 3388, 3260, 3132, 3004, + 2876, 2748, 2620, 2492, 2364, 2236, 2108, 1980, + 1884, 1820, 1756, 1692, 1628, 1564, 1500, 1436, + 1372, 1308, 1244, 1180, 1116, 1052, 988, 924, + 876, 844, 812, 780, 748, 716, 684, 652, + 620, 588, 556, 524, 492, 460, 428, 396, + 372, 356, 340, 324, 308, 292, 276, 260, + 244, 228, 212, 196, 180, 164, 148, 132, + 120, 112, 104, 96, 88, 80, 72, 64, + 56, 48, 40, 32, 24, 16, 8, 0 +} ; + +static +unsigned char ulaw_encode [8193] = +{ 0xff, 0xfe, 0xfe, 0xfd, 0xfd, 0xfc, 0xfc, 0xfb, 0xfb, 0xfa, 0xfa, 0xf9, + 0xf9, 0xf8, 0xf8, 0xf7, 0xf7, 0xf6, 0xf6, 0xf5, 0xf5, 0xf4, 0xf4, 0xf3, + 0xf3, 0xf2, 0xf2, 0xf1, 0xf1, 0xf0, 0xf0, 0xef, 0xef, 0xef, 0xef, 0xee, + 0xee, 0xee, 0xee, 0xed, 0xed, 0xed, 0xed, 0xec, 0xec, 0xec, 0xec, 0xeb, + 0xeb, 0xeb, 0xeb, 0xea, 0xea, 0xea, 0xea, 0xe9, 0xe9, 0xe9, 0xe9, 0xe8, + 0xe8, 0xe8, 0xe8, 0xe7, 0xe7, 0xe7, 0xe7, 0xe6, 0xe6, 0xe6, 0xe6, 0xe5, + 0xe5, 0xe5, 0xe5, 0xe4, 0xe4, 0xe4, 0xe4, 0xe3, 0xe3, 0xe3, 0xe3, 0xe2, + 0xe2, 0xe2, 0xe2, 0xe1, 0xe1, 0xe1, 0xe1, 0xe0, 0xe0, 0xe0, 0xe0, 0xdf, + 0xdf, 0xdf, 0xdf, 0xdf, 0xdf, 0xdf, 0xdf, 0xde, 0xde, 0xde, 0xde, 0xde, + 0xde, 0xde, 0xde, 0xdd, 0xdd, 0xdd, 0xdd, 0xdd, 0xdd, 0xdd, 0xdd, 0xdc, + 0xdc, 0xdc, 0xdc, 0xdc, 0xdc, 0xdc, 0xdc, 0xdb, 0xdb, 0xdb, 0xdb, 0xdb, + 0xdb, 0xdb, 0xdb, 0xda, 0xda, 0xda, 0xda, 0xda, 0xda, 0xda, 0xda, 0xd9, + 0xd9, 0xd9, 0xd9, 0xd9, 0xd9, 0xd9, 0xd9, 0xd8, 0xd8, 0xd8, 0xd8, 0xd8, + 0xd8, 0xd8, 0xd8, 0xd7, 0xd7, 0xd7, 0xd7, 0xd7, 0xd7, 0xd7, 0xd7, 0xd6, + 0xd6, 0xd6, 0xd6, 0xd6, 0xd6, 0xd6, 0xd6, 0xd5, 0xd5, 0xd5, 0xd5, 0xd5, + 0xd5, 0xd5, 0xd5, 0xd4, 0xd4, 0xd4, 0xd4, 0xd4, 0xd4, 0xd4, 0xd4, 0xd3, + 0xd3, 0xd3, 0xd3, 0xd3, 0xd3, 0xd3, 0xd3, 0xd2, 0xd2, 0xd2, 0xd2, 0xd2, + 0xd2, 0xd2, 0xd2, 0xd1, 0xd1, 0xd1, 0xd1, 0xd1, 0xd1, 0xd1, 0xd1, 0xd0, + 0xd0, 0xd0, 0xd0, 0xd0, 0xd0, 0xd0, 0xd0, 0xcf, 0xcf, 0xcf, 0xcf, 0xcf, + 0xcf, 0xcf, 0xcf, 0xcf, 0xcf, 0xcf, 0xcf, 0xcf, 0xcf, 0xcf, 0xcf, 0xce, + 0xce, 0xce, 0xce, 0xce, 0xce, 0xce, 0xce, 0xce, 0xce, 0xce, 0xce, 0xce, + 0xce, 0xce, 0xce, 0xcd, 0xcd, 0xcd, 0xcd, 0xcd, 0xcd, 0xcd, 0xcd, 0xcd, + 0xcd, 0xcd, 0xcd, 0xcd, 0xcd, 0xcd, 0xcd, 0xcc, 0xcc, 0xcc, 0xcc, 0xcc, + 0xcc, 0xcc, 0xcc, 0xcc, 0xcc, 0xcc, 0xcc, 0xcc, 0xcc, 0xcc, 0xcc, 0xcb, + 0xcb, 0xcb, 0xcb, 0xcb, 0xcb, 0xcb, 0xcb, 0xcb, 0xcb, 0xcb, 0xcb, 0xcb, + 0xcb, 0xcb, 0xcb, 0xca, 0xca, 0xca, 0xca, 0xca, 0xca, 0xca, 0xca, 0xca, + 0xca, 0xca, 0xca, 0xca, 0xca, 0xca, 0xca, 0xc9, 0xc9, 0xc9, 0xc9, 0xc9, + 0xc9, 0xc9, 0xc9, 0xc9, 0xc9, 0xc9, 0xc9, 0xc9, 0xc9, 0xc9, 0xc9, 0xc8, + 0xc8, 0xc8, 0xc8, 0xc8, 0xc8, 0xc8, 0xc8, 0xc8, 0xc8, 0xc8, 0xc8, 0xc8, + 0xc8, 0xc8, 0xc8, 0xc7, 0xc7, 0xc7, 0xc7, 0xc7, 0xc7, 0xc7, 0xc7, 0xc7, + 0xc7, 0xc7, 0xc7, 0xc7, 0xc7, 0xc7, 0xc7, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, + 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc6, 0xc5, + 0xc5, 0xc5, 0xc5, 0xc5, 0xc5, 0xc5, 0xc5, 0xc5, 0xc5, 0xc5, 0xc5, 0xc5, + 0xc5, 0xc5, 0xc5, 0xc4, 0xc4, 0xc4, 0xc4, 0xc4, 0xc4, 0xc4, 0xc4, 0xc4, + 0xc4, 0xc4, 0xc4, 0xc4, 0xc4, 0xc4, 0xc4, 0xc3, 0xc3, 0xc3, 0xc3, 0xc3, + 0xc3, 0xc3, 0xc3, 0xc3, 0xc3, 0xc3, 0xc3, 0xc3, 0xc3, 0xc3, 0xc3, 0xc2, + 0xc2, 0xc2, 0xc2, 0xc2, 0xc2, 0xc2, 0xc2, 0xc2, 0xc2, 0xc2, 0xc2, 0xc2, + 0xc2, 0xc2, 0xc2, 0xc1, 0xc1, 0xc1, 0xc1, 0xc1, 0xc1, 0xc1, 0xc1, 0xc1, + 0xc1, 0xc1, 0xc1, 0xc1, 0xc1, 0xc1, 0xc1, 0xc0, 0xc0, 0xc0, 0xc0, 0xc0, + 0xc0, 0xc0, 0xc0, 0xc0, 0xc0, 0xc0, 0xc0, 0xc0, 0xc0, 0xc0, 0xc0, 0xbf, + 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, + 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, + 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbf, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, + 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, + 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, 0xbe, + 0xbe, 0xbe, 0xbe, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, + 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, + 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbd, 0xbc, + 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, + 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, + 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbc, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, + 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, + 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, 0xbb, + 0xbb, 0xbb, 0xbb, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, + 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, + 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xba, 0xb9, + 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, + 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, + 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb9, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, + 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, + 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, 0xb8, + 0xb8, 0xb8, 0xb8, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, + 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, + 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb6, + 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, + 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, + 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb6, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, + 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, + 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, 0xb5, + 0xb5, 0xb5, 0xb5, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, + 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, + 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb4, 0xb3, + 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, + 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, + 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb3, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, + 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, + 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, 0xb2, + 0xb2, 0xb2, 0xb2, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, + 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, + 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb1, 0xb0, + 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, + 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, + 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, + 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, + 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, + 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, + 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, + 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xaf, 0xae, + 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, + 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, + 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, + 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, + 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, 0xae, + 0xae, 0xae, 0xae, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, + 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, + 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, + 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, + 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, + 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xad, 0xac, 0xac, 0xac, 0xac, 0xac, + 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, + 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, + 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, + 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, + 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xac, 0xab, + 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, + 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, + 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, + 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, + 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, 0xab, + 0xab, 0xab, 0xab, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, + 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, + 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, + 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, + 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, + 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, + 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, + 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, + 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, + 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, + 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa9, 0xa8, + 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, + 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, + 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, + 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, + 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, 0xa8, + 0xa8, 0xa8, 0xa8, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, + 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, + 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, + 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, + 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, + 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa7, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, + 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, + 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, + 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, + 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, + 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa6, 0xa5, + 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, + 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, + 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, + 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, + 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, 0xa5, + 0xa5, 0xa5, 0xa5, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, + 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, + 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, + 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, + 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, + 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa4, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, + 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, + 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, + 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, + 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, + 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa3, 0xa2, + 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, + 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, + 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, + 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, + 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, 0xa2, + 0xa2, 0xa2, 0xa2, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, + 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, + 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, + 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, + 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, + 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa1, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, + 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, + 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, + 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, + 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, + 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0xa0, 0x9f, + 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, + 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, + 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, + 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, + 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, + 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, + 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, + 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, + 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, + 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, + 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9f, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, + 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, + 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, + 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, + 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, + 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, + 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, + 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, + 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, + 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, + 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, + 0x9e, 0x9e, 0x9e, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, + 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, + 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, + 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, + 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, + 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, + 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, + 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, + 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, + 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, + 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9d, 0x9c, + 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, + 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, + 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, + 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, + 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, + 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, + 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, + 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, + 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, + 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, + 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9c, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, + 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, + 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, + 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, + 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, + 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, + 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, + 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, + 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, + 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, + 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, 0x9b, + 0x9b, 0x9b, 0x9b, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, + 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, + 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, + 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, + 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, + 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, + 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, + 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, + 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, + 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, + 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x9a, 0x99, + 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, + 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, + 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, + 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, + 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, + 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, + 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, + 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, + 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, + 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, + 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x98, 0x98, 0x98, 0x98, 0x98, + 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, + 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, + 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, + 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, + 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, + 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, + 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, + 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, + 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, + 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, 0x98, + 0x98, 0x98, 0x98, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, + 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, + 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, + 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, + 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, + 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, + 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, + 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, + 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, + 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, + 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x97, 0x96, + 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, + 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, + 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, + 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, + 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, + 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, + 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, + 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, + 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, + 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, + 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x96, 0x95, 0x95, 0x95, 0x95, 0x95, + 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, + 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, + 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, + 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, + 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, + 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, + 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, + 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, + 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, + 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, 0x95, + 0x95, 0x95, 0x95, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, + 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, + 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, + 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, + 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, + 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, + 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, + 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, + 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, + 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, + 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x94, 0x93, + 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, + 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, + 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, + 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, + 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, + 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, + 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, + 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, + 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, + 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, + 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x93, 0x92, 0x92, 0x92, 0x92, 0x92, + 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, + 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, + 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, + 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, + 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, + 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, + 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, + 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, + 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, + 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, 0x92, + 0x92, 0x92, 0x92, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, + 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, + 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, + 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, + 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, + 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, + 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, + 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, + 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, + 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, + 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x91, 0x90, + 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, + 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, + 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, + 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, + 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, + 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, + 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, + 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, + 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, + 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, + 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, + 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, + 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, + 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, + 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, + 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, + 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, + 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, + 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, + 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, + 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, + 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, + 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, + 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, + 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, + 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, + 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, + 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, + 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, + 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, + 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, + 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8f, 0x8e, + 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, + 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, + 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, + 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, + 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, + 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, + 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, + 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, + 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, + 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, + 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, + 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, + 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, + 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, + 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, + 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, + 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, + 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, + 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, + 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, + 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, 0x8e, + 0x8e, 0x8e, 0x8e, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, + 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, + 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, + 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, + 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, + 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, + 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, + 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, + 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, + 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, + 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, + 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, + 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, + 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, + 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, + 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, + 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, + 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, + 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, + 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, + 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, + 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8d, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, + 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, + 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, + 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, + 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, + 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, + 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, + 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, + 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, + 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, + 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, + 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, + 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, + 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, + 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, + 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, + 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, + 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, + 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, + 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, + 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, + 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8c, 0x8b, + 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, + 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, + 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, + 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, + 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, + 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, + 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, + 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, + 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, + 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, + 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, + 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, + 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, + 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, + 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, + 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, + 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, + 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, + 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, + 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, + 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, 0x8b, + 0x8b, 0x8b, 0x8b, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, + 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, + 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, + 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, + 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, + 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, + 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, + 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, + 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, + 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, + 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, + 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, + 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, + 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, + 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, + 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, + 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, + 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, + 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, + 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, + 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, + 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x8a, 0x89, 0x89, 0x89, 0x89, 0x89, + 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, + 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, + 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, + 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, + 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, + 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, + 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, + 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, + 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, + 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, + 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, + 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, + 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, + 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, + 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, + 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, + 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, + 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, + 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, + 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, + 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x89, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, + 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, + 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, + 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, + 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, + 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, + 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, + 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, + 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, + 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, + 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, + 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, + 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, + 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, + 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, + 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, + 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, + 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, + 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, + 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, + 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, + 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x87, 0x86, 0x86, 0x86, 0x86, 0x86, + 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, + 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, + 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, + 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, + 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, + 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, + 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, + 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, + 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, + 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, + 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, + 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, + 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, + 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, + 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, + 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, + 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, + 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, + 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, + 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, + 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x86, 0x85, + 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, + 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, + 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, + 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, + 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, + 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, + 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, + 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, + 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, + 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, + 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, + 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, + 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, + 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, + 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, + 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, + 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, + 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, + 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, + 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, + 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, 0x85, + 0x85, 0x85, 0x85, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, + 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, + 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, + 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, + 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, + 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, + 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, + 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, + 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, + 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, + 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, + 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, + 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, + 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, + 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, + 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, + 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, + 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, + 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, + 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, + 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, + 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x84, 0x83, 0x83, 0x83, 0x83, 0x83, + 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, + 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, + 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, + 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, + 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, + 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, + 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, + 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, + 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, + 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, + 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, + 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, + 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, + 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, + 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, + 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, + 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, + 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, + 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, + 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, + 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x83, 0x82, + 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, + 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, + 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, + 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, + 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, + 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, + 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, + 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, + 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, + 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, + 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, + 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, + 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, + 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, + 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, + 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, + 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, + 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, + 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, + 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, + 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, 0x82, + 0x82, 0x82, 0x82, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, + 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x81, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, + 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x00 +} ; + +static inline void +ulaw2s_array (unsigned char *buffer, int count, short *ptr) +{ while (--count >= 0) + ptr [count] = ulaw_decode [(int) buffer [count]] ; +} /* ulaw2s_array */ + +static inline void +ulaw2i_array (unsigned char *buffer, int count, int *ptr) +{ while (--count >= 0) + ptr [count] = ulaw_decode [buffer [count]] << 16 ; +} /* ulaw2i_array */ + +static inline void +ulaw2f_array (unsigned char *buffer, int count, float *ptr, float normfact) +{ while (--count >= 0) + ptr [count] = normfact * ulaw_decode [(int) buffer [count]] ; +} /* ulaw2f_array */ + +static inline void +ulaw2d_array (const unsigned char *buffer, int count, double *ptr, double normfact) +{ while (--count >= 0) + ptr [count] = normfact * ulaw_decode [(int) buffer [count]] ; +} /* ulaw2d_array */ + +static inline void +s2ulaw_array (const short *ptr, int count, unsigned char *buffer) +{ while (--count >= 0) + { if (ptr [count] >= 0) + buffer [count] = ulaw_encode [ptr [count] / 4] ; + else + buffer [count] = 0x7F & ulaw_encode [ptr [count] / -4] ; + } ; +} /* s2ulaw_array */ + +static inline void +i2ulaw_array (const int *ptr, int count, unsigned char *buffer) +{ while (--count >= 0) + { if (ptr [count] >= 0) + buffer [count] = ulaw_encode [ptr [count] >> (16 + 2)] ; + else + buffer [count] = 0x7F & ulaw_encode [-ptr [count] >> (16 + 2)] ; + } ; +} /* i2ulaw_array */ + +static inline void +f2ulaw_array (const float *ptr, int count, unsigned char *buffer, float normfact) +{ while (--count >= 0) + { if (ptr [count] >= 0) + buffer [count] = ulaw_encode [lrintf (normfact * ptr [count])] ; + else + buffer [count] = 0x7F & ulaw_encode [- lrintf (normfact * ptr [count])] ; + } ; +} /* f2ulaw_array */ + +static inline void +d2ulaw_array (const double *ptr, int count, unsigned char *buffer, double normfact) +{ while (--count >= 0) + { if (ptr [count] >= 0) + buffer [count] = ulaw_encode [lrint (normfact * ptr [count])] ; + else + buffer [count] = 0x7F & ulaw_encode [- lrint (normfact * ptr [count])] ; + } ; +} /* d2ulaw_array */ + +/*============================================================================== +*/ + +static sf_count_t +ulaw_read_ulaw2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ucbuf, 1, bufferlen, psf) ; + ulaw2s_array (psf->u.ucbuf, readcount, ptr + total) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* ulaw_read_ulaw2s */ + +static sf_count_t +ulaw_read_ulaw2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ucbuf, 1, bufferlen, psf) ; + ulaw2i_array (psf->u.ucbuf, readcount, ptr + total) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* ulaw_read_ulaw2i */ + +static sf_count_t +ulaw_read_ulaw2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + float normfact ; + + normfact = (psf->norm_float == SF_TRUE) ? 1.0 / ((float) 0x8000) : 1.0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ucbuf, 1, bufferlen, psf) ; + ulaw2f_array (psf->u.ucbuf, readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* ulaw_read_ulaw2f */ + +static sf_count_t +ulaw_read_ulaw2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ int bufferlen, readcount ; + sf_count_t total = 0 ; + double normfact ; + + normfact = (psf->norm_double) ? 1.0 / ((double) 0x8000) : 1.0 ; + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.ucbuf, 1, bufferlen, psf) ; + ulaw2d_array (psf->u.ucbuf, readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* ulaw_read_ulaw2d */ + +/*============================================================================================= +*/ + +static sf_count_t +ulaw_write_s2ulaw (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + s2ulaw_array (ptr + total, bufferlen, psf->u.ucbuf) ; + writecount = psf_fwrite (psf->u.ucbuf, 1, bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* ulaw_write_s2ulaw */ + +static sf_count_t +ulaw_write_i2ulaw (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + i2ulaw_array (ptr + total, bufferlen, psf->u.ucbuf) ; + writecount = psf_fwrite (psf->u.ucbuf, 1, bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* ulaw_write_i2ulaw */ + +static sf_count_t +ulaw_write_f2ulaw (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + float normfact ; + + /* Factor in a divide by 4. */ + normfact = (psf->norm_float == SF_TRUE) ? (0.25 * 0x7FFF) : 0.25 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + f2ulaw_array (ptr + total, bufferlen, psf->u.ucbuf, normfact) ; + writecount = psf_fwrite (psf->u.ucbuf, 1, bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* ulaw_write_f2ulaw */ + +static sf_count_t +ulaw_write_d2ulaw (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ int bufferlen, writecount ; + sf_count_t total = 0 ; + double normfact ; + + /* Factor in a divide by 4. */ + normfact = (psf->norm_double) ? (0.25 * 0x7FFF) : 0.25 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + d2ulaw_array (ptr + total, bufferlen, psf->u.ucbuf, normfact) ; + writecount = psf_fwrite (psf->u.ucbuf, 1, bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* ulaw_write_d2ulaw */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 655cc790-f058-45e8-89c9-86967cccc37e +*/ diff --git a/libs/libsndfile/src/voc.c b/libs/libsndfile/src/voc.c new file mode 100644 index 0000000000..e1388c4542 --- /dev/null +++ b/libs/libsndfile/src/voc.c @@ -0,0 +1,878 @@ +/* +** Copyright (C) 2001-2004 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +/* RANT: +** The VOC file format is the most brain damaged format I have yet had to deal +** with. No one programmer could have bee stupid enough to put this together. +** Instead it looks like a series of manic, dyslexic assembly language programmers +** hacked it to fit their needs. +** Utterly woeful. +*/ + +#include "sfconfig.h" + +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" + + +/*------------------------------------------------------------------------------ + * Typedefs for file chunks. +*/ + +#define VOC_MAX_SECTIONS 200 + +enum +{ VOC_TERMINATOR = 0, + VOC_SOUND_DATA = 1, + VOC_SOUND_CONTINUE = 2, + VOC_SILENCE = 3, + VOC_MARKER = 4, + VOC_ASCII = 5, + VOC_REPEAT = 6, + VOC_END_REPEAT = 7, + VOC_EXTENDED = 8, + VOC_EXTENDED_II = 9 +} ; + +typedef struct +{ int samples ; + int offset ; /* Offset of zero => silence. */ +} SND_DATA_BLOCKS ; + +typedef struct +{ unsigned int sections, section_types ; + int samplerate, channels, bitwidth ; + SND_DATA_BLOCKS blocks [VOC_MAX_SECTIONS] ; +} VOC_DATA ; + +/*------------------------------------------------------------------------------ + * Private static functions. +*/ + +static int voc_close (SF_PRIVATE *psf) ; +static int voc_write_header (SF_PRIVATE *psf, int calc_length) ; +static int voc_read_header (SF_PRIVATE *psf) ; + +static const char* voc_encoding2str (int encoding) ; + +#if 0 + +/* These functions would be required for files with more than one VOC_SOUND_DATA +** segment. Not sure whether to bother implementing this. +*/ + +static int voc_multi_init (SF_PRIVATE *psf, VOC_DATA *pvoc) ; + +static int voc_multi_read_uc2s (SF_PRIVATE *psf, short *ptr, int len) ; +static int voc_multi_read_les2s (SF_PRIVATE *psf, short *ptr, int len) ; + +static int voc_multi_read_uc2i (SF_PRIVATE *psf, int *ptr, int len) ; +static int voc_multi_read_les2i (SF_PRIVATE *psf, int *ptr, int len) ; + +static int voc_multi_read_uc2f (SF_PRIVATE *psf, float *ptr, int len) ; +static int voc_multi_read_les2f (SF_PRIVATE *psf, float *ptr, int len) ; + +static int voc_multi_read_uc2d (SF_PRIVATE *psf, double *ptr, int len) ; +static int voc_multi_read_les2d (SF_PRIVATE *psf, double *ptr, int len) ; +#endif + +/*------------------------------------------------------------------------------ +** Public function. +*/ + +int +voc_open (SF_PRIVATE *psf) +{ int subformat, error = 0 ; + + if (psf->is_pipe) + return SFE_VOC_NO_PIPE ; + + if (psf->mode == SFM_READ || (psf->mode == SFM_RDWR && psf->filelength > 0)) + { if ((error = voc_read_header (psf))) + return error ; + } ; + + subformat = psf->sf.format & SF_FORMAT_SUBMASK ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { if ((psf->sf.format & SF_FORMAT_TYPEMASK) != SF_FORMAT_VOC) + return SFE_BAD_OPEN_FORMAT ; + + psf->endian = SF_ENDIAN_LITTLE ; + + if ((error = voc_write_header (psf, SF_FALSE))) + return error ; + + psf->write_header = voc_write_header ; + } ; + + psf->blockwidth = psf->bytewidth * psf->sf.channels ; + + psf->container_close = voc_close ; + + switch (subformat) + { case SF_FORMAT_PCM_U8 : + case SF_FORMAT_PCM_16 : + error = pcm_init (psf) ; + break ; + + case SF_FORMAT_ALAW : + error = alaw_init (psf) ; + break ; + + case SF_FORMAT_ULAW : + error = ulaw_init (psf) ; + break ; + + default : return SFE_UNIMPLEMENTED ; + } ; + + return error ; +} /* voc_open */ + +/*------------------------------------------------------------------------------ +*/ + +static int +voc_read_header (SF_PRIVATE *psf) +{ VOC_DATA *pvoc ; + char creative [20] ; + unsigned char block_type, rate_byte ; + short version, checksum, encoding, dataoffset ; + int offset ; + + /* Set position to start of file to begin reading header. */ + offset = psf_binheader_readf (psf, "pb", 0, creative, SIGNED_SIZEOF (creative)) ; + + if (creative [sizeof (creative) - 1] != 0x1A) + return SFE_VOC_NO_CREATIVE ; + + /* Terminate the string. */ + creative [sizeof (creative) - 1] = 0 ; + + if (strcmp ("Creative Voice File", creative)) + return SFE_VOC_NO_CREATIVE ; + + psf_log_printf (psf, "%s\n", creative) ; + + offset += psf_binheader_readf (psf, "e222", &dataoffset, &version, &checksum) ; + + psf->dataoffset = dataoffset ; + + psf_log_printf (psf, "dataoffset : %d\n" + "version : 0x%X\n" + "checksum : 0x%X\n", psf->dataoffset, version, checksum) ; + + if (version != 0x010A && version != 0x0114) + return SFE_VOC_BAD_VERSION ; + + if (! (psf->fdata = malloc (sizeof (VOC_DATA)))) + return SFE_MALLOC_FAILED ; + + pvoc = (VOC_DATA*) psf->fdata ; + + memset (pvoc, 0, sizeof (VOC_DATA)) ; + + /* Set the default encoding now. */ + psf->sf.format = SF_FORMAT_VOC ; /* Major format */ + encoding = SF_FORMAT_PCM_U8 ; /* Minor format */ + psf->endian = SF_ENDIAN_LITTLE ; + + while (1) + { offset += psf_binheader_readf (psf, "1", &block_type) ; + + switch (block_type) + { case VOC_ASCII : + { int size ; + + offset += psf_binheader_readf (psf, "e3", &size) ; + + psf_log_printf (psf, " ASCII : %d\n", size) ; + + offset += psf_binheader_readf (psf, "b", psf->header, size) ; + psf->header [size] = 0 ; + psf_log_printf (psf, " text : %s\n", psf->header) ; + } ; + continue ; + + case VOC_SOUND_DATA : + case VOC_EXTENDED : + case VOC_EXTENDED_II : + break ; + + default : psf_log_printf (psf, "*** Weird block marker (%d)\n", block_type) ; + } ; + + break ; + } ; + + if (block_type == VOC_SOUND_DATA) + { unsigned char compression ; + int size ; + + offset += psf_binheader_readf (psf, "e311", &size, &rate_byte, &compression) ; + + psf->sf.samplerate = 1000000 / (256 - (rate_byte & 0xFF)) ; + + psf_log_printf (psf, " Sound Data : %d\n sr : %d => %dHz\n comp : %d\n", + size, rate_byte, psf->sf.samplerate, compression) ; + + if (offset + size - 1 > psf->filelength) + { psf_log_printf (psf, "Seems to be a truncated file.\n") ; + psf_log_printf (psf, "offset: %d size: %d sum: %d filelength: %D\n", offset, size, offset + size, psf->filelength) ; + return SFE_VOC_BAD_SECTIONS ; + } + else if (offset + size - 1 < psf->filelength) + { psf_log_printf (psf, "Seems to be a multi-segment file (#1).\n") ; + psf_log_printf (psf, "offset: %d size: %d sum: %d filelength: %D\n", offset, size, offset + size, psf->filelength) ; + return SFE_VOC_BAD_SECTIONS ; + } ; + + psf->dataoffset = offset ; + psf->dataend = psf->filelength - 1 ; + + psf->sf.channels = 1 ; + psf->bytewidth = 1 ; + + psf->sf.format = SF_FORMAT_VOC | SF_FORMAT_PCM_U8 ; + + return 0 ; + } ; + + if (block_type == VOC_EXTENDED) + { unsigned char pack, stereo, compression ; + unsigned short rate_short ; + int size ; + + offset += psf_binheader_readf (psf, "e3211", &size, &rate_short, &pack, &stereo) ; + + psf_log_printf (psf, " Extended : %d\n", size) ; + if (size == 4) + psf_log_printf (psf, " size : 4\n") ; + else + psf_log_printf (psf, " size : %d (should be 4)\n", size) ; + + psf_log_printf (psf, " pack : %d\n" + " stereo : %s\n", pack, (stereo ? "yes" : "no")) ; + + if (stereo) + { psf->sf.channels = 2 ; + psf->sf.samplerate = 128000000 / (65536 - rate_short) ; + } + else + { psf->sf.channels = 1 ; + psf->sf.samplerate = 256000000 / (65536 - rate_short) ; + } ; + + psf_log_printf (psf, " sr : %d => %dHz\n", (rate_short & 0xFFFF), psf->sf.samplerate) ; + + offset += psf_binheader_readf (psf, "1", &block_type) ; + + if (block_type != VOC_SOUND_DATA) + { psf_log_printf (psf, "*** Expecting VOC_SOUND_DATA section.\n") ; + return SFE_VOC_BAD_FORMAT ; + } ; + + offset += psf_binheader_readf (psf, "e311", &size, &rate_byte, &compression) ; + + psf_log_printf (psf, " Sound Data : %d\n" + " sr : %d\n" + " comp : %d\n", size, rate_byte, compression) ; + + + if (offset + size - 1 > psf->filelength) + { psf_log_printf (psf, "Seems to be a truncated file.\n") ; + psf_log_printf (psf, "offset: %d size: %d sum: %d filelength: %D\n", offset, size, offset + size, psf->filelength) ; + return SFE_VOC_BAD_SECTIONS ; + } + else if (offset + size - 1 < psf->filelength) + { psf_log_printf (psf, "Seems to be a multi-segment file (#2).\n") ; + psf_log_printf (psf, "offset: %d size: %d sum: %d filelength: %D\n", offset, size, offset + size, psf->filelength) ; + return SFE_VOC_BAD_SECTIONS ; + } ; + + psf->dataoffset = offset ; + psf->dataend = psf->filelength - 1 ; + + psf->bytewidth = 1 ; + + psf->sf.format = SF_FORMAT_VOC | SF_FORMAT_PCM_U8 ; + + return 0 ; + } + + if (block_type == VOC_EXTENDED_II) + { unsigned char bitwidth, channels ; + int size, fourbytes ; + + offset += psf_binheader_readf (psf, "e341124", &size, &psf->sf.samplerate, + &bitwidth, &channels, &encoding, &fourbytes) ; + + if (size * 2 == psf->filelength - 39) + { int temp_size = psf->filelength - 31 ; + + psf_log_printf (psf, " Extended II : %d (SoX bug: should be %d)\n", size, temp_size) ; + size = temp_size ; + } + else + psf_log_printf (psf, " Extended II : %d\n", size) ; + + psf_log_printf (psf, " sample rate : %d\n" + " bit width : %d\n" + " channels : %d\n", psf->sf.samplerate, bitwidth, channels) ; + + if (bitwidth == 16 && encoding == 0) + { encoding = 4 ; + psf_log_printf (psf, " encoding : 0 (SoX bug: should be 4 for 16 bit signed PCM)\n") ; + } + else + psf_log_printf (psf, " encoding : %d => %s\n", encoding, voc_encoding2str (encoding)) ; + + + psf_log_printf (psf, " fourbytes : %X\n", fourbytes) ; + + psf->sf.channels = channels ; + + psf->dataoffset = offset ; + psf->dataend = psf->filelength - 1 ; + + if (size + 31 == psf->filelength + 1) + { /* Hack for reading files produced using + ** sf_command (SFC_UPDATE_HEADER_NOW). + */ + psf_log_printf (psf, "Missing zero byte at end of file.\n") ; + size = psf->filelength - 30 ; + psf->dataend = 0 ; + } + else if (size + 31 > psf->filelength) + { psf_log_printf (psf, "Seems to be a truncated file.\n") ; + size = psf->filelength - 31 ; + } + else if (size + 31 < psf->filelength) + psf_log_printf (psf, "Seems to be a multi-segment file (#3).\n") ; + + switch (encoding) + { case 0 : + psf->sf.format = SF_FORMAT_VOC | SF_FORMAT_PCM_U8 ; + psf->bytewidth = 1 ; + break ; + + case 4 : + psf->sf.format = SF_FORMAT_VOC | SF_FORMAT_PCM_16 ; + psf->bytewidth = 2 ; + break ; + + case 6 : + psf->sf.format = SF_FORMAT_VOC | SF_FORMAT_ALAW ; + psf->bytewidth = 1 ; + break ; + + case 7 : + psf->sf.format = SF_FORMAT_VOC | SF_FORMAT_ULAW ; + psf->bytewidth = 1 ; + break ; + + default : /* Unknown */ + return SFE_UNKNOWN_FORMAT ; + break ; + } ; + + } ; + + return 0 ; +} /* voc_read_header */ + +/*==================================================================================== +*/ + +static int +voc_write_header (SF_PRIVATE *psf, int calc_length) +{ sf_count_t current ; + int rate_const, subformat ; + + current = psf_ftell (psf) ; + + if (calc_length) + { psf->filelength = psf_get_filelen (psf) ; + + psf->datalength = psf->filelength - psf->dataoffset ; + if (psf->dataend) + psf->datalength -= psf->filelength - psf->dataend ; + + psf->sf.frames = psf->datalength / (psf->bytewidth * psf->sf.channels) ; + } ; + + subformat = psf->sf.format & SF_FORMAT_SUBMASK ; + /* Reset the current header length to zero. */ + psf->header [0] = 0 ; + psf->headindex = 0 ; + psf_fseek (psf, 0, SEEK_SET) ; + + /* VOC marker and 0x1A byte. */ + psf_binheader_writef (psf, "eb1", "Creative Voice File", 19, 0x1A) ; + + /* Data offset, version and other. */ + psf_binheader_writef (psf, "e222", 26, 0x0114, 0x111F) ; + + /* Use same logic as SOX. + ** If the file is mono 8 bit data, use VOC_SOUND_DATA. + ** If the file is mono 16 bit data, use VOC_EXTENED. + ** Otherwise use VOC_EXTENED_2. + */ + + if (subformat == SF_FORMAT_PCM_U8 && psf->sf.channels == 1) + { /* samplerate = 1000000 / (256 - rate_const) ; */ + rate_const = 256 - 1000000 / psf->sf.samplerate ; + + /* First type marker, length, rate_const and compression */ + psf_binheader_writef (psf, "e1311", VOC_SOUND_DATA, (int) (psf->datalength + 1), rate_const, 0) ; + } + else if (subformat == SF_FORMAT_PCM_U8 && psf->sf.channels == 2) + { /* sample_rate = 128000000 / (65536 - rate_short) ; */ + rate_const = 65536 - 128000000 / psf->sf.samplerate ; + + /* First write the VOC_EXTENDED section + ** marker, length, rate_const and compression + */ + psf_binheader_writef (psf, "e13211", VOC_EXTENDED, 4, rate_const, 0, 1) ; + + /* samplerate = 1000000 / (256 - rate_const) ; */ + rate_const = 256 - 1000000 / psf->sf.samplerate ; + + /* Now write the VOC_SOUND_DATA section + ** marker, length, rate_const and compression + */ + psf_binheader_writef (psf, "e1311", VOC_SOUND_DATA, (int) (psf->datalength + 1), rate_const, 0) ; + } + else + { int length ; + + if (psf->sf.channels < 1 || psf->sf.channels > 2) + return SFE_CHANNEL_COUNT ; + + switch (subformat) + { case SF_FORMAT_PCM_U8 : + psf->bytewidth = 1 ; + length = psf->sf.frames * psf->sf.channels * psf->bytewidth + 12 ; + /* Marker, length, sample rate, bitwidth, stereo flag, encoding and fourt zero bytes. */ + psf_binheader_writef (psf, "e1341124", VOC_EXTENDED_II, length, psf->sf.samplerate, 16, psf->sf.channels, 4, 0) ; + break ; + + case SF_FORMAT_PCM_16 : + psf->bytewidth = 2 ; + length = psf->sf.frames * psf->sf.channels * psf->bytewidth + 12 ; + /* Marker, length, sample rate, bitwidth, stereo flag, encoding and fourt zero bytes. */ + psf_binheader_writef (psf, "e1341124", VOC_EXTENDED_II, length, psf->sf.samplerate, 16, psf->sf.channels, 4, 0) ; + break ; + + case SF_FORMAT_ALAW : + psf->bytewidth = 1 ; + length = psf->sf.frames * psf->sf.channels * psf->bytewidth + 12 ; + psf_binheader_writef (psf, "e1341124", VOC_EXTENDED_II, length, psf->sf.samplerate, 8, psf->sf.channels, 6, 0) ; + break ; + + case SF_FORMAT_ULAW : + psf->bytewidth = 1 ; + length = psf->sf.frames * psf->sf.channels * psf->bytewidth + 12 ; + psf_binheader_writef (psf, "e1341124", VOC_EXTENDED_II, length, psf->sf.samplerate, 8, psf->sf.channels, 7, 0) ; + break ; + + default : return SFE_UNIMPLEMENTED ; + } ; + } ; + + psf_fwrite (psf->header, psf->headindex, 1, psf) ; + + if (psf->error) + return psf->error ; + + psf->dataoffset = psf->headindex ; + + if (current > 0) + psf_fseek (psf, current, SEEK_SET) ; + + return psf->error ; +} /* voc_write_header */ + +static int +voc_close (SF_PRIVATE *psf) +{ + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { /* Now we know for certain the length of the file we can re-write + ** correct values for the FORM, 8SVX and BODY chunks. + */ + unsigned byte = VOC_TERMINATOR ; + + + psf_fseek (psf, 0, SEEK_END) ; + + /* Write terminator */ + psf_fwrite (&byte, 1, 1, psf) ; + + voc_write_header (psf, SF_TRUE) ; + } ; + + return 0 ; +} /* voc_close */ + +static const char* +voc_encoding2str (int encoding) +{ + switch (encoding) + { case 0 : return "8 bit unsigned PCM" ; + case 4 : return "16 bit signed PCM" ; + case 6 : return "A-law" ; + case 7 : return "u-law" ; + default : break ; + } + return "*** Unknown ***" ; +} /* voc_encoding2str */ + +/*==================================================================================== +*/ + +#if 0 +static int +voc_multi_init (SF_PRIVATE *psf, VOC_DATA *pvoc) +{ + psf->sf.frames = 0 ; + + if (pvoc->bitwidth == 8) + { psf->read_short = voc_multi_read_uc2s ; + psf->read_int = voc_multi_read_uc2i ; + psf->read_float = voc_multi_read_uc2f ; + psf->read_double = voc_multi_read_uc2d ; + return 0 ; + } ; + + if (pvoc->bitwidth == 16) + { psf->read_short = voc_multi_read_les2s ; + psf->read_int = voc_multi_read_les2i ; + psf->read_float = voc_multi_read_les2f ; + psf->read_double = voc_multi_read_les2d ; + return 0 ; + } ; + + psf_log_printf (psf, "Error : bitwith != 8 && bitwidth != 16.\n") ; + + return SFE_UNIMPLEMENTED ; +} /* voc_multi_read_int */ + +/*------------------------------------------------------------------------------------ +*/ + +static int +voc_multi_read_uc2s (SF_PRIVATE *psf, short *ptr, int len) +{ + + return 0 ; +} /* voc_multi_read_uc2s */ + +static int +voc_multi_read_les2s (SF_PRIVATE *psf, short *ptr, int len) +{ + + return 0 ; +} /* voc_multi_read_les2s */ + + +static int +voc_multi_read_uc2i (SF_PRIVATE *psf, int *ptr, int len) +{ + + return 0 ; +} /* voc_multi_read_uc2i */ + +static int +voc_multi_read_les2i (SF_PRIVATE *psf, int *ptr, int len) +{ + + return 0 ; +} /* voc_multi_read_les2i */ + + +static int +voc_multi_read_uc2f (SF_PRIVATE *psf, float *ptr, int len) +{ + + return 0 ; +} /* voc_multi_read_uc2f */ + +static int +voc_multi_read_les2f (SF_PRIVATE *psf, float *ptr, int len) +{ + + return 0 ; +} /* voc_multi_read_les2f */ + + +static int +voc_multi_read_uc2d (SF_PRIVATE *psf, double *ptr, int len) +{ + + return 0 ; +} /* voc_multi_read_uc2d */ + +static int +voc_multi_read_les2d (SF_PRIVATE *psf, double *ptr, int len) +{ + + return 0 ; +} /* voc_multi_read_les2d */ + +#endif + +/*------------------------------------------------------------------------------------ + +Creative Voice (VOC) file format +-------------------------------- + +~From: galt@dsd.es.com + +(byte numbers are hex!) + + HEADER (bytes 00-19) + Series of DATA BLOCKS (bytes 1A+) [Must end w/ Terminator Block] + +- --------------------------------------------------------------- + +HEADER: +======= + byte # Description + ------ ------------------------------------------ + 00-12 "Creative Voice File" + 13 1A (eof to abort printing of file) + 14-15 Offset of first datablock in .voc file (std 1A 00 + in Intel Notation) + 16-17 Version number (minor,major) (VOC-HDR puts 0A 01) + 18-19 1's Comp of Ver. # + 1234h (VOC-HDR puts 29 11) + +- --------------------------------------------------------------- + +DATA BLOCK: +=========== + + Data Block: TYPE(1-byte), SIZE(3-bytes), INFO(0+ bytes) + NOTE: Terminator Block is an exception -- it has only the TYPE byte. + + TYPE Description Size (3-byte int) Info + ---- ----------- ----------------- ----------------------- + 00 Terminator (NONE) (NONE) + 01 Sound data 2+length of data * + 02 Sound continue length of data Voice Data + 03 Silence 3 ** + 04 Marker 2 Marker# (2 bytes) + 05 ASCII length of string null terminated string + 06 Repeat 2 Count# (2 bytes) + 07 End repeat 0 (NONE) + 08 Extended 4 *** + + *Sound Info Format: + --------------------- + 00 Sample Rate + 01 Compression Type + 02+ Voice Data + + **Silence Info Format: + ---------------------------- + 00-01 Length of silence - 1 + 02 Sample Rate + + + ***Extended Info Format: + --------------------- + 00-01 Time Constant: Mono: 65536 - (256000000/sample_rate) + Stereo: 65536 - (25600000/(2*sample_rate)) + 02 Pack + 03 Mode: 0 = mono + 1 = stereo + + + Marker# -- Driver keeps the most recent marker in a status byte + Count# -- Number of repetitions + 1 + Count# may be 1 to FFFE for 0 - FFFD repetitions + or FFFF for endless repetitions + Sample Rate -- SR byte = 256-(1000000/sample_rate) + Length of silence -- in units of sampling cycle + Compression Type -- of voice data + 8-bits = 0 + 4-bits = 1 + 2.6-bits = 2 + 2-bits = 3 + Multi DAC = 3+(# of channels) [interesting-- + this isn't in the developer's manual] + + +--------------------------------------------------------------------------------- +Addendum submitted by Votis Kokavessis: + +After some experimenting with .VOC files I found out that there is a Data Block +Type 9, which is not covered in the VOC.TXT file. Here is what I was able to discover +about this block type: + + +TYPE: 09 +SIZE: 12 + length of data +INFO: 12 (twelve) bytes + +INFO STRUCTURE: + +Bytes 0-1: (Word) Sample Rate (e.g. 44100) +Bytes 2-3: zero (could be that bytes 0-3 are a DWord for Sample Rate) +Byte 4: Sample Size in bits (e.g. 16) +Byte 5: Number of channels (e.g. 1 for mono, 2 for stereo) +Byte 6: Unknown (equal to 4 in all files I examined) +Bytes 7-11: zero + + +-------------------------------------------------------------------------------------*/ + +/*===================================================================================== +**===================================================================================== +**===================================================================================== +**===================================================================================== +*/ + +/*------------------------------------------------------------------------ +The following is taken from the Audio File Formats FAQ dated 2-Jan-1995 +and submitted by Guido van Rossum . +-------------------------------------------------------------------------- +Creative Voice (VOC) file format +-------------------------------- + +From: galt@dsd.es.com + +(byte numbers are hex!) + + HEADER (bytes 00-19) + Series of DATA BLOCKS (bytes 1A+) [Must end w/ Terminator Block] + +- --------------------------------------------------------------- + +HEADER: +------- + byte # Description + ------ ------------------------------------------ + 00-12 "Creative Voice File" + 13 1A (eof to abort printing of file) + 14-15 Offset of first datablock in .voc file (std 1A 00 + in Intel Notation) + 16-17 Version number (minor,major) (VOC-HDR puts 0A 01) + 18-19 2's Comp of Ver. # + 1234h (VOC-HDR puts 29 11) + +- --------------------------------------------------------------- + +DATA BLOCK: +----------- + + Data Block: TYPE(1-byte), SIZE(3-bytes), INFO(0+ bytes) + NOTE: Terminator Block is an exception -- it has only the TYPE byte. + + TYPE Description Size (3-byte int) Info + ---- ----------- ----------------- ----------------------- + 00 Terminator (NONE) (NONE) + 01 Sound data 2+length of data * + 02 Sound continue length of data Voice Data + 03 Silence 3 ** + 04 Marker 2 Marker# (2 bytes) + 05 ASCII length of string null terminated string + 06 Repeat 2 Count# (2 bytes) + 07 End repeat 0 (NONE) + 08 Extended 4 *** + + *Sound Info Format: **Silence Info Format: + --------------------- ---------------------------- + 00 Sample Rate 00-01 Length of silence - 1 + 01 Compression Type 02 Sample Rate + 02+ Voice Data + + ***Extended Info Format: + --------------------- + 00-01 Time Constant: Mono: 65536 - (256000000/sample_rate) + Stereo: 65536 - (25600000/(2*sample_rate)) + 02 Pack + 03 Mode: 0 = mono + 1 = stereo + + + Marker# -- Driver keeps the most recent marker in a status byte + Count# -- Number of repetitions + 1 + Count# may be 1 to FFFE for 0 - FFFD repetitions + or FFFF for endless repetitions + Sample Rate -- SR byte = 256-(1000000/sample_rate) + Length of silence -- in units of sampling cycle + Compression Type -- of voice data + 8-bits = 0 + 4-bits = 1 + 2.6-bits = 2 + 2-bits = 3 + Multi DAC = 3+(# of channels) [interesting-- + this isn't in the developer's manual] + +Detailed description of new data blocks (VOC files version 1.20 and above): + + (Source is fax from Barry Boone at Creative Labs, 405/742-6622) + +BLOCK 8 - digitized sound attribute extension, must preceed block 1. + Used to define stereo, 8 bit audio + BYTE bBlockID; // = 8 + BYTE nBlockLen[3]; // 3 byte length + WORD wTimeConstant; // time constant = same as block 1 + BYTE bPackMethod; // same as in block 1 + BYTE bVoiceMode; // 0-mono, 1-stereo + + Data is stored left, right + +BLOCK 9 - data block that supersedes blocks 1 and 8. + Used for stereo, 16 bit. + + BYTE bBlockID; // = 9 + BYTE nBlockLen[3]; // length 12 plus length of sound + DWORD dwSamplesPerSec; // samples per second, not time const. + BYTE bBitsPerSample; // e.g., 8 or 16 + BYTE bChannels; // 1 for mono, 2 for stereo + WORD wFormat; // see below + BYTE reserved[4]; // pad to make block w/o data + // have a size of 16 bytes + + Valid values of wFormat are: + + 0x0000 8-bit unsigned PCM + 0x0001 Creative 8-bit to 4-bit ADPCM + 0x0002 Creative 8-bit to 3-bit ADPCM + 0x0003 Creative 8-bit to 2-bit ADPCM + 0x0004 16-bit signed PCM + 0x0006 CCITT a-Law + 0x0007 CCITT u-Law + 0x02000 Creative 16-bit to 4-bit ADPCM + + Data is stored left, right + +------------------------------------------------------------------------*/ +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 40a50167-a81c-463a-9e1d-3282ff84e09d +*/ diff --git a/libs/libsndfile/src/vox_adpcm.c b/libs/libsndfile/src/vox_adpcm.c new file mode 100644 index 0000000000..f743a72911 --- /dev/null +++ b/libs/libsndfile/src/vox_adpcm.c @@ -0,0 +1,537 @@ +/* +** Copyright (C) 2002-2005 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +/* +** This is the OKI / Dialogic ADPCM encoder/decoder. It converts from +** 12 bit linear sample data to a 4 bit ADPCM. +** +** Implemented from the description found here: +** +** http://www.comptek.ru:8100/telephony/tnotes/tt1-13.html +** +** and compared against the encoder/decoder found here: +** +** http://ibiblio.org/pub/linux/apps/sound/convert/vox.tar.gz +*/ + +#include "sfconfig.h" + +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "float_cast.h" +#include "common.h" + +#define VOX_DATA_LEN 2048 +#define PCM_DATA_LEN (VOX_DATA_LEN *2) + +typedef struct +{ short last ; + short step_index ; + + int vox_bytes, pcm_samples ; + + unsigned char vox_data [VOX_DATA_LEN] ; + short pcm_data [PCM_DATA_LEN] ; +} VOX_ADPCM_PRIVATE ; + +static int vox_adpcm_encode_block (VOX_ADPCM_PRIVATE *pvox) ; +static int vox_adpcm_decode_block (VOX_ADPCM_PRIVATE *pvox) ; + +static short vox_adpcm_decode (char code, VOX_ADPCM_PRIVATE *pvox) ; +static char vox_adpcm_encode (short samp, VOX_ADPCM_PRIVATE *pvox) ; + +static sf_count_t vox_read_s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t vox_read_i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t vox_read_f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t vox_read_d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; + +static sf_count_t vox_write_s (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t vox_write_i (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t vox_write_f (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t vox_write_d (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; + +static int vox_read_block (SF_PRIVATE *psf, VOX_ADPCM_PRIVATE *pvox, short *ptr, int len) ; + +/*============================================================================================ +** Predefined OKI ADPCM encoder/decoder tables. +*/ + +static short step_size_table [49] = +{ 16, 17, 19, 21, 23, 25, 28, 31, 34, 37, 41, 45, 50, 55, 60, + 66, 73, 80, 88, 97, 107, 118, 130, 143, 157, 173, 190, 209, + 230, 253, 279, 307, 337, 371, 408, 449, 494, 544, 598, 658, + 724, 796, 876, 963, 1060, 1166, 1282, 1408, 1552 +} ; /* step_size_table */ + +static short step_adjust_table [8] = +{ -1, -1, -1, -1, 2, 4, 6, 8 +} ; /* step_adjust_table */ + +/*------------------------------------------------------------------------------ +*/ + +int +vox_adpcm_init (SF_PRIVATE *psf) +{ VOX_ADPCM_PRIVATE *pvox = NULL ; + + if (psf->mode == SFM_RDWR) + return SFE_BAD_MODE_RW ; + + if (psf->mode == SFM_WRITE && psf->sf.channels != 1) + return SFE_CHANNEL_COUNT ; + + if ((pvox = malloc (sizeof (VOX_ADPCM_PRIVATE))) == NULL) + return SFE_MALLOC_FAILED ; + + psf->fdata = (void*) pvox ; + memset (pvox, 0, sizeof (VOX_ADPCM_PRIVATE)) ; + + if (psf->mode == SFM_WRITE) + { psf->write_short = vox_write_s ; + psf->write_int = vox_write_i ; + psf->write_float = vox_write_f ; + psf->write_double = vox_write_d ; + } + else + { psf_log_printf (psf, "Header-less OKI Dialogic ADPCM encoded file.\n") ; + psf_log_printf (psf, "Setting up for 8kHz, mono, Vox ADPCM.\n") ; + + psf->read_short = vox_read_s ; + psf->read_int = vox_read_i ; + psf->read_float = vox_read_f ; + psf->read_double = vox_read_d ; + } ; + + /* Standard sample rate chennels etc. */ + if (psf->sf.samplerate < 1) + psf->sf.samplerate = 8000 ; + psf->sf.channels = 1 ; + + psf->sf.frames = psf->filelength * 2 ; + + psf->sf.seekable = SF_FALSE ; + + /* Seek back to start of data. */ + if (psf_fseek (psf, 0 , SEEK_SET) == -1) + return SFE_BAD_SEEK ; + + return 0 ; +} /* vox_adpcm_init */ + +/*------------------------------------------------------------------------------ +*/ + +static char +vox_adpcm_encode (short samp, VOX_ADPCM_PRIVATE *pvox) +{ short code ; + short diff, error, stepsize ; + + stepsize = step_size_table [pvox->step_index] ; + code = 0 ; + + diff = samp - pvox->last ; + if (diff < 0) + { code = 0x08 ; + error = -diff ; + } + else + error = diff ; + + if (error >= stepsize) + { code = code | 0x04 ; + error -= stepsize ; + } ; + + if (error >= stepsize / 2) + { code = code | 0x02 ; + error -= stepsize / 2 ; + } ; + + if (error >= stepsize / 4) + code = code | 0x01 ; + + /* + ** To close the feedback loop, the deocder is used to set the + ** estimate of last sample and in doing so, also set the step_index. + */ + pvox->last = vox_adpcm_decode (code, pvox) ; + + return code ; +} /* vox_adpcm_encode */ + +static short +vox_adpcm_decode (char code, VOX_ADPCM_PRIVATE *pvox) +{ short diff, error, stepsize, samp ; + + stepsize = step_size_table [pvox->step_index] ; + + error = stepsize / 8 ; + + if (code & 0x01) + error += stepsize / 4 ; + + if (code & 0x02) + error += stepsize / 2 ; + + if (code & 0x04) + error += stepsize ; + + diff = (code & 0x08) ? -error : error ; + samp = pvox->last + diff ; + + /* + ** Apply clipping. + */ + if (samp > 2048) + samp = 2048 ; + if (samp < -2048) + samp = -2048 ; + + pvox->last = samp ; + pvox->step_index += step_adjust_table [code & 0x7] ; + + if (pvox->step_index < 0) + pvox->step_index = 0 ; + if (pvox->step_index > 48) + pvox->step_index = 48 ; + + return samp ; +} /* vox_adpcm_decode */ + +static int +vox_adpcm_encode_block (VOX_ADPCM_PRIVATE *pvox) +{ unsigned char code ; + int j, k ; + + /* If data_count is odd, add an extra zero valued sample. */ + if (pvox->pcm_samples & 1) + pvox->pcm_data [pvox->pcm_samples++] = 0 ; + + for (j = k = 0 ; k < pvox->pcm_samples ; j++) + { code = vox_adpcm_encode (pvox->pcm_data [k++] / 16, pvox) << 4 ; + code |= vox_adpcm_encode (pvox->pcm_data [k++] / 16, pvox) ; + pvox->vox_data [j] = code ; + } ; + + pvox->vox_bytes = j ; + + return 0 ; +} /* vox_adpcm_encode_block */ + +static int +vox_adpcm_decode_block (VOX_ADPCM_PRIVATE *pvox) +{ unsigned char code ; + int j, k ; + + for (j = k = 0 ; j < pvox->vox_bytes ; j++) + { code = pvox->vox_data [j] ; + pvox->pcm_data [k++] = 16 * vox_adpcm_decode ((code >> 4) & 0x0f, pvox) ; + pvox->pcm_data [k++] = 16 * vox_adpcm_decode (code & 0x0f, pvox) ; + } ; + + pvox->pcm_samples = k ; + + return 0 ; +} /* vox_adpcm_decode_block */ + +/*============================================================================== +*/ + +static int +vox_read_block (SF_PRIVATE *psf, VOX_ADPCM_PRIVATE *pvox, short *ptr, int len) +{ int indx = 0, k ; + + while (indx < len) + { pvox->vox_bytes = (len - indx > PCM_DATA_LEN) ? VOX_DATA_LEN : (len - indx + 1) / 2 ; + + if ((k = psf_fread (pvox->vox_data, 1, pvox->vox_bytes, psf)) != pvox->vox_bytes) + { if (psf_ftell (psf) + k != psf->filelength) + psf_log_printf (psf, "*** Warning : short read (%d != %d).\n", k, pvox->vox_bytes) ; + if (k == 0) + break ; + } ; + + pvox->vox_bytes = k ; + + vox_adpcm_decode_block (pvox) ; + + memcpy (&(ptr [indx]), pvox->pcm_data, pvox->pcm_samples * sizeof (short)) ; + indx += pvox->pcm_samples ; + } ; + + return indx ; +} /* vox_read_block */ + + +static sf_count_t +vox_read_s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ VOX_ADPCM_PRIVATE *pvox ; + int readcount, count ; + sf_count_t total = 0 ; + + if (! psf->fdata) + return 0 ; + pvox = (VOX_ADPCM_PRIVATE*) psf->fdata ; + + while (len > 0) + { readcount = (len > 0x10000000) ? 0x10000000 : (int) len ; + + count = vox_read_block (psf, pvox, ptr, readcount) ; + + total += count ; + len -= count ; + if (count != readcount) + break ; + } ; + + return total ; +} /* vox_read_s */ + +static sf_count_t +vox_read_i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ VOX_ADPCM_PRIVATE *pvox ; + short *sptr ; + int k, bufferlen, readcount, count ; + sf_count_t total = 0 ; + + if (! psf->fdata) + return 0 ; + pvox = (VOX_ADPCM_PRIVATE*) psf->fdata ; + + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : (int) len ; + count = vox_read_block (psf, pvox, sptr, readcount) ; + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = ((int) sptr [k]) << 16 ; + total += count ; + len -= readcount ; + if (count != readcount) + break ; + } ; + + return total ; +} /* vox_read_i */ + +static sf_count_t +vox_read_f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ VOX_ADPCM_PRIVATE *pvox ; + short *sptr ; + int k, bufferlen, readcount, count ; + sf_count_t total = 0 ; + float normfact ; + + if (! psf->fdata) + return 0 ; + pvox = (VOX_ADPCM_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_float == SF_TRUE) ? 1.0 / ((float) 0x8000) : 1.0 ; + + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : (int) len ; + count = vox_read_block (psf, pvox, sptr, readcount) ; + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = normfact * (float) (sptr [k]) ; + total += count ; + len -= readcount ; + if (count != readcount) + break ; + } ; + + return total ; +} /* vox_read_f */ + +static sf_count_t +vox_read_d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ VOX_ADPCM_PRIVATE *pvox ; + short *sptr ; + int k, bufferlen, readcount, count ; + sf_count_t total = 0 ; + double normfact ; + + if (! psf->fdata) + return 0 ; + pvox = (VOX_ADPCM_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_double == SF_TRUE) ? 1.0 / ((double) 0x8000) : 1.0 ; + + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { readcount = (len >= bufferlen) ? bufferlen : (int) len ; + count = vox_read_block (psf, pvox, sptr, readcount) ; + for (k = 0 ; k < readcount ; k++) + ptr [total + k] = normfact * (double) (sptr [k]) ; + total += count ; + len -= readcount ; + if (count != readcount) + break ; + } ; + + return total ; +} /* vox_read_d */ + +/*------------------------------------------------------------------------------ +*/ + +static int +vox_write_block (SF_PRIVATE *psf, VOX_ADPCM_PRIVATE *pvox, const short *ptr, int len) +{ int indx = 0, k ; + + while (indx < len) + { pvox->pcm_samples = (len - indx > PCM_DATA_LEN) ? PCM_DATA_LEN : len - indx ; + + memcpy (pvox->pcm_data, &(ptr [indx]), pvox->pcm_samples * sizeof (short)) ; + + vox_adpcm_encode_block (pvox) ; + + if ((k = psf_fwrite (pvox->vox_data, 1, pvox->vox_bytes, psf)) != pvox->vox_bytes) + psf_log_printf (psf, "*** Warning : short read (%d != %d).\n", k, pvox->vox_bytes) ; + + indx += pvox->pcm_samples ; + } ; + + return indx ; +} /* vox_write_block */ + +static sf_count_t +vox_write_s (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ VOX_ADPCM_PRIVATE *pvox ; + int writecount, count ; + sf_count_t total = 0 ; + + if (! psf->fdata) + return 0 ; + pvox = (VOX_ADPCM_PRIVATE*) psf->fdata ; + + while (len) + { writecount = (len > 0x10000000) ? 0x10000000 : (int) len ; + + count = vox_write_block (psf, pvox, ptr, writecount) ; + + total += count ; + len -= count ; + if (count != writecount) + break ; + } ; + + return total ; +} /* vox_write_s */ + +static sf_count_t +vox_write_i (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ VOX_ADPCM_PRIVATE *pvox ; + short *sptr ; + int k, bufferlen, writecount, count ; + sf_count_t total = 0 ; + + if (! psf->fdata) + return 0 ; + pvox = (VOX_ADPCM_PRIVATE*) psf->fdata ; + + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : (int) len ; + for (k = 0 ; k < writecount ; k++) + sptr [k] = ptr [total + k] >> 16 ; + count = vox_write_block (psf, pvox, sptr, writecount) ; + total += count ; + len -= writecount ; + if (count != writecount) + break ; + } ; + + return total ; +} /* vox_write_i */ + +static sf_count_t +vox_write_f (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ VOX_ADPCM_PRIVATE *pvox ; + short *sptr ; + int k, bufferlen, writecount, count ; + sf_count_t total = 0 ; + float normfact ; + + if (! psf->fdata) + return 0 ; + pvox = (VOX_ADPCM_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_float == SF_TRUE) ? (1.0 * 0x7FFF) : 1.0 ; + + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : (int) len ; + for (k = 0 ; k < writecount ; k++) + sptr [k] = lrintf (normfact * ptr [total + k]) ; + count = vox_write_block (psf, pvox, sptr, writecount) ; + total += count ; + len -= writecount ; + if (count != writecount) + break ; + } ; + + return total ; +} /* vox_write_f */ + +static sf_count_t +vox_write_d (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ VOX_ADPCM_PRIVATE *pvox ; + short *sptr ; + int k, bufferlen, writecount, count ; + sf_count_t total = 0 ; + double normfact ; + + if (! psf->fdata) + return 0 ; + pvox = (VOX_ADPCM_PRIVATE*) psf->fdata ; + + normfact = (psf->norm_double == SF_TRUE) ? (1.0 * 0x7FFF) : 1.0 ; + + sptr = psf->u.sbuf ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (len > 0) + { writecount = (len >= bufferlen) ? bufferlen : (int) len ; + for (k = 0 ; k < writecount ; k++) + sptr [k] = lrint (normfact * ptr [total + k]) ; + count = vox_write_block (psf, pvox, sptr, writecount) ; + total += count ; + len -= writecount ; + if (count != writecount) + break ; + } ; + + return total ; +} /* vox_write_d */ + + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: e15e97fe-ff9d-4b46-a489-7059fb2d0b1e +*/ diff --git a/libs/libsndfile/src/w64.c b/libs/libsndfile/src/w64.c new file mode 100644 index 0000000000..756b093153 --- /dev/null +++ b/libs/libsndfile/src/w64.c @@ -0,0 +1,578 @@ +/* +** Copyright (C) 1999-2005 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" +#include "wav_w64.h" + +/*------------------------------------------------------------------------------ +** W64 files use 16 byte markers as opposed to the four byte marker of +** WAV files. +** For comparison purposes, an integer is required, so make an integer +** hash for the 16 bytes using MAKE_HASH16 macro, but also create a 16 +** byte array containing the complete 16 bytes required when writing the +** header. +*/ + +#define MAKE_HASH16(x0,x1,x2,x3,x4,x5,x6,x7,x8,x9,xa,xb,xc,xd,xe,xf) \ + ( (x0) ^ ((x1) << 1) ^ ((x2) << 2) ^ ((x3) << 3) ^ \ + ((x4) << 4) ^ ((x5) << 5) ^ ((x6) << 6) ^ ((x7) << 7) ^ \ + ((x8) << 8) ^ ((x9) << 9) ^ ((xa) << 10) ^ ((xb) << 11) ^ \ + ((xc) << 12) ^ ((xd) << 13) ^ ((xe) << 14) ^ ((xf) << 15) ) + +#define MAKE_MARKER16(name,x0,x1,x2,x3,x4,x5,x6,x7,x8,x9,xa,xb,xc,xd,xe,xf) \ + static unsigned char name [16] = { (x0), (x1), (x2), (x3), (x4), (x5), \ + (x6), (x7), (x8), (x9), (xa), (xb), (xc), (xd), (xe), (xf) } + +#define riff_HASH16 MAKE_HASH16 ('r', 'i', 'f', 'f', 0x2E, 0x91, 0xCF, 0x11, 0xA5, \ + 0xD6, 0x28, 0xDB, 0x04, 0xC1, 0x00, 0x00) + +#define wave_HASH16 MAKE_HASH16 ('w', 'a', 'v', 'e', 0xF3, 0xAC, 0xD3, 0x11, \ + 0x8C, 0xD1, 0x00, 0xC0, 0x4F, 0x8E, 0xDB, 0x8A) + +#define fmt_HASH16 MAKE_HASH16 ('f', 'm', 't', ' ', 0xF3, 0xAC, 0xD3, 0x11, \ + 0x8C, 0xD1, 0x00, 0xC0, 0x4F, 0x8E, 0xDB, 0x8A) + +#define fact_HASH16 MAKE_HASH16 ('f', 'a', 'c', 't', 0xF3, 0xAC, 0xD3, 0x11, \ + 0x8C, 0xD1, 0x00, 0xC0, 0x4F, 0x8E, 0xDB, 0x8A) + +#define data_HASH16 MAKE_HASH16 ('d', 'a', 't', 'a', 0xF3, 0xAC, 0xD3, 0x11, \ + 0x8C, 0xD1, 0x00, 0xC0, 0x4F, 0x8E, 0xDB, 0x8A) + +#define ACID_HASH16 MAKE_HASH16 (0x6D, 0x07, 0x1C, 0xEA, 0xA3, 0xEF, 0x78, 0x4C, \ + 0x90, 0x57, 0x7F, 0x79, 0xEE, 0x25, 0x2A, 0xAE) + +MAKE_MARKER16 (riff_MARKER16, 'r', 'i', 'f', 'f', 0x2E, 0x91, 0xCF, 0x11, + 0xA5, 0xD6, 0x28, 0xDB, 0x04, 0xC1, 0x00, 0x00) ; + + +MAKE_MARKER16 (wave_MARKER16, 'w', 'a', 'v', 'e', 0xF3, 0xAC, 0xD3, 0x11, + 0x8C, 0xD1, 0x00, 0xC0, 0x4F, 0x8E, 0xDB, 0x8A) ; + +MAKE_MARKER16 (fmt_MARKER16, 'f', 'm', 't', ' ', 0xF3, 0xAC, 0xD3, 0x11, + 0x8C, 0xD1, 0x00, 0xC0, 0x4F, 0x8E, 0xDB, 0x8A) ; + +MAKE_MARKER16 (fact_MARKER16, 'f', 'a', 'c', 't', 0xF3, 0xAC, 0xD3, 0x11, + 0x8C, 0xD1, 0x00, 0xC0, 0x4F, 0x8E, 0xDB, 0x8A) ; + +MAKE_MARKER16 (data_MARKER16, 'd', 'a', 't', 'a', 0xF3, 0xAC, 0xD3, 0x11, + 0x8C, 0xD1, 0x00, 0xC0, 0x4F, 0x8E, 0xDB, 0x8A) ; + +enum +{ HAVE_riff = 0x01, + HAVE_wave = 0x02, + HAVE_fmt = 0x04, + HAVE_fact = 0x08, + HAVE_data = 0x20 +} ; + +/*------------------------------------------------------------------------------ + * Private static functions. + */ + +static int w64_read_header (SF_PRIVATE *psf, int *blockalign, int *framesperblock) ; +static int w64_write_header (SF_PRIVATE *psf, int calc_length) ; +static int w64_close (SF_PRIVATE *psf) ; + +/*------------------------------------------------------------------------------ +** Public function. +*/ + +int +w64_open (SF_PRIVATE *psf) +{ int subformat, error, blockalign = 0, framesperblock = 0 ; + + if (psf->mode == SFM_READ || (psf->mode == SFM_RDWR &&psf->filelength > 0)) + { if ((error = w64_read_header (psf, &blockalign, &framesperblock))) + return error ; + } ; + + if ((psf->sf.format & SF_FORMAT_TYPEMASK) != SF_FORMAT_W64) + return SFE_BAD_OPEN_FORMAT ; + + subformat = psf->sf.format & SF_FORMAT_SUBMASK ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { if (psf->is_pipe) + return SFE_NO_PIPE_WRITE ; + + psf->endian = SF_ENDIAN_LITTLE ; /* All W64 files are little endian. */ + + psf->blockwidth = psf->bytewidth * psf->sf.channels ; + + if (subformat == SF_FORMAT_IMA_ADPCM || subformat == SF_FORMAT_MS_ADPCM) + { blockalign = wav_w64_srate2blocksize (psf->sf.samplerate * psf->sf.channels) ; + framesperblock = -1 ; + + /* FIXME : This block must go */ + psf->filelength = SF_COUNT_MAX ; + psf->datalength = psf->filelength ; + if (psf->sf.frames <= 0) + psf->sf.frames = (psf->blockwidth) ? psf->filelength / psf->blockwidth : psf->filelength ; + /* EMXIF : This block must go */ + } ; + + if ((error = w64_write_header (psf, SF_FALSE))) + return error ; + + psf->write_header = w64_write_header ; + } ; + + psf->container_close = w64_close ; + + switch (subformat) + { case SF_FORMAT_PCM_U8 : + error = pcm_init (psf) ; + break ; + + case SF_FORMAT_PCM_16 : + case SF_FORMAT_PCM_24 : + case SF_FORMAT_PCM_32 : + error = pcm_init (psf) ; + break ; + + case SF_FORMAT_ULAW : + error = ulaw_init (psf) ; + break ; + + case SF_FORMAT_ALAW : + error = alaw_init (psf) ; + break ; + + /* Lite remove start */ + case SF_FORMAT_FLOAT : + error = float32_init (psf) ; + break ; + + case SF_FORMAT_DOUBLE : + error = double64_init (psf) ; + break ; + + case SF_FORMAT_IMA_ADPCM : + error = wav_w64_ima_init (psf, blockalign, framesperblock) ; + break ; + + case SF_FORMAT_MS_ADPCM : + error = wav_w64_msadpcm_init (psf, blockalign, framesperblock) ; + break ; + /* Lite remove end */ + + case SF_FORMAT_GSM610 : + error = gsm610_init (psf) ; + break ; + + default : return SFE_UNIMPLEMENTED ; + } ; + + return error ; +} /* w64_open */ + +/*========================================================================= +** Private functions. +*/ + +static int +w64_read_header (SF_PRIVATE *psf, int *blockalign, int *framesperblock) +{ WAV_FMT wav_fmt ; + int dword = 0, marker, format = 0 ; + sf_count_t chunk_size, bytesread = 0 ; + int parsestage = 0, error, done = 0 ; + + /* Set position to start of file to begin reading header. */ + memset (&wav_fmt, 0, sizeof (wav_fmt)) ; + psf_binheader_readf (psf, "p", 0) ; + + while (! done) + { /* Read the 4 byte marker and jump 12 bytes. */ + bytesread += psf_binheader_readf (psf, "h", &marker) ; + chunk_size = 0 ; + + switch (marker) + { case riff_HASH16 : + if (parsestage) + return SFE_W64_NO_RIFF ; + + bytesread += psf_binheader_readf (psf, "e8", &chunk_size) ; + + if (psf->filelength < chunk_size) + psf_log_printf (psf, "riff : %D (should be %D)\n", chunk_size, psf->filelength) ; + else + psf_log_printf (psf, "riff : %D\n", chunk_size) ; + + parsestage |= HAVE_riff ; + break ; + + case ACID_HASH16: + psf_log_printf (psf, "Looks like an ACID file. Exiting.\n") ; + return SFE_UNIMPLEMENTED ; + + case wave_HASH16 : + if ((parsestage & HAVE_riff) != HAVE_riff) + return SFE_W64_NO_WAVE ; + psf_log_printf (psf, "wave\n") ; + parsestage |= HAVE_wave ; + break ; + + case fmt_HASH16 : + if ((parsestage & (HAVE_riff | HAVE_wave)) != (HAVE_riff | HAVE_wave)) + return SFE_W64_NO_FMT ; + + bytesread += psf_binheader_readf (psf, "e8", &chunk_size) ; + psf_log_printf (psf, " fmt : %D\n", chunk_size) ; + + /* size of 16 byte marker and 8 byte chunk_size value. */ + chunk_size -= 24 ; + + if ((error = wav_w64_read_fmt_chunk (psf, &wav_fmt, (int) chunk_size))) + return error ; + + if (chunk_size % 8) + psf_binheader_readf (psf, "j", 8 - (chunk_size % 8)) ; + + format = wav_fmt.format ; + parsestage |= HAVE_fmt ; + break ; + + case fact_HASH16: + { sf_count_t frames ; + + psf_binheader_readf (psf, "e88", &chunk_size, &frames) ; + psf_log_printf (psf, " fact : %D\n frames : %D\n", + chunk_size, frames) ; + } ; + break ; + + + case data_HASH16 : + if ((parsestage & (HAVE_riff | HAVE_wave | HAVE_fmt)) != (HAVE_riff | HAVE_wave | HAVE_fmt)) + return SFE_W64_NO_DATA ; + + psf_binheader_readf (psf, "e8", &chunk_size) ; + + psf->dataoffset = psf_ftell (psf) ; + + psf->datalength = chunk_size - 24 ; + + if (chunk_size % 8) + chunk_size += 8 - (chunk_size % 8) ; + + psf_log_printf (psf, "data : %D\n", chunk_size) ; + + parsestage |= HAVE_data ; + + if (! psf->sf.seekable) + break ; + + /* Seek past data and continue reading header. */ + psf_fseek (psf, chunk_size, SEEK_CUR) ; + break ; + + default : + if (psf_ftell (psf) & 0x0F) + { psf_log_printf (psf, " Unknown chunk marker at position %d. Resynching.\n", dword - 4) ; + psf_binheader_readf (psf, "j", -3) ; + break ; + } ; + psf_log_printf (psf, "*** Unknown chunk marker : %X. Exiting parser.\n", marker) ; + done = SF_TRUE ; + break ; + } ; /* switch (dword) */ + + if (psf->sf.seekable == 0 && (parsestage & HAVE_data)) + break ; + + if (psf_ftell (psf) >= (psf->filelength - (2 * SIGNED_SIZEOF (dword)))) + break ; + } ; /* while (1) */ + + if (! psf->dataoffset) + return SFE_W64_NO_DATA ; + + psf->endian = SF_ENDIAN_LITTLE ; /* All WAV files are little endian. */ + + if (psf_ftell (psf) != psf->dataoffset) + psf_fseek (psf, psf->dataoffset, SEEK_SET) ; + + if (psf->blockwidth) + { if (psf->filelength - psf->dataoffset < psf->datalength) + psf->sf.frames = (psf->filelength - psf->dataoffset) / psf->blockwidth ; + else + psf->sf.frames = psf->datalength / psf->blockwidth ; + } ; + + switch (format) + { case WAVE_FORMAT_PCM : + case WAVE_FORMAT_EXTENSIBLE : + /* extensible might be FLOAT, MULAW, etc as well! */ + psf->sf.format = SF_FORMAT_W64 | u_bitwidth_to_subformat (psf->bytewidth * 8) ; + break ; + + case WAVE_FORMAT_MULAW : + psf->sf.format = (SF_FORMAT_W64 | SF_FORMAT_ULAW) ; + break ; + + case WAVE_FORMAT_ALAW : + psf->sf.format = (SF_FORMAT_W64 | SF_FORMAT_ALAW) ; + break ; + + case WAVE_FORMAT_MS_ADPCM : + psf->sf.format = (SF_FORMAT_W64 | SF_FORMAT_MS_ADPCM) ; + *blockalign = wav_fmt.msadpcm.blockalign ; + *framesperblock = wav_fmt.msadpcm.samplesperblock ; + break ; + + case WAVE_FORMAT_IMA_ADPCM : + psf->sf.format = (SF_FORMAT_W64 | SF_FORMAT_IMA_ADPCM) ; + *blockalign = wav_fmt.ima.blockalign ; + *framesperblock = wav_fmt.ima.samplesperblock ; + break ; + + case WAVE_FORMAT_GSM610 : + psf->sf.format = (SF_FORMAT_W64 | SF_FORMAT_GSM610) ; + break ; + + case WAVE_FORMAT_IEEE_FLOAT : + psf->sf.format = SF_FORMAT_W64 ; + psf->sf.format |= (psf->bytewidth == 8) ? SF_FORMAT_DOUBLE : SF_FORMAT_FLOAT ; + break ; + + default : return SFE_UNIMPLEMENTED ; + } ; + + return 0 ; +} /* w64_read_header */ + +static int +w64_write_header (SF_PRIVATE *psf, int calc_length) +{ sf_count_t fmt_size, current ; + size_t fmt_pad = 0 ; + int subformat, add_fact_chunk = SF_FALSE ; + + current = psf_ftell (psf) ; + + if (calc_length) + { psf->filelength = psf_get_filelen (psf) ; + + psf->datalength = psf->filelength - psf->dataoffset ; + if (psf->dataend) + psf->datalength -= psf->filelength - psf->dataend ; + + if (psf->bytewidth) + psf->sf.frames = psf->datalength / (psf->bytewidth * psf->sf.channels) ; + } ; + + /* Reset the current header length to zero. */ + psf->header [0] = 0 ; + psf->headindex = 0 ; + psf_fseek (psf, 0, SEEK_SET) ; + + /* riff marker, length, wave and 'fmt ' markers. */ + psf_binheader_writef (psf, "eh8hh", riff_MARKER16, psf->filelength - 8, wave_MARKER16, fmt_MARKER16) ; + + subformat = psf->sf.format & SF_FORMAT_SUBMASK ; + + switch (subformat) + { case SF_FORMAT_PCM_U8 : + case SF_FORMAT_PCM_16 : + case SF_FORMAT_PCM_24 : + case SF_FORMAT_PCM_32 : + fmt_size = 24 + 2 + 2 + 4 + 4 + 2 + 2 ; + fmt_pad = (size_t) (8 - (fmt_size & 0x7)) ; + fmt_size += fmt_pad ; + + /* fmt : format, channels, samplerate */ + psf_binheader_writef (psf, "e8224", fmt_size, WAVE_FORMAT_PCM, psf->sf.channels, psf->sf.samplerate) ; + /* fmt : bytespersec */ + psf_binheader_writef (psf, "e4", psf->sf.samplerate * psf->bytewidth * psf->sf.channels) ; + /* fmt : blockalign, bitwidth */ + psf_binheader_writef (psf, "e22", psf->bytewidth * psf->sf.channels, psf->bytewidth * 8) ; + break ; + + case SF_FORMAT_FLOAT : + case SF_FORMAT_DOUBLE : + fmt_size = 24 + 2 + 2 + 4 + 4 + 2 + 2 ; + fmt_pad = (size_t) (8 - (fmt_size & 0x7)) ; + fmt_size += fmt_pad ; + + /* fmt : format, channels, samplerate */ + psf_binheader_writef (psf, "e8224", fmt_size, WAVE_FORMAT_IEEE_FLOAT, psf->sf.channels, psf->sf.samplerate) ; + /* fmt : bytespersec */ + psf_binheader_writef (psf, "e4", psf->sf.samplerate * psf->bytewidth * psf->sf.channels) ; + /* fmt : blockalign, bitwidth */ + psf_binheader_writef (psf, "e22", psf->bytewidth * psf->sf.channels, psf->bytewidth * 8) ; + + add_fact_chunk = SF_TRUE ; + break ; + + case SF_FORMAT_ULAW : + fmt_size = 24 + 2 + 2 + 4 + 4 + 2 + 2 ; + fmt_pad = (size_t) (8 - (fmt_size & 0x7)) ; + fmt_size += fmt_pad ; + + /* fmt : format, channels, samplerate */ + psf_binheader_writef (psf, "e8224", fmt_size, WAVE_FORMAT_MULAW, psf->sf.channels, psf->sf.samplerate) ; + /* fmt : bytespersec */ + psf_binheader_writef (psf, "e4", psf->sf.samplerate * psf->bytewidth * psf->sf.channels) ; + /* fmt : blockalign, bitwidth */ + psf_binheader_writef (psf, "e22", psf->bytewidth * psf->sf.channels, 8) ; + + add_fact_chunk = SF_TRUE ; + break ; + + case SF_FORMAT_ALAW : + fmt_size = 24 + 2 + 2 + 4 + 4 + 2 + 2 ; + fmt_pad = (size_t) (8 - (fmt_size & 0x7)) ; + fmt_size += fmt_pad ; + + /* fmt : format, channels, samplerate */ + psf_binheader_writef (psf, "e8224", fmt_size, WAVE_FORMAT_ALAW, psf->sf.channels, psf->sf.samplerate) ; + /* fmt : bytespersec */ + psf_binheader_writef (psf, "e4", psf->sf.samplerate * psf->bytewidth * psf->sf.channels) ; + /* fmt : blockalign, bitwidth */ + psf_binheader_writef (psf, "e22", psf->bytewidth * psf->sf.channels, 8) ; + + add_fact_chunk = SF_TRUE ; + break ; + + /* Lite remove start */ + case SF_FORMAT_IMA_ADPCM : + { int blockalign, framesperblock, bytespersec ; + + blockalign = wav_w64_srate2blocksize (psf->sf.samplerate * psf->sf.channels) ; + framesperblock = 2 * (blockalign - 4 * psf->sf.channels) / psf->sf.channels + 1 ; + bytespersec = (psf->sf.samplerate * blockalign) / framesperblock ; + + /* fmt chunk. */ + fmt_size = 24 + 2 + 2 + 4 + 4 + 2 + 2 + 2 + 2 ; + fmt_pad = (size_t) (8 - (fmt_size & 0x7)) ; + fmt_size += fmt_pad ; + + /* fmt : size, WAV format type, channels. */ + psf_binheader_writef (psf, "e822", fmt_size, WAVE_FORMAT_IMA_ADPCM, psf->sf.channels) ; + + /* fmt : samplerate, bytespersec. */ + psf_binheader_writef (psf, "e44", psf->sf.samplerate, bytespersec) ; + + /* fmt : blockalign, bitwidth, extrabytes, framesperblock. */ + psf_binheader_writef (psf, "e2222", blockalign, 4, 2, framesperblock) ; + } ; + + add_fact_chunk = SF_TRUE ; + break ; + + case SF_FORMAT_MS_ADPCM : + { int blockalign, framesperblock, bytespersec, extrabytes ; + + blockalign = wav_w64_srate2blocksize (psf->sf.samplerate * psf->sf.channels) ; + framesperblock = 2 + 2 * (blockalign - 7 * psf->sf.channels) / psf->sf.channels ; + bytespersec = (psf->sf.samplerate * blockalign) / framesperblock ; + + /* fmt chunk. */ + extrabytes = 2 + 2 + MSADPCM_ADAPT_COEFF_COUNT * (2 + 2) ; + fmt_size = 24 + 2 + 2 + 4 + 4 + 2 + 2 + 2 + extrabytes ; + fmt_pad = (size_t) (8 - (fmt_size & 0x7)) ; + fmt_size += fmt_pad ; + + /* fmt : size, W64 format type, channels. */ + psf_binheader_writef (psf, "e822", fmt_size, WAVE_FORMAT_MS_ADPCM, psf->sf.channels) ; + + /* fmt : samplerate, bytespersec. */ + psf_binheader_writef (psf, "e44", psf->sf.samplerate, bytespersec) ; + + /* fmt : blockalign, bitwidth, extrabytes, framesperblock. */ + psf_binheader_writef (psf, "e22222", blockalign, 4, extrabytes, framesperblock, 7) ; + + msadpcm_write_adapt_coeffs (psf) ; + } ; + + add_fact_chunk = SF_TRUE ; + break ; + /* Lite remove end */ + + case SF_FORMAT_GSM610 : + { int bytespersec ; + + bytespersec = (psf->sf.samplerate * WAV_W64_GSM610_BLOCKSIZE) / WAV_W64_GSM610_SAMPLES ; + + /* fmt chunk. */ + fmt_size = 24 + 2 + 2 + 4 + 4 + 2 + 2 + 2 + 2 ; + fmt_pad = (size_t) (8 - (fmt_size & 0x7)) ; + fmt_size += fmt_pad ; + + /* fmt : size, WAV format type, channels. */ + psf_binheader_writef (psf, "e822", fmt_size, WAVE_FORMAT_GSM610, psf->sf.channels) ; + + /* fmt : samplerate, bytespersec. */ + psf_binheader_writef (psf, "e44", psf->sf.samplerate, bytespersec) ; + + /* fmt : blockalign, bitwidth, extrabytes, framesperblock. */ + psf_binheader_writef (psf, "e2222", WAV_W64_GSM610_BLOCKSIZE, 0, 2, WAV_W64_GSM610_SAMPLES) ; + } ; + + add_fact_chunk = SF_TRUE ; + break ; + + default : return SFE_UNIMPLEMENTED ; + } ; + + /* Pad to 8 bytes with zeros. */ + if (fmt_pad > 0) + psf_binheader_writef (psf, "z", fmt_pad) ; + + if (add_fact_chunk) + psf_binheader_writef (psf, "eh88", fact_MARKER16, (sf_count_t) (16 + 8 + 8), psf->sf.frames) ; + + psf_binheader_writef (psf, "eh8", data_MARKER16, psf->datalength + 24) ; + psf_fwrite (psf->header, psf->headindex, 1, psf) ; + + if (psf->error) + return psf->error ; + + psf->dataoffset = psf->headindex ; + + if (current > 0) + psf_fseek (psf, current, SEEK_SET) ; + + return psf->error ; +} /* w64_write_header */ + +static int +w64_close (SF_PRIVATE *psf) +{ + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + w64_write_header (psf, SF_TRUE) ; + + return 0 ; +} /* w64_close */ + + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 9aa4e141-538a-4dd9-99c9-b3f0f2dd4f4a +*/ diff --git a/libs/libsndfile/src/wav.c b/libs/libsndfile/src/wav.c new file mode 100644 index 0000000000..f2fbcd7b50 --- /dev/null +++ b/libs/libsndfile/src/wav.c @@ -0,0 +1,1633 @@ +/* +** Copyright (C) 1999-2006 Erik de Castro Lopo +** Copyright (C) 2004-2005 David Viens +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" +#include "wav_w64.h" + +/*------------------------------------------------------------------------------ + * Macros to handle big/little endian issues. + */ + +#define RIFF_MARKER (MAKE_MARKER ('R', 'I', 'F', 'F')) +#define RIFX_MARKER (MAKE_MARKER ('R', 'I', 'F', 'X')) +#define WAVE_MARKER (MAKE_MARKER ('W', 'A', 'V', 'E')) +#define fmt_MARKER (MAKE_MARKER ('f', 'm', 't', ' ')) +#define data_MARKER (MAKE_MARKER ('d', 'a', 't', 'a')) +#define fact_MARKER (MAKE_MARKER ('f', 'a', 'c', 't')) +#define PEAK_MARKER (MAKE_MARKER ('P', 'E', 'A', 'K')) + +#define cue_MARKER (MAKE_MARKER ('c', 'u', 'e', ' ')) +#define LIST_MARKER (MAKE_MARKER ('L', 'I', 'S', 'T')) +#define slnt_MARKER (MAKE_MARKER ('s', 'l', 'n', 't')) +#define wavl_MARKER (MAKE_MARKER ('w', 'a', 'v', 'l')) +#define INFO_MARKER (MAKE_MARKER ('I', 'N', 'F', 'O')) +#define plst_MARKER (MAKE_MARKER ('p', 'l', 's', 't')) +#define adtl_MARKER (MAKE_MARKER ('a', 'd', 't', 'l')) +#define labl_MARKER (MAKE_MARKER ('l', 'a', 'b', 'l')) +#define ltxt_MARKER (MAKE_MARKER ('l', 't', 'x', 't')) +#define note_MARKER (MAKE_MARKER ('n', 'o', 't', 'e')) +#define smpl_MARKER (MAKE_MARKER ('s', 'm', 'p', 'l')) +#define bext_MARKER (MAKE_MARKER ('b', 'e', 'x', 't')) +#define levl_MARKER (MAKE_MARKER ('l', 'e', 'v', 'l')) +#define MEXT_MARKER (MAKE_MARKER ('M', 'E', 'X', 'T')) +#define DISP_MARKER (MAKE_MARKER ('D', 'I', 'S', 'P')) +#define acid_MARKER (MAKE_MARKER ('a', 'c', 'i', 'd')) +#define strc_MARKER (MAKE_MARKER ('s', 't', 'r', 'c')) +#define PAD_MARKER (MAKE_MARKER ('P', 'A', 'D', ' ')) +#define afsp_MARKER (MAKE_MARKER ('a', 'f', 's', 'p')) +#define clm_MARKER (MAKE_MARKER ('c', 'l', 'm', ' ')) +#define elmo_MARKER (MAKE_MARKER ('e', 'l', 'm', 'o')) + +#define ISFT_MARKER (MAKE_MARKER ('I', 'S', 'F', 'T')) +#define ICRD_MARKER (MAKE_MARKER ('I', 'C', 'R', 'D')) +#define ICOP_MARKER (MAKE_MARKER ('I', 'C', 'O', 'P')) +#define IARL_MARKER (MAKE_MARKER ('I', 'A', 'R', 'L')) +#define IART_MARKER (MAKE_MARKER ('I', 'A', 'R', 'T')) +#define INAM_MARKER (MAKE_MARKER ('I', 'N', 'A', 'M')) +#define IENG_MARKER (MAKE_MARKER ('I', 'E', 'N', 'G')) +#define IART_MARKER (MAKE_MARKER ('I', 'A', 'R', 'T')) +#define ICOP_MARKER (MAKE_MARKER ('I', 'C', 'O', 'P')) +#define IPRD_MARKER (MAKE_MARKER ('I', 'P', 'R', 'D')) +#define ISRC_MARKER (MAKE_MARKER ('I', 'S', 'R', 'C')) +#define ISBJ_MARKER (MAKE_MARKER ('I', 'S', 'B', 'J')) +#define ICMT_MARKER (MAKE_MARKER ('I', 'C', 'M', 'T')) + +/* Weird WAVPACK marker which can show up at the start of the DATA section. */ +#define wvpk_MARKER (MAKE_MARKER ('w', 'v', 'p', 'k')) +#define OggS_MARKER (MAKE_MARKER ('O', 'g', 'g', 'S')) + +#define WAV_PEAK_CHUNK_SIZE(ch) (2 * sizeof (int) + ch * (sizeof (float) + sizeof (int))) +#define WAV_BEXT_CHUNK_SIZE 602 + +enum +{ HAVE_RIFF = 0x01, + HAVE_WAVE = 0x02, + HAVE_fmt = 0x04, + HAVE_fact = 0x08, + HAVE_PEAK = 0x10, + HAVE_data = 0x20, + HAVE_other = 0x80000000 +} ; + + + +/* known WAVEFORMATEXTENSIBLE GUIDS */ +static const EXT_SUBFORMAT MSGUID_SUBTYPE_PCM = +{ 0x00000001, 0x0000, 0x0010, { 0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71 } +} ; + +static const EXT_SUBFORMAT MSGUID_SUBTYPE_MS_ADPCM = +{ 0x00000002, 0x0000, 0x0010, { 0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71 } +} ; + +static const EXT_SUBFORMAT MSGUID_SUBTYPE_IEEE_FLOAT = +{ 0x00000003, 0x0000, 0x0010, { 0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71 } +} ; + +static const EXT_SUBFORMAT MSGUID_SUBTYPE_ALAW = +{ 0x00000006, 0x0000, 0x0010, { 0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71 } +} ; + +static const EXT_SUBFORMAT MSGUID_SUBTYPE_MULAW = +{ 0x00000007, 0x0000, 0x0010, { 0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71 } +} ; + +/* +** the next two are from +** http://dream.cs.bath.ac.uk/researchdev/wave-ex/bformat.html +*/ +static const EXT_SUBFORMAT MSGUID_SUBTYPE_AMBISONIC_B_FORMAT_PCM = +{ 0x00000001, 0x0721, 0x11d3, { 0x86, 0x44, 0xC8, 0xC1, 0xCA, 0x00, 0x00, 0x00 } +} ; + +static const EXT_SUBFORMAT MSGUID_SUBTYPE_AMBISONIC_B_FORMAT_IEEE_FLOAT = +{ 0x00000003, 0x0721, 0x11d3, { 0x86, 0x44, 0xC8, 0xC1, 0xCA, 0x00, 0x00, 0x00 } +} ; + + +#if 0 +/* maybe interesting one day to read the following through sf_read_raw */ +/* http://www.bath.ac.uk/~masrwd/pvocex/pvocex.html */ +static const EXT_SUBFORMAT MSGUID_SUBTYPE_PVOCEX = +{ 0x8312B9C2, 0x2E6E, 0x11d4, { 0xA8, 0x24, 0xDE, 0x5B, 0x96, 0xC3, 0xAB, 0x21 } +} ; +#endif + +/*------------------------------------------------------------------------------ +** Private static functions. +*/ + +static int wav_read_header (SF_PRIVATE *psf, int *blockalign, int *framesperblock) ; +static int wav_write_header (SF_PRIVATE *psf, int calc_length) ; + +static int wavex_write_header (SF_PRIVATE *psf, int calc_length) ; + +static int wav_write_tailer (SF_PRIVATE *psf) ; +static void wav_write_strings (SF_PRIVATE *psf, int location) ; +static int wav_command (SF_PRIVATE *psf, int command, void *data, int datasize) ; +static int wav_close (SF_PRIVATE *psf) ; + +static int wav_subchunk_parse (SF_PRIVATE *psf, int chunk) ; +static int wav_read_smpl_chunk (SF_PRIVATE *psf, unsigned int chunklen) ; +static int wav_read_acid_chunk (SF_PRIVATE *psf, unsigned int chunklen) ; +static int wav_read_bext_chunk (SF_PRIVATE *psf, unsigned int chunklen) ; +static int wav_write_bext_chunk (SF_PRIVATE *psf) ; + +/*------------------------------------------------------------------------------ +** Public function. +*/ + +int +wav_open (SF_PRIVATE *psf) +{ int format, subformat, error, blockalign = 0, framesperblock = 0 ; + + if (psf->mode == SFM_READ || (psf->mode == SFM_RDWR && psf->filelength > 0)) + { if ((error = wav_read_header (psf, &blockalign, &framesperblock))) + return error ; + } ; + + subformat = psf->sf.format & SF_FORMAT_SUBMASK ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { if (psf->is_pipe) + return SFE_NO_PIPE_WRITE ; + + format = psf->sf.format & SF_FORMAT_TYPEMASK ; + if (format != SF_FORMAT_WAV && format != SF_FORMAT_WAVEX) + return SFE_BAD_OPEN_FORMAT ; + + psf->blockwidth = psf->bytewidth * psf->sf.channels ; + + /* RIFF WAVs are little-endian, RIFX WAVs are big-endian, default to little */ + psf->endian = psf->sf.format & SF_FORMAT_ENDMASK ; + if (CPU_IS_BIG_ENDIAN && psf->endian == SF_ENDIAN_CPU) + psf->endian = SF_ENDIAN_BIG ; + else if (psf->endian != SF_ENDIAN_BIG) + psf->endian = SF_ENDIAN_LITTLE ; + + if (psf->mode != SFM_RDWR || psf->filelength < 44) + { psf->filelength = 0 ; + psf->datalength = 0 ; + psf->dataoffset = 0 ; + psf->sf.frames = 0 ; + } ; + + if (subformat == SF_FORMAT_IMA_ADPCM || subformat == SF_FORMAT_MS_ADPCM) + { blockalign = wav_w64_srate2blocksize (psf->sf.samplerate * psf->sf.channels) ; + framesperblock = -1 ; /* Corrected later. */ + } ; + + psf->str_flags = SF_STR_ALLOW_START | SF_STR_ALLOW_END ; + + /* By default, add the peak chunk to floating point files. Default behaviour + ** can be switched off using sf_command (SFC_SET_PEAK_CHUNK, SF_FALSE). + */ + if (psf->mode == SFM_WRITE && (subformat == SF_FORMAT_FLOAT || subformat == SF_FORMAT_DOUBLE)) + { if ((psf->peak_info = peak_info_calloc (psf->sf.channels)) == NULL) + return SFE_MALLOC_FAILED ; + psf->peak_info->peak_loc = SF_PEAK_START ; + } ; + + psf->write_header = (format == SF_FORMAT_WAV) ? wav_write_header : wavex_write_header ; + } ; + + psf->container_close = wav_close ; + psf->command = wav_command ; + + switch (subformat) + { case SF_FORMAT_PCM_U8 : + case SF_FORMAT_PCM_16 : + case SF_FORMAT_PCM_24 : + case SF_FORMAT_PCM_32 : + error = pcm_init (psf) ; + break ; + + case SF_FORMAT_ULAW : + error = ulaw_init (psf) ; + break ; + + case SF_FORMAT_ALAW : + error = alaw_init (psf) ; + break ; + + /* Lite remove start */ + case SF_FORMAT_FLOAT : + error = float32_init (psf) ; + break ; + + case SF_FORMAT_DOUBLE : + error = double64_init (psf) ; + break ; + + case SF_FORMAT_IMA_ADPCM : + error = wav_w64_ima_init (psf, blockalign, framesperblock) ; + break ; + + case SF_FORMAT_MS_ADPCM : + error = wav_w64_msadpcm_init (psf, blockalign, framesperblock) ; + break ; + + case SF_FORMAT_G721_32 : + error = g72x_init (psf) ; + break ; + /* Lite remove end */ + + case SF_FORMAT_GSM610 : + error = gsm610_init (psf) ; + break ; + + default : return SFE_UNIMPLEMENTED ; + } ; + + if (psf->mode == SFM_WRITE || (psf->mode == SFM_RDWR && psf->filelength == 0)) + return psf->write_header (psf, SF_FALSE) ; + + return error ; +} /* wav_open */ + +/*========================================================================= +** Private functions. +*/ + +static int +wav_read_header (SF_PRIVATE *psf, int *blockalign, int *framesperblock) +{ WAV_FMT wav_fmt ; + FACT_CHUNK fact_chunk ; + unsigned dword = 0, marker, RIFFsize, done = 0 ; + int parsestage = 0, error, format = 0 ; + char *cptr ; + + memset (&wav_fmt, 0, sizeof (wav_fmt)) ; + /* Set position to start of file to begin reading header. */ + psf_binheader_readf (psf, "p", 0) ; + + while (! done) + { psf_binheader_readf (psf, "m", &marker) ; + + switch (marker) + { case RIFF_MARKER : + case RIFX_MARKER : + if (parsestage) + return SFE_WAV_NO_RIFF ; + + parsestage |= HAVE_RIFF ; + + /* RIFX signifies big-endian format for all header and data + ** to prevent lots of code copying here, we'll set the psf->rwf_endian + ** flag once here, and never specify endian-ness for all other header ops + */ + if (marker == RIFF_MARKER) + psf->rwf_endian = SF_ENDIAN_LITTLE ; + else + psf->rwf_endian = SF_ENDIAN_BIG ; + + psf_binheader_readf (psf, "4", &RIFFsize) ; + + if (psf->fileoffset > 0 && psf->filelength > RIFFsize + 8) + { /* Set file length. */ + psf->filelength = RIFFsize + 8 ; + if (marker == RIFF_MARKER) + psf_log_printf (psf, "RIFF : %u\n", RIFFsize) ; + else + psf_log_printf (psf, "RIFX : %u\n", RIFFsize) ; + } + else if (psf->filelength < RIFFsize + 2 * SIGNED_SIZEOF (dword)) + { if (marker == RIFF_MARKER) + psf_log_printf (psf, "RIFF : %u (should be %D)\n", RIFFsize, psf->filelength - 2 * SIGNED_SIZEOF (dword)) ; + else + psf_log_printf (psf, "RIFX : %u (should be %D)\n", RIFFsize, psf->filelength - 2 * SIGNED_SIZEOF (dword)) ; + + RIFFsize = dword ; + } + else + { if (marker == RIFF_MARKER) + psf_log_printf (psf, "RIFF : %u\n", RIFFsize) ; + else + psf_log_printf (psf, "RIFX : %u\n", RIFFsize) ; + } ; + break ; + + case WAVE_MARKER : + if ((parsestage & HAVE_RIFF) != HAVE_RIFF) + return SFE_WAV_NO_WAVE ; + parsestage |= HAVE_WAVE ; + + psf_log_printf (psf, "WAVE\n") ; + break ; + + case fmt_MARKER : + if ((parsestage & (HAVE_RIFF | HAVE_WAVE)) != (HAVE_RIFF | HAVE_WAVE)) + return SFE_WAV_NO_FMT ; + + /* If this file has a SECOND fmt chunk, I don't want to know about it. */ + if (parsestage & HAVE_fmt) + break ; + + parsestage |= HAVE_fmt ; + + psf_binheader_readf (psf, "4", &dword) ; + psf_log_printf (psf, "fmt : %d\n", dword) ; + + if ((error = wav_w64_read_fmt_chunk (psf, &wav_fmt, dword))) + return error ; + + format = wav_fmt.format ; + break ; + + case data_MARKER : + if ((parsestage & (HAVE_RIFF | HAVE_WAVE | HAVE_fmt)) != (HAVE_RIFF | HAVE_WAVE | HAVE_fmt)) + return SFE_WAV_NO_DATA ; + + if (psf->mode == SFM_RDWR && (parsestage & HAVE_other) != 0) + return SFE_RDWR_BAD_HEADER ; + + parsestage |= HAVE_data ; + + psf_binheader_readf (psf, "4", &dword) ; + + psf->datalength = dword ; + psf->dataoffset = psf_ftell (psf) ; + + if (dword == 0 && RIFFsize == 8 && psf->filelength > 44) + { psf_log_printf (psf, "*** Looks like a WAV file which wasn't closed properly. Fixing it.\n") ; + psf->datalength = dword = psf->filelength - psf->dataoffset ; + } ; + + if (psf->datalength > psf->filelength - psf->dataoffset) + { psf_log_printf (psf, "data : %D (should be %D)\n", psf->datalength, psf->filelength - psf->dataoffset) ; + psf->datalength = psf->filelength - psf->dataoffset ; + } + else + psf_log_printf (psf, "data : %D\n", psf->datalength) ; + + /* Only set dataend if there really is data at the end. */ + if (psf->datalength + psf->dataoffset < psf->filelength) + psf->dataend = psf->datalength + psf->dataoffset ; + + if (format == WAVE_FORMAT_MS_ADPCM && psf->datalength % 2) + { psf->datalength ++ ; + psf_log_printf (psf, "*** Data length odd. Increasing it by 1.\n") ; + } ; + + if (! psf->sf.seekable) + break ; + + /* Seek past data and continue reading header. */ + psf_fseek (psf, psf->datalength, SEEK_CUR) ; + + dword = psf_ftell (psf) ; + if (dword != (sf_count_t) (psf->dataoffset + psf->datalength)) + psf_log_printf (psf, "*** psf_fseek past end error ***\n", dword, psf->dataoffset + psf->datalength) ; + break ; + + case fact_MARKER : + if ((parsestage & (HAVE_RIFF | HAVE_WAVE)) != (HAVE_RIFF | HAVE_WAVE)) + return SFE_WAV_BAD_FACT ; + + parsestage |= HAVE_fact ; + + if ((parsestage & HAVE_fmt) != HAVE_fmt) + psf_log_printf (psf, "*** Should have 'fmt ' chunk before 'fact'\n") ; + + psf_binheader_readf (psf, "44", &dword, & (fact_chunk.frames)) ; + + if (dword > SIGNED_SIZEOF (fact_chunk)) + psf_binheader_readf (psf, "j", (int) (dword - SIGNED_SIZEOF (fact_chunk))) ; + + if (dword) + psf_log_printf (psf, "%M : %d\n", marker, dword) ; + else + psf_log_printf (psf, "%M : %d (should not be zero)\n", marker, dword) ; + + psf_log_printf (psf, " frames : %d\n", fact_chunk.frames) ; + break ; + + case PEAK_MARKER : + if ((parsestage & (HAVE_RIFF | HAVE_WAVE | HAVE_fmt)) != (HAVE_RIFF | HAVE_WAVE | HAVE_fmt)) + return SFE_WAV_PEAK_B4_FMT ; + + parsestage |= HAVE_PEAK ; + + psf_binheader_readf (psf, "4", &dword) ; + + psf_log_printf (psf, "%M : %d\n", marker, dword) ; + if (dword != WAV_PEAK_CHUNK_SIZE (psf->sf.channels)) + { psf_binheader_readf (psf, "j", dword) ; + psf_log_printf (psf, "*** File PEAK chunk size doesn't fit with number of channels (%d).\n", psf->sf.channels) ; + return SFE_WAV_BAD_PEAK ; + } ; + + if ((psf->peak_info = peak_info_calloc (psf->sf.channels)) == NULL) + return SFE_MALLOC_FAILED ; + + /* read in rest of PEAK chunk. */ + psf_binheader_readf (psf, "44", & (psf->peak_info->version), & (psf->peak_info->timestamp)) ; + + if (psf->peak_info->version != 1) + psf_log_printf (psf, " version : %d *** (should be version 1)\n", psf->peak_info->version) ; + else + psf_log_printf (psf, " version : %d\n", psf->peak_info->version) ; + + psf_log_printf (psf, " time stamp : %d\n", psf->peak_info->timestamp) ; + psf_log_printf (psf, " Ch Position Value\n") ; + + cptr = psf->u.cbuf ; + for (dword = 0 ; dword < (unsigned) psf->sf.channels ; dword++) + { float value ; + unsigned int position ; + psf_binheader_readf (psf, "f4", &value, &position) ; + psf->peak_info->peaks [dword].value = value ; + psf->peak_info->peaks [dword].position = position ; + + LSF_SNPRINTF (cptr, sizeof (psf->u.cbuf), " %2d %-12ld %g\n", + dword, (long) psf->peak_info->peaks [dword].position, psf->peak_info->peaks [dword].value) ; + cptr [sizeof (psf->u.cbuf) - 1] = 0 ; + psf_log_printf (psf, cptr) ; + } ; + + psf->peak_info->peak_loc = ((parsestage & HAVE_data) == 0) ? SF_PEAK_START : SF_PEAK_END ; + break ; + + case cue_MARKER : + parsestage |= HAVE_other ; + + { unsigned bytesread, cue_count ; + int id, position, chunk_id, chunk_start, block_start, offset ; + + bytesread = psf_binheader_readf (psf, "44", &dword, &cue_count) ; + bytesread -= 4 ; /* Remove bytes for first dword. */ + psf_log_printf (psf, "%M : %u\n", marker, dword) ; + + if (cue_count > 10) + { psf_log_printf (psf, " Count : %d (skipping)\n", cue_count) ; + psf_binheader_readf (psf, "j", cue_count * 24) ; + break ; + } ; + + psf_log_printf (psf, " Count : %d\n", cue_count) ; + + while (cue_count) + { bytesread += psf_binheader_readf (psf, "444444", &id, &position, + &chunk_id, &chunk_start, &block_start, &offset) ; + psf_log_printf (psf, " Cue ID : %2d" + " Pos : %5u Chunk : %M" + " Chk Start : %d Blk Start : %d" + " Offset : %5d\n", + id, position, chunk_id, chunk_start, block_start, offset) ; + cue_count -- ; + } ; + + if (bytesread != dword) + { psf_log_printf (psf, "**** Chunk size weirdness (%d != %d)\n", dword, bytesread) ; + psf_binheader_readf (psf, "j", dword - bytesread) ; + } ; + } ; + break ; + + case smpl_MARKER : + parsestage |= HAVE_other ; + + psf_binheader_readf (psf, "4", &dword) ; + psf_log_printf (psf, "smpl : %u\n", dword) ; + + if ((error = wav_read_smpl_chunk (psf, dword))) + return error ; + break ; + + case acid_MARKER : + parsestage |= HAVE_other ; + + psf_binheader_readf (psf, "4", &dword) ; + psf_log_printf (psf, "acid : %u\n", dword) ; + + if ((error = wav_read_acid_chunk (psf, dword))) + return error ; + break ; + + case INFO_MARKER : + case LIST_MARKER : + parsestage |= HAVE_other ; + + if ((error = wav_subchunk_parse (psf, marker)) != 0) + return error ; + break ; + + case bext_MARKER : + parsestage |= HAVE_other ; + + psf_binheader_readf (psf, "4", &dword) ; + if (dword < WAV_BEXT_CHUNK_SIZE) + psf_log_printf (psf, "bext : %u (should be >= %d)\n", dword, WAV_BEXT_CHUNK_SIZE) ; + else + psf_log_printf (psf, "bext : %u\n", dword) ; + + if ((error = wav_read_bext_chunk (psf, dword))) + return error ; + break ; + + case strc_MARKER : /* Multiple of 32 bytes. */ + + case afsp_MARKER : + case clm_MARKER : + case elmo_MARKER : + case levl_MARKER : + case plst_MARKER : + case DISP_MARKER : + case MEXT_MARKER : + case PAD_MARKER : + parsestage |= HAVE_other ; + + psf_binheader_readf (psf, "4", &dword) ; + psf_log_printf (psf, "%M : %u\n", marker, dword) ; + dword += (dword & 1) ; + psf_binheader_readf (psf, "j", dword) ; + break ; + + default : + parsestage |= HAVE_other ; + if (isprint ((marker >> 24) & 0xFF) && isprint ((marker >> 16) & 0xFF) + && isprint ((marker >> 8) & 0xFF) && isprint (marker & 0xFF)) + { psf_binheader_readf (psf, "4", &dword) ; + psf_log_printf (psf, "*** %M : %d (unknown marker)\n", marker, dword) ; + psf_binheader_readf (psf, "j", dword) ; + break ; + } ; + if (psf_ftell (psf) & 0x03) + { psf_log_printf (psf, " Unknown chunk marker at position %d. Resynching.\n", dword - 4) ; + psf_binheader_readf (psf, "j", -3) ; + break ; + } ; + psf_log_printf (psf, "*** Unknown chunk marker (%X) at position %D. Exiting parser.\n", marker, psf_ftell (psf) - 4) ; + done = SF_TRUE ; + break ; + } ; /* switch (dword) */ + + if (! psf->sf.seekable && (parsestage & HAVE_data)) + break ; + + if (psf_ftell (psf) >= psf->filelength - SIGNED_SIZEOF (dword)) + { psf_log_printf (psf, "End\n") ; + break ; + } ; + } ; /* while (1) */ + + if (! psf->dataoffset) + return SFE_WAV_NO_DATA ; + + /* WAVs can be little or big endian */ + psf->endian = psf->rwf_endian ; + + psf_fseek (psf, psf->dataoffset, SEEK_SET) ; + + if (psf->is_pipe == 0) + { /* + ** Check for 'wvpk' at the start of the DATA section. Not able to + ** handle this. + */ + psf_binheader_readf (psf, "4", &marker) ; + if (marker == wvpk_MARKER || marker == OggS_MARKER) + return SFE_WAV_WVPK_DATA ; + } ; + + /* Seek to start of DATA section. */ + psf_fseek (psf, psf->dataoffset, SEEK_SET) ; + + if (psf->blockwidth) + { if (psf->filelength - psf->dataoffset < psf->datalength) + psf->sf.frames = (psf->filelength - psf->dataoffset) / psf->blockwidth ; + else + psf->sf.frames = psf->datalength / psf->blockwidth ; + } ; + + switch (format) + { case WAVE_FORMAT_EXTENSIBLE : + if (psf->sf.format == (SF_FORMAT_WAVEX | SF_FORMAT_MS_ADPCM)) + { *blockalign = wav_fmt.msadpcm.blockalign ; + *framesperblock = wav_fmt.msadpcm.samplesperblock ; + } ; + break ; + + case WAVE_FORMAT_PCM : + psf->sf.format = SF_FORMAT_WAV | u_bitwidth_to_subformat (psf->bytewidth * 8) ; + break ; + + case WAVE_FORMAT_MULAW : + case IBM_FORMAT_MULAW : + psf->sf.format = (SF_FORMAT_WAV | SF_FORMAT_ULAW) ; + break ; + + case WAVE_FORMAT_ALAW : + case IBM_FORMAT_ALAW : + psf->sf.format = (SF_FORMAT_WAV | SF_FORMAT_ALAW) ; + break ; + + case WAVE_FORMAT_MS_ADPCM : + psf->sf.format = (SF_FORMAT_WAV | SF_FORMAT_MS_ADPCM) ; + *blockalign = wav_fmt.msadpcm.blockalign ; + *framesperblock = wav_fmt.msadpcm.samplesperblock ; + break ; + + case WAVE_FORMAT_IMA_ADPCM : + psf->sf.format = (SF_FORMAT_WAV | SF_FORMAT_IMA_ADPCM) ; + *blockalign = wav_fmt.ima.blockalign ; + *framesperblock = wav_fmt.ima.samplesperblock ; + break ; + + case WAVE_FORMAT_GSM610 : + psf->sf.format = (SF_FORMAT_WAV | SF_FORMAT_GSM610) ; + break ; + + case WAVE_FORMAT_IEEE_FLOAT : + psf->sf.format = SF_FORMAT_WAV ; + psf->sf.format |= (psf->bytewidth == 8) ? SF_FORMAT_DOUBLE : SF_FORMAT_FLOAT ; + break ; + + case WAVE_FORMAT_G721_ADPCM : + psf->sf.format = SF_FORMAT_WAV | SF_FORMAT_G721_32 ; + break ; + + default : return SFE_UNIMPLEMENTED ; + } ; + + /* Only set the format endian-ness if its non-standard big-endian. */ + if (psf->endian == SF_ENDIAN_BIG) + psf->sf.format |= SF_ENDIAN_BIG ; + + return 0 ; +} /* wav_read_header */ + +static int +wav_write_header (SF_PRIVATE *psf, int calc_length) +{ sf_count_t current ; + int fmt_size, k, subformat, add_fact_chunk = SF_FALSE ; + + current = psf_ftell (psf) ; + + if (calc_length) + { psf->filelength = psf_get_filelen (psf) ; + + psf->datalength = psf->filelength - psf->dataoffset ; + + if (psf->dataend) + psf->datalength -= psf->filelength - psf->dataend ; + + if (psf->bytewidth > 0) + psf->sf.frames = psf->datalength / (psf->bytewidth * psf->sf.channels) ; + } ; + + /* Reset the current header length to zero. */ + psf->header [0] = 0 ; + psf->headindex = 0 ; + psf_fseek (psf, 0, SEEK_SET) ; + + /* + ** RIFX signifies big-endian format for all header and data. + ** To prevent lots of code copying here, we'll set the psf->rwf_endian flag + ** once here, and never specify endian-ness for all other header operations. + */ + + /* RIFF/RIFX marker, length, WAVE and 'fmt ' markers. */ + + if (psf->endian == SF_ENDIAN_LITTLE) + psf_binheader_writef (psf, "etm8", RIFF_MARKER, (psf->filelength < 8) ? 8 : psf->filelength - 8) ; + else + psf_binheader_writef (psf, "Etm8", RIFX_MARKER, (psf->filelength < 8) ? 8 : psf->filelength - 8) ; + + /* WAVE and 'fmt ' markers. */ + psf_binheader_writef (psf, "mm", WAVE_MARKER, fmt_MARKER) ; + + subformat = psf->sf.format & SF_FORMAT_SUBMASK ; + + switch (subformat) + { case SF_FORMAT_PCM_U8 : + case SF_FORMAT_PCM_16 : + case SF_FORMAT_PCM_24 : + case SF_FORMAT_PCM_32 : + fmt_size = 2 + 2 + 4 + 4 + 2 + 2 ; + + /* fmt : format, channels, samplerate */ + psf_binheader_writef (psf, "4224", fmt_size, WAVE_FORMAT_PCM, psf->sf.channels, psf->sf.samplerate) ; + /* fmt : bytespersec */ + psf_binheader_writef (psf, "4", psf->sf.samplerate * psf->bytewidth * psf->sf.channels) ; + /* fmt : blockalign, bitwidth */ + psf_binheader_writef (psf, "22", psf->bytewidth * psf->sf.channels, psf->bytewidth * 8) ; + break ; + + case SF_FORMAT_FLOAT : + case SF_FORMAT_DOUBLE : + fmt_size = 2 + 2 + 4 + 4 + 2 + 2 ; + + /* fmt : format, channels, samplerate */ + psf_binheader_writef (psf, "4224", fmt_size, WAVE_FORMAT_IEEE_FLOAT, psf->sf.channels, psf->sf.samplerate) ; + /* fmt : bytespersec */ + psf_binheader_writef (psf, "4", psf->sf.samplerate * psf->bytewidth * psf->sf.channels) ; + /* fmt : blockalign, bitwidth */ + psf_binheader_writef (psf, "22", psf->bytewidth * psf->sf.channels, psf->bytewidth * 8) ; + + add_fact_chunk = SF_TRUE ; + break ; + + case SF_FORMAT_ULAW : + fmt_size = 2 + 2 + 4 + 4 + 2 + 2 ; + + /* fmt : format, channels, samplerate */ + psf_binheader_writef (psf, "4224", fmt_size, WAVE_FORMAT_MULAW, psf->sf.channels, psf->sf.samplerate) ; + /* fmt : bytespersec */ + psf_binheader_writef (psf, "4", psf->sf.samplerate * psf->bytewidth * psf->sf.channels) ; + /* fmt : blockalign, bitwidth */ + psf_binheader_writef (psf, "22", psf->bytewidth * psf->sf.channels, 8) ; + + add_fact_chunk = SF_TRUE ; + break ; + + case SF_FORMAT_ALAW : + fmt_size = 2 + 2 + 4 + 4 + 2 + 2 ; + + /* fmt : format, channels, samplerate */ + psf_binheader_writef (psf, "4224", fmt_size, WAVE_FORMAT_ALAW, psf->sf.channels, psf->sf.samplerate) ; + /* fmt : bytespersec */ + psf_binheader_writef (psf, "4", psf->sf.samplerate * psf->bytewidth * psf->sf.channels) ; + /* fmt : blockalign, bitwidth */ + psf_binheader_writef (psf, "22", psf->bytewidth * psf->sf.channels, 8) ; + + add_fact_chunk = SF_TRUE ; + break ; + + /* Lite remove start */ + case SF_FORMAT_IMA_ADPCM : + { int blockalign, framesperblock, bytespersec ; + + blockalign = wav_w64_srate2blocksize (psf->sf.samplerate * psf->sf.channels) ; + framesperblock = 2 * (blockalign - 4 * psf->sf.channels) / psf->sf.channels + 1 ; + bytespersec = (psf->sf.samplerate * blockalign) / framesperblock ; + + /* fmt chunk. */ + fmt_size = 2 + 2 + 4 + 4 + 2 + 2 + 2 + 2 ; + + /* fmt : size, WAV format type, channels, samplerate, bytespersec */ + psf_binheader_writef (psf, "42244", fmt_size, WAVE_FORMAT_IMA_ADPCM, + psf->sf.channels, psf->sf.samplerate, bytespersec) ; + + /* fmt : blockalign, bitwidth, extrabytes, framesperblock. */ + psf_binheader_writef (psf, "2222", blockalign, 4, 2, framesperblock) ; + } ; + + add_fact_chunk = SF_TRUE ; + break ; + + case SF_FORMAT_MS_ADPCM : + { int blockalign, framesperblock, bytespersec, extrabytes ; + + blockalign = wav_w64_srate2blocksize (psf->sf.samplerate * psf->sf.channels) ; + framesperblock = 2 + 2 * (blockalign - 7 * psf->sf.channels) / psf->sf.channels ; + bytespersec = (psf->sf.samplerate * blockalign) / framesperblock ; + + /* fmt chunk. */ + extrabytes = 2 + 2 + MSADPCM_ADAPT_COEFF_COUNT * (2 + 2) ; + fmt_size = 2 + 2 + 4 + 4 + 2 + 2 + 2 + extrabytes ; + + /* fmt : size, WAV format type, channels. */ + psf_binheader_writef (psf, "422", fmt_size, WAVE_FORMAT_MS_ADPCM, psf->sf.channels) ; + + /* fmt : samplerate, bytespersec. */ + psf_binheader_writef (psf, "44", psf->sf.samplerate, bytespersec) ; + + /* fmt : blockalign, bitwidth, extrabytes, framesperblock. */ + psf_binheader_writef (psf, "22222", blockalign, 4, extrabytes, framesperblock, 7) ; + + msadpcm_write_adapt_coeffs (psf) ; + } ; + + add_fact_chunk = SF_TRUE ; + break ; + + + case SF_FORMAT_G721_32 : + /* fmt chunk. */ + fmt_size = 2 + 2 + 4 + 4 + 2 + 2 + 2 + 2 ; + + /* fmt : size, WAV format type, channels, samplerate, bytespersec */ + psf_binheader_writef (psf, "42244", fmt_size, WAVE_FORMAT_G721_ADPCM, + psf->sf.channels, psf->sf.samplerate, psf->sf.samplerate * psf->sf.channels / 2) ; + + /* fmt : blockalign, bitwidth, extrabytes, auxblocksize. */ + psf_binheader_writef (psf, "2222", 64, 4, 2, 0) ; + + add_fact_chunk = SF_TRUE ; + break ; + + /* Lite remove end */ + + case SF_FORMAT_GSM610 : + { int blockalign, framesperblock, bytespersec ; + + blockalign = WAV_W64_GSM610_BLOCKSIZE ; + framesperblock = WAV_W64_GSM610_SAMPLES ; + bytespersec = (psf->sf.samplerate * blockalign) / framesperblock ; + + /* fmt chunk. */ + fmt_size = 2 + 2 + 4 + 4 + 2 + 2 + 2 + 2 ; + + /* fmt : size, WAV format type, channels. */ + psf_binheader_writef (psf, "422", fmt_size, WAVE_FORMAT_GSM610, psf->sf.channels) ; + + /* fmt : samplerate, bytespersec. */ + psf_binheader_writef (psf, "44", psf->sf.samplerate, bytespersec) ; + + /* fmt : blockalign, bitwidth, extrabytes, framesperblock. */ + psf_binheader_writef (psf, "2222", blockalign, 0, 2, framesperblock) ; + } ; + + add_fact_chunk = SF_TRUE ; + break ; + + default : return SFE_UNIMPLEMENTED ; + } ; + + if (add_fact_chunk) + psf_binheader_writef (psf, "tm48", fact_MARKER, 4, psf->sf.frames) ; + + if (psf->str_flags & SF_STR_LOCATE_START) + wav_write_strings (psf, SF_STR_LOCATE_START) ; + + if (psf->peak_info != NULL && psf->peak_info->peak_loc == SF_PEAK_START) + { psf_binheader_writef (psf, "m4", PEAK_MARKER, WAV_PEAK_CHUNK_SIZE (psf->sf.channels)) ; + psf_binheader_writef (psf, "44", 1, time (NULL)) ; + for (k = 0 ; k < psf->sf.channels ; k++) + psf_binheader_writef (psf, "ft8", (float) psf->peak_info->peaks [k].value, psf->peak_info->peaks [k].position) ; + } ; + + if (psf->broadcast_info != NULL) + wav_write_bext_chunk (psf) ; + + if (psf->instrument != NULL) + { int tmp ; + double dtune = (double) (0x40000000) / 25.0 ; + + psf_binheader_writef (psf, "m4", smpl_MARKER, 9 * 4 + psf->instrument->loop_count * 6 * 4) ; + psf_binheader_writef (psf, "44", 0, 0) ; /* Manufacturer zero is everyone */ + tmp = (int) (1.0e9 / psf->sf.samplerate) ; /* Sample period in nano seconds */ + psf_binheader_writef (psf, "44", tmp, psf->instrument->basenote) ; + tmp = (unsigned int) (psf->instrument->detune * dtune + 0.5) ; + psf_binheader_writef (psf, "4", tmp) ; + psf_binheader_writef (psf, "44", 0, 0) ; /* SMTPE format */ + psf_binheader_writef (psf, "44", psf->instrument->loop_count, 0) ; + + for (tmp = 0 ; tmp < psf->instrument->loop_count ; tmp++) + { int type ; + + type = psf->instrument->loops [tmp].mode ; + type = (type == SF_LOOP_FORWARD ? 0 : type==SF_LOOP_BACKWARD ? 2 : type == SF_LOOP_ALTERNATING ? 1 : 32) ; + + psf_binheader_writef (psf, "44", tmp, type) ; + psf_binheader_writef (psf, "44", psf->instrument->loops [tmp].start, psf->instrument->loops [tmp].end) ; + psf_binheader_writef (psf, "44", 0, psf->instrument->loops [tmp].count) ; + } ; + } ; + + psf_binheader_writef (psf, "tm8", data_MARKER, psf->datalength) ; + psf_fwrite (psf->header, psf->headindex, 1, psf) ; + if (psf->error) + return psf->error ; + + psf->dataoffset = psf->headindex ; + + if (current < psf->dataoffset) + psf_fseek (psf, psf->dataoffset, SEEK_SET) ; + else if (current > 0) + psf_fseek (psf, current, SEEK_SET) ; + + return psf->error ; +} /* wav_write_header */ + + + +static int +wavex_write_header (SF_PRIVATE *psf, int calc_length) +{ sf_count_t current ; + int fmt_size, k, subformat, add_fact_chunk = SF_FALSE ; + + current = psf_ftell (psf) ; + + if (calc_length) + { psf->filelength = psf_get_filelen (psf) ; + + psf->datalength = psf->filelength - psf->dataoffset ; + + if (psf->dataend) + psf->datalength -= psf->filelength - psf->dataend ; + + if (psf->bytewidth > 0) + psf->sf.frames = psf->datalength / (psf->bytewidth * psf->sf.channels) ; + } ; + + + /* Reset the current header length to zero. */ + psf->header [0] = 0 ; + psf->headindex = 0 ; + psf_fseek (psf, 0, SEEK_SET) ; + + /* RIFX signifies big-endian format for all header and data + ** to prevent lots of code copying here, we'll set the psf->rwf_endian + ** flag once here, and never specify endian-ness for all other header ops + */ + + /* RIFF marker, length, WAVE and 'fmt ' markers. */ + + if (psf->endian == SF_ENDIAN_LITTLE) + { if (psf->filelength < 8) + psf_binheader_writef (psf, "tm8", RIFF_MARKER, 8) ; + else + psf_binheader_writef (psf, "tm8", RIFF_MARKER, psf->filelength - 8) ; + } + else + { if (psf->filelength < 8) + psf_binheader_writef (psf, "Etm8", RIFX_MARKER, 8) ; + else + psf_binheader_writef (psf, "Etm8", RIFX_MARKER, psf->filelength - 8) ; + } ; + + /* WAVE and 'fmt ' markers. */ + psf_binheader_writef (psf, "mm", WAVE_MARKER, fmt_MARKER) ; + + subformat = psf->sf.format & SF_FORMAT_SUBMASK ; + + /* initial section (same for all, it appears) */ + switch (subformat) + { case SF_FORMAT_PCM_U8 : + case SF_FORMAT_PCM_16 : + case SF_FORMAT_PCM_24 : + case SF_FORMAT_PCM_32 : + case SF_FORMAT_FLOAT : + case SF_FORMAT_DOUBLE : + case SF_FORMAT_ULAW : + case SF_FORMAT_ALAW : + fmt_size = 2 + 2 + 4 + 4 + 2 + 2 + 2 + 2 + 4 + 4 + 2 + 2 + 8 ; + + /* fmt : format, channels, samplerate */ + psf_binheader_writef (psf, "4224", fmt_size, WAVE_FORMAT_EXTENSIBLE, psf->sf.channels, psf->sf.samplerate) ; + /* fmt : bytespersec */ + psf_binheader_writef (psf, "4", psf->sf.samplerate * psf->bytewidth * psf->sf.channels) ; + /* fmt : blockalign, bitwidth */ + psf_binheader_writef (psf, "22", psf->bytewidth * psf->sf.channels, psf->bytewidth * 8) ; + + /* cbSize 22 is sizeof (WAVEFORMATEXTENSIBLE) - sizeof (WAVEFORMATEX) */ + psf_binheader_writef (psf, "2", 22) ; + + /* wValidBitsPerSample, for our use same as bitwidth as we use it fully */ + psf_binheader_writef (psf, "2", psf->bytewidth * 8) ; + + /* + ** Ok some liberty is taken here to use the most commonly used channel masks + ** instead of "no mapping". If you really want to use "no mapping" for 8 channels and less + ** please don't use wavex. (otherwise we'll have to create a new SF_COMMAND) + */ + switch (psf->sf.channels) + { case 1 : /* center channel mono */ + psf_binheader_writef (psf, "4", 0x4) ; + break ; + + case 2 : /* front left and right */ + psf_binheader_writef (psf, "4", 0x1 | 0x2) ; + break ; + + case 4 : /* Quad */ + psf_binheader_writef (psf, "4", 0x1 | 0x2 | 0x10 | 0x20) ; + break ; + + case 6 : /* 5.1 */ + psf_binheader_writef (psf, "4", 0x1 | 0x2 | 0x4 | 0x8 | 0x10 | 0x20) ; + break ; + + case 8 : /* 7.1 */ + psf_binheader_writef (psf, "4", 0x1 | 0x2 | 0x4 | 0x8 | 0x10 | 0x20 | 0x40 | 0x80) ; + break ; + + default : /* 0 when in doubt , use direct out, ie NO mapping*/ + psf_binheader_writef (psf, "4", 0x0) ; + break ; + } + + break ; + + case SF_FORMAT_MS_ADPCM : /* Todo, GUID exists might have different header as per wav_write_header */ + default : + return SFE_UNIMPLEMENTED ; + } ; + + /* GUID section, different for each */ + + switch (subformat) + { case SF_FORMAT_PCM_U8 : + case SF_FORMAT_PCM_16 : + case SF_FORMAT_PCM_24 : + case SF_FORMAT_PCM_32 : + wavex_write_guid (psf, &MSGUID_SUBTYPE_PCM) ; + break ; + + case SF_FORMAT_FLOAT : + case SF_FORMAT_DOUBLE : + wavex_write_guid (psf, &MSGUID_SUBTYPE_IEEE_FLOAT) ; + add_fact_chunk = SF_TRUE ; + break ; + + case SF_FORMAT_ULAW : + wavex_write_guid (psf, &MSGUID_SUBTYPE_MULAW) ; + add_fact_chunk = SF_TRUE ; + break ; + + case SF_FORMAT_ALAW : + wavex_write_guid (psf, &MSGUID_SUBTYPE_ALAW) ; + add_fact_chunk = SF_TRUE ; + break ; + + case SF_FORMAT_MS_ADPCM : /* todo, GUID exists */ + + default : return SFE_UNIMPLEMENTED ; + } ; + + if (add_fact_chunk) + psf_binheader_writef (psf, "tm48", fact_MARKER, 4, psf->sf.frames) ; + + if (psf->str_flags & SF_STR_LOCATE_START) + wav_write_strings (psf, SF_STR_LOCATE_START) ; + + if (psf->peak_info != NULL && psf->peak_info->peak_loc == SF_PEAK_START) + { psf_binheader_writef (psf, "m4", PEAK_MARKER, WAV_PEAK_CHUNK_SIZE (psf->sf.channels)) ; + psf_binheader_writef (psf, "44", 1, time (NULL)) ; + for (k = 0 ; k < psf->sf.channels ; k++) + psf_binheader_writef (psf, "ft8", (float) psf->peak_info->peaks [k].value, psf->peak_info->peaks [k].position) ; + } ; + + psf_binheader_writef (psf, "tm8", data_MARKER, psf->datalength) ; + psf_fwrite (psf->header, psf->headindex, 1, psf) ; + if (psf->error) + return psf->error ; + + psf->dataoffset = psf->headindex ; + + if (current < psf->dataoffset) + psf_fseek (psf, psf->dataoffset, SEEK_SET) ; + else if (current > 0) + psf_fseek (psf, current, SEEK_SET) ; + + return psf->error ; +} /* wavex_write_header */ + + + +static int +wav_write_tailer (SF_PRIVATE *psf) +{ int k ; + + /* Reset the current header buffer length to zero. */ + psf->header [0] = 0 ; + psf->headindex = 0 ; + + psf->dataend = psf_fseek (psf, 0, SEEK_END) ; + + /* Add a PEAK chunk if requested. */ + if (psf->peak_info != NULL && psf->peak_info->peak_loc == SF_PEAK_END) + { psf_binheader_writef (psf, "m4", PEAK_MARKER, WAV_PEAK_CHUNK_SIZE (psf->sf.channels)) ; + psf_binheader_writef (psf, "44", 1, time (NULL)) ; + for (k = 0 ; k < psf->sf.channels ; k++) + psf_binheader_writef (psf, "f4", psf->peak_info->peaks [k].value, psf->peak_info->peaks [k].position) ; + } ; + + if (psf->str_flags & SF_STR_LOCATE_END) + wav_write_strings (psf, SF_STR_LOCATE_END) ; + + /* Write the tailer. */ + if (psf->headindex > 0) + psf_fwrite (psf->header, psf->headindex, 1, psf) ; + + return 0 ; +} /* wav_write_tailer */ + +static void +wav_write_strings (SF_PRIVATE *psf, int location) +{ int k, prev_head_index, saved_head_index ; + + prev_head_index = psf->headindex + 4 ; + + psf_binheader_writef (psf, "m4m", LIST_MARKER, 0xBADBAD, INFO_MARKER) ; + + for (k = 0 ; k < SF_MAX_STRINGS ; k++) + { if (psf->strings [k].type == 0) + break ; + if (psf->strings [k].flags != location) + continue ; + + switch (psf->strings [k].type) + { case SF_STR_SOFTWARE : + psf_binheader_writef (psf, "ms", ISFT_MARKER, psf->strings [k].str) ; + break ; + + case SF_STR_TITLE : + psf_binheader_writef (psf, "ms", INAM_MARKER, psf->strings [k].str) ; + break ; + + case SF_STR_COPYRIGHT : + psf_binheader_writef (psf, "ms", ICOP_MARKER, psf->strings [k].str) ; + break ; + + case SF_STR_ARTIST : + psf_binheader_writef (psf, "ms", IART_MARKER, psf->strings [k].str) ; + break ; + + case SF_STR_COMMENT : + psf_binheader_writef (psf, "ms", ICMT_MARKER, psf->strings [k].str) ; + break ; + + case SF_STR_DATE : + psf_binheader_writef (psf, "ms", ICRD_MARKER, psf->strings [k].str) ; + break ; + } ; + } ; + + saved_head_index = psf->headindex ; + psf->headindex = prev_head_index ; + psf_binheader_writef (psf, "4", saved_head_index - prev_head_index - 4) ; + psf->headindex = saved_head_index ; + +} /* wav_write_strings */ + +static int +wav_close (SF_PRIVATE *psf) +{ + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { wav_write_tailer (psf) ; + + psf->write_header (psf, SF_TRUE) ; + } ; + + return 0 ; +} /* wav_close */ + +static int +wav_command (SF_PRIVATE *psf, int command, void *data, int datasize) +{ + /* Avoid compiler warnings. */ + psf = psf ; + data = data ; + datasize = datasize ; + + switch (command) + { default : break ; + } ; + + return 0 ; +} /* wav_command */ + +static int +wav_subchunk_parse (SF_PRIVATE *psf, int chunk) +{ sf_count_t current_pos ; + char *cptr ; + int dword, bytesread, length ; + + current_pos = psf_fseek (psf, 0, SEEK_CUR) ; + + bytesread = psf_binheader_readf (psf, "4", &length) ; + + if (length <= 8) + { /* This case is for broken files generated by PEAK. */ + psf_log_printf (psf, "%M : %d (weird length)\n", chunk, length) ; + psf_binheader_readf (psf, "mj", &chunk, length - 4) ; + psf_log_printf (psf, " %M\n", chunk) ; + return 0 ; + } ; + + if (psf->headindex + length > SIGNED_SIZEOF (psf->header)) + { psf_log_printf (psf, "%M : %d (too long)\n", chunk, length) ; + psf_binheader_readf (psf, "j", length) ; + return 0 ; + } ; + + if (current_pos + length > psf->filelength) + { psf_log_printf (psf, "%M : %d (should be %d)\n", chunk, length, (int) (psf->filelength - current_pos)) ; + length = psf->filelength - current_pos ; + } + else + psf_log_printf (psf, "%M : %d\n", chunk, length) ; + + while (bytesread < length) + { bytesread += psf_binheader_readf (psf, "m", &chunk) ; + + switch (chunk) + { case adtl_MARKER : + case INFO_MARKER : + /* These markers don't contain anything. */ + psf_log_printf (psf, " %M\n", chunk) ; + break ; + + case data_MARKER: + psf_log_printf (psf, " %M inside a LIST block??? Backing out.\n", chunk) ; + /* Jump back four bytes and return to caller. */ + psf_binheader_readf (psf, "j", -4) ; + return 0 ; + + case ISFT_MARKER : + case ICOP_MARKER : + case IARL_MARKER : + case IART_MARKER : + case ICMT_MARKER : + case ICRD_MARKER : + case IENG_MARKER : + + case INAM_MARKER : + case IPRD_MARKER : + case ISBJ_MARKER : + case ISRC_MARKER : + bytesread += psf_binheader_readf (psf, "4", &dword) ; + dword += (dword & 1) ; + if (dword < 0 || dword > SIGNED_SIZEOF (psf->u.cbuf)) + { psf_log_printf (psf, " *** %M : %d (too big)\n", chunk, dword) ; + psf_binheader_readf (psf, "j", dword) ; + break ; + } ; + + cptr = psf->u.cbuf ; + psf_binheader_readf (psf, "b", cptr, dword) ; + bytesread += dword ; + cptr [dword - 1] = 0 ; + psf_log_printf (psf, " %M : %s\n", chunk, cptr) ; + break ; + + case labl_MARKER : + { int mark_id ; + + bytesread += psf_binheader_readf (psf, "44", &dword, &mark_id) ; + dword -= 4 ; + dword += (dword & 1) ; + if (dword < 1 || dword > SIGNED_SIZEOF (psf->u.cbuf)) + { psf_log_printf (psf, " *** %M : %d (too big)\n", chunk, dword) ; + psf_binheader_readf (psf, "j", dword) ; + break ; + } ; + + cptr = psf->u.cbuf ; + psf_binheader_readf (psf, "b", cptr, dword) ; + bytesread += dword ; + cptr [dword - 1] = 0 ; + psf_log_printf (psf, " %M : %d : %s\n", chunk, mark_id, cptr) ; + } ; + break ; + + + case DISP_MARKER : + case ltxt_MARKER : + case note_MARKER : + bytesread += psf_binheader_readf (psf, "4", &dword) ; + dword += (dword & 1) ; + psf_binheader_readf (psf, "j", dword) ; + bytesread += dword ; + psf_log_printf (psf, " %M : %d\n", chunk, dword) ; + break ; + + default : + psf_binheader_readf (psf, "4", &dword) ; + bytesread += sizeof (dword) ; + dword += (dword & 1) ; + psf_binheader_readf (psf, "j", dword) ; + bytesread += dword ; + psf_log_printf (psf, " *** %M : %d\n", chunk, dword) ; + if (dword > length) + return 0 ; + break ; + } ; + + switch (chunk) + { case ISFT_MARKER : + psf_store_string (psf, SF_STR_SOFTWARE, psf->u.cbuf) ; + break ; + case ICOP_MARKER : + psf_store_string (psf, SF_STR_COPYRIGHT, psf->u.cbuf) ; + break ; + case INAM_MARKER : + psf_store_string (psf, SF_STR_TITLE, psf->u.cbuf) ; + break ; + case IART_MARKER : + psf_store_string (psf, SF_STR_ARTIST, psf->u.cbuf) ; + break ; + case ICMT_MARKER : + psf_store_string (psf, SF_STR_COMMENT, psf->u.cbuf) ; + break ; + case ICRD_MARKER : + psf_store_string (psf, SF_STR_DATE, psf->u.cbuf) ; + break ; + } ; + } ; + + current_pos = psf_fseek (psf, 0, SEEK_CUR) - current_pos ; + + if (current_pos - 4 != length) + psf_log_printf (psf, "**** Bad chunk length %d sbould be %D\n", length, current_pos - 4) ; + + return 0 ; +} /* wav_subchunk_parse */ + +static int +wav_read_smpl_chunk (SF_PRIVATE *psf, unsigned int chunklen) +{ unsigned int bytesread = 0, dword, sampler_data, loop_count ; + unsigned int note, start, end, type = -1, count ; + int j, k ; + + chunklen += (chunklen & 1) ; + + bytesread += psf_binheader_readf (psf, "4", &dword) ; + psf_log_printf (psf, " Manufacturer : %X\n", dword) ; + + bytesread += psf_binheader_readf (psf, "4", &dword) ; + psf_log_printf (psf, " Product : %u\n", dword) ; + + bytesread += psf_binheader_readf (psf, "4", &dword) ; + psf_log_printf (psf, " Period : %u nsec\n", dword) ; + + bytesread += psf_binheader_readf (psf, "4", ¬e) ; + psf_log_printf (psf, " Midi Note : %u\n", note) ; + + bytesread += psf_binheader_readf (psf, "4", &dword) ; + if (dword != 0) + { LSF_SNPRINTF (psf->u.cbuf, sizeof (psf->u.cbuf), "%f", + (1.0 * 0x80000000) / ((unsigned int) dword)) ; + psf_log_printf (psf, " Pitch Fract. : %s\n", psf->u.cbuf) ; + } + else + psf_log_printf (psf, " Pitch Fract. : 0\n") ; + + bytesread += psf_binheader_readf (psf, "4", &dword) ; + psf_log_printf (psf, " SMPTE Format : %u\n", dword) ; + + bytesread += psf_binheader_readf (psf, "4", &dword) ; + LSF_SNPRINTF (psf->u.cbuf, sizeof (psf->u.cbuf), "%02d:%02d:%02d %02d", + (dword >> 24) & 0x7F, (dword >> 16) & 0x7F, (dword >> 8) & 0x7F, dword & 0x7F) ; + psf_log_printf (psf, " SMPTE Offset : %s\n", psf->u.cbuf) ; + + bytesread += psf_binheader_readf (psf, "4", &loop_count) ; + psf_log_printf (psf, " Loop Count : %u\n", loop_count) ; + + /* Sampler Data holds the number of data bytes after the CUE chunks which + ** is not actually CUE data. Display value after CUE data. + */ + bytesread += psf_binheader_readf (psf, "4", &sampler_data) ; + + if ((psf->instrument = psf_instrument_alloc ()) == NULL) + return SFE_MALLOC_FAILED ; + + psf->instrument->loop_count = loop_count ; + + for (j = 0 ; loop_count > 0 && chunklen - bytesread >= 24 ; j ++) + { bytesread += psf_binheader_readf (psf, "4", &dword) ; + psf_log_printf (psf, " Cue ID : %2u", dword) ; + + bytesread += psf_binheader_readf (psf, "4", &type) ; + psf_log_printf (psf, " Type : %2u", type) ; + + bytesread += psf_binheader_readf (psf, "4", &start) ; + psf_log_printf (psf, " Start : %5u", start) ; + + bytesread += psf_binheader_readf (psf, "4", &end) ; + psf_log_printf (psf, " End : %5u", end) ; + + bytesread += psf_binheader_readf (psf, "4", &dword) ; + psf_log_printf (psf, " Fraction : %5u", dword) ; + + bytesread += psf_binheader_readf (psf, "4", &count) ; + psf_log_printf (psf, " Count : %5u\n", count) ; + + if (j < ARRAY_LEN (psf->instrument->loops)) + { psf->instrument->loops [j].start = start ; + psf->instrument->loops [j].end = end ; + psf->instrument->loops [j].count = count ; + + switch (type) + { case 0 : + psf->instrument->loops [j].mode = SF_LOOP_FORWARD ; + break ; + case 1 : + psf->instrument->loops [j].mode = SF_LOOP_ALTERNATING ; + break ; + case 2 : + psf->instrument->loops [j].mode = SF_LOOP_BACKWARD ; + break ; + default: + psf->instrument->loops [j].mode = SF_LOOP_NONE ; + break ; + } ; + } ; + + loop_count -- ; + } ; + + if (chunklen - bytesread == 0) + { if (sampler_data != 0) + psf_log_printf (psf, " Sampler Data : %u (should be 0)\n", sampler_data) ; + else + psf_log_printf (psf, " Sampler Data : %u\n", sampler_data) ; + } + else + { if (sampler_data != chunklen - bytesread) + { psf_log_printf (psf, " Sampler Data : %u (should have been %u)\n", sampler_data, chunklen - bytesread) ; + sampler_data = chunklen - bytesread ; + } + else + psf_log_printf (psf, " Sampler Data : %u\n", sampler_data) ; + + psf_log_printf (psf, " ") ; + for (k = 0 ; k < (int) sampler_data ; k++) + { char ch ; + + if (k > 0 && (k % 20) == 0) + psf_log_printf (psf, "\n ") ; + + bytesread += psf_binheader_readf (psf, "1", &ch) ; + psf_log_printf (psf, "%02X ", ch & 0xFF) ; + } ; + + psf_log_printf (psf, "\n") ; + } ; + + psf->instrument->basenote = note ; + psf->instrument->gain = 1 ; + psf->instrument->velocity_lo = psf->instrument->key_lo = 0 ; + psf->instrument->velocity_hi = psf->instrument->key_hi = 127 ; + + return 0 ; +} /* wav_read_smpl_chunk */ + +/* +** The acid chunk goes a little something like this: +** +** 4 bytes 'acid' +** 4 bytes (int) length of chunk starting at next byte +** +** 4 bytes (int) type of file: +** this appears to be a bit mask,however some combinations +** are probably impossible and/or qualified as "errors" +** +** 0x01 On: One Shot Off: Loop +** 0x02 On: Root note is Set Off: No root +** 0x04 On: Stretch is On, Off: Strech is OFF +** 0x08 On: Disk Based Off: Ram based +** 0x10 On: ?????????? Off: ????????? (Acidizer puts that ON) +** +** 2 bytes (short) root note +** if type 0x10 is OFF : [C,C#,(...),B] -> [0x30 to 0x3B] +** if type 0x10 is ON : [C,C#,(...),B] -> [0x3C to 0x47] +** (both types fit on same MIDI pitch albeit different octaves, so who cares) +** +** 2 bytes (short) ??? always set to 0x8000 +** 4 bytes (float) ??? seems to be always 0 +** 4 bytes (int) number of beats +** 2 bytes (short) meter denominator //always 4 in SF/ACID +** 2 bytes (short) meter numerator //always 4 in SF/ACID +** //are we sure about the order?? usually its num/denom +** 4 bytes (float) tempo +** +*/ + +static int +wav_read_acid_chunk (SF_PRIVATE *psf, unsigned int chunklen) +{ unsigned int bytesread = 0 ; + int beats, flags ; + short rootnote, q1, meter_denom, meter_numer ; + float q2, tempo ; + + chunklen += (chunklen & 1) ; + + bytesread += psf_binheader_readf (psf, "422f", &flags, &rootnote, &q1, &q2) ; + + LSF_SNPRINTF (psf->u.cbuf, sizeof (psf->u.cbuf), "%f", q2) ; + + psf_log_printf (psf, " Flags : 0x%04x (%s,%s,%s,%s,%s)\n", flags, + (flags & 0x01) ? "OneShot" : "Loop", + (flags & 0x02) ? "RootNoteValid" : "RootNoteInvalid", + (flags & 0x04) ? "StretchOn" : "StretchOff", + (flags & 0x08) ? "DiskBased" : "RAMBased", + (flags & 0x10) ? "??On" : "??Off") ; + + psf_log_printf (psf, " Root note : 0x%x\n ???? : 0x%04x\n ???? : %s\n", + rootnote, q1, psf->u.cbuf) ; + + bytesread += psf_binheader_readf (psf, "422f", &beats, &meter_denom, &meter_numer, &tempo) ; + LSF_SNPRINTF (psf->u.cbuf, sizeof (psf->u.cbuf), "%f", tempo) ; + psf_log_printf (psf, " Beats : %d\n Meter : %d/%d\n Tempo : %s\n", + beats, meter_numer, meter_denom, psf->u.cbuf) ; + + psf_binheader_readf (psf, "j", chunklen - bytesread) ; + + if ((psf->loop_info = calloc (1, sizeof (SF_LOOP_INFO))) == NULL) + return SFE_MALLOC_FAILED ; + + psf->loop_info->time_sig_num = meter_numer ; + psf->loop_info->time_sig_den = meter_denom ; + psf->loop_info->loop_mode = (flags & 0x01) ? SF_LOOP_NONE : SF_LOOP_FORWARD ; + psf->loop_info->num_beats = beats ; + psf->loop_info->bpm = tempo ; + psf->loop_info->root_key = (flags & 0x02) ? rootnote : -1 ; + + return 0 ; +} /* wav_read_acid_chunk */ + +int +wav_read_bext_chunk (SF_PRIVATE *psf, unsigned int chunksize) +{ + SF_BROADCAST_INFO* b ; + + if ((psf->broadcast_info = calloc (1, sizeof (SF_BROADCAST_INFO))) == NULL) + { psf->error = SFE_MALLOC_FAILED ; + return -1 ; + } ; + + b = psf->broadcast_info ; + + psf_binheader_readf (psf, "b", b->description, sizeof (b->description)) ; + psf_binheader_readf (psf, "b", b->originator, sizeof (b->originator)) ; + psf_binheader_readf (psf, "b", b->originator_reference, sizeof (b->originator_reference)) ; + psf_binheader_readf (psf, "b", b->origination_date, sizeof (b->origination_date)) ; + psf_binheader_readf (psf, "b", b->origination_time, sizeof (b->origination_time)) ; + psf_binheader_readf (psf, "442", &b->time_reference_low, &b->time_reference_high, &b->version) ; + psf_binheader_readf (psf, "bj", &b->umid, sizeof (b->umid), 190) ; + + if (chunksize > WAV_BEXT_CHUNK_SIZE) + { /* File has coding history data. */ + + b->coding_history_size = chunksize - WAV_BEXT_CHUNK_SIZE ; + + if (b->coding_history_size > SIGNED_SIZEOF (b->coding_history)) + { free (psf->broadcast_info) ; + psf->broadcast_info = NULL ; + psf->error = SFE_MALLOC_FAILED ; + return -1 ; + } ; + + /* We do not parse the coding history */ + psf_binheader_readf (psf, "b", b->coding_history, b->coding_history_size) ; + b->coding_history [sizeof (b->coding_history) - 1] = 0 ; + } ; + + return 0 ; +} /* wav_read_bext_chunk */ + +static int +wav_write_bext_chunk (SF_PRIVATE *psf) +{ SF_BROADCAST_INFO *b ; + + if ((b = psf->broadcast_info) == NULL) + return -1 ; + + psf_binheader_writef (psf, "m4", bext_MARKER, WAV_BEXT_CHUNK_SIZE + b->coding_history_size) ; + + /* + ** Note that it is very important the the field widths of the SF_BROADCAST_INFO + ** struct match those for the bext chunk fields. + */ + + psf_binheader_writef (psf, "b", b->description, sizeof (b->description)) ; + psf_binheader_writef (psf, "b", b->originator, sizeof (b->originator)) ; + psf_binheader_writef (psf, "b", b->originator_reference, sizeof (b->originator_reference)) ; + psf_binheader_writef (psf, "b", b->origination_date, sizeof (b->origination_date)) ; + psf_binheader_writef (psf, "b", b->origination_time, sizeof (b->origination_time)) ; + psf_binheader_writef (psf, "442", b->time_reference_low, b->time_reference_high, b->version) ; + psf_binheader_writef (psf, "b", b->umid, sizeof (b->umid)) ; + psf_binheader_writef (psf, "z", make_size_t (190)) ; + + if (b->coding_history_size > 0) + psf_binheader_writef (psf, "b", b->coding_history, b->coding_history_size) ; + + return 0 ; +} /* wav_write_bext_chunk */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 9c551689-a1d8-4905-9f56-26a204374f18 +*/ diff --git a/libs/libsndfile/src/wav_w64.c b/libs/libsndfile/src/wav_w64.c new file mode 100644 index 0000000000..85cb1323ec --- /dev/null +++ b/libs/libsndfile/src/wav_w64.c @@ -0,0 +1,494 @@ +/* +** Copyright (C) 1999-2005 Erik de Castro Lopo +** Copyright (C) 2004-2005 David Viens +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" +#include "wav_w64.h" + +/* Known WAVEFORMATEXTENSIBLE GUIDS. */ +static const EXT_SUBFORMAT MSGUID_SUBTYPE_PCM = +{ 0x00000001, 0x0000, 0x0010, { 0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71 } +} ; + +static const EXT_SUBFORMAT MSGUID_SUBTYPE_MS_ADPCM = +{ 0x00000002, 0x0000, 0x0010, { 0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71 } +} ; + +static const EXT_SUBFORMAT MSGUID_SUBTYPE_IEEE_FLOAT = +{ 0x00000003, 0x0000, 0x0010, { 0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71 } +} ; + +static const EXT_SUBFORMAT MSGUID_SUBTYPE_ALAW = +{ 0x00000006, 0x0000, 0x0010, { 0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71 } +} ; + +static const EXT_SUBFORMAT MSGUID_SUBTYPE_MULAW = +{ 0x00000007, 0x0000, 0x0010, { 0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71 } +} ; + +/* +** the next two are from +** http://dream.cs.bath.ac.uk/researchdev/wave-ex/bformat.html +*/ + +static const EXT_SUBFORMAT MSGUID_SUBTYPE_AMBISONIC_B_FORMAT_PCM = +{ 0x00000001, 0x0721, 0x11d3, { 0x86, 0x44, 0xC8, 0xC1, 0xCA, 0x00, 0x00, 0x00 } +} ; + +static const EXT_SUBFORMAT MSGUID_SUBTYPE_AMBISONIC_B_FORMAT_IEEE_FLOAT = +{ 0x00000003, 0x0721, 0x11d3, { 0x86, 0x44, 0xC8, 0xC1, 0xCA, 0x00, 0x00, 0x00 } +} ; + + +#if 0 +/* maybe interesting one day to read the following through sf_read_raw */ +/* http://www.bath.ac.uk/~masrwd/pvocex/pvocex.html */ +static const EXT_SUBFORMAT MSGUID_SUBTYPE_PVOCEX = +{ 0x8312B9C2, 0x2E6E, 0x11d4, { 0xA8, 0x24, 0xDE, 0x5B, 0x96, 0xC3, 0xAB, 0x21 } +} ; +#endif + +/*------------------------------------------------------------------------------ + * Private static functions. + */ + +static int +wavex_write_guid_equal (const EXT_SUBFORMAT * first, const EXT_SUBFORMAT * second) +{ return !memcmp (first, second, sizeof (EXT_SUBFORMAT)) ; +} /* wavex_write_guid_equal */ + + + +int +wav_w64_read_fmt_chunk (SF_PRIVATE *psf, WAV_FMT *wav_fmt, int structsize) +{ int bytesread, k, bytespersec = 0 ; + + memset (wav_fmt, 0, sizeof (WAV_FMT)) ; + + if (structsize < 16) + return SFE_WAV_FMT_SHORT ; + + /* assume psf->rwf_endian is already properly set */ + + /* Read the minimal WAV file header here. */ + bytesread = + psf_binheader_readf (psf, "224422", &(wav_fmt->format), &(wav_fmt->min.channels), + &(wav_fmt->min.samplerate), &(wav_fmt->min.bytespersec), + &(wav_fmt->min.blockalign), &(wav_fmt->min.bitwidth)) ; + + psf_log_printf (psf, " Format : 0x%X => %s\n", wav_fmt->format, wav_w64_format_str (wav_fmt->format)) ; + psf_log_printf (psf, " Channels : %d\n", wav_fmt->min.channels) ; + psf_log_printf (psf, " Sample Rate : %d\n", wav_fmt->min.samplerate) ; + psf_log_printf (psf, " Block Align : %d\n", wav_fmt->min.blockalign) ; + + if (wav_fmt->format == WAVE_FORMAT_PCM && wav_fmt->min.bitwidth == 24 && + wav_fmt->min.blockalign == 4 * wav_fmt->min.channels) + { + psf_log_printf (psf, "\nInvalid file generated by Syntrillium's Cooledit!\n" + "Treating as WAVE_FORMAT_IEEE_FLOAT 32 bit floating point file.\n\n") ; + psf_log_printf (psf, " Bit Width : 24 (should be 32)\n") ; + wav_fmt->min.bitwidth = 32 ; + wav_fmt->format = WAVE_FORMAT_IEEE_FLOAT ; + } + else if (wav_fmt->format != WAVE_FORMAT_GSM610 && wav_fmt->min.bitwidth == 0) + psf_log_printf (psf, " Bit Width : %d (should not be 0)\n", wav_fmt->min.bitwidth) ; + else if (wav_fmt->format == WAVE_FORMAT_GSM610 && wav_fmt->min.bitwidth != 0) + psf_log_printf (psf, " Bit Width : %d (should be 0)\n", wav_fmt->min.bitwidth) ; + else + psf_log_printf (psf, " Bit Width : %d\n", wav_fmt->min.bitwidth) ; + + psf->sf.samplerate = wav_fmt->min.samplerate ; + psf->sf.frames = 0 ; /* Correct this when reading data chunk. */ + psf->sf.channels = wav_fmt->min.channels ; + + switch (wav_fmt->format) + { case WAVE_FORMAT_PCM : + case WAVE_FORMAT_IEEE_FLOAT : + bytespersec = wav_fmt->min.samplerate * wav_fmt->min.blockalign ; + if (wav_fmt->min.bytespersec != (unsigned) bytespersec) + psf_log_printf (psf, " Bytes/sec : %d (should be %d)\n", wav_fmt->min.bytespersec, bytespersec) ; + else + psf_log_printf (psf, " Bytes/sec : %d\n", wav_fmt->min.bytespersec) ; + + psf->bytewidth = BITWIDTH2BYTES (wav_fmt->min.bitwidth) ; + break ; + + case WAVE_FORMAT_ALAW : + case WAVE_FORMAT_MULAW : + if (wav_fmt->min.bytespersec / wav_fmt->min.blockalign != wav_fmt->min.samplerate) + psf_log_printf (psf, " Bytes/sec : %d (should be %d)\n", wav_fmt->min.bytespersec, wav_fmt->min.samplerate * wav_fmt->min.blockalign) ; + else + psf_log_printf (psf, " Bytes/sec : %d\n", wav_fmt->min.bytespersec) ; + + psf->bytewidth = 1 ; + if (structsize >= 18) + { bytesread += psf_binheader_readf (psf, "2", &(wav_fmt->size20.extrabytes)) ; + psf_log_printf (psf, " Extra Bytes : %d\n", wav_fmt->size20.extrabytes) ; + } ; + break ; + + case WAVE_FORMAT_IMA_ADPCM : + if (wav_fmt->min.bitwidth != 4) + return SFE_WAV_ADPCM_NOT4BIT ; + if (wav_fmt->min.channels < 1 || wav_fmt->min.channels > 2) + return SFE_WAV_ADPCM_CHANNELS ; + + bytesread += + psf_binheader_readf (psf, "22", &(wav_fmt->ima.extrabytes), &(wav_fmt->ima.samplesperblock)) ; + + bytespersec = (wav_fmt->ima.samplerate * wav_fmt->ima.blockalign) / wav_fmt->ima.samplesperblock ; + if (wav_fmt->ima.bytespersec != (unsigned) bytespersec) + psf_log_printf (psf, " Bytes/sec : %d (should be %d)\n", wav_fmt->ima.bytespersec, bytespersec) ; + else + psf_log_printf (psf, " Bytes/sec : %d\n", wav_fmt->ima.bytespersec) ; + + psf->bytewidth = 2 ; + psf_log_printf (psf, " Extra Bytes : %d\n", wav_fmt->ima.extrabytes) ; + psf_log_printf (psf, " Samples/Block : %d\n", wav_fmt->ima.samplesperblock) ; + break ; + + case WAVE_FORMAT_MS_ADPCM : + if (wav_fmt->msadpcm.bitwidth != 4) + return SFE_WAV_ADPCM_NOT4BIT ; + if (wav_fmt->msadpcm.channels < 1 || wav_fmt->msadpcm.channels > 2) + return SFE_WAV_ADPCM_CHANNELS ; + + bytesread += + psf_binheader_readf (psf, "222", &(wav_fmt->msadpcm.extrabytes), + &(wav_fmt->msadpcm.samplesperblock), &(wav_fmt->msadpcm.numcoeffs)) ; + + bytespersec = (wav_fmt->min.samplerate * wav_fmt->min.blockalign) / wav_fmt->msadpcm.samplesperblock ; + if (wav_fmt->min.bytespersec == (unsigned) bytespersec) + psf_log_printf (psf, " Bytes/sec : %d\n", wav_fmt->min.bytespersec) ; + else if (wav_fmt->min.bytespersec == (wav_fmt->min.samplerate / wav_fmt->msadpcm.samplesperblock) * wav_fmt->min.blockalign) + psf_log_printf (psf, " Bytes/sec : %d (should be %d (MS BUG!))\n", wav_fmt->min.bytespersec, bytespersec) ; + else + psf_log_printf (psf, " Bytes/sec : %d (should be %d)\n", wav_fmt->min.bytespersec, bytespersec) ; + + + psf->bytewidth = 2 ; + psf_log_printf (psf, " Extra Bytes : %d\n", wav_fmt->msadpcm.extrabytes) ; + psf_log_printf (psf, " Samples/Block : %d\n", wav_fmt->msadpcm.samplesperblock) ; + if (wav_fmt->msadpcm.numcoeffs > SIGNED_SIZEOF (MS_ADPCM_WAV_FMT) / SIGNED_SIZEOF (int)) + { psf_log_printf (psf, " No. of Coeffs : %d ****\n", wav_fmt->msadpcm.numcoeffs) ; + wav_fmt->msadpcm.numcoeffs = SIGNED_SIZEOF (MS_ADPCM_WAV_FMT) / SIGNED_SIZEOF (int) ; + } + else + psf_log_printf (psf, " No. of Coeffs : %d\n", wav_fmt->msadpcm.numcoeffs) ; + + psf_log_printf (psf, " Index Coeffs1 Coeffs2\n") ; + for (k = 0 ; k < wav_fmt->msadpcm.numcoeffs ; k++) + { bytesread += + psf_binheader_readf (psf, "22", &(wav_fmt->msadpcm.coeffs [k].coeff1), &(wav_fmt->msadpcm.coeffs [k].coeff2)) ; + LSF_SNPRINTF (psf->u.cbuf, sizeof (psf->u.cbuf), " %2d %7d %7d\n", k, wav_fmt->msadpcm.coeffs [k].coeff1, wav_fmt->msadpcm.coeffs [k].coeff2) ; + psf_log_printf (psf, psf->u.cbuf) ; + } ; + break ; + + case WAVE_FORMAT_GSM610 : + if (wav_fmt->gsm610.channels != 1 || wav_fmt->gsm610.blockalign != 65) + return SFE_WAV_GSM610_FORMAT ; + + bytesread += + psf_binheader_readf (psf, "22", &(wav_fmt->gsm610.extrabytes), &(wav_fmt->gsm610.samplesperblock)) ; + + if (wav_fmt->gsm610.samplesperblock != 320) + return SFE_WAV_GSM610_FORMAT ; + + bytespersec = (wav_fmt->gsm610.samplerate * wav_fmt->gsm610.blockalign) / wav_fmt->gsm610.samplesperblock ; + if (wav_fmt->gsm610.bytespersec != (unsigned) bytespersec) + psf_log_printf (psf, " Bytes/sec : %d (should be %d)\n", wav_fmt->gsm610.bytespersec, bytespersec) ; + else + psf_log_printf (psf, " Bytes/sec : %d\n", wav_fmt->gsm610.bytespersec) ; + + psf->bytewidth = 2 ; + psf_log_printf (psf, " Extra Bytes : %d\n", wav_fmt->gsm610.extrabytes) ; + psf_log_printf (psf, " Samples/Block : %d\n", wav_fmt->gsm610.samplesperblock) ; + break ; + + case WAVE_FORMAT_EXTENSIBLE : + if (wav_fmt->ext.bytespersec / wav_fmt->ext.blockalign != wav_fmt->ext.samplerate) + psf_log_printf (psf, " Bytes/sec : %d (should be %d)\n", wav_fmt->ext.bytespersec, wav_fmt->ext.samplerate * wav_fmt->ext.blockalign) ; + else + psf_log_printf (psf, " Bytes/sec : %d\n", wav_fmt->ext.bytespersec) ; + + bytesread += + psf_binheader_readf (psf, "224", &(wav_fmt->ext.extrabytes), &(wav_fmt->ext.validbits), + &(wav_fmt->ext.channelmask)) ; + + psf_log_printf (psf, " Valid Bits : %d\n", wav_fmt->ext.validbits) ; + psf_log_printf (psf, " Channel Mask : 0x%X\n", wav_fmt->ext.channelmask) ; + + bytesread += + psf_binheader_readf (psf, "422", &(wav_fmt->ext.esf.esf_field1), &(wav_fmt->ext.esf.esf_field2), + &(wav_fmt->ext.esf.esf_field3)) ; + + /* compare the esf_fields with each known GUID? and print? */ + psf_log_printf (psf, " Subformat\n") ; + psf_log_printf (psf, " esf_field1 : 0x%X\n", wav_fmt->ext.esf.esf_field1) ; + psf_log_printf (psf, " esf_field2 : 0x%X\n", wav_fmt->ext.esf.esf_field2) ; + psf_log_printf (psf, " esf_field3 : 0x%X\n", wav_fmt->ext.esf.esf_field3) ; + psf_log_printf (psf, " esf_field4 : ") ; + for (k = 0 ; k < 8 ; k++) + { bytesread += psf_binheader_readf (psf, "1", &(wav_fmt->ext.esf.esf_field4 [k])) ; + psf_log_printf (psf, "0x%X ", wav_fmt->ext.esf.esf_field4 [k] & 0xFF) ; + } ; + psf_log_printf (psf, "\n") ; + psf->bytewidth = BITWIDTH2BYTES (wav_fmt->ext.bitwidth) ; + + /* Compare GUIDs for known ones. */ + if (wavex_write_guid_equal (&wav_fmt->ext.esf, &MSGUID_SUBTYPE_PCM) + || wavex_write_guid_equal (&wav_fmt->ext.esf, &MSGUID_SUBTYPE_AMBISONIC_B_FORMAT_PCM)) + { psf->sf.format = SF_FORMAT_WAVEX | u_bitwidth_to_subformat (psf->bytewidth * 8) ; + psf_log_printf (psf, " format : pcm\n") ; + } + else if (wavex_write_guid_equal (&wav_fmt->ext.esf, &MSGUID_SUBTYPE_MS_ADPCM)) + { psf->sf.format = (SF_FORMAT_WAVEX | SF_FORMAT_MS_ADPCM) ; + psf_log_printf (psf, " format : ms adpcm\n") ; + } + else if (wavex_write_guid_equal (&wav_fmt->ext.esf, &MSGUID_SUBTYPE_IEEE_FLOAT) + || wavex_write_guid_equal (&wav_fmt->ext.esf, &MSGUID_SUBTYPE_AMBISONIC_B_FORMAT_PCM)) + { psf->sf.format = SF_FORMAT_WAVEX | ((psf->bytewidth == 8) ? SF_FORMAT_DOUBLE : SF_FORMAT_FLOAT) ; + psf_log_printf (psf, " format : IEEE float\n") ; + } + else if (wavex_write_guid_equal (&wav_fmt->ext.esf, &MSGUID_SUBTYPE_ALAW)) + { psf->sf.format = (SF_FORMAT_WAVEX | SF_FORMAT_ALAW) ; + psf_log_printf (psf, " format : A-law\n") ; + } + else if (wavex_write_guid_equal (&wav_fmt->ext.esf, &MSGUID_SUBTYPE_MULAW)) + { psf->sf.format = (SF_FORMAT_WAVEX | SF_FORMAT_ULAW) ; + psf_log_printf (psf, " format : u-law\n") ; + } + else + return SFE_UNIMPLEMENTED ; + break ; + + case WAVE_FORMAT_G721_ADPCM : + psf_log_printf (psf, " Bytes/sec : %d\n", wav_fmt->g72x.bytespersec) ; + if (structsize >= 20) + { bytesread += psf_binheader_readf (psf, "22", &(wav_fmt->g72x.extrabytes), &(wav_fmt->g72x.auxblocksize)) ; + if (wav_fmt->g72x.extrabytes == 0) + psf_log_printf (psf, " Extra Bytes : %d (should be 2)\n", wav_fmt->g72x.extrabytes) ; + else + psf_log_printf (psf, " Extra Bytes : %d\n", wav_fmt->g72x.extrabytes) ; + psf_log_printf (psf, " Aux Blk Size : %d\n", wav_fmt->g72x.auxblocksize) ; + } + else if (structsize == 18) + { bytesread += psf_binheader_readf (psf, "2", &(wav_fmt->g72x.extrabytes)) ; + psf_log_printf (psf, " Extra Bytes : %d%s\n", wav_fmt->g72x.extrabytes, wav_fmt->g72x.extrabytes != 0 ? " (should be 0)" : "") ; + } + else + psf_log_printf (psf, "*** 'fmt ' chunk should be bigger than this!\n") ; + break ; + + default : + psf_log_printf (psf, "*** No 'fmt ' chunk dumper for this format!\n") ; + break ; + } ; + + if (bytesread > structsize) + { psf_log_printf (psf, "*** wav_w64_read_fmt_chunk (bytesread > structsize)\n") ; + return SFE_W64_FMT_SHORT ; + } + else + psf_binheader_readf (psf, "j", structsize - bytesread) ; + + psf->blockwidth = wav_fmt->min.channels * psf->bytewidth ; + + return 0 ; +} /* wav_w64_read_fmt_chunk */ + +void +wavex_write_guid (SF_PRIVATE *psf, const EXT_SUBFORMAT * subformat) +{ + psf_binheader_writef (psf, "422b", subformat->esf_field1, + subformat->esf_field2, subformat->esf_field3, + subformat->esf_field4, 8) ; +} /* wavex_write_guid */ + + +/*============================================================================== +*/ + +typedef struct +{ int ID ; + const char *name ; +} WAV_FORMAT_DESC ; + +#define STR(x) #x +#define FORMAT_TYPE(x) { x, STR (x) } + +static WAV_FORMAT_DESC wave_descs [] = +{ FORMAT_TYPE (WAVE_FORMAT_PCM), + FORMAT_TYPE (WAVE_FORMAT_MS_ADPCM), + FORMAT_TYPE (WAVE_FORMAT_IEEE_FLOAT), + FORMAT_TYPE (WAVE_FORMAT_VSELP), + FORMAT_TYPE (WAVE_FORMAT_IBM_CVSD), + FORMAT_TYPE (WAVE_FORMAT_ALAW), + FORMAT_TYPE (WAVE_FORMAT_MULAW), + FORMAT_TYPE (WAVE_FORMAT_OKI_ADPCM), + FORMAT_TYPE (WAVE_FORMAT_IMA_ADPCM), + FORMAT_TYPE (WAVE_FORMAT_MEDIASPACE_ADPCM), + FORMAT_TYPE (WAVE_FORMAT_SIERRA_ADPCM), + FORMAT_TYPE (WAVE_FORMAT_G723_ADPCM), + FORMAT_TYPE (WAVE_FORMAT_DIGISTD), + FORMAT_TYPE (WAVE_FORMAT_DIGIFIX), + FORMAT_TYPE (WAVE_FORMAT_DIALOGIC_OKI_ADPCM), + FORMAT_TYPE (WAVE_FORMAT_MEDIAVISION_ADPCM), + FORMAT_TYPE (WAVE_FORMAT_CU_CODEC), + FORMAT_TYPE (WAVE_FORMAT_YAMAHA_ADPCM), + FORMAT_TYPE (WAVE_FORMAT_SONARC), + FORMAT_TYPE (WAVE_FORMAT_DSPGROUP_TRUESPEECH), + FORMAT_TYPE (WAVE_FORMAT_ECHOSC1), + FORMAT_TYPE (WAVE_FORMAT_AUDIOFILE_AF36), + FORMAT_TYPE (WAVE_FORMAT_APTX), + FORMAT_TYPE (WAVE_FORMAT_AUDIOFILE_AF10), + FORMAT_TYPE (WAVE_FORMAT_PROSODY_1612), + FORMAT_TYPE (WAVE_FORMAT_LRC), + FORMAT_TYPE (WAVE_FORMAT_DOLBY_AC2), + FORMAT_TYPE (WAVE_FORMAT_GSM610), + FORMAT_TYPE (WAVE_FORMAT_MSNAUDIO), + FORMAT_TYPE (WAVE_FORMAT_ANTEX_ADPCME), + FORMAT_TYPE (WAVE_FORMAT_CONTROL_RES_VQLPC), + FORMAT_TYPE (WAVE_FORMAT_DIGIREAL), + FORMAT_TYPE (WAVE_FORMAT_DIGIADPCM), + FORMAT_TYPE (WAVE_FORMAT_CONTROL_RES_CR10), + FORMAT_TYPE (WAVE_FORMAT_NMS_VBXADPCM), + FORMAT_TYPE (WAVE_FORMAT_ROLAND_RDAC), + FORMAT_TYPE (WAVE_FORMAT_ECHOSC3), + FORMAT_TYPE (WAVE_FORMAT_ROCKWELL_ADPCM), + FORMAT_TYPE (WAVE_FORMAT_ROCKWELL_DIGITALK), + FORMAT_TYPE (WAVE_FORMAT_XEBEC), + FORMAT_TYPE (WAVE_FORMAT_G721_ADPCM), + FORMAT_TYPE (WAVE_FORMAT_G728_CELP), + FORMAT_TYPE (WAVE_FORMAT_MSG723), + FORMAT_TYPE (WAVE_FORMAT_MPEG), + FORMAT_TYPE (WAVE_FORMAT_RT24), + FORMAT_TYPE (WAVE_FORMAT_PAC), + FORMAT_TYPE (WAVE_FORMAT_MPEGLAYER3), + FORMAT_TYPE (WAVE_FORMAT_LUCENT_G723), + FORMAT_TYPE (WAVE_FORMAT_CIRRUS), + FORMAT_TYPE (WAVE_FORMAT_ESPCM), + FORMAT_TYPE (WAVE_FORMAT_VOXWARE), + FORMAT_TYPE (WAVE_FORMAT_CANOPUS_ATRAC), + FORMAT_TYPE (WAVE_FORMAT_G726_ADPCM), + FORMAT_TYPE (WAVE_FORMAT_G722_ADPCM), + FORMAT_TYPE (WAVE_FORMAT_DSAT), + FORMAT_TYPE (WAVE_FORMAT_DSAT_DISPLAY), + FORMAT_TYPE (WAVE_FORMAT_VOXWARE_BYTE_ALIGNED), + FORMAT_TYPE (WAVE_FORMAT_VOXWARE_AC8), + FORMAT_TYPE (WAVE_FORMAT_VOXWARE_AC10), + FORMAT_TYPE (WAVE_FORMAT_VOXWARE_AC16), + FORMAT_TYPE (WAVE_FORMAT_VOXWARE_AC20), + FORMAT_TYPE (WAVE_FORMAT_VOXWARE_RT24), + FORMAT_TYPE (WAVE_FORMAT_VOXWARE_RT29), + FORMAT_TYPE (WAVE_FORMAT_VOXWARE_RT29HW), + FORMAT_TYPE (WAVE_FORMAT_VOXWARE_VR12), + FORMAT_TYPE (WAVE_FORMAT_VOXWARE_VR18), + FORMAT_TYPE (WAVE_FORMAT_VOXWARE_TQ40), + FORMAT_TYPE (WAVE_FORMAT_SOFTSOUND), + FORMAT_TYPE (WAVE_FORMAT_VOXARE_TQ60), + FORMAT_TYPE (WAVE_FORMAT_MSRT24), + FORMAT_TYPE (WAVE_FORMAT_G729A), + FORMAT_TYPE (WAVE_FORMAT_MVI_MV12), + FORMAT_TYPE (WAVE_FORMAT_DF_G726), + FORMAT_TYPE (WAVE_FORMAT_DF_GSM610), + FORMAT_TYPE (WAVE_FORMAT_ONLIVE), + FORMAT_TYPE (WAVE_FORMAT_SBC24), + FORMAT_TYPE (WAVE_FORMAT_DOLBY_AC3_SPDIF), + FORMAT_TYPE (WAVE_FORMAT_ZYXEL_ADPCM), + FORMAT_TYPE (WAVE_FORMAT_PHILIPS_LPCBB), + FORMAT_TYPE (WAVE_FORMAT_PACKED), + FORMAT_TYPE (WAVE_FORMAT_RHETOREX_ADPCM), + FORMAT_TYPE (IBM_FORMAT_MULAW), + FORMAT_TYPE (IBM_FORMAT_ALAW), + FORMAT_TYPE (IBM_FORMAT_ADPCM), + FORMAT_TYPE (WAVE_FORMAT_VIVO_G723), + FORMAT_TYPE (WAVE_FORMAT_VIVO_SIREN), + FORMAT_TYPE (WAVE_FORMAT_DIGITAL_G723), + FORMAT_TYPE (WAVE_FORMAT_CREATIVE_ADPCM), + FORMAT_TYPE (WAVE_FORMAT_CREATIVE_FASTSPEECH8), + FORMAT_TYPE (WAVE_FORMAT_CREATIVE_FASTSPEECH10), + FORMAT_TYPE (WAVE_FORMAT_QUARTERDECK), + FORMAT_TYPE (WAVE_FORMAT_FM_TOWNS_SND), + FORMAT_TYPE (WAVE_FORMAT_BZV_DIGITAL), + FORMAT_TYPE (WAVE_FORMAT_VME_VMPCM), + FORMAT_TYPE (WAVE_FORMAT_OLIGSM), + FORMAT_TYPE (WAVE_FORMAT_OLIADPCM), + FORMAT_TYPE (WAVE_FORMAT_OLICELP), + FORMAT_TYPE (WAVE_FORMAT_OLISBC), + FORMAT_TYPE (WAVE_FORMAT_OLIOPR), + FORMAT_TYPE (WAVE_FORMAT_LH_CODEC), + FORMAT_TYPE (WAVE_FORMAT_NORRIS), + FORMAT_TYPE (WAVE_FORMAT_SOUNDSPACE_MUSICOMPRESS), + FORMAT_TYPE (WAVE_FORMAT_DVM), + FORMAT_TYPE (WAVE_FORMAT_INTERWAV_VSC112), + FORMAT_TYPE (WAVE_FORMAT_EXTENSIBLE), +} ; + +char const* +wav_w64_format_str (int k) +{ int lower, upper, mid ; + + lower = -1 ; + upper = sizeof (wave_descs) / sizeof (WAV_FORMAT_DESC) ; + + /* binary search */ + if ((wave_descs [0].ID <= k) & (k <= wave_descs [upper - 1].ID)) + { + while (lower + 1 < upper) + { mid = (upper + lower) / 2 ; + + if (k == wave_descs [mid].ID) + return wave_descs [mid].name ; + if (k < wave_descs [mid].ID) + upper = mid ; + else + lower = mid ; + } ; + } ; + + return "Unknown format" ; +} /* wav_w64_format_str */ + +int +wav_w64_srate2blocksize (int srate_chan_product) +{ if (srate_chan_product < 12000) + return 256 ; + if (srate_chan_product < 23000) + return 512 ; + if (srate_chan_product < 44000) + return 1024 ; + return 2048 ; +} /* srate2blocksize */ +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 43c1b1dd-8abd-43da-a8cd-44da914b64a5 +*/ diff --git a/libs/libsndfile/src/wav_w64.h b/libs/libsndfile/src/wav_w64.h new file mode 100644 index 0000000000..3f33f1b800 --- /dev/null +++ b/libs/libsndfile/src/wav_w64.h @@ -0,0 +1,283 @@ +/* +** Copyright (C) 1999-2005 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +/* This file contains definitions commong to WAV and W64 files. */ + + +#ifndef WAV_W64_H_INCLUDED +#define WAV_W64_H_INCLUDED + +/*------------------------------------------------------------------------------ +** List of known WAV format tags +*/ + +enum +{ + /* keep sorted for wav_w64_format_str() */ + WAVE_FORMAT_UNKNOWN = 0x0000, /* Microsoft Corporation */ + WAVE_FORMAT_PCM = 0x0001, /* Microsoft PCM format */ + WAVE_FORMAT_MS_ADPCM = 0x0002, /* Microsoft ADPCM */ + WAVE_FORMAT_IEEE_FLOAT = 0x0003, /* Micrososft 32 bit float format */ + WAVE_FORMAT_VSELP = 0x0004, /* Compaq Computer Corporation */ + WAVE_FORMAT_IBM_CVSD = 0x0005, /* IBM Corporation */ + WAVE_FORMAT_ALAW = 0x0006, /* Microsoft Corporation */ + WAVE_FORMAT_MULAW = 0x0007, /* Microsoft Corporation */ + WAVE_FORMAT_OKI_ADPCM = 0x0010, /* OKI */ + WAVE_FORMAT_IMA_ADPCM = 0x0011, /* Intel Corporation */ + WAVE_FORMAT_MEDIASPACE_ADPCM = 0x0012, /* Videologic */ + WAVE_FORMAT_SIERRA_ADPCM = 0x0013, /* Sierra Semiconductor Corp */ + WAVE_FORMAT_G723_ADPCM = 0x0014, /* Antex Electronics Corporation */ + WAVE_FORMAT_DIGISTD = 0x0015, /* DSP Solutions, Inc. */ + WAVE_FORMAT_DIGIFIX = 0x0016, /* DSP Solutions, Inc. */ + WAVE_FORMAT_DIALOGIC_OKI_ADPCM = 0x0017, /* Dialogic Corporation */ + WAVE_FORMAT_MEDIAVISION_ADPCM = 0x0018, /* Media Vision, Inc. */ + WAVE_FORMAT_CU_CODEC = 0x0019, /* Hewlett-Packard Company */ + WAVE_FORMAT_YAMAHA_ADPCM = 0x0020, /* Yamaha Corporation of America */ + WAVE_FORMAT_SONARC = 0x0021, /* Speech Compression */ + WAVE_FORMAT_DSPGROUP_TRUESPEECH = 0x0022, /* DSP Group, Inc */ + WAVE_FORMAT_ECHOSC1 = 0x0023, /* Echo Speech Corporation */ + WAVE_FORMAT_AUDIOFILE_AF36 = 0x0024, /* Audiofile, Inc. */ + WAVE_FORMAT_APTX = 0x0025, /* Audio Processing Technology */ + WAVE_FORMAT_AUDIOFILE_AF10 = 0x0026, /* Audiofile, Inc. */ + WAVE_FORMAT_PROSODY_1612 = 0x0027, /* Aculab plc */ + WAVE_FORMAT_LRC = 0x0028, /* Merging Technologies S.A. */ + WAVE_FORMAT_DOLBY_AC2 = 0x0030, /* Dolby Laboratories */ + WAVE_FORMAT_GSM610 = 0x0031, /* Microsoft Corporation */ + WAVE_FORMAT_MSNAUDIO = 0x0032, /* Microsoft Corporation */ + WAVE_FORMAT_ANTEX_ADPCME = 0x0033, /* Antex Electronics Corporation */ + WAVE_FORMAT_CONTROL_RES_VQLPC = 0x0034, /* Control Resources Limited */ + WAVE_FORMAT_DIGIREAL = 0x0035, /* DSP Solutions, Inc. */ + WAVE_FORMAT_DIGIADPCM = 0x0036, /* DSP Solutions, Inc. */ + WAVE_FORMAT_CONTROL_RES_CR10 = 0x0037, /* Control Resources Limited */ + WAVE_FORMAT_NMS_VBXADPCM = 0x0038, /* Natural MicroSystems */ + WAVE_FORMAT_ROLAND_RDAC = 0x0039, /* Roland */ + WAVE_FORMAT_ECHOSC3 = 0x003A, /* Echo Speech Corporation */ + WAVE_FORMAT_ROCKWELL_ADPCM = 0x003B, /* Rockwell International */ + WAVE_FORMAT_ROCKWELL_DIGITALK = 0x003C, /* Rockwell International */ + WAVE_FORMAT_XEBEC = 0x003D, /* Xebec Multimedia Solutions Limited */ + WAVE_FORMAT_G721_ADPCM = 0x0040, /* Antex Electronics Corporation */ + WAVE_FORMAT_G728_CELP = 0x0041, /* Antex Electronics Corporation */ + WAVE_FORMAT_MSG723 = 0x0042, /* Microsoft Corporation */ + WAVE_FORMAT_MPEG = 0x0050, /* Microsoft Corporation */ + WAVE_FORMAT_RT24 = 0x0052, /* InSoft Inc. */ + WAVE_FORMAT_PAC = 0x0053, /* InSoft Inc. */ + WAVE_FORMAT_MPEGLAYER3 = 0x0055, /* MPEG 3 Layer 1 */ + WAVE_FORMAT_LUCENT_G723 = 0x0059, /* Lucent Technologies */ + WAVE_FORMAT_CIRRUS = 0x0060, /* Cirrus Logic */ + WAVE_FORMAT_ESPCM = 0x0061, /* ESS Technology */ + WAVE_FORMAT_VOXWARE = 0x0062, /* Voxware Inc */ + WAVE_FORMAT_CANOPUS_ATRAC = 0x0063, /* Canopus, Co., Ltd. */ + WAVE_FORMAT_G726_ADPCM = 0x0064, /* APICOM */ + WAVE_FORMAT_G722_ADPCM = 0x0065, /* APICOM */ + WAVE_FORMAT_DSAT = 0x0066, /* Microsoft Corporation */ + WAVE_FORMAT_DSAT_DISPLAY = 0x0067, /* Microsoft Corporation */ + WAVE_FORMAT_VOXWARE_BYTE_ALIGNED = 0x0069, /* Voxware Inc. */ + WAVE_FORMAT_VOXWARE_AC8 = 0x0070, /* Voxware Inc. */ + WAVE_FORMAT_VOXWARE_AC10 = 0x0071, /* Voxware Inc. */ + WAVE_FORMAT_VOXWARE_AC16 = 0x0072, /* Voxware Inc. */ + WAVE_FORMAT_VOXWARE_AC20 = 0x0073, /* Voxware Inc. */ + WAVE_FORMAT_VOXWARE_RT24 = 0x0074, /* Voxware Inc. */ + WAVE_FORMAT_VOXWARE_RT29 = 0x0075, /* Voxware Inc. */ + WAVE_FORMAT_VOXWARE_RT29HW = 0x0076, /* Voxware Inc. */ + WAVE_FORMAT_VOXWARE_VR12 = 0x0077, /* Voxware Inc. */ + WAVE_FORMAT_VOXWARE_VR18 = 0x0078, /* Voxware Inc. */ + WAVE_FORMAT_VOXWARE_TQ40 = 0x0079, /* Voxware Inc. */ + WAVE_FORMAT_SOFTSOUND = 0x0080, /* Softsound, Ltd. */ + WAVE_FORMAT_VOXARE_TQ60 = 0x0081, /* Voxware Inc. */ + WAVE_FORMAT_MSRT24 = 0x0082, /* Microsoft Corporation */ + WAVE_FORMAT_G729A = 0x0083, /* AT&T Laboratories */ + WAVE_FORMAT_MVI_MV12 = 0x0084, /* Motion Pixels */ + WAVE_FORMAT_DF_G726 = 0x0085, /* DataFusion Systems (Pty) (Ltd) */ + WAVE_FORMAT_DF_GSM610 = 0x0086, /* DataFusion Systems (Pty) (Ltd) */ + /* removed because duplicate */ + /* WAVE_FORMAT_ISIAUDIO = 0x0088, */ /* Iterated Systems, Inc. */ + WAVE_FORMAT_ONLIVE = 0x0089, /* OnLive! Technologies, Inc. */ + WAVE_FORMAT_SBC24 = 0x0091, /* Siemens Business Communications Systems */ + WAVE_FORMAT_DOLBY_AC3_SPDIF = 0x0092, /* Sonic Foundry */ + WAVE_FORMAT_ZYXEL_ADPCM = 0x0097, /* ZyXEL Communications, Inc. */ + WAVE_FORMAT_PHILIPS_LPCBB = 0x0098, /* Philips Speech Processing */ + WAVE_FORMAT_PACKED = 0x0099, /* Studer Professional Audio AG */ + WAVE_FORMAT_RHETOREX_ADPCM = 0x0100, /* Rhetorex, Inc. */ + + /* removed because of the following */ + /* WAVE_FORMAT_IRAT = 0x0101,*/ /* BeCubed Software Inc. */ + + /* these three are unofficial */ + IBM_FORMAT_MULAW = 0x0101, /* IBM mu-law format */ + IBM_FORMAT_ALAW = 0x0102, /* IBM a-law format */ + IBM_FORMAT_ADPCM = 0x0103, /* IBM AVC Adaptive Differential PCM format */ + + WAVE_FORMAT_VIVO_G723 = 0x0111, /* Vivo Software */ + WAVE_FORMAT_VIVO_SIREN = 0x0112, /* Vivo Software */ + WAVE_FORMAT_DIGITAL_G723 = 0x0123, /* Digital Equipment Corporation */ + WAVE_FORMAT_CREATIVE_ADPCM = 0x0200, /* Creative Labs, Inc */ + WAVE_FORMAT_CREATIVE_FASTSPEECH8 = 0x0202, /* Creative Labs, Inc */ + WAVE_FORMAT_CREATIVE_FASTSPEECH10 = 0x0203, /* Creative Labs, Inc */ + WAVE_FORMAT_QUARTERDECK = 0x0220, /* Quarterdeck Corporation */ + WAVE_FORMAT_FM_TOWNS_SND = 0x0300, /* Fujitsu Corporation */ + WAVE_FORMAT_BZV_DIGITAL = 0x0400, /* Brooktree Corporation */ + WAVE_FORMAT_VME_VMPCM = 0x0680, /* AT&T Labs, Inc. */ + WAVE_FORMAT_OLIGSM = 0x1000, /* Ing C. Olivetti & C., S.p.A. */ + WAVE_FORMAT_OLIADPCM = 0x1001, /* Ing C. Olivetti & C., S.p.A. */ + WAVE_FORMAT_OLICELP = 0x1002, /* Ing C. Olivetti & C., S.p.A. */ + WAVE_FORMAT_OLISBC = 0x1003, /* Ing C. Olivetti & C., S.p.A. */ + WAVE_FORMAT_OLIOPR = 0x1004, /* Ing C. Olivetti & C., S.p.A. */ + WAVE_FORMAT_LH_CODEC = 0x1100, /* Lernout & Hauspie */ + WAVE_FORMAT_NORRIS = 0x1400, /* Norris Communications, Inc. */ + /* removed because duplicate */ + /* WAVE_FORMAT_ISIAUDIO = 0x1401, */ /* AT&T Labs, Inc. */ + WAVE_FORMAT_SOUNDSPACE_MUSICOMPRESS = 0x1500, /* AT&T Labs, Inc. */ + WAVE_FORMAT_DVM = 0x2000, /* FAST Multimedia AG */ + WAVE_FORMAT_INTERWAV_VSC112 = 0x7150, /* ????? */ + WAVE_FORMAT_EXTENSIBLE = 0xFFFE +} ; + +typedef struct +{ unsigned short format ; + unsigned short channels ; + unsigned int samplerate ; + unsigned int bytespersec ; + unsigned short blockalign ; + unsigned short bitwidth ; +} MIN_WAV_FMT ; + +typedef struct +{ unsigned short format ; + unsigned short channels ; + unsigned int samplerate ; + unsigned int bytespersec ; + unsigned short blockalign ; + unsigned short bitwidth ; + unsigned short extrabytes ; + unsigned short dummy ; +} WAV_FMT_SIZE20 ; + +typedef struct +{ unsigned short format ; + unsigned short channels ; + unsigned int samplerate ; + unsigned int bytespersec ; + unsigned short blockalign ; + unsigned short bitwidth ; + unsigned short extrabytes ; + unsigned short samplesperblock ; + unsigned short numcoeffs ; + struct + { short coeff1 ; + short coeff2 ; + } coeffs [7] ; +} MS_ADPCM_WAV_FMT ; + +typedef struct +{ unsigned short format ; + unsigned short channels ; + unsigned int samplerate ; + unsigned int bytespersec ; + unsigned short blockalign ; + unsigned short bitwidth ; + unsigned short extrabytes ; + unsigned short samplesperblock ; +} IMA_ADPCM_WAV_FMT ; + +typedef struct +{ unsigned short format ; + unsigned short channels ; + unsigned int samplerate ; + unsigned int bytespersec ; + unsigned short blockalign ; + unsigned short bitwidth ; + unsigned short extrabytes ; + unsigned short auxblocksize ; +} G72x_ADPCM_WAV_FMT ; + + +typedef struct +{ unsigned short format ; + unsigned short channels ; + unsigned int samplerate ; + unsigned int bytespersec ; + unsigned short blockalign ; + unsigned short bitwidth ; + unsigned short extrabytes ; + unsigned short samplesperblock ; +} GSM610_WAV_FMT ; + +typedef struct +{ unsigned int esf_field1 ; + unsigned short esf_field2 ; + unsigned short esf_field3 ; + char esf_field4 [8] ; +} EXT_SUBFORMAT ; + +typedef struct +{ unsigned short format ; + unsigned short channels ; + unsigned int samplerate ; + unsigned int bytespersec ; + unsigned short blockalign ; + unsigned short bitwidth ; + unsigned short extrabytes ; + unsigned short validbits ; + unsigned int channelmask ; + EXT_SUBFORMAT esf ; +} EXTENSIBLE_WAV_FMT ; + +typedef union +{ unsigned short format ; + MIN_WAV_FMT min ; + IMA_ADPCM_WAV_FMT ima ; + MS_ADPCM_WAV_FMT msadpcm ; + G72x_ADPCM_WAV_FMT g72x ; + EXTENSIBLE_WAV_FMT ext ; + GSM610_WAV_FMT gsm610 ; + WAV_FMT_SIZE20 size20 ; + char padding [512] ; +} WAV_FMT ; + +typedef struct +{ int frames ; +} FACT_CHUNK ; + +#define WAV_W64_GSM610_BLOCKSIZE 65 +#define WAV_W64_GSM610_SAMPLES 320 + +/*------------------------------------------------------------------------------------ +** Functions defined in wav_ms_adpcm.c +*/ + +#define MSADPCM_ADAPT_COEFF_COUNT 7 + +void msadpcm_write_adapt_coeffs (SF_PRIVATE *psf) ; + +/*------------------------------------------------------------------------------------ +** Functions defined in wav_w64.c +*/ + +int wav_w64_srate2blocksize (int srate_chan_product) ; +char const* wav_w64_format_str (int k) ; +int wav_w64_read_fmt_chunk (SF_PRIVATE *psf, WAV_FMT *wav_fmt, int structsize) ; +void wavex_write_guid (SF_PRIVATE *psf, const EXT_SUBFORMAT * subformat) ; + +#endif +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 877fde12-9be3-4a31-8a5a-fdae39958613 +*/ diff --git a/libs/libsndfile/src/wve.c b/libs/libsndfile/src/wve.c new file mode 100644 index 0000000000..54a08336c2 --- /dev/null +++ b/libs/libsndfile/src/wve.c @@ -0,0 +1,125 @@ +/* +** Copyright (C) 2002-2004 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" + +#if (ENABLE_EXPERIMENTAL_CODE == 0) + +int +wve_open (SF_PRIVATE *psf) +{ if (psf) + return SFE_UNIMPLEMENTED ; + return (psf && 0) ; +} /* wve_open */ + +#else + +#define SFE_WVE_NOT_WVE 666 + +/*------------------------------------------------------------------------------ +** Macros to handle big/little endian issues. +*/ + +#define ALAW_MARKER MAKE_MARKER ('A', 'L', 'a', 'w') +#define SOUN_MARKER MAKE_MARKER ('S', 'o', 'u', 'n') +#define DFIL_MARKER MAKE_MARKER ('d', 'F', 'i', 'l') + +/*------------------------------------------------------------------------------ +** Private static functions. +*/ + +static int wve_read_header (SF_PRIVATE *psf) ; + +/*------------------------------------------------------------------------------ +** Public function. +*/ + +int +wve_open (SF_PRIVATE *psf) +{ int subformat, error = 0 ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + return SFE_UNIMPLEMENTED ; + + if ((error = wve_read_header (psf))) + return error ; + + if ((psf->sf.format & SF_FORMAT_TYPEMASK) != SF_FORMAT_WVE) + return SFE_BAD_OPEN_FORMAT ; + + subformat = psf->sf.format & SF_FORMAT_SUBMASK ; + + return error ; +} /* wve_open */ + +/*------------------------------------------------------------------------------ +*/ + +static int +wve_read_header (SF_PRIVATE *psf) +{ int marker ; + + /* Set position to start of file to begin reading header. */ + psf_binheader_readf (psf, "pm", 0, &marker) ; + if (marker != ALAW_MARKER) + return SFE_WVE_NOT_WVE ; + + psf_binheader_readf (psf, "m", &marker) ; + if (marker != SOUN_MARKER) + return SFE_WVE_NOT_WVE ; + + psf_binheader_readf (psf, "m", &marker) ; + if (marker != DFIL_MARKER) + return SFE_WVE_NOT_WVE ; + + psf_log_printf (psf, "Read only : Psion Palmtop Alaw (.wve)\n" + " Sample Rate : 8000\n" + " Channels : 1\n" + " Encoding : A-law\n") ; + + psf->dataoffset = 0x20 ; + psf->datalength = psf->filelength - psf->dataoffset ; + + psf->sf.format = SF_FORMAT_WVE | SF_FORMAT_ALAW ; + psf->sf.samplerate = 8000 ; + psf->sf.frames = psf->datalength ; + psf->sf.channels = 1 ; + + return alaw_init (psf) ; +} /* wve_read_header */ + +/*------------------------------------------------------------------------------ +*/ + +#endif +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: ba368cb5-523f-45e4-98c1-5b99a102f73f +*/ diff --git a/libs/libsndfile/src/xi.c b/libs/libsndfile/src/xi.c new file mode 100644 index 0000000000..dcd8120b1e --- /dev/null +++ b/libs/libsndfile/src/xi.c @@ -0,0 +1,1204 @@ +/* +** Copyright (C) 2003-2006 Erik de Castro Lopo +** +** This program is free software; you can redistribute it and/or modify +** it under the terms of the GNU Lesser General Public License as published by +** the Free Software Foundation; either version 2.1 of the License, or +** (at your option) any later version. +** +** This program is distributed in the hope that it will be useful, +** but WITHOUT ANY WARRANTY; without even the implied warranty of +** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +** GNU Lesser General Public License for more details. +** +** You should have received a copy of the GNU Lesser General Public License +** along with this program; if not, write to the Free Software +** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +*/ + +#include "sfconfig.h" + +#include +#include +#include +#include +#include + +#include "sndfile.h" +#include "sfendian.h" +#include "common.h" +#include "float_cast.h" + +#define MAX_XI_SAMPLES 16 + +/*------------------------------------------------------------------------------ +** Private static functions and tyepdefs. +*/ + +typedef struct +{ /* Warning, this filename is NOT nul terminated. */ + char filename [22] ; + char software [20] ; + char sample_name [22] ; + + int loop_begin, loop_end ; + int sample_flags ; + + /* Data for encoder and decoder. */ + short last_16 ; +} XI_PRIVATE ; + +static int xi_close (SF_PRIVATE *psf) ; +static int xi_write_header (SF_PRIVATE *psf, int calc_length) ; +static int xi_read_header (SF_PRIVATE *psf) ; +static int dpcm_init (SF_PRIVATE *psf) ; + + +static sf_count_t dpcm_seek (SF_PRIVATE *psf, int mode, sf_count_t offset) ; + +/*------------------------------------------------------------------------------ +** Public function. +*/ + +int +xi_open (SF_PRIVATE *psf) +{ XI_PRIVATE *pxi ; + int subformat, error = 0 ; + + if (psf->is_pipe) + return SFE_XI_NO_PIPE ; + + if (psf->fdata) + pxi = psf->fdata ; + else if ((pxi = calloc (1, sizeof (XI_PRIVATE))) == NULL) + return SFE_MALLOC_FAILED ; + + psf->fdata = pxi ; + + if (psf->mode == SFM_READ || (psf->mode == SFM_RDWR && psf->filelength > 0)) + { if ((error = xi_read_header (psf))) + return error ; + } ; + + subformat = psf->sf.format & SF_FORMAT_SUBMASK ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { if ((psf->sf.format & SF_FORMAT_TYPEMASK) != SF_FORMAT_XI) + return SFE_BAD_OPEN_FORMAT ; + + psf->endian = SF_ENDIAN_LITTLE ; + psf->sf.channels = 1 ; /* Always mono */ + psf->sf.samplerate = 44100 ; /* Always */ + + /* Set up default instrument and software name. */ + memcpy (pxi->filename, "Default Name ", sizeof (pxi->filename)) ; + memcpy (pxi->software, PACKAGE "-" VERSION " ", sizeof (pxi->software)) ; + + memset (pxi->sample_name, 0, sizeof (pxi->sample_name)) ; + LSF_SNPRINTF (pxi->sample_name, sizeof (pxi->sample_name), "%s", "Sample #1") ; + + pxi->sample_flags = (subformat == SF_FORMAT_DPCM_16) ? 16 : 0 ; + + if (xi_write_header (psf, SF_FALSE)) + return psf->error ; + + psf->write_header = xi_write_header ; + } ; + + psf->container_close = xi_close ; + psf->seek = dpcm_seek ; + + psf->sf.seekable = SF_FALSE ; + + psf->blockwidth = psf->bytewidth * psf->sf.channels ; + + switch (subformat) + { case SF_FORMAT_DPCM_8 : /* 8-bit differential PCM. */ + case SF_FORMAT_DPCM_16 : /* 16-bit differential PCM. */ + error = dpcm_init (psf) ; + break ; + + default : break ; + } ; + + return error ; +} /* xi_open */ + +/*------------------------------------------------------------------------------ +*/ + +static int +xi_close (SF_PRIVATE *psf) +{ + psf = psf ; + + return 0 ; +} /* xi_close */ + +/*============================================================================== +*/ + +static sf_count_t dpcm_read_dsc2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t dpcm_read_dsc2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t dpcm_read_dsc2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t dpcm_read_dsc2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; + +static sf_count_t dpcm_write_s2dsc (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t dpcm_write_i2dsc (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t dpcm_write_f2dsc (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t dpcm_write_d2dsc (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; + +static sf_count_t dpcm_read_dles2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) ; +static sf_count_t dpcm_read_dles2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) ; +static sf_count_t dpcm_read_dles2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) ; +static sf_count_t dpcm_read_dles2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) ; + +static sf_count_t dpcm_write_s2dles (SF_PRIVATE *psf, const short *ptr, sf_count_t len) ; +static sf_count_t dpcm_write_i2dles (SF_PRIVATE *psf, const int *ptr, sf_count_t len) ; +static sf_count_t dpcm_write_f2dles (SF_PRIVATE *psf, const float *ptr, sf_count_t len) ; +static sf_count_t dpcm_write_d2dles (SF_PRIVATE *psf, const double *ptr, sf_count_t len) ; + +static int +dpcm_init (SF_PRIVATE *psf) +{ if (psf->bytewidth == 0 || psf->sf.channels == 0) + return SFE_INTERNAL ; + + psf->blockwidth = psf->bytewidth * psf->sf.channels ; + + if (psf->mode == SFM_READ || psf->mode == SFM_RDWR) + { switch (psf->bytewidth) + { case 1 : + psf->read_short = dpcm_read_dsc2s ; + psf->read_int = dpcm_read_dsc2i ; + psf->read_float = dpcm_read_dsc2f ; + psf->read_double = dpcm_read_dsc2d ; + break ; + case 2 : + psf->read_short = dpcm_read_dles2s ; + psf->read_int = dpcm_read_dles2i ; + psf->read_float = dpcm_read_dles2f ; + psf->read_double = dpcm_read_dles2d ; + break ; + default : + psf_log_printf (psf, "dpcm_init() returning SFE_UNIMPLEMENTED\n") ; + return SFE_UNIMPLEMENTED ; + } ; + } ; + + if (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR) + { switch (psf->bytewidth) + { case 1 : + psf->write_short = dpcm_write_s2dsc ; + psf->write_int = dpcm_write_i2dsc ; + psf->write_float = dpcm_write_f2dsc ; + psf->write_double = dpcm_write_d2dsc ; + break ; + case 2 : + psf->write_short = dpcm_write_s2dles ; + psf->write_int = dpcm_write_i2dles ; + psf->write_float = dpcm_write_f2dles ; + psf->write_double = dpcm_write_d2dles ; + break ; + default : + psf_log_printf (psf, "dpcm_init() returning SFE_UNIMPLEMENTED\n") ; + return SFE_UNIMPLEMENTED ; + } ; + } ; + + psf->filelength = psf_get_filelen (psf) ; + psf->datalength = (psf->dataend) ? psf->dataend - psf->dataoffset : + psf->filelength - psf->dataoffset ; + psf->sf.frames = psf->datalength / psf->blockwidth ; + + return 0 ; +} /* dpcm_init */ + +/*============================================================================== +*/ + +static sf_count_t +dpcm_seek (SF_PRIVATE *psf, int mode, sf_count_t offset) +{ XI_PRIVATE *pxi ; + int total, bufferlen, len ; + + if ((pxi = psf->fdata) == NULL) + return SFE_INTERNAL ; + + if (psf->datalength < 0 || psf->dataoffset < 0) + { psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; + } ; + + if (offset == 0) + { psf_fseek (psf, psf->dataoffset, SEEK_SET) ; + pxi->last_16 = 0 ; + return 0 ; + } ; + + if (offset < 0 || offset > psf->sf.frames) + { psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; + } ; + + if (mode != SFM_READ) + { /* What to do about write??? */ + psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; + } ; + + psf_fseek (psf, psf->dataoffset, SEEK_SET) ; + + if ((psf->sf.format & SF_FORMAT_SUBMASK) == SF_FORMAT_DPCM_16) + { total = offset ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (total > 0) + { len = (total > bufferlen) ? bufferlen : total ; + total -= dpcm_read_dles2s (psf, psf->u.sbuf, len) ; + } ; + } + else + { total = offset ; + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + while (total > 0) + { len = (total > bufferlen) ? bufferlen : total ; + total -= dpcm_read_dsc2s (psf, psf->u.sbuf, len) ; + } ; + } ; + + return offset ; +} /* dpcm_seek */ + + +static int +xi_write_header (SF_PRIVATE *psf, int calc_length) +{ XI_PRIVATE *pxi ; + sf_count_t current ; + const char *string ; + + if ((pxi = psf->fdata) == NULL) + return SFE_INTERNAL ; + + calc_length = calc_length ; /* Avoid a compiler warning. */ + + current = psf_ftell (psf) ; + + /* Reset the current header length to zero. */ + psf->header [0] = 0 ; + psf->headindex = 0 ; + psf_fseek (psf, 0, SEEK_SET) ; + + string = "Extended Instrument: " ; + psf_binheader_writef (psf, "b", string, strlen (string)) ; + psf_binheader_writef (psf, "b1", pxi->filename, sizeof (pxi->filename), 0x1A) ; + + /* Write software version and two byte XI version. */ + psf_binheader_writef (psf, "eb2", pxi->software, sizeof (pxi->software), (1 << 8) + 2) ; + + /* + ** Jump note numbers (96), volume envelope (48), pan envelope (48), + ** volume points (1), pan points (1) + */ + psf_binheader_writef (psf, "z", (size_t) (96 + 48 + 48 + 1 + 1)) ; + + /* Jump volume loop (3 bytes), pan loop (3), envelope flags (3), vibrato (3) + ** fade out (2), 22 unknown bytes, and then write sample_count (2 bytes). + */ + psf_binheader_writef (psf, "ez2z2", (size_t) (4 * 3), 0x1234, make_size_t (22), 1) ; + + pxi->loop_begin = 0 ; + pxi->loop_end = 0 ; + + psf_binheader_writef (psf, "et844", psf->sf.frames, pxi->loop_begin, pxi->loop_end) ; + + /* volume, fine tune, flags, pan, note, namelen */ + psf_binheader_writef (psf, "111111", 128, 0, pxi->sample_flags, 128, 0, strlen (pxi->sample_name)) ; + + psf_binheader_writef (psf, "b", pxi->sample_name, sizeof (pxi->sample_name)) ; + + + + + + /* Header construction complete so write it out. */ + psf_fwrite (psf->header, psf->headindex, 1, psf) ; + + if (psf->error) + return psf->error ; + + psf->dataoffset = psf->headindex ; + + if (current > 0) + psf_fseek (psf, current, SEEK_SET) ; + + return psf->error ; +} /* xi_write_header */ + +static int +xi_read_header (SF_PRIVATE *psf) +{ char buffer [64], name [32] ; + short version, fade_out, sample_count ; + int k, loop_begin, loop_end ; + int sample_sizes [MAX_XI_SAMPLES] ; + + psf_binheader_readf (psf, "pb", 0, buffer, 21) ; + + memset (sample_sizes, 0, sizeof (sample_sizes)) ; + + buffer [20] = 0 ; + if (strcmp (buffer, "Extended Instrument:") != 0) + return SFE_XI_BAD_HEADER ; + + memset (buffer, 0, sizeof (buffer)) ; + psf_binheader_readf (psf, "b", buffer, 23) ; + + if (buffer [22] != 0x1A) + return SFE_XI_BAD_HEADER ; + + buffer [22] = 0 ; + psf_log_printf (psf, "Extended Instrument : %s\n", buffer) ; + + psf_binheader_readf (psf, "be2", buffer, 20, &version) ; + buffer [19] = 0 ; + psf_log_printf (psf, "Software : %s\nVersion : %d.%02d\n", buffer, version / 256, version % 256) ; + + /* Jump note numbers (96), volume envelope (48), pan envelope (48), + ** volume points (1), pan points (1) + */ + psf_binheader_readf (psf, "j", 96 + 48 + 48 + 1 + 1) ; + + psf_binheader_readf (psf, "b", buffer, 12) ; + psf_log_printf (psf, "Volume Loop\n sustain : %u\n begin : %u\n end : %u\n", + buffer [0], buffer [1], buffer [2]) ; + psf_log_printf (psf, "Pan Loop\n sustain : %u\n begin : %u\n end : %u\n", + buffer [3], buffer [4], buffer [5]) ; + psf_log_printf (psf, "Envelope Flags\n volume : 0x%X\n pan : 0x%X\n", + buffer [6] & 0xFF, buffer [7] & 0xFF) ; + + psf_log_printf (psf, "Vibrato\n type : %u\n sweep : %u\n depth : %u\n rate : %u\n", + buffer [8], buffer [9], buffer [10], buffer [11]) ; + + /* + ** Read fade_out then jump reserved (2 bytes) and ???? (20 bytes) and + ** sample_count. + */ + psf_binheader_readf (psf, "e2j2", &fade_out, 2 + 20, &sample_count) ; + psf_log_printf (psf, "Fade out : %d\n", fade_out) ; + + /* XI file can contain up to 16 samples. */ + if (sample_count > MAX_XI_SAMPLES) + return SFE_XI_EXCESS_SAMPLES ; + + if (psf->instrument == NULL && (psf->instrument = psf_instrument_alloc ()) == NULL) + return SFE_MALLOC_FAILED ; + + /* Log all data for each sample. */ + for (k = 0 ; k < sample_count ; k++) + { psf_binheader_readf (psf, "e444", &(sample_sizes [k]), &loop_begin, &loop_end) ; + + /* Read 5 know bytes, 1 unknown byte and 22 name bytes. */ + psf_binheader_readf (psf, "bb", buffer, 6, name, 22) ; + name [21] = 0 ; + + psf_log_printf (psf, "Sample #%d\n name : %s\n", k + 1, name) ; + + psf_log_printf (psf, " size : %d\n", sample_sizes [k]) ; + + + + psf_log_printf (psf, " loop\n begin : %d\n end : %d\n", loop_begin, loop_end) ; + + psf_log_printf (psf, " volume : %u\n f. tune : %d\n flags : 0x%02X ", + buffer [0] & 0xFF, buffer [1] & 0xFF, buffer [2] & 0xFF) ; + + psf_log_printf (psf, " (") ; + if (buffer [2] & 1) + psf_log_printf (psf, " Loop") ; + if (buffer [2] & 2) + psf_log_printf (psf, " PingPong") ; + psf_log_printf (psf, (buffer [2] & 16) ? " 16bit" : " 8bit") ; + psf_log_printf (psf, " )\n") ; + + psf_log_printf (psf, " pan : %u\n note : %d\n namelen : %d\n", + buffer [3] & 0xFF, buffer [4], buffer [5]) ; + + if (k != 0) + continue ; + + if (buffer [2] & 16) + { psf->sf.format = SF_FORMAT_XI | SF_FORMAT_DPCM_16 ; + psf->bytewidth = 2 ; + } + else + { psf->sf.format = SF_FORMAT_XI | SF_FORMAT_DPCM_8 ; + psf->bytewidth = 1 ; + } ; + } ; + + while (sample_count > 1 && sample_sizes [sample_count - 1] == 0) + sample_count -- ; + + /* Currently, we can only handle 1 sample per file. */ + + if (sample_count > 2) + { psf_log_printf (psf, "*** Sample count is less than 16 but more than 1.\n") ; + psf_log_printf (psf, " sample count : %d sample_sizes [%d] : %d\n", + sample_count, sample_count - 1, sample_sizes [sample_count - 1]) ; + return SFE_XI_EXCESS_SAMPLES ; + } ; + + psf->dataoffset = psf_fseek (psf, 0, SEEK_CUR) ; + psf_log_printf (psf, "Data Offset : %D\n", psf->dataoffset) ; + + psf->datalength = sample_sizes [0] ; + + if (psf->dataoffset + psf->datalength > psf->filelength) + { psf_log_printf (psf, "*** File seems to be truncated. Should be at least %D bytes long.\n", + psf->dataoffset + sample_sizes [0]) ; + psf->datalength = psf->filelength - psf->dataoffset ; + } ; + + if (psf_fseek (psf, psf->dataoffset, SEEK_SET) != psf->dataoffset) + return SFE_BAD_SEEK ; + + psf->endian = SF_ENDIAN_LITTLE ; + psf->sf.channels = 1 ; /* Always mono */ + psf->sf.samplerate = 44100 ; /* Always */ + + psf->blockwidth = psf->sf.channels * psf->bytewidth ; + + if (! psf->sf.frames && psf->blockwidth) + psf->sf.frames = (psf->filelength - psf->dataoffset) / psf->blockwidth ; + + psf->instrument->basenote = 0 ; + psf->instrument->gain = 1 ; + psf->instrument->velocity_lo = psf->instrument->key_lo = 0 ; + psf->instrument->velocity_hi = psf->instrument->key_hi = 127 ; + + return 0 ; +} /* xi_read_header */ + +/*============================================================================== +*/ + +static void dsc2s_array (XI_PRIVATE *pxi, signed char *src, int count, short *dest) ; +static void dsc2i_array (XI_PRIVATE *pxi, signed char *src, int count, int *dest) ; +static void dsc2f_array (XI_PRIVATE *pxi, signed char *src, int count, float *dest, float normfact) ; +static void dsc2d_array (XI_PRIVATE *pxi, signed char *src, int count, double *dest, double normfact) ; + +static void dles2s_array (XI_PRIVATE *pxi, short *src, int count, short *dest) ; +static void dles2i_array (XI_PRIVATE *pxi, short *src, int count, int *dest) ; +static void dles2f_array (XI_PRIVATE *pxi, short *src, int count, float *dest, float normfact) ; +static void dles2d_array (XI_PRIVATE *pxi, short *src, int count, double *dest, double normfact) ; + +static sf_count_t +dpcm_read_dsc2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ XI_PRIVATE *pxi ; + int bufferlen, readcount ; + sf_count_t total = 0 ; + + if ((pxi = psf->fdata) == NULL) + return 0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.scbuf, sizeof (signed char), bufferlen, psf) ; + dsc2s_array (pxi, psf->u.scbuf, readcount, ptr + total) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* dpcm_read_dsc2s */ + +static sf_count_t +dpcm_read_dsc2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ XI_PRIVATE *pxi ; + int bufferlen, readcount ; + sf_count_t total = 0 ; + + if ((pxi = psf->fdata) == NULL) + return 0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.scbuf, sizeof (signed char), bufferlen, psf) ; + dsc2i_array (pxi, psf->u.scbuf, readcount, ptr + total) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* dpcm_read_dsc2i */ + +static sf_count_t +dpcm_read_dsc2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ XI_PRIVATE *pxi ; + int bufferlen, readcount ; + sf_count_t total = 0 ; + float normfact ; + + if ((pxi = psf->fdata) == NULL) + return 0 ; + + normfact = (psf->norm_float == SF_TRUE) ? 1.0 / ((float) 0x80) : 1.0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.scbuf, sizeof (signed char), bufferlen, psf) ; + dsc2f_array (pxi, psf->u.scbuf, readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* dpcm_read_dsc2f */ + +static sf_count_t +dpcm_read_dsc2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ XI_PRIVATE *pxi ; + int bufferlen, readcount ; + sf_count_t total = 0 ; + double normfact ; + + if ((pxi = psf->fdata) == NULL) + return 0 ; + + normfact = (psf->norm_double == SF_TRUE) ? 1.0 / ((double) 0x80) : 1.0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.scbuf, sizeof (signed char), bufferlen, psf) ; + dsc2d_array (pxi, psf->u.scbuf, readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* dpcm_read_dsc2d */ + +/*------------------------------------------------------------------------------ +*/ + +static sf_count_t +dpcm_read_dles2s (SF_PRIVATE *psf, short *ptr, sf_count_t len) +{ XI_PRIVATE *pxi ; + int bufferlen, readcount ; + sf_count_t total = 0 ; + + if ((pxi = psf->fdata) == NULL) + return 0 ; + + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.sbuf, sizeof (short), bufferlen, psf) ; + dles2s_array (pxi, psf->u.sbuf, readcount, ptr + total) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* dpcm_read_dles2s */ + +static sf_count_t +dpcm_read_dles2i (SF_PRIVATE *psf, int *ptr, sf_count_t len) +{ XI_PRIVATE *pxi ; + int bufferlen, readcount ; + sf_count_t total = 0 ; + + if ((pxi = psf->fdata) == NULL) + return 0 ; + + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.sbuf, sizeof (short), bufferlen, psf) ; + dles2i_array (pxi, psf->u.sbuf, readcount, ptr + total) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* dpcm_read_dles2i */ + +static sf_count_t +dpcm_read_dles2f (SF_PRIVATE *psf, float *ptr, sf_count_t len) +{ XI_PRIVATE *pxi ; + int bufferlen, readcount ; + sf_count_t total = 0 ; + float normfact ; + + if ((pxi = psf->fdata) == NULL) + return 0 ; + + normfact = (psf->norm_float == SF_TRUE) ? 1.0 / ((float) 0x8000) : 1.0 ; + + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.sbuf, sizeof (short), bufferlen, psf) ; + dles2f_array (pxi, psf->u.sbuf, readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* dpcm_read_dles2f */ + +static sf_count_t +dpcm_read_dles2d (SF_PRIVATE *psf, double *ptr, sf_count_t len) +{ XI_PRIVATE *pxi ; + int bufferlen, readcount ; + sf_count_t total = 0 ; + double normfact ; + + if ((pxi = psf->fdata) == NULL) + return 0 ; + + normfact = (psf->norm_double == SF_TRUE) ? 1.0 / ((double) 0x8000) : 1.0 ; + + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + readcount = psf_fread (psf->u.sbuf, sizeof (short), bufferlen, psf) ; + dles2d_array (pxi, psf->u.sbuf, readcount, ptr + total, normfact) ; + total += readcount ; + if (readcount < bufferlen) + break ; + len -= readcount ; + } ; + + return total ; +} /* dpcm_read_dles2d */ + +/*============================================================================== +*/ + +static void s2dsc_array (XI_PRIVATE *pxi, const short *src, signed char *dest, int count) ; +static void i2dsc_array (XI_PRIVATE *pxi, const int *src, signed char *dest, int count) ; +static void f2dsc_array (XI_PRIVATE *pxi, const float *src, signed char *dest, int count, float normfact) ; +static void d2dsc_array (XI_PRIVATE *pxi, const double *src, signed char *dest, int count, double normfact) ; + +static void s2dles_array (XI_PRIVATE *pxi, const short *src, short *dest, int count) ; +static void i2dles_array (XI_PRIVATE *pxi, const int *src, short *dest, int count) ; +static void f2dles_array (XI_PRIVATE *pxi, const float *src, short *dest, int count, float normfact) ; +static void d2dles_array (XI_PRIVATE *pxi, const double *src, short *dest, int count, double normfact) ; + + +static sf_count_t +dpcm_write_s2dsc (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ XI_PRIVATE *pxi ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + + if ((pxi = psf->fdata) == NULL) + return 0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + s2dsc_array (pxi, ptr + total, psf->u.scbuf, bufferlen) ; + writecount = psf_fwrite (psf->u.scbuf, sizeof (signed char), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* dpcm_write_s2dsc */ + +static sf_count_t +dpcm_write_i2dsc (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ XI_PRIVATE *pxi ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + + if ((pxi = psf->fdata) == NULL) + return 0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + i2dsc_array (pxi, ptr + total, psf->u.scbuf, bufferlen) ; + writecount = psf_fwrite (psf->u.scbuf, sizeof (signed char), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* dpcm_write_i2dsc */ + +static sf_count_t +dpcm_write_f2dsc (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ XI_PRIVATE *pxi ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + float normfact ; + + if ((pxi = psf->fdata) == NULL) + return 0 ; + + normfact = (psf->norm_float == SF_TRUE) ? (1.0 * 0x7F) : 1.0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + f2dsc_array (pxi, ptr + total, psf->u.scbuf, bufferlen, normfact) ; + writecount = psf_fwrite (psf->u.scbuf, sizeof (signed char), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* dpcm_write_f2dsc */ + +static sf_count_t +dpcm_write_d2dsc (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ XI_PRIVATE *pxi ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + double normfact ; + + if ((pxi = psf->fdata) == NULL) + return 0 ; + + normfact = (psf->norm_double == SF_TRUE) ? (1.0 * 0x7F) : 1.0 ; + + bufferlen = ARRAY_LEN (psf->u.ucbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + d2dsc_array (pxi, ptr + total, psf->u.scbuf, bufferlen, normfact) ; + writecount = psf_fwrite (psf->u.scbuf, sizeof (signed char), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* dpcm_write_d2dsc */ + + +static sf_count_t +dpcm_write_s2dles (SF_PRIVATE *psf, const short *ptr, sf_count_t len) +{ XI_PRIVATE *pxi ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + + if ((pxi = psf->fdata) == NULL) + return 0 ; + + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + s2dles_array (pxi, ptr + total, psf->u.sbuf, bufferlen) ; + writecount = psf_fwrite (psf->u.sbuf, sizeof (short), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* dpcm_write_s2dles */ + +static sf_count_t +dpcm_write_i2dles (SF_PRIVATE *psf, const int *ptr, sf_count_t len) +{ XI_PRIVATE *pxi ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + + if ((pxi = psf->fdata) == NULL) + return 0 ; + + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + i2dles_array (pxi, ptr + total, psf->u.sbuf, bufferlen) ; + writecount = psf_fwrite (psf->u.sbuf, sizeof (short), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* dpcm_write_i2dles */ + +static sf_count_t +dpcm_write_f2dles (SF_PRIVATE *psf, const float *ptr, sf_count_t len) +{ XI_PRIVATE *pxi ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + float normfact ; + + if ((pxi = psf->fdata) == NULL) + return 0 ; + + normfact = (psf->norm_float == SF_TRUE) ? (1.0 * 0x7FFF) : 1.0 ; + + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + f2dles_array (pxi, ptr + total, psf->u.sbuf, bufferlen, normfact) ; + writecount = psf_fwrite (psf->u.sbuf, sizeof (short), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* dpcm_write_f2dles */ + +static sf_count_t +dpcm_write_d2dles (SF_PRIVATE *psf, const double *ptr, sf_count_t len) +{ XI_PRIVATE *pxi ; + int bufferlen, writecount ; + sf_count_t total = 0 ; + double normfact ; + + if ((pxi = psf->fdata) == NULL) + return 0 ; + + normfact = (psf->norm_double == SF_TRUE) ? (1.0 * 0x7FFF) : 1.0 ; + + bufferlen = ARRAY_LEN (psf->u.sbuf) ; + + while (len > 0) + { if (len < bufferlen) + bufferlen = (int) len ; + d2dles_array (pxi, ptr + total, psf->u.sbuf, bufferlen, normfact) ; + writecount = psf_fwrite (psf->u.sbuf, sizeof (short), bufferlen, psf) ; + total += writecount ; + if (writecount < bufferlen) + break ; + len -= writecount ; + } ; + + return total ; +} /* dpcm_write_d2dles */ + + +/*============================================================================== +*/ + +static void +dsc2s_array (XI_PRIVATE *pxi, signed char *src, int count, short *dest) +{ signed char last_val ; + int k ; + + last_val = pxi->last_16 >> 8 ; + + for (k = 0 ; k < count ; k++) + { last_val += src [k] ; + dest [k] = last_val << 8 ; + } ; + + pxi->last_16 = last_val << 8 ; +} /* dsc2s_array */ + +static void +dsc2i_array (XI_PRIVATE *pxi, signed char *src, int count, int *dest) +{ signed char last_val ; + int k ; + + last_val = pxi->last_16 >> 8 ; + + for (k = 0 ; k < count ; k++) + { last_val += src [k] ; + dest [k] = last_val << 24 ; + } ; + + pxi->last_16 = last_val << 8 ; +} /* dsc2i_array */ + +static void +dsc2f_array (XI_PRIVATE *pxi, signed char *src, int count, float *dest, float normfact) +{ signed char last_val ; + int k ; + + last_val = pxi->last_16 >> 8 ; + + for (k = 0 ; k < count ; k++) + { last_val += src [k] ; + dest [k] = last_val * normfact ; + } ; + + pxi->last_16 = last_val << 8 ; +} /* dsc2f_array */ + +static void +dsc2d_array (XI_PRIVATE *pxi, signed char *src, int count, double *dest, double normfact) +{ signed char last_val ; + int k ; + + last_val = pxi->last_16 >> 8 ; + + for (k = 0 ; k < count ; k++) + { last_val += src [k] ; + dest [k] = last_val * normfact ; + } ; + + pxi->last_16 = last_val << 8 ; +} /* dsc2d_array */ + +/*------------------------------------------------------------------------------ +*/ + +static void +s2dsc_array (XI_PRIVATE *pxi, const short *src, signed char *dest, int count) +{ signed char last_val, current ; + int k ; + + last_val = pxi->last_16 >> 8 ; + + for (k = 0 ; k < count ; k++) + { current = src [k] >> 8 ; + dest [k] = current - last_val ; + last_val = current ; + } ; + + pxi->last_16 = last_val << 8 ; +} /* s2dsc_array */ + +static void +i2dsc_array (XI_PRIVATE *pxi, const int *src, signed char *dest, int count) +{ signed char last_val, current ; + int k ; + + last_val = pxi->last_16 >> 8 ; + + for (k = 0 ; k < count ; k++) + { current = src [k] >> 24 ; + dest [k] = current - last_val ; + last_val = current ; + } ; + + pxi->last_16 = last_val << 8 ; +} /* i2dsc_array */ + +static void +f2dsc_array (XI_PRIVATE *pxi, const float *src, signed char *dest, int count, float normfact) +{ signed char last_val, current ; + int k ; + + last_val = pxi->last_16 >> 8 ; + + for (k = 0 ; k < count ; k++) + { current = lrintf (src [k] * normfact) ; + dest [k] = current - last_val ; + last_val = current ; + } ; + + pxi->last_16 = last_val << 8 ; +} /* f2dsc_array */ + +static void +d2dsc_array (XI_PRIVATE *pxi, const double *src, signed char *dest, int count, double normfact) +{ signed char last_val, current ; + int k ; + + last_val = pxi->last_16 >> 8 ; + + for (k = 0 ; k < count ; k++) + { current = lrint (src [k] * normfact) ; + dest [k] = current - last_val ; + last_val = current ; + } ; + + pxi->last_16 = last_val << 8 ; +} /* d2dsc_array */ + +/*============================================================================== +*/ + +static void +dles2s_array (XI_PRIVATE *pxi, short *src, int count, short *dest) +{ short last_val ; + int k ; + + last_val = pxi->last_16 ; + + for (k = 0 ; k < count ; k++) + { last_val += LES2H_SHORT (src [k]) ; + dest [k] = last_val ; + } ; + + pxi->last_16 = last_val ; +} /* dles2s_array */ + +static void +dles2i_array (XI_PRIVATE *pxi, short *src, int count, int *dest) +{ short last_val ; + int k ; + + last_val = pxi->last_16 ; + + for (k = 0 ; k < count ; k++) + { last_val += LES2H_SHORT (src [k]) ; + dest [k] = last_val << 16 ; + } ; + + pxi->last_16 = last_val ; +} /* dles2i_array */ + +static void +dles2f_array (XI_PRIVATE *pxi, short *src, int count, float *dest, float normfact) +{ short last_val ; + int k ; + + last_val = pxi->last_16 ; + + for (k = 0 ; k < count ; k++) + { last_val += LES2H_SHORT (src [k]) ; + dest [k] = last_val * normfact ; + } ; + + pxi->last_16 = last_val ; +} /* dles2f_array */ + +static void +dles2d_array (XI_PRIVATE *pxi, short *src, int count, double *dest, double normfact) +{ short last_val ; + int k ; + + last_val = pxi->last_16 ; + + for (k = 0 ; k < count ; k++) + { last_val += LES2H_SHORT (src [k]) ; + dest [k] = last_val * normfact ; + } ; + + pxi->last_16 = last_val ; +} /* dles2d_array */ + +/*------------------------------------------------------------------------------ +*/ + +static void +s2dles_array (XI_PRIVATE *pxi, const short *src, short *dest, int count) +{ short diff, last_val ; + int k ; + + last_val = pxi->last_16 ; + + for (k = 0 ; k < count ; k++) + { diff = src [k] - last_val ; + dest [k] = LES2H_SHORT (diff) ; + last_val = src [k] ; + } ; + + pxi->last_16 = last_val ; +} /* s2dles_array */ + +static void +i2dles_array (XI_PRIVATE *pxi, const int *src, short *dest, int count) +{ short diff, last_val ; + int k ; + + last_val = pxi->last_16 ; + + for (k = 0 ; k < count ; k++) + { diff = (src [k] >> 16) - last_val ; + dest [k] = LES2H_SHORT (diff) ; + last_val = src [k] >> 16 ; + } ; + + pxi->last_16 = last_val ; +} /* i2dles_array */ + +static void +f2dles_array (XI_PRIVATE *pxi, const float *src, short *dest, int count, float normfact) +{ short diff, last_val, current ; + int k ; + + last_val = pxi->last_16 ; + + for (k = 0 ; k < count ; k++) + { current = lrintf (src [k] * normfact) ; + diff = current - last_val ; + dest [k] = LES2H_SHORT (diff) ; + last_val = current ; + } ; + + pxi->last_16 = last_val ; +} /* f2dles_array */ + +static void +d2dles_array (XI_PRIVATE *pxi, const double *src, short *dest, int count, double normfact) +{ short diff, last_val, current ; + int k ; + + last_val = pxi->last_16 ; + + for (k = 0 ; k < count ; k++) + { current = lrint (src [k] * normfact) ; + diff = current - last_val ; + dest [k] = LES2H_SHORT (diff) ; + last_val = current ; + } ; + + pxi->last_16 = last_val ; +} /* d2dles_array */ + +/* +** Do not edit or modify anything in this comment block. +** The arch-tag line is a file identity tag for the GNU Arch +** revision control system. +** +** arch-tag: 1ab2dbe0-29af-4d80-9c6f-cb21b67521bc +*/ diff --git a/libs/midi++2/SConscript b/libs/midi++2/SConscript index 7c3267a6c7..928372909c 100644 --- a/libs/midi++2/SConscript +++ b/libs/midi++2/SConscript @@ -7,7 +7,7 @@ import glob Import('env libraries install_prefix') midi2 = env.Copy() -midi2.Merge([ libraries['sigc2'], libraries['xml'], libraries['pbd3'] ]) +midi2.Merge([ libraries['sigc2'], libraries['xml'], libraries['glib2'], libraries['pbd3'] ]) domain = 'midipp' diff --git a/libs/midi++2/midi++/port.h b/libs/midi++2/midi++/port.h index 81e28615d0..a186f1fd5f 100644 --- a/libs/midi++2/midi++/port.h +++ b/libs/midi++2/midi++/port.h @@ -24,7 +24,6 @@ #include -#include #include #include @@ -67,7 +66,7 @@ class Port : public sigc::trackable { virtual int selectable() const = 0; - void selector_read_callback (Select::Selectable *, Select::Condition); + //void selector_read_callback (Select::Selectable *, Select::Condition); static void xforms_read_callback (int cond, int fd, void *ptr); static void gtk_read_callback (void *ptr, int fd, int cond); diff --git a/libs/midi++2/midimanager.cc b/libs/midi++2/midimanager.cc index 7b3ed7d336..692c06fe92 100644 --- a/libs/midi++2/midimanager.cc +++ b/libs/midi++2/midimanager.cc @@ -18,8 +18,10 @@ */ #include + +#include + #include -#include #include #include @@ -30,6 +32,8 @@ using namespace std; using namespace MIDI; +/* XXX check for strdup leaks */ + Manager *Manager::theManager = 0; Manager::Manager () @@ -312,7 +316,7 @@ Manager::parse_port_request (string str, Port::Type type) "devicename" is the full path to the requested file "tagname" (optional) is the name used to refer to the - port. If not given, PBD::basename (devicename) + port. If not given, g_path_get_basename (devicename) will be used. "mode" (optional) is either "r" or "w" or something else. @@ -360,7 +364,8 @@ Manager::parse_port_request (string str, Port::Type type) } } else { - req->tagname = strdup (PBD::basename (req->devname)); + // check when tagname is freed + req->tagname = g_path_get_basename (req->devname); req->mode = O_RDWR; } diff --git a/libs/midi++2/midiport.cc b/libs/midi++2/midiport.cc index 6d374ed8c0..a42aac2984 100644 --- a/libs/midi++2/midiport.cc +++ b/libs/midi++2/midiport.cc @@ -26,7 +26,7 @@ #include #include -using namespace Select; +//using namespace Select; using namespace MIDI; size_t Port::nports = 0; @@ -96,6 +96,7 @@ Port::clock () return 0; } +/* void Port::selector_read_callback (Selectable *s, Select::Condition cond) @@ -103,6 +104,7 @@ Port::selector_read_callback (Selectable *s, Select::Condition cond) byte buf[64]; read (buf, sizeof (buf)); } +*/ void Port::xforms_read_callback (int cond, int fd, void *ptr) diff --git a/libs/pbd3/SConscript b/libs/pbd3/SConscript index 65264adcee..4e64f12d43 100644 --- a/libs/pbd3/SConscript +++ b/libs/pbd3/SConscript @@ -10,7 +10,7 @@ pbd3 = env.Copy() domain = 'libpbd' -pbd3.Append(DOMAIN=domain,MAJOR=3,MINOR=2,MICRO=0) +pbd3.Append(DOMAIN=domain,MAJOR=4,MINOR=0,MICRO=0) pbd3.Append(CXXFLAGS="-DPACKAGE=\\\"" + domain + "\\\"") pbd3.Append(CXXFLAGS="-D_REENTRANT -D_LARGEFILE_SOURCE -D_LARGEFILE64_SOURCE") pbd3.Append(CXXFLAGS="-DLIBSIGC_DISABLE_DEPRECATED") @@ -21,7 +21,6 @@ pbd3_files = Split(""" basename.cc base_ui.cc convert.cc -dirname.cc dmalloc.cc mountpoint.cc pathscanner.cc @@ -33,7 +32,6 @@ strsplit.cc textreceiver.cc transmitter.cc undo.cc -unescape.cc version.cc whitespace.cc xml++.cc @@ -46,7 +44,7 @@ if conf.CheckCHeader('execinfo.h'): conf.env.Append(CXXFLAGS="-DHAVE_EXECINFO") pbd3 = conf.Finish() -pbd3.Merge ([ libraries['sigc2'], libraries['xml'] ]) +pbd3.Merge ([ libraries['sigc2'], libraries['xml'], libraries['glibmm2'], libraries['glib2'] ]) pbd3.VersionBuild(['version.cc','pbd/version.h'], 'SConscript') diff --git a/libs/pbd3/basename.cc b/libs/pbd3/basename.cc index b8c5c64d91..a51e393b78 100644 --- a/libs/pbd3/basename.cc +++ b/libs/pbd3/basename.cc @@ -2,37 +2,10 @@ #include #include -char * -PBD::basename (const char *path) - -{ - char *slash; - - if ((slash = strrchr (path, '/')) == 0) { - return strdup (path); - } - - if (*(slash+1) == '\0') { - return strdup (""); - } - - return strdup (slash+1); -} +// implement this using Glib::path_get_basename std::string -PBD::basename (const std::string str) -{ - std::string::size_type slash = str.find_last_of ('/'); - - if (slash == std::string::npos) { - return str; - } - - return str.substr (slash+1); -} - -std::string -PBD::basename_nosuffix (const std::string str) +PBD::basename_nosuffix (const std::string& str) { std::string::size_type slash = str.find_last_of ('/'); std::string noslash; diff --git a/libs/pbd3/dirname.cc b/libs/pbd3/dirname.cc deleted file mode 100644 index 6b97ac7e3a..0000000000 --- a/libs/pbd3/dirname.cc +++ /dev/null @@ -1,51 +0,0 @@ -#include -#include -#include -#include - - -char * -PBD::dirname (const char *path) - -{ - char *slash; - size_t len; - char *ret; - - if ((slash = strrchr (path, '/')) == 0) { - return strdup (path); - } - - if (*(slash+1) == '\0') { - return strdup (""); - } - - len = (size_t) (slash - path); - ret = (char *) malloc (sizeof (char) * (len + 1)); - - snprintf (ret, len, "%*s", (int)len, path); - return ret; -} - -std::string -PBD::dirname (const std::string str) -{ - std::string::size_type slash = str.find_last_of ('/'); - std::string dir; - - if (slash == std::string::npos) { - return str; - } - - /* remove trailing multiple slashes (legal under POSIX) */ - - dir = str.substr (0, slash); - slash = dir.length(); - - while (slash > 1 && dir[slash-1] == '/') { - slash--; - dir = dir.substr (0, slash); - } - - return dir; -} diff --git a/libs/pbd3/pbd/abstract_ui.cc b/libs/pbd3/pbd/abstract_ui.cc index 06cf1665a3..0e34787a2d 100644 --- a/libs/pbd3/pbd/abstract_ui.cc +++ b/libs/pbd3/pbd/abstract_ui.cc @@ -29,7 +29,7 @@ AbstractUI::register_thread_with_request_count (pthread_t thread_ RequestBuffer* b = new RequestBuffer (num_requests); { - PBD::LockMonitor lm (request_buffer_map_lock, __LINE__, __FILE__); + Glib::Mutex::Lock lm (request_buffer_map_lock); request_buffers[thread_id] = b; } diff --git a/libs/pbd3/pbd/abstract_ui.h b/libs/pbd3/pbd/abstract_ui.h index 98f077cb48..f80db7bf1a 100644 --- a/libs/pbd3/pbd/abstract_ui.h +++ b/libs/pbd3/pbd/abstract_ui.h @@ -27,8 +27,9 @@ #include +#include + #include -#include #include #include @@ -62,7 +63,7 @@ class AbstractUI : public BaseUI typedef typename RequestBuffer::rw_vector RequestBufferVector; typedef typename std::map::iterator RequestBufferMapIterator; - PBD::Lock request_buffer_map_lock; + Glib::Mutex request_buffer_map_lock; typedef std::map RequestBufferMap; RequestBufferMap request_buffers; pthread_key_t thread_request_buffer_key; diff --git a/libs/pbd3/pbd/atomic.h b/libs/pbd3/pbd/atomic.h deleted file mode 100644 index 81e76f41fa..0000000000 --- a/libs/pbd3/pbd/atomic.h +++ /dev/null @@ -1,1232 +0,0 @@ -/* - Copyright (C) 2001 Paul Davis and others (see below) - Code derived from various headers from the Linux kernel. - Copyright attributions maintained where present. - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ - -#ifndef __libpbd_atomic_h__ -#define __libpbd_atomic_h__ - -#ifdef HAVE_SMP /* a macro we control, to manage ... */ -#define CONFIG_SMP /* ... the macro the kernel headers use */ -#endif - -#if defined(__powerpc__) || defined(__ppc__) - -/* - * BK Id: SCCS/s.atomic.h 1.15 10/28/01 10:37:22 trini - */ -/* - * PowerPC atomic operations - */ - -#ifndef _ASM_PPC_ATOMIC_H_ -#define _ASM_PPC_ATOMIC_H_ - -typedef struct { volatile int counter; } atomic_t; - - -#define ATOMIC_INIT(i) { (i) } - -#define atomic_read(v) ((v)->counter) -#define atomic_set(v,i) (((v)->counter) = (i)) - -extern void atomic_clear_mask(unsigned long mask, unsigned long *addr); -extern void atomic_set_mask(unsigned long mask, unsigned long *addr); - -#ifdef CONFIG_SMP -#define SMP_ISYNC "\n\tisync" -#else -#define SMP_ISYNC -#endif - -static __inline__ void atomic_add(int a, atomic_t *v) -{ - int t; - - __asm__ __volatile__( -"1: lwarx %0,0,%3\n\ - add %0,%2,%0\n\ - stwcx. %0,0,%3\n\ - bne- 1b" - : "=&r" (t), "=m" (v->counter) - : "r" (a), "r" (&v->counter), "m" (v->counter) - : "cc"); -} - -static __inline__ int atomic_add_return(int a, atomic_t *v) -{ - int t; - - __asm__ __volatile__( -"1: lwarx %0,0,%2\n\ - add %0,%1,%0\n\ - stwcx. %0,0,%2\n\ - bne- 1b" - SMP_ISYNC - : "=&r" (t) - : "r" (a), "r" (&v->counter) - : "cc", "memory"); - - return t; -} - -static __inline__ void atomic_sub(int a, atomic_t *v) -{ - int t; - - __asm__ __volatile__( -"1: lwarx %0,0,%3\n\ - subf %0,%2,%0\n\ - stwcx. %0,0,%3\n\ - bne- 1b" - : "=&r" (t), "=m" (v->counter) - : "r" (a), "r" (&v->counter), "m" (v->counter) - : "cc"); -} - -static __inline__ int atomic_sub_return(int a, atomic_t *v) -{ - int t; - - __asm__ __volatile__( -"1: lwarx %0,0,%2\n\ - subf %0,%1,%0\n\ - stwcx. %0,0,%2\n\ - bne- 1b" - SMP_ISYNC - : "=&r" (t) - : "r" (a), "r" (&v->counter) - : "cc", "memory"); - - return t; -} - -static __inline__ void atomic_inc(atomic_t *v) -{ - int t; - - __asm__ __volatile__( -"1: lwarx %0,0,%2\n\ - addic %0,%0,1\n\ - stwcx. %0,0,%2\n\ - bne- 1b" - : "=&r" (t), "=m" (v->counter) - : "r" (&v->counter), "m" (v->counter) - : "cc"); -} - -static __inline__ int atomic_inc_return(atomic_t *v) -{ - int t; - - __asm__ __volatile__( -"1: lwarx %0,0,%1\n\ - addic %0,%0,1\n\ - stwcx. %0,0,%1\n\ - bne- 1b" - SMP_ISYNC - : "=&r" (t) - : "r" (&v->counter) - : "cc", "memory"); - - return t; -} - -static __inline__ void atomic_dec(atomic_t *v) -{ - int t; - - __asm__ __volatile__( -"1: lwarx %0,0,%2\n\ - addic %0,%0,-1\n\ - stwcx. %0,0,%2\n\ - bne- 1b" - : "=&r" (t), "=m" (v->counter) - : "r" (&v->counter), "m" (v->counter) - : "cc"); -} - -static __inline__ int atomic_dec_return(atomic_t *v) -{ - int t; - - __asm__ __volatile__( -"1: lwarx %0,0,%1\n\ - addic %0,%0,-1\n\ - stwcx. %0,0,%1\n\ - bne- 1b" - SMP_ISYNC - : "=&r" (t) - : "r" (&v->counter) - : "cc", "memory"); - - return t; -} - -#define atomic_sub_and_test(a, v) (atomic_sub_return((a), (v)) == 0) -#define atomic_dec_and_test(v) (atomic_dec_return((v)) == 0) - -/* - * Atomically test *v and decrement if it is greater than 0. - * The function returns the old value of *v minus 1. - */ -static __inline__ int atomic_dec_if_positive(atomic_t *v) -{ - int t; - - __asm__ __volatile__( -"1: lwarx %0,0,%1\n\ - addic. %0,%0,-1\n\ - blt- 2f\n\ - stwcx. %0,0,%1\n\ - bne- 1b" - SMP_ISYNC - "\n\ -2:" : "=&r" (t) - : "r" (&v->counter) - : "cc", "memory"); - - return t; -} - -#define smp_mb__before_atomic_dec() smp_mb() -#define smp_mb__after_atomic_dec() smp_mb() -#define smp_mb__before_atomic_inc() smp_mb() -#define smp_mb__after_atomic_inc() smp_mb() - -#endif /* _ASM_PPC_ATOMIC_H_ */ - -/***********************************************************************/ - -# else /* !PPC */ - -#if defined(__i386__) || defined(__x86_64__) - -#ifndef __ARCH_I386_ATOMIC__ -#define __ARCH_I386_ATOMIC__ - -/* - * Atomic operations that C can't guarantee us. Useful for - * resource counting etc.. - */ - -#ifdef CONFIG_SMP -#define SMP_LOCK "lock ; " -#else -#define SMP_LOCK "" -#endif - -/* - * Make sure gcc doesn't try to be clever and move things around - * on us. We need to use _exactly_ the address the user gave us, - * not some alias that contains the same information. - */ -typedef struct { volatile int counter; } atomic_t; - -#define ATOMIC_INIT(i) { (i) } - -/** - * atomic_read - read atomic variable - * @v: pointer of type atomic_t - * - * Atomically reads the value of @v. Note that the guaranteed - * useful range of an atomic_t is only 24 bits. - */ -#define atomic_read(v) ((v)->counter) - -/** - * atomic_set - set atomic variable - * @v: pointer of type atomic_t - * @i: required value - * - * Atomically sets the value of @v to @i. Note that the guaranteed - * useful range of an atomic_t is only 24 bits. - */ -#define atomic_set(v,i) (((v)->counter) = (i)) - -/** - * atomic_add - add integer to atomic variable - * @i: integer value to add - * @v: pointer of type atomic_t - * - * Atomically adds @i to @v. Note that the guaranteed useful range - * of an atomic_t is only 24 bits. - */ -static __inline__ void atomic_add(int i, atomic_t *v) -{ - __asm__ __volatile__( - SMP_LOCK "addl %1,%0" - :"=m" (v->counter) - :"ir" (i), "m" (v->counter)); -} - -/** - * atomic_sub - subtract the atomic variable - * @i: integer value to subtract - * @v: pointer of type atomic_t - * - * Atomically subtracts @i from @v. Note that the guaranteed - * useful range of an atomic_t is only 24 bits. - */ -static __inline__ void atomic_sub(int i, atomic_t *v) -{ - __asm__ __volatile__( - SMP_LOCK "subl %1,%0" - :"=m" (v->counter) - :"ir" (i), "m" (v->counter)); -} - -/** - * atomic_sub_and_test - subtract value from variable and test result - * @i: integer value to subtract - * @v: pointer of type atomic_t - * - * Atomically subtracts @i from @v and returns - * true if the result is zero, or false for all - * other cases. Note that the guaranteed - * useful range of an atomic_t is only 24 bits. - */ -static __inline__ int atomic_sub_and_test(int i, atomic_t *v) -{ - unsigned char c; - - __asm__ __volatile__( - SMP_LOCK "subl %2,%0; sete %1" - :"=m" (v->counter), "=qm" (c) - :"ir" (i), "m" (v->counter) : "memory"); - return c; -} - -/** - * atomic_inc - increment atomic variable - * @v: pointer of type atomic_t - * - * Atomically increments @v by 1. Note that the guaranteed - * useful range of an atomic_t is only 24 bits. - */ -static __inline__ void atomic_inc(atomic_t *v) -{ - __asm__ __volatile__( - SMP_LOCK "incl %0" - :"=m" (v->counter) - :"m" (v->counter)); -} - -/** - * atomic_dec - decrement atomic variable - * @v: pointer of type atomic_t - * - * Atomically decrements @v by 1. Note that the guaranteed - * useful range of an atomic_t is only 24 bits. - */ -static __inline__ void atomic_dec(atomic_t *v) -{ - __asm__ __volatile__( - SMP_LOCK "decl %0" - :"=m" (v->counter) - :"m" (v->counter)); -} - -/** - * atomic_dec_and_test - decrement and test - * @v: pointer of type atomic_t - * - * Atomically decrements @v by 1 and - * returns true if the result is 0, or false for all other - * cases. Note that the guaranteed - * useful range of an atomic_t is only 24 bits. - */ -static __inline__ int atomic_dec_and_test(atomic_t *v) -{ - unsigned char c; - - __asm__ __volatile__( - SMP_LOCK "decl %0; sete %1" - :"=m" (v->counter), "=qm" (c) - :"m" (v->counter) : "memory"); - return c != 0; -} - -/** - * atomic_inc_and_test - increment and test - * @v: pointer of type atomic_t - * - * Atomically increments @v by 1 - * and returns true if the result is zero, or false for all - * other cases. Note that the guaranteed - * useful range of an atomic_t is only 24 bits. - */ -static __inline__ int atomic_inc_and_test(atomic_t *v) -{ - unsigned char c; - - __asm__ __volatile__( - SMP_LOCK "incl %0; sete %1" - :"=m" (v->counter), "=qm" (c) - :"m" (v->counter) : "memory"); - return c != 0; -} - -/** - * atomic_add_negative - add and test if negative - * @v: pointer of type atomic_t - * @i: integer value to add - * - * Atomically adds @i to @v and returns true - * if the result is negative, or false when - * result is greater than or equal to zero. Note that the guaranteed - * useful range of an atomic_t is only 24 bits. - */ -static __inline__ int atomic_add_negative(int i, atomic_t *v) -{ - unsigned char c; - - __asm__ __volatile__( - SMP_LOCK "addl %2,%0; sets %1" - :"=m" (v->counter), "=qm" (c) - :"ir" (i), "m" (v->counter) : "memory"); - return c; -} - -/* These are x86-specific, used by some header files */ -#define atomic_clear_mask(mask, addr) \ -__asm__ __volatile__(SMP_LOCK "andl %0,%1" \ -: : "r" (~(mask)),"m" (*addr) : "memory") - -#define atomic_set_mask(mask, addr) \ -__asm__ __volatile__(SMP_LOCK "orl %0,%1" \ -: : "r" (mask),"m" (*addr) : "memory") - -/* Atomic operations are already serializing on x86 */ -#define smp_mb__before_atomic_dec() barrier() -#define smp_mb__after_atomic_dec() barrier() -#define smp_mb__before_atomic_inc() barrier() -#define smp_mb__after_atomic_inc() barrier() - -#endif /* __ARCH_I386_ATOMIC__ */ - -/***********************************************************************/ - -#else /* !PPC && !i386 */ - -#ifdef __sparc__ - -/* atomic.h: These still suck, but the I-cache hit rate is higher. - * - * Copyright (C) 1996 David S. Miller (davem@caip.rutgers.edu) - * Copyright (C) 2000 Anton Blanchard (anton@linuxcare.com.au) - */ - -#ifndef __ARCH_SPARC_ATOMIC__ -#define __ARCH_SPARC_ATOMIC__ - -typedef struct { volatile int counter; } atomic_t; - -#ifndef CONFIG_SMP - -#define ATOMIC_INIT(i) { (i) } -#define atomic_read(v) ((v)->counter) -#define atomic_set(v, i) (((v)->counter) = i) - -#else -/* We do the bulk of the actual work out of line in two common - * routines in assembler, see arch/sparc/lib/atomic.S for the - * "fun" details. - * - * For SMP the trick is you embed the spin lock byte within - * the word, use the low byte so signedness is easily retained - * via a quick arithmetic shift. It looks like this: - * - * ---------------------------------------- - * | signed 24-bit counter value | lock | atomic_t - * ---------------------------------------- - * 31 8 7 0 - */ - -#define ATOMIC_INIT(i) { (i << 8) } - -static __inline__ int atomic_read(atomic_t *v) -{ - int ret = v->counter; - - while(ret & 0xff) - ret = v->counter; - - return ret >> 8; -} - -#define atomic_set(v, i) (((v)->counter) = ((i) << 8)) -#endif - -static __inline__ int __atomic_add(int i, atomic_t *v) -{ - register volatile int *ptr asm("g1"); - register int increment asm("g2"); - - ptr = &v->counter; - increment = i; - - __asm__ __volatile__( - "mov %%o7, %%g4\n\t" - "call ___atomic_add\n\t" - " add %%o7, 8, %%o7\n" - : "=&r" (increment) - : "0" (increment), "r" (ptr) - : "g3", "g4", "g7", "memory", "cc"); - - return increment; -} - -static __inline__ int __atomic_sub(int i, atomic_t *v) -{ - register volatile int *ptr asm("g1"); - register int increment asm("g2"); - - ptr = &v->counter; - increment = i; - - __asm__ __volatile__( - "mov %%o7, %%g4\n\t" - "call ___atomic_sub\n\t" - " add %%o7, 8, %%o7\n" - : "=&r" (increment) - : "0" (increment), "r" (ptr) - : "g3", "g4", "g7", "memory", "cc"); - - return increment; -} - -#define atomic_add(i, v) ((void)__atomic_add((i), (v))) -#define atomic_sub(i, v) ((void)__atomic_sub((i), (v))) - -#define atomic_dec_return(v) __atomic_sub(1, (v)) -#define atomic_inc_return(v) __atomic_add(1, (v)) - -#define atomic_sub_and_test(i, v) (__atomic_sub((i), (v)) == 0) -#define atomic_dec_and_test(v) (__atomic_sub(1, (v)) == 0) - -#define atomic_inc(v) ((void)__atomic_add(1, (v))) -#define atomic_dec(v) ((void)__atomic_sub(1, (v))) - -#define atomic_add_negative(i, v) (__atomic_add((i), (v)) < 0) - -/* Atomic operations are already serializing */ -#define smp_mb__before_atomic_dec() barrier() -#define smp_mb__after_atomic_dec() barrier() -#define smp_mb__before_atomic_inc() barrier() -#define smp_mb__after_atomic_inc() barrier() - - -#endif /* !(__ARCH_SPARC_ATOMIC__) */ - -/***********************************************************************/ - -#else - -#ifdef __ia64__ - -#ifndef __ARCH_IA64_ATOMIC__ -#define __ARCH_IA64_ATOMIC__ - -typedef volatile int atomic_t; - -inline -int -atomic_read (const atomic_t * a) -{ - return *a; -} - -inline -void -atomic_set(atomic_t *a, int v) -{ - *a = v; -} - -inline -void -atomic_inc (atomic_t *v) -{ - int old, r; - - do { - old = atomic_read(v); - __asm__ __volatile__ ("mov ar.ccv=%0;;" :: "rO" (old)); - __asm__ __volatile__ ("cmpxchg4.acq %0=[%1],%2,ar.ccv" - : "=r"(r) : "r"(v), "r"(old + 1) - : "memory"); - } while (r != old); -} - -inline -void -atomic_dec (atomic_t *v) -{ - int old, r; - - do { - old = atomic_read(v); - __asm__ __volatile__ ("mov ar.ccv=%0;;" :: "rO" (old)); - __asm__ __volatile__ ("cmpxchg4.acq %0=[%1],%2,ar.ccv" - : "=r"(r) : "r"(v), "r"(old - 1) - : "memory"); - } while (r != old); -} - -inline -int -atomic_dec_and_test (atomic_t *v) -{ - int old, r; - - do { - old = atomic_read(v); - __asm__ __volatile__ ("mov ar.ccv=%0;;" :: "rO" (old)); - __asm__ __volatile__ ("cmpxchg4.acq %0=[%1],%2,ar.ccv" - : "=r"(r) : "r"(v), "r"(old - 1) - : "memory"); - } while (r != old); - return old != 1; -} - -#endif /* !(__ARCH_IA64_ATOMIC__) */ - -#else - -#ifdef __alpha__ - -#ifndef _ALPHA_ATOMIC_H -#define _ALPHA_ATOMIC_H - -/* - * Atomic operations that C can't guarantee us. Useful for - * resource counting etc... - * - * But use these as seldom as possible since they are much slower - * than regular operations. - */ - - -/* - * Counter is volatile to make sure gcc doesn't try to be clever - * and move things around on us. We need to use _exactly_ the address - * the user gave us, not some alias that contains the same information. - */ -typedef struct { volatile int counter; } atomic_t; - -#define ATOMIC_INIT(i) ( (atomic_t) { (i) } ) - -#define atomic_read(v) ((v)->counter) -#define atomic_set(v,i) ((v)->counter = (i)) - -/* - * To get proper branch prediction for the main line, we must branch - * forward to code at the end of this object's .text section, then - * branch back to restart the operation. - */ - -static __inline__ void atomic_add(int i, atomic_t * v) -{ - unsigned long temp; - __asm__ __volatile__( - "1: ldl_l %0,%1\n" - " addl %0,%2,%0\n" - " stl_c %0,%1\n" - " beq %0,2f\n" - ".subsection 2\n" - "2: br 1b\n" - ".previous" - :"=&r" (temp), "=m" (v->counter) - :"Ir" (i), "m" (v->counter)); -} - -static __inline__ void atomic_sub(int i, atomic_t * v) -{ - unsigned long temp; - __asm__ __volatile__( - "1: ldl_l %0,%1\n" - " subl %0,%2,%0\n" - " stl_c %0,%1\n" - " beq %0,2f\n" - ".subsection 2\n" - "2: br 1b\n" - ".previous" - :"=&r" (temp), "=m" (v->counter) - :"Ir" (i), "m" (v->counter)); -} - -/* - * Same as above, but return the result value - */ -static __inline__ long atomic_add_return(int i, atomic_t * v) -{ - long temp, result; - __asm__ __volatile__( - "1: ldl_l %0,%1\n" - " addl %0,%3,%2\n" - " addl %0,%3,%0\n" - " stl_c %0,%1\n" - " beq %0,2f\n" - " mb\n" - ".subsection 2\n" - "2: br 1b\n" - ".previous" - :"=&r" (temp), "=m" (v->counter), "=&r" (result) - :"Ir" (i), "m" (v->counter) : "memory"); - return result; -} - -static __inline__ long atomic_sub_return(int i, atomic_t * v) -{ - long temp, result; - __asm__ __volatile__( - "1: ldl_l %0,%1\n" - " subl %0,%3,%2\n" - " subl %0,%3,%0\n" - " stl_c %0,%1\n" - " beq %0,2f\n" - " mb\n" - ".subsection 2\n" - "2: br 1b\n" - ".previous" - :"=&r" (temp), "=m" (v->counter), "=&r" (result) - :"Ir" (i), "m" (v->counter) : "memory"); - return result; -} - -#define atomic_dec_return(v) atomic_sub_return(1,(v)) -#define atomic_inc_return(v) atomic_add_return(1,(v)) - -#define atomic_sub_and_test(i,v) (atomic_sub_return((i), (v)) == 0) -#define atomic_dec_and_test(v) (atomic_sub_return(1, (v)) == 0) - -#define atomic_inc(v) atomic_add(1,(v)) -#define atomic_dec(v) atomic_sub(1,(v)) - -#define smp_mb__before_atomic_dec() smp_mb() -#define smp_mb__after_atomic_dec() smp_mb() -#define smp_mb__before_atomic_inc() smp_mb() -#define smp_mb__after_atomic_inc() smp_mb() - -#endif /* _ALPHA_ATOMIC_H */ - -#else - -#ifdef __s390__ - -#ifndef __ARCH_S390_ATOMIC__ -#define __ARCH_S390_ATOMIC__ - -/* - * include/asm-s390/atomic.h - * - * S390 version - * Copyright (C) 1999,2000 IBM Deutschland Entwicklung GmbH, IBM Corporation - * Author(s): Martin Schwidefsky (schwidefsky@de.ibm.com), - * Denis Joseph Barrow - * - * Derived from "include/asm-i386/bitops.h" - * Copyright (C) 1992, Linus Torvalds - * - */ - -/* - * Atomic operations that C can't guarantee us. Useful for - * resource counting etc.. - * S390 uses 'Compare And Swap' for atomicity in SMP enviroment - */ - -typedef struct { volatile int counter; } __attribute__ ((aligned (4))) atomic_t; -#define ATOMIC_INIT(i) { (i) } - -#define atomic_eieio() __asm__ __volatile__ ("BCR 15,0") - -#define __CS_LOOP(old_val, new_val, ptr, op_val, op_string) \ - __asm__ __volatile__(" l %0,0(%2)\n" \ - "0: lr %1,%0\n" \ - op_string " %1,%3\n" \ - " cs %0,%1,0(%2)\n" \ - " jl 0b" \ - : "=&d" (old_val), "=&d" (new_val) \ - : "a" (ptr), "d" (op_val) : "cc" ); - -#define atomic_read(v) ((v)->counter) -#define atomic_set(v,i) (((v)->counter) = (i)) - -static __inline__ void atomic_add(int i, atomic_t *v) -{ - int old_val, new_val; - __CS_LOOP(old_val, new_val, v, i, "ar"); -} - -static __inline__ int atomic_add_return (int i, atomic_t *v) -{ - int old_val, new_val; - __CS_LOOP(old_val, new_val, v, i, "ar"); - return new_val; -} - -static __inline__ int atomic_add_negative(int i, atomic_t *v) -{ - int old_val, new_val; - __CS_LOOP(old_val, new_val, v, i, "ar"); - return new_val < 0; -} - -static __inline__ void atomic_sub(int i, atomic_t *v) -{ - int old_val, new_val; - __CS_LOOP(old_val, new_val, v, i, "sr"); -} - -static __inline__ void atomic_inc(volatile atomic_t *v) -{ - int old_val, new_val; - __CS_LOOP(old_val, new_val, v, 1, "ar"); -} - -static __inline__ int atomic_inc_return(volatile atomic_t *v) -{ - int old_val, new_val; - __CS_LOOP(old_val, new_val, v, 1, "ar"); - return new_val; -} - -static __inline__ int atomic_inc_and_test(volatile atomic_t *v) -{ - int old_val, new_val; - __CS_LOOP(old_val, new_val, v, 1, "ar"); - return new_val != 0; -} - -static __inline__ void atomic_dec(volatile atomic_t *v) -{ - int old_val, new_val; - __CS_LOOP(old_val, new_val, v, 1, "sr"); -} - -static __inline__ int atomic_dec_return(volatile atomic_t *v) -{ - int old_val, new_val; - __CS_LOOP(old_val, new_val, v, 1, "sr"); - return new_val; -} - -static __inline__ int atomic_dec_and_test(volatile atomic_t *v) -{ - int old_val, new_val; - __CS_LOOP(old_val, new_val, v, 1, "sr"); - return new_val == 0; -} - -static __inline__ void atomic_clear_mask(unsigned long mask, atomic_t *v) -{ - int old_val, new_val; - __CS_LOOP(old_val, new_val, v, ~mask, "nr"); -} - -static __inline__ void atomic_set_mask(unsigned long mask, atomic_t *v) -{ - int old_val, new_val; - __CS_LOOP(old_val, new_val, v, mask, "or"); -} - -/* - returns 0 if expected_oldval==value in *v ( swap was successful ) - returns 1 if unsuccessful. -*/ -static __inline__ int -atomic_compare_and_swap(int expected_oldval,int new_val,atomic_t *v) -{ - int retval; - - __asm__ __volatile__( - " lr 0,%2\n" - " cs 0,%3,0(%1)\n" - " ipm %0\n" - " srl %0,28\n" - "0:" - : "=&d" (retval) - : "a" (v), "d" (expected_oldval) , "d" (new_val) - : "0", "cc"); - return retval; -} - -/* - Spin till *v = expected_oldval then swap with newval. - */ -static __inline__ void -atomic_compare_and_swap_spin(int expected_oldval,int new_val,atomic_t *v) -{ - __asm__ __volatile__( - "0: lr 0,%1\n" - " cs 0,%2,0(%0)\n" - " jl 0b\n" - : : "a" (v), "d" (expected_oldval) , "d" (new_val) - : "cc", "0" ); -} - -#define smp_mb__before_atomic_dec() smp_mb() -#define smp_mb__after_atomic_dec() smp_mb() -#define smp_mb__before_atomic_inc() smp_mb() -#define smp_mb__after_atomic_inc() smp_mb() - -#endif /* __ARCH_S390_ATOMIC __ */ - -#else - -#ifdef __mips__ - -/* - * Atomic operations that C can't guarantee us. Useful for - * resource counting etc.. - * - * But use these as seldom as possible since they are much more slower - * than regular operations. - * - * This file is subject to the terms and conditions of the GNU General Public - * License. See the file "COPYING" in the main directory of this archive - * for more details. - * - * Copyright (C) 1996, 1997, 2000 by Ralf Baechle - */ -#ifndef __ASM_ATOMIC_H -#define __ASM_ATOMIC_H - -typedef struct { volatile int counter; } atomic_t; - -#define ATOMIC_INIT(i) { (i) } - -/* - * atomic_read - read atomic variable - * @v: pointer of type atomic_t - * - * Atomically reads the value of @v. Note that the guaranteed - * useful range of an atomic_t is only 24 bits. - */ -#define atomic_read(v) ((v)->counter) - -/* - * atomic_set - set atomic variable - * @v: pointer of type atomic_t - * @i: required value - * - * Atomically sets the value of @v to @i. Note that the guaranteed - * useful range of an atomic_t is only 24 bits. - */ -#define atomic_set(v,i) ((v)->counter = (i)) - -/* - * ... while for MIPS II and better we can use ll/sc instruction. This - * implementation is SMP safe ... - */ - -/* - * atomic_add - add integer to atomic variable - * @i: integer value to add - * @v: pointer of type atomic_t - * - * Atomically adds @i to @v. Note that the guaranteed useful range - * of an atomic_t is only 24 bits. - */ -extern __inline__ void atomic_add(int i, atomic_t * v) -{ - unsigned long temp; - - __asm__ __volatile__( - ".set push # atomic_add\n" - ".set mips2 \n" - "1: ll %0, %1 \n" - " addu %0, %2 \n" - " sc %0, %1 \n" - " beqz %0, 1b \n" - ".set pop \n" - : "=&r" (temp), "=m" (v->counter) - : "Ir" (i), "m" (v->counter)); -} - -/* - * atomic_sub - subtract the atomic variable - * @i: integer value to subtract - * @v: pointer of type atomic_t - * - * Atomically subtracts @i from @v. Note that the guaranteed - * useful range of an atomic_t is only 24 bits. - */ -extern __inline__ void atomic_sub(int i, atomic_t * v) -{ - unsigned long temp; - - __asm__ __volatile__( - ".set push # atomic_sub\n" - ".set mips2 \n" - "1: ll %0, %1 \n" - " subu %0, %2 \n" - " sc %0, %1 \n" - " beqz %0, 1b \n" - ".set pop \n" - : "=&r" (temp), "=m" (v->counter) - : "Ir" (i), "m" (v->counter)); -} - -/* - * Same as above, but return the result value - */ -extern __inline__ int atomic_add_return(int i, atomic_t * v) -{ - unsigned long temp, result; - - __asm__ __volatile__( - ".set push # atomic_add_return\n" - ".set mips2 \n" - ".set noreorder \n" - "1: ll %1, %2 \n" - " addu %0, %1, %3 \n" - " sc %0, %2 \n" - " beqz %0, 1b \n" - " addu %0, %1, %3 \n" - " sync \n" - ".set pop \n" - : "=&r" (result), "=&r" (temp), "=m" (v->counter) - : "Ir" (i), "m" (v->counter) - : "memory"); - - return result; -} - -extern __inline__ int atomic_sub_return(int i, atomic_t * v) -{ - unsigned long temp, result; - - __asm__ __volatile__( - ".set push # atomic_sub_return\n" - ".set mips2 \n" - ".set noreorder \n" - "1: ll %1, %2 \n" - " subu %0, %1, %3 \n" - " sc %0, %2 \n" - " beqz %0, 1b \n" - " subu %0, %1, %3 \n" - " sync \n" - ".set pop \n" - : "=&r" (result), "=&r" (temp), "=m" (v->counter) - : "Ir" (i), "m" (v->counter) - : "memory"); - - return result; -} - -#define atomic_dec_return(v) atomic_sub_return(1,(v)) -#define atomic_inc_return(v) atomic_add_return(1,(v)) - -/* - * atomic_sub_and_test - subtract value from variable and test result - * @i: integer value to subtract - * @v: pointer of type atomic_t - * - * Atomically subtracts @i from @v and returns - * true if the result is zero, or false for all - * other cases. Note that the guaranteed - * useful range of an atomic_t is only 24 bits. - */ -#define atomic_sub_and_test(i,v) (atomic_sub_return((i), (v)) == 0) - -/* - * atomic_inc_and_test - increment and test - * @v: pointer of type atomic_t - * - * Atomically increments @v by 1 - * and returns true if the result is zero, or false for all - * other cases. Note that the guaranteed - * useful range of an atomic_t is only 24 bits. - */ -#define atomic_inc_and_test(v) (atomic_inc_return(1, (v)) == 0) - -/* - * atomic_dec_and_test - decrement by 1 and test - * @v: pointer of type atomic_t - * - * Atomically decrements @v by 1 and - * returns true if the result is 0, or false for all other - * cases. Note that the guaranteed - * useful range of an atomic_t is only 24 bits. - */ -#define atomic_dec_and_test(v) (atomic_sub_return(1, (v)) == 0) - -/* - * atomic_inc - increment atomic variable - * @v: pointer of type atomic_t - * - * Atomically increments @v by 1. Note that the guaranteed - * useful range of an atomic_t is only 24 bits. - */ -#define atomic_inc(v) atomic_add(1,(v)) - -/* - * atomic_dec - decrement and test - * @v: pointer of type atomic_t - * - * Atomically decrements @v by 1. Note that the guaranteed - * useful range of an atomic_t is only 24 bits. - */ -#define atomic_dec(v) atomic_sub(1,(v)) - -/* - * atomic_add_negative - add and test if negative - * @v: pointer of type atomic_t - * @i: integer value to add - * - * Atomically adds @i to @v and returns true - * if the result is negative, or false when - * result is greater than or equal to zero. Note that the guaranteed - * useful range of an atomic_t is only 24 bits. - * - * Currently not implemented for MIPS. - */ - -/* Atomic operations are already serializing */ -#define smp_mb__before_atomic_dec() smp_mb() -#define smp_mb__after_atomic_dec() smp_mb() -#define smp_mb__before_atomic_inc() smp_mb() -#define smp_mb__after_atomic_inc() smp_mb() - -#endif /* __ASM_ATOMIC_H */ - -#else - -#if defined(__m68k__) - -#ifndef __ARCH_M68K_ATOMIC__ -#define __ARCH_M68K_ATOMIC__ - -/* - * Atomic operations that C can't guarantee us. Useful for - * resource counting etc.. - */ - -/* - * We do not have SMP m68k systems, so we don't have to deal with that. - */ - -typedef struct { int counter; } atomic_t; -#define ATOMIC_INIT(i) { (i) } - -#define atomic_read(v) ((v)->counter) -#define atomic_set(v, i) (((v)->counter) = i) - -static __inline__ void atomic_add(int i, atomic_t *v) -{ - __asm__ __volatile__("addl %1,%0" : "=m" (*v) : "id" (i), "0" (*v)); -} - -static __inline__ void atomic_sub(int i, atomic_t *v) -{ - __asm__ __volatile__("subl %1,%0" : "=m" (*v) : "id" (i), "0" (*v)); -} - -static __inline__ void atomic_inc(volatile atomic_t *v) -{ - __asm__ __volatile__("addql #1,%0" : "=m" (*v): "0" (*v)); -} - -static __inline__ void atomic_dec(volatile atomic_t *v) -{ - __asm__ __volatile__("subql #1,%0" : "=m" (*v): "0" (*v)); -} - -static __inline__ int atomic_dec_and_test(volatile atomic_t *v) -{ - char c; - __asm__ __volatile__("subql #1,%1; seq %0" : "=d" (c), "=m" (*v): "1" (*v)); - return c != 0; -} - -#define atomic_clear_mask(mask, v) \ - __asm__ __volatile__("andl %1,%0" : "=m" (*v) : "id" (~(mask)),"0"(*v)) - -#define atomic_set_mask(mask, v) \ - __asm__ __volatile__("orl %1,%0" : "=m" (*v) : "id" (mask),"0"(*v)) - -/* Atomic operations are already serializing */ -#define smp_mb__before_atomic_dec() barrier() -#define smp_mb__after_atomic_dec() barrier() -#define smp_mb__before_atomic_inc() barrier() -#define smp_mb__after_atomic_inc() barrier() - -#endif /* __ARCH_M68K_ATOMIC __ */ - -#else - -#warning libs/pbd has no implementation of strictly atomic operations for your hardware. - -#define __NO_STRICT_ATOMIC -#ifdef __NO_STRICT_ATOMIC - -/* - * Because the implementations from the kernel (where all these come - * from) use cli and spinlocks for hppa and arm... - */ - -typedef struct { volatile int counter; } atomic_t; - -#define ATOMIC_INIT(i) ( (atomic_t) { (i) } ) - -#define atomic_read(v) ((v)->counter) -#define atomic_set(v,i) ((v)->counter = (i)) - -static __inline__ void atomic_inc(atomic_t *v) -{ - v->counter++; -} - -static __inline__ void atomic_dec(atomic_t *v) -{ - v->counter--; -} - -static __inline__ int atomic_dec_and_test(atomic_t *v) -{ - int res; - v->counter--; - res = v->counter; - return res == 0; -} - -static __inline__ int atomic_inc_and_test(atomic_t *v) -{ - int res; - v->counter++; - res = v->counter; - return res == 0; -} - -# endif /* __NO_STRICT_ATOMIC */ -# endif /* m68k */ -# endif /* mips */ -# endif /* s390 */ -# endif /* alpha */ -# endif /* ia64 */ -# endif /* sparc */ -# endif /* i386 */ -# endif /* ppc */ - -#endif /* __libpbd_atomic_h__ */ - diff --git a/libs/pbd3/pbd/basename.h b/libs/pbd3/pbd/basename.h index 01f40b6b6a..35aebe166c 100644 --- a/libs/pbd3/pbd/basename.h +++ b/libs/pbd3/pbd/basename.h @@ -6,9 +6,7 @@ namespace PBD { -extern char *basename (const char *); -extern std::string basename (const std::string); -extern std::string basename_nosuffix (const std::string); +extern std::string basename_nosuffix (const std::string&); }; diff --git a/libs/pbd3/pbd/datum.h b/libs/pbd3/pbd/datum.h deleted file mode 100644 index 1f2704b429..0000000000 --- a/libs/pbd3/pbd/datum.h +++ /dev/null @@ -1,57 +0,0 @@ -/* - Copyright (C) 1998-99 Paul Barton-Davis - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ - -#ifndef __qm_datum_h__ -#define __qm_datum_h__ - -/* A basic data type used whenever we want to represent - something that might be a string or a number. -*/ - -struct Datum { - enum Type { - String, - Numeric, - }; - Type type; - union { - const char *str; - float n; - }; - - Datum &operator=(float val) { - type = Numeric; - n = val; - return *this; - } - - Datum &operator=(int val) { - type = Numeric; - n=(float) val; - return *this; - } - - Datum &operator=(const char *val) { - type = String; - str = val; - return *this; - } -}; - -#endif // __qm_datum_h__ diff --git a/libs/pbd3/pbd/dirname.h b/libs/pbd3/pbd/dirname.h deleted file mode 100644 index 5e63ddb55d..0000000000 --- a/libs/pbd3/pbd/dirname.h +++ /dev/null @@ -1,11 +0,0 @@ -#ifndef __stupid_dirname_h__ -#define __stupid_dirname_h__ - - -#include - -namespace PBD { - extern char *dirname (const char *); - extern std::string dirname (const std::string); -} -#endif // __stupid_dirname_h__ diff --git a/libs/pbd3/pbd/ellipsoid.h b/libs/pbd3/pbd/ellipsoid.h deleted file mode 100644 index 3758e415c2..0000000000 --- a/libs/pbd3/pbd/ellipsoid.h +++ /dev/null @@ -1,74 +0,0 @@ -/* - Copyright (C) 1998-99 Paul Barton-Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ - -#ifndef __qm_ellipsoid_h__ -#define __qm_ellipsoid_h__ - -struct Arc -{ - int rect_x; - int rect_y; - int rect_h; - int rect_w; - int start_angle; - int arc_angle; - bool counter_clockwise; -}; - -class Ellipsoid -{ - int start_x; - int end_x; - int start_y; - int end_y; - static const unsigned int narcs; - - public: - Arc arc[2]; - - Ellipsoid () { - start_x = -1; - end_x = -1; - } - - bool ready() { return start_x != -1 && end_x != -1; } - void set_start (int x, int y); - void set_end (int x, int y); - void compute (); - - void set_start_angle (int n, int which_arc = -1) { - if (which_arc < 0) { - arc[0].start_angle = n * 64; - arc[1].start_angle = n * 64; - } else if (which_arc < (int) narcs) { - arc[which_arc].start_angle = n * 64; - } - } - void set_arc_angle (int n, int which_arc = -1) { - if (which_arc < 0) { - arc[0].arc_angle = n * 64; - arc[1].arc_angle = n * 64; - } else if (which_arc < (int) narcs) { - arc[which_arc].arc_angle = n * 64; - } - } -}; - -#endif // __qm_ellipsoid_h__ diff --git a/libs/pbd3/pbd/foreach.h b/libs/pbd3/pbd/foreach.h deleted file mode 100644 index 5102d81bb0..0000000000 --- a/libs/pbd3/pbd/foreach.h +++ /dev/null @@ -1,42 +0,0 @@ -/* - Copyright (C) 2002 Paul Barton-Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ - -#ifndef __lib_pbd_foreach_h__ -#define __lib_pbd_foreach_h__ - -template void foreach (Iter first, Iter last, void (T::*method)()) { - for (; first != last; ++first) { - ((*first).*method)(); - } -} - -template void foreach (Iter first, Iter last, void (T::*method)(A a), A arg) { - for (; first != last; ++first) { - ((*first).*method)(arg); - } -} - -template void foreach (Iter first, Iter last, void (T::*method)(A1, A2), A1 arg1, A2 arg2) { - for (; first != last; ++first) { - ((*first).*method)(arg1, arg2); - } -} - -#endif /* __lib_pbd_foreach_h__ */ diff --git a/libs/pbd3/pbd/lock_free_fifo.h b/libs/pbd3/pbd/lock_free_fifo.h deleted file mode 100644 index cbe653fcb5..0000000000 --- a/libs/pbd3/pbd/lock_free_fifo.h +++ /dev/null @@ -1,86 +0,0 @@ -/* - Copyright (C) 2000 Paul Barton-Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ - -#ifndef __pbd_lockfree_fifo_h__ -#define __pbd_lockfree_fifo_h__ - -#include -#include - -template -class LockFreeFIFO -{ -public: - LockFreeFIFO (int sz) { - size = sz; - push_ptr = 0; - pop_ptr = 0; - buf = new T[size]; - }; - - virtual ~LockFreeFIFO() { - delete [] buf; - } - - - int pop (T& r) { - if (pop_ptr == push_ptr) { - return -1; - } else { - r = buf[pop_ptr]; - pop_ptr++; - if (pop_ptr >= size) { - pop_ptr = 0; - } - return 0; - } - } - - int top (T& r) { - if (pop_ptr == push_ptr) { - return -1; - } else { - r = buf[pop_ptr]; - return 0; - } - } - - int push (T& t) { - if ((size_t) abs (static_cast(push_ptr - pop_ptr)) < size) { - buf[push_ptr] = t; - push_ptr++; - if (push_ptr >= size) { - push_ptr = 0; - } - return 0; - } else { - return -1; - } - } - - protected: - T *buf; - volatile size_t push_ptr; - volatile size_t pop_ptr; - size_t size; -}; - - -#endif /* __pbd_lockfree_fifo_h__ */ diff --git a/libs/pbd3/pbd/lockmonitor.h b/libs/pbd3/pbd/lockmonitor.h deleted file mode 100644 index c91a041e9b..0000000000 --- a/libs/pbd3/pbd/lockmonitor.h +++ /dev/null @@ -1,325 +0,0 @@ -/* - Copyright (C) 2000 Paul Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ - -#ifndef __pbd_lockmonitor_h__ -#define __pbd_lockmonitor_h__ - -#include -#include - -#undef DEBUG_LOCK_MONITOR - -#ifdef DEBUG_LOCK_MONITOR -#include -#include -#endif - -namespace PBD -{ -class Lock { - public: - Lock() { pthread_mutex_init (&_mutex, 0); } - virtual ~Lock() {} - - virtual int lock () { return pthread_mutex_lock (&_mutex); } - virtual int unlock() { return pthread_mutex_unlock (&_mutex); } - - pthread_mutex_t *mutex() { return &_mutex; } - - protected: - pthread_mutex_t _mutex; -}; - -class NonBlockingLock : public Lock { - public: - NonBlockingLock() {} - ~NonBlockingLock(){} - - int lock () { return pthread_mutex_lock (&_mutex); } - int trylock () { return pthread_mutex_trylock (&_mutex); } - int unlock() { return pthread_mutex_unlock (&_mutex); } -}; - -class RWLock { - public: - RWLock() { pthread_rwlock_init (&_mutex, 0); } - virtual ~RWLock() { pthread_rwlock_destroy(&_mutex); } - - virtual int write_lock () { return pthread_rwlock_wrlock (&_mutex); } - virtual int read_lock () { return pthread_rwlock_rdlock (&_mutex); } - virtual int unlock() { return pthread_rwlock_unlock (&_mutex); } - - pthread_rwlock_t *mutex() { return &_mutex; } - - protected: - pthread_rwlock_t _mutex; -}; - -class NonBlockingRWLock : public RWLock { - public: - NonBlockingRWLock() {} - ~NonBlockingRWLock(){} - - int write_trylock () { return pthread_rwlock_trywrlock (&_mutex); } - int read_trylock () { return pthread_rwlock_tryrdlock (&_mutex); } -}; - - -class LockMonitor -{ - public: - LockMonitor (Lock& lck, unsigned long l, const char *f) - : lock (lck) -#ifdef DEBUG_LOCK_MONITOR - , line (l), file (f) -#endif - { - -#ifdef DEBUG_LOCK_MONITOR - unsigned long long when; - when = get_cycles(); - cerr << when << " lock " << &lock << " at " << line << " in " << file << endl; -#endif - lock.lock (); -#ifdef DEBUG_LOCK_MONITOR - when = get_cycles(); - cerr << '\t' << when - << " locked: " - << &lock << " at " - << line << " in " << file << endl; -#endif - } - - ~LockMonitor () { - lock.unlock (); -#ifdef DEBUG_LOCK_MONITOR - unsigned long long when; - when = get_cycles(); - cerr << '\t' << when << ' ' - << " UNLOCKED " - << &lock << " at " - << line << " in " << file << endl; -#endif - } - private: - Lock& lock; -#ifdef DEBUG_LOCK_MONITOR - unsigned long line; - const char * file; -#endif -}; - -class TentativeLockMonitor -{ - public: - TentativeLockMonitor (NonBlockingLock& lck, unsigned long l, const char *f) - : lock (lck) -#ifdef DEBUG_LOCK_MONITOR - , line (l), file (f) -#endif - { - -#ifdef DEBUG_LOCK_MONITOR - unsigned long long when; - when = get_cycles(); - cerr << when << " tentative lock " << &lock << " at " << line << " in " << file << endl; -#endif - _locked = (lock.trylock() == 0); - -#ifdef DEBUG_LOCK_MONITOR - when = get_cycles(); - cerr << '\t' << when << ' ' - << _locked - << " lock: " - << &lock << " at " - << line << " in " << file << endl; -#endif - } - - ~TentativeLockMonitor () { - if (_locked) { - lock.unlock (); -#ifdef DEBUG_LOCK_MONITOR - unsigned long long when; - when = get_cycles(); - cerr << '\t' << when << ' ' - << " UNLOCKED " - << &lock << " at " - << line << " in " << file << endl; -#endif - } - } - - bool locked() { return _locked; } - - private: - NonBlockingLock& lock; - bool _locked; -#ifdef DEBUG_LOCK_MONITOR - unsigned long line; - const char * file; -#endif -}; - -class SpinLockMonitor -{ - public: - SpinLockMonitor (pthread_mutex_t *lck, unsigned long l, const char *f) - : lock (lck) -#ifdef DEBUG_LOCK_MONITOR - , line (l), file (f) -#endif - { - -#ifdef DEBUG_LOCK_MONITOR - unsigned long long when; - when = get_cycles(); - cerr << when << " spinlock " << lck << " at " << line << " in " << file << endl; -#endif - pthread_mutex_spinlock (lck); -#ifdef DEBUG_LOCK_MONITOR - when = get_cycles(); - cerr << '\t' << when - << " locked at " - << &lock << " at " - << line << " in " << file << endl; -#endif - } - - ~SpinLockMonitor () { - pthread_mutex_unlock (lock); - } - private: - pthread_mutex_t *lock; -#ifdef DEBUG_LOCK_MONITOR - unsigned long line; - const char * file; -#endif -}; - - -class RWLockMonitor -{ - public: - RWLockMonitor (RWLock& lck, bool write, unsigned long l, const char *f) - : lock (lck) -#ifdef DEBUG_LOCK_MONITOR - , line (l), file (f) -#endif - { - -#ifdef DEBUG_LOCK_MONITOR - unsigned long long when; - when = get_cycles(); - cerr << when << " lock " << &lock << " at " << line << " in " << file << endl; -#endif - if (write) { - lock.write_lock (); - } else { - lock.read_lock (); - } -#ifdef DEBUG_LOCK_MONITOR - when = get_cycles(); - cerr << '\t' << when - << " locked: " - << &lock << " at " - << line << " in " << file << endl; -#endif - } - - ~RWLockMonitor () { - lock.unlock (); -#ifdef DEBUG_LOCK_MONITOR - unsigned long long when; - when = get_cycles(); - cerr << '\t' << when << ' ' - << " UNLOCKED " - << &lock << " at " - << line << " in " << file << endl; -#endif - } - private: - RWLock& lock; -#ifdef DEBUG_LOCK_MONITOR - unsigned long line; - const char * file; -#endif -}; - -class TentativeRWLockMonitor -{ - public: - TentativeRWLockMonitor (NonBlockingRWLock& lck, bool write, unsigned long l, const char *f) - : lock (lck) -#ifdef DEBUG_LOCK_MONITOR - , line (l), file (f) -#endif - { - -#ifdef DEBUG_LOCK_MONITOR - unsigned long long when; - when = get_cycles(); - cerr << when << " tentative lock " << &lock << " at " << line << " in " << file << endl; -#endif - if (write) { - _locked = (lock.write_trylock() == 0); - } else { - _locked = (lock.read_trylock() == 0); - } - -#ifdef DEBUG_LOCK_MONITOR - when = get_cycles(); - cerr << '\t' << when << ' ' - << _locked - << " lock: " - << &lock << " at " - << line << " in " << file << endl; -#endif - } - - ~TentativeRWLockMonitor () { - if (_locked) { - lock.unlock (); -#ifdef DEBUG_LOCK_MONITOR - unsigned long long when; - when = get_cycles(); - cerr << '\t' << when << ' ' - << " UNLOCKED " - << &lock << " at " - << line << " in " << file << endl; -#endif - } - } - - bool locked() { return _locked; } - - private: - NonBlockingRWLock& lock; - bool _locked; -#ifdef DEBUG_LOCK_MONITOR - unsigned long line; - const char * file; -#endif -}; - - -} /* namespace */ - -#endif /* __pbd_lockmonitor_h__*/ diff --git a/libs/pbd3/pbd/pool.h b/libs/pbd3/pbd/pool.h index c8e9740acd..f8e19e72fb 100644 --- a/libs/pbd3/pbd/pool.h +++ b/libs/pbd3/pbd/pool.h @@ -23,7 +23,9 @@ #include #include -#include + +#include + #include class Pool @@ -53,7 +55,7 @@ class SingleAllocMultiReleasePool : public Pool virtual void release (void *); private: - pthread_mutex_t lock; + Glib::Mutex* m_lock; }; @@ -67,8 +69,7 @@ class MultiAllocSingleReleasePool : public Pool virtual void release (void *); private: - pthread_mutex_t lock; + Glib::Mutex* m_lock; }; - #endif // __qm_pool_h__ diff --git a/libs/pbd3/pbd/position.h b/libs/pbd3/pbd/position.h deleted file mode 100644 index c8241af085..0000000000 --- a/libs/pbd3/pbd/position.h +++ /dev/null @@ -1,38 +0,0 @@ -/* - Copyright (C) 1998-99 Paul Barton-Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ - -#ifndef __qui_position_h__ -#define __qui_position_h__ - -enum Position { - Top, - Left, - Right, - Bottom, - UpperLeft, - LowerLeft, - UpperRight, - LowerRight, - Center, - Nowhere, -}; - - -#endif // __qui_position_h__ diff --git a/libs/pbd3/pbd/precision_timer.h b/libs/pbd3/pbd/precision_timer.h deleted file mode 100644 index a103b4800d..0000000000 --- a/libs/pbd3/pbd/precision_timer.h +++ /dev/null @@ -1,61 +0,0 @@ -/* - Copyright (C) 1998-99 Paul Barton-Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ - -#ifndef __precision_timer_h__ -#define __precision_timer_h__ - -#include - -typedef cycles_t precision_time_t; - -class PrecisionTimer { - public: - PrecisionTimer (); - - /* returns current time in microseconds since - the time base was created (which may be - the same as when the PrecisionTimer was - created or it may not). - */ - -#ifdef PBD_HAVE_CYCLE_COUNTER - - precision_time_t current () { - return get_cycles() / cycles_per_usec; - } - -#else /* !HAVE_CYCLE_COUNTER */ - - precision_time_t current () { - struct timeval now; - gettimeofday (&now, 0); - return (precision_time_t) ((now.tv_sec * 1000000) + now.tv_usec); - } - -#endif /* HAVE_CYCLE_COUNTER */ - - private: - int get_mhz(); - static precision_time_t cycles_per_usec; -}; - -#endif // __precision_timer.h - - diff --git a/libs/pbd3/pbd/pthread_spinlock.h b/libs/pbd3/pbd/pthread_spinlock.h deleted file mode 100644 index 71835221fa..0000000000 --- a/libs/pbd3/pbd/pthread_spinlock.h +++ /dev/null @@ -1,29 +0,0 @@ -/* - Copyright (C) 1998-99 Paul Barton-Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ -#ifndef __pthread_mutex_spinlock_h__ -#define __pthread_mutex_spinlock_h__ - -#include - -extern unsigned int pthread_calibrate_spinlimit (); -extern void pthread_set_spinlimit (unsigned int spins); -extern int pthread_mutex_spinlock (pthread_mutex_t *mp); - -#endif // __pthread_mutex_spinlock_h__ diff --git a/libs/pbd3/pbd/rcpointer.h b/libs/pbd3/pbd/rcpointer.h deleted file mode 100644 index c634208437..0000000000 --- a/libs/pbd3/pbd/rcpointer.h +++ /dev/null @@ -1,61 +0,0 @@ -/* - Copyright (C) 1998-99 Paul Barton-Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ - -#ifndef __qm_rcpointer_h__ -#define __qm_rcpointer_h__ - -template class RCPointer { - public: - T *operator->() { return _ptr; } - bool operator==(T *p) { return _ptr == p; } - bool operator!=(T *p) { return _ptr != p; } - - int refcount() { return _ptr->count; } - - RCPointer () { _ptr = 0; } - - RCPointer (T *p) : _ptr (p) { - if (_ptr) _ptr->count++; - } - - RCPointer (const RCPointer& r) : _ptr (r._ptr) { - if (_ptr) _ptr->count++; - } - - RCPointer &operator= (const RCPointer &r) { - if (_ptr == r._ptr) return *this; - if (_ptr && --_ptr->count == 0) { - delete _ptr; - } - _ptr = r._ptr; - if (_ptr) _ptr->count++; - return *this; - } - ~RCPointer () { - if (_ptr && --_ptr->count == 0) { - delete _ptr; - } - } - - private: - T *_ptr; -}; - -#endif // __qm_rcpointer_h__ diff --git a/libs/pbd3/pbd/relation.h b/libs/pbd3/pbd/relation.h deleted file mode 100644 index f28aaecfa1..0000000000 --- a/libs/pbd3/pbd/relation.h +++ /dev/null @@ -1,35 +0,0 @@ -/* - Copyright (C) 1999 Paul Barton-Davis - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ - -#ifndef __pbd_relation_h__ -#define __pbd_relation_h__ - -enum RelationalCondition { - Equal = 0, - NotEqual, - LessThan, - LessThanOrEqual, - GreaterThan, - GreaterThanOrEqual, - Changed, - - NumConditions -}; - -#endif // __pbd_relation_h__ diff --git a/libs/pbd3/pbd/ringbuffer.h b/libs/pbd3/pbd/ringbuffer.h index cca9cbfc01..1d9c9b04e3 100644 --- a/libs/pbd3/pbd/ringbuffer.h +++ b/libs/pbd3/pbd/ringbuffer.h @@ -21,8 +21,9 @@ #ifndef ringbuffer_h #define ringbuffer_h -#include -#include +//#include + +#include template class RingBuffer @@ -47,14 +48,14 @@ class RingBuffer void reset () { /* !!! NOT THREAD SAFE !!! */ - atomic_set (&write_ptr, 0); - atomic_set (&read_ptr, 0); + g_atomic_int_set (&write_ptr, 0); + g_atomic_int_set (&read_ptr, 0); } void set (size_t r, size_t w) { /* !!! NOT THREAD SAFE !!! */ - atomic_set (&write_ptr, w); - atomic_set (&read_ptr, r); + g_atomic_int_set (&write_ptr, w); + g_atomic_int_set (&read_ptr, r); } size_t read (T *dest, size_t cnt); @@ -69,22 +70,22 @@ class RingBuffer void get_write_vector (rw_vector *); void decrement_read_ptr (size_t cnt) { - atomic_set (&read_ptr, (atomic_read(&read_ptr) - cnt) & size_mask); + g_atomic_int_set (&read_ptr, (g_atomic_int_get(&read_ptr) - cnt) & size_mask); } void increment_read_ptr (size_t cnt) { - atomic_set (&read_ptr, (atomic_read(&read_ptr) + cnt) & size_mask); + g_atomic_int_set (&read_ptr, (g_atomic_int_get(&read_ptr) + cnt) & size_mask); } void increment_write_ptr (size_t cnt) { - atomic_set (&write_ptr, (atomic_read(&write_ptr) + cnt) & size_mask); + g_atomic_int_set (&write_ptr, (g_atomic_int_get(&write_ptr) + cnt) & size_mask); } size_t write_space () { size_t w, r; - w = atomic_read (&write_ptr); - r = atomic_read (&read_ptr); + w = g_atomic_int_get (&write_ptr); + r = g_atomic_int_get (&read_ptr); if (w > r) { return ((r - w + size) & size_mask) - 1; @@ -98,8 +99,8 @@ class RingBuffer size_t read_space () { size_t w, r; - w = atomic_read (&write_ptr); - r = atomic_read (&read_ptr); + w = g_atomic_int_get (&write_ptr); + r = g_atomic_int_get (&read_ptr); if (w > r) { return w - r; @@ -109,15 +110,15 @@ class RingBuffer } T *buffer () { return buf; } - size_t get_write_ptr () const { return atomic_read (&write_ptr); } - size_t get_read_ptr () const { return atomic_read (&read_ptr); } + size_t get_write_ptr () const { return g_atomic_int_get (&write_ptr); } + size_t get_read_ptr () const { return g_atomic_int_get (&read_ptr); } size_t bufsize () const { return size; } protected: T *buf; size_t size; - atomic_t write_ptr; - atomic_t read_ptr; + mutable gint write_ptr; + mutable gint read_ptr; size_t size_mask; }; @@ -130,7 +131,7 @@ RingBuffer::read (T *dest, size_t cnt) size_t n1, n2; size_t priv_read_ptr; - priv_read_ptr=atomic_read(&read_ptr); + priv_read_ptr=g_atomic_int_get(&read_ptr); if ((free_cnt = read_space ()) == 0) { return 0; @@ -156,7 +157,7 @@ RingBuffer::read (T *dest, size_t cnt) priv_read_ptr = n2; } - atomic_set(&read_ptr, priv_read_ptr); + g_atomic_int_set(&read_ptr, priv_read_ptr); return to_read; } @@ -170,7 +171,7 @@ RingBuffer::write (T *src, size_t cnt) size_t n1, n2; size_t priv_write_ptr; - priv_write_ptr=atomic_read(&write_ptr); + priv_write_ptr=g_atomic_int_get(&write_ptr); if ((free_cnt = write_space ()) == 0) { return 0; @@ -196,7 +197,7 @@ RingBuffer::write (T *src, size_t cnt) priv_write_ptr = n2; } - atomic_set(&write_ptr, priv_write_ptr); + g_atomic_int_set(&write_ptr, priv_write_ptr); return to_write; } @@ -208,8 +209,8 @@ RingBuffer::get_read_vector (RingBuffer::rw_vector *vec) size_t cnt2; size_t w, r; - w = atomic_read (&write_ptr); - r = atomic_read (&read_ptr); + w = g_atomic_int_get (&write_ptr); + r = g_atomic_int_get (&read_ptr); if (w > r) { free_cnt = w - r; @@ -248,8 +249,8 @@ RingBuffer::get_write_vector (RingBuffer::rw_vector *vec) size_t cnt2; size_t w, r; - w = atomic_read (&write_ptr); - r = atomic_read (&read_ptr); + w = g_atomic_int_get (&write_ptr); + r = g_atomic_int_get (&read_ptr); if (w > r) { free_cnt = ((r - w + size) & size_mask) - 1; diff --git a/libs/pbd3/pbd/ringbufferNPT.h b/libs/pbd3/pbd/ringbufferNPT.h index d559a53d94..fee2efce3d 100644 --- a/libs/pbd3/pbd/ringbufferNPT.h +++ b/libs/pbd3/pbd/ringbufferNPT.h @@ -21,8 +21,9 @@ #ifndef ringbuffer_npt_h #define ringbuffer_npt_h -#include -#include +//#include + +#include /* ringbuffer class where the element size is not required to be a power of two */ @@ -43,14 +44,14 @@ class RingBufferNPT void reset () { /* !!! NOT THREAD SAFE !!! */ - atomic_set (&write_ptr, 0); - atomic_set (&read_ptr, 0); + g_atomic_int_set (&write_ptr, 0); + g_atomic_int_set (&read_ptr, 0); } void set (size_t r, size_t w) { /* !!! NOT THREAD SAFE !!! */ - atomic_set (&write_ptr, w); - atomic_set (&read_ptr, r); + g_atomic_int_set (&write_ptr, w); + g_atomic_int_set (&read_ptr, r); } size_t read (T *dest, size_t cnt); @@ -65,22 +66,22 @@ class RingBufferNPT void get_write_vector (rw_vector *); void decrement_read_ptr (size_t cnt) { - atomic_set (&read_ptr, (atomic_read(&read_ptr) - cnt) % size); + g_atomic_int_set (&read_ptr, (g_atomic_int_get(&read_ptr) - cnt) % size); } void increment_read_ptr (size_t cnt) { - atomic_set (&read_ptr, (atomic_read(&read_ptr) + cnt) % size); + g_atomic_int_set (&read_ptr, (g_atomic_int_get(&read_ptr) + cnt) % size); } void increment_write_ptr (size_t cnt) { - atomic_set (&write_ptr, (atomic_read(&write_ptr) + cnt) % size); + g_atomic_int_set (&write_ptr, (g_atomic_int_get(&write_ptr) + cnt) % size); } size_t write_space () { size_t w, r; - w = atomic_read (&write_ptr); - r = atomic_read (&read_ptr); + w = g_atomic_int_get (&write_ptr); + r = g_atomic_int_get (&read_ptr); if (w > r) { return ((r - w + size) % size) - 1; @@ -94,8 +95,8 @@ class RingBufferNPT size_t read_space () { size_t w, r; - w = atomic_read (&write_ptr); - r = atomic_read (&read_ptr); + w = g_atomic_int_get (&write_ptr); + r = g_atomic_int_get (&read_ptr); if (w > r) { return w - r; @@ -105,15 +106,15 @@ class RingBufferNPT } T *buffer () { return buf; } - size_t get_write_ptr () const { return atomic_read (&write_ptr); } - size_t get_read_ptr () const { return atomic_read (&read_ptr); } + size_t get_write_ptr () const { return g_atomic_int_get (&write_ptr); } + size_t get_read_ptr () const { return g_atomic_int_get (&read_ptr); } size_t bufsize () const { return size; } protected: T *buf; size_t size; - atomic_t write_ptr; - atomic_t read_ptr; + mutable gint write_ptr; + mutable gint read_ptr; }; template size_t @@ -125,7 +126,7 @@ RingBufferNPT::read (T *dest, size_t cnt) size_t n1, n2; size_t priv_read_ptr; - priv_read_ptr=atomic_read(&read_ptr); + priv_read_ptr=g_atomic_int_get(&read_ptr); if ((free_cnt = read_space ()) == 0) { return 0; @@ -151,7 +152,7 @@ RingBufferNPT::read (T *dest, size_t cnt) priv_read_ptr = n2; } - atomic_set(&read_ptr, priv_read_ptr); + g_atomic_int_set(&read_ptr, priv_read_ptr); return to_read; } @@ -164,7 +165,7 @@ RingBufferNPT::write (T *src, size_t cnt) size_t n1, n2; size_t priv_write_ptr; - priv_write_ptr=atomic_read(&write_ptr); + priv_write_ptr=g_atomic_int_get(&write_ptr); if ((free_cnt = write_space ()) == 0) { return 0; @@ -190,7 +191,7 @@ RingBufferNPT::write (T *src, size_t cnt) priv_write_ptr = n2; } - atomic_set(&write_ptr, priv_write_ptr); + g_atomic_int_set(&write_ptr, priv_write_ptr); return to_write; } @@ -201,8 +202,8 @@ RingBufferNPT::get_read_vector (RingBufferNPT::rw_vector *vec) size_t cnt2; size_t w, r; - w = atomic_read (&write_ptr); - r = atomic_read (&read_ptr); + w = g_atomic_int_get (&write_ptr); + r = g_atomic_int_get (&read_ptr); if (w > r) { free_cnt = w - r; @@ -240,8 +241,8 @@ RingBufferNPT::get_write_vector (RingBufferNPT::rw_vector *vec) size_t cnt2; size_t w, r; - w = atomic_read (&write_ptr); - r = atomic_read (&read_ptr); + w = g_atomic_int_get (&write_ptr); + r = g_atomic_int_get (&read_ptr); if (w > r) { free_cnt = ((r - w + size) % size) - 1; diff --git a/libs/pbd3/pbd/rt.h b/libs/pbd3/pbd/rt.h deleted file mode 100644 index aa954fcd42..0000000000 --- a/libs/pbd3/pbd/rt.h +++ /dev/null @@ -1,25 +0,0 @@ -/* - Copyright (C) 1998-99 Paul Barton-Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ -#ifndef __libmisc_rt_h__ -#define __libmisc_rt_h__ - -extern int become_real_time_thread (int rt_priorty = 10, bool fifo = true); - -#endif // __libmisc_rt_h__ diff --git a/libs/pbd3/pbd/rtthread.h b/libs/pbd3/pbd/rtthread.h deleted file mode 100644 index b99c69ba79..0000000000 --- a/libs/pbd3/pbd/rtthread.h +++ /dev/null @@ -1,30 +0,0 @@ -/* - Copyright (C) 1998-99 Paul Barton-Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ -#ifndef __rtthread_h__ -#define __rtthread_h__ - -#include - -extern int pthread_create_realtime (pthread_t *new_thread, - void *(*start)(void *), void *arg, - int priority = 10); - - -#endif // __rtthread_h__ diff --git a/libs/pbd3/pbd/scale.h b/libs/pbd3/pbd/scale.h deleted file mode 100644 index 0384ae52aa..0000000000 --- a/libs/pbd3/pbd/scale.h +++ /dev/null @@ -1,53 +0,0 @@ -/* - Copyright (C) 2000 Paul Barton-Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ - -#ifndef __pbd_scale_h__ -#define __pbd_scale_h__ - -#include - -inline float -scale (float value, float lower, float upper) -{ - return fabs (lower + value) / (upper-lower); -} - -inline float -scale_with_range (float value, float lower, float range) -{ - return fabs (lower + value) / range; -} - - -inline float -scale_to (float value, float lower, float upper, float to) -{ - return (fabs (lower + value) / (upper-lower)) * to; -} - -inline float -scale_to_with_range (float value, float lower, float range, float to) -{ - return (fabs (lower + value) / range) * to; -} - -#endif /* __pbd_scale_h__ */ - - diff --git a/libs/pbd3/pbd/thread.h b/libs/pbd3/pbd/thread.h deleted file mode 100644 index c1d5c3c78d..0000000000 --- a/libs/pbd3/pbd/thread.h +++ /dev/null @@ -1,127 +0,0 @@ -/* - Copyright (C) 1998-99 Paul Barton-Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ - -#ifndef __qm_thread_h__ -#define __qm_thread_h__ - -#include - -/* A generic base class for Quasimodo objects requiring their own - thread to do work. -*/ - -class QMThread - -{ - public: - QMThread (const char *name, - void *(start)(void *), void *, - bool realtime = false, int rt_priority = 10); - - virtual ~QMThread(); - - int run (); - void poke (); - void pause (); - void stop (); - void *wait (); - - /* This doesn't guarantee anything about the state of - the thread, but if you do things the right way, and - make sure that the do_work() routine checks - work_no_more() at the right times, and that the - thread is awake, then calling this will cause - the thread to exit fairly quickly. - */ - - void halt() { _must_exit = true ; } - - void exit (void *status); - pthread_t thread_id() { return _thread; } - - bool thread_ok () { return _have_thread; } - bool thread_active() { return _thread_active; } - - bool thread_running () { - /* XXX not atomic */ - return _running && _thread_active; - } - - bool thread_waiting () { return _thread_waiting; } - - static void try_to_kill_all_threads() { - all_threads_must_die = true; - } - - protected: - void *main (); - - bool work_no_more () { return (!_running || _must_exit || all_threads_must_die); } - - bool myself () { - return pthread_equal (_thread, pthread_self()); - } - - void suspend() { - _running = false; - } - - void lock (pthread_mutex_t *lock) { - pthread_mutex_lock (lock); - } - - void unlock (pthread_mutex_t *lock) { - pthread_mutex_unlock (lock); - } - - virtual void *do_work () = 0; - - private: - const char *_name; - bool _must_exit; - bool _running; - bool _thread_active; - bool _thread_waiting; - bool _have_thread; - - size_t work_cnt; - - pthread_mutex_t status_lock; - pthread_cond_t wake_up; /* protected by status_lock */ - pthread_cond_t asleep; /* protected by status_lock */ - pthread_cond_t running; /* protected by status_lock */ - pthread_cond_t exited; /* protected by status_lock */ - pthread_t _thread; - - void lock () { - pthread_mutex_lock (&status_lock); - } - - void unlock () { - pthread_mutex_unlock (&status_lock); - } - - static bool all_threads_must_die; - - static void signal_catcher (int sig); - void setup_signals (); -}; - -#endif // __qm_thread_h__ diff --git a/libs/pbd3/pbd/types.h b/libs/pbd3/pbd/types.h deleted file mode 100644 index 52f067fd04..0000000000 --- a/libs/pbd3/pbd/types.h +++ /dev/null @@ -1,32 +0,0 @@ -/* - Copyright (C) 1999 Paul Barton-Davis - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ - -#ifndef __pbd_types_h__ -#define __pbd_types_h__ - -typedef unsigned char byte; -typedef char int8; -typedef unsigned short uint16; -typedef short int16; -typedef unsigned int uint32; -typedef int int32; -typedef unsigned long long int uint64; -typedef long long int int64; - -#endif // __pbd_types_h__ diff --git a/libs/pbd3/pbd/unescape.h b/libs/pbd3/pbd/unescape.h deleted file mode 100644 index 6596a86113..0000000000 --- a/libs/pbd3/pbd/unescape.h +++ /dev/null @@ -1,6 +0,0 @@ -#ifndef __unescape_h__ -#define __unescape_h__ - -void unescape (char *); - -#endif // __unescape_h__ diff --git a/libs/pbd3/pool.cc b/libs/pbd3/pool.cc index f05d88381c..7318bd4398 100644 --- a/libs/pbd3/pool.cc +++ b/libs/pbd3/pool.cc @@ -19,13 +19,10 @@ */ #include -#include #include #include #include -#include -#include using namespace std; @@ -84,32 +81,39 @@ Pool::release (void *ptr) /*---------------------------------------------*/ MultiAllocSingleReleasePool::MultiAllocSingleReleasePool (string n, unsigned long isize, unsigned long nitems) - : Pool (n, isize, nitems) + : Pool (n, isize, nitems), + m_lock(0) { - pthread_mutex_init (&lock, 0); } MultiAllocSingleReleasePool::~MultiAllocSingleReleasePool () { + if(m_lock) delete m_lock; } SingleAllocMultiReleasePool::SingleAllocMultiReleasePool (string n, unsigned long isize, unsigned long nitems) - : Pool (n, isize, nitems) + : Pool (n, isize, nitems), + m_lock(0) { - pthread_mutex_init (&lock, 0); } SingleAllocMultiReleasePool::~SingleAllocMultiReleasePool () { + if(m_lock) delete m_lock; } void* MultiAllocSingleReleasePool::alloc () { void *ptr; - pthread_mutex_lock (&lock); + if(!m_lock) { + m_lock = new Glib::Mutex(); + // umm, I'm not sure that this doesn't also allocate memory. + if(!m_lock) error << "cannot create Glib::Mutex in pool.cc" << endmsg; + } + + Glib::Mutex::Lock guard(*m_lock); ptr = Pool::alloc (); - pthread_mutex_unlock (&lock); return ptr; } @@ -128,8 +132,12 @@ SingleAllocMultiReleasePool::alloc () void SingleAllocMultiReleasePool::release (void* ptr) { - pthread_mutex_lock (&lock); + if(!m_lock) { + m_lock = new Glib::Mutex(); + // umm, I'm not sure that this doesn't also allocate memory. + if(!m_lock) error << "cannot create Glib::Mutex in pool.cc" << endmsg; + } + Glib::Mutex::Lock guard(*m_lock); Pool::release (ptr); - pthread_mutex_unlock (&lock); } diff --git a/libs/pbd3/unescape.cc b/libs/pbd3/unescape.cc deleted file mode 100644 index 2c79740e4a..0000000000 --- a/libs/pbd3/unescape.cc +++ /dev/null @@ -1,137 +0,0 @@ -#include - -#include - -void -unescape (char *str) - -{ - char *p; - bool escaped; - long offset; - char octal[4]; - int noct; - char hex[3]; - int nhex; - - escaped = false; - offset = 0; - octal[3] = '\0'; - hex[2] = '\0'; - - p = str; - - while (*p) { - if (!escaped) { - if (*p == '\\') { - escaped = true; - } else { - *(p-offset) = *p; - } - p++; - continue; - } - - switch (*p) { - case 'f': - offset++; - *(p-offset) = '\f'; - break; - case 'r': - offset++; - *(p-offset) = '\r'; - break; - - case 'v': - offset++; - *(p-offset) = '\v'; - break; - - case 'n': - offset++; - *(p-offset) = '\n'; - break; - - case 't': - offset++; - *(p-offset) = '\t'; - break; - - case 'b': - offset++; - *(p-offset) = '\b'; - break; - - case '0': - case '1': - case '2': - case '3': - case '4': - case '5': - case '6': - case '7': - noct = 0; - while (noct < 3 && - (*p >= '0' && *p <= '7')) { - octal[noct++] = *p; - offset++; - p++; - } - p--; - *(p-offset) = strtol (octal, 0, 8); - break; - - case 'x': - nhex = 0; - p++; - offset++; - - while (nhex < 2 && - ((*p >= '0' && *p <= '9') || - (*p >= 'a' && *p <= 'f') || - (*p >= 'A' && *p <= 'F'))) { - hex[nhex++] = *p; - offset++; - p++; - } - p--; - *(p-offset) = strtol (hex, 0, 16); - break; - - case '\\': - offset++; - *(p-offset) = '\\'; - break; - - case '"': - offset++; - *(p-offset) = '"'; - break; - - case '\'': - offset++; - *(p-offset) = '\''; - break; - - default: - *(p-offset) = *p; - } - - escaped = false; - p++; - } - - *(p-offset) = '\0'; -} - -#ifdef TEST -#include - -main (int argc, char *argv[]) - -{ - unescape (argv[1]); - printf ("%s\n", argv[1]); -} - -#endif diff --git a/libs/surfaces/control_protocol/SConscript b/libs/surfaces/control_protocol/SConscript index eeac7bed8b..38ff95d9f0 100644 --- a/libs/surfaces/control_protocol/SConscript +++ b/libs/surfaces/control_protocol/SConscript @@ -36,7 +36,9 @@ cp.Merge ([ libraries['pbd3'], libraries['midi++2'], libraries['xml'], - libraries['usb'] + libraries['usb'], + libraries['glib2'], + libraries['glibmm2'] ]) libardour_cp = cp.SharedLibrary('ardour_cp', cp_files) diff --git a/libs/surfaces/generic_midi/SConscript b/libs/surfaces/generic_midi/SConscript index 97998f864f..1760eb24e9 100644 --- a/libs/surfaces/generic_midi/SConscript +++ b/libs/surfaces/generic_midi/SConscript @@ -37,7 +37,9 @@ genericmidi.Merge ([ libraries['pbd3'], libraries['sigc2'], libraries['usb'], - libraries['xml'] + libraries['xml'], + libraries['glib2'], + libraries['glibmm2'] ]) libardour_genericmidi = genericmidi.SharedLibrary('ardour_genericmidi', genericmidi_files) diff --git a/libs/surfaces/tranzport/SConscript b/libs/surfaces/tranzport/SConscript index 55dae57cc1..8f3568aa8f 100644 --- a/libs/surfaces/tranzport/SConscript +++ b/libs/surfaces/tranzport/SConscript @@ -37,7 +37,9 @@ tranzport.Merge ([ libraries['pbd3'], libraries['midi++2'], libraries['xml'], - libraries['usb'] + libraries['usb'], + libraries['glib2'], + libraries['glibmm2'] ]) libardour_tranzport = tranzport.SharedLibrary('ardour_tranzport', tranzport_files) diff --git a/libs/surfaces/tranzport/tranzport_control_protocol.h b/libs/surfaces/tranzport/tranzport_control_protocol.h index 0311140f8c..44045f6834 100644 --- a/libs/surfaces/tranzport/tranzport_control_protocol.h +++ b/libs/surfaces/tranzport/tranzport_control_protocol.h @@ -4,10 +4,11 @@ #include #include -#include #include #include +#include + #include #include "control_protocol.h" @@ -95,7 +96,7 @@ class TranzportControlProtocol : public ARDOUR::ControlProtocol DisplayMode display_mode; ARDOUR::gain_t gain_fraction; - PBD::Lock update_lock; + Glib::Mutex update_lock; char current_screen[2][20]; char pending_screen[2][20]; bool lights[7]; @@ -112,7 +113,7 @@ class TranzportControlProtocol : public ARDOUR::ControlProtocol struct timeval last_wheel_motion; int last_wheel_dir; - PBD::Lock io_lock; + Glib::Mutex io_lock; int open (); int read (uint32_t timeout_override = 0); From 7c9361b8657a4deafcb7cffcdf4584a441fd9ce6 Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Thu, 15 Jun 2006 18:21:31 +0000 Subject: [PATCH 04/27] r59@gandalf: fugalh | 2006-06-15 12:16:20 -0600 renamed UndoCommand to UndoTransaction, and created new UndoCommand class and its templated subclass SlotCommand. Those two are still in considerable flux. git-svn-id: svn://localhost/ardour2/branches/undo@606 d708f5d6-7413-0410-9779-e7cbd77b26cf --- gtk2_ardour/editor.h | 2 +- libs/ardour/ardour/session.h | 10 ++++----- libs/ardour/session_state.cc | 12 +++++------ libs/pbd3/pbd/undo.h | 40 +++++++++++++++++++++--------------- libs/pbd3/undo.cc | 36 ++++++++++++++++---------------- 5 files changed, 53 insertions(+), 47 deletions(-) diff --git a/gtk2_ardour/editor.h b/gtk2_ardour/editor.h index 8b7b2af1d0..e73d44971b 100644 --- a/gtk2_ardour/editor.h +++ b/gtk2_ardour/editor.h @@ -1616,7 +1616,7 @@ class Editor : public PublicEditor /* visual history */ UndoHistory visual_history; - UndoCommand current_visual_command; + UndoTransaction current_visual_command; void begin_reversible_visual_command (const string & cmd_name); void commit_reversible_visual_command (); diff --git a/libs/ardour/ardour/session.h b/libs/ardour/ardour/session.h index 83acb3f82a..3d164a4b05 100644 --- a/libs/ardour/ardour/session.h +++ b/libs/ardour/ardour/session.h @@ -489,7 +489,7 @@ class Session : public sigc::trackable, public Stateful static vector* possible_states(string path); XMLNode& get_state(); - int set_state(const XMLNode& node); + int set_state(const XMLNode& node); // not idempotent XMLNode& get_template(); void add_instant_xml (XMLNode&, const std::string& dir); @@ -849,13 +849,13 @@ class Session : public sigc::trackable, public Stateful void commit_reversible_command (UndoAction* private_redo = 0); void add_undo (const UndoAction& ua) { - current_cmd.add_undo (ua); + current_trans.add_undo (ua); } void add_redo (const UndoAction& ua) { - current_cmd.add_redo (ua); + current_trans.add_redo (ua); } void add_redo_no_execute (const UndoAction& ua) { - current_cmd.add_redo_no_execute (ua); + current_trans.add_redo_no_execute (ua); } UndoAction global_solo_memento (void *src); @@ -1635,7 +1635,7 @@ class Session : public sigc::trackable, public Stateful void reverse_diskstream_buffers (); UndoHistory history; - UndoCommand current_cmd; + UndoTransaction current_trans; GlobalRouteBooleanState get_global_route_boolean (bool (Route::*method)(void) const); GlobalRouteMeterState get_global_route_metering (); diff --git a/libs/ardour/session_state.cc b/libs/ardour/session_state.cc index cf510e9881..5ef717de8a 100644 --- a/libs/ardour/session_state.cc +++ b/libs/ardour/session_state.cc @@ -2562,11 +2562,11 @@ Session::set_meter_falloff (float val) void Session::begin_reversible_command (string name, UndoAction* private_undo) { - current_cmd.clear (); - current_cmd.set_name (name); + current_trans.clear (); + current_trans.set_name (name); if (private_undo) { - current_cmd.add_undo (*private_undo); + current_trans.add_undo (*private_undo); } } @@ -2576,13 +2576,13 @@ Session::commit_reversible_command (UndoAction* private_redo) struct timeval now; if (private_redo) { - current_cmd.add_redo_no_execute (*private_redo); + current_trans.add_redo_no_execute (*private_redo); } gettimeofday (&now, 0); - current_cmd.set_timestamp (now); + current_trans.set_timestamp (now); - history.add (current_cmd); + history.add (current_trans); } Session::GlobalRouteBooleanState diff --git a/libs/pbd3/pbd/undo.h b/libs/pbd3/pbd/undo.h index b540179012..488e896706 100644 --- a/libs/pbd3/pbd/undo.h +++ b/libs/pbd3/pbd/undo.h @@ -23,6 +23,7 @@ #include #include +#include #include #include #include @@ -33,42 +34,47 @@ using std::list; typedef sigc::slot UndoAction; -class Serializable; - -class MementoBase +// TODO stick this in its own file, and make the arguments multiply-inherit it +class Serializable { public: - MementoBase(std::string key); + XMLNode &serialize(); +}; + +class UndoCommand +{ +public: + UndoCommand(id_t object_id, std::string method_name); void operator() () { return _slot(); } XMLNode &serialize(); protected: sigc::slot _slot; - std::list _args; }; template -class Memento; +class SlotCommand; template <> -class Memento <> : public MementoBase {}; +class SlotCommand <> : public UndoCommand {}; template -class Memento : public MementoBase +class SlotCommand : public UndoCommand { + T1 _arg1; public: - Memento(std::string key, T1 arg1) : MementoBase(key) + SlotCommand(id_t object_id, std::string key, T1 arg1) + : UndoCommand(object_id, key), _arg1(arg1) { - _args.push_back(arg1); _slot = sigc::bind(_slot, arg1); } }; -class UndoCommand +class UndoTransaction { public: - UndoCommand (); - UndoCommand (const UndoCommand&); - UndoCommand& operator= (const UndoCommand&); + UndoTransaction (); + UndoTransaction (const UndoTransaction&); + UndoTransaction& operator= (const UndoTransaction&); void clear (); @@ -105,7 +111,7 @@ class UndoHistory UndoHistory() {} ~UndoHistory() {} - void add (UndoCommand uc); + void add (UndoTransaction ut); void undo (unsigned int n); void redo (unsigned int n); @@ -120,8 +126,8 @@ class UndoHistory void clear_redo (); private: - list UndoList; - list RedoList; + list UndoList; + list RedoList; }; diff --git a/libs/pbd3/undo.cc b/libs/pbd3/undo.cc index f2f11b1c5c..0aac58effc 100644 --- a/libs/pbd3/undo.cc +++ b/libs/pbd3/undo.cc @@ -25,11 +25,11 @@ using namespace std; using namespace sigc; -UndoCommand::UndoCommand () +UndoTransaction::UndoTransaction () { } -UndoCommand::UndoCommand (const UndoCommand& rhs) +UndoTransaction::UndoTransaction (const UndoTransaction& rhs) { _name = rhs._name; clear (); @@ -37,8 +37,8 @@ UndoCommand::UndoCommand (const UndoCommand& rhs) redo_actions.insert(redo_actions.end(),rhs.redo_actions.begin(),rhs.redo_actions.end()); } -UndoCommand& -UndoCommand::operator= (const UndoCommand& rhs) +UndoTransaction& +UndoTransaction::operator= (const UndoTransaction& rhs) { if (this == &rhs) return *this; _name = rhs._name; @@ -49,33 +49,33 @@ UndoCommand::operator= (const UndoCommand& rhs) } void -UndoCommand::add_undo (const UndoAction& action) +UndoTransaction::add_undo (const UndoAction& action) { undo_actions.push_back (action); } void -UndoCommand::add_redo (const UndoAction& action) +UndoTransaction::add_redo (const UndoAction& action) { redo_actions.push_back (action); redo_actions.back()(); // operator() } void -UndoCommand::add_redo_no_execute (const UndoAction& action) +UndoTransaction::add_redo_no_execute (const UndoAction& action) { redo_actions.push_back (action); } void -UndoCommand::clear () +UndoTransaction::clear () { undo_actions.clear (); redo_actions.clear (); } void -UndoCommand::undo () +UndoTransaction::undo () { cerr << "Undo " << _name << endl; for (list::reverse_iterator i = undo_actions.rbegin(); i != undo_actions.rend(); ++i) { @@ -84,7 +84,7 @@ UndoCommand::undo () } void -UndoCommand::redo () +UndoTransaction::redo () { cerr << "Redo " << _name << endl; for (list::iterator i = redo_actions.begin(); i != redo_actions.end(); ++i) { @@ -93,9 +93,9 @@ UndoCommand::redo () } void -UndoHistory::add (UndoCommand uc) +UndoHistory::add (UndoTransaction ut) { - UndoList.push_back (uc); + UndoList.push_back (ut); } void @@ -105,10 +105,10 @@ UndoHistory::undo (unsigned int n) if (UndoList.size() == 0) { return; } - UndoCommand uc = UndoList.back (); + UndoTransaction ut = UndoList.back (); UndoList.pop_back (); - uc.undo (); - RedoList.push_back (uc); + ut.undo (); + RedoList.push_back (ut); } } @@ -119,10 +119,10 @@ UndoHistory::redo (unsigned int n) if (RedoList.size() == 0) { return; } - UndoCommand cmd = RedoList.back (); + UndoTransaction trans = RedoList.back (); RedoList.pop_back (); - cmd.redo (); - UndoList.push_back (cmd); + trans.redo (); + UndoList.push_back (trans); } } From 4078b9ec645f4fc71dc3693c7ee70354183393d5 Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Thu, 22 Jun 2006 22:37:08 +0000 Subject: [PATCH 05/27] r80@gandalf: fugalh | 2006-06-22 16:37:01 -0600 reworked templatization of UndoCommand git-svn-id: svn://localhost/ardour2/branches/undo@636 d708f5d6-7413-0410-9779-e7cbd77b26cf --- libs/pbd3/pbd/serializable.h | 32 +++++++++++++++ libs/pbd3/pbd/undo.h | 37 +---------------- libs/pbd3/pbd/undo_command.h | 80 ++++++++++++++++++++++++++++++++++++ 3 files changed, 113 insertions(+), 36 deletions(-) create mode 100644 libs/pbd3/pbd/serializable.h create mode 100644 libs/pbd3/pbd/undo_command.h diff --git a/libs/pbd3/pbd/serializable.h b/libs/pbd3/pbd/serializable.h new file mode 100644 index 0000000000..8032f0038a --- /dev/null +++ b/libs/pbd3/pbd/serializable.h @@ -0,0 +1,32 @@ +/* + Copyright (C) 2006 Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + + $Id: /local/undo/libs/pbd3/pbd/undo.h 59 2006-06-15T18:16:20.960977Z fugalh $ +*/ + +#ifndef __lib_pbd_serializable_h__ +#define __lib_pbd_serializable_h__ + +#include + +class Serializable +{ +public: + XMLNode &serialize(); +}; + +#endif // __lib_pbd_serializable_h__ diff --git a/libs/pbd3/pbd/undo.h b/libs/pbd3/pbd/undo.h index 488e896706..d2ad6088cd 100644 --- a/libs/pbd3/pbd/undo.h +++ b/libs/pbd3/pbd/undo.h @@ -27,48 +27,13 @@ #include #include #include -#include +#include using std::string; using std::list; typedef sigc::slot UndoAction; -// TODO stick this in its own file, and make the arguments multiply-inherit it -class Serializable -{ -public: - XMLNode &serialize(); -}; - -class UndoCommand -{ -public: - UndoCommand(id_t object_id, std::string method_name); - void operator() () { return _slot(); } - XMLNode &serialize(); -protected: - sigc::slot _slot; -}; - -template -class SlotCommand; - -template <> -class SlotCommand <> : public UndoCommand {}; - -template -class SlotCommand : public UndoCommand -{ - T1 _arg1; -public: - SlotCommand(id_t object_id, std::string key, T1 arg1) - : UndoCommand(object_id, key), _arg1(arg1) - { - _slot = sigc::bind(_slot, arg1); - } -}; - class UndoTransaction { public: diff --git a/libs/pbd3/pbd/undo_command.h b/libs/pbd3/pbd/undo_command.h new file mode 100644 index 0000000000..2f45e2799a --- /dev/null +++ b/libs/pbd3/pbd/undo_command.h @@ -0,0 +1,80 @@ +/* + Copyright (C) 2006 Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + + $Id: /local/undo/libs/pbd3/pbd/undo.h 59 2006-06-15T18:16:20.960977Z fugalh $ +*/ + +#ifndef __lib_pbd_undo_command_h__ +#define __lib_pbd_undo_command_h__ + +#include + +using sigc::nil; +using sigc::slot; +using std::list; +using std::string; + +template +class UndoCommand +{ + public: + /* It only makes sense to use the constructor corresponding to the + * template given. e.g. + * + * UndoCommand cmd(id, key, foo_instance); + */ + UndoCommand(id_t object_id, string key) + : _obj_id(object_id), _key(key) {} + UndoCommand(id_t object_id, string key, T1 arg1) + : _obj_id(object_id), _key(key) + { + _args.push_back(arg1); + } + UndoCommand(id_t object_id, string key, T1 arg1, T2 arg2) + : _obj_id(object_id), _key(key) + { + _args.push_back(arg1); + _args.push_back(arg2); + } + UndoCommand(id_t object_id, string key, T1 arg1, T2 arg2, T3 arg3) + : _obj_id(object_id), _key(key) + { + _args.push_back(arg1); + _args.push_back(arg2); + _args.push_back(arg3); + } + UndoCommand(id_t object_id, string key, T1 arg1, T2 arg2, T3 arg3, T4 arg4) + : _obj_id(object_id), _key(key) + { + _args.push_back(arg1); + _args.push_back(arg2); + _args.push_back(arg3); + _args.push_back(arg4); + } + + void operator() () { return _slot(); } + XMLNode &serialize(); + protected: + id_t _obj_id; + string _key; + slot _slot; + // Note that arguments must be instances of Serializable or this will + // rightly cause a compiler error when compiling the constructor. + list _args; +}; + +#endif // __lib_pbd_undo_command_h__ From fd742b30fa1071c44d053cf4676149641f977a35 Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Thu, 22 Jun 2006 23:38:19 +0000 Subject: [PATCH 06/27] r111@gandalf: fugalh | 2006-06-22 17:38:14 -0600 progress on UndoCommand constructors git-svn-id: svn://localhost/ardour2/branches/undo@637 d708f5d6-7413-0410-9779-e7cbd77b26cf --- libs/pbd3/pbd/undo_command.h | 57 ++++++++++++++++++++++++++---------- 1 file changed, 41 insertions(+), 16 deletions(-) diff --git a/libs/pbd3/pbd/undo_command.h b/libs/pbd3/pbd/undo_command.h index 2f45e2799a..26550650be 100644 --- a/libs/pbd3/pbd/undo_command.h +++ b/libs/pbd3/pbd/undo_command.h @@ -21,13 +21,23 @@ #ifndef __lib_pbd_undo_command_h__ #define __lib_pbd_undo_command_h__ +#include +#include +#include +#include #include using sigc::nil; using sigc::slot; +using sigc::bind; +using sigc::mem_fun; using std::list; using std::string; + +/* One of the joys of templates is that you have to do everything right here + * in the header file; you can't split this to make undo_command.cc */ + template class UndoCommand { @@ -38,40 +48,55 @@ class UndoCommand * UndoCommand cmd(id, key, foo_instance); */ UndoCommand(id_t object_id, string key) - : _obj_id(object_id), _key(key) {} - UndoCommand(id_t object_id, string key, T1 arg1) : _obj_id(object_id), _key(key) - { - _args.push_back(arg1); + { + _slot = mem_fun( get_object(object_id), get_method(key) ); } - UndoCommand(id_t object_id, string key, T1 arg1, T2 arg2) + UndoCommand(id_t object_id, string key, T1 &arg1) : _obj_id(object_id), _key(key) { - _args.push_back(arg1); - _args.push_back(arg2); + _slot = bind( mem_fun( get_object(object_id), get_method(key) ), + arg1); + _args.push_back(&arg1); } - UndoCommand(id_t object_id, string key, T1 arg1, T2 arg2, T3 arg3) + UndoCommand(id_t object_id, string key, T1 &arg1, T2 &arg2) : _obj_id(object_id), _key(key) { - _args.push_back(arg1); - _args.push_back(arg2); - _args.push_back(arg3); + _slot = bind( mem_fun( get_object(object_id), get_method(key) ), + arg1, arg2); + _args.push_back(&arg1); + _args.push_back(&arg2); } - UndoCommand(id_t object_id, string key, T1 arg1, T2 arg2, T3 arg3, T4 arg4) + UndoCommand(id_t object_id, string key, T1 &arg1, T2 &arg2, T3 &arg3) : _obj_id(object_id), _key(key) { - _args.push_back(arg1); - _args.push_back(arg2); - _args.push_back(arg3); - _args.push_back(arg4); + _slot = bind( mem_fun( get_object(object_id), get_method(key) ), + arg1, arg2, arg3); + _args.push_back(&arg1); + _args.push_back(&arg2); + _args.push_back(&arg3); + } + UndoCommand(id_t object_id, string key, T1 &arg1, T2 &arg2, T3 &arg3, T4 &arg4) + : _obj_id(object_id), _key(key) + { + _slot = bind( mem_fun( get_object(object_id), get_method(key) ), + arg1, arg2, arg4); + _args.push_back(&arg1); + _args.push_back(&arg2); + _args.push_back(&arg3); + _args.push_back(&arg4); } void operator() () { return _slot(); } + XMLNode &serialize(); protected: + template T_object &get_object(id_t); + template T_method &get_method(string); id_t _obj_id; string _key; slot _slot; + // Note that arguments must be instances of Serializable or this will // rightly cause a compiler error when compiling the constructor. list _args; From 7ff370e79895d7eb293e7214689b791bd98415fb Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Thu, 22 Jun 2006 23:40:55 +0000 Subject: [PATCH 07/27] Merging from trunk git-svn-id: svn://localhost/ardour2/branches/undo@638 d708f5d6-7413-0410-9779-e7cbd77b26cf --- SConstruct | 80 +- gtk2_ardour/SConscript | 46 +- gtk2_ardour/about.cc | 1 + gtk2_ardour/actions.cc | 1 + gtk2_ardour/add_route_dialog.cc | 1 + gtk2_ardour/analysis_window.cc | 1 + gtk2_ardour/ardev_common.sh | 2 +- gtk2_ardour/ardour.menus | 2 + gtk2_ardour/ardour_ui.cc | 51 +- gtk2_ardour/ardour_ui.h | 10 +- gtk2_ardour/ardour_ui2.cc | 1 + gtk2_ardour/ardour_ui_dependents.cc | 1 + gtk2_ardour/ardour_ui_dialogs.cc | 5 +- gtk2_ardour/ardour_ui_ed.cc | 10 +- gtk2_ardour/ardour_ui_mixer.cc | 1 + gtk2_ardour/ardour_ui_options.cc | 5 +- gtk2_ardour/audio_clock.cc | 42 +- gtk2_ardour/audio_clock.h | 2 + gtk2_ardour/audio_time_axis.cc | 19 +- gtk2_ardour/audio_time_axis.h | 2 +- gtk2_ardour/automation_gain_line.cc | 1 + gtk2_ardour/automation_line.cc | 1 + gtk2_ardour/automation_pan_line.cc | 1 + gtk2_ardour/automation_time_axis.cc | 1 + gtk2_ardour/axis_view.h | 10 +- gtk2_ardour/canvas-waveview.c | 24 +- gtk2_ardour/color_manager.cc | 1 + gtk2_ardour/connection_editor.cc | 1 + gtk2_ardour/crossfade_edit.cc | 2 + gtk2_ardour/crossfade_view.cc | 10 +- gtk2_ardour/crossfade_view.h | 1 - gtk2_ardour/curvetest.cc | 1 + gtk2_ardour/editor.cc | 13 +- gtk2_ardour/editor.h | 4 +- gtk2_ardour/editor_actions.cc | 1 + gtk2_ardour/editor_audio_import.cc | 12 +- gtk2_ardour/editor_audiotrack.cc | 3 +- gtk2_ardour/editor_canvas.cc | 1 + gtk2_ardour/editor_canvas_events.cc | 3 +- gtk2_ardour/editor_cursors.cc | 1 + gtk2_ardour/editor_edit_groups.cc | 1 + gtk2_ardour/editor_export_audio.cc | 30 +- gtk2_ardour/editor_hscroller.cc | 1 + gtk2_ardour/editor_imageframe.cc | 1 + gtk2_ardour/editor_keys.cc | 1 + gtk2_ardour/editor_markers.cc | 1 + gtk2_ardour/editor_mouse.cc | 11 +- gtk2_ardour/editor_nudge.cc | 1 + gtk2_ardour/editor_ops.cc | 9 +- gtk2_ardour/editor_region_list.cc | 2 + gtk2_ardour/editor_route_list.cc | 1 + gtk2_ardour/editor_rulers.cc | 21 +- gtk2_ardour/editor_selection_list.cc | 1 + gtk2_ardour/editor_tempodisplay.cc | 1 + gtk2_ardour/editor_timefx.cc | 3 +- gtk2_ardour/export_dialog.cc | 1 + gtk2_ardour/export_range_markers_dialog.cc | 1 + gtk2_ardour/gain_automation_time_axis.cc | 1 + gtk2_ardour/gain_meter.cc | 33 +- gtk2_ardour/glade_factory.cc | 37 - gtk2_ardour/glade_factory.h | 45 - gtk2_ardour/glade_path.cc | 38 - gtk2_ardour/glade_path.h | 49 - gtk2_ardour/imageframe_socket_handler.cc | 3 +- gtk2_ardour/imageframe_time_axis.cc | 1 + gtk2_ardour/imageframe_time_axis_view.cc | 6 +- gtk2_ardour/imageframe_view.cc | 7 +- gtk2_ardour/imageframe_view.h | 2 +- gtk2_ardour/io_selector.cc | 3 +- gtk2_ardour/keyboard.cc | 2 + gtk2_ardour/location_ui.cc | 1 + gtk2_ardour/main.cc | 28 +- gtk2_ardour/marker_time_axis.cc | 1 + gtk2_ardour/meter_bridge.cc | 3 +- gtk2_ardour/meter_bridge_strip.cc | 1 + gtk2_ardour/mixer_strip.cc | 10 +- gtk2_ardour/mixer_strip.h | 2 +- gtk2_ardour/mixer_ui.cc | 3 +- gtk2_ardour/mixer_ui.h | 2 +- gtk2_ardour/new_session_dialog.cc | 5 + gtk2_ardour/option_editor.cc | 1 + gtk2_ardour/opts.cc | 6 +- gtk2_ardour/pan_automation_time_axis.cc | 1 + gtk2_ardour/panner2d.cc | 3 +- gtk2_ardour/panner2d.h | 2 +- gtk2_ardour/panner_ui.cc | 1 + gtk2_ardour/playlist_selector.cc | 7 +- gtk2_ardour/plugin_selector.cc | 7 + gtk2_ardour/plugin_ui.cc | 1 + gtk2_ardour/plugin_ui.h | 2 +- gtk2_ardour/po/de_DE.po | 3061 ++++++++-------- gtk2_ardour/po/el_GR.po | 3103 ++++++++-------- gtk2_ardour/po/es_ES.po | 3074 ++++++++-------- gtk2_ardour/po/fr_FR.po | 3130 +++++++++-------- gtk2_ardour/po/it_IT.po | 3056 ++++++++-------- gtk2_ardour/po/pt_BR.po | 3085 ++++++++-------- gtk2_ardour/po/pt_PT.po | 3074 ++++++++-------- gtk2_ardour/po/ru_RU.po | 3094 ++++++++-------- gtk2_ardour/redirect_automation_line.cc | 1 + gtk2_ardour/redirect_automation_line.h | 2 - gtk2_ardour/redirect_automation_time_axis.cc | 1 + gtk2_ardour/redirect_box.cc | 3 +- gtk2_ardour/region_editor.cc | 1 + gtk2_ardour/region_gain_line.cc | 1 + gtk2_ardour/region_selection.cc | 1 + gtk2_ardour/regionview.cc | 10 +- gtk2_ardour/regionview.h | 1 - gtk2_ardour/route_params_ui.cc | 3 +- gtk2_ardour/route_redirect_selection.cc | 1 + gtk2_ardour/route_ui.cc | 13 +- gtk2_ardour/route_ui.h | 4 +- gtk2_ardour/selectable.h | 18 +- gtk2_ardour/selection.cc | 1 + gtk2_ardour/send_ui.cc | 1 + gtk2_ardour/sfdb_ui.cc | 11 +- gtk2_ardour/sfdb_ui.h | 4 +- gtk2_ardour/streamview.cc | 16 +- gtk2_ardour/streamview.h | 6 +- gtk2_ardour/taperegionview.cc | 4 +- gtk2_ardour/tempo_dialog.cc | 1 + gtk2_ardour/time_axis_view.cc | 1 + gtk2_ardour/time_axis_view_item.cc | 17 +- gtk2_ardour/time_axis_view_item.h | 18 +- gtk2_ardour/time_selection.cc | 1 + gtk2_ardour/utils.cc | 1 + gtk2_ardour/visual_time_axis.cc | 1 + gtk2_ardour/vst_pluginui.cc | 38 +- libs/ardour/SConscript | 14 +- libs/ardour/ardour/ardour.h | 2 +- .../{diskstream.h => audio_diskstream.h} | 26 +- libs/ardour/ardour/audio_track.h | 8 +- libs/ardour/ardour/audiofilesource.h | 157 + libs/ardour/ardour/audiofilter.h | 2 - libs/ardour/ardour/audioregion.h | 12 +- libs/ardour/ardour/audiosource.h | 166 + libs/ardour/ardour/constsource.h | 60 - libs/ardour/ardour/coreaudio_source.h | 9 +- libs/ardour/ardour/cycle_timer.h | 18 +- libs/ardour/ardour/destructive_filesource.h | 19 +- libs/ardour/ardour/externalsource.h | 67 - libs/ardour/ardour/filesource.h | 201 -- libs/ardour/ardour/io.h | 1 - libs/ardour/ardour/osc.h | 2 +- libs/ardour/ardour/playlist.h | 1 - libs/ardour/ardour/region.h | 1 - libs/ardour/ardour/route.h | 2 +- libs/ardour/ardour/seqsource.h | 55 - libs/ardour/ardour/session.h | 98 +- libs/ardour/ardour/session_diskstream.h | 6 +- libs/ardour/ardour/silentsource.h | 56 - libs/ardour/ardour/sndfilesource.h | 46 +- libs/ardour/ardour/source.h | 130 +- libs/ardour/ardour/types.h | 40 +- .../{diskstream.cc => audio_diskstream.cc} | 211 +- libs/ardour/audio_library.cc | 1 + libs/ardour/audio_playlist.cc | 1 + libs/ardour/audio_track.cc | 44 +- libs/ardour/audioengine.cc | 10 +- libs/ardour/audiofilesource.cc | 662 ++++ libs/ardour/audiofilter.cc | 13 +- libs/ardour/audioregion.cc | 17 +- libs/ardour/audiosource.cc | 899 +++++ libs/ardour/auditioner.cc | 2 +- libs/ardour/automation_event.cc | 1 + libs/ardour/configuration.cc | 5 +- libs/ardour/connection.cc | 1 + libs/ardour/control_protocol_manager.cc | 6 +- libs/ardour/coreaudio_source.cc | 9 +- libs/ardour/crossfade.cc | 2 +- libs/ardour/curve.cc | 1 + libs/ardour/cycle_timer.cc | 2 + libs/ardour/destructive_filesource.cc | 200 +- libs/ardour/externalsource.cc | 246 -- libs/ardour/filesource.cc | 1513 -------- libs/ardour/globals.cc | 7 +- libs/ardour/import.cc | 16 +- libs/ardour/insert.cc | 2 +- libs/ardour/io.cc | 11 +- libs/ardour/jack_slave.cc | 1 - libs/ardour/ladspa_plugin.cc | 1 + libs/ardour/location.cc | 1 + libs/ardour/mtc_slave.cc | 3 +- libs/ardour/named_selection.cc | 1 + libs/ardour/osc.cc | 1 - libs/ardour/panner.cc | 2 +- libs/ardour/playlist.cc | 2 +- libs/ardour/playlist_factory.cc | 23 + libs/ardour/plugin.cc | 1 + libs/ardour/plugin_manager.cc | 1 + libs/ardour/po/el_GR.po | 1391 ++++---- libs/ardour/po/it_IT.po | 1361 +++---- libs/ardour/po/ru_RU.po | 1208 +++---- libs/ardour/recent_sessions.cc | 2 +- libs/ardour/redirect.cc | 2 +- libs/ardour/region.cc | 1 + libs/ardour/reverse.cc | 2 +- libs/ardour/route.cc | 4 +- libs/ardour/route_group.cc | 2 +- libs/ardour/send.cc | 1 + libs/ardour/session.cc | 199 +- libs/ardour/session_butler.cc | 28 +- libs/ardour/session_click.cc | 1 + libs/ardour/session_control.cc | 6 +- libs/ardour/session_events.cc | 8 +- libs/ardour/session_export.cc | 6 +- libs/ardour/session_feedback.cc | 5 +- libs/ardour/session_midi.cc | 16 +- libs/ardour/session_process.cc | 24 +- libs/ardour/session_state.cc | 105 +- libs/ardour/session_time.cc | 395 +-- libs/ardour/session_timefx.cc | 14 +- libs/ardour/session_transport.cc | 47 +- libs/ardour/sndfilesource.cc | 467 ++- libs/ardour/source.cc | 777 +--- libs/ardour/state_manager.cc | 1 + libs/ardour/stateful.cc | 2 + libs/ardour/tempo.cc | 1 + libs/ardour/utils.cc | 3 +- libs/ardour/vst_plugin.cc | 1 + libs/fst/SConscript | 27 + libs/fst/fst.c | 27 + libs/fst/fst.h | 108 + libs/fst/fstinfofile.c | 266 ++ libs/fst/jackvst.h | 35 + libs/fst/vsti.c | 181 + libs/fst/vstwin.c | 583 +++ libs/gtkmm2ext/fastmeter.cc | 3 +- libs/gtkmm2ext/gtk_ui.cc | 1 + libs/gtkmm2ext/po/el_GR.po | 6 +- libs/gtkmm2ext/po/es_ES.po | 6 +- libs/gtkmm2ext/po/pt_BR.po | 6 +- libs/gtkmm2ext/po/ru_RU.po | 6 +- libs/gtkmm2ext/selector.cc | 1 - libs/libsndfile/src/sndfile.c | 18 +- libs/libsndfile/src/wav.c | 1 - libs/midi++2/fd_midiport.cc | 1 + libs/midi++2/midicontrollable.cc | 1 + libs/midi++2/midimanager.cc | 1 + libs/midi++2/mmc.cc | 1 + libs/midi++2/mmctest.cc | 1 + libs/pbd3/SConscript | 1 + libs/pbd3/base_ui.cc | 1 + libs/pbd3/error.cc | 7 + libs/pbd3/pathscanner.cc | 2 + libs/pbd3/pbd/error.h | 18 +- libs/pbd3/pbd/transmitter.h | 1 + libs/pbd3/pool.cc | 1 + libs/pbd3/transmitter.cc | 11 +- libs/surfaces/control_protocol/SConscript | 3 +- libs/surfaces/control_protocol/basic_ui.cc | 15 +- .../control_protocol/control_protocol.cc | 2 +- .../{ => control_protocol}/basic_ui.h | 25 +- .../{ => control_protocol}/control_protocol.h | 2 +- .../control_protocol/control_protocol/smpte.h | 80 + libs/surfaces/control_protocol/smpte.cc | 406 +++ .../generic_midi_control_protocol.h | 2 +- libs/surfaces/generic_midi/interface.cc | 3 +- libs/surfaces/tranzport/interface.cc | 3 +- .../tranzport/tranzport_control_protocol.cc | 8 +- .../tranzport/tranzport_control_protocol.h | 2 +- templates/SConscript | 2 +- vst/SConscript | 54 + vst/winmain.c | 17 + 263 files changed, 20008 insertions(+), 18770 deletions(-) delete mode 100644 gtk2_ardour/glade_factory.cc delete mode 100644 gtk2_ardour/glade_factory.h delete mode 100644 gtk2_ardour/glade_path.cc delete mode 100644 gtk2_ardour/glade_path.h rename libs/ardour/ardour/{diskstream.h => audio_diskstream.h} (94%) create mode 100644 libs/ardour/ardour/audiofilesource.h create mode 100644 libs/ardour/ardour/audiosource.h delete mode 100644 libs/ardour/ardour/constsource.h delete mode 100644 libs/ardour/ardour/externalsource.h delete mode 100644 libs/ardour/ardour/filesource.h delete mode 100644 libs/ardour/ardour/seqsource.h delete mode 100644 libs/ardour/ardour/silentsource.h rename libs/ardour/{diskstream.cc => audio_diskstream.cc} (89%) create mode 100644 libs/ardour/audiofilesource.cc create mode 100644 libs/ardour/audiosource.cc delete mode 100644 libs/ardour/externalsource.cc delete mode 100644 libs/ardour/filesource.cc create mode 100644 libs/fst/SConscript create mode 100644 libs/fst/fst.c create mode 100644 libs/fst/fst.h create mode 100644 libs/fst/fstinfofile.c create mode 100644 libs/fst/jackvst.h create mode 100644 libs/fst/vsti.c create mode 100644 libs/fst/vstwin.c create mode 100644 libs/pbd3/error.cc rename libs/surfaces/control_protocol/{ => control_protocol}/basic_ui.h (77%) rename libs/surfaces/control_protocol/{ => control_protocol}/control_protocol.h (98%) create mode 100644 libs/surfaces/control_protocol/control_protocol/smpte.h create mode 100644 libs/surfaces/control_protocol/smpte.cc create mode 100644 vst/SConscript create mode 100644 vst/winmain.c diff --git a/SConstruct b/SConstruct index b0c0bb07cc..65dfd3b06e 100644 --- a/SConstruct +++ b/SConstruct @@ -8,13 +8,14 @@ import glob import errno import time import platform +import string from sets import Set import SCons.Node.FS SConsignFile() EnsureSConsVersion(0, 96) -version = '2.0beta1' +version = '2.0beta2' subst_dict = { } @@ -25,20 +26,20 @@ subst_dict = { } opts = Options('scache.conf') opts.AddOptions( ('ARCH', 'Set architecture-specific compilation flags by hand (all flags as 1 argument)',''), - BoolOption('SYSLIBS', 'USE AT YOUR OWN RISK: CANCELS ALL SUPPORT FROM ARDOUR AUTHORS: Use existing system versions of various libraries instead of internal ones', 0), + BoolOption('COREAUDIO', 'Compile with Apple\'s CoreAudio library', 0), BoolOption('DEBUG', 'Set to build with debugging information and no optimizations', 0), PathOption('DESTDIR', 'Set the intermediate install "prefix"', '/'), + EnumOption('DIST_TARGET', 'Build target for cross compiling packagers', 'auto', allowed_values=('auto', 'i386', 'i686', 'x86_64', 'powerpc', 'tiger', 'panther', 'none' ), ignorecase=2), + BoolOption('DMALLOC', 'Compile and link using the dmalloc library', 0), + BoolOption('FFT_ANALYSIS', 'Include FFT analysis window', 0), + BoolOption('FPU_OPTIMIZATION', 'Build runtime checked assembler code', 1), + BoolOption('LIBLO', 'Compile with support for liblo library', 1), BoolOption('NLS', 'Set to turn on i18n support', 1), PathOption('PREFIX', 'Set the install "prefix"', '/usr/local'), - BoolOption('VST', 'Compile with support for VST', 0), - BoolOption('VERSIONED', 'Add version information to ardour/gtk executable name inside the build directory', 0), - EnumOption('DIST_TARGET', 'Build target for cross compiling packagers', 'auto', allowed_values=('auto', 'i386', 'i686', 'x86_64', 'powerpc', 'tiger', 'panther', 'none' ), ignorecase=2), - BoolOption('FPU_OPTIMIZATION', 'Build runtime checked assembler code', 1), - BoolOption('FFT_ANALYSIS', 'Include FFT analysis window', 0), BoolOption('SURFACES', 'Build support for control surfaces', 0), - BoolOption('DMALLOC', 'Compile and link using the dmalloc library', 0), - BoolOption('LIBLO', 'Compile with support for liblo library', 1), - BoolOption('COREAUDIO', 'Compile with Apple\'s CoreAudio library -- UNSTABLE', 0) + BoolOption('SYSLIBS', 'USE AT YOUR OWN RISK: CANCELS ALL SUPPORT FROM ARDOUR AUTHORS: Use existing system versions of various libraries instead of internal ones', 0), + BoolOption('VERSIONED', 'Add version information to ardour/gtk executable name inside the build directory', 0), + BoolOption('VST', 'Compile with support for VST', 0) ) #---------------------------------------------------------------------- @@ -58,8 +59,8 @@ class LibraryInfo(Environment): self.Append (LINKFLAGS = other.get('LINKFLAGS', [])) self.Replace(LIBPATH = list(Set(self.get('LIBPATH', [])))) self.Replace(CPPPATH = list(Set(self.get('CPPPATH',[])))) - #doing LINKFLAGS breaks -framework - #doing LIBS break link order dependency + #doing LINKFLAGS breaks -framework + #doing LIBS break link order dependency env = LibraryInfo (options = opts, @@ -345,6 +346,21 @@ tarball_bld = Builder (action = tarballer, env.Append (BUILDERS = {'Distribute' : dist_bld}) env.Append (BUILDERS = {'Tarball' : tarball_bld}) +# +# Make sure they know what they are doing +# + +if env['VST']: + sys.stdout.write ("Are you building Ardour for personal use (rather than distributiont to others)? [no]: ") + answer = sys.stdin.readline () + answer = answer.rstrip().strip() + if answer != "yes" and answer != "y": + print 'You cannot build Ardour with VST support for distribution to others.\nIt is a violation of several different licenses. VST support disabled.' + env['VST'] = 0; + else: + print "OK, VST support will be enabled" + + # ---------------------------------------------------------------------- # Construction environment setup # ---------------------------------------------------------------------- @@ -353,7 +369,7 @@ libraries = { } libraries['core'] = LibraryInfo (CCFLAGS = '-Ilibs') -#libraries['sndfile'] = LibraryInfo(CCFLAGS = '-Ilibs/libsndfile/src') +#libraries['sndfile'] = LibraryInfo() #libraries['sndfile'].ParseConfig('pkg-config --cflags --libs sndfile') libraries['lrdf'] = LibraryInfo() @@ -408,10 +424,6 @@ libraries['pbd3'] = LibraryInfo (LIBS='pbd', LIBPATH='#libs/pbd3', CPPPATH='# libraries['gtkmm2ext'] = LibraryInfo (LIBS='gtkmm2ext', LIBPATH='#libs/gtkmm2ext', CPPPATH='#libs/gtkmm2ext') #libraries['cassowary'] = LibraryInfo(LIBS='cassowary', LIBPATH='#libs/cassowary', CPPPATH='#libs/cassowary') -libraries['fst'] = LibraryInfo() -if env['VST']: - libraries['fst'].ParseConfig('pkg-config --cflags --libs libfst') - # # Check for libusb @@ -425,6 +437,15 @@ else: libraries['usb'] = conf.Finish () +# +# Check for FLAC + +libraries['flac'] = LibraryInfo () + +conf = Configure (libraries['flac']) +conf.CheckLib ('FLAC', 'FLAC__stream_decoder_new') +libraries['flac'] = conf.Finish () + # # Check for liblo @@ -497,6 +518,14 @@ if env['SYSLIBS']: libraries['libgnomecanvasmm'] = LibraryInfo() libraries['libgnomecanvasmm'].ParseConfig ('pkg-config --cflags --libs libgnomecanvasmm-2.6') +# +# cannot use system one for the time being +# + + libraries['sndfile'] = LibraryInfo(LIBS='libsndfile', + LIBPATH='#libs/libsndfile', + CPPPATH=['#libs/libsndfile', '#libs/libsndfile/src']) + # libraries['libglademm'] = LibraryInfo() # libraries['libglademm'].ParseConfig ('pkg-config --cflags --libs libglademm-2.4') @@ -509,11 +538,15 @@ if env['SYSLIBS']: ] subdirs = [ + 'libs/libsndfile', 'libs/pbd3', 'libs/midi++2', 'libs/ardour' ] + if env['VST']: + subdirs = ['libs/fst'] + subdirs + ['vst'] + gtk_subdirs = [ # 'libs/flowcanvas', 'libs/gtkmm2ext', @@ -548,7 +581,7 @@ else: CPPPATH=['#libs', '#libs/soundtouch']) libraries['sndfile'] = LibraryInfo(LIBS='libsndfile', LIBPATH='#libs/libsndfile', - CPPPATH='#libs/libsndfile') + CPPPATH=['#libs/libsndfile', '#libs/libsndfile/src']) # libraries['libglademm'] = LibraryInfo(LIBS='libglademm', # LIBPATH='#libs/libglademm', # CPPPATH='#libs/libglademm') @@ -567,6 +600,9 @@ else: 'libs/ardour' ] + if env['VST']: + subdirs = ['libs/fst'] + subdirs + ['vst'] + gtk_subdirs = [ 'libs/glibmm2', 'libs/gtkmm2/pango', @@ -769,10 +805,12 @@ if env['DEBUG'] == 1: else: env.Append(CCFLAGS=" ".join (opt_flags)) -env.Append(CCFLAGS="-Wall") +# +# warnings flags +# -if env['VST']: - env.Append(CCFLAGS="-DVST_SUPPORT") +env.Append(CCFLAGS="-Wall") +env.Append(CXXFLAGS="-Woverloaded-virtual") if env['LIBLO']: env.Append(CCFLAGS="-DHAVE_LIBLO") diff --git a/gtk2_ardour/SConscript b/gtk2_ardour/SConscript index 8ab1c0c19c..55fa26ec85 100644 --- a/gtk2_ardour/SConscript +++ b/gtk2_ardour/SConscript @@ -26,7 +26,6 @@ gtkardour.Merge ([ libraries['ardour'], libraries['ardour_cp'], libraries['gtkmm2ext'], -# libraries['flowcanvas'], libraries['midi++2'], libraries['pbd3'], libraries['gtkmm2'], @@ -35,6 +34,7 @@ gtkardour.Merge ([ libraries['libgnomecanvasmm'], libraries['sysmidi'], libraries['sndfile'], + libraries['flac'], libraries['lrdf'], libraries['glibmm2'], libraries['pangomm'], @@ -57,13 +57,11 @@ if gtkardour['FFT_ANALYSIS']: gtkardour.Merge ([libraries['fftw3f']]) gtkardour.Append(CCFLAGS='-DFFT_ANALYSIS') -if gtkardour['VST']: - gtkardour.Merge ([ libraries['fst']]) - skipped_files=Split(""" connection_editor.cc """) + gtkardour_files=Split(""" about.cc actions.cc @@ -183,6 +181,7 @@ visual_time_axis.cc waveview.cc """) + fft_analysis_files=Split(""" analysis_window.cc fft_graph.cc @@ -202,15 +201,16 @@ itest.cc """) extra_sources = [] + vst_files = [ 'vst_pluginui.cc' ] if env['VST']: - extra_sources += vst_files - + extra_sources += vst_files + gtkardour.Append (CCFLAGS="-DVST_SUPPORT", CPPPATH="#libs/fst") + if env['FFT_ANALYSIS']: extra_sources += fft_analysis_files - intl_files += extra_sources gtkardour.Append(CCFLAGS="-D_REENTRANT -D_LARGEFILE_SOURCE -D_LARGEFILE64_SOURCE") @@ -225,6 +225,8 @@ gtkardour.VersionBuild(['version.cc','version.h'], 'SConscript') executable = 'ardour.bin' ardour = gtkardour.Program(target = executable, source = gtkardour_files + extra_sources) +ardourlib = gtkardour.SharedLibrary(target = 'ardourgtk', source = gtkardour_files + extra_sources) + mtest = gtkardour.Program(target = 'mtest', source = mtest_files) itest = gtkardour.Program(target = 'itest', source = itest_files) @@ -234,21 +236,28 @@ my_subst_dict['%INSTALL_PREFIX%'] = install_prefix ardoursh = env.SubstInFile ('ardour.sh','ardour.sh.in', SUBST_DICT = my_subst_dict); env.AddPostAction (ardoursh, Chmod ('$TARGET', 0755)) -Default(ardour) +if env['VST']: + Default(ardourlib) + # the library - into the library dir + env.Alias('install', env.Install(os.path.join(install_prefix, 'lib/ardour2'), ardourlib)) +else: -if env['VERSIONED']: - Default (env.VersionedExecutable ('tagged_executable', ardour)) + if env['VERSIONED']: + Default (env.VersionedExecutable ('tagged_executable', ardour)) + else: + Default(ardour) + + #install + + # the executable - into the library dir + env.Alias('install', env.Install(os.path.join(install_prefix, 'lib/ardour2'), ardour)) + # the script - into the bin dir + env.Alias('install', env.InstallAs(os.path.join(install_prefix, 'bin')+'/ardour2', ardoursh)) if env['NLS']: - Export('gtkardour', 'intl_files') - SConscript ('po/SConscript') + Export('gtkardour', 'intl_files') + SConscript ('po/SConscript') -#install - -# the executable - into the library dir -env.Alias('install', env.Install(os.path.join(install_prefix, 'lib/ardour2'), ardour)) -# the script - into the bin dir -env.Alias('install', env.InstallAs(os.path.join(install_prefix, 'bin')+'/ardour2', ardoursh)) # configuration files env.Alias('install', env.Install(os.path.join(config_prefix, 'ardour2'), 'ardour2_ui.rc')) env.Alias('install', env.Install(os.path.join(config_prefix, 'ardour2'), 'ardour.menus')) @@ -258,6 +267,7 @@ env.Alias('install', env.Install(os.path.join(config_prefix, 'ardour2'), 'ardour env.Alias('install', env.Install(os.path.join(install_prefix, 'share/ardour2'), 'splash.ppm')) env.Alias('install', env.Install(os.path.join(install_prefix, 'share/ardour2/pixmaps'), pixmap_files)) + #dist env.Alias ('tarball', env.Distribute (env['DISTTREE'], [ 'SConscript', diff --git a/gtk2_ardour/about.cc b/gtk2_ardour/about.cc index 94284f58d4..033b5c4604 100644 --- a/gtk2_ardour/about.cc +++ b/gtk2_ardour/about.cc @@ -43,6 +43,7 @@ using namespace Gdk; using namespace std; using namespace sigc; using namespace ARDOUR; +using namespace PBD; #ifdef WITH_PAYMENT_OPTIONS diff --git a/gtk2_ardour/actions.cc b/gtk2_ardour/actions.cc index 78acffd6d1..ee688c3660 100644 --- a/gtk2_ardour/actions.cc +++ b/gtk2_ardour/actions.cc @@ -39,6 +39,7 @@ using namespace std; using namespace Gtk; using namespace Glib; using namespace sigc; +using namespace PBD; vector > ActionManager::session_sensitive_actions; vector > ActionManager::region_list_selection_sensitive_actions; diff --git a/gtk2_ardour/add_route_dialog.cc b/gtk2_ardour/add_route_dialog.cc index 8664dae61c..7e89489afd 100644 --- a/gtk2_ardour/add_route_dialog.cc +++ b/gtk2_ardour/add_route_dialog.cc @@ -35,6 +35,7 @@ using namespace Gtk; using namespace Gtkmm2ext; using namespace sigc; using namespace std; +using namespace PBD; static const char* channel_setup_names[] = { "Mono", diff --git a/gtk2_ardour/analysis_window.cc b/gtk2_ardour/analysis_window.cc index f044ca7388..b8318f45fe 100644 --- a/gtk2_ardour/analysis_window.cc +++ b/gtk2_ardour/analysis_window.cc @@ -40,6 +40,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; AnalysisWindow::AnalysisWindow() : ArdourDialog(_("analysis window")), diff --git a/gtk2_ardour/ardev_common.sh b/gtk2_ardour/ardev_common.sh index 9483ae2971..5c68933a96 100755 --- a/gtk2_ardour/ardev_common.sh +++ b/gtk2_ardour/ardev_common.sh @@ -2,7 +2,7 @@ export ARDOUR_PATH=./glade:./pixmaps:. -export LD_LIBRARY_PATH=../libs/surfaces/control_protocol:../libs/ardour:../libs/midi++2:../libs/pbd3:../libs/soundtouch:../libs/gtkmm2ext:../libs/sigc++2:../libs/glibmm2:../libs/gtkmm2/atk:../libs/gtkmm2/pango:../libs/gtkmm2/gdk:../libs/gtkmm2/gtk:../libs/libgnomecanvasmm:../libs/libglademm:$LD_LIBRARY_PATH +export LD_LIBRARY_PATH=../libs/surfaces/control_protocol:../libs/ardour:../libs/midi++2:../libs/pbd3:../libs/soundtouch:../libs/gtkmm2ext:../libs/sigc++2:../libs/glibmm2:../libs/gtkmm2/atk:../libs/gtkmm2/pango:../libs/gtkmm2/gdk:../libs/gtkmm2/gtk:../libs/libgnomecanvasmm:../libs/libsndfile:$LD_LIBRARY_PATH # DYLD_LIBRARY_PATH is for darwin. export DYLD_LIBRARY_PATH=$LD_LIBRARY_PATH diff --git a/gtk2_ardour/ardour.menus b/gtk2_ardour/ardour.menus index 3c13ac8342..9293883067 100644 --- a/gtk2_ardour/ardour.menus +++ b/gtk2_ardour/ardour.menus @@ -207,6 +207,8 @@ + + diff --git a/gtk2_ardour/ardour_ui.cc b/gtk2_ardour/ardour_ui.cc index 640b62df1f..f452ec9c7e 100644 --- a/gtk2_ardour/ardour_ui.cc +++ b/gtk2_ardour/ardour_ui.cc @@ -50,8 +50,8 @@ #include #include #include -#include -#include +#include +#include #include #include #include @@ -76,6 +76,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace Gtkmm2ext; using namespace Gtk; using namespace sigc; @@ -184,9 +185,9 @@ ARDOUR_UI::ARDOUR_UI (int *argcp, char **argvp[], string rcfile) gettimeofday (&last_peak_grab, 0); gettimeofday (&last_shuttle_request, 0); - ARDOUR::DiskStream::DeleteSources.connect (mem_fun(*this, &ARDOUR_UI::delete_sources_in_the_right_thread)); - ARDOUR::DiskStream::DiskOverrun.connect (mem_fun(*this, &ARDOUR_UI::disk_overrun_handler)); - ARDOUR::DiskStream::DiskUnderrun.connect (mem_fun(*this, &ARDOUR_UI::disk_underrun_handler)); + ARDOUR::AudioDiskstream::DeleteSources.connect (mem_fun(*this, &ARDOUR_UI::delete_sources_in_the_right_thread)); + ARDOUR::AudioDiskstream::DiskOverrun.connect (mem_fun(*this, &ARDOUR_UI::disk_overrun_handler)); + ARDOUR::AudioDiskstream::DiskUnderrun.connect (mem_fun(*this, &ARDOUR_UI::disk_underrun_handler)); /* handle pending state with a dialog */ @@ -241,10 +242,10 @@ ARDOUR_UI::set_engine (AudioEngine& e) /* this being a GUI and all, we want peakfiles */ - FileSource::set_build_peakfiles (true); - FileSource::set_build_missing_peakfiles (true); + AudioFileSource::set_build_peakfiles (true); + AudioFileSource::set_build_missing_peakfiles (true); - if (Source::start_peak_thread ()) { + if (AudioSource::start_peak_thread ()) { throw failed_constructor(); } @@ -281,7 +282,7 @@ ARDOUR_UI::~ARDOUR_UI () delete add_route_dialog; } - Source::stop_peak_thread (); + AudioSource::stop_peak_thread (); } gint @@ -542,7 +543,7 @@ ARDOUR_UI::update_buffer_load () } void -ARDOUR_UI::count_recenabled_diskstreams (DiskStream& ds) +ARDOUR_UI::count_recenabled_diskstreams (AudioDiskstream& ds) { if (ds.record_enabled()) { rec_enabled_diskstreams++; @@ -570,7 +571,7 @@ ARDOUR_UI::update_disk_space() if (session->actively_recording()){ rec_enabled_diskstreams = 0; - session->foreach_diskstream (this, &ARDOUR_UI::count_recenabled_diskstreams); + session->foreach_audio_diskstream (this, &ARDOUR_UI::count_recenabled_diskstreams); if (rec_enabled_diskstreams) { frames /= rec_enabled_diskstreams; @@ -917,7 +918,7 @@ restart JACK with more ports.")); } void -ARDOUR_UI::diskstream_added (DiskStream* ds) +ARDOUR_UI::diskstream_added (AudioDiskstream* ds) { } @@ -1164,7 +1165,7 @@ ARDOUR_UI::toggle_monitor_enable (guint32 dstream) return; } - DiskStream *ds; + AudioDiskstream *ds; if ((ds = session->diskstream_by_id (dstream)) != 0) { Port *port = ds->io()->input (0); @@ -1179,7 +1180,7 @@ ARDOUR_UI::toggle_record_enable (guint32 dstream) return; } - DiskStream *ds; + AudioDiskstream *ds; if ((ds = session->diskstream_by_id (dstream)) != 0) { ds->set_record_enabled (!ds->record_enabled(), this); @@ -1386,7 +1387,7 @@ ARDOUR_UI::stop_blinking () void -ARDOUR_UI::add_diskstream_to_menu (DiskStream& dstream) +ARDOUR_UI::add_diskstream_to_menu (AudioDiskstream& dstream) { using namespace Gtk; using namespace Menu_Helpers; @@ -1424,7 +1425,7 @@ ARDOUR_UI::select_diskstream (GdkEventButton *ev) MenuList& items = diskstream_menu->items(); items.push_back (MenuElem (_("No Stream"), (bind (mem_fun(*this, &ARDOUR_UI::diskstream_selected), -1)))); - session->foreach_diskstream (this, &ARDOUR_UI::add_diskstream_to_menu); + session->foreach_audio_diskstream (this, &ARDOUR_UI::add_diskstream_to_menu); if (ev) { diskstream_menu->popup (ev->button, ev->time); @@ -1569,7 +1570,7 @@ ARDOUR_UI::secondary_clock_value_changed () } void -ARDOUR_UI::rec_enable_button_blink (bool onoff, DiskStream *dstream, Widget *w) +ARDOUR_UI::rec_enable_button_blink (bool onoff, AudioDiskstream *dstream, Widget *w) { if (session && dstream && dstream->record_enabled()) { @@ -2216,11 +2217,11 @@ ARDOUR_UI::halt_on_xrun_message () } void -ARDOUR_UI::delete_sources_in_the_right_thread (list* deletion_list) +ARDOUR_UI::delete_sources_in_the_right_thread (list* deletion_list) { ENSURE_GUI_THREAD (bind (mem_fun(*this, &ARDOUR_UI::delete_sources_in_the_right_thread), deletion_list)); - for (list::iterator i = deletion_list->begin(); i != deletion_list->end(); ++i) { + for (list::iterator i = deletion_list->begin(); i != deletion_list->end(); ++i) { delete *i; } @@ -2377,6 +2378,12 @@ ARDOUR_UI::set_native_file_header_format (HeaderFormat hf) case RF64: act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatRF64")); break; + case CAF: + act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatCAF")); + break; + case AIFF: + act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatAIFF")); + break; } if (act) { @@ -2451,6 +2458,12 @@ ARDOUR_UI::use_config () case RF64: act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatRF64")); break; + case CAF: + act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatCAF")); + break; + case AIFF: + act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatAIFF")); + break; } if (act) { diff --git a/gtk2_ardour/ardour_ui.h b/gtk2_ardour/ardour_ui.h index a759c6cd61..678342f32b 100644 --- a/gtk2_ardour/ardour_ui.h +++ b/gtk2_ardour/ardour_ui.h @@ -167,7 +167,7 @@ class ARDOUR_UI : public Gtkmm2ext::UI blinking rec-enable buttons. */ - void rec_enable_button_blink (bool onoff, ARDOUR::DiskStream *, Gtk::Widget *w); + void rec_enable_button_blink (bool onoff, ARDOUR::AudioDiskstream *, Gtk::Widget *w); void name_io_setup (ARDOUR::AudioEngine&, string&, ARDOUR::IO& io, bool in); void choose_io (ARDOUR::IO&, bool input); @@ -522,7 +522,7 @@ class ARDOUR_UI : public Gtkmm2ext::UI sigc::connection point_one_second_connection; sigc::connection point_zero_one_second_connection; - void diskstream_added (ARDOUR::DiskStream*); + void diskstream_added (ARDOUR::AudioDiskstream*); gint session_menu (GdkEventButton *); @@ -539,7 +539,7 @@ class ARDOUR_UI : public Gtkmm2ext::UI void session_add_audio_route (bool disk, int32_t input_channels, int32_t output_channels, ARDOUR::TrackMode mode); - void add_diskstream_to_menu (ARDOUR::DiskStream&); + void add_diskstream_to_menu (ARDOUR::AudioDiskstream&); void diskstream_selected (gint32); Gtk::Menu *diskstream_menu; gint32 selected_dstream; @@ -630,7 +630,7 @@ class ARDOUR_UI : public Gtkmm2ext::UI void toggle_monitor_enable (guint32); uint32_t rec_enabled_diskstreams; - void count_recenabled_diskstreams (ARDOUR::DiskStream&); + void count_recenabled_diskstreams (ARDOUR::AudioDiskstream&); About* about; bool shown_flag; @@ -649,7 +649,7 @@ class ARDOUR_UI : public Gtkmm2ext::UI struct timeval last_peak_grab; struct timeval last_shuttle_request; - void delete_sources_in_the_right_thread (list*); + void delete_sources_in_the_right_thread (list*); void editor_display_control_changed (Editing::DisplayControl c); diff --git a/gtk2_ardour/ardour_ui2.cc b/gtk2_ardour/ardour_ui2.cc index af1f3094bc..f92201e36c 100644 --- a/gtk2_ardour/ardour_ui2.cc +++ b/gtk2_ardour/ardour_ui2.cc @@ -47,6 +47,7 @@ using namespace std; using namespace ARDOUR; +using namespace PBD; using namespace Gtkmm2ext; using namespace Gtk; using namespace Glib; diff --git a/gtk2_ardour/ardour_ui_dependents.cc b/gtk2_ardour/ardour_ui_dependents.cc index 1f8b0ef702..0603fc6baa 100644 --- a/gtk2_ardour/ardour_ui_dependents.cc +++ b/gtk2_ardour/ardour_ui_dependents.cc @@ -36,6 +36,7 @@ using namespace sigc; using namespace Gtk; +using namespace PBD; namespace ARDOUR { class Session; diff --git a/gtk2_ardour/ardour_ui_dialogs.cc b/gtk2_ardour/ardour_ui_dialogs.cc index 6b1d0224db..202fa88b59 100644 --- a/gtk2_ardour/ardour_ui_dialogs.cc +++ b/gtk2_ardour/ardour_ui_dialogs.cc @@ -39,6 +39,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace Glib; using namespace Gtk; using namespace Gtkmm2ext; @@ -75,8 +76,8 @@ ARDOUR_UI::connect_to_session (Session *s) rec_button.set_sensitive (true); shuttle_box.set_sensitive (true); - if (session->n_diskstreams() == 0) { - session->DiskStreamAdded.connect (mem_fun(*this, &ARDOUR_UI::diskstream_added)); + if (session->n_audio_diskstreams() == 0) { + session->AudioDiskstreamAdded.connect (mem_fun(*this, &ARDOUR_UI::diskstream_added)); } if (connection_editor) { diff --git a/gtk2_ardour/ardour_ui_ed.cc b/gtk2_ardour/ardour_ui_ed.cc index 5bcad97d26..1bc2de26d1 100644 --- a/gtk2_ardour/ardour_ui_ed.cc +++ b/gtk2_ardour/ardour_ui_ed.cc @@ -35,11 +35,12 @@ #include #include -#include "control_protocol.h" +#include #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace Gtk; using namespace Gtkmm2ext; @@ -364,7 +365,7 @@ ARDOUR_UI::install_actions () act = ActionManager::register_toggle_action (option_actions, X_("SendMTC"), _("Send MTC"), mem_fun (*this, &ARDOUR_UI::toggle_send_mtc)); ActionManager::session_sensitive_actions.push_back (act); - act = ActionManager::register_toggle_action (option_actions, X_("SendMMC"), _("Send MMC"), mem_fun (*this, &ARDOUR_UI::toggle_send_mtc)); + act = ActionManager::register_toggle_action (option_actions, X_("SendMMC"), _("Send MMC"), mem_fun (*this, &ARDOUR_UI::toggle_send_mmc)); ActionManager::session_sensitive_actions.push_back (act); act = ActionManager::register_toggle_action (option_actions, X_("UseMMC"), _("Use MMC"), mem_fun (*this, &ARDOUR_UI::toggle_use_mmc)); ActionManager::session_sensitive_actions.push_back (act); @@ -381,8 +382,9 @@ ARDOUR_UI::install_actions () act = ActionManager::register_radio_action (option_actions, file_header_group, X_("FileHeaderFormatBWF"), X_("Broadcast WAVE"), bind (mem_fun (*this, &ARDOUR_UI::set_native_file_header_format), ARDOUR::BWF)); act = ActionManager::register_radio_action (option_actions, file_header_group, X_("FileHeaderFormatWAVE"), X_("WAVE"), bind (mem_fun (*this, &ARDOUR_UI::set_native_file_header_format), ARDOUR::WAVE)); act = ActionManager::register_radio_action (option_actions, file_header_group, X_("FileHeaderFormatWAVE64"), X_("WAVE-64"), bind (mem_fun (*this, &ARDOUR_UI::set_native_file_header_format), ARDOUR::WAVE64)); - act = ActionManager::register_radio_action (option_actions, file_header_group, X_("FileHeaderFormatiXML"), X_("iXML"), bind (mem_fun (*this, &ARDOUR_UI::set_native_file_header_format), ARDOUR::iXML)); - act = ActionManager::register_radio_action (option_actions, file_header_group, X_("FileHeaderFormatRF64"), X_("RF64"), bind (mem_fun (*this, &ARDOUR_UI::set_native_file_header_format), ARDOUR::RF64)); + // act = ActionManager::register_radio_action (option_actions, file_header_group, X_("FileHeaderFormatiXML"), X_("iXML"), bind (mem_fun (*this, &ARDOUR_UI::set_native_file_header_format), ARDOUR::iXML)); + // act = ActionManager::register_radio_action (option_actions, file_header_group, X_("FileHeaderFormatRF64"), X_("RF64"), bind (mem_fun (*this, &ARDOUR_UI::set_native_file_header_format), ARDOUR::RF64)); + act = ActionManager::register_radio_action (option_actions, file_header_group, X_("FileHeaderFormatCAF"), X_("CAF"), bind (mem_fun (*this, &ARDOUR_UI::set_native_file_header_format), ARDOUR::CAF)); RadioAction::Group file_data_group; diff --git a/gtk2_ardour/ardour_ui_mixer.cc b/gtk2_ardour/ardour_ui_mixer.cc index 8d92f70ae2..991f37c3a7 100644 --- a/gtk2_ardour/ardour_ui_mixer.cc +++ b/gtk2_ardour/ardour_ui_mixer.cc @@ -28,6 +28,7 @@ #include "mixer_ui.h" using namespace ARDOUR; +using namespace PBD; int ARDOUR_UI::create_mixer () diff --git a/gtk2_ardour/ardour_ui_options.cc b/gtk2_ardour/ardour_ui_options.cc index dbdcd6ae45..665c92d264 100644 --- a/gtk2_ardour/ardour_ui_options.cc +++ b/gtk2_ardour/ardour_ui_options.cc @@ -35,6 +35,7 @@ using namespace Gtk; using namespace Gtkmm2ext; using namespace ARDOUR; +using namespace PBD; void ARDOUR_UI::setup_config_options () @@ -46,7 +47,7 @@ ARDOUR_UI::setup_config_options () struct { char* name; bool (Configuration::*method)(void) const; - char act_type; // (t)oggle or (r)adio + char act_type; //(t)oggle or (r)adio } options[] = { { "ToggleTimeMaster", &Configuration::get_jack_time_master, 't' }, { "StopPluginsWithTransport", &Configuration::get_plugins_stop_with_transport, 't' }, @@ -76,7 +77,6 @@ ARDOUR_UI::setup_config_options () Glib::RefPtr act = ActionManager::get_action (i->c_str(), options[n].name); if (act) { Glib::RefPtr tact = Glib::RefPtr::cast_dynamic(act); - cerr << "action = " << (options[n].name) << " val = " << (Config->*(options[n].method))() << endl;//DEBUG if (options[n].act_type == 't' || (options[n].act_type == 'r' && (Config->*(options[n].method))())) tact->set_active ((Config->*(options[n].method))()); continue; @@ -257,7 +257,6 @@ ARDOUR_UI::toggle_UseHardwareMonitoring() Glib::RefPtr act = ActionManager::get_action ("options", "UseHardwareMonitoring"); if (act) { Glib::RefPtr tact = Glib::RefPtr::cast_dynamic(act); - cerr << "get_active() cond = " << tact->get_active() << endl;//DEBUG if (tact->get_active()) { Config->set_use_hardware_monitoring (true); Config->set_use_sw_monitoring (false); diff --git a/gtk2_ardour/audio_clock.cc b/gtk2_ardour/audio_clock.cc index a5e7aa7193..8c6f3a7d82 100644 --- a/gtk2_ardour/audio_clock.cc +++ b/gtk2_ardour/audio_clock.cc @@ -37,6 +37,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace sigc; using namespace Gtk; @@ -195,6 +196,8 @@ AudioClock::AudioClock (const string& name, bool allow_edit, bool duration, bool clock_base.add_events (Gdk::BUTTON_PRESS_MASK|Gdk::BUTTON_RELEASE_MASK|Gdk::SCROLL_MASK); clock_base.signal_button_release_event().connect (bind (mem_fun (*this, &AudioClock::field_button_release_event), SMPTE_Hours)); + Session::SMPTEOffsetChanged.connect (mem_fun (*this, &AudioClock::smpte_offset_changed)); + if (editable) { setup_events (); } @@ -389,6 +392,25 @@ AudioClock::set (jack_nframes_t when, bool force) last_when = when; } +void +AudioClock::smpte_offset_changed () +{ + jack_nframes_t current; + + switch (_mode) { + case SMPTE: + if (is_duration) { + current = current_duration(); + } else { + current = current_time (); + } + set (current, true); + break; + default: + break; + } +} + void AudioClock::set_frames (jack_nframes_t when, bool force) { @@ -436,7 +458,7 @@ void AudioClock::set_smpte (jack_nframes_t when, bool force) { char buf[32]; - SMPTE_Time smpte; + SMPTE::Time smpte; if (is_duration) { session->smpte_duration (when, smpte); @@ -446,9 +468,9 @@ AudioClock::set_smpte (jack_nframes_t when, bool force) if (force || smpte.hours != last_hrs || smpte.negative != last_negative) { if (smpte.negative) { - sprintf (buf, "-%02ld", smpte.hours); + sprintf (buf, "-%02" PRIu32, smpte.hours); } else { - sprintf (buf, " %02ld", smpte.hours); + sprintf (buf, " %02" PRIu32, smpte.hours); } hours_label.set_text (buf); last_hrs = smpte.hours; @@ -456,19 +478,19 @@ AudioClock::set_smpte (jack_nframes_t when, bool force) } if (force || smpte.minutes != last_mins) { - sprintf (buf, "%02ld", smpte.minutes); + sprintf (buf, "%02" PRIu32, smpte.minutes); minutes_label.set_text (buf); last_mins = smpte.minutes; } if (force || smpte.seconds != last_secs) { - sprintf (buf, "%02ld", smpte.seconds); + sprintf (buf, "%02" PRIu32, smpte.seconds); seconds_label.set_text (buf); last_secs = smpte.seconds; } if (force || smpte.frames != last_frames) { - sprintf (buf, "%02ld", smpte.frames); + sprintf (buf, "%02" PRIu32, smpte.frames); frames_label.set_text (buf); last_frames = smpte.frames; } @@ -1260,14 +1282,14 @@ AudioClock::smpte_frame_from_display () const return 0; } - SMPTE_Time smpte; + SMPTE::Time smpte; jack_nframes_t sample; smpte.hours = atoi (hours_label.get_text()); smpte.minutes = atoi (minutes_label.get_text()); smpte.seconds = atoi (seconds_label.get_text()); smpte.frames = atoi (frames_label.get_text()); - + session->smpte_to_sample( smpte, sample, false /* use_offset */, false /* use_subframes */ ); @@ -1281,10 +1303,10 @@ AudioClock::smpte_frame_from_display () const #define SMPTE_SAMPLE_TEST_7 // Testcode for smpte<->sample conversions (P.S.) - SMPTE_Time smpte1; + SMPTE::Time smpte1; jack_nframes_t sample1; jack_nframes_t oldsample = 0; - SMPTE_Time smpte2; + SMPTE::Time smpte2; jack_nframes_t sample_increment; sample_increment = (long)rint(session->frame_rate() / session->smpte_frames_per_second); diff --git a/gtk2_ardour/audio_clock.h b/gtk2_ardour/audio_clock.h index a0733e7de3..14dc6ba673 100644 --- a/gtk2_ardour/audio_clock.h +++ b/gtk2_ardour/audio_clock.h @@ -175,6 +175,8 @@ class AudioClock : public Gtk::HBox void build_ops_menu (); void setup_events (); + void smpte_offset_changed (); + static const uint32_t field_length[(int)AudioFrames+1]; }; diff --git a/gtk2_ardour/audio_time_axis.cc b/gtk2_ardour/audio_time_axis.cc index 84c7bf7e15..01205abfc8 100644 --- a/gtk2_ardour/audio_time_axis.cc +++ b/gtk2_ardour/audio_time_axis.cc @@ -38,7 +38,7 @@ #include #include -#include +#include #include #include #include @@ -80,6 +80,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace LADSPA; using namespace Gtk; using namespace Editing; @@ -823,7 +824,7 @@ AudioTimeAxisView::rename_current_playlist () string name; AudioPlaylist *pl; - DiskStream *ds; + AudioDiskstream *ds; if (((ds = get_diskstream()) == 0) || ds->destructive() || ((pl = ds->playlist()) == 0)) { return; @@ -851,7 +852,7 @@ void AudioTimeAxisView::use_copy_playlist (bool prompt) { AudioPlaylist *pl; - DiskStream *ds; + AudioDiskstream *ds; string name; if (((ds = get_diskstream()) == 0) || ds->destructive() || ((pl = ds->playlist()) == 0)) { @@ -891,7 +892,7 @@ void AudioTimeAxisView::use_new_playlist (bool prompt) { AudioPlaylist *pl; - DiskStream *ds; + AudioDiskstream *ds; string name; if (((ds = get_diskstream()) == 0) || ds->destructive() || ((pl = ds->playlist()) == 0)) { @@ -930,7 +931,7 @@ void AudioTimeAxisView::clear_playlist () { AudioPlaylist *pl; - DiskStream *ds; + AudioDiskstream *ds; if ((ds = get_diskstream()) != 0) { if ((pl = ds->playlist()) != 0) { @@ -988,7 +989,7 @@ AudioTimeAxisView::diskstream_changed (void *src) void AudioTimeAxisView::update_diskstream_display () { - DiskStream *ds; + AudioDiskstream *ds; if ((ds = get_diskstream()) != 0) { set_playlist (ds->playlist ()); @@ -1092,7 +1093,7 @@ AudioTimeAxisView::name() const Playlist * AudioTimeAxisView::playlist () const { - DiskStream *ds; + AudioDiskstream *ds; if ((ds = get_diskstream()) != 0) { return ds->playlist(); @@ -1142,7 +1143,7 @@ AudioTimeAxisView::hide_click () Region* AudioTimeAxisView::find_next_region (jack_nframes_t pos, RegionPoint point, int32_t dir) { - DiskStream *stream; + AudioDiskstream *stream; AudioPlaylist *playlist; if ((stream = get_diskstream()) != 0 && (playlist = stream->playlist()) != 0) { @@ -1717,7 +1718,7 @@ bool AudioTimeAxisView::cut_copy_clear (Selection& selection, CutCopyOp op) { Playlist* what_we_got; - DiskStream* ds = get_diskstream(); + AudioDiskstream* ds = get_diskstream(); Playlist* playlist; bool ret = false; diff --git a/gtk2_ardour/audio_time_axis.h b/gtk2_ardour/audio_time_axis.h index d1fbde3e9c..b319d0ea99 100644 --- a/gtk2_ardour/audio_time_axis.h +++ b/gtk2_ardour/audio_time_axis.h @@ -48,7 +48,7 @@ namespace ALSA { namespace ARDOUR { class Session; - class DiskStream; + class AudioDiskstream; class RouteGroup; class Redirect; class Insert; diff --git a/gtk2_ardour/automation_gain_line.cc b/gtk2_ardour/automation_gain_line.cc index 272e6cfc52..74e4f64e3c 100644 --- a/gtk2_ardour/automation_gain_line.cc +++ b/gtk2_ardour/automation_gain_line.cc @@ -31,6 +31,7 @@ using namespace std; using namespace ARDOUR; +using namespace PBD; AutomationGainLine::AutomationGainLine (const string & name, Session& s, TimeAxisView& tv, ArdourCanvas::Group& parent, Curve& c) diff --git a/gtk2_ardour/automation_line.cc b/gtk2_ardour/automation_line.cc index 70bc676fca..b87a71ca87 100644 --- a/gtk2_ardour/automation_line.cc +++ b/gtk2_ardour/automation_line.cc @@ -48,6 +48,7 @@ using namespace std; using namespace sigc; using namespace ARDOUR; +using namespace PBD; using namespace Editing; using namespace Gnome; // for Canvas diff --git a/gtk2_ardour/automation_pan_line.cc b/gtk2_ardour/automation_pan_line.cc index 7a264502af..aacfbdde75 100644 --- a/gtk2_ardour/automation_pan_line.cc +++ b/gtk2_ardour/automation_pan_line.cc @@ -31,6 +31,7 @@ #include using namespace ARDOUR; +using namespace PBD; AutomationPanLine::AutomationPanLine (const string & name, Session& s, TimeAxisView& tv, ArdourCanvas::Group& parent, Curve& c) diff --git a/gtk2_ardour/automation_time_axis.cc b/gtk2_ardour/automation_time_axis.cc index 670a718736..165e124add 100644 --- a/gtk2_ardour/automation_time_axis.cc +++ b/gtk2_ardour/automation_time_axis.cc @@ -16,6 +16,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace Gtk; using namespace Editing; diff --git a/gtk2_ardour/axis_view.h b/gtk2_ardour/axis_view.h index 38deece11a..12b7d32188 100644 --- a/gtk2_ardour/axis_view.h +++ b/gtk2_ardour/axis_view.h @@ -28,6 +28,7 @@ #include #include "prompter.h" +#include "selectable.h" namespace ARDOUR { class Session; @@ -37,7 +38,7 @@ namespace ARDOUR { * AxisView defines the abstract base class for time-axis trackviews and routes. * */ -class AxisView : public virtual sigc::trackable +class AxisView : public virtual Selectable { public: /** @@ -51,12 +52,6 @@ class AxisView : public virtual sigc::trackable virtual string name() const = 0; - virtual void set_selected (bool yn) { - if (yn != _selected) { - _selected = yn; - } - } - virtual bool marked_for_display() const { return _marked_for_display; } virtual void set_marked_for_display (bool yn) { @@ -65,7 +60,6 @@ class AxisView : public virtual sigc::trackable } } - virtual bool selected() const { return _selected; } sigc::signal Hiding; sigc::signal GoingAway; diff --git a/gtk2_ardour/canvas-waveview.c b/gtk2_ardour/canvas-waveview.c index 34b64770a6..3e4a14d86a 100644 --- a/gtk2_ardour/canvas-waveview.c +++ b/gtk2_ardour/canvas-waveview.c @@ -389,7 +389,11 @@ gnome_canvas_waveview_ensure_cache (GnomeCanvasWaveView *waveview, gulong start_ /* but make sure it doesn't extend beyond the end of the source material */ rf3 = (gulong) (waveview->sourcefile_length_function (waveview->data_src, waveview->samples_per_unit)) + 1; - rf3 -= new_cache_start; + if (rf3 < new_cache_start) { + rf3 = 0; + } else { + rf3 -= new_cache_start; + } #if DEBUG_CACHE fprintf (stderr, "\n\nAVAILABLE FRAMES = %lu of %lu, start = %lu, sstart = %lu, cstart = %lu\n", @@ -405,8 +409,8 @@ gnome_canvas_waveview_ensure_cache (GnomeCanvasWaveView *waveview, gulong start_ #if DEBUG_CACHE fprintf (stderr, "new cache = %lu - %lu\n", new_cache_start, new_cache_end); - fprintf(stderr,"required_cach_entries = %lu, samples_per_unit = %f\n", - required_cache_entries,waveview->samples_per_unit); + fprintf(stderr,"required_cach_entries = %lu, samples_per_unit = %f req frames = %lu\n", + required_cache_entries,waveview->samples_per_unit, required_frames); #endif if (required_cache_entries > cache->allocated) { @@ -514,8 +518,8 @@ gnome_canvas_waveview_ensure_cache (GnomeCanvasWaveView *waveview, gulong start_ // fprintf(stderr,"length == %lu\n",waveview->length_function (waveview->data_src)); // required_frames = MIN (waveview->length_function (waveview->data_src) - new_cache_start, required_frames); + npeaks = (gulong) floor (required_frames / waveview->samples_per_unit); - npeaks = MAX (1, npeaks); required_frames = npeaks * waveview->samples_per_unit; #if DEBUG_CACHE @@ -532,11 +536,15 @@ gnome_canvas_waveview_ensure_cache (GnomeCanvasWaveView *waveview, gulong start_ // start_sample, end_sample); #endif - waveview->peak_function (waveview->data_src, npeaks, new_cache_start, required_frames, cache->data + offset, waveview->channel,waveview->samples_per_unit); + if (required_frames) { + waveview->peak_function (waveview->data_src, npeaks, new_cache_start, required_frames, cache->data + offset, waveview->channel,waveview->samples_per_unit); - /* take into account any copied peaks */ - - npeaks += copied; + /* take into account any copied peaks */ + + npeaks += copied; + } else { + npeaks = copied; + } if (npeaks < cache->allocated) { #if DEBUG_CACHE diff --git a/gtk2_ardour/color_manager.cc b/gtk2_ardour/color_manager.cc index db88e6622c..2f1a286467 100644 --- a/gtk2_ardour/color_manager.cc +++ b/gtk2_ardour/color_manager.cc @@ -12,6 +12,7 @@ using namespace std; using namespace Gtk; +using namespace PBD; /* the global color map */ diff --git a/gtk2_ardour/connection_editor.cc b/gtk2_ardour/connection_editor.cc index f411f945c8..a7c6e265ed 100644 --- a/gtk2_ardour/connection_editor.cc +++ b/gtk2_ardour/connection_editor.cc @@ -43,6 +43,7 @@ using namespace std; using namespace ARDOUR; +using namespace PBD; using namespace Gtk; using namespace sigc; diff --git a/gtk2_ardour/crossfade_edit.cc b/gtk2_ardour/crossfade_edit.cc index 6363178004..5b587594de 100644 --- a/gtk2_ardour/crossfade_edit.cc +++ b/gtk2_ardour/crossfade_edit.cc @@ -34,6 +34,7 @@ #include #include #include +#include #include #include @@ -51,6 +52,7 @@ using namespace std; using namespace ARDOUR; +using namespace PBD; using namespace Gtk; using namespace sigc; using namespace Editing; diff --git a/gtk2_ardour/crossfade_view.cc b/gtk2_ardour/crossfade_view.cc index aef54f2c5d..350698ec48 100644 --- a/gtk2_ardour/crossfade_view.cc +++ b/gtk2_ardour/crossfade_view.cc @@ -35,6 +35,7 @@ using namespace sigc; using namespace ARDOUR; +using namespace PBD; using namespace Editing; using namespace Gnome; using namespace Canvas; @@ -50,7 +51,7 @@ CrossfadeView::CrossfadeView (ArdourCanvas::Group *parent, AudioRegionView& rview) - : TimeAxisViewItem ("xf.name()", *parent, tv, spu, basic_color, xf.position(), + : TimeAxisViewItem ("xfade" /*xf.name()*/, *parent, tv, spu, basic_color, xf.position(), xf.overlap_length(), TimeAxisViewItem::Visibility (TimeAxisViewItem::ShowFrame)), crossfade (xf), left_view (lview), @@ -91,13 +92,6 @@ CrossfadeView::~CrossfadeView () GoingAway (this) ; /* EMIT_SIGNAL */ } -std::string -CrossfadeView::get_item_name () -{ - return "xfade"; -// return crossfade.name(); -} - void CrossfadeView::reset_width_dependent_items (double pixel_width) { diff --git a/gtk2_ardour/crossfade_view.h b/gtk2_ardour/crossfade_view.h index b4931c94c0..403edfe297 100644 --- a/gtk2_ardour/crossfade_view.h +++ b/gtk2_ardour/crossfade_view.h @@ -46,7 +46,6 @@ struct CrossfadeView : public TimeAxisViewItem AudioRegionView& left_view; // and these too AudioRegionView& right_view; - std::string get_item_name(); void set_height (double); bool valid() const { return _valid; } diff --git a/gtk2_ardour/curvetest.cc b/gtk2_ardour/curvetest.cc index 613835aa4c..3c9836a5e6 100644 --- a/gtk2_ardour/curvetest.cc +++ b/gtk2_ardour/curvetest.cc @@ -7,6 +7,7 @@ using namespace std; using namespace ARDOUR; +using namespace PBD; int curvetest (string filename) diff --git a/gtk2_ardour/editor.cc b/gtk2_ardour/editor.cc index c7956386ce..08c716d442 100644 --- a/gtk2_ardour/editor.cc +++ b/gtk2_ardour/editor.cc @@ -38,7 +38,7 @@ #include #include -#include +#include #include #include #include @@ -48,7 +48,7 @@ #include #include -#include "control_protocol.h" +#include #include "ardour_ui.h" #include "editor.h" @@ -84,6 +84,7 @@ using namespace std; using namespace sigc; using namespace ARDOUR; +using namespace PBD; using namespace Gtk; using namespace Glib; using namespace Gtkmm2ext; @@ -1636,7 +1637,7 @@ Editor::build_track_region_context_menu (jack_nframes_t frame) AudioTimeAxisView* atv = dynamic_cast (clicked_trackview); if (atv) { - DiskStream* ds; + AudioDiskstream* ds; Playlist* pl; if ((ds = atv->get_diskstream()) && ((pl = ds->playlist()))) { @@ -1663,7 +1664,7 @@ Editor::build_track_crossfade_context_menu (jack_nframes_t frame) AudioTimeAxisView* atv = dynamic_cast (clicked_trackview); if (atv) { - DiskStream* ds; + AudioDiskstream* ds; Playlist* pl; AudioPlaylist* apl; @@ -3107,7 +3108,7 @@ Editor::mapped_set_selected_regionview_from_click (AudioTimeAxisView& atv, uint3 AudioPlaylist* pl; vector results; AudioRegionView* marv; - DiskStream* ds; + AudioDiskstream* ds; if ((ds = atv.get_diskstream()) == 0) { /* bus */ @@ -3338,7 +3339,7 @@ Editor::set_selected_regionview_from_region_list (Region& r, Selection::Operatio AudioPlaylist* pl; vector results; AudioRegionView* marv; - DiskStream* ds; + AudioDiskstream* ds; if ((ds = tatv->get_diskstream()) == 0) { /* bus */ diff --git a/gtk2_ardour/editor.h b/gtk2_ardour/editor.h index e73d44971b..e517b1eaf1 100644 --- a/gtk2_ardour/editor.h +++ b/gtk2_ardour/editor.h @@ -45,7 +45,6 @@ #include #include #include -#include #include "audio_clock.h" #include "gtk-custom-ruler.h" @@ -67,9 +66,8 @@ namespace LinuxAudioSystems { } namespace ARDOUR { - class DiskStream; + class AudioDiskstream; class RouteGroup; - class Source; class Playlist; class Region; class Location; diff --git a/gtk2_ardour/editor_actions.cc b/gtk2_ardour/editor_actions.cc index d88cda61e6..e20e6ee8eb 100644 --- a/gtk2_ardour/editor_actions.cc +++ b/gtk2_ardour/editor_actions.cc @@ -12,6 +12,7 @@ using namespace Glib; using namespace std; using namespace sigc; using namespace ARDOUR; +using namespace PBD; using namespace Editing; void diff --git a/gtk2_ardour/editor_audio_import.cc b/gtk2_ardour/editor_audio_import.cc index ee73c46b24..f3e2ee1cb2 100644 --- a/gtk2_ardour/editor_audio_import.cc +++ b/gtk2_ardour/editor_audio_import.cc @@ -26,12 +26,11 @@ #include #include #include -#include -#include -#include +#include #include #include #include +#include #include "ardour_ui.h" #include "editor.h" @@ -43,6 +42,7 @@ using namespace std; using namespace ARDOUR; +using namespace PBD; using namespace sigc; using namespace Gtk; using namespace Editing; @@ -187,7 +187,7 @@ int Editor::embed_sndfile (Glib::ustring path, bool split, bool multiple_files, bool& check_sample_rate, ImportMode mode, AudioTrack* track, jack_nframes_t& pos, bool prompt) { - ExternalSource *source = 0; /* keep g++ quiet */ + AudioFileSource *source = 0; /* keep g++ quiet */ AudioRegion::SourceList sources; AudioRegion* region; string idspec; @@ -220,7 +220,7 @@ Editor::embed_sndfile (Glib::ustring path, bool split, bool multiple_files, bool string error_msg; - if (!ExternalSource::get_soundfile_info (path, finfo, error_msg)) { + if (!AudioFileSource::get_soundfile_info (path, finfo, error_msg)) { error << string_compose(_("Editor: cannot open file \"%1\", (%2)"), selection, error_msg ) << endmsg; return 0; } @@ -267,7 +267,7 @@ Editor::embed_sndfile (Glib::ustring path, bool split, bool multiple_files, bool idspec += string_compose(":%1", n); try { - source = ExternalSource::create (idspec.c_str()); + source = AudioFileSource::create (idspec.c_str()); sources.push_back(source); } diff --git a/gtk2_ardour/editor_audiotrack.cc b/gtk2_ardour/editor_audiotrack.cc index b9ae734bde..acad3371a0 100644 --- a/gtk2_ardour/editor_audiotrack.cc +++ b/gtk2_ardour/editor_audiotrack.cc @@ -1,5 +1,5 @@ #include -#include +#include #include "editor.h" #include "editing.h" @@ -8,6 +8,7 @@ #include "selection.h" using namespace ARDOUR; +using namespace PBD; void Editor::set_route_loop_selection () diff --git a/gtk2_ardour/editor_canvas.cc b/gtk2_ardour/editor_canvas.cc index 69aa6428a6..41350a1da4 100644 --- a/gtk2_ardour/editor_canvas.cc +++ b/gtk2_ardour/editor_canvas.cc @@ -46,6 +46,7 @@ using namespace std; using namespace sigc; using namespace ARDOUR; +using namespace PBD; using namespace Gtk; using namespace Glib; using namespace Gtkmm2ext; diff --git a/gtk2_ardour/editor_canvas_events.cc b/gtk2_ardour/editor_canvas_events.cc index 29997f5f57..43114534c5 100644 --- a/gtk2_ardour/editor_canvas_events.cc +++ b/gtk2_ardour/editor_canvas_events.cc @@ -21,7 +21,7 @@ #include #include -#include +#include #include #include "editor.h" @@ -42,6 +42,7 @@ using namespace sigc; using namespace ARDOUR; +using namespace PBD; using namespace Gtk; bool diff --git a/gtk2_ardour/editor_cursors.cc b/gtk2_ardour/editor_cursors.cc index 5dd1eb075b..2353481daf 100644 --- a/gtk2_ardour/editor_cursors.cc +++ b/gtk2_ardour/editor_cursors.cc @@ -28,6 +28,7 @@ using namespace sigc; using namespace ARDOUR; +using namespace PBD; using namespace Gtk; Editor::Cursor::Cursor (Editor& ed, const string& color, bool (Editor::*callbck)(GdkEvent*,ArdourCanvas::Item*)) diff --git a/gtk2_ardour/editor_edit_groups.cc b/gtk2_ardour/editor_edit_groups.cc index 0047999f71..8df76fef25 100644 --- a/gtk2_ardour/editor_edit_groups.cc +++ b/gtk2_ardour/editor_edit_groups.cc @@ -38,6 +38,7 @@ using namespace sigc; using namespace ARDOUR; +using namespace PBD; using namespace Gtk; void diff --git a/gtk2_ardour/editor_export_audio.cc b/gtk2_ardour/editor_export_audio.cc index 8ad432ece6..7339536e42 100644 --- a/gtk2_ardour/editor_export_audio.cc +++ b/gtk2_ardour/editor_export_audio.cc @@ -37,8 +37,8 @@ #include #include #include -#include -#include +#include +#include #include #include @@ -46,6 +46,7 @@ using namespace std; using namespace ARDOUR; +using namespace PBD; using namespace Gtk; void @@ -154,7 +155,7 @@ Editor::bounce_region_selection () bool Editor::write_region (string path, AudioRegion& region) { - FileSource* fs; + AudioFileSource* fs; const jack_nframes_t chunk_size = 4096; jack_nframes_t to_read; Sample buf[chunk_size]; @@ -163,7 +164,7 @@ Editor::write_region (string path, AudioRegion& region) jack_nframes_t pos; char s[PATH_MAX+1]; uint32_t cnt; - vector sources; + vector sources; uint32_t nchans; nchans = region.n_channels(); @@ -204,7 +205,7 @@ Editor::write_region (string path, AudioRegion& region) try { - fs = new FileSource (path, session->frame_rate()); + fs = AudioFileSource::create (path); } catch (failed_constructor& err) { @@ -227,10 +228,10 @@ Editor::write_region (string path, AudioRegion& region) this_time = min (to_read, chunk_size); - for (vector::iterator src=sources.begin(); src != sources.end(); ++src) { - - fs = (*src); + for (vector::iterator src=sources.begin(); src != sources.end(); ++src) { + fs = (*src); + if (region.read_at (buf, buf, gain_buffer, workbuf, pos, this_time) != this_time) { break; } @@ -250,7 +251,7 @@ Editor::write_region (string path, AudioRegion& region) time (&tnow); now = localtime (&tnow); - for (vector::iterator src = sources.begin(); src != sources.end(); ++src) { + for (vector::iterator src = sources.begin(); src != sources.end(); ++src) { (*src)->update_header (0, *now, tnow); } @@ -258,7 +259,8 @@ Editor::write_region (string path, AudioRegion& region) error_out: - for (vector::iterator i = sources.begin(); i != sources.end(); ++i) { + for (vector::iterator i = sources.begin(); i != sources.end(); ++i) { + (*i)->mark_for_remove (); delete (*i); } @@ -300,7 +302,7 @@ Editor::write_audio_selection (TimeSelection& ts) bool Editor::write_audio_range (Playlist& playlist, uint32_t channels, list& range) { - FileSource* fs; + AudioFileSource* fs; const jack_nframes_t chunk_size = 4096; jack_nframes_t nframes; Sample buf[chunk_size]; @@ -310,7 +312,7 @@ Editor::write_audio_range (Playlist& playlist, uint32_t channels, list sources; + vector sources; for (uint32_t n=0; n < channels; ++n) { @@ -337,7 +339,7 @@ Editor::write_audio_range (Playlist& playlist, uint32_t channels, listframe_rate()); + fs = AudioFileSource::create (path); } catch (failed_constructor& err) { @@ -420,7 +422,7 @@ Editor::write_audio_range (Playlist& playlist, uint32_t channels, list::iterator i = sources.begin(); i != sources.end(); ++i) { + for (vector::iterator i = sources.begin(); i != sources.end(); ++i) { (*i)->mark_for_remove (); delete *i; } diff --git a/gtk2_ardour/editor_hscroller.cc b/gtk2_ardour/editor_hscroller.cc index 5b2da7dc83..8504667daa 100644 --- a/gtk2_ardour/editor_hscroller.cc +++ b/gtk2_ardour/editor_hscroller.cc @@ -24,6 +24,7 @@ using namespace std; using namespace ARDOUR; +using namespace PBD; void Editor::hscrollbar_allocate (Gtk::Allocation &alloc) diff --git a/gtk2_ardour/editor_imageframe.cc b/gtk2_ardour/editor_imageframe.cc index a8dce7d64b..6b8691b09f 100644 --- a/gtk2_ardour/editor_imageframe.cc +++ b/gtk2_ardour/editor_imageframe.cc @@ -44,6 +44,7 @@ #include "public_editor.h" using namespace Gtk; +using namespace PBD; /* */ diff --git a/gtk2_ardour/editor_keys.cc b/gtk2_ardour/editor_keys.cc index 00469281fc..baa158cbf8 100644 --- a/gtk2_ardour/editor_keys.cc +++ b/gtk2_ardour/editor_keys.cc @@ -36,6 +36,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace sigc; void diff --git a/gtk2_ardour/editor_markers.cc b/gtk2_ardour/editor_markers.cc index df64b9ed43..a584561e42 100644 --- a/gtk2_ardour/editor_markers.cc +++ b/gtk2_ardour/editor_markers.cc @@ -41,6 +41,7 @@ using namespace std; using namespace sigc; using namespace ARDOUR; +using namespace PBD; using namespace Gtk; void diff --git a/gtk2_ardour/editor_mouse.cc b/gtk2_ardour/editor_mouse.cc index 249b1d781a..6c2919f5dd 100644 --- a/gtk2_ardour/editor_mouse.cc +++ b/gtk2_ardour/editor_mouse.cc @@ -47,7 +47,7 @@ #include #include #include -#include +#include #include #include #include @@ -61,6 +61,7 @@ using namespace std; using namespace ARDOUR; +using namespace PBD; using namespace sigc; using namespace Gtk; using namespace Editing; @@ -195,7 +196,7 @@ Editor::set_mouse_mode (MouseMode m, bool force) */ for (TrackSelection::iterator i = selection->tracks.begin(); i != selection->tracks.end(); ++i) { - if ((*i)->selected()) { + if ((*i)->get_selected()) { (*i)->show_selection (selection->time); } } @@ -286,7 +287,7 @@ Editor::step_mouse_mode (bool next) void Editor::button_selection (ArdourCanvas::Item* item, GdkEvent* event, ItemType item_type) { - bool commit; + bool commit = false; bool c1; bool c2; @@ -3458,7 +3459,7 @@ void Editor::show_verbose_time_cursor (jack_nframes_t frame, double offset, double xpos, double ypos) { char buf[128]; - SMPTE_Time smpte; + SMPTE::Time smpte; BBT_Time bbt; float secs; @@ -3502,7 +3503,7 @@ void Editor::show_verbose_duration_cursor (jack_nframes_t start, jack_nframes_t end, double offset, double xpos, double ypos) { char buf[128]; - SMPTE_Time smpte; + SMPTE::Time smpte; BBT_Time sbbt; BBT_Time ebbt; float secs; diff --git a/gtk2_ardour/editor_nudge.cc b/gtk2_ardour/editor_nudge.cc index 4bcafac93d..c6f5eeeb48 100644 --- a/gtk2_ardour/editor_nudge.cc +++ b/gtk2_ardour/editor_nudge.cc @@ -27,4 +27,5 @@ using namespace sigc; using namespace ARDOUR; +using namespace PBD; using namespace Gtk; diff --git a/gtk2_ardour/editor_ops.cc b/gtk2_ardour/editor_ops.cc index acf205d06f..d3845dd26b 100644 --- a/gtk2_ardour/editor_ops.cc +++ b/gtk2_ardour/editor_ops.cc @@ -36,9 +36,7 @@ #include #include #include -#include -#include -#include +#include #include #include #include @@ -66,6 +64,7 @@ using namespace std; using namespace ARDOUR; +using namespace PBD; using namespace sigc; using namespace Gtk; using namespace Editing; @@ -122,9 +121,9 @@ Editor::set_meter_hold (int32_t cnt) void Editor::set_meter_falloff (int intval) { - float val; + float val = 0.0f; /* off */ std::string str; - cerr << "set_meter_falloff () called: intval = " << intval << endl; + Config->set_meter_falloff_off(false); Config->set_meter_falloff_slowest(false); Config->set_meter_falloff_slow(false); diff --git a/gtk2_ardour/editor_region_list.cc b/gtk2_ardour/editor_region_list.cc index bbcfb09a29..5cf099433b 100644 --- a/gtk2_ardour/editor_region_list.cc +++ b/gtk2_ardour/editor_region_list.cc @@ -26,6 +26,7 @@ #include #include +#include #include #include @@ -41,6 +42,7 @@ using namespace sigc; using namespace ARDOUR; +using namespace PBD; using namespace Gtk; using namespace Glib; using namespace Editing; diff --git a/gtk2_ardour/editor_route_list.cc b/gtk2_ardour/editor_route_list.cc index 79b67a544a..2e036f5001 100644 --- a/gtk2_ardour/editor_route_list.cc +++ b/gtk2_ardour/editor_route_list.cc @@ -35,6 +35,7 @@ using namespace sigc; using namespace ARDOUR; +using namespace PBD; using namespace Gtk; void diff --git a/gtk2_ardour/editor_rulers.cc b/gtk2_ardour/editor_rulers.cc index fa08050885..47641655e7 100644 --- a/gtk2_ardour/editor_rulers.cc +++ b/gtk2_ardour/editor_rulers.cc @@ -35,6 +35,7 @@ using namespace sigc; using namespace ARDOUR; +using namespace PBD; using namespace Gtk; using namespace Editing; @@ -798,7 +799,7 @@ Editor::metric_get_smpte (GtkCustomRulerMark **marks, gdouble lower, gdouble upp jack_nframes_t pos; jack_nframes_t spacer; jack_nframes_t fr; - SMPTE_Time smpte; + SMPTE::Time smpte; gchar buf[16]; gint nmarks = 0; gint n; @@ -927,13 +928,13 @@ Editor::metric_get_smpte (GtkCustomRulerMark **marks, gdouble lower, gdouble upp (*marks)[n].position = pos; // Increment subframes by one - session->smpte_increment_subframes( smpte ); + SMPTE::increment_subframes( smpte ); } } else if (show_seconds) { // Find smpte time of this sample (pos) session->sample_to_smpte(pos, smpte, true /* use_offset */, false /* use_subframes */ ); // Go to next whole second down - session->smpte_seconds_floor( smpte ); + SMPTE::seconds_floor( smpte ); for (n = 0; n < nmarks; n++) { session->smpte_to_sample(smpte, pos, true /* use_offset */, false /* use_subframes */ ); @@ -953,13 +954,13 @@ Editor::metric_get_smpte (GtkCustomRulerMark **marks, gdouble lower, gdouble upp } (*marks)[n].label = g_strdup (buf); - session->smpte_increment_seconds( smpte ); + SMPTE::increment_seconds( smpte ); } } else if (show_minutes) { // Find smpte time of this sample (pos) session->sample_to_smpte(pos, smpte, true /* use_offset */, false /* use_subframes */ ); // Go to next whole minute down - session->smpte_minutes_floor( smpte ); + SMPTE::minutes_floor( smpte ); for (n = 0; n < nmarks; n++) { session->smpte_to_sample(smpte, pos, true /* use_offset */, false /* use_subframes */ ); @@ -977,13 +978,13 @@ Editor::metric_get_smpte (GtkCustomRulerMark **marks, gdouble lower, gdouble upp } (*marks)[n].label = g_strdup (buf); (*marks)[n].position = pos; - session->smpte_increment_minutes( smpte ); + SMPTE::increment_minutes( smpte ); } } else if (show_hours) { // Find smpte time of this sample (pos) session->sample_to_smpte(pos, smpte, true /* use_offset */, false /* use_subframes */ ); // Go to next whole hour down - session->smpte_hours_floor( smpte ); + SMPTE::hours_floor( smpte ); for (n = 0; n < nmarks; n++) { session->smpte_to_sample(smpte, pos, true /* use_offset */, false /* use_subframes */ ); @@ -998,13 +999,13 @@ Editor::metric_get_smpte (GtkCustomRulerMark **marks, gdouble lower, gdouble upp (*marks)[n].label = g_strdup (buf); (*marks)[n].position = pos; - session->smpte_increment_hours( smpte ); + SMPTE::increment_hours( smpte ); } } else { // show_frames // Find smpte time of this sample (pos) session->sample_to_smpte(pos, smpte, true /* use_offset */, false /* use_subframes */ ); // Go to next whole frame down - session->smpte_frames_floor( smpte ); + SMPTE::frames_floor( smpte ); for (n = 0; n < nmarks; n++) { session->smpte_to_sample(smpte, pos, true /* use_offset */, false /* use_subframes */ ); @@ -1019,7 +1020,7 @@ Editor::metric_get_smpte (GtkCustomRulerMark **marks, gdouble lower, gdouble upp } (*marks)[n].label = g_strdup (buf); - session->smpte_increment( smpte ); + SMPTE::increment( smpte ); } } diff --git a/gtk2_ardour/editor_selection_list.cc b/gtk2_ardour/editor_selection_list.cc index 3b5d00d9ed..959da1ad2d 100644 --- a/gtk2_ardour/editor_selection_list.cc +++ b/gtk2_ardour/editor_selection_list.cc @@ -40,6 +40,7 @@ using namespace sigc; using namespace ARDOUR; +using namespace PBD; using namespace Gtk; using namespace Gtkmm2ext; diff --git a/gtk2_ardour/editor_tempodisplay.cc b/gtk2_ardour/editor_tempodisplay.cc index f4351fe518..5f998ada9f 100644 --- a/gtk2_ardour/editor_tempodisplay.cc +++ b/gtk2_ardour/editor_tempodisplay.cc @@ -49,6 +49,7 @@ using namespace std; using namespace sigc; using namespace ARDOUR; +using namespace PBD; using namespace Gtk; using namespace Gtkmm2ext; using namespace Editing; diff --git a/gtk2_ardour/editor_timefx.cc b/gtk2_ardour/editor_timefx.cc index 9760c5116b..6ff467454d 100644 --- a/gtk2_ardour/editor_timefx.cc +++ b/gtk2_ardour/editor_timefx.cc @@ -36,11 +36,12 @@ #include #include #include -#include +#include #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace sigc; using namespace Gtk; diff --git a/gtk2_ardour/export_dialog.cc b/gtk2_ardour/export_dialog.cc index 834127e042..bcf8cd85ad 100644 --- a/gtk2_ardour/export_dialog.cc +++ b/gtk2_ardour/export_dialog.cc @@ -49,6 +49,7 @@ using namespace std; using namespace ARDOUR; +using namespace PBD; using namespace sigc; using namespace Gtk; diff --git a/gtk2_ardour/export_range_markers_dialog.cc b/gtk2_ardour/export_range_markers_dialog.cc index 3ff6ae783d..e43eb20cd1 100644 --- a/gtk2_ardour/export_range_markers_dialog.cc +++ b/gtk2_ardour/export_range_markers_dialog.cc @@ -32,6 +32,7 @@ using namespace Gtk; using namespace ARDOUR; +using namespace PBD; using namespace std; ExportRangeMarkersDialog::ExportRangeMarkersDialog (PublicEditor& editor) diff --git a/gtk2_ardour/gain_automation_time_axis.cc b/gtk2_ardour/gain_automation_time_axis.cc index cb96774cdb..8f41f5def0 100644 --- a/gtk2_ardour/gain_automation_time_axis.cc +++ b/gtk2_ardour/gain_automation_time_axis.cc @@ -28,6 +28,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace Gtk; GainAutomationTimeAxisView::GainAutomationTimeAxisView (Session& s, Route& r, PublicEditor& e, TimeAxisView& parent, ArdourCanvas::Canvas& canvas, const string & n, ARDOUR::Curve& c) diff --git a/gtk2_ardour/gain_meter.cc b/gtk2_ardour/gain_meter.cc index 9d0228dba6..b7746c4b19 100644 --- a/gtk2_ardour/gain_meter.cc +++ b/gtk2_ardour/gain_meter.cc @@ -47,6 +47,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace Gtkmm2ext; using namespace Gtk; using namespace sigc; @@ -326,23 +327,27 @@ GainMeter::update_meters () char buf[32]; for (n = 0, i = meters.begin(); i != meters.end(); ++i, ++n) { - if ((*i).packed) { - peak = _io.peak_input_power (n); + if ((*i).packed) { + peak = _io.peak_input_power (n); (*i).meter->set (log_meter (peak), peak); - - if (peak > max_peak) { - max_peak = peak; - /* set peak display */ - snprintf (buf, sizeof(buf), "%.1f", max_peak); - peak_display_label.set_text (buf); + + if (peak > max_peak) { + max_peak = peak; + /* set peak display */ + if (max_peak <= -200.0f) { + peak_display_label.set_text (_("-inf")); + } else { + snprintf (buf, sizeof(buf), "%.1f", max_peak); + peak_display_label.set_text (buf); + } - if (max_peak >= 0.0f) { - peak_display.set_name ("MixerStripPeakDisplayPeak"); - } - } - } - } + if (max_peak >= 0.0f) { + peak_display.set_name ("MixerStripPeakDisplayPeak"); + } + } + } + } } void diff --git a/gtk2_ardour/glade_factory.cc b/gtk2_ardour/glade_factory.cc deleted file mode 100644 index 6dbced388a..0000000000 --- a/gtk2_ardour/glade_factory.cc +++ /dev/null @@ -1,37 +0,0 @@ -/* - Copyright (C) 2005 Paul Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ - -#include - -#include "glade_factory.h" - -Glib::RefPtr -GladeFactory::create(const std::string& full_path_to_file, - const Glib::ustring& toplevel_widget) -{ - try { - return Gnome::Glade::Xml::create(full_path_to_file, - toplevel_widget, - PACKAGE ); - } catch(const Gnome::Glade::XmlError& ex) { - std::cerr << ex.what() << std::endl; - throw ex; - } -} diff --git a/gtk2_ardour/glade_factory.h b/gtk2_ardour/glade_factory.h deleted file mode 100644 index 2fff3bd167..0000000000 --- a/gtk2_ardour/glade_factory.h +++ /dev/null @@ -1,45 +0,0 @@ -/* - Copyright (C) 2005 Paul Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ - -// -*- c++ -*- - -#ifndef GLADE_FACTORY_H -#define GLADE_FACTORY_H - -#include -#include - -typedef Glib::RefPtr GladeRef; - -/** - This is the base class for all glade - factories so that the same domain is - used. -*/ -class GladeFactory { - -protected: - static GladeRef - create(const std::string& full_path, - const Glib::ustring& toplevel_widget = Glib::ustring()); -}; - - -#endif // GLADE_FACTORY_H diff --git a/gtk2_ardour/glade_path.cc b/gtk2_ardour/glade_path.cc deleted file mode 100644 index 29bca7151f..0000000000 --- a/gtk2_ardour/glade_path.cc +++ /dev/null @@ -1,38 +0,0 @@ -/* - Copyright (C) 2005 Paul Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ - -#include -#include - -#include - -#include "i18n.h" -#include "glade_path.h" - -#include - -std::string -GladePath::path(const std::string& glade_file) -{ - std::string full_path; - - full_path = ARDOUR::find_data_file(glade_file, "glade"); - return full_path; -} diff --git a/gtk2_ardour/glade_path.h b/gtk2_ardour/glade_path.h deleted file mode 100644 index a651b5fd1c..0000000000 --- a/gtk2_ardour/glade_path.h +++ /dev/null @@ -1,49 +0,0 @@ -/* - Copyright (C) 2005 Paul Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ - -#ifndef GLADE_PATH_H -#define GLADE_PATH_H - -#include - -struct GladePath { - - /** - @return Path to glade file. - - XXX subject to change upon discussion. - - glade files are currently looked for in - three possible directories in this order. - - In the directory defined in the environment - variable ARDOUR_GLADE_PATH - - In the users .ardour/glade directory. - - In the system defined glade path. - */ - static std::string - path(const std::string& glade_filename); - -}; - -#endif // GLADE_PATH_H - diff --git a/gtk2_ardour/imageframe_socket_handler.cc b/gtk2_ardour/imageframe_socket_handler.cc index 4f08954a8d..905a96de7d 100644 --- a/gtk2_ardour/imageframe_socket_handler.cc +++ b/gtk2_ardour/imageframe_socket_handler.cc @@ -52,6 +52,7 @@ using namespace std; using namespace ardourvis ; using namespace sigc; using namespace ARDOUR; +using namespace PBD; ImageFrameSocketHandler* ImageFrameSocketHandler::_instance = 0 ; @@ -1091,7 +1092,7 @@ ImageFrameSocketHandler::handle_item_selected(const char* msg) } else { - ifv->set_selected(true, this) ; + ifv->set_selected(true) ; ifta->get_view()->set_selected_imageframe_view(iftag, ifv) ; thePublicEditor.scroll_timeaxis_to_imageframe_item(ifv) ; diff --git a/gtk2_ardour/imageframe_time_axis.cc b/gtk2_ardour/imageframe_time_axis.cc index 4ed36f55e7..ae288ec9ab 100644 --- a/gtk2_ardour/imageframe_time_axis.cc +++ b/gtk2_ardour/imageframe_time_axis.cc @@ -47,6 +47,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace sigc; using namespace Gtk; diff --git a/gtk2_ardour/imageframe_time_axis_view.cc b/gtk2_ardour/imageframe_time_axis_view.cc index e00c399e7f..a725082863 100644 --- a/gtk2_ardour/imageframe_time_axis_view.cc +++ b/gtk2_ardour/imageframe_time_axis_view.cc @@ -365,11 +365,11 @@ ImageFrameTimeAxisView::set_selected_imageframe_view(ImageFrameTimeAxisGroup* if if(selected_imageframe_view) { - selected_imageframe_view->set_selected(false, this) ; + selected_imageframe_view->set_selected(false) ; } selected_imageframe_view = ifv ; - selected_imageframe_view->set_selected(true, this) ; + selected_imageframe_view->set_selected(true) ; } /** @@ -386,7 +386,7 @@ ImageFrameTimeAxisView::clear_selected_imageframe_item(bool clear_group) if(selected_imageframe_view) { - selected_imageframe_view->set_selected(false, this) ; + selected_imageframe_view->set_selected(false) ; } selected_imageframe_view = 0 ; } diff --git a/gtk2_ardour/imageframe_view.cc b/gtk2_ardour/imageframe_view.cc index e8ff878486..ac17a7cc1a 100644 --- a/gtk2_ardour/imageframe_view.cc +++ b/gtk2_ardour/imageframe_view.cc @@ -172,16 +172,15 @@ delete imageframe; * @return true if the position change was a success, false otherwise */ bool -ImageFrameView::set_position(jack_nframes_t pos, void* src) +ImageFrameView::set_position(jack_nframes_t pos, void* src, double* delta) { jack_nframes_t old_pos = frame_position ; // do the standard stuff - bool ret = TimeAxisViewItem::set_position(pos, src) ; + bool ret = TimeAxisViewItem::set_position(pos, src, delta) ; // everything went ok with the standard stuff? - if(ret) - { + if (ret) { /* move each of our associated markers with this ImageFrameView */ for (MarkerViewList::iterator i = marker_view_list.begin(); i != marker_view_list.end(); ++i) { diff --git a/gtk2_ardour/imageframe_view.h b/gtk2_ardour/imageframe_view.h index c599082580..5ae8aaded6 100644 --- a/gtk2_ardour/imageframe_view.h +++ b/gtk2_ardour/imageframe_view.h @@ -91,7 +91,7 @@ class ImageFrameView : public TimeAxisViewItem * @param src the identity of the object that initiated the change * @return true if the position change was a success, false otherwise */ - virtual bool set_position(jack_nframes_t pos, void* src) ; + virtual bool set_position(jack_nframes_t pos, void* src, double* delta = 0) ; /** * Sets the duration of this item diff --git a/gtk2_ardour/io_selector.cc b/gtk2_ardour/io_selector.cc index b45966c5e3..b0ecd05077 100644 --- a/gtk2_ardour/io_selector.cc +++ b/gtk2_ardour/io_selector.cc @@ -31,7 +31,7 @@ #include #include #include -#include +#include #include #include @@ -49,6 +49,7 @@ using namespace Gtk; using namespace Glib; using namespace sigc; using namespace ARDOUR; +using namespace PBD; using namespace Gtkmm2ext; IOSelectorWindow::IOSelectorWindow (Session& sess, IO& ior, bool input, bool can_cancel) diff --git a/gtk2_ardour/keyboard.cc b/gtk2_ardour/keyboard.cc index 92dce01bb6..17390b8b4d 100644 --- a/gtk2_ardour/keyboard.cc +++ b/gtk2_ardour/keyboard.cc @@ -35,6 +35,8 @@ #include "i18n.h" +using namespace PBD; + #define KBD_DEBUG 1 bool debug_keyboard = false; diff --git a/gtk2_ardour/location_ui.cc b/gtk2_ardour/location_ui.cc index 21d0fb5b15..f0fe230b57 100644 --- a/gtk2_ardour/location_ui.cc +++ b/gtk2_ardour/location_ui.cc @@ -38,6 +38,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace Gtk; using namespace Gtkmm2ext; diff --git a/gtk2_ardour/main.cc b/gtk2_ardour/main.cc index e9ac25a8f8..778355c858 100644 --- a/gtk2_ardour/main.cc +++ b/gtk2_ardour/main.cc @@ -53,6 +53,7 @@ using namespace Gtk; using namespace GTK_ARDOUR; using namespace ARDOUR; +using namespace PBD; using namespace sigc; TextReceiver text_receiver ("ardour"); @@ -102,12 +103,6 @@ handler (int sig) shutdown (1); } -static void -handler2 (int sig, siginfo_t* ctxt, void* ignored) -{ - handler (sig); -} - static void * signal_thread (void *arg) { @@ -361,8 +356,17 @@ To create it from the command line, start ardour as \"ardour --new %1"), path) return true; } -int -main (int argc, char *argv[]) +#ifdef VST_SUPPORT +/* this is called from the entry point of a wine-compiled + executable that is linked against gtk2_ardour built + as a shared library. +*/ +extern "C" { +int ardour_main (int argc, char *argv[]) +#else +int main (int argc, char *argv[]) +#endif + { ARDOUR::AudioEngine *engine; vector null_file_list; @@ -442,7 +446,7 @@ main (int argc, char *argv[]) try { engine = new ARDOUR::AudioEngine (jack_client_name); - ARDOUR::init (*engine, use_vst, try_hw_optimization, handler2); + ARDOUR::init (*engine, use_vst, try_hw_optimization); ui->set_engine (*engine); } catch (AudioEngine::NoBackendAvailable& err) { gui_jack_error (); @@ -458,11 +462,13 @@ main (int argc, char *argv[]) ui = 0; } - out: delete engine; ARDOUR::cleanup (); shutdown (0); - /* just another commit forcing change */ + return 0; } +#ifdef VST_SUPPORT +} // end of extern C block +#endif diff --git a/gtk2_ardour/marker_time_axis.cc b/gtk2_ardour/marker_time_axis.cc index acb88257e0..1c6e7af2c7 100644 --- a/gtk2_ardour/marker_time_axis.cc +++ b/gtk2_ardour/marker_time_axis.cc @@ -42,6 +42,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace sigc; using namespace Gtk; diff --git a/gtk2_ardour/meter_bridge.cc b/gtk2_ardour/meter_bridge.cc index 6b83a34322..65434d5e82 100644 --- a/gtk2_ardour/meter_bridge.cc +++ b/gtk2_ardour/meter_bridge.cc @@ -20,7 +20,7 @@ #include #include -#include +#include #include #include "ardour_ui.h" @@ -32,6 +32,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace Gtk; using namespace sigc; diff --git a/gtk2_ardour/meter_bridge_strip.cc b/gtk2_ardour/meter_bridge_strip.cc index 50562a68d0..ea3b609720 100644 --- a/gtk2_ardour/meter_bridge_strip.cc +++ b/gtk2_ardour/meter_bridge_strip.cc @@ -40,6 +40,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace Gtk; using namespace Gtkmm2ext; diff --git a/gtk2_ardour/mixer_strip.cc b/gtk2_ardour/mixer_strip.cc index 9bdc8c340a..47d884be5e 100644 --- a/gtk2_ardour/mixer_strip.cc +++ b/gtk2_ardour/mixer_strip.cc @@ -37,7 +37,7 @@ #include #include #include -#include +#include #include #include #include @@ -63,6 +63,7 @@ using namespace sigc; using namespace ARDOUR; +using namespace PBD; using namespace Gtk; using namespace Gtkmm2ext; @@ -125,7 +126,6 @@ MixerStrip::MixerStrip (Mixer_UI& mx, Session& sess, Route& rt, bool in_mixer) output_button.set_name ("MixerIOButton"); output_label.set_name ("MixerIOButtonLabel"); - _route.meter_change.connect (mem_fun(*this, &MixerStrip::meter_changed)); meter_point_button.add (meter_point_label); meter_point_button.set_name ("MixerStripMeterPreButton"); @@ -665,9 +665,9 @@ MixerStrip::select_stream_input () MenuList& items = stream_menu->items(); stream_menu->set_name ("ArdourContextMenu"); - Session::DiskStreamList streams = _session.disk_streams(); + Session::AudioDiskstreamList streams = _session.audio_disk_streams(); - for (Session::DiskStreamList::iterator i = streams.begin(); i != streams.end(); ++i) { + for (Session::AudioDiskstreamList::iterator i = streams.begin(); i != streams.end(); ++i) { if (!(*i)->hidden()) { @@ -685,7 +685,7 @@ MixerStrip::select_stream_input () } void -MixerStrip::stream_input_chosen (DiskStream *stream) +MixerStrip::stream_input_chosen (AudioDiskstream *stream) { if (is_audio_track()) { audio_track()->set_diskstream (*stream, this); diff --git a/gtk2_ardour/mixer_strip.h b/gtk2_ardour/mixer_strip.h index 65be3c00c1..0cc8fed8e3 100644 --- a/gtk2_ardour/mixer_strip.h +++ b/gtk2_ardour/mixer_strip.h @@ -170,7 +170,7 @@ class MixerStrip : public RouteUI, public Gtk::EventBox Gtk::Menu output_menu; void add_connection_to_output_menu (ARDOUR::Connection *); - void stream_input_chosen (ARDOUR::DiskStream*); + void stream_input_chosen (ARDOUR::AudioDiskstream*); void select_stream_input (); void connection_input_chosen (ARDOUR::Connection *); void connection_output_chosen (ARDOUR::Connection *); diff --git a/gtk2_ardour/mixer_ui.cc b/gtk2_ardour/mixer_ui.cc index 1ded8625c6..983903d6dd 100644 --- a/gtk2_ardour/mixer_ui.cc +++ b/gtk2_ardour/mixer_ui.cc @@ -34,7 +34,7 @@ #include #include #include -#include +#include #include #include "mixer_ui.h" @@ -49,6 +49,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace Gtk; using namespace Glib; using namespace Gtkmm2ext; diff --git a/gtk2_ardour/mixer_ui.h b/gtk2_ardour/mixer_ui.h index 35320b3a48..5108df6014 100644 --- a/gtk2_ardour/mixer_ui.h +++ b/gtk2_ardour/mixer_ui.h @@ -45,7 +45,7 @@ namespace ARDOUR { class Route; class RouteGroup; class Session; - class DiskStream; + class AudioDiskstream; class AudioEngine; }; diff --git a/gtk2_ardour/new_session_dialog.cc b/gtk2_ardour/new_session_dialog.cc index 88944aacb7..d1059cebe0 100644 --- a/gtk2_ardour/new_session_dialog.cc +++ b/gtk2_ardour/new_session_dialog.cc @@ -302,6 +302,11 @@ NewSessionDialog::NewSessionDialog() if (!path.empty()) { m_template->set_current_folder (path + X_("templates/")); } + + const std::string sys_templates_dir = ARDOUR::get_system_data_path() + X_("templates"); + if (Glib::file_test(sys_templates_dir, Glib::FILE_TEST_IS_DIR)) + m_template->add_shortcut_folder(sys_templates_dir); + m_template->set_title(_("select template")); Gtk::FileFilter* session_filter = manage (new (Gtk::FileFilter)); session_filter->add_pattern(X_("*.ardour")); diff --git a/gtk2_ardour/option_editor.cc b/gtk2_ardour/option_editor.cc index 5ac4bf5a8d..d4c2715742 100644 --- a/gtk2_ardour/option_editor.cc +++ b/gtk2_ardour/option_editor.cc @@ -43,6 +43,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace Gtk; using namespace Editing; using namespace Gtkmm2ext; diff --git a/gtk2_ardour/opts.cc b/gtk2_ardour/opts.cc index 2ea5805098..69b8128824 100644 --- a/gtk2_ardour/opts.cc +++ b/gtk2_ardour/opts.cc @@ -83,7 +83,7 @@ GTK_ARDOUR::parse_opts (int argc, char *argv[]) { "name", 1, 0, 'c' }, { "novst", 0, 0, 'V' }, { "new", 1, 0, 'N' }, - { "use-hw-optimizations", 0, 0, 'o' }, + { "no-hw-optimizations", 0, 0, 'O' }, { "curvetest", 1, 0, 'C' }, { "gtktheme", 0, 0, 'g' }, { 0, 0, 0, 0 } @@ -124,8 +124,8 @@ GTK_ARDOUR::parse_opts (int argc, char *argv[]) session_name = optarg; break; - case 'o': - try_hw_optimization = true; + case 'O': + try_hw_optimization = false; break; case 'V': diff --git a/gtk2_ardour/pan_automation_time_axis.cc b/gtk2_ardour/pan_automation_time_axis.cc index 36e6c31245..b72eda78bd 100644 --- a/gtk2_ardour/pan_automation_time_axis.cc +++ b/gtk2_ardour/pan_automation_time_axis.cc @@ -31,6 +31,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace Gtk; PanAutomationTimeAxisView::PanAutomationTimeAxisView (Session& s, Route& r, PublicEditor& e, TimeAxisView& parent, Canvas& canvas, std::string n) diff --git a/gtk2_ardour/panner2d.cc b/gtk2_ardour/panner2d.cc index c6b2bad6c9..1fb94a1321 100644 --- a/gtk2_ardour/panner2d.cc +++ b/gtk2_ardour/panner2d.cc @@ -39,6 +39,7 @@ using namespace std; using namespace Gtk; using namespace sigc; using namespace ARDOUR; +using namespace PBD; Panner2d::Target::Target (float xa, float ya, const char *txt) : x (xa), y (ya), text (txt ? strdup (txt) : 0) @@ -127,7 +128,7 @@ Panner2d::reset (uint32_t n_inputs) } void -Panner2d::on_size_allocate (Gtk::Allocation alloc) +Panner2d::on_size_allocate (Gtk::Allocation& alloc) { width = alloc.get_width(); height = alloc.get_height(); diff --git a/gtk2_ardour/panner2d.h b/gtk2_ardour/panner2d.h index ff81ea3987..1bf8879ba5 100644 --- a/gtk2_ardour/panner2d.h +++ b/gtk2_ardour/panner2d.h @@ -78,7 +78,7 @@ class Panner2d : public Gtk::DrawingArea bool on_button_press_event (GdkEventButton *); bool on_button_release_event (GdkEventButton *); bool on_motion_notify_event (GdkEventMotion *); - void on_size_allocate (Gtk::Allocation alloc); + void on_size_allocate (Gtk::Allocation& alloc); private: struct Target { diff --git a/gtk2_ardour/panner_ui.cc b/gtk2_ardour/panner_ui.cc index 850070fabf..63a19867a8 100644 --- a/gtk2_ardour/panner_ui.cc +++ b/gtk2_ardour/panner_ui.cc @@ -41,6 +41,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace Gtkmm2ext; using namespace Gtk; using namespace sigc; diff --git a/gtk2_ardour/playlist_selector.cc b/gtk2_ardour/playlist_selector.cc index eb0e7e3203..f1a975d5dc 100644 --- a/gtk2_ardour/playlist_selector.cc +++ b/gtk2_ardour/playlist_selector.cc @@ -22,7 +22,7 @@ #include #include -#include +#include #include #include #include @@ -40,6 +40,7 @@ using namespace std; using namespace sigc; using namespace Gtk; using namespace ARDOUR; +using namespace PBD; PlaylistSelector::PlaylistSelector () : ArdourDialog ("playlist selector") @@ -89,7 +90,7 @@ void PlaylistSelector::show_for (RouteUI* ruix) { vector item; - DiskStream* this_ds; + AudioDiskstream* this_ds; string str; rui = ruix; @@ -115,7 +116,7 @@ PlaylistSelector::show_for (RouteUI* ruix) for (DSPL_Map::iterator x = dspl_map.begin(); x != dspl_map.end(); ++x) { - DiskStream* ds = session->diskstream_by_id (x->first); + AudioDiskstream* ds = session->diskstream_by_id (x->first); if (ds == 0) { continue; diff --git a/gtk2_ardour/plugin_selector.cc b/gtk2_ardour/plugin_selector.cc index 56f5fab9c8..16796df160 100644 --- a/gtk2_ardour/plugin_selector.cc +++ b/gtk2_ardour/plugin_selector.cc @@ -36,6 +36,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace Gtk; PluginSelector::PluginSelector (PluginManager *mgr) @@ -149,6 +150,9 @@ PluginSelector::PluginSelector (PluginManager *mgr) added_list.get_selection()->signal_changed().connect (mem_fun(*this, &PluginSelector::added_list_selection_changed)); input_refiller (); +#ifdef VST_SUPPORT + vst_refiller (); +#endif } void @@ -306,6 +310,9 @@ PluginSelector::btn_update_clicked() { manager->refresh (); input_refiller (); +#ifdef VST_SUPPORT + vst_refiller (); +#endif } #ifdef VST_SUPPORT diff --git a/gtk2_ardour/plugin_ui.cc b/gtk2_ardour/plugin_ui.cc index 66231adcc3..749ab9d4ac 100644 --- a/gtk2_ardour/plugin_ui.cc +++ b/gtk2_ardour/plugin_ui.cc @@ -56,6 +56,7 @@ using namespace std; using namespace ARDOUR; +using namespace PBD; using namespace Gtkmm2ext; using namespace Gtk; using namespace sigc; diff --git a/gtk2_ardour/plugin_ui.h b/gtk2_ardour/plugin_ui.h index 958b7995c6..e5800e8ece 100644 --- a/gtk2_ardour/plugin_ui.h +++ b/gtk2_ardour/plugin_ui.h @@ -228,7 +228,7 @@ class VSTPluginUI : public PlugUIBase, public Gtk::VBox Gtk::HBox preset_box; Gtk::VBox vpacker; - gboolean configure_handler (GdkEventConfigure*, Gtk::Socket*); + bool configure_handler (GdkEventConfigure*, Gtk::Socket*); void save_plugin_setting (); }; #endif diff --git a/gtk2_ardour/po/de_DE.po b/gtk2_ardour/po/de_DE.po index eb90ed4a3f..a51f6108bc 100644 --- a/gtk2_ardour/po/de_DE.po +++ b/gtk2_ardour/po/de_DE.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: gtk-ardour 0.347.2\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-04-25 17:46-0400\n" +"POT-Creation-Date: 2006-06-21 18:09-0400\n" "PO-Revision-Date: 2003-05-11 17:36+0200\n" "Last-Translator: Karsten Petersen \n" "Language-Team: Deutsch \n" @@ -17,202 +17,202 @@ msgstr "" "Plural-Forms: nplurals=2; plural=(n != 1);\n" "X-Generator: KBabel 0.9.6\n" -#: about.cc:119 +#: about.cc:120 msgid "Paul Davis" msgstr "" -#: about.cc:120 +#: about.cc:121 #, fuzzy msgid "Jesse Chappell" msgstr "bestmöglich" -#: about.cc:121 +#: about.cc:122 msgid "Taybin Rutkin" msgstr "" -#: about.cc:122 +#: about.cc:123 msgid "Marcus Andersson" msgstr "" -#: about.cc:123 +#: about.cc:124 msgid "Jeremy Hall" msgstr "" -#: about.cc:124 +#: about.cc:125 msgid "Steve Harris" msgstr "" -#: about.cc:125 +#: about.cc:126 msgid "Tim Mayberry" msgstr "" -#: about.cc:126 +#: about.cc:127 msgid "Mark Stewart" msgstr "" -#: about.cc:127 +#: about.cc:128 msgid "Sam Chessman" msgstr "" -#: about.cc:128 +#: about.cc:129 msgid "Jack O'Quin" msgstr "" -#: about.cc:129 +#: about.cc:130 msgid "Matt Krai" msgstr "" -#: about.cc:130 +#: about.cc:131 msgid "Ben Bell" msgstr "" -#: about.cc:131 +#: about.cc:132 msgid "Gerard van Dongen" msgstr "" -#: about.cc:132 +#: about.cc:133 msgid "Thomas Charbonnel" msgstr "" -#: about.cc:133 +#: about.cc:134 msgid "Nick Mainsbridge" msgstr "" -#: about.cc:134 +#: about.cc:135 msgid "Colin Law" msgstr "" -#: about.cc:135 +#: about.cc:136 msgid "Sampo Savolainen" msgstr "" -#: about.cc:136 +#: about.cc:137 msgid "Joshua Leach" msgstr "" -#: about.cc:137 +#: about.cc:138 msgid "Rob Holland" msgstr "" -#: about.cc:138 +#: about.cc:139 msgid "Per Sigmond" msgstr "" -#: about.cc:139 +#: about.cc:140 msgid "Doug Mclain" msgstr "" -#: about.cc:140 +#: about.cc:141 msgid "Petter Sundlöf" msgstr "" -#: about.cc:145 +#: about.cc:146 msgid "" "French:\n" "\tAlain Fréhel \n" msgstr "" -#: about.cc:146 +#: about.cc:147 msgid "" "German:\n" "\tKarsten Petersen \n" msgstr "" -#: about.cc:147 +#: about.cc:148 msgid "" "Italian:\n" "\tFilippo Pappalardo \n" msgstr "" -#: about.cc:148 +#: about.cc:149 msgid "" "Portuguese:\n" "\tRui Nuno Capela \n" msgstr "" -#: about.cc:149 +#: about.cc:150 msgid "" "Brazilian Portuguese:\n" "\tAlexander da Franca Fernandes \n" "\tChris Ross \n" msgstr "" -#: about.cc:151 +#: about.cc:152 msgid "" "Spanish:\n" "\t Alex Krohn \n" msgstr "" -#: about.cc:152 +#: about.cc:153 msgid "" "Russian:\n" "\t Igor Blinov \n" msgstr "" -#: about.cc:180 +#: about.cc:181 msgid "Copyright (C) 1999-2005 Paul Davis\n" msgstr "" -#: about.cc:181 +#: about.cc:182 msgid "" "Ardour comes with ABSOLUTELY NO WARRANTY\n" "This is free software, and you are welcome to redistribute it\n" "under certain conditions; see the file COPYING for details.\n" msgstr "" -#: about.cc:187 +#: about.cc:188 msgid "" "%1\n" "(built with ardour/gtk %2.%3.%4 libardour: %5.%6.%7)" msgstr "" -#: actions.cc:260 +#: actions.cc:261 msgid "programmer error: %1 %2" msgstr "" -#: add_route_dialog.cc:61 +#: add_route_dialog.cc:62 #, fuzzy msgid "ardour: add track/bus" msgstr "Ardour: Editor" #. path = "1" -#: add_route_dialog.cc:62 editor_route_list.cc:72 +#: add_route_dialog.cc:63 editor_route_list.cc:73 msgid "Tracks" msgstr "Spuren" #. path = "0" -#: add_route_dialog.cc:63 editor_route_list.cc:69 +#: add_route_dialog.cc:64 editor_route_list.cc:70 msgid "Busses" msgstr "" -#: add_route_dialog.cc:95 plugin_ui.cc:832 +#: add_route_dialog.cc:96 plugin_ui.cc:833 msgid "Add" msgstr "Hinzufügen" -#: add_route_dialog.cc:113 +#: add_route_dialog.cc:114 #, fuzzy msgid "Name (template)" msgstr "Name für Mixer-Voreinstellung" -#: add_route_dialog.cc:119 +#: add_route_dialog.cc:120 #, fuzzy msgid "Channel Configuration" msgstr "Importieren Abbrechen" -#: add_route_dialog.cc:176 editor.cc:131 editor.cc:3660 time_axis_view.cc:551 +#: add_route_dialog.cc:177 editor.cc:134 editor.cc:3688 time_axis_view.cc:552 msgid "Normal" msgstr "" -#: add_route_dialog.cc:178 +#: add_route_dialog.cc:179 #, fuzzy msgid "Tape" msgstr "Anfang" -#: add_route_dialog.cc:195 +#: add_route_dialog.cc:196 msgid "Mono" msgstr "" -#: add_route_dialog.cc:197 +#: add_route_dialog.cc:198 #, fuzzy msgid "Stereo" msgstr "Stop" @@ -285,27 +285,11 @@ msgstr "" msgid "SOLO" msgstr "" -#: ardour_ui.cc:207 -msgid "" -"You cannot record-enable\n" -"track %1\n" -"because it has no input connections.\n" -"You would be wasting space recording silence." -msgstr "" - -#: ardour_ui.cc:236 -msgid "no vertical meter strip image found" -msgstr "" - -#: ardour_ui.cc:243 -msgid "no horizontal meter strip image found" -msgstr "" - -#: ardour_ui.cc:410 +#: ardour_ui.cc:375 msgid "quit" msgstr "Verlassen" -#: ardour_ui.cc:419 +#: ardour_ui.cc:384 msgid "" "Ardour was unable to save your session.\n" "\n" @@ -314,33 +298,33 @@ msgid "" "\"Just quit\" option." msgstr "" -#: ardour_ui.cc:438 +#: ardour_ui.cc:403 msgid "ardour: save session?" msgstr "Ardour: Sitzung speichern?" -#: ardour_ui.cc:445 +#: ardour_ui.cc:410 msgid "Don't %1" msgstr "Ohne %1" -#: ardour_ui.cc:447 +#: ardour_ui.cc:412 msgid "Just %1" msgstr "Nur %1" -#: ardour_ui.cc:449 +#: ardour_ui.cc:414 msgid "Save and %1" msgstr "Speichern und %1" -#: ardour_ui.cc:461 +#: ardour_ui.cc:426 #, fuzzy msgid "session" msgstr "Sitzung" -#: ardour_ui.cc:463 +#: ardour_ui.cc:428 #, fuzzy msgid "snapshot" msgstr "Schnappschuß" -#: ardour_ui.cc:465 +#: ardour_ui.cc:430 #, fuzzy msgid "" "The %1\"%2\"\n" @@ -359,81 +343,81 @@ msgstr "" "\n" "Was wollen Sie machen?" -#: ardour_ui.cc:479 +#: ardour_ui.cc:444 msgid "Prompter" msgstr "" -#: ardour_ui.cc:538 +#: ardour_ui.cc:503 #, fuzzy, c-format msgid "disconnected" msgstr "Trennen" -#: ardour_ui.cc:545 +#: ardour_ui.cc:510 #, c-format msgid "SR: %.1f kHz / %4.1f msecs" msgstr "" -#: ardour_ui.cc:549 +#: ardour_ui.cc:514 #, c-format msgid "SR: %u kHz / %4.1f msecs" msgstr "" -#: ardour_ui.cc:562 +#: ardour_ui.cc:527 #, fuzzy, c-format msgid "DSP Load: %.1f%%" msgstr "Auslastung der CPU: %.1f%%" -#: ardour_ui.cc:572 +#: ardour_ui.cc:537 #, c-format msgid "Buffers p:%%% c:%%%" msgstr "" -#: ardour_ui.cc:599 +#: ardour_ui.cc:564 msgid "space: 24hrs+" msgstr "Platz: >24 Stunden" -#: ardour_ui.cc:629 +#: ardour_ui.cc:594 #, c-format msgid "space: %02dh:%02dm:%02ds" msgstr "Platz: %02dh:%02dm:%02ds" -#: ardour_ui.cc:668 +#: ardour_ui.cc:633 msgid "programming error: impossible control method" msgstr "" -#: ardour_ui.cc:776 new_session_dialog.cc:89 +#: ardour_ui.cc:741 new_session_dialog.cc:294 #, fuzzy msgid "Recent Sessions" msgstr "Sitzung" #. ardour sessions are folders -#: ardour_ui.cc:867 +#: ardour_ui.cc:834 #, fuzzy msgid "open session" msgstr "Sitzung" -#: ardour_ui.cc:873 +#: ardour_ui.cc:840 #, fuzzy msgid "Ardour sessions" msgstr "Ardour: Neue Sitzung" -#: ardour_ui.cc:906 +#: ardour_ui.cc:873 msgid "Patience is a virtue.\n" msgstr "Geduld ist eine Tugend.\n" -#: ardour_ui.cc:915 +#: ardour_ui.cc:882 msgid "You cannot add a track without a session already loaded." msgstr "Sie können erst eine Spur hinzufügen, wenn eine Sitzung geladen wurde." -#: ardour_ui.cc:922 +#: ardour_ui.cc:889 msgid "could not create new audio track" msgstr "Konnte neue Spur nicht erstellen." -#: ardour_ui.cc:926 +#: ardour_ui.cc:893 msgid "could not create new audio bus" msgstr "Konnte neuen Audiokanal nicht erstellen." -#: ardour_ui.cc:945 +#: ardour_ui.cc:912 msgid "" "There are insufficient JACK ports available\n" "to create a new track or bus.\n" @@ -441,14 +425,14 @@ msgid "" "restart JACK with more ports." msgstr "" -#: ardour_ui.cc:1069 +#: ardour_ui.cc:1036 msgid "" "Please create 1 or more track\n" "before trying to record.\n" "Check the Session menu." msgstr "" -#: ardour_ui.cc:1298 +#: ardour_ui.cc:1265 #, fuzzy msgid "" "JACK has either been shutdown or it\n" @@ -461,59 +445,57 @@ msgstr "" "schnell genug war. Sie sollten die Sitzung\n" "speichern und JACK sowie Ardour neu starten." -#: ardour_ui.cc:1315 +#: ardour_ui.cc:1282 msgid "Unable to create all required ports" msgstr "" -#: ardour_ui.cc:1323 +#: ardour_ui.cc:1290 #, fuzzy msgid "Unable to start the session running" msgstr "An den Anfang der Sitzung springen" -#: ardour_ui.cc:1459 +#: ardour_ui.cc:1426 msgid "No Stream" msgstr "Kein Datenstrom" -#: ardour_ui.cc:1486 ardour_ui.cc:1505 +#: ardour_ui.cc:1453 ardour_ui.cc:1472 msgid "none" msgstr "keine" -#: ardour_ui.cc:1495 ardour_ui.cc:1514 automation_time_axis.cc:183 -#: automation_time_axis.cc:212 automation_time_axis.cc:459 mixer_strip.cc:174 -#: mixer_strip.cc:186 mixer_strip.cc:881 plugin_ui.cc:391 plugin_ui.cc:634 +#: ardour_ui.cc:1462 ardour_ui.cc:1481 msgid "off" msgstr "aus" -#: ardour_ui.cc:1538 +#: ardour_ui.cc:1505 #, fuzzy msgid "Name of New Snapshot" msgstr "Name für Schnappschuß" -#: ardour_ui.cc:1684 +#: ardour_ui.cc:1651 msgid "Name for mix template:" msgstr "Name für Mixer-Voreinstellung" -#: ardour_ui.cc:1685 +#: ardour_ui.cc:1652 #, fuzzy msgid "-template" msgstr "Voreinstellung" -#: ardour_ui.cc:1836 +#: ardour_ui.cc:1809 msgid "" "You do not have write access to this session.\n" "This prevents the session from being loaded." msgstr "" -#: ardour_ui.cc:1849 ardour_ui.cc:1904 +#: ardour_ui.cc:1822 ardour_ui.cc:1877 #, fuzzy msgid "Session \"%1 (snapshot %2)\" did not load successfully" msgstr "Sitzung \"%1\" konnte nicht geladen werden." -#: ardour_ui.cc:1960 +#: ardour_ui.cc:1933 msgid "No audio files were ready for cleanup" msgstr "" -#: ardour_ui.cc:1964 +#: ardour_ui.cc:1937 msgid "" "If this seems suprising, \n" "check for any existing snapshots.\n" @@ -521,24 +503,24 @@ msgid "" "require some unused files to continue to exist." msgstr "" -#: ardour_ui.cc:1973 +#: ardour_ui.cc:1946 #, fuzzy msgid "ardour: cleanup" msgstr "Ardour: Uhr" -#: ardour_ui.cc:2009 ardour_ui.cc:2015 +#: ardour_ui.cc:1982 ardour_ui.cc:1988 msgid "files were" msgstr "" -#: ardour_ui.cc:2011 ardour_ui.cc:2017 +#: ardour_ui.cc:1984 ardour_ui.cc:1990 msgid "file was" msgstr "" -#: ardour_ui.cc:2058 +#: ardour_ui.cc:2031 msgid "Are you sure you want to cleanup?" msgstr "" -#: ardour_ui.cc:2063 +#: ardour_ui.cc:2036 msgid "" "Cleanup is a destructive operation.\n" "ALL undo/redo information will be lost if you cleanup.\n" @@ -546,26 +528,26 @@ msgid "" "location." msgstr "" -#: ardour_ui.cc:2069 +#: ardour_ui.cc:2042 #, fuzzy msgid "Clean Up" msgstr "leeren" -#: ardour_ui.cc:2072 +#: ardour_ui.cc:2045 #, fuzzy msgid "CleanupDialog" msgstr "leeren" -#: ardour_ui.cc:2073 +#: ardour_ui.cc:2046 #, fuzzy msgid "ardour_cleanup" msgstr "Ardour: Uhr" -#: ardour_ui.cc:2092 +#: ardour_ui.cc:2065 msgid "cleaned files" msgstr "" -#: ardour_ui.cc:2093 +#: ardour_ui.cc:2066 msgid "" "The following %1 %2 not in use and \n" "have been moved to:\n" @@ -576,23 +558,23 @@ msgid "" "%4 %5bytes of disk space.\n" msgstr "" -#: ardour_ui.cc:2118 +#: ardour_ui.cc:2091 #, fuzzy msgid "deleted file" msgstr "entfernen" -#: ardour_ui.cc:2119 +#: ardour_ui.cc:2092 msgid "" "The following %1 %2 deleted from\n" "%3,\n" "releasing %4 %5bytes of disk space" msgstr "" -#: ardour_ui.cc:2242 +#: ardour_ui.cc:2215 msgid "Recording was stopped because your system could not keep up." msgstr "" -#: ardour_ui.cc:2265 +#: ardour_ui.cc:2238 msgid "" "The disk system on your computer\n" "was not able to keep up with Ardour.\n" @@ -601,7 +583,7 @@ msgid "" "quickly enough to keep up with recording.\n" msgstr "" -#: ardour_ui.cc:2284 +#: ardour_ui.cc:2257 msgid "" "The disk system on your computer\n" "was not able to keep up with Ardour.\n" @@ -610,7 +592,7 @@ msgid "" "quickly enough to keep up with playback.\n" msgstr "" -#: ardour_ui.cc:2310 +#: ardour_ui.cc:2283 msgid "" "This session appears to have been in\n" "middle of recording when ardour or\n" @@ -621,370 +603,370 @@ msgid "" "what you would like to do.\n" msgstr "" -#: ardour_ui.cc:2320 +#: ardour_ui.cc:2293 msgid "Recover from crash" msgstr "" -#: ardour_ui.cc:2321 +#: ardour_ui.cc:2294 msgid "Ignore crash data" msgstr "" -#: ardour_ui.cc:2339 +#: ardour_ui.cc:2312 msgid "Could not disconnect from JACK" msgstr "" -#: ardour_ui.cc:2352 +#: ardour_ui.cc:2325 msgid "Could not reconnect to JACK" msgstr "" -#: ardour_ui2.cc:59 +#: ardour_ui2.cc:60 msgid "UI: cannot setup editor" msgstr "Der Editor konnte nicht initialisiert werden." -#: ardour_ui2.cc:64 +#: ardour_ui2.cc:65 msgid "UI: cannot setup mixer" msgstr "Der Mixer konnte nicht initialisiert werden." -#: ardour_ui2.cc:90 +#: ardour_ui2.cc:91 msgid "MMC + Local" msgstr "" -#: ardour_ui2.cc:91 +#: ardour_ui2.cc:92 msgid "MMC" msgstr "" -#: ardour_ui2.cc:92 +#: ardour_ui2.cc:93 msgid "Local" msgstr "" -#: ardour_ui2.cc:109 +#: ardour_ui2.cc:110 msgid "MMC ID" msgstr "" -#: ardour_ui2.cc:290 +#: ardour_ui2.cc:291 msgid "Play from playhead" msgstr "Wiedergabe ab Playhead" -#: ardour_ui2.cc:291 +#: ardour_ui2.cc:292 msgid "Stop playback" msgstr "Wiedergabe anhalten" -#: ardour_ui2.cc:292 +#: ardour_ui2.cc:293 #, fuzzy msgid "Play range/selection" msgstr "Auswahl wiedergeben" -#: ardour_ui2.cc:293 +#: ardour_ui2.cc:294 msgid "Go to start of session" msgstr "An den Anfang der Sitzung springen" -#: ardour_ui2.cc:294 +#: ardour_ui2.cc:295 msgid "Go to end of session" msgstr "Ans Ende der Sitzung springen" -#: ardour_ui2.cc:295 +#: ardour_ui2.cc:296 #, fuzzy msgid "Play loop range" msgstr "Bereich" -#: ardour_ui2.cc:296 +#: ardour_ui2.cc:297 msgid "Return to last playback start when stopped" msgstr "Bei Stopp zum Wiedergabeanfang springen" -#: ardour_ui2.cc:297 +#: ardour_ui2.cc:298 msgid "Start playback after any locate" msgstr "" -#: ardour_ui2.cc:298 +#: ardour_ui2.cc:299 msgid "Be sensible about input monitoring" msgstr "" -#: ardour_ui2.cc:299 +#: ardour_ui2.cc:300 msgid "Start recording at auto-punch start" msgstr "" -#: ardour_ui2.cc:300 +#: ardour_ui2.cc:301 msgid "Stop recording at auto-punch end" msgstr "" -#: ardour_ui2.cc:301 +#: ardour_ui2.cc:302 msgid "Enable/Disable audio click" msgstr "" -#: ardour_ui2.cc:302 +#: ardour_ui2.cc:303 msgid "Positional sync source" msgstr "" -#: ardour_ui2.cc:303 +#: ardour_ui2.cc:304 msgid "Does Ardour control the time?" msgstr "" -#: ardour_ui2.cc:304 +#: ardour_ui2.cc:305 msgid "Shuttle speed control" msgstr "" -#: ardour_ui2.cc:305 +#: ardour_ui2.cc:306 #, c-format msgid "Select semitones or %%-age for speed display" msgstr "" -#: ardour_ui2.cc:306 +#: ardour_ui2.cc:307 msgid "Current transport speed" msgstr "" -#: ardour_ui2.cc:329 +#: ardour_ui2.cc:330 #, fuzzy msgid "Primary clock" msgstr "Ardour: Uhr" -#: ardour_ui2.cc:330 +#: ardour_ui2.cc:331 msgid "secondary clock" msgstr "" #. XXX: this should really be saved in instant.xml or something similar and restored from there #. Combo's are stupid - they steal space from the entry for the button -#: ardour_ui2.cc:387 ardour_ui2.cc:823 ardour_ui2.cc:836 ardour_ui2.cc:899 -#: ardour_ui2.cc:901 +#: ardour_ui2.cc:388 ardour_ui2.cc:833 ardour_ui2.cc:846 ardour_ui2.cc:909 +#: ardour_ui2.cc:911 msgid "sprung" msgstr "" -#: ardour_ui2.cc:388 ardour_ui2.cc:825 ardour_ui2.cc:847 +#: ardour_ui2.cc:389 ardour_ui2.cc:835 ardour_ui2.cc:857 msgid "wheel" msgstr "" -#: ardour_ui2.cc:450 +#: ardour_ui2.cc:451 msgid "ardour: clock" msgstr "Ardour: Uhr" -#: ardour_ui2.cc:595 +#: ardour_ui2.cc:596 msgid "Maximum speed" msgstr "" -#: ardour_ui2.cc:813 +#: ardour_ui2.cc:823 #, fuzzy msgid "st" msgstr "bestmöglich" -#: ardour_ui2.cc:857 ardour_ui2.cc:880 ardour_ui2.cc:897 +#: ardour_ui2.cc:867 ardour_ui2.cc:890 ardour_ui2.cc:907 msgid "stopped" msgstr "" -#: ardour_ui_dialogs.cc:152 playlist_selector.cc:69 +#: ardour_ui_dialogs.cc:153 playlist_selector.cc:70 #, fuzzy msgid "close" msgstr "Schließen" -#: ardour_ui_dialogs.cc:359 ardour_ui_ed.cc:181 +#: ardour_ui_dialogs.cc:360 ardour_ui_ed.cc:184 #, fuzzy msgid "Sound File Browser" msgstr "Ardour: Audio Bibliothek" #. menus + submenus that need action items -#: ardour_ui_ed.cc:69 +#: ardour_ui_ed.cc:72 msgid "Session" msgstr "Sitzung" -#: ardour_ui_ed.cc:70 ardour_ui_ed.cc:127 editor.cc:1843 export_dialog.cc:350 +#: ardour_ui_ed.cc:73 ardour_ui_ed.cc:130 editor.cc:1836 export_dialog.cc:350 #: export_dialog.cc:1059 export_dialog.cc:1063 msgid "Export" msgstr "Exportieren" -#: ardour_ui_ed.cc:71 +#: ardour_ui_ed.cc:74 #, fuzzy msgid "Cleanup" msgstr "leeren" -#: ardour_ui_ed.cc:72 option_editor.cc:125 +#: ardour_ui_ed.cc:75 option_editor.cc:126 msgid "Sync" msgstr "" -#: ardour_ui_ed.cc:73 ardour_ui_ed.cc:74 +#: ardour_ui_ed.cc:76 ardour_ui_ed.cc:77 #, fuzzy msgid "Options" msgstr "Geschwindigkeitseditor" -#: ardour_ui_ed.cc:75 +#: ardour_ui_ed.cc:78 msgid "Help" msgstr "" -#: ardour_ui_ed.cc:76 +#: ardour_ui_ed.cc:79 msgid "KeyMouse Actions" msgstr "" -#: ardour_ui_ed.cc:77 +#: ardour_ui_ed.cc:80 #, fuzzy msgid "Audio File Format" msgstr "Ardour: Audio Bibliothek" -#: ardour_ui_ed.cc:78 +#: ardour_ui_ed.cc:81 #, fuzzy msgid "Header" msgstr "Verbergen" -#: ardour_ui_ed.cc:79 +#: ardour_ui_ed.cc:82 msgid "Data" msgstr "" -#: ardour_ui_ed.cc:80 +#: ardour_ui_ed.cc:83 msgid "Control Surfaces" msgstr "" #. the real actions -#: ardour_ui_ed.cc:84 audio_time_axis.cc:1856 new_session_dialog.cc:342 +#: ardour_ui_ed.cc:87 audio_time_axis.cc:1854 new_session_dialog.cc:529 #, fuzzy msgid "New" msgstr "Neu..." -#: ardour_ui_ed.cc:86 new_session_dialog.cc:334 +#: ardour_ui_ed.cc:89 new_session_dialog.cc:517 #, fuzzy msgid "Open" msgstr "Öffnen..." -#: ardour_ui_ed.cc:87 +#: ardour_ui_ed.cc:90 #, fuzzy msgid "Recent" msgstr "Zurücksetzen" -#: ardour_ui_ed.cc:88 io_selector.cc:57 io_selector.cc:791 +#: ardour_ui_ed.cc:91 io_selector.cc:58 io_selector.cc:792 msgid "Close" msgstr "Schließen" -#: ardour_ui_ed.cc:91 route_params_ui.cc:512 +#: ardour_ui_ed.cc:94 route_params_ui.cc:514 #, fuzzy msgid "Add Track/Bus" msgstr "MIDI Spur(en) hinzufügen" -#: ardour_ui_ed.cc:102 +#: ardour_ui_ed.cc:105 #, fuzzy msgid "Connect" msgstr "Verbindungen" #. -#: ardour_ui_ed.cc:110 +#: ardour_ui_ed.cc:113 msgid "Snapshot" msgstr "Schnappschuß" -#: ardour_ui_ed.cc:113 +#: ardour_ui_ed.cc:116 msgid "Save Template..." msgstr "Speichern als Voreinstellung..." -#: ardour_ui_ed.cc:116 +#: ardour_ui_ed.cc:119 msgid "Export session to audiofile..." msgstr "Export als Audio-Datei..." -#: ardour_ui_ed.cc:119 +#: ardour_ui_ed.cc:122 #, fuzzy msgid "Export selection to audiofile..." msgstr "Export als Audio-Datei..." -#: ardour_ui_ed.cc:123 +#: ardour_ui_ed.cc:126 #, fuzzy msgid "Export range markers to audiofile..." msgstr "Export als Audio-Datei..." -#: ardour_ui_ed.cc:130 +#: ardour_ui_ed.cc:133 msgid "Cleanup unused sources" msgstr "" -#: ardour_ui_ed.cc:132 +#: ardour_ui_ed.cc:135 msgid "Flush wastebasket" msgstr "" -#: ardour_ui_ed.cc:138 ardour_ui_options.cc:381 ardour_ui_options.cc:390 -#: ardour_ui_options.cc:462 +#: ardour_ui_ed.cc:141 ardour_ui_options.cc:408 ardour_ui_options.cc:417 +#: ardour_ui_options.cc:489 msgid "JACK" msgstr "" -#: ardour_ui_ed.cc:139 +#: ardour_ui_ed.cc:142 msgid "Latency" msgstr "" -#: ardour_ui_ed.cc:141 +#: ardour_ui_ed.cc:144 #, fuzzy msgid "Reconnect" msgstr "Verbindungen" -#: ardour_ui_ed.cc:144 mixer_strip.cc:514 mixer_strip.cc:574 +#: ardour_ui_ed.cc:147 mixer_strip.cc:497 mixer_strip.cc:565 msgid "Disconnect" msgstr "Trennen" -#: ardour_ui_ed.cc:171 +#: ardour_ui_ed.cc:174 msgid "Windows" msgstr "Fenster" -#: ardour_ui_ed.cc:172 +#: ardour_ui_ed.cc:175 msgid "start prefix" msgstr "" -#: ardour_ui_ed.cc:173 +#: ardour_ui_ed.cc:176 msgid "Quit" msgstr "Beenden" #. windows visibility actions -#: ardour_ui_ed.cc:177 +#: ardour_ui_ed.cc:180 msgid "Maximise Editor Space" msgstr "" -#: ardour_ui_ed.cc:179 +#: ardour_ui_ed.cc:182 #, fuzzy msgid "Show Editor" msgstr "Geschwindigkeitseditor" -#: ardour_ui_ed.cc:180 +#: ardour_ui_ed.cc:183 #, fuzzy msgid "Show Mixer" msgstr "Mixer" -#: ardour_ui_ed.cc:182 +#: ardour_ui_ed.cc:185 #, fuzzy msgid "Options Editor" msgstr "Geschwindigkeitseditor" -#: ardour_ui_ed.cc:183 +#: ardour_ui_ed.cc:186 msgid "Track/Bus Inspector" msgstr "" -#: ardour_ui_ed.cc:185 +#: ardour_ui_ed.cc:188 msgid "Connections" msgstr "Verbindungen" -#: ardour_ui_ed.cc:187 +#: ardour_ui_ed.cc:190 msgid "Locations" msgstr "Stellen" -#: ardour_ui_ed.cc:189 +#: ardour_ui_ed.cc:192 msgid "Big Clock" msgstr "Große Uhr" -#: ardour_ui_ed.cc:191 +#: ardour_ui_ed.cc:194 msgid "About" msgstr "" -#: ardour_ui_ed.cc:192 +#: ardour_ui_ed.cc:195 #, fuzzy msgid "Colors" msgstr "solo" -#: ardour_ui_ed.cc:194 +#: ardour_ui_ed.cc:197 #, fuzzy msgid "Add Audio Track" msgstr "MIDI Spur(en) hinzufügen" -#: ardour_ui_ed.cc:196 +#: ardour_ui_ed.cc:199 msgid "Add Audio Bus" msgstr "" -#: ardour_ui_ed.cc:198 +#: ardour_ui_ed.cc:201 msgid "Save" msgstr "Speichern" -#: ardour_ui_ed.cc:200 editor_actions.cc:254 +#: ardour_ui_ed.cc:203 editor_actions.cc:255 #, fuzzy msgid "Remove Last Capture" msgstr "Synchronisationspunkt entfernen" #. do-nothing action for the "transport" menu bar item -#: ardour_ui_ed.cc:207 +#: ardour_ui_ed.cc:210 #, fuzzy msgid "Transport" msgstr "dreieckig" @@ -992,74 +974,74 @@ msgstr "dreieckig" #. these two are not used by key bindings, instead use ToggleRoll for that. these two do show up in #. menus and via button proxies. #. -#: ardour_ui_ed.cc:213 sfdb_ui.cc:57 +#: ardour_ui_ed.cc:216 sfdb_ui.cc:57 #, fuzzy msgid "Stop" msgstr "Stop" -#: ardour_ui_ed.cc:216 +#: ardour_ui_ed.cc:219 msgid "Roll" msgstr "" -#: ardour_ui_ed.cc:220 +#: ardour_ui_ed.cc:223 #, fuzzy msgid "Start/Stop" msgstr "Anfang:" -#: ardour_ui_ed.cc:223 +#: ardour_ui_ed.cc:226 msgid "Stop + Forget Capture" msgstr "" -#: ardour_ui_ed.cc:226 +#: ardour_ui_ed.cc:229 #, fuzzy msgid "Play Loop Range" msgstr "Bereich" -#: ardour_ui_ed.cc:229 +#: ardour_ui_ed.cc:232 #, fuzzy msgid "Play Selection" msgstr "Wiedergabe der ausgewählten Region" -#: ardour_ui_ed.cc:233 +#: ardour_ui_ed.cc:236 #, fuzzy msgid "Enable Record" msgstr "Wiederherstellen" -#: ardour_ui_ed.cc:236 +#: ardour_ui_ed.cc:239 #, fuzzy msgid "Rewind" msgstr "Suchen" -#: ardour_ui_ed.cc:239 +#: ardour_ui_ed.cc:242 msgid "Rewind (Slow)" msgstr "" -#: ardour_ui_ed.cc:242 +#: ardour_ui_ed.cc:245 msgid "Rewind (Fast)" msgstr "" -#: ardour_ui_ed.cc:245 +#: ardour_ui_ed.cc:248 msgid "Forward" msgstr "" -#: ardour_ui_ed.cc:248 +#: ardour_ui_ed.cc:251 msgid "Forward (Slow)" msgstr "" -#: ardour_ui_ed.cc:251 +#: ardour_ui_ed.cc:254 msgid "Forward (Fast)" msgstr "" -#: ardour_ui_ed.cc:254 +#: ardour_ui_ed.cc:257 msgid "Goto Zero" msgstr "" -#: ardour_ui_ed.cc:257 +#: ardour_ui_ed.cc:260 #, fuzzy msgid "Goto Start" msgstr "Anfang:" -#: ardour_ui_ed.cc:260 +#: ardour_ui_ed.cc:263 msgid "Goto End" msgstr "" @@ -1067,310 +1049,310 @@ msgstr "" #. that proxies for these action to be more compact. It would be nice to find a way to override the action #. name appearance on the buttons. #. -#: ardour_ui_ed.cc:269 +#: ardour_ui_ed.cc:272 msgid "" "Punch\n" "in" msgstr "" -#: ardour_ui_ed.cc:272 +#: ardour_ui_ed.cc:275 msgid "" "Punch\n" "out" msgstr "" -#: ardour_ui_ed.cc:275 option_editor.cc:128 +#: ardour_ui_ed.cc:278 option_editor.cc:129 msgid "Click" msgstr "" -#: ardour_ui_ed.cc:278 +#: ardour_ui_ed.cc:281 #, fuzzy msgid "" "Auto\n" "input" msgstr "Port hinzufügen" -#: ardour_ui_ed.cc:281 +#: ardour_ui_ed.cc:284 msgid "" "Auto\n" "play" msgstr "" -#: ardour_ui_ed.cc:284 +#: ardour_ui_ed.cc:287 msgid "" "Auto\n" "return" msgstr "" -#: ardour_ui_ed.cc:288 +#: ardour_ui_ed.cc:291 msgid "" "Time\n" "master" msgstr "" -#: ardour_ui_ed.cc:291 +#: ardour_ui_ed.cc:294 msgid "Toggle Record Enable Track1" msgstr "" -#: ardour_ui_ed.cc:293 +#: ardour_ui_ed.cc:296 msgid "Toggle Record Enable Track2" msgstr "" -#: ardour_ui_ed.cc:295 +#: ardour_ui_ed.cc:298 msgid "Toggle Record Enable Track3" msgstr "" -#: ardour_ui_ed.cc:297 +#: ardour_ui_ed.cc:300 msgid "Toggle Record Enable Track4" msgstr "" -#: ardour_ui_ed.cc:299 +#: ardour_ui_ed.cc:302 msgid "Toggle Record Enable Track5" msgstr "" -#: ardour_ui_ed.cc:301 +#: ardour_ui_ed.cc:304 msgid "Toggle Record Enable Track6" msgstr "" -#: ardour_ui_ed.cc:303 +#: ardour_ui_ed.cc:306 msgid "Toggle Record Enable Track7" msgstr "" -#: ardour_ui_ed.cc:305 +#: ardour_ui_ed.cc:308 msgid "Toggle Record Enable Track8" msgstr "" -#: ardour_ui_ed.cc:307 +#: ardour_ui_ed.cc:310 msgid "Toggle Record Enable Track9" msgstr "" -#: ardour_ui_ed.cc:309 +#: ardour_ui_ed.cc:312 msgid "Toggle Record Enable Track10" msgstr "" -#: ardour_ui_ed.cc:311 +#: ardour_ui_ed.cc:314 msgid "Toggle Record Enable Track11" msgstr "" -#: ardour_ui_ed.cc:313 +#: ardour_ui_ed.cc:316 msgid "Toggle Record Enable Track12" msgstr "" -#: ardour_ui_ed.cc:315 +#: ardour_ui_ed.cc:318 msgid "Toggle Record Enable Track13" msgstr "" -#: ardour_ui_ed.cc:317 +#: ardour_ui_ed.cc:320 msgid "Toggle Record Enable Track14" msgstr "" -#: ardour_ui_ed.cc:319 +#: ardour_ui_ed.cc:322 msgid "Toggle Record Enable Track15" msgstr "" -#: ardour_ui_ed.cc:321 +#: ardour_ui_ed.cc:324 msgid "Toggle Record Enable Track16" msgstr "" -#: ardour_ui_ed.cc:323 +#: ardour_ui_ed.cc:326 msgid "Toggle Record Enable Track17" msgstr "" -#: ardour_ui_ed.cc:325 +#: ardour_ui_ed.cc:328 msgid "Toggle Record Enable Track18" msgstr "" -#: ardour_ui_ed.cc:327 +#: ardour_ui_ed.cc:330 msgid "Toggle Record Enable Track19" msgstr "" -#: ardour_ui_ed.cc:329 +#: ardour_ui_ed.cc:332 msgid "Toggle Record Enable Track20" msgstr "" -#: ardour_ui_ed.cc:331 +#: ardour_ui_ed.cc:334 msgid "Toggle Record Enable Track21" msgstr "" -#: ardour_ui_ed.cc:333 +#: ardour_ui_ed.cc:336 msgid "Toggle Record Enable Track22" msgstr "" -#: ardour_ui_ed.cc:335 +#: ardour_ui_ed.cc:338 msgid "Toggle Record Enable Track23" msgstr "" -#: ardour_ui_ed.cc:337 +#: ardour_ui_ed.cc:340 msgid "Toggle Record Enable Track24" msgstr "" -#: ardour_ui_ed.cc:339 +#: ardour_ui_ed.cc:342 msgid "Toggle Record Enable Track25" msgstr "" -#: ardour_ui_ed.cc:341 +#: ardour_ui_ed.cc:344 msgid "Toggle Record Enable Track26" msgstr "" -#: ardour_ui_ed.cc:343 +#: ardour_ui_ed.cc:346 msgid "Toggle Record Enable Track27" msgstr "" -#: ardour_ui_ed.cc:345 +#: ardour_ui_ed.cc:348 msgid "Toggle Record Enable Track28" msgstr "" -#: ardour_ui_ed.cc:347 +#: ardour_ui_ed.cc:350 msgid "Toggle Record Enable Track29" msgstr "" -#: ardour_ui_ed.cc:349 +#: ardour_ui_ed.cc:352 msgid "Toggle Record Enable Track30" msgstr "" -#: ardour_ui_ed.cc:351 +#: ardour_ui_ed.cc:354 msgid "Toggle Record Enable Track31" msgstr "" -#: ardour_ui_ed.cc:353 +#: ardour_ui_ed.cc:356 msgid "Toggle Record Enable Track32" msgstr "" -#: ardour_ui_ed.cc:358 +#: ardour_ui_ed.cc:361 #, fuzzy msgid "Percentage" msgstr "Zurücksetzen" -#: ardour_ui_ed.cc:359 +#: ardour_ui_ed.cc:362 #, fuzzy msgid "Semitones" msgstr "Sitzung" -#: ardour_ui_ed.cc:363 +#: ardour_ui_ed.cc:366 msgid "Send MTC" msgstr "MTC senden" -#: ardour_ui_ed.cc:365 +#: ardour_ui_ed.cc:368 msgid "Send MMC" msgstr "MMC senden" -#: ardour_ui_ed.cc:367 +#: ardour_ui_ed.cc:370 #, fuzzy msgid "Use MMC" msgstr "MMC senden" -#: ardour_ui_ed.cc:369 +#: ardour_ui_ed.cc:372 msgid "Send MIDI feedback" msgstr "" -#: ardour_ui_ed.cc:371 +#: ardour_ui_ed.cc:374 msgid "Use MIDI control" msgstr "" -#: ardour_ui_ed.cc:374 -msgid "Connect newtrack inputs to hardware" -msgstr "" - -#: ardour_ui_ed.cc:392 -msgid "Connect new track outputs to hardware" -msgstr "" - -#: ardour_ui_ed.cc:394 -msgid "Connect new track outputs to master" +#: ardour_ui_ed.cc:377 +msgid "Connect new track inputs to hardware" msgstr "" #: ardour_ui_ed.cc:396 +msgid "Connect new track outputs to hardware" +msgstr "" + +#: ardour_ui_ed.cc:398 +msgid "Connect new track outputs to master" +msgstr "" + +#: ardour_ui_ed.cc:400 msgid "Manually connect new track outputs" msgstr "" -#: ardour_ui_ed.cc:401 +#: ardour_ui_ed.cc:405 msgid "Hardware monitoring" msgstr "" -#: ardour_ui_ed.cc:402 +#: ardour_ui_ed.cc:406 msgid "Software monitoring" msgstr "" -#: ardour_ui_ed.cc:403 +#: ardour_ui_ed.cc:407 msgid "External monitoring" msgstr "" #. Configuration object options (i.e. not session specific) -#: ardour_ui_ed.cc:407 +#: ardour_ui_ed.cc:411 msgid "Stop plugins with transport" msgstr "" -#: ardour_ui_ed.cc:408 +#: ardour_ui_ed.cc:412 #, fuzzy msgid "Verify remove last capture" msgstr "Synchronisationspunkt entfernen" -#: ardour_ui_ed.cc:409 +#: ardour_ui_ed.cc:413 msgid "Stop recording on xrun" msgstr "" -#: ardour_ui_ed.cc:410 +#: ardour_ui_ed.cc:414 #, fuzzy msgid "Stop transport at session end" msgstr "Ans Ende der Sitzung springen" -#: ardour_ui_ed.cc:411 +#: ardour_ui_ed.cc:415 msgid "-12dB gain reduce ffwd/rewind" msgstr "" -#: ardour_ui_ed.cc:412 +#: ardour_ui_ed.cc:416 msgid "Rec-enable stays engaged at stop" msgstr "" #. session options -#: ardour_ui_ed.cc:416 +#: ardour_ui_ed.cc:420 #, fuzzy msgid "Do not run plugins while recording" msgstr "Wellenform zeigen" -#: ardour_ui_ed.cc:419 +#: ardour_ui_ed.cc:423 msgid "Latched solo" msgstr "" -#: ardour_ui_ed.cc:424 +#: ardour_ui_ed.cc:428 #, fuzzy msgid "Solo in-place" msgstr "solo" -#: ardour_ui_ed.cc:426 +#: ardour_ui_ed.cc:430 msgid "Solo via bus" msgstr "" -#: ardour_ui_ed.cc:429 +#: ardour_ui_ed.cc:433 msgid "Automatically create crossfades" msgstr "" -#: ardour_ui_ed.cc:431 +#: ardour_ui_ed.cc:435 msgid "Unmute new full crossfades" msgstr "" -#: ardour_ui_options.cc:379 ardour_ui_options.cc:389 ardour_ui_options.cc:456 +#: ardour_ui_options.cc:406 ardour_ui_options.cc:416 ardour_ui_options.cc:483 #, fuzzy msgid "Internal" msgstr "mittelmäßig" -#: ardour_ui_options.cc:380 ardour_ui_options.cc:459 +#: ardour_ui_options.cc:407 ardour_ui_options.cc:486 msgid "MTC" msgstr "" -#: audio_clock.cc:1719 editor.cc:185 +#: audio_clock.cc:1742 editor.cc:188 msgid "SMPTE" msgstr "" -#: audio_clock.cc:1720 editor.cc:184 editor_rulers.cc:359 +#: audio_clock.cc:1743 editor.cc:187 editor_rulers.cc:360 msgid "Bars:Beats" msgstr "" -#: audio_clock.cc:1721 +#: audio_clock.cc:1744 msgid "Minutes:Seconds" msgstr "Minuten:Sekunden" -#: audio_clock.cc:1722 +#: audio_clock.cc:1745 msgid "Audio Frames" msgstr "" @@ -1378,306 +1360,322 @@ msgstr "" #. Slowest = 6.6dB/sec falloff at update rate of 40ms #. Slow = 6.8dB/sec falloff at update rate of 40ms #. -#: audio_clock.cc:1723 editor_actions.cc:374 editor_actions.cc:382 +#: audio_clock.cc:1746 editor_actions.cc:375 editor_actions.cc:383 +#: gain_meter.cc:172 panner_ui.cc:89 plugin_ui.cc:392 plugin_ui.cc:635 msgid "Off" msgstr "Aus" -#: audio_clock.cc:1725 +#: audio_clock.cc:1748 msgid "Mode" msgstr "Modus" -#: audio_time_axis.cc:90 mixer_strip.cc:458 +#: audio_time_axis.cc:91 msgid "m" msgstr "" -#: audio_time_axis.cc:90 mixer_strip.cc:459 +#: audio_time_axis.cc:91 msgid "s" msgstr "" -#: audio_time_axis.cc:90 +#: audio_time_axis.cc:91 msgid "r" msgstr "" -#: audio_time_axis.cc:94 +#: audio_time_axis.cc:95 msgid "g" msgstr "" #. group -#: audio_time_axis.cc:95 +#: audio_time_axis.cc:96 msgid "p" msgstr "" -#: audio_time_axis.cc:96 automation_time_axis.cc:31 visual_time_axis.cc:73 +#: audio_time_axis.cc:97 automation_time_axis.cc:32 visual_time_axis.cc:74 msgid "h" msgstr "" #. height -#: audio_time_axis.cc:97 +#: audio_time_axis.cc:98 msgid "a" msgstr "" -#: audio_time_axis.cc:98 visual_time_axis.cc:72 +#: audio_time_axis.cc:99 visual_time_axis.cc:73 msgid "v" msgstr "" -#: audio_time_axis.cc:173 +#: audio_time_axis.cc:168 mixer_strip.cc:86 #, fuzzy msgid "Record" msgstr "Wiederherstellen" -#: audio_time_axis.cc:174 editor_actions.cc:36 +#: audio_time_axis.cc:169 editor_actions.cc:37 mixer_strip.cc:86 #, fuzzy msgid "Solo" msgstr "solo" -#: audio_time_axis.cc:175 editor.cc:1767 editor.cc:1866 panner_ui.cc:385 +#: audio_time_axis.cc:170 editor.cc:1760 editor.cc:1859 mixer_strip.cc:86 +#: panner_ui.cc:427 #, fuzzy msgid "Mute" msgstr "mute" -#: audio_time_axis.cc:176 +#: audio_time_axis.cc:171 #, fuzzy msgid "Edit Group" msgstr "Mix Gruppen" -#: audio_time_axis.cc:177 visual_time_axis.cc:91 +#: audio_time_axis.cc:172 visual_time_axis.cc:92 #, fuzzy msgid "Display Height" msgstr "Anzeige" -#: audio_time_axis.cc:178 +#: audio_time_axis.cc:173 #, fuzzy msgid "Playlist" msgstr "Wiedergabe" -#: audio_time_axis.cc:179 audio_time_axis.cc:743 +#: audio_time_axis.cc:174 audio_time_axis.cc:741 #, fuzzy msgid "Automation" msgstr "Stellen" -#: audio_time_axis.cc:180 visual_time_axis.cc:92 +#: audio_time_axis.cc:175 visual_time_axis.cc:93 msgid "Visual options" msgstr "" -#: audio_time_axis.cc:181 visual_time_axis.cc:93 +#: audio_time_axis.cc:176 visual_time_axis.cc:94 msgid "Hide this track" msgstr "" -#: audio_time_axis.cc:337 +#: audio_time_axis.cc:333 mixer_strip.cc:927 #, fuzzy msgid "No group" msgstr "keine Gruppe" -#: audio_time_axis.cc:704 automation_time_axis.cc:448 -#: imageframe_time_axis.cc:256 marker_time_axis.cc:210 +#: audio_time_axis.cc:702 automation_time_axis.cc:450 +#: imageframe_time_axis.cc:255 marker_time_axis.cc:211 #, fuzzy msgid "Height" msgstr "Rechts" -#: audio_time_axis.cc:705 color_manager.cc:40 imageframe_time_axis.cc:257 -#: marker_time_axis.cc:211 +#: audio_time_axis.cc:703 color_manager.cc:41 imageframe_time_axis.cc:256 +#: marker_time_axis.cc:212 #, fuzzy msgid "Color" msgstr "solo" -#: audio_time_axis.cc:709 +#: audio_time_axis.cc:707 msgid "Hide all crossfades" msgstr "" -#: audio_time_axis.cc:710 +#: audio_time_axis.cc:708 msgid "Show all crossfades" msgstr "" -#: audio_time_axis.cc:714 mixer_strip.cc:1236 +#: audio_time_axis.cc:712 mixer_strip.cc:1011 #, fuzzy msgid "Remote Control ID" msgstr "Synchronisationspunkt entfernen" -#: audio_time_axis.cc:720 +#: audio_time_axis.cc:718 #, fuzzy -msgid "show all automation" +msgid "Show all automation" msgstr "Stellen" -#: audio_time_axis.cc:723 +#: audio_time_axis.cc:721 #, fuzzy -msgid "show existing automation" +msgid "Show existing automation" msgstr "Stellen" -#: audio_time_axis.cc:726 +#: audio_time_axis.cc:724 #, fuzzy -msgid "hide all automation" +msgid "Hide all automation" msgstr "Stellen" -#: audio_time_axis.cc:731 audio_time_axis.cc:1169 editor.cc:215 -msgid "gain" +#: audio_time_axis.cc:729 +#, fuzzy +msgid "Fader" +msgstr "Verbergen" + +#: audio_time_axis.cc:734 +msgid "Pan" msgstr "" -#: audio_time_axis.cc:736 audio_time_axis.cc:1209 -msgid "pan" -msgstr "" - -#: audio_time_axis.cc:741 +#: audio_time_axis.cc:739 msgid "Plugins" msgstr "" -#: audio_time_axis.cc:749 +#: audio_time_axis.cc:747 #, fuzzy msgid "Show waveforms" msgstr "Wellenform zeigen" -#: audio_time_axis.cc:757 +#: audio_time_axis.cc:755 msgid "Traditional" msgstr "" -#: audio_time_axis.cc:760 +#: audio_time_axis.cc:758 msgid "Rectified" msgstr "" -#: audio_time_axis.cc:763 +#: audio_time_axis.cc:761 #, fuzzy msgid "Waveform" msgstr "Wellenform zeigen" -#: audio_time_axis.cc:773 -msgid "align with existing material" +#: audio_time_axis.cc:771 +msgid "Align with existing material" msgstr "" -#: audio_time_axis.cc:778 -msgid "align with capture time" +#: audio_time_axis.cc:776 +msgid "Align with capture time" msgstr "" -#: audio_time_axis.cc:784 +#: audio_time_axis.cc:782 msgid "Alignment" msgstr "" -#: audio_time_axis.cc:790 editor.cc:523 editor_actions.cc:59 -#: mixer_strip.cc:1225 +#: audio_time_axis.cc:788 editor.cc:527 editor_actions.cc:60 +#: mixer_strip.cc:1000 mixer_ui.cc:111 msgid "Active" msgstr "Aktiv" -#: audio_time_axis.cc:795 editor.cc:1929 editor_actions.cc:319 -#: editor_markers.cc:507 imageframe_time_axis.cc:260 location_ui.cc:56 -#: marker_time_axis.cc:214 mixer_strip.cc:1239 +#: audio_time_axis.cc:793 editor.cc:1922 editor_actions.cc:320 +#: editor_markers.cc:508 imageframe_time_axis.cc:259 location_ui.cc:57 +#: marker_time_axis.cc:215 mixer_strip.cc:1014 msgid "Remove" msgstr "Entfernen" -#: audio_time_axis.cc:835 +#: audio_time_axis.cc:833 #, fuzzy msgid "Name for playlist" msgstr "Name für Schnappschuß" -#: audio_time_axis.cc:837 audio_time_axis.cc:1853 editor_markers.cc:826 -#: editor_mouse.cc:4609 imageframe_time_axis.cc:249 marker_time_axis.cc:207 -#: meter_bridge_strip.cc:223 mixer_strip.cc:1223 redirect_box.cc:749 -#: redirect_box.cc:1063 route_ui.cc:732 visual_time_axis.cc:325 +#: audio_time_axis.cc:835 audio_time_axis.cc:1851 editor_markers.cc:827 +#: editor_mouse.cc:4673 imageframe_time_axis.cc:248 marker_time_axis.cc:208 +#: meter_bridge_strip.cc:224 mixer_strip.cc:998 redirect_box.cc:751 +#: redirect_box.cc:1065 route_ui.cc:739 visual_time_axis.cc:326 msgid "Rename" msgstr "Umbenennen" -#: audio_time_axis.cc:870 audio_time_axis.cc:910 +#: audio_time_axis.cc:868 audio_time_axis.cc:908 #, fuzzy msgid "Name for Playlist" msgstr "Name für Schnappschuß" -#: audio_time_axis.cc:1128 visual_time_axis.cc:382 +#: audio_time_axis.cc:1126 visual_time_axis.cc:383 msgid "a track already exists with that name" msgstr "" -#: audio_time_axis.cc:1412 editor.cc:1490 selection.cc:622 +#: audio_time_axis.cc:1167 editor.cc:218 +msgid "gain" +msgstr "" + +#: audio_time_axis.cc:1207 +msgid "pan" +msgstr "" + +#: audio_time_axis.cc:1410 editor.cc:1483 selection.cc:634 msgid "programming error: " msgstr "" -#: audio_time_axis.cc:1850 +#: audio_time_axis.cc:1848 msgid "Current: %1" msgstr "" -#: audio_time_axis.cc:1857 +#: audio_time_axis.cc:1855 #, fuzzy msgid "New Copy" msgstr "Kopieren" -#: audio_time_axis.cc:1859 +#: audio_time_axis.cc:1857 msgid "Clear Current" msgstr "" -#: audio_time_axis.cc:1861 editor.cc:2031 editor.cc:2107 +#: audio_time_axis.cc:1859 editor.cc:2024 editor.cc:2100 msgid "Select" msgstr "Auswahl" -#: automation_line.cc:883 +#: automation_line.cc:884 #, fuzzy msgid "automation event move" msgstr "Stellen" -#: automation_line.cc:885 +#: automation_line.cc:886 #, fuzzy msgid "automation range drag" msgstr "Stellen" -#: automation_line.cc:1014 region_gain_line.cc:61 +#: automation_line.cc:1015 region_gain_line.cc:62 #, fuzzy msgid "remove control point" msgstr "Synchronisationspunkt entfernen" -#: automation_time_axis.cc:32 editor_ops.cc:2813 +#: automation_time_axis.cc:33 editor_ops.cc:2885 msgid "clear" msgstr "leeren" -#: automation_time_axis.cc:74 +#: automation_time_axis.cc:75 msgid "track height" msgstr "" -#: automation_time_axis.cc:75 +#: automation_time_axis.cc:76 #, fuzzy msgid "automation state" msgstr "Stellen" -#: automation_time_axis.cc:76 +#: automation_time_axis.cc:77 #, fuzzy msgid "clear track" msgstr "Verbindungen löschen" -#: automation_time_axis.cc:77 +#: automation_time_axis.cc:78 #, fuzzy msgid "hide track" msgstr "Stille einfügen" -#: automation_time_axis.cc:185 automation_time_axis.cc:223 -#: automation_time_axis.cc:463 mixer_strip.cc:176 mixer_strip.cc:188 -#: plugin_ui.cc:394 plugin_ui.cc:636 region_editor.cc:53 -msgid "play" +#: automation_time_axis.cc:184 automation_time_axis.cc:213 +#: automation_time_axis.cc:461 +msgid "Manual" msgstr "" -#: automation_time_axis.cc:187 automation_time_axis.cc:234 -#: automation_time_axis.cc:467 mixer_strip.cc:178 mixer_strip.cc:190 -#: plugin_ui.cc:397 plugin_ui.cc:638 -msgid "write" +#: automation_time_axis.cc:186 automation_time_axis.cc:224 +#: automation_time_axis.cc:465 editor.cc:2001 editor.cc:2082 gain_meter.cc:174 +#: panner_ui.cc:91 plugin_ui.cc:395 plugin_ui.cc:637 sfdb_ui.cc:56 +msgid "Play" +msgstr "Wiedergabe" + +#: automation_time_axis.cc:188 automation_time_axis.cc:235 +#: automation_time_axis.cc:469 gain_meter.cc:176 panner_ui.cc:93 +#: plugin_ui.cc:398 plugin_ui.cc:639 +msgid "Write" msgstr "" -#: automation_time_axis.cc:189 automation_time_axis.cc:245 -#: automation_time_axis.cc:471 mixer_strip.cc:180 mixer_strip.cc:192 -#: mixer_strip.cc:887 plugin_ui.cc:400 plugin_ui.cc:640 -msgid "touch" +#: automation_time_axis.cc:190 automation_time_axis.cc:246 +#: automation_time_axis.cc:473 gain_meter.cc:178 panner_ui.cc:95 +#: plugin_ui.cc:401 plugin_ui.cc:641 +msgid "Touch" msgstr "" -#: automation_time_axis.cc:256 option_editor.cc:182 option_editor.cc:188 -#: plugin_ui.cc:403 +#: automation_time_axis.cc:257 option_editor.cc:183 option_editor.cc:189 +#: plugin_ui.cc:404 msgid "???" msgstr "" -#: automation_time_axis.cc:270 +#: automation_time_axis.cc:271 #, fuzzy msgid "clear automation" msgstr "Verbindungen löschen" -#: automation_time_axis.cc:450 editor_actions.cc:317 +#: automation_time_axis.cc:452 editor_actions.cc:318 msgid "Hide" msgstr "Verbergen" -#: automation_time_axis.cc:452 crossfade_edit.cc:76 redirect_box.cc:1055 +#: automation_time_axis.cc:454 crossfade_edit.cc:78 redirect_box.cc:1057 msgid "Clear" msgstr "leeren" -#: automation_time_axis.cc:475 +#: automation_time_axis.cc:477 #, fuzzy msgid "State" msgstr "Anfang" @@ -1822,1596 +1820,1583 @@ msgstr "" msgid "color of fill" msgstr "" -#: color_manager.cc:39 +#: color_manager.cc:40 #, fuzzy msgid "Object" msgstr "Objekt" -#: color_manager.cc:77 +#: color_manager.cc:78 msgid "cannot open color definition file %1: %2" msgstr "" -#: crossfade_edit.cc:73 +#: crossfade_edit.cc:75 #, fuzzy msgid "ardour: x-fade edit" msgstr "Ardour: Editor" -#: crossfade_edit.cc:77 panner_ui.cc:401 +#: crossfade_edit.cc:79 panner_ui.cc:443 #, fuzzy msgid "Reset" msgstr "bestmöglich" -#: crossfade_edit.cc:78 +#: crossfade_edit.cc:80 msgid "Fade" msgstr "" -#: crossfade_edit.cc:79 +#: crossfade_edit.cc:81 msgid "Out (dry)" msgstr "" -#: crossfade_edit.cc:80 +#: crossfade_edit.cc:82 #, fuzzy msgid "Out" msgstr "Ausgänge" -#: crossfade_edit.cc:81 +#: crossfade_edit.cc:83 msgid "In (dry)" msgstr "" -#: crossfade_edit.cc:82 +#: crossfade_edit.cc:84 msgid "In" msgstr "" -#: crossfade_edit.cc:84 +#: crossfade_edit.cc:86 msgid "With Pre-roll" msgstr "" -#: crossfade_edit.cc:85 +#: crossfade_edit.cc:87 msgid "With Post-roll" msgstr "" -#: crossfade_edit.cc:93 +#: crossfade_edit.cc:95 msgid "Fade In" msgstr "" -#: crossfade_edit.cc:94 +#: crossfade_edit.cc:96 msgid "Fade Out" msgstr "" -#: crossfade_edit.cc:170 editor.cc:1842 editor_actions.cc:315 -#: option_editor.cc:129 +#: crossfade_edit.cc:172 editor.cc:1835 editor_actions.cc:316 +#: option_editor.cc:130 msgid "Audition" msgstr "" -#: editor.cc:101 editor.cc:3588 +#: editor.cc:104 editor.cc:3616 msgid "Slide" msgstr "" -#: editor.cc:102 editor.cc:3586 +#: editor.cc:105 editor.cc:3614 msgid "Splice" msgstr "" -#: editor.cc:107 editor.cc:3643 export_dialog.cc:78 export_dialog.cc:92 -#: export_dialog.cc:893 export_dialog.cc:1225 +#. note that this menu list starts at zero, not 1, because zero +#. is a valid, if useless, ID. +#. +#. leave some breathing room +#: editor.cc:110 editor.cc:3671 export_dialog.cc:78 export_dialog.cc:92 +#: export_dialog.cc:893 export_dialog.cc:1225 route_ui.cc:437 msgid "None" msgstr "Nichts" -#: editor.cc:108 editor.cc:3631 +#: editor.cc:111 editor.cc:3659 msgid "CD Frames" msgstr "" -#: editor.cc:109 editor.cc:3633 +#: editor.cc:112 editor.cc:3661 msgid "SMPTE Frames" msgstr "" -#: editor.cc:110 editor.cc:3635 +#: editor.cc:113 editor.cc:3663 msgid "SMPTE Seconds" msgstr "" -#: editor.cc:111 editor.cc:3637 +#: editor.cc:114 editor.cc:3665 msgid "SMPTE Minutes" msgstr "" -#: editor.cc:112 editor.cc:3639 +#: editor.cc:115 editor.cc:3667 #, fuzzy msgid "Seconds" msgstr "Minuten:Sekunden" -#: editor.cc:113 editor.cc:3641 +#: editor.cc:116 editor.cc:3669 #, fuzzy msgid "Minutes" msgstr "mute" -#: editor.cc:114 editor.cc:3613 +#: editor.cc:117 editor.cc:3641 msgid "Beats/32" msgstr "" -#: editor.cc:115 editor.cc:3611 +#: editor.cc:118 editor.cc:3639 msgid "Beats/16" msgstr "" -#: editor.cc:116 editor.cc:3609 +#: editor.cc:119 editor.cc:3637 msgid "Beats/8" msgstr "" -#: editor.cc:117 editor.cc:3607 +#: editor.cc:120 editor.cc:3635 msgid "Beats/4" msgstr "" -#: editor.cc:118 editor.cc:3605 +#: editor.cc:121 editor.cc:3633 msgid "Beats/3" msgstr "" -#: editor.cc:119 editor.cc:3615 +#: editor.cc:122 editor.cc:3643 msgid "Beats" msgstr "" -#: editor.cc:120 editor.cc:3617 +#: editor.cc:123 editor.cc:3645 msgid "Bars" msgstr "" -#: editor.cc:121 editor.cc:3619 +#: editor.cc:124 editor.cc:3647 msgid "Marks" msgstr "" -#: editor.cc:122 editor.cc:141 editor.cc:3621 editor.cc:3687 +#: editor.cc:125 editor.cc:144 editor.cc:3649 editor.cc:3715 msgid "Edit Cursor" msgstr "" -#: editor.cc:123 editor.cc:3623 +#: editor.cc:126 editor.cc:3651 #, fuzzy msgid "Region starts" msgstr "Regionen" -#: editor.cc:124 editor.cc:3625 +#: editor.cc:127 editor.cc:3653 #, fuzzy msgid "Region ends" msgstr "Regionen" -#: editor.cc:125 editor.cc:3629 +#: editor.cc:128 editor.cc:3657 #, fuzzy msgid "Region syncs" msgstr "Regionen" -#: editor.cc:126 editor.cc:3627 +#: editor.cc:129 editor.cc:3655 #, fuzzy msgid "Region bounds" msgstr "Regionen" -#: editor.cc:132 editor.cc:3662 +#: editor.cc:135 editor.cc:3690 #, fuzzy msgid "Magnetic" msgstr "generisch" -#: editor.cc:137 editor.cc:3679 export_dialog.cc:140 export_dialog.cc:156 +#: editor.cc:140 editor.cc:3707 export_dialog.cc:140 export_dialog.cc:156 #: export_dialog.cc:1068 export_dialog.cc:1072 msgid "Left" msgstr "Links" -#: editor.cc:138 editor.cc:3681 export_dialog.cc:141 export_dialog.cc:157 +#: editor.cc:141 editor.cc:3709 export_dialog.cc:141 export_dialog.cc:157 msgid "Right" msgstr "Rechts" -#: editor.cc:139 editor.cc:3683 +#: editor.cc:142 editor.cc:3711 msgid "Center" msgstr "Mitte" -#: editor.cc:140 editor.cc:3685 +#: editor.cc:143 editor.cc:3713 msgid "Playhead" msgstr "" #. time display buttons -#: editor.cc:183 +#: editor.cc:186 msgid "Mins:Secs" msgstr "Min:Sek" -#: editor.cc:186 editor_rulers.cc:353 +#: editor.cc:189 editor_rulers.cc:354 msgid "Frames" msgstr "" -#: editor.cc:187 editor_rulers.cc:373 +#: editor.cc:190 editor_rulers.cc:374 msgid "Tempo" msgstr "" -#: editor.cc:188 editor_rulers.cc:367 +#: editor.cc:191 editor_rulers.cc:368 msgid "Meter" msgstr "" -#: editor.cc:189 editor_rulers.cc:379 +#: editor.cc:192 editor_rulers.cc:380 #, fuzzy msgid "Location Markers" msgstr "Stellen" -#: editor.cc:190 editor_rulers.cc:385 +#: editor.cc:193 editor_rulers.cc:386 msgid "Range Markers" msgstr "" -#: editor.cc:191 editor_rulers.cc:391 +#: editor.cc:194 editor_rulers.cc:392 msgid "Loop/Punch Ranges" msgstr "" -#: editor.cc:213 +#: editor.cc:216 msgid "range" msgstr "Bereich" -#: editor.cc:214 +#: editor.cc:217 msgid "object" msgstr "Objekt" -#: editor.cc:216 +#: editor.cc:219 msgid "zoom" msgstr "" -#: editor.cc:217 +#: editor.cc:220 msgid "timefx" msgstr "" -#: editor.cc:218 +#: editor.cc:221 msgid "listen" msgstr "" -#: editor.cc:220 +#: editor.cc:223 msgid "mode" msgstr "Modus" -#: editor.cc:221 +#: editor.cc:224 msgid "automation" msgstr "" -#: editor.cc:223 +#: editor.cc:226 msgid "Edit Mode" msgstr "Bearbeitungs Modus" -#: editor.cc:224 editor_actions.cc:283 +#: editor.cc:227 editor_actions.cc:284 msgid "Snap To" msgstr "" -#: editor.cc:225 +#: editor.cc:228 #, fuzzy msgid "Snap Mode" msgstr "Modus" -#: editor.cc:226 +#: editor.cc:229 #, fuzzy msgid "Zoom Focus" msgstr "Verkleinern" #. #. nudge -#: editor.cc:234 editor.cc:1907 editor.cc:2073 editor.cc:2129 +#: editor.cc:237 editor.cc:1900 editor.cc:2066 editor.cc:2122 msgid "Nudge" msgstr "" -#: editor.cc:466 +#: editor.cc:470 msgid "Zoom in" msgstr "Vergrößern" -#: editor.cc:467 +#: editor.cc:471 msgid "Zoom out" msgstr "Verkleinern" -#: editor.cc:470 +#: editor.cc:474 #, fuzzy msgid "Zoom to session" msgstr "Vergrößern auf Auswahl" -#: editor.cc:485 +#: editor.cc:489 #, fuzzy msgid "Zoom Span" msgstr "Vergrößern" -#: editor.cc:498 editor.cc:524 editor_actions.cc:61 mixer_ui.cc:85 +#: editor.cc:502 editor.cc:528 editor_actions.cc:62 mixer_ui.cc:86 +#: mixer_ui.cc:112 msgid "Visible" msgstr "" -#: editor.cc:499 editor.cc:522 +#: editor.cc:503 editor.cc:526 #, fuzzy msgid "Name" msgstr "Umbenennen" -#: editor.cc:595 editor.cc:661 +#: editor.cc:602 editor.cc:669 #, fuzzy msgid "Regions" msgstr "Regionen" -#: editor.cc:634 editor.cc:673 +#: editor.cc:642 editor.cc:681 msgid "Chunks" msgstr "Stücke" -#: editor.cc:664 +#: editor.cc:672 #, fuzzy msgid "Tracks/Busses" msgstr "MIDI Spur(en) hinzufügen" -#: editor.cc:667 +#: editor.cc:675 msgid "Snapshots" msgstr "Schnapschüsse" -#: editor.cc:670 +#: editor.cc:678 msgid "Edit Groups" msgstr "" -#: editor.cc:719 +#: editor.cc:727 msgid "Nudge region/selection forwards" msgstr "" -#: editor.cc:720 +#: editor.cc:728 msgid "Nudge region/selection backwards" msgstr "" -#: editor.cc:727 editor_mixer.cc:298 +#: editor.cc:735 editor_mixer.cc:299 msgid "ardour: editor" msgstr "Ardour: Editor" -#: editor.cc:728 +#: editor.cc:736 #, fuzzy msgid "ardour_editor" msgstr "Ardour: Editor" -#: editor.cc:1190 +#: editor.cc:1183 msgid "ardour: editor: " msgstr "Ardour: Editor: " #. force name -#: editor.cc:1275 editor.cc:1284 editor_markers.cc:869 +#: editor.cc:1268 editor.cc:1277 editor_markers.cc:870 msgid "Loop" msgstr "Schleife" #. force name -#: editor.cc:1289 editor.cc:1298 editor_markers.cc:895 +#: editor.cc:1282 editor.cc:1291 editor_markers.cc:896 msgid "Punch" msgstr "" -#: editor.cc:1446 editor_mouse.cc:1721 +#: editor.cc:1439 editor_mouse.cc:1742 msgid "programming error: fade in canvas item has no regionview data pointer!" msgstr "" -#: editor.cc:1458 editor.cc:1475 redirect_box.cc:1071 +#: editor.cc:1451 editor.cc:1468 redirect_box.cc:1073 #, fuzzy msgid "Deactivate" msgstr "Alles deaktivieren" #. activation -#: editor.cc:1460 editor.cc:1477 redirect_box.cc:1069 +#: editor.cc:1453 editor.cc:1470 redirect_box.cc:1071 #, fuzzy msgid "Activate" msgstr "Aktiv" -#: editor.cc:1465 editor.cc:1482 +#: editor.cc:1458 editor.cc:1475 msgid "Linear" msgstr "" -#: editor.cc:1466 editor.cc:1483 editor_actions.cc:375 +#: editor.cc:1459 editor.cc:1476 editor_actions.cc:376 #, fuzzy msgid "Slowest" msgstr "Alle zeigen" -#: editor.cc:1467 editor.cc:1484 editor_actions.cc:376 +#: editor.cc:1460 editor.cc:1477 editor_actions.cc:377 #, fuzzy msgid "Slow" msgstr "solo" -#: editor.cc:1468 editor.cc:1485 editor_actions.cc:378 +#: editor.cc:1461 editor.cc:1478 editor_actions.cc:379 #, fuzzy msgid "Fast" msgstr "Einfügen" -#: editor.cc:1469 editor.cc:1486 editor_actions.cc:380 +#: editor.cc:1462 editor.cc:1479 editor_actions.cc:381 #, fuzzy msgid "Fastest" msgstr "schnellstmöglich" -#: editor.cc:1596 editor.cc:1604 +#: editor.cc:1589 editor.cc:1597 msgid "Freeze" msgstr "" -#: editor.cc:1600 +#: editor.cc:1593 msgid "Unfreeze" msgstr "" -#: editor.cc:1769 editor.cc:1864 +#: editor.cc:1762 editor.cc:1857 #, fuzzy msgid "Unmute" msgstr "mute" #. non-operative menu items for menu bar #. show editors -#: editor.cc:1773 editor.cc:2053 editor.cc:2755 editor_actions.cc:26 -#: editor_markers.cc:506 mixer_strip.cc:512 mixer_strip.cc:572 -#: redirect_box.cc:1077 +#: editor.cc:1766 editor.cc:2046 editor.cc:2748 editor_actions.cc:27 +#: editor_markers.cc:507 mixer_strip.cc:495 mixer_strip.cc:563 +#: redirect_box.cc:1079 msgid "Edit" msgstr "Bearbeiten" -#: editor.cc:1778 +#: editor.cc:1771 msgid "Convert to short" msgstr "" -#: editor.cc:1780 +#: editor.cc:1773 msgid "Convert to full" msgstr "" -#: editor.cc:1791 +#: editor.cc:1784 #, fuzzy msgid "Crossfade" msgstr "Ardour: Editor" -#: editor.cc:1834 +#: editor.cc:1827 msgid "Popup region editor" msgstr "Regionen Editor öffnen" -#: editor.cc:1835 +#: editor.cc:1828 #, fuzzy msgid "Raise to top layer" msgstr "Region ganz nach oben" -#: editor.cc:1836 +#: editor.cc:1829 #, fuzzy msgid "Lower to bottom layer" msgstr "Region ganz nach unten" -#: editor.cc:1838 +#: editor.cc:1831 msgid "Define sync point" msgstr "Synchronisationspunkt definieren" -#: editor.cc:1839 +#: editor.cc:1832 msgid "Remove sync point" msgstr "Synchronisationspunkt entfernen" -#: editor.cc:1844 +#: editor.cc:1837 #, fuzzy msgid "Bounce" msgstr "Bereich" -#: editor.cc:1847 +#: editor.cc:1840 #, fuzzy msgid "Analyze region" msgstr "Wiedergabe der Region" -#: editor.cc:1859 +#: editor.cc:1852 #, fuzzy msgid "Lock" msgstr "OK" -#: editor.cc:1860 +#: editor.cc:1853 #, fuzzy msgid "Unlock" msgstr "Rückgängig" -#: editor.cc:1870 +#: editor.cc:1863 #, fuzzy msgid "Original position" msgstr "Regionen" -#: editor.cc:1876 +#: editor.cc:1869 msgid "Toggle envelope visibility" msgstr "" -#: editor.cc:1877 +#: editor.cc:1870 msgid "Toggle envelope active" msgstr "" -#: editor.cc:1881 +#: editor.cc:1874 #, fuzzy msgid "DeNormalize" msgstr "Ardour: Region" -#: editor.cc:1883 +#: editor.cc:1876 #, fuzzy msgid "Normalize" msgstr "Ardour: Region" -#: editor.cc:1886 +#: editor.cc:1879 #, fuzzy msgid "Reverse" msgstr "Entfernen" #. range related stuff -#: editor.cc:1892 +#: editor.cc:1885 #, fuzzy msgid "Add Range Markers" msgstr "Ardour: Region umbenennen" -#: editor.cc:1893 +#: editor.cc:1886 #, fuzzy msgid "Set Range" msgstr "Ausgewählten Bereich wiedergeben" -#: editor.cc:1902 +#: editor.cc:1895 msgid "Nudge fwd" msgstr "" -#: editor.cc:1903 +#: editor.cc:1896 msgid "Nudge bwd" msgstr "" -#: editor.cc:1904 +#: editor.cc:1897 msgid "Nudge fwd by capture offset" msgstr "" -#: editor.cc:1905 +#: editor.cc:1898 msgid "Nudge bwd by capture offset" msgstr "" -#: editor.cc:1914 +#: editor.cc:1907 msgid "Start to edit cursor" msgstr "" -#: editor.cc:1915 +#: editor.cc:1908 msgid "Edit cursor to end" msgstr "" -#: editor.cc:1917 +#: editor.cc:1910 gain_meter.cc:181 gain_meter.cc:813 panner_ui.cc:98 +#: panner_ui.cc:803 msgid "Trim" msgstr "" -#: editor.cc:1920 +#: editor.cc:1913 msgid "Split" msgstr "Teilen" -#: editor.cc:1923 +#: editor.cc:1916 #, fuzzy msgid "Make mono regions" msgstr "Name für Region:" -#: editor.cc:1926 +#: editor.cc:1919 msgid "Duplicate" msgstr "Duplizieren" -#: editor.cc:1927 +#: editor.cc:1920 #, fuzzy msgid "Fill Track" msgstr "Spur" -#: editor.cc:1931 +#: editor.cc:1924 msgid "Destroy" msgstr "" -#: editor.cc:1961 +#: editor.cc:1954 #, fuzzy msgid "Play range" msgstr "Bereich" -#: editor.cc:1962 +#: editor.cc:1955 #, fuzzy msgid "Loop range" msgstr "Bereich" -#: editor.cc:1966 +#: editor.cc:1959 #, fuzzy msgid "Analyze range" msgstr "Bereich" -#: editor.cc:1970 +#: editor.cc:1963 #, fuzzy msgid "Separate range to track" msgstr "Ausgewählten Bereich wiedergeben" -#: editor.cc:1971 +#: editor.cc:1964 #, fuzzy msgid "Separate range to region list" msgstr "Auswahl zu Schleife machen" -#: editor.cc:1974 +#: editor.cc:1967 #, fuzzy msgid "Select all in range" msgstr "Auswahl" -#: editor.cc:1976 editor.cc:2021 +#: editor.cc:1969 editor.cc:2014 #, fuzzy msgid "Set range to loop range" msgstr "Ausgewählten Bereich wiedergeben" -#: editor.cc:1977 editor.cc:2022 +#: editor.cc:1970 editor.cc:2015 #, fuzzy msgid "Set range to punch range" msgstr "Ausgewählten Bereich wiedergeben" -#: editor.cc:1979 +#: editor.cc:1972 #, fuzzy msgid "Crop region to range" msgstr "Regionen Editor öffnen" -#: editor.cc:1980 +#: editor.cc:1973 #, fuzzy msgid "Fill range with region" msgstr "Region erstellen" -#: editor.cc:1981 +#: editor.cc:1974 #, fuzzy msgid "Duplicate range" msgstr "Duplizieren" -#: editor.cc:1982 +#: editor.cc:1975 #, fuzzy msgid "Create chunk from range" msgstr "Auswahl zu Abschnitt machen" -#: editor.cc:1984 +#: editor.cc:1977 #, fuzzy msgid "Bounce range" msgstr "Bereich" -#: editor.cc:1985 +#: editor.cc:1978 #, fuzzy msgid "Export range" msgstr "Name für Region:" -#: editor.cc:1987 +#: editor.cc:1980 #, fuzzy msgid "Range" msgstr "Bereich" -#: editor.cc:2002 editor.cc:2087 +#: editor.cc:1995 editor.cc:2080 #, fuzzy msgid "Play from edit cursor" msgstr "Wiedergabe ab Cursor" -#: editor.cc:2003 editor.cc:2088 +#: editor.cc:1996 editor.cc:2081 msgid "Play from start" msgstr "Wiedergabe ab Anfang" -#: editor.cc:2004 +#: editor.cc:1997 #, fuzzy msgid "Play region" msgstr "Wiedergabe der Region" -#: editor.cc:2006 +#: editor.cc:1999 #, fuzzy msgid "Loop Region" msgstr "Auswahl zu Schleife machen" -#: editor.cc:2008 editor.cc:2089 sfdb_ui.cc:56 -msgid "Play" -msgstr "Wiedergabe" - -#: editor.cc:2016 editor.cc:2097 +#: editor.cc:2009 editor.cc:2090 #, fuzzy msgid "Select All in track" msgstr "Auswahl" -#: editor.cc:2017 editor.cc:2098 redirect_box.cc:1065 +#: editor.cc:2010 editor.cc:2091 redirect_box.cc:1067 #, fuzzy msgid "Select All" msgstr "Auswahl" -#: editor.cc:2018 editor.cc:2099 +#: editor.cc:2011 editor.cc:2092 #, fuzzy msgid "Invert selection in track" msgstr "Stille einfügen" -#: editor.cc:2019 editor.cc:2100 +#: editor.cc:2012 editor.cc:2093 #, fuzzy msgid "Invert selection" msgstr "Auswahl zu Schleife machen" -#: editor.cc:2024 editor.cc:2102 +#: editor.cc:2017 editor.cc:2095 #, fuzzy msgid "Select all after edit cursor" msgstr "Wiedergabe ab Cursor" -#: editor.cc:2025 editor.cc:2103 +#: editor.cc:2018 editor.cc:2096 #, fuzzy msgid "Select all before edit cursor" msgstr "Wiedergabe ab Cursor" -#: editor.cc:2026 editor.cc:2104 +#: editor.cc:2019 editor.cc:2097 #, fuzzy msgid "Select all after playhead" msgstr "Wiedergabe ab Playhead" -#: editor.cc:2027 editor.cc:2105 +#: editor.cc:2020 editor.cc:2098 #, fuzzy msgid "Select all before playhead" msgstr "Wiedergabe ab Playhead" -#: editor.cc:2028 +#: editor.cc:2021 #, fuzzy msgid "Select all between cursors" msgstr "Wiedergabe ab Cursor" #. standard editing stuff -#: editor.cc:2039 editor.cc:2115 editor.cc:3455 editor_actions.cc:213 -#: redirect_box.cc:1058 +#: editor.cc:2032 editor.cc:2108 editor.cc:3483 editor_actions.cc:214 +#: redirect_box.cc:1060 msgid "Cut" msgstr "Ausschneiden" -#: editor.cc:2040 editor.cc:2116 editor.cc:3457 editor_actions.cc:218 -#: redirect_box.cc:1060 +#: editor.cc:2033 editor.cc:2109 editor.cc:3485 editor_actions.cc:219 +#: redirect_box.cc:1062 msgid "Copy" msgstr "Kopieren" -#: editor.cc:2041 +#: editor.cc:2034 #, fuzzy msgid "Paste at edit cursor" msgstr "Wiedergabe ab Cursor" -#: editor.cc:2042 +#: editor.cc:2035 msgid "Paste at mouse" msgstr "" -#: editor.cc:2046 editor.cc:3462 +#: editor.cc:2039 editor.cc:3490 msgid "Align" msgstr "" -#: editor.cc:2047 editor.cc:3464 +#: editor.cc:2040 editor.cc:3492 msgid "Align Relative" msgstr "" -#: editor.cc:2051 +#: editor.cc:2044 msgid "Insert chunk" msgstr "Abschnitt einfügen" -#: editor.cc:2058 +#: editor.cc:2051 #, fuzzy msgid "Insert Selected Region" msgstr "Auswahl zu Schleife machen" -#: editor.cc:2059 +#: editor.cc:2052 msgid "Insert Existing Audio" msgstr "" -#: editor.cc:2068 editor.cc:2124 +#: editor.cc:2061 editor.cc:2117 msgid "Nudge entire track fwd" msgstr "" -#: editor.cc:2069 editor.cc:2125 +#: editor.cc:2062 editor.cc:2118 msgid "Nudge track after edit cursor fwd" msgstr "" -#: editor.cc:2070 editor.cc:2126 +#: editor.cc:2063 editor.cc:2119 msgid "Nudge entire track bwd" msgstr "" -#: editor.cc:2071 editor.cc:2127 +#: editor.cc:2064 editor.cc:2120 msgid "Nudge track after edit cursor bwd" msgstr "" -#: editor.cc:2117 editor.cc:3459 editor_actions.cc:220 redirect_box.cc:1062 +#: editor.cc:2110 editor.cc:3487 editor_actions.cc:221 redirect_box.cc:1064 msgid "Paste" msgstr "Einfügen" -#: editor.cc:2637 +#: editor.cc:2630 msgid "select/move objects" msgstr "" -#: editor.cc:2638 +#: editor.cc:2631 #, fuzzy msgid "select/move ranges" msgstr "Ausgewählten Bereich wiedergeben" -#: editor.cc:2639 +#: editor.cc:2632 msgid "draw gain automation" msgstr "" -#: editor.cc:2640 +#: editor.cc:2633 #, fuzzy msgid "select zoom range" msgstr "Ausgewählten Bereich wiedergeben" -#: editor.cc:2641 +#: editor.cc:2634 msgid "stretch/shrink regions" msgstr "" -#: editor.cc:2642 +#: editor.cc:2635 #, fuzzy msgid "listen to specific regions" msgstr "Auswahl zu Schleife machen" -#: editor.cc:2753 +#: editor.cc:2746 msgid "Start:" msgstr "Anfang:" -#: editor.cc:2754 +#: editor.cc:2747 msgid "End:" msgstr "Ende:" -#: editor.cc:3097 -#, fuzzy -msgid "set selected trackview" -msgstr "Stille einfügen" - -#: editor.cc:3137 -#, fuzzy -msgid "set selected control point" -msgstr "Synchronisationspunkt entfernen" - -#: editor.cc:3246 -#, fuzzy -msgid "set selected regionview" -msgstr "Auswahl zu Schleife machen" - -#: editor.cc:3334 editor.cc:3374 +#: editor.cc:3362 editor.cc:3402 #, fuzzy msgid "set selected regions" msgstr "Auswahl zu Schleife machen" -#: editor.cc:3430 editor_actions.cc:203 +#: editor.cc:3458 editor_actions.cc:204 msgid "Undo" msgstr "Rückgängig" -#: editor.cc:3432 +#: editor.cc:3460 msgid "Undo (%1)" msgstr "Rückgängig (%1)" -#: editor.cc:3442 editor_actions.cc:205 +#: editor.cc:3470 editor_actions.cc:206 msgid "Redo" msgstr "Wiederherstellen" -#: editor.cc:3444 +#: editor.cc:3472 msgid "Redo (%1)" msgstr "Wiederherstellen (%1)" -#: editor.cc:3478 +#: editor.cc:3506 msgid "... as new track" msgstr "" -#: editor.cc:3479 +#: editor.cc:3507 #, fuzzy msgid "... as new region" msgstr "Ardour: Region" -#: editor.cc:3481 +#: editor.cc:3509 #, fuzzy msgid "Import audio (copy)" msgstr "Audio Importieren" -#: editor.cc:3484 +#: editor.cc:3512 #, fuzzy msgid "Remove last capture" msgstr "Synchronisationspunkt entfernen" -#: editor.cc:3508 +#: editor.cc:3536 msgid "Duplicate how many times?" msgstr "Wie häufig duplizieren?" -#: editor.cc:3994 +#: editor.cc:4022 msgid "" "Playlist %1 is currently unused.\n" "If left alone, no audio files used by it will be cleaned.\n" "If deleted, audio files used by it alone by will cleaned." msgstr "" -#: editor.cc:4002 +#: editor.cc:4030 #, fuzzy msgid "Delete playlist" msgstr "Name für Schnappschuß" -#: editor.cc:4003 +#: editor.cc:4031 #, fuzzy msgid "Keep playlist" msgstr "Name für Schnappschuß" -#: editor.cc:4004 editor_audio_import.cc:237 editor_ops.cc:1976 -#: editor_timefx.cc:52 export_dialog.cc:971 io_selector.cc:58 -#: io_selector.cc:792 redirect_box.cc:901 tempo_dialog.cc:19 -#: tempo_dialog.cc:36 tempo_dialog.cc:152 tempo_dialog.cc:170 +#: editor.cc:4032 editor_audio_import.cc:236 editor_ops.cc:2048 +#: editor_timefx.cc:71 export_dialog.cc:971 io_selector.cc:59 +#: io_selector.cc:793 redirect_box.cc:903 tempo_dialog.cc:20 +#: tempo_dialog.cc:37 tempo_dialog.cc:202 tempo_dialog.cc:220 msgid "Cancel" msgstr "Abbrechen" -#: editor.cc:4171 +#: editor.cc:4199 #, fuzzy msgid "new playlists" msgstr "Name für Schnappschuß" -#: editor.cc:4179 +#: editor.cc:4207 #, fuzzy msgid "copy playlists" msgstr "Name für Schnappschuß" -#: editor.cc:4187 +#: editor.cc:4215 #, fuzzy msgid "clear playlists" msgstr "Name für Schnappschuß" -#: editor_actions.cc:27 +#: editor_actions.cc:28 #, fuzzy msgid "Select regions" msgstr "Auswahl zu Schleife machen" -#: editor_actions.cc:28 +#: editor_actions.cc:29 #, fuzzy msgid "Select range operations" msgstr "Auswahl zu Schleife machen" -#: editor_actions.cc:29 +#: editor_actions.cc:30 #, fuzzy msgid "Move edit cursor" msgstr "Wiedergabe ab Cursor" -#: editor_actions.cc:30 +#: editor_actions.cc:31 #, fuzzy msgid "Region operations" msgstr "Regionen" -#: editor_actions.cc:31 +#: editor_actions.cc:32 msgid "Tools" msgstr "" -#: editor_actions.cc:32 +#: editor_actions.cc:33 msgid "View" msgstr "" -#: editor_actions.cc:33 +#: editor_actions.cc:34 #, fuzzy msgid "ZoomFocus" msgstr "Verkleinern" -#: editor_actions.cc:34 +#: editor_actions.cc:35 msgid "Meter hold" msgstr "" -#: editor_actions.cc:35 +#: editor_actions.cc:36 msgid "Meter falloff" msgstr "" -#: editor_actions.cc:37 +#: editor_actions.cc:38 #, fuzzy msgid "Crossfades" msgstr "Ardour: Editor" -#: editor_actions.cc:38 +#: editor_actions.cc:39 msgid "Monitoring" msgstr "" -#: editor_actions.cc:39 +#: editor_actions.cc:40 #, fuzzy msgid "Autoconnect" msgstr "Verbindungen" -#: editor_actions.cc:40 +#: editor_actions.cc:41 #, fuzzy msgid "Layering" msgstr "Schicht" -#: editor_actions.cc:41 +#: editor_actions.cc:42 #, fuzzy msgid "Metering" msgstr "Schicht" -#: editor_actions.cc:42 +#: editor_actions.cc:43 msgid "Fall off rate" msgstr "" -#: editor_actions.cc:43 +#: editor_actions.cc:44 msgid "Hold Time" msgstr "" -#: editor_actions.cc:44 +#: editor_actions.cc:45 msgid "Add Existing Audio" msgstr "" #. add named actions for the editor -#: editor_actions.cc:49 +#: editor_actions.cc:50 #, fuzzy msgid "Show Editor Mixer" msgstr "Ardour: Mixer" -#: editor_actions.cc:54 +#: editor_actions.cc:55 #, fuzzy msgid "Span Entire Overlap" msgstr "Region eine Ebene nach oben" -#: editor_actions.cc:56 editor_actions.cc:383 +#: editor_actions.cc:57 editor_actions.cc:384 #, fuzzy msgid "Short" msgstr "Anschluß" -#: editor_actions.cc:63 +#: editor_actions.cc:64 msgid "Created Automatically" msgstr "" -#: editor_actions.cc:66 +#: editor_actions.cc:67 msgid "Playhead to Next Region Start" msgstr "" -#: editor_actions.cc:68 +#: editor_actions.cc:69 msgid "Playhead to Next Region End" msgstr "" -#: editor_actions.cc:70 +#: editor_actions.cc:71 msgid "Playhead to Next Region Sync" msgstr "" -#: editor_actions.cc:73 +#: editor_actions.cc:74 msgid "Playhead to Previous Region Start" msgstr "" -#: editor_actions.cc:75 +#: editor_actions.cc:76 msgid "Playhead to Previous Region End" msgstr "" -#: editor_actions.cc:77 +#: editor_actions.cc:78 msgid "Playhead to Previous Region Sync" msgstr "" -#: editor_actions.cc:80 +#: editor_actions.cc:81 msgid "Edit Cursor to Next Region Start" msgstr "" -#: editor_actions.cc:82 +#: editor_actions.cc:83 msgid "Edit Cursor to Next Region End" msgstr "" -#: editor_actions.cc:84 +#: editor_actions.cc:85 msgid "Edit Cursor to Next Region Sync" msgstr "" -#: editor_actions.cc:87 +#: editor_actions.cc:88 msgid "Edit Cursor to Previous Region Start" msgstr "" -#: editor_actions.cc:89 +#: editor_actions.cc:90 msgid "Edit Cursor to Previous Region End" msgstr "" -#: editor_actions.cc:91 +#: editor_actions.cc:92 msgid "Edit Cursor to Previous Region Sync" msgstr "" -#: editor_actions.cc:94 +#: editor_actions.cc:95 msgid "Playhead to Range Start" msgstr "" -#: editor_actions.cc:96 +#: editor_actions.cc:97 #, fuzzy msgid "Playhead to Range End" msgstr "Bereich" -#: editor_actions.cc:99 +#: editor_actions.cc:100 msgid "Edit Cursor to Range Start" msgstr "" -#: editor_actions.cc:101 +#: editor_actions.cc:102 msgid "Edit Cursor to Range End" msgstr "" -#: editor_actions.cc:104 editor_ops.cc:1300 +#: editor_actions.cc:105 editor_ops.cc:1363 #, fuzzy msgid "select all" msgstr "Auswahl" -#: editor_actions.cc:106 +#: editor_actions.cc:107 #, fuzzy msgid "Select All After Edit Cursor" msgstr "Wiedergabe ab Cursor" -#: editor_actions.cc:108 +#: editor_actions.cc:109 msgid "Select All Before Edit Cursor" msgstr "" -#: editor_actions.cc:111 +#: editor_actions.cc:112 #, fuzzy msgid "Select All After Playhead" msgstr "Wiedergabe ab Playhead" -#: editor_actions.cc:113 +#: editor_actions.cc:114 #, fuzzy msgid "Select All Before Playhead" msgstr "Wiedergabe ab Playhead" -#: editor_actions.cc:115 +#: editor_actions.cc:116 #, fuzzy msgid "Select All Between Cursors" msgstr "Wiedergabe ab Cursor" -#: editor_actions.cc:118 +#: editor_actions.cc:119 #, fuzzy msgid "Select All in Punch Range" msgstr "Ausgewählten Bereich wiedergeben" -#: editor_actions.cc:120 +#: editor_actions.cc:121 #, fuzzy msgid "Select All in Loop Range" msgstr "Ausgewählten Bereich wiedergeben" -#: editor_actions.cc:123 +#: editor_actions.cc:124 msgid "Jump Forward to Mark" msgstr "" -#: editor_actions.cc:125 +#: editor_actions.cc:126 msgid "Jump Backward to Mark" msgstr "" -#: editor_actions.cc:127 +#: editor_actions.cc:128 #, fuzzy msgid "Add Location from Playhead" msgstr "Wiedergabe ab Playhead" -#: editor_actions.cc:130 +#: editor_actions.cc:131 msgid "Nudge Forward" msgstr "" -#: editor_actions.cc:132 +#: editor_actions.cc:133 msgid "Nudge Next Forward" msgstr "" -#: editor_actions.cc:134 +#: editor_actions.cc:135 #, fuzzy msgid "Nudge Backward" msgstr "Stille einfügen" -#: editor_actions.cc:136 +#: editor_actions.cc:137 #, fuzzy msgid "Nudge Next Backward" msgstr "Stille einfügen" -#: editor_actions.cc:139 +#: editor_actions.cc:140 #, fuzzy msgid "Zoom Out" msgstr "Verkleinern" -#: editor_actions.cc:141 +#: editor_actions.cc:142 #, fuzzy msgid "Zoom In" msgstr "Vergrößern" -#: editor_actions.cc:143 +#: editor_actions.cc:144 #, fuzzy msgid "Zoom to Session" msgstr "Vergrößern auf Auswahl" -#: editor_actions.cc:146 +#: editor_actions.cc:147 #, fuzzy msgid "Scroll Tracks Up" msgstr "Spur" -#: editor_actions.cc:148 +#: editor_actions.cc:149 msgid "Scroll Tracks Down" msgstr "" -#: editor_actions.cc:150 +#: editor_actions.cc:151 #, fuzzy msgid "Step Tracks Up" msgstr "Stille einfügen" -#: editor_actions.cc:152 +#: editor_actions.cc:153 msgid "Step Tracks Down" msgstr "" -#: editor_actions.cc:155 +#: editor_actions.cc:156 msgid "Scroll Backward" msgstr "" -#: editor_actions.cc:157 +#: editor_actions.cc:158 msgid "Scroll Forward" msgstr "" -#: editor_actions.cc:159 +#: editor_actions.cc:160 msgid "goto" msgstr "" -#: editor_actions.cc:161 +#: editor_actions.cc:162 #, fuzzy msgid "Center Playhead" msgstr "Wiedergabe ab Playhead" -#: editor_actions.cc:163 +#: editor_actions.cc:164 #, fuzzy msgid "Center Edit Cursor" msgstr "Wiedergabe ab Cursor" -#: editor_actions.cc:165 +#: editor_actions.cc:166 msgid "Playhead Forward" msgstr "" -#: editor_actions.cc:167 +#: editor_actions.cc:168 msgid "Playhead Backward" msgstr "" -#: editor_actions.cc:169 +#: editor_actions.cc:170 msgid "Playhead to Edit" msgstr "" -#: editor_actions.cc:171 +#: editor_actions.cc:172 #, fuzzy msgid "Edit to Playhead" msgstr "Wiedergabe ab Playhead" -#: editor_actions.cc:174 +#: editor_actions.cc:175 #, fuzzy msgid "Align Regions Start" msgstr "Regionen" -#: editor_actions.cc:176 +#: editor_actions.cc:177 #, fuzzy msgid "Align Regions Start Relative" msgstr "nach Anfang der Region in der Datei" -#: editor_actions.cc:178 +#: editor_actions.cc:179 #, fuzzy msgid "Align Regions End" msgstr "Ardour: Region" -#: editor_actions.cc:180 +#: editor_actions.cc:181 msgid "Align Regions End Relative" msgstr "" -#: editor_actions.cc:183 +#: editor_actions.cc:184 #, fuzzy msgid "Align Regions Sync" msgstr "Ardour: Region" -#: editor_actions.cc:185 +#: editor_actions.cc:186 msgid "Align Regions Sync Relative" msgstr "" -#: editor_actions.cc:188 +#: editor_actions.cc:189 msgid "Audition at Mouse" msgstr "" -#: editor_actions.cc:190 +#: editor_actions.cc:191 msgid "Brush at Mouse" msgstr "" -#: editor_actions.cc:192 +#: editor_actions.cc:193 #, fuzzy msgid "Set Edit Cursor" msgstr "Wiedergabe ab Cursor" -#: editor_actions.cc:194 +#: editor_actions.cc:195 #, fuzzy msgid "Mute/Unmute Region" msgstr "Region erstellen" -#: editor_actions.cc:196 +#: editor_actions.cc:197 #, fuzzy msgid "Set Playhead" msgstr "Wiedergabe ab Playhead" -#: editor_actions.cc:198 +#: editor_actions.cc:199 #, fuzzy msgid "Split Region" msgstr "Auswahl zu Schleife machen" -#: editor_actions.cc:200 +#: editor_actions.cc:201 #, fuzzy msgid "Set Region Sync Position" msgstr "nach Zeitstempel der Region" -#: editor_actions.cc:208 +#: editor_actions.cc:209 #, fuzzy msgid "Export Session" msgstr "Name für Region:" -#: editor_actions.cc:210 +#: editor_actions.cc:211 #, fuzzy msgid "Export Range" msgstr "Ausgewählten Bereich wiedergeben" #. Note: for now, editor-delete does the exact same thing as editor-cut -#: editor_actions.cc:216 +#: editor_actions.cc:217 #, fuzzy msgid "Delete" msgstr "entfernen" -#: editor_actions.cc:222 +#: editor_actions.cc:223 #, fuzzy msgid "Duplicate Region" msgstr "Auswahl zu Schleife machen" -#: editor_actions.cc:224 +#: editor_actions.cc:225 #, fuzzy msgid "Duplicate Range" msgstr "Duplizieren" -#: editor_actions.cc:226 +#: editor_actions.cc:227 msgid "Insert Region" msgstr "" -#: editor_actions.cc:228 +#: editor_actions.cc:229 #, fuzzy msgid "Reverse Region" msgstr "Name für Region:" -#: editor_actions.cc:230 +#: editor_actions.cc:231 #, fuzzy msgid "Normalize Region" msgstr "Ardour: Region" -#: editor_actions.cc:232 +#: editor_actions.cc:233 #, fuzzy msgid "crop" msgstr "Kopieren" -#: editor_actions.cc:234 +#: editor_actions.cc:235 #, fuzzy msgid "Insert Chunk" msgstr "Abschnitt einfügen" -#: editor_actions.cc:237 +#: editor_actions.cc:238 #, fuzzy msgid "Split at edit cursor" msgstr "Wiedergabe ab Cursor" -#: editor_actions.cc:240 +#: editor_actions.cc:241 #, fuzzy msgid "Start Range" msgstr "Ausgewählten Bereich wiedergeben" -#: editor_actions.cc:242 +#: editor_actions.cc:243 msgid "Finish Range" msgstr "" -#: editor_actions.cc:244 +#: editor_actions.cc:245 msgid "Finish add Range" msgstr "" -#: editor_actions.cc:247 +#: editor_actions.cc:248 msgid "Extend Range to End of Region" msgstr "" -#: editor_actions.cc:249 +#: editor_actions.cc:250 #, fuzzy msgid "Extend Range to Start of Region" msgstr "An den Anfang der Sitzung springen" -#: editor_actions.cc:252 +#: editor_actions.cc:253 #, fuzzy msgid "Follow Playhead" msgstr "Wiedergabe ab Playhead" -#: editor_actions.cc:260 +#: editor_actions.cc:261 #, fuzzy msgid "Zoom Focus Left" msgstr "Verkleinern" -#: editor_actions.cc:262 +#: editor_actions.cc:263 #, fuzzy msgid "Zoom Focus Right" msgstr "Verkleinern" -#: editor_actions.cc:264 +#: editor_actions.cc:265 #, fuzzy msgid "Zoom Focus Center" msgstr "Verkleinern" -#: editor_actions.cc:266 +#: editor_actions.cc:267 #, fuzzy msgid "Zoom Focus Playhead" msgstr "Verkleinern" -#: editor_actions.cc:268 +#: editor_actions.cc:269 #, fuzzy msgid "Zoom Focus Edit" msgstr "Verkleinern" -#: editor_actions.cc:274 +#: editor_actions.cc:275 msgid "Object Tool" msgstr "" -#: editor_actions.cc:275 +#: editor_actions.cc:276 #, fuzzy msgid "Range Tool" msgstr "Bereich" -#: editor_actions.cc:276 +#: editor_actions.cc:277 msgid "Gain Tool" msgstr "" -#: editor_actions.cc:277 +#: editor_actions.cc:278 #, fuzzy msgid "Zoom Tool" msgstr "Verkleinern" -#: editor_actions.cc:278 +#: editor_actions.cc:279 msgid "Timefx Tool" msgstr "" -#: editor_actions.cc:285 +#: editor_actions.cc:286 #, fuzzy msgid "Snap to frame" msgstr "Modus" -#: editor_actions.cc:286 +#: editor_actions.cc:287 #, fuzzy msgid "Snap to cd frame" msgstr "Modus" -#: editor_actions.cc:287 +#: editor_actions.cc:288 msgid "Snap to SMPTE frame" msgstr "" -#: editor_actions.cc:288 +#: editor_actions.cc:289 msgid "Snap to SMPTE seconds" msgstr "" -#: editor_actions.cc:289 +#: editor_actions.cc:290 msgid "Snap to SMPTE minutes" msgstr "" -#: editor_actions.cc:290 +#: editor_actions.cc:291 #, fuzzy msgid "Snap to seconds" msgstr "Minuten:Sekunden" -#: editor_actions.cc:291 +#: editor_actions.cc:292 msgid "Snap to minutes" msgstr "" -#: editor_actions.cc:292 +#: editor_actions.cc:293 msgid "Snap to thirtyseconds" msgstr "" -#: editor_actions.cc:293 +#: editor_actions.cc:294 msgid "Snap to asixteenthbeat" msgstr "" -#: editor_actions.cc:294 +#: editor_actions.cc:295 msgid "Snap to eighths" msgstr "" -#: editor_actions.cc:295 +#: editor_actions.cc:296 msgid "Snap to quarters" msgstr "" -#: editor_actions.cc:296 +#: editor_actions.cc:297 #, fuzzy msgid "Snap to thirds" msgstr "Modus" -#: editor_actions.cc:297 +#: editor_actions.cc:298 #, fuzzy msgid "Snap to beat" msgstr "Modus" -#: editor_actions.cc:298 +#: editor_actions.cc:299 #, fuzzy msgid "Snap to bar" msgstr "Modus" -#: editor_actions.cc:299 +#: editor_actions.cc:300 #, fuzzy msgid "Snap to mark" msgstr "Ardour: Region umbenennen" -#: editor_actions.cc:300 +#: editor_actions.cc:301 #, fuzzy msgid "Snap to edit cursor" msgstr "Wiedergabe ab Cursor" -#: editor_actions.cc:301 +#: editor_actions.cc:302 #, fuzzy msgid "Snap to region start" msgstr "Regionen" -#: editor_actions.cc:302 +#: editor_actions.cc:303 #, fuzzy msgid "Snap to region end" msgstr "Regionen" -#: editor_actions.cc:303 +#: editor_actions.cc:304 #, fuzzy msgid "Snap to region sync" msgstr "Regionen" -#: editor_actions.cc:304 +#: editor_actions.cc:305 #, fuzzy msgid "Snap to region boundary" msgstr "Regionen" #. the region list popup menu -#: editor_actions.cc:313 +#: editor_actions.cc:314 #, fuzzy msgid "Sort" msgstr "Anschluß" -#: editor_actions.cc:321 +#: editor_actions.cc:322 msgid "Show all" msgstr "Alle zeigen" -#: editor_actions.cc:322 +#: editor_actions.cc:323 #, fuzzy msgid "Show automatic regions" msgstr "Stellen" -#: editor_actions.cc:324 +#: editor_actions.cc:325 msgid "Ascending" msgstr "aufsteigend" -#: editor_actions.cc:326 +#: editor_actions.cc:327 msgid "Descending" msgstr "absteigend" -#: editor_actions.cc:329 +#: editor_actions.cc:330 msgid "By Region Name" msgstr "nach Name der Region" -#: editor_actions.cc:331 +#: editor_actions.cc:332 msgid "By Region Length" msgstr "nach Länge der Region" -#: editor_actions.cc:333 +#: editor_actions.cc:334 #, fuzzy msgid "By Region Position" msgstr "nach Zeitstempel der Region" -#: editor_actions.cc:335 +#: editor_actions.cc:336 msgid "By Region Timestamp" msgstr "nach Zeitstempel der Region" -#: editor_actions.cc:337 +#: editor_actions.cc:338 msgid "By Region Start in File" msgstr "nach Anfang der Region in der Datei" -#: editor_actions.cc:339 +#: editor_actions.cc:340 msgid "By Region End in File" msgstr "nach Ende der Region in der Datei" -#: editor_actions.cc:341 +#: editor_actions.cc:342 msgid "By Source File Name" msgstr "nach Namen der Quelldatei" -#: editor_actions.cc:343 +#: editor_actions.cc:344 msgid "By Source File Length" msgstr "nach Länge der Quelldatei" -#: editor_actions.cc:345 +#: editor_actions.cc:346 msgid "By Source File Creation Date" msgstr "nach Erstellungsdatum der Quelldatei" -#: editor_actions.cc:347 +#: editor_actions.cc:348 msgid "By Source Filesystem" msgstr "nach Dateisystem der Quelle" #. the next two are duplicate items with different names for use in two different contexts -#: editor_actions.cc:353 +#: editor_actions.cc:354 #, fuzzy msgid "Add External Audio" msgstr "Ardour: Region" -#: editor_actions.cc:355 +#: editor_actions.cc:356 #, fuzzy msgid "as Region(s)" msgstr "Ardour: Region" -#: editor_actions.cc:357 +#: editor_actions.cc:358 #, fuzzy msgid "as Tracks" msgstr "Spuren" -#: editor_actions.cc:359 +#: editor_actions.cc:360 #, fuzzy msgid "to Tracks" msgstr "Spuren" -#: editor_actions.cc:362 +#: editor_actions.cc:363 #, fuzzy msgid "Show Waveforms" msgstr "Wellenform zeigen" -#: editor_actions.cc:363 +#: editor_actions.cc:364 #, fuzzy msgid "Show Waveforms While Recording" msgstr "Wellenform zeigen" -#: editor_actions.cc:364 +#: editor_actions.cc:365 msgid "Show Measures" msgstr "" -#: editor_actions.cc:377 editor_actions.cc:384 +#: editor_actions.cc:378 editor_actions.cc:385 msgid "Medium" msgstr "" -#: editor_actions.cc:379 +#: editor_actions.cc:380 #, fuzzy msgid "Faster" msgstr "Einfügen" -#: editor_actions.cc:385 +#: editor_actions.cc:386 msgid "Long" msgstr "" -#: editor_actions.cc:389 +#: editor_actions.cc:390 #, fuzzy msgid "Later is Higher" msgstr "Region eine Ebene nach unten" -#: editor_actions.cc:390 +#: editor_actions.cc:391 #, fuzzy msgid "Most Recently Moved/Added is Higher" msgstr "Region eine Ebene nach unten" -#: editor_actions.cc:391 +#: editor_actions.cc:392 #, fuzzy msgid "Most Recently Added is Higher" msgstr "Region eine Ebene nach unten" @@ -3427,113 +3412,100 @@ msgstr "" msgid "Add existing audio to session" msgstr "Stellen" -#: editor_audio_import.cc:143 +#: editor_audio_import.cc:142 #, fuzzy msgid "ardour: importing %1" msgstr "Ardour: Exportieren" -#: editor_audio_import.cc:147 +#: editor_audio_import.cc:146 msgid "Cancel Import" msgstr "Importieren Abbrechen" -#: editor_audio_import.cc:225 +#: editor_audio_import.cc:224 msgid "Editor: cannot open file \"%1\", (%2)" msgstr "" -#: editor_audio_import.cc:233 +#: editor_audio_import.cc:232 #, fuzzy msgid "Cancel entire import" msgstr "Importieren Abbrechen" -#: editor_audio_import.cc:234 +#: editor_audio_import.cc:233 #, fuzzy msgid "Don't embed it" msgstr "Ohne %1" -#: editor_audio_import.cc:235 +#: editor_audio_import.cc:234 msgid "Embed all without questions" msgstr "" -#: editor_audio_import.cc:240 +#: editor_audio_import.cc:239 msgid "Embed it anyway" msgstr "" -#: editor_audio_import.cc:243 +#: editor_audio_import.cc:242 msgid "" "%1\n" "This audiofile's sample rate doesn't match the session sample rate!" msgstr "" -#: editor_audio_import.cc:276 +#: editor_audio_import.cc:275 msgid "could not open %1" msgstr "Konnte \"%s\" nicht öffnen." -#: editor_audio_import.cc:321 +#: editor_audio_import.cc:320 #, fuzzy msgid "insert sndfile" msgstr "Stille einfügen" #. stuff for the verbose canvas cursor -#: editor_canvas.cc:117 +#: editor_canvas.cc:118 msgid "VerboseCanvasCursor" msgstr "" -#: editor_canvas.cc:285 -#, fuzzy -msgid "Start a new session\n" -msgstr "Bitte mittels des \"Sitzung\"-Menüs\n" - -#: editor_canvas.cc:285 -msgid "via Session menu" -msgstr "eine Sitzung laden oder eine neue erstellen!" - -#: editor_canvas.cc:288 -msgid "FirstActionMessage" -msgstr "" - -#: editor_edit_groups.cc:52 mixer_ui.cc:732 +#: editor_edit_groups.cc:53 mixer_ui.cc:736 #, fuzzy msgid "Activate All" msgstr "Aktiv" -#: editor_edit_groups.cc:53 mixer_ui.cc:733 +#: editor_edit_groups.cc:54 mixer_ui.cc:737 #, fuzzy msgid "Disable All" msgstr "Trennen" -#: editor_edit_groups.cc:55 mixer_ui.cc:735 +#: editor_edit_groups.cc:56 mixer_ui.cc:739 #, fuzzy msgid "Add group" msgstr "keine Gruppe" -#: editor_edit_groups.cc:225 mixer_ui.cc:964 +#: editor_edit_groups.cc:229 mixer_ui.cc:970 #, fuzzy msgid "unnamed" msgstr "Umbenennen" -#: editor_edit_groups.cc:252 mixer_ui.cc:830 +#: editor_edit_groups.cc:258 mixer_ui.cc:834 msgid "-all-" msgstr "-alle-" -#: editor_export_audio.cc:64 +#: editor_export_audio.cc:65 msgid "" "There is no selection to export.\n" "\n" "Select a selection using the range mouse mode" msgstr "" -#: editor_export_audio.cc:109 +#: editor_export_audio.cc:110 msgid "" "There are no ranges to export.\n" "\n" "Create 1 or more ranges by dragging the mouse in the range bar" msgstr "" -#: editor_imageframe.cc:624 editor_imageframe.cc:654 +#: editor_imageframe.cc:625 editor_imageframe.cc:655 msgid "programming error: no ImageFrameView selected" msgstr "" -#: editor_imageframe.cc:847 editor_imageframe.cc:869 +#: editor_imageframe.cc:848 editor_imageframe.cc:870 msgid "programming error: no MarkerView selected" msgstr "" @@ -3542,142 +3514,142 @@ msgstr "" msgid "mute region" msgstr "Name für Region:" -#: editor_keys.cc:45 +#: editor_keys.cc:46 #, fuzzy msgid "keyboard selection" msgstr "Auswahl zu Abschnitt machen" -#: editor_markers.cc:291 editor_ops.cc:1227 editor_ops.cc:1240 -#: editor_ops.cc:1258 location_ui.cc:773 +#: editor_markers.cc:292 editor_ops.cc:1290 editor_ops.cc:1303 +#: editor_ops.cc:1321 location_ui.cc:774 msgid "add marker" msgstr "" -#: editor_markers.cc:306 editor_markers.cc:379 editor_markers.cc:551 -#: editor_markers.cc:569 editor_markers.cc:588 editor_markers.cc:607 -#: editor_markers.cc:637 editor_markers.cc:665 editor_markers.cc:693 -#: editor_markers.cc:731 editor_markers.cc:758 editor_markers.cc:781 -#: editor_markers.cc:800 editor_mouse.cc:1994 editor_mouse.cc:4237 +#: editor_markers.cc:307 editor_markers.cc:380 editor_markers.cc:552 +#: editor_markers.cc:570 editor_markers.cc:589 editor_markers.cc:608 +#: editor_markers.cc:638 editor_markers.cc:666 editor_markers.cc:694 +#: editor_markers.cc:732 editor_markers.cc:759 editor_markers.cc:782 +#: editor_markers.cc:801 editor_mouse.cc:2015 editor_mouse.cc:4275 msgid "programming error: marker canvas item has no marker object pointer!" msgstr "" -#: editor_markers.cc:330 location_ui.cc:655 +#: editor_markers.cc:331 location_ui.cc:656 msgid "remove marker" msgstr "" -#: editor_markers.cc:457 +#: editor_markers.cc:458 #, fuzzy msgid "Locate to Mark" msgstr "Stellen" -#: editor_markers.cc:458 +#: editor_markers.cc:459 #, fuzzy msgid "Play from Mark" msgstr "Wiedergabe ab Anfang" -#: editor_markers.cc:459 +#: editor_markers.cc:460 #, fuzzy msgid "Set Mark from Playhead" msgstr "Wiedergabe ab Playhead" -#: editor_markers.cc:463 +#: editor_markers.cc:464 #, fuzzy msgid "Rename Mark" msgstr "Umbenennen" -#: editor_markers.cc:464 +#: editor_markers.cc:465 #, fuzzy msgid "Hide Mark" msgstr "Stille einfügen" -#: editor_markers.cc:465 +#: editor_markers.cc:466 #, fuzzy msgid "Remove Mark" msgstr "Feld entfernen" -#: editor_markers.cc:478 editor_markers.cc:534 +#: editor_markers.cc:479 editor_markers.cc:535 #, fuzzy msgid "Locate to Range Mark" msgstr "Stellen" -#: editor_markers.cc:479 editor_markers.cc:535 +#: editor_markers.cc:480 editor_markers.cc:536 #, fuzzy msgid "Play from Range Mark" msgstr "Bereich" -#: editor_markers.cc:480 +#: editor_markers.cc:481 #, fuzzy msgid "Loop Range" msgstr "Bereich" -#: editor_markers.cc:481 editor_markers.cc:536 +#: editor_markers.cc:482 editor_markers.cc:537 #, fuzzy msgid "Set Range Mark from Playhead" msgstr "Wiedergabe ab Playhead" -#: editor_markers.cc:482 editor_markers.cc:537 +#: editor_markers.cc:483 editor_markers.cc:538 #, fuzzy msgid "Set Range from Range Selection" msgstr "Auswahl wiedergeben" -#: editor_markers.cc:486 +#: editor_markers.cc:487 #, fuzzy msgid "Rename Range" msgstr "Umbenennen" -#: editor_markers.cc:487 editor_markers.cc:539 +#: editor_markers.cc:488 editor_markers.cc:540 #, fuzzy msgid "Hide Range" msgstr "Bereich" -#: editor_markers.cc:488 +#: editor_markers.cc:489 #, fuzzy msgid "Remove Range" msgstr "Feld entfernen" -#: editor_markers.cc:492 editor_markers.cc:541 +#: editor_markers.cc:493 editor_markers.cc:542 msgid "Separate Regions in Range" msgstr "" -#: editor_markers.cc:493 editor_markers.cc:542 +#: editor_markers.cc:494 editor_markers.cc:543 #, fuzzy msgid "Select All in Range" msgstr "Auswahl" -#: editor_markers.cc:519 +#: editor_markers.cc:520 #, fuzzy msgid "Set Loop Range" msgstr "Ausgewählten Bereich wiedergeben" -#: editor_markers.cc:520 +#: editor_markers.cc:521 msgid "Set Punch Range" msgstr "" -#: editor_markers.cc:814 +#: editor_markers.cc:815 #, fuzzy msgid "New Name:" msgstr "Neuer Name: " -#: editor_markers.cc:817 +#: editor_markers.cc:818 #, fuzzy msgid "ardour: rename mark" msgstr "Ardour: Region umbenennen" -#: editor_markers.cc:819 +#: editor_markers.cc:820 #, fuzzy msgid "ardour: rename range" msgstr "Ardour: Region umbenennen" -#: editor_markers.cc:839 +#: editor_markers.cc:840 #, fuzzy msgid "rename marker" msgstr "Feld entfernen" -#: editor_markers.cc:864 +#: editor_markers.cc:865 #, fuzzy msgid "set loop range" msgstr "Ausgewählten Bereich wiedergeben" -#: editor_markers.cc:890 +#: editor_markers.cc:891 #, fuzzy msgid "set punch range" msgstr "Ausgewählten Bereich wiedergeben" @@ -3686,421 +3658,427 @@ msgstr "Ausgewählten Bereich wiedergeben" msgid "Editor::event_frame() used on unhandled event type %1" msgstr "" -#: editor_mouse.cc:1589 +#: editor_mouse.cc:313 +#, fuzzy +msgid "select on click" +msgstr "Auswahl" + +#: editor_mouse.cc:1590 msgid "programming error: start_grab called without drag item" msgstr "" -#: editor_mouse.cc:1793 +#: editor_mouse.cc:1814 msgid "change fade in length" msgstr "" -#: editor_mouse.cc:1811 +#: editor_mouse.cc:1832 msgid "programming error: fade out canvas item has no regionview data pointer!" msgstr "" -#: editor_mouse.cc:1885 +#: editor_mouse.cc:1906 #, fuzzy msgid "change fade out length" msgstr "Ardour: Editor" -#: editor_mouse.cc:1904 +#: editor_mouse.cc:1925 msgid "programming error: cursor canvas item has no cursor data pointer!" msgstr "" -#: editor_mouse.cc:2119 +#: editor_mouse.cc:2142 #, fuzzy msgid "move marker" msgstr "Feld entfernen" -#: editor_mouse.cc:2142 editor_mouse.cc:2173 editor_tempodisplay.cc:461 +#: editor_mouse.cc:2165 editor_mouse.cc:2196 editor_tempodisplay.cc:459 msgid "" "programming error: meter marker canvas item has no marker object pointer!" msgstr "" -#: editor_mouse.cc:2241 +#: editor_mouse.cc:2264 #, fuzzy msgid "copy meter mark" msgstr "Ardour: Region umbenennen" -#: editor_mouse.cc:2251 +#: editor_mouse.cc:2274 msgid "move meter mark" msgstr "" -#: editor_mouse.cc:2266 editor_mouse.cc:2299 editor_tempodisplay.cc:327 -#: editor_tempodisplay.cc:411 editor_tempodisplay.cc:430 +#: editor_mouse.cc:2289 editor_mouse.cc:2322 editor_tempodisplay.cc:331 +#: editor_tempodisplay.cc:409 editor_tempodisplay.cc:428 msgid "" "programming error: tempo marker canvas item has no marker object pointer!" msgstr "" -#: editor_mouse.cc:2271 editor_mouse.cc:2304 editor_tempodisplay.cc:332 -#: editor_tempodisplay.cc:416 +#: editor_mouse.cc:2294 editor_mouse.cc:2327 editor_tempodisplay.cc:336 +#: editor_tempodisplay.cc:414 msgid "programming error: marker for tempo is not a tempo marker!" msgstr "" -#: editor_mouse.cc:2371 +#: editor_mouse.cc:2394 #, fuzzy msgid "copy tempo mark" msgstr "Ardour: Region umbenennen" -#: editor_mouse.cc:2381 +#: editor_mouse.cc:2404 msgid "move tempo mark" msgstr "" -#: editor_mouse.cc:2395 editor_mouse.cc:2414 editor_mouse.cc:2427 +#: editor_mouse.cc:2418 editor_mouse.cc:2437 editor_mouse.cc:2450 msgid "" "programming error: control point canvas item has no control point object " "pointer!" msgstr "" -#: editor_mouse.cc:2525 +#: editor_mouse.cc:2555 msgid "programming error: line canvas item has no line pointer!" msgstr "" -#: editor_mouse.cc:2634 +#: editor_mouse.cc:2664 #, fuzzy msgid "move region(s)" msgstr "Name für Region:" -#. this is committed in the grab finished callback. -#: editor_mouse.cc:2646 -msgid "Drag region copy" -msgstr "" - -#: editor_mouse.cc:2758 +#: editor_mouse.cc:2727 #, fuzzy msgid "Drag region brush" msgstr "Ardour: Region" +#. don't copy again +#. this is committed in the grab finished callback. +#: editor_mouse.cc:2751 +msgid "Drag region copy" +msgstr "" + #. A selection grab currently creates two undo/redo operations, one for #. creating the new region and another for moving it. #. -#: editor_mouse.cc:3574 +#: editor_mouse.cc:3609 #, fuzzy msgid "selection grab" msgstr "Auswahl" -#: editor_mouse.cc:3615 +#: editor_mouse.cc:3650 #, fuzzy msgid "cancel selection" msgstr "Auswahl wiedergeben" -#: editor_mouse.cc:3722 +#: editor_mouse.cc:3760 #, fuzzy msgid "range selection" msgstr "Auswahl wiedergeben" -#: editor_mouse.cc:3738 +#: editor_mouse.cc:3776 #, fuzzy msgid "trim selection start" msgstr "Auswahl zu Abschnitt machen" -#: editor_mouse.cc:3754 +#: editor_mouse.cc:3792 #, fuzzy msgid "trim selection end" msgstr "Auswahl zu Abschnitt machen" -#: editor_mouse.cc:3771 +#: editor_mouse.cc:3809 #, fuzzy msgid "move selection" msgstr "Auswahl zu Schleife machen" -#: editor_mouse.cc:4157 +#: editor_mouse.cc:4195 msgid "Start point trim" msgstr "" -#: editor_mouse.cc:4185 +#: editor_mouse.cc:4223 msgid "End point trim" msgstr "" -#: editor_mouse.cc:4224 +#: editor_mouse.cc:4262 #, fuzzy msgid "trimmed region" msgstr "Ardour: Region" -#: editor_mouse.cc:4363 +#: editor_mouse.cc:4400 #, fuzzy msgid "new range marker" msgstr "Ardour: Region umbenennen" -#: editor_mouse.cc:4578 +#: editor_mouse.cc:4642 #, fuzzy msgid "select regions" msgstr "Auswahl zu Schleife machen" -#: editor_mouse.cc:4607 +#: editor_mouse.cc:4671 msgid "Name for region:" msgstr "Name für Region:" -#: editor_mouse.cc:4671 +#: editor_mouse.cc:4735 #, fuzzy msgid "timestretch" msgstr "Ardour: Mixer" -#: editor_ops.cc:132 +#: editor_ops.cc:195 #, fuzzy msgid "split" msgstr "Teilen" -#: editor_ops.cc:168 +#: editor_ops.cc:231 #, fuzzy msgid "remove region" msgstr "Name für Region:" -#: editor_ops.cc:187 +#: editor_ops.cc:250 msgid "" " This is destructive, will possibly delete audio files\n" "It cannot be undone\n" "Do you really want to destroy %1 ?" msgstr "" -#: editor_ops.cc:191 +#: editor_ops.cc:254 #, fuzzy msgid "these regions" msgstr "Name für Region:" -#: editor_ops.cc:191 +#: editor_ops.cc:254 #, fuzzy msgid "this region" msgstr "Name für Region:" -#: editor_ops.cc:193 editor_ops.cc:3229 route_ui.cc:700 -#: visual_time_axis.cc:277 +#: editor_ops.cc:256 editor_ops.cc:3318 route_ui.cc:707 +#: visual_time_axis.cc:278 msgid "No, do nothing." msgstr "Nein, nichts machen." -#: editor_ops.cc:196 +#: editor_ops.cc:259 #, fuzzy msgid "Yes, destroy them." msgstr "Ja, entfernen." -#: editor_ops.cc:198 editor_ops.cc:3230 +#: editor_ops.cc:261 editor_ops.cc:3319 #, fuzzy msgid "Yes, destroy it." msgstr "Ja, entfernen." -#: editor_ops.cc:289 editor_ops.cc:317 +#: editor_ops.cc:352 editor_ops.cc:380 #, fuzzy msgid "extend selection" msgstr "Auswahl zu Abschnitt machen" -#: editor_ops.cc:333 editor_ops.cc:367 editor_ops.cc:411 editor_ops.cc:437 +#: editor_ops.cc:396 editor_ops.cc:430 editor_ops.cc:474 editor_ops.cc:500 msgid "nudge forward" msgstr "" -#: editor_ops.cc:501 +#: editor_ops.cc:564 msgid "build_region_boundary_cache called with snap_type = %1" msgstr "" -#: editor_ops.cc:1354 +#: editor_ops.cc:1420 #, fuzzy msgid "select all within" msgstr "Auswahl" -#: editor_ops.cc:1380 +#: editor_ops.cc:1452 #, fuzzy msgid "set selection from region" msgstr "Ausgewählten Bereich wiedergeben" -#: editor_ops.cc:1413 +#: editor_ops.cc:1485 #, fuzzy msgid "set selection from range" msgstr "Ausgewählten Bereich wiedergeben" -#: editor_ops.cc:1443 +#: editor_ops.cc:1515 #, fuzzy msgid "select all from range" msgstr "Ausgewählten Bereich wiedergeben" -#: editor_ops.cc:1465 +#: editor_ops.cc:1537 #, fuzzy msgid "select all from punch" msgstr "Auswahl" -#: editor_ops.cc:1487 +#: editor_ops.cc:1559 #, fuzzy msgid "select all from loop" msgstr "Auswahl" -#: editor_ops.cc:1501 +#: editor_ops.cc:1573 #, fuzzy msgid "select all after cursor" msgstr "Wiedergabe ab Cursor" -#: editor_ops.cc:1506 +#: editor_ops.cc:1578 #, fuzzy msgid "select all before cursor" msgstr "Wiedergabe ab Cursor" -#: editor_ops.cc:1536 +#: editor_ops.cc:1608 #, fuzzy msgid "select all between cursors" msgstr "Wiedergabe ab Cursor" -#: editor_ops.cc:1667 +#: editor_ops.cc:1739 msgid "clear markers" msgstr "" -#: editor_ops.cc:1679 +#: editor_ops.cc:1751 #, fuzzy msgid "clear ranges" msgstr "Verbindungen löschen" -#: editor_ops.cc:1698 +#: editor_ops.cc:1770 #, fuzzy msgid "clear locations" msgstr "Verbindungen löschen" -#: editor_ops.cc:1748 +#: editor_ops.cc:1820 #, fuzzy msgid "insert dragged region" msgstr "Ardour: Region" -#: editor_ops.cc:1784 +#: editor_ops.cc:1856 #, fuzzy msgid "insert region" msgstr "Name für Region:" -#: editor_ops.cc:1975 io_selector.cc:57 io_selector.cc:791 +#: editor_ops.cc:2047 io_selector.cc:58 io_selector.cc:792 msgid "OK" msgstr "" -#: editor_ops.cc:1982 +#: editor_ops.cc:2054 msgid "ardour: rename region" msgstr "Ardour: Region umbenennen" -#: editor_ops.cc:2205 editor_ops.cc:2254 +#: editor_ops.cc:2277 editor_ops.cc:2326 #, fuzzy msgid "separate" msgstr "Ausgewählten Bereich wiedergeben" -#: editor_ops.cc:2316 +#: editor_ops.cc:2388 #, fuzzy msgid "trim to selection" msgstr "Auswahl zu Abschnitt machen" -#: editor_ops.cc:2356 +#: editor_ops.cc:2428 msgid "region fill" msgstr "" -#: editor_ops.cc:2415 +#: editor_ops.cc:2487 #, fuzzy msgid "fill selection" msgstr "Auswahl zu Schleife machen" -#: editor_ops.cc:2436 +#: editor_ops.cc:2508 msgid "Programming error. that region doesn't cover that position" msgstr "" -#: editor_ops.cc:2439 +#: editor_ops.cc:2511 #, fuzzy msgid "set region sync position" msgstr "Regionen" -#: editor_ops.cc:2454 +#: editor_ops.cc:2526 msgid "Place the edit cursor at the desired sync point" msgstr "" "Positionieren sie den Arbeits-Cursor am gewünschten Synchronisationspunkt" -#: editor_ops.cc:2459 +#: editor_ops.cc:2531 #, fuzzy msgid "set sync from edit cursor" msgstr "Wiedergabe ab Cursor" -#: editor_ops.cc:2471 +#: editor_ops.cc:2543 #, fuzzy msgid "remove sync" msgstr "Synchronisationspunkt entfernen" -#: editor_ops.cc:2485 +#: editor_ops.cc:2557 #, fuzzy msgid "naturalize" msgstr "Ardour: Region" -#: editor_ops.cc:2549 +#: editor_ops.cc:2621 msgid "align selection (relative)" msgstr "" -#: editor_ops.cc:2577 +#: editor_ops.cc:2649 #, fuzzy msgid "align selection" msgstr "Auswahl zu Schleife machen" -#: editor_ops.cc:2589 +#: editor_ops.cc:2661 #, fuzzy msgid "align region" msgstr "Ardour: Region" -#: editor_ops.cc:2636 editor_ops.cc:2661 +#: editor_ops.cc:2708 editor_ops.cc:2733 msgid "trim to edit" msgstr "" -#: editor_ops.cc:2712 +#: editor_ops.cc:2784 #, fuzzy msgid "ardour: freeze" msgstr "Ardour: " -#: editor_ops.cc:2717 +#: editor_ops.cc:2789 #, fuzzy msgid "Cancel Freeze" msgstr "Abbrechen" -#: editor_ops.cc:2754 +#: editor_ops.cc:2826 #, fuzzy msgid "bounce range" msgstr "Bereich" -#: editor_ops.cc:2807 +#: editor_ops.cc:2879 #, fuzzy msgid "cut" msgstr "Ausschneiden" -#: editor_ops.cc:2810 +#: editor_ops.cc:2882 #, fuzzy msgid "copy" msgstr "Kopieren" -#: editor_ops.cc:2823 +#: editor_ops.cc:2895 #, fuzzy msgid " objects" msgstr "Objekt" -#: editor_ops.cc:2849 +#: editor_ops.cc:2921 #, fuzzy msgid " range" msgstr "Bereich" -#: editor_ops.cc:3006 +#: editor_ops.cc:3078 #, fuzzy msgid "paste" msgstr "Einfügen" -#: editor_ops.cc:3044 +#: editor_ops.cc:3116 #, fuzzy msgid "paste chunk" msgstr "Abschnitt erzeugen:" #. clear (below) will clear the argument list -#: editor_ops.cc:3085 +#: editor_ops.cc:3157 #, fuzzy msgid "duplicate region" msgstr "Auswahl zu Schleife machen" -#: editor_ops.cc:3130 +#: editor_ops.cc:3202 #, fuzzy msgid "duplicate selection" msgstr "Auswahl zu Schleife machen" -#: editor_ops.cc:3170 +#: editor_ops.cc:3259 #, fuzzy msgid "clear playlist" msgstr "Name für Schnappschuß" -#: editor_ops.cc:3199 +#: editor_ops.cc:3288 #, fuzzy msgid "nudge track" msgstr "Stille einfügen" -#: editor_ops.cc:3226 +#: editor_ops.cc:3315 #, fuzzy msgid "" "Do you really want to destroy the last capture?\n" @@ -4109,172 +4087,169 @@ msgstr "" "Wollen Sie wirklich die Spur \"%1\" löschen?\n" "(Kann nicht rückgängig gemacht werden!)" -#: editor_ops.cc:3254 +#: editor_ops.cc:3343 #, fuzzy msgid "normalize" msgstr "Ardour: Region" -#: editor_ops.cc:3301 +#: editor_ops.cc:3390 #, fuzzy msgid "reverse regions" msgstr "Name für Region:" -#: editor_region_list.cc:93 editor_region_list.cc:98 editor_region_list.cc:101 -#: location_ui.cc:55 +#: editor_region_list.cc:98 editor_region_list.cc:103 +#: editor_region_list.cc:106 location_ui.cc:56 #, fuzzy msgid "Hidden" msgstr "Verbergen" #. added a new fresh one at the end -#: editor_route_list.cc:101 editor_route_list.cc:102 editor_route_list.cc:246 +#: editor_route_list.cc:102 editor_route_list.cc:103 editor_route_list.cc:247 msgid "editor" msgstr "" -#: editor_route_list.cc:309 mixer_ui.cc:695 +#: editor_route_list.cc:310 mixer_ui.cc:699 msgid "Show All" msgstr "Alles zeigen" -#: editor_route_list.cc:310 mixer_ui.cc:696 +#: editor_route_list.cc:311 mixer_ui.cc:700 msgid "Hide All" msgstr "Alle verstecken" -#: editor_route_list.cc:311 mixer_ui.cc:697 +#: editor_route_list.cc:312 mixer_ui.cc:701 #, fuzzy msgid "Show All Audio Tracks" msgstr "Auswahl" -#: editor_route_list.cc:312 mixer_ui.cc:698 +#: editor_route_list.cc:313 mixer_ui.cc:702 #, fuzzy msgid "Hide All Audio Tracks" msgstr "Auswahl" -#: editor_route_list.cc:313 mixer_ui.cc:699 +#: editor_route_list.cc:314 mixer_ui.cc:703 msgid "Show All Audio Busses" msgstr "" -#: editor_route_list.cc:314 mixer_ui.cc:700 +#: editor_route_list.cc:315 mixer_ui.cc:704 msgid "Hide All Audio Busses" msgstr "" -#: editor_rulers.cc:311 +#: editor_rulers.cc:312 #, fuzzy msgid "New location marker" msgstr "Stellen" -#: editor_rulers.cc:312 +#: editor_rulers.cc:313 #, fuzzy msgid "Clear all locations" msgstr "Verbindungen löschen" #. ruler_items.push_back (MenuElem (_("New Range"))); -#: editor_rulers.cc:317 +#: editor_rulers.cc:318 #, fuzzy msgid "Clear all ranges" msgstr "Verbindungen löschen" -#: editor_rulers.cc:326 +#: editor_rulers.cc:327 msgid "New Tempo" msgstr "" -#: editor_rulers.cc:327 +#: editor_rulers.cc:328 #, fuzzy msgid "Clear tempo" msgstr "leeren" -#: editor_rulers.cc:332 +#: editor_rulers.cc:333 msgid "New Meter" msgstr "" -#: editor_rulers.cc:333 +#: editor_rulers.cc:334 #, fuzzy msgid "Clear meter" msgstr "leeren" -#: editor_rulers.cc:341 +#: editor_rulers.cc:342 #, fuzzy msgid "Min:Secs" msgstr "Min:Sek" -#: editor_selection_list.cc:110 +#: editor_selection_list.cc:108 #, fuzzy msgid "Name for Chunk:" msgstr "Name für Abschnitt:" -#: editor_selection_list.cc:113 +#: editor_selection_list.cc:111 #, fuzzy msgid "Create Chunk" msgstr "Abschnitt erzeugen:" -#: editor_selection_list.cc:113 +#: editor_selection_list.cc:111 msgid "Forget it" msgstr "Abbrechen" -#: editor_tempodisplay.cc:249 editor_tempodisplay.cc:289 +#: editor_tempodisplay.cc:253 editor_tempodisplay.cc:293 #, fuzzy msgid "add" msgstr "Hinzufügen" -#: editor_tempodisplay.cc:271 +#: editor_tempodisplay.cc:275 #, fuzzy msgid "add tempo mark" msgstr "Ardour: Region umbenennen" -#: editor_tempodisplay.cc:311 +#: editor_tempodisplay.cc:315 #, fuzzy msgid "add meter mark" msgstr "Ardour: Region umbenennen" -#: editor_tempodisplay.cc:344 editor_tempodisplay.cc:375 +#: editor_tempodisplay.cc:348 editor_tempodisplay.cc:376 #, fuzzy msgid "done" msgstr "keine" -#: editor_tempodisplay.cc:365 editor_tempodisplay.cc:396 +#: editor_tempodisplay.cc:366 editor_tempodisplay.cc:394 msgid "replace tempo mark" msgstr "" -#: editor_tempodisplay.cc:435 editor_tempodisplay.cc:466 +#: editor_tempodisplay.cc:433 editor_tempodisplay.cc:464 msgid "programming error: marker for meter is not a meter marker!" msgstr "" -#: editor_tempodisplay.cc:445 editor_tempodisplay.cc:478 +#: editor_tempodisplay.cc:443 editor_tempodisplay.cc:476 #, fuzzy msgid "remove tempo mark" msgstr "Ja, entfernen." -#: editor_timefx.cc:50 +#: editor_timefx.cc:51 msgid "Quick but Ugly" msgstr "" -#: editor_timefx.cc:51 +#: editor_timefx.cc:52 msgid "Skip Anti-aliasing" msgstr "" -#: editor_timefx.cc:53 -msgid "Stretch/Shrink it" -msgstr "" - -#: editor_timefx.cc:57 +#: editor_timefx.cc:56 #, fuzzy msgid "ardour: timestretch" msgstr "Ardour: Mixer" -#: editor_timefx.cc:58 +#: editor_timefx.cc:57 msgid "TimeStretchDialog" msgstr "" -#: editor_timefx.cc:80 editor_timefx.cc:81 editor_timefx.cc:82 -#: editor_timefx.cc:83 +#: editor_timefx.cc:70 +msgid "Stretch/Shrink it" +msgstr "" + +#: editor_timefx.cc:73 editor_timefx.cc:74 msgid "TimeStretchButton" msgstr "" -#: editor_timefx.cc:84 +#: editor_timefx.cc:75 msgid "TimeStretchProgress" msgstr "" -#. GTK2FIX -#. current_timestretch->close (); -#: editor_timefx.cc:153 +#: editor_timefx.cc:139 msgid "timestretch cannot be started - thread creation error" msgstr "" @@ -4408,7 +4383,7 @@ msgstr "" msgid "Export to File" msgstr "Export nach CD" -#: export_dialog.cc:113 option_editor.cc:82 option_editor.cc:83 +#: export_dialog.cc:113 option_editor.cc:83 option_editor.cc:84 msgid "Browse" msgstr "" @@ -4425,7 +4400,8 @@ msgstr "Ardour: Exportieren" msgid "ardour_export" msgstr "Ardour: Exportieren" -#: export_dialog.cc:139 export_dialog.cc:155 +#: export_dialog.cc:139 export_dialog.cc:155 mixer_strip.cc:124 +#: mixer_strip.cc:767 #, fuzzy msgid "Output" msgstr "Ausgänge" @@ -4462,140 +4438,72 @@ msgstr "" msgid "File already exists, do you want to overwrite it?" msgstr "" -#: export_dialog.cc:1159 export_range_markers_dialog.cc:154 +#: export_dialog.cc:1159 export_range_markers_dialog.cc:153 msgid "Cannot write file in: " msgstr "" #. warning dialog -#: export_range_markers_dialog.cc:136 +#: export_range_markers_dialog.cc:135 msgid "Please enter a valid target directory." msgstr "" -#: export_range_markers_dialog.cc:144 +#: export_range_markers_dialog.cc:143 msgid "" "Please select an existing target directory. Files\n" "are not allowed!" msgstr "" -#: gain_automation_time_axis.cc:61 +#: gain_automation_time_axis.cc:62 #, fuzzy msgid "add gain automation event" msgstr "Stellen" -#: gain_meter.cc:66 +#: gain_meter.cc:67 msgid "cannot find images for fader slider" msgstr "" -#: gain_meter.cc:73 +#: gain_meter.cc:74 msgid "cannot find images for fader rail" msgstr "" -#: gain_meter.cc:88 -msgid "dbFS" -msgstr "" - -#: gain_meter.cc:89 gain_meter.cc:143 gain_meter.cc:704 -msgid "pre" -msgstr "" - -#: gain_meter.cc:139 gain_meter.cc:700 -#, fuzzy -msgid "input" -msgstr "%1 Eingang" - -#: gain_meter.cc:147 gain_meter.cc:708 -#, fuzzy -msgid "post" -msgstr "Anschluß" - -#. TRANSLATORS: this string should be longest of the strings -#. used to describe meter points. In english, its "input". -#. -#: gain_meter.cc:155 -msgid "tupni" -msgstr "" - -#: gain_meter.cc:174 gain_meter.cc:458 gain_meter.cc:480 gain_meter.cc:525 +#: gain_meter.cc:130 gain_meter.cc:339 gain_meter.cc:494 gain_meter.cc:539 msgid "-inf" msgstr "" -#: glade/new_session_dialog.glade.h:1 +#: gain_meter.cc:140 #, fuzzy -msgid "Advanced" -msgstr "Feld hinzufügen..." +msgid "Fader automation mode" +msgstr "Stellen" -#: glade/new_session_dialog.glade.h:2 -msgid "Input" +#: gain_meter.cc:141 +#, fuzzy +msgid "Fader automation type" +msgstr "Stellen" + +#. XXX it might different in different languages +#: gain_meter.cc:182 gain_meter.cc:817 panner_ui.cc:99 panner_ui.cc:807 +msgid "Abs" msgstr "" -#: glade/new_session_dialog.glade.h:3 -#, fuzzy -msgid "Output" -msgstr "Ausgänge" - -#: glade/new_session_dialog.glade.h:4 -#, fuzzy -msgid "Automatically connect inputs" -msgstr "Verfügbare Verbindungen" - -#: glade/new_session_dialog.glade.h:5 -#, fuzzy -msgid "Automatically connect outputs" -msgstr "Verfügbare Verbindungen" - -#: glade/new_session_dialog.glade.h:6 -#, fuzzy -msgid "Channel Count" -msgstr "Importieren Abbrechen" - -#: glade/new_session_dialog.glade.h:7 -msgid "Connect to Master Bus" +#: gain_meter.cc:472 +msgid "-Inf" msgstr "" -#: glade/new_session_dialog.glade.h:8 -msgid "Connect to physical outputs" +#: gain_meter.cc:781 mixer_strip.cc:770 panner_ui.cc:771 +#, fuzzy +msgid "O" +msgstr "ODER" + +#: gain_meter.cc:784 panner_ui.cc:774 +msgid "P" msgstr "" -#: glade/new_session_dialog.glade.h:9 -msgid "Create Control Bus" +#: gain_meter.cc:787 panner_ui.cc:777 +msgid "T" msgstr "" -#: glade/new_session_dialog.glade.h:10 -msgid "Create Master Bus" -msgstr "" - -#: glade/new_session_dialog.glade.h:11 -#, fuzzy -msgid "New Session" -msgstr "Sitzung" - -#: glade/new_session_dialog.glade.h:12 -#, fuzzy -msgid "Open Recent Session" -msgstr "Sitzung" - -#: glade/new_session_dialog.glade.h:13 -#, fuzzy -msgid "Open Session" -msgstr "Sitzung" - -#: glade/new_session_dialog.glade.h:14 -#, fuzzy -msgid "Port limit" -msgstr "Abbrechen" - -#: glade/new_session_dialog.glade.h:15 -#, fuzzy -msgid "Select a File" -msgstr "Auswahl" - -#: glade/new_session_dialog.glade.h:16 -#, fuzzy -msgid "Select a Session" -msgstr "Auswahl zu Schleife machen" - -#: glade/new_session_dialog.glade.h:17 -msgid "Track/Bus connection options" +#: gain_meter.cc:790 panner_ui.cc:780 +msgid "W" msgstr "" #: gtk-custom-ruler.c:126 @@ -4643,251 +4551,251 @@ msgid "Draw current ruler position" msgstr "" #. end-of-file, other end closed or shutdown? -#: imageframe_socket_handler.cc:126 +#: imageframe_socket_handler.cc:127 msgid "Image Compositor Socket has been shutdown/closed" msgstr "" -#: imageframe_time_axis.cc:287 +#: imageframe_time_axis.cc:286 #, fuzzy msgid "0.5 seconds" msgstr "Minuten:Sekunden" -#: imageframe_time_axis.cc:288 marker_time_axis.cc:241 +#: imageframe_time_axis.cc:287 marker_time_axis.cc:242 #, fuzzy msgid "1 seconds" msgstr "Minuten:Sekunden" -#: imageframe_time_axis.cc:289 marker_time_axis.cc:242 +#: imageframe_time_axis.cc:288 marker_time_axis.cc:243 #, fuzzy msgid "1.5 seconds" msgstr "Minuten:Sekunden" -#: imageframe_time_axis.cc:290 marker_time_axis.cc:243 +#: imageframe_time_axis.cc:289 marker_time_axis.cc:244 #, fuzzy msgid "2 seconds" msgstr "Minuten:Sekunden" -#: imageframe_time_axis.cc:291 marker_time_axis.cc:244 +#: imageframe_time_axis.cc:290 marker_time_axis.cc:245 #, fuzzy msgid "2.5 seconds" msgstr "Minuten:Sekunden" -#: imageframe_time_axis.cc:292 marker_time_axis.cc:245 +#: imageframe_time_axis.cc:291 marker_time_axis.cc:246 #, fuzzy msgid "3 seconds" msgstr "Minuten:Sekunden" #. duration_items.push_back(SeparatorElem()) ; #. duration_items.push_back(MenuElem (_("custom"), mem_fun(*this, &ImageFrameTimeAxis::set_marker_duration_custom))) ; -#: imageframe_time_axis.cc:297 marker_time_axis.cc:250 +#: imageframe_time_axis.cc:296 marker_time_axis.cc:251 #, fuzzy msgid "Duration (sec)" msgstr "Ardour: Region" -#: imageframe_time_axis.cc:302 +#: imageframe_time_axis.cc:301 #, fuzzy msgid "Remove Frame" msgstr "Feld entfernen" -#: imageframe_time_axis.cc:305 +#: imageframe_time_axis.cc:304 msgid "Image Frame" msgstr "" -#: imageframe_time_axis.cc:306 marker_time_axis.cc:256 +#: imageframe_time_axis.cc:305 marker_time_axis.cc:257 #, fuzzy msgid "Rename Track" msgstr "Umbenennen" -#: io_selector.cc:59 io_selector.cc:793 +#: io_selector.cc:60 io_selector.cc:794 #, fuzzy msgid "Rescan" msgstr "Auffrischen" -#: io_selector.cc:67 +#: io_selector.cc:68 msgid "%1 input" msgstr "%1 Eingang" -#: io_selector.cc:69 +#: io_selector.cc:70 msgid "%1 output" msgstr "%1 Ausgang" -#: io_selector.cc:141 route_params_ui.cc:106 +#: io_selector.cc:142 route_params_ui.cc:107 #, fuzzy msgid "Inputs" msgstr "Eingänge" -#: io_selector.cc:141 route_params_ui.cc:107 +#: io_selector.cc:142 route_params_ui.cc:108 #, fuzzy msgid "Outputs" msgstr "Ausgänge" -#: io_selector.cc:142 +#: io_selector.cc:143 #, fuzzy msgid "Add Input" msgstr "Port hinzufügen" -#: io_selector.cc:142 +#: io_selector.cc:143 #, fuzzy msgid "Add Output" msgstr "%1 Ausgang" -#: io_selector.cc:143 +#: io_selector.cc:144 #, fuzzy msgid "Remove Input" msgstr "Synchronisationspunkt entfernen" -#: io_selector.cc:143 +#: io_selector.cc:144 #, fuzzy msgid "Remove Output" msgstr "Ausgänge" -#: io_selector.cc:144 +#: io_selector.cc:145 #, fuzzy msgid "Disconnect All" msgstr "Trennen" -#: io_selector.cc:158 +#: io_selector.cc:159 msgid "Available connections" msgstr "Verfügbare Verbindungen" -#: io_selector.cc:554 io_selector.cc:573 +#: io_selector.cc:555 io_selector.cc:574 msgid "There are no more JACK ports available." msgstr "" -#: io_selector.cc:648 io_selector.cc:675 io_selector.cc:728 +#: io_selector.cc:649 io_selector.cc:676 io_selector.cc:729 msgid "port" msgstr "Anschluß" -#: io_selector.cc:797 +#: io_selector.cc:798 msgid "ardour: " msgstr "Ardour: " -#: keyboard.cc:297 +#: keyboard.cc:299 msgid "KeyboardTarget: keyname \"%1\" is unknown." msgstr "" -#: keyboard.cc:523 +#: keyboard.cc:525 msgid "" "Your system is completely broken - NumLock uses \"%1\"as its modifier. This " "is madness - see the man page for xmodmap to find out how to fix this." msgstr "" -#: keyboard.cc:531 +#: keyboard.cc:533 msgid "" "Your system generates \"%1\" when the NumLock key is pressed. This can cause " "problems when editing so Ardour will use %2 to mean Meta rather than %1" msgstr "" -#: keyboard.cc:592 +#: keyboard.cc:594 msgid "You have %1 keys bound to \"mod1\"" msgstr "" -#: keyboard.cc:607 +#: keyboard.cc:609 msgid "You have %1 keys bound to \"mod2\"" msgstr "" -#: keyboard.cc:622 +#: keyboard.cc:624 msgid "You have %1 keys bound to \"mod3\"" msgstr "" -#: keyboard.cc:637 +#: keyboard.cc:639 msgid "You have %1 keys bound to \"mod4\"" msgstr "" -#: keyboard.cc:652 +#: keyboard.cc:654 msgid "You have %1 keys bound to \"mod5\"" msgstr "" -#: location_ui.cc:47 location_ui.cc:50 +#: location_ui.cc:48 location_ui.cc:51 #, fuzzy msgid "Set" msgstr "Auswahl" -#: location_ui.cc:48 location_ui.cc:51 +#: location_ui.cc:49 location_ui.cc:52 msgid "Go" msgstr "" -#: location_ui.cc:54 +#: location_ui.cc:55 msgid "CD" msgstr "CD" -#: location_ui.cc:57 +#: location_ui.cc:58 msgid "SCMS" msgstr "" -#: location_ui.cc:58 +#: location_ui.cc:59 msgid "Pre-Emphasis" msgstr "" -#: location_ui.cc:569 +#: location_ui.cc:570 #, fuzzy msgid "Add New Location" msgstr "Stellen" -#: location_ui.cc:570 +#: location_ui.cc:571 msgid "Add New Range" msgstr "" -#: location_ui.cc:574 +#: location_ui.cc:575 msgid "ardour: locations" msgstr "" -#: location_ui.cc:575 +#: location_ui.cc:576 #, fuzzy msgid "ardour_locations" msgstr "Ardour: Verbindungen" -#: location_ui.cc:603 +#: location_ui.cc:604 #, fuzzy msgid "Location (CD Index) Markers" msgstr "Stellen" -#: location_ui.cc:623 +#: location_ui.cc:624 msgid "Range (CD Track) Markers" msgstr "" -#: location_ui.cc:789 +#: location_ui.cc:790 #, fuzzy msgid "add range marker" msgstr "Ardour: Region umbenennen" -#: main.cc:71 +#: main.cc:72 msgid "ardour is killing itself for a clean exit\n" msgstr "" -#: main.cc:80 +#: main.cc:81 msgid "stopping user interface\n" msgstr "" #. XXX its doubtful that snprintf() is async-safe -#: main.cc:99 +#: main.cc:100 #, c-format msgid "%d(%d): received signal %d\n" msgstr "" -#: main.cc:185 +#: main.cc:186 msgid "cannot become new process group leader (%1)" msgstr "" -#: main.cc:212 +#: main.cc:213 msgid "cannot setup signal handling for %1" msgstr "" -#: main.cc:223 +#: main.cc:224 msgid "cannot set default signal mask (%1)" msgstr "" -#: main.cc:253 +#: main.cc:254 msgid "" "Without a UI style file, ardour will look strange.\n" " Please set ARDOUR2_UI_RC to point to a valid UI style file" msgstr "" -#: main.cc:273 +#: main.cc:276 msgid "Ardour could not connect to JACK." msgstr "" -#: main.cc:277 +#: main.cc:280 msgid "" "There are several possible reasons:\n" "\n" @@ -4898,69 +4806,12 @@ msgid "" "Please consider the possibilities, and perhaps (re)start JACK." msgstr "" -#: main.cc:324 -msgid "Ardour/GTK " -msgstr "" - -#: main.cc:326 -msgid "" -"\n" -" (built using " -msgstr "" - -#: main.cc:330 -msgid " with libardour " -msgstr "" - -#: main.cc:335 -msgid " and GCC version " -msgstr "" - -#: main.cc:345 -msgid "Copyright (C) 1999-2005 Paul Davis" -msgstr "" - -#: main.cc:346 -msgid "" -"Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " -"Baker" -msgstr "" - -#: main.cc:348 -msgid "Ardour comes with ABSOLUTELY NO WARRANTY" -msgstr "Achtung: Es gibt zu Ardour KEINERLEI Gewährleistung!" - -#: main.cc:349 -msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." -msgstr "" - -#: main.cc:350 -msgid "This is free software, and you are welcome to redistribute it " -msgstr "Dies ist freie Software und Sie dürfen sie gerne weiterverbreiten," - -#: main.cc:351 -#, fuzzy -msgid "under certain conditions; see the source for copying conditions." -msgstr "solange Sie sich an die Spielregeln aus der Datei COPYING halten." - -#: main.cc:360 -msgid "could not create ARDOUR GUI" -msgstr "" - -#: main.cc:378 -msgid "Could not connect to JACK server as \"%1\"" -msgstr "" - -#: main.cc:381 -msgid "could not initialize Ardour." -msgstr "" - -#: main.cc:392 +#: main.cc:310 msgid "could not load command line session \"%1\"" msgstr "" #. it wasn't new, but we require a new session -#: main.cc:412 +#: main.cc:330 msgid "" "\n" "\n" @@ -4968,7 +4819,7 @@ msgid "" "To avoid this message, start ardour as \"ardour %1" msgstr "" -#: main.cc:423 +#: main.cc:341 msgid "" "\n" "\n" @@ -4976,310 +4827,443 @@ msgid "" "To create it from the command line, start ardour as \"ardour --new %1" msgstr "" +#: main.cc:405 +msgid "Ardour/GTK " +msgstr "" + +#: main.cc:407 +msgid "" +"\n" +" (built using " +msgstr "" + +#: main.cc:411 +msgid " with libardour " +msgstr "" + +#: main.cc:416 +msgid " and GCC version " +msgstr "" + +#: main.cc:426 +msgid "Copyright (C) 1999-2006 Paul Davis" +msgstr "" + +#: main.cc:427 +msgid "" +"Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " +"Baker" +msgstr "" + +#: main.cc:429 +msgid "Ardour comes with ABSOLUTELY NO WARRANTY" +msgstr "Achtung: Es gibt zu Ardour KEINERLEI Gewährleistung!" + +#: main.cc:430 +msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." +msgstr "" + +#: main.cc:431 +msgid "This is free software, and you are welcome to redistribute it " +msgstr "Dies ist freie Software und Sie dürfen sie gerne weiterverbreiten," + +#: main.cc:432 +#, fuzzy +msgid "under certain conditions; see the source for copying conditions." +msgstr "solange Sie sich an die Spielregeln aus der Datei COPYING halten." + +#: main.cc:441 +msgid "could not create ARDOUR GUI" +msgstr "" + +#: main.cc:459 +msgid "Could not connect to JACK server as \"%1\"" +msgstr "" + +#: main.cc:462 +msgid "could not initialize Ardour." +msgstr "" + #: marker.cc:244 #, fuzzy msgid "MarkerText" msgstr "Schicht" -#: marker_time_axis.cc:253 +#: marker_time_axis.cc:254 #, fuzzy msgid "Remove Marker" msgstr "Feld entfernen" -#: marker_time_axis.cc:255 +#: marker_time_axis.cc:256 #, fuzzy msgid "Marker" msgstr "Schicht" -#: meter_bridge.cc:77 +#: meter_bridge.cc:78 msgid "ardour: meter bridge" msgstr "" -#: meter_bridge.cc:78 +#: meter_bridge.cc:79 msgid "ardour_meter_bridge" msgstr "" -#: meter_bridge_strip.cc:79 meter_bridge_strip.cc:93 +#: meter_bridge_strip.cc:80 meter_bridge_strip.cc:94 #, c-format msgid "# of %u-sample overs" msgstr "" -#: meter_bridge_strip.cc:221 +#: meter_bridge_strip.cc:222 #, fuzzy msgid "New Name for Meter:" msgstr "Name für Mixer-Voreinstellung" -#: mixer_strip.cc:85 mixer_strip.cc:437 region_editor.cc:46 -msgid "mute" -msgstr "mute" +#: mixer_strip.cc:95 mixer_strip.cc:140 mixer_strip.cc:1227 +msgid "pre" +msgstr "" -#: mixer_strip.cc:85 mixer_strip.cc:438 -msgid "solo" -msgstr "solo" - -#: mixer_strip.cc:85 mixer_strip.cc:436 -msgid "RECORD" -msgstr "AUFNAHME" - -#: mixer_strip.cc:96 mixer_strip.cc:441 mixer_strip.cc:1064 +#: mixer_strip.cc:96 mixer_strip.cc:822 msgid "Comments" msgstr "" -#: mixer_strip.cc:120 mixer_strip.cc:752 -msgid "INPUT" -msgstr "EINGANG" - -#: mixer_strip.cc:125 mixer_strip.cc:773 -msgid "OUTPUT" -msgstr "AUSGANG" - -#: mixer_strip.cc:140 +#: mixer_strip.cc:119 #, fuzzy -msgid "Pan automation mode" -msgstr "Stellen" +msgid "Input" +msgstr "Eingänge" -#: mixer_strip.cc:141 +#: mixer_strip.cc:136 mixer_strip.cc:1223 #, fuzzy -msgid "Gain automation mode" -msgstr "Stellen" +msgid "input" +msgstr "%1 Eingang" -#: mixer_strip.cc:143 +#: mixer_strip.cc:144 mixer_strip.cc:1231 #, fuzzy -msgid "Pan automation type" -msgstr "Stellen" +msgid "post" +msgstr "Anschluß" -#: mixer_strip.cc:144 -#, fuzzy -msgid "Gain automation type" -msgstr "Stellen" - -#: mixer_strip.cc:183 mixer_strip.cc:195 mixer_strip.cc:913 -#, fuzzy -msgid "trim" -msgstr "Streifen" - -#. XXX it might different in different languages -#: mixer_strip.cc:184 mixer_strip.cc:196 mixer_strip.cc:917 -msgid "abs" +#. TRANSLATORS: this string should be longest of the strings +#. used to describe meter points. In english, its "input". +#. +#: mixer_strip.cc:152 +msgid "tupni" msgstr "" -#: mixer_strip.cc:203 -#, fuzzy -msgid "gain automation mode" -msgstr "Stellen" - -#: mixer_strip.cc:204 -#, fuzzy -msgid "pan automation mode" -msgstr "Stellen" - -#: mixer_strip.cc:205 -#, fuzzy -msgid "gain automation state" -msgstr "Stellen" - -#: mixer_strip.cc:206 -#, fuzzy -msgid "pan automation state" -msgstr "Stellen" - -#: mixer_strip.cc:223 -msgid "varispeed" +#: mixer_strip.cc:207 +msgid "Varispeed" msgstr "" -#: mixer_strip.cc:245 mixer_strip.cc:1078 +#: mixer_strip.cc:233 mixer_strip.cc:836 msgid "Click to Add/Edit Comments" msgstr "" -#: mixer_strip.cc:393 +#: mixer_strip.cc:374 msgid "unknown strip width \"%1\" in XML GUI information" msgstr "" -#: mixer_strip.cc:443 mixer_strip.cc:1062 -msgid "*Comments*" +#: mixer_strip.cc:417 +#, fuzzy +msgid "record" +msgstr "Wiederherstellen" + +#: mixer_strip.cc:418 region_editor.cc:47 +msgid "mute" +msgstr "mute" + +#: mixer_strip.cc:419 +msgid "solo" +msgstr "solo" + +#: mixer_strip.cc:422 +msgid "comments" msgstr "" -#: mixer_strip.cc:457 -msgid "REC" +#: mixer_strip.cc:424 +msgid "*comments*" msgstr "" -#: mixer_strip.cc:462 mixer_strip.cc:1072 +#: mixer_strip.cc:438 +#, fuzzy +msgid "Rec" +msgstr "Auffrischen" + +#: mixer_strip.cc:439 +msgid "M" +msgstr "" + +#: mixer_strip.cc:440 +msgid "S" +msgstr "" + +#: mixer_strip.cc:443 mixer_strip.cc:830 #, fuzzy msgid "Cmt" msgstr "Ausschneiden" -#: mixer_strip.cc:464 mixer_strip.cc:1070 +#: mixer_strip.cc:445 mixer_strip.cc:828 msgid "*Cmt*" msgstr "" -#: mixer_strip.cc:503 mixer_strip.cc:562 redirect_box.cc:1004 +#: mixer_strip.cc:483 mixer_strip.cc:549 redirect_box.cc:1006 msgid "Not connected to JACK - no I/O changes are possible" msgstr "" -#: mixer_strip.cc:569 +#: mixer_strip.cc:560 msgid "Track" msgstr "Spur" -#: mixer_strip.cc:593 mixer_strip.cc:609 +#: mixer_strip.cc:588 mixer_strip.cc:604 msgid "could not register new ports required for that connection" msgstr "" -#: mixer_strip.cc:755 -msgid "IN" +#: mixer_strip.cc:747 +#, fuzzy +msgid " Input" +msgstr "Eingänge" + +#: mixer_strip.cc:750 +msgid "I" msgstr "" -#: mixer_strip.cc:776 -msgid "OUT" +#: mixer_strip.cc:820 +msgid "*Comments*" msgstr "" -#: mixer_strip.cc:884 -msgid "aplay" -msgstr "" - -#: mixer_strip.cc:890 -msgid "awrite" -msgstr "" - -#: mixer_strip.cc:1095 +#: mixer_strip.cc:859 #, fuzzy msgid ": comment editor" msgstr "Der Editor konnte nicht initialisiert werden." -#: mixer_strip.cc:1157 mixer_strip.cc:1178 -msgid "no group" -msgstr "keine Gruppe" +#: mixer_strip.cc:953 +msgid "Grp" +msgstr "" -#: mixer_strip.cc:1181 +#: mixer_strip.cc:956 msgid "~G" msgstr "" -#: mixer_strip.cc:1229 +#: mixer_strip.cc:1004 #, fuzzy msgid "Invert Polarity" msgstr "Polarität" -#: mixer_ui.cc:84 +#: mixer_ui.cc:85 msgid "Strips" msgstr "Streifen" -#: mixer_ui.cc:108 -msgid "groupname" -msgstr "" +#: mixer_ui.cc:110 +#, fuzzy +msgid "Group" +msgstr "Mix Gruppen" -#: mixer_ui.cc:109 region_editor.cc:48 region_editor.cc:191 -#: region_editor.cc:225 -msgid "active" -msgstr "" - -#: mixer_ui.cc:110 region_editor.cc:49 -msgid "visible" -msgstr "" - -#: mixer_ui.cc:207 mixer_ui.cc:366 +#: mixer_ui.cc:211 mixer_ui.cc:370 msgid "ardour: mixer" msgstr "Ardour: Mixer" -#: mixer_ui.cc:208 +#: mixer_ui.cc:212 #, fuzzy msgid "ardour_mixer" msgstr "Ardour: Mixer" -#: mixer_ui.cc:342 +#: mixer_ui.cc:346 msgid "ardour: mixer: " msgstr "Ardour: Mixer: " -#: mixer_ui.cc:569 +#: mixer_ui.cc:573 msgid "signal" msgstr "Signal" -#: mixer_ui.cc:719 +#: mixer_ui.cc:723 msgid "track display list item for renamed strip not found!" msgstr "" -#: option_editor.cc:75 +#: new_session_dialog.cc:39 +#, fuzzy +msgid "New Session Name :" +msgstr "Name der Sitzung" + +#: new_session_dialog.cc:41 +msgid "Create Session Directory In :" +msgstr "" + +#: new_session_dialog.cc:43 +#, fuzzy +msgid "Use Session Template :" +msgstr "Name der Sitzung" + +#: new_session_dialog.cc:45 +#, fuzzy +msgid "Channel Count" +msgstr "Importieren Abbrechen" + +#: new_session_dialog.cc:46 +msgid "Create Monitor Bus" +msgstr "" + +#: new_session_dialog.cc:53 +msgid "Create Master Bus" +msgstr "" + +#: new_session_dialog.cc:55 +#, fuzzy +msgid "Automatically Connect Inputs" +msgstr "Verfügbare Verbindungen" + +#: new_session_dialog.cc:56 new_session_dialog.cc:67 +#, fuzzy +msgid "Port Limit" +msgstr "Abbrechen" + +#: new_session_dialog.cc:64 +#, fuzzy +msgid "Track/Bus Inputs" +msgstr "Ausgänge" + +#: new_session_dialog.cc:66 +#, fuzzy +msgid "Automatically Connect Outputs" +msgstr "Verfügbare Verbindungen" + +#: new_session_dialog.cc:75 +msgid "Connect to Master Bus" +msgstr "" + +#: new_session_dialog.cc:76 +msgid "Connect to Physical Outputs" +msgstr "" + +#: new_session_dialog.cc:80 +#, fuzzy +msgid "Track/Bus Outputs" +msgstr "Ausgänge" + +#: new_session_dialog.cc:83 +#, fuzzy +msgid "Advanced Options" +msgstr "Geschwindigkeitseditor" + +#: new_session_dialog.cc:91 +#, fuzzy +msgid "Open Recent Session" +msgstr "Sitzung" + +#: new_session_dialog.cc:127 +#, fuzzy +msgid "Open Session File :" +msgstr "Sitzung" + +#: new_session_dialog.cc:274 +#, fuzzy +msgid "New Session" +msgstr "Sitzung" + +#: new_session_dialog.cc:276 +#, fuzzy +msgid "Open Session" +msgstr "Sitzung" + +#: new_session_dialog.cc:281 +#, fuzzy +msgid "ardour: session control" +msgstr "Ardour: Neue Sitzung" + +#: new_session_dialog.cc:310 +#, fuzzy +msgid "select template" +msgstr "Voreinstellung" + +#: new_session_dialog.cc:316 +#, fuzzy +msgid "select session file" +msgstr "Auswahl zu Schleife machen" + +#: new_session_dialog.cc:325 +#, fuzzy +msgid "select directory" +msgstr "Auswahl zu Schleife machen" + +#: option_editor.cc:76 msgid "SMPTE offset is negative" msgstr "" -#: option_editor.cc:101 +#: option_editor.cc:102 #, fuzzy msgid "ardour: options editor" msgstr "Ardour: Einstellungen" -#: option_editor.cc:102 +#: option_editor.cc:103 #, fuzzy msgid "ardour_option_editor" msgstr "Ardour: Einstellungen" -#: option_editor.cc:126 +#: option_editor.cc:127 msgid "Paths/Files" msgstr "Pfade- und Dateinamen" -#: option_editor.cc:127 +#: option_editor.cc:128 msgid "Kbd/Mouse" msgstr "" -#: option_editor.cc:130 +#: option_editor.cc:131 msgid "Layers & Fades" msgstr "" -#: option_editor.cc:134 +#: option_editor.cc:135 msgid "MIDI" msgstr "" -#: option_editor.cc:176 +#: option_editor.cc:177 msgid "24 FPS" msgstr "" -#: option_editor.cc:178 +#: option_editor.cc:179 msgid "25 FPS" msgstr "" -#: option_editor.cc:180 +#: option_editor.cc:181 msgid "30 FPS" msgstr "" -#: option_editor.cc:186 +#: option_editor.cc:187 msgid "30 FPS drop" msgstr "" -#: option_editor.cc:243 +#: option_editor.cc:244 msgid "session RAID path" msgstr "" -#: option_editor.cc:248 +#: option_editor.cc:249 #, fuzzy msgid "Soundfile Search Paths" msgstr "Ardour: Audio Bibliothek" -#: option_editor.cc:253 +#: option_editor.cc:254 #, fuzzy msgid "Paths" msgstr "Pfade- und Dateinamen" -#: option_editor.cc:267 option_editor.cc:273 option_editor.cc:724 -#: option_editor.cc:751 +#: option_editor.cc:268 option_editor.cc:274 option_editor.cc:723 +#: option_editor.cc:750 #, fuzzy msgid "internal" msgstr "mittelmäßig" -#: option_editor.cc:286 +#: option_editor.cc:287 msgid "Short crossfade length (msecs)" msgstr "" -#: option_editor.cc:298 +#: option_editor.cc:299 msgid "Destructive crossfade length (msecs)" msgstr "" -#: option_editor.cc:366 +#: option_editor.cc:367 msgid "SMPTE Frames/second" msgstr "" -#: option_editor.cc:367 +#: option_editor.cc:368 msgid "SMPTE Offset" msgstr "" -#: option_editor.cc:461 option_editor.cc:468 option_editor.cc:471 -#: option_editor.cc:617 +#: option_editor.cc:462 option_editor.cc:469 option_editor.cc:472 +#: option_editor.cc:618 #, fuzzy msgid "online" msgstr "Verbindungen" @@ -5287,11 +5271,11 @@ msgstr "Verbindungen" #. remember, we have to handle the i18n case where the relative #. lengths of the strings in language N is different than in english. #. -#: option_editor.cc:468 option_editor.cc:469 option_editor.cc:614 +#: option_editor.cc:469 option_editor.cc:470 option_editor.cc:615 msgid "offline" msgstr "" -#: option_editor.cc:669 +#: option_editor.cc:670 msgid "Choose Click" msgstr "" @@ -5299,15 +5283,15 @@ msgstr "" msgid "Choose Click Emphasis" msgstr "" -#: option_editor.cc:804 +#: option_editor.cc:803 msgid "Click audio file" msgstr "" -#: option_editor.cc:810 +#: option_editor.cc:809 msgid "Click emphasis audiofile" msgstr "" -#: option_editor.cc:847 +#: option_editor.cc:846 msgid "" "The auditioner is a dedicated mixer strip used\n" "for listening to specific regions outside the context\n" @@ -5315,37 +5299,37 @@ msgid "" "other mixer strip." msgstr "" -#: option_editor.cc:920 +#: option_editor.cc:919 #, fuzzy msgid "Edit using" msgstr "Mix Gruppen" -#: option_editor.cc:927 option_editor.cc:954 +#: option_editor.cc:926 option_editor.cc:953 msgid "+ button" msgstr "" -#: option_editor.cc:947 +#: option_editor.cc:946 #, fuzzy msgid "Delete using" msgstr "Messungen" -#: option_editor.cc:974 +#: option_editor.cc:973 msgid "Ignore snap using" msgstr "" -#: opts.cc:47 +#: opts.cc:46 msgid "Usage: " msgstr "Aufruf:" -#: opts.cc:48 +#: opts.cc:47 msgid " -v, --version Show version information\n" msgstr " -v, --version Versionsinformation ausgeben\n" -#: opts.cc:49 +#: opts.cc:48 msgid " -h, --help Print this message\n" msgstr " -h, --help Diese Hinweise\n" -#: opts.cc:50 +#: opts.cc:49 msgid "" " -b, --bindings Print all possible keyboard binding " "names\n" @@ -5353,212 +5337,227 @@ msgstr "" " -b, --bindings Alle möglichen Tastenzuweisungsnamen " "ausgeben\n" -#: opts.cc:51 +#: opts.cc:50 #, fuzzy msgid " -n, --show-splash Show splash screen\n" msgstr " -h, --help Diese Hinweise\n" -#: opts.cc:52 +#: opts.cc:51 #, fuzzy msgid "" " -c, --name name Use a specific jack client name, default " "is ardour\n" msgstr " -U, --ui-rcfile=FILENAME Dateiname für UI Einstellungen\n" -#: opts.cc:53 +#: opts.cc:52 #, fuzzy msgid "" " -N, --new session-name Create a new session from the command " "line\n" msgstr " [session-name] Name der zu ladenden Sitzung\n" -#: opts.cc:54 +#: opts.cc:53 msgid "" " -o, --use-hw-optimizations Try to use h/w specific optimizations\n" msgstr "" -#: opts.cc:56 +#: opts.cc:55 #, fuzzy msgid " -V, --novst Do not use VST support\n" msgstr " -h, --help Diese Hinweise\n" -#: opts.cc:58 +#: opts.cc:57 msgid " [session-name] Name of session to load\n" msgstr " [session-name] Name der zu ladenden Sitzung\n" -#: opts.cc:59 +#: opts.cc:58 msgid " -C, --curvetest filename Curve algorithm debugger\n" msgstr "" -#: opts.cc:60 +#: opts.cc:59 #, fuzzy msgid " -g, --gtktheme Allow GTK to load a theme\n" msgstr " -h, --help Diese Hinweise\n" -#: pan_automation_time_axis.cc:59 +#: pan_automation_time_axis.cc:60 msgid "You can't graphically edit panning of more than stream" msgstr "" -#: pan_automation_time_axis.cc:79 +#: pan_automation_time_axis.cc:80 #, fuzzy msgid "add pan automation event" msgstr "Stellen" -#: panner2d.cc:588 panner_ui.cc:393 plugin_ui.cc:833 +#: panner2d.cc:589 panner_ui.cc:435 plugin_ui.cc:834 msgid "Bypass" msgstr "" -#: panner_ui.cc:57 panner_ui.cc:187 +#: panner_ui.cc:58 panner_ui.cc:225 #, fuzzy msgid "link" msgstr "leer" +#: panner_ui.cc:69 +#, fuzzy +msgid "Pan automation mode" +msgstr "Stellen" + #: panner_ui.cc:70 +#, fuzzy +msgid "Pan automation type" +msgstr "Stellen" + +#: panner_ui.cc:81 msgid "panning link control" msgstr "" -#: panner_ui.cc:72 +#: panner_ui.cc:83 msgid "panning link direction" msgstr "" -#: panner_ui.cc:197 +#: panner_ui.cc:235 msgid "L" msgstr "" -#: panner_ui.cc:296 +#: panner_ui.cc:335 +#, c-format +msgid "panner for channel %lu" +msgstr "" + +#: panner_ui.cc:337 #, c-format msgid "panner for channel %u" msgstr "" -#: panner_ui.cc:403 +#: panner_ui.cc:445 #, fuzzy msgid "Reset all" msgstr "bestmöglich" -#: playlist_selector.cc:51 +#: playlist_selector.cc:52 #, fuzzy msgid "ardour: playlists" msgstr "Ardour: Plugins" -#: playlist_selector.cc:58 +#: playlist_selector.cc:59 msgid "Playlists grouped by track" msgstr "" -#: playlist_selector.cc:97 +#: playlist_selector.cc:98 #, fuzzy msgid "ardour: playlist for " msgstr "Ardour: Editor: " -#: playlist_selector.cc:113 +#: playlist_selector.cc:114 #, fuzzy msgid "Other tracks" msgstr "Stille einfügen" -#: playlist_selector.cc:129 +#: playlist_selector.cc:130 msgid "unassigned" msgstr "" -#: plugin_selector.cc:42 +#: plugin_selector.cc:43 msgid "ardour: plugins" msgstr "Ardour: Plugins" -#: plugin_selector.cc:55 +#: plugin_selector.cc:56 #, fuzzy msgid "Available LADSPA Plugins" msgstr "Verfügbare LADSPA Plugins" -#: plugin_selector.cc:56 +#: plugin_selector.cc:57 msgid "Type" msgstr "Typ" -#: plugin_selector.cc:57 plugin_selector.cc:80 +#: plugin_selector.cc:58 plugin_selector.cc:81 msgid "# Inputs" msgstr "Eingänge" -#: plugin_selector.cc:58 plugin_selector.cc:81 +#: plugin_selector.cc:59 plugin_selector.cc:82 msgid "# Outputs" msgstr "Ausgänge" -#: plugin_selector.cc:67 +#: plugin_selector.cc:68 msgid "Plugins to be Connected to Insert" msgstr "" -#: plugin_selector.cc:79 +#: plugin_selector.cc:80 #, fuzzy msgid "Available plugins" msgstr "Verfügbare LADSPA Plugins" -#: plugin_selector.cc:97 +#: plugin_selector.cc:98 msgid "Add a plugin to the effect list" msgstr "Plugin zur Effektliste hinzufügen" -#: plugin_selector.cc:99 +#: plugin_selector.cc:102 msgid "Remove a plugin from the effect list" msgstr "Plugin aus der Effektliste entfernen" -#: plugin_selector.cc:101 +#: plugin_selector.cc:104 msgid "Update available plugins" msgstr "Verfügbare Plugins auffrischen" -#: plugin_selector.cc:123 +#: plugin_selector.cc:126 msgid "LADSPA" msgstr "" -#: plugin_selector.cc:126 +#: plugin_selector.cc:129 msgid "VST" msgstr "" -#: plugin_ui.cc:83 +#: plugin_ui.cc:84 msgid "" "unknown type of editor-supplying plugin (note: no VST support in this " "version of ardour)" msgstr "" -#: plugin_ui.cc:138 +#: plugin_ui.cc:139 msgid "Presets" msgstr "" -#: plugin_ui.cc:229 +#: plugin_ui.cc:230 #, fuzzy msgid "Controls" msgstr "Verbindungen" -#: plugin_ui.cc:266 +#: plugin_ui.cc:267 msgid "Plugin Editor: could not build control element for port %1" msgstr "" -#: plugin_ui.cc:357 +#: plugin_ui.cc:358 #, fuzzy -msgid "automation control" +msgid "Automation control" msgstr "Stellen" -#: plugin_ui.cc:853 +#: plugin_ui.cc:854 msgid "Plugin preset %1 not found" msgstr "" -#: plugin_ui.cc:863 +#: plugin_ui.cc:864 #, fuzzy msgid "Name of New Preset:" msgstr "Name für neue Verbindung:" -#: redirect_automation_line.cc:53 +#: redirect_automation_line.cc:54 msgid "redirect automation created for non-plugin" msgstr "" -#: redirect_automation_time_axis.cc:93 +#: redirect_automation_time_axis.cc:94 #, fuzzy msgid "add automation event to " msgstr "Stellen" -#: redirect_box.cc:222 +#: redirect_box.cc:223 msgid "New send" msgstr "" -#: redirect_box.cc:223 +#: redirect_box.cc:224 msgid "Show send controls" msgstr "" -#: redirect_box.cc:377 +#: redirect_box.cc:383 msgid "" "You attempted to add a plugin (%1).\n" "The plugin has %2 inputs\n" @@ -5569,7 +5568,7 @@ msgid "" "part of the signal." msgstr "" -#: redirect_box.cc:389 +#: redirect_box.cc:395 msgid "" "You attempted to add a plugin (%1).\n" "The plugin has %2 inputs\n" @@ -5581,7 +5580,7 @@ msgid "" "support this type of configuration." msgstr "" -#: redirect_box.cc:402 +#: redirect_box.cc:408 msgid "" "You attempted to add a plugin (%1).\n" "\n" @@ -5594,34 +5593,34 @@ msgid "" "Ardour does not understand what to do in such situations.\n" msgstr "" -#: redirect_box.cc:493 +#: redirect_box.cc:495 msgid "Pre-fader inserts, sends & plugins:" msgstr "" -#: redirect_box.cc:496 +#: redirect_box.cc:498 msgid "Post-fader inserts, sends & plugins:" msgstr "" -#: redirect_box.cc:642 +#: redirect_box.cc:644 msgid "" "You cannot reorder this set of redirects\n" "in that way because the inputs and\n" "outputs do not work correctly." msgstr "" -#: redirect_box.cc:747 +#: redirect_box.cc:749 #, fuzzy msgid "rename redirect" msgstr "Ardour: Region umbenennen" -#: redirect_box.cc:824 redirect_box.cc:872 +#: redirect_box.cc:826 redirect_box.cc:874 msgid "" "Copying the set of redirects on the clipboard failed,\n" "probably because the I/O configuration of the plugins\n" "could not match the configuration of this track." msgstr "" -#: redirect_box.cc:894 +#: redirect_box.cc:896 #, fuzzy msgid "" "Do you really want to remove all redirects from this track?\n" @@ -5630,7 +5629,7 @@ msgstr "" "Wollen Sie wirklich die Spur \"%1\" löschen?\n" "(Kann nicht rückgängig gemacht werden!)" -#: redirect_box.cc:897 +#: redirect_box.cc:899 #, fuzzy msgid "" "Do you really want to remove all redirects from this bus?\n" @@ -5639,248 +5638,260 @@ msgstr "" "Wollen Sie wirklich die Spur \"%1\" löschen?\n" "(Kann nicht rückgängig gemacht werden!)" -#: redirect_box.cc:902 +#: redirect_box.cc:904 #, fuzzy msgid "Yes, remove them all" msgstr "Ja, entfernen." -#: redirect_box.cc:938 +#: redirect_box.cc:940 #, fuzzy msgid "ardour: %1" msgstr "Ardour: " -#: redirect_box.cc:980 +#: redirect_box.cc:982 #, fuzzy msgid "ardour: %1: %2 (by %3)" msgstr "Ardour: " #. new stuff -#: redirect_box.cc:1052 +#: redirect_box.cc:1054 msgid "New Plugin ..." msgstr "" -#: redirect_box.cc:1053 +#: redirect_box.cc:1055 #, fuzzy msgid "New Insert" msgstr "Neuer Eingang" -#: redirect_box.cc:1054 +#: redirect_box.cc:1056 msgid "New Send ..." msgstr "" -#: redirect_box.cc:1066 +#: redirect_box.cc:1068 #, fuzzy msgid "Deselect All" msgstr "Auswahl" -#: redirect_box.cc:1073 +#: redirect_box.cc:1075 #, fuzzy msgid "Activate all" msgstr "Aktiv" -#: redirect_box.cc:1074 +#: redirect_box.cc:1076 #, fuzzy msgid "Deactivate all" msgstr "Alles deaktivieren" -#: region_editor.cc:44 +#: region_editor.cc:45 msgid "NAME:" msgstr "" -#: region_editor.cc:45 +#: region_editor.cc:46 msgid "lock" msgstr "" -#: region_editor.cc:47 +#: region_editor.cc:48 msgid "opaque" msgstr "" -#: region_editor.cc:52 +#: region_editor.cc:49 region_editor.cc:192 region_editor.cc:226 +msgid "active" +msgstr "" + +#: region_editor.cc:50 +msgid "visible" +msgstr "" + +#: region_editor.cc:53 msgid "Layer" msgstr "Schicht" -#: region_editor.cc:60 +#: region_editor.cc:54 +msgid "play" +msgstr "" + +#: region_editor.cc:61 msgid "ENVELOPE" msgstr "" -#: region_editor.cc:106 +#: region_editor.cc:107 #, fuzzy msgid "mute this region" msgstr "Name für Region:" -#: region_editor.cc:107 +#: region_editor.cc:108 msgid "regions underneath this one cannot be heard" msgstr "" -#: region_editor.cc:108 +#: region_editor.cc:109 msgid "prevent any changes to this region" msgstr "" -#: region_editor.cc:109 +#: region_editor.cc:110 msgid "use the gain envelope during playback" msgstr "" -#: region_editor.cc:110 +#: region_editor.cc:111 msgid "show the gain envelope" msgstr "" -#: region_editor.cc:111 +#: region_editor.cc:112 msgid "use fade in curve during playback" msgstr "" -#: region_editor.cc:112 +#: region_editor.cc:113 msgid "use fade out curve during playback" msgstr "" -#: region_editor.cc:113 +#: region_editor.cc:114 msgid "audition this region" msgstr "" -#: region_editor.cc:146 +#: region_editor.cc:147 msgid "START:" msgstr "" -#: region_editor.cc:148 +#: region_editor.cc:149 msgid "END:" msgstr "" -#: region_editor.cc:150 +#: region_editor.cc:151 msgid "LENGTH:" msgstr "" -#: region_editor.cc:190 +#: region_editor.cc:191 msgid "FADE IN" msgstr "" -#: region_editor.cc:192 region_editor.cc:226 +#: region_editor.cc:193 region_editor.cc:227 msgid "msecs" msgstr "" -#: region_editor.cc:224 +#: region_editor.cc:225 msgid "FADE OUT" msgstr "" -#: region_editor.cc:264 +#: region_editor.cc:265 msgid "ardour: region " msgstr "Ardour: Region" -#: region_editor.cc:401 +#: region_editor.cc:402 msgid "fade in edit" msgstr "" -#: region_editor.cc:413 +#: region_editor.cc:414 #, fuzzy msgid "fade out edit" msgstr "Ardour: Editor" -#: regionview.cc:1140 +#: regionview.cc:1146 #, fuzzy msgid "add gain control point" msgstr "Synchronisationspunkt entfernen" -#: route_params_ui.cc:88 +#: route_params_ui.cc:89 msgid "Tracks/Buses" msgstr "" -#: route_params_ui.cc:108 +#: route_params_ui.cc:109 msgid "Pre-fader Redirects" msgstr "" -#: route_params_ui.cc:109 +#: route_params_ui.cc:110 msgid "Post-fader Redirects" msgstr "" -#: route_params_ui.cc:141 +#: route_params_ui.cc:144 #, fuzzy msgid "ardour: track/bus inspector" msgstr "Ardour: Editor" -#: route_params_ui.cc:142 +#: route_params_ui.cc:145 #, fuzzy msgid "ardour_route_parameters" msgstr "Ardour: Route" -#: route_params_ui.cc:199 +#: route_params_ui.cc:202 msgid "route display list item for renamed route not found!" msgstr "" -#: route_params_ui.cc:451 +#: route_params_ui.cc:453 msgid "NO TRACK" msgstr "" -#: route_params_ui.cc:693 +#: route_params_ui.cc:695 #, fuzzy msgid "ardour: track/bus inspector: " msgstr "Ardour: Editor" -#: route_params_ui.cc:697 +#: route_params_ui.cc:699 msgid "No Route Selected" msgstr "Keine Route ausgewählt" -#: route_params_ui.cc:698 +#: route_params_ui.cc:700 #, fuzzy msgid "ardour: track/bus/inspector: no route selected" msgstr "Ardour: Route: keine Route ausgewählt" #. ctrl-shift-click applies change to all routes -#: route_ui.cc:133 +#: route_ui.cc:134 #, fuzzy msgid "mute change" msgstr "Bereich" #. ctrl-shift-click applies change to all routes #. ctrl-alt-click: exclusively solo this track, not a toggle */ -#: route_ui.cc:208 route_ui.cc:218 +#: route_ui.cc:209 route_ui.cc:219 #, fuzzy msgid "solo change" msgstr "Bereich" -#: route_ui.cc:281 +#: route_ui.cc:282 msgid "rec-enable change" msgstr "" -#: route_ui.cc:472 +#: route_ui.cc:479 #, fuzzy msgid "Solo-safe" msgstr "solo" -#: route_ui.cc:480 route_ui.cc:523 +#: route_ui.cc:487 route_ui.cc:530 msgid "MIDI Bind" msgstr "" -#: route_ui.cc:494 +#: route_ui.cc:501 msgid "Pre Fader" msgstr "" -#: route_ui.cc:501 +#: route_ui.cc:508 msgid "Post Fader" msgstr "" -#: route_ui.cc:508 +#: route_ui.cc:515 msgid "Control Outs" msgstr "" -#: route_ui.cc:515 +#: route_ui.cc:522 msgid "Main Outs" msgstr "" -#: route_ui.cc:552 +#: route_ui.cc:559 msgid "mix group solo change" msgstr "" -#: route_ui.cc:586 +#: route_ui.cc:593 msgid "mix group mute change" msgstr "" -#: route_ui.cc:602 +#: route_ui.cc:609 msgid "mix group rec-enable change" msgstr "" -#: route_ui.cc:619 visual_time_axis.cc:236 +#: route_ui.cc:626 visual_time_axis.cc:237 msgid "ardour: color selection" msgstr "Ardour: Farbe auswählen" -#: route_ui.cc:695 +#: route_ui.cc:702 #, fuzzy msgid "" "Do you really want to remove track \"%1\" ?\n" @@ -5891,17 +5902,17 @@ msgstr "" "Wollen Sie wirklich die Spur \"%1\" löschen?\n" "(Kann nicht rückgängig gemacht werden!)" -#: route_ui.cc:697 +#: route_ui.cc:704 msgid "" "Do you really want to remove bus \"%1\" ?\n" "(cannot be undone)" msgstr "" -#: route_ui.cc:701 visual_time_axis.cc:278 +#: route_ui.cc:708 visual_time_axis.cc:279 msgid "Yes, remove it." msgstr "Ja, entfernen." -#: route_ui.cc:730 +#: route_ui.cc:737 #, fuzzy msgid "New Name: " msgstr "Neuer Name: " @@ -5959,150 +5970,151 @@ msgstr "" msgid "Name for Field" msgstr "Name für Region:" -#: sfdb_ui.cc:333 +#: sfdb_ui.cc:335 msgid "Split Channels" msgstr "" -#: sfdb_ui.cc:340 +#: sfdb_ui.cc:342 msgid "Create a region for each channel" msgstr "" -#: sfdb_ui.cc:342 +#: sfdb_ui.cc:344 msgid "Embed" msgstr "" -#: sfdb_ui.cc:344 +#: sfdb_ui.cc:346 msgid "Link to an external file" msgstr "" -#: sfdb_ui.cc:346 +#: sfdb_ui.cc:348 msgid "Import" msgstr "Importieren" -#: sfdb_ui.cc:348 +#: sfdb_ui.cc:350 msgid "Copy a file to the session folder" msgstr "" -#: sfdb_ui.cc:412 +#: sfdb_ui.cc:414 msgid "programming error: %1" msgstr "" -#: tempo_dialog.cc:17 tempo_dialog.cc:34 +#: tempo_dialog.cc:18 tempo_dialog.cc:35 msgid "Beats per minute" msgstr "" -#: tempo_dialog.cc:20 tempo_dialog.cc:37 tempo_dialog.cc:153 -#: tempo_dialog.cc:171 +#: tempo_dialog.cc:21 tempo_dialog.cc:38 tempo_dialog.cc:203 +#: tempo_dialog.cc:221 msgid "Bar" msgstr "" -#: tempo_dialog.cc:21 tempo_dialog.cc:38 tempo_dialog.cc:154 -#: tempo_dialog.cc:172 +#: tempo_dialog.cc:22 tempo_dialog.cc:39 tempo_dialog.cc:204 +#: tempo_dialog.cc:222 msgid "Beat" msgstr "" -#: tempo_dialog.cc:23 tempo_dialog.cc:40 tempo_dialog.cc:155 -#: tempo_dialog.cc:173 +#: tempo_dialog.cc:24 tempo_dialog.cc:41 tempo_dialog.cc:205 +#: tempo_dialog.cc:223 #, fuzzy msgid "Location" msgstr "Stellen" -#: tempo_dialog.cc:149 tempo_dialog.cc:167 +#: tempo_dialog.cc:199 tempo_dialog.cc:217 msgid "Meter denominator" msgstr "" -#: tempo_dialog.cc:150 tempo_dialog.cc:168 +#: tempo_dialog.cc:200 tempo_dialog.cc:218 msgid "Beats per bar" msgstr "" -#: tempo_dialog.cc:186 tempo_dialog.cc:197 +#: tempo_dialog.cc:236 tempo_dialog.cc:247 msgid "whole (1)" msgstr "" -#: tempo_dialog.cc:187 tempo_dialog.cc:199 +#: tempo_dialog.cc:237 tempo_dialog.cc:249 msgid "second (2)" msgstr "" -#: tempo_dialog.cc:188 tempo_dialog.cc:201 +#: tempo_dialog.cc:238 tempo_dialog.cc:251 msgid "third (3)" msgstr "" -#: tempo_dialog.cc:189 tempo_dialog.cc:203 tempo_dialog.cc:211 +#: tempo_dialog.cc:239 tempo_dialog.cc:253 tempo_dialog.cc:261 msgid "quarter (4)" msgstr "" -#: tempo_dialog.cc:190 tempo_dialog.cc:205 +#: tempo_dialog.cc:240 tempo_dialog.cc:255 msgid "eighth (8)" msgstr "" -#: tempo_dialog.cc:191 tempo_dialog.cc:207 +#: tempo_dialog.cc:241 tempo_dialog.cc:257 msgid "sixteenth (16)" msgstr "" -#: tempo_dialog.cc:192 tempo_dialog.cc:209 +#: tempo_dialog.cc:242 tempo_dialog.cc:259 msgid "thirty-second (32)" msgstr "" -#: tempo_dialog.cc:321 +#: tempo_dialog.cc:420 msgid "garbaged note type entry (%1)" msgstr "" -#: tempo_dialog.cc:331 +#: tempo_dialog.cc:430 msgid "incomprehensible note type entry (%1)" msgstr "" -#: time_axis_view.cc:111 +#: time_axis_view.cc:112 msgid "gTortnam" msgstr "" -#: time_axis_view.cc:548 +#: time_axis_view.cc:549 msgid "Largest" msgstr "" -#: time_axis_view.cc:549 +#: time_axis_view.cc:550 #, fuzzy msgid "Large" msgstr "Schicht" -#: time_axis_view.cc:550 +#: time_axis_view.cc:551 #, fuzzy msgid "Larger" msgstr "Schicht" -#: time_axis_view.cc:552 +#: time_axis_view.cc:553 msgid "Smaller" msgstr "" -#: time_axis_view.cc:553 +#: time_axis_view.cc:554 #, fuzzy msgid "Small" msgstr "Alle zeigen" -#: time_axis_view.cc:869 +#: time_axis_view.cc:870 msgid "unknown track height name \"%1\" in XML GUI information" msgstr "" -#: time_axis_view_item.cc:71 +#. first constructed item sets up font info +#: time_axis_view_item.cc:79 msgid "TimeAxisViewItemName" msgstr "" -#: time_axis_view_item.cc:271 +#: time_axis_view_item.cc:298 msgid "new duration %1 frames is out of bounds for %2" msgstr "" -#: time_selection.cc:40 +#: time_selection.cc:41 msgid "programming error: request for non-existent audio range (%1)!" msgstr "" -#: utils.cc:106 utils.cc:149 +#: utils.cc:107 utils.cc:150 msgid "bad XPM header %1" msgstr "" -#: utils.cc:331 +#: utils.cc:332 msgid "missing RGBA style for \"%1\"" msgstr "" -#: visual_time_axis.cc:275 +#: visual_time_axis.cc:276 msgid "" "Do you really want to remove track \"%1\" ?\n" "(cannot be undone)" @@ -6110,14 +6122,77 @@ msgstr "" "Wollen Sie wirklich die Spur \"%1\" löschen?\n" "(Kann nicht rückgängig gemacht werden!)" -#: visual_time_axis.cc:324 +#: visual_time_axis.cc:325 msgid "new name: " msgstr "Neuer Name: " -#: visual_time_axis.cc:335 +#: visual_time_axis.cc:336 msgid "A track already exists with that name" msgstr "" +#, fuzzy +#~ msgid "set selected trackview" +#~ msgstr "Stille einfügen" + +#, fuzzy +#~ msgid "set selected control point" +#~ msgstr "Synchronisationspunkt entfernen" + +#, fuzzy +#~ msgid "set selected regionview" +#~ msgstr "Auswahl zu Schleife machen" + +#, fuzzy +#~ msgid "Start a new session\n" +#~ msgstr "Bitte mittels des \"Sitzung\"-Menüs\n" + +#~ msgid "via Session menu" +#~ msgstr "eine Sitzung laden oder eine neue erstellen!" + +#, fuzzy +#~ msgid "Advanced" +#~ msgstr "Feld hinzufügen..." + +#, fuzzy +#~ msgid "Select a File" +#~ msgstr "Auswahl" + +#~ msgid "RECORD" +#~ msgstr "AUFNAHME" + +#~ msgid "INPUT" +#~ msgstr "EINGANG" + +#~ msgid "OUTPUT" +#~ msgstr "AUSGANG" + +#, fuzzy +#~ msgid "Gain automation mode" +#~ msgstr "Stellen" + +#, fuzzy +#~ msgid "Gain automation type" +#~ msgstr "Stellen" + +#, fuzzy +#~ msgid "trim" +#~ msgstr "Streifen" + +#, fuzzy +#~ msgid "gain automation mode" +#~ msgstr "Stellen" + +#, fuzzy +#~ msgid "gain automation state" +#~ msgstr "Stellen" + +#, fuzzy +#~ msgid "pan automation state" +#~ msgstr "Stellen" + +#~ msgid "no group" +#~ msgstr "keine Gruppe" + #, fuzzy #~ msgid "normal" #~ msgstr "Ardour: Region" @@ -6304,9 +6379,6 @@ msgstr "" #~ msgid "AND" #~ msgstr "UND" -#~ msgid "OR" -#~ msgstr "ODER" - #~ msgid "Results" #~ msgstr "Ergebnisse" @@ -6316,16 +6388,9 @@ msgstr "" #~ msgid "Ardour: Search Results" #~ msgstr "Ardour: Suchergebnisse" -#~ msgid "Mix Groups" -#~ msgstr "Mix Gruppen" - #~ msgid "Name for new mix group" #~ msgstr "Name für neue Mix Gruppe" -#, fuzzy -#~ msgid "Session name:" -#~ msgstr "Name der Sitzung" - #, fuzzy #~ msgid "Create" #~ msgstr "Abschnitt erzeugen:" @@ -6338,17 +6403,9 @@ msgstr "" #~ msgid "new session setup" #~ msgstr "Name der Sitzung" -#, fuzzy -#~ msgid "Session template" -#~ msgstr "Name der Sitzung" - #~ msgid "blank" #~ msgstr "leer" -#, fuzzy -#~ msgid "No template" -#~ msgstr "Voreinstellung" - #, fuzzy #~ msgid "Slave to MTC" #~ msgstr "MTC senden" diff --git a/gtk2_ardour/po/el_GR.po b/gtk2_ardour/po/el_GR.po index 1e017f9740..e737aa7ca0 100644 --- a/gtk2_ardour/po/el_GR.po +++ b/gtk2_ardour/po/el_GR.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: 0.99beta23\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-04-25 17:46-0400\n" +"POT-Creation-Date: 2006-06-21 18:09-0400\n" "PO-Revision-Date: 2005-01-11\n" "Last-Translator: Muadibas \n" "Language-Team: Hellenic(Greek) \n" @@ -15,144 +15,144 @@ msgstr "" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" -#: about.cc:119 +#: about.cc:120 msgid "Paul Davis" msgstr "" -#: about.cc:120 +#: about.cc:121 #, fuzzy msgid "Jesse Chappell" msgstr "Επιλογή όλων" -#: about.cc:121 +#: about.cc:122 msgid "Taybin Rutkin" msgstr "" -#: about.cc:122 +#: about.cc:123 msgid "Marcus Andersson" msgstr "" -#: about.cc:123 +#: about.cc:124 msgid "Jeremy Hall" msgstr "" -#: about.cc:124 +#: about.cc:125 msgid "Steve Harris" msgstr "" -#: about.cc:125 +#: about.cc:126 msgid "Tim Mayberry" msgstr "" -#: about.cc:126 +#: about.cc:127 msgid "Mark Stewart" msgstr "" -#: about.cc:127 +#: about.cc:128 msgid "Sam Chessman" msgstr "" -#: about.cc:128 +#: about.cc:129 msgid "Jack O'Quin" msgstr "" -#: about.cc:129 +#: about.cc:130 msgid "Matt Krai" msgstr "" -#: about.cc:130 +#: about.cc:131 msgid "Ben Bell" msgstr "" -#: about.cc:131 +#: about.cc:132 msgid "Gerard van Dongen" msgstr "" -#: about.cc:132 +#: about.cc:133 msgid "Thomas Charbonnel" msgstr "" -#: about.cc:133 +#: about.cc:134 msgid "Nick Mainsbridge" msgstr "" -#: about.cc:134 +#: about.cc:135 msgid "Colin Law" msgstr "" -#: about.cc:135 +#: about.cc:136 msgid "Sampo Savolainen" msgstr "" -#: about.cc:136 +#: about.cc:137 msgid "Joshua Leach" msgstr "" -#: about.cc:137 +#: about.cc:138 msgid "Rob Holland" msgstr "" -#: about.cc:138 +#: about.cc:139 msgid "Per Sigmond" msgstr "" -#: about.cc:139 +#: about.cc:140 msgid "Doug Mclain" msgstr "" -#: about.cc:140 +#: about.cc:141 msgid "Petter Sundlöf" msgstr "" -#: about.cc:145 +#: about.cc:146 msgid "" "French:\n" "\tAlain Fréhel \n" msgstr "" -#: about.cc:146 +#: about.cc:147 msgid "" "German:\n" "\tKarsten Petersen \n" msgstr "" -#: about.cc:147 +#: about.cc:148 msgid "" "Italian:\n" "\tFilippo Pappalardo \n" msgstr "" -#: about.cc:148 +#: about.cc:149 msgid "" "Portuguese:\n" "\tRui Nuno Capela \n" msgstr "" -#: about.cc:149 +#: about.cc:150 msgid "" "Brazilian Portuguese:\n" "\tAlexander da Franca Fernandes \n" "\tChris Ross \n" msgstr "" -#: about.cc:151 +#: about.cc:152 msgid "" "Spanish:\n" "\t Alex Krohn \n" msgstr "" -#: about.cc:152 +#: about.cc:153 msgid "" "Russian:\n" "\t Igor Blinov \n" msgstr "" -#: about.cc:180 +#: about.cc:181 #, fuzzy msgid "Copyright (C) 1999-2005 Paul Davis\n" msgstr "Πνευματικα Δικαιώματα 1999-2004 Paul Davis" -#: about.cc:181 +#: about.cc:182 #, fuzzy msgid "" "Ardour comes with ABSOLUTELY NO WARRANTY\n" @@ -164,7 +164,7 @@ msgstr "" "Το παÏόν ειναι δωÏεάν λογισμικό, είστε ευπÏόσδεκτοι να το επαναδιανείμετε \n" "υπό ειδικοÏÏ‚ ÏŒÏους; διαβάστε το αÏχείο COPYING για λεπτομέÏειες.\n" -#: about.cc:187 +#: about.cc:188 #, fuzzy msgid "" "%1\n" @@ -173,53 +173,53 @@ msgstr "" "Ardour: %1\n" "(Κτισμένο με ardour/gtk %2 libardour: %3.%4.%5)" -#: actions.cc:260 +#: actions.cc:261 #, fuzzy msgid "programmer error: %1 %2" msgstr "σφάλμα Ï€ÏογÏαμματισμοÏ: " -#: add_route_dialog.cc:61 +#: add_route_dialog.cc:62 msgid "ardour: add track/bus" msgstr "ardour: Εισαγωγή καναλιοÏ/διαÏλου" #. path = "1" -#: add_route_dialog.cc:62 editor_route_list.cc:72 +#: add_route_dialog.cc:63 editor_route_list.cc:73 msgid "Tracks" msgstr "Κανάλια" #. path = "0" -#: add_route_dialog.cc:63 editor_route_list.cc:69 +#: add_route_dialog.cc:64 editor_route_list.cc:70 msgid "Busses" msgstr "Δίαυλοι" -#: add_route_dialog.cc:95 plugin_ui.cc:832 +#: add_route_dialog.cc:96 plugin_ui.cc:833 msgid "Add" msgstr "ΠÏόσθεση" -#: add_route_dialog.cc:113 +#: add_route_dialog.cc:114 msgid "Name (template)" msgstr "Όνομα (Ï€Ïοσχέδιο)" -#: add_route_dialog.cc:119 +#: add_route_dialog.cc:120 #, fuzzy msgid "Channel Configuration" msgstr "Διάταξη" -#: add_route_dialog.cc:176 editor.cc:131 editor.cc:3660 time_axis_view.cc:551 +#: add_route_dialog.cc:177 editor.cc:134 editor.cc:3688 time_axis_view.cc:552 msgid "Normal" msgstr "Κανονικό" -#: add_route_dialog.cc:178 +#: add_route_dialog.cc:179 #, fuzzy msgid "Tape" msgstr "ΑÏχή:" -#: add_route_dialog.cc:195 +#: add_route_dialog.cc:196 #, fuzzy msgid "Mono" msgstr "mono" -#: add_route_dialog.cc:197 +#: add_route_dialog.cc:198 #, fuzzy msgid "Stereo" msgstr "stereo" @@ -305,27 +305,11 @@ msgstr "ΑΚΡΟΑΣΗ" msgid "SOLO" msgstr "ΣΟΛΟ" -#: ardour_ui.cc:207 -msgid "" -"You cannot record-enable\n" -"track %1\n" -"because it has no input connections.\n" -"You would be wasting space recording silence." -msgstr "" - -#: ardour_ui.cc:236 -msgid "no vertical meter strip image found" -msgstr "" - -#: ardour_ui.cc:243 -msgid "no horizontal meter strip image found" -msgstr "" - -#: ardour_ui.cc:410 +#: ardour_ui.cc:375 msgid "quit" msgstr "Έξοδος" -#: ardour_ui.cc:419 +#: ardour_ui.cc:384 msgid "" "Ardour was unable to save your session.\n" "\n" @@ -334,33 +318,33 @@ msgid "" "\"Just quit\" option." msgstr "" -#: ardour_ui.cc:438 +#: ardour_ui.cc:403 msgid "ardour: save session?" msgstr "ardour: αποθήκευση συνεδÏίας;" -#: ardour_ui.cc:445 +#: ardour_ui.cc:410 msgid "Don't %1" msgstr "Μη %1" -#: ardour_ui.cc:447 +#: ardour_ui.cc:412 msgid "Just %1" msgstr "Απλά %1" -#: ardour_ui.cc:449 +#: ardour_ui.cc:414 msgid "Save and %1" msgstr "Αποθήκευση και %1" -#: ardour_ui.cc:461 +#: ardour_ui.cc:426 #, fuzzy msgid "session" msgstr "ΣυνεδÏία" -#: ardour_ui.cc:463 +#: ardour_ui.cc:428 #, fuzzy msgid "snapshot" msgstr "Στιγμιότυπο" -#: ardour_ui.cc:465 +#: ardour_ui.cc:430 #, fuzzy msgid "" "The %1\"%2\"\n" @@ -379,80 +363,80 @@ msgstr "" "\n" "τί θέλετε να κάνετε;" -#: ardour_ui.cc:479 +#: ardour_ui.cc:444 msgid "Prompter" msgstr "Υποβολέας" -#: ardour_ui.cc:538 +#: ardour_ui.cc:503 #, fuzzy, c-format msgid "disconnected" msgstr "ΑποσÏνδεση" -#: ardour_ui.cc:545 +#: ardour_ui.cc:510 #, fuzzy, c-format msgid "SR: %.1f kHz / %4.1f msecs" msgstr "SR: %.1f kHz" -#: ardour_ui.cc:549 +#: ardour_ui.cc:514 #, c-format msgid "SR: %u kHz / %4.1f msecs" msgstr "" -#: ardour_ui.cc:562 +#: ardour_ui.cc:527 #, c-format msgid "DSP Load: %.1f%%" msgstr "ΦοÏτίο DSP: %.1f%%" -#: ardour_ui.cc:572 +#: ardour_ui.cc:537 #, fuzzy, c-format msgid "Buffers p:%%% c:%%%" msgstr "Buffers p:%5.0f%% c:%5.0f%%" -#: ardour_ui.cc:599 +#: ardour_ui.cc:564 msgid "space: 24hrs+" msgstr "χώÏος : 24hrs+" -#: ardour_ui.cc:629 +#: ardour_ui.cc:594 #, c-format msgid "space: %02dh:%02dm:%02ds" msgstr "χώÏος: %02dh:%02dm:%02ds" -#: ardour_ui.cc:668 +#: ardour_ui.cc:633 msgid "programming error: impossible control method" msgstr "Σφάλμα Ï€ÏογÏαμματισμοÏ: Μη-πιθανή μέθοδος ελέγχου" -#: ardour_ui.cc:776 new_session_dialog.cc:89 +#: ardour_ui.cc:741 new_session_dialog.cc:294 #, fuzzy msgid "Recent Sessions" msgstr "Άνοιγμα συνεδÏίας" #. ardour sessions are folders -#: ardour_ui.cc:867 +#: ardour_ui.cc:834 msgid "open session" msgstr "Άνοιγμα συνεδÏίας" -#: ardour_ui.cc:873 +#: ardour_ui.cc:840 #, fuzzy msgid "Ardour sessions" msgstr "ardour_νέα_συνεδÏία" -#: ardour_ui.cc:906 +#: ardour_ui.cc:873 msgid "Patience is a virtue.\n" msgstr "Η Υπομονή ειναι ΧÏυσός.\n" -#: ardour_ui.cc:915 +#: ardour_ui.cc:882 msgid "You cannot add a track without a session already loaded." msgstr "Δεν γίνεται να Ï€Ïοστεθεί κανάλι χωÏίς ήδη φοÏτωμένη συνεδÏία." -#: ardour_ui.cc:922 +#: ardour_ui.cc:889 msgid "could not create new audio track" msgstr "Δεν γίνεται να δημιουÏγηθεί νέο ηχητικό κανάλι" -#: ardour_ui.cc:926 +#: ardour_ui.cc:893 msgid "could not create new audio bus" msgstr "Δεν γίνεται να δημιουÏγηθεί νέος ηχητικός δίαυλος" -#: ardour_ui.cc:945 +#: ardour_ui.cc:912 msgid "" "There are insufficient JACK ports available\n" "to create a new track or bus.\n" @@ -460,14 +444,14 @@ msgid "" "restart JACK with more ports." msgstr "" -#: ardour_ui.cc:1069 +#: ardour_ui.cc:1036 msgid "" "Please create 1 or more track\n" "before trying to record.\n" "Check the Session menu." msgstr "" -#: ardour_ui.cc:1298 +#: ardour_ui.cc:1265 #, fuzzy msgid "" "JACK has either been shutdown or it\n" @@ -480,57 +464,55 @@ msgstr "" "δεν ήταν αÏκετά γÏήγοÏο. ΚαλÏτεÏα να αποθηκεÏσετε τη\n" "συνεδÏία και να επανακινήσετε και τον JACK και το Ardour." -#: ardour_ui.cc:1315 +#: ardour_ui.cc:1282 msgid "Unable to create all required ports" msgstr "" -#: ardour_ui.cc:1323 +#: ardour_ui.cc:1290 #, fuzzy msgid "Unable to start the session running" msgstr "ΑÏχή της συνεδÏίας" -#: ardour_ui.cc:1459 +#: ardour_ui.cc:1426 msgid "No Stream" msgstr "Δεν υπάÏχει Ïοή(No stream)" -#: ardour_ui.cc:1486 ardour_ui.cc:1505 +#: ardour_ui.cc:1453 ardour_ui.cc:1472 msgid "none" msgstr "Κανένα" -#: ardour_ui.cc:1495 ardour_ui.cc:1514 automation_time_axis.cc:183 -#: automation_time_axis.cc:212 automation_time_axis.cc:459 mixer_strip.cc:174 -#: mixer_strip.cc:186 mixer_strip.cc:881 plugin_ui.cc:391 plugin_ui.cc:634 +#: ardour_ui.cc:1462 ardour_ui.cc:1481 msgid "off" msgstr "εκτός" -#: ardour_ui.cc:1538 +#: ardour_ui.cc:1505 #, fuzzy msgid "Name of New Snapshot" msgstr "Όνομα για στιγμιότυπο" -#: ardour_ui.cc:1684 +#: ardour_ui.cc:1651 msgid "Name for mix template:" msgstr "Όνομα για Ï€Ïοσχεδίο μίξεως:" -#: ardour_ui.cc:1685 +#: ardour_ui.cc:1652 msgid "-template" msgstr "-Ï€Ïοσχέδιο" -#: ardour_ui.cc:1836 +#: ardour_ui.cc:1809 msgid "" "You do not have write access to this session.\n" "This prevents the session from being loaded." msgstr "" -#: ardour_ui.cc:1849 ardour_ui.cc:1904 +#: ardour_ui.cc:1822 ardour_ui.cc:1877 msgid "Session \"%1 (snapshot %2)\" did not load successfully" msgstr "Η ΣυνεδÏία \"%1 (στιγμιότυπο %2)\" δεν φοÏτώθηκε επιτυχώς" -#: ardour_ui.cc:1960 +#: ardour_ui.cc:1933 msgid "No audio files were ready for cleanup" msgstr "" -#: ardour_ui.cc:1964 +#: ardour_ui.cc:1937 msgid "" "If this seems suprising, \n" "check for any existing snapshots.\n" @@ -538,25 +520,25 @@ msgid "" "require some unused files to continue to exist." msgstr "" -#: ardour_ui.cc:1973 +#: ardour_ui.cc:1946 msgid "ardour: cleanup" msgstr "ardour: εκκαθάÏιση" -#: ardour_ui.cc:2009 ardour_ui.cc:2015 +#: ardour_ui.cc:1982 ardour_ui.cc:1988 #, fuzzy msgid "files were" msgstr "αÏχεία" -#: ardour_ui.cc:2011 ardour_ui.cc:2017 +#: ardour_ui.cc:1984 ardour_ui.cc:1990 #, fuzzy msgid "file was" msgstr "αÏχεία" -#: ardour_ui.cc:2058 +#: ardour_ui.cc:2031 msgid "Are you sure you want to cleanup?" msgstr "" -#: ardour_ui.cc:2063 +#: ardour_ui.cc:2036 msgid "" "Cleanup is a destructive operation.\n" "ALL undo/redo information will be lost if you cleanup.\n" @@ -564,26 +546,26 @@ msgid "" "location." msgstr "" -#: ardour_ui.cc:2069 +#: ardour_ui.cc:2042 #, fuzzy msgid "Clean Up" msgstr "ΕκκαθάÏιση" -#: ardour_ui.cc:2072 +#: ardour_ui.cc:2045 #, fuzzy msgid "CleanupDialog" msgstr "ΕκκαθάÏιση" -#: ardour_ui.cc:2073 +#: ardour_ui.cc:2046 #, fuzzy msgid "ardour_cleanup" msgstr "ardour: εκκαθάÏιση" -#: ardour_ui.cc:2092 +#: ardour_ui.cc:2065 msgid "cleaned files" msgstr "καθαÏισμένα αÏχεία" -#: ardour_ui.cc:2093 +#: ardour_ui.cc:2066 #, fuzzy msgid "" "The following %1 %2 not in use and \n" @@ -599,11 +581,11 @@ msgstr "" "θα ελευθεÏωθοÏν %3 %4bytes\n" "χώÏου στο δίσκο" -#: ardour_ui.cc:2118 +#: ardour_ui.cc:2091 msgid "deleted file" msgstr "διαγÏαμμένα αÏχεία" -#: ardour_ui.cc:2119 +#: ardour_ui.cc:2092 #, fuzzy msgid "" "The following %1 %2 deleted from\n" @@ -612,11 +594,11 @@ msgid "" msgstr "" "Τα ακόλουθα %1 file%2 διεγÏάφησαν, ελευθεÏώνοντας %3 %4bytes χώÏου στο δίσκο" -#: ardour_ui.cc:2242 +#: ardour_ui.cc:2215 msgid "Recording was stopped because your system could not keep up." msgstr "η ΕγγÏαφή διεκόπη διότι το σÏστημά δεν μποÏοÏσε να ανταπεξέλθει." -#: ardour_ui.cc:2265 +#: ardour_ui.cc:2238 msgid "" "The disk system on your computer\n" "was not able to keep up with Ardour.\n" @@ -625,7 +607,7 @@ msgid "" "quickly enough to keep up with recording.\n" msgstr "" -#: ardour_ui.cc:2284 +#: ardour_ui.cc:2257 msgid "" "The disk system on your computer\n" "was not able to keep up with Ardour.\n" @@ -634,7 +616,7 @@ msgid "" "quickly enough to keep up with playback.\n" msgstr "" -#: ardour_ui.cc:2310 +#: ardour_ui.cc:2283 msgid "" "This session appears to have been in\n" "middle of recording when ardour or\n" @@ -645,366 +627,366 @@ msgid "" "what you would like to do.\n" msgstr "" -#: ardour_ui.cc:2320 +#: ardour_ui.cc:2293 msgid "Recover from crash" msgstr "" -#: ardour_ui.cc:2321 +#: ardour_ui.cc:2294 msgid "Ignore crash data" msgstr "" -#: ardour_ui.cc:2339 +#: ardour_ui.cc:2312 #, fuzzy msgid "Could not disconnect from JACK" msgstr "Δεν γινόταν να συνδεθώ στον JACK server σαν \"%1\"" -#: ardour_ui.cc:2352 +#: ardour_ui.cc:2325 #, fuzzy msgid "Could not reconnect to JACK" msgstr "Δεν γινόταν να συνδεθώ στον JACK server σαν \"%1\"" -#: ardour_ui2.cc:59 +#: ardour_ui2.cc:60 msgid "UI: cannot setup editor" msgstr "UI: Ο 'editor' δεν μποÏεί να εγεÏθεί" -#: ardour_ui2.cc:64 +#: ardour_ui2.cc:65 msgid "UI: cannot setup mixer" msgstr "UI: ο μίκτης δεν μποÏεί να εγεÏθεί" -#: ardour_ui2.cc:90 +#: ardour_ui2.cc:91 msgid "MMC + Local" msgstr "MMC + Τοπικό" -#: ardour_ui2.cc:91 +#: ardour_ui2.cc:92 msgid "MMC" msgstr "MMC" -#: ardour_ui2.cc:92 +#: ardour_ui2.cc:93 msgid "Local" msgstr "Τοπικό" -#: ardour_ui2.cc:109 +#: ardour_ui2.cc:110 msgid "MMC ID" msgstr "MMC ID" -#: ardour_ui2.cc:290 +#: ardour_ui2.cc:291 msgid "Play from playhead" msgstr "ΑναπαÏ/γή από τον ΑναπαÏαγωγέα" -#: ardour_ui2.cc:291 +#: ardour_ui2.cc:292 msgid "Stop playback" msgstr "Διακοπή ΑναπαÏ/γής" -#: ardour_ui2.cc:292 +#: ardour_ui2.cc:293 msgid "Play range/selection" msgstr "ΑναπαÏ/γή διαστήματος/επιλογής" -#: ardour_ui2.cc:293 +#: ardour_ui2.cc:294 msgid "Go to start of session" msgstr "ΑÏχή της συνεδÏίας" -#: ardour_ui2.cc:294 +#: ardour_ui2.cc:295 msgid "Go to end of session" msgstr "Τέλος του συνεδÏίας" -#: ardour_ui2.cc:295 +#: ardour_ui2.cc:296 msgid "Play loop range" msgstr "Επαναληπτική αναπαÏ/γή διαστήματος" -#: ardour_ui2.cc:296 +#: ardour_ui2.cc:297 msgid "Return to last playback start when stopped" msgstr "ΕπιστÏοφή στην τελευταία θεση μετα απο παÏση" -#: ardour_ui2.cc:297 +#: ardour_ui2.cc:298 msgid "Start playback after any locate" msgstr "ΑÏχή αναπαÏ/γής μετά από κάθε τοποθέτηση" -#: ardour_ui2.cc:298 +#: ardour_ui2.cc:299 msgid "Be sensible about input monitoring" msgstr "ΠÏοσοχή στο input monitoring" -#: ardour_ui2.cc:299 +#: ardour_ui2.cc:300 msgid "Start recording at auto-punch start" msgstr "ΈναÏξη εγγÏαφής στην αÏχή αυτο-εναπόθεσης" -#: ardour_ui2.cc:300 +#: ardour_ui2.cc:301 msgid "Stop recording at auto-punch end" msgstr "Λήξη εγγÏαφής στο τέλος αυτο-εναπόθεσης" -#: ardour_ui2.cc:301 +#: ardour_ui2.cc:302 msgid "Enable/Disable audio click" msgstr "ΆÏση/ΠαÏση μετÏονόμου" -#: ardour_ui2.cc:302 +#: ardour_ui2.cc:303 #, fuzzy msgid "Positional sync source" msgstr "Τοποθεσιακό Sync" -#: ardour_ui2.cc:303 +#: ardour_ui2.cc:304 msgid "Does Ardour control the time?" msgstr "" -#: ardour_ui2.cc:304 +#: ardour_ui2.cc:305 msgid "Shuttle speed control" msgstr "Έλεγχος ταχÏτητας Shuttle" -#: ardour_ui2.cc:305 +#: ardour_ui2.cc:306 #, fuzzy, c-format msgid "Select semitones or %%-age for speed display" msgstr "Επιλογή ημιτονίων ή %- για απεικόνιση ταχÏτητος" -#: ardour_ui2.cc:306 +#: ardour_ui2.cc:307 msgid "Current transport speed" msgstr "ΤÏέχουσα ταχÏτητα μεταφοÏάς" -#: ardour_ui2.cc:329 +#: ardour_ui2.cc:330 msgid "Primary clock" msgstr "ΠÏωτεÏον ωÏολόγιον" -#: ardour_ui2.cc:330 +#: ardour_ui2.cc:331 msgid "secondary clock" msgstr "ΔευτεÏέυον ωÏολόγιον" #. XXX: this should really be saved in instant.xml or something similar and restored from there #. Combo's are stupid - they steal space from the entry for the button -#: ardour_ui2.cc:387 ardour_ui2.cc:823 ardour_ui2.cc:836 ardour_ui2.cc:899 -#: ardour_ui2.cc:901 +#: ardour_ui2.cc:388 ardour_ui2.cc:833 ardour_ui2.cc:846 ardour_ui2.cc:909 +#: ardour_ui2.cc:911 msgid "sprung" msgstr "έλασμα" -#: ardour_ui2.cc:388 ardour_ui2.cc:825 ardour_ui2.cc:847 +#: ardour_ui2.cc:389 ardour_ui2.cc:835 ardour_ui2.cc:857 msgid "wheel" msgstr "Ï„Ïοχός" -#: ardour_ui2.cc:450 +#: ardour_ui2.cc:451 msgid "ardour: clock" msgstr "ardour: ΩÏολόγιον" -#: ardour_ui2.cc:595 +#: ardour_ui2.cc:596 #, fuzzy msgid "Maximum speed" msgstr "μεταβλητή ταχÏτητα" -#: ardour_ui2.cc:813 +#: ardour_ui2.cc:823 msgid "st" msgstr "st" -#: ardour_ui2.cc:857 ardour_ui2.cc:880 ardour_ui2.cc:897 +#: ardour_ui2.cc:867 ardour_ui2.cc:890 ardour_ui2.cc:907 msgid "stopped" msgstr "παÏση" -#: ardour_ui_dialogs.cc:152 playlist_selector.cc:69 +#: ardour_ui_dialogs.cc:153 playlist_selector.cc:70 #, fuzzy msgid "close" msgstr "Κλείσιμο" -#: ardour_ui_dialogs.cc:359 ardour_ui_ed.cc:181 +#: ardour_ui_dialogs.cc:360 ardour_ui_ed.cc:184 #, fuzzy msgid "Sound File Browser" msgstr "Βιβλιοθήκη Soundfiles" #. menus + submenus that need action items -#: ardour_ui_ed.cc:69 +#: ardour_ui_ed.cc:72 msgid "Session" msgstr "ΣυνεδÏία" -#: ardour_ui_ed.cc:70 ardour_ui_ed.cc:127 editor.cc:1843 export_dialog.cc:350 +#: ardour_ui_ed.cc:73 ardour_ui_ed.cc:130 editor.cc:1836 export_dialog.cc:350 #: export_dialog.cc:1059 export_dialog.cc:1063 msgid "Export" msgstr "Εξαγωγή" -#: ardour_ui_ed.cc:71 +#: ardour_ui_ed.cc:74 msgid "Cleanup" msgstr "ΕκκαθάÏιση" -#: ardour_ui_ed.cc:72 option_editor.cc:125 +#: ardour_ui_ed.cc:75 option_editor.cc:126 msgid "Sync" msgstr "Sync" -#: ardour_ui_ed.cc:73 ardour_ui_ed.cc:74 +#: ardour_ui_ed.cc:76 ardour_ui_ed.cc:77 #, fuzzy msgid "Options" msgstr "Επεξ/στης Ρυθμίσεων" -#: ardour_ui_ed.cc:75 +#: ardour_ui_ed.cc:78 msgid "Help" msgstr "" -#: ardour_ui_ed.cc:76 +#: ardour_ui_ed.cc:79 msgid "KeyMouse Actions" msgstr "" -#: ardour_ui_ed.cc:77 +#: ardour_ui_ed.cc:80 #, fuzzy msgid "Audio File Format" msgstr "Ηχητικά frames" -#: ardour_ui_ed.cc:78 +#: ardour_ui_ed.cc:81 #, fuzzy msgid "Header" msgstr "ΠÏο Fader" -#: ardour_ui_ed.cc:79 +#: ardour_ui_ed.cc:82 msgid "Data" msgstr "" -#: ardour_ui_ed.cc:80 +#: ardour_ui_ed.cc:83 #, fuzzy msgid "Control Surfaces" msgstr "Control Outs" #. the real actions -#: ardour_ui_ed.cc:84 audio_time_axis.cc:1856 new_session_dialog.cc:342 +#: ardour_ui_ed.cc:87 audio_time_axis.cc:1854 new_session_dialog.cc:529 msgid "New" msgstr "Îέο" -#: ardour_ui_ed.cc:86 new_session_dialog.cc:334 +#: ardour_ui_ed.cc:89 new_session_dialog.cc:517 msgid "Open" msgstr "Άνοιγμα" -#: ardour_ui_ed.cc:87 +#: ardour_ui_ed.cc:90 msgid "Recent" msgstr "ΠÏόσφατο" -#: ardour_ui_ed.cc:88 io_selector.cc:57 io_selector.cc:791 +#: ardour_ui_ed.cc:91 io_selector.cc:58 io_selector.cc:792 msgid "Close" msgstr "Κλείσιμο" -#: ardour_ui_ed.cc:91 route_params_ui.cc:512 +#: ardour_ui_ed.cc:94 route_params_ui.cc:514 msgid "Add Track/Bus" msgstr "ΠÏόσθεση καναλιοÏ/διαÏλου" -#: ardour_ui_ed.cc:102 +#: ardour_ui_ed.cc:105 msgid "Connect" msgstr "ΣÏνδεση" #. -#: ardour_ui_ed.cc:110 +#: ardour_ui_ed.cc:113 msgid "Snapshot" msgstr "Στιγμιότυπο" -#: ardour_ui_ed.cc:113 +#: ardour_ui_ed.cc:116 msgid "Save Template..." msgstr "Αποθήκευση Ï€Ïοσχεδίου..." -#: ardour_ui_ed.cc:116 +#: ardour_ui_ed.cc:119 msgid "Export session to audiofile..." msgstr "Εξαγωγή συνεδÏίας σε αÏχείο..." -#: ardour_ui_ed.cc:119 +#: ardour_ui_ed.cc:122 #, fuzzy msgid "Export selection to audiofile..." msgstr "Εξαγωγή συνεδÏίας σε αÏχείο..." -#: ardour_ui_ed.cc:123 +#: ardour_ui_ed.cc:126 #, fuzzy msgid "Export range markers to audiofile..." msgstr "Εξαγωγή διαστήματος σε αÏχείο..." -#: ardour_ui_ed.cc:130 +#: ardour_ui_ed.cc:133 msgid "Cleanup unused sources" msgstr "ΕκκαθάÏιση αχÏήστων πηγών" -#: ardour_ui_ed.cc:132 +#: ardour_ui_ed.cc:135 msgid "Flush wastebasket" msgstr "Άδειασμα κάδου" -#: ardour_ui_ed.cc:138 ardour_ui_options.cc:381 ardour_ui_options.cc:390 -#: ardour_ui_options.cc:462 +#: ardour_ui_ed.cc:141 ardour_ui_options.cc:408 ardour_ui_options.cc:417 +#: ardour_ui_options.cc:489 msgid "JACK" msgstr "" -#: ardour_ui_ed.cc:139 +#: ardour_ui_ed.cc:142 msgid "Latency" msgstr "" -#: ardour_ui_ed.cc:141 +#: ardour_ui_ed.cc:144 #, fuzzy msgid "Reconnect" msgstr "ΣÏνδεση" -#: ardour_ui_ed.cc:144 mixer_strip.cc:514 mixer_strip.cc:574 +#: ardour_ui_ed.cc:147 mixer_strip.cc:497 mixer_strip.cc:565 msgid "Disconnect" msgstr "ΑποσÏνδεση" -#: ardour_ui_ed.cc:171 +#: ardour_ui_ed.cc:174 msgid "Windows" msgstr "ΠαÏάθυÏα" -#: ardour_ui_ed.cc:172 +#: ardour_ui_ed.cc:175 msgid "start prefix" msgstr "" -#: ardour_ui_ed.cc:173 +#: ardour_ui_ed.cc:176 msgid "Quit" msgstr "Έξοδος" #. windows visibility actions -#: ardour_ui_ed.cc:177 +#: ardour_ui_ed.cc:180 msgid "Maximise Editor Space" msgstr "" -#: ardour_ui_ed.cc:179 +#: ardour_ui_ed.cc:182 #, fuzzy msgid "Show Editor" msgstr "ΕπεξεÏγαστής" -#: ardour_ui_ed.cc:180 +#: ardour_ui_ed.cc:183 #, fuzzy msgid "Show Mixer" msgstr "Μίκτης" -#: ardour_ui_ed.cc:182 +#: ardour_ui_ed.cc:185 msgid "Options Editor" msgstr "Επεξ/στης Ρυθμίσεων" -#: ardour_ui_ed.cc:183 +#: ardour_ui_ed.cc:186 #, fuzzy msgid "Track/Bus Inspector" msgstr "κανάλια/δίαυλοι" -#: ardour_ui_ed.cc:185 +#: ardour_ui_ed.cc:188 msgid "Connections" msgstr "Συνδέσεις" -#: ardour_ui_ed.cc:187 +#: ardour_ui_ed.cc:190 msgid "Locations" msgstr "Τοποθεσίες" -#: ardour_ui_ed.cc:189 +#: ardour_ui_ed.cc:192 msgid "Big Clock" msgstr "Μεγάλο ωÏολόγιον" -#: ardour_ui_ed.cc:191 +#: ardour_ui_ed.cc:194 msgid "About" msgstr "ΠληÏοφοÏίες" -#: ardour_ui_ed.cc:192 +#: ardour_ui_ed.cc:195 #, fuzzy msgid "Colors" msgstr "ΧÏώμα" -#: ardour_ui_ed.cc:194 +#: ardour_ui_ed.cc:197 #, fuzzy msgid "Add Audio Track" msgstr "ΠÏόσθεση καναλιοÏ/διαÏλου" -#: ardour_ui_ed.cc:196 +#: ardour_ui_ed.cc:199 #, fuzzy msgid "Add Audio Bus" msgstr "ΑπόκÏυψη όλων των ΗχοδιαÏλων" -#: ardour_ui_ed.cc:198 +#: ardour_ui_ed.cc:201 msgid "Save" msgstr "Αποθήκευση" -#: ardour_ui_ed.cc:200 editor_actions.cc:254 +#: ardour_ui_ed.cc:203 editor_actions.cc:255 #, fuzzy msgid "Remove Last Capture" msgstr "Απαλοιφή τελευταίας λήψης" #. do-nothing action for the "transport" menu bar item -#: ardour_ui_ed.cc:207 +#: ardour_ui_ed.cc:210 #, fuzzy msgid "Transport" msgstr "ΜεταφÏαστές" @@ -1012,74 +994,74 @@ msgstr "ΜεταφÏαστές" #. these two are not used by key bindings, instead use ToggleRoll for that. these two do show up in #. menus and via button proxies. #. -#: ardour_ui_ed.cc:213 sfdb_ui.cc:57 +#: ardour_ui_ed.cc:216 sfdb_ui.cc:57 msgid "Stop" msgstr "ΠαÏση" -#: ardour_ui_ed.cc:216 +#: ardour_ui_ed.cc:219 msgid "Roll" msgstr "" -#: ardour_ui_ed.cc:220 +#: ardour_ui_ed.cc:223 #, fuzzy msgid "Start/Stop" msgstr "ΑÏχή:" -#: ardour_ui_ed.cc:223 +#: ardour_ui_ed.cc:226 msgid "Stop + Forget Capture" msgstr "" -#: ardour_ui_ed.cc:226 +#: ardour_ui_ed.cc:229 #, fuzzy msgid "Play Loop Range" msgstr "Επαναληπτική αναπαÏ/γή διαστήματος" -#: ardour_ui_ed.cc:229 +#: ardour_ui_ed.cc:232 #, fuzzy msgid "Play Selection" msgstr "ΑναπαÏ/γή επιλεγμένης ΠεÏιοχής" -#: ardour_ui_ed.cc:233 +#: ardour_ui_ed.cc:236 #, fuzzy msgid "Enable Record" msgstr "ΕγγÏαφή" -#: ardour_ui_ed.cc:236 +#: ardour_ui_ed.cc:239 #, fuzzy msgid "Rewind" msgstr "ΠεÏιοχή" -#: ardour_ui_ed.cc:239 +#: ardour_ui_ed.cc:242 msgid "Rewind (Slow)" msgstr "" -#: ardour_ui_ed.cc:242 +#: ardour_ui_ed.cc:245 msgid "Rewind (Fast)" msgstr "" -#: ardour_ui_ed.cc:245 +#: ardour_ui_ed.cc:248 #, fuzzy msgid "Forward" msgstr "νÏξη εμπÏός" -#: ardour_ui_ed.cc:248 +#: ardour_ui_ed.cc:251 msgid "Forward (Slow)" msgstr "" -#: ardour_ui_ed.cc:251 +#: ardour_ui_ed.cc:254 msgid "Forward (Fast)" msgstr "" -#: ardour_ui_ed.cc:254 +#: ardour_ui_ed.cc:257 msgid "Goto Zero" msgstr "" -#: ardour_ui_ed.cc:257 +#: ardour_ui_ed.cc:260 #, fuzzy msgid "Goto Start" msgstr "ΑÏχή:" -#: ardour_ui_ed.cc:260 +#: ardour_ui_ed.cc:263 msgid "Goto End" msgstr "" @@ -1087,29 +1069,29 @@ msgstr "" #. that proxies for these action to be more compact. It would be nice to find a way to override the action #. name appearance on the buttons. #. -#: ardour_ui_ed.cc:269 -#, fuzzy -msgid "" -"Punch\n" -"in" -msgstr "" -"punch\n" -"in" - #: ardour_ui_ed.cc:272 #, fuzzy msgid "" "Punch\n" +"in" +msgstr "" +"punch\n" +"in" + +#: ardour_ui_ed.cc:275 +#, fuzzy +msgid "" +"Punch\n" "out" msgstr "" "punch\n" "out" -#: ardour_ui_ed.cc:275 option_editor.cc:128 +#: ardour_ui_ed.cc:278 option_editor.cc:129 msgid "Click" msgstr "ΜετÏονόμος" -#: ardour_ui_ed.cc:278 +#: ardour_ui_ed.cc:281 #, fuzzy msgid "" "Auto\n" @@ -1118,7 +1100,7 @@ msgstr "" "αυτόματο\n" "input" -#: ardour_ui_ed.cc:281 +#: ardour_ui_ed.cc:284 #, fuzzy msgid "" "Auto\n" @@ -1127,7 +1109,7 @@ msgstr "" "αυτόματη\n" "αναπαÏ/γή" -#: ardour_ui_ed.cc:284 +#: ardour_ui_ed.cc:287 #, fuzzy msgid "" "Auto\n" @@ -1136,283 +1118,283 @@ msgstr "" "αυτόματη\n" "επιστÏοφή" -#: ardour_ui_ed.cc:288 +#: ardour_ui_ed.cc:291 #, fuzzy msgid "" "Time\n" "master" msgstr "JACK master χÏόνου" -#: ardour_ui_ed.cc:291 +#: ardour_ui_ed.cc:294 msgid "Toggle Record Enable Track1" msgstr "" -#: ardour_ui_ed.cc:293 +#: ardour_ui_ed.cc:296 msgid "Toggle Record Enable Track2" msgstr "" -#: ardour_ui_ed.cc:295 +#: ardour_ui_ed.cc:298 msgid "Toggle Record Enable Track3" msgstr "" -#: ardour_ui_ed.cc:297 +#: ardour_ui_ed.cc:300 msgid "Toggle Record Enable Track4" msgstr "" -#: ardour_ui_ed.cc:299 +#: ardour_ui_ed.cc:302 msgid "Toggle Record Enable Track5" msgstr "" -#: ardour_ui_ed.cc:301 +#: ardour_ui_ed.cc:304 msgid "Toggle Record Enable Track6" msgstr "" -#: ardour_ui_ed.cc:303 +#: ardour_ui_ed.cc:306 msgid "Toggle Record Enable Track7" msgstr "" -#: ardour_ui_ed.cc:305 +#: ardour_ui_ed.cc:308 msgid "Toggle Record Enable Track8" msgstr "" -#: ardour_ui_ed.cc:307 +#: ardour_ui_ed.cc:310 msgid "Toggle Record Enable Track9" msgstr "" -#: ardour_ui_ed.cc:309 +#: ardour_ui_ed.cc:312 msgid "Toggle Record Enable Track10" msgstr "" -#: ardour_ui_ed.cc:311 +#: ardour_ui_ed.cc:314 msgid "Toggle Record Enable Track11" msgstr "" -#: ardour_ui_ed.cc:313 +#: ardour_ui_ed.cc:316 msgid "Toggle Record Enable Track12" msgstr "" -#: ardour_ui_ed.cc:315 +#: ardour_ui_ed.cc:318 msgid "Toggle Record Enable Track13" msgstr "" -#: ardour_ui_ed.cc:317 +#: ardour_ui_ed.cc:320 msgid "Toggle Record Enable Track14" msgstr "" -#: ardour_ui_ed.cc:319 +#: ardour_ui_ed.cc:322 msgid "Toggle Record Enable Track15" msgstr "" -#: ardour_ui_ed.cc:321 +#: ardour_ui_ed.cc:324 msgid "Toggle Record Enable Track16" msgstr "" -#: ardour_ui_ed.cc:323 +#: ardour_ui_ed.cc:326 msgid "Toggle Record Enable Track17" msgstr "" -#: ardour_ui_ed.cc:325 +#: ardour_ui_ed.cc:328 msgid "Toggle Record Enable Track18" msgstr "" -#: ardour_ui_ed.cc:327 +#: ardour_ui_ed.cc:330 msgid "Toggle Record Enable Track19" msgstr "" -#: ardour_ui_ed.cc:329 +#: ardour_ui_ed.cc:332 msgid "Toggle Record Enable Track20" msgstr "" -#: ardour_ui_ed.cc:331 +#: ardour_ui_ed.cc:334 msgid "Toggle Record Enable Track21" msgstr "" -#: ardour_ui_ed.cc:333 +#: ardour_ui_ed.cc:336 msgid "Toggle Record Enable Track22" msgstr "" -#: ardour_ui_ed.cc:335 +#: ardour_ui_ed.cc:338 msgid "Toggle Record Enable Track23" msgstr "" -#: ardour_ui_ed.cc:337 +#: ardour_ui_ed.cc:340 msgid "Toggle Record Enable Track24" msgstr "" -#: ardour_ui_ed.cc:339 +#: ardour_ui_ed.cc:342 msgid "Toggle Record Enable Track25" msgstr "" -#: ardour_ui_ed.cc:341 +#: ardour_ui_ed.cc:344 msgid "Toggle Record Enable Track26" msgstr "" -#: ardour_ui_ed.cc:343 +#: ardour_ui_ed.cc:346 msgid "Toggle Record Enable Track27" msgstr "" -#: ardour_ui_ed.cc:345 +#: ardour_ui_ed.cc:348 msgid "Toggle Record Enable Track28" msgstr "" -#: ardour_ui_ed.cc:347 +#: ardour_ui_ed.cc:350 msgid "Toggle Record Enable Track29" msgstr "" -#: ardour_ui_ed.cc:349 +#: ardour_ui_ed.cc:352 msgid "Toggle Record Enable Track30" msgstr "" -#: ardour_ui_ed.cc:351 +#: ardour_ui_ed.cc:354 msgid "Toggle Record Enable Track31" msgstr "" -#: ardour_ui_ed.cc:353 +#: ardour_ui_ed.cc:356 msgid "Toggle Record Enable Track32" msgstr "" -#: ardour_ui_ed.cc:358 +#: ardour_ui_ed.cc:361 msgid "Percentage" msgstr "Ποσοστό" -#: ardour_ui_ed.cc:359 +#: ardour_ui_ed.cc:362 msgid "Semitones" msgstr "Ημιτόνια" -#: ardour_ui_ed.cc:363 +#: ardour_ui_ed.cc:366 msgid "Send MTC" msgstr "Αποστολή MTC" -#: ardour_ui_ed.cc:365 +#: ardour_ui_ed.cc:368 msgid "Send MMC" msgstr "Αποστολή MMC" -#: ardour_ui_ed.cc:367 +#: ardour_ui_ed.cc:370 #, fuzzy msgid "Use MMC" msgstr "Αποστολή MMC" -#: ardour_ui_ed.cc:369 +#: ardour_ui_ed.cc:372 msgid "Send MIDI feedback" msgstr "" -#: ardour_ui_ed.cc:371 +#: ardour_ui_ed.cc:374 #, fuzzy msgid "Use MIDI control" msgstr "ΕξωτεÏικός Έλεγχος MIDI" -#: ardour_ui_ed.cc:374 +#: ardour_ui_ed.cc:377 #, fuzzy -msgid "Connect newtrack inputs to hardware" +msgid "Connect new track inputs to hardware" msgstr "Αυτο-σÏνδεση νέων καναλιών" -#: ardour_ui_ed.cc:392 +#: ardour_ui_ed.cc:396 #, fuzzy msgid "Connect new track outputs to hardware" msgstr "Αυτο-σÏνδεση νέων καναλιών" -#: ardour_ui_ed.cc:394 +#: ardour_ui_ed.cc:398 #, fuzzy msgid "Connect new track outputs to master" msgstr "αυτόματη σÏνδεση outputs καναλιών σε master outs" -#: ardour_ui_ed.cc:396 +#: ardour_ui_ed.cc:400 #, fuzzy msgid "Manually connect new track outputs" msgstr "χειÏοκίνητη σÏνδεση των outputs των καναλιών" -#: ardour_ui_ed.cc:401 +#: ardour_ui_ed.cc:405 #, fuzzy msgid "Hardware monitoring" msgstr "ΧÏήση Hardware Monitoring" -#: ardour_ui_ed.cc:402 +#: ardour_ui_ed.cc:406 #, fuzzy msgid "Software monitoring" msgstr "ΧÏήση Software Monitoring" -#: ardour_ui_ed.cc:403 +#: ardour_ui_ed.cc:407 #, fuzzy msgid "External monitoring" msgstr "ΕξωτεÏικός Έλεγχος MIDI" #. Configuration object options (i.e. not session specific) -#: ardour_ui_ed.cc:407 +#: ardour_ui_ed.cc:411 msgid "Stop plugins with transport" msgstr "Λήξη των plugins με την παÏση" -#: ardour_ui_ed.cc:408 +#: ardour_ui_ed.cc:412 #, fuzzy msgid "Verify remove last capture" msgstr "Απαλοιφή τελευταίας λήψης" -#: ardour_ui_ed.cc:409 +#: ardour_ui_ed.cc:413 msgid "Stop recording on xrun" msgstr "ΠαÏση εγγÏαφής στα xrun" -#: ardour_ui_ed.cc:410 +#: ardour_ui_ed.cc:414 #, fuzzy msgid "Stop transport at session end" msgstr "Στάση αναπαÏαγωγέα στο τέλος της συνεδÏίας" -#: ardour_ui_ed.cc:411 +#: ardour_ui_ed.cc:415 msgid "-12dB gain reduce ffwd/rewind" msgstr "" -#: ardour_ui_ed.cc:412 +#: ardour_ui_ed.cc:416 msgid "Rec-enable stays engaged at stop" msgstr "" #. session options -#: ardour_ui_ed.cc:416 +#: ardour_ui_ed.cc:420 #, fuzzy msgid "Do not run plugins while recording" msgstr "ΛειτουÏγία plugins κατα την εγγÏαφή" -#: ardour_ui_ed.cc:419 +#: ardour_ui_ed.cc:423 msgid "Latched solo" msgstr "ΠÏοσκολλημένο σόλο" -#: ardour_ui_ed.cc:424 +#: ardour_ui_ed.cc:428 #, fuzzy msgid "Solo in-place" msgstr "Σόλο" -#: ardour_ui_ed.cc:426 +#: ardour_ui_ed.cc:430 msgid "Solo via bus" msgstr "Solo μέσω διαÏλου" -#: ardour_ui_ed.cc:429 +#: ardour_ui_ed.cc:433 #, fuzzy msgid "Automatically create crossfades" msgstr "Αυτόματο crossfade στα overlap" -#: ardour_ui_ed.cc:431 +#: ardour_ui_ed.cc:435 msgid "Unmute new full crossfades" msgstr "" -#: ardour_ui_options.cc:379 ardour_ui_options.cc:389 ardour_ui_options.cc:456 +#: ardour_ui_options.cc:406 ardour_ui_options.cc:416 ardour_ui_options.cc:483 msgid "Internal" msgstr "ΕσωτεÏικό" -#: ardour_ui_options.cc:380 ardour_ui_options.cc:459 +#: ardour_ui_options.cc:407 ardour_ui_options.cc:486 #, fuzzy msgid "MTC" msgstr "MMC" -#: audio_clock.cc:1719 editor.cc:185 +#: audio_clock.cc:1742 editor.cc:188 msgid "SMPTE" msgstr "SMPTE" -#: audio_clock.cc:1720 editor.cc:184 editor_rulers.cc:359 +#: audio_clock.cc:1743 editor.cc:187 editor_rulers.cc:360 msgid "Bars:Beats" msgstr "ΜπάÏες:ΚτÏποι" -#: audio_clock.cc:1721 +#: audio_clock.cc:1744 msgid "Minutes:Seconds" msgstr "Λεπτά:ΔεÏτεÏα" -#: audio_clock.cc:1722 +#: audio_clock.cc:1745 msgid "Audio Frames" msgstr "Ηχητικά frames" @@ -1420,288 +1402,310 @@ msgstr "Ηχητικά frames" #. Slowest = 6.6dB/sec falloff at update rate of 40ms #. Slow = 6.8dB/sec falloff at update rate of 40ms #. -#: audio_clock.cc:1723 editor_actions.cc:374 editor_actions.cc:382 +#: audio_clock.cc:1746 editor_actions.cc:375 editor_actions.cc:383 +#: gain_meter.cc:172 panner_ui.cc:89 plugin_ui.cc:392 plugin_ui.cc:635 msgid "Off" msgstr "Εκτός" -#: audio_clock.cc:1725 +#: audio_clock.cc:1748 msgid "Mode" msgstr "ΛειτουÏγία" -#: audio_time_axis.cc:90 mixer_strip.cc:458 +#: audio_time_axis.cc:91 msgid "m" msgstr "m" -#: audio_time_axis.cc:90 mixer_strip.cc:459 +#: audio_time_axis.cc:91 msgid "s" msgstr "s" -#: audio_time_axis.cc:90 +#: audio_time_axis.cc:91 msgid "r" msgstr "r" -#: audio_time_axis.cc:94 +#: audio_time_axis.cc:95 msgid "g" msgstr "g" #. group -#: audio_time_axis.cc:95 +#: audio_time_axis.cc:96 msgid "p" msgstr "p" -#: audio_time_axis.cc:96 automation_time_axis.cc:31 visual_time_axis.cc:73 +#: audio_time_axis.cc:97 automation_time_axis.cc:32 visual_time_axis.cc:74 msgid "h" msgstr "h" #. height -#: audio_time_axis.cc:97 +#: audio_time_axis.cc:98 msgid "a" msgstr "a" -#: audio_time_axis.cc:98 visual_time_axis.cc:72 +#: audio_time_axis.cc:99 visual_time_axis.cc:73 msgid "v" msgstr "v" -#: audio_time_axis.cc:173 +#: audio_time_axis.cc:168 mixer_strip.cc:86 msgid "Record" msgstr "ΕγγÏαφή" -#: audio_time_axis.cc:174 editor_actions.cc:36 +#: audio_time_axis.cc:169 editor_actions.cc:37 mixer_strip.cc:86 msgid "Solo" msgstr "Σόλο" -#: audio_time_axis.cc:175 editor.cc:1767 editor.cc:1866 panner_ui.cc:385 +#: audio_time_axis.cc:170 editor.cc:1760 editor.cc:1859 mixer_strip.cc:86 +#: panner_ui.cc:427 msgid "Mute" msgstr "Σιγή" -#: audio_time_axis.cc:176 +#: audio_time_axis.cc:171 msgid "Edit Group" msgstr "ΔιαμόÏφωση Ομάδας" -#: audio_time_axis.cc:177 visual_time_axis.cc:91 +#: audio_time_axis.cc:172 visual_time_axis.cc:92 msgid "Display Height" msgstr "Απεικόνιση Ïψους" -#: audio_time_axis.cc:178 +#: audio_time_axis.cc:173 msgid "Playlist" msgstr "Playlist" -#: audio_time_axis.cc:179 audio_time_axis.cc:743 +#: audio_time_axis.cc:174 audio_time_axis.cc:741 msgid "Automation" msgstr "Αυτοματισμός" -#: audio_time_axis.cc:180 visual_time_axis.cc:92 +#: audio_time_axis.cc:175 visual_time_axis.cc:93 msgid "Visual options" msgstr "Επιλογές Εμφανίσεως" -#: audio_time_axis.cc:181 visual_time_axis.cc:93 +#: audio_time_axis.cc:176 visual_time_axis.cc:94 msgid "Hide this track" msgstr "ΑπόκÏυψη παÏόντος καναλιοÏ" -#: audio_time_axis.cc:337 +#: audio_time_axis.cc:333 mixer_strip.cc:927 msgid "No group" msgstr "ΧωÏίς ομάδα" -#: audio_time_axis.cc:704 automation_time_axis.cc:448 -#: imageframe_time_axis.cc:256 marker_time_axis.cc:210 +#: audio_time_axis.cc:702 automation_time_axis.cc:450 +#: imageframe_time_axis.cc:255 marker_time_axis.cc:211 msgid "Height" msgstr "Ύψος" -#: audio_time_axis.cc:705 color_manager.cc:40 imageframe_time_axis.cc:257 -#: marker_time_axis.cc:211 +#: audio_time_axis.cc:703 color_manager.cc:41 imageframe_time_axis.cc:256 +#: marker_time_axis.cc:212 msgid "Color" msgstr "ΧÏώμα" -#: audio_time_axis.cc:709 +#: audio_time_axis.cc:707 msgid "Hide all crossfades" msgstr "" -#: audio_time_axis.cc:710 +#: audio_time_axis.cc:708 msgid "Show all crossfades" msgstr "" -#: audio_time_axis.cc:714 mixer_strip.cc:1236 +#: audio_time_axis.cc:712 mixer_strip.cc:1011 #, fuzzy msgid "Remote Control ID" msgstr "απαλοιφή σημείου ελέγχου" -#: audio_time_axis.cc:720 -msgid "show all automation" +#: audio_time_axis.cc:718 +#, fuzzy +msgid "Show all automation" msgstr "Ανάδειξη όλων των αυτοματισμών" -#: audio_time_axis.cc:723 -msgid "show existing automation" +#: audio_time_axis.cc:721 +#, fuzzy +msgid "Show existing automation" msgstr "Ανάδειξη υπαÏχόντων αυτοματισμών" -#: audio_time_axis.cc:726 -msgid "hide all automation" +#: audio_time_axis.cc:724 +#, fuzzy +msgid "Hide all automation" msgstr "ΚÏÏψιμο όλων των αυτοματισμών" -#: audio_time_axis.cc:731 audio_time_axis.cc:1169 editor.cc:215 -msgid "gain" -msgstr "gain" +#: audio_time_axis.cc:729 +#, fuzzy +msgid "Fader" +msgstr "Fades" -#: audio_time_axis.cc:736 audio_time_axis.cc:1209 -msgid "pan" +#: audio_time_axis.cc:734 +#, fuzzy +msgid "Pan" msgstr "pan" -#: audio_time_axis.cc:741 +#: audio_time_axis.cc:739 msgid "Plugins" msgstr "Plugins" -#: audio_time_axis.cc:749 +#: audio_time_axis.cc:747 msgid "Show waveforms" msgstr "Ανάδειξη κυματομοÏφών" -#: audio_time_axis.cc:757 +#: audio_time_axis.cc:755 msgid "Traditional" msgstr "ΠαÏαδοσιακή" -#: audio_time_axis.cc:760 +#: audio_time_axis.cc:758 msgid "Rectified" msgstr "ΑνοÏθωμένή" -#: audio_time_axis.cc:763 +#: audio_time_axis.cc:761 msgid "Waveform" msgstr "ΚυματομοÏφή" -#: audio_time_axis.cc:773 +#: audio_time_axis.cc:771 #, fuzzy -msgid "align with existing material" +msgid "Align with existing material" msgstr "ΥπάÏχον υλικό" -#: audio_time_axis.cc:778 +#: audio_time_axis.cc:776 #, fuzzy -msgid "align with capture time" +msgid "Align with capture time" msgstr "ΧÏόνος Λήψεως" -#: audio_time_axis.cc:784 +#: audio_time_axis.cc:782 #, fuzzy msgid "Alignment" msgstr "ΕυθυγÏάμμιση" -#: audio_time_axis.cc:790 editor.cc:523 editor_actions.cc:59 -#: mixer_strip.cc:1225 +#: audio_time_axis.cc:788 editor.cc:527 editor_actions.cc:60 +#: mixer_strip.cc:1000 mixer_ui.cc:111 msgid "Active" msgstr "ΕνεÏγό" -#: audio_time_axis.cc:795 editor.cc:1929 editor_actions.cc:319 -#: editor_markers.cc:507 imageframe_time_axis.cc:260 location_ui.cc:56 -#: marker_time_axis.cc:214 mixer_strip.cc:1239 +#: audio_time_axis.cc:793 editor.cc:1922 editor_actions.cc:320 +#: editor_markers.cc:508 imageframe_time_axis.cc:259 location_ui.cc:57 +#: marker_time_axis.cc:215 mixer_strip.cc:1014 msgid "Remove" msgstr "Απαλοιφή" -#: audio_time_axis.cc:835 +#: audio_time_axis.cc:833 msgid "Name for playlist" msgstr "Όνομα για playlist" -#: audio_time_axis.cc:837 audio_time_axis.cc:1853 editor_markers.cc:826 -#: editor_mouse.cc:4609 imageframe_time_axis.cc:249 marker_time_axis.cc:207 -#: meter_bridge_strip.cc:223 mixer_strip.cc:1223 redirect_box.cc:749 -#: redirect_box.cc:1063 route_ui.cc:732 visual_time_axis.cc:325 +#: audio_time_axis.cc:835 audio_time_axis.cc:1851 editor_markers.cc:827 +#: editor_mouse.cc:4673 imageframe_time_axis.cc:248 marker_time_axis.cc:208 +#: meter_bridge_strip.cc:224 mixer_strip.cc:998 redirect_box.cc:751 +#: redirect_box.cc:1065 route_ui.cc:739 visual_time_axis.cc:326 msgid "Rename" msgstr "Μετονομασία" -#: audio_time_axis.cc:870 audio_time_axis.cc:910 +#: audio_time_axis.cc:868 audio_time_axis.cc:908 #, fuzzy msgid "Name for Playlist" msgstr "Όνομα για playlist" -#: audio_time_axis.cc:1128 visual_time_axis.cc:382 +#: audio_time_axis.cc:1126 visual_time_axis.cc:383 msgid "a track already exists with that name" msgstr "Κανάλι με αυτό το όνομα ήδη υπάÏχει" -#: audio_time_axis.cc:1412 editor.cc:1490 selection.cc:622 +#: audio_time_axis.cc:1167 editor.cc:218 +msgid "gain" +msgstr "gain" + +#: audio_time_axis.cc:1207 +msgid "pan" +msgstr "pan" + +#: audio_time_axis.cc:1410 editor.cc:1483 selection.cc:634 msgid "programming error: " msgstr "σφάλμα Ï€ÏογÏαμματισμοÏ: " -#: audio_time_axis.cc:1850 +#: audio_time_axis.cc:1848 msgid "Current: %1" msgstr "ΤÏέχον: %1" -#: audio_time_axis.cc:1857 +#: audio_time_axis.cc:1855 msgid "New Copy" msgstr "Îέο αντίγÏαφο" -#: audio_time_axis.cc:1859 +#: audio_time_axis.cc:1857 msgid "Clear Current" msgstr "ΕκκαθάÏιση Ï„Ïέχοντος" -#: audio_time_axis.cc:1861 editor.cc:2031 editor.cc:2107 +#: audio_time_axis.cc:1859 editor.cc:2024 editor.cc:2100 msgid "Select" msgstr "Επιλογή" -#: automation_line.cc:883 +#: automation_line.cc:884 msgid "automation event move" msgstr "μετακίνηση συμβάντος αυτοματισμοÏ" -#: automation_line.cc:885 +#: automation_line.cc:886 msgid "automation range drag" msgstr "έλξη διαστήματος αυτοματισμοÏ" -#: automation_line.cc:1014 region_gain_line.cc:61 +#: automation_line.cc:1015 region_gain_line.cc:62 msgid "remove control point" msgstr "απαλοιφή σημείου ελέγχου" -#: automation_time_axis.cc:32 editor_ops.cc:2813 +#: automation_time_axis.cc:33 editor_ops.cc:2885 msgid "clear" msgstr "εκκαθάÏιση" -#: automation_time_axis.cc:74 +#: automation_time_axis.cc:75 msgid "track height" msgstr "" -#: automation_time_axis.cc:75 +#: automation_time_axis.cc:76 #, fuzzy msgid "automation state" msgstr "Κατάσταση Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï pan" -#: automation_time_axis.cc:76 +#: automation_time_axis.cc:77 #, fuzzy msgid "clear track" msgstr "διαγÏαφή διαστημάτων" -#: automation_time_axis.cc:77 +#: automation_time_axis.cc:78 #, fuzzy msgid "hide track" msgstr "νÏξη καναλιοÏ" -#: automation_time_axis.cc:185 automation_time_axis.cc:223 -#: automation_time_axis.cc:463 mixer_strip.cc:176 mixer_strip.cc:188 -#: plugin_ui.cc:394 plugin_ui.cc:636 region_editor.cc:53 -msgid "play" -msgstr "αναπαÏαγωγή" +#: automation_time_axis.cc:184 automation_time_axis.cc:213 +#: automation_time_axis.cc:461 +msgid "Manual" +msgstr "" -#: automation_time_axis.cc:187 automation_time_axis.cc:234 -#: automation_time_axis.cc:467 mixer_strip.cc:178 mixer_strip.cc:190 -#: plugin_ui.cc:397 plugin_ui.cc:638 -msgid "write" +#: automation_time_axis.cc:186 automation_time_axis.cc:224 +#: automation_time_axis.cc:465 editor.cc:2001 editor.cc:2082 gain_meter.cc:174 +#: panner_ui.cc:91 plugin_ui.cc:395 plugin_ui.cc:637 sfdb_ui.cc:56 +msgid "Play" +msgstr "ΑναπαÏ/γή" + +#: automation_time_axis.cc:188 automation_time_axis.cc:235 +#: automation_time_axis.cc:469 gain_meter.cc:176 panner_ui.cc:93 +#: plugin_ui.cc:398 plugin_ui.cc:639 +#, fuzzy +msgid "Write" msgstr "εγγÏαφή" -#: automation_time_axis.cc:189 automation_time_axis.cc:245 -#: automation_time_axis.cc:471 mixer_strip.cc:180 mixer_strip.cc:192 -#: mixer_strip.cc:887 plugin_ui.cc:400 plugin_ui.cc:640 -msgid "touch" +#: automation_time_axis.cc:190 automation_time_axis.cc:246 +#: automation_time_axis.cc:473 gain_meter.cc:178 panner_ui.cc:95 +#: plugin_ui.cc:401 plugin_ui.cc:641 +#, fuzzy +msgid "Touch" msgstr "άγγιγμα" -#: automation_time_axis.cc:256 option_editor.cc:182 option_editor.cc:188 -#: plugin_ui.cc:403 +#: automation_time_axis.cc:257 option_editor.cc:183 option_editor.cc:189 +#: plugin_ui.cc:404 msgid "???" msgstr "???" -#: automation_time_axis.cc:270 +#: automation_time_axis.cc:271 msgid "clear automation" msgstr "εκκαθάÏιση αυτοματισμοÏ" -#: automation_time_axis.cc:450 editor_actions.cc:317 +#: automation_time_axis.cc:452 editor_actions.cc:318 msgid "Hide" msgstr "ΚÏÏψιμο" -#: automation_time_axis.cc:452 crossfade_edit.cc:76 redirect_box.cc:1055 +#: automation_time_axis.cc:454 crossfade_edit.cc:78 redirect_box.cc:1057 msgid "Clear" msgstr "ΕκκαθάÏιση" -#: automation_time_axis.cc:475 +#: automation_time_axis.cc:477 #, fuzzy msgid "State" msgstr "ΑÏχή:" @@ -1849,822 +1853,811 @@ msgstr "" msgid "color of fill" msgstr "" -#: color_manager.cc:39 +#: color_manager.cc:40 #, fuzzy msgid "Object" msgstr "αντικείμενο" -#: color_manager.cc:77 +#: color_manager.cc:78 #, fuzzy msgid "cannot open color definition file %1: %2" msgstr "Η εισαγωγική εικόνα δεν ανοίγει\"%1\"" -#: crossfade_edit.cc:73 +#: crossfade_edit.cc:75 msgid "ardour: x-fade edit" msgstr "ardour: επεξεÏγασία x-fade" -#: crossfade_edit.cc:77 panner_ui.cc:401 +#: crossfade_edit.cc:79 panner_ui.cc:443 #, fuzzy msgid "Reset" msgstr "reset" -#: crossfade_edit.cc:78 +#: crossfade_edit.cc:80 #, fuzzy msgid "Fade" msgstr "Fades" -#: crossfade_edit.cc:79 +#: crossfade_edit.cc:81 #, fuzzy msgid "Out (dry)" msgstr "out (dry)" -#: crossfade_edit.cc:80 +#: crossfade_edit.cc:82 #, fuzzy msgid "Out" msgstr "Έξοδοι" -#: crossfade_edit.cc:81 +#: crossfade_edit.cc:83 #, fuzzy msgid "In (dry)" msgstr "in (dry)" -#: crossfade_edit.cc:82 +#: crossfade_edit.cc:84 msgid "In" msgstr "" -#: crossfade_edit.cc:84 +#: crossfade_edit.cc:86 #, fuzzy msgid "With Pre-roll" msgstr "με pre-roll" -#: crossfade_edit.cc:85 +#: crossfade_edit.cc:87 #, fuzzy msgid "With Post-roll" msgstr "με post-roll" -#: crossfade_edit.cc:93 +#: crossfade_edit.cc:95 msgid "Fade In" msgstr "Fade In" -#: crossfade_edit.cc:94 +#: crossfade_edit.cc:96 msgid "Fade Out" msgstr "Fade Out" -#: crossfade_edit.cc:170 editor.cc:1842 editor_actions.cc:315 -#: option_editor.cc:129 +#: crossfade_edit.cc:172 editor.cc:1835 editor_actions.cc:316 +#: option_editor.cc:130 msgid "Audition" msgstr "ΑκÏόαση" -#: editor.cc:101 editor.cc:3588 +#: editor.cc:104 editor.cc:3616 msgid "Slide" msgstr "Ολίσθηση" -#: editor.cc:102 editor.cc:3586 +#: editor.cc:105 editor.cc:3614 msgid "Splice" msgstr "Splice" -#: editor.cc:107 editor.cc:3643 export_dialog.cc:78 export_dialog.cc:92 -#: export_dialog.cc:893 export_dialog.cc:1225 +#. note that this menu list starts at zero, not 1, because zero +#. is a valid, if useless, ID. +#. +#. leave some breathing room +#: editor.cc:110 editor.cc:3671 export_dialog.cc:78 export_dialog.cc:92 +#: export_dialog.cc:893 export_dialog.cc:1225 route_ui.cc:437 msgid "None" msgstr "Ουδέν" -#: editor.cc:108 editor.cc:3631 +#: editor.cc:111 editor.cc:3659 #, fuzzy msgid "CD Frames" msgstr "Frames" -#: editor.cc:109 editor.cc:3633 +#: editor.cc:112 editor.cc:3661 msgid "SMPTE Frames" msgstr "SMPTE Frames" -#: editor.cc:110 editor.cc:3635 +#: editor.cc:113 editor.cc:3663 msgid "SMPTE Seconds" msgstr "SMPTE ΔευτεÏόλεπτα" -#: editor.cc:111 editor.cc:3637 +#: editor.cc:114 editor.cc:3665 msgid "SMPTE Minutes" msgstr "SMPTE Λεπτά" -#: editor.cc:112 editor.cc:3639 +#: editor.cc:115 editor.cc:3667 msgid "Seconds" msgstr "ΔευτεÏόλεπτα" -#: editor.cc:113 editor.cc:3641 +#: editor.cc:116 editor.cc:3669 msgid "Minutes" msgstr "Λεπτά" -#: editor.cc:114 editor.cc:3613 +#: editor.cc:117 editor.cc:3641 msgid "Beats/32" msgstr "ΚτÏποι/32" -#: editor.cc:115 editor.cc:3611 +#: editor.cc:118 editor.cc:3639 msgid "Beats/16" msgstr "ΚτÏποι/16" -#: editor.cc:116 editor.cc:3609 +#: editor.cc:119 editor.cc:3637 msgid "Beats/8" msgstr "ΚτÏποι/8" -#: editor.cc:117 editor.cc:3607 +#: editor.cc:120 editor.cc:3635 msgid "Beats/4" msgstr "ΚτÏποι/4" -#: editor.cc:118 editor.cc:3605 +#: editor.cc:121 editor.cc:3633 msgid "Beats/3" msgstr "ΚτÏποι/3" -#: editor.cc:119 editor.cc:3615 +#: editor.cc:122 editor.cc:3643 msgid "Beats" msgstr "ΚτÏποι" -#: editor.cc:120 editor.cc:3617 +#: editor.cc:123 editor.cc:3645 msgid "Bars" msgstr "ΜπάÏες" -#: editor.cc:121 editor.cc:3619 +#: editor.cc:124 editor.cc:3647 msgid "Marks" msgstr "Στίγματα" -#: editor.cc:122 editor.cc:141 editor.cc:3621 editor.cc:3687 +#: editor.cc:125 editor.cc:144 editor.cc:3649 editor.cc:3715 msgid "Edit Cursor" msgstr "ΚέÏσοÏας επεξεÏγασίας" -#: editor.cc:123 editor.cc:3623 +#: editor.cc:126 editor.cc:3651 msgid "Region starts" msgstr "ΑÏχές ΠεÏιοχών" -#: editor.cc:124 editor.cc:3625 +#: editor.cc:127 editor.cc:3653 msgid "Region ends" msgstr "Τέλη ΠεÏιοχών" -#: editor.cc:125 editor.cc:3629 +#: editor.cc:128 editor.cc:3657 msgid "Region syncs" msgstr "ΣυγχÏονισμός ΠεÏιοχών" -#: editor.cc:126 editor.cc:3627 +#: editor.cc:129 editor.cc:3655 msgid "Region bounds" msgstr "ÎŒÏια πεÏιοχών" -#: editor.cc:132 editor.cc:3662 +#: editor.cc:135 editor.cc:3690 msgid "Magnetic" msgstr "Μαγνητικό" -#: editor.cc:137 editor.cc:3679 export_dialog.cc:140 export_dialog.cc:156 +#: editor.cc:140 editor.cc:3707 export_dialog.cc:140 export_dialog.cc:156 #: export_dialog.cc:1068 export_dialog.cc:1072 msgid "Left" msgstr "ΑÏιστεÏÏŒ" -#: editor.cc:138 editor.cc:3681 export_dialog.cc:141 export_dialog.cc:157 +#: editor.cc:141 editor.cc:3709 export_dialog.cc:141 export_dialog.cc:157 msgid "Right" msgstr "Δεξιό" -#: editor.cc:139 editor.cc:3683 +#: editor.cc:142 editor.cc:3711 msgid "Center" msgstr "ΚέντÏο" -#: editor.cc:140 editor.cc:3685 +#: editor.cc:143 editor.cc:3713 msgid "Playhead" msgstr "ΑναπαÏαγωγέας" #. time display buttons -#: editor.cc:183 +#: editor.cc:186 msgid "Mins:Secs" msgstr "Λεπτά:ΔέυτεÏα" -#: editor.cc:186 editor_rulers.cc:353 +#: editor.cc:189 editor_rulers.cc:354 msgid "Frames" msgstr "Frames" -#: editor.cc:187 editor_rulers.cc:373 +#: editor.cc:190 editor_rulers.cc:374 msgid "Tempo" msgstr "ΧÏόνος" -#: editor.cc:188 editor_rulers.cc:367 +#: editor.cc:191 editor_rulers.cc:368 msgid "Meter" msgstr "ΜετÏητής" -#: editor.cc:189 editor_rulers.cc:379 +#: editor.cc:192 editor_rulers.cc:380 msgid "Location Markers" msgstr "Στίγματα Τοποθεσίας" -#: editor.cc:190 editor_rulers.cc:385 +#: editor.cc:193 editor_rulers.cc:386 msgid "Range Markers" msgstr "Στίγματα διαστημάτων" -#: editor.cc:191 editor_rulers.cc:391 +#: editor.cc:194 editor_rulers.cc:392 msgid "Loop/Punch Ranges" msgstr "Διαστήματα Loop/Punch" -#: editor.cc:213 +#: editor.cc:216 msgid "range" msgstr "διάστημα" -#: editor.cc:214 +#: editor.cc:217 msgid "object" msgstr "αντικείμενο" -#: editor.cc:216 +#: editor.cc:219 msgid "zoom" msgstr "zoom" -#: editor.cc:217 +#: editor.cc:220 msgid "timefx" msgstr "timefx" -#: editor.cc:218 +#: editor.cc:221 #, fuzzy msgid "listen" msgstr "link" -#: editor.cc:220 +#: editor.cc:223 msgid "mode" msgstr "λειτουÏγία" -#: editor.cc:221 +#: editor.cc:224 msgid "automation" msgstr "αυτοματισμός" -#: editor.cc:223 +#: editor.cc:226 msgid "Edit Mode" msgstr "ΛειτουÏγία Επεξ/σίας" -#: editor.cc:224 editor_actions.cc:283 +#: editor.cc:227 editor_actions.cc:284 msgid "Snap To" msgstr "Έλξη σε" -#: editor.cc:225 +#: editor.cc:228 msgid "Snap Mode" msgstr "ΛειτουÏγία Έλξεως" -#: editor.cc:226 +#: editor.cc:229 msgid "Zoom Focus" msgstr "Εστίαση Zoom" #. #. nudge -#: editor.cc:234 editor.cc:1907 editor.cc:2073 editor.cc:2129 +#: editor.cc:237 editor.cc:1900 editor.cc:2066 editor.cc:2122 msgid "Nudge" msgstr "ÎÏξη" -#: editor.cc:466 +#: editor.cc:470 msgid "Zoom in" msgstr "Zoom in" -#: editor.cc:467 +#: editor.cc:471 msgid "Zoom out" msgstr "Zoom out" -#: editor.cc:470 +#: editor.cc:474 msgid "Zoom to session" msgstr "Zoom στη συνεδÏία" -#: editor.cc:485 +#: editor.cc:489 msgid "Zoom Span" msgstr "ΕÏÏος Zoom" -#: editor.cc:498 editor.cc:524 editor_actions.cc:61 mixer_ui.cc:85 +#: editor.cc:502 editor.cc:528 editor_actions.cc:62 mixer_ui.cc:86 +#: mixer_ui.cc:112 #, fuzzy msgid "Visible" msgstr "οÏατό" -#: editor.cc:499 editor.cc:522 +#: editor.cc:503 editor.cc:526 #, fuzzy msgid "Name" msgstr "Frames" -#: editor.cc:595 editor.cc:661 +#: editor.cc:602 editor.cc:669 #, fuzzy msgid "Regions" msgstr "ΠεÏιοχή" -#: editor.cc:634 editor.cc:673 +#: editor.cc:642 editor.cc:681 msgid "Chunks" msgstr "Κομμάτια" -#: editor.cc:664 +#: editor.cc:672 #, fuzzy msgid "Tracks/Busses" msgstr "κανάλια/δίαυλοι" -#: editor.cc:667 +#: editor.cc:675 msgid "Snapshots" msgstr "" -#: editor.cc:670 +#: editor.cc:678 msgid "Edit Groups" msgstr "ΠÏόσθεση Ομάδων" -#: editor.cc:719 +#: editor.cc:727 msgid "Nudge region/selection forwards" msgstr "ÎÏξη πεÏιοχής/επιλογής εμπÏός" -#: editor.cc:720 +#: editor.cc:728 msgid "Nudge region/selection backwards" msgstr "ÎÏξη πεÏιοχής/επιλογής πίσω" -#: editor.cc:727 editor_mixer.cc:298 +#: editor.cc:735 editor_mixer.cc:299 msgid "ardour: editor" msgstr "ardour: επεξεÏγαστής" -#: editor.cc:728 +#: editor.cc:736 msgid "ardour_editor" msgstr "ardour_επεξεÏγαστής" -#: editor.cc:1190 +#: editor.cc:1183 msgid "ardour: editor: " msgstr "ardour: επεξεÏγαστής: " #. force name -#: editor.cc:1275 editor.cc:1284 editor_markers.cc:869 +#: editor.cc:1268 editor.cc:1277 editor_markers.cc:870 msgid "Loop" msgstr "Loop" #. force name -#: editor.cc:1289 editor.cc:1298 editor_markers.cc:895 +#: editor.cc:1282 editor.cc:1291 editor_markers.cc:896 msgid "Punch" msgstr "Punch" -#: editor.cc:1446 editor_mouse.cc:1721 +#: editor.cc:1439 editor_mouse.cc:1742 msgid "programming error: fade in canvas item has no regionview data pointer!" msgstr "" "Σφάλμα Ï€ÏογÏαμματισμοÏ: το αντικείμενο 'fade in canvas' δεν διαθέτει δείκτη " "δεδομένων οπτικής πεÏιοχών!" -#: editor.cc:1458 editor.cc:1475 redirect_box.cc:1071 +#: editor.cc:1451 editor.cc:1468 redirect_box.cc:1073 msgid "Deactivate" msgstr "ΑπενεÏγοποίηση" #. activation -#: editor.cc:1460 editor.cc:1477 redirect_box.cc:1069 +#: editor.cc:1453 editor.cc:1470 redirect_box.cc:1071 msgid "Activate" msgstr "ΕνεÏγοποίηση" -#: editor.cc:1465 editor.cc:1482 +#: editor.cc:1458 editor.cc:1475 msgid "Linear" msgstr "ΓÏαμμικό" -#: editor.cc:1466 editor.cc:1483 editor_actions.cc:375 +#: editor.cc:1459 editor.cc:1476 editor_actions.cc:376 msgid "Slowest" msgstr "ΑÏγότατο" -#: editor.cc:1467 editor.cc:1484 editor_actions.cc:376 +#: editor.cc:1460 editor.cc:1477 editor_actions.cc:377 msgid "Slow" msgstr "ΑÏγό" -#: editor.cc:1468 editor.cc:1485 editor_actions.cc:378 +#: editor.cc:1461 editor.cc:1478 editor_actions.cc:379 msgid "Fast" msgstr "ΤαχÏ" -#: editor.cc:1469 editor.cc:1486 editor_actions.cc:380 +#: editor.cc:1462 editor.cc:1479 editor_actions.cc:381 msgid "Fastest" msgstr "ΤαχÏτατο" -#: editor.cc:1596 editor.cc:1604 +#: editor.cc:1589 editor.cc:1597 msgid "Freeze" msgstr "Πάγωμα" -#: editor.cc:1600 +#: editor.cc:1593 msgid "Unfreeze" msgstr "Ξεπάγωμα" -#: editor.cc:1769 editor.cc:1864 +#: editor.cc:1762 editor.cc:1857 #, fuzzy msgid "Unmute" msgstr "σιγή" #. non-operative menu items for menu bar #. show editors -#: editor.cc:1773 editor.cc:2053 editor.cc:2755 editor_actions.cc:26 -#: editor_markers.cc:506 mixer_strip.cc:512 mixer_strip.cc:572 -#: redirect_box.cc:1077 +#: editor.cc:1766 editor.cc:2046 editor.cc:2748 editor_actions.cc:27 +#: editor_markers.cc:507 mixer_strip.cc:495 mixer_strip.cc:563 +#: redirect_box.cc:1079 msgid "Edit" msgstr "ΕπεξεÏγασία" -#: editor.cc:1778 +#: editor.cc:1771 msgid "Convert to short" msgstr "" -#: editor.cc:1780 +#: editor.cc:1773 msgid "Convert to full" msgstr "" -#: editor.cc:1791 +#: editor.cc:1784 #, fuzzy msgid "Crossfade" msgstr "Crossfade" -#: editor.cc:1834 +#: editor.cc:1827 msgid "Popup region editor" msgstr "Εμφάνιση του Ïυθμιστή πεÏιοχής" -#: editor.cc:1835 +#: editor.cc:1828 #, fuzzy msgid "Raise to top layer" msgstr "ΑνόÏθωση πεÏιοχής στο ανώτατο στÏώμα" -#: editor.cc:1836 +#: editor.cc:1829 #, fuzzy msgid "Lower to bottom layer" msgstr "Υποβίβαση πεÏιοχής στο κατώτατο στÏώμα" -#: editor.cc:1838 +#: editor.cc:1831 msgid "Define sync point" msgstr "ΠÏοσδιοÏισμός σημείου συγχÏονισμοÏ" -#: editor.cc:1839 +#: editor.cc:1832 msgid "Remove sync point" msgstr "Απαλοιφή σημείου συγχÏονισμοÏ" -#: editor.cc:1844 +#: editor.cc:1837 #, fuzzy msgid "Bounce" msgstr "Αναπήδηση διαστήματος" -#: editor.cc:1847 +#: editor.cc:1840 #, fuzzy msgid "Analyze region" msgstr "ΑναπαÏ/γή ΠεÏιοχής" -#: editor.cc:1859 +#: editor.cc:1852 msgid "Lock" msgstr "Κλείδωμα" -#: editor.cc:1860 +#: editor.cc:1853 msgid "Unlock" msgstr "Ξεκλείδωμα" -#: editor.cc:1870 +#: editor.cc:1863 msgid "Original position" msgstr "ΠÏωταÏχική θέση" -#: editor.cc:1876 +#: editor.cc:1869 msgid "Toggle envelope visibility" msgstr "" -#: editor.cc:1877 +#: editor.cc:1870 #, fuzzy msgid "Toggle envelope active" msgstr "Διακόπτης ΕνεÏγοÏ" -#: editor.cc:1881 +#: editor.cc:1874 #, fuzzy msgid "DeNormalize" msgstr "Εξομάλυνση" -#: editor.cc:1883 +#: editor.cc:1876 msgid "Normalize" msgstr "Εξομάλυνση" -#: editor.cc:1886 +#: editor.cc:1879 msgid "Reverse" msgstr "ΑντιστÏοφή" #. range related stuff -#: editor.cc:1892 +#: editor.cc:1885 #, fuzzy msgid "Add Range Markers" msgstr "Στίγματα διαστημάτων" -#: editor.cc:1893 +#: editor.cc:1886 #, fuzzy msgid "Set Range" msgstr "ΞεχωÏιστό διάστημα" -#: editor.cc:1902 +#: editor.cc:1895 #, fuzzy msgid "Nudge fwd" msgstr "νÏξη εμπÏός" -#: editor.cc:1903 +#: editor.cc:1896 #, fuzzy msgid "Nudge bwd" msgstr "ÎÏξη" -#: editor.cc:1904 +#: editor.cc:1897 msgid "Nudge fwd by capture offset" msgstr "" -#: editor.cc:1905 +#: editor.cc:1898 msgid "Nudge bwd by capture offset" msgstr "" -#: editor.cc:1914 +#: editor.cc:1907 msgid "Start to edit cursor" msgstr "Από αÏχή μέχÏι κέÏσοÏα επεξεÏγασίας" -#: editor.cc:1915 +#: editor.cc:1908 msgid "Edit cursor to end" msgstr "Από κέÏσοÏα επεξεÏγασίας μέχÏι τέλους" -#: editor.cc:1917 +#: editor.cc:1910 gain_meter.cc:181 gain_meter.cc:813 panner_ui.cc:98 +#: panner_ui.cc:803 msgid "Trim" msgstr "Ισοστάθμιση" -#: editor.cc:1920 +#: editor.cc:1913 msgid "Split" msgstr "ΔιαχωÏισμός" -#: editor.cc:1923 +#: editor.cc:1916 msgid "Make mono regions" msgstr "ΔημιουÏγία mono πεÏιοχών" -#: editor.cc:1926 +#: editor.cc:1919 msgid "Duplicate" msgstr "ΑντιγÏαφή" -#: editor.cc:1927 +#: editor.cc:1920 msgid "Fill Track" msgstr "Γόμωση καναλιοÏ" -#: editor.cc:1931 +#: editor.cc:1924 msgid "Destroy" msgstr "ΚαταστÏοφή" -#: editor.cc:1961 +#: editor.cc:1954 msgid "Play range" msgstr "ΑναπαÏ/γή διαστήματος" -#: editor.cc:1962 +#: editor.cc:1955 msgid "Loop range" msgstr "Loop διαστήματος" -#: editor.cc:1966 +#: editor.cc:1959 #, fuzzy msgid "Analyze range" msgstr "ΑναπαÏ/γή διαστήματος" -#: editor.cc:1970 +#: editor.cc:1963 #, fuzzy msgid "Separate range to track" msgstr "ΞεχωÏιστό διάστημα" -#: editor.cc:1971 +#: editor.cc:1964 #, fuzzy msgid "Separate range to region list" msgstr "θέση επιλεγμένης οπτικής πεÏιοχής" -#: editor.cc:1974 +#: editor.cc:1967 #, fuzzy msgid "Select all in range" msgstr "Επιλογή όλων στο κανάλι" -#: editor.cc:1976 editor.cc:2021 +#: editor.cc:1969 editor.cc:2014 #, fuzzy msgid "Set range to loop range" msgstr "Επιλογή διαστήματος loop" -#: editor.cc:1977 editor.cc:2022 +#: editor.cc:1970 editor.cc:2015 #, fuzzy msgid "Set range to punch range" msgstr "Επιλογή διαστήματος punch" -#: editor.cc:1979 +#: editor.cc:1972 #, fuzzy msgid "Crop region to range" msgstr "Κοπή ΠεÏιοχής στο διάστημα" -#: editor.cc:1980 +#: editor.cc:1973 #, fuzzy msgid "Fill range with region" msgstr "Γέμισμα διαστήματος μ/ΠεÏιοχή" -#: editor.cc:1981 +#: editor.cc:1974 #, fuzzy msgid "Duplicate range" msgstr "ΑντιγÏαφή" -#: editor.cc:1982 +#: editor.cc:1975 msgid "Create chunk from range" msgstr "ΔημιουÏγία ÎºÎ¿Î¼Î¼Î±Ï„Î¹Î¿Ï Î±Ï€ÏŒ διάστημα" -#: editor.cc:1984 +#: editor.cc:1977 msgid "Bounce range" msgstr "Αναπήδηση διαστήματος" -#: editor.cc:1985 +#: editor.cc:1978 #, fuzzy msgid "Export range" msgstr "Εξαγωγή πεÏιοχής" -#: editor.cc:1987 +#: editor.cc:1980 msgid "Range" msgstr "Διάστημα" -#: editor.cc:2002 editor.cc:2087 +#: editor.cc:1995 editor.cc:2080 msgid "Play from edit cursor" msgstr "ΑναπαÏ/γή από ΚέÏσοÏα ΕπεξεÏγασίας" -#: editor.cc:2003 editor.cc:2088 +#: editor.cc:1996 editor.cc:2081 msgid "Play from start" msgstr "ΑναπαÏ/γή από αÏχή" -#: editor.cc:2004 +#: editor.cc:1997 #, fuzzy msgid "Play region" msgstr "ΑναπαÏ/γή ΠεÏιοχής" -#: editor.cc:2006 +#: editor.cc:1999 msgid "Loop Region" msgstr "Loop ΠεÏιοχής" -#: editor.cc:2008 editor.cc:2089 sfdb_ui.cc:56 -msgid "Play" -msgstr "ΑναπαÏ/γή" - -#: editor.cc:2016 editor.cc:2097 +#: editor.cc:2009 editor.cc:2090 msgid "Select All in track" msgstr "Επιλογή όλων στο κανάλι" -#: editor.cc:2017 editor.cc:2098 redirect_box.cc:1065 +#: editor.cc:2010 editor.cc:2091 redirect_box.cc:1067 msgid "Select All" msgstr "Επιλογή όλων" -#: editor.cc:2018 editor.cc:2099 +#: editor.cc:2011 editor.cc:2092 #, fuzzy msgid "Invert selection in track" msgstr "ΑντιστÏοφή στο κανάλι" -#: editor.cc:2019 editor.cc:2100 +#: editor.cc:2012 editor.cc:2093 #, fuzzy msgid "Invert selection" msgstr "μετακίνηση επιλογής" -#: editor.cc:2024 editor.cc:2102 +#: editor.cc:2017 editor.cc:2095 #, fuzzy msgid "Select all after edit cursor" msgstr "Από αÏχή μέχÏι κέÏσοÏα επεξεÏγασίας" -#: editor.cc:2025 editor.cc:2103 +#: editor.cc:2018 editor.cc:2096 #, fuzzy msgid "Select all before edit cursor" msgstr "Από αÏχή μέχÏι κέÏσοÏα επεξεÏγασίας" -#: editor.cc:2026 editor.cc:2104 +#: editor.cc:2019 editor.cc:2097 #, fuzzy msgid "Select all after playhead" msgstr "Θέση από αναπαÏαγωγέα" -#: editor.cc:2027 editor.cc:2105 +#: editor.cc:2020 editor.cc:2098 #, fuzzy msgid "Select all before playhead" msgstr "Θέση από αναπαÏαγωγέα" -#: editor.cc:2028 +#: editor.cc:2021 #, fuzzy msgid "Select all between cursors" msgstr "Από αÏχή μέχÏι κέÏσοÏα επεξεÏγασίας" #. standard editing stuff -#: editor.cc:2039 editor.cc:2115 editor.cc:3455 editor_actions.cc:213 -#: redirect_box.cc:1058 +#: editor.cc:2032 editor.cc:2108 editor.cc:3483 editor_actions.cc:214 +#: redirect_box.cc:1060 msgid "Cut" msgstr "Κοπή" -#: editor.cc:2040 editor.cc:2116 editor.cc:3457 editor_actions.cc:218 -#: redirect_box.cc:1060 +#: editor.cc:2033 editor.cc:2109 editor.cc:3485 editor_actions.cc:219 +#: redirect_box.cc:1062 msgid "Copy" msgstr "ΑντιγÏαφή" -#: editor.cc:2041 +#: editor.cc:2034 #, fuzzy msgid "Paste at edit cursor" msgstr "Από αÏχή μέχÏι κέÏσοÏα επεξεÏγασίας" -#: editor.cc:2042 +#: editor.cc:2035 #, fuzzy msgid "Paste at mouse" msgstr "χÏήση των master outs" -#: editor.cc:2046 editor.cc:3462 +#: editor.cc:2039 editor.cc:3490 msgid "Align" msgstr "ΕυθυγÏάμμιση" -#: editor.cc:2047 editor.cc:3464 +#: editor.cc:2040 editor.cc:3492 msgid "Align Relative" msgstr "ΕυθυγÏάμμιση σχετικών" -#: editor.cc:2051 +#: editor.cc:2044 msgid "Insert chunk" msgstr "ΠÏοσθήκη κομματιοÏ" -#: editor.cc:2058 +#: editor.cc:2051 #, fuzzy msgid "Insert Selected Region" msgstr "θέση επιλεγμένης οπτικής πεÏιοχής" -#: editor.cc:2059 +#: editor.cc:2052 msgid "Insert Existing Audio" msgstr "" -#: editor.cc:2068 editor.cc:2124 +#: editor.cc:2061 editor.cc:2117 msgid "Nudge entire track fwd" msgstr "ÎÏξη ολόκληÏου ÎºÎ±Î½Î±Î»Î¹Î¿Ï ÎµÎ¼Ï€Ïός" -#: editor.cc:2069 editor.cc:2125 +#: editor.cc:2062 editor.cc:2118 msgid "Nudge track after edit cursor fwd" msgstr "ÎÏξη ÎºÎ±Î½Î±Î»Î¹Î¿Ï Î¼ÎµÏ„Î¬ του κέÏσοÏα επεξεÏγασίας εμπÏός" -#: editor.cc:2070 editor.cc:2126 +#: editor.cc:2063 editor.cc:2119 msgid "Nudge entire track bwd" msgstr "ÎÏξη ολοκλήÏου ÎºÎ±Î½Î±Î»Î¹Î¿Ï Ï€Î¯ÏƒÏ‰" -#: editor.cc:2071 editor.cc:2127 +#: editor.cc:2064 editor.cc:2120 msgid "Nudge track after edit cursor bwd" msgstr "ÎÏξη κανάλι μετά του κέÏσοÏα επεξεÏγασίας πίσω" -#: editor.cc:2117 editor.cc:3459 editor_actions.cc:220 redirect_box.cc:1062 +#: editor.cc:2110 editor.cc:3487 editor_actions.cc:221 redirect_box.cc:1064 msgid "Paste" msgstr "Επικόλληση" -#: editor.cc:2637 +#: editor.cc:2630 msgid "select/move objects" msgstr "επιλογή/μετακίνηση αντικειμένων" -#: editor.cc:2638 +#: editor.cc:2631 msgid "select/move ranges" msgstr "επιλογή/μετακίνηση διαστημάτων" -#: editor.cc:2639 +#: editor.cc:2632 msgid "draw gain automation" msgstr "σχεδιασμός Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï Ï„Î¿Ï… gain" -#: editor.cc:2640 +#: editor.cc:2633 msgid "select zoom range" msgstr "επιλογή διαστήματος zoom" -#: editor.cc:2641 +#: editor.cc:2634 msgid "stretch/shrink regions" msgstr "μεγέθυνση/σμίκÏυνση πεÏιοχών" -#: editor.cc:2642 +#: editor.cc:2635 #, fuzzy msgid "listen to specific regions" msgstr "θέση επιλεγμένης οπτικής πεÏιοχής" -#: editor.cc:2753 +#: editor.cc:2746 msgid "Start:" msgstr "ΑÏχή:" -#: editor.cc:2754 +#: editor.cc:2747 msgid "End:" msgstr "Τέλος:" -#: editor.cc:3097 -msgid "set selected trackview" -msgstr "θέση επιλεγμένης οπτικής καναλιοÏ" - -#: editor.cc:3137 -#, fuzzy -msgid "set selected control point" -msgstr "απαλοιφή σημείου ελέγχου" - -#: editor.cc:3246 -msgid "set selected regionview" -msgstr "θέση επιλεγμένης οπτικής πεÏιοχής" - -#: editor.cc:3334 editor.cc:3374 +#: editor.cc:3362 editor.cc:3402 #, fuzzy msgid "set selected regions" msgstr "θέση επιλεγμένης οπτικής πεÏιοχής" -#: editor.cc:3430 editor_actions.cc:203 +#: editor.cc:3458 editor_actions.cc:204 msgid "Undo" msgstr "Undo" -#: editor.cc:3432 +#: editor.cc:3460 msgid "Undo (%1)" msgstr "Undo (%1)" -#: editor.cc:3442 editor_actions.cc:205 +#: editor.cc:3470 editor_actions.cc:206 msgid "Redo" msgstr "Redo" -#: editor.cc:3444 +#: editor.cc:3472 msgid "Redo (%1)" msgstr "Redo (%1)" -#: editor.cc:3478 +#: editor.cc:3506 msgid "... as new track" msgstr "" -#: editor.cc:3479 +#: editor.cc:3507 #, fuzzy msgid "... as new region" msgstr "ευθυγÏάμμιση πεÏιοχής" -#: editor.cc:3481 +#: editor.cc:3509 msgid "Import audio (copy)" msgstr "Εισαγωγή ήχου (αντίγÏαφο)" -#: editor.cc:3484 +#: editor.cc:3512 msgid "Remove last capture" msgstr "Απαλοιφή τελευταίας λήψης" -#: editor.cc:3508 +#: editor.cc:3536 msgid "Duplicate how many times?" msgstr "ΑντιγÏαφή πόσες φοÏές?" -#: editor.cc:3994 +#: editor.cc:4022 msgid "" "Playlist %1 is currently unused.\n" "If left alone, no audio files used by it will be cleaned.\n" @@ -2676,767 +2669,767 @@ msgstr "" "Εάν διαγÏαφεί, τα ηχητικά αÏχεία που χÏησιμοποιοÏνται μόνο απ'αυτήν θα " "διαγÏαφοÏν." -#: editor.cc:4002 +#: editor.cc:4030 msgid "Delete playlist" msgstr "ΔιαγÏαφή λίστας αναπαÏ/γής" -#: editor.cc:4003 +#: editor.cc:4031 msgid "Keep playlist" msgstr "ΔιατήÏηση λίστας αναπαÏ/γής" -#: editor.cc:4004 editor_audio_import.cc:237 editor_ops.cc:1976 -#: editor_timefx.cc:52 export_dialog.cc:971 io_selector.cc:58 -#: io_selector.cc:792 redirect_box.cc:901 tempo_dialog.cc:19 -#: tempo_dialog.cc:36 tempo_dialog.cc:152 tempo_dialog.cc:170 +#: editor.cc:4032 editor_audio_import.cc:236 editor_ops.cc:2048 +#: editor_timefx.cc:71 export_dialog.cc:971 io_selector.cc:59 +#: io_selector.cc:793 redirect_box.cc:903 tempo_dialog.cc:20 +#: tempo_dialog.cc:37 tempo_dialog.cc:202 tempo_dialog.cc:220 msgid "Cancel" msgstr "ΑκÏÏωση" -#: editor.cc:4171 +#: editor.cc:4199 #, fuzzy msgid "new playlists" msgstr "ΔιατήÏηση λίστας αναπαÏ/γής" -#: editor.cc:4179 +#: editor.cc:4207 #, fuzzy msgid "copy playlists" msgstr "ΔιατήÏηση λίστας αναπαÏ/γής" -#: editor.cc:4187 +#: editor.cc:4215 #, fuzzy msgid "clear playlists" msgstr "εκκαθάÏιση playlist" -#: editor_actions.cc:27 +#: editor_actions.cc:28 #, fuzzy msgid "Select regions" msgstr "επιλογή πεÏιοχών" -#: editor_actions.cc:28 +#: editor_actions.cc:29 #, fuzzy msgid "Select range operations" msgstr "επιλογή πεÏιοχών" -#: editor_actions.cc:29 +#: editor_actions.cc:30 #, fuzzy msgid "Move edit cursor" msgstr "Από αÏχή μέχÏι κέÏσοÏα επεξεÏγασίας" -#: editor_actions.cc:30 +#: editor_actions.cc:31 #, fuzzy msgid "Region operations" msgstr "ΠεÏιοχές/δημιουÏγία" -#: editor_actions.cc:31 +#: editor_actions.cc:32 msgid "Tools" msgstr "" -#: editor_actions.cc:32 +#: editor_actions.cc:33 msgid "View" msgstr "" -#: editor_actions.cc:33 +#: editor_actions.cc:34 #, fuzzy msgid "ZoomFocus" msgstr "Εστίαση Zoom" -#: editor_actions.cc:34 +#: editor_actions.cc:35 #, fuzzy msgid "Meter hold" msgstr "ΜετÏητής" -#: editor_actions.cc:35 +#: editor_actions.cc:36 msgid "Meter falloff" msgstr "" -#: editor_actions.cc:37 +#: editor_actions.cc:38 #, fuzzy msgid "Crossfades" msgstr "Crossfade" -#: editor_actions.cc:38 +#: editor_actions.cc:39 #, fuzzy msgid "Monitoring" msgstr "ΧÏήση Hardware Monitoring" -#: editor_actions.cc:39 +#: editor_actions.cc:40 #, fuzzy msgid "Autoconnect" msgstr "ΣÏνδεση" -#: editor_actions.cc:40 +#: editor_actions.cc:41 #, fuzzy msgid "Layering" msgstr "ΣτÏώμα" -#: editor_actions.cc:41 +#: editor_actions.cc:42 #, fuzzy msgid "Metering" msgstr "ΜετÏητής" -#: editor_actions.cc:42 +#: editor_actions.cc:43 msgid "Fall off rate" msgstr "" -#: editor_actions.cc:43 +#: editor_actions.cc:44 msgid "Hold Time" msgstr "" -#: editor_actions.cc:44 +#: editor_actions.cc:45 msgid "Add Existing Audio" msgstr "" #. add named actions for the editor -#: editor_actions.cc:49 +#: editor_actions.cc:50 #, fuzzy msgid "Show Editor Mixer" msgstr "Ανάδειξη όλων των ΔιαδÏόμωνΜίξεως των καναλιών" -#: editor_actions.cc:54 +#: editor_actions.cc:55 #, fuzzy msgid "Span Entire Overlap" msgstr "ΑνόÏθωση πεÏιοχής κατά ένα στÏώμα" -#: editor_actions.cc:56 editor_actions.cc:383 +#: editor_actions.cc:57 editor_actions.cc:384 #, fuzzy msgid "Short" msgstr "θÏÏα" -#: editor_actions.cc:63 +#: editor_actions.cc:64 msgid "Created Automatically" msgstr "" -#: editor_actions.cc:66 +#: editor_actions.cc:67 msgid "Playhead to Next Region Start" msgstr "" -#: editor_actions.cc:68 +#: editor_actions.cc:69 msgid "Playhead to Next Region End" msgstr "" -#: editor_actions.cc:70 +#: editor_actions.cc:71 msgid "Playhead to Next Region Sync" msgstr "" -#: editor_actions.cc:73 +#: editor_actions.cc:74 msgid "Playhead to Previous Region Start" msgstr "" -#: editor_actions.cc:75 +#: editor_actions.cc:76 msgid "Playhead to Previous Region End" msgstr "" -#: editor_actions.cc:77 +#: editor_actions.cc:78 msgid "Playhead to Previous Region Sync" msgstr "" -#: editor_actions.cc:80 +#: editor_actions.cc:81 #, fuzzy msgid "Edit Cursor to Next Region Start" msgstr "Από κέÏσοÏα επεξεÏγασίας μέχÏι τέλους" -#: editor_actions.cc:82 +#: editor_actions.cc:83 #, fuzzy msgid "Edit Cursor to Next Region End" msgstr "Από κέÏσοÏα επεξεÏγασίας μέχÏι τέλους" -#: editor_actions.cc:84 +#: editor_actions.cc:85 #, fuzzy msgid "Edit Cursor to Next Region Sync" msgstr "Από κέÏσοÏα επεξεÏγασίας μέχÏι τέλους" -#: editor_actions.cc:87 +#: editor_actions.cc:88 msgid "Edit Cursor to Previous Region Start" msgstr "" -#: editor_actions.cc:89 +#: editor_actions.cc:90 #, fuzzy msgid "Edit Cursor to Previous Region End" msgstr "Από κέÏσοÏα επεξεÏγασίας μέχÏι τέλους" -#: editor_actions.cc:91 +#: editor_actions.cc:92 #, fuzzy msgid "Edit Cursor to Previous Region Sync" msgstr "Από κέÏσοÏα επεξεÏγασίας μέχÏι τέλους" -#: editor_actions.cc:94 +#: editor_actions.cc:95 msgid "Playhead to Range Start" msgstr "" -#: editor_actions.cc:96 +#: editor_actions.cc:97 #, fuzzy msgid "Playhead to Range End" msgstr "Επαναληπτική αναπαÏ/γή διαστήματος" -#: editor_actions.cc:99 +#: editor_actions.cc:100 #, fuzzy msgid "Edit Cursor to Range Start" msgstr "Από κέÏσοÏα επεξεÏγασίας μέχÏι τέλους" -#: editor_actions.cc:101 +#: editor_actions.cc:102 #, fuzzy msgid "Edit Cursor to Range End" msgstr "Από κέÏσοÏα επεξεÏγασίας μέχÏι τέλους" -#: editor_actions.cc:104 editor_ops.cc:1300 +#: editor_actions.cc:105 editor_ops.cc:1363 #, fuzzy msgid "select all" msgstr "Επιλογή όλων" -#: editor_actions.cc:106 +#: editor_actions.cc:107 #, fuzzy msgid "Select All After Edit Cursor" msgstr "Θέση συγχÏονισμοÏ(sync) απο κέÏσοÏα επεξεÏ/σίας" -#: editor_actions.cc:108 +#: editor_actions.cc:109 msgid "Select All Before Edit Cursor" msgstr "" -#: editor_actions.cc:111 +#: editor_actions.cc:112 #, fuzzy msgid "Select All After Playhead" msgstr "Θέση από αναπαÏαγωγέα" -#: editor_actions.cc:113 +#: editor_actions.cc:114 #, fuzzy msgid "Select All Before Playhead" msgstr "Θέση από αναπαÏαγωγέα" -#: editor_actions.cc:115 +#: editor_actions.cc:116 #, fuzzy msgid "Select All Between Cursors" msgstr "Θέση συγχÏονισμοÏ(sync) απο κέÏσοÏα επεξεÏ/σίας" -#: editor_actions.cc:118 +#: editor_actions.cc:119 #, fuzzy msgid "Select All in Punch Range" msgstr "Θέση Punch Διαστήματος" -#: editor_actions.cc:120 +#: editor_actions.cc:121 #, fuzzy msgid "Select All in Loop Range" msgstr "Επιλογή διαστήματος loop" -#: editor_actions.cc:123 +#: editor_actions.cc:124 msgid "Jump Forward to Mark" msgstr "" -#: editor_actions.cc:125 +#: editor_actions.cc:126 msgid "Jump Backward to Mark" msgstr "" -#: editor_actions.cc:127 +#: editor_actions.cc:128 #, fuzzy msgid "Add Location from Playhead" msgstr "Θέση από αναπαÏαγωγέα" -#: editor_actions.cc:130 +#: editor_actions.cc:131 #, fuzzy msgid "Nudge Forward" msgstr "νÏξη εμπÏός" -#: editor_actions.cc:132 +#: editor_actions.cc:133 #, fuzzy msgid "Nudge Next Forward" msgstr "νÏξη εμπÏός" -#: editor_actions.cc:134 +#: editor_actions.cc:135 #, fuzzy msgid "Nudge Backward" msgstr "ÎÏξη" -#: editor_actions.cc:136 +#: editor_actions.cc:137 #, fuzzy msgid "Nudge Next Backward" msgstr "ÎÏξη ολόκληÏου ÎºÎ±Î½Î±Î»Î¹Î¿Ï ÎµÎ¼Ï€Ïός" -#: editor_actions.cc:139 +#: editor_actions.cc:140 #, fuzzy msgid "Zoom Out" msgstr "Zoom out" -#: editor_actions.cc:141 +#: editor_actions.cc:142 #, fuzzy msgid "Zoom In" msgstr "Zoom in" -#: editor_actions.cc:143 +#: editor_actions.cc:144 #, fuzzy msgid "Zoom to Session" msgstr "Zoom στη συνεδÏία" -#: editor_actions.cc:146 +#: editor_actions.cc:147 #, fuzzy msgid "Scroll Tracks Up" msgstr "Γόμωση καναλιοÏ" -#: editor_actions.cc:148 +#: editor_actions.cc:149 msgid "Scroll Tracks Down" msgstr "" -#: editor_actions.cc:150 +#: editor_actions.cc:151 #, fuzzy msgid "Step Tracks Up" msgstr "νÏξη καναλιοÏ" -#: editor_actions.cc:152 +#: editor_actions.cc:153 msgid "Step Tracks Down" msgstr "" -#: editor_actions.cc:155 +#: editor_actions.cc:156 msgid "Scroll Backward" msgstr "" -#: editor_actions.cc:157 +#: editor_actions.cc:158 msgid "Scroll Forward" msgstr "" -#: editor_actions.cc:159 +#: editor_actions.cc:160 msgid "goto" msgstr "" -#: editor_actions.cc:161 +#: editor_actions.cc:162 #, fuzzy msgid "Center Playhead" msgstr "ΑναπαÏαγωγέας" -#: editor_actions.cc:163 +#: editor_actions.cc:164 #, fuzzy msgid "Center Edit Cursor" msgstr "ΚέÏσοÏας επεξεÏγασίας" -#: editor_actions.cc:165 +#: editor_actions.cc:166 #, fuzzy msgid "Playhead Forward" msgstr "ΑναπαÏαγωγέας" -#: editor_actions.cc:167 +#: editor_actions.cc:168 #, fuzzy msgid "Playhead Backward" msgstr "ΑναπαÏαγωγέας" -#: editor_actions.cc:169 +#: editor_actions.cc:170 #, fuzzy msgid "Playhead to Edit" msgstr "ΑναπαÏαγωγέας" -#: editor_actions.cc:171 +#: editor_actions.cc:172 #, fuzzy msgid "Edit to Playhead" msgstr "Θέση από αναπαÏαγωγέα" -#: editor_actions.cc:174 +#: editor_actions.cc:175 #, fuzzy msgid "Align Regions Start" msgstr "ΑÏχές ΠεÏιοχών" -#: editor_actions.cc:176 +#: editor_actions.cc:177 #, fuzzy msgid "Align Regions Start Relative" msgstr "ευθυγÏάμμιση επιλογής (σχετική)" -#: editor_actions.cc:178 +#: editor_actions.cc:179 #, fuzzy msgid "Align Regions End" msgstr "ευθυγÏάμμιση πεÏιοχής" -#: editor_actions.cc:180 +#: editor_actions.cc:181 #, fuzzy msgid "Align Regions End Relative" msgstr "ΕυθυγÏάμμιση σχετικών" -#: editor_actions.cc:183 +#: editor_actions.cc:184 #, fuzzy msgid "Align Regions Sync" msgstr "ευθυγÏάμμιση πεÏιοχής" -#: editor_actions.cc:185 +#: editor_actions.cc:186 #, fuzzy msgid "Align Regions Sync Relative" msgstr "ΕυθυγÏάμμιση σχετικών" -#: editor_actions.cc:188 +#: editor_actions.cc:189 #, fuzzy msgid "Audition at Mouse" msgstr "ΑκÏόαση" -#: editor_actions.cc:190 +#: editor_actions.cc:191 #, fuzzy msgid "Brush at Mouse" msgstr "χÏήση των master outs" -#: editor_actions.cc:192 +#: editor_actions.cc:193 #, fuzzy msgid "Set Edit Cursor" msgstr "ΚέÏσοÏας επεξεÏγασίας" -#: editor_actions.cc:194 +#: editor_actions.cc:195 #, fuzzy msgid "Mute/Unmute Region" msgstr "ΔημιουÏγία πεÏιοχής" -#: editor_actions.cc:196 +#: editor_actions.cc:197 #, fuzzy msgid "Set Playhead" msgstr "ΑναπαÏαγωγέας" -#: editor_actions.cc:198 +#: editor_actions.cc:199 #, fuzzy msgid "Split Region" msgstr "ΔιαχωÏισμός πεÏιοχής" -#: editor_actions.cc:200 +#: editor_actions.cc:201 #, fuzzy msgid "Set Region Sync Position" msgstr "Με Θέση ΠεÏιοχής" -#: editor_actions.cc:208 +#: editor_actions.cc:209 #, fuzzy msgid "Export Session" msgstr "Εξαγωγή πεÏιοχής" -#: editor_actions.cc:210 +#: editor_actions.cc:211 #, fuzzy msgid "Export Range" msgstr "ΞεχωÏιστό διάστημα" #. Note: for now, editor-delete does the exact same thing as editor-cut -#: editor_actions.cc:216 +#: editor_actions.cc:217 #, fuzzy msgid "Delete" msgstr "διαγÏαφή" -#: editor_actions.cc:222 +#: editor_actions.cc:223 #, fuzzy msgid "Duplicate Region" msgstr "αντιγÏαφή πεÏιοχής" -#: editor_actions.cc:224 +#: editor_actions.cc:225 #, fuzzy msgid "Duplicate Range" msgstr "ΑντιγÏαφή" -#: editor_actions.cc:226 +#: editor_actions.cc:227 msgid "Insert Region" msgstr "ΠÏοσθήκη πεÏιοχής" -#: editor_actions.cc:228 +#: editor_actions.cc:229 #, fuzzy msgid "Reverse Region" msgstr "αντιστÏοφή πεÏιοχών" -#: editor_actions.cc:230 +#: editor_actions.cc:231 #, fuzzy msgid "Normalize Region" msgstr "Εξομάλυνση" -#: editor_actions.cc:232 +#: editor_actions.cc:233 #, fuzzy msgid "crop" msgstr "αντιγÏαφή" -#: editor_actions.cc:234 +#: editor_actions.cc:235 #, fuzzy msgid "Insert Chunk" msgstr "ΠÏοσθήκη κομματιοÏ" -#: editor_actions.cc:237 +#: editor_actions.cc:238 #, fuzzy msgid "Split at edit cursor" msgstr "Από αÏχή μέχÏι κέÏσοÏα επεξεÏγασίας" -#: editor_actions.cc:240 +#: editor_actions.cc:241 #, fuzzy msgid "Start Range" msgstr "ΞεχωÏιστό διάστημα" -#: editor_actions.cc:242 +#: editor_actions.cc:243 msgid "Finish Range" msgstr "" -#: editor_actions.cc:244 +#: editor_actions.cc:245 msgid "Finish add Range" msgstr "" -#: editor_actions.cc:247 +#: editor_actions.cc:248 msgid "Extend Range to End of Region" msgstr "" -#: editor_actions.cc:249 +#: editor_actions.cc:250 #, fuzzy msgid "Extend Range to Start of Region" msgstr "ΑÏχή της συνεδÏίας" -#: editor_actions.cc:252 +#: editor_actions.cc:253 #, fuzzy msgid "Follow Playhead" msgstr "Ακολουθία ΑναπαÏαγωγέα" -#: editor_actions.cc:260 +#: editor_actions.cc:261 #, fuzzy msgid "Zoom Focus Left" msgstr "Εστίαση Zoom" -#: editor_actions.cc:262 +#: editor_actions.cc:263 #, fuzzy msgid "Zoom Focus Right" msgstr "Εστίαση Zoom" -#: editor_actions.cc:264 +#: editor_actions.cc:265 #, fuzzy msgid "Zoom Focus Center" msgstr "Εστίαση Zoom" -#: editor_actions.cc:266 +#: editor_actions.cc:267 #, fuzzy msgid "Zoom Focus Playhead" msgstr "Εστίαση Zoom" -#: editor_actions.cc:268 +#: editor_actions.cc:269 #, fuzzy msgid "Zoom Focus Edit" msgstr "Εστίαση Zoom" -#: editor_actions.cc:274 +#: editor_actions.cc:275 msgid "Object Tool" msgstr "" -#: editor_actions.cc:275 +#: editor_actions.cc:276 #, fuzzy msgid "Range Tool" msgstr "Διάστημα" -#: editor_actions.cc:276 +#: editor_actions.cc:277 msgid "Gain Tool" msgstr "" -#: editor_actions.cc:277 +#: editor_actions.cc:278 #, fuzzy msgid "Zoom Tool" msgstr "Zoom out" -#: editor_actions.cc:278 +#: editor_actions.cc:279 msgid "Timefx Tool" msgstr "" -#: editor_actions.cc:285 +#: editor_actions.cc:286 #, fuzzy msgid "Snap to frame" msgstr "zoom σε καÏέ" -#: editor_actions.cc:286 +#: editor_actions.cc:287 #, fuzzy msgid "Snap to cd frame" msgstr "ΛειτουÏγία Έλξεως" -#: editor_actions.cc:287 +#: editor_actions.cc:288 #, fuzzy msgid "Snap to SMPTE frame" msgstr "SMPTE Frames" -#: editor_actions.cc:288 +#: editor_actions.cc:289 #, fuzzy msgid "Snap to SMPTE seconds" msgstr "SMPTE ΔευτεÏόλεπτα" -#: editor_actions.cc:289 +#: editor_actions.cc:290 #, fuzzy msgid "Snap to SMPTE minutes" msgstr "SMPTE Λεπτά" -#: editor_actions.cc:290 +#: editor_actions.cc:291 #, fuzzy msgid "Snap to seconds" msgstr "ΔευτεÏόλεπτα" -#: editor_actions.cc:291 +#: editor_actions.cc:292 msgid "Snap to minutes" msgstr "" -#: editor_actions.cc:292 +#: editor_actions.cc:293 #, fuzzy msgid "Snap to thirtyseconds" msgstr "Ï„Ïιακοστό-όγδοο (32)" -#: editor_actions.cc:293 +#: editor_actions.cc:294 msgid "Snap to asixteenthbeat" msgstr "" -#: editor_actions.cc:294 +#: editor_actions.cc:295 msgid "Snap to eighths" msgstr "" -#: editor_actions.cc:295 +#: editor_actions.cc:296 msgid "Snap to quarters" msgstr "" -#: editor_actions.cc:296 +#: editor_actions.cc:297 #, fuzzy msgid "Snap to thirds" msgstr "ΛειτουÏγία Έλξεως" -#: editor_actions.cc:297 +#: editor_actions.cc:298 #, fuzzy msgid "Snap to beat" msgstr "ΛειτουÏγία Έλξεως" -#: editor_actions.cc:298 +#: editor_actions.cc:299 #, fuzzy msgid "Snap to bar" msgstr "Έλξη σε" -#: editor_actions.cc:299 +#: editor_actions.cc:300 #, fuzzy msgid "Snap to mark" msgstr "Ï€Ïόσθεση στίγματος χÏόνου" -#: editor_actions.cc:300 +#: editor_actions.cc:301 #, fuzzy msgid "Snap to edit cursor" msgstr "Από αÏχή μέχÏι κέÏσοÏα επεξεÏγασίας" -#: editor_actions.cc:301 +#: editor_actions.cc:302 #, fuzzy msgid "Snap to region start" msgstr "ΑÏχές ΠεÏιοχών" -#: editor_actions.cc:302 +#: editor_actions.cc:303 #, fuzzy msgid "Snap to region end" msgstr "Τέλη ΠεÏιοχών" -#: editor_actions.cc:303 +#: editor_actions.cc:304 #, fuzzy msgid "Snap to region sync" msgstr "ΣυγχÏονισμός ΠεÏιοχών" -#: editor_actions.cc:304 +#: editor_actions.cc:305 #, fuzzy msgid "Snap to region boundary" msgstr "ÎŒÏια πεÏιοχών" #. the region list popup menu -#: editor_actions.cc:313 +#: editor_actions.cc:314 #, fuzzy msgid "Sort" msgstr "θÏÏα" -#: editor_actions.cc:321 +#: editor_actions.cc:322 msgid "Show all" msgstr "Ανάδειξη όλων" -#: editor_actions.cc:322 +#: editor_actions.cc:323 #, fuzzy msgid "Show automatic regions" msgstr "Ανάδειξη όλων των αυτοματισμών" -#: editor_actions.cc:324 +#: editor_actions.cc:325 msgid "Ascending" msgstr "ΑÏξουσα" -#: editor_actions.cc:326 +#: editor_actions.cc:327 msgid "Descending" msgstr "Φθίνουσα" -#: editor_actions.cc:329 +#: editor_actions.cc:330 msgid "By Region Name" msgstr "Με Όνομα ΠεÏιοχής" -#: editor_actions.cc:331 +#: editor_actions.cc:332 msgid "By Region Length" msgstr "Με Μέγεθος ΠεÏιοχής" -#: editor_actions.cc:333 +#: editor_actions.cc:334 msgid "By Region Position" msgstr "Με Θέση ΠεÏιοχής" -#: editor_actions.cc:335 +#: editor_actions.cc:336 msgid "By Region Timestamp" msgstr "Με ΧÏονο-στάμπα ΠεÏιοχής" -#: editor_actions.cc:337 +#: editor_actions.cc:338 msgid "By Region Start in File" msgstr "Με ΑÏχή-στο-αÏχείο της ΠεÏιοχής" -#: editor_actions.cc:339 +#: editor_actions.cc:340 msgid "By Region End in File" msgstr "Με Τέλος-στο -αÏχείο της ΠεÏιοχής" -#: editor_actions.cc:341 +#: editor_actions.cc:342 msgid "By Source File Name" msgstr "Με Όνομα ΑÏχείου Πηγής" -#: editor_actions.cc:343 +#: editor_actions.cc:344 msgid "By Source File Length" msgstr "Με Μέγεθος ΑÏχείου Πηγής" -#: editor_actions.cc:345 +#: editor_actions.cc:346 msgid "By Source File Creation Date" msgstr "Με Ημ/νία ΑÏχείου Πηγής" -#: editor_actions.cc:347 +#: editor_actions.cc:348 msgid "By Source Filesystem" msgstr "Με Filesystem Πηγής" #. the next two are duplicate items with different names for use in two different contexts -#: editor_actions.cc:353 +#: editor_actions.cc:354 #, fuzzy msgid "Add External Audio" msgstr "ΠÏόσθεση σε Λίστα ΕξωτεÏικής ΠεÏιοχής" -#: editor_actions.cc:355 +#: editor_actions.cc:356 #, fuzzy msgid "as Region(s)" msgstr "Έλξη πεÏιοχής(ων)" -#: editor_actions.cc:357 +#: editor_actions.cc:358 #, fuzzy msgid "as Tracks" msgstr "Κανάλια" -#: editor_actions.cc:359 +#: editor_actions.cc:360 #, fuzzy msgid "to Tracks" msgstr "Κανάλια" -#: editor_actions.cc:362 +#: editor_actions.cc:363 #, fuzzy msgid "Show Waveforms" msgstr "Ανάδειξη κυματομοÏφών" -#: editor_actions.cc:363 +#: editor_actions.cc:364 #, fuzzy msgid "Show Waveforms While Recording" msgstr "Ανάδειξη κυματομοÏφών κατά την εγγÏαφή" -#: editor_actions.cc:364 +#: editor_actions.cc:365 #, fuzzy msgid "Show Measures" msgstr "Ανάδειξη γÏαμμών μετÏήσεων" -#: editor_actions.cc:377 editor_actions.cc:384 +#: editor_actions.cc:378 editor_actions.cc:385 msgid "Medium" msgstr "" -#: editor_actions.cc:379 +#: editor_actions.cc:380 #, fuzzy msgid "Faster" msgstr "ΤαχÏ" -#: editor_actions.cc:385 +#: editor_actions.cc:386 msgid "Long" msgstr "" -#: editor_actions.cc:389 +#: editor_actions.cc:390 #, fuzzy msgid "Later is Higher" msgstr "Υποβίβαση πεÏιοχής κατά ένα στÏώμα" -#: editor_actions.cc:390 +#: editor_actions.cc:391 #, fuzzy msgid "Most Recently Moved/Added is Higher" msgstr "Υποβίβαση πεÏιοχής κατά ένα στÏώμα" -#: editor_actions.cc:391 +#: editor_actions.cc:392 #, fuzzy msgid "Most Recently Added is Higher" msgstr "Υποβίβαση πεÏιοχής κατά ένα στÏώμα" @@ -3451,39 +3444,39 @@ msgstr "Δεν γίνεται να εισαχθεί ήχος χωÏίς να έ msgid "Add existing audio to session" msgstr "Ανάδειξη υπαÏχόντων αυτοματισμών" -#: editor_audio_import.cc:143 +#: editor_audio_import.cc:142 msgid "ardour: importing %1" msgstr "ardour: εισαγωγή εν εξελίξι %1" -#: editor_audio_import.cc:147 +#: editor_audio_import.cc:146 msgid "Cancel Import" msgstr "ΑκÏÏωση Εισαγωγής" -#: editor_audio_import.cc:225 +#: editor_audio_import.cc:224 #, fuzzy msgid "Editor: cannot open file \"%1\", (%2)" msgstr "Editor: δεν γίνεται να ανοίξει το αÏχείο \"%1\" (%2)" -#: editor_audio_import.cc:233 +#: editor_audio_import.cc:232 #, fuzzy msgid "Cancel entire import" msgstr "ΑκÏÏωση Εισαγωγής" -#: editor_audio_import.cc:234 +#: editor_audio_import.cc:233 #, fuzzy msgid "Don't embed it" msgstr "Μη %1" -#: editor_audio_import.cc:235 +#: editor_audio_import.cc:234 msgid "Embed all without questions" msgstr "" -#: editor_audio_import.cc:240 +#: editor_audio_import.cc:239 #, fuzzy msgid "Embed it anyway" msgstr "%1 το οÏτως ή άλλως" -#: editor_audio_import.cc:243 +#: editor_audio_import.cc:242 msgid "" "%1\n" "This audiofile's sample rate doesn't match the session sample rate!" @@ -3492,73 +3485,61 @@ msgstr "" "Ο Ïυθμός δειγματοληψίας Î±Ï…Ï„Î¿Ï Ï„Î¿Ï… αÏχείου δεν ταιÏιάζει με αυτόν της " "συνεδÏίας!" -#: editor_audio_import.cc:276 +#: editor_audio_import.cc:275 msgid "could not open %1" msgstr "δεν μπόÏεσα να ανοίξω το %1" -#: editor_audio_import.cc:321 +#: editor_audio_import.cc:320 msgid "insert sndfile" msgstr "Ï€Ïοσθήκη ηχο-αÏχείου" #. stuff for the verbose canvas cursor -#: editor_canvas.cc:117 +#: editor_canvas.cc:118 msgid "VerboseCanvasCursor" msgstr "" -#: editor_canvas.cc:285 -msgid "Start a new session\n" -msgstr "ΑÏχή καινοÏÏιας συνεδÏίας\n" - -#: editor_canvas.cc:285 -msgid "via Session menu" -msgstr "μέσω του Î¼ÎµÎ½Î¿Ï Î£Ï…Î½ÎµÎ´Ïίας" - -#: editor_canvas.cc:288 -msgid "FirstActionMessage" -msgstr "" - -#: editor_edit_groups.cc:52 mixer_ui.cc:732 +#: editor_edit_groups.cc:53 mixer_ui.cc:736 msgid "Activate All" msgstr "ΕνεÏγοποίηση όλων" -#: editor_edit_groups.cc:53 mixer_ui.cc:733 +#: editor_edit_groups.cc:54 mixer_ui.cc:737 #, fuzzy msgid "Disable All" msgstr "ΑποσÏνδεση" -#: editor_edit_groups.cc:55 mixer_ui.cc:735 +#: editor_edit_groups.cc:56 mixer_ui.cc:739 #, fuzzy msgid "Add group" msgstr "ΧωÏίς ομάδα" -#: editor_edit_groups.cc:225 mixer_ui.cc:964 +#: editor_edit_groups.cc:229 mixer_ui.cc:970 #, fuzzy msgid "unnamed" msgstr "Μετονομασία" -#: editor_edit_groups.cc:252 mixer_ui.cc:830 +#: editor_edit_groups.cc:258 mixer_ui.cc:834 msgid "-all-" msgstr "-όλα-" -#: editor_export_audio.cc:64 +#: editor_export_audio.cc:65 msgid "" "There is no selection to export.\n" "\n" "Select a selection using the range mouse mode" msgstr "" -#: editor_export_audio.cc:109 +#: editor_export_audio.cc:110 msgid "" "There are no ranges to export.\n" "\n" "Create 1 or more ranges by dragging the mouse in the range bar" msgstr "" -#: editor_imageframe.cc:624 editor_imageframe.cc:654 +#: editor_imageframe.cc:625 editor_imageframe.cc:655 msgid "programming error: no ImageFrameView selected" msgstr "Σφάλμα Ï€ÏογÏαμματισμοÏ: δεν επιλέχθηκε οπτική καÏέ εικόνας" -#: editor_imageframe.cc:847 editor_imageframe.cc:869 +#: editor_imageframe.cc:848 editor_imageframe.cc:870 msgid "programming error: no MarkerView selected" msgstr "Σφάλμα Ï€ÏογÏαμματισμοÏ: δεν επιλέχθηκε οπτική στίγματος" @@ -3567,142 +3548,142 @@ msgstr "Σφάλμα Ï€ÏογÏαμματισμοÏ: δεν επιλέχθηκε msgid "mute region" msgstr "σιγή παÏοÏσας πεÏιοχής" -#: editor_keys.cc:45 +#: editor_keys.cc:46 #, fuzzy msgid "keyboard selection" msgstr "επέκταση επιλογής" -#: editor_markers.cc:291 editor_ops.cc:1227 editor_ops.cc:1240 -#: editor_ops.cc:1258 location_ui.cc:773 +#: editor_markers.cc:292 editor_ops.cc:1290 editor_ops.cc:1303 +#: editor_ops.cc:1321 location_ui.cc:774 msgid "add marker" msgstr "Ï€Ïόσθεση στίγματος" -#: editor_markers.cc:306 editor_markers.cc:379 editor_markers.cc:551 -#: editor_markers.cc:569 editor_markers.cc:588 editor_markers.cc:607 -#: editor_markers.cc:637 editor_markers.cc:665 editor_markers.cc:693 -#: editor_markers.cc:731 editor_markers.cc:758 editor_markers.cc:781 -#: editor_markers.cc:800 editor_mouse.cc:1994 editor_mouse.cc:4237 +#: editor_markers.cc:307 editor_markers.cc:380 editor_markers.cc:552 +#: editor_markers.cc:570 editor_markers.cc:589 editor_markers.cc:608 +#: editor_markers.cc:638 editor_markers.cc:666 editor_markers.cc:694 +#: editor_markers.cc:732 editor_markers.cc:759 editor_markers.cc:782 +#: editor_markers.cc:801 editor_mouse.cc:2015 editor_mouse.cc:4275 msgid "programming error: marker canvas item has no marker object pointer!" msgstr "" "Σφάλμα Ï€ÏογÏαμματισμοÏ: ο καμβάς στιγμάτων δεν έχει δείκτη αντικειμένου " "στιγμάτων!" -#: editor_markers.cc:330 location_ui.cc:655 +#: editor_markers.cc:331 location_ui.cc:656 msgid "remove marker" msgstr "απαλοιφή στίγματος" -#: editor_markers.cc:457 +#: editor_markers.cc:458 #, fuzzy msgid "Locate to Mark" msgstr "Τοποθέτηση στο" -#: editor_markers.cc:458 +#: editor_markers.cc:459 #, fuzzy msgid "Play from Mark" msgstr "ΑναπαÏ/γή από αÏχή" -#: editor_markers.cc:459 +#: editor_markers.cc:460 #, fuzzy msgid "Set Mark from Playhead" msgstr "Θέση από αναπαÏαγωγέα" -#: editor_markers.cc:463 +#: editor_markers.cc:464 #, fuzzy msgid "Rename Mark" msgstr "Μετονομασία" -#: editor_markers.cc:464 +#: editor_markers.cc:465 #, fuzzy msgid "Hide Mark" msgstr "νÏξη καναλιοÏ" -#: editor_markers.cc:465 +#: editor_markers.cc:466 #, fuzzy msgid "Remove Mark" msgstr "απαλοιφή στίγματος" -#: editor_markers.cc:478 editor_markers.cc:534 +#: editor_markers.cc:479 editor_markers.cc:535 #, fuzzy msgid "Locate to Range Mark" msgstr "Στίγματα Τοποθεσίας" -#: editor_markers.cc:479 editor_markers.cc:535 +#: editor_markers.cc:480 editor_markers.cc:536 #, fuzzy msgid "Play from Range Mark" msgstr "Επαναληπτική αναπαÏ/γή διαστήματος" -#: editor_markers.cc:480 +#: editor_markers.cc:481 #, fuzzy msgid "Loop Range" msgstr "Loop διαστήματος" -#: editor_markers.cc:481 editor_markers.cc:536 +#: editor_markers.cc:482 editor_markers.cc:537 #, fuzzy msgid "Set Range Mark from Playhead" msgstr "Θέση από αναπαÏαγωγέα" -#: editor_markers.cc:482 editor_markers.cc:537 +#: editor_markers.cc:483 editor_markers.cc:538 #, fuzzy msgid "Set Range from Range Selection" msgstr "επιλογή διαστήματος" -#: editor_markers.cc:486 +#: editor_markers.cc:487 #, fuzzy msgid "Rename Range" msgstr "Μετονομασία" -#: editor_markers.cc:487 editor_markers.cc:539 +#: editor_markers.cc:488 editor_markers.cc:540 #, fuzzy msgid "Hide Range" msgstr "ΠÏόσθεση νέου διαστήματος" -#: editor_markers.cc:488 +#: editor_markers.cc:489 #, fuzzy msgid "Remove Range" msgstr "Απαλοιφή Πεδίου" -#: editor_markers.cc:492 editor_markers.cc:541 +#: editor_markers.cc:493 editor_markers.cc:542 #, fuzzy msgid "Separate Regions in Range" msgstr "Îέα πεÏιοχή από διάστημα" -#: editor_markers.cc:493 editor_markers.cc:542 +#: editor_markers.cc:494 editor_markers.cc:543 #, fuzzy msgid "Select All in Range" msgstr "Επιλογή όλων στο κανάλι" -#: editor_markers.cc:519 +#: editor_markers.cc:520 msgid "Set Loop Range" msgstr "Θέση Loop Διαστήματος" -#: editor_markers.cc:520 +#: editor_markers.cc:521 msgid "Set Punch Range" msgstr "Θέση Punch Διαστήματος" -#: editor_markers.cc:814 +#: editor_markers.cc:815 #, fuzzy msgid "New Name:" msgstr "νέο όνομα: " -#: editor_markers.cc:817 +#: editor_markers.cc:818 msgid "ardour: rename mark" msgstr "ardour: μετονομασία στίγματος" -#: editor_markers.cc:819 +#: editor_markers.cc:820 #, fuzzy msgid "ardour: rename range" msgstr "ardour: μετονομασία πεÏιοχής" -#: editor_markers.cc:839 +#: editor_markers.cc:840 #, fuzzy msgid "rename marker" msgstr "απαλοιφή στίγματος" -#: editor_markers.cc:864 +#: editor_markers.cc:865 msgid "set loop range" msgstr "Θέση loop διαστήματος" -#: editor_markers.cc:890 +#: editor_markers.cc:891 msgid "set punch range" msgstr "θέση punch διαστήματος" @@ -3711,76 +3692,81 @@ msgid "Editor::event_frame() used on unhandled event type %1" msgstr "" "ΕπαξεÏγαστής::event_frame() χÏησιμοποιήθηκε στο αδιαχείÏιστο συμβάν Ï„Ïπου %1" -#: editor_mouse.cc:1589 +#: editor_mouse.cc:313 +#, fuzzy +msgid "select on click" +msgstr "ΧÏήση όπως στο μετÏονόμο" + +#: editor_mouse.cc:1590 msgid "programming error: start_grab called without drag item" msgstr "" "σφάλμα Ï€ÏογÏαμματισμοÏ: η Ïουτίνα start_grab εκλήθη δίχως 'drag' αντικείμενο" -#: editor_mouse.cc:1793 +#: editor_mouse.cc:1814 msgid "change fade in length" msgstr "αλλαγή μήκους fade in" -#: editor_mouse.cc:1811 +#: editor_mouse.cc:1832 msgid "programming error: fade out canvas item has no regionview data pointer!" msgstr "" "σφάλμα Ï€ÏογÏαμματισμοÏ: ο καμβάς fade out δεν έχει δείκτη δεδομένων της " "οπτικής πεÏιοχών!" -#: editor_mouse.cc:1885 +#: editor_mouse.cc:1906 msgid "change fade out length" msgstr "αλλαγή μήκους fade out" -#: editor_mouse.cc:1904 +#: editor_mouse.cc:1925 msgid "programming error: cursor canvas item has no cursor data pointer!" msgstr "" "σφάλμα Ï€ÏογÏαμματισμοÏ: ο καμβάς του κέÏσοÏα δεν έχει δείκτη δεδομένων του " "κέÏσοÏα!" -#: editor_mouse.cc:2119 +#: editor_mouse.cc:2142 #, fuzzy msgid "move marker" msgstr "απαλοιφή στίγματος" -#: editor_mouse.cc:2142 editor_mouse.cc:2173 editor_tempodisplay.cc:461 +#: editor_mouse.cc:2165 editor_mouse.cc:2196 editor_tempodisplay.cc:459 msgid "" "programming error: meter marker canvas item has no marker object pointer!" msgstr "" "σφάλμα Ï€ÏογÏαμματισμοÏ: ο καμβάς του μετÏητή στιγμάτων δεν έχει δείκτη " "αντικειμένου στιγμάτων!" -#: editor_mouse.cc:2241 +#: editor_mouse.cc:2264 #, fuzzy msgid "copy meter mark" msgstr "μετακίνηση στίγματος μετÏητή" -#: editor_mouse.cc:2251 +#: editor_mouse.cc:2274 msgid "move meter mark" msgstr "μετακίνηση στίγματος μετÏητή" -#: editor_mouse.cc:2266 editor_mouse.cc:2299 editor_tempodisplay.cc:327 -#: editor_tempodisplay.cc:411 editor_tempodisplay.cc:430 +#: editor_mouse.cc:2289 editor_mouse.cc:2322 editor_tempodisplay.cc:331 +#: editor_tempodisplay.cc:409 editor_tempodisplay.cc:428 msgid "" "programming error: tempo marker canvas item has no marker object pointer!" msgstr "" "σφάλμα Ï€ÏογÏαμματισμοÏ: ο καμβάς στίξης του tempo δεν έχει δείκτη " "αντικειμένου στιγμάτων!" -#: editor_mouse.cc:2271 editor_mouse.cc:2304 editor_tempodisplay.cc:332 -#: editor_tempodisplay.cc:416 +#: editor_mouse.cc:2294 editor_mouse.cc:2327 editor_tempodisplay.cc:336 +#: editor_tempodisplay.cc:414 msgid "programming error: marker for tempo is not a tempo marker!" msgstr "" "σφάλμα Ï€ÏογÏαμματισμοÏ: το στίγμα για το tempo δεν είναι στιγμα για tempo!" -#: editor_mouse.cc:2371 +#: editor_mouse.cc:2394 #, fuzzy msgid "copy tempo mark" msgstr "μετακίνηση στίγματος tempo" -#: editor_mouse.cc:2381 +#: editor_mouse.cc:2404 msgid "move tempo mark" msgstr "μετακίνηση στίγματος tempo" -#: editor_mouse.cc:2395 editor_mouse.cc:2414 editor_mouse.cc:2427 +#: editor_mouse.cc:2418 editor_mouse.cc:2437 editor_mouse.cc:2450 msgid "" "programming error: control point canvas item has no control point object " "pointer!" @@ -3788,320 +3774,321 @@ msgstr "" "Σφάλμα ΠÏογÏαμματισμοÏ: ο καμβάς του σημείου ελέγχου δεν έχει δείκτη " "αναφοÏάς!" -#: editor_mouse.cc:2525 +#: editor_mouse.cc:2555 msgid "programming error: line canvas item has no line pointer!" msgstr "σφάλμα Ï€ÏογÏαμματισμοÏ: ο καμβάς γÏαμμών δεν έχει δείκτη γÏαμμών!" -#: editor_mouse.cc:2634 +#: editor_mouse.cc:2664 #, fuzzy msgid "move region(s)" msgstr "απαλοιφή πεÏιοχής" -#. this is committed in the grab finished callback. -#: editor_mouse.cc:2646 -msgid "Drag region copy" -msgstr "Έλξη αντιγÏαφής πεÏιοχής" - -#: editor_mouse.cc:2758 +#: editor_mouse.cc:2727 #, fuzzy msgid "Drag region brush" msgstr "Έλξη πεÏιοχής(ων)" +#. don't copy again +#. this is committed in the grab finished callback. +#: editor_mouse.cc:2751 +msgid "Drag region copy" +msgstr "Έλξη αντιγÏαφής πεÏιοχής" + #. A selection grab currently creates two undo/redo operations, one for #. creating the new region and another for moving it. #. -#: editor_mouse.cc:3574 +#: editor_mouse.cc:3609 msgid "selection grab" msgstr "αÏπαγή επιλεγμένων" -#: editor_mouse.cc:3615 +#: editor_mouse.cc:3650 #, fuzzy msgid "cancel selection" msgstr "επιλογή διαστήματος" -#: editor_mouse.cc:3722 +#: editor_mouse.cc:3760 msgid "range selection" msgstr "επιλογή διαστήματος" -#: editor_mouse.cc:3738 +#: editor_mouse.cc:3776 msgid "trim selection start" msgstr "αÏχή επιλογής Ï€Ïος ισοστάθμιση" -#: editor_mouse.cc:3754 +#: editor_mouse.cc:3792 msgid "trim selection end" msgstr "τέλος επιλογής Ï€Ïος ισοστάθμιση" -#: editor_mouse.cc:3771 +#: editor_mouse.cc:3809 msgid "move selection" msgstr "μετακίνηση επιλογής" -#: editor_mouse.cc:4157 +#: editor_mouse.cc:4195 msgid "Start point trim" msgstr "ΑÏχή σημείου ισοσταθμίσεως" -#: editor_mouse.cc:4185 +#: editor_mouse.cc:4223 msgid "End point trim" msgstr "Τέλος σημείου ισοσταθμίσεως" -#: editor_mouse.cc:4224 +#: editor_mouse.cc:4262 msgid "trimmed region" msgstr "ισοσταθμισμένη πεÏιοχή" -#: editor_mouse.cc:4363 +#: editor_mouse.cc:4400 msgid "new range marker" msgstr "νέο στίγμα διαστήματος" -#: editor_mouse.cc:4578 +#: editor_mouse.cc:4642 msgid "select regions" msgstr "επιλογή πεÏιοχών" -#: editor_mouse.cc:4607 +#: editor_mouse.cc:4671 msgid "Name for region:" msgstr "Όνομα για πεÏιοχή:" -#: editor_mouse.cc:4671 +#: editor_mouse.cc:4735 msgid "timestretch" msgstr "κάμψη χÏόνου" -#: editor_ops.cc:132 +#: editor_ops.cc:195 msgid "split" msgstr "διαχωÏισμός" -#: editor_ops.cc:168 +#: editor_ops.cc:231 msgid "remove region" msgstr "απαλοιφή πεÏιοχής" -#: editor_ops.cc:187 +#: editor_ops.cc:250 msgid "" " This is destructive, will possibly delete audio files\n" "It cannot be undone\n" "Do you really want to destroy %1 ?" msgstr "" -#: editor_ops.cc:191 +#: editor_ops.cc:254 #, fuzzy msgid "these regions" msgstr "αντιστÏοφή πεÏιοχών" -#: editor_ops.cc:191 +#: editor_ops.cc:254 #, fuzzy msgid "this region" msgstr "σιγή παÏοÏσας πεÏιοχής" -#: editor_ops.cc:193 editor_ops.cc:3229 route_ui.cc:700 -#: visual_time_axis.cc:277 +#: editor_ops.cc:256 editor_ops.cc:3318 route_ui.cc:707 +#: visual_time_axis.cc:278 msgid "No, do nothing." msgstr "Όχι, να μην γίνει τίποτα." -#: editor_ops.cc:196 +#: editor_ops.cc:259 #, fuzzy msgid "Yes, destroy them." msgstr "Îαι, να καταστÏαφεί." -#: editor_ops.cc:198 editor_ops.cc:3230 +#: editor_ops.cc:261 editor_ops.cc:3319 msgid "Yes, destroy it." msgstr "Îαι, να καταστÏαφεί." -#: editor_ops.cc:289 editor_ops.cc:317 +#: editor_ops.cc:352 editor_ops.cc:380 msgid "extend selection" msgstr "επέκταση επιλογής" -#: editor_ops.cc:333 editor_ops.cc:367 editor_ops.cc:411 editor_ops.cc:437 +#: editor_ops.cc:396 editor_ops.cc:430 editor_ops.cc:474 editor_ops.cc:500 msgid "nudge forward" msgstr "νÏξη εμπÏός" -#: editor_ops.cc:501 +#: editor_ops.cc:564 msgid "build_region_boundary_cache called with snap_type = %1" msgstr "build_region_boundary_cache εκλήθη με snap_type = %1" -#: editor_ops.cc:1354 +#: editor_ops.cc:1420 #, fuzzy msgid "select all within" msgstr "Επιλογή όλων" -#: editor_ops.cc:1380 +#: editor_ops.cc:1452 #, fuzzy msgid "set selection from region" msgstr "θέση επιλογής από διάστημα" -#: editor_ops.cc:1413 +#: editor_ops.cc:1485 msgid "set selection from range" msgstr "θέση επιλογής από διάστημα" -#: editor_ops.cc:1443 +#: editor_ops.cc:1515 #, fuzzy msgid "select all from range" msgstr "επιλογή διαστήματος zoom" -#: editor_ops.cc:1465 +#: editor_ops.cc:1537 #, fuzzy msgid "select all from punch" msgstr "Επιλογή όλων" -#: editor_ops.cc:1487 +#: editor_ops.cc:1559 #, fuzzy msgid "select all from loop" msgstr "Επιλογή όλων" -#: editor_ops.cc:1501 +#: editor_ops.cc:1573 #, fuzzy msgid "select all after cursor" msgstr "Από αÏχή μέχÏι κέÏσοÏα επεξεÏγασίας" -#: editor_ops.cc:1506 +#: editor_ops.cc:1578 #, fuzzy msgid "select all before cursor" msgstr "Θέση συγχÏονισμοÏ(sync) απο κέÏσοÏα επεξεÏ/σίας" -#: editor_ops.cc:1536 +#: editor_ops.cc:1608 #, fuzzy msgid "select all between cursors" msgstr "Θέση συγχÏονισμοÏ(sync) απο κέÏσοÏα επεξεÏ/σίας" -#: editor_ops.cc:1667 +#: editor_ops.cc:1739 msgid "clear markers" msgstr "εκκαθάÏιση στιγμάτων" -#: editor_ops.cc:1679 +#: editor_ops.cc:1751 msgid "clear ranges" msgstr "διαγÏαφή διαστημάτων" -#: editor_ops.cc:1698 +#: editor_ops.cc:1770 msgid "clear locations" msgstr "διαγÏαφή τοποθεσιών" -#: editor_ops.cc:1748 +#: editor_ops.cc:1820 msgid "insert dragged region" msgstr "Ï€Ïοσθήκη ελκομένης πεÏιοχής" -#: editor_ops.cc:1784 +#: editor_ops.cc:1856 msgid "insert region" msgstr "Ï€Ïοσθήκη πεÏιοχής" -#: editor_ops.cc:1975 io_selector.cc:57 io_selector.cc:791 +#: editor_ops.cc:2047 io_selector.cc:58 io_selector.cc:792 msgid "OK" msgstr "OK" -#: editor_ops.cc:1982 +#: editor_ops.cc:2054 msgid "ardour: rename region" msgstr "ardour: μετονομασία πεÏιοχής" -#: editor_ops.cc:2205 editor_ops.cc:2254 +#: editor_ops.cc:2277 editor_ops.cc:2326 msgid "separate" msgstr "διαχωÏισμός" -#: editor_ops.cc:2316 +#: editor_ops.cc:2388 msgid "trim to selection" msgstr "ισοστάθμιση Ï€Ïος τα επιλεγμένα" -#: editor_ops.cc:2356 +#: editor_ops.cc:2428 msgid "region fill" msgstr "γόμωση πεÏιοχής" -#: editor_ops.cc:2415 +#: editor_ops.cc:2487 msgid "fill selection" msgstr "γόμωση επιλογής" -#: editor_ops.cc:2436 +#: editor_ops.cc:2508 #, fuzzy msgid "Programming error. that region doesn't cover that position" msgstr "" "Σφάλμα Ï€ÏογÏαμματισμοÏ: ο χάÏτης τοποθεσίας/στίγματος δεν πεÏιέχει " "τοποθεσίες!" -#: editor_ops.cc:2439 +#: editor_ops.cc:2511 #, fuzzy msgid "set region sync position" msgstr "ΠεÏιοχές/θέση" -#: editor_ops.cc:2454 +#: editor_ops.cc:2526 msgid "Place the edit cursor at the desired sync point" msgstr "Τοποθετήστε τον κεÏσοÏα επεξεÏ/σίας στο επιθÏμητό σημείο συγχÏονισμοÏ" -#: editor_ops.cc:2459 +#: editor_ops.cc:2531 msgid "set sync from edit cursor" msgstr "Θέση συγχÏονισμοÏ(sync) απο κέÏσοÏα επεξεÏ/σίας" -#: editor_ops.cc:2471 +#: editor_ops.cc:2543 msgid "remove sync" msgstr "απαλοιφή συγχÏονισμοÏ(sync)" -#: editor_ops.cc:2485 +#: editor_ops.cc:2557 msgid "naturalize" msgstr "φυσικοποίηση" -#: editor_ops.cc:2549 +#: editor_ops.cc:2621 msgid "align selection (relative)" msgstr "ευθυγÏάμμιση επιλογής (σχετική)" -#: editor_ops.cc:2577 +#: editor_ops.cc:2649 msgid "align selection" msgstr "ευθυγÏάμμιση επιλογής" -#: editor_ops.cc:2589 +#: editor_ops.cc:2661 msgid "align region" msgstr "ευθυγÏάμμιση πεÏιοχής" -#: editor_ops.cc:2636 editor_ops.cc:2661 +#: editor_ops.cc:2708 editor_ops.cc:2733 msgid "trim to edit" msgstr "ισοστάθμιση Ï€Ïος σÏνταξη" -#: editor_ops.cc:2712 +#: editor_ops.cc:2784 #, fuzzy msgid "ardour: freeze" msgstr "ardour: " -#: editor_ops.cc:2717 +#: editor_ops.cc:2789 #, fuzzy msgid "Cancel Freeze" msgstr "ΑκÏÏωση" -#: editor_ops.cc:2754 +#: editor_ops.cc:2826 msgid "bounce range" msgstr "αναπήδηση διαστήματο" -#: editor_ops.cc:2807 +#: editor_ops.cc:2879 msgid "cut" msgstr "κοπή" -#: editor_ops.cc:2810 +#: editor_ops.cc:2882 msgid "copy" msgstr "αντιγÏαφή" -#: editor_ops.cc:2823 +#: editor_ops.cc:2895 msgid " objects" msgstr " αντικειμένων" -#: editor_ops.cc:2849 +#: editor_ops.cc:2921 msgid " range" msgstr " διαστήματος" -#: editor_ops.cc:3006 +#: editor_ops.cc:3078 msgid "paste" msgstr "επικόλληση" -#: editor_ops.cc:3044 +#: editor_ops.cc:3116 msgid "paste chunk" msgstr "επικόλληση κομματιοÏ" #. clear (below) will clear the argument list -#: editor_ops.cc:3085 +#: editor_ops.cc:3157 msgid "duplicate region" msgstr "αντιγÏαφή πεÏιοχής" -#: editor_ops.cc:3130 +#: editor_ops.cc:3202 msgid "duplicate selection" msgstr "αντιγÏαφή επιλογής" -#: editor_ops.cc:3170 +#: editor_ops.cc:3259 msgid "clear playlist" msgstr "εκκαθάÏιση playlist" -#: editor_ops.cc:3199 +#: editor_ops.cc:3288 msgid "nudge track" msgstr "νÏξη καναλιοÏ" -#: editor_ops.cc:3226 +#: editor_ops.cc:3315 msgid "" "Do you really want to destroy the last capture?\n" "(This is destructive and cannot be undone)" @@ -4109,160 +4096,157 @@ msgstr "" "Στ'αλήθεια θέλετε να καταστÏέψετε την τελευταία λήψη?\n" "(Η Ï€Ïάξη είνα‎ι καταστÏεπτική και δεν γίνεται επαναφοÏά της)" -#: editor_ops.cc:3254 +#: editor_ops.cc:3343 msgid "normalize" msgstr "εξομάλυνση" -#: editor_ops.cc:3301 +#: editor_ops.cc:3390 msgid "reverse regions" msgstr "αντιστÏοφή πεÏιοχών" -#: editor_region_list.cc:93 editor_region_list.cc:98 editor_region_list.cc:101 -#: location_ui.cc:55 +#: editor_region_list.cc:98 editor_region_list.cc:103 +#: editor_region_list.cc:106 location_ui.cc:56 msgid "Hidden" msgstr "ΚÏυμμένο" #. added a new fresh one at the end -#: editor_route_list.cc:101 editor_route_list.cc:102 editor_route_list.cc:246 +#: editor_route_list.cc:102 editor_route_list.cc:103 editor_route_list.cc:247 msgid "editor" msgstr "επεξεÏγαστής" -#: editor_route_list.cc:309 mixer_ui.cc:695 +#: editor_route_list.cc:310 mixer_ui.cc:699 msgid "Show All" msgstr "Εμφάνιση Όλων" -#: editor_route_list.cc:310 mixer_ui.cc:696 +#: editor_route_list.cc:311 mixer_ui.cc:700 msgid "Hide All" msgstr "ΑπόκÏυψη όλων" -#: editor_route_list.cc:311 mixer_ui.cc:697 +#: editor_route_list.cc:312 mixer_ui.cc:701 #, fuzzy msgid "Show All Audio Tracks" msgstr "Ανάδειξη όλων των ΗχοδιαÏλων" -#: editor_route_list.cc:312 mixer_ui.cc:698 +#: editor_route_list.cc:313 mixer_ui.cc:702 #, fuzzy msgid "Hide All Audio Tracks" msgstr "ΑπόκÏυψη όλων των ΗχοδιαÏλων" -#: editor_route_list.cc:313 mixer_ui.cc:699 +#: editor_route_list.cc:314 mixer_ui.cc:703 #, fuzzy msgid "Show All Audio Busses" msgstr "Ανάδειξη όλων των ΗχοδιαÏλων" -#: editor_route_list.cc:314 mixer_ui.cc:700 +#: editor_route_list.cc:315 mixer_ui.cc:704 #, fuzzy msgid "Hide All Audio Busses" msgstr "ΑπόκÏυψη όλων των ΗχοδιαÏλων" -#: editor_rulers.cc:311 +#: editor_rulers.cc:312 msgid "New location marker" msgstr "Îέο στίγμα θέσεως" -#: editor_rulers.cc:312 +#: editor_rulers.cc:313 msgid "Clear all locations" msgstr "ΕκκαθάÏιση όλων των θέσεων" #. ruler_items.push_back (MenuElem (_("New Range"))); -#: editor_rulers.cc:317 +#: editor_rulers.cc:318 msgid "Clear all ranges" msgstr "ΕκκαθάÏιση όλων των διαστημάτων" -#: editor_rulers.cc:326 +#: editor_rulers.cc:327 msgid "New Tempo" msgstr "Îέος ΧÏόνος" -#: editor_rulers.cc:327 +#: editor_rulers.cc:328 msgid "Clear tempo" msgstr "ΕκκαθάÏιση ΧÏόνου" -#: editor_rulers.cc:332 +#: editor_rulers.cc:333 msgid "New Meter" msgstr "Îέο μέτÏο" -#: editor_rulers.cc:333 +#: editor_rulers.cc:334 msgid "Clear meter" msgstr "ΕκκαθάÏιση μέτÏου" -#: editor_rulers.cc:341 +#: editor_rulers.cc:342 msgid "Min:Secs" msgstr "Λεπ:ΔεÏÏ„" -#: editor_selection_list.cc:110 +#: editor_selection_list.cc:108 #, fuzzy msgid "Name for Chunk:" msgstr "όνομα για κομμάτι:" -#: editor_selection_list.cc:113 +#: editor_selection_list.cc:111 #, fuzzy msgid "Create Chunk" msgstr "ΔημιουÏγία κομματιοÏ" -#: editor_selection_list.cc:113 +#: editor_selection_list.cc:111 msgid "Forget it" msgstr "Ξέχασέ το" -#: editor_tempodisplay.cc:249 editor_tempodisplay.cc:289 +#: editor_tempodisplay.cc:253 editor_tempodisplay.cc:293 msgid "add" msgstr "Ï€Ïόσθεση" -#: editor_tempodisplay.cc:271 +#: editor_tempodisplay.cc:275 msgid "add tempo mark" msgstr "Ï€Ïόσθεση στίγματος χÏόνου" -#: editor_tempodisplay.cc:311 +#: editor_tempodisplay.cc:315 msgid "add meter mark" msgstr "Ï€Ïόσθεση στίγματος μέτÏου" -#: editor_tempodisplay.cc:344 editor_tempodisplay.cc:375 +#: editor_tempodisplay.cc:348 editor_tempodisplay.cc:376 msgid "done" msgstr "έγινε" -#: editor_tempodisplay.cc:365 editor_tempodisplay.cc:396 +#: editor_tempodisplay.cc:366 editor_tempodisplay.cc:394 msgid "replace tempo mark" msgstr "αντικατάσταση στίγματος χÏόνου" -#: editor_tempodisplay.cc:435 editor_tempodisplay.cc:466 +#: editor_tempodisplay.cc:433 editor_tempodisplay.cc:464 msgid "programming error: marker for meter is not a meter marker!" msgstr "" "Σφάλμα Ï€ÏογÏαμματισμοÏ: το στίγμα για το μέτÏο δεν είναι στίγμα μέτÏου!" -#: editor_tempodisplay.cc:445 editor_tempodisplay.cc:478 +#: editor_tempodisplay.cc:443 editor_tempodisplay.cc:476 msgid "remove tempo mark" msgstr "απαλοιφή στίγματος χÏόνου" -#: editor_timefx.cc:50 +#: editor_timefx.cc:51 msgid "Quick but Ugly" msgstr "ΓÏήγοÏο αλλά Άσχημο" -#: editor_timefx.cc:51 +#: editor_timefx.cc:52 msgid "Skip Anti-aliasing" msgstr "ΠαÏάκαμψη Anti-aliasing" -#: editor_timefx.cc:53 -msgid "Stretch/Shrink it" -msgstr "Μεγέθυνέ/ΣμίκÏυνέ το" - -#: editor_timefx.cc:57 +#: editor_timefx.cc:56 msgid "ardour: timestretch" msgstr "ardour: χÏονοκάμψη" -#: editor_timefx.cc:58 +#: editor_timefx.cc:57 msgid "TimeStretchDialog" msgstr "ΔιάλογοςΧÏονοκάμψης" -#: editor_timefx.cc:80 editor_timefx.cc:81 editor_timefx.cc:82 -#: editor_timefx.cc:83 +#: editor_timefx.cc:70 +msgid "Stretch/Shrink it" +msgstr "Μεγέθυνέ/ΣμίκÏυνέ το" + +#: editor_timefx.cc:73 editor_timefx.cc:74 msgid "TimeStretchButton" msgstr "ΚουμπίΧÏονοκάμψης" -#: editor_timefx.cc:84 +#: editor_timefx.cc:75 msgid "TimeStretchProgress" msgstr "ΠÏόοδοςΧÏονοκάμψης" -#. GTK2FIX -#. current_timestretch->close (); -#: editor_timefx.cc:153 +#: editor_timefx.cc:139 msgid "timestretch cannot be started - thread creation error" msgstr "" @@ -4397,7 +4381,7 @@ msgstr "Εξαγωγή σε CD από μαÏκάÏισμα καναλιοÏ" msgid "Export to File" msgstr "Εξαγωγή σε CD" -#: export_dialog.cc:113 option_editor.cc:82 option_editor.cc:83 +#: export_dialog.cc:113 option_editor.cc:83 option_editor.cc:84 msgid "Browse" msgstr "Αναζήτηση" @@ -4413,7 +4397,8 @@ msgstr "ardour: εξαγωγή" msgid "ardour_export" msgstr "ardour_εξαγωγή" -#: export_dialog.cc:139 export_dialog.cc:155 +#: export_dialog.cc:139 export_dialog.cc:155 mixer_strip.cc:124 +#: mixer_strip.cc:767 #, fuzzy msgid "Output" msgstr "Έξοδοι" @@ -4452,145 +4437,76 @@ msgstr "" msgid "File already exists, do you want to overwrite it?" msgstr "" -#: export_dialog.cc:1159 export_range_markers_dialog.cc:154 +#: export_dialog.cc:1159 export_range_markers_dialog.cc:153 msgid "Cannot write file in: " msgstr "" #. warning dialog -#: export_range_markers_dialog.cc:136 +#: export_range_markers_dialog.cc:135 msgid "Please enter a valid target directory." msgstr "" -#: export_range_markers_dialog.cc:144 +#: export_range_markers_dialog.cc:143 msgid "" "Please select an existing target directory. Files\n" "are not allowed!" msgstr "" -#: gain_automation_time_axis.cc:61 +#: gain_automation_time_axis.cc:62 #, fuzzy msgid "add gain automation event" msgstr "Ï€Ïόσθεση συμβάντος Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï ÏƒÎµ " -#: gain_meter.cc:66 +#: gain_meter.cc:67 msgid "cannot find images for fader slider" msgstr "" -#: gain_meter.cc:73 +#: gain_meter.cc:74 msgid "cannot find images for fader rail" msgstr "" -#: gain_meter.cc:88 -msgid "dbFS" -msgstr "dbFS" - -#: gain_meter.cc:89 gain_meter.cc:143 gain_meter.cc:704 -msgid "pre" -msgstr "Ï€Ïο" - -#: gain_meter.cc:139 gain_meter.cc:700 -#, fuzzy -msgid "input" -msgstr "%1 είσοδος" - -#: gain_meter.cc:147 gain_meter.cc:708 -#, fuzzy -msgid "post" -msgstr "θÏÏα" - -#. TRANSLATORS: this string should be longest of the strings -#. used to describe meter points. In english, its "input". -#. -#: gain_meter.cc:155 -msgid "tupni" -msgstr "" - -#: gain_meter.cc:174 gain_meter.cc:458 gain_meter.cc:480 gain_meter.cc:525 +#: gain_meter.cc:130 gain_meter.cc:339 gain_meter.cc:494 gain_meter.cc:539 msgid "-inf" msgstr "-inf" -#: glade/new_session_dialog.glade.h:1 +#: gain_meter.cc:140 #, fuzzy -msgid "Advanced" -msgstr "ΠÏοχωÏημένα..." +msgid "Fader automation mode" +msgstr "ΛειτουÏγία Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï pan" -#: glade/new_session_dialog.glade.h:2 -msgid "Input" +#: gain_meter.cc:141 +#, fuzzy +msgid "Fader automation type" +msgstr "ΤÏπος Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï Pan" + +#. XXX it might different in different languages +#: gain_meter.cc:182 gain_meter.cc:817 panner_ui.cc:99 panner_ui.cc:807 +#, fuzzy +msgid "Abs" +msgstr "abs" + +#: gain_meter.cc:472 +#, fuzzy +msgid "-Inf" +msgstr "-inf" + +#: gain_meter.cc:781 mixer_strip.cc:770 panner_ui.cc:771 +#, fuzzy +msgid "O" +msgstr "OR" + +#: gain_meter.cc:784 panner_ui.cc:774 +msgid "P" msgstr "" -#: glade/new_session_dialog.glade.h:3 -#, fuzzy -msgid "Output" -msgstr "Έξοδοι" - -#: glade/new_session_dialog.glade.h:4 -#, fuzzy -msgid "Automatically connect inputs" -msgstr "αυτόματη σÏνδεση inputs καναλιών σε φυσικές θÏÏες" - -#: glade/new_session_dialog.glade.h:5 -#, fuzzy -msgid "Automatically connect outputs" -msgstr "χειÏοκίνητη σÏνδεση των outputs των καναλιών" - -#: glade/new_session_dialog.glade.h:6 -#, fuzzy -msgid "Channel Count" -msgstr "ΑκÏÏωση Εισαγωγής" - -#: glade/new_session_dialog.glade.h:7 -msgid "Connect to Master Bus" +#: gain_meter.cc:787 panner_ui.cc:777 +msgid "T" msgstr "" -#: glade/new_session_dialog.glade.h:8 -msgid "Connect to physical outputs" +#: gain_meter.cc:790 panner_ui.cc:780 +msgid "W" msgstr "" -#: glade/new_session_dialog.glade.h:9 -#, fuzzy -msgid "Create Control Bus" -msgstr "Control Outs" - -#: glade/new_session_dialog.glade.h:10 -#, fuzzy -msgid "Create Master Bus" -msgstr "χÏήση των master outs" - -#: glade/new_session_dialog.glade.h:11 -#, fuzzy -msgid "New Session" -msgstr "ΣυνεδÏία" - -#: glade/new_session_dialog.glade.h:12 -#, fuzzy -msgid "Open Recent Session" -msgstr "Άνοιγμα συνεδÏίας" - -#: glade/new_session_dialog.glade.h:13 -#, fuzzy -msgid "Open Session" -msgstr "Άνοιγμα συνεδÏίας" - -#: glade/new_session_dialog.glade.h:14 -#, fuzzy -msgid "Port limit" -msgstr "Ξέχασέ το" - -#: glade/new_session_dialog.glade.h:15 -#, fuzzy -msgid "Select a File" -msgstr "Επιλογή όλων" - -#: glade/new_session_dialog.glade.h:16 -#, fuzzy -msgid "Select a Session" -msgstr "επιλογή πεÏιοχών" - -#: glade/new_session_dialog.glade.h:17 -#, fuzzy -msgid "Track/Bus connection options" -msgstr "κανάλια/δίαυλοι" - #: gtk-custom-ruler.c:126 #, fuzzy msgid "Lower" @@ -4636,129 +4552,129 @@ msgid "Draw current ruler position" msgstr "" #. end-of-file, other end closed or shutdown? -#: imageframe_socket_handler.cc:126 +#: imageframe_socket_handler.cc:127 msgid "Image Compositor Socket has been shutdown/closed" msgstr "Η Socket για τον Image Compositor έχει τεÏματιστεί/κλείσει" -#: imageframe_time_axis.cc:287 +#: imageframe_time_axis.cc:286 #, fuzzy msgid "0.5 seconds" msgstr "ΔευτεÏόλεπτα" -#: imageframe_time_axis.cc:288 marker_time_axis.cc:241 +#: imageframe_time_axis.cc:287 marker_time_axis.cc:242 #, fuzzy msgid "1 seconds" msgstr "ΔευτεÏόλεπτα" -#: imageframe_time_axis.cc:289 marker_time_axis.cc:242 +#: imageframe_time_axis.cc:288 marker_time_axis.cc:243 #, fuzzy msgid "1.5 seconds" msgstr "ΔευτεÏόλεπτα" -#: imageframe_time_axis.cc:290 marker_time_axis.cc:243 +#: imageframe_time_axis.cc:289 marker_time_axis.cc:244 #, fuzzy msgid "2 seconds" msgstr "ΔευτεÏόλεπτα" -#: imageframe_time_axis.cc:291 marker_time_axis.cc:244 +#: imageframe_time_axis.cc:290 marker_time_axis.cc:245 #, fuzzy msgid "2.5 seconds" msgstr "ΔευτεÏόλεπτα" -#: imageframe_time_axis.cc:292 marker_time_axis.cc:245 +#: imageframe_time_axis.cc:291 marker_time_axis.cc:246 #, fuzzy msgid "3 seconds" msgstr "ΔευτεÏόλεπτα" #. duration_items.push_back(SeparatorElem()) ; #. duration_items.push_back(MenuElem (_("custom"), mem_fun(*this, &ImageFrameTimeAxis::set_marker_duration_custom))) ; -#: imageframe_time_axis.cc:297 marker_time_axis.cc:250 +#: imageframe_time_axis.cc:296 marker_time_axis.cc:251 #, fuzzy msgid "Duration (sec)" msgstr "Έλξη πεÏιοχής(ων)" -#: imageframe_time_axis.cc:302 +#: imageframe_time_axis.cc:301 #, fuzzy msgid "Remove Frame" msgstr "Απαλοιφή Πεδίου" -#: imageframe_time_axis.cc:305 +#: imageframe_time_axis.cc:304 #, fuzzy msgid "Image Frame" msgstr "Frames" -#: imageframe_time_axis.cc:306 marker_time_axis.cc:256 +#: imageframe_time_axis.cc:305 marker_time_axis.cc:257 #, fuzzy msgid "Rename Track" msgstr "Μετονομασία" -#: io_selector.cc:59 io_selector.cc:793 +#: io_selector.cc:60 io_selector.cc:794 #, fuzzy msgid "Rescan" msgstr "Επανα-ανίχνευση" -#: io_selector.cc:67 +#: io_selector.cc:68 msgid "%1 input" msgstr "%1 είσοδος" -#: io_selector.cc:69 +#: io_selector.cc:70 msgid "%1 output" msgstr "%1 έξοδος" -#: io_selector.cc:141 route_params_ui.cc:106 +#: io_selector.cc:142 route_params_ui.cc:107 msgid "Inputs" msgstr "Είσοδοι" -#: io_selector.cc:141 route_params_ui.cc:107 +#: io_selector.cc:142 route_params_ui.cc:108 msgid "Outputs" msgstr "Έξοδοι" -#: io_selector.cc:142 +#: io_selector.cc:143 #, fuzzy msgid "Add Input" msgstr "Ï€Ïόσθεση εισόδου" -#: io_selector.cc:142 +#: io_selector.cc:143 #, fuzzy msgid "Add Output" msgstr "Ï€Ïόσθεση εξόδου" -#: io_selector.cc:143 +#: io_selector.cc:144 #, fuzzy msgid "Remove Input" msgstr "Απαλοιφή σημείου συγχÏονισμοÏ" -#: io_selector.cc:143 +#: io_selector.cc:144 #, fuzzy msgid "Remove Output" msgstr "# Έξοδοι" -#: io_selector.cc:144 +#: io_selector.cc:145 #, fuzzy msgid "Disconnect All" msgstr "ΑποσÏνδεση" -#: io_selector.cc:158 +#: io_selector.cc:159 msgid "Available connections" msgstr "Διαθέσιμες Συνδέσεις" -#: io_selector.cc:554 io_selector.cc:573 +#: io_selector.cc:555 io_selector.cc:574 msgid "There are no more JACK ports available." msgstr "" -#: io_selector.cc:648 io_selector.cc:675 io_selector.cc:728 +#: io_selector.cc:649 io_selector.cc:676 io_selector.cc:729 msgid "port" msgstr "θÏÏα" -#: io_selector.cc:797 +#: io_selector.cc:798 msgid "ardour: " msgstr "ardour: " -#: keyboard.cc:297 +#: keyboard.cc:299 msgid "KeyboardTarget: keyname \"%1\" is unknown." msgstr "KeyboardTarget: το Όνομα ΠλήκτÏου \"%1\" είναι άγνωστο." -#: keyboard.cc:523 +#: keyboard.cc:525 msgid "" "Your system is completely broken - NumLock uses \"%1\"as its modifier. This " "is madness - see the man page for xmodmap to find out how to fix this." @@ -4767,7 +4683,7 @@ msgstr "" "μεταβλητή του. Αυτό είναι Ï„Ïέλα - ανατÏέξτε στην man page του xmodmap για να " "βÏείτε πώς θα το φτιάξετε." -#: keyboard.cc:531 +#: keyboard.cc:533 msgid "" "Your system generates \"%1\" when the NumLock key is pressed. This can cause " "problems when editing so Ardour will use %2 to mean Meta rather than %1" @@ -4776,103 +4692,103 @@ msgstr "" "μποÏεί να δημιουÏγήσει Ï€Ïοβλήματα στην επεξεÏγασία οπότε ο Ardour θα " "χÏησιμοποιήσει %2 για Meta αντί του %1" -#: keyboard.cc:592 +#: keyboard.cc:594 msgid "You have %1 keys bound to \"mod1\"" msgstr "ΥπάÏχουν %1 πλήκτÏα αναθεμένα στο \"mod1\"" -#: keyboard.cc:607 +#: keyboard.cc:609 msgid "You have %1 keys bound to \"mod2\"" msgstr "ΥπάÏχουν %1 πλήκτÏα αναθεμένα στο \"mod2\"" -#: keyboard.cc:622 +#: keyboard.cc:624 msgid "You have %1 keys bound to \"mod3\"" msgstr "ΥπάÏχουν %1 πλήκτÏα αναθεμένα στο \"mod3\"" -#: keyboard.cc:637 +#: keyboard.cc:639 msgid "You have %1 keys bound to \"mod4\"" msgstr "ΥπάÏχουν %1 πλήκτÏα αναθεμένα στο \"mod4\"" -#: keyboard.cc:652 +#: keyboard.cc:654 msgid "You have %1 keys bound to \"mod5\"" msgstr "ΥπάÏχουν %1 πλήκτÏα αναθεμένα στο \"mod5\"" -#: location_ui.cc:47 location_ui.cc:50 +#: location_ui.cc:48 location_ui.cc:51 msgid "Set" msgstr "Θέση" -#: location_ui.cc:48 location_ui.cc:51 +#: location_ui.cc:49 location_ui.cc:52 msgid "Go" msgstr "Πήγαινε" -#: location_ui.cc:54 +#: location_ui.cc:55 msgid "CD" msgstr "CD" -#: location_ui.cc:57 +#: location_ui.cc:58 msgid "SCMS" msgstr "" -#: location_ui.cc:58 +#: location_ui.cc:59 msgid "Pre-Emphasis" msgstr "" -#: location_ui.cc:569 +#: location_ui.cc:570 msgid "Add New Location" msgstr "ΠÏόσθεση νέας τοποθεσίας" -#: location_ui.cc:570 +#: location_ui.cc:571 msgid "Add New Range" msgstr "ΠÏόσθεση νέου διαστήματος" -#: location_ui.cc:574 +#: location_ui.cc:575 msgid "ardour: locations" msgstr "ardour: τοποθεσίες" -#: location_ui.cc:575 +#: location_ui.cc:576 msgid "ardour_locations" msgstr "ardour_τοποθεσίες" -#: location_ui.cc:603 +#: location_ui.cc:604 #, fuzzy msgid "Location (CD Index) Markers" msgstr "Στίγματα Τοποθεσίας" -#: location_ui.cc:623 +#: location_ui.cc:624 #, fuzzy msgid "Range (CD Track) Markers" msgstr "Στίγματα διαστημάτων" -#: location_ui.cc:789 +#: location_ui.cc:790 msgid "add range marker" msgstr "Ï€Ïόσθεση στίγματος διαστήματος" -#: main.cc:71 +#: main.cc:72 msgid "ardour is killing itself for a clean exit\n" msgstr "Ο ardour σκοτώνει τον εαυτό του για καθαÏή έξοδο\n" -#: main.cc:80 +#: main.cc:81 msgid "stopping user interface\n" msgstr "παÏση του user interface\n" #. XXX its doubtful that snprintf() is async-safe -#: main.cc:99 +#: main.cc:100 #, fuzzy, c-format msgid "%d(%d): received signal %d\n" msgstr "%d: εδέχθη σήμα %d\n" -#: main.cc:185 +#: main.cc:186 msgid "cannot become new process group leader (%1)" msgstr "" -#: main.cc:212 +#: main.cc:213 msgid "cannot setup signal handling for %1" msgstr "δεν γίνεται να διαμοÏφώθεί η διαχείÏηση σημάτων για %1" -#: main.cc:223 +#: main.cc:224 msgid "cannot set default signal mask (%1)" msgstr "δεν γίνεται να διαμοÏφώθεί η Ï€ÏοκαθοÏισμένη μάσκα σημάτων (%1)" -#: main.cc:253 +#: main.cc:254 #, fuzzy msgid "" "Without a UI style file, ardour will look strange.\n" @@ -4881,12 +4797,12 @@ msgstr "" "Δίχως αÏχείο εμφάνισεως UI, ο ardour θα φαίνεται παÏάξενα.\n" "ΠαÏακαλώ θέστε το ARDOUR_UI_RC να δείχνει σε ενεÏγό αÏχείο εμφανίσεως UI" -#: main.cc:273 +#: main.cc:276 #, fuzzy msgid "Ardour could not connect to JACK." msgstr "Δεν γινόταν να συνδεθώ στον JACK server σαν \"%1\"" -#: main.cc:277 +#: main.cc:280 #, fuzzy msgid "" "There are several possible reasons:\n" @@ -4906,72 +4822,12 @@ msgstr "" "\n" "ΠαÏακαλώ αναλογιστείτε τις πιθανότητες, και ίσως (ξανα)ξεκινήστε τον JACK." -#: main.cc:324 -msgid "Ardour/GTK " -msgstr "Ardour/GTK " - -#: main.cc:326 -msgid "" -"\n" -" (built using " -msgstr "" - -#: main.cc:330 -#, fuzzy -msgid " with libardour " -msgstr " Ï„Ïέχοντας με libardour " - -#: main.cc:335 -msgid " and GCC version " -msgstr "" - -#: main.cc:345 -#, fuzzy -msgid "Copyright (C) 1999-2005 Paul Davis" -msgstr "Πνευματικα Δικαιώματα 1999-2004 Paul Davis" - -#: main.cc:346 -msgid "" -"Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " -"Baker" -msgstr "" - -#: main.cc:348 -msgid "Ardour comes with ABSOLUTELY NO WARRANTY" -msgstr "Ο Ardour έÏχεται με απολÏτως ΚΑΜΙΑ ΕΓΓΥΗΣΗ" - -#: main.cc:349 -msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." -msgstr "" - -#: main.cc:350 -msgid "This is free software, and you are welcome to redistribute it " -msgstr "" -"Το παÏόν είναι ελεÏθεÏο λογισμικό, είστε ελεÏθεÏοι να το επαναδιανείμετε " - -#: main.cc:351 -#, fuzzy -msgid "under certain conditions; see the source for copying conditions." -msgstr "υπό οÏισμένους ÏŒÏους, ανατÏέξτε στο αÏχείο COPYING για λεπτομέÏειες" - -#: main.cc:360 -msgid "could not create ARDOUR GUI" -msgstr "δεν γινόταν να δημιουÏγηθεί ARDOUR GUI" - -#: main.cc:378 -msgid "Could not connect to JACK server as \"%1\"" -msgstr "Δεν γινόταν να συνδεθώ στον JACK server σαν \"%1\"" - -#: main.cc:381 -msgid "could not initialize Ardour." -msgstr "δεν γινόταν να εκκινηθεί ο Ardour." - -#: main.cc:392 +#: main.cc:310 msgid "could not load command line session \"%1\"" msgstr "δεν γινόταν να φοÏτωθεί η συνεδÏία γÏαμμής εντολών \"%1\"" #. it wasn't new, but we require a new session -#: main.cc:412 +#: main.cc:330 msgid "" "\n" "\n" @@ -4979,7 +4835,7 @@ msgid "" "To avoid this message, start ardour as \"ardour %1" msgstr "" -#: main.cc:423 +#: main.cc:341 msgid "" "\n" "\n" @@ -4987,299 +4843,448 @@ msgid "" "To create it from the command line, start ardour as \"ardour --new %1" msgstr "" +#: main.cc:405 +msgid "Ardour/GTK " +msgstr "Ardour/GTK " + +#: main.cc:407 +msgid "" +"\n" +" (built using " +msgstr "" + +#: main.cc:411 +#, fuzzy +msgid " with libardour " +msgstr " Ï„Ïέχοντας με libardour " + +#: main.cc:416 +msgid " and GCC version " +msgstr "" + +#: main.cc:426 +#, fuzzy +msgid "Copyright (C) 1999-2006 Paul Davis" +msgstr "Πνευματικα Δικαιώματα 1999-2004 Paul Davis" + +#: main.cc:427 +msgid "" +"Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " +"Baker" +msgstr "" + +#: main.cc:429 +msgid "Ardour comes with ABSOLUTELY NO WARRANTY" +msgstr "Ο Ardour έÏχεται με απολÏτως ΚΑΜΙΑ ΕΓΓΥΗΣΗ" + +#: main.cc:430 +msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." +msgstr "" + +#: main.cc:431 +msgid "This is free software, and you are welcome to redistribute it " +msgstr "" +"Το παÏόν είναι ελεÏθεÏο λογισμικό, είστε ελεÏθεÏοι να το επαναδιανείμετε " + +#: main.cc:432 +#, fuzzy +msgid "under certain conditions; see the source for copying conditions." +msgstr "υπό οÏισμένους ÏŒÏους, ανατÏέξτε στο αÏχείο COPYING για λεπτομέÏειες" + +#: main.cc:441 +msgid "could not create ARDOUR GUI" +msgstr "δεν γινόταν να δημιουÏγηθεί ARDOUR GUI" + +#: main.cc:459 +msgid "Could not connect to JACK server as \"%1\"" +msgstr "Δεν γινόταν να συνδεθώ στον JACK server σαν \"%1\"" + +#: main.cc:462 +msgid "could not initialize Ardour." +msgstr "δεν γινόταν να εκκινηθεί ο Ardour." + #: marker.cc:244 #, fuzzy msgid "MarkerText" msgstr "Στίγματα" -#: marker_time_axis.cc:253 +#: marker_time_axis.cc:254 #, fuzzy msgid "Remove Marker" msgstr "απαλοιφή στίγματος" -#: marker_time_axis.cc:255 +#: marker_time_axis.cc:256 #, fuzzy msgid "Marker" msgstr "Στίγματα" -#: meter_bridge.cc:77 +#: meter_bridge.cc:78 msgid "ardour: meter bridge" msgstr "ardour: γέφυÏα μετÏήσεων" -#: meter_bridge.cc:78 +#: meter_bridge.cc:79 msgid "ardour_meter_bridge" msgstr "ardour_γέφυÏα_μετÏήσεων" -#: meter_bridge_strip.cc:79 meter_bridge_strip.cc:93 +#: meter_bridge_strip.cc:80 meter_bridge_strip.cc:94 #, c-format msgid "# of %u-sample overs" msgstr "# από %u-sample overs" -#: meter_bridge_strip.cc:221 +#: meter_bridge_strip.cc:222 #, fuzzy msgid "New Name for Meter:" msgstr "Îέο όνομα για μετÏητή:" -#: mixer_strip.cc:85 mixer_strip.cc:437 region_editor.cc:46 -msgid "mute" -msgstr "σιγή" +#: mixer_strip.cc:95 mixer_strip.cc:140 mixer_strip.cc:1227 +msgid "pre" +msgstr "Ï€Ïο" -#: mixer_strip.cc:85 mixer_strip.cc:438 -msgid "solo" -msgstr "σόλο" - -#: mixer_strip.cc:85 mixer_strip.cc:436 -msgid "RECORD" -msgstr "ΕΓΓΡΑΦΗ" - -#: mixer_strip.cc:96 mixer_strip.cc:441 mixer_strip.cc:1064 +#: mixer_strip.cc:96 mixer_strip.cc:822 msgid "Comments" msgstr "" -#: mixer_strip.cc:120 mixer_strip.cc:752 -msgid "INPUT" -msgstr "ΕΙΣΟΔΟΣ" +#: mixer_strip.cc:119 +#, fuzzy +msgid "Input" +msgstr "Είσοδοι" -#: mixer_strip.cc:125 mixer_strip.cc:773 -msgid "OUTPUT" -msgstr "ΕΞΟΔΟΣ" +#: mixer_strip.cc:136 mixer_strip.cc:1223 +#, fuzzy +msgid "input" +msgstr "%1 είσοδος" -#: mixer_strip.cc:140 -msgid "Pan automation mode" -msgstr "ΛειτουÏγία Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï Pan" +#: mixer_strip.cc:144 mixer_strip.cc:1231 +#, fuzzy +msgid "post" +msgstr "θÏÏα" -#: mixer_strip.cc:141 -msgid "Gain automation mode" -msgstr "ΛειτουÏγία Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï Gain" +#. TRANSLATORS: this string should be longest of the strings +#. used to describe meter points. In english, its "input". +#. +#: mixer_strip.cc:152 +msgid "tupni" +msgstr "" -#: mixer_strip.cc:143 -msgid "Pan automation type" -msgstr "ΤÏπος Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï Pan" - -#: mixer_strip.cc:144 -msgid "Gain automation type" -msgstr "ΤÏπος Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï Gain" - -#: mixer_strip.cc:183 mixer_strip.cc:195 mixer_strip.cc:913 -msgid "trim" -msgstr "ισοστάθμιση" - -#. XXX it might different in different languages -#: mixer_strip.cc:184 mixer_strip.cc:196 mixer_strip.cc:917 -msgid "abs" -msgstr "abs" - -#: mixer_strip.cc:203 -msgid "gain automation mode" -msgstr "ΛειτουÏγία Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï gain" - -#: mixer_strip.cc:204 -msgid "pan automation mode" -msgstr "ΛειτουÏγία Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï pan" - -#: mixer_strip.cc:205 -msgid "gain automation state" -msgstr "Κατάσταση Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï gain" - -#: mixer_strip.cc:206 -msgid "pan automation state" -msgstr "Κατάσταση Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï pan" - -#: mixer_strip.cc:223 -msgid "varispeed" +#: mixer_strip.cc:207 +#, fuzzy +msgid "Varispeed" msgstr "μεταβλητή ταχÏτητα" -#: mixer_strip.cc:245 mixer_strip.cc:1078 +#: mixer_strip.cc:233 mixer_strip.cc:836 msgid "Click to Add/Edit Comments" msgstr "" -#: mixer_strip.cc:393 +#: mixer_strip.cc:374 msgid "unknown strip width \"%1\" in XML GUI information" msgstr "άγνωστο εÏÏος διαδÏόμου \"%1\" στις πληÏοφοÏίες του XML GUI" -#: mixer_strip.cc:443 mixer_strip.cc:1062 -msgid "*Comments*" +#: mixer_strip.cc:417 +#, fuzzy +msgid "record" +msgstr "ΕγγÏαφή" + +#: mixer_strip.cc:418 region_editor.cc:47 +msgid "mute" +msgstr "σιγή" + +#: mixer_strip.cc:419 +msgid "solo" +msgstr "σόλο" + +#: mixer_strip.cc:422 +msgid "comments" msgstr "" -#: mixer_strip.cc:457 -msgid "REC" -msgstr "REC" +#: mixer_strip.cc:424 +msgid "*comments*" +msgstr "" -#: mixer_strip.cc:462 mixer_strip.cc:1072 +#: mixer_strip.cc:438 +#, fuzzy +msgid "Rec" +msgstr "Επανα-ανίχνευση" + +#: mixer_strip.cc:439 +msgid "M" +msgstr "" + +#: mixer_strip.cc:440 +msgid "S" +msgstr "" + +#: mixer_strip.cc:443 mixer_strip.cc:830 #, fuzzy msgid "Cmt" msgstr "κοπή" -#: mixer_strip.cc:464 mixer_strip.cc:1070 +#: mixer_strip.cc:445 mixer_strip.cc:828 msgid "*Cmt*" msgstr "" -#: mixer_strip.cc:503 mixer_strip.cc:562 redirect_box.cc:1004 +#: mixer_strip.cc:483 mixer_strip.cc:549 redirect_box.cc:1006 msgid "Not connected to JACK - no I/O changes are possible" msgstr "" -#: mixer_strip.cc:569 +#: mixer_strip.cc:560 msgid "Track" msgstr "Κανάλι" -#: mixer_strip.cc:593 mixer_strip.cc:609 +#: mixer_strip.cc:588 mixer_strip.cc:604 msgid "could not register new ports required for that connection" msgstr "" -#: mixer_strip.cc:755 -msgid "IN" +#: mixer_strip.cc:747 +#, fuzzy +msgid " Input" +msgstr "# Είσοδοι" + +#: mixer_strip.cc:750 +#, fuzzy +msgid "I" msgstr "IN" -#: mixer_strip.cc:776 -msgid "OUT" -msgstr "OUT" +#: mixer_strip.cc:820 +msgid "*Comments*" +msgstr "" -#: mixer_strip.cc:884 -msgid "aplay" -msgstr "aplay" - -#: mixer_strip.cc:890 -msgid "awrite" -msgstr "awrite" - -#: mixer_strip.cc:1095 +#: mixer_strip.cc:859 #, fuzzy msgid ": comment editor" msgstr "UI: Ο 'editor' δεν μποÏεί να εγεÏθεί" -#: mixer_strip.cc:1157 mixer_strip.cc:1178 -msgid "no group" -msgstr "καμία ομάδα" +#: mixer_strip.cc:953 +msgid "Grp" +msgstr "" -#: mixer_strip.cc:1181 +#: mixer_strip.cc:956 msgid "~G" msgstr "~G" -#: mixer_strip.cc:1229 +#: mixer_strip.cc:1004 #, fuzzy msgid "Invert Polarity" msgstr "πολικότητα" -#: mixer_ui.cc:84 +#: mixer_ui.cc:85 msgid "Strips" msgstr "ΔιάδÏομοι" -#: mixer_ui.cc:108 -msgid "groupname" -msgstr "" +#: mixer_ui.cc:110 +#, fuzzy +msgid "Group" +msgstr "Ανάμειξη ομάδων" -#: mixer_ui.cc:109 region_editor.cc:48 region_editor.cc:191 -#: region_editor.cc:225 -msgid "active" -msgstr "ενεÏγό" - -#: mixer_ui.cc:110 region_editor.cc:49 -msgid "visible" -msgstr "οÏατό" - -#: mixer_ui.cc:207 mixer_ui.cc:366 +#: mixer_ui.cc:211 mixer_ui.cc:370 msgid "ardour: mixer" msgstr "ardour: μίκτης" -#: mixer_ui.cc:208 +#: mixer_ui.cc:212 msgid "ardour_mixer" msgstr "ardour_μίκτης" -#: mixer_ui.cc:342 +#: mixer_ui.cc:346 msgid "ardour: mixer: " msgstr "ardour: μίκτης: " -#: mixer_ui.cc:569 +#: mixer_ui.cc:573 msgid "signal" msgstr "σήμα" -#: mixer_ui.cc:719 +#: mixer_ui.cc:723 msgid "track display list item for renamed strip not found!" msgstr "Λίστα αναδείξεως καναλιών για μετονομασμένο διάδÏομο δεν ευÏέθη!" -#: option_editor.cc:75 +#: new_session_dialog.cc:39 +#, fuzzy +msgid "New Session Name :" +msgstr "Όνομα συνεδÏίας:" + +#: new_session_dialog.cc:41 +msgid "Create Session Directory In :" +msgstr "" + +#: new_session_dialog.cc:43 +#, fuzzy +msgid "Use Session Template :" +msgstr "ΠÏοσχέδιο συνεδÏίας" + +#: new_session_dialog.cc:45 +#, fuzzy +msgid "Channel Count" +msgstr "ΑκÏÏωση Εισαγωγής" + +#: new_session_dialog.cc:46 +#, fuzzy +msgid "Create Monitor Bus" +msgstr "Control Outs" + +#: new_session_dialog.cc:53 +#, fuzzy +msgid "Create Master Bus" +msgstr "χÏήση των master outs" + +#: new_session_dialog.cc:55 +#, fuzzy +msgid "Automatically Connect Inputs" +msgstr "αυτόματη σÏνδεση inputs καναλιών σε φυσικές θÏÏες" + +#: new_session_dialog.cc:56 new_session_dialog.cc:67 +#, fuzzy +msgid "Port Limit" +msgstr "Ξέχασέ το" + +#: new_session_dialog.cc:64 +#, fuzzy +msgid "Track/Bus Inputs" +msgstr "κανάλια/δίαυλοι" + +#: new_session_dialog.cc:66 +#, fuzzy +msgid "Automatically Connect Outputs" +msgstr "χειÏοκίνητη σÏνδεση των outputs των καναλιών" + +#: new_session_dialog.cc:75 +msgid "Connect to Master Bus" +msgstr "" + +#: new_session_dialog.cc:76 +msgid "Connect to Physical Outputs" +msgstr "" + +#: new_session_dialog.cc:80 +#, fuzzy +msgid "Track/Bus Outputs" +msgstr "Έξοδοι" + +#: new_session_dialog.cc:83 +#, fuzzy +msgid "Advanced Options" +msgstr "Επεξ/στης Ρυθμίσεων" + +#: new_session_dialog.cc:91 +#, fuzzy +msgid "Open Recent Session" +msgstr "Άνοιγμα συνεδÏίας" + +#: new_session_dialog.cc:127 +#, fuzzy +msgid "Open Session File :" +msgstr "Άνοιγμα συνεδÏίας" + +#: new_session_dialog.cc:274 +#, fuzzy +msgid "New Session" +msgstr "ΣυνεδÏία" + +#: new_session_dialog.cc:276 +#, fuzzy +msgid "Open Session" +msgstr "Άνοιγμα συνεδÏίας" + +#: new_session_dialog.cc:281 +#, fuzzy +msgid "ardour: session control" +msgstr "ardour_νέα_συνεδÏία" + +#: new_session_dialog.cc:310 +#, fuzzy +msgid "select template" +msgstr "ΧωÏίς Ï€Ïοσχέδιο" + +#: new_session_dialog.cc:316 +#, fuzzy +msgid "select session file" +msgstr "επιλογή πεÏιοχών" + +#: new_session_dialog.cc:325 +#, fuzzy +msgid "select directory" +msgstr "επιλογή πεÏιοχών" + +#: option_editor.cc:76 #, fuzzy msgid "SMPTE offset is negative" msgstr "SMPTE ΈναÏξη" -#: option_editor.cc:101 +#: option_editor.cc:102 msgid "ardour: options editor" msgstr "ardour: επεξεÏγαστής Ïυθμίσεων" -#: option_editor.cc:102 +#: option_editor.cc:103 msgid "ardour_option_editor" msgstr "ardour_επεξεÏγαστής_Ïυθμίσεων" -#: option_editor.cc:126 +#: option_editor.cc:127 msgid "Paths/Files" msgstr "Paths/ΑÏχεία" -#: option_editor.cc:127 +#: option_editor.cc:128 msgid "Kbd/Mouse" msgstr "ΠλκτÏ/Ποντίκι" -#: option_editor.cc:130 +#: option_editor.cc:131 msgid "Layers & Fades" msgstr "" -#: option_editor.cc:134 +#: option_editor.cc:135 msgid "MIDI" msgstr "MIDI" -#: option_editor.cc:176 +#: option_editor.cc:177 msgid "24 FPS" msgstr "24 FPS" -#: option_editor.cc:178 +#: option_editor.cc:179 msgid "25 FPS" msgstr "25 FPS" -#: option_editor.cc:180 +#: option_editor.cc:181 #, fuzzy msgid "30 FPS" msgstr "30 FPS drop" -#: option_editor.cc:186 +#: option_editor.cc:187 msgid "30 FPS drop" msgstr "30 FPS drop" -#: option_editor.cc:243 +#: option_editor.cc:244 msgid "session RAID path" msgstr "RAID path συνεδÏίας" -#: option_editor.cc:248 +#: option_editor.cc:249 #, fuzzy msgid "Soundfile Search Paths" msgstr "Βιβλιοθήκη Soundfiles" -#: option_editor.cc:253 +#: option_editor.cc:254 #, fuzzy msgid "Paths" msgstr "Paths/ΑÏχεία" -#: option_editor.cc:267 option_editor.cc:273 option_editor.cc:724 -#: option_editor.cc:751 +#: option_editor.cc:268 option_editor.cc:274 option_editor.cc:723 +#: option_editor.cc:750 msgid "internal" msgstr "εσωτεÏικό" -#: option_editor.cc:286 +#: option_editor.cc:287 msgid "Short crossfade length (msecs)" msgstr "" -#: option_editor.cc:298 +#: option_editor.cc:299 msgid "Destructive crossfade length (msecs)" msgstr "" -#: option_editor.cc:366 +#: option_editor.cc:367 msgid "SMPTE Frames/second" msgstr "SMPTE ΚαÏέ/δεÏτεÏα" -#: option_editor.cc:367 +#: option_editor.cc:368 msgid "SMPTE Offset" msgstr "SMPTE ΈναÏξη" -#: option_editor.cc:461 option_editor.cc:468 option_editor.cc:471 -#: option_editor.cc:617 +#: option_editor.cc:462 option_editor.cc:469 option_editor.cc:472 +#: option_editor.cc:618 #, fuzzy msgid "online" msgstr "γÏαμμική" @@ -5287,12 +5292,12 @@ msgstr "γÏαμμική" #. remember, we have to handle the i18n case where the relative #. lengths of the strings in language N is different than in english. #. -#: option_editor.cc:468 option_editor.cc:469 option_editor.cc:614 +#: option_editor.cc:469 option_editor.cc:470 option_editor.cc:615 #, fuzzy msgid "offline" msgstr "γÏαμμική" -#: option_editor.cc:669 +#: option_editor.cc:670 msgid "Choose Click" msgstr "" @@ -5301,15 +5306,15 @@ msgstr "" msgid "Choose Click Emphasis" msgstr "Έμφαση χÏήσεως όπως στο μετÏονόμο" -#: option_editor.cc:804 +#: option_editor.cc:803 msgid "Click audio file" msgstr "ΑÏχείο ήχου ΜετÏονόμου" -#: option_editor.cc:810 +#: option_editor.cc:809 msgid "Click emphasis audiofile" msgstr "ΑÏχείο ήχου εμφάσεως ΜετÏονόμου" -#: option_editor.cc:847 +#: option_editor.cc:846 msgid "" "The auditioner is a dedicated mixer strip used\n" "for listening to specific regions outside the context\n" @@ -5321,35 +5326,35 @@ msgstr "" "του Î³ÎµÎ½Î¹ÎºÎ¿Ï Î¼Î¹Î¾Î±Ïίσματος. ΜποÏεί να συνδεθεί σαν άλλος ένας\n" "διάδÏομος μίξεως ή κανάλι." -#: option_editor.cc:920 +#: option_editor.cc:919 msgid "Edit using" msgstr "ΕπεξεÏγασία με" -#: option_editor.cc:927 option_editor.cc:954 +#: option_editor.cc:926 option_editor.cc:953 msgid "+ button" msgstr "+ κουμπί" -#: option_editor.cc:947 +#: option_editor.cc:946 msgid "Delete using" msgstr "ΔιαγÏαφή με" -#: option_editor.cc:974 +#: option_editor.cc:973 msgid "Ignore snap using" msgstr "Άγνοια έλξεως με" -#: opts.cc:47 +#: opts.cc:46 msgid "Usage: " msgstr "ΧÏήση: " -#: opts.cc:48 +#: opts.cc:47 msgid " -v, --version Show version information\n" msgstr " -v, --version ΠληÏοφοÏίες εκδόσεως\n" -#: opts.cc:49 +#: opts.cc:48 msgid " -h, --help Print this message\n" msgstr " -h, --help ΠÏοβολή του παÏόντος\n" -#: opts.cc:50 +#: opts.cc:49 msgid "" " -b, --bindings Print all possible keyboard binding " "names\n" @@ -5357,12 +5362,12 @@ msgstr "" " -b, --bindings ΠÏοβολή όλων των πιθανών δεσμών " "πληκτÏολογίου ονόματα\n" -#: opts.cc:51 +#: opts.cc:50 #, fuzzy msgid " -n, --show-splash Show splash screen\n" msgstr " -n, --no-splash Μήν δείξεις την εισαγωγική εικόνα\n" -#: opts.cc:52 +#: opts.cc:51 #, fuzzy msgid "" " -c, --name name Use a specific jack client name, default " @@ -5371,151 +5376,164 @@ msgstr "" " -c, --jack-client-name name ΧÏήση συγκεκÏιμένου ονόματος για τον " "jack, το Ï€ÏοκαθοÏισμένο είναι ardour\n" -#: opts.cc:53 +#: opts.cc:52 #, fuzzy msgid "" " -N, --new session-name Create a new session from the command " "line\n" msgstr " [όνομα-συνεδÏίας] Όνομα συνεδÏίας Ï€Ïος φόÏτωση\n" -#: opts.cc:54 +#: opts.cc:53 msgid "" " -o, --use-hw-optimizations Try to use h/w specific optimizations\n" msgstr "" -#: opts.cc:56 +#: opts.cc:55 #, fuzzy msgid " -V, --novst Do not use VST support\n" msgstr " -n, --no-splash Μήν δείξεις την εισαγωγική εικόνα\n" -#: opts.cc:58 +#: opts.cc:57 msgid " [session-name] Name of session to load\n" msgstr " [όνομα-συνεδÏίας] Όνομα συνεδÏίας Ï€Ïος φόÏτωση\n" -#: opts.cc:59 +#: opts.cc:58 msgid " -C, --curvetest filename Curve algorithm debugger\n" msgstr "" -#: opts.cc:60 +#: opts.cc:59 #, fuzzy msgid " -g, --gtktheme Allow GTK to load a theme\n" msgstr " -h, --help ΠÏοβολή του παÏόντος\n" -#: pan_automation_time_axis.cc:59 +#: pan_automation_time_axis.cc:60 msgid "You can't graphically edit panning of more than stream" msgstr "" -#: pan_automation_time_axis.cc:79 +#: pan_automation_time_axis.cc:80 #, fuzzy msgid "add pan automation event" msgstr "Ï€Ïόσθεση συμβάντος Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï ÏƒÎµ " -#: panner2d.cc:588 panner_ui.cc:393 plugin_ui.cc:833 +#: panner2d.cc:589 panner_ui.cc:435 plugin_ui.cc:834 #, fuzzy msgid "Bypass" msgstr "bypass" -#: panner_ui.cc:57 panner_ui.cc:187 +#: panner_ui.cc:58 panner_ui.cc:225 #, fuzzy msgid "link" msgstr "in" +#: panner_ui.cc:69 +msgid "Pan automation mode" +msgstr "ΛειτουÏγία Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï Pan" + #: panner_ui.cc:70 +msgid "Pan automation type" +msgstr "ΤÏπος Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï Pan" + +#: panner_ui.cc:81 msgid "panning link control" msgstr "έλεγχος panning link" -#: panner_ui.cc:72 +#: panner_ui.cc:83 msgid "panning link direction" msgstr "κατεÏθυνση panning link" -#: panner_ui.cc:197 +#: panner_ui.cc:235 msgid "L" msgstr "L" -#: panner_ui.cc:296 +#: panner_ui.cc:335 +#, fuzzy, c-format +msgid "panner for channel %lu" +msgstr "panner για το κανάλι %u" + +#: panner_ui.cc:337 #, c-format msgid "panner for channel %u" msgstr "panner για το κανάλι %u" -#: panner_ui.cc:403 +#: panner_ui.cc:445 #, fuzzy msgid "Reset all" msgstr "Επιλογή όλων" -#: playlist_selector.cc:51 +#: playlist_selector.cc:52 #, fuzzy msgid "ardour: playlists" msgstr "ardour: plugins" -#: playlist_selector.cc:58 +#: playlist_selector.cc:59 msgid "Playlists grouped by track" msgstr "" -#: playlist_selector.cc:97 +#: playlist_selector.cc:98 #, fuzzy msgid "ardour: playlist for " msgstr "ardour: επεξεÏγαστής: " -#: playlist_selector.cc:113 +#: playlist_selector.cc:114 #, fuzzy msgid "Other tracks" msgstr "νÏξη καναλιοÏ" -#: playlist_selector.cc:129 +#: playlist_selector.cc:130 msgid "unassigned" msgstr "" -#: plugin_selector.cc:42 +#: plugin_selector.cc:43 msgid "ardour: plugins" msgstr "ardour: plugins" -#: plugin_selector.cc:55 +#: plugin_selector.cc:56 #, fuzzy msgid "Available LADSPA Plugins" msgstr "Διαθέσιμα LADSPA plugins" -#: plugin_selector.cc:56 +#: plugin_selector.cc:57 msgid "Type" msgstr "ΤÏπωση" -#: plugin_selector.cc:57 plugin_selector.cc:80 +#: plugin_selector.cc:58 plugin_selector.cc:81 msgid "# Inputs" msgstr "# Είσοδοι" -#: plugin_selector.cc:58 plugin_selector.cc:81 +#: plugin_selector.cc:59 plugin_selector.cc:82 msgid "# Outputs" msgstr "# Έξοδοι" -#: plugin_selector.cc:67 +#: plugin_selector.cc:68 msgid "Plugins to be Connected to Insert" msgstr "" -#: plugin_selector.cc:79 +#: plugin_selector.cc:80 #, fuzzy msgid "Available plugins" msgstr "Διαθέσιμα VST plugins" -#: plugin_selector.cc:97 +#: plugin_selector.cc:98 msgid "Add a plugin to the effect list" msgstr "ΠÏόσθεση plugin στη λίστα των εφφέ" -#: plugin_selector.cc:99 +#: plugin_selector.cc:102 msgid "Remove a plugin from the effect list" msgstr "Απαλοιφή plugin από τη λίστα των εφφέ" -#: plugin_selector.cc:101 +#: plugin_selector.cc:104 msgid "Update available plugins" msgstr "Ανανέωση διαθέσιμων plugins" -#: plugin_selector.cc:123 +#: plugin_selector.cc:126 msgid "LADSPA" msgstr "LADSPA" -#: plugin_selector.cc:126 +#: plugin_selector.cc:129 msgid "VST" msgstr "VST" -#: plugin_ui.cc:83 +#: plugin_ui.cc:84 msgid "" "unknown type of editor-supplying plugin (note: no VST support in this " "version of ardour)" @@ -5523,50 +5541,51 @@ msgstr "" "άγνωστος Ï„Ïπος Ï€Ïομηθευμένου plugin για τον editor(σημείωση: δεν υπάÏχει " "υποστήÏιξη VST στην παÏοÏσα έκδοση του ardour)" -#: plugin_ui.cc:138 +#: plugin_ui.cc:139 msgid "Presets" msgstr "" -#: plugin_ui.cc:229 +#: plugin_ui.cc:230 #, fuzzy msgid "Controls" msgstr "Control Outs" -#: plugin_ui.cc:266 +#: plugin_ui.cc:267 msgid "Plugin Editor: could not build control element for port %1" msgstr "" "ΕπεξεÏγαστής Plugin: δεν μπόÏεσα να κτίσω στοιχείο ελέγχου για τη θÏÏα %1" -#: plugin_ui.cc:357 -msgid "automation control" +#: plugin_ui.cc:358 +#, fuzzy +msgid "Automation control" msgstr "έλεγχος αυτοματισμοÏ" -#: plugin_ui.cc:853 +#: plugin_ui.cc:854 msgid "Plugin preset %1 not found" msgstr "ΠÏο-ÏÏθμιση plugin %1 δεν ευÏέθη" -#: plugin_ui.cc:863 +#: plugin_ui.cc:864 #, fuzzy msgid "Name of New Preset:" msgstr "Όνομα για νέα σÏνδεση:" -#: redirect_automation_line.cc:53 +#: redirect_automation_line.cc:54 msgid "redirect automation created for non-plugin" msgstr "Ï€Ïοώθηση Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï Î´Î·Î¼Î¹Î¿Ï…Ïγημένου για non-plugin" -#: redirect_automation_time_axis.cc:93 +#: redirect_automation_time_axis.cc:94 msgid "add automation event to " msgstr "Ï€Ïόσθεση συμβάντος Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï ÏƒÎµ " -#: redirect_box.cc:222 +#: redirect_box.cc:223 msgid "New send" msgstr "Nέο send" -#: redirect_box.cc:223 +#: redirect_box.cc:224 msgid "Show send controls" msgstr "Ανάδειξη Ïυθμίσεων send" -#: redirect_box.cc:377 +#: redirect_box.cc:383 msgid "" "You attempted to add a plugin (%1).\n" "The plugin has %2 inputs\n" @@ -5584,7 +5603,7 @@ msgstr "" "Δεν έχει νόημα - έτσι χαÏαμίζετε\n" "μέÏος του σήματος." -#: redirect_box.cc:389 +#: redirect_box.cc:395 msgid "" "You attempted to add a plugin (%1).\n" "The plugin has %2 inputs\n" @@ -5604,7 +5623,7 @@ msgstr "" "επι μέÏους inputs. Μελλοντική έκδοση του Ardour θα\n" "υποστηÏίζει αυτον τον Ï„Ïπο διατάξεως." -#: redirect_box.cc:402 +#: redirect_box.cc:408 msgid "" "You attempted to add a plugin (%1).\n" "\n" @@ -5626,34 +5645,34 @@ msgstr "" "\n" "Ο Ardour δεν γνωÏίζει τι να κάνει σε τέτοιες πεÏιπτώσεις.\n" -#: redirect_box.cc:493 +#: redirect_box.cc:495 msgid "Pre-fader inserts, sends & plugins:" msgstr "Pre-fader εισαγωγές, sends & plugins:" -#: redirect_box.cc:496 +#: redirect_box.cc:498 msgid "Post-fader inserts, sends & plugins:" msgstr "Post-fader εισαγωγές, sends & plugins:" -#: redirect_box.cc:642 +#: redirect_box.cc:644 msgid "" "You cannot reorder this set of redirects\n" "in that way because the inputs and\n" "outputs do not work correctly." msgstr "" -#: redirect_box.cc:747 +#: redirect_box.cc:749 #, fuzzy msgid "rename redirect" msgstr "ardour: μετονομασία redirect" -#: redirect_box.cc:824 redirect_box.cc:872 +#: redirect_box.cc:826 redirect_box.cc:874 msgid "" "Copying the set of redirects on the clipboard failed,\n" "probably because the I/O configuration of the plugins\n" "could not match the configuration of this track." msgstr "" -#: redirect_box.cc:894 +#: redirect_box.cc:896 msgid "" "Do you really want to remove all redirects from this track?\n" "(this cannot be undone)" @@ -5661,7 +5680,7 @@ msgstr "" "Στ'αλήθεια θέλετε να απαλοίψετε όλα τα redirects από το κανάλι?\n" "(δεν μποÏεί να ανακληθεί)" -#: redirect_box.cc:897 +#: redirect_box.cc:899 msgid "" "Do you really want to remove all redirects from this bus?\n" "(this cannot be undone)" @@ -5669,243 +5688,255 @@ msgstr "" "Στ'αλήθεια θέλετε να απαλοίψετε όλα τα redirects από το δίαυλο?\n" "(δεν μποÏεί να ανακληθεί)" -#: redirect_box.cc:902 +#: redirect_box.cc:904 msgid "Yes, remove them all" msgstr "Îαι, απάλοιψέ τα όλα" -#: redirect_box.cc:938 +#: redirect_box.cc:940 msgid "ardour: %1" msgstr "ardour: %1" -#: redirect_box.cc:980 +#: redirect_box.cc:982 #, fuzzy msgid "ardour: %1: %2 (by %3)" msgstr "ardour: %1: %2" #. new stuff -#: redirect_box.cc:1052 +#: redirect_box.cc:1054 msgid "New Plugin ..." msgstr "Îέο Plugin ..." -#: redirect_box.cc:1053 +#: redirect_box.cc:1055 msgid "New Insert" msgstr "Îέο ΠÏοσθήκη" -#: redirect_box.cc:1054 +#: redirect_box.cc:1056 msgid "New Send ..." msgstr "Îέο Send ..." -#: redirect_box.cc:1066 +#: redirect_box.cc:1068 #, fuzzy msgid "Deselect All" msgstr "Επιλογή όλων" -#: redirect_box.cc:1073 +#: redirect_box.cc:1075 #, fuzzy msgid "Activate all" msgstr "ΕνεÏγοποίηση όλων" -#: redirect_box.cc:1074 +#: redirect_box.cc:1076 #, fuzzy msgid "Deactivate all" msgstr "ΑπενεÏγοποίηση όλων" -#: region_editor.cc:44 +#: region_editor.cc:45 msgid "NAME:" msgstr "ÎŒÎΟΜΑ:" -#: region_editor.cc:45 +#: region_editor.cc:46 msgid "lock" msgstr "κλείδωμα" -#: region_editor.cc:47 +#: region_editor.cc:48 msgid "opaque" msgstr "αδιαφανής" -#: region_editor.cc:52 +#: region_editor.cc:49 region_editor.cc:192 region_editor.cc:226 +msgid "active" +msgstr "ενεÏγό" + +#: region_editor.cc:50 +msgid "visible" +msgstr "οÏατό" + +#: region_editor.cc:53 msgid "Layer" msgstr "ΣτÏώμα" -#: region_editor.cc:60 +#: region_editor.cc:54 +msgid "play" +msgstr "αναπαÏαγωγή" + +#: region_editor.cc:61 msgid "ENVELOPE" msgstr "ΧΡΟÎΟΔΙΑΓΡΑΜΜΑ" -#: region_editor.cc:106 +#: region_editor.cc:107 msgid "mute this region" msgstr "σιγή παÏοÏσας πεÏιοχής" -#: region_editor.cc:107 +#: region_editor.cc:108 msgid "regions underneath this one cannot be heard" msgstr "πεÏιοχές κάτωθι της παÏοÏσας δεν μποÏοÏν να ακουστοÏν" -#: region_editor.cc:108 +#: region_editor.cc:109 msgid "prevent any changes to this region" msgstr "αποτÏοπή αλλαγών σε αυτή την πεÏιοχή" -#: region_editor.cc:109 +#: region_editor.cc:110 msgid "use the gain envelope during playback" msgstr "χÏήση χÏονοδιαγÏάμματος του gain κατά την αναπαÏ/γή" -#: region_editor.cc:110 +#: region_editor.cc:111 msgid "show the gain envelope" msgstr "ανάδειξη χÏονοδιαγÏάμματος του gain" -#: region_editor.cc:111 +#: region_editor.cc:112 msgid "use fade in curve during playback" msgstr "χÏήση της καμπÏλης fade in κατά την αναπαÏ/γή" -#: region_editor.cc:112 +#: region_editor.cc:113 msgid "use fade out curve during playback" msgstr "χÏήση της καμπÏλης fade out κατά την αναπαÏ/γή" -#: region_editor.cc:113 +#: region_editor.cc:114 msgid "audition this region" msgstr "ακÏόαση της πεÏιοχής" -#: region_editor.cc:146 +#: region_editor.cc:147 msgid "START:" msgstr "ΑΡΧΗ:" -#: region_editor.cc:148 +#: region_editor.cc:149 msgid "END:" msgstr "ΛΗΞΗ:" -#: region_editor.cc:150 +#: region_editor.cc:151 msgid "LENGTH:" msgstr "ΜΗΚΟΣ:" -#: region_editor.cc:190 +#: region_editor.cc:191 msgid "FADE IN" msgstr "FADE IN" -#: region_editor.cc:192 region_editor.cc:226 +#: region_editor.cc:193 region_editor.cc:227 msgid "msecs" msgstr "msecs" -#: region_editor.cc:224 +#: region_editor.cc:225 msgid "FADE OUT" msgstr "FADE OUT" -#: region_editor.cc:264 +#: region_editor.cc:265 msgid "ardour: region " msgstr "ardour: πεÏιοχή " -#: region_editor.cc:401 +#: region_editor.cc:402 msgid "fade in edit" msgstr "επεξεÏ/σία fade in" -#: region_editor.cc:413 +#: region_editor.cc:414 msgid "fade out edit" msgstr "επεξεÏ/σία fade out" -#: regionview.cc:1140 +#: regionview.cc:1146 #, fuzzy msgid "add gain control point" msgstr "απαλοιφή σημείου ελέγχου" -#: route_params_ui.cc:88 +#: route_params_ui.cc:89 msgid "Tracks/Buses" msgstr "κανάλια/δίαυλοι" -#: route_params_ui.cc:108 +#: route_params_ui.cc:109 #, fuzzy msgid "Pre-fader Redirects" msgstr "ΠÏο-Redirects" -#: route_params_ui.cc:109 +#: route_params_ui.cc:110 #, fuzzy msgid "Post-fader Redirects" msgstr "Μετα-Redirects" -#: route_params_ui.cc:141 +#: route_params_ui.cc:144 #, fuzzy msgid "ardour: track/bus inspector" msgstr "ardour: Εισαγωγή καναλιοÏ/διαÏλου" -#: route_params_ui.cc:142 +#: route_params_ui.cc:145 msgid "ardour_route_parameters" msgstr "ardour_παÏάμετÏοι_διαδÏομών" -#: route_params_ui.cc:199 +#: route_params_ui.cc:202 msgid "route display list item for renamed route not found!" msgstr "Η λίστα ανάδειξης διαδÏομών για μετονομασμένη διαδÏομή δεν ευÏέθη!" -#: route_params_ui.cc:451 +#: route_params_ui.cc:453 msgid "NO TRACK" msgstr "Κανένα κανάλι" -#: route_params_ui.cc:693 +#: route_params_ui.cc:695 #, fuzzy msgid "ardour: track/bus inspector: " msgstr "ardour: Εισαγωγή καναλιοÏ/διαÏλου" -#: route_params_ui.cc:697 +#: route_params_ui.cc:699 msgid "No Route Selected" msgstr "Δεν επελέχθη διαδÏομή" -#: route_params_ui.cc:698 +#: route_params_ui.cc:700 #, fuzzy msgid "ardour: track/bus/inspector: no route selected" msgstr "ardour: παÏάμετÏοι διαδÏομών: δεν επελέχθη διαδÏομή" #. ctrl-shift-click applies change to all routes -#: route_ui.cc:133 +#: route_ui.cc:134 msgid "mute change" msgstr "αλλαγή σιγής" #. ctrl-shift-click applies change to all routes #. ctrl-alt-click: exclusively solo this track, not a toggle */ -#: route_ui.cc:208 route_ui.cc:218 +#: route_ui.cc:209 route_ui.cc:219 msgid "solo change" msgstr "αλλαγή σόλο" -#: route_ui.cc:281 +#: route_ui.cc:282 msgid "rec-enable change" msgstr "αλλαγή rec-enable" -#: route_ui.cc:472 +#: route_ui.cc:479 #, fuzzy msgid "Solo-safe" msgstr "Σόλο" -#: route_ui.cc:480 route_ui.cc:523 +#: route_ui.cc:487 route_ui.cc:530 #, fuzzy msgid "MIDI Bind" msgstr "MIDI" -#: route_ui.cc:494 +#: route_ui.cc:501 msgid "Pre Fader" msgstr "ΠÏο Fader" -#: route_ui.cc:501 +#: route_ui.cc:508 msgid "Post Fader" msgstr "Μετά Fader" -#: route_ui.cc:508 +#: route_ui.cc:515 msgid "Control Outs" msgstr "Control Outs" -#: route_ui.cc:515 +#: route_ui.cc:522 msgid "Main Outs" msgstr "Main Outs" -#: route_ui.cc:552 +#: route_ui.cc:559 msgid "mix group solo change" msgstr "αλλαγή solo ομάδας μίξεως" -#: route_ui.cc:586 +#: route_ui.cc:593 msgid "mix group mute change" msgstr "αλλαγή mute ομάδας μίξεως" -#: route_ui.cc:602 +#: route_ui.cc:609 msgid "mix group rec-enable change" msgstr "αλλαγή rec-enable ομάδας μίξεως" -#: route_ui.cc:619 visual_time_axis.cc:236 +#: route_ui.cc:626 visual_time_axis.cc:237 msgid "ardour: color selection" msgstr "ardour: επιλογή χÏωμάτων" -#: route_ui.cc:695 +#: route_ui.cc:702 #, fuzzy msgid "" "Do you really want to remove track \"%1\" ?\n" @@ -5917,7 +5948,7 @@ msgstr "" "Πιθανόν να χάσετε και τη λίστα που χÏησιμοποιείται από το κανάλι.\n" "(δεν μποÏεί να ανακληθεί)" -#: route_ui.cc:697 +#: route_ui.cc:704 msgid "" "Do you really want to remove bus \"%1\" ?\n" "(cannot be undone)" @@ -5925,11 +5956,11 @@ msgstr "" "Στ'αλήθεια θέλετε να απαλοίψετε το κανάλι \"%1\" ?\n" "(δεν μποÏεί να ανακληθεί)" -#: route_ui.cc:701 visual_time_axis.cc:278 +#: route_ui.cc:708 visual_time_axis.cc:279 msgid "Yes, remove it." msgstr "Îαι, απάλοιψε το." -#: route_ui.cc:730 +#: route_ui.cc:737 #, fuzzy msgid "New Name: " msgstr "νέο όνομα: " @@ -5987,148 +6018,149 @@ msgstr "Δεν γινόταν να διαβαστεί το soundfile: " msgid "Name for Field" msgstr "Όνομα για πεÏιοχή:" -#: sfdb_ui.cc:333 +#: sfdb_ui.cc:335 msgid "Split Channels" msgstr "ΔιαχωÏισμός Καναλιών" -#: sfdb_ui.cc:340 +#: sfdb_ui.cc:342 msgid "Create a region for each channel" msgstr "" -#: sfdb_ui.cc:342 +#: sfdb_ui.cc:344 msgid "Embed" msgstr "" -#: sfdb_ui.cc:344 +#: sfdb_ui.cc:346 #, fuzzy msgid "Link to an external file" msgstr "ΠÏοσθήκη εξωτεÏÎ¹ÎºÎ¿Ï Î±Ïχείου ήχου" -#: sfdb_ui.cc:346 +#: sfdb_ui.cc:348 msgid "Import" msgstr "Εισαγωγή" -#: sfdb_ui.cc:348 +#: sfdb_ui.cc:350 msgid "Copy a file to the session folder" msgstr "" -#: sfdb_ui.cc:412 +#: sfdb_ui.cc:414 #, fuzzy msgid "programming error: %1" msgstr "σφάλμα Ï€ÏογÏαμματισμοÏ: " -#: tempo_dialog.cc:17 tempo_dialog.cc:34 +#: tempo_dialog.cc:18 tempo_dialog.cc:35 msgid "Beats per minute" msgstr "ΚτÏποι ανά λεπτό" -#: tempo_dialog.cc:20 tempo_dialog.cc:37 tempo_dialog.cc:153 -#: tempo_dialog.cc:171 +#: tempo_dialog.cc:21 tempo_dialog.cc:38 tempo_dialog.cc:203 +#: tempo_dialog.cc:221 msgid "Bar" msgstr "ΜπάÏα" -#: tempo_dialog.cc:21 tempo_dialog.cc:38 tempo_dialog.cc:154 -#: tempo_dialog.cc:172 +#: tempo_dialog.cc:22 tempo_dialog.cc:39 tempo_dialog.cc:204 +#: tempo_dialog.cc:222 msgid "Beat" msgstr "ΚτÏπος" -#: tempo_dialog.cc:23 tempo_dialog.cc:40 tempo_dialog.cc:155 -#: tempo_dialog.cc:173 +#: tempo_dialog.cc:24 tempo_dialog.cc:41 tempo_dialog.cc:205 +#: tempo_dialog.cc:223 msgid "Location" msgstr "Τοποθεσία" -#: tempo_dialog.cc:149 tempo_dialog.cc:167 +#: tempo_dialog.cc:199 tempo_dialog.cc:217 msgid "Meter denominator" msgstr "ΠαÏονομαστής ΜέτÏου" -#: tempo_dialog.cc:150 tempo_dialog.cc:168 +#: tempo_dialog.cc:200 tempo_dialog.cc:218 msgid "Beats per bar" msgstr "ΚτÏποι ανά μπάÏα" -#: tempo_dialog.cc:186 tempo_dialog.cc:197 +#: tempo_dialog.cc:236 tempo_dialog.cc:247 msgid "whole (1)" msgstr "ολόκληÏο (1)" -#: tempo_dialog.cc:187 tempo_dialog.cc:199 +#: tempo_dialog.cc:237 tempo_dialog.cc:249 msgid "second (2)" msgstr "δεÏτεÏο (2)" -#: tempo_dialog.cc:188 tempo_dialog.cc:201 +#: tempo_dialog.cc:238 tempo_dialog.cc:251 msgid "third (3)" msgstr "Ï„Ïίτο (3)" -#: tempo_dialog.cc:189 tempo_dialog.cc:203 tempo_dialog.cc:211 +#: tempo_dialog.cc:239 tempo_dialog.cc:253 tempo_dialog.cc:261 msgid "quarter (4)" msgstr "τέταÏτο (4)" -#: tempo_dialog.cc:190 tempo_dialog.cc:205 +#: tempo_dialog.cc:240 tempo_dialog.cc:255 msgid "eighth (8)" msgstr "όγδοο (8)" -#: tempo_dialog.cc:191 tempo_dialog.cc:207 +#: tempo_dialog.cc:241 tempo_dialog.cc:257 msgid "sixteenth (16)" msgstr "δέκατο έκτο (16)" -#: tempo_dialog.cc:192 tempo_dialog.cc:209 +#: tempo_dialog.cc:242 tempo_dialog.cc:259 msgid "thirty-second (32)" msgstr "Ï„Ïιακοστό-όγδοο (32)" -#: tempo_dialog.cc:321 +#: tempo_dialog.cc:420 msgid "garbaged note type entry (%1)" msgstr "είσοδος(type entry) άχÏηστης σημειώσεως (%1)" -#: tempo_dialog.cc:331 +#: tempo_dialog.cc:430 msgid "incomprehensible note type entry (%1)" msgstr "είσοδος(type entry) ακατανόητης σημειώσεως (%1)" -#: time_axis_view.cc:111 +#: time_axis_view.cc:112 msgid "gTortnam" msgstr "gTortnam" -#: time_axis_view.cc:548 +#: time_axis_view.cc:549 msgid "Largest" msgstr "Μέγιστο" -#: time_axis_view.cc:549 +#: time_axis_view.cc:550 msgid "Large" msgstr "Μεγάλο" -#: time_axis_view.cc:550 +#: time_axis_view.cc:551 msgid "Larger" msgstr "ΜεγαλÏτεÏο" -#: time_axis_view.cc:552 +#: time_axis_view.cc:553 msgid "Smaller" msgstr "ΜικÏότεÏο" -#: time_axis_view.cc:553 +#: time_axis_view.cc:554 msgid "Small" msgstr "ΜικÏÏŒ" -#: time_axis_view.cc:869 +#: time_axis_view.cc:870 msgid "unknown track height name \"%1\" in XML GUI information" msgstr "Άγνωστο όνομα Ïψους καναλιοÏ\"%1\" στις XML GUI πληÏοφοÏίες" -#: time_axis_view_item.cc:71 +#. first constructed item sets up font info +#: time_axis_view_item.cc:79 msgid "TimeAxisViewItemName" msgstr "" -#: time_axis_view_item.cc:271 +#: time_axis_view_item.cc:298 msgid "new duration %1 frames is out of bounds for %2" msgstr "νέα διάÏκεια %1 καÏέ είναι εκτός οÏίων για %2" -#: time_selection.cc:40 +#: time_selection.cc:41 msgid "programming error: request for non-existent audio range (%1)!" msgstr "Σφάλμα Ï€ÏογÏαμματισμοÏ: request για μη-υπάÏχον ηχητικό διάστημα (%1)!" -#: utils.cc:106 utils.cc:149 +#: utils.cc:107 utils.cc:150 msgid "bad XPM header %1" msgstr "εσφαλμένος XPM header %1" -#: utils.cc:331 +#: utils.cc:332 msgid "missing RGBA style for \"%1\"" msgstr "" -#: visual_time_axis.cc:275 +#: visual_time_axis.cc:276 msgid "" "Do you really want to remove track \"%1\" ?\n" "(cannot be undone)" @@ -6136,14 +6168,87 @@ msgstr "" "Στ'αλήθεια θέλετε να απαλοίψετε το κανάλι \"%1\" ?\n" "(δεν μποÏεί να ανακληθεί)" -#: visual_time_axis.cc:324 +#: visual_time_axis.cc:325 msgid "new name: " msgstr "νέο όνομα: " -#: visual_time_axis.cc:335 +#: visual_time_axis.cc:336 msgid "A track already exists with that name" msgstr "Κανάλι με αυτό το όνομα ήδη υπάÏχει" +#~ msgid "set selected trackview" +#~ msgstr "θέση επιλεγμένης οπτικής καναλιοÏ" + +#, fuzzy +#~ msgid "set selected control point" +#~ msgstr "απαλοιφή σημείου ελέγχου" + +#~ msgid "set selected regionview" +#~ msgstr "θέση επιλεγμένης οπτικής πεÏιοχής" + +#~ msgid "Start a new session\n" +#~ msgstr "ΑÏχή καινοÏÏιας συνεδÏίας\n" + +#~ msgid "via Session menu" +#~ msgstr "μέσω του Î¼ÎµÎ½Î¿Ï Î£Ï…Î½ÎµÎ´Ïίας" + +#~ msgid "dbFS" +#~ msgstr "dbFS" + +#, fuzzy +#~ msgid "Advanced" +#~ msgstr "ΠÏοχωÏημένα..." + +#, fuzzy +#~ msgid "Select a File" +#~ msgstr "Επιλογή όλων" + +#, fuzzy +#~ msgid "Track/Bus connection options" +#~ msgstr "κανάλια/δίαυλοι" + +#~ msgid "RECORD" +#~ msgstr "ΕΓΓΡΑΦΗ" + +#~ msgid "INPUT" +#~ msgstr "ΕΙΣΟΔΟΣ" + +#~ msgid "OUTPUT" +#~ msgstr "ΕΞΟΔΟΣ" + +#~ msgid "Gain automation mode" +#~ msgstr "ΛειτουÏγία Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï Gain" + +#~ msgid "Gain automation type" +#~ msgstr "ΤÏπος Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï Gain" + +#~ msgid "trim" +#~ msgstr "ισοστάθμιση" + +#~ msgid "gain automation mode" +#~ msgstr "ΛειτουÏγία Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï gain" + +#~ msgid "gain automation state" +#~ msgstr "Κατάσταση Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï gain" + +#~ msgid "pan automation state" +#~ msgstr "Κατάσταση Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï pan" + +#~ msgid "REC" +#~ msgstr "REC" + +#~ msgid "OUT" +#~ msgstr "OUT" + +#~ msgid "aplay" +#~ msgstr "aplay" + +#~ msgid "awrite" +#~ msgstr "awrite" + +#~ msgid "no group" +#~ msgstr "καμία ομάδα" + #, fuzzy #~ msgid "normal" #~ msgstr "Κανονικό" @@ -6480,9 +6585,6 @@ msgstr "Κανάλι με αυτό το όνομα ήδη υπάÏχει" #~ msgid "AND" #~ msgstr "AND" -#~ msgid "OR" -#~ msgstr "OR" - #~ msgid "ardour: locate soundfiles" #~ msgstr "ardour: εÏÏεση soundfiles" @@ -6498,9 +6600,6 @@ msgstr "Κανάλι με αυτό το όνομα ήδη υπάÏχει" #~ msgid "Ardour: Search Results" #~ msgstr "Ardour: Αποτελέσματα Αναζητήσεως" -#~ msgid "Mix Groups" -#~ msgstr "Ανάμειξη ομάδων" - #~ msgid "Hide All AudioTrack MixerStrips" #~ msgstr "ΑπόκÏυψη όλων των ΔιαδÏόμωνΜίξεως των καναλιών" @@ -6513,9 +6612,6 @@ msgstr "Κανάλι με αυτό το όνομα ήδη υπάÏχει" #~ msgid "Name for new mix group" #~ msgstr "Όνομα για νέα ομάδα μίξεως" -#~ msgid "Session name:" -#~ msgstr "Όνομα συνεδÏίας:" - #~ msgid "Create" #~ msgstr "ΔημιουÏγία" @@ -6553,18 +6649,12 @@ msgstr "Κανάλι με αυτό το όνομα ήδη υπάÏχει" #~ "Αν επιθυμείτε να θέσετε διαφοÏετικό 'Ïυθμό'\n" #~ "παÏακαλώ βγείτε και επανεκκινήστε τον JACK" -#~ msgid "Session template" -#~ msgstr "ΠÏοσχέδιο συνεδÏίας" - #~ msgid "blank" #~ msgstr "κενό" #~ msgid "No template - create tracks/busses manually" #~ msgstr "ΧωÏίς Ï€Ïοσχέδιο - δημιουÏγία καναλιών/διαÏλων χειÏοκίνητα" -#~ msgid "No template" -#~ msgstr "ΧωÏίς Ï€Ïοσχέδιο" - #~ msgid "Slave to MTC" #~ msgstr "Slave στον MTC" @@ -6599,9 +6689,6 @@ msgstr "Κανάλι με αυτό το όνομα ήδη υπάÏχει" #~ msgid "Native Format" #~ msgstr "Εντόπιο Format" -#~ msgid "Use as click" -#~ msgstr "ΧÏήση όπως στο μετÏονόμο" - #~ msgid "--unknown--" #~ msgstr "--άγνωστο--" diff --git a/gtk2_ardour/po/es_ES.po b/gtk2_ardour/po/es_ES.po index 4c3e8b99bb..10468d6ab8 100644 --- a/gtk2_ardour/po/es_ES.po +++ b/gtk2_ardour/po/es_ES.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: ardour 0.688.4\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-04-25 17:46-0400\n" +"POT-Creation-Date: 2006-06-21 18:09-0400\n" "PO-Revision-Date: 2004-01-21 12:45+0100\n" "Last-Translator: Alex Krohn \n" "Language-Team: Spanish\n" @@ -15,143 +15,143 @@ msgstr "" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" -#: about.cc:119 +#: about.cc:120 msgid "Paul Davis" msgstr "" -#: about.cc:120 +#: about.cc:121 #, fuzzy msgid "Jesse Chappell" msgstr "resetear" -#: about.cc:121 +#: about.cc:122 msgid "Taybin Rutkin" msgstr "" -#: about.cc:122 +#: about.cc:123 msgid "Marcus Andersson" msgstr "" -#: about.cc:123 +#: about.cc:124 msgid "Jeremy Hall" msgstr "" -#: about.cc:124 +#: about.cc:125 msgid "Steve Harris" msgstr "" -#: about.cc:125 +#: about.cc:126 msgid "Tim Mayberry" msgstr "" -#: about.cc:126 +#: about.cc:127 msgid "Mark Stewart" msgstr "" -#: about.cc:127 +#: about.cc:128 msgid "Sam Chessman" msgstr "" -#: about.cc:128 +#: about.cc:129 msgid "Jack O'Quin" msgstr "" -#: about.cc:129 +#: about.cc:130 msgid "Matt Krai" msgstr "" -#: about.cc:130 +#: about.cc:131 msgid "Ben Bell" msgstr "" -#: about.cc:131 +#: about.cc:132 msgid "Gerard van Dongen" msgstr "" -#: about.cc:132 +#: about.cc:133 msgid "Thomas Charbonnel" msgstr "" -#: about.cc:133 +#: about.cc:134 msgid "Nick Mainsbridge" msgstr "" -#: about.cc:134 +#: about.cc:135 msgid "Colin Law" msgstr "" -#: about.cc:135 +#: about.cc:136 msgid "Sampo Savolainen" msgstr "" -#: about.cc:136 +#: about.cc:137 msgid "Joshua Leach" msgstr "" -#: about.cc:137 +#: about.cc:138 msgid "Rob Holland" msgstr "" -#: about.cc:138 +#: about.cc:139 msgid "Per Sigmond" msgstr "" -#: about.cc:139 +#: about.cc:140 msgid "Doug Mclain" msgstr "" -#: about.cc:140 +#: about.cc:141 msgid "Petter Sundlöf" msgstr "" -#: about.cc:145 +#: about.cc:146 msgid "" "French:\n" "\tAlain Fréhel \n" msgstr "" -#: about.cc:146 +#: about.cc:147 msgid "" "German:\n" "\tKarsten Petersen \n" msgstr "" -#: about.cc:147 +#: about.cc:148 msgid "" "Italian:\n" "\tFilippo Pappalardo \n" msgstr "" -#: about.cc:148 +#: about.cc:149 msgid "" "Portuguese:\n" "\tRui Nuno Capela \n" msgstr "" -#: about.cc:149 +#: about.cc:150 msgid "" "Brazilian Portuguese:\n" "\tAlexander da Franca Fernandes \n" "\tChris Ross \n" msgstr "" -#: about.cc:151 +#: about.cc:152 msgid "" "Spanish:\n" "\t Alex Krohn \n" msgstr "" -#: about.cc:152 +#: about.cc:153 msgid "" "Russian:\n" "\t Igor Blinov \n" msgstr "" -#: about.cc:180 +#: about.cc:181 msgid "Copyright (C) 1999-2005 Paul Davis\n" msgstr "" -#: about.cc:181 +#: about.cc:182 #, fuzzy msgid "" "Ardour comes with ABSOLUTELY NO WARRANTY\n" @@ -163,58 +163,58 @@ msgstr "" "bajo ciertas condiciones;lea el archivo COPYING(en ingl�)\n" "para m� detalles\n" -#: about.cc:187 +#: about.cc:188 msgid "" "%1\n" "(built with ardour/gtk %2.%3.%4 libardour: %5.%6.%7)" msgstr "" -#: actions.cc:260 +#: actions.cc:261 msgid "programmer error: %1 %2" msgstr "" -#: add_route_dialog.cc:61 +#: add_route_dialog.cc:62 msgid "ardour: add track/bus" msgstr "ardour: agregar Pistas/bus" #. path = "1" -#: add_route_dialog.cc:62 editor_route_list.cc:72 +#: add_route_dialog.cc:63 editor_route_list.cc:73 msgid "Tracks" msgstr "Pistas" #. path = "0" -#: add_route_dialog.cc:63 editor_route_list.cc:69 +#: add_route_dialog.cc:64 editor_route_list.cc:70 msgid "Busses" msgstr "Buses" -#: add_route_dialog.cc:95 plugin_ui.cc:832 +#: add_route_dialog.cc:96 plugin_ui.cc:833 msgid "Add" msgstr "Agregar" -#: add_route_dialog.cc:113 +#: add_route_dialog.cc:114 msgid "Name (template)" msgstr "Nombre (esquema)" -#: add_route_dialog.cc:119 +#: add_route_dialog.cc:120 #, fuzzy msgid "Channel Configuration" msgstr "Cancelar importacin" -#: add_route_dialog.cc:176 editor.cc:131 editor.cc:3660 time_axis_view.cc:551 +#: add_route_dialog.cc:177 editor.cc:134 editor.cc:3688 time_axis_view.cc:552 msgid "Normal" msgstr "Normal" -#: add_route_dialog.cc:178 +#: add_route_dialog.cc:179 #, fuzzy msgid "Tape" msgstr "Inicio" -#: add_route_dialog.cc:195 +#: add_route_dialog.cc:196 #, fuzzy msgid "Mono" msgstr "mono" -#: add_route_dialog.cc:197 +#: add_route_dialog.cc:198 #, fuzzy msgid "Stereo" msgstr "est�eo" @@ -292,27 +292,11 @@ msgstr "AUDITANDO" msgid "SOLO" msgstr "" -#: ardour_ui.cc:207 -msgid "" -"You cannot record-enable\n" -"track %1\n" -"because it has no input connections.\n" -"You would be wasting space recording silence." -msgstr "" - -#: ardour_ui.cc:236 -msgid "no vertical meter strip image found" -msgstr "" - -#: ardour_ui.cc:243 -msgid "no horizontal meter strip image found" -msgstr "" - -#: ardour_ui.cc:410 +#: ardour_ui.cc:375 msgid "quit" msgstr "salir" -#: ardour_ui.cc:419 +#: ardour_ui.cc:384 msgid "" "Ardour was unable to save your session.\n" "\n" @@ -321,33 +305,33 @@ msgid "" "\"Just quit\" option." msgstr "" -#: ardour_ui.cc:438 +#: ardour_ui.cc:403 msgid "ardour: save session?" msgstr "ardour: guardar sesin?" -#: ardour_ui.cc:445 +#: ardour_ui.cc:410 msgid "Don't %1" msgstr "No %1" -#: ardour_ui.cc:447 +#: ardour_ui.cc:412 msgid "Just %1" msgstr "Slo %1" -#: ardour_ui.cc:449 +#: ardour_ui.cc:414 msgid "Save and %1" msgstr "Guardar y %1" -#: ardour_ui.cc:461 +#: ardour_ui.cc:426 #, fuzzy msgid "session" msgstr "Sesin" -#: ardour_ui.cc:463 +#: ardour_ui.cc:428 #, fuzzy msgid "snapshot" msgstr "Capturar instant�ea de sesin" -#: ardour_ui.cc:465 +#: ardour_ui.cc:430 #, fuzzy msgid "" "The %1\"%2\"\n" @@ -366,82 +350,82 @@ msgstr "" "\n" "Qu�desea hacer?" -#: ardour_ui.cc:479 +#: ardour_ui.cc:444 msgid "Prompter" msgstr "" -#: ardour_ui.cc:538 +#: ardour_ui.cc:503 #, fuzzy, c-format msgid "disconnected" msgstr "Desconectar" -#: ardour_ui.cc:545 +#: ardour_ui.cc:510 #, fuzzy, c-format msgid "SR: %.1f kHz / %4.1f msecs" msgstr "SR: %.1f kHz" -#: ardour_ui.cc:549 +#: ardour_ui.cc:514 #, c-format msgid "SR: %u kHz / %4.1f msecs" msgstr "" -#: ardour_ui.cc:562 +#: ardour_ui.cc:527 #, fuzzy, c-format msgid "DSP Load: %.1f%%" msgstr "CPU usada: %.1f%%" -#: ardour_ui.cc:572 +#: ardour_ui.cc:537 #, fuzzy, c-format msgid "Buffers p:%%% c:%%%" msgstr "Buffers p:%5.0f%% c:%5.0f%%" -#: ardour_ui.cc:599 +#: ardour_ui.cc:564 msgid "space: 24hrs+" msgstr "disponible: 24hrs+" -#: ardour_ui.cc:629 +#: ardour_ui.cc:594 #, c-format msgid "space: %02dh:%02dm:%02ds" msgstr "disponible: %02dh:%02dm:%02ds" -#: ardour_ui.cc:668 +#: ardour_ui.cc:633 msgid "programming error: impossible control method" msgstr "" # -#: ardour_ui.cc:776 new_session_dialog.cc:89 +#: ardour_ui.cc:741 new_session_dialog.cc:294 #, fuzzy msgid "Recent Sessions" msgstr "Abrir sesin" # #. ardour sessions are folders -#: ardour_ui.cc:867 +#: ardour_ui.cc:834 msgid "open session" msgstr "Abrir sesin" -#: ardour_ui.cc:873 +#: ardour_ui.cc:840 #, fuzzy msgid "Ardour sessions" msgstr "ardour: guardar sesin?" -#: ardour_ui.cc:906 +#: ardour_ui.cc:873 msgid "Patience is a virtue.\n" msgstr "La paciencia es una virtud.\n" -#: ardour_ui.cc:915 +#: ardour_ui.cc:882 msgid "You cannot add a track without a session already loaded." msgstr "No puede agregar pistas hasta que haya creado o abierto una sesin." -#: ardour_ui.cc:922 +#: ardour_ui.cc:889 msgid "could not create new audio track" msgstr "no se pudo crear la nueva pista" -#: ardour_ui.cc:926 +#: ardour_ui.cc:893 msgid "could not create new audio bus" msgstr "no se pudo crear el nuevo bus" -#: ardour_ui.cc:945 +#: ardour_ui.cc:912 msgid "" "There are insufficient JACK ports available\n" "to create a new track or bus.\n" @@ -449,14 +433,14 @@ msgid "" "restart JACK with more ports." msgstr "" -#: ardour_ui.cc:1069 +#: ardour_ui.cc:1036 msgid "" "Please create 1 or more track\n" "before trying to record.\n" "Check the Session menu." msgstr "" -#: ardour_ui.cc:1298 +#: ardour_ui.cc:1265 #, fuzzy msgid "" "JACK has either been shutdown or it\n" @@ -470,57 +454,55 @@ msgstr "" "Usted puede guardar su sesin ahora\n" "sin perder los cambios hechos.Luego,reinicie a Ardour y a Jackd." -#: ardour_ui.cc:1315 +#: ardour_ui.cc:1282 msgid "Unable to create all required ports" msgstr "" -#: ardour_ui.cc:1323 +#: ardour_ui.cc:1290 #, fuzzy msgid "Unable to start the session running" msgstr "Ir al inicio de la sesin" -#: ardour_ui.cc:1459 +#: ardour_ui.cc:1426 msgid "No Stream" msgstr "Sin Flujo" -#: ardour_ui.cc:1486 ardour_ui.cc:1505 +#: ardour_ui.cc:1453 ardour_ui.cc:1472 msgid "none" msgstr "ninguno" -#: ardour_ui.cc:1495 ardour_ui.cc:1514 automation_time_axis.cc:183 -#: automation_time_axis.cc:212 automation_time_axis.cc:459 mixer_strip.cc:174 -#: mixer_strip.cc:186 mixer_strip.cc:881 plugin_ui.cc:391 plugin_ui.cc:634 +#: ardour_ui.cc:1462 ardour_ui.cc:1481 msgid "off" msgstr "off" -#: ardour_ui.cc:1538 +#: ardour_ui.cc:1505 #, fuzzy msgid "Name of New Snapshot" msgstr "Nombre a captura de sesin" -#: ardour_ui.cc:1684 +#: ardour_ui.cc:1651 msgid "Name for mix template:" msgstr "Nombre a esquema de mixer" -#: ardour_ui.cc:1685 +#: ardour_ui.cc:1652 msgid "-template" msgstr "-esquema" -#: ardour_ui.cc:1836 +#: ardour_ui.cc:1809 msgid "" "You do not have write access to this session.\n" "This prevents the session from being loaded." msgstr "" -#: ardour_ui.cc:1849 ardour_ui.cc:1904 +#: ardour_ui.cc:1822 ardour_ui.cc:1877 msgid "Session \"%1 (snapshot %2)\" did not load successfully" msgstr "No se puede cargar la sesin \"%1 (captura %2)\" " -#: ardour_ui.cc:1960 +#: ardour_ui.cc:1933 msgid "No audio files were ready for cleanup" msgstr "" -#: ardour_ui.cc:1964 +#: ardour_ui.cc:1937 msgid "" "If this seems suprising, \n" "check for any existing snapshots.\n" @@ -528,23 +510,23 @@ msgid "" "require some unused files to continue to exist." msgstr "" -#: ardour_ui.cc:1973 +#: ardour_ui.cc:1946 msgid "ardour: cleanup" msgstr "ardour: limpiar" -#: ardour_ui.cc:2009 ardour_ui.cc:2015 +#: ardour_ui.cc:1982 ardour_ui.cc:1988 msgid "files were" msgstr "" -#: ardour_ui.cc:2011 ardour_ui.cc:2017 +#: ardour_ui.cc:1984 ardour_ui.cc:1990 msgid "file was" msgstr "" -#: ardour_ui.cc:2058 +#: ardour_ui.cc:2031 msgid "Are you sure you want to cleanup?" msgstr "" -#: ardour_ui.cc:2063 +#: ardour_ui.cc:2036 msgid "" "Cleanup is a destructive operation.\n" "ALL undo/redo information will be lost if you cleanup.\n" @@ -552,26 +534,26 @@ msgid "" "location." msgstr "" -#: ardour_ui.cc:2069 +#: ardour_ui.cc:2042 #, fuzzy msgid "Clean Up" msgstr "Limpiar" -#: ardour_ui.cc:2072 +#: ardour_ui.cc:2045 #, fuzzy msgid "CleanupDialog" msgstr "Limpiar" -#: ardour_ui.cc:2073 +#: ardour_ui.cc:2046 #, fuzzy msgid "ardour_cleanup" msgstr "ardour: limpiar" -#: ardour_ui.cc:2092 +#: ardour_ui.cc:2065 msgid "cleaned files" msgstr "archivos limpios" -#: ardour_ui.cc:2093 +#: ardour_ui.cc:2066 #, fuzzy msgid "" "The following %1 %2 not in use and \n" @@ -586,12 +568,12 @@ msgstr "" "Cuando vuelva a vaciar la papelera\n" "se liberar�%2 megabytes de espacio en disco \n" -#: ardour_ui.cc:2118 +#: ardour_ui.cc:2091 #, fuzzy msgid "deleted file" msgstr "archivos eliminados" -#: ardour_ui.cc:2119 +#: ardour_ui.cc:2092 #, fuzzy msgid "" "The following %1 %2 deleted from\n" @@ -601,11 +583,11 @@ msgstr "" "Los siguientes %1 archivos fueron eliminados, liberando %2 megabytes de " "espacio" -#: ardour_ui.cc:2242 +#: ardour_ui.cc:2215 msgid "Recording was stopped because your system could not keep up." msgstr "Se detuvo la grabacin porque el sistema se sobrecarg" -#: ardour_ui.cc:2265 +#: ardour_ui.cc:2238 msgid "" "The disk system on your computer\n" "was not able to keep up with Ardour.\n" @@ -614,7 +596,7 @@ msgid "" "quickly enough to keep up with recording.\n" msgstr "" -#: ardour_ui.cc:2284 +#: ardour_ui.cc:2257 msgid "" "The disk system on your computer\n" "was not able to keep up with Ardour.\n" @@ -623,7 +605,7 @@ msgid "" "quickly enough to keep up with playback.\n" msgstr "" -#: ardour_ui.cc:2310 +#: ardour_ui.cc:2283 msgid "" "This session appears to have been in\n" "middle of recording when ardour or\n" @@ -634,372 +616,372 @@ msgid "" "what you would like to do.\n" msgstr "" -#: ardour_ui.cc:2320 +#: ardour_ui.cc:2293 msgid "Recover from crash" msgstr "" -#: ardour_ui.cc:2321 +#: ardour_ui.cc:2294 msgid "Ignore crash data" msgstr "" -#: ardour_ui.cc:2339 +#: ardour_ui.cc:2312 #, fuzzy msgid "Could not disconnect from JACK" msgstr "No se pudo conectar a JACK con el nombre \"%1\"" -#: ardour_ui.cc:2352 +#: ardour_ui.cc:2325 #, fuzzy msgid "Could not reconnect to JACK" msgstr "No se pudo conectar a JACK con el nombre \"%1\"" -#: ardour_ui2.cc:59 +#: ardour_ui2.cc:60 msgid "UI: cannot setup editor" msgstr "no se pudo iniciar el editor" -#: ardour_ui2.cc:64 +#: ardour_ui2.cc:65 msgid "UI: cannot setup mixer" msgstr "no se pudo iniciar el mixer" -#: ardour_ui2.cc:90 +#: ardour_ui2.cc:91 msgid "MMC + Local" msgstr "" -#: ardour_ui2.cc:91 +#: ardour_ui2.cc:92 msgid "MMC" msgstr "" -#: ardour_ui2.cc:92 +#: ardour_ui2.cc:93 msgid "Local" msgstr "" -#: ardour_ui2.cc:109 +#: ardour_ui2.cc:110 msgid "MMC ID" msgstr "" -#: ardour_ui2.cc:290 +#: ardour_ui2.cc:291 msgid "Play from playhead" msgstr "Reproduzir a partir del in�io" -#: ardour_ui2.cc:291 +#: ardour_ui2.cc:292 msgid "Stop playback" msgstr "Detener la reproduccion" -#: ardour_ui2.cc:292 +#: ardour_ui2.cc:293 #, fuzzy msgid "Play range/selection" msgstr "Reproducir seleccin" -#: ardour_ui2.cc:293 +#: ardour_ui2.cc:294 msgid "Go to start of session" msgstr "Ir al inicio de la sesin" -#: ardour_ui2.cc:294 +#: ardour_ui2.cc:295 msgid "Go to end of session" msgstr "Ir al final de la sesin" -#: ardour_ui2.cc:295 +#: ardour_ui2.cc:296 #, fuzzy msgid "Play loop range" msgstr "Reproducir el intervalo cont�uamente" -#: ardour_ui2.cc:296 +#: ardour_ui2.cc:297 msgid "Return to last playback start when stopped" msgstr "Al detenerse, volver a donde inici la reproduccin" -#: ardour_ui2.cc:297 +#: ardour_ui2.cc:298 msgid "Start playback after any locate" msgstr "" "Reproducir inmedi�amente despu� de relocalizar la barra de reproduccin" -#: ardour_ui2.cc:298 +#: ardour_ui2.cc:299 msgid "Be sensible about input monitoring" msgstr "Monitorizacin sensible de entradas" -#: ardour_ui2.cc:299 +#: ardour_ui2.cc:300 msgid "Start recording at auto-punch start" msgstr "Iniciar grabacin en el punto auto-punch start(inicio)" -#: ardour_ui2.cc:300 +#: ardour_ui2.cc:301 msgid "Stop recording at auto-punch end" msgstr "Detener grabacin en el punto auto-punch end(final)" -#: ardour_ui2.cc:301 +#: ardour_ui2.cc:302 msgid "Enable/Disable audio click" msgstr "Habilitar/desabilitar metrnomo" -#: ardour_ui2.cc:302 +#: ardour_ui2.cc:303 msgid "Positional sync source" msgstr "" -#: ardour_ui2.cc:303 +#: ardour_ui2.cc:304 msgid "Does Ardour control the time?" msgstr "" -#: ardour_ui2.cc:304 +#: ardour_ui2.cc:305 #, fuzzy msgid "Shuttle speed control" msgstr "Control de velocidad y sentido de reproduccin(pitch)" -#: ardour_ui2.cc:305 +#: ardour_ui2.cc:306 #, fuzzy, c-format msgid "Select semitones or %%-age for speed display" msgstr "Mostrar velocidad en semitonos o %-age" -#: ardour_ui2.cc:306 +#: ardour_ui2.cc:307 #, fuzzy msgid "Current transport speed" msgstr "Velocidad actual de transporte" -#: ardour_ui2.cc:329 +#: ardour_ui2.cc:330 msgid "Primary clock" msgstr "Reloj primario" -#: ardour_ui2.cc:330 +#: ardour_ui2.cc:331 msgid "secondary clock" msgstr "Reloj secundario" #. XXX: this should really be saved in instant.xml or something similar and restored from there #. Combo's are stupid - they steal space from the entry for the button -#: ardour_ui2.cc:387 ardour_ui2.cc:823 ardour_ui2.cc:836 ardour_ui2.cc:899 -#: ardour_ui2.cc:901 +#: ardour_ui2.cc:388 ardour_ui2.cc:833 ardour_ui2.cc:846 ardour_ui2.cc:909 +#: ardour_ui2.cc:911 #, fuzzy msgid "sprung" msgstr "Salto" -#: ardour_ui2.cc:388 ardour_ui2.cc:825 ardour_ui2.cc:847 +#: ardour_ui2.cc:389 ardour_ui2.cc:835 ardour_ui2.cc:857 #, fuzzy msgid "wheel" msgstr "Rueda" -#: ardour_ui2.cc:450 +#: ardour_ui2.cc:451 msgid "ardour: clock" msgstr "ardour: reloj" -#: ardour_ui2.cc:595 +#: ardour_ui2.cc:596 #, fuzzy msgid "Maximum speed" msgstr "velocidad" -#: ardour_ui2.cc:813 +#: ardour_ui2.cc:823 msgid "st" msgstr "" -#: ardour_ui2.cc:857 ardour_ui2.cc:880 ardour_ui2.cc:897 +#: ardour_ui2.cc:867 ardour_ui2.cc:890 ardour_ui2.cc:907 msgid "stopped" msgstr "detenido" -#: ardour_ui_dialogs.cc:152 playlist_selector.cc:69 +#: ardour_ui_dialogs.cc:153 playlist_selector.cc:70 #, fuzzy msgid "close" msgstr "Cerrar" -#: ardour_ui_dialogs.cc:359 ardour_ui_ed.cc:181 +#: ardour_ui_dialogs.cc:360 ardour_ui_ed.cc:184 #, fuzzy msgid "Sound File Browser" msgstr "Biblioteca de audio" #. menus + submenus that need action items -#: ardour_ui_ed.cc:69 +#: ardour_ui_ed.cc:72 msgid "Session" msgstr "Sesin" -#: ardour_ui_ed.cc:70 ardour_ui_ed.cc:127 editor.cc:1843 export_dialog.cc:350 +#: ardour_ui_ed.cc:73 ardour_ui_ed.cc:130 editor.cc:1836 export_dialog.cc:350 #: export_dialog.cc:1059 export_dialog.cc:1063 msgid "Export" msgstr "Exportar" -#: ardour_ui_ed.cc:71 +#: ardour_ui_ed.cc:74 msgid "Cleanup" msgstr "Limpiar" -#: ardour_ui_ed.cc:72 option_editor.cc:125 +#: ardour_ui_ed.cc:75 option_editor.cc:126 msgid "Sync" msgstr "Sincronizacin" -#: ardour_ui_ed.cc:73 ardour_ui_ed.cc:74 +#: ardour_ui_ed.cc:76 ardour_ui_ed.cc:77 #, fuzzy msgid "Options" msgstr "Opciones Editor" -#: ardour_ui_ed.cc:75 +#: ardour_ui_ed.cc:78 msgid "Help" msgstr "" -#: ardour_ui_ed.cc:76 +#: ardour_ui_ed.cc:79 msgid "KeyMouse Actions" msgstr "" -#: ardour_ui_ed.cc:77 +#: ardour_ui_ed.cc:80 #, fuzzy msgid "Audio File Format" msgstr "Cuadros de Audio" -#: ardour_ui_ed.cc:78 +#: ardour_ui_ed.cc:81 #, fuzzy msgid "Header" msgstr "Pre-Fader" -#: ardour_ui_ed.cc:79 +#: ardour_ui_ed.cc:82 msgid "Data" msgstr "" -#: ardour_ui_ed.cc:80 +#: ardour_ui_ed.cc:83 #, fuzzy msgid "Control Surfaces" msgstr "Control de Salidas" #. the real actions -#: ardour_ui_ed.cc:84 audio_time_axis.cc:1856 new_session_dialog.cc:342 +#: ardour_ui_ed.cc:87 audio_time_axis.cc:1854 new_session_dialog.cc:529 msgid "New" msgstr "Nuevo" -#: ardour_ui_ed.cc:86 new_session_dialog.cc:334 +#: ardour_ui_ed.cc:89 new_session_dialog.cc:517 msgid "Open" msgstr "Abrir" -#: ardour_ui_ed.cc:87 +#: ardour_ui_ed.cc:90 msgid "Recent" msgstr "Reciente" -#: ardour_ui_ed.cc:88 io_selector.cc:57 io_selector.cc:791 +#: ardour_ui_ed.cc:91 io_selector.cc:58 io_selector.cc:792 msgid "Close" msgstr "Cerrar" -#: ardour_ui_ed.cc:91 route_params_ui.cc:512 +#: ardour_ui_ed.cc:94 route_params_ui.cc:514 msgid "Add Track/Bus" msgstr "Agregar Pista/Bus" -#: ardour_ui_ed.cc:102 +#: ardour_ui_ed.cc:105 msgid "Connect" msgstr "Conectar" #. -#: ardour_ui_ed.cc:110 +#: ardour_ui_ed.cc:113 msgid "Snapshot" msgstr "Capturar instant�ea de sesin" -#: ardour_ui_ed.cc:113 +#: ardour_ui_ed.cc:116 msgid "Save Template..." msgstr "Guardar esquema" -#: ardour_ui_ed.cc:116 +#: ardour_ui_ed.cc:119 msgid "Export session to audiofile..." msgstr "Exportar sesin a archivo de audio" -#: ardour_ui_ed.cc:119 +#: ardour_ui_ed.cc:122 #, fuzzy msgid "Export selection to audiofile..." msgstr "Exportar sesin a archivo de audio" -#: ardour_ui_ed.cc:123 +#: ardour_ui_ed.cc:126 #, fuzzy msgid "Export range markers to audiofile..." msgstr "Exportar sesin a archivo de audio" -#: ardour_ui_ed.cc:130 +#: ardour_ui_ed.cc:133 msgid "Cleanup unused sources" msgstr "Arrojar archivos no usados a papelera" -#: ardour_ui_ed.cc:132 +#: ardour_ui_ed.cc:135 msgid "Flush wastebasket" msgstr "Vaciar papelera" -#: ardour_ui_ed.cc:138 ardour_ui_options.cc:381 ardour_ui_options.cc:390 -#: ardour_ui_options.cc:462 +#: ardour_ui_ed.cc:141 ardour_ui_options.cc:408 ardour_ui_options.cc:417 +#: ardour_ui_options.cc:489 msgid "JACK" msgstr "JACK" -#: ardour_ui_ed.cc:139 +#: ardour_ui_ed.cc:142 msgid "Latency" msgstr "" -#: ardour_ui_ed.cc:141 +#: ardour_ui_ed.cc:144 #, fuzzy msgid "Reconnect" msgstr "Conectar" -#: ardour_ui_ed.cc:144 mixer_strip.cc:514 mixer_strip.cc:574 +#: ardour_ui_ed.cc:147 mixer_strip.cc:497 mixer_strip.cc:565 msgid "Disconnect" msgstr "Desconectar" -#: ardour_ui_ed.cc:171 +#: ardour_ui_ed.cc:174 msgid "Windows" msgstr "Ventanas" -#: ardour_ui_ed.cc:172 +#: ardour_ui_ed.cc:175 msgid "start prefix" msgstr "" -#: ardour_ui_ed.cc:173 +#: ardour_ui_ed.cc:176 msgid "Quit" msgstr "Salir" #. windows visibility actions -#: ardour_ui_ed.cc:177 +#: ardour_ui_ed.cc:180 msgid "Maximise Editor Space" msgstr "" -#: ardour_ui_ed.cc:179 +#: ardour_ui_ed.cc:182 #, fuzzy msgid "Show Editor" msgstr "Editor" -#: ardour_ui_ed.cc:180 +#: ardour_ui_ed.cc:183 #, fuzzy msgid "Show Mixer" msgstr "Mixer" -#: ardour_ui_ed.cc:182 +#: ardour_ui_ed.cc:185 msgid "Options Editor" msgstr "Opciones Editor" -#: ardour_ui_ed.cc:183 +#: ardour_ui_ed.cc:186 #, fuzzy msgid "Track/Bus Inspector" msgstr "Pistas/Buses" -#: ardour_ui_ed.cc:185 +#: ardour_ui_ed.cc:188 msgid "Connections" msgstr "Conecciones" -#: ardour_ui_ed.cc:187 +#: ardour_ui_ed.cc:190 msgid "Locations" msgstr "Localizaciones" -#: ardour_ui_ed.cc:189 +#: ardour_ui_ed.cc:192 msgid "Big Clock" msgstr "Reloj Grande" -#: ardour_ui_ed.cc:191 +#: ardour_ui_ed.cc:194 msgid "About" msgstr "Acerca de" -#: ardour_ui_ed.cc:192 +#: ardour_ui_ed.cc:195 #, fuzzy msgid "Colors" msgstr "Color" -#: ardour_ui_ed.cc:194 +#: ardour_ui_ed.cc:197 #, fuzzy msgid "Add Audio Track" msgstr "Agregar Pista/Bus" -#: ardour_ui_ed.cc:196 +#: ardour_ui_ed.cc:199 #, fuzzy msgid "Add Audio Bus" msgstr "Ocultar todos los Buses" -#: ardour_ui_ed.cc:198 +#: ardour_ui_ed.cc:201 msgid "Save" msgstr "Guardar" -#: ardour_ui_ed.cc:200 editor_actions.cc:254 +#: ardour_ui_ed.cc:203 editor_actions.cc:255 #, fuzzy msgid "Remove Last Capture" msgstr "Quitar ltima captura" #. do-nothing action for the "transport" menu bar item -#: ardour_ui_ed.cc:207 +#: ardour_ui_ed.cc:210 #, fuzzy msgid "Transport" msgstr "Traductores" @@ -1007,73 +989,73 @@ msgstr "Traductores" #. these two are not used by key bindings, instead use ToggleRoll for that. these two do show up in #. menus and via button proxies. #. -#: ardour_ui_ed.cc:213 sfdb_ui.cc:57 +#: ardour_ui_ed.cc:216 sfdb_ui.cc:57 msgid "Stop" msgstr "Detener" -#: ardour_ui_ed.cc:216 +#: ardour_ui_ed.cc:219 msgid "Roll" msgstr "" -#: ardour_ui_ed.cc:220 +#: ardour_ui_ed.cc:223 #, fuzzy msgid "Start/Stop" msgstr "Inicio:" -#: ardour_ui_ed.cc:223 +#: ardour_ui_ed.cc:226 msgid "Stop + Forget Capture" msgstr "" -#: ardour_ui_ed.cc:226 +#: ardour_ui_ed.cc:229 #, fuzzy msgid "Play Loop Range" msgstr "Reproducir el intervalo cont�uamente" -#: ardour_ui_ed.cc:229 +#: ardour_ui_ed.cc:232 #, fuzzy msgid "Play Selection" msgstr "Reproducir regin selecionada" -#: ardour_ui_ed.cc:233 +#: ardour_ui_ed.cc:236 #, fuzzy msgid "Enable Record" msgstr "Grabar" -#: ardour_ui_ed.cc:236 +#: ardour_ui_ed.cc:239 #, fuzzy msgid "Rewind" msgstr "Regin" -#: ardour_ui_ed.cc:239 +#: ardour_ui_ed.cc:242 msgid "Rewind (Slow)" msgstr "" -#: ardour_ui_ed.cc:242 +#: ardour_ui_ed.cc:245 msgid "Rewind (Fast)" msgstr "" -#: ardour_ui_ed.cc:245 +#: ardour_ui_ed.cc:248 msgid "Forward" msgstr "" -#: ardour_ui_ed.cc:248 +#: ardour_ui_ed.cc:251 msgid "Forward (Slow)" msgstr "" -#: ardour_ui_ed.cc:251 +#: ardour_ui_ed.cc:254 msgid "Forward (Fast)" msgstr "" -#: ardour_ui_ed.cc:254 +#: ardour_ui_ed.cc:257 msgid "Goto Zero" msgstr "" -#: ardour_ui_ed.cc:257 +#: ardour_ui_ed.cc:260 #, fuzzy msgid "Goto Start" msgstr "Inicio:" -#: ardour_ui_ed.cc:260 +#: ardour_ui_ed.cc:263 msgid "Goto End" msgstr "" @@ -1081,25 +1063,25 @@ msgstr "" #. that proxies for these action to be more compact. It would be nice to find a way to override the action #. name appearance on the buttons. #. -#: ardour_ui_ed.cc:269 +#: ardour_ui_ed.cc:272 #, fuzzy msgid "" "Punch\n" "in" msgstr "Insercin" -#: ardour_ui_ed.cc:272 +#: ardour_ui_ed.cc:275 #, fuzzy msgid "" "Punch\n" "out" msgstr "Insercin" -#: ardour_ui_ed.cc:275 option_editor.cc:128 +#: ardour_ui_ed.cc:278 option_editor.cc:129 msgid "Click" msgstr "Metrnomo" -#: ardour_ui_ed.cc:278 +#: ardour_ui_ed.cc:281 #, fuzzy msgid "" "Auto\n" @@ -1108,7 +1090,7 @@ msgstr "" "auto\n" "monitoreo" -#: ardour_ui_ed.cc:281 +#: ardour_ui_ed.cc:284 #, fuzzy msgid "" "Auto\n" @@ -1117,7 +1099,7 @@ msgstr "" "reproduccn\n" "autom�ica" -#: ardour_ui_ed.cc:284 +#: ardour_ui_ed.cc:287 #, fuzzy msgid "" "Auto\n" @@ -1126,285 +1108,285 @@ msgstr "" "retorno\n" "autom�ico" -#: ardour_ui_ed.cc:288 +#: ardour_ui_ed.cc:291 #, fuzzy msgid "" "Time\n" "master" msgstr "M�ter de tiempo JACK" -#: ardour_ui_ed.cc:291 +#: ardour_ui_ed.cc:294 msgid "Toggle Record Enable Track1" msgstr "" -#: ardour_ui_ed.cc:293 +#: ardour_ui_ed.cc:296 msgid "Toggle Record Enable Track2" msgstr "" -#: ardour_ui_ed.cc:295 +#: ardour_ui_ed.cc:298 msgid "Toggle Record Enable Track3" msgstr "" -#: ardour_ui_ed.cc:297 +#: ardour_ui_ed.cc:300 msgid "Toggle Record Enable Track4" msgstr "" -#: ardour_ui_ed.cc:299 +#: ardour_ui_ed.cc:302 msgid "Toggle Record Enable Track5" msgstr "" -#: ardour_ui_ed.cc:301 +#: ardour_ui_ed.cc:304 msgid "Toggle Record Enable Track6" msgstr "" -#: ardour_ui_ed.cc:303 +#: ardour_ui_ed.cc:306 msgid "Toggle Record Enable Track7" msgstr "" -#: ardour_ui_ed.cc:305 +#: ardour_ui_ed.cc:308 msgid "Toggle Record Enable Track8" msgstr "" -#: ardour_ui_ed.cc:307 +#: ardour_ui_ed.cc:310 msgid "Toggle Record Enable Track9" msgstr "" -#: ardour_ui_ed.cc:309 +#: ardour_ui_ed.cc:312 msgid "Toggle Record Enable Track10" msgstr "" -#: ardour_ui_ed.cc:311 +#: ardour_ui_ed.cc:314 msgid "Toggle Record Enable Track11" msgstr "" -#: ardour_ui_ed.cc:313 +#: ardour_ui_ed.cc:316 msgid "Toggle Record Enable Track12" msgstr "" -#: ardour_ui_ed.cc:315 +#: ardour_ui_ed.cc:318 msgid "Toggle Record Enable Track13" msgstr "" -#: ardour_ui_ed.cc:317 +#: ardour_ui_ed.cc:320 msgid "Toggle Record Enable Track14" msgstr "" -#: ardour_ui_ed.cc:319 +#: ardour_ui_ed.cc:322 msgid "Toggle Record Enable Track15" msgstr "" -#: ardour_ui_ed.cc:321 +#: ardour_ui_ed.cc:324 msgid "Toggle Record Enable Track16" msgstr "" -#: ardour_ui_ed.cc:323 +#: ardour_ui_ed.cc:326 msgid "Toggle Record Enable Track17" msgstr "" -#: ardour_ui_ed.cc:325 +#: ardour_ui_ed.cc:328 msgid "Toggle Record Enable Track18" msgstr "" -#: ardour_ui_ed.cc:327 +#: ardour_ui_ed.cc:330 msgid "Toggle Record Enable Track19" msgstr "" -#: ardour_ui_ed.cc:329 +#: ardour_ui_ed.cc:332 msgid "Toggle Record Enable Track20" msgstr "" -#: ardour_ui_ed.cc:331 +#: ardour_ui_ed.cc:334 msgid "Toggle Record Enable Track21" msgstr "" -#: ardour_ui_ed.cc:333 +#: ardour_ui_ed.cc:336 msgid "Toggle Record Enable Track22" msgstr "" -#: ardour_ui_ed.cc:335 +#: ardour_ui_ed.cc:338 msgid "Toggle Record Enable Track23" msgstr "" -#: ardour_ui_ed.cc:337 +#: ardour_ui_ed.cc:340 msgid "Toggle Record Enable Track24" msgstr "" -#: ardour_ui_ed.cc:339 +#: ardour_ui_ed.cc:342 msgid "Toggle Record Enable Track25" msgstr "" -#: ardour_ui_ed.cc:341 +#: ardour_ui_ed.cc:344 msgid "Toggle Record Enable Track26" msgstr "" -#: ardour_ui_ed.cc:343 +#: ardour_ui_ed.cc:346 msgid "Toggle Record Enable Track27" msgstr "" -#: ardour_ui_ed.cc:345 +#: ardour_ui_ed.cc:348 msgid "Toggle Record Enable Track28" msgstr "" -#: ardour_ui_ed.cc:347 +#: ardour_ui_ed.cc:350 msgid "Toggle Record Enable Track29" msgstr "" -#: ardour_ui_ed.cc:349 +#: ardour_ui_ed.cc:352 msgid "Toggle Record Enable Track30" msgstr "" -#: ardour_ui_ed.cc:351 +#: ardour_ui_ed.cc:354 msgid "Toggle Record Enable Track31" msgstr "" -#: ardour_ui_ed.cc:353 +#: ardour_ui_ed.cc:356 msgid "Toggle Record Enable Track32" msgstr "" -#: ardour_ui_ed.cc:358 +#: ardour_ui_ed.cc:361 #, fuzzy msgid "Percentage" msgstr "Porcentage" -#: ardour_ui_ed.cc:359 +#: ardour_ui_ed.cc:362 #, fuzzy msgid "Semitones" msgstr "Semitonos" -#: ardour_ui_ed.cc:363 +#: ardour_ui_ed.cc:366 msgid "Send MTC" msgstr "Enviar MTC" -#: ardour_ui_ed.cc:365 +#: ardour_ui_ed.cc:368 msgid "Send MMC" msgstr "Enviar MMC" -#: ardour_ui_ed.cc:367 +#: ardour_ui_ed.cc:370 #, fuzzy msgid "Use MMC" msgstr "Enviar MMC" -#: ardour_ui_ed.cc:369 +#: ardour_ui_ed.cc:372 msgid "Send MIDI feedback" msgstr "" -#: ardour_ui_ed.cc:371 +#: ardour_ui_ed.cc:374 #, fuzzy msgid "Use MIDI control" msgstr "Puerto MMC" -#: ardour_ui_ed.cc:374 +#: ardour_ui_ed.cc:377 #, fuzzy -msgid "Connect newtrack inputs to hardware" +msgid "Connect new track inputs to hardware" msgstr "Conectar nuevas pistas autom�icamente" -#: ardour_ui_ed.cc:392 +#: ardour_ui_ed.cc:396 #, fuzzy msgid "Connect new track outputs to hardware" msgstr "Conectar nuevas pistas autom�icamente" -#: ardour_ui_ed.cc:394 +#: ardour_ui_ed.cc:398 #, fuzzy msgid "Connect new track outputs to master" msgstr "conectar autom�icamente salidas de pistas a salidas Master" -#: ardour_ui_ed.cc:396 +#: ardour_ui_ed.cc:400 #, fuzzy msgid "Manually connect new track outputs" msgstr "conectar pistas manualmente" -#: ardour_ui_ed.cc:401 +#: ardour_ui_ed.cc:405 #, fuzzy msgid "Hardware monitoring" msgstr "Monitorizacin por Hardware" -#: ardour_ui_ed.cc:402 +#: ardour_ui_ed.cc:406 #, fuzzy msgid "Software monitoring" msgstr "Monitorizacin por Software" -#: ardour_ui_ed.cc:403 +#: ardour_ui_ed.cc:407 #, fuzzy msgid "External monitoring" msgstr "Monitorizacin por Hardware" #. Configuration object options (i.e. not session specific) -#: ardour_ui_ed.cc:407 +#: ardour_ui_ed.cc:411 msgid "Stop plugins with transport" msgstr "No procesar plugins durante transporte" -#: ardour_ui_ed.cc:408 +#: ardour_ui_ed.cc:412 #, fuzzy msgid "Verify remove last capture" msgstr "Quitar ltima captura" -#: ardour_ui_ed.cc:409 +#: ardour_ui_ed.cc:413 msgid "Stop recording on xrun" msgstr "Detener grabacin al detectar un XRUN" -#: ardour_ui_ed.cc:410 +#: ardour_ui_ed.cc:414 #, fuzzy msgid "Stop transport at session end" msgstr "Detener el transporte al llegar al final de la sesin" -#: ardour_ui_ed.cc:411 +#: ardour_ui_ed.cc:415 msgid "-12dB gain reduce ffwd/rewind" msgstr "" -#: ardour_ui_ed.cc:412 +#: ardour_ui_ed.cc:416 msgid "Rec-enable stays engaged at stop" msgstr "" #. session options -#: ardour_ui_ed.cc:416 +#: ardour_ui_ed.cc:420 #, fuzzy msgid "Do not run plugins while recording" msgstr "Procesar plugins durante la grabacin" -#: ardour_ui_ed.cc:419 +#: ardour_ui_ed.cc:423 msgid "Latched solo" msgstr "" -#: ardour_ui_ed.cc:424 +#: ardour_ui_ed.cc:428 #, fuzzy msgid "Solo in-place" msgstr "Solo" -#: ardour_ui_ed.cc:426 +#: ardour_ui_ed.cc:430 msgid "Solo via bus" msgstr "" -#: ardour_ui_ed.cc:429 +#: ardour_ui_ed.cc:433 #, fuzzy msgid "Automatically create crossfades" msgstr "Crosfade autom�ico si dos regiones se superponen" -#: ardour_ui_ed.cc:431 +#: ardour_ui_ed.cc:435 msgid "Unmute new full crossfades" msgstr "" -#: ardour_ui_options.cc:379 ardour_ui_options.cc:389 ardour_ui_options.cc:456 +#: ardour_ui_options.cc:406 ardour_ui_options.cc:416 ardour_ui_options.cc:483 #, fuzzy msgid "Internal" msgstr "interno" -#: ardour_ui_options.cc:380 ardour_ui_options.cc:459 +#: ardour_ui_options.cc:407 ardour_ui_options.cc:486 msgid "MTC" msgstr "" -#: audio_clock.cc:1719 editor.cc:185 +#: audio_clock.cc:1742 editor.cc:188 msgid "SMPTE" msgstr "" -#: audio_clock.cc:1720 editor.cc:184 editor_rulers.cc:359 +#: audio_clock.cc:1743 editor.cc:187 editor_rulers.cc:360 msgid "Bars:Beats" msgstr "Compaces:Pulsos" -#: audio_clock.cc:1721 +#: audio_clock.cc:1744 msgid "Minutes:Seconds" msgstr "Minutos:Segundos" -#: audio_clock.cc:1722 +#: audio_clock.cc:1745 msgid "Audio Frames" msgstr "Cuadros de Audio" @@ -1412,297 +1394,315 @@ msgstr "Cuadros de Audio" #. Slowest = 6.6dB/sec falloff at update rate of 40ms #. Slow = 6.8dB/sec falloff at update rate of 40ms #. -#: audio_clock.cc:1723 editor_actions.cc:374 editor_actions.cc:382 +#: audio_clock.cc:1746 editor_actions.cc:375 editor_actions.cc:383 +#: gain_meter.cc:172 panner_ui.cc:89 plugin_ui.cc:392 plugin_ui.cc:635 msgid "Off" msgstr "Deshabilitar" -#: audio_clock.cc:1725 +#: audio_clock.cc:1748 msgid "Mode" msgstr "Modo" -#: audio_time_axis.cc:90 mixer_strip.cc:458 +#: audio_time_axis.cc:91 msgid "m" msgstr "" -#: audio_time_axis.cc:90 mixer_strip.cc:459 +#: audio_time_axis.cc:91 msgid "s" msgstr "" -#: audio_time_axis.cc:90 +#: audio_time_axis.cc:91 msgid "r" msgstr "" -#: audio_time_axis.cc:94 +#: audio_time_axis.cc:95 msgid "g" msgstr "" #. group -#: audio_time_axis.cc:95 +#: audio_time_axis.cc:96 msgid "p" msgstr "" -#: audio_time_axis.cc:96 automation_time_axis.cc:31 visual_time_axis.cc:73 +#: audio_time_axis.cc:97 automation_time_axis.cc:32 visual_time_axis.cc:74 msgid "h" msgstr "" #. height -#: audio_time_axis.cc:97 +#: audio_time_axis.cc:98 msgid "a" msgstr "" -#: audio_time_axis.cc:98 visual_time_axis.cc:72 +#: audio_time_axis.cc:99 visual_time_axis.cc:73 msgid "v" msgstr "" -#: audio_time_axis.cc:173 +#: audio_time_axis.cc:168 mixer_strip.cc:86 msgid "Record" msgstr "Grabar" -#: audio_time_axis.cc:174 editor_actions.cc:36 +#: audio_time_axis.cc:169 editor_actions.cc:37 mixer_strip.cc:86 msgid "Solo" msgstr "Solo" -#: audio_time_axis.cc:175 editor.cc:1767 editor.cc:1866 panner_ui.cc:385 +#: audio_time_axis.cc:170 editor.cc:1760 editor.cc:1859 mixer_strip.cc:86 +#: panner_ui.cc:427 msgid "Mute" msgstr "" -#: audio_time_axis.cc:176 +#: audio_time_axis.cc:171 msgid "Edit Group" msgstr "Editar Grupo" -#: audio_time_axis.cc:177 visual_time_axis.cc:91 +#: audio_time_axis.cc:172 visual_time_axis.cc:92 msgid "Display Height" msgstr "Tamao de pista" -#: audio_time_axis.cc:178 +#: audio_time_axis.cc:173 msgid "Playlist" msgstr "Lista de reproduccin" -#: audio_time_axis.cc:179 audio_time_axis.cc:743 +#: audio_time_axis.cc:174 audio_time_axis.cc:741 msgid "Automation" msgstr "Automatizacin" -#: audio_time_axis.cc:180 visual_time_axis.cc:92 +#: audio_time_axis.cc:175 visual_time_axis.cc:93 msgid "Visual options" msgstr "Opciones visuales" -#: audio_time_axis.cc:181 visual_time_axis.cc:93 +#: audio_time_axis.cc:176 visual_time_axis.cc:94 msgid "Hide this track" msgstr "Ocultar esta pista" -#: audio_time_axis.cc:337 +#: audio_time_axis.cc:333 mixer_strip.cc:927 msgid "No group" msgstr "Sin grupo" -#: audio_time_axis.cc:704 automation_time_axis.cc:448 -#: imageframe_time_axis.cc:256 marker_time_axis.cc:210 +#: audio_time_axis.cc:702 automation_time_axis.cc:450 +#: imageframe_time_axis.cc:255 marker_time_axis.cc:211 msgid "Height" msgstr "Altura" -#: audio_time_axis.cc:705 color_manager.cc:40 imageframe_time_axis.cc:257 -#: marker_time_axis.cc:211 +#: audio_time_axis.cc:703 color_manager.cc:41 imageframe_time_axis.cc:256 +#: marker_time_axis.cc:212 msgid "Color" msgstr "Color" -#: audio_time_axis.cc:709 +#: audio_time_axis.cc:707 msgid "Hide all crossfades" msgstr "" -#: audio_time_axis.cc:710 +#: audio_time_axis.cc:708 msgid "Show all crossfades" msgstr "" -#: audio_time_axis.cc:714 mixer_strip.cc:1236 +#: audio_time_axis.cc:712 mixer_strip.cc:1011 #, fuzzy msgid "Remote Control ID" msgstr "Remover punto de sincron�" -#: audio_time_axis.cc:720 +#: audio_time_axis.cc:718 #, fuzzy -msgid "show all automation" +msgid "Show all automation" msgstr "Mostrar toda automatizacin" -#: audio_time_axis.cc:723 +#: audio_time_axis.cc:721 #, fuzzy -msgid "show existing automation" +msgid "Show existing automation" msgstr "Mostrar toda automatizacin" -#: audio_time_axis.cc:726 +#: audio_time_axis.cc:724 #, fuzzy -msgid "hide all automation" +msgid "Hide all automation" msgstr "ocultar toda automatizacin" -#: audio_time_axis.cc:731 audio_time_axis.cc:1169 editor.cc:215 -msgid "gain" -msgstr "volumen" +#: audio_time_axis.cc:729 +#, fuzzy +msgid "Fader" +msgstr "Fades" -#: audio_time_axis.cc:736 audio_time_axis.cc:1209 -msgid "pan" +#: audio_time_axis.cc:734 +#, fuzzy +msgid "Pan" msgstr "balance" -#: audio_time_axis.cc:741 +#: audio_time_axis.cc:739 msgid "Plugins" msgstr "" -#: audio_time_axis.cc:749 +#: audio_time_axis.cc:747 msgid "Show waveforms" msgstr "Mostrar onda de audio" -#: audio_time_axis.cc:757 +#: audio_time_axis.cc:755 msgid "Traditional" msgstr "Tradicional" -#: audio_time_axis.cc:760 +#: audio_time_axis.cc:758 msgid "Rectified" msgstr "Corregido" -#: audio_time_axis.cc:763 +#: audio_time_axis.cc:761 msgid "Waveform" msgstr "Onda de audio" -#: audio_time_axis.cc:773 +#: audio_time_axis.cc:771 #, fuzzy -msgid "align with existing material" +msgid "Align with existing material" msgstr "Material existente" -#: audio_time_axis.cc:778 +#: audio_time_axis.cc:776 #, fuzzy -msgid "align with capture time" +msgid "Align with capture time" msgstr "Tiempo de captura" -#: audio_time_axis.cc:784 +#: audio_time_axis.cc:782 #, fuzzy msgid "Alignment" msgstr "Alinear" -#: audio_time_axis.cc:790 editor.cc:523 editor_actions.cc:59 -#: mixer_strip.cc:1225 +#: audio_time_axis.cc:788 editor.cc:527 editor_actions.cc:60 +#: mixer_strip.cc:1000 mixer_ui.cc:111 msgid "Active" msgstr "Activar" -#: audio_time_axis.cc:795 editor.cc:1929 editor_actions.cc:319 -#: editor_markers.cc:507 imageframe_time_axis.cc:260 location_ui.cc:56 -#: marker_time_axis.cc:214 mixer_strip.cc:1239 +#: audio_time_axis.cc:793 editor.cc:1922 editor_actions.cc:320 +#: editor_markers.cc:508 imageframe_time_axis.cc:259 location_ui.cc:57 +#: marker_time_axis.cc:215 mixer_strip.cc:1014 msgid "Remove" msgstr "Quitar" -#: audio_time_axis.cc:835 +#: audio_time_axis.cc:833 #, fuzzy msgid "Name for playlist" msgstr "Nombre a captura de sesin" -#: audio_time_axis.cc:837 audio_time_axis.cc:1853 editor_markers.cc:826 -#: editor_mouse.cc:4609 imageframe_time_axis.cc:249 marker_time_axis.cc:207 -#: meter_bridge_strip.cc:223 mixer_strip.cc:1223 redirect_box.cc:749 -#: redirect_box.cc:1063 route_ui.cc:732 visual_time_axis.cc:325 +#: audio_time_axis.cc:835 audio_time_axis.cc:1851 editor_markers.cc:827 +#: editor_mouse.cc:4673 imageframe_time_axis.cc:248 marker_time_axis.cc:208 +#: meter_bridge_strip.cc:224 mixer_strip.cc:998 redirect_box.cc:751 +#: redirect_box.cc:1065 route_ui.cc:739 visual_time_axis.cc:326 msgid "Rename" msgstr "Renombrar" -#: audio_time_axis.cc:870 audio_time_axis.cc:910 +#: audio_time_axis.cc:868 audio_time_axis.cc:908 #, fuzzy msgid "Name for Playlist" msgstr "Nombre a captura de sesin" -#: audio_time_axis.cc:1128 visual_time_axis.cc:382 +#: audio_time_axis.cc:1126 visual_time_axis.cc:383 msgid "a track already exists with that name" msgstr "ya existe una pista con este nombre" -#: audio_time_axis.cc:1412 editor.cc:1490 selection.cc:622 +#: audio_time_axis.cc:1167 editor.cc:218 +msgid "gain" +msgstr "volumen" + +#: audio_time_axis.cc:1207 +msgid "pan" +msgstr "balance" + +#: audio_time_axis.cc:1410 editor.cc:1483 selection.cc:634 msgid "programming error: " msgstr "" -#: audio_time_axis.cc:1850 +#: audio_time_axis.cc:1848 msgid "Current: %1" msgstr "Actual: %1" -#: audio_time_axis.cc:1857 +#: audio_time_axis.cc:1855 msgid "New Copy" msgstr "Nueva Copia" -#: audio_time_axis.cc:1859 +#: audio_time_axis.cc:1857 msgid "Clear Current" msgstr "Borrar actual" -#: audio_time_axis.cc:1861 editor.cc:2031 editor.cc:2107 +#: audio_time_axis.cc:1859 editor.cc:2024 editor.cc:2100 msgid "Select" msgstr "Seleccionar" -#: automation_line.cc:883 +#: automation_line.cc:884 #, fuzzy msgid "automation event move" msgstr "mover evento de automatizacin" -#: automation_line.cc:885 +#: automation_line.cc:886 #, fuzzy msgid "automation range drag" msgstr "desplazar intervalo de automatizacin" -#: automation_line.cc:1014 region_gain_line.cc:61 +#: automation_line.cc:1015 region_gain_line.cc:62 #, fuzzy msgid "remove control point" msgstr "Remover punto de sincron�" -#: automation_time_axis.cc:32 editor_ops.cc:2813 +#: automation_time_axis.cc:33 editor_ops.cc:2885 msgid "clear" msgstr "borrar" -#: automation_time_axis.cc:74 +#: automation_time_axis.cc:75 msgid "track height" msgstr "" -#: automation_time_axis.cc:75 +#: automation_time_axis.cc:76 #, fuzzy msgid "automation state" msgstr "estado de automatizacin de balance" -#: automation_time_axis.cc:76 +#: automation_time_axis.cc:77 #, fuzzy msgid "clear track" msgstr "borrar intervalos" -#: automation_time_axis.cc:77 +#: automation_time_axis.cc:78 #, fuzzy msgid "hide track" msgstr "Ocultar esta pista" -#: automation_time_axis.cc:185 automation_time_axis.cc:223 -#: automation_time_axis.cc:463 mixer_strip.cc:176 mixer_strip.cc:188 -#: plugin_ui.cc:394 plugin_ui.cc:636 region_editor.cc:53 -msgid "play" -msgstr "reproducir" +#: automation_time_axis.cc:184 automation_time_axis.cc:213 +#: automation_time_axis.cc:461 +msgid "Manual" +msgstr "" -#: automation_time_axis.cc:187 automation_time_axis.cc:234 -#: automation_time_axis.cc:467 mixer_strip.cc:178 mixer_strip.cc:190 -#: plugin_ui.cc:397 plugin_ui.cc:638 -msgid "write" +#: automation_time_axis.cc:186 automation_time_axis.cc:224 +#: automation_time_axis.cc:465 editor.cc:2001 editor.cc:2082 gain_meter.cc:174 +#: panner_ui.cc:91 plugin_ui.cc:395 plugin_ui.cc:637 sfdb_ui.cc:56 +msgid "Play" +msgstr "Reproducir" + +#: automation_time_axis.cc:188 automation_time_axis.cc:235 +#: automation_time_axis.cc:469 gain_meter.cc:176 panner_ui.cc:93 +#: plugin_ui.cc:398 plugin_ui.cc:639 +#, fuzzy +msgid "Write" msgstr "escritura" -#: automation_time_axis.cc:189 automation_time_axis.cc:245 -#: automation_time_axis.cc:471 mixer_strip.cc:180 mixer_strip.cc:192 -#: mixer_strip.cc:887 plugin_ui.cc:400 plugin_ui.cc:640 +#: automation_time_axis.cc:190 automation_time_axis.cc:246 +#: automation_time_axis.cc:473 gain_meter.cc:178 panner_ui.cc:95 +#: plugin_ui.cc:401 plugin_ui.cc:641 #, fuzzy -msgid "touch" +msgid "Touch" msgstr "tocar" -#: automation_time_axis.cc:256 option_editor.cc:182 option_editor.cc:188 -#: plugin_ui.cc:403 +#: automation_time_axis.cc:257 option_editor.cc:183 option_editor.cc:189 +#: plugin_ui.cc:404 msgid "???" msgstr "" -#: automation_time_axis.cc:270 +#: automation_time_axis.cc:271 #, fuzzy msgid "clear automation" msgstr "borrar localizaciones" -#: automation_time_axis.cc:450 editor_actions.cc:317 +#: automation_time_axis.cc:452 editor_actions.cc:318 msgid "Hide" msgstr "Ocultar" -#: automation_time_axis.cc:452 crossfade_edit.cc:76 redirect_box.cc:1055 +#: automation_time_axis.cc:454 crossfade_edit.cc:78 redirect_box.cc:1057 msgid "Clear" msgstr "Quitar todos" -#: automation_time_axis.cc:475 +#: automation_time_axis.cc:477 #, fuzzy msgid "State" msgstr "Inicio" @@ -1849,1614 +1849,1601 @@ msgstr "" msgid "color of fill" msgstr "" -#: color_manager.cc:39 +#: color_manager.cc:40 #, fuzzy msgid "Object" msgstr "objeto" -#: color_manager.cc:77 +#: color_manager.cc:78 #, fuzzy msgid "cannot open color definition file %1: %2" msgstr "no se pudo mostrar el la imagen Acerca de \"%1\"" -#: crossfade_edit.cc:73 +#: crossfade_edit.cc:75 msgid "ardour: x-fade edit" msgstr "" -#: crossfade_edit.cc:77 panner_ui.cc:401 +#: crossfade_edit.cc:79 panner_ui.cc:443 #, fuzzy msgid "Reset" msgstr "resetear" -#: crossfade_edit.cc:78 +#: crossfade_edit.cc:80 #, fuzzy msgid "Fade" msgstr "Fades" -#: crossfade_edit.cc:79 +#: crossfade_edit.cc:81 msgid "Out (dry)" msgstr "" -#: crossfade_edit.cc:80 +#: crossfade_edit.cc:82 #, fuzzy msgid "Out" msgstr "Salidas" -#: crossfade_edit.cc:81 +#: crossfade_edit.cc:83 msgid "In (dry)" msgstr "" -#: crossfade_edit.cc:82 +#: crossfade_edit.cc:84 msgid "In" msgstr "" -#: crossfade_edit.cc:84 +#: crossfade_edit.cc:86 msgid "With Pre-roll" msgstr "" -#: crossfade_edit.cc:85 +#: crossfade_edit.cc:87 msgid "With Post-roll" msgstr "" -#: crossfade_edit.cc:93 +#: crossfade_edit.cc:95 msgid "Fade In" msgstr "" -#: crossfade_edit.cc:94 +#: crossfade_edit.cc:96 msgid "Fade Out" msgstr "" -#: crossfade_edit.cc:170 editor.cc:1842 editor_actions.cc:315 -#: option_editor.cc:129 +#: crossfade_edit.cc:172 editor.cc:1835 editor_actions.cc:316 +#: option_editor.cc:130 msgid "Audition" msgstr "Audicionando" -#: editor.cc:101 editor.cc:3588 +#: editor.cc:104 editor.cc:3616 msgid "Slide" msgstr "Deslizar" -#: editor.cc:102 editor.cc:3586 +#: editor.cc:105 editor.cc:3614 msgid "Splice" msgstr "Reunir" -#: editor.cc:107 editor.cc:3643 export_dialog.cc:78 export_dialog.cc:92 -#: export_dialog.cc:893 export_dialog.cc:1225 +#. note that this menu list starts at zero, not 1, because zero +#. is a valid, if useless, ID. +#. +#. leave some breathing room +#: editor.cc:110 editor.cc:3671 export_dialog.cc:78 export_dialog.cc:92 +#: export_dialog.cc:893 export_dialog.cc:1225 route_ui.cc:437 msgid "None" msgstr "Ningn" -#: editor.cc:108 editor.cc:3631 +#: editor.cc:111 editor.cc:3659 #, fuzzy msgid "CD Frames" msgstr "Cuadros" -#: editor.cc:109 editor.cc:3633 +#: editor.cc:112 editor.cc:3661 #, fuzzy msgid "SMPTE Frames" msgstr "SMPTE Cuadros/segundo" -#: editor.cc:110 editor.cc:3635 +#: editor.cc:113 editor.cc:3663 #, fuzzy msgid "SMPTE Seconds" msgstr "SMPTE Cuadros/segundo" -#: editor.cc:111 editor.cc:3637 +#: editor.cc:114 editor.cc:3665 msgid "SMPTE Minutes" msgstr "" -#: editor.cc:112 editor.cc:3639 +#: editor.cc:115 editor.cc:3667 #, fuzzy msgid "Seconds" msgstr "Minutos:Segundos" -#: editor.cc:113 editor.cc:3641 +#: editor.cc:116 editor.cc:3669 #, fuzzy msgid "Minutes" msgstr "Salidas Principales" -#: editor.cc:114 editor.cc:3613 +#: editor.cc:117 editor.cc:3641 msgid "Beats/32" msgstr "Pulsos/32" -#: editor.cc:115 editor.cc:3611 +#: editor.cc:118 editor.cc:3639 msgid "Beats/16" msgstr "Pulsos/16" -#: editor.cc:116 editor.cc:3609 +#: editor.cc:119 editor.cc:3637 msgid "Beats/8" msgstr "Pulsos/8" -#: editor.cc:117 editor.cc:3607 +#: editor.cc:120 editor.cc:3635 msgid "Beats/4" msgstr "Pulsos/4" -#: editor.cc:118 editor.cc:3605 +#: editor.cc:121 editor.cc:3633 msgid "Beats/3" msgstr "Pulsos/3" -#: editor.cc:119 editor.cc:3615 +#: editor.cc:122 editor.cc:3643 msgid "Beats" msgstr "Pulsos" -#: editor.cc:120 editor.cc:3617 +#: editor.cc:123 editor.cc:3645 msgid "Bars" msgstr "Compaces" -#: editor.cc:121 editor.cc:3619 +#: editor.cc:124 editor.cc:3647 msgid "Marks" msgstr "Marcas" -#: editor.cc:122 editor.cc:141 editor.cc:3621 editor.cc:3687 +#: editor.cc:125 editor.cc:144 editor.cc:3649 editor.cc:3715 msgid "Edit Cursor" msgstr "Cursor de Edicin" -#: editor.cc:123 editor.cc:3623 +#: editor.cc:126 editor.cc:3651 msgid "Region starts" msgstr "Comienzos de regin" -#: editor.cc:124 editor.cc:3625 +#: editor.cc:127 editor.cc:3653 msgid "Region ends" msgstr "Fines de regin" -#: editor.cc:125 editor.cc:3629 +#: editor.cc:128 editor.cc:3657 msgid "Region syncs" msgstr "Sincronizaciones de region" -#: editor.cc:126 editor.cc:3627 +#: editor.cc:129 editor.cc:3655 msgid "Region bounds" msgstr "Bordes de regin" -#: editor.cc:132 editor.cc:3662 +#: editor.cc:135 editor.cc:3690 #, fuzzy msgid "Magnetic" msgstr "Magn�ico" -#: editor.cc:137 editor.cc:3679 export_dialog.cc:140 export_dialog.cc:156 +#: editor.cc:140 editor.cc:3707 export_dialog.cc:140 export_dialog.cc:156 #: export_dialog.cc:1068 export_dialog.cc:1072 msgid "Left" msgstr "Izquierdo" -#: editor.cc:138 editor.cc:3681 export_dialog.cc:141 export_dialog.cc:157 +#: editor.cc:141 editor.cc:3709 export_dialog.cc:141 export_dialog.cc:157 msgid "Right" msgstr "Derecho" -#: editor.cc:139 editor.cc:3683 +#: editor.cc:142 editor.cc:3711 msgid "Center" msgstr "Centro" -#: editor.cc:140 editor.cc:3685 +#: editor.cc:143 editor.cc:3713 msgid "Playhead" msgstr "Barra de reproduccin" #. time display buttons -#: editor.cc:183 +#: editor.cc:186 msgid "Mins:Secs" msgstr "Mins:Segs" -#: editor.cc:186 editor_rulers.cc:353 +#: editor.cc:189 editor_rulers.cc:354 msgid "Frames" msgstr "Cuadros" -#: editor.cc:187 editor_rulers.cc:373 +#: editor.cc:190 editor_rulers.cc:374 msgid "Tempo" msgstr "Tempo" -#: editor.cc:188 editor_rulers.cc:367 +#: editor.cc:191 editor_rulers.cc:368 msgid "Meter" msgstr "Vmetro" -#: editor.cc:189 editor_rulers.cc:379 +#: editor.cc:192 editor_rulers.cc:380 #, fuzzy msgid "Location Markers" msgstr "Marcadores de localizacin" -#: editor.cc:190 editor_rulers.cc:385 +#: editor.cc:193 editor_rulers.cc:386 #, fuzzy msgid "Range Markers" msgstr "Marcadores de intervalo" -#: editor.cc:191 editor_rulers.cc:391 +#: editor.cc:194 editor_rulers.cc:392 msgid "Loop/Punch Ranges" msgstr "" -#: editor.cc:213 +#: editor.cc:216 msgid "range" msgstr "intervalo" -#: editor.cc:214 +#: editor.cc:217 msgid "object" msgstr "objeto" -#: editor.cc:216 +#: editor.cc:219 msgid "zoom" msgstr "zoom" -#: editor.cc:217 +#: editor.cc:220 msgid "timefx" msgstr "" -#: editor.cc:218 +#: editor.cc:221 msgid "listen" msgstr "" -#: editor.cc:220 +#: editor.cc:223 msgid "mode" msgstr "modo" -#: editor.cc:221 +#: editor.cc:224 msgid "automation" msgstr "automatizacin" -#: editor.cc:223 +#: editor.cc:226 msgid "Edit Mode" msgstr "Modo de edicin" -#: editor.cc:224 editor_actions.cc:283 +#: editor.cc:227 editor_actions.cc:284 msgid "Snap To" msgstr "Ajustar a" -#: editor.cc:225 +#: editor.cc:228 #, fuzzy msgid "Snap Mode" msgstr "Modo de ajuste" -#: editor.cc:226 +#: editor.cc:229 msgid "Zoom Focus" msgstr "Foco de Zoom" #. #. nudge -#: editor.cc:234 editor.cc:1907 editor.cc:2073 editor.cc:2129 +#: editor.cc:237 editor.cc:1900 editor.cc:2066 editor.cc:2122 msgid "Nudge" msgstr "Retocar" -#: editor.cc:466 +#: editor.cc:470 msgid "Zoom in" msgstr "Acercar" -#: editor.cc:467 +#: editor.cc:471 msgid "Zoom out" msgstr "Alejar" -#: editor.cc:470 +#: editor.cc:474 msgid "Zoom to session" msgstr "Mostrar toda la sesin" -#: editor.cc:485 +#: editor.cc:489 msgid "Zoom Span" msgstr "Alcance de zoom" -#: editor.cc:498 editor.cc:524 editor_actions.cc:61 mixer_ui.cc:85 +#: editor.cc:502 editor.cc:528 editor_actions.cc:62 mixer_ui.cc:86 +#: mixer_ui.cc:112 #, fuzzy msgid "Visible" msgstr "visible" -#: editor.cc:499 editor.cc:522 +#: editor.cc:503 editor.cc:526 #, fuzzy msgid "Name" msgstr "Cuadros" -#: editor.cc:595 editor.cc:661 +#: editor.cc:602 editor.cc:669 #, fuzzy msgid "Regions" msgstr "Regin" -#: editor.cc:634 editor.cc:673 +#: editor.cc:642 editor.cc:681 msgid "Chunks" msgstr "Trechos" -#: editor.cc:664 +#: editor.cc:672 #, fuzzy msgid "Tracks/Busses" msgstr "Pistas/Buses" -#: editor.cc:667 +#: editor.cc:675 msgid "Snapshots" msgstr "Capturas" -#: editor.cc:670 +#: editor.cc:678 msgid "Edit Groups" msgstr "Editar Grupos" -#: editor.cc:719 +#: editor.cc:727 msgid "Nudge region/selection forwards" msgstr "Retocar regin/selecin adelante" -#: editor.cc:720 +#: editor.cc:728 msgid "Nudge region/selection backwards" msgstr "Retocar regin/selecin atr�" -#: editor.cc:727 editor_mixer.cc:298 +#: editor.cc:735 editor_mixer.cc:299 msgid "ardour: editor" msgstr "" -#: editor.cc:728 +#: editor.cc:736 msgid "ardour_editor" msgstr "" -#: editor.cc:1190 +#: editor.cc:1183 msgid "ardour: editor: " msgstr "" #. force name -#: editor.cc:1275 editor.cc:1284 editor_markers.cc:869 +#: editor.cc:1268 editor.cc:1277 editor_markers.cc:870 msgid "Loop" msgstr "c�lico" #. force name -#: editor.cc:1289 editor.cc:1298 editor_markers.cc:895 +#: editor.cc:1282 editor.cc:1291 editor_markers.cc:896 msgid "Punch" msgstr "Insercin" -#: editor.cc:1446 editor_mouse.cc:1721 +#: editor.cc:1439 editor_mouse.cc:1742 msgid "programming error: fade in canvas item has no regionview data pointer!" msgstr "" -#: editor.cc:1458 editor.cc:1475 redirect_box.cc:1071 +#: editor.cc:1451 editor.cc:1468 redirect_box.cc:1073 msgid "Deactivate" msgstr "Desactivar" #. activation -#: editor.cc:1460 editor.cc:1477 redirect_box.cc:1069 +#: editor.cc:1453 editor.cc:1470 redirect_box.cc:1071 msgid "Activate" msgstr "Activar" -#: editor.cc:1465 editor.cc:1482 +#: editor.cc:1458 editor.cc:1475 #, fuzzy msgid "Linear" msgstr "linear" -#: editor.cc:1466 editor.cc:1483 editor_actions.cc:375 +#: editor.cc:1459 editor.cc:1476 editor_actions.cc:376 #, fuzzy msgid "Slowest" msgstr "Menor" -#: editor.cc:1467 editor.cc:1484 editor_actions.cc:376 +#: editor.cc:1460 editor.cc:1477 editor_actions.cc:377 #, fuzzy msgid "Slow" msgstr "Solo" -#: editor.cc:1468 editor.cc:1485 editor_actions.cc:378 +#: editor.cc:1461 editor.cc:1478 editor_actions.cc:379 #, fuzzy msgid "Fast" msgstr "Fades" -#: editor.cc:1469 editor.cc:1486 editor_actions.cc:380 +#: editor.cc:1462 editor.cc:1479 editor_actions.cc:381 #, fuzzy msgid "Fastest" msgstr "r�ido" -#: editor.cc:1596 editor.cc:1604 +#: editor.cc:1589 editor.cc:1597 msgid "Freeze" msgstr "Unir regiones" -#: editor.cc:1600 +#: editor.cc:1593 msgid "Unfreeze" msgstr "Separar regiones" -#: editor.cc:1769 editor.cc:1864 +#: editor.cc:1762 editor.cc:1857 #, fuzzy msgid "Unmute" msgstr "mudo" #. non-operative menu items for menu bar #. show editors -#: editor.cc:1773 editor.cc:2053 editor.cc:2755 editor_actions.cc:26 -#: editor_markers.cc:506 mixer_strip.cc:512 mixer_strip.cc:572 -#: redirect_box.cc:1077 +#: editor.cc:1766 editor.cc:2046 editor.cc:2748 editor_actions.cc:27 +#: editor_markers.cc:507 mixer_strip.cc:495 mixer_strip.cc:563 +#: redirect_box.cc:1079 msgid "Edit" msgstr "Editar" -#: editor.cc:1778 +#: editor.cc:1771 msgid "Convert to short" msgstr "" -#: editor.cc:1780 +#: editor.cc:1773 msgid "Convert to full" msgstr "" -#: editor.cc:1791 +#: editor.cc:1784 #, fuzzy msgid "Crossfade" msgstr "editar fade in" -#: editor.cc:1834 +#: editor.cc:1827 msgid "Popup region editor" msgstr "Editor de regiones" -#: editor.cc:1835 +#: editor.cc:1828 #, fuzzy msgid "Raise to top layer" msgstr "Elevar regin a la capa m� alta" -#: editor.cc:1836 +#: editor.cc:1829 #, fuzzy msgid "Lower to bottom layer" msgstr "Enviar regin a capa m� baja" -#: editor.cc:1838 +#: editor.cc:1831 msgid "Define sync point" msgstr "Definir punto de sincron�" -#: editor.cc:1839 +#: editor.cc:1832 msgid "Remove sync point" msgstr "Remover punto de sincron�" -#: editor.cc:1844 +#: editor.cc:1837 #, fuzzy msgid "Bounce" msgstr "intervalo" -#: editor.cc:1847 +#: editor.cc:1840 #, fuzzy msgid "Analyze region" msgstr "Reproducir Regin" -#: editor.cc:1859 +#: editor.cc:1852 #, fuzzy msgid "Lock" msgstr "bloquear" -#: editor.cc:1860 +#: editor.cc:1853 #, fuzzy msgid "Unlock" msgstr "Desbloquear" -#: editor.cc:1870 +#: editor.cc:1863 #, fuzzy msgid "Original position" msgstr "Posicin original" -#: editor.cc:1876 +#: editor.cc:1869 msgid "Toggle envelope visibility" msgstr "" -#: editor.cc:1877 +#: editor.cc:1870 #, fuzzy msgid "Toggle envelope active" msgstr "activar" -#: editor.cc:1881 +#: editor.cc:1874 #, fuzzy msgid "DeNormalize" msgstr "Normalizar" -#: editor.cc:1883 +#: editor.cc:1876 #, fuzzy msgid "Normalize" msgstr "Normalizar" -#: editor.cc:1886 +#: editor.cc:1879 #, fuzzy msgid "Reverse" msgstr "Invertir" #. range related stuff -#: editor.cc:1892 +#: editor.cc:1885 #, fuzzy msgid "Add Range Markers" msgstr "Marcadores de intervalo" -#: editor.cc:1893 +#: editor.cc:1886 #, fuzzy msgid "Set Range" msgstr "Separar Regin" -#: editor.cc:1902 +#: editor.cc:1895 #, fuzzy msgid "Nudge fwd" msgstr "Retocar" -#: editor.cc:1903 +#: editor.cc:1896 #, fuzzy msgid "Nudge bwd" msgstr "Retocar" -#: editor.cc:1904 +#: editor.cc:1897 msgid "Nudge fwd by capture offset" msgstr "" -#: editor.cc:1905 +#: editor.cc:1898 msgid "Nudge bwd by capture offset" msgstr "" -#: editor.cc:1914 +#: editor.cc:1907 msgid "Start to edit cursor" msgstr "Desde principio hasta cursor de edicin" -#: editor.cc:1915 +#: editor.cc:1908 msgid "Edit cursor to end" msgstr "Desde cursor de edicin hasta final" -#: editor.cc:1917 +#: editor.cc:1910 gain_meter.cc:181 gain_meter.cc:813 panner_ui.cc:98 +#: panner_ui.cc:803 msgid "Trim" msgstr "Cortar" -#: editor.cc:1920 +#: editor.cc:1913 msgid "Split" msgstr "Separar" -#: editor.cc:1923 +#: editor.cc:1916 msgid "Make mono regions" msgstr "Crear regiones mono" -#: editor.cc:1926 +#: editor.cc:1919 msgid "Duplicate" msgstr "Duplicar" -#: editor.cc:1927 +#: editor.cc:1920 msgid "Fill Track" msgstr "Llenar Pista" -#: editor.cc:1931 +#: editor.cc:1924 #, fuzzy msgid "Destroy" msgstr "Destruir" -#: editor.cc:1961 +#: editor.cc:1954 #, fuzzy msgid "Play range" msgstr "Reproducir el intervalo cont�uamente" -#: editor.cc:1962 +#: editor.cc:1955 #, fuzzy msgid "Loop range" msgstr "rango de reproduccin cont�ua" -#: editor.cc:1966 +#: editor.cc:1959 #, fuzzy msgid "Analyze range" msgstr "Reproducir el intervalo cont�uamente" -#: editor.cc:1970 +#: editor.cc:1963 #, fuzzy msgid "Separate range to track" msgstr "Separar Regin" -#: editor.cc:1971 +#: editor.cc:1964 #, fuzzy msgid "Separate range to region list" msgstr "Reproducir regin seleccionada cont�uamente" -#: editor.cc:1974 +#: editor.cc:1967 #, fuzzy msgid "Select all in range" msgstr "Seleccionar todo dentro de pista" -#: editor.cc:1976 editor.cc:2021 +#: editor.cc:1969 editor.cc:2014 #, fuzzy msgid "Set range to loop range" msgstr "seleccionar rango de zoom" -#: editor.cc:1977 editor.cc:2022 +#: editor.cc:1970 editor.cc:2015 #, fuzzy msgid "Set range to punch range" msgstr "Seleccionar intervalo actual" -#: editor.cc:1979 +#: editor.cc:1972 #, fuzzy msgid "Crop region to range" msgstr "Acortar regin hasta la seleccin" -#: editor.cc:1980 +#: editor.cc:1973 #, fuzzy msgid "Fill range with region" msgstr "Crear Regin" -#: editor.cc:1981 +#: editor.cc:1974 #, fuzzy msgid "Duplicate range" msgstr "Duplicar" -#: editor.cc:1982 +#: editor.cc:1975 #, fuzzy msgid "Create chunk from range" msgstr "Crear trecho a partir de seleccin" -#: editor.cc:1984 +#: editor.cc:1977 #, fuzzy msgid "Bounce range" msgstr "intervalo" -#: editor.cc:1985 +#: editor.cc:1978 #, fuzzy msgid "Export range" msgstr "Exportar regin" -#: editor.cc:1987 +#: editor.cc:1980 #, fuzzy msgid "Range" msgstr "intervalo" -#: editor.cc:2002 editor.cc:2087 +#: editor.cc:1995 editor.cc:2080 #, fuzzy msgid "Play from edit cursor" msgstr "Reproducir desde el cursor" -#: editor.cc:2003 editor.cc:2088 +#: editor.cc:1996 editor.cc:2081 msgid "Play from start" msgstr "Reproducir desde el principio" -#: editor.cc:2004 +#: editor.cc:1997 #, fuzzy msgid "Play region" msgstr "Reproducir Regin" -#: editor.cc:2006 +#: editor.cc:1999 #, fuzzy msgid "Loop Region" msgstr "Reproducir regin cont�uamente" -#: editor.cc:2008 editor.cc:2089 sfdb_ui.cc:56 -msgid "Play" -msgstr "Reproducir" - -#: editor.cc:2016 editor.cc:2097 +#: editor.cc:2009 editor.cc:2090 #, fuzzy msgid "Select All in track" msgstr "Seleccionar todo dentro de pista" -#: editor.cc:2017 editor.cc:2098 redirect_box.cc:1065 +#: editor.cc:2010 editor.cc:2091 redirect_box.cc:1067 #, fuzzy msgid "Select All" msgstr "Seleccionar todo" -#: editor.cc:2018 editor.cc:2099 +#: editor.cc:2011 editor.cc:2092 #, fuzzy msgid "Invert selection in track" msgstr "Invertir dentro de pista" -#: editor.cc:2019 editor.cc:2100 +#: editor.cc:2012 editor.cc:2093 #, fuzzy msgid "Invert selection" msgstr "Grabar seleccin" -#: editor.cc:2024 editor.cc:2102 +#: editor.cc:2017 editor.cc:2095 #, fuzzy msgid "Select all after edit cursor" msgstr "Desde principio hasta cursor de edicin" -#: editor.cc:2025 editor.cc:2103 +#: editor.cc:2018 editor.cc:2096 #, fuzzy msgid "Select all before edit cursor" msgstr "Desde principio hasta cursor de edicin" -#: editor.cc:2026 editor.cc:2104 +#: editor.cc:2019 editor.cc:2097 #, fuzzy msgid "Select all after playhead" msgstr "Ubicar desde barra de reproduccin" -#: editor.cc:2027 editor.cc:2105 +#: editor.cc:2020 editor.cc:2098 #, fuzzy msgid "Select all before playhead" msgstr "Ubicar desde barra de reproduccin" -#: editor.cc:2028 +#: editor.cc:2021 #, fuzzy msgid "Select all between cursors" msgstr "Desde principio hasta cursor de edicin" #. standard editing stuff -#: editor.cc:2039 editor.cc:2115 editor.cc:3455 editor_actions.cc:213 -#: redirect_box.cc:1058 +#: editor.cc:2032 editor.cc:2108 editor.cc:3483 editor_actions.cc:214 +#: redirect_box.cc:1060 msgid "Cut" msgstr "Cortar" -#: editor.cc:2040 editor.cc:2116 editor.cc:3457 editor_actions.cc:218 -#: redirect_box.cc:1060 +#: editor.cc:2033 editor.cc:2109 editor.cc:3485 editor_actions.cc:219 +#: redirect_box.cc:1062 msgid "Copy" msgstr "Copiar" -#: editor.cc:2041 +#: editor.cc:2034 #, fuzzy msgid "Paste at edit cursor" msgstr "Desde principio hasta cursor de edicin" -#: editor.cc:2042 +#: editor.cc:2035 #, fuzzy msgid "Paste at mouse" msgstr "usar salidas Master" -#: editor.cc:2046 editor.cc:3462 +#: editor.cc:2039 editor.cc:3490 msgid "Align" msgstr "Alinear" -#: editor.cc:2047 editor.cc:3464 +#: editor.cc:2040 editor.cc:3492 msgid "Align Relative" msgstr "Alinear relativamente" -#: editor.cc:2051 +#: editor.cc:2044 msgid "Insert chunk" msgstr "Insertar trecho" -#: editor.cc:2058 +#: editor.cc:2051 #, fuzzy msgid "Insert Selected Region" msgstr "Reproducir regin seleccionada cont�uamente" -#: editor.cc:2059 +#: editor.cc:2052 msgid "Insert Existing Audio" msgstr "" -#: editor.cc:2068 editor.cc:2124 +#: editor.cc:2061 editor.cc:2117 msgid "Nudge entire track fwd" msgstr "Retocar toda la pista adelante" -#: editor.cc:2069 editor.cc:2125 +#: editor.cc:2062 editor.cc:2118 msgid "Nudge track after edit cursor fwd" msgstr "Retocar pista desde cursor de edicin adelante" -#: editor.cc:2070 editor.cc:2126 +#: editor.cc:2063 editor.cc:2119 msgid "Nudge entire track bwd" msgstr "Retocar toda la pista atr�" -#: editor.cc:2071 editor.cc:2127 +#: editor.cc:2064 editor.cc:2120 msgid "Nudge track after edit cursor bwd" msgstr "Retocar toda la pista, desde cursor de edicin atr�" -#: editor.cc:2117 editor.cc:3459 editor_actions.cc:220 redirect_box.cc:1062 +#: editor.cc:2110 editor.cc:3487 editor_actions.cc:221 redirect_box.cc:1064 msgid "Paste" msgstr "Pegar" -#: editor.cc:2637 +#: editor.cc:2630 msgid "select/move objects" msgstr "selecionar/mover objetos" -#: editor.cc:2638 +#: editor.cc:2631 msgid "select/move ranges" msgstr "selecionar/mover intervalos" -#: editor.cc:2639 +#: editor.cc:2632 msgid "draw gain automation" msgstr "dibujar automatizacin de volumen" -#: editor.cc:2640 +#: editor.cc:2633 msgid "select zoom range" msgstr "seleccionar rango de zoom" -#: editor.cc:2641 +#: editor.cc:2634 msgid "stretch/shrink regions" msgstr "estirar/encoger regiones" -#: editor.cc:2642 +#: editor.cc:2635 #, fuzzy msgid "listen to specific regions" msgstr "Reproducir regin seleccionada cont�uamente" -#: editor.cc:2753 +#: editor.cc:2746 msgid "Start:" msgstr "Inicio:" -#: editor.cc:2754 +#: editor.cc:2747 msgid "End:" msgstr "Final:" -#: editor.cc:3097 -#, fuzzy -msgid "set selected trackview" -msgstr "Insertar seleccin" - -#: editor.cc:3137 -#, fuzzy -msgid "set selected control point" -msgstr "Remover punto de sincron�" - -#: editor.cc:3246 -#, fuzzy -msgid "set selected regionview" -msgstr "Reproducir regin seleccionada cont�uamente" - -#: editor.cc:3334 editor.cc:3374 +#: editor.cc:3362 editor.cc:3402 #, fuzzy msgid "set selected regions" msgstr "Reproducir regin seleccionada cont�uamente" -#: editor.cc:3430 editor_actions.cc:203 +#: editor.cc:3458 editor_actions.cc:204 msgid "Undo" msgstr "Deshacer" -#: editor.cc:3432 +#: editor.cc:3460 msgid "Undo (%1)" msgstr "Deshacer (%1)" -#: editor.cc:3442 editor_actions.cc:205 +#: editor.cc:3470 editor_actions.cc:206 msgid "Redo" msgstr "Rehacer" -#: editor.cc:3444 +#: editor.cc:3472 msgid "Redo (%1)" msgstr "Rehacer (%1)" -#: editor.cc:3478 +#: editor.cc:3506 msgid "... as new track" msgstr "" -#: editor.cc:3479 +#: editor.cc:3507 #, fuzzy msgid "... as new region" msgstr "normalizar regiones" -#: editor.cc:3481 +#: editor.cc:3509 msgid "Import audio (copy)" msgstr "Importar audio (copiar)" -#: editor.cc:3484 +#: editor.cc:3512 #, fuzzy msgid "Remove last capture" msgstr "Quitar ltima captura" -#: editor.cc:3508 +#: editor.cc:3536 msgid "Duplicate how many times?" msgstr "Duplicar cuantas veces?" -#: editor.cc:3994 +#: editor.cc:4022 msgid "" "Playlist %1 is currently unused.\n" "If left alone, no audio files used by it will be cleaned.\n" "If deleted, audio files used by it alone by will cleaned." msgstr "" -#: editor.cc:4002 +#: editor.cc:4030 #, fuzzy msgid "Delete playlist" msgstr "Nombre a captura de sesin" -#: editor.cc:4003 +#: editor.cc:4031 #, fuzzy msgid "Keep playlist" msgstr "Nombre a captura de sesin" -#: editor.cc:4004 editor_audio_import.cc:237 editor_ops.cc:1976 -#: editor_timefx.cc:52 export_dialog.cc:971 io_selector.cc:58 -#: io_selector.cc:792 redirect_box.cc:901 tempo_dialog.cc:19 -#: tempo_dialog.cc:36 tempo_dialog.cc:152 tempo_dialog.cc:170 +#: editor.cc:4032 editor_audio_import.cc:236 editor_ops.cc:2048 +#: editor_timefx.cc:71 export_dialog.cc:971 io_selector.cc:59 +#: io_selector.cc:793 redirect_box.cc:903 tempo_dialog.cc:20 +#: tempo_dialog.cc:37 tempo_dialog.cc:202 tempo_dialog.cc:220 msgid "Cancel" msgstr "Cancelar" -#: editor.cc:4171 +#: editor.cc:4199 #, fuzzy msgid "new playlists" msgstr "Nombre a captura de sesin" -#: editor.cc:4179 +#: editor.cc:4207 #, fuzzy msgid "copy playlists" msgstr "Nombre a captura de sesin" -#: editor.cc:4187 +#: editor.cc:4215 #, fuzzy msgid "clear playlists" msgstr "Nombre a captura de sesin" -#: editor_actions.cc:27 +#: editor_actions.cc:28 #, fuzzy msgid "Select regions" msgstr "Reproducir regin seleccionada cont�uamente" -#: editor_actions.cc:28 +#: editor_actions.cc:29 #, fuzzy msgid "Select range operations" msgstr "Reproducir regin seleccionada cont�uamente" -#: editor_actions.cc:29 +#: editor_actions.cc:30 #, fuzzy msgid "Move edit cursor" msgstr "Desde principio hasta cursor de edicin" -#: editor_actions.cc:30 +#: editor_actions.cc:31 #, fuzzy msgid "Region operations" msgstr "Regiones/creacin" -#: editor_actions.cc:31 +#: editor_actions.cc:32 msgid "Tools" msgstr "" -#: editor_actions.cc:32 +#: editor_actions.cc:33 msgid "View" msgstr "" -#: editor_actions.cc:33 +#: editor_actions.cc:34 #, fuzzy msgid "ZoomFocus" msgstr "Foco de Zoom" -#: editor_actions.cc:34 +#: editor_actions.cc:35 #, fuzzy msgid "Meter hold" msgstr "Vmetro" -#: editor_actions.cc:35 +#: editor_actions.cc:36 msgid "Meter falloff" msgstr "" -#: editor_actions.cc:37 +#: editor_actions.cc:38 #, fuzzy msgid "Crossfades" msgstr "editar fade in" -#: editor_actions.cc:38 +#: editor_actions.cc:39 #, fuzzy msgid "Monitoring" msgstr "Monitorizacin por Hardware" -#: editor_actions.cc:39 +#: editor_actions.cc:40 #, fuzzy msgid "Autoconnect" msgstr "Conectar" -#: editor_actions.cc:40 +#: editor_actions.cc:41 #, fuzzy msgid "Layering" msgstr "Capa" -#: editor_actions.cc:41 +#: editor_actions.cc:42 #, fuzzy msgid "Metering" msgstr "Vmetro" -#: editor_actions.cc:42 +#: editor_actions.cc:43 msgid "Fall off rate" msgstr "" -#: editor_actions.cc:43 +#: editor_actions.cc:44 msgid "Hold Time" msgstr "" -#: editor_actions.cc:44 +#: editor_actions.cc:45 msgid "Add Existing Audio" msgstr "" #. add named actions for the editor -#: editor_actions.cc:49 +#: editor_actions.cc:50 #, fuzzy msgid "Show Editor Mixer" msgstr "Mostrar todas las pistas de Audio en el Mixer" -#: editor_actions.cc:54 +#: editor_actions.cc:55 #, fuzzy msgid "Span Entire Overlap" msgstr "Elevar regin una capa" -#: editor_actions.cc:56 editor_actions.cc:383 +#: editor_actions.cc:57 editor_actions.cc:384 #, fuzzy msgid "Short" msgstr "conector" -#: editor_actions.cc:63 +#: editor_actions.cc:64 msgid "Created Automatically" msgstr "" -#: editor_actions.cc:66 +#: editor_actions.cc:67 msgid "Playhead to Next Region Start" msgstr "" -#: editor_actions.cc:68 +#: editor_actions.cc:69 msgid "Playhead to Next Region End" msgstr "" -#: editor_actions.cc:70 +#: editor_actions.cc:71 msgid "Playhead to Next Region Sync" msgstr "" -#: editor_actions.cc:73 +#: editor_actions.cc:74 msgid "Playhead to Previous Region Start" msgstr "" -#: editor_actions.cc:75 +#: editor_actions.cc:76 msgid "Playhead to Previous Region End" msgstr "" -#: editor_actions.cc:77 +#: editor_actions.cc:78 msgid "Playhead to Previous Region Sync" msgstr "" -#: editor_actions.cc:80 +#: editor_actions.cc:81 #, fuzzy msgid "Edit Cursor to Next Region Start" msgstr "Desde cursor de edicin hasta final" -#: editor_actions.cc:82 +#: editor_actions.cc:83 #, fuzzy msgid "Edit Cursor to Next Region End" msgstr "Desde cursor de edicin hasta final" -#: editor_actions.cc:84 +#: editor_actions.cc:85 #, fuzzy msgid "Edit Cursor to Next Region Sync" msgstr "Desde cursor de edicin hasta final" -#: editor_actions.cc:87 +#: editor_actions.cc:88 msgid "Edit Cursor to Previous Region Start" msgstr "" -#: editor_actions.cc:89 +#: editor_actions.cc:90 #, fuzzy msgid "Edit Cursor to Previous Region End" msgstr "Desde cursor de edicin hasta final" -#: editor_actions.cc:91 +#: editor_actions.cc:92 #, fuzzy msgid "Edit Cursor to Previous Region Sync" msgstr "Desde cursor de edicin hasta final" -#: editor_actions.cc:94 +#: editor_actions.cc:95 msgid "Playhead to Range Start" msgstr "" -#: editor_actions.cc:96 +#: editor_actions.cc:97 #, fuzzy msgid "Playhead to Range End" msgstr "Reproducir el intervalo cont�uamente" -#: editor_actions.cc:99 +#: editor_actions.cc:100 #, fuzzy msgid "Edit Cursor to Range Start" msgstr "Desde cursor de edicin hasta final" -#: editor_actions.cc:101 +#: editor_actions.cc:102 #, fuzzy msgid "Edit Cursor to Range End" msgstr "Desde cursor de edicin hasta final" -#: editor_actions.cc:104 editor_ops.cc:1300 +#: editor_actions.cc:105 editor_ops.cc:1363 #, fuzzy msgid "select all" msgstr "Seleccionar todo" -#: editor_actions.cc:106 +#: editor_actions.cc:107 #, fuzzy msgid "Select All After Edit Cursor" msgstr "Reproducir desde el cursor" -#: editor_actions.cc:108 +#: editor_actions.cc:109 msgid "Select All Before Edit Cursor" msgstr "" -#: editor_actions.cc:111 +#: editor_actions.cc:112 #, fuzzy msgid "Select All After Playhead" msgstr "Ubicar desde barra de reproduccin" -#: editor_actions.cc:113 +#: editor_actions.cc:114 #, fuzzy msgid "Select All Before Playhead" msgstr "Ubicar desde barra de reproduccin" -#: editor_actions.cc:115 +#: editor_actions.cc:116 #, fuzzy msgid "Select All Between Cursors" msgstr "Reproducir desde el cursor" -#: editor_actions.cc:118 +#: editor_actions.cc:119 #, fuzzy msgid "Select All in Punch Range" msgstr "Seleccionar intervalo de punch" -#: editor_actions.cc:120 +#: editor_actions.cc:121 #, fuzzy msgid "Select All in Loop Range" msgstr "seleccionar rango de zoom" -#: editor_actions.cc:123 +#: editor_actions.cc:124 msgid "Jump Forward to Mark" msgstr "" -#: editor_actions.cc:125 +#: editor_actions.cc:126 msgid "Jump Backward to Mark" msgstr "" -#: editor_actions.cc:127 +#: editor_actions.cc:128 #, fuzzy msgid "Add Location from Playhead" msgstr "Ubicar desde barra de reproduccin" -#: editor_actions.cc:130 +#: editor_actions.cc:131 #, fuzzy msgid "Nudge Forward" msgstr "Retocar" -#: editor_actions.cc:132 +#: editor_actions.cc:133 #, fuzzy msgid "Nudge Next Forward" msgstr "Retocar regin/selecin adelante" -#: editor_actions.cc:134 +#: editor_actions.cc:135 #, fuzzy msgid "Nudge Backward" msgstr "Retocar" -#: editor_actions.cc:136 +#: editor_actions.cc:137 #, fuzzy msgid "Nudge Next Backward" msgstr "Retocar toda la pista adelante" -#: editor_actions.cc:139 +#: editor_actions.cc:140 #, fuzzy msgid "Zoom Out" msgstr "Alejar" -#: editor_actions.cc:141 +#: editor_actions.cc:142 #, fuzzy msgid "Zoom In" msgstr "Acercar" -#: editor_actions.cc:143 +#: editor_actions.cc:144 #, fuzzy msgid "Zoom to Session" msgstr "Mostrar toda la sesin" -#: editor_actions.cc:146 +#: editor_actions.cc:147 #, fuzzy msgid "Scroll Tracks Up" msgstr "Llenar Pista" -#: editor_actions.cc:148 +#: editor_actions.cc:149 msgid "Scroll Tracks Down" msgstr "" -#: editor_actions.cc:150 +#: editor_actions.cc:151 #, fuzzy msgid "Step Tracks Up" msgstr "Ocultar esta pista" -#: editor_actions.cc:152 +#: editor_actions.cc:153 msgid "Step Tracks Down" msgstr "" -#: editor_actions.cc:155 +#: editor_actions.cc:156 msgid "Scroll Backward" msgstr "" -#: editor_actions.cc:157 +#: editor_actions.cc:158 msgid "Scroll Forward" msgstr "" -#: editor_actions.cc:159 +#: editor_actions.cc:160 msgid "goto" msgstr "" -#: editor_actions.cc:161 +#: editor_actions.cc:162 #, fuzzy msgid "Center Playhead" msgstr "Barra de reproduccin" -#: editor_actions.cc:163 +#: editor_actions.cc:164 #, fuzzy msgid "Center Edit Cursor" msgstr "Cursor de Edicin" -#: editor_actions.cc:165 +#: editor_actions.cc:166 #, fuzzy msgid "Playhead Forward" msgstr "Barra de reproduccin" -#: editor_actions.cc:167 +#: editor_actions.cc:168 #, fuzzy msgid "Playhead Backward" msgstr "Barra de reproduccin" -#: editor_actions.cc:169 +#: editor_actions.cc:170 #, fuzzy msgid "Playhead to Edit" msgstr "Barra de reproduccin" -#: editor_actions.cc:171 +#: editor_actions.cc:172 #, fuzzy msgid "Edit to Playhead" msgstr "Ubicar desde barra de reproduccin" -#: editor_actions.cc:174 +#: editor_actions.cc:175 #, fuzzy msgid "Align Regions Start" msgstr "Comienzos de regin" -#: editor_actions.cc:176 +#: editor_actions.cc:177 #, fuzzy msgid "Align Regions Start Relative" msgstr "Alinear relativamente" -#: editor_actions.cc:178 +#: editor_actions.cc:179 #, fuzzy msgid "Align Regions End" msgstr "normalizar regiones" -#: editor_actions.cc:180 +#: editor_actions.cc:181 #, fuzzy msgid "Align Regions End Relative" msgstr "Alinear relativamente" -#: editor_actions.cc:183 +#: editor_actions.cc:184 #, fuzzy msgid "Align Regions Sync" msgstr "normalizar regiones" -#: editor_actions.cc:185 +#: editor_actions.cc:186 #, fuzzy msgid "Align Regions Sync Relative" msgstr "Alinear relativamente" -#: editor_actions.cc:188 +#: editor_actions.cc:189 #, fuzzy msgid "Audition at Mouse" msgstr "Audicionando" -#: editor_actions.cc:190 +#: editor_actions.cc:191 #, fuzzy msgid "Brush at Mouse" msgstr "usar salidas Master" -#: editor_actions.cc:192 +#: editor_actions.cc:193 #, fuzzy msgid "Set Edit Cursor" msgstr "Cursor de Edicin" -#: editor_actions.cc:194 +#: editor_actions.cc:195 #, fuzzy msgid "Mute/Unmute Region" msgstr "Crear Regin" -#: editor_actions.cc:196 +#: editor_actions.cc:197 #, fuzzy msgid "Set Playhead" msgstr "Barra de reproduccin" -#: editor_actions.cc:198 +#: editor_actions.cc:199 #, fuzzy msgid "Split Region" msgstr "Separar Regin" -#: editor_actions.cc:200 +#: editor_actions.cc:201 #, fuzzy msgid "Set Region Sync Position" msgstr "Por Posicin de regin" -#: editor_actions.cc:208 +#: editor_actions.cc:209 #, fuzzy msgid "Export Session" msgstr "Exportar regin" -#: editor_actions.cc:210 +#: editor_actions.cc:211 #, fuzzy msgid "Export Range" msgstr "Separar Regin" #. Note: for now, editor-delete does the exact same thing as editor-cut -#: editor_actions.cc:216 +#: editor_actions.cc:217 #, fuzzy msgid "Delete" msgstr "quitar" -#: editor_actions.cc:222 +#: editor_actions.cc:223 #, fuzzy msgid "Duplicate Region" msgstr "Reproducir regin seleccionada cont�uamente" -#: editor_actions.cc:224 +#: editor_actions.cc:225 #, fuzzy msgid "Duplicate Range" msgstr "Duplicar" -#: editor_actions.cc:226 +#: editor_actions.cc:227 msgid "Insert Region" msgstr "Insertar Regin" -#: editor_actions.cc:228 +#: editor_actions.cc:229 #, fuzzy msgid "Reverse Region" msgstr "invertir regiones" -#: editor_actions.cc:230 +#: editor_actions.cc:231 #, fuzzy msgid "Normalize Region" msgstr "Normalizar" -#: editor_actions.cc:232 +#: editor_actions.cc:233 #, fuzzy msgid "crop" msgstr "copiar" -#: editor_actions.cc:234 +#: editor_actions.cc:235 #, fuzzy msgid "Insert Chunk" msgstr "Insertar trecho" -#: editor_actions.cc:237 +#: editor_actions.cc:238 #, fuzzy msgid "Split at edit cursor" msgstr "Desde principio hasta cursor de edicin" -#: editor_actions.cc:240 +#: editor_actions.cc:241 #, fuzzy msgid "Start Range" msgstr "Separar Regin" -#: editor_actions.cc:242 +#: editor_actions.cc:243 msgid "Finish Range" msgstr "" -#: editor_actions.cc:244 +#: editor_actions.cc:245 msgid "Finish add Range" msgstr "" -#: editor_actions.cc:247 +#: editor_actions.cc:248 msgid "Extend Range to End of Region" msgstr "" -#: editor_actions.cc:249 +#: editor_actions.cc:250 #, fuzzy msgid "Extend Range to Start of Region" msgstr "Ir al inicio de la sesin" -#: editor_actions.cc:252 +#: editor_actions.cc:253 #, fuzzy msgid "Follow Playhead" msgstr "Seguir a la barra de reproduccin" -#: editor_actions.cc:260 +#: editor_actions.cc:261 #, fuzzy msgid "Zoom Focus Left" msgstr "Foco de Zoom" -#: editor_actions.cc:262 +#: editor_actions.cc:263 #, fuzzy msgid "Zoom Focus Right" msgstr "Foco de Zoom" -#: editor_actions.cc:264 +#: editor_actions.cc:265 #, fuzzy msgid "Zoom Focus Center" msgstr "Foco de Zoom" -#: editor_actions.cc:266 +#: editor_actions.cc:267 #, fuzzy msgid "Zoom Focus Playhead" msgstr "Foco de Zoom" -#: editor_actions.cc:268 +#: editor_actions.cc:269 #, fuzzy msgid "Zoom Focus Edit" msgstr "Foco de Zoom" -#: editor_actions.cc:274 +#: editor_actions.cc:275 msgid "Object Tool" msgstr "" -#: editor_actions.cc:275 +#: editor_actions.cc:276 #, fuzzy msgid "Range Tool" msgstr "intervalo" -#: editor_actions.cc:276 +#: editor_actions.cc:277 msgid "Gain Tool" msgstr "" -#: editor_actions.cc:277 +#: editor_actions.cc:278 #, fuzzy msgid "Zoom Tool" msgstr "Alejar" -#: editor_actions.cc:278 +#: editor_actions.cc:279 msgid "Timefx Tool" msgstr "" -#: editor_actions.cc:285 +#: editor_actions.cc:286 #, fuzzy msgid "Snap to frame" msgstr "Modo de ajuste" -#: editor_actions.cc:286 +#: editor_actions.cc:287 #, fuzzy msgid "Snap to cd frame" msgstr "Modo de ajuste" -#: editor_actions.cc:287 +#: editor_actions.cc:288 #, fuzzy msgid "Snap to SMPTE frame" msgstr "SMPTE Cuadros/segundo" -#: editor_actions.cc:288 +#: editor_actions.cc:289 #, fuzzy msgid "Snap to SMPTE seconds" msgstr "SMPTE Cuadros/segundo" -#: editor_actions.cc:289 +#: editor_actions.cc:290 msgid "Snap to SMPTE minutes" msgstr "" -#: editor_actions.cc:290 +#: editor_actions.cc:291 #, fuzzy msgid "Snap to seconds" msgstr "Minutos:Segundos" -#: editor_actions.cc:291 +#: editor_actions.cc:292 msgid "Snap to minutes" msgstr "" -#: editor_actions.cc:292 +#: editor_actions.cc:293 #, fuzzy msgid "Snap to thirtyseconds" msgstr "trig�ima segunda (32)" -#: editor_actions.cc:293 +#: editor_actions.cc:294 msgid "Snap to asixteenthbeat" msgstr "" -#: editor_actions.cc:294 +#: editor_actions.cc:295 msgid "Snap to eighths" msgstr "" -#: editor_actions.cc:295 +#: editor_actions.cc:296 msgid "Snap to quarters" msgstr "" -#: editor_actions.cc:296 +#: editor_actions.cc:297 #, fuzzy msgid "Snap to thirds" msgstr "Modo de ajuste" -#: editor_actions.cc:297 +#: editor_actions.cc:298 #, fuzzy msgid "Snap to beat" msgstr "Modo de ajuste" -#: editor_actions.cc:298 +#: editor_actions.cc:299 #, fuzzy msgid "Snap to bar" msgstr "Ajustar a" -#: editor_actions.cc:299 +#: editor_actions.cc:300 #, fuzzy msgid "Snap to mark" msgstr "agregar un marcador de regin" -#: editor_actions.cc:300 +#: editor_actions.cc:301 #, fuzzy msgid "Snap to edit cursor" msgstr "Desde principio hasta cursor de edicin" -#: editor_actions.cc:301 +#: editor_actions.cc:302 #, fuzzy msgid "Snap to region start" msgstr "Comienzos de regin" -#: editor_actions.cc:302 +#: editor_actions.cc:303 #, fuzzy msgid "Snap to region end" msgstr "Fines de regin" -#: editor_actions.cc:303 +#: editor_actions.cc:304 #, fuzzy msgid "Snap to region sync" msgstr "Sincronizaciones de region" -#: editor_actions.cc:304 +#: editor_actions.cc:305 #, fuzzy msgid "Snap to region boundary" msgstr "Bordes de regin" #. the region list popup menu -#: editor_actions.cc:313 +#: editor_actions.cc:314 #, fuzzy msgid "Sort" msgstr "conector" -#: editor_actions.cc:321 +#: editor_actions.cc:322 msgid "Show all" msgstr "Mostrar todo" -#: editor_actions.cc:322 +#: editor_actions.cc:323 #, fuzzy msgid "Show automatic regions" msgstr "Mostrar toda automatizacin" -#: editor_actions.cc:324 +#: editor_actions.cc:325 msgid "Ascending" msgstr "Ascendente" -#: editor_actions.cc:326 +#: editor_actions.cc:327 msgid "Descending" msgstr "Descendente" -#: editor_actions.cc:329 +#: editor_actions.cc:330 msgid "By Region Name" msgstr "Por Nombre de Regin" -#: editor_actions.cc:331 +#: editor_actions.cc:332 msgid "By Region Length" msgstr "Por Tamao de Regin" -#: editor_actions.cc:333 +#: editor_actions.cc:334 msgid "By Region Position" msgstr "Por Posicin de regin" -#: editor_actions.cc:335 +#: editor_actions.cc:336 msgid "By Region Timestamp" msgstr "Por fecha de Regin" -#: editor_actions.cc:337 +#: editor_actions.cc:338 msgid "By Region Start in File" msgstr "Por inicio de regin en archivo" -#: editor_actions.cc:339 +#: editor_actions.cc:340 msgid "By Region End in File" msgstr "Por fin de regin en archivo" -#: editor_actions.cc:341 +#: editor_actions.cc:342 msgid "By Source File Name" msgstr "Por nombre de archivo" -#: editor_actions.cc:343 +#: editor_actions.cc:344 msgid "By Source File Length" msgstr "Por tamao de archivo" -#: editor_actions.cc:345 +#: editor_actions.cc:346 msgid "By Source File Creation Date" msgstr "Por fecha de creacin" -#: editor_actions.cc:347 +#: editor_actions.cc:348 msgid "By Source Filesystem" msgstr "Por sistema de archivos" #. the next two are duplicate items with different names for use in two different contexts -#: editor_actions.cc:353 +#: editor_actions.cc:354 #, fuzzy msgid "Add External Audio" msgstr "Agregar a lista externa de regiones" -#: editor_actions.cc:355 +#: editor_actions.cc:356 #, fuzzy msgid "as Region(s)" msgstr "normalizar regiones" -#: editor_actions.cc:357 +#: editor_actions.cc:358 #, fuzzy msgid "as Tracks" msgstr "Pistas" -#: editor_actions.cc:359 +#: editor_actions.cc:360 #, fuzzy msgid "to Tracks" msgstr "Pistas" -#: editor_actions.cc:362 +#: editor_actions.cc:363 #, fuzzy msgid "Show Waveforms" msgstr "Mostrar onda de audio" -#: editor_actions.cc:363 +#: editor_actions.cc:364 #, fuzzy msgid "Show Waveforms While Recording" msgstr "Mostrar onda de audio" -#: editor_actions.cc:364 +#: editor_actions.cc:365 #, fuzzy msgid "Show Measures" msgstr "Mostrar l�eas de medida" -#: editor_actions.cc:377 editor_actions.cc:384 +#: editor_actions.cc:378 editor_actions.cc:385 msgid "Medium" msgstr "" -#: editor_actions.cc:379 +#: editor_actions.cc:380 #, fuzzy msgid "Faster" msgstr "Fades" -#: editor_actions.cc:385 +#: editor_actions.cc:386 msgid "Long" msgstr "" -#: editor_actions.cc:389 +#: editor_actions.cc:390 #, fuzzy msgid "Later is Higher" msgstr "Bajar regin una capa" -#: editor_actions.cc:390 +#: editor_actions.cc:391 #, fuzzy msgid "Most Recently Moved/Added is Higher" msgstr "Bajar regin una capa" -#: editor_actions.cc:391 +#: editor_actions.cc:392 #, fuzzy msgid "Most Recently Added is Higher" msgstr "Bajar regin una capa" @@ -3471,115 +3458,103 @@ msgstr "No puede importar un archivo a menos que abra o cree una sesin" msgid "Add existing audio to session" msgstr "Mostrar toda automatizacin" -#: editor_audio_import.cc:143 +#: editor_audio_import.cc:142 #, fuzzy msgid "ardour: importing %1" msgstr "ardour: exportar" -#: editor_audio_import.cc:147 +#: editor_audio_import.cc:146 msgid "Cancel Import" msgstr "Cancelar importacin" -#: editor_audio_import.cc:225 +#: editor_audio_import.cc:224 #, fuzzy msgid "Editor: cannot open file \"%1\", (%2)" msgstr "Editor: no se pudo abrir el archivo \"%1\" (%2)" -#: editor_audio_import.cc:233 +#: editor_audio_import.cc:232 #, fuzzy msgid "Cancel entire import" msgstr "Cancelar importacin" -#: editor_audio_import.cc:234 +#: editor_audio_import.cc:233 #, fuzzy msgid "Don't embed it" msgstr "No %1" -#: editor_audio_import.cc:235 +#: editor_audio_import.cc:234 msgid "Embed all without questions" msgstr "" -#: editor_audio_import.cc:240 +#: editor_audio_import.cc:239 #, fuzzy msgid "Embed it anyway" msgstr "Linquear de todas formas" -#: editor_audio_import.cc:243 +#: editor_audio_import.cc:242 #, fuzzy msgid "" "%1\n" "This audiofile's sample rate doesn't match the session sample rate!" msgstr "La frecuencia de muestreo de este archivo difiere de la de la sesin!" -#: editor_audio_import.cc:276 +#: editor_audio_import.cc:275 msgid "could not open %1" msgstr "no se pudo abrir %1" -#: editor_audio_import.cc:321 +#: editor_audio_import.cc:320 #, fuzzy msgid "insert sndfile" msgstr "Insertar archivo de audio externo" #. stuff for the verbose canvas cursor -#: editor_canvas.cc:117 +#: editor_canvas.cc:118 msgid "VerboseCanvasCursor" msgstr "" -#: editor_canvas.cc:285 -msgid "Start a new session\n" -msgstr "Iniciar una nueva sesin\n" - -#: editor_canvas.cc:285 -msgid "via Session menu" -msgstr "via men de Sesin" - -#: editor_canvas.cc:288 -msgid "FirstActionMessage" -msgstr "" - -#: editor_edit_groups.cc:52 mixer_ui.cc:732 +#: editor_edit_groups.cc:53 mixer_ui.cc:736 #, fuzzy msgid "Activate All" msgstr "Activar" -#: editor_edit_groups.cc:53 mixer_ui.cc:733 +#: editor_edit_groups.cc:54 mixer_ui.cc:737 #, fuzzy msgid "Disable All" msgstr "Desconectar" -#: editor_edit_groups.cc:55 mixer_ui.cc:735 +#: editor_edit_groups.cc:56 mixer_ui.cc:739 #, fuzzy msgid "Add group" msgstr "Sin grupo" -#: editor_edit_groups.cc:225 mixer_ui.cc:964 +#: editor_edit_groups.cc:229 mixer_ui.cc:970 #, fuzzy msgid "unnamed" msgstr "Renombrar" -#: editor_edit_groups.cc:252 mixer_ui.cc:830 +#: editor_edit_groups.cc:258 mixer_ui.cc:834 msgid "-all-" msgstr "-todo-" -#: editor_export_audio.cc:64 +#: editor_export_audio.cc:65 msgid "" "There is no selection to export.\n" "\n" "Select a selection using the range mouse mode" msgstr "" -#: editor_export_audio.cc:109 +#: editor_export_audio.cc:110 msgid "" "There are no ranges to export.\n" "\n" "Create 1 or more ranges by dragging the mouse in the range bar" msgstr "" -#: editor_imageframe.cc:624 editor_imageframe.cc:654 +#: editor_imageframe.cc:625 editor_imageframe.cc:655 msgid "programming error: no ImageFrameView selected" msgstr "" -#: editor_imageframe.cc:847 editor_imageframe.cc:869 +#: editor_imageframe.cc:848 editor_imageframe.cc:870 msgid "programming error: no MarkerView selected" msgstr "" @@ -3588,142 +3563,142 @@ msgstr "" msgid "mute region" msgstr "enmudecer a esta regin" -#: editor_keys.cc:45 +#: editor_keys.cc:46 #, fuzzy msgid "keyboard selection" msgstr "Separar Seleccin" -#: editor_markers.cc:291 editor_ops.cc:1227 editor_ops.cc:1240 -#: editor_ops.cc:1258 location_ui.cc:773 +#: editor_markers.cc:292 editor_ops.cc:1290 editor_ops.cc:1303 +#: editor_ops.cc:1321 location_ui.cc:774 msgid "add marker" msgstr "agregar marcador" -#: editor_markers.cc:306 editor_markers.cc:379 editor_markers.cc:551 -#: editor_markers.cc:569 editor_markers.cc:588 editor_markers.cc:607 -#: editor_markers.cc:637 editor_markers.cc:665 editor_markers.cc:693 -#: editor_markers.cc:731 editor_markers.cc:758 editor_markers.cc:781 -#: editor_markers.cc:800 editor_mouse.cc:1994 editor_mouse.cc:4237 +#: editor_markers.cc:307 editor_markers.cc:380 editor_markers.cc:552 +#: editor_markers.cc:570 editor_markers.cc:589 editor_markers.cc:608 +#: editor_markers.cc:638 editor_markers.cc:666 editor_markers.cc:694 +#: editor_markers.cc:732 editor_markers.cc:759 editor_markers.cc:782 +#: editor_markers.cc:801 editor_mouse.cc:2015 editor_mouse.cc:4275 msgid "programming error: marker canvas item has no marker object pointer!" msgstr "" -#: editor_markers.cc:330 location_ui.cc:655 +#: editor_markers.cc:331 location_ui.cc:656 msgid "remove marker" msgstr "quitar marcador" -#: editor_markers.cc:457 +#: editor_markers.cc:458 #, fuzzy msgid "Locate to Mark" msgstr "Localizar a" -#: editor_markers.cc:458 +#: editor_markers.cc:459 #, fuzzy msgid "Play from Mark" msgstr "Reproducir desde el principio" -#: editor_markers.cc:459 +#: editor_markers.cc:460 #, fuzzy msgid "Set Mark from Playhead" msgstr "Ubicar desde barra de reproduccin" -#: editor_markers.cc:463 +#: editor_markers.cc:464 #, fuzzy msgid "Rename Mark" msgstr "Renombrar" -#: editor_markers.cc:464 +#: editor_markers.cc:465 #, fuzzy msgid "Hide Mark" msgstr "Ocultar esta pista" -#: editor_markers.cc:465 +#: editor_markers.cc:466 #, fuzzy msgid "Remove Mark" msgstr "quitar marcador" -#: editor_markers.cc:478 editor_markers.cc:534 +#: editor_markers.cc:479 editor_markers.cc:535 #, fuzzy msgid "Locate to Range Mark" msgstr "Marcadores de localizacin" -#: editor_markers.cc:479 editor_markers.cc:535 +#: editor_markers.cc:480 editor_markers.cc:536 #, fuzzy msgid "Play from Range Mark" msgstr "Reproducir el intervalo cont�uamente" -#: editor_markers.cc:480 +#: editor_markers.cc:481 #, fuzzy msgid "Loop Range" msgstr "rango de reproduccin cont�ua" -#: editor_markers.cc:481 editor_markers.cc:536 +#: editor_markers.cc:482 editor_markers.cc:537 #, fuzzy msgid "Set Range Mark from Playhead" msgstr "Ubicar desde barra de reproduccin" -#: editor_markers.cc:482 editor_markers.cc:537 +#: editor_markers.cc:483 editor_markers.cc:538 #, fuzzy msgid "Set Range from Range Selection" msgstr "Reproducir seleccin" -#: editor_markers.cc:486 +#: editor_markers.cc:487 #, fuzzy msgid "Rename Range" msgstr "Renombrar" -#: editor_markers.cc:487 editor_markers.cc:539 +#: editor_markers.cc:488 editor_markers.cc:540 #, fuzzy msgid "Hide Range" msgstr "Agregar nueva regin" -#: editor_markers.cc:488 +#: editor_markers.cc:489 #, fuzzy msgid "Remove Range" msgstr "Quitar Campo" -#: editor_markers.cc:492 editor_markers.cc:541 +#: editor_markers.cc:493 editor_markers.cc:542 #, fuzzy msgid "Separate Regions in Range" msgstr "Nueva region a partir de seleccin" -#: editor_markers.cc:493 editor_markers.cc:542 +#: editor_markers.cc:494 editor_markers.cc:543 #, fuzzy msgid "Select All in Range" msgstr "Seleccionar todo dentro de pista" -#: editor_markers.cc:519 +#: editor_markers.cc:520 #, fuzzy msgid "Set Loop Range" msgstr "selecionar intervalo de reproduccin cont�ua" -#: editor_markers.cc:520 +#: editor_markers.cc:521 msgid "Set Punch Range" msgstr "Seleccionar intervalo de punch" -#: editor_markers.cc:814 +#: editor_markers.cc:815 #, fuzzy msgid "New Name:" msgstr "nuevo nombre: " -#: editor_markers.cc:817 +#: editor_markers.cc:818 msgid "ardour: rename mark" msgstr "ardour: renombrar marca" -#: editor_markers.cc:819 +#: editor_markers.cc:820 #, fuzzy msgid "ardour: rename range" msgstr "ardour: renombrar regin" -#: editor_markers.cc:839 +#: editor_markers.cc:840 #, fuzzy msgid "rename marker" msgstr "quitar marcador" -#: editor_markers.cc:864 +#: editor_markers.cc:865 #, fuzzy msgid "set loop range" msgstr "seleccionar rango de zoom" -#: editor_markers.cc:890 +#: editor_markers.cc:891 #, fuzzy msgid "set punch range" msgstr "Seleccionar intervalo actual" @@ -3732,423 +3707,429 @@ msgstr "Seleccionar intervalo actual" msgid "Editor::event_frame() used on unhandled event type %1" msgstr "" -#: editor_mouse.cc:1589 +#: editor_mouse.cc:313 +#, fuzzy +msgid "select on click" +msgstr "Usar como metrnomo" + +#: editor_mouse.cc:1590 msgid "programming error: start_grab called without drag item" msgstr "" -#: editor_mouse.cc:1793 +#: editor_mouse.cc:1814 #, fuzzy msgid "change fade in length" msgstr "editar fade in" -#: editor_mouse.cc:1811 +#: editor_mouse.cc:1832 msgid "programming error: fade out canvas item has no regionview data pointer!" msgstr "" -#: editor_mouse.cc:1885 +#: editor_mouse.cc:1906 #, fuzzy msgid "change fade out length" msgstr "agregar salida" -#: editor_mouse.cc:1904 +#: editor_mouse.cc:1925 msgid "programming error: cursor canvas item has no cursor data pointer!" msgstr "" -#: editor_mouse.cc:2119 +#: editor_mouse.cc:2142 #, fuzzy msgid "move marker" msgstr "quitar marcador" -#: editor_mouse.cc:2142 editor_mouse.cc:2173 editor_tempodisplay.cc:461 +#: editor_mouse.cc:2165 editor_mouse.cc:2196 editor_tempodisplay.cc:459 msgid "" "programming error: meter marker canvas item has no marker object pointer!" msgstr "" -#: editor_mouse.cc:2241 +#: editor_mouse.cc:2264 #, fuzzy msgid "copy meter mark" msgstr "quitar marcador" -#: editor_mouse.cc:2251 +#: editor_mouse.cc:2274 #, fuzzy msgid "move meter mark" msgstr "quitar marcador" -#: editor_mouse.cc:2266 editor_mouse.cc:2299 editor_tempodisplay.cc:327 -#: editor_tempodisplay.cc:411 editor_tempodisplay.cc:430 +#: editor_mouse.cc:2289 editor_mouse.cc:2322 editor_tempodisplay.cc:331 +#: editor_tempodisplay.cc:409 editor_tempodisplay.cc:428 msgid "" "programming error: tempo marker canvas item has no marker object pointer!" msgstr "" -#: editor_mouse.cc:2271 editor_mouse.cc:2304 editor_tempodisplay.cc:332 -#: editor_tempodisplay.cc:416 +#: editor_mouse.cc:2294 editor_mouse.cc:2327 editor_tempodisplay.cc:336 +#: editor_tempodisplay.cc:414 msgid "programming error: marker for tempo is not a tempo marker!" msgstr "" -#: editor_mouse.cc:2371 +#: editor_mouse.cc:2394 #, fuzzy msgid "copy tempo mark" msgstr "quitar marcador" -#: editor_mouse.cc:2381 +#: editor_mouse.cc:2404 #, fuzzy msgid "move tempo mark" msgstr "quitar marcador" -#: editor_mouse.cc:2395 editor_mouse.cc:2414 editor_mouse.cc:2427 +#: editor_mouse.cc:2418 editor_mouse.cc:2437 editor_mouse.cc:2450 msgid "" "programming error: control point canvas item has no control point object " "pointer!" msgstr "" -#: editor_mouse.cc:2525 +#: editor_mouse.cc:2555 msgid "programming error: line canvas item has no line pointer!" msgstr "" -#: editor_mouse.cc:2634 +#: editor_mouse.cc:2664 #, fuzzy msgid "move region(s)" msgstr "invertir regiones" -#. this is committed in the grab finished callback. -#: editor_mouse.cc:2646 -msgid "Drag region copy" -msgstr "" - -#: editor_mouse.cc:2758 +#: editor_mouse.cc:2727 #, fuzzy msgid "Drag region brush" msgstr "normalizar regiones" +#. don't copy again +#. this is committed in the grab finished callback. +#: editor_mouse.cc:2751 +msgid "Drag region copy" +msgstr "" + #. A selection grab currently creates two undo/redo operations, one for #. creating the new region and another for moving it. #. -#: editor_mouse.cc:3574 +#: editor_mouse.cc:3609 #, fuzzy msgid "selection grab" msgstr "Seleccin" -#: editor_mouse.cc:3615 +#: editor_mouse.cc:3650 #, fuzzy msgid "cancel selection" msgstr "Reproducir seleccin" -#: editor_mouse.cc:3722 +#: editor_mouse.cc:3760 #, fuzzy msgid "range selection" msgstr "Reproducir seleccin" -#: editor_mouse.cc:3738 +#: editor_mouse.cc:3776 #, fuzzy msgid "trim selection start" msgstr "Desde locacin" -#: editor_mouse.cc:3754 +#: editor_mouse.cc:3792 #, fuzzy msgid "trim selection end" msgstr "Desde locacin" -#: editor_mouse.cc:3771 +#: editor_mouse.cc:3809 #, fuzzy msgid "move selection" msgstr "Grabar seleccin" -#: editor_mouse.cc:4157 +#: editor_mouse.cc:4195 #, fuzzy msgid "Start point trim" msgstr "Desde principio hasta cursor de edicin" -#: editor_mouse.cc:4185 +#: editor_mouse.cc:4223 msgid "End point trim" msgstr "" -#: editor_mouse.cc:4224 +#: editor_mouse.cc:4262 msgid "trimmed region" msgstr "regin acortada" -#: editor_mouse.cc:4363 +#: editor_mouse.cc:4400 #, fuzzy msgid "new range marker" msgstr "agregar un marcador de regin" -#: editor_mouse.cc:4578 +#: editor_mouse.cc:4642 #, fuzzy msgid "select regions" msgstr "Reproducir regin seleccionada cont�uamente" -#: editor_mouse.cc:4607 +#: editor_mouse.cc:4671 msgid "Name for region:" msgstr "Nombre para regin:" -#: editor_mouse.cc:4671 +#: editor_mouse.cc:4735 msgid "timestretch" msgstr "" -#: editor_ops.cc:132 +#: editor_ops.cc:195 #, fuzzy msgid "split" msgstr "Separar" -#: editor_ops.cc:168 +#: editor_ops.cc:231 #, fuzzy msgid "remove region" msgstr "invertir regiones" -#: editor_ops.cc:187 +#: editor_ops.cc:250 msgid "" " This is destructive, will possibly delete audio files\n" "It cannot be undone\n" "Do you really want to destroy %1 ?" msgstr "" -#: editor_ops.cc:191 +#: editor_ops.cc:254 #, fuzzy msgid "these regions" msgstr "invertir regiones" -#: editor_ops.cc:191 +#: editor_ops.cc:254 #, fuzzy msgid "this region" msgstr "enmudecer a esta regin" -#: editor_ops.cc:193 editor_ops.cc:3229 route_ui.cc:700 -#: visual_time_axis.cc:277 +#: editor_ops.cc:256 editor_ops.cc:3318 route_ui.cc:707 +#: visual_time_axis.cc:278 #, fuzzy msgid "No, do nothing." msgstr "No, no hacer nada." -#: editor_ops.cc:196 +#: editor_ops.cc:259 #, fuzzy msgid "Yes, destroy them." msgstr "Si, eliminar." -#: editor_ops.cc:198 editor_ops.cc:3230 +#: editor_ops.cc:261 editor_ops.cc:3319 #, fuzzy msgid "Yes, destroy it." msgstr "Si, eliminar." -#: editor_ops.cc:289 editor_ops.cc:317 +#: editor_ops.cc:352 editor_ops.cc:380 #, fuzzy msgid "extend selection" msgstr "Separar Seleccin" -#: editor_ops.cc:333 editor_ops.cc:367 editor_ops.cc:411 editor_ops.cc:437 +#: editor_ops.cc:396 editor_ops.cc:430 editor_ops.cc:474 editor_ops.cc:500 msgid "nudge forward" msgstr "" -#: editor_ops.cc:501 +#: editor_ops.cc:564 msgid "build_region_boundary_cache called with snap_type = %1" msgstr "" -#: editor_ops.cc:1354 +#: editor_ops.cc:1420 #, fuzzy msgid "select all within" msgstr "Seleccionar todo" -#: editor_ops.cc:1380 +#: editor_ops.cc:1452 #, fuzzy msgid "set selection from region" msgstr "Nueva region a partir de seleccin" -#: editor_ops.cc:1413 +#: editor_ops.cc:1485 #, fuzzy msgid "set selection from range" msgstr "Nueva region a partir de seleccin" -#: editor_ops.cc:1443 +#: editor_ops.cc:1515 #, fuzzy msgid "select all from range" msgstr "seleccionar rango de zoom" -#: editor_ops.cc:1465 +#: editor_ops.cc:1537 #, fuzzy msgid "select all from punch" msgstr "Seleccionar todo" -#: editor_ops.cc:1487 +#: editor_ops.cc:1559 #, fuzzy msgid "select all from loop" msgstr "Seleccionar todo" -#: editor_ops.cc:1501 +#: editor_ops.cc:1573 #, fuzzy msgid "select all after cursor" msgstr "Desde principio hasta cursor de edicin" -#: editor_ops.cc:1506 +#: editor_ops.cc:1578 #, fuzzy msgid "select all before cursor" msgstr "Reproducir desde el cursor" -#: editor_ops.cc:1536 +#: editor_ops.cc:1608 #, fuzzy msgid "select all between cursors" msgstr "Reproducir desde el cursor" -#: editor_ops.cc:1667 +#: editor_ops.cc:1739 msgid "clear markers" msgstr "borrar marcadores" -#: editor_ops.cc:1679 +#: editor_ops.cc:1751 msgid "clear ranges" msgstr "borrar intervalos" -#: editor_ops.cc:1698 +#: editor_ops.cc:1770 msgid "clear locations" msgstr "borrar localizaciones" -#: editor_ops.cc:1748 +#: editor_ops.cc:1820 #, fuzzy msgid "insert dragged region" msgstr "Insertar Regin" -#: editor_ops.cc:1784 +#: editor_ops.cc:1856 #, fuzzy msgid "insert region" msgstr "Insertar Regin" -#: editor_ops.cc:1975 io_selector.cc:57 io_selector.cc:791 +#: editor_ops.cc:2047 io_selector.cc:58 io_selector.cc:792 msgid "OK" msgstr "OK" -#: editor_ops.cc:1982 +#: editor_ops.cc:2054 msgid "ardour: rename region" msgstr "ardour: renombrar regin" -#: editor_ops.cc:2205 editor_ops.cc:2254 +#: editor_ops.cc:2277 editor_ops.cc:2326 #, fuzzy msgid "separate" msgstr "Separar Regin" -#: editor_ops.cc:2316 +#: editor_ops.cc:2388 #, fuzzy msgid "trim to selection" msgstr "Desde locacin" -#: editor_ops.cc:2356 +#: editor_ops.cc:2428 msgid "region fill" msgstr "" -#: editor_ops.cc:2415 +#: editor_ops.cc:2487 #, fuzzy msgid "fill selection" msgstr "Reproducir seleccin cont�uamente" -#: editor_ops.cc:2436 +#: editor_ops.cc:2508 msgid "Programming error. that region doesn't cover that position" msgstr "" -#: editor_ops.cc:2439 +#: editor_ops.cc:2511 #, fuzzy msgid "set region sync position" msgstr "Regiones/posicin" -#: editor_ops.cc:2454 +#: editor_ops.cc:2526 msgid "Place the edit cursor at the desired sync point" msgstr "Coloque el cursor de edicin en el punto de sincron� deseado" -#: editor_ops.cc:2459 +#: editor_ops.cc:2531 #, fuzzy msgid "set sync from edit cursor" msgstr "Reproducir desde el cursor" -#: editor_ops.cc:2471 +#: editor_ops.cc:2543 #, fuzzy msgid "remove sync" msgstr "Remover punto de sincron�" -#: editor_ops.cc:2485 +#: editor_ops.cc:2557 #, fuzzy msgid "naturalize" msgstr "Normalizar" -#: editor_ops.cc:2549 +#: editor_ops.cc:2621 #, fuzzy msgid "align selection (relative)" msgstr "Alinear relativamente" -#: editor_ops.cc:2577 +#: editor_ops.cc:2649 #, fuzzy msgid "align selection" msgstr "Grabar seleccin" -#: editor_ops.cc:2589 +#: editor_ops.cc:2661 #, fuzzy msgid "align region" msgstr "normalizar regiones" -#: editor_ops.cc:2636 editor_ops.cc:2661 +#: editor_ops.cc:2708 editor_ops.cc:2733 #, fuzzy msgid "trim to edit" msgstr "Desde principio hasta cursor de edicin" -#: editor_ops.cc:2712 +#: editor_ops.cc:2784 #, fuzzy msgid "ardour: freeze" msgstr "ardour: renombrar regin" -#: editor_ops.cc:2717 +#: editor_ops.cc:2789 #, fuzzy msgid "Cancel Freeze" msgstr "Cancelar" -#: editor_ops.cc:2754 +#: editor_ops.cc:2826 #, fuzzy msgid "bounce range" msgstr "intervalo" -#: editor_ops.cc:2807 +#: editor_ops.cc:2879 #, fuzzy msgid "cut" msgstr "cortar" -#: editor_ops.cc:2810 +#: editor_ops.cc:2882 #, fuzzy msgid "copy" msgstr "copiar" -#: editor_ops.cc:2823 +#: editor_ops.cc:2895 #, fuzzy msgid " objects" msgstr "objetos" -#: editor_ops.cc:2849 +#: editor_ops.cc:2921 #, fuzzy msgid " range" msgstr "intervalo" -#: editor_ops.cc:3006 +#: editor_ops.cc:3078 #, fuzzy msgid "paste" msgstr "Pegar" -#: editor_ops.cc:3044 +#: editor_ops.cc:3116 #, fuzzy msgid "paste chunk" msgstr "Crear trecho" #. clear (below) will clear the argument list -#: editor_ops.cc:3085 +#: editor_ops.cc:3157 #, fuzzy msgid "duplicate region" msgstr "Reproducir regin seleccionada cont�uamente" -#: editor_ops.cc:3130 +#: editor_ops.cc:3202 #, fuzzy msgid "duplicate selection" msgstr "Grabar seleccin" -#: editor_ops.cc:3170 +#: editor_ops.cc:3259 #, fuzzy msgid "clear playlist" msgstr "Nombre a captura de sesin" -#: editor_ops.cc:3199 +#: editor_ops.cc:3288 #, fuzzy msgid "nudge track" msgstr "Ocultar esta pista" -#: editor_ops.cc:3226 +#: editor_ops.cc:3315 #, fuzzy msgid "" "Do you really want to destroy the last capture?\n" @@ -4157,173 +4138,170 @@ msgstr "" "Realmente desea quitar el bus \"%1\" ?\n" "(no podr�deshacer este cambio)" -#: editor_ops.cc:3254 +#: editor_ops.cc:3343 #, fuzzy msgid "normalize" msgstr "Normalizar" -#: editor_ops.cc:3301 +#: editor_ops.cc:3390 #, fuzzy msgid "reverse regions" msgstr "invertir regiones" -#: editor_region_list.cc:93 editor_region_list.cc:98 editor_region_list.cc:101 -#: location_ui.cc:55 +#: editor_region_list.cc:98 editor_region_list.cc:103 +#: editor_region_list.cc:106 location_ui.cc:56 #, fuzzy msgid "Hidden" msgstr "Oculto" #. added a new fresh one at the end -#: editor_route_list.cc:101 editor_route_list.cc:102 editor_route_list.cc:246 +#: editor_route_list.cc:102 editor_route_list.cc:103 editor_route_list.cc:247 msgid "editor" msgstr "editor" -#: editor_route_list.cc:309 mixer_ui.cc:695 +#: editor_route_list.cc:310 mixer_ui.cc:699 msgid "Show All" msgstr "Mostrar Todo" -#: editor_route_list.cc:310 mixer_ui.cc:696 +#: editor_route_list.cc:311 mixer_ui.cc:700 msgid "Hide All" msgstr "Ocultar Todo" -#: editor_route_list.cc:311 mixer_ui.cc:697 +#: editor_route_list.cc:312 mixer_ui.cc:701 #, fuzzy msgid "Show All Audio Tracks" msgstr "Mostrar todos los Buses" -#: editor_route_list.cc:312 mixer_ui.cc:698 +#: editor_route_list.cc:313 mixer_ui.cc:702 #, fuzzy msgid "Hide All Audio Tracks" msgstr "Ocultar todos los Buses" -#: editor_route_list.cc:313 mixer_ui.cc:699 +#: editor_route_list.cc:314 mixer_ui.cc:703 #, fuzzy msgid "Show All Audio Busses" msgstr "Mostrar todos los Buses" -#: editor_route_list.cc:314 mixer_ui.cc:700 +#: editor_route_list.cc:315 mixer_ui.cc:704 #, fuzzy msgid "Hide All Audio Busses" msgstr "Ocultar todos los Buses" -#: editor_rulers.cc:311 +#: editor_rulers.cc:312 #, fuzzy msgid "New location marker" msgstr "Nuevo marcador de localizacin" -#: editor_rulers.cc:312 +#: editor_rulers.cc:313 #, fuzzy msgid "Clear all locations" msgstr "Quitar todas las localizaciones" #. ruler_items.push_back (MenuElem (_("New Range"))); -#: editor_rulers.cc:317 +#: editor_rulers.cc:318 #, fuzzy msgid "Clear all ranges" msgstr "Quitar todas las selecciones" -#: editor_rulers.cc:326 +#: editor_rulers.cc:327 #, fuzzy msgid "New Tempo" msgstr "Nuevo tempo" -#: editor_rulers.cc:327 +#: editor_rulers.cc:328 #, fuzzy msgid "Clear tempo" msgstr "Resetear tempo" -#: editor_rulers.cc:332 +#: editor_rulers.cc:333 #, fuzzy msgid "New Meter" msgstr "Nuevo Medidor" -#: editor_rulers.cc:333 +#: editor_rulers.cc:334 #, fuzzy msgid "Clear meter" msgstr "Resetear Medidor" -#: editor_rulers.cc:341 +#: editor_rulers.cc:342 #, fuzzy msgid "Min:Secs" msgstr "Mins:Segs" -#: editor_selection_list.cc:110 +#: editor_selection_list.cc:108 #, fuzzy msgid "Name for Chunk:" msgstr "nombre para trecho" -#: editor_selection_list.cc:113 +#: editor_selection_list.cc:111 #, fuzzy msgid "Create Chunk" msgstr "Crear trecho" -#: editor_selection_list.cc:113 +#: editor_selection_list.cc:111 msgid "Forget it" msgstr "Olvidarlo" -#: editor_tempodisplay.cc:249 editor_tempodisplay.cc:289 +#: editor_tempodisplay.cc:253 editor_tempodisplay.cc:293 msgid "add" msgstr "agregar" -#: editor_tempodisplay.cc:271 +#: editor_tempodisplay.cc:275 #, fuzzy msgid "add tempo mark" msgstr "agregar un marcador de regin" -#: editor_tempodisplay.cc:311 +#: editor_tempodisplay.cc:315 #, fuzzy msgid "add meter mark" msgstr "agregar un marcador de regin" -#: editor_tempodisplay.cc:344 editor_tempodisplay.cc:375 +#: editor_tempodisplay.cc:348 editor_tempodisplay.cc:376 msgid "done" msgstr "listo" -#: editor_tempodisplay.cc:365 editor_tempodisplay.cc:396 +#: editor_tempodisplay.cc:366 editor_tempodisplay.cc:394 msgid "replace tempo mark" msgstr "" -#: editor_tempodisplay.cc:435 editor_tempodisplay.cc:466 +#: editor_tempodisplay.cc:433 editor_tempodisplay.cc:464 msgid "programming error: marker for meter is not a meter marker!" msgstr "" -#: editor_tempodisplay.cc:445 editor_tempodisplay.cc:478 +#: editor_tempodisplay.cc:443 editor_tempodisplay.cc:476 #, fuzzy msgid "remove tempo mark" msgstr "quitar marcador" -#: editor_timefx.cc:50 +#: editor_timefx.cc:51 msgid "Quick but Ugly" msgstr "R�ido pero pobre" -#: editor_timefx.cc:51 +#: editor_timefx.cc:52 msgid "Skip Anti-aliasing" msgstr "No usar Anti-aliasing" -#: editor_timefx.cc:53 -msgid "Stretch/Shrink it" -msgstr "Estirar/Encoger esto" - -#: editor_timefx.cc:57 +#: editor_timefx.cc:56 msgid "ardour: timestretch" msgstr "" -#: editor_timefx.cc:58 +#: editor_timefx.cc:57 msgid "TimeStretchDialog" msgstr "" -#: editor_timefx.cc:80 editor_timefx.cc:81 editor_timefx.cc:82 -#: editor_timefx.cc:83 +#: editor_timefx.cc:70 +msgid "Stretch/Shrink it" +msgstr "Estirar/Encoger esto" + +#: editor_timefx.cc:73 editor_timefx.cc:74 msgid "TimeStretchButton" msgstr "" -#: editor_timefx.cc:84 +#: editor_timefx.cc:75 msgid "TimeStretchProgress" msgstr "" -#. GTK2FIX -#. current_timestretch->close (); -#: editor_timefx.cc:153 +#: editor_timefx.cc:139 msgid "timestretch cannot be started - thread creation error" msgstr "" @@ -4457,7 +4435,7 @@ msgstr "" msgid "Export to File" msgstr "Exportar a CD" -#: export_dialog.cc:113 option_editor.cc:82 option_editor.cc:83 +#: export_dialog.cc:113 option_editor.cc:83 option_editor.cc:84 msgid "Browse" msgstr "Seleccionar" @@ -4473,7 +4451,8 @@ msgstr "ardour: exportar" msgid "ardour_export" msgstr "" -#: export_dialog.cc:139 export_dialog.cc:155 +#: export_dialog.cc:139 export_dialog.cc:155 mixer_strip.cc:124 +#: mixer_strip.cc:767 #, fuzzy msgid "Output" msgstr "Salidas" @@ -4512,147 +4491,75 @@ msgstr "" msgid "File already exists, do you want to overwrite it?" msgstr "" -#: export_dialog.cc:1159 export_range_markers_dialog.cc:154 +#: export_dialog.cc:1159 export_range_markers_dialog.cc:153 msgid "Cannot write file in: " msgstr "" #. warning dialog -#: export_range_markers_dialog.cc:136 +#: export_range_markers_dialog.cc:135 msgid "Please enter a valid target directory." msgstr "" -#: export_range_markers_dialog.cc:144 +#: export_range_markers_dialog.cc:143 msgid "" "Please select an existing target directory. Files\n" "are not allowed!" msgstr "" -#: gain_automation_time_axis.cc:61 +#: gain_automation_time_axis.cc:62 #, fuzzy msgid "add gain automation event" msgstr "agregar evento de automatizacin a " -#: gain_meter.cc:66 +#: gain_meter.cc:67 msgid "cannot find images for fader slider" msgstr "" -#: gain_meter.cc:73 +#: gain_meter.cc:74 msgid "cannot find images for fader rail" msgstr "" -#: gain_meter.cc:88 -msgid "dbFS" -msgstr "" - -#: gain_meter.cc:89 gain_meter.cc:143 gain_meter.cc:704 -msgid "pre" -msgstr "" - -#: gain_meter.cc:139 gain_meter.cc:700 -#, fuzzy -msgid "input" -msgstr "%1 entrada" - -#: gain_meter.cc:147 gain_meter.cc:708 -#, fuzzy -msgid "post" -msgstr "conector" - -#. TRANSLATORS: this string should be longest of the strings -#. used to describe meter points. In english, its "input". -#. -#: gain_meter.cc:155 -msgid "tupni" -msgstr "" - -#: gain_meter.cc:174 gain_meter.cc:458 gain_meter.cc:480 gain_meter.cc:525 +#: gain_meter.cc:130 gain_meter.cc:339 gain_meter.cc:494 gain_meter.cc:539 #, fuzzy msgid "-inf" msgstr "entrada" -#: glade/new_session_dialog.glade.h:1 +#: gain_meter.cc:140 #, fuzzy -msgid "Advanced" -msgstr "Avanzado..." +msgid "Fader automation mode" +msgstr "modo de automatizacin de balance" -#: glade/new_session_dialog.glade.h:2 -msgid "Input" +#: gain_meter.cc:141 +#, fuzzy +msgid "Fader automation type" +msgstr "estado de automatizacin de balance" + +#. XXX it might different in different languages +#: gain_meter.cc:182 gain_meter.cc:817 panner_ui.cc:99 panner_ui.cc:807 +msgid "Abs" msgstr "" -#: glade/new_session_dialog.glade.h:3 +#: gain_meter.cc:472 #, fuzzy -msgid "Output" -msgstr "Salidas" +msgid "-Inf" +msgstr "entrada" -#: glade/new_session_dialog.glade.h:4 +#: gain_meter.cc:781 mixer_strip.cc:770 panner_ui.cc:771 #, fuzzy -msgid "Automatically connect inputs" -msgstr "conectar autom�icamente entradas de pistas a entradas f�icas" +msgid "O" +msgstr "O" -#: glade/new_session_dialog.glade.h:5 -#, fuzzy -msgid "Automatically connect outputs" -msgstr "conectar pistas manualmente" - -#: glade/new_session_dialog.glade.h:6 -#, fuzzy -msgid "Channel Count" -msgstr "Cancelar importacin" - -#: glade/new_session_dialog.glade.h:7 -msgid "Connect to Master Bus" +#: gain_meter.cc:784 panner_ui.cc:774 +msgid "P" msgstr "" -#: glade/new_session_dialog.glade.h:8 -msgid "Connect to physical outputs" +#: gain_meter.cc:787 panner_ui.cc:777 +msgid "T" msgstr "" -#: glade/new_session_dialog.glade.h:9 -#, fuzzy -msgid "Create Control Bus" -msgstr "Control de Salidas" - -#: glade/new_session_dialog.glade.h:10 -#, fuzzy -msgid "Create Master Bus" -msgstr "usar salidas Master" - -#: glade/new_session_dialog.glade.h:11 -#, fuzzy -msgid "New Session" -msgstr "Sesin" - -# -#: glade/new_session_dialog.glade.h:12 -#, fuzzy -msgid "Open Recent Session" -msgstr "Abrir sesin" - -# -#: glade/new_session_dialog.glade.h:13 -#, fuzzy -msgid "Open Session" -msgstr "Abrir sesin" - -#: glade/new_session_dialog.glade.h:14 -#, fuzzy -msgid "Port limit" -msgstr "Olvidarlo" - -#: glade/new_session_dialog.glade.h:15 -#, fuzzy -msgid "Select a File" -msgstr "Seleccionar todo" - -#: glade/new_session_dialog.glade.h:16 -#, fuzzy -msgid "Select a Session" -msgstr "Reproducir regin seleccionada cont�uamente" - -#: glade/new_session_dialog.glade.h:17 -#, fuzzy -msgid "Track/Bus connection options" -msgstr "Pistas/Buses" +#: gain_meter.cc:790 panner_ui.cc:780 +msgid "W" +msgstr "" #: gtk-custom-ruler.c:126 #, fuzzy @@ -4699,240 +4606,240 @@ msgid "Draw current ruler position" msgstr "" #. end-of-file, other end closed or shutdown? -#: imageframe_socket_handler.cc:126 +#: imageframe_socket_handler.cc:127 msgid "Image Compositor Socket has been shutdown/closed" msgstr "Se desconect al Compositor de Imagen" -#: imageframe_time_axis.cc:287 +#: imageframe_time_axis.cc:286 #, fuzzy msgid "0.5 seconds" msgstr "Minutos:Segundos" -#: imageframe_time_axis.cc:288 marker_time_axis.cc:241 +#: imageframe_time_axis.cc:287 marker_time_axis.cc:242 #, fuzzy msgid "1 seconds" msgstr "Minutos:Segundos" -#: imageframe_time_axis.cc:289 marker_time_axis.cc:242 +#: imageframe_time_axis.cc:288 marker_time_axis.cc:243 #, fuzzy msgid "1.5 seconds" msgstr "Minutos:Segundos" -#: imageframe_time_axis.cc:290 marker_time_axis.cc:243 +#: imageframe_time_axis.cc:289 marker_time_axis.cc:244 #, fuzzy msgid "2 seconds" msgstr "Minutos:Segundos" -#: imageframe_time_axis.cc:291 marker_time_axis.cc:244 +#: imageframe_time_axis.cc:290 marker_time_axis.cc:245 #, fuzzy msgid "2.5 seconds" msgstr "Minutos:Segundos" -#: imageframe_time_axis.cc:292 marker_time_axis.cc:245 +#: imageframe_time_axis.cc:291 marker_time_axis.cc:246 #, fuzzy msgid "3 seconds" msgstr "Minutos:Segundos" #. duration_items.push_back(SeparatorElem()) ; #. duration_items.push_back(MenuElem (_("custom"), mem_fun(*this, &ImageFrameTimeAxis::set_marker_duration_custom))) ; -#: imageframe_time_axis.cc:297 marker_time_axis.cc:250 +#: imageframe_time_axis.cc:296 marker_time_axis.cc:251 #, fuzzy msgid "Duration (sec)" msgstr "normalizar regiones" -#: imageframe_time_axis.cc:302 +#: imageframe_time_axis.cc:301 #, fuzzy msgid "Remove Frame" msgstr "Quitar Campo" -#: imageframe_time_axis.cc:305 +#: imageframe_time_axis.cc:304 #, fuzzy msgid "Image Frame" msgstr "Cuadros" -#: imageframe_time_axis.cc:306 marker_time_axis.cc:256 +#: imageframe_time_axis.cc:305 marker_time_axis.cc:257 #, fuzzy msgid "Rename Track" msgstr "Renombrar" -#: io_selector.cc:59 io_selector.cc:793 +#: io_selector.cc:60 io_selector.cc:794 #, fuzzy msgid "Rescan" msgstr "buscar de nuevo" -#: io_selector.cc:67 +#: io_selector.cc:68 msgid "%1 input" msgstr "%1 entrada" -#: io_selector.cc:69 +#: io_selector.cc:70 msgid "%1 output" msgstr "%1 salida" -#: io_selector.cc:141 route_params_ui.cc:106 +#: io_selector.cc:142 route_params_ui.cc:107 msgid "Inputs" msgstr "Entradas" -#: io_selector.cc:141 route_params_ui.cc:107 +#: io_selector.cc:142 route_params_ui.cc:108 msgid "Outputs" msgstr "Salidas" -#: io_selector.cc:142 +#: io_selector.cc:143 #, fuzzy msgid "Add Input" msgstr "agregar entrada" -#: io_selector.cc:142 +#: io_selector.cc:143 #, fuzzy msgid "Add Output" msgstr "agregar salida" -#: io_selector.cc:143 +#: io_selector.cc:144 #, fuzzy msgid "Remove Input" msgstr "Remover punto de sincron�" -#: io_selector.cc:143 +#: io_selector.cc:144 #, fuzzy msgid "Remove Output" msgstr "# Salidas" -#: io_selector.cc:144 +#: io_selector.cc:145 #, fuzzy msgid "Disconnect All" msgstr "Desconectar" -#: io_selector.cc:158 +#: io_selector.cc:159 msgid "Available connections" msgstr "Conecciones disponibles" -#: io_selector.cc:554 io_selector.cc:573 +#: io_selector.cc:555 io_selector.cc:574 msgid "There are no more JACK ports available." msgstr "" -#: io_selector.cc:648 io_selector.cc:675 io_selector.cc:728 +#: io_selector.cc:649 io_selector.cc:676 io_selector.cc:729 msgid "port" msgstr "conector" -#: io_selector.cc:797 +#: io_selector.cc:798 msgid "ardour: " msgstr "" -#: keyboard.cc:297 +#: keyboard.cc:299 msgid "KeyboardTarget: keyname \"%1\" is unknown." msgstr "" -#: keyboard.cc:523 +#: keyboard.cc:525 msgid "" "Your system is completely broken - NumLock uses \"%1\"as its modifier. This " "is madness - see the man page for xmodmap to find out how to fix this." msgstr "" -#: keyboard.cc:531 +#: keyboard.cc:533 msgid "" "Your system generates \"%1\" when the NumLock key is pressed. This can cause " "problems when editing so Ardour will use %2 to mean Meta rather than %1" msgstr "" -#: keyboard.cc:592 +#: keyboard.cc:594 msgid "You have %1 keys bound to \"mod1\"" msgstr "Tiene %1 teclas asignadas a \"mod1\"" -#: keyboard.cc:607 +#: keyboard.cc:609 msgid "You have %1 keys bound to \"mod2\"" msgstr "Tiene %1 teclas asignadas a \"mod2\"" -#: keyboard.cc:622 +#: keyboard.cc:624 msgid "You have %1 keys bound to \"mod3\"" msgstr "Tiene %1 teclas asignadas a \"mod3\"" -#: keyboard.cc:637 +#: keyboard.cc:639 msgid "You have %1 keys bound to \"mod4\"" msgstr "Tiene %1 teclas asignadas a \"mod4\"" -#: keyboard.cc:652 +#: keyboard.cc:654 msgid "You have %1 keys bound to \"mod5\"" msgstr "Tiene %1 teclas asignadas a \"mod5\"" -#: location_ui.cc:47 location_ui.cc:50 +#: location_ui.cc:48 location_ui.cc:51 #, fuzzy msgid "Set" msgstr "Selecionar" -#: location_ui.cc:48 location_ui.cc:51 +#: location_ui.cc:49 location_ui.cc:52 msgid "Go" msgstr "" -#: location_ui.cc:54 +#: location_ui.cc:55 msgid "CD" msgstr "CD" -#: location_ui.cc:57 +#: location_ui.cc:58 msgid "SCMS" msgstr "" -#: location_ui.cc:58 +#: location_ui.cc:59 msgid "Pre-Emphasis" msgstr "" -#: location_ui.cc:569 +#: location_ui.cc:570 #, fuzzy msgid "Add New Location" msgstr "Agregar nueva localizacin" -#: location_ui.cc:570 +#: location_ui.cc:571 msgid "Add New Range" msgstr "Agregar nueva regin" -#: location_ui.cc:574 +#: location_ui.cc:575 msgid "ardour: locations" msgstr "ardour: localizaciones" -#: location_ui.cc:575 +#: location_ui.cc:576 msgid "ardour_locations" msgstr "" -#: location_ui.cc:603 +#: location_ui.cc:604 #, fuzzy msgid "Location (CD Index) Markers" msgstr "Marcadores de localizacin" -#: location_ui.cc:623 +#: location_ui.cc:624 #, fuzzy msgid "Range (CD Track) Markers" msgstr "Marcadores de intervalo" -#: location_ui.cc:789 +#: location_ui.cc:790 #, fuzzy msgid "add range marker" msgstr "agregar un marcador de regin" -#: main.cc:71 +#: main.cc:72 msgid "ardour is killing itself for a clean exit\n" msgstr "ardour se est�cerrando limpiamente\n" -#: main.cc:80 +#: main.cc:81 msgid "stopping user interface\n" msgstr "deteniendo interfase visual\n" #. XXX its doubtful that snprintf() is async-safe -#: main.cc:99 +#: main.cc:100 #, c-format msgid "%d(%d): received signal %d\n" msgstr "" -#: main.cc:185 +#: main.cc:186 msgid "cannot become new process group leader (%1)" msgstr "" -#: main.cc:212 +#: main.cc:213 msgid "cannot setup signal handling for %1" msgstr "" -#: main.cc:223 +#: main.cc:224 msgid "cannot set default signal mask (%1)" msgstr "" -#: main.cc:253 +#: main.cc:254 #, fuzzy msgid "" "Without a UI style file, ardour will look strange.\n" @@ -4941,12 +4848,12 @@ msgstr "" "Sin un archivo de interfase visual, Ardour no se \n" "ver�correctamente. Apunte ARDOUR_UI_RC a un archivo v�ido" -#: main.cc:273 +#: main.cc:276 #, fuzzy msgid "Ardour could not connect to JACK." msgstr "No se pudo conectar a JACK con el nombre \"%1\"" -#: main.cc:277 +#: main.cc:280 #, fuzzy msgid "" "There are several possible reasons:\n" @@ -4966,70 +4873,12 @@ msgstr "" "\n" "Considere estas posibilidades y o reinicie a JACK.\n" -#: main.cc:324 -msgid "Ardour/GTK " -msgstr "" - -#: main.cc:326 -msgid "" -"\n" -" (built using " -msgstr "" - -#: main.cc:330 -#, fuzzy -msgid " with libardour " -msgstr " corriendo con libardour " - -#: main.cc:335 -msgid " and GCC version " -msgstr "" - -#: main.cc:345 -msgid "Copyright (C) 1999-2005 Paul Davis" -msgstr "" - -#: main.cc:346 -msgid "" -"Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " -"Baker" -msgstr "" - -#: main.cc:348 -msgid "Ardour comes with ABSOLUTELY NO WARRANTY" -msgstr "Ardour no ofrece ningn tipo de garant�" - -#: main.cc:349 -msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." -msgstr "" - -#: main.cc:350 -msgid "This is free software, and you are welcome to redistribute it " -msgstr "Este software es gratuito.Usted puede distribuirlo " - -#: main.cc:351 -#, fuzzy -msgid "under certain conditions; see the source for copying conditions." -msgstr "bajo ciertas condiciones; lea el archivo COPYING para m� detalles" - -#: main.cc:360 -msgid "could not create ARDOUR GUI" -msgstr "no se pudo crear la interfase visual de Ardour" - -#: main.cc:378 -msgid "Could not connect to JACK server as \"%1\"" -msgstr "No se pudo conectar a JACK con el nombre \"%1\"" - -#: main.cc:381 -msgid "could not initialize Ardour." -msgstr "no se pudo iniciar a Ardour." - -#: main.cc:392 +#: main.cc:310 msgid "could not load command line session \"%1\"" msgstr "no se pudo cargar desde l�ea de comando a la sesin \"%1\"" #. it wasn't new, but we require a new session -#: main.cc:412 +#: main.cc:330 msgid "" "\n" "\n" @@ -5037,7 +4886,7 @@ msgid "" "To avoid this message, start ardour as \"ardour %1" msgstr "" -#: main.cc:423 +#: main.cc:341 msgid "" "\n" "\n" @@ -5045,306 +4894,448 @@ msgid "" "To create it from the command line, start ardour as \"ardour --new %1" msgstr "" +#: main.cc:405 +msgid "Ardour/GTK " +msgstr "" + +#: main.cc:407 +msgid "" +"\n" +" (built using " +msgstr "" + +#: main.cc:411 +#, fuzzy +msgid " with libardour " +msgstr " corriendo con libardour " + +#: main.cc:416 +msgid " and GCC version " +msgstr "" + +#: main.cc:426 +msgid "Copyright (C) 1999-2006 Paul Davis" +msgstr "" + +#: main.cc:427 +msgid "" +"Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " +"Baker" +msgstr "" + +#: main.cc:429 +msgid "Ardour comes with ABSOLUTELY NO WARRANTY" +msgstr "Ardour no ofrece ningn tipo de garant�" + +#: main.cc:430 +msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." +msgstr "" + +#: main.cc:431 +msgid "This is free software, and you are welcome to redistribute it " +msgstr "Este software es gratuito.Usted puede distribuirlo " + +#: main.cc:432 +#, fuzzy +msgid "under certain conditions; see the source for copying conditions." +msgstr "bajo ciertas condiciones; lea el archivo COPYING para m� detalles" + +#: main.cc:441 +msgid "could not create ARDOUR GUI" +msgstr "no se pudo crear la interfase visual de Ardour" + +#: main.cc:459 +msgid "Could not connect to JACK server as \"%1\"" +msgstr "No se pudo conectar a JACK con el nombre \"%1\"" + +#: main.cc:462 +msgid "could not initialize Ardour." +msgstr "no se pudo iniciar a Ardour." + #: marker.cc:244 #, fuzzy msgid "MarkerText" msgstr "Marcas" -#: marker_time_axis.cc:253 +#: marker_time_axis.cc:254 #, fuzzy msgid "Remove Marker" msgstr "quitar marcador" -#: marker_time_axis.cc:255 +#: marker_time_axis.cc:256 #, fuzzy msgid "Marker" msgstr "Marcas" -#: meter_bridge.cc:77 +#: meter_bridge.cc:78 msgid "ardour: meter bridge" msgstr "ardour: vmetro" -#: meter_bridge.cc:78 +#: meter_bridge.cc:79 msgid "ardour_meter_bridge" msgstr "" -#: meter_bridge_strip.cc:79 meter_bridge_strip.cc:93 +#: meter_bridge_strip.cc:80 meter_bridge_strip.cc:94 #, c-format msgid "# of %u-sample overs" msgstr "" -#: meter_bridge_strip.cc:221 +#: meter_bridge_strip.cc:222 #, fuzzy msgid "New Name for Meter:" msgstr "Nuevo nombre para vmetro" -#: mixer_strip.cc:85 mixer_strip.cc:437 region_editor.cc:46 -msgid "mute" -msgstr "mudo" +#: mixer_strip.cc:95 mixer_strip.cc:140 mixer_strip.cc:1227 +msgid "pre" +msgstr "" -#: mixer_strip.cc:85 mixer_strip.cc:438 -msgid "solo" -msgstr "solo" - -#: mixer_strip.cc:85 mixer_strip.cc:436 -msgid "RECORD" -msgstr "GRABAR" - -#: mixer_strip.cc:96 mixer_strip.cc:441 mixer_strip.cc:1064 +#: mixer_strip.cc:96 mixer_strip.cc:822 msgid "Comments" msgstr "" -#: mixer_strip.cc:120 mixer_strip.cc:752 -msgid "INPUT" -msgstr "ENTRADA" - -#: mixer_strip.cc:125 mixer_strip.cc:773 -msgid "OUTPUT" -msgstr "SALIDA" - -#: mixer_strip.cc:140 +#: mixer_strip.cc:119 #, fuzzy -msgid "Pan automation mode" -msgstr "modo de automatizacin de balance" +msgid "Input" +msgstr "Entradas" -#: mixer_strip.cc:141 +#: mixer_strip.cc:136 mixer_strip.cc:1223 #, fuzzy -msgid "Gain automation mode" -msgstr "modo de automatizacin de volumen" +msgid "input" +msgstr "%1 entrada" -#: mixer_strip.cc:143 +#: mixer_strip.cc:144 mixer_strip.cc:1231 #, fuzzy -msgid "Pan automation type" -msgstr "estado de automatizacin de balance" +msgid "post" +msgstr "conector" -#: mixer_strip.cc:144 -#, fuzzy -msgid "Gain automation type" -msgstr "estado de automatizacin de volumen" - -#: mixer_strip.cc:183 mixer_strip.cc:195 mixer_strip.cc:913 -#, fuzzy -msgid "trim" -msgstr "cortar" - -#. XXX it might different in different languages -#: mixer_strip.cc:184 mixer_strip.cc:196 mixer_strip.cc:917 -msgid "abs" +#. TRANSLATORS: this string should be longest of the strings +#. used to describe meter points. In english, its "input". +#. +#: mixer_strip.cc:152 +msgid "tupni" msgstr "" -#: mixer_strip.cc:203 +#: mixer_strip.cc:207 #, fuzzy -msgid "gain automation mode" -msgstr "modo de automatizacin de volumen" - -#: mixer_strip.cc:204 -#, fuzzy -msgid "pan automation mode" -msgstr "modo de automatizacin de balance" - -#: mixer_strip.cc:205 -#, fuzzy -msgid "gain automation state" -msgstr "estado de automatizacin de volumen" - -#: mixer_strip.cc:206 -#, fuzzy -msgid "pan automation state" -msgstr "estado de automatizacin de balance" - -#: mixer_strip.cc:223 -msgid "varispeed" +msgid "Varispeed" msgstr "velocidad" -#: mixer_strip.cc:245 mixer_strip.cc:1078 +#: mixer_strip.cc:233 mixer_strip.cc:836 msgid "Click to Add/Edit Comments" msgstr "" -#: mixer_strip.cc:393 +#: mixer_strip.cc:374 msgid "unknown strip width \"%1\" in XML GUI information" msgstr "" -#: mixer_strip.cc:443 mixer_strip.cc:1062 -msgid "*Comments*" +#: mixer_strip.cc:417 +#, fuzzy +msgid "record" +msgstr "Grabar" + +#: mixer_strip.cc:418 region_editor.cc:47 +msgid "mute" +msgstr "mudo" + +#: mixer_strip.cc:419 +msgid "solo" +msgstr "solo" + +#: mixer_strip.cc:422 +msgid "comments" msgstr "" -#: mixer_strip.cc:457 -msgid "REC" +#: mixer_strip.cc:424 +msgid "*comments*" msgstr "" -#: mixer_strip.cc:462 mixer_strip.cc:1072 +#: mixer_strip.cc:438 +#, fuzzy +msgid "Rec" +msgstr "buscar de nuevo" + +#: mixer_strip.cc:439 +msgid "M" +msgstr "" + +#: mixer_strip.cc:440 +msgid "S" +msgstr "" + +#: mixer_strip.cc:443 mixer_strip.cc:830 #, fuzzy msgid "Cmt" msgstr "cortar" -#: mixer_strip.cc:464 mixer_strip.cc:1070 +#: mixer_strip.cc:445 mixer_strip.cc:828 msgid "*Cmt*" msgstr "" -#: mixer_strip.cc:503 mixer_strip.cc:562 redirect_box.cc:1004 +#: mixer_strip.cc:483 mixer_strip.cc:549 redirect_box.cc:1006 msgid "Not connected to JACK - no I/O changes are possible" msgstr "" -#: mixer_strip.cc:569 +#: mixer_strip.cc:560 msgid "Track" msgstr "Pista" -#: mixer_strip.cc:593 mixer_strip.cc:609 +#: mixer_strip.cc:588 mixer_strip.cc:604 msgid "could not register new ports required for that connection" msgstr "" -#: mixer_strip.cc:755 -msgid "IN" +#: mixer_strip.cc:747 +#, fuzzy +msgid " Input" +msgstr "# Entradas" + +#: mixer_strip.cc:750 +#, fuzzy +msgid "I" msgstr "ENTRADA" -#: mixer_strip.cc:776 -msgid "OUT" -msgstr "SALIDA" - -#: mixer_strip.cc:884 -msgid "aplay" +#: mixer_strip.cc:820 +msgid "*Comments*" msgstr "" -#: mixer_strip.cc:890 -msgid "awrite" -msgstr "" - -#: mixer_strip.cc:1095 +#: mixer_strip.cc:859 #, fuzzy msgid ": comment editor" msgstr "no se pudo iniciar el editor" -#: mixer_strip.cc:1157 mixer_strip.cc:1178 -msgid "no group" -msgstr "sin grupo" +#: mixer_strip.cc:953 +msgid "Grp" +msgstr "" -#: mixer_strip.cc:1181 +#: mixer_strip.cc:956 msgid "~G" msgstr "" -#: mixer_strip.cc:1229 +#: mixer_strip.cc:1004 #, fuzzy msgid "Invert Polarity" msgstr "polaridad" -#: mixer_ui.cc:84 +#: mixer_ui.cc:85 msgid "Strips" msgstr "Pistas" -#: mixer_ui.cc:108 -msgid "groupname" -msgstr "" +#: mixer_ui.cc:110 +#, fuzzy +msgid "Group" +msgstr "Grupos de Mixer" -#: mixer_ui.cc:109 region_editor.cc:48 region_editor.cc:191 -#: region_editor.cc:225 -msgid "active" -msgstr "activo" - -#: mixer_ui.cc:110 region_editor.cc:49 -msgid "visible" -msgstr "visible" - -#: mixer_ui.cc:207 mixer_ui.cc:366 +#: mixer_ui.cc:211 mixer_ui.cc:370 msgid "ardour: mixer" msgstr "" -#: mixer_ui.cc:208 +#: mixer_ui.cc:212 msgid "ardour_mixer" msgstr "ardour_mixer" -#: mixer_ui.cc:342 +#: mixer_ui.cc:346 msgid "ardour: mixer: " msgstr "" -#: mixer_ui.cc:569 +#: mixer_ui.cc:573 msgid "signal" msgstr "seal" -#: mixer_ui.cc:719 +#: mixer_ui.cc:723 msgid "track display list item for renamed strip not found!" msgstr "" -#: option_editor.cc:75 +# +#: new_session_dialog.cc:39 +#, fuzzy +msgid "New Session Name :" +msgstr "Nombre de sesin:" + +#: new_session_dialog.cc:41 +msgid "Create Session Directory In :" +msgstr "" + +#: new_session_dialog.cc:43 +#, fuzzy +msgid "Use Session Template :" +msgstr "usar esquema existente" + +#: new_session_dialog.cc:45 +#, fuzzy +msgid "Channel Count" +msgstr "Cancelar importacin" + +#: new_session_dialog.cc:46 +#, fuzzy +msgid "Create Monitor Bus" +msgstr "Control de Salidas" + +#: new_session_dialog.cc:53 +#, fuzzy +msgid "Create Master Bus" +msgstr "usar salidas Master" + +#: new_session_dialog.cc:55 +#, fuzzy +msgid "Automatically Connect Inputs" +msgstr "conectar autom�icamente entradas de pistas a entradas f�icas" + +#: new_session_dialog.cc:56 new_session_dialog.cc:67 +#, fuzzy +msgid "Port Limit" +msgstr "Olvidarlo" + +#: new_session_dialog.cc:64 +#, fuzzy +msgid "Track/Bus Inputs" +msgstr "Pistas/Buses" + +#: new_session_dialog.cc:66 +#, fuzzy +msgid "Automatically Connect Outputs" +msgstr "conectar pistas manualmente" + +#: new_session_dialog.cc:75 +msgid "Connect to Master Bus" +msgstr "" + +#: new_session_dialog.cc:76 +msgid "Connect to Physical Outputs" +msgstr "" + +#: new_session_dialog.cc:80 +#, fuzzy +msgid "Track/Bus Outputs" +msgstr "Salidas" + +#: new_session_dialog.cc:83 +#, fuzzy +msgid "Advanced Options" +msgstr "Opciones Editor" + +# +#: new_session_dialog.cc:91 +#, fuzzy +msgid "Open Recent Session" +msgstr "Abrir sesin" + +# +#: new_session_dialog.cc:127 +#, fuzzy +msgid "Open Session File :" +msgstr "Abrir sesin" + +#: new_session_dialog.cc:274 +#, fuzzy +msgid "New Session" +msgstr "Sesin" + +# +#: new_session_dialog.cc:276 +#, fuzzy +msgid "Open Session" +msgstr "Abrir sesin" + +#: new_session_dialog.cc:281 +#, fuzzy +msgid "ardour: session control" +msgstr "ardour: guardar sesin?" + +#: new_session_dialog.cc:310 +#, fuzzy +msgid "select template" +msgstr "-esquema" + +#: new_session_dialog.cc:316 +#, fuzzy +msgid "select session file" +msgstr "Reproducir regin seleccionada cont�uamente" + +#: new_session_dialog.cc:325 +#, fuzzy +msgid "select directory" +msgstr "Reproducir regin seleccionada cont�uamente" + +#: option_editor.cc:76 msgid "SMPTE offset is negative" msgstr "" -#: option_editor.cc:101 +#: option_editor.cc:102 msgid "ardour: options editor" msgstr "ardour: opciones editor" -#: option_editor.cc:102 +#: option_editor.cc:103 msgid "ardour_option_editor" msgstr "" -#: option_editor.cc:126 +#: option_editor.cc:127 msgid "Paths/Files" msgstr "Carpetas/Archivos" -#: option_editor.cc:127 +#: option_editor.cc:128 msgid "Kbd/Mouse" msgstr "Teclado/Mouse" -#: option_editor.cc:130 +#: option_editor.cc:131 msgid "Layers & Fades" msgstr "" -#: option_editor.cc:134 +#: option_editor.cc:135 msgid "MIDI" msgstr "MIDI" -#: option_editor.cc:176 +#: option_editor.cc:177 msgid "24 FPS" msgstr "" -#: option_editor.cc:178 +#: option_editor.cc:179 msgid "25 FPS" msgstr "" -#: option_editor.cc:180 +#: option_editor.cc:181 msgid "30 FPS" msgstr "" -#: option_editor.cc:186 +#: option_editor.cc:187 msgid "30 FPS drop" msgstr "" -#: option_editor.cc:243 +#: option_editor.cc:244 msgid "session RAID path" msgstr "ubicacin de archivos de sesin" -#: option_editor.cc:248 +#: option_editor.cc:249 #, fuzzy msgid "Soundfile Search Paths" msgstr "Biblioteca de audio" -#: option_editor.cc:253 +#: option_editor.cc:254 #, fuzzy msgid "Paths" msgstr "Carpetas/Archivos" -#: option_editor.cc:267 option_editor.cc:273 option_editor.cc:724 -#: option_editor.cc:751 +#: option_editor.cc:268 option_editor.cc:274 option_editor.cc:723 +#: option_editor.cc:750 msgid "internal" msgstr "interno" -#: option_editor.cc:286 +#: option_editor.cc:287 msgid "Short crossfade length (msecs)" msgstr "" -#: option_editor.cc:298 +#: option_editor.cc:299 msgid "Destructive crossfade length (msecs)" msgstr "" -#: option_editor.cc:366 +#: option_editor.cc:367 msgid "SMPTE Frames/second" msgstr "SMPTE Cuadros/segundo" -#: option_editor.cc:367 +#: option_editor.cc:368 msgid "SMPTE Offset" msgstr "" -#: option_editor.cc:461 option_editor.cc:468 option_editor.cc:471 -#: option_editor.cc:617 +#: option_editor.cc:462 option_editor.cc:469 option_editor.cc:472 +#: option_editor.cc:618 #, fuzzy msgid "online" msgstr "linear" @@ -5352,12 +5343,12 @@ msgstr "linear" #. remember, we have to handle the i18n case where the relative #. lengths of the strings in language N is different than in english. #. -#: option_editor.cc:468 option_editor.cc:469 option_editor.cc:614 +#: option_editor.cc:469 option_editor.cc:470 option_editor.cc:615 #, fuzzy msgid "offline" msgstr "linear" -#: option_editor.cc:669 +#: option_editor.cc:670 msgid "Choose Click" msgstr "" @@ -5366,15 +5357,15 @@ msgstr "" msgid "Choose Click Emphasis" msgstr "Usar como �fasis de metrnomo" -#: option_editor.cc:804 +#: option_editor.cc:803 msgid "Click audio file" msgstr "Archivo de sonido para metrnomo" -#: option_editor.cc:810 +#: option_editor.cc:809 msgid "Click emphasis audiofile" msgstr "Archivo de sonido de �fasis de metrnomo" -#: option_editor.cc:847 +#: option_editor.cc:846 msgid "" "The auditioner is a dedicated mixer strip used\n" "for listening to specific regions outside the context\n" @@ -5386,36 +5377,36 @@ msgstr "" "escuchar archivos de sonido en el men Biblioteca de Audio\n" "Se puede configurar sus conecciones como a cualquier.otra del mixer" -#: option_editor.cc:920 +#: option_editor.cc:919 msgid "Edit using" msgstr "Editar con" -#: option_editor.cc:927 option_editor.cc:954 +#: option_editor.cc:926 option_editor.cc:953 msgid "+ button" msgstr "botn +" -#: option_editor.cc:947 +#: option_editor.cc:946 msgid "Delete using" msgstr "Eliminar con" -#: option_editor.cc:974 +#: option_editor.cc:973 msgid "Ignore snap using" msgstr "Ignorar trabar con" -#: opts.cc:47 +#: opts.cc:46 msgid "Usage: " msgstr "Uso: " -#: opts.cc:48 +#: opts.cc:47 msgid " -v, --version Show version information\n" msgstr "" " -v, --version Mostra informacin acerca de la versin\n" -#: opts.cc:49 +#: opts.cc:48 msgid " -h, --help Print this message\n" msgstr " -h, --help Muestra este mensage\n" -#: opts.cc:50 +#: opts.cc:49 msgid "" " -b, --bindings Print all possible keyboard binding " "names\n" @@ -5423,12 +5414,12 @@ msgstr "" " -b, --bindings Muestra todos los comandos asignables a " "botones del teclado(shortcuts)\n" -#: opts.cc:51 +#: opts.cc:50 #, fuzzy msgid " -n, --show-splash Show splash screen\n" msgstr " -n, --no-splash No mostrar recuadro inicial\n" -#: opts.cc:52 +#: opts.cc:51 #, fuzzy msgid "" " -c, --name name Use a specific jack client name, default " @@ -5437,202 +5428,217 @@ msgstr "" " -c, --jack-client-name nombre Nombre de cliente jack para Ardour. Si " "no selecciona ninguno, el nombre ser�ardour\n" -#: opts.cc:53 +#: opts.cc:52 #, fuzzy msgid "" " -N, --new session-name Create a new session from the command " "line\n" msgstr " [nombre-sesin] Nombre de sesin a cargar\n" -#: opts.cc:54 +#: opts.cc:53 msgid "" " -o, --use-hw-optimizations Try to use h/w specific optimizations\n" msgstr "" -#: opts.cc:56 +#: opts.cc:55 #, fuzzy msgid " -V, --novst Do not use VST support\n" msgstr " -n, --no-splash No mostrar recuadro inicial\n" -#: opts.cc:58 +#: opts.cc:57 msgid " [session-name] Name of session to load\n" msgstr " [nombre-sesin] Nombre de sesin a cargar\n" -#: opts.cc:59 +#: opts.cc:58 msgid " -C, --curvetest filename Curve algorithm debugger\n" msgstr "" -#: opts.cc:60 +#: opts.cc:59 #, fuzzy msgid " -g, --gtktheme Allow GTK to load a theme\n" msgstr " -h, --help Muestra este mensage\n" -#: pan_automation_time_axis.cc:59 +#: pan_automation_time_axis.cc:60 msgid "You can't graphically edit panning of more than stream" msgstr "" -#: pan_automation_time_axis.cc:79 +#: pan_automation_time_axis.cc:80 #, fuzzy msgid "add pan automation event" msgstr "agregar evento de automatizacin a " -#: panner2d.cc:588 panner_ui.cc:393 plugin_ui.cc:833 +#: panner2d.cc:589 panner_ui.cc:435 plugin_ui.cc:834 #, fuzzy msgid "Bypass" msgstr "no procesar" -#: panner_ui.cc:57 panner_ui.cc:187 +#: panner_ui.cc:58 panner_ui.cc:225 #, fuzzy msgid "link" msgstr "entrada" +#: panner_ui.cc:69 +#, fuzzy +msgid "Pan automation mode" +msgstr "modo de automatizacin de balance" + #: panner_ui.cc:70 +#, fuzzy +msgid "Pan automation type" +msgstr "estado de automatizacin de balance" + +#: panner_ui.cc:81 msgid "panning link control" msgstr "" -#: panner_ui.cc:72 +#: panner_ui.cc:83 msgid "panning link direction" msgstr "" -#: panner_ui.cc:197 +#: panner_ui.cc:235 msgid "L" msgstr "" -#: panner_ui.cc:296 +#: panner_ui.cc:335 +#, c-format +msgid "panner for channel %lu" +msgstr "" + +#: panner_ui.cc:337 #, c-format msgid "panner for channel %u" msgstr "" -#: panner_ui.cc:403 +#: panner_ui.cc:445 #, fuzzy msgid "Reset all" msgstr "resetear" -#: playlist_selector.cc:51 +#: playlist_selector.cc:52 #, fuzzy msgid "ardour: playlists" msgstr "ardour: plugins" -#: playlist_selector.cc:58 +#: playlist_selector.cc:59 msgid "Playlists grouped by track" msgstr "" -#: playlist_selector.cc:97 +#: playlist_selector.cc:98 #, fuzzy msgid "ardour: playlist for " msgstr "ardour: plugins" -#: playlist_selector.cc:113 +#: playlist_selector.cc:114 #, fuzzy msgid "Other tracks" msgstr "Ocultar esta pista" -#: playlist_selector.cc:129 +#: playlist_selector.cc:130 msgid "unassigned" msgstr "" -#: plugin_selector.cc:42 +#: plugin_selector.cc:43 msgid "ardour: plugins" msgstr "ardour: plugins" -#: plugin_selector.cc:55 +#: plugin_selector.cc:56 #, fuzzy msgid "Available LADSPA Plugins" msgstr "Plugins LADSPA dispon�les" -#: plugin_selector.cc:56 +#: plugin_selector.cc:57 msgid "Type" msgstr "Tipo" -#: plugin_selector.cc:57 plugin_selector.cc:80 +#: plugin_selector.cc:58 plugin_selector.cc:81 msgid "# Inputs" msgstr "# Entradas" -#: plugin_selector.cc:58 plugin_selector.cc:81 +#: plugin_selector.cc:59 plugin_selector.cc:82 msgid "# Outputs" msgstr "# Salidas" -#: plugin_selector.cc:67 +#: plugin_selector.cc:68 msgid "Plugins to be Connected to Insert" msgstr "" -#: plugin_selector.cc:79 +#: plugin_selector.cc:80 #, fuzzy msgid "Available plugins" msgstr "Plugins LADSPA dispon�les" -#: plugin_selector.cc:97 +#: plugin_selector.cc:98 msgid "Add a plugin to the effect list" msgstr "Agregar plugin a lista de efectos" -#: plugin_selector.cc:99 +#: plugin_selector.cc:102 msgid "Remove a plugin from the effect list" msgstr "Quitar plugin de lista de efectos" -#: plugin_selector.cc:101 +#: plugin_selector.cc:104 msgid "Update available plugins" msgstr "Actualizar plugins dispon�les" -#: plugin_selector.cc:123 +#: plugin_selector.cc:126 msgid "LADSPA" msgstr "" -#: plugin_selector.cc:126 +#: plugin_selector.cc:129 msgid "VST" msgstr "" -#: plugin_ui.cc:83 +#: plugin_ui.cc:84 msgid "" "unknown type of editor-supplying plugin (note: no VST support in this " "version of ardour)" msgstr "" -#: plugin_ui.cc:138 +#: plugin_ui.cc:139 msgid "Presets" msgstr "" -#: plugin_ui.cc:229 +#: plugin_ui.cc:230 #, fuzzy msgid "Controls" msgstr "Control de Salidas" -#: plugin_ui.cc:266 +#: plugin_ui.cc:267 msgid "Plugin Editor: could not build control element for port %1" msgstr "" -#: plugin_ui.cc:357 +#: plugin_ui.cc:358 #, fuzzy -msgid "automation control" +msgid "Automation control" msgstr "mover evento de automatizacin" -#: plugin_ui.cc:853 +#: plugin_ui.cc:854 msgid "Plugin preset %1 not found" msgstr "" -#: plugin_ui.cc:863 +#: plugin_ui.cc:864 #, fuzzy msgid "Name of New Preset:" msgstr "Nombre para nueva coneccin:" -#: redirect_automation_line.cc:53 +#: redirect_automation_line.cc:54 msgid "redirect automation created for non-plugin" msgstr "automatizacin creada para un redireccionamiento no-plugin" -#: redirect_automation_time_axis.cc:93 +#: redirect_automation_time_axis.cc:94 #, fuzzy msgid "add automation event to " msgstr "agregar evento de automatizacin a " -#: redirect_box.cc:222 +#: redirect_box.cc:223 msgid "New send" msgstr "" -#: redirect_box.cc:223 +#: redirect_box.cc:224 #, fuzzy msgid "Show send controls" msgstr "Control de velocidad y sentido de reproduccin(pitch)" -#: redirect_box.cc:377 +#: redirect_box.cc:383 msgid "" "You attempted to add a plugin (%1).\n" "The plugin has %2 inputs\n" @@ -5643,7 +5649,7 @@ msgid "" "part of the signal." msgstr "" -#: redirect_box.cc:389 +#: redirect_box.cc:395 msgid "" "You attempted to add a plugin (%1).\n" "The plugin has %2 inputs\n" @@ -5655,7 +5661,7 @@ msgid "" "support this type of configuration." msgstr "" -#: redirect_box.cc:402 +#: redirect_box.cc:408 msgid "" "You attempted to add a plugin (%1).\n" "\n" @@ -5668,34 +5674,34 @@ msgid "" "Ardour does not understand what to do in such situations.\n" msgstr "" -#: redirect_box.cc:493 +#: redirect_box.cc:495 msgid "Pre-fader inserts, sends & plugins:" msgstr "" -#: redirect_box.cc:496 +#: redirect_box.cc:498 msgid "Post-fader inserts, sends & plugins:" msgstr "" -#: redirect_box.cc:642 +#: redirect_box.cc:644 msgid "" "You cannot reorder this set of redirects\n" "in that way because the inputs and\n" "outputs do not work correctly." msgstr "" -#: redirect_box.cc:747 +#: redirect_box.cc:749 #, fuzzy msgid "rename redirect" msgstr "ardour: renombrar regin" -#: redirect_box.cc:824 redirect_box.cc:872 +#: redirect_box.cc:826 redirect_box.cc:874 msgid "" "Copying the set of redirects on the clipboard failed,\n" "probably because the I/O configuration of the plugins\n" "could not match the configuration of this track." msgstr "" -#: redirect_box.cc:894 +#: redirect_box.cc:896 #, fuzzy msgid "" "Do you really want to remove all redirects from this track?\n" @@ -5704,7 +5710,7 @@ msgstr "" "Realmente desea quitar la pista \"%1\" ?\n" "(no podr�deshacer esto)" -#: redirect_box.cc:897 +#: redirect_box.cc:899 #, fuzzy msgid "" "Do you really want to remove all redirects from this bus?\n" @@ -5713,249 +5719,261 @@ msgstr "" "Realmente desea quitar la pista \"%1\" ?\n" "(no podr�deshacer esto)" -#: redirect_box.cc:902 +#: redirect_box.cc:904 #, fuzzy msgid "Yes, remove them all" msgstr "Si, eliminar esto." -#: redirect_box.cc:938 +#: redirect_box.cc:940 #, fuzzy msgid "ardour: %1" msgstr "ardour: reloj" -#: redirect_box.cc:980 +#: redirect_box.cc:982 #, fuzzy msgid "ardour: %1: %2 (by %3)" msgstr "ardour: regin" #. new stuff -#: redirect_box.cc:1052 +#: redirect_box.cc:1054 msgid "New Plugin ..." msgstr "" -#: redirect_box.cc:1053 +#: redirect_box.cc:1055 #, fuzzy msgid "New Insert" msgstr "nueva entrada" -#: redirect_box.cc:1054 +#: redirect_box.cc:1056 msgid "New Send ..." msgstr "" -#: redirect_box.cc:1066 +#: redirect_box.cc:1068 #, fuzzy msgid "Deselect All" msgstr "Seleccionar todo" -#: redirect_box.cc:1073 +#: redirect_box.cc:1075 #, fuzzy msgid "Activate all" msgstr "Activar" -#: redirect_box.cc:1074 +#: redirect_box.cc:1076 #, fuzzy msgid "Deactivate all" msgstr "Desactivar" -#: region_editor.cc:44 +#: region_editor.cc:45 msgid "NAME:" msgstr "NOMBRE:" -#: region_editor.cc:45 +#: region_editor.cc:46 msgid "lock" msgstr "bloquear" -#: region_editor.cc:47 +#: region_editor.cc:48 msgid "opaque" msgstr "opaco" -#: region_editor.cc:52 +#: region_editor.cc:49 region_editor.cc:192 region_editor.cc:226 +msgid "active" +msgstr "activo" + +#: region_editor.cc:50 +msgid "visible" +msgstr "visible" + +#: region_editor.cc:53 msgid "Layer" msgstr "Capa" -#: region_editor.cc:60 +#: region_editor.cc:54 +msgid "play" +msgstr "reproducir" + +#: region_editor.cc:61 msgid "ENVELOPE" msgstr "ENVELOPE" -#: region_editor.cc:106 +#: region_editor.cc:107 msgid "mute this region" msgstr "enmudecer a esta regin" -#: region_editor.cc:107 +#: region_editor.cc:108 msgid "regions underneath this one cannot be heard" msgstr "no se oir� a las regiones que est� bajo �ta" -#: region_editor.cc:108 +#: region_editor.cc:109 msgid "prevent any changes to this region" msgstr "bloquear contra cambios a esta regin" -#: region_editor.cc:109 +#: region_editor.cc:110 msgid "use the gain envelope during playback" msgstr "usar envelope de volumen durante la reproduccin" -#: region_editor.cc:110 +#: region_editor.cc:111 msgid "show the gain envelope" msgstr "mostrar envelope de volumen" -#: region_editor.cc:111 +#: region_editor.cc:112 msgid "use fade in curve during playback" msgstr "usar fade-in durante reproduccin" -#: region_editor.cc:112 +#: region_editor.cc:113 msgid "use fade out curve during playback" msgstr "usar fade-out durante reproduccin" -#: region_editor.cc:113 +#: region_editor.cc:114 msgid "audition this region" msgstr "audicionar esta regin" -#: region_editor.cc:146 +#: region_editor.cc:147 msgid "START:" msgstr "INICIO" -#: region_editor.cc:148 +#: region_editor.cc:149 msgid "END:" msgstr "FINAL:" -#: region_editor.cc:150 +#: region_editor.cc:151 msgid "LENGTH:" msgstr "DURACI�:" -#: region_editor.cc:190 +#: region_editor.cc:191 msgid "FADE IN" msgstr "FADE IN" -#: region_editor.cc:192 region_editor.cc:226 +#: region_editor.cc:193 region_editor.cc:227 msgid "msecs" msgstr "milisecs." -#: region_editor.cc:224 +#: region_editor.cc:225 msgid "FADE OUT" msgstr "FADE OUT" -#: region_editor.cc:264 +#: region_editor.cc:265 msgid "ardour: region " msgstr "ardour: regin" -#: region_editor.cc:401 +#: region_editor.cc:402 msgid "fade in edit" msgstr "editar fade in" -#: region_editor.cc:413 +#: region_editor.cc:414 #, fuzzy msgid "fade out edit" msgstr "agregar salida" -#: regionview.cc:1140 +#: regionview.cc:1146 #, fuzzy msgid "add gain control point" msgstr "Remover punto de sincron�" -#: route_params_ui.cc:88 +#: route_params_ui.cc:89 msgid "Tracks/Buses" msgstr "Pistas/Buses" -#: route_params_ui.cc:108 +#: route_params_ui.cc:109 #, fuzzy msgid "Pre-fader Redirects" msgstr "Pre Redireccionamentos" -#: route_params_ui.cc:109 +#: route_params_ui.cc:110 #, fuzzy msgid "Post-fader Redirects" msgstr "Pst Redireccionamentos" -#: route_params_ui.cc:141 +#: route_params_ui.cc:144 #, fuzzy msgid "ardour: track/bus inspector" msgstr "ardour: agregar Pistas/bus" -#: route_params_ui.cc:142 +#: route_params_ui.cc:145 msgid "ardour_route_parameters" msgstr "ardour_route_parameters" -#: route_params_ui.cc:199 +#: route_params_ui.cc:202 msgid "route display list item for renamed route not found!" msgstr "" -#: route_params_ui.cc:451 +#: route_params_ui.cc:453 msgid "NO TRACK" msgstr "NINGUNA PISTA" -#: route_params_ui.cc:693 +#: route_params_ui.cc:695 #, fuzzy msgid "ardour: track/bus inspector: " msgstr "ardour: agregar Pistas/bus" -#: route_params_ui.cc:697 +#: route_params_ui.cc:699 msgid "No Route Selected" msgstr "No seleccion ninguna Ruta" -#: route_params_ui.cc:698 +#: route_params_ui.cc:700 #, fuzzy msgid "ardour: track/bus/inspector: no route selected" msgstr "ardour: par�etros de ruteo: no seleccion ninguna ruta" #. ctrl-shift-click applies change to all routes -#: route_ui.cc:133 +#: route_ui.cc:134 #, fuzzy msgid "mute change" msgstr "Seleccionar intervalo de punch" #. ctrl-shift-click applies change to all routes #. ctrl-alt-click: exclusively solo this track, not a toggle */ -#: route_ui.cc:208 route_ui.cc:218 +#: route_ui.cc:209 route_ui.cc:219 #, fuzzy msgid "solo change" msgstr "rango de reproduccin cont�ua" -#: route_ui.cc:281 +#: route_ui.cc:282 msgid "rec-enable change" msgstr "" -#: route_ui.cc:472 +#: route_ui.cc:479 #, fuzzy msgid "Solo-safe" msgstr "Solo" -#: route_ui.cc:480 route_ui.cc:523 +#: route_ui.cc:487 route_ui.cc:530 #, fuzzy msgid "MIDI Bind" msgstr "MIDI" -#: route_ui.cc:494 +#: route_ui.cc:501 msgid "Pre Fader" msgstr "Pre-Fader" -#: route_ui.cc:501 +#: route_ui.cc:508 msgid "Post Fader" msgstr "Pst-Fader" -#: route_ui.cc:508 +#: route_ui.cc:515 msgid "Control Outs" msgstr "Control de Salidas" -#: route_ui.cc:515 +#: route_ui.cc:522 msgid "Main Outs" msgstr "Salidas Principales" -#: route_ui.cc:552 +#: route_ui.cc:559 msgid "mix group solo change" msgstr "" -#: route_ui.cc:586 +#: route_ui.cc:593 msgid "mix group mute change" msgstr "" -#: route_ui.cc:602 +#: route_ui.cc:609 msgid "mix group rec-enable change" msgstr "" -#: route_ui.cc:619 visual_time_axis.cc:236 +#: route_ui.cc:626 visual_time_axis.cc:237 msgid "ardour: color selection" msgstr "ardour: seleccin de color" -#: route_ui.cc:695 +#: route_ui.cc:702 #, fuzzy msgid "" "Do you really want to remove track \"%1\" ?\n" @@ -5966,7 +5984,7 @@ msgstr "" "Realmente desea quitar la pista \"%1\" ?\n" "(no podr�deshacer esto)" -#: route_ui.cc:697 +#: route_ui.cc:704 msgid "" "Do you really want to remove bus \"%1\" ?\n" "(cannot be undone)" @@ -5974,11 +5992,11 @@ msgstr "" "Realmente desea quitar el bus \"%1\" ?\n" "(no podr�deshacer esto)" -#: route_ui.cc:701 visual_time_axis.cc:278 +#: route_ui.cc:708 visual_time_axis.cc:279 msgid "Yes, remove it." msgstr "Si, eliminar esto." -#: route_ui.cc:730 +#: route_ui.cc:737 #, fuzzy msgid "New Name: " msgstr "nuevo nombre: " @@ -6037,147 +6055,148 @@ msgstr "No se pudo acceder a archivo de audio" msgid "Name for Field" msgstr "Nombre para regin:" -#: sfdb_ui.cc:333 +#: sfdb_ui.cc:335 msgid "Split Channels" msgstr "Separar canales" -#: sfdb_ui.cc:340 +#: sfdb_ui.cc:342 msgid "Create a region for each channel" msgstr "" -#: sfdb_ui.cc:342 +#: sfdb_ui.cc:344 msgid "Embed" msgstr "" -#: sfdb_ui.cc:344 +#: sfdb_ui.cc:346 #, fuzzy msgid "Link to an external file" msgstr "Insertar archivo de audio externo" -#: sfdb_ui.cc:346 +#: sfdb_ui.cc:348 msgid "Import" msgstr "Importar" -#: sfdb_ui.cc:348 +#: sfdb_ui.cc:350 msgid "Copy a file to the session folder" msgstr "" -#: sfdb_ui.cc:412 +#: sfdb_ui.cc:414 msgid "programming error: %1" msgstr "" -#: tempo_dialog.cc:17 tempo_dialog.cc:34 +#: tempo_dialog.cc:18 tempo_dialog.cc:35 msgid "Beats per minute" msgstr "Pulsos por minuto" -#: tempo_dialog.cc:20 tempo_dialog.cc:37 tempo_dialog.cc:153 -#: tempo_dialog.cc:171 +#: tempo_dialog.cc:21 tempo_dialog.cc:38 tempo_dialog.cc:203 +#: tempo_dialog.cc:221 msgid "Bar" msgstr "Comp�" -#: tempo_dialog.cc:21 tempo_dialog.cc:38 tempo_dialog.cc:154 -#: tempo_dialog.cc:172 +#: tempo_dialog.cc:22 tempo_dialog.cc:39 tempo_dialog.cc:204 +#: tempo_dialog.cc:222 msgid "Beat" msgstr "Pulsos" -#: tempo_dialog.cc:23 tempo_dialog.cc:40 tempo_dialog.cc:155 -#: tempo_dialog.cc:173 +#: tempo_dialog.cc:24 tempo_dialog.cc:41 tempo_dialog.cc:205 +#: tempo_dialog.cc:223 msgid "Location" msgstr "Localizacin" -#: tempo_dialog.cc:149 tempo_dialog.cc:167 +#: tempo_dialog.cc:199 tempo_dialog.cc:217 msgid "Meter denominator" msgstr "Denominador m�rico" -#: tempo_dialog.cc:150 tempo_dialog.cc:168 +#: tempo_dialog.cc:200 tempo_dialog.cc:218 msgid "Beats per bar" msgstr "Pulsos por compaces" -#: tempo_dialog.cc:186 tempo_dialog.cc:197 +#: tempo_dialog.cc:236 tempo_dialog.cc:247 msgid "whole (1)" msgstr "toda (1)" -#: tempo_dialog.cc:187 tempo_dialog.cc:199 +#: tempo_dialog.cc:237 tempo_dialog.cc:249 msgid "second (2)" msgstr "segunda (2)" -#: tempo_dialog.cc:188 tempo_dialog.cc:201 +#: tempo_dialog.cc:238 tempo_dialog.cc:251 msgid "third (3)" msgstr "tercera (3)" -#: tempo_dialog.cc:189 tempo_dialog.cc:203 tempo_dialog.cc:211 +#: tempo_dialog.cc:239 tempo_dialog.cc:253 tempo_dialog.cc:261 msgid "quarter (4)" msgstr "cuarta (4)" -#: tempo_dialog.cc:190 tempo_dialog.cc:205 +#: tempo_dialog.cc:240 tempo_dialog.cc:255 msgid "eighth (8)" msgstr "octava (8)" -#: tempo_dialog.cc:191 tempo_dialog.cc:207 +#: tempo_dialog.cc:241 tempo_dialog.cc:257 msgid "sixteenth (16)" msgstr "d�ima sexta (16)" -#: tempo_dialog.cc:192 tempo_dialog.cc:209 +#: tempo_dialog.cc:242 tempo_dialog.cc:259 msgid "thirty-second (32)" msgstr "trig�ima segunda (32)" -#: tempo_dialog.cc:321 +#: tempo_dialog.cc:420 msgid "garbaged note type entry (%1)" msgstr "se descart el texto (%1)" -#: tempo_dialog.cc:331 +#: tempo_dialog.cc:430 msgid "incomprehensible note type entry (%1)" msgstr "El formato de este texto es incomprensible(%1)" -#: time_axis_view.cc:111 +#: time_axis_view.cc:112 msgid "gTortnam" msgstr "gTortnam" -#: time_axis_view.cc:548 +#: time_axis_view.cc:549 msgid "Largest" msgstr "Enorme" -#: time_axis_view.cc:549 +#: time_axis_view.cc:550 msgid "Large" msgstr "Grande" -#: time_axis_view.cc:550 +#: time_axis_view.cc:551 msgid "Larger" msgstr "Mayor" -#: time_axis_view.cc:552 +#: time_axis_view.cc:553 msgid "Smaller" msgstr "Menor" -#: time_axis_view.cc:553 +#: time_axis_view.cc:554 msgid "Small" msgstr "Chico" -#: time_axis_view.cc:869 +#: time_axis_view.cc:870 msgid "unknown track height name \"%1\" in XML GUI information" msgstr "" -#: time_axis_view_item.cc:71 +#. first constructed item sets up font info +#: time_axis_view_item.cc:79 msgid "TimeAxisViewItemName" msgstr "" -#: time_axis_view_item.cc:271 +#: time_axis_view_item.cc:298 msgid "new duration %1 frames is out of bounds for %2" msgstr "" -#: time_selection.cc:40 +#: time_selection.cc:41 msgid "programming error: request for non-existent audio range (%1)!" msgstr "" -#: utils.cc:106 utils.cc:149 +#: utils.cc:107 utils.cc:150 msgid "bad XPM header %1" msgstr "" -#: utils.cc:331 +#: utils.cc:332 msgid "missing RGBA style for \"%1\"" msgstr "" -#: visual_time_axis.cc:275 +#: visual_time_axis.cc:276 msgid "" "Do you really want to remove track \"%1\" ?\n" "(cannot be undone)" @@ -6185,14 +6204,83 @@ msgstr "" "Realmente desea quitar la pista \"%1\" ?\n" "(no podr�deshacer esto)" -#: visual_time_axis.cc:324 +#: visual_time_axis.cc:325 msgid "new name: " msgstr "nuevo nombre: " -#: visual_time_axis.cc:335 +#: visual_time_axis.cc:336 msgid "A track already exists with that name" msgstr "Ya existe una pista con este nombre" +#, fuzzy +#~ msgid "set selected trackview" +#~ msgstr "Insertar seleccin" + +#, fuzzy +#~ msgid "set selected control point" +#~ msgstr "Remover punto de sincron�" + +#, fuzzy +#~ msgid "set selected regionview" +#~ msgstr "Reproducir regin seleccionada cont�uamente" + +#~ msgid "Start a new session\n" +#~ msgstr "Iniciar una nueva sesin\n" + +#~ msgid "via Session menu" +#~ msgstr "via men de Sesin" + +#, fuzzy +#~ msgid "Advanced" +#~ msgstr "Avanzado..." + +#, fuzzy +#~ msgid "Select a File" +#~ msgstr "Seleccionar todo" + +#, fuzzy +#~ msgid "Track/Bus connection options" +#~ msgstr "Pistas/Buses" + +#~ msgid "RECORD" +#~ msgstr "GRABAR" + +#~ msgid "INPUT" +#~ msgstr "ENTRADA" + +#~ msgid "OUTPUT" +#~ msgstr "SALIDA" + +#, fuzzy +#~ msgid "Gain automation mode" +#~ msgstr "modo de automatizacin de volumen" + +#, fuzzy +#~ msgid "Gain automation type" +#~ msgstr "estado de automatizacin de volumen" + +#, fuzzy +#~ msgid "trim" +#~ msgstr "cortar" + +#, fuzzy +#~ msgid "gain automation mode" +#~ msgstr "modo de automatizacin de volumen" + +#, fuzzy +#~ msgid "gain automation state" +#~ msgstr "estado de automatizacin de volumen" + +#, fuzzy +#~ msgid "pan automation state" +#~ msgstr "estado de automatizacin de balance" + +#~ msgid "OUT" +#~ msgstr "SALIDA" + +#~ msgid "no group" +#~ msgstr "sin grupo" + #, fuzzy #~ msgid "normal" #~ msgstr "Normal" @@ -6458,9 +6546,6 @@ msgstr "Ya existe una pista con este nombre" #~ msgid "AND" #~ msgstr "Y" -#~ msgid "OR" -#~ msgstr "O" - #~ msgid "ardour: locate soundfiles" #~ msgstr "ardour: localizar archivos de audio" @@ -6476,9 +6561,6 @@ msgstr "Ya existe una pista con este nombre" #~ msgid "Ardour: Search Results" #~ msgstr "Ardour: Resultado de Bsqueda" -#~ msgid "Mix Groups" -#~ msgstr "Grupos de Mixer" - #~ msgid "Hide All AudioTrack MixerStrips" #~ msgstr "Ocultar todas las pistas de Audio en el Mixer" @@ -6491,11 +6573,6 @@ msgstr "Ya existe una pista con este nombre" #~ msgid "Name for new mix group" #~ msgstr "Nombre para nuevo grupo del mixer" -# -#, fuzzy -#~ msgid "Session name:" -#~ msgstr "Nombre de sesin:" - #, fuzzy #~ msgid "Create" #~ msgstr "Crear" @@ -6535,17 +6612,9 @@ msgstr "Ya existe una pista con este nombre" #~ "frecuencia de muestreo distinta, cierre Ardour,reinice\n" #~ "JACK y vuelva a ejecutar Ardour\n" -#, fuzzy -#~ msgid "Session template" -#~ msgstr "usar esquema existente" - #~ msgid "blank" #~ msgstr "en blanco" -#, fuzzy -#~ msgid "No template" -#~ msgstr "-esquema" - #, fuzzy #~ msgid "Slave to MTC" #~ msgstr "Enviar MTC" @@ -6565,9 +6634,6 @@ msgstr "Ya existe una pista con este nombre" #~ msgid "Native Format" #~ msgstr "Formato Nativo" -#~ msgid "Use as click" -#~ msgstr "Usar como metrnomo" - #~ msgid "--unknown--" #~ msgstr "--desconocido--" diff --git a/gtk2_ardour/po/fr_FR.po b/gtk2_ardour/po/fr_FR.po index c1d57a1806..4875e57712 100644 --- a/gtk2_ardour/po/fr_FR.po +++ b/gtk2_ardour/po/fr_FR.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: gtk-ardour 0.334.5\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-04-25 17:46-0400\n" +"POT-Creation-Date: 2006-06-21 18:09-0400\n" "PO-Revision-Date: 2005-02-14 11:19-0500\n" "Last-Translator: Alain Fréhel \n" "Language-Team: French \n" @@ -15,96 +15,96 @@ msgstr "" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" -#: about.cc:119 +#: about.cc:120 msgid "Paul Davis" msgstr "" -#: about.cc:120 +#: about.cc:121 #, fuzzy msgid "Jesse Chappell" msgstr "Réinitialiser" -#: about.cc:121 +#: about.cc:122 msgid "Taybin Rutkin" msgstr "" -#: about.cc:122 +#: about.cc:123 msgid "Marcus Andersson" msgstr "" -#: about.cc:123 +#: about.cc:124 msgid "Jeremy Hall" msgstr "" -#: about.cc:124 +#: about.cc:125 msgid "Steve Harris" msgstr "" -#: about.cc:125 +#: about.cc:126 msgid "Tim Mayberry" msgstr "" -#: about.cc:126 +#: about.cc:127 msgid "Mark Stewart" msgstr "" -#: about.cc:127 +#: about.cc:128 msgid "Sam Chessman" msgstr "" -#: about.cc:128 +#: about.cc:129 msgid "Jack O'Quin" msgstr "" -#: about.cc:129 +#: about.cc:130 msgid "Matt Krai" msgstr "" -#: about.cc:130 +#: about.cc:131 msgid "Ben Bell" msgstr "" -#: about.cc:131 +#: about.cc:132 msgid "Gerard van Dongen" msgstr "" -#: about.cc:132 +#: about.cc:133 msgid "Thomas Charbonnel" msgstr "" -#: about.cc:133 +#: about.cc:134 msgid "Nick Mainsbridge" msgstr "" -#: about.cc:134 +#: about.cc:135 msgid "Colin Law" msgstr "" -#: about.cc:135 +#: about.cc:136 msgid "Sampo Savolainen" msgstr "" -#: about.cc:136 +#: about.cc:137 msgid "Joshua Leach" msgstr "" -#: about.cc:137 +#: about.cc:138 msgid "Rob Holland" msgstr "" -#: about.cc:138 +#: about.cc:139 msgid "Per Sigmond" msgstr "" -#: about.cc:139 +#: about.cc:140 msgid "Doug Mclain" msgstr "" -#: about.cc:140 +#: about.cc:141 msgid "Petter Sundlöf" msgstr "" -#: about.cc:145 +#: about.cc:146 #, fuzzy msgid "" "French:\n" @@ -113,7 +113,7 @@ msgstr "" "Français :\n" "\tAlain Fréhel " -#: about.cc:146 +#: about.cc:147 #, fuzzy msgid "" "German:\n" @@ -122,7 +122,7 @@ msgstr "" "Allemand :\n" "\tKarsten Petersen " -#: about.cc:147 +#: about.cc:148 #, fuzzy msgid "" "Italian:\n" @@ -131,7 +131,7 @@ msgstr "" "Italien :\n" "\tFilippo Pappalardo " -#: about.cc:148 +#: about.cc:149 #, fuzzy msgid "" "Portuguese:\n" @@ -140,7 +140,7 @@ msgstr "" "Portugais :\n" "\tRui Nuno Capela " -#: about.cc:149 +#: about.cc:150 #, fuzzy msgid "" "Brazilian Portuguese:\n" @@ -151,7 +151,7 @@ msgstr "" "\tAlexander da Franca Fernandes \n" "\tChris Ross " -#: about.cc:151 +#: about.cc:152 #, fuzzy msgid "" "Spanish:\n" @@ -160,7 +160,7 @@ msgstr "" "Espagnol :\n" "\tAlex Krohn " -#: about.cc:152 +#: about.cc:153 #, fuzzy msgid "" "Russian:\n" @@ -169,12 +169,12 @@ msgstr "" "Russe :\n" "\tIgor Blinov " -#: about.cc:180 +#: about.cc:181 #, fuzzy msgid "Copyright (C) 1999-2005 Paul Davis\n" msgstr "Copyright (C) 1999-2005 Paul Davis" -#: about.cc:181 +#: about.cc:182 #, fuzzy msgid "" "Ardour comes with ABSOLUTELY NO WARRANTY\n" @@ -187,7 +187,7 @@ msgstr "" "Ceci est un logiciel libre, et vous êtes encouragés à le distribuer\n" "sous certaines conditions ; voir le fichier COPYING pour les détails.\n" -#: about.cc:187 +#: about.cc:188 #, fuzzy msgid "" "%1\n" @@ -196,53 +196,53 @@ msgstr "" "Ardour: %1\n" "(fonctionnant avec ardour/gtk %2 libardour: %3.%4.%5)" -#: actions.cc:260 +#: actions.cc:261 #, fuzzy msgid "programmer error: %1 %2" msgstr "erreur de programmation : " -#: add_route_dialog.cc:61 +#: add_route_dialog.cc:62 msgid "ardour: add track/bus" msgstr "ardour : ajouter piste/bus" #. path = "1" -#: add_route_dialog.cc:62 editor_route_list.cc:72 +#: add_route_dialog.cc:63 editor_route_list.cc:73 msgid "Tracks" msgstr "Pistes" #. path = "0" -#: add_route_dialog.cc:63 editor_route_list.cc:69 +#: add_route_dialog.cc:64 editor_route_list.cc:70 msgid "Busses" msgstr "Bus" -#: add_route_dialog.cc:95 plugin_ui.cc:832 +#: add_route_dialog.cc:96 plugin_ui.cc:833 msgid "Add" msgstr "Ajouter" -#: add_route_dialog.cc:113 +#: add_route_dialog.cc:114 msgid "Name (template)" msgstr "Nom (modèle)" -#: add_route_dialog.cc:119 +#: add_route_dialog.cc:120 #, fuzzy msgid "Channel Configuration" msgstr "Configuration" -#: add_route_dialog.cc:176 editor.cc:131 editor.cc:3660 time_axis_view.cc:551 +#: add_route_dialog.cc:177 editor.cc:134 editor.cc:3688 time_axis_view.cc:552 msgid "Normal" msgstr "Normal" -#: add_route_dialog.cc:178 +#: add_route_dialog.cc:179 #, fuzzy msgid "Tape" msgstr "État" -#: add_route_dialog.cc:195 +#: add_route_dialog.cc:196 #, fuzzy msgid "Mono" msgstr "mono" -#: add_route_dialog.cc:197 +#: add_route_dialog.cc:198 #, fuzzy msgid "Stereo" msgstr "stéréo" @@ -329,31 +329,11 @@ msgstr "ECOUTE" msgid "SOLO" msgstr "SOLO" -#: ardour_ui.cc:207 -msgid "" -"You cannot record-enable\n" -"track %1\n" -"because it has no input connections.\n" -"You would be wasting space recording silence." -msgstr "" -"Vous ne pouvez activer\n" -"l'enregistrement de la piste %1\n" -"car elle n'a pas de connections en entrée.\n" -"Vous gacheriez de l'espace en enregistrant du silence." - -#: ardour_ui.cc:236 -msgid "no vertical meter strip image found" -msgstr "" - -#: ardour_ui.cc:243 -msgid "no horizontal meter strip image found" -msgstr "" - -#: ardour_ui.cc:410 +#: ardour_ui.cc:375 msgid "quit" msgstr "quitter" -#: ardour_ui.cc:419 +#: ardour_ui.cc:384 msgid "" "Ardour was unable to save your session.\n" "\n" @@ -362,31 +342,31 @@ msgid "" "\"Just quit\" option." msgstr "" -#: ardour_ui.cc:438 +#: ardour_ui.cc:403 msgid "ardour: save session?" msgstr "ardour : enregistrer la session ?" -#: ardour_ui.cc:445 +#: ardour_ui.cc:410 msgid "Don't %1" msgstr "Ne pas %1" -#: ardour_ui.cc:447 +#: ardour_ui.cc:412 msgid "Just %1" msgstr "Juste %1" -#: ardour_ui.cc:449 +#: ardour_ui.cc:414 msgid "Save and %1" msgstr "Enregistrer et %1" -#: ardour_ui.cc:461 +#: ardour_ui.cc:426 msgid "session" msgstr "session" -#: ardour_ui.cc:463 +#: ardour_ui.cc:428 msgid "snapshot" msgstr "Instantané" -#: ardour_ui.cc:465 +#: ardour_ui.cc:430 #, fuzzy msgid "" "The %1\"%2\"\n" @@ -405,81 +385,81 @@ msgstr "" "\n" "Que voulez-vous faire ?" -#: ardour_ui.cc:479 +#: ardour_ui.cc:444 msgid "Prompter" msgstr "Prompter" -#: ardour_ui.cc:538 +#: ardour_ui.cc:503 #, c-format msgid "disconnected" msgstr "déconnecté" -#: ardour_ui.cc:545 +#: ardour_ui.cc:510 #, c-format msgid "SR: %.1f kHz / %4.1f msecs" msgstr "F.E. : %.1f kHz / %4.1f ms" -#: ardour_ui.cc:549 +#: ardour_ui.cc:514 #, c-format msgid "SR: %u kHz / %4.1f msecs" msgstr "F.E. : %u kHz / %4.1f ms" -#: ardour_ui.cc:562 +#: ardour_ui.cc:527 #, c-format msgid "DSP Load: %.1f%%" msgstr "Charge DSP : %.1f%%" -#: ardour_ui.cc:572 +#: ardour_ui.cc:537 #, c-format msgid "Buffers p:%%% c:%%%" msgstr "Tampons p:%%% c:%%%" -#: ardour_ui.cc:599 +#: ardour_ui.cc:564 msgid "space: 24hrs+" msgstr "espace : 24hrs+" -#: ardour_ui.cc:629 +#: ardour_ui.cc:594 #, c-format msgid "space: %02dh:%02dm:%02ds" msgstr "espace: %02dh:%02dm:%02ds" -#: ardour_ui.cc:668 +#: ardour_ui.cc:633 msgid "programming error: impossible control method" msgstr "erreur de programmation : méthode de contrôle impossible" -#: ardour_ui.cc:776 new_session_dialog.cc:89 +#: ardour_ui.cc:741 new_session_dialog.cc:294 #, fuzzy msgid "Recent Sessions" msgstr "ouvrir session" #. ardour sessions are folders -#: ardour_ui.cc:867 +#: ardour_ui.cc:834 msgid "open session" msgstr "ouvrir session" -#: ardour_ui.cc:873 +#: ardour_ui.cc:840 #, fuzzy msgid "Ardour sessions" msgstr "ardour_nouvelle_session" -#: ardour_ui.cc:906 +#: ardour_ui.cc:873 msgid "Patience is a virtue.\n" msgstr "La patience est une vertue.\n" -#: ardour_ui.cc:915 +#: ardour_ui.cc:882 msgid "You cannot add a track without a session already loaded." msgstr "" "Vous ne pouvez pas ajouter une piste sans qu'une session ait été chargée." -#: ardour_ui.cc:922 +#: ardour_ui.cc:889 msgid "could not create new audio track" msgstr "impossible de créer une nouvelle piste audio" -#: ardour_ui.cc:926 +#: ardour_ui.cc:893 msgid "could not create new audio bus" msgstr "impossible de créer un nouveau bus audio" -#: ardour_ui.cc:945 +#: ardour_ui.cc:912 msgid "" "There are insufficient JACK ports available\n" "to create a new track or bus.\n" @@ -491,7 +471,7 @@ msgstr "" "Vous devriez enregistrer, quitter, puis\n" "redémarrer JACK avec plus de ports." -#: ardour_ui.cc:1069 +#: ardour_ui.cc:1036 msgid "" "Please create 1 or more track\n" "before trying to record.\n" @@ -501,7 +481,7 @@ msgstr "" "avant d'essayer d'enregistrer.\n" "Regardez dans le menu Session." -#: ardour_ui.cc:1298 +#: ardour_ui.cc:1265 msgid "" "JACK has either been shutdown or it\n" "disconnected Ardour because Ardour\n" @@ -513,56 +493,54 @@ msgstr "" "Vous devriez enregistrer la session\n" "et/ou essayer de le reconnecter à JACK." -#: ardour_ui.cc:1315 +#: ardour_ui.cc:1282 msgid "Unable to create all required ports" msgstr "" -#: ardour_ui.cc:1323 +#: ardour_ui.cc:1290 msgid "Unable to start the session running" msgstr "Impossible de lancer la session" -#: ardour_ui.cc:1459 +#: ardour_ui.cc:1426 msgid "No Stream" msgstr "Pas de flux" -#: ardour_ui.cc:1486 ardour_ui.cc:1505 +#: ardour_ui.cc:1453 ardour_ui.cc:1472 msgid "none" msgstr "aucun" -#: ardour_ui.cc:1495 ardour_ui.cc:1514 automation_time_axis.cc:183 -#: automation_time_axis.cc:212 automation_time_axis.cc:459 mixer_strip.cc:174 -#: mixer_strip.cc:186 mixer_strip.cc:881 plugin_ui.cc:391 plugin_ui.cc:634 +#: ardour_ui.cc:1462 ardour_ui.cc:1481 msgid "off" msgstr "arrêt" -#: ardour_ui.cc:1538 +#: ardour_ui.cc:1505 #, fuzzy msgid "Name of New Snapshot" msgstr "Nom de l'instantané" -#: ardour_ui.cc:1684 +#: ardour_ui.cc:1651 msgid "Name for mix template:" msgstr "Nom du modèle de mélange : " -#: ardour_ui.cc:1685 +#: ardour_ui.cc:1652 msgid "-template" msgstr "-modèle" -#: ardour_ui.cc:1836 +#: ardour_ui.cc:1809 msgid "" "You do not have write access to this session.\n" "This prevents the session from being loaded." msgstr "" -#: ardour_ui.cc:1849 ardour_ui.cc:1904 +#: ardour_ui.cc:1822 ardour_ui.cc:1877 msgid "Session \"%1 (snapshot %2)\" did not load successfully" msgstr "La session \"%1 (instantané %2)\" ne s'est pas chargée correctement" -#: ardour_ui.cc:1960 +#: ardour_ui.cc:1933 msgid "No audio files were ready for cleanup" msgstr "" -#: ardour_ui.cc:1964 +#: ardour_ui.cc:1937 msgid "" "If this seems suprising, \n" "check for any existing snapshots.\n" @@ -570,25 +548,25 @@ msgid "" "require some unused files to continue to exist." msgstr "" -#: ardour_ui.cc:1973 +#: ardour_ui.cc:1946 msgid "ardour: cleanup" msgstr "ardour : nettoyage" -#: ardour_ui.cc:2009 ardour_ui.cc:2015 +#: ardour_ui.cc:1982 ardour_ui.cc:1988 #, fuzzy msgid "files were" msgstr "fichiers" -#: ardour_ui.cc:2011 ardour_ui.cc:2017 +#: ardour_ui.cc:1984 ardour_ui.cc:1990 #, fuzzy msgid "file was" msgstr "fichiers" -#: ardour_ui.cc:2058 +#: ardour_ui.cc:2031 msgid "Are you sure you want to cleanup?" msgstr "" -#: ardour_ui.cc:2063 +#: ardour_ui.cc:2036 msgid "" "Cleanup is a destructive operation.\n" "ALL undo/redo information will be lost if you cleanup.\n" @@ -596,26 +574,26 @@ msgid "" "location." msgstr "" -#: ardour_ui.cc:2069 +#: ardour_ui.cc:2042 #, fuzzy msgid "Clean Up" msgstr "Nettoyer" -#: ardour_ui.cc:2072 +#: ardour_ui.cc:2045 #, fuzzy msgid "CleanupDialog" msgstr "Nettoyer" -#: ardour_ui.cc:2073 +#: ardour_ui.cc:2046 #, fuzzy msgid "ardour_cleanup" msgstr "ardour : nettoyage" -#: ardour_ui.cc:2092 +#: ardour_ui.cc:2065 msgid "cleaned files" msgstr "fichiers nettoyés" -#: ardour_ui.cc:2093 +#: ardour_ui.cc:2066 #, fuzzy msgid "" "The following %1 %2 not in use and \n" @@ -631,11 +609,11 @@ msgstr "" "%3 %4-octets d'espace disque supplémentaires seront\n" "libérés" -#: ardour_ui.cc:2118 +#: ardour_ui.cc:2091 msgid "deleted file" msgstr "fichiers effacés" -#: ardour_ui.cc:2119 +#: ardour_ui.cc:2092 #, fuzzy msgid "" "The following %1 %2 deleted from\n" @@ -645,12 +623,12 @@ msgstr "" "Les %1 fichier%2 suivant%2 seront effacé%2, libérant %3 %4-octets d'espace " "disque" -#: ardour_ui.cc:2242 +#: ardour_ui.cc:2215 msgid "Recording was stopped because your system could not keep up." msgstr "" "L'enregistrement a été stoppé parce que votre système ne peut pas suivre." -#: ardour_ui.cc:2265 +#: ardour_ui.cc:2238 msgid "" "The disk system on your computer\n" "was not able to keep up with Ardour.\n" @@ -664,7 +642,7 @@ msgstr "" "Plus précisement, il a été incapable d'écrire les données\n" "sur le disque assez rapidement pour suivre l'enregistrement.\n" -#: ardour_ui.cc:2284 +#: ardour_ui.cc:2257 msgid "" "The disk system on your computer\n" "was not able to keep up with Ardour.\n" @@ -678,7 +656,7 @@ msgstr "" "Plus précisement, il a été incapable de lire les données\n" "sur le disque assez rapidement pour suivre la lecture.\n" -#: ardour_ui.cc:2310 +#: ardour_ui.cc:2283 msgid "" "This session appears to have been in\n" "middle of recording when ardour or\n" @@ -696,363 +674,363 @@ msgstr "" "ou vous pouvez l'ignorer. Veuillez décider\n" "sur ce que vous voulez faire.\n" -#: ardour_ui.cc:2320 +#: ardour_ui.cc:2293 msgid "Recover from crash" msgstr "Récupérer après un plantage" -#: ardour_ui.cc:2321 +#: ardour_ui.cc:2294 msgid "Ignore crash data" msgstr "Ignorer les données du plantage" -#: ardour_ui.cc:2339 +#: ardour_ui.cc:2312 msgid "Could not disconnect from JACK" msgstr "Impossible de se déconnecter de JACK" -#: ardour_ui.cc:2352 +#: ardour_ui.cc:2325 msgid "Could not reconnect to JACK" msgstr "Impossible de se reconnecter à JACK" -#: ardour_ui2.cc:59 +#: ardour_ui2.cc:60 msgid "UI: cannot setup editor" msgstr "IHM : impossible d'initialiser l'éditeur" -#: ardour_ui2.cc:64 +#: ardour_ui2.cc:65 msgid "UI: cannot setup mixer" msgstr "IHM : impossible d'initialiser la console de mixage" -#: ardour_ui2.cc:90 +#: ardour_ui2.cc:91 msgid "MMC + Local" msgstr "MMC + Local" -#: ardour_ui2.cc:91 +#: ardour_ui2.cc:92 msgid "MMC" msgstr "MMC" -#: ardour_ui2.cc:92 +#: ardour_ui2.cc:93 msgid "Local" msgstr "Local" -#: ardour_ui2.cc:109 +#: ardour_ui2.cc:110 msgid "MMC ID" msgstr "ID MMC" -#: ardour_ui2.cc:290 +#: ardour_ui2.cc:291 msgid "Play from playhead" msgstr "Jouer depuis la tête de lecture" -#: ardour_ui2.cc:291 +#: ardour_ui2.cc:292 msgid "Stop playback" msgstr "Arrêter la lecture" -#: ardour_ui2.cc:292 +#: ardour_ui2.cc:293 msgid "Play range/selection" msgstr "Jouer l'intervalle/la sélection" -#: ardour_ui2.cc:293 +#: ardour_ui2.cc:294 msgid "Go to start of session" msgstr "Aller au début de la session" -#: ardour_ui2.cc:294 +#: ardour_ui2.cc:295 msgid "Go to end of session" msgstr "Aller à la fin de la session" -#: ardour_ui2.cc:295 +#: ardour_ui2.cc:296 msgid "Play loop range" msgstr "Jouer l'intervalle de boucle" -#: ardour_ui2.cc:296 +#: ardour_ui2.cc:297 msgid "Return to last playback start when stopped" msgstr "Revenir au dernier départ de lecture lors de l'arrêt" -#: ardour_ui2.cc:297 +#: ardour_ui2.cc:298 msgid "Start playback after any locate" msgstr "Démarrer la lecture aprés chaque locate" -#: ardour_ui2.cc:298 +#: ardour_ui2.cc:299 msgid "Be sensible about input monitoring" msgstr "Être raisonnable avec la pré-écoute des entrées" -#: ardour_ui2.cc:299 +#: ardour_ui2.cc:300 msgid "Start recording at auto-punch start" msgstr "Démarrer l'enregistrement en début d'auto-punch" -#: ardour_ui2.cc:300 +#: ardour_ui2.cc:301 msgid "Stop recording at auto-punch end" msgstr "Arrêter l'enregistrement en fin d'auto-punch" -#: ardour_ui2.cc:301 +#: ardour_ui2.cc:302 msgid "Enable/Disable audio click" msgstr "Activer/Désactiver le clic sonore" -#: ardour_ui2.cc:302 +#: ardour_ui2.cc:303 #, fuzzy msgid "Positional sync source" msgstr "Synchro. positionelle" -#: ardour_ui2.cc:303 +#: ardour_ui2.cc:304 msgid "Does Ardour control the time?" msgstr "" -#: ardour_ui2.cc:304 +#: ardour_ui2.cc:305 #, fuzzy msgid "Shuttle speed control" msgstr "Contrôle de la vitesse avec molette" -#: ardour_ui2.cc:305 +#: ardour_ui2.cc:306 #, fuzzy, c-format msgid "Select semitones or %%-age for speed display" msgstr "Sélectionner les demi-tons ou le %-age pour l'affichage de la vitesse" -#: ardour_ui2.cc:306 +#: ardour_ui2.cc:307 msgid "Current transport speed" msgstr "Vitesse de transport courante" -#: ardour_ui2.cc:329 +#: ardour_ui2.cc:330 msgid "Primary clock" msgstr "Horloge principale" -#: ardour_ui2.cc:330 +#: ardour_ui2.cc:331 msgid "secondary clock" msgstr "Horloge secondaire" #. XXX: this should really be saved in instant.xml or something similar and restored from there #. Combo's are stupid - they steal space from the entry for the button -#: ardour_ui2.cc:387 ardour_ui2.cc:823 ardour_ui2.cc:836 ardour_ui2.cc:899 -#: ardour_ui2.cc:901 +#: ardour_ui2.cc:388 ardour_ui2.cc:833 ardour_ui2.cc:846 ardour_ui2.cc:909 +#: ardour_ui2.cc:911 msgid "sprung" msgstr "" -#: ardour_ui2.cc:388 ardour_ui2.cc:825 ardour_ui2.cc:847 +#: ardour_ui2.cc:389 ardour_ui2.cc:835 ardour_ui2.cc:857 msgid "wheel" msgstr "roulette" -#: ardour_ui2.cc:450 +#: ardour_ui2.cc:451 msgid "ardour: clock" msgstr "ardour : horloge" -#: ardour_ui2.cc:595 +#: ardour_ui2.cc:596 #, fuzzy msgid "Maximum speed" msgstr "varispeed" -#: ardour_ui2.cc:813 +#: ardour_ui2.cc:823 msgid "st" msgstr "er" -#: ardour_ui2.cc:857 ardour_ui2.cc:880 ardour_ui2.cc:897 +#: ardour_ui2.cc:867 ardour_ui2.cc:890 ardour_ui2.cc:907 msgid "stopped" msgstr "arrêté" -#: ardour_ui_dialogs.cc:152 playlist_selector.cc:69 +#: ardour_ui_dialogs.cc:153 playlist_selector.cc:70 #, fuzzy msgid "close" msgstr "Fermer" -#: ardour_ui_dialogs.cc:359 ardour_ui_ed.cc:181 +#: ardour_ui_dialogs.cc:360 ardour_ui_ed.cc:184 #, fuzzy msgid "Sound File Browser" msgstr "Bibliothèque audio" #. menus + submenus that need action items -#: ardour_ui_ed.cc:69 +#: ardour_ui_ed.cc:72 msgid "Session" msgstr "Session" -#: ardour_ui_ed.cc:70 ardour_ui_ed.cc:127 editor.cc:1843 export_dialog.cc:350 +#: ardour_ui_ed.cc:73 ardour_ui_ed.cc:130 editor.cc:1836 export_dialog.cc:350 #: export_dialog.cc:1059 export_dialog.cc:1063 msgid "Export" msgstr "Exporter" -#: ardour_ui_ed.cc:71 +#: ardour_ui_ed.cc:74 msgid "Cleanup" msgstr "Nettoyer" -#: ardour_ui_ed.cc:72 option_editor.cc:125 +#: ardour_ui_ed.cc:75 option_editor.cc:126 msgid "Sync" msgstr "Synchro." -#: ardour_ui_ed.cc:73 ardour_ui_ed.cc:74 +#: ardour_ui_ed.cc:76 ardour_ui_ed.cc:77 #, fuzzy msgid "Options" msgstr "Éditeur d'options" -#: ardour_ui_ed.cc:75 +#: ardour_ui_ed.cc:78 msgid "Help" msgstr "" -#: ardour_ui_ed.cc:76 +#: ardour_ui_ed.cc:79 msgid "KeyMouse Actions" msgstr "" -#: ardour_ui_ed.cc:77 +#: ardour_ui_ed.cc:80 #, fuzzy msgid "Audio File Format" msgstr "Trames audio" -#: ardour_ui_ed.cc:78 +#: ardour_ui_ed.cc:81 #, fuzzy msgid "Header" msgstr "Pré fader" -#: ardour_ui_ed.cc:79 +#: ardour_ui_ed.cc:82 msgid "Data" msgstr "" -#: ardour_ui_ed.cc:80 +#: ardour_ui_ed.cc:83 #, fuzzy msgid "Control Surfaces" msgstr "Sorties de contrôle" #. the real actions -#: ardour_ui_ed.cc:84 audio_time_axis.cc:1856 new_session_dialog.cc:342 +#: ardour_ui_ed.cc:87 audio_time_axis.cc:1854 new_session_dialog.cc:529 msgid "New" msgstr "Nouveau" -#: ardour_ui_ed.cc:86 new_session_dialog.cc:334 +#: ardour_ui_ed.cc:89 new_session_dialog.cc:517 msgid "Open" msgstr "Ouvrir" -#: ardour_ui_ed.cc:87 +#: ardour_ui_ed.cc:90 msgid "Recent" msgstr "Récent" -#: ardour_ui_ed.cc:88 io_selector.cc:57 io_selector.cc:791 +#: ardour_ui_ed.cc:91 io_selector.cc:58 io_selector.cc:792 msgid "Close" msgstr "Fermer" -#: ardour_ui_ed.cc:91 route_params_ui.cc:512 +#: ardour_ui_ed.cc:94 route_params_ui.cc:514 msgid "Add Track/Bus" msgstr "Ajouter piste/bus" -#: ardour_ui_ed.cc:102 +#: ardour_ui_ed.cc:105 msgid "Connect" msgstr "Connecter" #. -#: ardour_ui_ed.cc:110 +#: ardour_ui_ed.cc:113 msgid "Snapshot" msgstr "Instantané" -#: ardour_ui_ed.cc:113 +#: ardour_ui_ed.cc:116 msgid "Save Template..." msgstr "Enregistrer le modèle..." -#: ardour_ui_ed.cc:116 +#: ardour_ui_ed.cc:119 msgid "Export session to audiofile..." msgstr "Exporter la session dans un fichier audio..." -#: ardour_ui_ed.cc:119 +#: ardour_ui_ed.cc:122 #, fuzzy msgid "Export selection to audiofile..." msgstr "Exporter la session dans un fichier audio..." -#: ardour_ui_ed.cc:123 +#: ardour_ui_ed.cc:126 #, fuzzy msgid "Export range markers to audiofile..." msgstr "Exporter la range dans un fichier audio..." -#: ardour_ui_ed.cc:130 +#: ardour_ui_ed.cc:133 msgid "Cleanup unused sources" msgstr "Nettoyer les sources inutilisées" -#: ardour_ui_ed.cc:132 +#: ardour_ui_ed.cc:135 msgid "Flush wastebasket" msgstr "Vider la corbeille" -#: ardour_ui_ed.cc:138 ardour_ui_options.cc:381 ardour_ui_options.cc:390 -#: ardour_ui_options.cc:462 +#: ardour_ui_ed.cc:141 ardour_ui_options.cc:408 ardour_ui_options.cc:417 +#: ardour_ui_options.cc:489 msgid "JACK" msgstr "JACK" -#: ardour_ui_ed.cc:139 +#: ardour_ui_ed.cc:142 msgid "Latency" msgstr "Latence" -#: ardour_ui_ed.cc:141 +#: ardour_ui_ed.cc:144 msgid "Reconnect" msgstr "Reconnecter" -#: ardour_ui_ed.cc:144 mixer_strip.cc:514 mixer_strip.cc:574 +#: ardour_ui_ed.cc:147 mixer_strip.cc:497 mixer_strip.cc:565 msgid "Disconnect" msgstr "Déconnecter" -#: ardour_ui_ed.cc:171 +#: ardour_ui_ed.cc:174 msgid "Windows" msgstr "Fenêtres" -#: ardour_ui_ed.cc:172 +#: ardour_ui_ed.cc:175 msgid "start prefix" msgstr "" -#: ardour_ui_ed.cc:173 +#: ardour_ui_ed.cc:176 msgid "Quit" msgstr "Quitter" #. windows visibility actions -#: ardour_ui_ed.cc:177 +#: ardour_ui_ed.cc:180 msgid "Maximise Editor Space" msgstr "" -#: ardour_ui_ed.cc:179 +#: ardour_ui_ed.cc:182 #, fuzzy msgid "Show Editor" msgstr "Éditeur" -#: ardour_ui_ed.cc:180 +#: ardour_ui_ed.cc:183 #, fuzzy msgid "Show Mixer" msgstr "Console de mixage" -#: ardour_ui_ed.cc:182 +#: ardour_ui_ed.cc:185 msgid "Options Editor" msgstr "Éditeur d'options" -#: ardour_ui_ed.cc:183 +#: ardour_ui_ed.cc:186 msgid "Track/Bus Inspector" msgstr "Inspecteur de pistes/bus" -#: ardour_ui_ed.cc:185 +#: ardour_ui_ed.cc:188 msgid "Connections" msgstr "Connexions" -#: ardour_ui_ed.cc:187 +#: ardour_ui_ed.cc:190 msgid "Locations" msgstr "Emplacements" -#: ardour_ui_ed.cc:189 +#: ardour_ui_ed.cc:192 msgid "Big Clock" msgstr "Grande horloge" -#: ardour_ui_ed.cc:191 +#: ardour_ui_ed.cc:194 msgid "About" msgstr "À propos" -#: ardour_ui_ed.cc:192 +#: ardour_ui_ed.cc:195 #, fuzzy msgid "Colors" msgstr "Couleur" -#: ardour_ui_ed.cc:194 +#: ardour_ui_ed.cc:197 #, fuzzy msgid "Add Audio Track" msgstr "Ajouter piste/bus" -#: ardour_ui_ed.cc:196 +#: ardour_ui_ed.cc:199 #, fuzzy msgid "Add Audio Bus" msgstr "Cacher tous les BusAudio" -#: ardour_ui_ed.cc:198 +#: ardour_ui_ed.cc:201 msgid "Save" msgstr "Enregistrer" -#: ardour_ui_ed.cc:200 editor_actions.cc:254 +#: ardour_ui_ed.cc:203 editor_actions.cc:255 #, fuzzy msgid "Remove Last Capture" msgstr "Enlever la dernière capture" #. do-nothing action for the "transport" menu bar item -#: ardour_ui_ed.cc:207 +#: ardour_ui_ed.cc:210 #, fuzzy msgid "Transport" msgstr "Traducteurs" @@ -1060,74 +1038,74 @@ msgstr "Traducteurs" #. these two are not used by key bindings, instead use ToggleRoll for that. these two do show up in #. menus and via button proxies. #. -#: ardour_ui_ed.cc:213 sfdb_ui.cc:57 +#: ardour_ui_ed.cc:216 sfdb_ui.cc:57 msgid "Stop" msgstr "Arrêter" -#: ardour_ui_ed.cc:216 +#: ardour_ui_ed.cc:219 msgid "Roll" msgstr "" -#: ardour_ui_ed.cc:220 +#: ardour_ui_ed.cc:223 #, fuzzy msgid "Start/Stop" msgstr "Début :" -#: ardour_ui_ed.cc:223 +#: ardour_ui_ed.cc:226 msgid "Stop + Forget Capture" msgstr "" -#: ardour_ui_ed.cc:226 +#: ardour_ui_ed.cc:229 #, fuzzy msgid "Play Loop Range" msgstr "Jouer l'intervalle de boucle" -#: ardour_ui_ed.cc:229 +#: ardour_ui_ed.cc:232 #, fuzzy msgid "Play Selection" msgstr "Jouer l'emplacement sélectionné" -#: ardour_ui_ed.cc:233 +#: ardour_ui_ed.cc:236 #, fuzzy msgid "Enable Record" msgstr "Enregistrer" -#: ardour_ui_ed.cc:236 +#: ardour_ui_ed.cc:239 #, fuzzy msgid "Rewind" msgstr "Région" -#: ardour_ui_ed.cc:239 +#: ardour_ui_ed.cc:242 msgid "Rewind (Slow)" msgstr "" -#: ardour_ui_ed.cc:242 +#: ardour_ui_ed.cc:245 msgid "Rewind (Fast)" msgstr "" -#: ardour_ui_ed.cc:245 +#: ardour_ui_ed.cc:248 #, fuzzy msgid "Forward" msgstr "décaler vers l'avant" -#: ardour_ui_ed.cc:248 +#: ardour_ui_ed.cc:251 msgid "Forward (Slow)" msgstr "" -#: ardour_ui_ed.cc:251 +#: ardour_ui_ed.cc:254 msgid "Forward (Fast)" msgstr "" -#: ardour_ui_ed.cc:254 +#: ardour_ui_ed.cc:257 msgid "Goto Zero" msgstr "" -#: ardour_ui_ed.cc:257 +#: ardour_ui_ed.cc:260 #, fuzzy msgid "Goto Start" msgstr "Début :" -#: ardour_ui_ed.cc:260 +#: ardour_ui_ed.cc:263 msgid "Goto End" msgstr "" @@ -1135,29 +1113,29 @@ msgstr "" #. that proxies for these action to be more compact. It would be nice to find a way to override the action #. name appearance on the buttons. #. -#: ardour_ui_ed.cc:269 -#, fuzzy -msgid "" -"Punch\n" -"in" -msgstr "" -"punch\n" -"in" - #: ardour_ui_ed.cc:272 #, fuzzy msgid "" "Punch\n" +"in" +msgstr "" +"punch\n" +"in" + +#: ardour_ui_ed.cc:275 +#, fuzzy +msgid "" +"Punch\n" "out" msgstr "" "punch\n" "out" -#: ardour_ui_ed.cc:275 option_editor.cc:128 +#: ardour_ui_ed.cc:278 option_editor.cc:129 msgid "Click" msgstr "Clic" -#: ardour_ui_ed.cc:278 +#: ardour_ui_ed.cc:281 #, fuzzy msgid "" "Auto\n" @@ -1166,7 +1144,7 @@ msgstr "" "entrée\n" "auto." -#: ardour_ui_ed.cc:281 +#: ardour_ui_ed.cc:284 #, fuzzy msgid "" "Auto\n" @@ -1175,7 +1153,7 @@ msgstr "" "lecture\n" "auto." -#: ardour_ui_ed.cc:284 +#: ardour_ui_ed.cc:287 #, fuzzy msgid "" "Auto\n" @@ -1184,285 +1162,285 @@ msgstr "" "retour\n" "auto" -#: ardour_ui_ed.cc:288 +#: ardour_ui_ed.cc:291 #, fuzzy msgid "" "Time\n" "master" msgstr "JACK horloge maître" -#: ardour_ui_ed.cc:291 +#: ardour_ui_ed.cc:294 msgid "Toggle Record Enable Track1" msgstr "" -#: ardour_ui_ed.cc:293 +#: ardour_ui_ed.cc:296 msgid "Toggle Record Enable Track2" msgstr "" -#: ardour_ui_ed.cc:295 +#: ardour_ui_ed.cc:298 msgid "Toggle Record Enable Track3" msgstr "" -#: ardour_ui_ed.cc:297 +#: ardour_ui_ed.cc:300 msgid "Toggle Record Enable Track4" msgstr "" -#: ardour_ui_ed.cc:299 +#: ardour_ui_ed.cc:302 msgid "Toggle Record Enable Track5" msgstr "" -#: ardour_ui_ed.cc:301 +#: ardour_ui_ed.cc:304 msgid "Toggle Record Enable Track6" msgstr "" -#: ardour_ui_ed.cc:303 +#: ardour_ui_ed.cc:306 msgid "Toggle Record Enable Track7" msgstr "" -#: ardour_ui_ed.cc:305 +#: ardour_ui_ed.cc:308 msgid "Toggle Record Enable Track8" msgstr "" -#: ardour_ui_ed.cc:307 +#: ardour_ui_ed.cc:310 msgid "Toggle Record Enable Track9" msgstr "" -#: ardour_ui_ed.cc:309 +#: ardour_ui_ed.cc:312 msgid "Toggle Record Enable Track10" msgstr "" -#: ardour_ui_ed.cc:311 +#: ardour_ui_ed.cc:314 msgid "Toggle Record Enable Track11" msgstr "" -#: ardour_ui_ed.cc:313 +#: ardour_ui_ed.cc:316 msgid "Toggle Record Enable Track12" msgstr "" -#: ardour_ui_ed.cc:315 +#: ardour_ui_ed.cc:318 msgid "Toggle Record Enable Track13" msgstr "" -#: ardour_ui_ed.cc:317 +#: ardour_ui_ed.cc:320 msgid "Toggle Record Enable Track14" msgstr "" -#: ardour_ui_ed.cc:319 +#: ardour_ui_ed.cc:322 msgid "Toggle Record Enable Track15" msgstr "" -#: ardour_ui_ed.cc:321 +#: ardour_ui_ed.cc:324 msgid "Toggle Record Enable Track16" msgstr "" -#: ardour_ui_ed.cc:323 +#: ardour_ui_ed.cc:326 msgid "Toggle Record Enable Track17" msgstr "" -#: ardour_ui_ed.cc:325 +#: ardour_ui_ed.cc:328 msgid "Toggle Record Enable Track18" msgstr "" -#: ardour_ui_ed.cc:327 +#: ardour_ui_ed.cc:330 msgid "Toggle Record Enable Track19" msgstr "" -#: ardour_ui_ed.cc:329 +#: ardour_ui_ed.cc:332 msgid "Toggle Record Enable Track20" msgstr "" -#: ardour_ui_ed.cc:331 +#: ardour_ui_ed.cc:334 msgid "Toggle Record Enable Track21" msgstr "" -#: ardour_ui_ed.cc:333 +#: ardour_ui_ed.cc:336 msgid "Toggle Record Enable Track22" msgstr "" -#: ardour_ui_ed.cc:335 +#: ardour_ui_ed.cc:338 msgid "Toggle Record Enable Track23" msgstr "" -#: ardour_ui_ed.cc:337 +#: ardour_ui_ed.cc:340 msgid "Toggle Record Enable Track24" msgstr "" -#: ardour_ui_ed.cc:339 +#: ardour_ui_ed.cc:342 msgid "Toggle Record Enable Track25" msgstr "" -#: ardour_ui_ed.cc:341 +#: ardour_ui_ed.cc:344 msgid "Toggle Record Enable Track26" msgstr "" -#: ardour_ui_ed.cc:343 +#: ardour_ui_ed.cc:346 msgid "Toggle Record Enable Track27" msgstr "" -#: ardour_ui_ed.cc:345 +#: ardour_ui_ed.cc:348 msgid "Toggle Record Enable Track28" msgstr "" -#: ardour_ui_ed.cc:347 +#: ardour_ui_ed.cc:350 msgid "Toggle Record Enable Track29" msgstr "" -#: ardour_ui_ed.cc:349 +#: ardour_ui_ed.cc:352 msgid "Toggle Record Enable Track30" msgstr "" -#: ardour_ui_ed.cc:351 +#: ardour_ui_ed.cc:354 msgid "Toggle Record Enable Track31" msgstr "" -#: ardour_ui_ed.cc:353 +#: ardour_ui_ed.cc:356 msgid "Toggle Record Enable Track32" msgstr "" -#: ardour_ui_ed.cc:358 +#: ardour_ui_ed.cc:361 msgid "Percentage" msgstr "Pourcentage" -#: ardour_ui_ed.cc:359 +#: ardour_ui_ed.cc:362 msgid "Semitones" msgstr "Demi-tons" -#: ardour_ui_ed.cc:363 +#: ardour_ui_ed.cc:366 msgid "Send MTC" msgstr "Envoyer MTC" -#: ardour_ui_ed.cc:365 +#: ardour_ui_ed.cc:368 msgid "Send MMC" msgstr "Envoyer MMC" -#: ardour_ui_ed.cc:367 +#: ardour_ui_ed.cc:370 #, fuzzy msgid "Use MMC" msgstr "Envoyer MMC" -#: ardour_ui_ed.cc:369 +#: ardour_ui_ed.cc:372 #, fuzzy msgid "Send MIDI feedback" msgstr "Envoyer le retour de paramètre MIDI" -#: ardour_ui_ed.cc:371 +#: ardour_ui_ed.cc:374 #, fuzzy msgid "Use MIDI control" msgstr "Port MMC" -#: ardour_ui_ed.cc:374 +#: ardour_ui_ed.cc:377 #, fuzzy -msgid "Connect newtrack inputs to hardware" +msgid "Connect new track inputs to hardware" msgstr "Auto-connexion des nouvelles pistes" -#: ardour_ui_ed.cc:392 +#: ardour_ui_ed.cc:396 #, fuzzy msgid "Connect new track outputs to hardware" msgstr "Auto-connexion des nouvelles pistes" -#: ardour_ui_ed.cc:394 +#: ardour_ui_ed.cc:398 #, fuzzy msgid "Connect new track outputs to master" msgstr "connecter les sorties de piste aux sorties maître automatiquement" -#: ardour_ui_ed.cc:396 +#: ardour_ui_ed.cc:400 #, fuzzy msgid "Manually connect new track outputs" msgstr "connecter les sorties de piste manuellement" -#: ardour_ui_ed.cc:401 +#: ardour_ui_ed.cc:405 #, fuzzy msgid "Hardware monitoring" msgstr "Utiliser la pré-écoute matérielle" -#: ardour_ui_ed.cc:402 +#: ardour_ui_ed.cc:406 #, fuzzy msgid "Software monitoring" msgstr "Utiliser la pré-écoute logicielle" -#: ardour_ui_ed.cc:403 +#: ardour_ui_ed.cc:407 #, fuzzy msgid "External monitoring" msgstr "Utiliser la pré-écoute matérielle" #. Configuration object options (i.e. not session specific) -#: ardour_ui_ed.cc:407 +#: ardour_ui_ed.cc:411 msgid "Stop plugins with transport" msgstr "Arrêter les greffons avec le transport" -#: ardour_ui_ed.cc:408 +#: ardour_ui_ed.cc:412 #, fuzzy msgid "Verify remove last capture" msgstr "Enlever la dernière capture" -#: ardour_ui_ed.cc:409 +#: ardour_ui_ed.cc:413 msgid "Stop recording on xrun" msgstr "Arrêter l'enregistrement en cas de xrun" -#: ardour_ui_ed.cc:410 +#: ardour_ui_ed.cc:414 #, fuzzy msgid "Stop transport at session end" msgstr "Arrêter le transport à la fin de la session" -#: ardour_ui_ed.cc:411 +#: ardour_ui_ed.cc:415 msgid "-12dB gain reduce ffwd/rewind" msgstr "" -#: ardour_ui_ed.cc:412 +#: ardour_ui_ed.cc:416 msgid "Rec-enable stays engaged at stop" msgstr "" #. session options -#: ardour_ui_ed.cc:416 +#: ardour_ui_ed.cc:420 #, fuzzy msgid "Do not run plugins while recording" msgstr "Activer les greffons durant l'enregistrement" -#: ardour_ui_ed.cc:419 +#: ardour_ui_ed.cc:423 #, fuzzy msgid "Latched solo" msgstr "Solo collé" -#: ardour_ui_ed.cc:424 +#: ardour_ui_ed.cc:428 #, fuzzy msgid "Solo in-place" msgstr "Solo-safe" -#: ardour_ui_ed.cc:426 +#: ardour_ui_ed.cc:430 msgid "Solo via bus" msgstr "Solo via le bus" -#: ardour_ui_ed.cc:429 +#: ardour_ui_ed.cc:433 msgid "Automatically create crossfades" msgstr "Créer des fondus enchaînés automatiquement" -#: ardour_ui_ed.cc:431 +#: ardour_ui_ed.cc:435 #, fuzzy msgid "Unmute new full crossfades" msgstr "Montrer tous les fondus enchaînés" -#: ardour_ui_options.cc:379 ardour_ui_options.cc:389 ardour_ui_options.cc:456 +#: ardour_ui_options.cc:406 ardour_ui_options.cc:416 ardour_ui_options.cc:483 msgid "Internal" msgstr "Interne" -#: ardour_ui_options.cc:380 ardour_ui_options.cc:459 +#: ardour_ui_options.cc:407 ardour_ui_options.cc:486 #, fuzzy msgid "MTC" msgstr "TOC" -#: audio_clock.cc:1719 editor.cc:185 +#: audio_clock.cc:1742 editor.cc:188 msgid "SMPTE" msgstr "SMPTE" -#: audio_clock.cc:1720 editor.cc:184 editor_rulers.cc:359 +#: audio_clock.cc:1743 editor.cc:187 editor_rulers.cc:360 msgid "Bars:Beats" msgstr "Mesures:Temps" -#: audio_clock.cc:1721 +#: audio_clock.cc:1744 msgid "Minutes:Seconds" msgstr "Minutes:Secondes" -#: audio_clock.cc:1722 +#: audio_clock.cc:1745 msgid "Audio Frames" msgstr "Trames audio" @@ -1470,294 +1448,315 @@ msgstr "Trames audio" #. Slowest = 6.6dB/sec falloff at update rate of 40ms #. Slow = 6.8dB/sec falloff at update rate of 40ms #. -#: audio_clock.cc:1723 editor_actions.cc:374 editor_actions.cc:382 +#: audio_clock.cc:1746 editor_actions.cc:375 editor_actions.cc:383 +#: gain_meter.cc:172 panner_ui.cc:89 plugin_ui.cc:392 plugin_ui.cc:635 msgid "Off" msgstr "Arrêt" -#: audio_clock.cc:1725 +#: audio_clock.cc:1748 msgid "Mode" msgstr "Mode" -#: audio_time_axis.cc:90 mixer_strip.cc:458 +#: audio_time_axis.cc:91 msgid "m" msgstr "m" -#: audio_time_axis.cc:90 mixer_strip.cc:459 +#: audio_time_axis.cc:91 msgid "s" msgstr "s" -#: audio_time_axis.cc:90 +#: audio_time_axis.cc:91 msgid "r" msgstr "r" -#: audio_time_axis.cc:94 +#: audio_time_axis.cc:95 msgid "g" msgstr "g" #. group -#: audio_time_axis.cc:95 +#: audio_time_axis.cc:96 msgid "p" msgstr "p" -#: audio_time_axis.cc:96 automation_time_axis.cc:31 visual_time_axis.cc:73 +#: audio_time_axis.cc:97 automation_time_axis.cc:32 visual_time_axis.cc:74 msgid "h" msgstr "h" #. height -#: audio_time_axis.cc:97 +#: audio_time_axis.cc:98 msgid "a" msgstr "a" -#: audio_time_axis.cc:98 visual_time_axis.cc:72 +#: audio_time_axis.cc:99 visual_time_axis.cc:73 msgid "v" msgstr "v" -#: audio_time_axis.cc:173 +#: audio_time_axis.cc:168 mixer_strip.cc:86 msgid "Record" msgstr "Enregistrer" -#: audio_time_axis.cc:174 editor_actions.cc:36 +#: audio_time_axis.cc:169 editor_actions.cc:37 mixer_strip.cc:86 msgid "Solo" msgstr "Solo" -#: audio_time_axis.cc:175 editor.cc:1767 editor.cc:1866 panner_ui.cc:385 +#: audio_time_axis.cc:170 editor.cc:1760 editor.cc:1859 mixer_strip.cc:86 +#: panner_ui.cc:427 msgid "Mute" msgstr "Muet" -#: audio_time_axis.cc:176 +#: audio_time_axis.cc:171 msgid "Edit Group" msgstr "Groupe d'édition" -#: audio_time_axis.cc:177 visual_time_axis.cc:91 +#: audio_time_axis.cc:172 visual_time_axis.cc:92 msgid "Display Height" msgstr "Hauteur de l'affichage" -#: audio_time_axis.cc:178 +#: audio_time_axis.cc:173 msgid "Playlist" msgstr "Liste de lecture" -#: audio_time_axis.cc:179 audio_time_axis.cc:743 +#: audio_time_axis.cc:174 audio_time_axis.cc:741 msgid "Automation" msgstr "Automatisation" -#: audio_time_axis.cc:180 visual_time_axis.cc:92 +#: audio_time_axis.cc:175 visual_time_axis.cc:93 msgid "Visual options" msgstr "Options d'affichage" -#: audio_time_axis.cc:181 visual_time_axis.cc:93 +#: audio_time_axis.cc:176 visual_time_axis.cc:94 msgid "Hide this track" msgstr "Cacher cette piste" -#: audio_time_axis.cc:337 +#: audio_time_axis.cc:333 mixer_strip.cc:927 msgid "No group" msgstr "Pas de groupe" -#: audio_time_axis.cc:704 automation_time_axis.cc:448 -#: imageframe_time_axis.cc:256 marker_time_axis.cc:210 +#: audio_time_axis.cc:702 automation_time_axis.cc:450 +#: imageframe_time_axis.cc:255 marker_time_axis.cc:211 msgid "Height" msgstr "Hauteur" -#: audio_time_axis.cc:705 color_manager.cc:40 imageframe_time_axis.cc:257 -#: marker_time_axis.cc:211 +#: audio_time_axis.cc:703 color_manager.cc:41 imageframe_time_axis.cc:256 +#: marker_time_axis.cc:212 msgid "Color" msgstr "Couleur" -#: audio_time_axis.cc:709 +#: audio_time_axis.cc:707 #, fuzzy msgid "Hide all crossfades" msgstr "Cacher tous les fondus enchaînés" -#: audio_time_axis.cc:710 +#: audio_time_axis.cc:708 #, fuzzy msgid "Show all crossfades" msgstr "Montrer tous les fondus enchaînés" -#: audio_time_axis.cc:714 mixer_strip.cc:1236 +#: audio_time_axis.cc:712 mixer_strip.cc:1011 #, fuzzy msgid "Remote Control ID" msgstr "Enlever le point de contrôle" -#: audio_time_axis.cc:720 -msgid "show all automation" +#: audio_time_axis.cc:718 +#, fuzzy +msgid "Show all automation" msgstr "montrer toute l'automatisation" -#: audio_time_axis.cc:723 -msgid "show existing automation" +#: audio_time_axis.cc:721 +#, fuzzy +msgid "Show existing automation" msgstr "montrer l'automatisation existante" -#: audio_time_axis.cc:726 -msgid "hide all automation" +#: audio_time_axis.cc:724 +#, fuzzy +msgid "Hide all automation" msgstr "cacher toute l'automatisation" -#: audio_time_axis.cc:731 audio_time_axis.cc:1169 editor.cc:215 -msgid "gain" -msgstr "gain" +#: audio_time_axis.cc:729 +#, fuzzy +msgid "Fader" +msgstr "Fondu" -#: audio_time_axis.cc:736 audio_time_axis.cc:1209 -msgid "pan" +#: audio_time_axis.cc:734 +#, fuzzy +msgid "Pan" msgstr "panoramique" -#: audio_time_axis.cc:741 +#: audio_time_axis.cc:739 msgid "Plugins" msgstr "Greffons" -#: audio_time_axis.cc:749 +#: audio_time_axis.cc:747 msgid "Show waveforms" msgstr "Montrer les formes d'onde" -#: audio_time_axis.cc:757 +#: audio_time_axis.cc:755 msgid "Traditional" msgstr "Traditionnel" -#: audio_time_axis.cc:760 +#: audio_time_axis.cc:758 msgid "Rectified" msgstr "Rectifié" -#: audio_time_axis.cc:763 +#: audio_time_axis.cc:761 msgid "Waveform" msgstr "Forme d'onde" -#: audio_time_axis.cc:773 -msgid "align with existing material" +#: audio_time_axis.cc:771 +msgid "Align with existing material" msgstr "" -#: audio_time_axis.cc:778 -msgid "align with capture time" +#: audio_time_axis.cc:776 +msgid "Align with capture time" msgstr "" -#: audio_time_axis.cc:784 +#: audio_time_axis.cc:782 #, fuzzy msgid "Alignment" msgstr "Aligner" -#: audio_time_axis.cc:790 editor.cc:523 editor_actions.cc:59 -#: mixer_strip.cc:1225 +#: audio_time_axis.cc:788 editor.cc:527 editor_actions.cc:60 +#: mixer_strip.cc:1000 mixer_ui.cc:111 msgid "Active" msgstr "Actif" -#: audio_time_axis.cc:795 editor.cc:1929 editor_actions.cc:319 -#: editor_markers.cc:507 imageframe_time_axis.cc:260 location_ui.cc:56 -#: marker_time_axis.cc:214 mixer_strip.cc:1239 +#: audio_time_axis.cc:793 editor.cc:1922 editor_actions.cc:320 +#: editor_markers.cc:508 imageframe_time_axis.cc:259 location_ui.cc:57 +#: marker_time_axis.cc:215 mixer_strip.cc:1014 msgid "Remove" msgstr "Enlever" -#: audio_time_axis.cc:835 +#: audio_time_axis.cc:833 msgid "Name for playlist" msgstr "Nom de la liste de lecture" -#: audio_time_axis.cc:837 audio_time_axis.cc:1853 editor_markers.cc:826 -#: editor_mouse.cc:4609 imageframe_time_axis.cc:249 marker_time_axis.cc:207 -#: meter_bridge_strip.cc:223 mixer_strip.cc:1223 redirect_box.cc:749 -#: redirect_box.cc:1063 route_ui.cc:732 visual_time_axis.cc:325 +#: audio_time_axis.cc:835 audio_time_axis.cc:1851 editor_markers.cc:827 +#: editor_mouse.cc:4673 imageframe_time_axis.cc:248 marker_time_axis.cc:208 +#: meter_bridge_strip.cc:224 mixer_strip.cc:998 redirect_box.cc:751 +#: redirect_box.cc:1065 route_ui.cc:739 visual_time_axis.cc:326 msgid "Rename" msgstr "Renommer" -#: audio_time_axis.cc:870 audio_time_axis.cc:910 +#: audio_time_axis.cc:868 audio_time_axis.cc:908 #, fuzzy msgid "Name for Playlist" msgstr "Nom de la liste de lecture" -#: audio_time_axis.cc:1128 visual_time_axis.cc:382 +#: audio_time_axis.cc:1126 visual_time_axis.cc:383 msgid "a track already exists with that name" msgstr "une piste avec le même nom existe déjà" -#: audio_time_axis.cc:1412 editor.cc:1490 selection.cc:622 +#: audio_time_axis.cc:1167 editor.cc:218 +msgid "gain" +msgstr "gain" + +#: audio_time_axis.cc:1207 +msgid "pan" +msgstr "panoramique" + +#: audio_time_axis.cc:1410 editor.cc:1483 selection.cc:634 msgid "programming error: " msgstr "erreur de programmation : " -#: audio_time_axis.cc:1850 +#: audio_time_axis.cc:1848 msgid "Current: %1" msgstr "Courant : %1" -#: audio_time_axis.cc:1857 +#: audio_time_axis.cc:1855 msgid "New Copy" msgstr "Nouvelle copie" -#: audio_time_axis.cc:1859 +#: audio_time_axis.cc:1857 #, fuzzy msgid "Clear Current" msgstr "Effacer courante" -#: audio_time_axis.cc:1861 editor.cc:2031 editor.cc:2107 +#: audio_time_axis.cc:1859 editor.cc:2024 editor.cc:2100 msgid "Select" msgstr "Sélectionner" -#: automation_line.cc:883 +#: automation_line.cc:884 #, fuzzy msgid "automation event move" msgstr "déplacement d'évenement d'automatisation" -#: automation_line.cc:885 +#: automation_line.cc:886 #, fuzzy msgid "automation range drag" msgstr "déplacement d'intervalle d'automatisation" -#: automation_line.cc:1014 region_gain_line.cc:61 +#: automation_line.cc:1015 region_gain_line.cc:62 #, fuzzy msgid "remove control point" msgstr "Enlever le point de contrôle" -#: automation_time_axis.cc:32 editor_ops.cc:2813 +#: automation_time_axis.cc:33 editor_ops.cc:2885 msgid "clear" msgstr "effacer" -#: automation_time_axis.cc:74 +#: automation_time_axis.cc:75 msgid "track height" msgstr "" -#: automation_time_axis.cc:75 +#: automation_time_axis.cc:76 #, fuzzy msgid "automation state" msgstr "état de l'automatisation de panoramique" -#: automation_time_axis.cc:76 +#: automation_time_axis.cc:77 #, fuzzy msgid "clear track" msgstr "effacer les intervalles" -#: automation_time_axis.cc:77 +#: automation_time_axis.cc:78 #, fuzzy msgid "hide track" msgstr "décaler la piste" -#: automation_time_axis.cc:185 automation_time_axis.cc:223 -#: automation_time_axis.cc:463 mixer_strip.cc:176 mixer_strip.cc:188 -#: plugin_ui.cc:394 plugin_ui.cc:636 region_editor.cc:53 -msgid "play" -msgstr "jouer" +#: automation_time_axis.cc:184 automation_time_axis.cc:213 +#: automation_time_axis.cc:461 +msgid "Manual" +msgstr "" -#: automation_time_axis.cc:187 automation_time_axis.cc:234 -#: automation_time_axis.cc:467 mixer_strip.cc:178 mixer_strip.cc:190 -#: plugin_ui.cc:397 plugin_ui.cc:638 -msgid "write" +#: automation_time_axis.cc:186 automation_time_axis.cc:224 +#: automation_time_axis.cc:465 editor.cc:2001 editor.cc:2082 gain_meter.cc:174 +#: panner_ui.cc:91 plugin_ui.cc:395 plugin_ui.cc:637 sfdb_ui.cc:56 +msgid "Play" +msgstr "Jouer" + +#: automation_time_axis.cc:188 automation_time_axis.cc:235 +#: automation_time_axis.cc:469 gain_meter.cc:176 panner_ui.cc:93 +#: plugin_ui.cc:398 plugin_ui.cc:639 +#, fuzzy +msgid "Write" msgstr "écrire" -#: automation_time_axis.cc:189 automation_time_axis.cc:245 -#: automation_time_axis.cc:471 mixer_strip.cc:180 mixer_strip.cc:192 -#: mixer_strip.cc:887 plugin_ui.cc:400 plugin_ui.cc:640 +#: automation_time_axis.cc:190 automation_time_axis.cc:246 +#: automation_time_axis.cc:473 gain_meter.cc:178 panner_ui.cc:95 +#: plugin_ui.cc:401 plugin_ui.cc:641 #, fuzzy -msgid "touch" +msgid "Touch" msgstr "toucher" -#: automation_time_axis.cc:256 option_editor.cc:182 option_editor.cc:188 -#: plugin_ui.cc:403 +#: automation_time_axis.cc:257 option_editor.cc:183 option_editor.cc:189 +#: plugin_ui.cc:404 msgid "???" msgstr "???" -#: automation_time_axis.cc:270 +#: automation_time_axis.cc:271 #, fuzzy msgid "clear automation" msgstr "effacer l'automatisation" -#: automation_time_axis.cc:450 editor_actions.cc:317 +#: automation_time_axis.cc:452 editor_actions.cc:318 msgid "Hide" msgstr "Cacher" -#: automation_time_axis.cc:452 crossfade_edit.cc:76 redirect_box.cc:1055 +#: automation_time_axis.cc:454 crossfade_edit.cc:78 redirect_box.cc:1057 msgid "Clear" msgstr "Effacer" -#: automation_time_axis.cc:475 +#: automation_time_axis.cc:477 msgid "State" msgstr "État" @@ -1904,822 +1903,809 @@ msgstr "" msgid "color of fill" msgstr "" -#: color_manager.cc:39 +#: color_manager.cc:40 #, fuzzy msgid "Object" msgstr "objet" -#: color_manager.cc:77 +#: color_manager.cc:78 #, fuzzy msgid "cannot open color definition file %1: %2" msgstr "impossible d'ouvrir l'image de l'écran de démarrage \"%1\"" -#: crossfade_edit.cc:73 +#: crossfade_edit.cc:75 msgid "ardour: x-fade edit" msgstr "ardour : édition fondu enchaîné" -#: crossfade_edit.cc:77 panner_ui.cc:401 +#: crossfade_edit.cc:79 panner_ui.cc:443 msgid "Reset" msgstr "Réinitialiser" -#: crossfade_edit.cc:78 +#: crossfade_edit.cc:80 msgid "Fade" msgstr "Fondu" -#: crossfade_edit.cc:79 +#: crossfade_edit.cc:81 #, fuzzy msgid "Out (dry)" msgstr "Sortie (sec)" -#: crossfade_edit.cc:80 +#: crossfade_edit.cc:82 #, fuzzy msgid "Out" msgstr "Sortie" -#: crossfade_edit.cc:81 +#: crossfade_edit.cc:83 #, fuzzy msgid "In (dry)" msgstr "Entrée (sec)" -#: crossfade_edit.cc:82 +#: crossfade_edit.cc:84 msgid "In" msgstr "Entrée" -#: crossfade_edit.cc:84 +#: crossfade_edit.cc:86 #, fuzzy msgid "With Pre-roll" msgstr "Avec pré-roll" -#: crossfade_edit.cc:85 +#: crossfade_edit.cc:87 #, fuzzy msgid "With Post-roll" msgstr "Avec post-roll" -#: crossfade_edit.cc:93 +#: crossfade_edit.cc:95 msgid "Fade In" msgstr "Fondu d'ouverture" -#: crossfade_edit.cc:94 +#: crossfade_edit.cc:96 msgid "Fade Out" msgstr "Fondu de fermeture" -#: crossfade_edit.cc:170 editor.cc:1842 editor_actions.cc:315 -#: option_editor.cc:129 +#: crossfade_edit.cc:172 editor.cc:1835 editor_actions.cc:316 +#: option_editor.cc:130 msgid "Audition" msgstr "Audition" -#: editor.cc:101 editor.cc:3588 +#: editor.cc:104 editor.cc:3616 msgid "Slide" msgstr "Curseur" -#: editor.cc:102 editor.cc:3586 +#: editor.cc:105 editor.cc:3614 msgid "Splice" msgstr "Réunion" -#: editor.cc:107 editor.cc:3643 export_dialog.cc:78 export_dialog.cc:92 -#: export_dialog.cc:893 export_dialog.cc:1225 +#. note that this menu list starts at zero, not 1, because zero +#. is a valid, if useless, ID. +#. +#. leave some breathing room +#: editor.cc:110 editor.cc:3671 export_dialog.cc:78 export_dialog.cc:92 +#: export_dialog.cc:893 export_dialog.cc:1225 route_ui.cc:437 msgid "None" msgstr "Aucun" -#: editor.cc:108 editor.cc:3631 +#: editor.cc:111 editor.cc:3659 #, fuzzy msgid "CD Frames" msgstr "Trames CD" -#: editor.cc:109 editor.cc:3633 +#: editor.cc:112 editor.cc:3661 #, fuzzy msgid "SMPTE Frames" msgstr "Trames SMPTE" -#: editor.cc:110 editor.cc:3635 +#: editor.cc:113 editor.cc:3663 msgid "SMPTE Seconds" msgstr "Secondes SMPTE" -#: editor.cc:111 editor.cc:3637 +#: editor.cc:114 editor.cc:3665 msgid "SMPTE Minutes" msgstr "Minutes SMPTE" -#: editor.cc:112 editor.cc:3639 +#: editor.cc:115 editor.cc:3667 msgid "Seconds" msgstr "Secondes" -#: editor.cc:113 editor.cc:3641 +#: editor.cc:116 editor.cc:3669 msgid "Minutes" msgstr "Minutes" -#: editor.cc:114 editor.cc:3613 +#: editor.cc:117 editor.cc:3641 msgid "Beats/32" msgstr "Temps/32" -#: editor.cc:115 editor.cc:3611 +#: editor.cc:118 editor.cc:3639 msgid "Beats/16" msgstr "Temps/16" -#: editor.cc:116 editor.cc:3609 +#: editor.cc:119 editor.cc:3637 msgid "Beats/8" msgstr "Temps/8" -#: editor.cc:117 editor.cc:3607 +#: editor.cc:120 editor.cc:3635 msgid "Beats/4" msgstr "Temps/4" -#: editor.cc:118 editor.cc:3605 +#: editor.cc:121 editor.cc:3633 msgid "Beats/3" msgstr "Temps/3" -#: editor.cc:119 editor.cc:3615 +#: editor.cc:122 editor.cc:3643 msgid "Beats" msgstr "Temps" -#: editor.cc:120 editor.cc:3617 +#: editor.cc:123 editor.cc:3645 msgid "Bars" msgstr "Mesures" -#: editor.cc:121 editor.cc:3619 +#: editor.cc:124 editor.cc:3647 msgid "Marks" msgstr "Marques" -#: editor.cc:122 editor.cc:141 editor.cc:3621 editor.cc:3687 +#: editor.cc:125 editor.cc:144 editor.cc:3649 editor.cc:3715 msgid "Edit Cursor" msgstr "Curseur d'édition" -#: editor.cc:123 editor.cc:3623 +#: editor.cc:126 editor.cc:3651 #, fuzzy msgid "Region starts" msgstr "Débuts de régions" -#: editor.cc:124 editor.cc:3625 +#: editor.cc:127 editor.cc:3653 #, fuzzy msgid "Region ends" msgstr "Fins de régions" -#: editor.cc:125 editor.cc:3629 +#: editor.cc:128 editor.cc:3657 #, fuzzy msgid "Region syncs" msgstr "Syncro. de régions" -#: editor.cc:126 editor.cc:3627 +#: editor.cc:129 editor.cc:3655 #, fuzzy msgid "Region bounds" msgstr "Limites de régions" -#: editor.cc:132 editor.cc:3662 +#: editor.cc:135 editor.cc:3690 msgid "Magnetic" msgstr "Magnétique" -#: editor.cc:137 editor.cc:3679 export_dialog.cc:140 export_dialog.cc:156 +#: editor.cc:140 editor.cc:3707 export_dialog.cc:140 export_dialog.cc:156 #: export_dialog.cc:1068 export_dialog.cc:1072 msgid "Left" msgstr "Gauche" -#: editor.cc:138 editor.cc:3681 export_dialog.cc:141 export_dialog.cc:157 +#: editor.cc:141 editor.cc:3709 export_dialog.cc:141 export_dialog.cc:157 msgid "Right" msgstr "Droite" -#: editor.cc:139 editor.cc:3683 +#: editor.cc:142 editor.cc:3711 msgid "Center" msgstr "Centre" -#: editor.cc:140 editor.cc:3685 +#: editor.cc:143 editor.cc:3713 msgid "Playhead" msgstr "Tête de lecture" #. time display buttons -#: editor.cc:183 +#: editor.cc:186 msgid "Mins:Secs" msgstr "Mins:Secs" -#: editor.cc:186 editor_rulers.cc:353 +#: editor.cc:189 editor_rulers.cc:354 msgid "Frames" msgstr "Trames" -#: editor.cc:187 editor_rulers.cc:373 +#: editor.cc:190 editor_rulers.cc:374 msgid "Tempo" msgstr "Tempo" -#: editor.cc:188 editor_rulers.cc:367 +#: editor.cc:191 editor_rulers.cc:368 msgid "Meter" msgstr "Vu-mètre" -#: editor.cc:189 editor_rulers.cc:379 +#: editor.cc:192 editor_rulers.cc:380 msgid "Location Markers" msgstr "Marqueurs d'emplacements" -#: editor.cc:190 editor_rulers.cc:385 +#: editor.cc:193 editor_rulers.cc:386 msgid "Range Markers" msgstr "Marqueurs d'intervalle" -#: editor.cc:191 editor_rulers.cc:391 +#: editor.cc:194 editor_rulers.cc:392 msgid "Loop/Punch Ranges" msgstr "Intervalles de boucle/punch" -#: editor.cc:213 +#: editor.cc:216 msgid "range" msgstr "intervalle" -#: editor.cc:214 +#: editor.cc:217 msgid "object" msgstr "objet" -#: editor.cc:216 +#: editor.cc:219 msgid "zoom" msgstr "zoom" -#: editor.cc:217 +#: editor.cc:220 #, fuzzy msgid "timefx" msgstr "Effet temporel" -#: editor.cc:218 +#: editor.cc:221 msgid "listen" msgstr "écouter" -#: editor.cc:220 +#: editor.cc:223 msgid "mode" msgstr "mode" -#: editor.cc:221 +#: editor.cc:224 msgid "automation" msgstr "automatisation" -#: editor.cc:223 +#: editor.cc:226 msgid "Edit Mode" msgstr "Mode d'édition" -#: editor.cc:224 editor_actions.cc:283 +#: editor.cc:227 editor_actions.cc:284 #, fuzzy msgid "Snap To" msgstr "Snap to" -#: editor.cc:225 +#: editor.cc:228 #, fuzzy msgid "Snap Mode" msgstr "Snap mode" -#: editor.cc:226 +#: editor.cc:229 msgid "Zoom Focus" msgstr "Focus du zoom" #. #. nudge -#: editor.cc:234 editor.cc:1907 editor.cc:2073 editor.cc:2129 +#: editor.cc:237 editor.cc:1900 editor.cc:2066 editor.cc:2122 msgid "Nudge" msgstr "Décaler" -#: editor.cc:466 +#: editor.cc:470 msgid "Zoom in" msgstr "Zoom avant" -#: editor.cc:467 +#: editor.cc:471 msgid "Zoom out" msgstr "Zoom arrière" -#: editor.cc:470 +#: editor.cc:474 msgid "Zoom to session" msgstr "Zoomer vers la session" -#: editor.cc:485 +#: editor.cc:489 #, fuzzy msgid "Zoom Span" msgstr "Largeur du zoom" -#: editor.cc:498 editor.cc:524 editor_actions.cc:61 mixer_ui.cc:85 +#: editor.cc:502 editor.cc:528 editor_actions.cc:62 mixer_ui.cc:86 +#: mixer_ui.cc:112 #, fuzzy msgid "Visible" msgstr "visible" -#: editor.cc:499 editor.cc:522 +#: editor.cc:503 editor.cc:526 #, fuzzy msgid "Name" msgstr "Trames" -#: editor.cc:595 editor.cc:661 +#: editor.cc:602 editor.cc:669 #, fuzzy msgid "Regions" msgstr "Région" -#: editor.cc:634 editor.cc:673 +#: editor.cc:642 editor.cc:681 msgid "Chunks" msgstr "Fragments" -#: editor.cc:664 +#: editor.cc:672 #, fuzzy msgid "Tracks/Busses" msgstr "Pistes/Bus" -#: editor.cc:667 +#: editor.cc:675 msgid "Snapshots" msgstr "Instantanés" -#: editor.cc:670 +#: editor.cc:678 msgid "Edit Groups" msgstr "Groupes d'édition" -#: editor.cc:719 +#: editor.cc:727 msgid "Nudge region/selection forwards" msgstr "Décaller région/sélection vers l'avant" -#: editor.cc:720 +#: editor.cc:728 msgid "Nudge region/selection backwards" msgstr "Décaller région/sélection vers l'arrière" -#: editor.cc:727 editor_mixer.cc:298 +#: editor.cc:735 editor_mixer.cc:299 msgid "ardour: editor" msgstr "ardour : éditeur" -#: editor.cc:728 +#: editor.cc:736 msgid "ardour_editor" msgstr "ardour_éditeur" -#: editor.cc:1190 +#: editor.cc:1183 msgid "ardour: editor: " msgstr "ardour : éditeur : " #. force name -#: editor.cc:1275 editor.cc:1284 editor_markers.cc:869 +#: editor.cc:1268 editor.cc:1277 editor_markers.cc:870 msgid "Loop" msgstr "Boucle" #. force name -#: editor.cc:1289 editor.cc:1298 editor_markers.cc:895 +#: editor.cc:1282 editor.cc:1291 editor_markers.cc:896 msgid "Punch" msgstr "Insérer" -#: editor.cc:1446 editor_mouse.cc:1721 +#: editor.cc:1439 editor_mouse.cc:1742 msgid "programming error: fade in canvas item has no regionview data pointer!" msgstr "programming error: fade in canvas item has no regionview data pointer!" -#: editor.cc:1458 editor.cc:1475 redirect_box.cc:1071 +#: editor.cc:1451 editor.cc:1468 redirect_box.cc:1073 msgid "Deactivate" msgstr "Désactiver" #. activation -#: editor.cc:1460 editor.cc:1477 redirect_box.cc:1069 +#: editor.cc:1453 editor.cc:1470 redirect_box.cc:1071 msgid "Activate" msgstr "Activer" -#: editor.cc:1465 editor.cc:1482 +#: editor.cc:1458 editor.cc:1475 msgid "Linear" msgstr "Linéaire" -#: editor.cc:1466 editor.cc:1483 editor_actions.cc:375 +#: editor.cc:1459 editor.cc:1476 editor_actions.cc:376 msgid "Slowest" msgstr "Plus lent" -#: editor.cc:1467 editor.cc:1484 editor_actions.cc:376 +#: editor.cc:1460 editor.cc:1477 editor_actions.cc:377 msgid "Slow" msgstr "Lent" -#: editor.cc:1468 editor.cc:1485 editor_actions.cc:378 +#: editor.cc:1461 editor.cc:1478 editor_actions.cc:379 msgid "Fast" msgstr "Rapide" -#: editor.cc:1469 editor.cc:1486 editor_actions.cc:380 +#: editor.cc:1462 editor.cc:1479 editor_actions.cc:381 msgid "Fastest" msgstr "Plus rapide" -#: editor.cc:1596 editor.cc:1604 +#: editor.cc:1589 editor.cc:1597 msgid "Freeze" msgstr "Bloquer" -#: editor.cc:1600 +#: editor.cc:1593 msgid "Unfreeze" msgstr "Débloquer" -#: editor.cc:1769 editor.cc:1864 +#: editor.cc:1762 editor.cc:1857 #, fuzzy msgid "Unmute" msgstr "Non muet" #. non-operative menu items for menu bar #. show editors -#: editor.cc:1773 editor.cc:2053 editor.cc:2755 editor_actions.cc:26 -#: editor_markers.cc:506 mixer_strip.cc:512 mixer_strip.cc:572 -#: redirect_box.cc:1077 +#: editor.cc:1766 editor.cc:2046 editor.cc:2748 editor_actions.cc:27 +#: editor_markers.cc:507 mixer_strip.cc:495 mixer_strip.cc:563 +#: redirect_box.cc:1079 msgid "Edit" msgstr "Édition" -#: editor.cc:1778 +#: editor.cc:1771 msgid "Convert to short" msgstr "Convertir en court" -#: editor.cc:1780 +#: editor.cc:1773 msgid "Convert to full" msgstr "Convertir en complet" -#: editor.cc:1791 +#: editor.cc:1784 #, fuzzy msgid "Crossfade" msgstr "Modèle de fondu enchaîné" -#: editor.cc:1834 +#: editor.cc:1827 msgid "Popup region editor" msgstr "Ouvrir l'éditeur de région" -#: editor.cc:1835 +#: editor.cc:1828 msgid "Raise to top layer" msgstr "Monter vers la couche du haut" -#: editor.cc:1836 +#: editor.cc:1829 msgid "Lower to bottom layer" msgstr "Descendre vers la couche du bas" -#: editor.cc:1838 +#: editor.cc:1831 msgid "Define sync point" msgstr "Définir le point de synchronisation" -#: editor.cc:1839 +#: editor.cc:1832 msgid "Remove sync point" msgstr "Enlever le point de synchronisation" -#: editor.cc:1844 +#: editor.cc:1837 msgid "Bounce" msgstr "Bounce" -#: editor.cc:1847 +#: editor.cc:1840 #, fuzzy msgid "Analyze region" msgstr "Jouer la région" -#: editor.cc:1859 +#: editor.cc:1852 msgid "Lock" msgstr "Verrouiller" -#: editor.cc:1860 +#: editor.cc:1853 msgid "Unlock" msgstr "Déverrouiller" -#: editor.cc:1870 +#: editor.cc:1863 msgid "Original position" msgstr "Position d'origine" -#: editor.cc:1876 +#: editor.cc:1869 msgid "Toggle envelope visibility" msgstr "" -#: editor.cc:1877 +#: editor.cc:1870 #, fuzzy msgid "Toggle envelope active" msgstr "Activer" -#: editor.cc:1881 +#: editor.cc:1874 msgid "DeNormalize" msgstr "Dénormaliser" -#: editor.cc:1883 +#: editor.cc:1876 msgid "Normalize" msgstr "Normaliser" -#: editor.cc:1886 +#: editor.cc:1879 #, fuzzy msgid "Reverse" msgstr "Retourner" #. range related stuff -#: editor.cc:1892 +#: editor.cc:1885 #, fuzzy msgid "Add Range Markers" msgstr "Marqueurs d'intervalle" -#: editor.cc:1893 +#: editor.cc:1886 #, fuzzy msgid "Set Range" msgstr "Séparer l'intervalle" -#: editor.cc:1902 +#: editor.cc:1895 msgid "Nudge fwd" msgstr "Décaler vers l'avant" -#: editor.cc:1903 +#: editor.cc:1896 #, fuzzy msgid "Nudge bwd" msgstr "Décaler vers l'arrière" -#: editor.cc:1904 +#: editor.cc:1897 msgid "Nudge fwd by capture offset" msgstr "Décaler vers l'avant du décalage de la capture" -#: editor.cc:1905 +#: editor.cc:1898 msgid "Nudge bwd by capture offset" msgstr "Décaler vers l'arrière du décallage de la capture" -#: editor.cc:1914 +#: editor.cc:1907 msgid "Start to edit cursor" msgstr "Démarrer depuis le curseur d'édition" -#: editor.cc:1915 +#: editor.cc:1908 msgid "Edit cursor to end" msgstr "Curseur d'édition à la fin" -#: editor.cc:1917 +#: editor.cc:1910 gain_meter.cc:181 gain_meter.cc:813 panner_ui.cc:98 +#: panner_ui.cc:803 msgid "Trim" msgstr "Élaguer" -#: editor.cc:1920 +#: editor.cc:1913 msgid "Split" msgstr "Séparer" -#: editor.cc:1923 +#: editor.cc:1916 msgid "Make mono regions" msgstr "Créer des régions mono" -#: editor.cc:1926 +#: editor.cc:1919 msgid "Duplicate" msgstr "Dupliquer" -#: editor.cc:1927 +#: editor.cc:1920 msgid "Fill Track" msgstr "Remplir la piste" -#: editor.cc:1931 +#: editor.cc:1924 msgid "Destroy" msgstr "Détruire" -#: editor.cc:1961 +#: editor.cc:1954 msgid "Play range" msgstr "Jouer l'intervalle" -#: editor.cc:1962 +#: editor.cc:1955 msgid "Loop range" msgstr "Boucler sur l'intervalle" -#: editor.cc:1966 +#: editor.cc:1959 #, fuzzy msgid "Analyze range" msgstr "Jouer l'intervalle" -#: editor.cc:1970 +#: editor.cc:1963 #, fuzzy msgid "Separate range to track" msgstr "Séparer l'intervalle" -#: editor.cc:1971 +#: editor.cc:1964 #, fuzzy msgid "Separate range to region list" msgstr "définir les régions sélectionnées" -#: editor.cc:1974 +#: editor.cc:1967 #, fuzzy msgid "Select all in range" msgstr "Tout sélectionner dans la piste" -#: editor.cc:1976 editor.cc:2021 +#: editor.cc:1969 editor.cc:2014 #, fuzzy msgid "Set range to loop range" msgstr "Sélectionner l'intervalle de boucle" -#: editor.cc:1977 editor.cc:2022 +#: editor.cc:1970 editor.cc:2015 #, fuzzy msgid "Set range to punch range" msgstr "Sélectionner l'intervalle d'insertion" -#: editor.cc:1979 +#: editor.cc:1972 #, fuzzy msgid "Crop region to range" msgstr "Découper la région vers l'intervalle" -#: editor.cc:1980 +#: editor.cc:1973 #, fuzzy msgid "Fill range with region" msgstr "Remplir l'intervalle avec une région" -#: editor.cc:1981 +#: editor.cc:1974 #, fuzzy msgid "Duplicate range" msgstr "Dupliquer" -#: editor.cc:1982 +#: editor.cc:1975 msgid "Create chunk from range" msgstr "Nouveau fragment à partir de l'intervalle" -#: editor.cc:1984 +#: editor.cc:1977 #, fuzzy msgid "Bounce range" msgstr "Bounce intervalle" -#: editor.cc:1985 +#: editor.cc:1978 #, fuzzy msgid "Export range" msgstr "Région" -#: editor.cc:1987 +#: editor.cc:1980 msgid "Range" msgstr "Intervalle" -#: editor.cc:2002 editor.cc:2087 +#: editor.cc:1995 editor.cc:2080 msgid "Play from edit cursor" msgstr "Jouer à partir du curseur d'édition" -#: editor.cc:2003 editor.cc:2088 +#: editor.cc:1996 editor.cc:2081 msgid "Play from start" msgstr "Jouer depuis le début" -#: editor.cc:2004 +#: editor.cc:1997 msgid "Play region" msgstr "Jouer la région" -#: editor.cc:2006 +#: editor.cc:1999 msgid "Loop Region" msgstr "Boucler sur la région" -#: editor.cc:2008 editor.cc:2089 sfdb_ui.cc:56 -msgid "Play" -msgstr "Jouer" - -#: editor.cc:2016 editor.cc:2097 +#: editor.cc:2009 editor.cc:2090 msgid "Select All in track" msgstr "Tout sélectionner dans la piste" -#: editor.cc:2017 editor.cc:2098 redirect_box.cc:1065 +#: editor.cc:2010 editor.cc:2091 redirect_box.cc:1067 msgid "Select All" msgstr "Tout sélectionner" -#: editor.cc:2018 editor.cc:2099 +#: editor.cc:2011 editor.cc:2092 #, fuzzy msgid "Invert selection in track" msgstr "Inverser dans la piste" -#: editor.cc:2019 editor.cc:2100 +#: editor.cc:2012 editor.cc:2093 #, fuzzy msgid "Invert selection" msgstr "déplacer la sélection" -#: editor.cc:2024 editor.cc:2102 +#: editor.cc:2017 editor.cc:2095 #, fuzzy msgid "Select all after edit cursor" msgstr "Démarrer depuis le curseur d'édition" -#: editor.cc:2025 editor.cc:2103 +#: editor.cc:2018 editor.cc:2096 #, fuzzy msgid "Select all before edit cursor" msgstr "Démarrer depuis le curseur d'édition" -#: editor.cc:2026 editor.cc:2104 +#: editor.cc:2019 editor.cc:2097 #, fuzzy msgid "Select all after playhead" msgstr "Jouer depuis la tête de lecture" -#: editor.cc:2027 editor.cc:2105 +#: editor.cc:2020 editor.cc:2098 #, fuzzy msgid "Select all before playhead" msgstr "Jouer depuis la tête de lecture" -#: editor.cc:2028 +#: editor.cc:2021 #, fuzzy msgid "Select all between cursors" msgstr "Démarrer depuis le curseur d'édition" #. standard editing stuff -#: editor.cc:2039 editor.cc:2115 editor.cc:3455 editor_actions.cc:213 -#: redirect_box.cc:1058 +#: editor.cc:2032 editor.cc:2108 editor.cc:3483 editor_actions.cc:214 +#: redirect_box.cc:1060 msgid "Cut" msgstr "Couper" -#: editor.cc:2040 editor.cc:2116 editor.cc:3457 editor_actions.cc:218 -#: redirect_box.cc:1060 +#: editor.cc:2033 editor.cc:2109 editor.cc:3485 editor_actions.cc:219 +#: redirect_box.cc:1062 msgid "Copy" msgstr "Copier" -#: editor.cc:2041 +#: editor.cc:2034 msgid "Paste at edit cursor" msgstr "Coller au curseur d'édition" -#: editor.cc:2042 +#: editor.cc:2035 msgid "Paste at mouse" msgstr "Coller au pointeur de la souris" -#: editor.cc:2046 editor.cc:3462 +#: editor.cc:2039 editor.cc:3490 msgid "Align" msgstr "Aligner" -#: editor.cc:2047 editor.cc:3464 +#: editor.cc:2040 editor.cc:3492 msgid "Align Relative" msgstr "Aligner relativement" -#: editor.cc:2051 +#: editor.cc:2044 msgid "Insert chunk" msgstr "Insérer un fragment" -#: editor.cc:2058 +#: editor.cc:2051 #, fuzzy msgid "Insert Selected Region" msgstr "définir les régions sélectionnées" -#: editor.cc:2059 +#: editor.cc:2052 msgid "Insert Existing Audio" msgstr "" -#: editor.cc:2068 editor.cc:2124 +#: editor.cc:2061 editor.cc:2117 msgid "Nudge entire track fwd" msgstr "Décaler la piste entière en avant" -#: editor.cc:2069 editor.cc:2125 +#: editor.cc:2062 editor.cc:2118 msgid "Nudge track after edit cursor fwd" msgstr "Décaler la piste vers l'avant après le curseur d'édition" -#: editor.cc:2070 editor.cc:2126 +#: editor.cc:2063 editor.cc:2119 msgid "Nudge entire track bwd" msgstr "Décaler la piste entière vers l'arrière" -#: editor.cc:2071 editor.cc:2127 +#: editor.cc:2064 editor.cc:2120 msgid "Nudge track after edit cursor bwd" msgstr "Décaler la piste vers l'arrière après le curseur d'édition" -#: editor.cc:2117 editor.cc:3459 editor_actions.cc:220 redirect_box.cc:1062 +#: editor.cc:2110 editor.cc:3487 editor_actions.cc:221 redirect_box.cc:1064 msgid "Paste" msgstr "Coller" -#: editor.cc:2637 +#: editor.cc:2630 msgid "select/move objects" msgstr "sélectionner/déplacer des objets" -#: editor.cc:2638 +#: editor.cc:2631 msgid "select/move ranges" msgstr "sélectionner/déplacer des intervalles" -#: editor.cc:2639 +#: editor.cc:2632 msgid "draw gain automation" msgstr "dessiner l'automatisation du gain" -#: editor.cc:2640 +#: editor.cc:2633 msgid "select zoom range" msgstr "sélectionner la plage de zoom" -#: editor.cc:2641 +#: editor.cc:2634 msgid "stretch/shrink regions" msgstr "étirer/rétrécir les régions" -#: editor.cc:2642 +#: editor.cc:2635 #, fuzzy msgid "listen to specific regions" msgstr "Écouter des régions spécifiques" -#: editor.cc:2753 +#: editor.cc:2746 msgid "Start:" msgstr "Début :" -#: editor.cc:2754 +#: editor.cc:2747 msgid "End:" msgstr "Fin :" -#: editor.cc:3097 -#, fuzzy -msgid "set selected trackview" -msgstr "définir la vue de piste sélectionnée" - -#: editor.cc:3137 -#, fuzzy -msgid "set selected control point" -msgstr "Enlever le point de contrôle" - -#: editor.cc:3246 -#, fuzzy -msgid "set selected regionview" -msgstr "définir la vue de région sélectionnée" - -#: editor.cc:3334 editor.cc:3374 +#: editor.cc:3362 editor.cc:3402 #, fuzzy msgid "set selected regions" msgstr "définir les régions sélectionnées" -#: editor.cc:3430 editor_actions.cc:203 +#: editor.cc:3458 editor_actions.cc:204 msgid "Undo" msgstr "Annuler" -#: editor.cc:3432 +#: editor.cc:3460 msgid "Undo (%1)" msgstr "Annuler (%1)" -#: editor.cc:3442 editor_actions.cc:205 +#: editor.cc:3470 editor_actions.cc:206 msgid "Redo" msgstr "Refaire" -#: editor.cc:3444 +#: editor.cc:3472 msgid "Redo (%1)" msgstr "Refaire (%1)" -#: editor.cc:3478 +#: editor.cc:3506 msgid "... as new track" msgstr "" -#: editor.cc:3479 +#: editor.cc:3507 #, fuzzy msgid "... as new region" msgstr "aligner la région" -#: editor.cc:3481 +#: editor.cc:3509 msgid "Import audio (copy)" msgstr "Importer audio (copie)" -#: editor.cc:3484 +#: editor.cc:3512 msgid "Remove last capture" msgstr "Enlever la dernière capture" -#: editor.cc:3508 +#: editor.cc:3536 msgid "Duplicate how many times?" msgstr "Dupliquer combien de fois ?" -#: editor.cc:3994 +#: editor.cc:4022 msgid "" "Playlist %1 is currently unused.\n" "If left alone, no audio files used by it will be cleaned.\n" @@ -2729,766 +2715,766 @@ msgstr "" "Si vous la convervez, aucun fichier audio qu'elle utilise ne sera nettoyé.\n" "Si vous l'effacez, les fichiers audio qu'elle seule utilise seront nettoyés." -#: editor.cc:4002 +#: editor.cc:4030 msgid "Delete playlist" msgstr "Supprimer la playlist" -#: editor.cc:4003 +#: editor.cc:4031 msgid "Keep playlist" msgstr "Garder la playlist" -#: editor.cc:4004 editor_audio_import.cc:237 editor_ops.cc:1976 -#: editor_timefx.cc:52 export_dialog.cc:971 io_selector.cc:58 -#: io_selector.cc:792 redirect_box.cc:901 tempo_dialog.cc:19 -#: tempo_dialog.cc:36 tempo_dialog.cc:152 tempo_dialog.cc:170 +#: editor.cc:4032 editor_audio_import.cc:236 editor_ops.cc:2048 +#: editor_timefx.cc:71 export_dialog.cc:971 io_selector.cc:59 +#: io_selector.cc:793 redirect_box.cc:903 tempo_dialog.cc:20 +#: tempo_dialog.cc:37 tempo_dialog.cc:202 tempo_dialog.cc:220 msgid "Cancel" msgstr "Annuler" -#: editor.cc:4171 +#: editor.cc:4199 #, fuzzy msgid "new playlists" msgstr "Garder la playlist" -#: editor.cc:4179 +#: editor.cc:4207 #, fuzzy msgid "copy playlists" msgstr "Garder la playlist" -#: editor.cc:4187 +#: editor.cc:4215 #, fuzzy msgid "clear playlists" msgstr "effacer la liste de lecture" -#: editor_actions.cc:27 +#: editor_actions.cc:28 #, fuzzy msgid "Select regions" msgstr "sélectionner les régions" -#: editor_actions.cc:28 +#: editor_actions.cc:29 #, fuzzy msgid "Select range operations" msgstr "sélectionner les régions" -#: editor_actions.cc:29 +#: editor_actions.cc:30 #, fuzzy msgid "Move edit cursor" msgstr "Coller au curseur d'édition" -#: editor_actions.cc:30 +#: editor_actions.cc:31 #, fuzzy msgid "Region operations" msgstr "Régions/création" -#: editor_actions.cc:31 +#: editor_actions.cc:32 msgid "Tools" msgstr "" -#: editor_actions.cc:32 +#: editor_actions.cc:33 msgid "View" msgstr "" -#: editor_actions.cc:33 +#: editor_actions.cc:34 #, fuzzy msgid "ZoomFocus" msgstr "Focus du zoom" -#: editor_actions.cc:34 +#: editor_actions.cc:35 #, fuzzy msgid "Meter hold" msgstr "Maintien du pic de vu-mètre" -#: editor_actions.cc:35 +#: editor_actions.cc:36 #, fuzzy msgid "Meter falloff" msgstr "Temps de chute du vu-mètre" -#: editor_actions.cc:37 +#: editor_actions.cc:38 #, fuzzy msgid "Crossfades" msgstr "Modèle de fondu enchaîné" -#: editor_actions.cc:38 +#: editor_actions.cc:39 #, fuzzy msgid "Monitoring" msgstr "Utiliser la pré-écoute matérielle" -#: editor_actions.cc:39 +#: editor_actions.cc:40 #, fuzzy msgid "Autoconnect" msgstr "Reconnecter" -#: editor_actions.cc:40 +#: editor_actions.cc:41 #, fuzzy msgid "Layering" msgstr "Couche" -#: editor_actions.cc:41 +#: editor_actions.cc:42 #, fuzzy msgid "Metering" msgstr "Vu-mètre" -#: editor_actions.cc:42 +#: editor_actions.cc:43 msgid "Fall off rate" msgstr "" -#: editor_actions.cc:43 +#: editor_actions.cc:44 msgid "Hold Time" msgstr "" -#: editor_actions.cc:44 +#: editor_actions.cc:45 msgid "Add Existing Audio" msgstr "" #. add named actions for the editor -#: editor_actions.cc:49 +#: editor_actions.cc:50 #, fuzzy msgid "Show Editor Mixer" msgstr "Montrer toutes les tranches de mixage de piste audio" -#: editor_actions.cc:54 +#: editor_actions.cc:55 #, fuzzy msgid "Span Entire Overlap" msgstr "Mesurer le recouvrement de régions en entier" -#: editor_actions.cc:56 editor_actions.cc:383 +#: editor_actions.cc:57 editor_actions.cc:384 msgid "Short" msgstr "Court" -#: editor_actions.cc:63 +#: editor_actions.cc:64 msgid "Created Automatically" msgstr "" -#: editor_actions.cc:66 +#: editor_actions.cc:67 msgid "Playhead to Next Region Start" msgstr "" -#: editor_actions.cc:68 +#: editor_actions.cc:69 msgid "Playhead to Next Region End" msgstr "" -#: editor_actions.cc:70 +#: editor_actions.cc:71 msgid "Playhead to Next Region Sync" msgstr "" -#: editor_actions.cc:73 +#: editor_actions.cc:74 msgid "Playhead to Previous Region Start" msgstr "" -#: editor_actions.cc:75 +#: editor_actions.cc:76 msgid "Playhead to Previous Region End" msgstr "" -#: editor_actions.cc:77 +#: editor_actions.cc:78 msgid "Playhead to Previous Region Sync" msgstr "" -#: editor_actions.cc:80 +#: editor_actions.cc:81 #, fuzzy msgid "Edit Cursor to Next Region Start" msgstr "Curseur d'édition à la fin" -#: editor_actions.cc:82 +#: editor_actions.cc:83 #, fuzzy msgid "Edit Cursor to Next Region End" msgstr "Curseur d'édition à la fin" -#: editor_actions.cc:84 +#: editor_actions.cc:85 #, fuzzy msgid "Edit Cursor to Next Region Sync" msgstr "Curseur d'édition à la fin" -#: editor_actions.cc:87 +#: editor_actions.cc:88 msgid "Edit Cursor to Previous Region Start" msgstr "" -#: editor_actions.cc:89 +#: editor_actions.cc:90 #, fuzzy msgid "Edit Cursor to Previous Region End" msgstr "Curseur d'édition à la fin" -#: editor_actions.cc:91 +#: editor_actions.cc:92 #, fuzzy msgid "Edit Cursor to Previous Region Sync" msgstr "Curseur d'édition à la fin" -#: editor_actions.cc:94 +#: editor_actions.cc:95 msgid "Playhead to Range Start" msgstr "" -#: editor_actions.cc:96 +#: editor_actions.cc:97 #, fuzzy msgid "Playhead to Range End" msgstr "Jouer l'intervalle de boucle" -#: editor_actions.cc:99 +#: editor_actions.cc:100 #, fuzzy msgid "Edit Cursor to Range Start" msgstr "Curseur d'édition à la fin" -#: editor_actions.cc:101 +#: editor_actions.cc:102 #, fuzzy msgid "Edit Cursor to Range End" msgstr "Curseur d'édition à la fin" -#: editor_actions.cc:104 editor_ops.cc:1300 +#: editor_actions.cc:105 editor_ops.cc:1363 #, fuzzy msgid "select all" msgstr "Tout sélectionner" -#: editor_actions.cc:106 +#: editor_actions.cc:107 #, fuzzy msgid "Select All After Edit Cursor" msgstr "définir la synchro. au curseur d'édition" -#: editor_actions.cc:108 +#: editor_actions.cc:109 msgid "Select All Before Edit Cursor" msgstr "" -#: editor_actions.cc:111 +#: editor_actions.cc:112 #, fuzzy msgid "Select All After Playhead" msgstr "Jouer depuis la tête de lecture" -#: editor_actions.cc:113 +#: editor_actions.cc:114 #, fuzzy msgid "Select All Before Playhead" msgstr "Jouer depuis la tête de lecture" -#: editor_actions.cc:115 +#: editor_actions.cc:116 #, fuzzy msgid "Select All Between Cursors" msgstr "définir la synchro. au curseur d'édition" -#: editor_actions.cc:118 +#: editor_actions.cc:119 #, fuzzy msgid "Select All in Punch Range" msgstr "Définir l'intervalle d'insertion" -#: editor_actions.cc:120 +#: editor_actions.cc:121 #, fuzzy msgid "Select All in Loop Range" msgstr "Sélectionner l'intervalle de boucle" -#: editor_actions.cc:123 +#: editor_actions.cc:124 msgid "Jump Forward to Mark" msgstr "" -#: editor_actions.cc:125 +#: editor_actions.cc:126 msgid "Jump Backward to Mark" msgstr "" -#: editor_actions.cc:127 +#: editor_actions.cc:128 #, fuzzy msgid "Add Location from Playhead" msgstr "Jouer depuis la tête de lecture" -#: editor_actions.cc:130 +#: editor_actions.cc:131 #, fuzzy msgid "Nudge Forward" msgstr "décaler vers l'avant" -#: editor_actions.cc:132 +#: editor_actions.cc:133 #, fuzzy msgid "Nudge Next Forward" msgstr "décaler vers l'avant" -#: editor_actions.cc:134 +#: editor_actions.cc:135 #, fuzzy msgid "Nudge Backward" msgstr "Décaler vers l'arrière" -#: editor_actions.cc:136 +#: editor_actions.cc:137 #, fuzzy msgid "Nudge Next Backward" msgstr "Décaler la piste entière en avant" -#: editor_actions.cc:139 +#: editor_actions.cc:140 #, fuzzy msgid "Zoom Out" msgstr "Zoom arrière" -#: editor_actions.cc:141 +#: editor_actions.cc:142 #, fuzzy msgid "Zoom In" msgstr "Zoom avant" -#: editor_actions.cc:143 +#: editor_actions.cc:144 #, fuzzy msgid "Zoom to Session" msgstr "Zoomer vers la session" -#: editor_actions.cc:146 +#: editor_actions.cc:147 #, fuzzy msgid "Scroll Tracks Up" msgstr "Remplir la piste" -#: editor_actions.cc:148 +#: editor_actions.cc:149 msgid "Scroll Tracks Down" msgstr "" -#: editor_actions.cc:150 +#: editor_actions.cc:151 #, fuzzy msgid "Step Tracks Up" msgstr "décaler la piste" -#: editor_actions.cc:152 +#: editor_actions.cc:153 msgid "Step Tracks Down" msgstr "" -#: editor_actions.cc:155 +#: editor_actions.cc:156 msgid "Scroll Backward" msgstr "" -#: editor_actions.cc:157 +#: editor_actions.cc:158 msgid "Scroll Forward" msgstr "" -#: editor_actions.cc:159 +#: editor_actions.cc:160 msgid "goto" msgstr "" -#: editor_actions.cc:161 +#: editor_actions.cc:162 #, fuzzy msgid "Center Playhead" msgstr "Tête de lecture" -#: editor_actions.cc:163 +#: editor_actions.cc:164 #, fuzzy msgid "Center Edit Cursor" msgstr "Curseur d'édition" -#: editor_actions.cc:165 +#: editor_actions.cc:166 #, fuzzy msgid "Playhead Forward" msgstr "Tête de lecture" -#: editor_actions.cc:167 +#: editor_actions.cc:168 #, fuzzy msgid "Playhead Backward" msgstr "Tête de lecture" -#: editor_actions.cc:169 +#: editor_actions.cc:170 #, fuzzy msgid "Playhead to Edit" msgstr "Tête de lecture" -#: editor_actions.cc:171 +#: editor_actions.cc:172 #, fuzzy msgid "Edit to Playhead" msgstr "Jouer depuis la tête de lecture" -#: editor_actions.cc:174 +#: editor_actions.cc:175 #, fuzzy msgid "Align Regions Start" msgstr "Débuts de régions" -#: editor_actions.cc:176 +#: editor_actions.cc:177 #, fuzzy msgid "Align Regions Start Relative" msgstr "Aligner la sélection (relativement)" -#: editor_actions.cc:178 +#: editor_actions.cc:179 #, fuzzy msgid "Align Regions End" msgstr "aligner la région" -#: editor_actions.cc:180 +#: editor_actions.cc:181 #, fuzzy msgid "Align Regions End Relative" msgstr "Aligner relativement" -#: editor_actions.cc:183 +#: editor_actions.cc:184 #, fuzzy msgid "Align Regions Sync" msgstr "aligner la région" -#: editor_actions.cc:185 +#: editor_actions.cc:186 #, fuzzy msgid "Align Regions Sync Relative" msgstr "Aligner relativement" -#: editor_actions.cc:188 +#: editor_actions.cc:189 #, fuzzy msgid "Audition at Mouse" msgstr "Audition" -#: editor_actions.cc:190 +#: editor_actions.cc:191 #, fuzzy msgid "Brush at Mouse" msgstr "Coller au pointeur de la souris" -#: editor_actions.cc:192 +#: editor_actions.cc:193 #, fuzzy msgid "Set Edit Cursor" msgstr "Curseur d'édition" -#: editor_actions.cc:194 +#: editor_actions.cc:195 #, fuzzy msgid "Mute/Unmute Region" msgstr "Créer une région" -#: editor_actions.cc:196 +#: editor_actions.cc:197 #, fuzzy msgid "Set Playhead" msgstr "Tête de lecture" -#: editor_actions.cc:198 +#: editor_actions.cc:199 #, fuzzy msgid "Split Region" msgstr "Séparer la région" -#: editor_actions.cc:200 +#: editor_actions.cc:201 #, fuzzy msgid "Set Region Sync Position" msgstr "Par position de région" -#: editor_actions.cc:208 +#: editor_actions.cc:209 #, fuzzy msgid "Export Session" msgstr "Région" -#: editor_actions.cc:210 +#: editor_actions.cc:211 #, fuzzy msgid "Export Range" msgstr "Séparer l'intervalle" #. Note: for now, editor-delete does the exact same thing as editor-cut -#: editor_actions.cc:216 +#: editor_actions.cc:217 msgid "Delete" msgstr "Supprimer" -#: editor_actions.cc:222 +#: editor_actions.cc:223 #, fuzzy msgid "Duplicate Region" msgstr "dupliquer la région" -#: editor_actions.cc:224 +#: editor_actions.cc:225 #, fuzzy msgid "Duplicate Range" msgstr "Dupliquer" -#: editor_actions.cc:226 +#: editor_actions.cc:227 msgid "Insert Region" msgstr "Insérer une région" -#: editor_actions.cc:228 +#: editor_actions.cc:229 #, fuzzy msgid "Reverse Region" msgstr "inverser les régions" -#: editor_actions.cc:230 +#: editor_actions.cc:231 #, fuzzy msgid "Normalize Region" msgstr "Normaliser" -#: editor_actions.cc:232 +#: editor_actions.cc:233 #, fuzzy msgid "crop" msgstr "copier" -#: editor_actions.cc:234 +#: editor_actions.cc:235 #, fuzzy msgid "Insert Chunk" msgstr "Insérer un fragment" -#: editor_actions.cc:237 +#: editor_actions.cc:238 #, fuzzy msgid "Split at edit cursor" msgstr "Démarrer depuis le curseur d'édition" -#: editor_actions.cc:240 +#: editor_actions.cc:241 #, fuzzy msgid "Start Range" msgstr "Séparer l'intervalle" -#: editor_actions.cc:242 +#: editor_actions.cc:243 msgid "Finish Range" msgstr "" -#: editor_actions.cc:244 +#: editor_actions.cc:245 msgid "Finish add Range" msgstr "" -#: editor_actions.cc:247 +#: editor_actions.cc:248 msgid "Extend Range to End of Region" msgstr "" -#: editor_actions.cc:249 +#: editor_actions.cc:250 #, fuzzy msgid "Extend Range to Start of Region" msgstr "Aller au début de la session" -#: editor_actions.cc:252 +#: editor_actions.cc:253 #, fuzzy msgid "Follow Playhead" msgstr "Suivre la tête de lecture" -#: editor_actions.cc:260 +#: editor_actions.cc:261 #, fuzzy msgid "Zoom Focus Left" msgstr "Focus du zoom" -#: editor_actions.cc:262 +#: editor_actions.cc:263 #, fuzzy msgid "Zoom Focus Right" msgstr "Focus du zoom" -#: editor_actions.cc:264 +#: editor_actions.cc:265 #, fuzzy msgid "Zoom Focus Center" msgstr "Focus du zoom" -#: editor_actions.cc:266 +#: editor_actions.cc:267 #, fuzzy msgid "Zoom Focus Playhead" msgstr "Focus du zoom" -#: editor_actions.cc:268 +#: editor_actions.cc:269 #, fuzzy msgid "Zoom Focus Edit" msgstr "Focus du zoom" -#: editor_actions.cc:274 +#: editor_actions.cc:275 msgid "Object Tool" msgstr "" -#: editor_actions.cc:275 +#: editor_actions.cc:276 #, fuzzy msgid "Range Tool" msgstr "Intervalle" -#: editor_actions.cc:276 +#: editor_actions.cc:277 msgid "Gain Tool" msgstr "" -#: editor_actions.cc:277 +#: editor_actions.cc:278 #, fuzzy msgid "Zoom Tool" msgstr "Zoom arrière" -#: editor_actions.cc:278 +#: editor_actions.cc:279 msgid "Timefx Tool" msgstr "" -#: editor_actions.cc:285 +#: editor_actions.cc:286 #, fuzzy msgid "Snap to frame" msgstr "Snap mode" -#: editor_actions.cc:286 +#: editor_actions.cc:287 #, fuzzy msgid "Snap to cd frame" msgstr "Snap mode" -#: editor_actions.cc:287 +#: editor_actions.cc:288 #, fuzzy msgid "Snap to SMPTE frame" msgstr "Trames SMPTE" -#: editor_actions.cc:288 +#: editor_actions.cc:289 #, fuzzy msgid "Snap to SMPTE seconds" msgstr "Secondes SMPTE" -#: editor_actions.cc:289 +#: editor_actions.cc:290 #, fuzzy msgid "Snap to SMPTE minutes" msgstr "Minutes SMPTE" -#: editor_actions.cc:290 +#: editor_actions.cc:291 #, fuzzy msgid "Snap to seconds" msgstr "3 secondes" -#: editor_actions.cc:291 +#: editor_actions.cc:292 msgid "Snap to minutes" msgstr "" -#: editor_actions.cc:292 +#: editor_actions.cc:293 #, fuzzy msgid "Snap to thirtyseconds" msgstr "trente-deuxième (32)" -#: editor_actions.cc:293 +#: editor_actions.cc:294 msgid "Snap to asixteenthbeat" msgstr "" -#: editor_actions.cc:294 +#: editor_actions.cc:295 msgid "Snap to eighths" msgstr "" -#: editor_actions.cc:295 +#: editor_actions.cc:296 msgid "Snap to quarters" msgstr "" -#: editor_actions.cc:296 +#: editor_actions.cc:297 #, fuzzy msgid "Snap to thirds" msgstr "Snap mode" -#: editor_actions.cc:297 +#: editor_actions.cc:298 #, fuzzy msgid "Snap to beat" msgstr "Snap mode" -#: editor_actions.cc:298 +#: editor_actions.cc:299 #, fuzzy msgid "Snap to bar" msgstr "Snap to" -#: editor_actions.cc:299 +#: editor_actions.cc:300 #, fuzzy msgid "Snap to mark" msgstr "ajouter un marqueur de tempo" -#: editor_actions.cc:300 +#: editor_actions.cc:301 #, fuzzy msgid "Snap to edit cursor" msgstr "Démarrer depuis le curseur d'édition" -#: editor_actions.cc:301 +#: editor_actions.cc:302 #, fuzzy msgid "Snap to region start" msgstr "Débuts de régions" -#: editor_actions.cc:302 +#: editor_actions.cc:303 #, fuzzy msgid "Snap to region end" msgstr "Fins de régions" -#: editor_actions.cc:303 +#: editor_actions.cc:304 #, fuzzy msgid "Snap to region sync" msgstr "Syncro. de régions" -#: editor_actions.cc:304 +#: editor_actions.cc:305 #, fuzzy msgid "Snap to region boundary" msgstr "Limites de régions" #. the region list popup menu -#: editor_actions.cc:313 +#: editor_actions.cc:314 #, fuzzy msgid "Sort" msgstr "Court" -#: editor_actions.cc:321 +#: editor_actions.cc:322 msgid "Show all" msgstr "Tout montrer" -#: editor_actions.cc:322 +#: editor_actions.cc:323 #, fuzzy msgid "Show automatic regions" msgstr "montrer toute l'automatisation" -#: editor_actions.cc:324 +#: editor_actions.cc:325 msgid "Ascending" msgstr "Montant" -#: editor_actions.cc:326 +#: editor_actions.cc:327 msgid "Descending" msgstr "Descendant" -#: editor_actions.cc:329 +#: editor_actions.cc:330 msgid "By Region Name" msgstr "Par nom de région" -#: editor_actions.cc:331 +#: editor_actions.cc:332 msgid "By Region Length" msgstr "Par longueur de région" -#: editor_actions.cc:333 +#: editor_actions.cc:334 msgid "By Region Position" msgstr "Par position de région" -#: editor_actions.cc:335 +#: editor_actions.cc:336 msgid "By Region Timestamp" msgstr "Par date de région" -#: editor_actions.cc:337 +#: editor_actions.cc:338 msgid "By Region Start in File" msgstr "Par début de région dans le fichier" -#: editor_actions.cc:339 +#: editor_actions.cc:340 msgid "By Region End in File" msgstr "Par fin de région dans le fichier" -#: editor_actions.cc:341 +#: editor_actions.cc:342 msgid "By Source File Name" msgstr "Par nom de fichier source" -#: editor_actions.cc:343 +#: editor_actions.cc:344 msgid "By Source File Length" msgstr "Par longueur de fichier source" -#: editor_actions.cc:345 +#: editor_actions.cc:346 msgid "By Source File Creation Date" msgstr "Par date de création du fichier source" -#: editor_actions.cc:347 +#: editor_actions.cc:348 msgid "By Source Filesystem" msgstr "Par système de fichier source" #. the next two are duplicate items with different names for use in two different contexts -#: editor_actions.cc:353 +#: editor_actions.cc:354 #, fuzzy msgid "Add External Audio" msgstr "Ajouter à la liste des régions externes" -#: editor_actions.cc:355 +#: editor_actions.cc:356 #, fuzzy msgid "as Region(s)" msgstr "Déplacer la/les région(s)" -#: editor_actions.cc:357 +#: editor_actions.cc:358 #, fuzzy msgid "as Tracks" msgstr "Pistes" -#: editor_actions.cc:359 +#: editor_actions.cc:360 #, fuzzy msgid "to Tracks" msgstr "Pistes" -#: editor_actions.cc:362 +#: editor_actions.cc:363 #, fuzzy msgid "Show Waveforms" msgstr "Montrer les formes d'onde" -#: editor_actions.cc:363 +#: editor_actions.cc:364 #, fuzzy msgid "Show Waveforms While Recording" msgstr "Montrer les formes d'onde pendant l'enregistrement" -#: editor_actions.cc:364 +#: editor_actions.cc:365 #, fuzzy msgid "Show Measures" msgstr "Montrer les barres de mesures" -#: editor_actions.cc:377 editor_actions.cc:384 +#: editor_actions.cc:378 editor_actions.cc:385 msgid "Medium" msgstr "Moyen" -#: editor_actions.cc:379 +#: editor_actions.cc:380 msgid "Faster" msgstr "Plus rapide" -#: editor_actions.cc:385 +#: editor_actions.cc:386 msgid "Long" msgstr "Long" -#: editor_actions.cc:389 +#: editor_actions.cc:390 #, fuzzy msgid "Later is Higher" msgstr "Les dernières régions sont placées au-dessus" -#: editor_actions.cc:390 +#: editor_actions.cc:391 #, fuzzy msgid "Most Recently Moved/Added is Higher" msgstr "" "Les régions ajoutées/déplacées/élaguées en dernier sont placées au-dessus" -#: editor_actions.cc:391 +#: editor_actions.cc:392 #, fuzzy msgid "Most Recently Added is Higher" msgstr "" @@ -3506,39 +3492,39 @@ msgstr "" msgid "Add existing audio to session" msgstr "montrer l'automatisation existante" -#: editor_audio_import.cc:143 +#: editor_audio_import.cc:142 msgid "ardour: importing %1" msgstr "ardour : importation de %1" -#: editor_audio_import.cc:147 +#: editor_audio_import.cc:146 msgid "Cancel Import" msgstr "Annuler l'importation" -#: editor_audio_import.cc:225 +#: editor_audio_import.cc:224 #, fuzzy msgid "Editor: cannot open file \"%1\", (%2)" msgstr "Éditeur : impossible d'ouvrir le fichier \"%1\" (%2)" -#: editor_audio_import.cc:233 +#: editor_audio_import.cc:232 #, fuzzy msgid "Cancel entire import" msgstr "Annuler l'importation" -#: editor_audio_import.cc:234 +#: editor_audio_import.cc:233 #, fuzzy msgid "Don't embed it" msgstr "Ne pas %1" -#: editor_audio_import.cc:235 +#: editor_audio_import.cc:234 msgid "Embed all without questions" msgstr "" -#: editor_audio_import.cc:240 +#: editor_audio_import.cc:239 #, fuzzy msgid "Embed it anyway" msgstr "le %1 quand même" -#: editor_audio_import.cc:243 +#: editor_audio_import.cc:242 msgid "" "%1\n" "This audiofile's sample rate doesn't match the session sample rate!" @@ -3547,74 +3533,62 @@ msgstr "" "La fréquence d'échantillonage de ce fichier audio ne correspond pas à celle " "de la session !" -#: editor_audio_import.cc:276 +#: editor_audio_import.cc:275 msgid "could not open %1" msgstr "impossible d'ouvrir %1" -#: editor_audio_import.cc:321 +#: editor_audio_import.cc:320 msgid "insert sndfile" msgstr "Insérer un fichier son" #. stuff for the verbose canvas cursor -#: editor_canvas.cc:117 +#: editor_canvas.cc:118 msgid "VerboseCanvasCursor" msgstr "VerboseCanvasCursor" -#: editor_canvas.cc:285 -msgid "Start a new session\n" -msgstr "Commencer une nouvelle session\n" - -#: editor_canvas.cc:285 -msgid "via Session menu" -msgstr "via le menu Session" - -#: editor_canvas.cc:288 -msgid "FirstActionMessage" -msgstr "FirstActionCursor" - -#: editor_edit_groups.cc:52 mixer_ui.cc:732 +#: editor_edit_groups.cc:53 mixer_ui.cc:736 #, fuzzy msgid "Activate All" msgstr "Activer" -#: editor_edit_groups.cc:53 mixer_ui.cc:733 +#: editor_edit_groups.cc:54 mixer_ui.cc:737 #, fuzzy msgid "Disable All" msgstr "Déconnecter tout" -#: editor_edit_groups.cc:55 mixer_ui.cc:735 +#: editor_edit_groups.cc:56 mixer_ui.cc:739 #, fuzzy msgid "Add group" msgstr "Pas de groupe" -#: editor_edit_groups.cc:225 mixer_ui.cc:964 +#: editor_edit_groups.cc:229 mixer_ui.cc:970 #, fuzzy msgid "unnamed" msgstr "Renommer" -#: editor_edit_groups.cc:252 mixer_ui.cc:830 +#: editor_edit_groups.cc:258 mixer_ui.cc:834 msgid "-all-" msgstr "-tout-" -#: editor_export_audio.cc:64 +#: editor_export_audio.cc:65 msgid "" "There is no selection to export.\n" "\n" "Select a selection using the range mouse mode" msgstr "" -#: editor_export_audio.cc:109 +#: editor_export_audio.cc:110 msgid "" "There are no ranges to export.\n" "\n" "Create 1 or more ranges by dragging the mouse in the range bar" msgstr "" -#: editor_imageframe.cc:624 editor_imageframe.cc:654 +#: editor_imageframe.cc:625 editor_imageframe.cc:655 msgid "programming error: no ImageFrameView selected" msgstr "erreur de programmation : aucun ImageFrameView selectionné" -#: editor_imageframe.cc:847 editor_imageframe.cc:869 +#: editor_imageframe.cc:848 editor_imageframe.cc:870 msgid "programming error: no MarkerView selected" msgstr "erreur de programmation : aucun MarkerView sélectionné" @@ -3623,141 +3597,141 @@ msgstr "erreur de programmation : aucun MarkerView sélectionné" msgid "mute region" msgstr "Assourdir cette région" -#: editor_keys.cc:45 +#: editor_keys.cc:46 #, fuzzy msgid "keyboard selection" msgstr "étendre la sélection" -#: editor_markers.cc:291 editor_ops.cc:1227 editor_ops.cc:1240 -#: editor_ops.cc:1258 location_ui.cc:773 +#: editor_markers.cc:292 editor_ops.cc:1290 editor_ops.cc:1303 +#: editor_ops.cc:1321 location_ui.cc:774 msgid "add marker" msgstr "ajouter un marqueur" -#: editor_markers.cc:306 editor_markers.cc:379 editor_markers.cc:551 -#: editor_markers.cc:569 editor_markers.cc:588 editor_markers.cc:607 -#: editor_markers.cc:637 editor_markers.cc:665 editor_markers.cc:693 -#: editor_markers.cc:731 editor_markers.cc:758 editor_markers.cc:781 -#: editor_markers.cc:800 editor_mouse.cc:1994 editor_mouse.cc:4237 +#: editor_markers.cc:307 editor_markers.cc:380 editor_markers.cc:552 +#: editor_markers.cc:570 editor_markers.cc:589 editor_markers.cc:608 +#: editor_markers.cc:638 editor_markers.cc:666 editor_markers.cc:694 +#: editor_markers.cc:732 editor_markers.cc:759 editor_markers.cc:782 +#: editor_markers.cc:801 editor_mouse.cc:2015 editor_mouse.cc:4275 msgid "programming error: marker canvas item has no marker object pointer!" msgstr "" "erreur de programmation : objet canvas de marqueur sans pointeur d'objet " "marqueur !" -#: editor_markers.cc:330 location_ui.cc:655 +#: editor_markers.cc:331 location_ui.cc:656 msgid "remove marker" msgstr "enlever le marqueur" -#: editor_markers.cc:457 +#: editor_markers.cc:458 #, fuzzy msgid "Locate to Mark" msgstr "Locate to" -#: editor_markers.cc:458 +#: editor_markers.cc:459 #, fuzzy msgid "Play from Mark" msgstr "Jouer depuis le début" -#: editor_markers.cc:459 +#: editor_markers.cc:460 #, fuzzy msgid "Set Mark from Playhead" msgstr "Jouer depuis la tête de lecture" -#: editor_markers.cc:463 +#: editor_markers.cc:464 #, fuzzy msgid "Rename Mark" msgstr "Renommer la piste" -#: editor_markers.cc:464 +#: editor_markers.cc:465 #, fuzzy msgid "Hide Mark" msgstr "décaler la piste" -#: editor_markers.cc:465 +#: editor_markers.cc:466 #, fuzzy msgid "Remove Mark" msgstr "Enlever les marqueurs" -#: editor_markers.cc:478 editor_markers.cc:534 +#: editor_markers.cc:479 editor_markers.cc:535 #, fuzzy msgid "Locate to Range Mark" msgstr "Marqueurs d'emplacements" -#: editor_markers.cc:479 editor_markers.cc:535 +#: editor_markers.cc:480 editor_markers.cc:536 #, fuzzy msgid "Play from Range Mark" msgstr "Jouer l'intervalle de boucle" -#: editor_markers.cc:480 +#: editor_markers.cc:481 #, fuzzy msgid "Loop Range" msgstr "Boucler sur l'intervalle" -#: editor_markers.cc:481 editor_markers.cc:536 +#: editor_markers.cc:482 editor_markers.cc:537 #, fuzzy msgid "Set Range Mark from Playhead" msgstr "Jouer depuis la tête de lecture" -#: editor_markers.cc:482 editor_markers.cc:537 +#: editor_markers.cc:483 editor_markers.cc:538 #, fuzzy msgid "Set Range from Range Selection" msgstr "sélection d'intervalle" -#: editor_markers.cc:486 +#: editor_markers.cc:487 #, fuzzy msgid "Rename Range" msgstr "Renommer la piste" -#: editor_markers.cc:487 editor_markers.cc:539 +#: editor_markers.cc:488 editor_markers.cc:540 #, fuzzy msgid "Hide Range" msgstr "Ajouter un nouvel intervalle" -#: editor_markers.cc:488 +#: editor_markers.cc:489 #, fuzzy msgid "Remove Range" msgstr "Enlever une trame" -#: editor_markers.cc:492 editor_markers.cc:541 +#: editor_markers.cc:493 editor_markers.cc:542 #, fuzzy msgid "Separate Regions in Range" msgstr "Nouvelle région à partir de l'intervalle" -#: editor_markers.cc:493 editor_markers.cc:542 +#: editor_markers.cc:494 editor_markers.cc:543 #, fuzzy msgid "Select All in Range" msgstr "Tout sélectionner dans la piste" -#: editor_markers.cc:519 +#: editor_markers.cc:520 msgid "Set Loop Range" msgstr "Définir l'intervalle de boucle" -#: editor_markers.cc:520 +#: editor_markers.cc:521 msgid "Set Punch Range" msgstr "Définir l'intervalle d'insertion" -#: editor_markers.cc:814 +#: editor_markers.cc:815 #, fuzzy msgid "New Name:" msgstr "nouveau nom :" -#: editor_markers.cc:817 +#: editor_markers.cc:818 msgid "ardour: rename mark" msgstr "ardour : renommer le marqueur" -#: editor_markers.cc:819 +#: editor_markers.cc:820 msgid "ardour: rename range" msgstr "ardour : renommer l'intervalle" -#: editor_markers.cc:839 +#: editor_markers.cc:840 #, fuzzy msgid "rename marker" msgstr "enlever le marqueur" -#: editor_markers.cc:864 +#: editor_markers.cc:865 msgid "set loop range" msgstr "définir l'intervalle de boucle" -#: editor_markers.cc:890 +#: editor_markers.cc:891 msgid "set punch range" msgstr "définir l'intervalle d'insertion" @@ -3765,76 +3739,81 @@ msgstr "définir l'intervalle d'insertion" msgid "Editor::event_frame() used on unhandled event type %1" msgstr "Editor::event_frame() utilisé sur un évènement non géré de type %1" -#: editor_mouse.cc:1589 +#: editor_mouse.cc:313 +#, fuzzy +msgid "select on click" +msgstr "Utiliser comme clic" + +#: editor_mouse.cc:1590 msgid "programming error: start_grab called without drag item" msgstr "erreur de programmation : start_grab appelé sans objet a ramasser" -#: editor_mouse.cc:1793 +#: editor_mouse.cc:1814 msgid "change fade in length" msgstr "modifier la longueur du fondu d'ouverture" -#: editor_mouse.cc:1811 +#: editor_mouse.cc:1832 #, fuzzy msgid "programming error: fade out canvas item has no regionview data pointer!" msgstr "" "programming error: fade out canvas item has no regionview data pointer!" -#: editor_mouse.cc:1885 +#: editor_mouse.cc:1906 msgid "change fade out length" msgstr "modifier la longueur du fondu de fermeture" -#: editor_mouse.cc:1904 +#: editor_mouse.cc:1925 msgid "programming error: cursor canvas item has no cursor data pointer!" msgstr "" "erreur de programmation : objet canvas de curseur sans pointeur de données " "curseur" -#: editor_mouse.cc:2119 +#: editor_mouse.cc:2142 #, fuzzy msgid "move marker" msgstr "enlever le marqueur" -#: editor_mouse.cc:2142 editor_mouse.cc:2173 editor_tempodisplay.cc:461 +#: editor_mouse.cc:2165 editor_mouse.cc:2196 editor_tempodisplay.cc:459 msgid "" "programming error: meter marker canvas item has no marker object pointer!" msgstr "" "erreur de programmation: meter marker canvas item has no marker object " "pointer!" -#: editor_mouse.cc:2241 +#: editor_mouse.cc:2264 #, fuzzy msgid "copy meter mark" msgstr "déplacer le marqueur de vu-mètre" -#: editor_mouse.cc:2251 +#: editor_mouse.cc:2274 msgid "move meter mark" msgstr "déplacer le marqueur de vu-mètre" -#: editor_mouse.cc:2266 editor_mouse.cc:2299 editor_tempodisplay.cc:327 -#: editor_tempodisplay.cc:411 editor_tempodisplay.cc:430 +#: editor_mouse.cc:2289 editor_mouse.cc:2322 editor_tempodisplay.cc:331 +#: editor_tempodisplay.cc:409 editor_tempodisplay.cc:428 msgid "" "programming error: tempo marker canvas item has no marker object pointer!" msgstr "" "erreur de programmation : objet canvas de marqueur de tempo sans pointeur " "d'objet marqueur !" -#: editor_mouse.cc:2271 editor_mouse.cc:2304 editor_tempodisplay.cc:332 -#: editor_tempodisplay.cc:416 +#: editor_mouse.cc:2294 editor_mouse.cc:2327 editor_tempodisplay.cc:336 +#: editor_tempodisplay.cc:414 msgid "programming error: marker for tempo is not a tempo marker!" msgstr "" "erreur de programmation : le marqueur du tempo n'est pas un marqueur de " "tempo !" -#: editor_mouse.cc:2371 +#: editor_mouse.cc:2394 #, fuzzy msgid "copy tempo mark" msgstr "déplacer le marqueur de tempo" -#: editor_mouse.cc:2381 +#: editor_mouse.cc:2404 msgid "move tempo mark" msgstr "déplacer le marqueur de tempo" -#: editor_mouse.cc:2395 editor_mouse.cc:2414 editor_mouse.cc:2427 +#: editor_mouse.cc:2418 editor_mouse.cc:2437 editor_mouse.cc:2450 msgid "" "programming error: control point canvas item has no control point object " "pointer!" @@ -3842,92 +3821,93 @@ msgstr "" "erreur de programmation : point de contrôle de l'objet canvas sans pointeur " "d'objet point de contrôle !" -#: editor_mouse.cc:2525 +#: editor_mouse.cc:2555 msgid "programming error: line canvas item has no line pointer!" msgstr "" "erreur de programmation : objet canvas de ligne sans pointeur de ligne !" -#: editor_mouse.cc:2634 +#: editor_mouse.cc:2664 #, fuzzy msgid "move region(s)" msgstr "enlever la région" -#. this is committed in the grab finished callback. -#: editor_mouse.cc:2646 -msgid "Drag region copy" -msgstr "Déplacer la copie de la région" - -#: editor_mouse.cc:2758 +#: editor_mouse.cc:2727 #, fuzzy msgid "Drag region brush" msgstr "Déplacer la/les région(s)" +#. don't copy again +#. this is committed in the grab finished callback. +#: editor_mouse.cc:2751 +msgid "Drag region copy" +msgstr "Déplacer la copie de la région" + #. A selection grab currently creates two undo/redo operations, one for #. creating the new region and another for moving it. #. -#: editor_mouse.cc:3574 +#: editor_mouse.cc:3609 #, fuzzy msgid "selection grab" msgstr "attraper la sélection" -#: editor_mouse.cc:3615 +#: editor_mouse.cc:3650 #, fuzzy msgid "cancel selection" msgstr "sélection d'intervalle" -#: editor_mouse.cc:3722 +#: editor_mouse.cc:3760 msgid "range selection" msgstr "sélection d'intervalle" -#: editor_mouse.cc:3738 +#: editor_mouse.cc:3776 msgid "trim selection start" msgstr "élaguer le début de la sélection" -#: editor_mouse.cc:3754 +#: editor_mouse.cc:3792 msgid "trim selection end" msgstr "élaguer la fin de la sélection" -#: editor_mouse.cc:3771 +#: editor_mouse.cc:3809 msgid "move selection" msgstr "déplacer la sélection" -#: editor_mouse.cc:4157 +#: editor_mouse.cc:4195 msgid "Start point trim" msgstr "Point de départ d'élaguage" -#: editor_mouse.cc:4185 +#: editor_mouse.cc:4223 msgid "End point trim" msgstr "Point de fin d'élaguage" -#: editor_mouse.cc:4224 +#: editor_mouse.cc:4262 msgid "trimmed region" msgstr "région élaguée" -#: editor_mouse.cc:4363 +#: editor_mouse.cc:4400 msgid "new range marker" msgstr "nouveau marqueur d'intervalle" -#: editor_mouse.cc:4578 +#: editor_mouse.cc:4642 msgid "select regions" msgstr "sélectionner les régions" -#: editor_mouse.cc:4607 +#: editor_mouse.cc:4671 msgid "Name for region:" msgstr "Nom de la région :" -#: editor_mouse.cc:4671 +#: editor_mouse.cc:4735 msgid "timestretch" msgstr "déformation temporelle" -#: editor_ops.cc:132 +#: editor_ops.cc:195 msgid "split" msgstr "séparer" -#: editor_ops.cc:168 +#: editor_ops.cc:231 msgid "remove region" msgstr "enlever la région" -#: editor_ops.cc:187 +#: editor_ops.cc:250 msgid "" " This is destructive, will possibly delete audio files\n" "It cannot be undone\n" @@ -3937,229 +3917,229 @@ msgstr "" "Cela ne pourra être annulé\n" "Voulez-vous vraiment détruire %1 ?" -#: editor_ops.cc:191 +#: editor_ops.cc:254 msgid "these regions" msgstr "ces régions" -#: editor_ops.cc:191 +#: editor_ops.cc:254 msgid "this region" msgstr "cette région" -#: editor_ops.cc:193 editor_ops.cc:3229 route_ui.cc:700 -#: visual_time_axis.cc:277 +#: editor_ops.cc:256 editor_ops.cc:3318 route_ui.cc:707 +#: visual_time_axis.cc:278 msgid "No, do nothing." msgstr "Non, ne rien faire." -#: editor_ops.cc:196 +#: editor_ops.cc:259 msgid "Yes, destroy them." msgstr "Oui, les détruire." -#: editor_ops.cc:198 editor_ops.cc:3230 +#: editor_ops.cc:261 editor_ops.cc:3319 msgid "Yes, destroy it." msgstr "Oui, la supprimer." -#: editor_ops.cc:289 editor_ops.cc:317 +#: editor_ops.cc:352 editor_ops.cc:380 msgid "extend selection" msgstr "étendre la sélection" -#: editor_ops.cc:333 editor_ops.cc:367 editor_ops.cc:411 editor_ops.cc:437 +#: editor_ops.cc:396 editor_ops.cc:430 editor_ops.cc:474 editor_ops.cc:500 msgid "nudge forward" msgstr "décaler vers l'avant" -#: editor_ops.cc:501 +#: editor_ops.cc:564 msgid "build_region_boundary_cache called with snap_type = %1" msgstr "build_region_boundary_cache appelé avec snap_type = %1" -#: editor_ops.cc:1354 +#: editor_ops.cc:1420 #, fuzzy msgid "select all within" msgstr "Tout sélectionner" -#: editor_ops.cc:1380 +#: editor_ops.cc:1452 #, fuzzy msgid "set selection from region" msgstr "définir la sélection à partir de l'intervalle" -#: editor_ops.cc:1413 +#: editor_ops.cc:1485 msgid "set selection from range" msgstr "définir la sélection à partir de l'intervalle" -#: editor_ops.cc:1443 +#: editor_ops.cc:1515 #, fuzzy msgid "select all from range" msgstr "sélectionner la plage de zoom" -#: editor_ops.cc:1465 +#: editor_ops.cc:1537 #, fuzzy msgid "select all from punch" msgstr "Tout sélectionner" -#: editor_ops.cc:1487 +#: editor_ops.cc:1559 #, fuzzy msgid "select all from loop" msgstr "Tout sélectionner" -#: editor_ops.cc:1501 +#: editor_ops.cc:1573 #, fuzzy msgid "select all after cursor" msgstr "Coller au curseur d'édition" -#: editor_ops.cc:1506 +#: editor_ops.cc:1578 #, fuzzy msgid "select all before cursor" msgstr "définir la synchro. au curseur d'édition" -#: editor_ops.cc:1536 +#: editor_ops.cc:1608 #, fuzzy msgid "select all between cursors" msgstr "définir la synchro. au curseur d'édition" -#: editor_ops.cc:1667 +#: editor_ops.cc:1739 msgid "clear markers" msgstr "effacer les marqueurs" -#: editor_ops.cc:1679 +#: editor_ops.cc:1751 msgid "clear ranges" msgstr "effacer les intervalles" -#: editor_ops.cc:1698 +#: editor_ops.cc:1770 msgid "clear locations" msgstr "effacer les emplacements" -#: editor_ops.cc:1748 +#: editor_ops.cc:1820 msgid "insert dragged region" msgstr "insérer la région déplacée" -#: editor_ops.cc:1784 +#: editor_ops.cc:1856 msgid "insert region" msgstr "insérer une région" -#: editor_ops.cc:1975 io_selector.cc:57 io_selector.cc:791 +#: editor_ops.cc:2047 io_selector.cc:58 io_selector.cc:792 msgid "OK" msgstr "OK" -#: editor_ops.cc:1982 +#: editor_ops.cc:2054 msgid "ardour: rename region" msgstr "ardour : renommer la région" -#: editor_ops.cc:2205 editor_ops.cc:2254 +#: editor_ops.cc:2277 editor_ops.cc:2326 msgid "separate" msgstr "séparer" -#: editor_ops.cc:2316 +#: editor_ops.cc:2388 msgid "trim to selection" msgstr "élaguer selon la sélection" -#: editor_ops.cc:2356 +#: editor_ops.cc:2428 msgid "region fill" msgstr "remplissage de la région" -#: editor_ops.cc:2415 +#: editor_ops.cc:2487 msgid "fill selection" msgstr "remplir la sélection" -#: editor_ops.cc:2436 +#: editor_ops.cc:2508 #, fuzzy msgid "Programming error. that region doesn't cover that position" msgstr "" "erreur de programmation : la carte d'emplacements/marqueurs ne contient pas " "d'emplacements !" -#: editor_ops.cc:2439 +#: editor_ops.cc:2511 #, fuzzy msgid "set region sync position" msgstr "Régions/position" -#: editor_ops.cc:2454 +#: editor_ops.cc:2526 msgid "Place the edit cursor at the desired sync point" msgstr "Placer le curseur d'édition au point de synchro. désiré" -#: editor_ops.cc:2459 +#: editor_ops.cc:2531 msgid "set sync from edit cursor" msgstr "définir la synchro. au curseur d'édition" -#: editor_ops.cc:2471 +#: editor_ops.cc:2543 msgid "remove sync" msgstr "enlever la synchro." -#: editor_ops.cc:2485 +#: editor_ops.cc:2557 msgid "naturalize" msgstr "normaliser" -#: editor_ops.cc:2549 +#: editor_ops.cc:2621 msgid "align selection (relative)" msgstr "Aligner la sélection (relativement)" -#: editor_ops.cc:2577 +#: editor_ops.cc:2649 msgid "align selection" msgstr "aligner la sélection" -#: editor_ops.cc:2589 +#: editor_ops.cc:2661 msgid "align region" msgstr "aligner la région" -#: editor_ops.cc:2636 editor_ops.cc:2661 +#: editor_ops.cc:2708 editor_ops.cc:2733 #, fuzzy msgid "trim to edit" msgstr "élaguer to edit" -#: editor_ops.cc:2712 +#: editor_ops.cc:2784 #, fuzzy msgid "ardour: freeze" msgstr "ardour :" -#: editor_ops.cc:2717 +#: editor_ops.cc:2789 #, fuzzy msgid "Cancel Freeze" msgstr "Annuler" -#: editor_ops.cc:2754 +#: editor_ops.cc:2826 #, fuzzy msgid "bounce range" msgstr "bounce intervalle" -#: editor_ops.cc:2807 +#: editor_ops.cc:2879 msgid "cut" msgstr "couper" -#: editor_ops.cc:2810 +#: editor_ops.cc:2882 msgid "copy" msgstr "copier" -#: editor_ops.cc:2823 +#: editor_ops.cc:2895 msgid " objects" msgstr " objets" -#: editor_ops.cc:2849 +#: editor_ops.cc:2921 msgid " range" msgstr " intervalle" -#: editor_ops.cc:3006 +#: editor_ops.cc:3078 msgid "paste" msgstr "coller" -#: editor_ops.cc:3044 +#: editor_ops.cc:3116 msgid "paste chunk" msgstr "coller le fragment" #. clear (below) will clear the argument list -#: editor_ops.cc:3085 +#: editor_ops.cc:3157 msgid "duplicate region" msgstr "dupliquer la région" -#: editor_ops.cc:3130 +#: editor_ops.cc:3202 msgid "duplicate selection" msgstr "dupliquer la sélection" -#: editor_ops.cc:3170 +#: editor_ops.cc:3259 msgid "clear playlist" msgstr "effacer la liste de lecture" -#: editor_ops.cc:3199 +#: editor_ops.cc:3288 msgid "nudge track" msgstr "décaler la piste" -#: editor_ops.cc:3226 +#: editor_ops.cc:3315 msgid "" "Do you really want to destroy the last capture?\n" "(This is destructive and cannot be undone)" @@ -4167,159 +4147,156 @@ msgstr "" "Voulez-vous vraiment supprimer la dernière capture ?\n" "(cette opération est destructive et ne pourra pas être annulée)" -#: editor_ops.cc:3254 +#: editor_ops.cc:3343 msgid "normalize" msgstr "normaliser" -#: editor_ops.cc:3301 +#: editor_ops.cc:3390 msgid "reverse regions" msgstr "inverser les régions" -#: editor_region_list.cc:93 editor_region_list.cc:98 editor_region_list.cc:101 -#: location_ui.cc:55 +#: editor_region_list.cc:98 editor_region_list.cc:103 +#: editor_region_list.cc:106 location_ui.cc:56 msgid "Hidden" msgstr "Caché" #. added a new fresh one at the end -#: editor_route_list.cc:101 editor_route_list.cc:102 editor_route_list.cc:246 +#: editor_route_list.cc:102 editor_route_list.cc:103 editor_route_list.cc:247 msgid "editor" msgstr "éditeur" -#: editor_route_list.cc:309 mixer_ui.cc:695 +#: editor_route_list.cc:310 mixer_ui.cc:699 msgid "Show All" msgstr "Tout montrer" -#: editor_route_list.cc:310 mixer_ui.cc:696 +#: editor_route_list.cc:311 mixer_ui.cc:700 msgid "Hide All" msgstr "Tout cacher" -#: editor_route_list.cc:311 mixer_ui.cc:697 +#: editor_route_list.cc:312 mixer_ui.cc:701 #, fuzzy msgid "Show All Audio Tracks" msgstr "Montrer tous les BusAudio" -#: editor_route_list.cc:312 mixer_ui.cc:698 +#: editor_route_list.cc:313 mixer_ui.cc:702 #, fuzzy msgid "Hide All Audio Tracks" msgstr "Cacher tous les BusAudio" -#: editor_route_list.cc:313 mixer_ui.cc:699 +#: editor_route_list.cc:314 mixer_ui.cc:703 #, fuzzy msgid "Show All Audio Busses" msgstr "Montrer tous les BusAudio" -#: editor_route_list.cc:314 mixer_ui.cc:700 +#: editor_route_list.cc:315 mixer_ui.cc:704 #, fuzzy msgid "Hide All Audio Busses" msgstr "Cacher tous les BusAudio" -#: editor_rulers.cc:311 +#: editor_rulers.cc:312 msgid "New location marker" msgstr "Nouveau marqueur d'emplacement" -#: editor_rulers.cc:312 +#: editor_rulers.cc:313 msgid "Clear all locations" msgstr "Effacer tous les emplacements" #. ruler_items.push_back (MenuElem (_("New Range"))); -#: editor_rulers.cc:317 +#: editor_rulers.cc:318 msgid "Clear all ranges" msgstr "Effacer tous les intervalles" -#: editor_rulers.cc:326 +#: editor_rulers.cc:327 msgid "New Tempo" msgstr "Nouveau tempo" -#: editor_rulers.cc:327 +#: editor_rulers.cc:328 msgid "Clear tempo" msgstr "Effacer le tempo" -#: editor_rulers.cc:332 +#: editor_rulers.cc:333 msgid "New Meter" msgstr "Nouveau vu-mètre" -#: editor_rulers.cc:333 +#: editor_rulers.cc:334 msgid "Clear meter" msgstr "Effacer les vu-mètre" -#: editor_rulers.cc:341 +#: editor_rulers.cc:342 msgid "Min:Secs" msgstr "Mins:Secs" -#: editor_selection_list.cc:110 +#: editor_selection_list.cc:108 #, fuzzy msgid "Name for Chunk:" msgstr "nom du fragment :" -#: editor_selection_list.cc:113 +#: editor_selection_list.cc:111 #, fuzzy msgid "Create Chunk" msgstr "Créer un fragment" -#: editor_selection_list.cc:113 +#: editor_selection_list.cc:111 msgid "Forget it" msgstr "Oublier" -#: editor_tempodisplay.cc:249 editor_tempodisplay.cc:289 +#: editor_tempodisplay.cc:253 editor_tempodisplay.cc:293 msgid "add" msgstr "ajouter" -#: editor_tempodisplay.cc:271 +#: editor_tempodisplay.cc:275 msgid "add tempo mark" msgstr "ajouter un marqueur de tempo" -#: editor_tempodisplay.cc:311 +#: editor_tempodisplay.cc:315 msgid "add meter mark" msgstr "ajouter un marqueur de vu-mètre" -#: editor_tempodisplay.cc:344 editor_tempodisplay.cc:375 +#: editor_tempodisplay.cc:348 editor_tempodisplay.cc:376 msgid "done" msgstr "terminé" -#: editor_tempodisplay.cc:365 editor_tempodisplay.cc:396 +#: editor_tempodisplay.cc:366 editor_tempodisplay.cc:394 msgid "replace tempo mark" msgstr "remplacer le marqueur de tempo" -#: editor_tempodisplay.cc:435 editor_tempodisplay.cc:466 +#: editor_tempodisplay.cc:433 editor_tempodisplay.cc:464 msgid "programming error: marker for meter is not a meter marker!" msgstr "erreur de programmation : marker for meter is not a meter marker!" -#: editor_tempodisplay.cc:445 editor_tempodisplay.cc:478 +#: editor_tempodisplay.cc:443 editor_tempodisplay.cc:476 msgid "remove tempo mark" msgstr "enlever le marqueur de tempo" -#: editor_timefx.cc:50 +#: editor_timefx.cc:51 msgid "Quick but Ugly" msgstr "Rapide mais sale" -#: editor_timefx.cc:51 +#: editor_timefx.cc:52 msgid "Skip Anti-aliasing" msgstr "Sauter l'anti-crénelage" -#: editor_timefx.cc:53 -msgid "Stretch/Shrink it" -msgstr "Étirer/Rétrécir" - -#: editor_timefx.cc:57 +#: editor_timefx.cc:56 msgid "ardour: timestretch" msgstr "ardour : déformation temporelle" -#: editor_timefx.cc:58 +#: editor_timefx.cc:57 msgid "TimeStretchDialog" msgstr "TimeStretchDialog" -#: editor_timefx.cc:80 editor_timefx.cc:81 editor_timefx.cc:82 -#: editor_timefx.cc:83 +#: editor_timefx.cc:70 +msgid "Stretch/Shrink it" +msgstr "Étirer/Rétrécir" + +#: editor_timefx.cc:73 editor_timefx.cc:74 msgid "TimeStretchButton" msgstr "TimeStretchButton" -#: editor_timefx.cc:84 +#: editor_timefx.cc:75 msgid "TimeStretchProgress" msgstr "TimeStretchProgress" -#. GTK2FIX -#. current_timestretch->close (); -#: editor_timefx.cc:153 +#: editor_timefx.cc:139 msgid "timestretch cannot be started - thread creation error" msgstr "" @@ -4454,7 +4431,7 @@ msgstr "" msgid "Export to File" msgstr "Exporter sur CD" -#: export_dialog.cc:113 option_editor.cc:82 option_editor.cc:83 +#: export_dialog.cc:113 option_editor.cc:83 option_editor.cc:84 msgid "Browse" msgstr "Parcourir" @@ -4470,7 +4447,8 @@ msgstr "ardour : exporter" msgid "ardour_export" msgstr "ardour_exporter" -#: export_dialog.cc:139 export_dialog.cc:155 +#: export_dialog.cc:139 export_dialog.cc:155 mixer_strip.cc:124 +#: mixer_strip.cc:767 msgid "Output" msgstr "Sortie" @@ -4507,146 +4485,77 @@ msgstr "" msgid "File already exists, do you want to overwrite it?" msgstr "" -#: export_dialog.cc:1159 export_range_markers_dialog.cc:154 +#: export_dialog.cc:1159 export_range_markers_dialog.cc:153 msgid "Cannot write file in: " msgstr "" #. warning dialog -#: export_range_markers_dialog.cc:136 +#: export_range_markers_dialog.cc:135 msgid "Please enter a valid target directory." msgstr "" -#: export_range_markers_dialog.cc:144 +#: export_range_markers_dialog.cc:143 msgid "" "Please select an existing target directory. Files\n" "are not allowed!" msgstr "" -#: gain_automation_time_axis.cc:61 +#: gain_automation_time_axis.cc:62 #, fuzzy msgid "add gain automation event" msgstr "ajouter les évènements d'automatisation à " -#: gain_meter.cc:66 +#: gain_meter.cc:67 msgid "cannot find images for fader slider" msgstr "" -#: gain_meter.cc:73 +#: gain_meter.cc:74 msgid "cannot find images for fader rail" msgstr "" -#: gain_meter.cc:88 -msgid "dbFS" -msgstr "" - -#: gain_meter.cc:89 gain_meter.cc:143 gain_meter.cc:704 -msgid "pre" -msgstr "" - -#: gain_meter.cc:139 gain_meter.cc:700 -#, fuzzy -msgid "input" -msgstr "entrée %1" - -#: gain_meter.cc:147 gain_meter.cc:708 -#, fuzzy -msgid "post" -msgstr "port" - -#. TRANSLATORS: this string should be longest of the strings -#. used to describe meter points. In english, its "input". -#. -#: gain_meter.cc:155 -msgid "tupni" -msgstr "" - -#: gain_meter.cc:174 gain_meter.cc:458 gain_meter.cc:480 gain_meter.cc:525 +#: gain_meter.cc:130 gain_meter.cc:339 gain_meter.cc:494 gain_meter.cc:539 #, fuzzy msgid "-inf" msgstr "entrée" -#: glade/new_session_dialog.glade.h:1 +#: gain_meter.cc:140 #, fuzzy -msgid "Advanced" -msgstr "Avancé..." +msgid "Fader automation mode" +msgstr "mode d'automatisation de panoramique" -#: glade/new_session_dialog.glade.h:2 -msgid "Input" +#: gain_meter.cc:141 +#, fuzzy +msgid "Fader automation type" +msgstr "Type d'automatisation de panoramique" + +#. XXX it might different in different languages +#: gain_meter.cc:182 gain_meter.cc:817 panner_ui.cc:99 panner_ui.cc:807 +#, fuzzy +msgid "Abs" +msgstr "abs" + +#: gain_meter.cc:472 +#, fuzzy +msgid "-Inf" +msgstr "entrée" + +#: gain_meter.cc:781 mixer_strip.cc:770 panner_ui.cc:771 +#, fuzzy +msgid "O" +msgstr "OU" + +#: gain_meter.cc:784 panner_ui.cc:774 +msgid "P" msgstr "" -#: glade/new_session_dialog.glade.h:3 -#, fuzzy -msgid "Output" -msgstr "Sortie" - -#: glade/new_session_dialog.glade.h:4 -#, fuzzy -msgid "Automatically connect inputs" -msgstr "connecter les entrées de piste aux ports physiques automatiquement" - -#: glade/new_session_dialog.glade.h:5 -#, fuzzy -msgid "Automatically connect outputs" -msgstr "connecter les sorties de piste manuellement" - -#: glade/new_session_dialog.glade.h:6 -#, fuzzy -msgid "Channel Count" -msgstr "Annuler l'importation" - -#: glade/new_session_dialog.glade.h:7 -msgid "Connect to Master Bus" +#: gain_meter.cc:787 panner_ui.cc:777 +msgid "T" msgstr "" -#: glade/new_session_dialog.glade.h:8 -msgid "Connect to physical outputs" +#: gain_meter.cc:790 panner_ui.cc:780 +msgid "W" msgstr "" -#: glade/new_session_dialog.glade.h:9 -#, fuzzy -msgid "Create Control Bus" -msgstr "Sorties de contrôle" - -#: glade/new_session_dialog.glade.h:10 -#, fuzzy -msgid "Create Master Bus" -msgstr "utiliser les sorties maître" - -#: glade/new_session_dialog.glade.h:11 -#, fuzzy -msgid "New Session" -msgstr "Session" - -#: glade/new_session_dialog.glade.h:12 -#, fuzzy -msgid "Open Recent Session" -msgstr "ouvrir session" - -#: glade/new_session_dialog.glade.h:13 -#, fuzzy -msgid "Open Session" -msgstr "ouvrir session" - -#: glade/new_session_dialog.glade.h:14 -#, fuzzy -msgid "Port limit" -msgstr "Oublier" - -#: glade/new_session_dialog.glade.h:15 -#, fuzzy -msgid "Select a File" -msgstr "Tout sélectionner" - -#: glade/new_session_dialog.glade.h:16 -#, fuzzy -msgid "Select a Session" -msgstr "sélectionner les régions" - -#: glade/new_session_dialog.glade.h:17 -#, fuzzy -msgid "Track/Bus connection options" -msgstr "Inspecteur de pistes/bus" - #: gtk-custom-ruler.c:126 #, fuzzy msgid "Lower" @@ -4692,113 +4601,113 @@ msgid "Draw current ruler position" msgstr "" #. end-of-file, other end closed or shutdown? -#: imageframe_socket_handler.cc:126 +#: imageframe_socket_handler.cc:127 msgid "Image Compositor Socket has been shutdown/closed" msgstr "La socket du compositeur d'image a été arrêtée/fermée" -#: imageframe_time_axis.cc:287 +#: imageframe_time_axis.cc:286 msgid "0.5 seconds" msgstr "0.5 secondes" -#: imageframe_time_axis.cc:288 marker_time_axis.cc:241 +#: imageframe_time_axis.cc:287 marker_time_axis.cc:242 msgid "1 seconds" msgstr "1 seconde" -#: imageframe_time_axis.cc:289 marker_time_axis.cc:242 +#: imageframe_time_axis.cc:288 marker_time_axis.cc:243 msgid "1.5 seconds" msgstr "1.5 secondes" -#: imageframe_time_axis.cc:290 marker_time_axis.cc:243 +#: imageframe_time_axis.cc:289 marker_time_axis.cc:244 msgid "2 seconds" msgstr "2 secondes" -#: imageframe_time_axis.cc:291 marker_time_axis.cc:244 +#: imageframe_time_axis.cc:290 marker_time_axis.cc:245 msgid "2.5 seconds" msgstr "2.5 secondes" -#: imageframe_time_axis.cc:292 marker_time_axis.cc:245 +#: imageframe_time_axis.cc:291 marker_time_axis.cc:246 msgid "3 seconds" msgstr "3 secondes" #. duration_items.push_back(SeparatorElem()) ; #. duration_items.push_back(MenuElem (_("custom"), mem_fun(*this, &ImageFrameTimeAxis::set_marker_duration_custom))) ; -#: imageframe_time_axis.cc:297 marker_time_axis.cc:250 +#: imageframe_time_axis.cc:296 marker_time_axis.cc:251 msgid "Duration (sec)" msgstr "Durée (s)" -#: imageframe_time_axis.cc:302 +#: imageframe_time_axis.cc:301 msgid "Remove Frame" msgstr "Enlever une trame" -#: imageframe_time_axis.cc:305 +#: imageframe_time_axis.cc:304 msgid "Image Frame" msgstr "Trame d'image" -#: imageframe_time_axis.cc:306 marker_time_axis.cc:256 +#: imageframe_time_axis.cc:305 marker_time_axis.cc:257 msgid "Rename Track" msgstr "Renommer la piste" -#: io_selector.cc:59 io_selector.cc:793 +#: io_selector.cc:60 io_selector.cc:794 msgid "Rescan" msgstr "Rafraîchir" -#: io_selector.cc:67 +#: io_selector.cc:68 msgid "%1 input" msgstr "entrée %1" -#: io_selector.cc:69 +#: io_selector.cc:70 msgid "%1 output" msgstr "sortie %1" -#: io_selector.cc:141 route_params_ui.cc:106 +#: io_selector.cc:142 route_params_ui.cc:107 msgid "Inputs" msgstr "Entrées" -#: io_selector.cc:141 route_params_ui.cc:107 +#: io_selector.cc:142 route_params_ui.cc:108 msgid "Outputs" msgstr "Sorties" -#: io_selector.cc:142 +#: io_selector.cc:143 msgid "Add Input" msgstr "Ajouter une entrée" -#: io_selector.cc:142 +#: io_selector.cc:143 msgid "Add Output" msgstr "Ajouter une sortie" -#: io_selector.cc:143 +#: io_selector.cc:144 msgid "Remove Input" msgstr "Enlever une entrée" -#: io_selector.cc:143 +#: io_selector.cc:144 msgid "Remove Output" msgstr "Enlever une sortie" -#: io_selector.cc:144 +#: io_selector.cc:145 msgid "Disconnect All" msgstr "Déconnecter tout" -#: io_selector.cc:158 +#: io_selector.cc:159 msgid "Available connections" msgstr "Connexions disponibles" -#: io_selector.cc:554 io_selector.cc:573 +#: io_selector.cc:555 io_selector.cc:574 msgid "There are no more JACK ports available." msgstr "Il n'y a plus de ports JACK disponibles" -#: io_selector.cc:648 io_selector.cc:675 io_selector.cc:728 +#: io_selector.cc:649 io_selector.cc:676 io_selector.cc:729 msgid "port" msgstr "port" -#: io_selector.cc:797 +#: io_selector.cc:798 msgid "ardour: " msgstr "ardour :" -#: keyboard.cc:297 +#: keyboard.cc:299 msgid "KeyboardTarget: keyname \"%1\" is unknown." msgstr "KeyboardTarget : nom de touche \"%1\" inconnue" -#: keyboard.cc:523 +#: keyboard.cc:525 msgid "" "Your system is completely broken - NumLock uses \"%1\"as its modifier. This " "is madness - see the man page for xmodmap to find out how to fix this." @@ -4807,7 +4716,7 @@ msgstr "" "utilise \"%1\" comme modificateur. C'est n'importe quoi -- consultez la page " "de manuel de xmodmap pour trouver comment réparer ça." -#: keyboard.cc:531 +#: keyboard.cc:533 msgid "" "Your system generates \"%1\" when the NumLock key is pressed. This can cause " "problems when editing so Ardour will use %2 to mean Meta rather than %1" @@ -4816,103 +4725,103 @@ msgstr "" "pressée. Cela peut causer des problèmes pendant l'édition, aussi Ardour " "utilisera %2 comme touche Meta plutôt que %1" -#: keyboard.cc:592 +#: keyboard.cc:594 msgid "You have %1 keys bound to \"mod1\"" msgstr "Vous avez %1 touches affectées à \"mod1\"" -#: keyboard.cc:607 +#: keyboard.cc:609 msgid "You have %1 keys bound to \"mod2\"" msgstr "Vous avez %1 touches affectées à \"mod2\"" -#: keyboard.cc:622 +#: keyboard.cc:624 msgid "You have %1 keys bound to \"mod3\"" msgstr "Vous avez %1 touches affectées à \"mod3\"" -#: keyboard.cc:637 +#: keyboard.cc:639 msgid "You have %1 keys bound to \"mod4\"" msgstr "Vous avez %1 touches affectées à \"mod4\"" -#: keyboard.cc:652 +#: keyboard.cc:654 msgid "You have %1 keys bound to \"mod5\"" msgstr "Vous avez %1 touches affectées à \"mod5\"" -#: location_ui.cc:47 location_ui.cc:50 +#: location_ui.cc:48 location_ui.cc:51 msgid "Set" msgstr "Définir" -#: location_ui.cc:48 location_ui.cc:51 +#: location_ui.cc:49 location_ui.cc:52 msgid "Go" msgstr "Aller" -#: location_ui.cc:54 +#: location_ui.cc:55 msgid "CD" msgstr "CD" -#: location_ui.cc:57 +#: location_ui.cc:58 msgid "SCMS" msgstr "SCMS" -#: location_ui.cc:58 +#: location_ui.cc:59 msgid "Pre-Emphasis" msgstr "Pré-emphase" -#: location_ui.cc:569 +#: location_ui.cc:570 msgid "Add New Location" msgstr "Ajouter un nouvel emplacement" -#: location_ui.cc:570 +#: location_ui.cc:571 msgid "Add New Range" msgstr "Ajouter un nouvel intervalle" -#: location_ui.cc:574 +#: location_ui.cc:575 msgid "ardour: locations" msgstr "ardour : emplacements" -#: location_ui.cc:575 +#: location_ui.cc:576 msgid "ardour_locations" msgstr "ardour_emplacements" -#: location_ui.cc:603 +#: location_ui.cc:604 #, fuzzy msgid "Location (CD Index) Markers" msgstr "Marqueurs d'emplacements (Index de CD)" -#: location_ui.cc:623 +#: location_ui.cc:624 #, fuzzy msgid "Range (CD Track) Markers" msgstr "Marqueurs d'intervalles (Piste de CD)" -#: location_ui.cc:789 +#: location_ui.cc:790 msgid "add range marker" msgstr "ajouter marqueur d'intervalle" -#: main.cc:71 +#: main.cc:72 msgid "ardour is killing itself for a clean exit\n" msgstr "ardour se termine lui-même pour une sortie propre\n" -#: main.cc:80 +#: main.cc:81 msgid "stopping user interface\n" msgstr "en train d'arrêter l'interface utilisateur\n" #. XXX its doubtful that snprintf() is async-safe -#: main.cc:99 +#: main.cc:100 #, c-format msgid "%d(%d): received signal %d\n" msgstr "%d(%d) : reçu le signal %d\n" -#: main.cc:185 +#: main.cc:186 msgid "cannot become new process group leader (%1)" msgstr "" -#: main.cc:212 +#: main.cc:213 msgid "cannot setup signal handling for %1" msgstr "impossible d'installer le gestionnaire de signaux pour %1" -#: main.cc:223 +#: main.cc:224 msgid "cannot set default signal mask (%1)" msgstr "impossible de définir le masque de signalisation" -#: main.cc:253 +#: main.cc:254 #, fuzzy msgid "" "Without a UI style file, ardour will look strange.\n" @@ -4921,12 +4830,12 @@ msgstr "" "Sans un fichier de style pour son IHM, ardour aura une apparence bizarre.\n" "Veuillez faire pointer ARDOUR_UI_RC vers un fichier de style d'IHM valide" -#: main.cc:273 +#: main.cc:276 #, fuzzy msgid "Ardour could not connect to JACK." msgstr "Impossible de se reconnecter à JACK" -#: main.cc:277 +#: main.cc:280 #, fuzzy msgid "" "There are several possible reasons:\n" @@ -4946,74 +4855,12 @@ msgstr "" "\n" "Veuillez étudier les possibilités, et peut-être (re)lancer JACK." -#: main.cc:324 -msgid "Ardour/GTK " -msgstr "Ardour/GTK" - -#: main.cc:326 -msgid "" -"\n" -" (built using " -msgstr "" -"\n" -" (fonctionnant avec " - -#: main.cc:330 -msgid " with libardour " -msgstr " avec libardour " - -#: main.cc:335 -msgid " and GCC version " -msgstr "" - -#: main.cc:345 -msgid "Copyright (C) 1999-2005 Paul Davis" -msgstr "Copyright (C) 1999-2005 Paul Davis" - -#: main.cc:346 -msgid "" -"Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " -"Baker" -msgstr "" -"Certaines parties Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " -"Baker" - -#: main.cc:348 -msgid "Ardour comes with ABSOLUTELY NO WARRANTY" -msgstr "Ardour est distribué sans AUCUNE GARANTIE" - -#: main.cc:349 -msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." -msgstr "ni même pour la COMMERCIALISATION ou pour UN BUT PARTICULIER." - -#: main.cc:350 -msgid "This is free software, and you are welcome to redistribute it " -msgstr "Ceci est un logiciel libre, et vous êtes encouragé à le distribuer " - -#: main.cc:351 -msgid "under certain conditions; see the source for copying conditions." -msgstr "" -"sous certaines conditions ; voir le fichier source pour les conditions de " -"distribution." - -#: main.cc:360 -msgid "could not create ARDOUR GUI" -msgstr "impossible de créer l'interface utilisateur d'ARDOUR" - -#: main.cc:378 -msgid "Could not connect to JACK server as \"%1\"" -msgstr "Impossible de se connecter au serveur JACK en tant que \"%1\"" - -#: main.cc:381 -msgid "could not initialize Ardour." -msgstr "impossible d'initialiser Ardour." - -#: main.cc:392 +#: main.cc:310 msgid "could not load command line session \"%1\"" msgstr "impossible de charger la session indiqué en ligne de commande \"%1\"" #. it wasn't new, but we require a new session -#: main.cc:412 +#: main.cc:330 msgid "" "\n" "\n" @@ -5025,7 +4872,7 @@ msgstr "" "Une session nommé \"%1\" existe déjà.\n" "Pour éviter ce message, lancez ardour comme cela : \"ardour %1" -#: main.cc:423 +#: main.cc:341 msgid "" "\n" "\n" @@ -5038,306 +4885,458 @@ msgstr "" "Pour la créer depuis la ligne de commande, lancez ardour comme cela : " "\"ardour --new %1" +#: main.cc:405 +msgid "Ardour/GTK " +msgstr "Ardour/GTK" + +#: main.cc:407 +msgid "" +"\n" +" (built using " +msgstr "" +"\n" +" (fonctionnant avec " + +#: main.cc:411 +msgid " with libardour " +msgstr " avec libardour " + +#: main.cc:416 +msgid " and GCC version " +msgstr "" + +#: main.cc:426 +#, fuzzy +msgid "Copyright (C) 1999-2006 Paul Davis" +msgstr "Copyright (C) 1999-2005 Paul Davis" + +#: main.cc:427 +msgid "" +"Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " +"Baker" +msgstr "" +"Certaines parties Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " +"Baker" + +#: main.cc:429 +msgid "Ardour comes with ABSOLUTELY NO WARRANTY" +msgstr "Ardour est distribué sans AUCUNE GARANTIE" + +#: main.cc:430 +msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." +msgstr "ni même pour la COMMERCIALISATION ou pour UN BUT PARTICULIER." + +#: main.cc:431 +msgid "This is free software, and you are welcome to redistribute it " +msgstr "Ceci est un logiciel libre, et vous êtes encouragé à le distribuer " + +#: main.cc:432 +msgid "under certain conditions; see the source for copying conditions." +msgstr "" +"sous certaines conditions ; voir le fichier source pour les conditions de " +"distribution." + +#: main.cc:441 +msgid "could not create ARDOUR GUI" +msgstr "impossible de créer l'interface utilisateur d'ARDOUR" + +#: main.cc:459 +msgid "Could not connect to JACK server as \"%1\"" +msgstr "Impossible de se connecter au serveur JACK en tant que \"%1\"" + +#: main.cc:462 +msgid "could not initialize Ardour." +msgstr "impossible d'initialiser Ardour." + #: marker.cc:244 #, fuzzy msgid "MarkerText" msgstr "Marqueur" -#: marker_time_axis.cc:253 +#: marker_time_axis.cc:254 msgid "Remove Marker" msgstr "Enlever les marqueurs" -#: marker_time_axis.cc:255 +#: marker_time_axis.cc:256 msgid "Marker" msgstr "Marqueur" -#: meter_bridge.cc:77 +#: meter_bridge.cc:78 msgid "ardour: meter bridge" msgstr "ardour : bandeau de vu-mètre" -#: meter_bridge.cc:78 +#: meter_bridge.cc:79 msgid "ardour_meter_bridge" msgstr "ardour_bandeau_vu-mètre" -#: meter_bridge_strip.cc:79 meter_bridge_strip.cc:93 +#: meter_bridge_strip.cc:80 meter_bridge_strip.cc:94 #, c-format msgid "# of %u-sample overs" msgstr "# de %u-échantillons en dépassement" -#: meter_bridge_strip.cc:221 +#: meter_bridge_strip.cc:222 #, fuzzy msgid "New Name for Meter:" msgstr "Nouveau nom du vu-mètre :" -#: mixer_strip.cc:85 mixer_strip.cc:437 region_editor.cc:46 -msgid "mute" -msgstr "muet" +#: mixer_strip.cc:95 mixer_strip.cc:140 mixer_strip.cc:1227 +msgid "pre" +msgstr "" -#: mixer_strip.cc:85 mixer_strip.cc:438 -msgid "solo" -msgstr "solo" - -#: mixer_strip.cc:85 mixer_strip.cc:436 -msgid "RECORD" -msgstr "ENREGISTRER" - -#: mixer_strip.cc:96 mixer_strip.cc:441 mixer_strip.cc:1064 +#: mixer_strip.cc:96 mixer_strip.cc:822 #, fuzzy msgid "Comments" msgstr "commentaires" -#: mixer_strip.cc:120 mixer_strip.cc:752 -msgid "INPUT" -msgstr "ENTRÉE" +#: mixer_strip.cc:119 +#, fuzzy +msgid "Input" +msgstr "Entrées" -#: mixer_strip.cc:125 mixer_strip.cc:773 -msgid "OUTPUT" -msgstr "SORTIE" +#: mixer_strip.cc:136 mixer_strip.cc:1223 +#, fuzzy +msgid "input" +msgstr "entrée %1" -#: mixer_strip.cc:140 -msgid "Pan automation mode" -msgstr "Mode d'automatisation de panoramique" +#: mixer_strip.cc:144 mixer_strip.cc:1231 +#, fuzzy +msgid "post" +msgstr "port" -#: mixer_strip.cc:141 -msgid "Gain automation mode" -msgstr "Mode d'automatisation du gain" +#. TRANSLATORS: this string should be longest of the strings +#. used to describe meter points. In english, its "input". +#. +#: mixer_strip.cc:152 +msgid "tupni" +msgstr "" -#: mixer_strip.cc:143 -msgid "Pan automation type" -msgstr "Type d'automatisation de panoramique" - -#: mixer_strip.cc:144 -msgid "Gain automation type" -msgstr "dessiner l'automatisation du gain" - -#: mixer_strip.cc:183 mixer_strip.cc:195 mixer_strip.cc:913 -msgid "trim" -msgstr "élaguer" - -#. XXX it might different in different languages -#: mixer_strip.cc:184 mixer_strip.cc:196 mixer_strip.cc:917 -msgid "abs" -msgstr "abs" - -#: mixer_strip.cc:203 -msgid "gain automation mode" -msgstr "mode d'automatisation du gain" - -#: mixer_strip.cc:204 -msgid "pan automation mode" -msgstr "mode d'automatisation de panoramique" - -#: mixer_strip.cc:205 -msgid "gain automation state" -msgstr "état de l'automatisation du gain" - -#: mixer_strip.cc:206 -msgid "pan automation state" -msgstr "état de l'automatisation de panoramique" - -#: mixer_strip.cc:223 -msgid "varispeed" +#: mixer_strip.cc:207 +#, fuzzy +msgid "Varispeed" msgstr "varispeed" -#: mixer_strip.cc:245 mixer_strip.cc:1078 +#: mixer_strip.cc:233 mixer_strip.cc:836 #, fuzzy msgid "Click to Add/Edit Comments" msgstr "cliquer pour ajouter/éditer des commentaires" -#: mixer_strip.cc:393 +#: mixer_strip.cc:374 msgid "unknown strip width \"%1\" in XML GUI information" msgstr "" "largeur de tranche inconnue \"%1\" dans les données XML de l'interface " "utilisateur" -#: mixer_strip.cc:443 mixer_strip.cc:1062 +#: mixer_strip.cc:417 #, fuzzy -msgid "*Comments*" +msgid "record" +msgstr "Enregistrer" + +#: mixer_strip.cc:418 region_editor.cc:47 +msgid "mute" +msgstr "muet" + +#: mixer_strip.cc:419 +msgid "solo" +msgstr "solo" + +#: mixer_strip.cc:422 +#, fuzzy +msgid "comments" msgstr "commentaires" -#: mixer_strip.cc:457 -msgid "REC" -msgstr "ENR." +#: mixer_strip.cc:424 +#, fuzzy +msgid "*comments*" +msgstr "commentaires" -#: mixer_strip.cc:462 mixer_strip.cc:1072 +#: mixer_strip.cc:438 +#, fuzzy +msgid "Rec" +msgstr "Rafraîchir" + +#: mixer_strip.cc:439 +msgid "M" +msgstr "" + +#: mixer_strip.cc:440 +msgid "S" +msgstr "" + +#: mixer_strip.cc:443 mixer_strip.cc:830 #, fuzzy msgid "Cmt" msgstr "cmt" -#: mixer_strip.cc:464 mixer_strip.cc:1070 +#: mixer_strip.cc:445 mixer_strip.cc:828 msgid "*Cmt*" msgstr "" -#: mixer_strip.cc:503 mixer_strip.cc:562 redirect_box.cc:1004 +#: mixer_strip.cc:483 mixer_strip.cc:549 redirect_box.cc:1006 msgid "Not connected to JACK - no I/O changes are possible" msgstr "" -#: mixer_strip.cc:569 +#: mixer_strip.cc:560 msgid "Track" msgstr "Piste" -#: mixer_strip.cc:593 mixer_strip.cc:609 +#: mixer_strip.cc:588 mixer_strip.cc:604 msgid "could not register new ports required for that connection" msgstr "impossible de définir les nouveaux ports requis pour cette connexion" -#: mixer_strip.cc:755 -msgid "IN" +#: mixer_strip.cc:747 +#, fuzzy +msgid " Input" +msgstr "# entrées" + +#: mixer_strip.cc:750 +#, fuzzy +msgid "I" msgstr "ENTRÉE" -#: mixer_strip.cc:776 -msgid "OUT" -msgstr "SORTIE" - -#: mixer_strip.cc:884 +#: mixer_strip.cc:820 #, fuzzy -msgid "aplay" -msgstr "aplay" +msgid "*Comments*" +msgstr "commentaires" -#: mixer_strip.cc:890 -#, fuzzy -msgid "awrite" -msgstr "awrite" - -#: mixer_strip.cc:1095 +#: mixer_strip.cc:859 msgid ": comment editor" msgstr ": éditeur de commentaires" -#: mixer_strip.cc:1157 mixer_strip.cc:1178 -msgid "no group" -msgstr "aucun groupe" +#: mixer_strip.cc:953 +msgid "Grp" +msgstr "" -#: mixer_strip.cc:1181 +#: mixer_strip.cc:956 msgid "~G" msgstr "~G" -#: mixer_strip.cc:1229 +#: mixer_strip.cc:1004 #, fuzzy msgid "Invert Polarity" msgstr "polarité" -#: mixer_ui.cc:84 +#: mixer_ui.cc:85 msgid "Strips" msgstr "Tranches" -#: mixer_ui.cc:108 -msgid "groupname" -msgstr "" +#: mixer_ui.cc:110 +#, fuzzy +msgid "Group" +msgstr "Groupes de mixage" -#: mixer_ui.cc:109 region_editor.cc:48 region_editor.cc:191 -#: region_editor.cc:225 -msgid "active" -msgstr "actif" - -#: mixer_ui.cc:110 region_editor.cc:49 -msgid "visible" -msgstr "visible" - -#: mixer_ui.cc:207 mixer_ui.cc:366 +#: mixer_ui.cc:211 mixer_ui.cc:370 msgid "ardour: mixer" msgstr "ardour : console de mixage" -#: mixer_ui.cc:208 +#: mixer_ui.cc:212 msgid "ardour_mixer" msgstr "ardour_console_de_mixage" -#: mixer_ui.cc:342 +#: mixer_ui.cc:346 msgid "ardour: mixer: " msgstr "ardour : console de mixage :" -#: mixer_ui.cc:569 +#: mixer_ui.cc:573 msgid "signal" msgstr "signal" -#: mixer_ui.cc:719 +#: mixer_ui.cc:723 msgid "track display list item for renamed strip not found!" msgstr "" -#: option_editor.cc:75 +#: new_session_dialog.cc:39 +#, fuzzy +msgid "New Session Name :" +msgstr "Nom de la session :" + +#: new_session_dialog.cc:41 +msgid "Create Session Directory In :" +msgstr "" + +#: new_session_dialog.cc:43 +#, fuzzy +msgid "Use Session Template :" +msgstr "Modèle de session" + +#: new_session_dialog.cc:45 +#, fuzzy +msgid "Channel Count" +msgstr "Annuler l'importation" + +#: new_session_dialog.cc:46 +#, fuzzy +msgid "Create Monitor Bus" +msgstr "Sorties de contrôle" + +#: new_session_dialog.cc:53 +#, fuzzy +msgid "Create Master Bus" +msgstr "utiliser les sorties maître" + +#: new_session_dialog.cc:55 +#, fuzzy +msgid "Automatically Connect Inputs" +msgstr "connecter les entrées de piste aux ports physiques automatiquement" + +#: new_session_dialog.cc:56 new_session_dialog.cc:67 +#, fuzzy +msgid "Port Limit" +msgstr "Oublier" + +#: new_session_dialog.cc:64 +#, fuzzy +msgid "Track/Bus Inputs" +msgstr "Inspecteur de pistes/bus" + +#: new_session_dialog.cc:66 +#, fuzzy +msgid "Automatically Connect Outputs" +msgstr "connecter les sorties de piste manuellement" + +#: new_session_dialog.cc:75 +msgid "Connect to Master Bus" +msgstr "" + +#: new_session_dialog.cc:76 +msgid "Connect to Physical Outputs" +msgstr "" + +#: new_session_dialog.cc:80 +#, fuzzy +msgid "Track/Bus Outputs" +msgstr "Sortie" + +#: new_session_dialog.cc:83 +#, fuzzy +msgid "Advanced Options" +msgstr "Éditeur d'options" + +#: new_session_dialog.cc:91 +#, fuzzy +msgid "Open Recent Session" +msgstr "ouvrir session" + +#: new_session_dialog.cc:127 +#, fuzzy +msgid "Open Session File :" +msgstr "ouvrir session" + +#: new_session_dialog.cc:274 +#, fuzzy +msgid "New Session" +msgstr "Session" + +#: new_session_dialog.cc:276 +#, fuzzy +msgid "Open Session" +msgstr "ouvrir session" + +#: new_session_dialog.cc:281 +#, fuzzy +msgid "ardour: session control" +msgstr "ardour_nouvelle_session" + +#: new_session_dialog.cc:310 +#, fuzzy +msgid "select template" +msgstr "Pas de modèle" + +#: new_session_dialog.cc:316 +#, fuzzy +msgid "select session file" +msgstr "sélectionner les régions" + +#: new_session_dialog.cc:325 +#, fuzzy +msgid "select directory" +msgstr "sélectionner les régions" + +#: option_editor.cc:76 #, fuzzy msgid "SMPTE offset is negative" msgstr "Décalage SMPTE" -#: option_editor.cc:101 +#: option_editor.cc:102 msgid "ardour: options editor" msgstr "ardour : éditeur d'options" -#: option_editor.cc:102 +#: option_editor.cc:103 msgid "ardour_option_editor" msgstr "ardour_éditeur_d_options" -#: option_editor.cc:126 +#: option_editor.cc:127 msgid "Paths/Files" msgstr "Chemins/Fichiers" -#: option_editor.cc:127 +#: option_editor.cc:128 msgid "Kbd/Mouse" msgstr "Clavier/Souris" -#: option_editor.cc:130 +#: option_editor.cc:131 msgid "Layers & Fades" msgstr "Couches & fondus" -#: option_editor.cc:134 +#: option_editor.cc:135 msgid "MIDI" msgstr "MIDI" -#: option_editor.cc:176 +#: option_editor.cc:177 msgid "24 FPS" msgstr "24 TPS" -#: option_editor.cc:178 +#: option_editor.cc:179 #, fuzzy msgid "25 FPS" msgstr "25 TPS" -#: option_editor.cc:180 +#: option_editor.cc:181 #, fuzzy msgid "30 FPS" msgstr "30 TPS drop" -#: option_editor.cc:186 +#: option_editor.cc:187 #, fuzzy msgid "30 FPS drop" msgstr "30 TPS drop" -#: option_editor.cc:243 +#: option_editor.cc:244 msgid "session RAID path" msgstr "chemin de session RAID" -#: option_editor.cc:248 +#: option_editor.cc:249 #, fuzzy msgid "Soundfile Search Paths" msgstr "Bibliothèque audio" -#: option_editor.cc:253 +#: option_editor.cc:254 #, fuzzy msgid "Paths" msgstr "Chemins/Fichiers" -#: option_editor.cc:267 option_editor.cc:273 option_editor.cc:724 -#: option_editor.cc:751 +#: option_editor.cc:268 option_editor.cc:274 option_editor.cc:723 +#: option_editor.cc:750 msgid "internal" msgstr "interne" -#: option_editor.cc:286 +#: option_editor.cc:287 msgid "Short crossfade length (msecs)" msgstr "fondu enchaîné court (ms)" -#: option_editor.cc:298 +#: option_editor.cc:299 #, fuzzy msgid "Destructive crossfade length (msecs)" msgstr "fondu enchaîné court (ms)" -#: option_editor.cc:366 +#: option_editor.cc:367 msgid "SMPTE Frames/second" msgstr "Trames SMPTE/seconde" -#: option_editor.cc:367 +#: option_editor.cc:368 msgid "SMPTE Offset" msgstr "Décalage SMPTE" -#: option_editor.cc:461 option_editor.cc:468 option_editor.cc:471 -#: option_editor.cc:617 +#: option_editor.cc:462 option_editor.cc:469 option_editor.cc:472 +#: option_editor.cc:618 #, fuzzy msgid "online" msgstr "linéaire" @@ -5345,12 +5344,12 @@ msgstr "linéaire" #. remember, we have to handle the i18n case where the relative #. lengths of the strings in language N is different than in english. #. -#: option_editor.cc:468 option_editor.cc:469 option_editor.cc:614 +#: option_editor.cc:469 option_editor.cc:470 option_editor.cc:615 #, fuzzy msgid "offline" msgstr "linéaire" -#: option_editor.cc:669 +#: option_editor.cc:670 msgid "Choose Click" msgstr "" @@ -5359,15 +5358,15 @@ msgstr "" msgid "Choose Click Emphasis" msgstr "Utiliser comme emphase de clic" -#: option_editor.cc:804 +#: option_editor.cc:803 msgid "Click audio file" msgstr "Fichier audio de clic" -#: option_editor.cc:810 +#: option_editor.cc:809 msgid "Click emphasis audiofile" msgstr "Fichier audio d'emphase de clic" -#: option_editor.cc:847 +#: option_editor.cc:846 msgid "" "The auditioner is a dedicated mixer strip used\n" "for listening to specific regions outside the context\n" @@ -5379,36 +5378,36 @@ msgstr "" "du mixage global. Il peut être connecté tout comme n'importe\n" "quelle autre tranche de mixage." -#: option_editor.cc:920 +#: option_editor.cc:919 msgid "Edit using" msgstr "Édition en utilisant" -#: option_editor.cc:927 option_editor.cc:954 +#: option_editor.cc:926 option_editor.cc:953 msgid "+ button" msgstr "touche +" -#: option_editor.cc:947 +#: option_editor.cc:946 msgid "Delete using" msgstr "Effacer en utilisant" -#: option_editor.cc:974 +#: option_editor.cc:973 msgid "Ignore snap using" msgstr "Ignorer clac en utilisant" -#: opts.cc:47 +#: opts.cc:46 msgid "Usage: " msgstr "Usage :" -#: opts.cc:48 +#: opts.cc:47 msgid " -v, --version Show version information\n" msgstr "" " -v, --version Montre les informations de version\n" -#: opts.cc:49 +#: opts.cc:48 msgid " -h, --help Print this message\n" msgstr " -h, --help Affiche ce message\n" -#: opts.cc:50 +#: opts.cc:49 msgid "" " -b, --bindings Print all possible keyboard binding " "names\n" @@ -5416,11 +5415,11 @@ msgstr "" " -b, --bindings Affiche tous raccourcis clavier " "possibles\n" -#: opts.cc:51 +#: opts.cc:50 msgid " -n, --show-splash Show splash screen\n" msgstr " -n, --show-splash Afficher l'écran de démarrage\n" -#: opts.cc:52 +#: opts.cc:51 msgid "" " -c, --name name Use a specific jack client name, default " "is ardour\n" @@ -5428,149 +5427,162 @@ msgstr "" " -c, --name nom Utiliser un nom de client jack " "spécifique, la valeur par défaut est ardour\n" -#: opts.cc:53 +#: opts.cc:52 msgid "" " -N, --new session-name Create a new session from the command " "line\n" msgstr " -N, --new nom-de-session Nom de la session à charger\n" -#: opts.cc:54 +#: opts.cc:53 msgid "" " -o, --use-hw-optimizations Try to use h/w specific optimizations\n" msgstr "" -#: opts.cc:56 +#: opts.cc:55 msgid " -V, --novst Do not use VST support\n" msgstr "" -#: opts.cc:58 +#: opts.cc:57 msgid " [session-name] Name of session to load\n" msgstr " [nom-de-session] Nom de la session à charger\n" -#: opts.cc:59 +#: opts.cc:58 msgid " -C, --curvetest filename Curve algorithm debugger\n" msgstr "" " -C, --curvetest nom-de-fichier Débogueur d'algorithme de courbe\n" -#: opts.cc:60 +#: opts.cc:59 #, fuzzy msgid " -g, --gtktheme Allow GTK to load a theme\n" msgstr " -h, --help Affiche ce message\n" -#: pan_automation_time_axis.cc:59 +#: pan_automation_time_axis.cc:60 msgid "You can't graphically edit panning of more than stream" msgstr "" -#: pan_automation_time_axis.cc:79 +#: pan_automation_time_axis.cc:80 #, fuzzy msgid "add pan automation event" msgstr "ajouter les évènements d'automatisation à " -#: panner2d.cc:588 panner_ui.cc:393 plugin_ui.cc:833 +#: panner2d.cc:589 panner_ui.cc:435 plugin_ui.cc:834 msgid "Bypass" msgstr "Bypass" -#: panner_ui.cc:57 panner_ui.cc:187 +#: panner_ui.cc:58 panner_ui.cc:225 #, fuzzy msgid "link" msgstr "entrée" +#: panner_ui.cc:69 +msgid "Pan automation mode" +msgstr "Mode d'automatisation de panoramique" + #: panner_ui.cc:70 +msgid "Pan automation type" +msgstr "Type d'automatisation de panoramique" + +#: panner_ui.cc:81 msgid "panning link control" msgstr "" -#: panner_ui.cc:72 +#: panner_ui.cc:83 msgid "panning link direction" msgstr "" -#: panner_ui.cc:197 +#: panner_ui.cc:235 msgid "L" msgstr "" -#: panner_ui.cc:296 +#: panner_ui.cc:335 +#, c-format +msgid "panner for channel %lu" +msgstr "" + +#: panner_ui.cc:337 #, c-format msgid "panner for channel %u" msgstr "" -#: panner_ui.cc:403 +#: panner_ui.cc:445 #, fuzzy msgid "Reset all" msgstr "Réinitialiser" -#: playlist_selector.cc:51 +#: playlist_selector.cc:52 #, fuzzy msgid "ardour: playlists" msgstr "ardour : greffons" -#: playlist_selector.cc:58 +#: playlist_selector.cc:59 msgid "Playlists grouped by track" msgstr "" -#: playlist_selector.cc:97 +#: playlist_selector.cc:98 #, fuzzy msgid "ardour: playlist for " msgstr "ardour : éditeur : " -#: playlist_selector.cc:113 +#: playlist_selector.cc:114 #, fuzzy msgid "Other tracks" msgstr "décaler la piste" -#: playlist_selector.cc:129 +#: playlist_selector.cc:130 msgid "unassigned" msgstr "" -#: plugin_selector.cc:42 +#: plugin_selector.cc:43 msgid "ardour: plugins" msgstr "ardour : greffons" -#: plugin_selector.cc:55 +#: plugin_selector.cc:56 #, fuzzy msgid "Available LADSPA Plugins" msgstr "Greffons LADSPA disponibles" -#: plugin_selector.cc:56 +#: plugin_selector.cc:57 msgid "Type" msgstr "Type" -#: plugin_selector.cc:57 plugin_selector.cc:80 +#: plugin_selector.cc:58 plugin_selector.cc:81 msgid "# Inputs" msgstr "# entrées" -#: plugin_selector.cc:58 plugin_selector.cc:81 +#: plugin_selector.cc:59 plugin_selector.cc:82 msgid "# Outputs" msgstr "# sorties" -#: plugin_selector.cc:67 +#: plugin_selector.cc:68 msgid "Plugins to be Connected to Insert" msgstr "" -#: plugin_selector.cc:79 +#: plugin_selector.cc:80 #, fuzzy msgid "Available plugins" msgstr "Greffons VST disponibles" -#: plugin_selector.cc:97 +#: plugin_selector.cc:98 msgid "Add a plugin to the effect list" msgstr "Ajouter un greffon à la liste d'effets" -#: plugin_selector.cc:99 +#: plugin_selector.cc:102 msgid "Remove a plugin from the effect list" msgstr "Retirer un greffon à la liste d'effets" -#: plugin_selector.cc:101 +#: plugin_selector.cc:104 msgid "Update available plugins" msgstr "Rafraîchir les greffons disponibles" -#: plugin_selector.cc:123 +#: plugin_selector.cc:126 msgid "LADSPA" msgstr "LADSPA" -#: plugin_selector.cc:126 +#: plugin_selector.cc:129 msgid "VST" msgstr "VST" -#: plugin_ui.cc:83 +#: plugin_ui.cc:84 msgid "" "unknown type of editor-supplying plugin (note: no VST support in this " "version of ardour)" @@ -5578,53 +5590,54 @@ msgstr "" "type de greffon éditeur inconnu (note : pas de support VST dans cette " "version d'ardour)" -#: plugin_ui.cc:138 +#: plugin_ui.cc:139 msgid "Presets" msgstr "" -#: plugin_ui.cc:229 +#: plugin_ui.cc:230 #, fuzzy msgid "Controls" msgstr "Sorties de contrôle" -#: plugin_ui.cc:266 +#: plugin_ui.cc:267 msgid "Plugin Editor: could not build control element for port %1" msgstr "" "Éditeur de greffon : impossible de construire l'élément de contrôle pour le " "port %1" -#: plugin_ui.cc:357 -msgid "automation control" +#: plugin_ui.cc:358 +#, fuzzy +msgid "Automation control" msgstr "contrôle d'automatisation" -#: plugin_ui.cc:853 +#: plugin_ui.cc:854 #, fuzzy msgid "Plugin preset %1 not found" msgstr "Pré-réglage de greffon %1 non trouvé" -#: plugin_ui.cc:863 +#: plugin_ui.cc:864 #, fuzzy msgid "Name of New Preset:" msgstr "Nom de la nouvelle connexion :" -#: redirect_automation_line.cc:53 +#: redirect_automation_line.cc:54 msgid "redirect automation created for non-plugin" msgstr "rediriger l'automatisation créée pour le non-greffon" -#: redirect_automation_time_axis.cc:93 +#: redirect_automation_time_axis.cc:94 msgid "add automation event to " msgstr "ajouter les évènements d'automatisation à " -#: redirect_box.cc:222 +#: redirect_box.cc:223 msgid "New send" msgstr "" -#: redirect_box.cc:223 +#: redirect_box.cc:224 #, fuzzy msgid "Show send controls" msgstr "Contrôle de la vitesse avec molette" -#: redirect_box.cc:377 +#: redirect_box.cc:383 msgid "" "You attempted to add a plugin (%1).\n" "The plugin has %2 inputs\n" @@ -5635,7 +5648,7 @@ msgid "" "part of the signal." msgstr "" -#: redirect_box.cc:389 +#: redirect_box.cc:395 msgid "" "You attempted to add a plugin (%1).\n" "The plugin has %2 inputs\n" @@ -5647,7 +5660,7 @@ msgid "" "support this type of configuration." msgstr "" -#: redirect_box.cc:402 +#: redirect_box.cc:408 msgid "" "You attempted to add a plugin (%1).\n" "\n" @@ -5660,34 +5673,34 @@ msgid "" "Ardour does not understand what to do in such situations.\n" msgstr "" -#: redirect_box.cc:493 +#: redirect_box.cc:495 msgid "Pre-fader inserts, sends & plugins:" msgstr "" -#: redirect_box.cc:496 +#: redirect_box.cc:498 msgid "Post-fader inserts, sends & plugins:" msgstr "" -#: redirect_box.cc:642 +#: redirect_box.cc:644 msgid "" "You cannot reorder this set of redirects\n" "in that way because the inputs and\n" "outputs do not work correctly." msgstr "" -#: redirect_box.cc:747 +#: redirect_box.cc:749 #, fuzzy msgid "rename redirect" msgstr "ardour : renommer la région" -#: redirect_box.cc:824 redirect_box.cc:872 +#: redirect_box.cc:826 redirect_box.cc:874 msgid "" "Copying the set of redirects on the clipboard failed,\n" "probably because the I/O configuration of the plugins\n" "could not match the configuration of this track." msgstr "" -#: redirect_box.cc:894 +#: redirect_box.cc:896 #, fuzzy msgid "" "Do you really want to remove all redirects from this track?\n" @@ -5696,7 +5709,7 @@ msgstr "" "Voulez-vous vraiment supprimer la piste \"%1\" ?\n" "(cela ne pourra pas être annulé)" -#: redirect_box.cc:897 +#: redirect_box.cc:899 #, fuzzy msgid "" "Do you really want to remove all redirects from this bus?\n" @@ -5705,241 +5718,253 @@ msgstr "" "Voulez-vous vraiment supprimer la piste \"%1\" ?\n" "(cela ne pourra pas être annulé)" -#: redirect_box.cc:902 +#: redirect_box.cc:904 #, fuzzy msgid "Yes, remove them all" msgstr "Oui, le supprimer." -#: redirect_box.cc:938 +#: redirect_box.cc:940 #, fuzzy msgid "ardour: %1" msgstr "ardour :" -#: redirect_box.cc:980 +#: redirect_box.cc:982 #, fuzzy msgid "ardour: %1: %2 (by %3)" msgstr "ardour :" #. new stuff -#: redirect_box.cc:1052 +#: redirect_box.cc:1054 msgid "New Plugin ..." msgstr "" -#: redirect_box.cc:1053 +#: redirect_box.cc:1055 #, fuzzy msgid "New Insert" msgstr "Nouvelle entrée" -#: redirect_box.cc:1054 +#: redirect_box.cc:1056 msgid "New Send ..." msgstr "" -#: redirect_box.cc:1066 +#: redirect_box.cc:1068 #, fuzzy msgid "Deselect All" msgstr "Tout sélectionner" -#: redirect_box.cc:1073 +#: redirect_box.cc:1075 #, fuzzy msgid "Activate all" msgstr "Activer" -#: redirect_box.cc:1074 +#: redirect_box.cc:1076 #, fuzzy msgid "Deactivate all" msgstr "Désactiver" -#: region_editor.cc:44 +#: region_editor.cc:45 msgid "NAME:" msgstr "NOM :" -#: region_editor.cc:45 +#: region_editor.cc:46 msgid "lock" msgstr "verrouiller" -#: region_editor.cc:47 +#: region_editor.cc:48 msgid "opaque" msgstr "opaque" -#: region_editor.cc:52 +#: region_editor.cc:49 region_editor.cc:192 region_editor.cc:226 +msgid "active" +msgstr "actif" + +#: region_editor.cc:50 +msgid "visible" +msgstr "visible" + +#: region_editor.cc:53 msgid "Layer" msgstr "Couche" -#: region_editor.cc:60 +#: region_editor.cc:54 +msgid "play" +msgstr "jouer" + +#: region_editor.cc:61 msgid "ENVELOPE" msgstr "ENVELOPPE" -#: region_editor.cc:106 +#: region_editor.cc:107 msgid "mute this region" msgstr "Assourdir cette région" -#: region_editor.cc:107 +#: region_editor.cc:108 msgid "regions underneath this one cannot be heard" msgstr "les régions en dessous de celle-ci ne peuvent être entendues" -#: region_editor.cc:108 +#: region_editor.cc:109 msgid "prevent any changes to this region" msgstr "empêche toute modification de cette région" -#: region_editor.cc:109 +#: region_editor.cc:110 msgid "use the gain envelope during playback" msgstr "utiliser l'enveloppe de gain pendant la lecture" -#: region_editor.cc:110 +#: region_editor.cc:111 msgid "show the gain envelope" msgstr "montrer l'enveloppe de gain" -#: region_editor.cc:111 +#: region_editor.cc:112 msgid "use fade in curve during playback" msgstr "utiliser une courbe de fondu d'ouverture durant la lecture" -#: region_editor.cc:112 +#: region_editor.cc:113 msgid "use fade out curve during playback" msgstr "utiliser une courbe de fondu de fermeture durant la lecture" -#: region_editor.cc:113 +#: region_editor.cc:114 msgid "audition this region" msgstr "écouter cette région" -#: region_editor.cc:146 +#: region_editor.cc:147 msgid "START:" msgstr "DÉBUT :" -#: region_editor.cc:148 +#: region_editor.cc:149 msgid "END:" msgstr "FIN :" -#: region_editor.cc:150 +#: region_editor.cc:151 msgid "LENGTH:" msgstr "LONGUEUR :" -#: region_editor.cc:190 +#: region_editor.cc:191 msgid "FADE IN" msgstr "FONDU D'OUVERTURE" -#: region_editor.cc:192 region_editor.cc:226 +#: region_editor.cc:193 region_editor.cc:227 msgid "msecs" msgstr "ms" -#: region_editor.cc:224 +#: region_editor.cc:225 msgid "FADE OUT" msgstr "FONDU DE FERMETURE" -#: region_editor.cc:264 +#: region_editor.cc:265 msgid "ardour: region " msgstr "ardour : région " -#: region_editor.cc:401 +#: region_editor.cc:402 msgid "fade in edit" msgstr "édition de fondu d'ouverture" -#: region_editor.cc:413 +#: region_editor.cc:414 msgid "fade out edit" msgstr "édition de fondu de fermeture" -#: regionview.cc:1140 +#: regionview.cc:1146 #, fuzzy msgid "add gain control point" msgstr "Enlever le point de contrôle" -#: route_params_ui.cc:88 +#: route_params_ui.cc:89 msgid "Tracks/Buses" msgstr "Pistes/Bus" -#: route_params_ui.cc:108 +#: route_params_ui.cc:109 msgid "Pre-fader Redirects" msgstr "Redirections pré-fader" -#: route_params_ui.cc:109 +#: route_params_ui.cc:110 msgid "Post-fader Redirects" msgstr "Redirections post-fader" -#: route_params_ui.cc:141 +#: route_params_ui.cc:144 msgid "ardour: track/bus inspector" msgstr "ardour : inspecteur de piste/bus" -#: route_params_ui.cc:142 +#: route_params_ui.cc:145 msgid "ardour_route_parameters" msgstr "ardour_paramètres_de_route" -#: route_params_ui.cc:199 +#: route_params_ui.cc:202 msgid "route display list item for renamed route not found!" msgstr "" -#: route_params_ui.cc:451 +#: route_params_ui.cc:453 msgid "NO TRACK" msgstr "PAS DE PISTE" -#: route_params_ui.cc:693 +#: route_params_ui.cc:695 msgid "ardour: track/bus inspector: " msgstr "ardour : inspecteur de piste/bus" -#: route_params_ui.cc:697 +#: route_params_ui.cc:699 msgid "No Route Selected" msgstr "Aucune route sélectionnée" -#: route_params_ui.cc:698 +#: route_params_ui.cc:700 msgid "ardour: track/bus/inspector: no route selected" msgstr "ardour : inspecteur de piste/bus : aucune route sélectionnée" #. ctrl-shift-click applies change to all routes -#: route_ui.cc:133 +#: route_ui.cc:134 msgid "mute change" msgstr "modification de la sourdine" #. ctrl-shift-click applies change to all routes #. ctrl-alt-click: exclusively solo this track, not a toggle */ -#: route_ui.cc:208 route_ui.cc:218 +#: route_ui.cc:209 route_ui.cc:219 msgid "solo change" msgstr "modification du solo" -#: route_ui.cc:281 +#: route_ui.cc:282 #, fuzzy msgid "rec-enable change" msgstr "modification de rec-enable" -#: route_ui.cc:472 +#: route_ui.cc:479 #, fuzzy msgid "Solo-safe" msgstr "Solo-safe" -#: route_ui.cc:480 route_ui.cc:523 +#: route_ui.cc:487 route_ui.cc:530 msgid "MIDI Bind" msgstr "Assignement MIDI" -#: route_ui.cc:494 +#: route_ui.cc:501 msgid "Pre Fader" msgstr "Pré fader" -#: route_ui.cc:501 +#: route_ui.cc:508 msgid "Post Fader" msgstr "Post fader" -#: route_ui.cc:508 +#: route_ui.cc:515 msgid "Control Outs" msgstr "Sorties de contrôle" -#: route_ui.cc:515 +#: route_ui.cc:522 msgid "Main Outs" msgstr "Sorties principales" -#: route_ui.cc:552 +#: route_ui.cc:559 msgid "mix group solo change" msgstr "" -#: route_ui.cc:586 +#: route_ui.cc:593 msgid "mix group mute change" msgstr "" -#: route_ui.cc:602 +#: route_ui.cc:609 msgid "mix group rec-enable change" msgstr "" -#: route_ui.cc:619 visual_time_axis.cc:236 +#: route_ui.cc:626 visual_time_axis.cc:237 msgid "ardour: color selection" msgstr "ardour : sélection de couleur" -#: route_ui.cc:695 +#: route_ui.cc:702 #, fuzzy msgid "" "Do you really want to remove track \"%1\" ?\n" @@ -5951,7 +5976,7 @@ msgstr "" "Vous perdrez peut-être aussi la liste de lecture utilisée par cette piste" "(cela ne pourra pas être annulé)" -#: route_ui.cc:697 +#: route_ui.cc:704 msgid "" "Do you really want to remove bus \"%1\" ?\n" "(cannot be undone)" @@ -5959,11 +5984,11 @@ msgstr "" "Voulez-vous vraiment supprimer le bus \"%1\" ?\n" "(cela ne pourra pas être annulé)" -#: route_ui.cc:701 visual_time_axis.cc:278 +#: route_ui.cc:708 visual_time_axis.cc:279 msgid "Yes, remove it." msgstr "Oui, le supprimer." -#: route_ui.cc:730 +#: route_ui.cc:737 #, fuzzy msgid "New Name: " msgstr "nouveau nom :" @@ -6021,148 +6046,149 @@ msgstr "Impossible d'accéder au fichier son : " msgid "Name for Field" msgstr "Nom de la région :" -#: sfdb_ui.cc:333 +#: sfdb_ui.cc:335 msgid "Split Channels" msgstr "Séparer les voies" -#: sfdb_ui.cc:340 +#: sfdb_ui.cc:342 msgid "Create a region for each channel" msgstr "" -#: sfdb_ui.cc:342 +#: sfdb_ui.cc:344 msgid "Embed" msgstr "" -#: sfdb_ui.cc:344 +#: sfdb_ui.cc:346 #, fuzzy msgid "Link to an external file" msgstr "Insérer un fichier son externe" -#: sfdb_ui.cc:346 +#: sfdb_ui.cc:348 msgid "Import" msgstr "Importer" -#: sfdb_ui.cc:348 +#: sfdb_ui.cc:350 msgid "Copy a file to the session folder" msgstr "" -#: sfdb_ui.cc:412 +#: sfdb_ui.cc:414 #, fuzzy msgid "programming error: %1" msgstr "erreur de programmation : " -#: tempo_dialog.cc:17 tempo_dialog.cc:34 +#: tempo_dialog.cc:18 tempo_dialog.cc:35 msgid "Beats per minute" msgstr "Temps par minute" -#: tempo_dialog.cc:20 tempo_dialog.cc:37 tempo_dialog.cc:153 -#: tempo_dialog.cc:171 +#: tempo_dialog.cc:21 tempo_dialog.cc:38 tempo_dialog.cc:203 +#: tempo_dialog.cc:221 msgid "Bar" msgstr "Mesure" -#: tempo_dialog.cc:21 tempo_dialog.cc:38 tempo_dialog.cc:154 -#: tempo_dialog.cc:172 +#: tempo_dialog.cc:22 tempo_dialog.cc:39 tempo_dialog.cc:204 +#: tempo_dialog.cc:222 msgid "Beat" msgstr "Temps" -#: tempo_dialog.cc:23 tempo_dialog.cc:40 tempo_dialog.cc:155 -#: tempo_dialog.cc:173 +#: tempo_dialog.cc:24 tempo_dialog.cc:41 tempo_dialog.cc:205 +#: tempo_dialog.cc:223 msgid "Location" msgstr "Emplacement" -#: tempo_dialog.cc:149 tempo_dialog.cc:167 +#: tempo_dialog.cc:199 tempo_dialog.cc:217 msgid "Meter denominator" msgstr "Dénominateur du vu-mètre" -#: tempo_dialog.cc:150 tempo_dialog.cc:168 +#: tempo_dialog.cc:200 tempo_dialog.cc:218 msgid "Beats per bar" msgstr "Temps par mesure" -#: tempo_dialog.cc:186 tempo_dialog.cc:197 +#: tempo_dialog.cc:236 tempo_dialog.cc:247 msgid "whole (1)" msgstr "noire (1)" -#: tempo_dialog.cc:187 tempo_dialog.cc:199 +#: tempo_dialog.cc:237 tempo_dialog.cc:249 msgid "second (2)" msgstr "croche (2)" -#: tempo_dialog.cc:188 tempo_dialog.cc:201 +#: tempo_dialog.cc:238 tempo_dialog.cc:251 msgid "third (3)" msgstr "triolet (3)" -#: tempo_dialog.cc:189 tempo_dialog.cc:203 tempo_dialog.cc:211 +#: tempo_dialog.cc:239 tempo_dialog.cc:253 tempo_dialog.cc:261 msgid "quarter (4)" msgstr "double croche (4)" -#: tempo_dialog.cc:190 tempo_dialog.cc:205 +#: tempo_dialog.cc:240 tempo_dialog.cc:255 msgid "eighth (8)" msgstr "huitième (8)" -#: tempo_dialog.cc:191 tempo_dialog.cc:207 +#: tempo_dialog.cc:241 tempo_dialog.cc:257 msgid "sixteenth (16)" msgstr "seizième (16)" -#: tempo_dialog.cc:192 tempo_dialog.cc:209 +#: tempo_dialog.cc:242 tempo_dialog.cc:259 msgid "thirty-second (32)" msgstr "trente-deuxième (32)" -#: tempo_dialog.cc:321 +#: tempo_dialog.cc:420 msgid "garbaged note type entry (%1)" msgstr "entrée type de note endommagée (%1)" -#: tempo_dialog.cc:331 +#: tempo_dialog.cc:430 msgid "incomprehensible note type entry (%1)" msgstr "entrée type de note incompréhensible (%1)" -#: time_axis_view.cc:111 +#: time_axis_view.cc:112 msgid "gTortnam" msgstr "gTortnam" -#: time_axis_view.cc:548 +#: time_axis_view.cc:549 msgid "Largest" msgstr "Énorme" -#: time_axis_view.cc:549 +#: time_axis_view.cc:550 msgid "Large" msgstr "Grand" -#: time_axis_view.cc:550 +#: time_axis_view.cc:551 msgid "Larger" msgstr "Plus grand" -#: time_axis_view.cc:552 +#: time_axis_view.cc:553 msgid "Smaller" msgstr "Plus petit" -#: time_axis_view.cc:553 +#: time_axis_view.cc:554 msgid "Small" msgstr "Petit" -#: time_axis_view.cc:869 +#: time_axis_view.cc:870 msgid "unknown track height name \"%1\" in XML GUI information" msgstr "nom de hauteur de piste inconnu \"%1\" dans les données XML de l'IHM" -#: time_axis_view_item.cc:71 +#. first constructed item sets up font info +#: time_axis_view_item.cc:79 msgid "TimeAxisViewItemName" msgstr "" -#: time_axis_view_item.cc:271 +#: time_axis_view_item.cc:298 msgid "new duration %1 frames is out of bounds for %2" msgstr "la nouvelle durée %1 trames est hors limite pour %2" -#: time_selection.cc:40 +#: time_selection.cc:41 msgid "programming error: request for non-existent audio range (%1)!" msgstr "programming error: request for non-existent audio range (%1)!" -#: utils.cc:106 utils.cc:149 +#: utils.cc:107 utils.cc:150 msgid "bad XPM header %1" msgstr "mauvais entête XPM %1" -#: utils.cc:331 +#: utils.cc:332 msgid "missing RGBA style for \"%1\"" msgstr "" -#: visual_time_axis.cc:275 +#: visual_time_axis.cc:276 msgid "" "Do you really want to remove track \"%1\" ?\n" "(cannot be undone)" @@ -6170,14 +6196,102 @@ msgstr "" "Voulez-vous vraiment supprimer la piste \"%1\" ?\n" "(cela ne pourra pas être annulé)" -#: visual_time_axis.cc:324 +#: visual_time_axis.cc:325 msgid "new name: " msgstr "nouveau nom :" -#: visual_time_axis.cc:335 +#: visual_time_axis.cc:336 msgid "A track already exists with that name" msgstr "Une piste portant le même nom existe déjà" +#~ msgid "" +#~ "You cannot record-enable\n" +#~ "track %1\n" +#~ "because it has no input connections.\n" +#~ "You would be wasting space recording silence." +#~ msgstr "" +#~ "Vous ne pouvez activer\n" +#~ "l'enregistrement de la piste %1\n" +#~ "car elle n'a pas de connections en entrée.\n" +#~ "Vous gacheriez de l'espace en enregistrant du silence." + +#, fuzzy +#~ msgid "set selected trackview" +#~ msgstr "définir la vue de piste sélectionnée" + +#, fuzzy +#~ msgid "set selected control point" +#~ msgstr "Enlever le point de contrôle" + +#, fuzzy +#~ msgid "set selected regionview" +#~ msgstr "définir la vue de région sélectionnée" + +#~ msgid "Start a new session\n" +#~ msgstr "Commencer une nouvelle session\n" + +#~ msgid "via Session menu" +#~ msgstr "via le menu Session" + +#~ msgid "FirstActionMessage" +#~ msgstr "FirstActionCursor" + +#, fuzzy +#~ msgid "Advanced" +#~ msgstr "Avancé..." + +#, fuzzy +#~ msgid "Select a File" +#~ msgstr "Tout sélectionner" + +#, fuzzy +#~ msgid "Track/Bus connection options" +#~ msgstr "Inspecteur de pistes/bus" + +#~ msgid "RECORD" +#~ msgstr "ENREGISTRER" + +#~ msgid "INPUT" +#~ msgstr "ENTRÉE" + +#~ msgid "OUTPUT" +#~ msgstr "SORTIE" + +#~ msgid "Gain automation mode" +#~ msgstr "Mode d'automatisation du gain" + +#~ msgid "Gain automation type" +#~ msgstr "dessiner l'automatisation du gain" + +#~ msgid "trim" +#~ msgstr "élaguer" + +#~ msgid "gain automation mode" +#~ msgstr "mode d'automatisation du gain" + +#~ msgid "gain automation state" +#~ msgstr "état de l'automatisation du gain" + +#~ msgid "pan automation state" +#~ msgstr "état de l'automatisation de panoramique" + +#~ msgid "REC" +#~ msgstr "ENR." + +#~ msgid "OUT" +#~ msgstr "SORTIE" + +#, fuzzy +#~ msgid "aplay" +#~ msgstr "aplay" + +#, fuzzy +#~ msgid "awrite" +#~ msgstr "awrite" + +#~ msgid "no group" +#~ msgstr "aucun groupe" + #, fuzzy #~ msgid "normal" #~ msgstr "Normal" @@ -6528,9 +6642,6 @@ msgstr "Une piste portant le même nom existe déjà" #~ msgid "AND" #~ msgstr "ET" -#~ msgid "OR" -#~ msgstr "OU" - #~ msgid "ardour: locate soundfiles" #~ msgstr "ardour : trouver fichiers audio" @@ -6549,9 +6660,6 @@ msgstr "Une piste portant le même nom existe déjà" #~ msgid "***" #~ msgstr "***" -#~ msgid "Mix Groups" -#~ msgstr "Groupes de mixage" - #~ msgid "Hide All AudioTrack MixerStrips" #~ msgstr "Cacher toutes les tranches de mixage de piste audio" @@ -6564,9 +6672,6 @@ msgstr "Une piste portant le même nom existe déjà" #~ msgid "Name for new mix group" #~ msgstr "Nom pour le nouveau groupe de mixage" -#~ msgid "Session name:" -#~ msgstr "Nom de la session :" - #~ msgid "Create" #~ msgstr "Créer" @@ -6604,18 +6709,12 @@ msgstr "Une piste portant le même nom existe déjà" #~ "Si vous voulez utiliser une autre fréquence d'échantillonage\n" #~ "veuillez arrêter puis relancer JACK" -#~ msgid "Session template" -#~ msgstr "Modèle de session" - #~ msgid "blank" #~ msgstr "vide" #~ msgid "No template - create tracks/busses manually" #~ msgstr "Pas de modèle -- créez les pistes/bus manuellement" -#~ msgid "No template" -#~ msgstr "Pas de modèle" - #~ msgid "Slave to MTC" #~ msgstr "Esclave du MTC" @@ -6661,9 +6760,6 @@ msgstr "Une piste portant le même nom existe déjà" #~ msgid "Native Format" #~ msgstr "Format natif" -#~ msgid "Use as click" -#~ msgstr "Utiliser comme clic" - #~ msgid "--unknown--" #~ msgstr "--inconnu--" diff --git a/gtk2_ardour/po/it_IT.po b/gtk2_ardour/po/it_IT.po index 44b2bd86a0..f283f846da 100644 --- a/gtk2_ardour/po/it_IT.po +++ b/gtk2_ardour/po/it_IT.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: ardour 0.354.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-04-25 17:46-0400\n" +"POT-Creation-Date: 2006-06-21 18:09-0400\n" "PO-Revision-Date: 2003-05-20 13:03-0500\n" "Last-Translator: Filippo Pappalardo \n" "Language-Team: Italian\n" @@ -15,201 +15,201 @@ msgstr "" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" -#: about.cc:119 +#: about.cc:120 msgid "Paul Davis" msgstr "" -#: about.cc:120 +#: about.cc:121 #, fuzzy msgid "Jesse Chappell" msgstr "azzera" -#: about.cc:121 +#: about.cc:122 msgid "Taybin Rutkin" msgstr "" -#: about.cc:122 +#: about.cc:123 msgid "Marcus Andersson" msgstr "" -#: about.cc:123 +#: about.cc:124 msgid "Jeremy Hall" msgstr "" -#: about.cc:124 +#: about.cc:125 msgid "Steve Harris" msgstr "" -#: about.cc:125 +#: about.cc:126 msgid "Tim Mayberry" msgstr "" -#: about.cc:126 +#: about.cc:127 msgid "Mark Stewart" msgstr "" -#: about.cc:127 +#: about.cc:128 msgid "Sam Chessman" msgstr "" -#: about.cc:128 +#: about.cc:129 msgid "Jack O'Quin" msgstr "" -#: about.cc:129 +#: about.cc:130 msgid "Matt Krai" msgstr "" -#: about.cc:130 +#: about.cc:131 msgid "Ben Bell" msgstr "" -#: about.cc:131 +#: about.cc:132 msgid "Gerard van Dongen" msgstr "" -#: about.cc:132 +#: about.cc:133 msgid "Thomas Charbonnel" msgstr "" -#: about.cc:133 +#: about.cc:134 msgid "Nick Mainsbridge" msgstr "" -#: about.cc:134 +#: about.cc:135 msgid "Colin Law" msgstr "" -#: about.cc:135 +#: about.cc:136 msgid "Sampo Savolainen" msgstr "" -#: about.cc:136 +#: about.cc:137 msgid "Joshua Leach" msgstr "" -#: about.cc:137 +#: about.cc:138 msgid "Rob Holland" msgstr "" -#: about.cc:138 +#: about.cc:139 msgid "Per Sigmond" msgstr "" -#: about.cc:139 +#: about.cc:140 msgid "Doug Mclain" msgstr "" -#: about.cc:140 +#: about.cc:141 msgid "Petter Sundlöf" msgstr "" -#: about.cc:145 +#: about.cc:146 msgid "" "French:\n" "\tAlain Fréhel \n" msgstr "" -#: about.cc:146 +#: about.cc:147 msgid "" "German:\n" "\tKarsten Petersen \n" msgstr "" -#: about.cc:147 +#: about.cc:148 msgid "" "Italian:\n" "\tFilippo Pappalardo \n" msgstr "" -#: about.cc:148 +#: about.cc:149 msgid "" "Portuguese:\n" "\tRui Nuno Capela \n" msgstr "" -#: about.cc:149 +#: about.cc:150 msgid "" "Brazilian Portuguese:\n" "\tAlexander da Franca Fernandes \n" "\tChris Ross \n" msgstr "" -#: about.cc:151 +#: about.cc:152 msgid "" "Spanish:\n" "\t Alex Krohn \n" msgstr "" -#: about.cc:152 +#: about.cc:153 msgid "" "Russian:\n" "\t Igor Blinov \n" msgstr "" -#: about.cc:180 +#: about.cc:181 msgid "Copyright (C) 1999-2005 Paul Davis\n" msgstr "" -#: about.cc:181 +#: about.cc:182 msgid "" "Ardour comes with ABSOLUTELY NO WARRANTY\n" "This is free software, and you are welcome to redistribute it\n" "under certain conditions; see the file COPYING for details.\n" msgstr "" -#: about.cc:187 +#: about.cc:188 msgid "" "%1\n" "(built with ardour/gtk %2.%3.%4 libardour: %5.%6.%7)" msgstr "" -#: actions.cc:260 +#: actions.cc:261 #, fuzzy msgid "programmer error: %1 %2" msgstr "errore di programmazione: " -#: add_route_dialog.cc:61 +#: add_route_dialog.cc:62 msgid "ardour: add track/bus" msgstr "ardour: aggiungi traccia/bus" #. path = "1" -#: add_route_dialog.cc:62 editor_route_list.cc:72 +#: add_route_dialog.cc:63 editor_route_list.cc:73 msgid "Tracks" msgstr "Tracce" #. path = "0" -#: add_route_dialog.cc:63 editor_route_list.cc:69 +#: add_route_dialog.cc:64 editor_route_list.cc:70 msgid "Busses" msgstr "Bus" -#: add_route_dialog.cc:95 plugin_ui.cc:832 +#: add_route_dialog.cc:96 plugin_ui.cc:833 msgid "Add" msgstr "Aggiungi" -#: add_route_dialog.cc:113 +#: add_route_dialog.cc:114 msgid "Name (template)" msgstr "Nome (modello)" -#: add_route_dialog.cc:119 +#: add_route_dialog.cc:120 #, fuzzy msgid "Channel Configuration" msgstr "Annullare l'importazione" -#: add_route_dialog.cc:176 editor.cc:131 editor.cc:3660 time_axis_view.cc:551 +#: add_route_dialog.cc:177 editor.cc:134 editor.cc:3688 time_axis_view.cc:552 msgid "Normal" msgstr "Normale" -#: add_route_dialog.cc:178 +#: add_route_dialog.cc:179 #, fuzzy msgid "Tape" msgstr "Inizio:" -#: add_route_dialog.cc:195 +#: add_route_dialog.cc:196 msgid "Mono" msgstr "" -#: add_route_dialog.cc:197 +#: add_route_dialog.cc:198 msgid "Stereo" msgstr "" @@ -280,27 +280,11 @@ msgstr "" msgid "SOLO" msgstr "" -#: ardour_ui.cc:207 -msgid "" -"You cannot record-enable\n" -"track %1\n" -"because it has no input connections.\n" -"You would be wasting space recording silence." -msgstr "" - -#: ardour_ui.cc:236 -msgid "no vertical meter strip image found" -msgstr "" - -#: ardour_ui.cc:243 -msgid "no horizontal meter strip image found" -msgstr "" - -#: ardour_ui.cc:410 +#: ardour_ui.cc:375 msgid "quit" msgstr "Esci" -#: ardour_ui.cc:419 +#: ardour_ui.cc:384 msgid "" "Ardour was unable to save your session.\n" "\n" @@ -309,33 +293,33 @@ msgid "" "\"Just quit\" option." msgstr "" -#: ardour_ui.cc:438 +#: ardour_ui.cc:403 msgid "ardour: save session?" msgstr "ardour: salvare la sessione?" -#: ardour_ui.cc:445 +#: ardour_ui.cc:410 msgid "Don't %1" msgstr "Non uscire" -#: ardour_ui.cc:447 +#: ardour_ui.cc:412 msgid "Just %1" msgstr "%1 e basta" -#: ardour_ui.cc:449 +#: ardour_ui.cc:414 msgid "Save and %1" msgstr "Salva ed esci" -#: ardour_ui.cc:461 +#: ardour_ui.cc:426 #, fuzzy msgid "session" msgstr "Sessione" -#: ardour_ui.cc:463 +#: ardour_ui.cc:428 #, fuzzy msgid "snapshot" msgstr "Istantanea" -#: ardour_ui.cc:465 +#: ardour_ui.cc:430 #, fuzzy msgid "" "The %1\"%2\"\n" @@ -354,81 +338,81 @@ msgstr "" "\n" "Cosa vuoi fare?" -#: ardour_ui.cc:479 +#: ardour_ui.cc:444 msgid "Prompter" msgstr "" -#: ardour_ui.cc:538 +#: ardour_ui.cc:503 #, fuzzy, c-format msgid "disconnected" msgstr "Disconnetti" -#: ardour_ui.cc:545 +#: ardour_ui.cc:510 #, c-format msgid "SR: %.1f kHz / %4.1f msecs" msgstr "" -#: ardour_ui.cc:549 +#: ardour_ui.cc:514 #, c-format msgid "SR: %u kHz / %4.1f msecs" msgstr "" -#: ardour_ui.cc:562 +#: ardour_ui.cc:527 #, c-format msgid "DSP Load: %.1f%%" msgstr "Carico DSP: %.1f%%" -#: ardour_ui.cc:572 +#: ardour_ui.cc:537 #, c-format msgid "Buffers p:%%% c:%%%" msgstr "" -#: ardour_ui.cc:599 +#: ardour_ui.cc:564 msgid "space: 24hrs+" msgstr "Spazio: 24hrs+" -#: ardour_ui.cc:629 +#: ardour_ui.cc:594 #, c-format msgid "space: %02dh:%02dm:%02ds" msgstr "Spazio: %02dh:%02dm:%02ds" -#: ardour_ui.cc:668 +#: ardour_ui.cc:633 msgid "programming error: impossible control method" msgstr "errore di programmazione: metodo di controllo impossibile" -#: ardour_ui.cc:776 new_session_dialog.cc:89 +#: ardour_ui.cc:741 new_session_dialog.cc:294 #, fuzzy msgid "Recent Sessions" msgstr "apri sessione" #. ardour sessions are folders -#: ardour_ui.cc:867 +#: ardour_ui.cc:834 msgid "open session" msgstr "apri sessione" -#: ardour_ui.cc:873 +#: ardour_ui.cc:840 #, fuzzy msgid "Ardour sessions" msgstr "ardour_nuova_sessione" -#: ardour_ui.cc:906 +#: ardour_ui.cc:873 msgid "Patience is a virtue.\n" msgstr "La pazienza è una virtù.\n" -#: ardour_ui.cc:915 +#: ardour_ui.cc:882 msgid "You cannot add a track without a session already loaded." msgstr "" "Non si può aggiungere una traccia senza prima aver caricato una sessione." -#: ardour_ui.cc:922 +#: ardour_ui.cc:889 msgid "could not create new audio track" msgstr "Impossibile creare una nuova traccia audio" -#: ardour_ui.cc:926 +#: ardour_ui.cc:893 msgid "could not create new audio bus" msgstr "Impossibile creare un nuovo bus audio" -#: ardour_ui.cc:945 +#: ardour_ui.cc:912 msgid "" "There are insufficient JACK ports available\n" "to create a new track or bus.\n" @@ -436,14 +420,14 @@ msgid "" "restart JACK with more ports." msgstr "" -#: ardour_ui.cc:1069 +#: ardour_ui.cc:1036 msgid "" "Please create 1 or more track\n" "before trying to record.\n" "Check the Session menu." msgstr "" -#: ardour_ui.cc:1298 +#: ardour_ui.cc:1265 #, fuzzy msgid "" "JACK has either been shutdown or it\n" @@ -456,57 +440,55 @@ msgstr "" "E' consigliato salvare la sessione e riavviare\n" "sia JACK che Ardour." -#: ardour_ui.cc:1315 +#: ardour_ui.cc:1282 msgid "Unable to create all required ports" msgstr "" -#: ardour_ui.cc:1323 +#: ardour_ui.cc:1290 #, fuzzy msgid "Unable to start the session running" msgstr "Vai all'inizio della sessione" -#: ardour_ui.cc:1459 +#: ardour_ui.cc:1426 msgid "No Stream" msgstr "Nessun flusso" -#: ardour_ui.cc:1486 ardour_ui.cc:1505 +#: ardour_ui.cc:1453 ardour_ui.cc:1472 msgid "none" msgstr "Nessuno" -#: ardour_ui.cc:1495 ardour_ui.cc:1514 automation_time_axis.cc:183 -#: automation_time_axis.cc:212 automation_time_axis.cc:459 mixer_strip.cc:174 -#: mixer_strip.cc:186 mixer_strip.cc:881 plugin_ui.cc:391 plugin_ui.cc:634 +#: ardour_ui.cc:1462 ardour_ui.cc:1481 msgid "off" msgstr "Off" -#: ardour_ui.cc:1538 +#: ardour_ui.cc:1505 #, fuzzy msgid "Name of New Snapshot" msgstr "Nome dell' istantanea" -#: ardour_ui.cc:1684 +#: ardour_ui.cc:1651 msgid "Name for mix template:" msgstr "Nome per il modello di mixaggio" -#: ardour_ui.cc:1685 +#: ardour_ui.cc:1652 msgid "-template" msgstr "-modello" -#: ardour_ui.cc:1836 +#: ardour_ui.cc:1809 msgid "" "You do not have write access to this session.\n" "This prevents the session from being loaded." msgstr "" -#: ardour_ui.cc:1849 ardour_ui.cc:1904 +#: ardour_ui.cc:1822 ardour_ui.cc:1877 msgid "Session \"%1 (snapshot %2)\" did not load successfully" msgstr "La sessione \"%1 (istantanea %2)\" non è stata caricata correttamente" -#: ardour_ui.cc:1960 +#: ardour_ui.cc:1933 msgid "No audio files were ready for cleanup" msgstr "" -#: ardour_ui.cc:1964 +#: ardour_ui.cc:1937 msgid "" "If this seems suprising, \n" "check for any existing snapshots.\n" @@ -514,23 +496,23 @@ msgid "" "require some unused files to continue to exist." msgstr "" -#: ardour_ui.cc:1973 +#: ardour_ui.cc:1946 msgid "ardour: cleanup" msgstr "ardour: pulisci" -#: ardour_ui.cc:2009 ardour_ui.cc:2015 +#: ardour_ui.cc:1982 ardour_ui.cc:1988 msgid "files were" msgstr "" -#: ardour_ui.cc:2011 ardour_ui.cc:2017 +#: ardour_ui.cc:1984 ardour_ui.cc:1990 msgid "file was" msgstr "" -#: ardour_ui.cc:2058 +#: ardour_ui.cc:2031 msgid "Are you sure you want to cleanup?" msgstr "" -#: ardour_ui.cc:2063 +#: ardour_ui.cc:2036 msgid "" "Cleanup is a destructive operation.\n" "ALL undo/redo information will be lost if you cleanup.\n" @@ -538,26 +520,26 @@ msgid "" "location." msgstr "" -#: ardour_ui.cc:2069 +#: ardour_ui.cc:2042 #, fuzzy msgid "Clean Up" msgstr "Pulisci" -#: ardour_ui.cc:2072 +#: ardour_ui.cc:2045 #, fuzzy msgid "CleanupDialog" msgstr "Pulisci" -#: ardour_ui.cc:2073 +#: ardour_ui.cc:2046 #, fuzzy msgid "ardour_cleanup" msgstr "ardour: pulisci" -#: ardour_ui.cc:2092 +#: ardour_ui.cc:2065 msgid "cleaned files" msgstr "files ripuliti" -#: ardour_ui.cc:2093 +#: ardour_ui.cc:2066 #, fuzzy msgid "" "The following %1 %2 not in use and \n" @@ -572,12 +554,12 @@ msgstr "" "La prossima volta che il cestino verr svuotato\n" "Saranno liberati %2 megabytes di spazio su disco" -#: ardour_ui.cc:2118 +#: ardour_ui.cc:2091 #, fuzzy msgid "deleted file" msgstr "files eliminati" -#: ardour_ui.cc:2119 +#: ardour_ui.cc:2092 #, fuzzy msgid "" "The following %1 %2 deleted from\n" @@ -587,11 +569,11 @@ msgstr "" "I seguenti %1 files sono stati eliminati, rilasciati %2 megabytes di spazio " "disco" -#: ardour_ui.cc:2242 +#: ardour_ui.cc:2215 msgid "Recording was stopped because your system could not keep up." msgstr "Registazione fermata perche' il sistema non ha retto" -#: ardour_ui.cc:2265 +#: ardour_ui.cc:2238 msgid "" "The disk system on your computer\n" "was not able to keep up with Ardour.\n" @@ -600,7 +582,7 @@ msgid "" "quickly enough to keep up with recording.\n" msgstr "" -#: ardour_ui.cc:2284 +#: ardour_ui.cc:2257 msgid "" "The disk system on your computer\n" "was not able to keep up with Ardour.\n" @@ -609,7 +591,7 @@ msgid "" "quickly enough to keep up with playback.\n" msgstr "" -#: ardour_ui.cc:2310 +#: ardour_ui.cc:2283 msgid "" "This session appears to have been in\n" "middle of recording when ardour or\n" @@ -620,361 +602,361 @@ msgid "" "what you would like to do.\n" msgstr "" -#: ardour_ui.cc:2320 +#: ardour_ui.cc:2293 msgid "Recover from crash" msgstr "" -#: ardour_ui.cc:2321 +#: ardour_ui.cc:2294 msgid "Ignore crash data" msgstr "" -#: ardour_ui.cc:2339 +#: ardour_ui.cc:2312 msgid "Could not disconnect from JACK" msgstr "" -#: ardour_ui.cc:2352 +#: ardour_ui.cc:2325 msgid "Could not reconnect to JACK" msgstr "" -#: ardour_ui2.cc:59 +#: ardour_ui2.cc:60 msgid "UI: cannot setup editor" msgstr "IU: impossibile avviare l'editor" -#: ardour_ui2.cc:64 +#: ardour_ui2.cc:65 msgid "UI: cannot setup mixer" msgstr "IU: impossibile avviare il mixer" -#: ardour_ui2.cc:90 +#: ardour_ui2.cc:91 msgid "MMC + Local" msgstr "" -#: ardour_ui2.cc:91 +#: ardour_ui2.cc:92 msgid "MMC" msgstr "" -#: ardour_ui2.cc:92 +#: ardour_ui2.cc:93 msgid "Local" msgstr "" -#: ardour_ui2.cc:109 +#: ardour_ui2.cc:110 msgid "MMC ID" msgstr "" -#: ardour_ui2.cc:290 +#: ardour_ui2.cc:291 msgid "Play from playhead" msgstr "Suona dal cursore" -#: ardour_ui2.cc:291 +#: ardour_ui2.cc:292 msgid "Stop playback" msgstr "Ferma" -#: ardour_ui2.cc:292 +#: ardour_ui2.cc:293 msgid "Play range/selection" msgstr "Suona intervallo/selezione" -#: ardour_ui2.cc:293 +#: ardour_ui2.cc:294 msgid "Go to start of session" msgstr "Vai all'inizio della sessione" -#: ardour_ui2.cc:294 +#: ardour_ui2.cc:295 msgid "Go to end of session" msgstr "Vai alla fine della sessione" -#: ardour_ui2.cc:295 +#: ardour_ui2.cc:296 msgid "Play loop range" msgstr "Suona l'intervallo di loop" -#: ardour_ui2.cc:296 +#: ardour_ui2.cc:297 msgid "Return to last playback start when stopped" msgstr "Torna al punto d'inizio una volta fermato" -#: ardour_ui2.cc:297 +#: ardour_ui2.cc:298 msgid "Start playback after any locate" msgstr "Comincia a suonare dopo ogni posizione" -#: ardour_ui2.cc:298 +#: ardour_ui2.cc:299 msgid "Be sensible about input monitoring" msgstr "Monitorizza le entrate" -#: ardour_ui2.cc:299 +#: ardour_ui2.cc:300 msgid "Start recording at auto-punch start" msgstr "Comincia a registrare al'inizio dell'auto-punch" -#: ardour_ui2.cc:300 +#: ardour_ui2.cc:301 msgid "Stop recording at auto-punch end" msgstr "Ferma la registrazione alla fine dell'auto-punch" -#: ardour_ui2.cc:301 +#: ardour_ui2.cc:302 msgid "Enable/Disable audio click" msgstr "Abilita/Disabilita il click audio" -#: ardour_ui2.cc:302 +#: ardour_ui2.cc:303 msgid "Positional sync source" msgstr "" -#: ardour_ui2.cc:303 +#: ardour_ui2.cc:304 msgid "Does Ardour control the time?" msgstr "" -#: ardour_ui2.cc:304 +#: ardour_ui2.cc:305 msgid "Shuttle speed control" msgstr "" -#: ardour_ui2.cc:305 +#: ardour_ui2.cc:306 #, fuzzy, c-format msgid "Select semitones or %%-age for speed display" msgstr "Seleziona semitoni o percentuale di velocita' del display" -#: ardour_ui2.cc:306 +#: ardour_ui2.cc:307 msgid "Current transport speed" msgstr "Velocita' del trasporto attuale" -#: ardour_ui2.cc:329 +#: ardour_ui2.cc:330 msgid "Primary clock" msgstr "Orologio principale" -#: ardour_ui2.cc:330 +#: ardour_ui2.cc:331 msgid "secondary clock" msgstr "orologio secondario" #. XXX: this should really be saved in instant.xml or something similar and restored from there #. Combo's are stupid - they steal space from the entry for the button -#: ardour_ui2.cc:387 ardour_ui2.cc:823 ardour_ui2.cc:836 ardour_ui2.cc:899 -#: ardour_ui2.cc:901 +#: ardour_ui2.cc:388 ardour_ui2.cc:833 ardour_ui2.cc:846 ardour_ui2.cc:909 +#: ardour_ui2.cc:911 msgid "sprung" msgstr "" -#: ardour_ui2.cc:388 ardour_ui2.cc:825 ardour_ui2.cc:847 +#: ardour_ui2.cc:389 ardour_ui2.cc:835 ardour_ui2.cc:857 msgid "wheel" msgstr "" -#: ardour_ui2.cc:450 +#: ardour_ui2.cc:451 msgid "ardour: clock" msgstr "ardour: orologio" -#: ardour_ui2.cc:595 +#: ardour_ui2.cc:596 msgid "Maximum speed" msgstr "" -#: ardour_ui2.cc:813 +#: ardour_ui2.cc:823 msgid "st" msgstr "" -#: ardour_ui2.cc:857 ardour_ui2.cc:880 ardour_ui2.cc:897 +#: ardour_ui2.cc:867 ardour_ui2.cc:890 ardour_ui2.cc:907 msgid "stopped" msgstr "fermato" -#: ardour_ui_dialogs.cc:152 playlist_selector.cc:69 +#: ardour_ui_dialogs.cc:153 playlist_selector.cc:70 #, fuzzy msgid "close" msgstr "Chiudi" -#: ardour_ui_dialogs.cc:359 ardour_ui_ed.cc:181 +#: ardour_ui_dialogs.cc:360 ardour_ui_ed.cc:184 #, fuzzy msgid "Sound File Browser" msgstr "Libreria Audio" #. menus + submenus that need action items -#: ardour_ui_ed.cc:69 +#: ardour_ui_ed.cc:72 msgid "Session" msgstr "Sessione" -#: ardour_ui_ed.cc:70 ardour_ui_ed.cc:127 editor.cc:1843 export_dialog.cc:350 +#: ardour_ui_ed.cc:73 ardour_ui_ed.cc:130 editor.cc:1836 export_dialog.cc:350 #: export_dialog.cc:1059 export_dialog.cc:1063 msgid "Export" msgstr "Esporta" -#: ardour_ui_ed.cc:71 +#: ardour_ui_ed.cc:74 msgid "Cleanup" msgstr "Pulisci" -#: ardour_ui_ed.cc:72 option_editor.cc:125 +#: ardour_ui_ed.cc:75 option_editor.cc:126 msgid "Sync" msgstr "" -#: ardour_ui_ed.cc:73 ardour_ui_ed.cc:74 +#: ardour_ui_ed.cc:76 ardour_ui_ed.cc:77 #, fuzzy msgid "Options" msgstr "Editor delle Opzioni" -#: ardour_ui_ed.cc:75 +#: ardour_ui_ed.cc:78 msgid "Help" msgstr "" -#: ardour_ui_ed.cc:76 +#: ardour_ui_ed.cc:79 msgid "KeyMouse Actions" msgstr "" -#: ardour_ui_ed.cc:77 +#: ardour_ui_ed.cc:80 #, fuzzy msgid "Audio File Format" msgstr "Formato Nativo" -#: ardour_ui_ed.cc:78 +#: ardour_ui_ed.cc:81 #, fuzzy msgid "Header" msgstr "smorzamento" -#: ardour_ui_ed.cc:79 +#: ardour_ui_ed.cc:82 msgid "Data" msgstr "" -#: ardour_ui_ed.cc:80 +#: ardour_ui_ed.cc:83 #, fuzzy msgid "Control Surfaces" msgstr "Uscite di Controllo" #. the real actions -#: ardour_ui_ed.cc:84 audio_time_axis.cc:1856 new_session_dialog.cc:342 +#: ardour_ui_ed.cc:87 audio_time_axis.cc:1854 new_session_dialog.cc:529 msgid "New" msgstr "Nuovo" -#: ardour_ui_ed.cc:86 new_session_dialog.cc:334 +#: ardour_ui_ed.cc:89 new_session_dialog.cc:517 msgid "Open" msgstr "Apri" -#: ardour_ui_ed.cc:87 +#: ardour_ui_ed.cc:90 msgid "Recent" msgstr "Recenti" -#: ardour_ui_ed.cc:88 io_selector.cc:57 io_selector.cc:791 +#: ardour_ui_ed.cc:91 io_selector.cc:58 io_selector.cc:792 msgid "Close" msgstr "Chiudi" -#: ardour_ui_ed.cc:91 route_params_ui.cc:512 +#: ardour_ui_ed.cc:94 route_params_ui.cc:514 msgid "Add Track/Bus" msgstr "Aggiungi Tracce/Bus" -#: ardour_ui_ed.cc:102 +#: ardour_ui_ed.cc:105 msgid "Connect" msgstr "Connetti" #. -#: ardour_ui_ed.cc:110 +#: ardour_ui_ed.cc:113 msgid "Snapshot" msgstr "Istantanea" -#: ardour_ui_ed.cc:113 +#: ardour_ui_ed.cc:116 msgid "Save Template..." msgstr "Salva Modello..." -#: ardour_ui_ed.cc:116 +#: ardour_ui_ed.cc:119 msgid "Export session to audiofile..." msgstr "Esporta la sessione come file audio..." -#: ardour_ui_ed.cc:119 +#: ardour_ui_ed.cc:122 #, fuzzy msgid "Export selection to audiofile..." msgstr "Esporta la sessione come file audio..." -#: ardour_ui_ed.cc:123 +#: ardour_ui_ed.cc:126 #, fuzzy msgid "Export range markers to audiofile..." msgstr "Esporta l'intervallo come file audio..." -#: ardour_ui_ed.cc:130 +#: ardour_ui_ed.cc:133 msgid "Cleanup unused sources" msgstr "Pulisci sorgenti inutilizzate" -#: ardour_ui_ed.cc:132 +#: ardour_ui_ed.cc:135 msgid "Flush wastebasket" msgstr "Svuota il cestino" -#: ardour_ui_ed.cc:138 ardour_ui_options.cc:381 ardour_ui_options.cc:390 -#: ardour_ui_options.cc:462 +#: ardour_ui_ed.cc:141 ardour_ui_options.cc:408 ardour_ui_options.cc:417 +#: ardour_ui_options.cc:489 msgid "JACK" msgstr "" -#: ardour_ui_ed.cc:139 +#: ardour_ui_ed.cc:142 msgid "Latency" msgstr "" -#: ardour_ui_ed.cc:141 +#: ardour_ui_ed.cc:144 #, fuzzy msgid "Reconnect" msgstr "Connetti" -#: ardour_ui_ed.cc:144 mixer_strip.cc:514 mixer_strip.cc:574 +#: ardour_ui_ed.cc:147 mixer_strip.cc:497 mixer_strip.cc:565 msgid "Disconnect" msgstr "Disconnetti" -#: ardour_ui_ed.cc:171 +#: ardour_ui_ed.cc:174 msgid "Windows" msgstr "Finestre" -#: ardour_ui_ed.cc:172 +#: ardour_ui_ed.cc:175 msgid "start prefix" msgstr "" -#: ardour_ui_ed.cc:173 +#: ardour_ui_ed.cc:176 msgid "Quit" msgstr "Esci" #. windows visibility actions -#: ardour_ui_ed.cc:177 +#: ardour_ui_ed.cc:180 msgid "Maximise Editor Space" msgstr "" -#: ardour_ui_ed.cc:179 +#: ardour_ui_ed.cc:182 #, fuzzy msgid "Show Editor" msgstr "Editor delle Opzioni" -#: ardour_ui_ed.cc:180 +#: ardour_ui_ed.cc:183 msgid "Show Mixer" msgstr "" -#: ardour_ui_ed.cc:182 +#: ardour_ui_ed.cc:185 msgid "Options Editor" msgstr "Editor delle Opzioni" -#: ardour_ui_ed.cc:183 +#: ardour_ui_ed.cc:186 #, fuzzy msgid "Track/Bus Inspector" msgstr "Tracce/Bus" -#: ardour_ui_ed.cc:185 +#: ardour_ui_ed.cc:188 msgid "Connections" msgstr "Connessioni" -#: ardour_ui_ed.cc:187 +#: ardour_ui_ed.cc:190 msgid "Locations" msgstr "Posizioni" -#: ardour_ui_ed.cc:189 +#: ardour_ui_ed.cc:192 msgid "Big Clock" msgstr "Orologio grande" -#: ardour_ui_ed.cc:191 +#: ardour_ui_ed.cc:194 msgid "About" msgstr "Circa" -#: ardour_ui_ed.cc:192 +#: ardour_ui_ed.cc:195 #, fuzzy msgid "Colors" msgstr "Colore" -#: ardour_ui_ed.cc:194 +#: ardour_ui_ed.cc:197 #, fuzzy msgid "Add Audio Track" msgstr "Aggiungi Tracce/Bus" -#: ardour_ui_ed.cc:196 +#: ardour_ui_ed.cc:199 #, fuzzy msgid "Add Audio Bus" msgstr "Nascondi tutti i Bus Audio" -#: ardour_ui_ed.cc:198 +#: ardour_ui_ed.cc:201 msgid "Save" msgstr "Salva" -#: ardour_ui_ed.cc:200 editor_actions.cc:254 +#: ardour_ui_ed.cc:203 editor_actions.cc:255 #, fuzzy msgid "Remove Last Capture" msgstr "Rimuovi l'ultima registrazione" #. do-nothing action for the "transport" menu bar item -#: ardour_ui_ed.cc:207 +#: ardour_ui_ed.cc:210 #, fuzzy msgid "Transport" msgstr "Traduttori" @@ -982,73 +964,73 @@ msgstr "Traduttori" #. these two are not used by key bindings, instead use ToggleRoll for that. these two do show up in #. menus and via button proxies. #. -#: ardour_ui_ed.cc:213 sfdb_ui.cc:57 +#: ardour_ui_ed.cc:216 sfdb_ui.cc:57 msgid "Stop" msgstr "" -#: ardour_ui_ed.cc:216 +#: ardour_ui_ed.cc:219 msgid "Roll" msgstr "" -#: ardour_ui_ed.cc:220 +#: ardour_ui_ed.cc:223 #, fuzzy msgid "Start/Stop" msgstr "Inizio:" -#: ardour_ui_ed.cc:223 +#: ardour_ui_ed.cc:226 msgid "Stop + Forget Capture" msgstr "" -#: ardour_ui_ed.cc:226 +#: ardour_ui_ed.cc:229 #, fuzzy msgid "Play Loop Range" msgstr "Suona l'intervallo di loop" -#: ardour_ui_ed.cc:229 +#: ardour_ui_ed.cc:232 #, fuzzy msgid "Play Selection" msgstr "Suona la regione selezionata" -#: ardour_ui_ed.cc:233 +#: ardour_ui_ed.cc:236 #, fuzzy msgid "Enable Record" msgstr "Registra" -#: ardour_ui_ed.cc:236 +#: ardour_ui_ed.cc:239 #, fuzzy msgid "Rewind" msgstr "Regione" -#: ardour_ui_ed.cc:239 +#: ardour_ui_ed.cc:242 msgid "Rewind (Slow)" msgstr "" -#: ardour_ui_ed.cc:242 +#: ardour_ui_ed.cc:245 msgid "Rewind (Fast)" msgstr "" -#: ardour_ui_ed.cc:245 +#: ardour_ui_ed.cc:248 msgid "Forward" msgstr "" -#: ardour_ui_ed.cc:248 +#: ardour_ui_ed.cc:251 msgid "Forward (Slow)" msgstr "" -#: ardour_ui_ed.cc:251 +#: ardour_ui_ed.cc:254 msgid "Forward (Fast)" msgstr "" -#: ardour_ui_ed.cc:254 +#: ardour_ui_ed.cc:257 msgid "Goto Zero" msgstr "" -#: ardour_ui_ed.cc:257 +#: ardour_ui_ed.cc:260 #, fuzzy msgid "Goto Start" msgstr "Inizio:" -#: ardour_ui_ed.cc:260 +#: ardour_ui_ed.cc:263 msgid "Goto End" msgstr "" @@ -1056,316 +1038,316 @@ msgstr "" #. that proxies for these action to be more compact. It would be nice to find a way to override the action #. name appearance on the buttons. #. -#: ardour_ui_ed.cc:269 +#: ardour_ui_ed.cc:272 msgid "" "Punch\n" "in" msgstr "" -#: ardour_ui_ed.cc:272 +#: ardour_ui_ed.cc:275 msgid "" "Punch\n" "out" msgstr "" -#: ardour_ui_ed.cc:275 option_editor.cc:128 +#: ardour_ui_ed.cc:278 option_editor.cc:129 msgid "Click" msgstr "" -#: ardour_ui_ed.cc:278 +#: ardour_ui_ed.cc:281 #, fuzzy msgid "" "Auto\n" "input" msgstr "entrata %1" -#: ardour_ui_ed.cc:281 +#: ardour_ui_ed.cc:284 #, fuzzy msgid "" "Auto\n" "play" msgstr "suona" -#: ardour_ui_ed.cc:284 +#: ardour_ui_ed.cc:287 msgid "" "Auto\n" "return" msgstr "" -#: ardour_ui_ed.cc:288 +#: ardour_ui_ed.cc:291 msgid "" "Time\n" "master" msgstr "" -#: ardour_ui_ed.cc:291 +#: ardour_ui_ed.cc:294 msgid "Toggle Record Enable Track1" msgstr "" -#: ardour_ui_ed.cc:293 +#: ardour_ui_ed.cc:296 msgid "Toggle Record Enable Track2" msgstr "" -#: ardour_ui_ed.cc:295 +#: ardour_ui_ed.cc:298 msgid "Toggle Record Enable Track3" msgstr "" -#: ardour_ui_ed.cc:297 +#: ardour_ui_ed.cc:300 msgid "Toggle Record Enable Track4" msgstr "" -#: ardour_ui_ed.cc:299 +#: ardour_ui_ed.cc:302 msgid "Toggle Record Enable Track5" msgstr "" -#: ardour_ui_ed.cc:301 +#: ardour_ui_ed.cc:304 msgid "Toggle Record Enable Track6" msgstr "" -#: ardour_ui_ed.cc:303 +#: ardour_ui_ed.cc:306 msgid "Toggle Record Enable Track7" msgstr "" -#: ardour_ui_ed.cc:305 +#: ardour_ui_ed.cc:308 msgid "Toggle Record Enable Track8" msgstr "" -#: ardour_ui_ed.cc:307 +#: ardour_ui_ed.cc:310 msgid "Toggle Record Enable Track9" msgstr "" -#: ardour_ui_ed.cc:309 +#: ardour_ui_ed.cc:312 msgid "Toggle Record Enable Track10" msgstr "" -#: ardour_ui_ed.cc:311 +#: ardour_ui_ed.cc:314 msgid "Toggle Record Enable Track11" msgstr "" -#: ardour_ui_ed.cc:313 +#: ardour_ui_ed.cc:316 msgid "Toggle Record Enable Track12" msgstr "" -#: ardour_ui_ed.cc:315 +#: ardour_ui_ed.cc:318 msgid "Toggle Record Enable Track13" msgstr "" -#: ardour_ui_ed.cc:317 +#: ardour_ui_ed.cc:320 msgid "Toggle Record Enable Track14" msgstr "" -#: ardour_ui_ed.cc:319 +#: ardour_ui_ed.cc:322 msgid "Toggle Record Enable Track15" msgstr "" -#: ardour_ui_ed.cc:321 +#: ardour_ui_ed.cc:324 msgid "Toggle Record Enable Track16" msgstr "" -#: ardour_ui_ed.cc:323 +#: ardour_ui_ed.cc:326 msgid "Toggle Record Enable Track17" msgstr "" -#: ardour_ui_ed.cc:325 +#: ardour_ui_ed.cc:328 msgid "Toggle Record Enable Track18" msgstr "" -#: ardour_ui_ed.cc:327 +#: ardour_ui_ed.cc:330 msgid "Toggle Record Enable Track19" msgstr "" -#: ardour_ui_ed.cc:329 +#: ardour_ui_ed.cc:332 msgid "Toggle Record Enable Track20" msgstr "" -#: ardour_ui_ed.cc:331 +#: ardour_ui_ed.cc:334 msgid "Toggle Record Enable Track21" msgstr "" -#: ardour_ui_ed.cc:333 +#: ardour_ui_ed.cc:336 msgid "Toggle Record Enable Track22" msgstr "" -#: ardour_ui_ed.cc:335 +#: ardour_ui_ed.cc:338 msgid "Toggle Record Enable Track23" msgstr "" -#: ardour_ui_ed.cc:337 +#: ardour_ui_ed.cc:340 msgid "Toggle Record Enable Track24" msgstr "" -#: ardour_ui_ed.cc:339 +#: ardour_ui_ed.cc:342 msgid "Toggle Record Enable Track25" msgstr "" -#: ardour_ui_ed.cc:341 +#: ardour_ui_ed.cc:344 msgid "Toggle Record Enable Track26" msgstr "" -#: ardour_ui_ed.cc:343 +#: ardour_ui_ed.cc:346 msgid "Toggle Record Enable Track27" msgstr "" -#: ardour_ui_ed.cc:345 +#: ardour_ui_ed.cc:348 msgid "Toggle Record Enable Track28" msgstr "" -#: ardour_ui_ed.cc:347 +#: ardour_ui_ed.cc:350 msgid "Toggle Record Enable Track29" msgstr "" -#: ardour_ui_ed.cc:349 +#: ardour_ui_ed.cc:352 msgid "Toggle Record Enable Track30" msgstr "" -#: ardour_ui_ed.cc:351 +#: ardour_ui_ed.cc:354 msgid "Toggle Record Enable Track31" msgstr "" -#: ardour_ui_ed.cc:353 +#: ardour_ui_ed.cc:356 msgid "Toggle Record Enable Track32" msgstr "" -#: ardour_ui_ed.cc:358 +#: ardour_ui_ed.cc:361 msgid "Percentage" msgstr "Percentuale" -#: ardour_ui_ed.cc:359 +#: ardour_ui_ed.cc:362 msgid "Semitones" msgstr "Semitoni" -#: ardour_ui_ed.cc:363 +#: ardour_ui_ed.cc:366 msgid "Send MTC" msgstr "Invia MTC" -#: ardour_ui_ed.cc:365 +#: ardour_ui_ed.cc:368 msgid "Send MMC" msgstr "Invia MMC" -#: ardour_ui_ed.cc:367 +#: ardour_ui_ed.cc:370 #, fuzzy msgid "Use MMC" msgstr "Invia MMC" -#: ardour_ui_ed.cc:369 +#: ardour_ui_ed.cc:372 msgid "Send MIDI feedback" msgstr "" -#: ardour_ui_ed.cc:371 +#: ardour_ui_ed.cc:374 #, fuzzy msgid "Use MIDI control" msgstr "Porta MMC" -#: ardour_ui_ed.cc:374 +#: ardour_ui_ed.cc:377 #, fuzzy -msgid "Connect newtrack inputs to hardware" +msgid "Connect new track inputs to hardware" msgstr "Connetti automaticamente nuove tracce" -#: ardour_ui_ed.cc:392 +#: ardour_ui_ed.cc:396 #, fuzzy msgid "Connect new track outputs to hardware" msgstr "Connetti automaticamente nuove tracce" -#: ardour_ui_ed.cc:394 +#: ardour_ui_ed.cc:398 #, fuzzy msgid "Connect new track outputs to master" msgstr "autoconnetti le uscite delle tracce alle uscite master" -#: ardour_ui_ed.cc:396 +#: ardour_ui_ed.cc:400 #, fuzzy msgid "Manually connect new track outputs" msgstr "connetti manualmente le uscite delle tracce" -#: ardour_ui_ed.cc:401 +#: ardour_ui_ed.cc:405 #, fuzzy msgid "Hardware monitoring" msgstr "Usa il Monitoraggio Hardware" -#: ardour_ui_ed.cc:402 +#: ardour_ui_ed.cc:406 #, fuzzy msgid "Software monitoring" msgstr "Usa il Monitoraggio Software" -#: ardour_ui_ed.cc:403 +#: ardour_ui_ed.cc:407 #, fuzzy msgid "External monitoring" msgstr "Usa il Monitoraggio Hardware" #. Configuration object options (i.e. not session specific) -#: ardour_ui_ed.cc:407 +#: ardour_ui_ed.cc:411 msgid "Stop plugins with transport" msgstr "Ferma i plugin durante il transport" -#: ardour_ui_ed.cc:408 +#: ardour_ui_ed.cc:412 #, fuzzy msgid "Verify remove last capture" msgstr "Rimuovi l'ultima registrazione" -#: ardour_ui_ed.cc:409 +#: ardour_ui_ed.cc:413 msgid "Stop recording on xrun" msgstr "Ferma la registrazione in caso di xrun" -#: ardour_ui_ed.cc:410 +#: ardour_ui_ed.cc:414 #, fuzzy msgid "Stop transport at session end" msgstr "Ferma il transport a fine sessione" -#: ardour_ui_ed.cc:411 +#: ardour_ui_ed.cc:415 msgid "-12dB gain reduce ffwd/rewind" msgstr "" -#: ardour_ui_ed.cc:412 +#: ardour_ui_ed.cc:416 msgid "Rec-enable stays engaged at stop" msgstr "" #. session options -#: ardour_ui_ed.cc:416 +#: ardour_ui_ed.cc:420 #, fuzzy msgid "Do not run plugins while recording" msgstr "Avvia i plugin durante la registrazione" -#: ardour_ui_ed.cc:419 +#: ardour_ui_ed.cc:423 msgid "Latched solo" msgstr "" -#: ardour_ui_ed.cc:424 +#: ardour_ui_ed.cc:428 msgid "Solo in-place" msgstr "" -#: ardour_ui_ed.cc:426 +#: ardour_ui_ed.cc:430 msgid "Solo via bus" msgstr "" -#: ardour_ui_ed.cc:429 +#: ardour_ui_ed.cc:433 #, fuzzy msgid "Automatically create crossfades" msgstr "Smorzamento incrociato automatico in caso sovrapposizione" -#: ardour_ui_ed.cc:431 +#: ardour_ui_ed.cc:435 msgid "Unmute new full crossfades" msgstr "" -#: ardour_ui_options.cc:379 ardour_ui_options.cc:389 ardour_ui_options.cc:456 +#: ardour_ui_options.cc:406 ardour_ui_options.cc:416 ardour_ui_options.cc:483 msgid "Internal" msgstr "interno" -#: ardour_ui_options.cc:380 ardour_ui_options.cc:459 +#: ardour_ui_options.cc:407 ardour_ui_options.cc:486 msgid "MTC" msgstr "" -#: audio_clock.cc:1719 editor.cc:185 +#: audio_clock.cc:1742 editor.cc:188 msgid "SMPTE" msgstr "" -#: audio_clock.cc:1720 editor.cc:184 editor_rulers.cc:359 +#: audio_clock.cc:1743 editor.cc:187 editor_rulers.cc:360 msgid "Bars:Beats" msgstr "Battuta:Battiti" -#: audio_clock.cc:1721 +#: audio_clock.cc:1744 msgid "Minutes:Seconds" msgstr "Minuti:Secondi" -#: audio_clock.cc:1722 +#: audio_clock.cc:1745 msgid "Audio Frames" msgstr "" @@ -1373,290 +1355,311 @@ msgstr "" #. Slowest = 6.6dB/sec falloff at update rate of 40ms #. Slow = 6.8dB/sec falloff at update rate of 40ms #. -#: audio_clock.cc:1723 editor_actions.cc:374 editor_actions.cc:382 +#: audio_clock.cc:1746 editor_actions.cc:375 editor_actions.cc:383 +#: gain_meter.cc:172 panner_ui.cc:89 plugin_ui.cc:392 plugin_ui.cc:635 msgid "Off" msgstr "" -#: audio_clock.cc:1725 +#: audio_clock.cc:1748 msgid "Mode" msgstr "Modo" -#: audio_time_axis.cc:90 mixer_strip.cc:458 +#: audio_time_axis.cc:91 msgid "m" msgstr "" -#: audio_time_axis.cc:90 mixer_strip.cc:459 +#: audio_time_axis.cc:91 msgid "s" msgstr "" -#: audio_time_axis.cc:90 +#: audio_time_axis.cc:91 msgid "r" msgstr "" -#: audio_time_axis.cc:94 +#: audio_time_axis.cc:95 msgid "g" msgstr "" #. group -#: audio_time_axis.cc:95 +#: audio_time_axis.cc:96 msgid "p" msgstr "" -#: audio_time_axis.cc:96 automation_time_axis.cc:31 visual_time_axis.cc:73 +#: audio_time_axis.cc:97 automation_time_axis.cc:32 visual_time_axis.cc:74 msgid "h" msgstr "" #. height -#: audio_time_axis.cc:97 +#: audio_time_axis.cc:98 msgid "a" msgstr "" -#: audio_time_axis.cc:98 visual_time_axis.cc:72 +#: audio_time_axis.cc:99 visual_time_axis.cc:73 msgid "v" msgstr "" -#: audio_time_axis.cc:173 +#: audio_time_axis.cc:168 mixer_strip.cc:86 msgid "Record" msgstr "Registra" -#: audio_time_axis.cc:174 editor_actions.cc:36 +#: audio_time_axis.cc:169 editor_actions.cc:37 mixer_strip.cc:86 msgid "Solo" msgstr "" -#: audio_time_axis.cc:175 editor.cc:1767 editor.cc:1866 panner_ui.cc:385 +#: audio_time_axis.cc:170 editor.cc:1760 editor.cc:1859 mixer_strip.cc:86 +#: panner_ui.cc:427 msgid "Mute" msgstr "Muto" -#: audio_time_axis.cc:176 +#: audio_time_axis.cc:171 msgid "Edit Group" msgstr "Modifica Gruppo" -#: audio_time_axis.cc:177 visual_time_axis.cc:91 +#: audio_time_axis.cc:172 visual_time_axis.cc:92 msgid "Display Height" msgstr "Altezza" -#: audio_time_axis.cc:178 +#: audio_time_axis.cc:173 msgid "Playlist" msgstr "" -#: audio_time_axis.cc:179 audio_time_axis.cc:743 +#: audio_time_axis.cc:174 audio_time_axis.cc:741 msgid "Automation" msgstr "Automazione" -#: audio_time_axis.cc:180 visual_time_axis.cc:92 +#: audio_time_axis.cc:175 visual_time_axis.cc:93 msgid "Visual options" msgstr "Opzioni di visualizzazione" -#: audio_time_axis.cc:181 visual_time_axis.cc:93 +#: audio_time_axis.cc:176 visual_time_axis.cc:94 msgid "Hide this track" msgstr "Nascondi traccia" -#: audio_time_axis.cc:337 +#: audio_time_axis.cc:333 mixer_strip.cc:927 msgid "No group" msgstr "nessun gruppo" -#: audio_time_axis.cc:704 automation_time_axis.cc:448 -#: imageframe_time_axis.cc:256 marker_time_axis.cc:210 +#: audio_time_axis.cc:702 automation_time_axis.cc:450 +#: imageframe_time_axis.cc:255 marker_time_axis.cc:211 msgid "Height" msgstr "Altezza" -#: audio_time_axis.cc:705 color_manager.cc:40 imageframe_time_axis.cc:257 -#: marker_time_axis.cc:211 +#: audio_time_axis.cc:703 color_manager.cc:41 imageframe_time_axis.cc:256 +#: marker_time_axis.cc:212 msgid "Color" msgstr "Colore" -#: audio_time_axis.cc:709 +#: audio_time_axis.cc:707 msgid "Hide all crossfades" msgstr "" -#: audio_time_axis.cc:710 +#: audio_time_axis.cc:708 msgid "Show all crossfades" msgstr "" -#: audio_time_axis.cc:714 mixer_strip.cc:1236 +#: audio_time_axis.cc:712 mixer_strip.cc:1011 #, fuzzy msgid "Remote Control ID" msgstr "Rimuovi il punto di sincronizzazione" -#: audio_time_axis.cc:720 -msgid "show all automation" +#: audio_time_axis.cc:718 +#, fuzzy +msgid "Show all automation" msgstr "mostra tutte le automazioni" -#: audio_time_axis.cc:723 -msgid "show existing automation" +#: audio_time_axis.cc:721 +#, fuzzy +msgid "Show existing automation" msgstr "mostra le automazioni esistenti" -#: audio_time_axis.cc:726 -msgid "hide all automation" +#: audio_time_axis.cc:724 +#, fuzzy +msgid "Hide all automation" msgstr "nascondi tutte le automazioni" -#: audio_time_axis.cc:731 audio_time_axis.cc:1169 editor.cc:215 -msgid "gain" +#: audio_time_axis.cc:729 +#, fuzzy +msgid "Fader" +msgstr "Smorzamenti" + +#: audio_time_axis.cc:734 +msgid "Pan" msgstr "" -#: audio_time_axis.cc:736 audio_time_axis.cc:1209 -msgid "pan" -msgstr "" - -#: audio_time_axis.cc:741 +#: audio_time_axis.cc:739 msgid "Plugins" msgstr "" -#: audio_time_axis.cc:749 +#: audio_time_axis.cc:747 msgid "Show waveforms" msgstr "Mostra le forme Wave" -#: audio_time_axis.cc:757 +#: audio_time_axis.cc:755 msgid "Traditional" msgstr "Tradizionale" -#: audio_time_axis.cc:760 +#: audio_time_axis.cc:758 msgid "Rectified" msgstr "Rettificato" -#: audio_time_axis.cc:763 +#: audio_time_axis.cc:761 msgid "Waveform" msgstr "Forme wave" -#: audio_time_axis.cc:773 +#: audio_time_axis.cc:771 #, fuzzy -msgid "align with existing material" +msgid "Align with existing material" msgstr "Materiale esistente" -#: audio_time_axis.cc:778 +#: audio_time_axis.cc:776 #, fuzzy -msgid "align with capture time" +msgid "Align with capture time" msgstr "Tempo di registrazione" -#: audio_time_axis.cc:784 +#: audio_time_axis.cc:782 #, fuzzy msgid "Alignment" msgstr "Allinea" -#: audio_time_axis.cc:790 editor.cc:523 editor_actions.cc:59 -#: mixer_strip.cc:1225 +#: audio_time_axis.cc:788 editor.cc:527 editor_actions.cc:60 +#: mixer_strip.cc:1000 mixer_ui.cc:111 msgid "Active" msgstr "Attivo" -#: audio_time_axis.cc:795 editor.cc:1929 editor_actions.cc:319 -#: editor_markers.cc:507 imageframe_time_axis.cc:260 location_ui.cc:56 -#: marker_time_axis.cc:214 mixer_strip.cc:1239 +#: audio_time_axis.cc:793 editor.cc:1922 editor_actions.cc:320 +#: editor_markers.cc:508 imageframe_time_axis.cc:259 location_ui.cc:57 +#: marker_time_axis.cc:215 mixer_strip.cc:1014 msgid "Remove" msgstr "Rimuovi" -#: audio_time_axis.cc:835 +#: audio_time_axis.cc:833 #, fuzzy msgid "Name for playlist" msgstr "Nome dell' istantanea" -#: audio_time_axis.cc:837 audio_time_axis.cc:1853 editor_markers.cc:826 -#: editor_mouse.cc:4609 imageframe_time_axis.cc:249 marker_time_axis.cc:207 -#: meter_bridge_strip.cc:223 mixer_strip.cc:1223 redirect_box.cc:749 -#: redirect_box.cc:1063 route_ui.cc:732 visual_time_axis.cc:325 +#: audio_time_axis.cc:835 audio_time_axis.cc:1851 editor_markers.cc:827 +#: editor_mouse.cc:4673 imageframe_time_axis.cc:248 marker_time_axis.cc:208 +#: meter_bridge_strip.cc:224 mixer_strip.cc:998 redirect_box.cc:751 +#: redirect_box.cc:1065 route_ui.cc:739 visual_time_axis.cc:326 msgid "Rename" msgstr "Rinomina" -#: audio_time_axis.cc:870 audio_time_axis.cc:910 +#: audio_time_axis.cc:868 audio_time_axis.cc:908 #, fuzzy msgid "Name for Playlist" msgstr "Nome dell' istantanea" -#: audio_time_axis.cc:1128 visual_time_axis.cc:382 +#: audio_time_axis.cc:1126 visual_time_axis.cc:383 msgid "a track already exists with that name" msgstr "esiste già una traccia con quel nome" -#: audio_time_axis.cc:1412 editor.cc:1490 selection.cc:622 +#: audio_time_axis.cc:1167 editor.cc:218 +msgid "gain" +msgstr "" + +#: audio_time_axis.cc:1207 +msgid "pan" +msgstr "" + +#: audio_time_axis.cc:1410 editor.cc:1483 selection.cc:634 msgid "programming error: " msgstr "errore di programmazione: " -#: audio_time_axis.cc:1850 +#: audio_time_axis.cc:1848 msgid "Current: %1" msgstr "Corrente %1" -#: audio_time_axis.cc:1857 +#: audio_time_axis.cc:1855 msgid "New Copy" msgstr "Nuova Copia" -#: audio_time_axis.cc:1859 +#: audio_time_axis.cc:1857 msgid "Clear Current" msgstr "Pulisci Corrente" -#: audio_time_axis.cc:1861 editor.cc:2031 editor.cc:2107 +#: audio_time_axis.cc:1859 editor.cc:2024 editor.cc:2100 msgid "Select" msgstr "Seleziona" -#: automation_line.cc:883 +#: automation_line.cc:884 msgid "automation event move" msgstr "" -#: automation_line.cc:885 +#: automation_line.cc:886 msgid "automation range drag" msgstr "" -#: automation_line.cc:1014 region_gain_line.cc:61 +#: automation_line.cc:1015 region_gain_line.cc:62 #, fuzzy msgid "remove control point" msgstr "Rimuovi il punto di sincronizzazione" -#: automation_time_axis.cc:32 editor_ops.cc:2813 +#: automation_time_axis.cc:33 editor_ops.cc:2885 msgid "clear" msgstr "pulisci" -#: automation_time_axis.cc:74 +#: automation_time_axis.cc:75 msgid "track height" msgstr "" -#: automation_time_axis.cc:75 +#: automation_time_axis.cc:76 #, fuzzy msgid "automation state" msgstr "stato dell'automazione pan" -#: automation_time_axis.cc:76 +#: automation_time_axis.cc:77 #, fuzzy msgid "clear track" msgstr "azzera gli intervalli" -#: automation_time_axis.cc:77 +#: automation_time_axis.cc:78 #, fuzzy msgid "hide track" msgstr "Nascondi traccia" -#: automation_time_axis.cc:185 automation_time_axis.cc:223 -#: automation_time_axis.cc:463 mixer_strip.cc:176 mixer_strip.cc:188 -#: plugin_ui.cc:394 plugin_ui.cc:636 region_editor.cc:53 -msgid "play" -msgstr "suona" +#: automation_time_axis.cc:184 automation_time_axis.cc:213 +#: automation_time_axis.cc:461 +msgid "Manual" +msgstr "" -#: automation_time_axis.cc:187 automation_time_axis.cc:234 -#: automation_time_axis.cc:467 mixer_strip.cc:178 mixer_strip.cc:190 -#: plugin_ui.cc:397 plugin_ui.cc:638 -msgid "write" +#: automation_time_axis.cc:186 automation_time_axis.cc:224 +#: automation_time_axis.cc:465 editor.cc:2001 editor.cc:2082 gain_meter.cc:174 +#: panner_ui.cc:91 plugin_ui.cc:395 plugin_ui.cc:637 sfdb_ui.cc:56 +msgid "Play" +msgstr "Suona" + +#: automation_time_axis.cc:188 automation_time_axis.cc:235 +#: automation_time_axis.cc:469 gain_meter.cc:176 panner_ui.cc:93 +#: plugin_ui.cc:398 plugin_ui.cc:639 +#, fuzzy +msgid "Write" msgstr "scrivi" -#: automation_time_axis.cc:189 automation_time_axis.cc:245 -#: automation_time_axis.cc:471 mixer_strip.cc:180 mixer_strip.cc:192 -#: mixer_strip.cc:887 plugin_ui.cc:400 plugin_ui.cc:640 -msgid "touch" +#: automation_time_axis.cc:190 automation_time_axis.cc:246 +#: automation_time_axis.cc:473 gain_meter.cc:178 panner_ui.cc:95 +#: plugin_ui.cc:401 plugin_ui.cc:641 +#, fuzzy +msgid "Touch" msgstr "crea" -#: automation_time_axis.cc:256 option_editor.cc:182 option_editor.cc:188 -#: plugin_ui.cc:403 +#: automation_time_axis.cc:257 option_editor.cc:183 option_editor.cc:189 +#: plugin_ui.cc:404 msgid "???" msgstr "" -#: automation_time_axis.cc:270 +#: automation_time_axis.cc:271 msgid "clear automation" msgstr "pulisci l'automazione" -#: automation_time_axis.cc:450 editor_actions.cc:317 +#: automation_time_axis.cc:452 editor_actions.cc:318 msgid "Hide" msgstr "Nascondi" -#: automation_time_axis.cc:452 crossfade_edit.cc:76 redirect_box.cc:1055 +#: automation_time_axis.cc:454 crossfade_edit.cc:78 redirect_box.cc:1057 msgid "Clear" msgstr "Pulisci" -#: automation_time_axis.cc:475 +#: automation_time_axis.cc:477 #, fuzzy msgid "State" msgstr "Inizio:" @@ -1803,1579 +1806,1566 @@ msgstr "" msgid "color of fill" msgstr "" -#: color_manager.cc:39 +#: color_manager.cc:40 #, fuzzy msgid "Object" msgstr "oggetto" -#: color_manager.cc:77 +#: color_manager.cc:78 #, fuzzy msgid "cannot open color definition file %1: %2" msgstr "Editor: impossibile l'immagine per lo splash \"%1\" (%2)" -#: crossfade_edit.cc:73 +#: crossfade_edit.cc:75 msgid "ardour: x-fade edit" msgstr "ardour: modifica lo smorzamento incrociato" -#: crossfade_edit.cc:77 panner_ui.cc:401 +#: crossfade_edit.cc:79 panner_ui.cc:443 #, fuzzy msgid "Reset" msgstr "azzera" -#: crossfade_edit.cc:78 +#: crossfade_edit.cc:80 #, fuzzy msgid "Fade" msgstr "Smorzamenti" -#: crossfade_edit.cc:79 +#: crossfade_edit.cc:81 msgid "Out (dry)" msgstr "" -#: crossfade_edit.cc:80 +#: crossfade_edit.cc:82 #, fuzzy msgid "Out" msgstr "Uscite" -#: crossfade_edit.cc:81 +#: crossfade_edit.cc:83 msgid "In (dry)" msgstr "" -#: crossfade_edit.cc:82 +#: crossfade_edit.cc:84 msgid "In" msgstr "" -#: crossfade_edit.cc:84 +#: crossfade_edit.cc:86 #, fuzzy msgid "With Pre-roll" msgstr "con pre-roll" -#: crossfade_edit.cc:85 +#: crossfade_edit.cc:87 #, fuzzy msgid "With Post-roll" msgstr "con post-roll" -#: crossfade_edit.cc:93 +#: crossfade_edit.cc:95 msgid "Fade In" msgstr "SMORZA Entrata" -#: crossfade_edit.cc:94 +#: crossfade_edit.cc:96 msgid "Fade Out" msgstr "SMORZA Uscita" -#: crossfade_edit.cc:170 editor.cc:1842 editor_actions.cc:315 -#: option_editor.cc:129 +#: crossfade_edit.cc:172 editor.cc:1835 editor_actions.cc:316 +#: option_editor.cc:130 msgid "Audition" msgstr "" -#: editor.cc:101 editor.cc:3588 +#: editor.cc:104 editor.cc:3616 msgid "Slide" msgstr "" -#: editor.cc:102 editor.cc:3586 +#: editor.cc:105 editor.cc:3614 msgid "Splice" msgstr "" -#: editor.cc:107 editor.cc:3643 export_dialog.cc:78 export_dialog.cc:92 -#: export_dialog.cc:893 export_dialog.cc:1225 +#. note that this menu list starts at zero, not 1, because zero +#. is a valid, if useless, ID. +#. +#. leave some breathing room +#: editor.cc:110 editor.cc:3671 export_dialog.cc:78 export_dialog.cc:92 +#: export_dialog.cc:893 export_dialog.cc:1225 route_ui.cc:437 msgid "None" msgstr "Nessuno" -#: editor.cc:108 editor.cc:3631 +#: editor.cc:111 editor.cc:3659 msgid "CD Frames" msgstr "" -#: editor.cc:109 editor.cc:3633 +#: editor.cc:112 editor.cc:3661 msgid "SMPTE Frames" msgstr "" -#: editor.cc:110 editor.cc:3635 +#: editor.cc:113 editor.cc:3663 msgid "SMPTE Seconds" msgstr "" -#: editor.cc:111 editor.cc:3637 +#: editor.cc:114 editor.cc:3665 msgid "SMPTE Minutes" msgstr "" -#: editor.cc:112 editor.cc:3639 +#: editor.cc:115 editor.cc:3667 msgid "Seconds" msgstr "Secondi" -#: editor.cc:113 editor.cc:3641 +#: editor.cc:116 editor.cc:3669 msgid "Minutes" msgstr "Minuti" -#: editor.cc:114 editor.cc:3613 +#: editor.cc:117 editor.cc:3641 msgid "Beats/32" msgstr "Battiti/32" -#: editor.cc:115 editor.cc:3611 +#: editor.cc:118 editor.cc:3639 msgid "Beats/16" msgstr "Battiti/16" -#: editor.cc:116 editor.cc:3609 +#: editor.cc:119 editor.cc:3637 msgid "Beats/8" msgstr "Battiti/8" -#: editor.cc:117 editor.cc:3607 +#: editor.cc:120 editor.cc:3635 msgid "Beats/4" msgstr "Battiti/4" -#: editor.cc:118 editor.cc:3605 +#: editor.cc:121 editor.cc:3633 msgid "Beats/3" msgstr "Battiti/3" -#: editor.cc:119 editor.cc:3615 +#: editor.cc:122 editor.cc:3643 msgid "Beats" msgstr "Battiti" -#: editor.cc:120 editor.cc:3617 +#: editor.cc:123 editor.cc:3645 msgid "Bars" msgstr "Battute" -#: editor.cc:121 editor.cc:3619 +#: editor.cc:124 editor.cc:3647 msgid "Marks" msgstr "Marcatori" -#: editor.cc:122 editor.cc:141 editor.cc:3621 editor.cc:3687 +#: editor.cc:125 editor.cc:144 editor.cc:3649 editor.cc:3715 msgid "Edit Cursor" msgstr "Cursore di modifica" -#: editor.cc:123 editor.cc:3623 +#: editor.cc:126 editor.cc:3651 msgid "Region starts" msgstr "Regioni/inizio" -#: editor.cc:124 editor.cc:3625 +#: editor.cc:127 editor.cc:3653 msgid "Region ends" msgstr "Regioni/fine" -#: editor.cc:125 editor.cc:3629 +#: editor.cc:128 editor.cc:3657 msgid "Region syncs" msgstr "Regioni/sincronizzazione" -#: editor.cc:126 editor.cc:3627 +#: editor.cc:129 editor.cc:3655 msgid "Region bounds" msgstr "Regioni/confini" -#: editor.cc:132 editor.cc:3662 +#: editor.cc:135 editor.cc:3690 msgid "Magnetic" msgstr "Magnetico" -#: editor.cc:137 editor.cc:3679 export_dialog.cc:140 export_dialog.cc:156 +#: editor.cc:140 editor.cc:3707 export_dialog.cc:140 export_dialog.cc:156 #: export_dialog.cc:1068 export_dialog.cc:1072 msgid "Left" msgstr "Sinistra" -#: editor.cc:138 editor.cc:3681 export_dialog.cc:141 export_dialog.cc:157 +#: editor.cc:141 editor.cc:3709 export_dialog.cc:141 export_dialog.cc:157 msgid "Right" msgstr "Destra" -#: editor.cc:139 editor.cc:3683 +#: editor.cc:142 editor.cc:3711 msgid "Center" msgstr "Centro" -#: editor.cc:140 editor.cc:3685 +#: editor.cc:143 editor.cc:3713 msgid "Playhead" msgstr "Inizio" #. time display buttons -#: editor.cc:183 +#: editor.cc:186 msgid "Mins:Secs" msgstr "Min:Sec" -#: editor.cc:186 editor_rulers.cc:353 +#: editor.cc:189 editor_rulers.cc:354 msgid "Frames" msgstr "" -#: editor.cc:187 editor_rulers.cc:373 +#: editor.cc:190 editor_rulers.cc:374 msgid "Tempo" msgstr "" -#: editor.cc:188 editor_rulers.cc:367 +#: editor.cc:191 editor_rulers.cc:368 msgid "Meter" msgstr "" -#: editor.cc:189 editor_rulers.cc:379 +#: editor.cc:192 editor_rulers.cc:380 msgid "Location Markers" msgstr "Marcatori di posizione" -#: editor.cc:190 editor_rulers.cc:385 +#: editor.cc:193 editor_rulers.cc:386 msgid "Range Markers" msgstr "Marcatori di intervallo" -#: editor.cc:191 editor_rulers.cc:391 +#: editor.cc:194 editor_rulers.cc:392 msgid "Loop/Punch Ranges" msgstr "Intervalli di Loop/Punch" -#: editor.cc:213 +#: editor.cc:216 msgid "range" msgstr "intervallo" -#: editor.cc:214 +#: editor.cc:217 msgid "object" msgstr "oggetto" -#: editor.cc:216 +#: editor.cc:219 msgid "zoom" msgstr "" -#: editor.cc:217 +#: editor.cc:220 msgid "timefx" msgstr "" -#: editor.cc:218 +#: editor.cc:221 msgid "listen" msgstr "" -#: editor.cc:220 +#: editor.cc:223 msgid "mode" msgstr "modo" -#: editor.cc:221 +#: editor.cc:224 msgid "automation" msgstr "automazione" -#: editor.cc:223 +#: editor.cc:226 msgid "Edit Mode" msgstr "Modalità di modifica" -#: editor.cc:224 editor_actions.cc:283 +#: editor.cc:227 editor_actions.cc:284 msgid "Snap To" msgstr "Allinea a" -#: editor.cc:225 +#: editor.cc:228 msgid "Snap Mode" msgstr "Modalita' di Allineamento" -#: editor.cc:226 +#: editor.cc:229 msgid "Zoom Focus" msgstr "" #. #. nudge -#: editor.cc:234 editor.cc:1907 editor.cc:2073 editor.cc:2129 +#: editor.cc:237 editor.cc:1900 editor.cc:2066 editor.cc:2122 msgid "Nudge" msgstr "Sposta" -#: editor.cc:466 +#: editor.cc:470 msgid "Zoom in" msgstr "Zoom avanti" -#: editor.cc:467 +#: editor.cc:471 msgid "Zoom out" msgstr "Zoom indietro" -#: editor.cc:470 +#: editor.cc:474 msgid "Zoom to session" msgstr "Zoom alla selezione" -#: editor.cc:485 +#: editor.cc:489 msgid "Zoom Span" msgstr "" -#: editor.cc:498 editor.cc:524 editor_actions.cc:61 mixer_ui.cc:85 +#: editor.cc:502 editor.cc:528 editor_actions.cc:62 mixer_ui.cc:86 +#: mixer_ui.cc:112 #, fuzzy msgid "Visible" msgstr "visibile" -#: editor.cc:499 editor.cc:522 +#: editor.cc:503 editor.cc:526 #, fuzzy msgid "Name" msgstr "Rinomina" -#: editor.cc:595 editor.cc:661 +#: editor.cc:602 editor.cc:669 #, fuzzy msgid "Regions" msgstr "Regione" -#: editor.cc:634 editor.cc:673 +#: editor.cc:642 editor.cc:681 msgid "Chunks" msgstr "Spezzoni" -#: editor.cc:664 +#: editor.cc:672 #, fuzzy msgid "Tracks/Busses" msgstr "Tracce/Bus" -#: editor.cc:667 +#: editor.cc:675 msgid "Snapshots" msgstr "Istantanee" -#: editor.cc:670 +#: editor.cc:678 msgid "Edit Groups" msgstr "Modifica Gruppi" -#: editor.cc:719 +#: editor.cc:727 msgid "Nudge region/selection forwards" msgstr "Sposta regione/selezione in avanti" -#: editor.cc:720 +#: editor.cc:728 msgid "Nudge region/selection backwards" msgstr "Sposta regione/selezione indietro" -#: editor.cc:727 editor_mixer.cc:298 +#: editor.cc:735 editor_mixer.cc:299 msgid "ardour: editor" msgstr "" -#: editor.cc:728 +#: editor.cc:736 msgid "ardour_editor" msgstr "" -#: editor.cc:1190 +#: editor.cc:1183 msgid "ardour: editor: " msgstr "" #. force name -#: editor.cc:1275 editor.cc:1284 editor_markers.cc:869 +#: editor.cc:1268 editor.cc:1277 editor_markers.cc:870 msgid "Loop" msgstr "" #. force name -#: editor.cc:1289 editor.cc:1298 editor_markers.cc:895 +#: editor.cc:1282 editor.cc:1291 editor_markers.cc:896 msgid "Punch" msgstr "" -#: editor.cc:1446 editor_mouse.cc:1721 +#: editor.cc:1439 editor_mouse.cc:1742 msgid "programming error: fade in canvas item has no regionview data pointer!" msgstr "" -#: editor.cc:1458 editor.cc:1475 redirect_box.cc:1071 +#: editor.cc:1451 editor.cc:1468 redirect_box.cc:1073 msgid "Deactivate" msgstr "Disattiva" #. activation -#: editor.cc:1460 editor.cc:1477 redirect_box.cc:1069 +#: editor.cc:1453 editor.cc:1470 redirect_box.cc:1071 msgid "Activate" msgstr "Attiva" -#: editor.cc:1465 editor.cc:1482 +#: editor.cc:1458 editor.cc:1475 msgid "Linear" msgstr "Lineare" -#: editor.cc:1466 editor.cc:1483 editor_actions.cc:375 +#: editor.cc:1459 editor.cc:1476 editor_actions.cc:376 msgid "Slowest" msgstr "Piu' Lento" -#: editor.cc:1467 editor.cc:1484 editor_actions.cc:376 +#: editor.cc:1460 editor.cc:1477 editor_actions.cc:377 msgid "Slow" msgstr "Lento" -#: editor.cc:1468 editor.cc:1485 editor_actions.cc:378 +#: editor.cc:1461 editor.cc:1478 editor_actions.cc:379 msgid "Fast" msgstr "Veloce" -#: editor.cc:1469 editor.cc:1486 editor_actions.cc:380 +#: editor.cc:1462 editor.cc:1479 editor_actions.cc:381 msgid "Fastest" msgstr "Più Veloce" -#: editor.cc:1596 editor.cc:1604 +#: editor.cc:1589 editor.cc:1597 msgid "Freeze" msgstr "" -#: editor.cc:1600 +#: editor.cc:1593 msgid "Unfreeze" msgstr "" -#: editor.cc:1769 editor.cc:1864 +#: editor.cc:1762 editor.cc:1857 #, fuzzy msgid "Unmute" msgstr "muto" #. non-operative menu items for menu bar #. show editors -#: editor.cc:1773 editor.cc:2053 editor.cc:2755 editor_actions.cc:26 -#: editor_markers.cc:506 mixer_strip.cc:512 mixer_strip.cc:572 -#: redirect_box.cc:1077 +#: editor.cc:1766 editor.cc:2046 editor.cc:2748 editor_actions.cc:27 +#: editor_markers.cc:507 mixer_strip.cc:495 mixer_strip.cc:563 +#: redirect_box.cc:1079 msgid "Edit" msgstr "Modifica" -#: editor.cc:1778 +#: editor.cc:1771 msgid "Convert to short" msgstr "" -#: editor.cc:1780 +#: editor.cc:1773 msgid "Convert to full" msgstr "" -#: editor.cc:1791 +#: editor.cc:1784 #, fuzzy msgid "Crossfade" msgstr "Smorzamento Incrociato" -#: editor.cc:1834 +#: editor.cc:1827 msgid "Popup region editor" msgstr "Mostra l'editor di regione" -#: editor.cc:1835 +#: editor.cc:1828 #, fuzzy msgid "Raise to top layer" msgstr "Porta la regione al primo livello" -#: editor.cc:1836 +#: editor.cc:1829 #, fuzzy msgid "Lower to bottom layer" msgstr "Porta la regione all'ultimo livello" -#: editor.cc:1838 +#: editor.cc:1831 msgid "Define sync point" msgstr "Definisci il punto di sincronizzazione" -#: editor.cc:1839 +#: editor.cc:1832 msgid "Remove sync point" msgstr "Rimuovi il punto di sincronizzazione" -#: editor.cc:1844 +#: editor.cc:1837 #, fuzzy msgid "Bounce" msgstr "Fai il Bounce dell'intervallo" -#: editor.cc:1847 +#: editor.cc:1840 #, fuzzy msgid "Analyze region" msgstr "Suona la Regione" -#: editor.cc:1859 +#: editor.cc:1852 msgid "Lock" msgstr "Blocca" -#: editor.cc:1860 +#: editor.cc:1853 msgid "Unlock" msgstr "Sblocca" -#: editor.cc:1870 +#: editor.cc:1863 msgid "Original position" msgstr "Posizione originale" -#: editor.cc:1876 +#: editor.cc:1869 msgid "Toggle envelope visibility" msgstr "" -#: editor.cc:1877 +#: editor.cc:1870 #, fuzzy msgid "Toggle envelope active" msgstr "attivo/passivo" -#: editor.cc:1881 +#: editor.cc:1874 #, fuzzy msgid "DeNormalize" msgstr "Normalizza" -#: editor.cc:1883 +#: editor.cc:1876 msgid "Normalize" msgstr "Normalizza" -#: editor.cc:1886 +#: editor.cc:1879 msgid "Reverse" msgstr "" #. range related stuff -#: editor.cc:1892 +#: editor.cc:1885 #, fuzzy msgid "Add Range Markers" msgstr "Marcatori di intervallo" -#: editor.cc:1893 +#: editor.cc:1886 #, fuzzy msgid "Set Range" msgstr "Separa l'intervallo" -#: editor.cc:1902 +#: editor.cc:1895 #, fuzzy msgid "Nudge fwd" msgstr "Sposta" -#: editor.cc:1903 +#: editor.cc:1896 #, fuzzy msgid "Nudge bwd" msgstr "Sposta" -#: editor.cc:1904 +#: editor.cc:1897 msgid "Nudge fwd by capture offset" msgstr "" -#: editor.cc:1905 +#: editor.cc:1898 msgid "Nudge bwd by capture offset" msgstr "" -#: editor.cc:1914 +#: editor.cc:1907 msgid "Start to edit cursor" msgstr "Inizio al cursore di modifica" -#: editor.cc:1915 +#: editor.cc:1908 msgid "Edit cursor to end" msgstr "Cursore di modifica alla fine" -#: editor.cc:1917 +#: editor.cc:1910 gain_meter.cc:181 gain_meter.cc:813 panner_ui.cc:98 +#: panner_ui.cc:803 msgid "Trim" msgstr "" -#: editor.cc:1920 +#: editor.cc:1913 msgid "Split" msgstr "Dividi" -#: editor.cc:1923 +#: editor.cc:1916 msgid "Make mono regions" msgstr "Crea regioni mono" -#: editor.cc:1926 +#: editor.cc:1919 msgid "Duplicate" msgstr "Duplica" -#: editor.cc:1927 +#: editor.cc:1920 msgid "Fill Track" msgstr "Riempi Traccia" -#: editor.cc:1931 +#: editor.cc:1924 msgid "Destroy" msgstr "Distruggi" -#: editor.cc:1961 +#: editor.cc:1954 msgid "Play range" msgstr "Suona l'intervallo" -#: editor.cc:1962 +#: editor.cc:1955 msgid "Loop range" msgstr "Intervallo di loop" -#: editor.cc:1966 +#: editor.cc:1959 #, fuzzy msgid "Analyze range" msgstr "Suona l'intervallo" -#: editor.cc:1970 +#: editor.cc:1963 #, fuzzy msgid "Separate range to track" msgstr "Separa l'intervallo" -#: editor.cc:1971 +#: editor.cc:1964 #, fuzzy msgid "Separate range to region list" msgstr "Esegui la regione selezionata come loop" -#: editor.cc:1974 +#: editor.cc:1967 #, fuzzy msgid "Select all in range" msgstr "Seleziona tutto nella traccia" -#: editor.cc:1976 editor.cc:2021 +#: editor.cc:1969 editor.cc:2014 #, fuzzy msgid "Set range to loop range" msgstr "Seleziona l'intervallo di loop" -#: editor.cc:1977 editor.cc:2022 +#: editor.cc:1970 editor.cc:2015 #, fuzzy msgid "Set range to punch range" msgstr "Seleziona l'intervallo di punch" -#: editor.cc:1979 +#: editor.cc:1972 #, fuzzy msgid "Crop region to range" msgstr "Ridimensiona la Regione alla selezione" -#: editor.cc:1980 +#: editor.cc:1973 #, fuzzy msgid "Fill range with region" msgstr "Riempi intervallo con Regione" -#: editor.cc:1981 +#: editor.cc:1974 #, fuzzy msgid "Duplicate range" msgstr "Duplica" -#: editor.cc:1982 +#: editor.cc:1975 msgid "Create chunk from range" msgstr "Crea uno spezzone dall'intervallo" -#: editor.cc:1984 +#: editor.cc:1977 msgid "Bounce range" msgstr "Fai il Bounce dell'intervallo" -#: editor.cc:1985 +#: editor.cc:1978 #, fuzzy msgid "Export range" msgstr "Esporta regione" -#: editor.cc:1987 +#: editor.cc:1980 msgid "Range" msgstr "Intervallo" -#: editor.cc:2002 editor.cc:2087 +#: editor.cc:1995 editor.cc:2080 msgid "Play from edit cursor" msgstr "Suona dal cursore di modifica" -#: editor.cc:2003 editor.cc:2088 +#: editor.cc:1996 editor.cc:2081 msgid "Play from start" msgstr "Suona dall'inizio" -#: editor.cc:2004 +#: editor.cc:1997 #, fuzzy msgid "Play region" msgstr "Suona la Regione" -#: editor.cc:2006 +#: editor.cc:1999 msgid "Loop Region" msgstr "Regione in loop" -#: editor.cc:2008 editor.cc:2089 sfdb_ui.cc:56 -msgid "Play" -msgstr "Suona" - -#: editor.cc:2016 editor.cc:2097 +#: editor.cc:2009 editor.cc:2090 msgid "Select All in track" msgstr "Seleziona tutto nella traccia" -#: editor.cc:2017 editor.cc:2098 redirect_box.cc:1065 +#: editor.cc:2010 editor.cc:2091 redirect_box.cc:1067 msgid "Select All" msgstr "Seleziona tutto" -#: editor.cc:2018 editor.cc:2099 +#: editor.cc:2011 editor.cc:2092 #, fuzzy msgid "Invert selection in track" msgstr "Inerti nella traccia" -#: editor.cc:2019 editor.cc:2100 +#: editor.cc:2012 editor.cc:2093 #, fuzzy msgid "Invert selection" msgstr "Esegui la regione selezionata come loop" -#: editor.cc:2024 editor.cc:2102 +#: editor.cc:2017 editor.cc:2095 #, fuzzy msgid "Select all after edit cursor" msgstr "Inizio al cursore di modifica" -#: editor.cc:2025 editor.cc:2103 +#: editor.cc:2018 editor.cc:2096 #, fuzzy msgid "Select all before edit cursor" msgstr "Inizio al cursore di modifica" -#: editor.cc:2026 editor.cc:2104 +#: editor.cc:2019 editor.cc:2097 #, fuzzy msgid "Select all after playhead" msgstr "Imposta dall'inizio" -#: editor.cc:2027 editor.cc:2105 +#: editor.cc:2020 editor.cc:2098 #, fuzzy msgid "Select all before playhead" msgstr "Imposta dall'inizio" -#: editor.cc:2028 +#: editor.cc:2021 #, fuzzy msgid "Select all between cursors" msgstr "Inizio al cursore di modifica" #. standard editing stuff -#: editor.cc:2039 editor.cc:2115 editor.cc:3455 editor_actions.cc:213 -#: redirect_box.cc:1058 +#: editor.cc:2032 editor.cc:2108 editor.cc:3483 editor_actions.cc:214 +#: redirect_box.cc:1060 msgid "Cut" msgstr "Taglia" -#: editor.cc:2040 editor.cc:2116 editor.cc:3457 editor_actions.cc:218 -#: redirect_box.cc:1060 +#: editor.cc:2033 editor.cc:2109 editor.cc:3485 editor_actions.cc:219 +#: redirect_box.cc:1062 msgid "Copy" msgstr "Copia" -#: editor.cc:2041 +#: editor.cc:2034 #, fuzzy msgid "Paste at edit cursor" msgstr "Inizio al cursore di modifica" -#: editor.cc:2042 +#: editor.cc:2035 #, fuzzy msgid "Paste at mouse" msgstr "utilizza le uscite master" -#: editor.cc:2046 editor.cc:3462 +#: editor.cc:2039 editor.cc:3490 msgid "Align" msgstr "Allinea" -#: editor.cc:2047 editor.cc:3464 +#: editor.cc:2040 editor.cc:3492 msgid "Align Relative" msgstr "Allinea Realtivo" -#: editor.cc:2051 +#: editor.cc:2044 msgid "Insert chunk" msgstr "Inserisci lo Spezzone" -#: editor.cc:2058 +#: editor.cc:2051 #, fuzzy msgid "Insert Selected Region" msgstr "Esegui la regione selezionata come loop" -#: editor.cc:2059 +#: editor.cc:2052 msgid "Insert Existing Audio" msgstr "" -#: editor.cc:2068 editor.cc:2124 +#: editor.cc:2061 editor.cc:2117 msgid "Nudge entire track fwd" msgstr "Sposta l'intera traccia in avanti" -#: editor.cc:2069 editor.cc:2125 +#: editor.cc:2062 editor.cc:2118 msgid "Nudge track after edit cursor fwd" msgstr "Avanza la traccia dopo il cursore di modifica" -#: editor.cc:2070 editor.cc:2126 +#: editor.cc:2063 editor.cc:2119 msgid "Nudge entire track bwd" msgstr "Arretra l'intera traccia" -#: editor.cc:2071 editor.cc:2127 +#: editor.cc:2064 editor.cc:2120 msgid "Nudge track after edit cursor bwd" msgstr "Arretra la traccia dopo il cursore di modifica" -#: editor.cc:2117 editor.cc:3459 editor_actions.cc:220 redirect_box.cc:1062 +#: editor.cc:2110 editor.cc:3487 editor_actions.cc:221 redirect_box.cc:1064 msgid "Paste" msgstr "Incolla" -#: editor.cc:2637 +#: editor.cc:2630 msgid "select/move objects" msgstr "seleziona/muovi gli oggetti" -#: editor.cc:2638 +#: editor.cc:2631 msgid "select/move ranges" msgstr "seleziona/muovi range" -#: editor.cc:2639 +#: editor.cc:2632 msgid "draw gain automation" msgstr "disegna l'automazione gain" -#: editor.cc:2640 +#: editor.cc:2633 msgid "select zoom range" msgstr "seleziona l'intervallo di zoom" -#: editor.cc:2641 +#: editor.cc:2634 msgid "stretch/shrink regions" msgstr "allunga/restringi le regioni" -#: editor.cc:2642 +#: editor.cc:2635 #, fuzzy msgid "listen to specific regions" msgstr "Esegui la regione selezionata come loop" -#: editor.cc:2753 +#: editor.cc:2746 msgid "Start:" msgstr "Inizio:" -#: editor.cc:2754 +#: editor.cc:2747 msgid "End:" msgstr "Fine:" -#: editor.cc:3097 -#, fuzzy -msgid "set selected trackview" -msgstr "Inserisci selezione" - -#: editor.cc:3137 -#, fuzzy -msgid "set selected control point" -msgstr "Rimuovi il punto di sincronizzazione" - -#: editor.cc:3246 -#, fuzzy -msgid "set selected regionview" -msgstr "Esegui la regione selezionata come loop" - -#: editor.cc:3334 editor.cc:3374 +#: editor.cc:3362 editor.cc:3402 #, fuzzy msgid "set selected regions" msgstr "Esegui la regione selezionata come loop" -#: editor.cc:3430 editor_actions.cc:203 +#: editor.cc:3458 editor_actions.cc:204 msgid "Undo" msgstr "Annulla" -#: editor.cc:3432 +#: editor.cc:3460 msgid "Undo (%1)" msgstr "Annulla (%1)" -#: editor.cc:3442 editor_actions.cc:205 +#: editor.cc:3470 editor_actions.cc:206 msgid "Redo" msgstr "Ripristina" -#: editor.cc:3444 +#: editor.cc:3472 msgid "Redo (%1)" msgstr "Ripristina (%1)" -#: editor.cc:3478 +#: editor.cc:3506 msgid "... as new track" msgstr "" -#: editor.cc:3479 +#: editor.cc:3507 #, fuzzy msgid "... as new region" msgstr "Sposta Regione/i" -#: editor.cc:3481 +#: editor.cc:3509 msgid "Import audio (copy)" msgstr "Importa audio (copia)" -#: editor.cc:3484 +#: editor.cc:3512 msgid "Remove last capture" msgstr "Rimuovi l'ultima registrazione" -#: editor.cc:3508 +#: editor.cc:3536 msgid "Duplicate how many times?" msgstr "Quante volte duplico?" -#: editor.cc:3994 +#: editor.cc:4022 msgid "" "Playlist %1 is currently unused.\n" "If left alone, no audio files used by it will be cleaned.\n" "If deleted, audio files used by it alone by will cleaned." msgstr "" -#: editor.cc:4002 +#: editor.cc:4030 msgid "Delete playlist" msgstr "" -#: editor.cc:4003 +#: editor.cc:4031 msgid "Keep playlist" msgstr "" -#: editor.cc:4004 editor_audio_import.cc:237 editor_ops.cc:1976 -#: editor_timefx.cc:52 export_dialog.cc:971 io_selector.cc:58 -#: io_selector.cc:792 redirect_box.cc:901 tempo_dialog.cc:19 -#: tempo_dialog.cc:36 tempo_dialog.cc:152 tempo_dialog.cc:170 +#: editor.cc:4032 editor_audio_import.cc:236 editor_ops.cc:2048 +#: editor_timefx.cc:71 export_dialog.cc:971 io_selector.cc:59 +#: io_selector.cc:793 redirect_box.cc:903 tempo_dialog.cc:20 +#: tempo_dialog.cc:37 tempo_dialog.cc:202 tempo_dialog.cc:220 msgid "Cancel" msgstr "Cancella" -#: editor.cc:4171 +#: editor.cc:4199 #, fuzzy msgid "new playlists" msgstr "azzera le posizioni" -#: editor.cc:4179 +#: editor.cc:4207 #, fuzzy msgid "copy playlists" msgstr "azzera le posizioni" -#: editor.cc:4187 +#: editor.cc:4215 #, fuzzy msgid "clear playlists" msgstr "azzera le posizioni" -#: editor_actions.cc:27 +#: editor_actions.cc:28 #, fuzzy msgid "Select regions" msgstr "Esegui la regione selezionata come loop" -#: editor_actions.cc:28 +#: editor_actions.cc:29 #, fuzzy msgid "Select range operations" msgstr "Esegui la regione selezionata come loop" -#: editor_actions.cc:29 +#: editor_actions.cc:30 #, fuzzy msgid "Move edit cursor" msgstr "Inizio al cursore di modifica" -#: editor_actions.cc:30 +#: editor_actions.cc:31 #, fuzzy msgid "Region operations" msgstr "Regioni/creazione" -#: editor_actions.cc:31 +#: editor_actions.cc:32 msgid "Tools" msgstr "" -#: editor_actions.cc:32 +#: editor_actions.cc:33 msgid "View" msgstr "" -#: editor_actions.cc:33 +#: editor_actions.cc:34 #, fuzzy msgid "ZoomFocus" msgstr "Zoom indietro" -#: editor_actions.cc:34 +#: editor_actions.cc:35 msgid "Meter hold" msgstr "" -#: editor_actions.cc:35 +#: editor_actions.cc:36 msgid "Meter falloff" msgstr "" -#: editor_actions.cc:37 +#: editor_actions.cc:38 #, fuzzy msgid "Crossfades" msgstr "Smorzamento Incrociato" -#: editor_actions.cc:38 +#: editor_actions.cc:39 #, fuzzy msgid "Monitoring" msgstr "Usa il Monitoraggio Hardware" -#: editor_actions.cc:39 +#: editor_actions.cc:40 #, fuzzy msgid "Autoconnect" msgstr "Connetti" -#: editor_actions.cc:40 +#: editor_actions.cc:41 #, fuzzy msgid "Layering" msgstr "Livello" -#: editor_actions.cc:41 +#: editor_actions.cc:42 #, fuzzy msgid "Metering" msgstr "Usa il Monitoraggio Hardware" -#: editor_actions.cc:42 +#: editor_actions.cc:43 msgid "Fall off rate" msgstr "" -#: editor_actions.cc:43 +#: editor_actions.cc:44 msgid "Hold Time" msgstr "" -#: editor_actions.cc:44 +#: editor_actions.cc:45 msgid "Add Existing Audio" msgstr "" #. add named actions for the editor -#: editor_actions.cc:49 +#: editor_actions.cc:50 #, fuzzy msgid "Show Editor Mixer" msgstr "Mostra tutte le Tracce del Mixer" -#: editor_actions.cc:54 +#: editor_actions.cc:55 #, fuzzy msgid "Span Entire Overlap" msgstr "Porta la regione su di un livello" -#: editor_actions.cc:56 editor_actions.cc:383 +#: editor_actions.cc:57 editor_actions.cc:384 #, fuzzy msgid "Short" msgstr "entrata" -#: editor_actions.cc:63 +#: editor_actions.cc:64 msgid "Created Automatically" msgstr "" -#: editor_actions.cc:66 +#: editor_actions.cc:67 msgid "Playhead to Next Region Start" msgstr "" -#: editor_actions.cc:68 +#: editor_actions.cc:69 msgid "Playhead to Next Region End" msgstr "" -#: editor_actions.cc:70 +#: editor_actions.cc:71 msgid "Playhead to Next Region Sync" msgstr "" -#: editor_actions.cc:73 +#: editor_actions.cc:74 msgid "Playhead to Previous Region Start" msgstr "" -#: editor_actions.cc:75 +#: editor_actions.cc:76 msgid "Playhead to Previous Region End" msgstr "" -#: editor_actions.cc:77 +#: editor_actions.cc:78 msgid "Playhead to Previous Region Sync" msgstr "" -#: editor_actions.cc:80 +#: editor_actions.cc:81 #, fuzzy msgid "Edit Cursor to Next Region Start" msgstr "Cursore di modifica alla fine" -#: editor_actions.cc:82 +#: editor_actions.cc:83 #, fuzzy msgid "Edit Cursor to Next Region End" msgstr "Cursore di modifica alla fine" -#: editor_actions.cc:84 +#: editor_actions.cc:85 #, fuzzy msgid "Edit Cursor to Next Region Sync" msgstr "Cursore di modifica alla fine" -#: editor_actions.cc:87 +#: editor_actions.cc:88 msgid "Edit Cursor to Previous Region Start" msgstr "" -#: editor_actions.cc:89 +#: editor_actions.cc:90 #, fuzzy msgid "Edit Cursor to Previous Region End" msgstr "Cursore di modifica alla fine" -#: editor_actions.cc:91 +#: editor_actions.cc:92 #, fuzzy msgid "Edit Cursor to Previous Region Sync" msgstr "Cursore di modifica alla fine" -#: editor_actions.cc:94 +#: editor_actions.cc:95 msgid "Playhead to Range Start" msgstr "" -#: editor_actions.cc:96 +#: editor_actions.cc:97 #, fuzzy msgid "Playhead to Range End" msgstr "Suona l'intervallo di loop" -#: editor_actions.cc:99 +#: editor_actions.cc:100 #, fuzzy msgid "Edit Cursor to Range Start" msgstr "Cursore di modifica alla fine" -#: editor_actions.cc:101 +#: editor_actions.cc:102 #, fuzzy msgid "Edit Cursor to Range End" msgstr "Cursore di modifica alla fine" -#: editor_actions.cc:104 editor_ops.cc:1300 +#: editor_actions.cc:105 editor_ops.cc:1363 #, fuzzy msgid "select all" msgstr "Seleziona tutto" -#: editor_actions.cc:106 +#: editor_actions.cc:107 #, fuzzy msgid "Select All After Edit Cursor" msgstr "Suona dal cursore di modifica" -#: editor_actions.cc:108 +#: editor_actions.cc:109 msgid "Select All Before Edit Cursor" msgstr "" -#: editor_actions.cc:111 +#: editor_actions.cc:112 #, fuzzy msgid "Select All After Playhead" msgstr "Imposta dall'inizio" -#: editor_actions.cc:113 +#: editor_actions.cc:114 #, fuzzy msgid "Select All Before Playhead" msgstr "Imposta dall'inizio" -#: editor_actions.cc:115 +#: editor_actions.cc:116 #, fuzzy msgid "Select All Between Cursors" msgstr "Suona dal cursore di modifica" -#: editor_actions.cc:118 +#: editor_actions.cc:119 #, fuzzy msgid "Select All in Punch Range" msgstr "Imposta l'intervallo di Punch" -#: editor_actions.cc:120 +#: editor_actions.cc:121 #, fuzzy msgid "Select All in Loop Range" msgstr "Seleziona l'intervallo di loop" -#: editor_actions.cc:123 +#: editor_actions.cc:124 msgid "Jump Forward to Mark" msgstr "" -#: editor_actions.cc:125 +#: editor_actions.cc:126 msgid "Jump Backward to Mark" msgstr "" -#: editor_actions.cc:127 +#: editor_actions.cc:128 #, fuzzy msgid "Add Location from Playhead" msgstr "Imposta dall'inizio" -#: editor_actions.cc:130 +#: editor_actions.cc:131 #, fuzzy msgid "Nudge Forward" msgstr "Sposta" -#: editor_actions.cc:132 +#: editor_actions.cc:133 #, fuzzy msgid "Nudge Next Forward" msgstr "Sposta regione/selezione in avanti" -#: editor_actions.cc:134 +#: editor_actions.cc:135 #, fuzzy msgid "Nudge Backward" msgstr "Sposta" -#: editor_actions.cc:136 +#: editor_actions.cc:137 #, fuzzy msgid "Nudge Next Backward" msgstr "Sposta l'intera traccia in avanti" -#: editor_actions.cc:139 +#: editor_actions.cc:140 #, fuzzy msgid "Zoom Out" msgstr "Zoom indietro" -#: editor_actions.cc:141 +#: editor_actions.cc:142 #, fuzzy msgid "Zoom In" msgstr "Zoom avanti" -#: editor_actions.cc:143 +#: editor_actions.cc:144 #, fuzzy msgid "Zoom to Session" msgstr "Zoom alla selezione" -#: editor_actions.cc:146 +#: editor_actions.cc:147 #, fuzzy msgid "Scroll Tracks Up" msgstr "Riempi Traccia" -#: editor_actions.cc:148 +#: editor_actions.cc:149 msgid "Scroll Tracks Down" msgstr "" -#: editor_actions.cc:150 +#: editor_actions.cc:151 #, fuzzy msgid "Step Tracks Up" msgstr "Nascondi traccia" -#: editor_actions.cc:152 +#: editor_actions.cc:153 msgid "Step Tracks Down" msgstr "" -#: editor_actions.cc:155 +#: editor_actions.cc:156 msgid "Scroll Backward" msgstr "" -#: editor_actions.cc:157 +#: editor_actions.cc:158 msgid "Scroll Forward" msgstr "" -#: editor_actions.cc:159 +#: editor_actions.cc:160 msgid "goto" msgstr "" -#: editor_actions.cc:161 +#: editor_actions.cc:162 #, fuzzy msgid "Center Playhead" msgstr "Inizio" -#: editor_actions.cc:163 +#: editor_actions.cc:164 #, fuzzy msgid "Center Edit Cursor" msgstr "Cursore di modifica" -#: editor_actions.cc:165 +#: editor_actions.cc:166 #, fuzzy msgid "Playhead Forward" msgstr "Inizio" -#: editor_actions.cc:167 +#: editor_actions.cc:168 #, fuzzy msgid "Playhead Backward" msgstr "Inizio" -#: editor_actions.cc:169 +#: editor_actions.cc:170 #, fuzzy msgid "Playhead to Edit" msgstr "Inizio" -#: editor_actions.cc:171 +#: editor_actions.cc:172 #, fuzzy msgid "Edit to Playhead" msgstr "Imposta dall'inizio" -#: editor_actions.cc:174 +#: editor_actions.cc:175 #, fuzzy msgid "Align Regions Start" msgstr "Regioni/inizio" -#: editor_actions.cc:176 +#: editor_actions.cc:177 #, fuzzy msgid "Align Regions Start Relative" msgstr "Allinea Realtivo" -#: editor_actions.cc:178 +#: editor_actions.cc:179 #, fuzzy msgid "Align Regions End" msgstr "Sposta Regione/i" -#: editor_actions.cc:180 +#: editor_actions.cc:181 #, fuzzy msgid "Align Regions End Relative" msgstr "Allinea Realtivo" -#: editor_actions.cc:183 +#: editor_actions.cc:184 #, fuzzy msgid "Align Regions Sync" msgstr "Sposta Regione/i" -#: editor_actions.cc:185 +#: editor_actions.cc:186 #, fuzzy msgid "Align Regions Sync Relative" msgstr "Allinea Realtivo" -#: editor_actions.cc:188 +#: editor_actions.cc:189 msgid "Audition at Mouse" msgstr "" -#: editor_actions.cc:190 +#: editor_actions.cc:191 #, fuzzy msgid "Brush at Mouse" msgstr "utilizza le uscite master" -#: editor_actions.cc:192 +#: editor_actions.cc:193 #, fuzzy msgid "Set Edit Cursor" msgstr "Cursore di modifica" -#: editor_actions.cc:194 +#: editor_actions.cc:195 #, fuzzy msgid "Mute/Unmute Region" msgstr "Crea una Regione" -#: editor_actions.cc:196 +#: editor_actions.cc:197 #, fuzzy msgid "Set Playhead" msgstr "Inizio" -#: editor_actions.cc:198 +#: editor_actions.cc:199 #, fuzzy msgid "Split Region" msgstr "Separa la Regione" -#: editor_actions.cc:200 +#: editor_actions.cc:201 #, fuzzy msgid "Set Region Sync Position" msgstr "Per Posizione della Regione" -#: editor_actions.cc:208 +#: editor_actions.cc:209 #, fuzzy msgid "Export Session" msgstr "Esporta regione" -#: editor_actions.cc:210 +#: editor_actions.cc:211 #, fuzzy msgid "Export Range" msgstr "Separa l'intervallo" #. Note: for now, editor-delete does the exact same thing as editor-cut -#: editor_actions.cc:216 +#: editor_actions.cc:217 #, fuzzy msgid "Delete" msgstr "Elimina" -#: editor_actions.cc:222 +#: editor_actions.cc:223 #, fuzzy msgid "Duplicate Region" msgstr "Esegui la regione selezionata come loop" -#: editor_actions.cc:224 +#: editor_actions.cc:225 #, fuzzy msgid "Duplicate Range" msgstr "Duplica" -#: editor_actions.cc:226 +#: editor_actions.cc:227 msgid "Insert Region" msgstr "Inserisci la Regione" -#: editor_actions.cc:228 +#: editor_actions.cc:229 #, fuzzy msgid "Reverse Region" msgstr "fai il Reverse della regione" -#: editor_actions.cc:230 +#: editor_actions.cc:231 #, fuzzy msgid "Normalize Region" msgstr "Normalizza" -#: editor_actions.cc:232 +#: editor_actions.cc:233 #, fuzzy msgid "crop" msgstr "copia" -#: editor_actions.cc:234 +#: editor_actions.cc:235 #, fuzzy msgid "Insert Chunk" msgstr "Inserisci lo Spezzone" -#: editor_actions.cc:237 +#: editor_actions.cc:238 #, fuzzy msgid "Split at edit cursor" msgstr "Inizio al cursore di modifica" -#: editor_actions.cc:240 +#: editor_actions.cc:241 #, fuzzy msgid "Start Range" msgstr "Separa l'intervallo" -#: editor_actions.cc:242 +#: editor_actions.cc:243 msgid "Finish Range" msgstr "" -#: editor_actions.cc:244 +#: editor_actions.cc:245 msgid "Finish add Range" msgstr "" -#: editor_actions.cc:247 +#: editor_actions.cc:248 msgid "Extend Range to End of Region" msgstr "" -#: editor_actions.cc:249 +#: editor_actions.cc:250 #, fuzzy msgid "Extend Range to Start of Region" msgstr "Vai all'inizio della sessione" -#: editor_actions.cc:252 +#: editor_actions.cc:253 #, fuzzy msgid "Follow Playhead" msgstr "Segui il cursore" -#: editor_actions.cc:260 +#: editor_actions.cc:261 #, fuzzy msgid "Zoom Focus Left" msgstr "Zoom indietro" -#: editor_actions.cc:262 +#: editor_actions.cc:263 #, fuzzy msgid "Zoom Focus Right" msgstr "Zoom indietro" -#: editor_actions.cc:264 +#: editor_actions.cc:265 #, fuzzy msgid "Zoom Focus Center" msgstr "Zoom indietro" -#: editor_actions.cc:266 +#: editor_actions.cc:267 msgid "Zoom Focus Playhead" msgstr "" -#: editor_actions.cc:268 +#: editor_actions.cc:269 #, fuzzy msgid "Zoom Focus Edit" msgstr "Zoom indietro" -#: editor_actions.cc:274 +#: editor_actions.cc:275 msgid "Object Tool" msgstr "" -#: editor_actions.cc:275 +#: editor_actions.cc:276 #, fuzzy msgid "Range Tool" msgstr "Intervallo" -#: editor_actions.cc:276 +#: editor_actions.cc:277 msgid "Gain Tool" msgstr "" -#: editor_actions.cc:277 +#: editor_actions.cc:278 #, fuzzy msgid "Zoom Tool" msgstr "Zoom indietro" -#: editor_actions.cc:278 +#: editor_actions.cc:279 msgid "Timefx Tool" msgstr "" -#: editor_actions.cc:285 +#: editor_actions.cc:286 #, fuzzy msgid "Snap to frame" msgstr "Modalita' di Allineamento" -#: editor_actions.cc:286 +#: editor_actions.cc:287 #, fuzzy msgid "Snap to cd frame" msgstr "Modalita' di Allineamento" -#: editor_actions.cc:287 +#: editor_actions.cc:288 msgid "Snap to SMPTE frame" msgstr "" -#: editor_actions.cc:288 +#: editor_actions.cc:289 msgid "Snap to SMPTE seconds" msgstr "" -#: editor_actions.cc:289 +#: editor_actions.cc:290 msgid "Snap to SMPTE minutes" msgstr "" -#: editor_actions.cc:290 +#: editor_actions.cc:291 #, fuzzy msgid "Snap to seconds" msgstr "Secondi" -#: editor_actions.cc:291 +#: editor_actions.cc:292 msgid "Snap to minutes" msgstr "" -#: editor_actions.cc:292 +#: editor_actions.cc:293 #, fuzzy msgid "Snap to thirtyseconds" msgstr "trentaduesimo (32)" -#: editor_actions.cc:293 +#: editor_actions.cc:294 msgid "Snap to asixteenthbeat" msgstr "" -#: editor_actions.cc:294 +#: editor_actions.cc:295 msgid "Snap to eighths" msgstr "" -#: editor_actions.cc:295 +#: editor_actions.cc:296 msgid "Snap to quarters" msgstr "" -#: editor_actions.cc:296 +#: editor_actions.cc:297 #, fuzzy msgid "Snap to thirds" msgstr "Modalita' di Allineamento" -#: editor_actions.cc:297 +#: editor_actions.cc:298 #, fuzzy msgid "Snap to beat" msgstr "Modalita' di Allineamento" -#: editor_actions.cc:298 +#: editor_actions.cc:299 #, fuzzy msgid "Snap to bar" msgstr "Allinea a" -#: editor_actions.cc:299 +#: editor_actions.cc:300 #, fuzzy msgid "Snap to mark" msgstr "agggiungi marcatore di intervallo" -#: editor_actions.cc:300 +#: editor_actions.cc:301 #, fuzzy msgid "Snap to edit cursor" msgstr "Inizio al cursore di modifica" -#: editor_actions.cc:301 +#: editor_actions.cc:302 #, fuzzy msgid "Snap to region start" msgstr "Regioni/inizio" -#: editor_actions.cc:302 +#: editor_actions.cc:303 #, fuzzy msgid "Snap to region end" msgstr "Regioni/fine" -#: editor_actions.cc:303 +#: editor_actions.cc:304 #, fuzzy msgid "Snap to region sync" msgstr "Regioni/sincronizzazione" -#: editor_actions.cc:304 +#: editor_actions.cc:305 #, fuzzy msgid "Snap to region boundary" msgstr "Regioni/confini" #. the region list popup menu -#: editor_actions.cc:313 +#: editor_actions.cc:314 #, fuzzy msgid "Sort" msgstr "entrata" -#: editor_actions.cc:321 +#: editor_actions.cc:322 msgid "Show all" msgstr "Mostra tutto" -#: editor_actions.cc:322 +#: editor_actions.cc:323 #, fuzzy msgid "Show automatic regions" msgstr "mostra tutte le automazioni" -#: editor_actions.cc:324 +#: editor_actions.cc:325 msgid "Ascending" msgstr "Ascendente" -#: editor_actions.cc:326 +#: editor_actions.cc:327 msgid "Descending" msgstr "Discendente" -#: editor_actions.cc:329 +#: editor_actions.cc:330 msgid "By Region Name" msgstr "Per Nome di Regione" -#: editor_actions.cc:331 +#: editor_actions.cc:332 msgid "By Region Length" msgstr "Per Lunghezza di Regione" -#: editor_actions.cc:333 +#: editor_actions.cc:334 msgid "By Region Position" msgstr "Per Posizione della Regione" -#: editor_actions.cc:335 +#: editor_actions.cc:336 msgid "By Region Timestamp" msgstr "Per Data di Regione" -#: editor_actions.cc:337 +#: editor_actions.cc:338 msgid "By Region Start in File" msgstr "Per Inizio di Regione nel file" -#: editor_actions.cc:339 +#: editor_actions.cc:340 msgid "By Region End in File" msgstr "Per Fine di Regione nel file" -#: editor_actions.cc:341 +#: editor_actions.cc:342 msgid "By Source File Name" msgstr "Per Nome di sorgente del file" -#: editor_actions.cc:343 +#: editor_actions.cc:344 msgid "By Source File Length" msgstr "Per Lunghezza di sorgente del file" -#: editor_actions.cc:345 +#: editor_actions.cc:346 msgid "By Source File Creation Date" msgstr "Per Data di creazione di sorgente del file" -#: editor_actions.cc:347 +#: editor_actions.cc:348 msgid "By Source Filesystem" msgstr "Per Filesystem di sorgente" #. the next two are duplicate items with different names for use in two different contexts -#: editor_actions.cc:353 +#: editor_actions.cc:354 #, fuzzy msgid "Add External Audio" msgstr "Aggiungi alla lista di Regioni Esterne" -#: editor_actions.cc:355 +#: editor_actions.cc:356 #, fuzzy msgid "as Region(s)" msgstr "Sposta Regione/i" -#: editor_actions.cc:357 +#: editor_actions.cc:358 #, fuzzy msgid "as Tracks" msgstr "Tracce" -#: editor_actions.cc:359 +#: editor_actions.cc:360 #, fuzzy msgid "to Tracks" msgstr "Tracce" -#: editor_actions.cc:362 +#: editor_actions.cc:363 #, fuzzy msgid "Show Waveforms" msgstr "Mostra le forme Wave" -#: editor_actions.cc:363 +#: editor_actions.cc:364 #, fuzzy msgid "Show Waveforms While Recording" msgstr "Mostra le forme Wave in registrazione" -#: editor_actions.cc:364 +#: editor_actions.cc:365 #, fuzzy msgid "Show Measures" msgstr "Mostra le linee delle Misure" -#: editor_actions.cc:377 editor_actions.cc:384 +#: editor_actions.cc:378 editor_actions.cc:385 msgid "Medium" msgstr "" -#: editor_actions.cc:379 +#: editor_actions.cc:380 #, fuzzy msgid "Faster" msgstr "Veloce" -#: editor_actions.cc:385 +#: editor_actions.cc:386 msgid "Long" msgstr "" -#: editor_actions.cc:389 +#: editor_actions.cc:390 #, fuzzy msgid "Later is Higher" msgstr "Porta la regione giù di un livello" -#: editor_actions.cc:390 +#: editor_actions.cc:391 #, fuzzy msgid "Most Recently Moved/Added is Higher" msgstr "Porta la regione giù di un livello" -#: editor_actions.cc:391 +#: editor_actions.cc:392 #, fuzzy msgid "Most Recently Added is Higher" msgstr "Porta la regione giù di un livello" @@ -3391,114 +3381,102 @@ msgstr "" msgid "Add existing audio to session" msgstr "mostra le automazioni esistenti" -#: editor_audio_import.cc:143 +#: editor_audio_import.cc:142 msgid "ardour: importing %1" msgstr "ardour: importazione di %1" -#: editor_audio_import.cc:147 +#: editor_audio_import.cc:146 msgid "Cancel Import" msgstr "Annullare l'importazione" -#: editor_audio_import.cc:225 +#: editor_audio_import.cc:224 #, fuzzy msgid "Editor: cannot open file \"%1\", (%2)" msgstr "Editor: impossibile aprire il file \"%1\" (%2)" -#: editor_audio_import.cc:233 +#: editor_audio_import.cc:232 #, fuzzy msgid "Cancel entire import" msgstr "Annullare l'importazione" -#: editor_audio_import.cc:234 +#: editor_audio_import.cc:233 #, fuzzy msgid "Don't embed it" msgstr "Non uscire" -#: editor_audio_import.cc:235 +#: editor_audio_import.cc:234 msgid "Embed all without questions" msgstr "" -#: editor_audio_import.cc:240 +#: editor_audio_import.cc:239 #, fuzzy msgid "Embed it anyway" msgstr "%1 comunque" -#: editor_audio_import.cc:243 +#: editor_audio_import.cc:242 #, fuzzy msgid "" "%1\n" "This audiofile's sample rate doesn't match the session sample rate!" msgstr "Il sample rate del file audio non corrisponde a quello della sessione!" -#: editor_audio_import.cc:276 +#: editor_audio_import.cc:275 msgid "could not open %1" msgstr "impossibile aprire %1" -#: editor_audio_import.cc:321 +#: editor_audio_import.cc:320 #, fuzzy msgid "insert sndfile" msgstr "Inserisci un file audio esterno" #. stuff for the verbose canvas cursor -#: editor_canvas.cc:117 +#: editor_canvas.cc:118 msgid "VerboseCanvasCursor" msgstr "" -#: editor_canvas.cc:285 -msgid "Start a new session\n" -msgstr "Inizia una nuova sessione\n" - -#: editor_canvas.cc:285 -msgid "via Session menu" -msgstr "tramite il menu Sessione" - -#: editor_canvas.cc:288 -msgid "FirstActionMessage" -msgstr "" - -#: editor_edit_groups.cc:52 mixer_ui.cc:732 +#: editor_edit_groups.cc:53 mixer_ui.cc:736 #, fuzzy msgid "Activate All" msgstr "Attiva" -#: editor_edit_groups.cc:53 mixer_ui.cc:733 +#: editor_edit_groups.cc:54 mixer_ui.cc:737 #, fuzzy msgid "Disable All" msgstr "Disconnetti" -#: editor_edit_groups.cc:55 mixer_ui.cc:735 +#: editor_edit_groups.cc:56 mixer_ui.cc:739 #, fuzzy msgid "Add group" msgstr "nessun gruppo" -#: editor_edit_groups.cc:225 mixer_ui.cc:964 +#: editor_edit_groups.cc:229 mixer_ui.cc:970 #, fuzzy msgid "unnamed" msgstr "Rinomina" -#: editor_edit_groups.cc:252 mixer_ui.cc:830 +#: editor_edit_groups.cc:258 mixer_ui.cc:834 msgid "-all-" msgstr "-tutto-" -#: editor_export_audio.cc:64 +#: editor_export_audio.cc:65 msgid "" "There is no selection to export.\n" "\n" "Select a selection using the range mouse mode" msgstr "" -#: editor_export_audio.cc:109 +#: editor_export_audio.cc:110 msgid "" "There are no ranges to export.\n" "\n" "Create 1 or more ranges by dragging the mouse in the range bar" msgstr "" -#: editor_imageframe.cc:624 editor_imageframe.cc:654 +#: editor_imageframe.cc:625 editor_imageframe.cc:655 msgid "programming error: no ImageFrameView selected" msgstr "" -#: editor_imageframe.cc:847 editor_imageframe.cc:869 +#: editor_imageframe.cc:848 editor_imageframe.cc:870 msgid "programming error: no MarkerView selected" msgstr "" @@ -3507,141 +3485,141 @@ msgstr "" msgid "mute region" msgstr "Metti in muto questa regione" -#: editor_keys.cc:45 +#: editor_keys.cc:46 #, fuzzy msgid "keyboard selection" msgstr "Esegui la regione selezionata come loop" -#: editor_markers.cc:291 editor_ops.cc:1227 editor_ops.cc:1240 -#: editor_ops.cc:1258 location_ui.cc:773 +#: editor_markers.cc:292 editor_ops.cc:1290 editor_ops.cc:1303 +#: editor_ops.cc:1321 location_ui.cc:774 msgid "add marker" msgstr "aggiungi marcatore" -#: editor_markers.cc:306 editor_markers.cc:379 editor_markers.cc:551 -#: editor_markers.cc:569 editor_markers.cc:588 editor_markers.cc:607 -#: editor_markers.cc:637 editor_markers.cc:665 editor_markers.cc:693 -#: editor_markers.cc:731 editor_markers.cc:758 editor_markers.cc:781 -#: editor_markers.cc:800 editor_mouse.cc:1994 editor_mouse.cc:4237 +#: editor_markers.cc:307 editor_markers.cc:380 editor_markers.cc:552 +#: editor_markers.cc:570 editor_markers.cc:589 editor_markers.cc:608 +#: editor_markers.cc:638 editor_markers.cc:666 editor_markers.cc:694 +#: editor_markers.cc:732 editor_markers.cc:759 editor_markers.cc:782 +#: editor_markers.cc:801 editor_mouse.cc:2015 editor_mouse.cc:4275 msgid "programming error: marker canvas item has no marker object pointer!" msgstr "" -#: editor_markers.cc:330 location_ui.cc:655 +#: editor_markers.cc:331 location_ui.cc:656 msgid "remove marker" msgstr "rimuovi marcatore" -#: editor_markers.cc:457 +#: editor_markers.cc:458 #, fuzzy msgid "Locate to Mark" msgstr "Posiziona a" -#: editor_markers.cc:458 +#: editor_markers.cc:459 #, fuzzy msgid "Play from Mark" msgstr "Suona dall'inizio" -#: editor_markers.cc:459 +#: editor_markers.cc:460 #, fuzzy msgid "Set Mark from Playhead" msgstr "Imposta dall'inizio" -#: editor_markers.cc:463 +#: editor_markers.cc:464 #, fuzzy msgid "Rename Mark" msgstr "Rinomina" -#: editor_markers.cc:464 +#: editor_markers.cc:465 #, fuzzy msgid "Hide Mark" msgstr "Nascondi traccia" -#: editor_markers.cc:465 +#: editor_markers.cc:466 #, fuzzy msgid "Remove Mark" msgstr "rimuovi marcatore" -#: editor_markers.cc:478 editor_markers.cc:534 +#: editor_markers.cc:479 editor_markers.cc:535 #, fuzzy msgid "Locate to Range Mark" msgstr "Marcatori di posizione" -#: editor_markers.cc:479 editor_markers.cc:535 +#: editor_markers.cc:480 editor_markers.cc:536 #, fuzzy msgid "Play from Range Mark" msgstr "Suona l'intervallo di loop" -#: editor_markers.cc:480 +#: editor_markers.cc:481 #, fuzzy msgid "Loop Range" msgstr "Intervallo di loop" -#: editor_markers.cc:481 editor_markers.cc:536 +#: editor_markers.cc:482 editor_markers.cc:537 #, fuzzy msgid "Set Range Mark from Playhead" msgstr "Imposta dall'inizio" -#: editor_markers.cc:482 editor_markers.cc:537 +#: editor_markers.cc:483 editor_markers.cc:538 #, fuzzy msgid "Set Range from Range Selection" msgstr "Suona intervallo/selezione" -#: editor_markers.cc:486 +#: editor_markers.cc:487 #, fuzzy msgid "Rename Range" msgstr "Rinomina" -#: editor_markers.cc:487 editor_markers.cc:539 +#: editor_markers.cc:488 editor_markers.cc:540 #, fuzzy msgid "Hide Range" msgstr "Aggiungi un nuovo Intervallo" -#: editor_markers.cc:488 +#: editor_markers.cc:489 #, fuzzy msgid "Remove Range" msgstr "Rimuovi Campo" -#: editor_markers.cc:492 editor_markers.cc:541 +#: editor_markers.cc:493 editor_markers.cc:542 #, fuzzy msgid "Separate Regions in Range" msgstr "Nuova Regione dall'intervallo" -#: editor_markers.cc:493 editor_markers.cc:542 +#: editor_markers.cc:494 editor_markers.cc:543 #, fuzzy msgid "Select All in Range" msgstr "Seleziona tutto nella traccia" -#: editor_markers.cc:519 +#: editor_markers.cc:520 msgid "Set Loop Range" msgstr "Imposta l'intervallo di loop" -#: editor_markers.cc:520 +#: editor_markers.cc:521 msgid "Set Punch Range" msgstr "Imposta l'intervallo di Punch" -#: editor_markers.cc:814 +#: editor_markers.cc:815 #, fuzzy msgid "New Name:" msgstr "nuovo nome: " -#: editor_markers.cc:817 +#: editor_markers.cc:818 msgid "ardour: rename mark" msgstr "ardour: rinomina il marcatore" -#: editor_markers.cc:819 +#: editor_markers.cc:820 #, fuzzy msgid "ardour: rename range" msgstr "ardour: rinomina la regione" -#: editor_markers.cc:839 +#: editor_markers.cc:840 #, fuzzy msgid "rename marker" msgstr "rimuovi marcatore" -#: editor_markers.cc:864 +#: editor_markers.cc:865 #, fuzzy msgid "set loop range" msgstr "Seleziona l'intervallo di loop" -#: editor_markers.cc:890 +#: editor_markers.cc:891 #, fuzzy msgid "set punch range" msgstr "Seleziona l'intervallo di punch" @@ -3650,418 +3628,424 @@ msgstr "Seleziona l'intervallo di punch" msgid "Editor::event_frame() used on unhandled event type %1" msgstr "" -#: editor_mouse.cc:1589 +#: editor_mouse.cc:313 +#, fuzzy +msgid "select on click" +msgstr "Usa come click" + +#: editor_mouse.cc:1590 msgid "programming error: start_grab called without drag item" msgstr "" -#: editor_mouse.cc:1793 +#: editor_mouse.cc:1814 msgid "change fade in length" msgstr "modifica la lunghezza dello smorzamento in entrata" -#: editor_mouse.cc:1811 +#: editor_mouse.cc:1832 msgid "programming error: fade out canvas item has no regionview data pointer!" msgstr "" -#: editor_mouse.cc:1885 +#: editor_mouse.cc:1906 msgid "change fade out length" msgstr "cambia la durata dello smorzamento in uscita" -#: editor_mouse.cc:1904 +#: editor_mouse.cc:1925 msgid "programming error: cursor canvas item has no cursor data pointer!" msgstr "" -#: editor_mouse.cc:2119 +#: editor_mouse.cc:2142 #, fuzzy msgid "move marker" msgstr "rimuovi marcatore" -#: editor_mouse.cc:2142 editor_mouse.cc:2173 editor_tempodisplay.cc:461 +#: editor_mouse.cc:2165 editor_mouse.cc:2196 editor_tempodisplay.cc:459 msgid "" "programming error: meter marker canvas item has no marker object pointer!" msgstr "" -#: editor_mouse.cc:2241 +#: editor_mouse.cc:2264 #, fuzzy msgid "copy meter mark" msgstr "rimuovi marcatore" -#: editor_mouse.cc:2251 +#: editor_mouse.cc:2274 #, fuzzy msgid "move meter mark" msgstr "rimuovi marcatore" -#: editor_mouse.cc:2266 editor_mouse.cc:2299 editor_tempodisplay.cc:327 -#: editor_tempodisplay.cc:411 editor_tempodisplay.cc:430 +#: editor_mouse.cc:2289 editor_mouse.cc:2322 editor_tempodisplay.cc:331 +#: editor_tempodisplay.cc:409 editor_tempodisplay.cc:428 msgid "" "programming error: tempo marker canvas item has no marker object pointer!" msgstr "" -#: editor_mouse.cc:2271 editor_mouse.cc:2304 editor_tempodisplay.cc:332 -#: editor_tempodisplay.cc:416 +#: editor_mouse.cc:2294 editor_mouse.cc:2327 editor_tempodisplay.cc:336 +#: editor_tempodisplay.cc:414 msgid "programming error: marker for tempo is not a tempo marker!" msgstr "" -#: editor_mouse.cc:2371 +#: editor_mouse.cc:2394 #, fuzzy msgid "copy tempo mark" msgstr "rimuovi marcatore" -#: editor_mouse.cc:2381 +#: editor_mouse.cc:2404 #, fuzzy msgid "move tempo mark" msgstr "rimuovi marcatore" -#: editor_mouse.cc:2395 editor_mouse.cc:2414 editor_mouse.cc:2427 +#: editor_mouse.cc:2418 editor_mouse.cc:2437 editor_mouse.cc:2450 msgid "" "programming error: control point canvas item has no control point object " "pointer!" msgstr "" -#: editor_mouse.cc:2525 +#: editor_mouse.cc:2555 msgid "programming error: line canvas item has no line pointer!" msgstr "" -#: editor_mouse.cc:2634 +#: editor_mouse.cc:2664 #, fuzzy msgid "move region(s)" msgstr "fai il Reverse della regione" -#. this is committed in the grab finished callback. -#: editor_mouse.cc:2646 -msgid "Drag region copy" -msgstr "" - -#: editor_mouse.cc:2758 +#: editor_mouse.cc:2727 #, fuzzy msgid "Drag region brush" msgstr "Sposta Regione/i" +#. don't copy again +#. this is committed in the grab finished callback. +#: editor_mouse.cc:2751 +msgid "Drag region copy" +msgstr "" + #. A selection grab currently creates two undo/redo operations, one for #. creating the new region and another for moving it. #. -#: editor_mouse.cc:3574 +#: editor_mouse.cc:3609 #, fuzzy msgid "selection grab" msgstr "seleziona l'intervallo di zoom" -#: editor_mouse.cc:3615 +#: editor_mouse.cc:3650 #, fuzzy msgid "cancel selection" msgstr "Suona intervallo/selezione" -#: editor_mouse.cc:3722 +#: editor_mouse.cc:3760 #, fuzzy msgid "range selection" msgstr "Suona intervallo/selezione" -#: editor_mouse.cc:3738 +#: editor_mouse.cc:3776 #, fuzzy msgid "trim selection start" msgstr "Regioni/inizio" -#: editor_mouse.cc:3754 +#: editor_mouse.cc:3792 #, fuzzy msgid "trim selection end" msgstr "Importa selezione" -#: editor_mouse.cc:3771 +#: editor_mouse.cc:3809 #, fuzzy msgid "move selection" msgstr "Esegui la regione selezionata come loop" -#: editor_mouse.cc:4157 +#: editor_mouse.cc:4195 #, fuzzy msgid "Start point trim" msgstr "Inizio al cursore di modifica" -#: editor_mouse.cc:4185 +#: editor_mouse.cc:4223 msgid "End point trim" msgstr "" -#: editor_mouse.cc:4224 +#: editor_mouse.cc:4262 msgid "trimmed region" msgstr "" -#: editor_mouse.cc:4363 +#: editor_mouse.cc:4400 #, fuzzy msgid "new range marker" msgstr "agggiungi marcatore di intervallo" -#: editor_mouse.cc:4578 +#: editor_mouse.cc:4642 #, fuzzy msgid "select regions" msgstr "Esegui la regione selezionata come loop" -#: editor_mouse.cc:4607 +#: editor_mouse.cc:4671 msgid "Name for region:" msgstr "Nome per la Regione" -#: editor_mouse.cc:4671 +#: editor_mouse.cc:4735 msgid "timestretch" msgstr "" -#: editor_ops.cc:132 +#: editor_ops.cc:195 #, fuzzy msgid "split" msgstr "Dividi" -#: editor_ops.cc:168 +#: editor_ops.cc:231 #, fuzzy msgid "remove region" msgstr "fai il Reverse della regione" -#: editor_ops.cc:187 +#: editor_ops.cc:250 msgid "" " This is destructive, will possibly delete audio files\n" "It cannot be undone\n" "Do you really want to destroy %1 ?" msgstr "" -#: editor_ops.cc:191 +#: editor_ops.cc:254 #, fuzzy msgid "these regions" msgstr "fai il Reverse della regione" -#: editor_ops.cc:191 +#: editor_ops.cc:254 #, fuzzy msgid "this region" msgstr "Metti in muto questa regione" -#: editor_ops.cc:193 editor_ops.cc:3229 route_ui.cc:700 -#: visual_time_axis.cc:277 +#: editor_ops.cc:256 editor_ops.cc:3318 route_ui.cc:707 +#: visual_time_axis.cc:278 msgid "No, do nothing." msgstr "No, non fare niente." -#: editor_ops.cc:196 +#: editor_ops.cc:259 #, fuzzy msgid "Yes, destroy them." msgstr "Si, rimuovi." -#: editor_ops.cc:198 editor_ops.cc:3230 +#: editor_ops.cc:261 editor_ops.cc:3319 msgid "Yes, destroy it." msgstr "Si, rimuovi." -#: editor_ops.cc:289 editor_ops.cc:317 +#: editor_ops.cc:352 editor_ops.cc:380 msgid "extend selection" msgstr "" -#: editor_ops.cc:333 editor_ops.cc:367 editor_ops.cc:411 editor_ops.cc:437 +#: editor_ops.cc:396 editor_ops.cc:430 editor_ops.cc:474 editor_ops.cc:500 msgid "nudge forward" msgstr "" -#: editor_ops.cc:501 +#: editor_ops.cc:564 msgid "build_region_boundary_cache called with snap_type = %1" msgstr "" -#: editor_ops.cc:1354 +#: editor_ops.cc:1420 #, fuzzy msgid "select all within" msgstr "Seleziona tutto" -#: editor_ops.cc:1380 +#: editor_ops.cc:1452 #, fuzzy msgid "set selection from region" msgstr "Nuova Regione dall'intervallo" -#: editor_ops.cc:1413 +#: editor_ops.cc:1485 #, fuzzy msgid "set selection from range" msgstr "Nuova Regione dall'intervallo" -#: editor_ops.cc:1443 +#: editor_ops.cc:1515 #, fuzzy msgid "select all from range" msgstr "seleziona l'intervallo di zoom" -#: editor_ops.cc:1465 +#: editor_ops.cc:1537 #, fuzzy msgid "select all from punch" msgstr "Seleziona tutto" -#: editor_ops.cc:1487 +#: editor_ops.cc:1559 #, fuzzy msgid "select all from loop" msgstr "Seleziona tutto" -#: editor_ops.cc:1501 +#: editor_ops.cc:1573 #, fuzzy msgid "select all after cursor" msgstr "Inizio al cursore di modifica" -#: editor_ops.cc:1506 +#: editor_ops.cc:1578 #, fuzzy msgid "select all before cursor" msgstr "Suona dal cursore di modifica" -#: editor_ops.cc:1536 +#: editor_ops.cc:1608 #, fuzzy msgid "select all between cursors" msgstr "Suona dal cursore di modifica" -#: editor_ops.cc:1667 +#: editor_ops.cc:1739 msgid "clear markers" msgstr "azzera i marcatori" -#: editor_ops.cc:1679 +#: editor_ops.cc:1751 msgid "clear ranges" msgstr "azzera gli intervalli" -#: editor_ops.cc:1698 +#: editor_ops.cc:1770 msgid "clear locations" msgstr "azzera le posizioni" -#: editor_ops.cc:1748 +#: editor_ops.cc:1820 #, fuzzy msgid "insert dragged region" msgstr "Inserisci la Regione" -#: editor_ops.cc:1784 +#: editor_ops.cc:1856 #, fuzzy msgid "insert region" msgstr "Inserisci la Regione" -#: editor_ops.cc:1975 io_selector.cc:57 io_selector.cc:791 +#: editor_ops.cc:2047 io_selector.cc:58 io_selector.cc:792 msgid "OK" msgstr "" -#: editor_ops.cc:1982 +#: editor_ops.cc:2054 msgid "ardour: rename region" msgstr "ardour: rinomina la regione" -#: editor_ops.cc:2205 editor_ops.cc:2254 +#: editor_ops.cc:2277 editor_ops.cc:2326 #, fuzzy msgid "separate" msgstr "Separa l'intervallo" -#: editor_ops.cc:2316 +#: editor_ops.cc:2388 #, fuzzy msgid "trim to selection" msgstr "ardour: selezione del colore" -#: editor_ops.cc:2356 +#: editor_ops.cc:2428 msgid "region fill" msgstr "" -#: editor_ops.cc:2415 +#: editor_ops.cc:2487 #, fuzzy msgid "fill selection" msgstr "Suona intervallo/selezione" -#: editor_ops.cc:2436 +#: editor_ops.cc:2508 #, fuzzy msgid "Programming error. that region doesn't cover that position" msgstr "" "errore di programmazione: la mappa di posizioni/marcatori non contiene " "alcuna posizione!" -#: editor_ops.cc:2439 +#: editor_ops.cc:2511 #, fuzzy msgid "set region sync position" msgstr "Regioni/posizione" -#: editor_ops.cc:2454 +#: editor_ops.cc:2526 msgid "Place the edit cursor at the desired sync point" msgstr "" "Posiziona il cursore di modifica al punto di sincronizzazione desiderato" -#: editor_ops.cc:2459 +#: editor_ops.cc:2531 #, fuzzy msgid "set sync from edit cursor" msgstr "Suona dal cursore di modifica" -#: editor_ops.cc:2471 +#: editor_ops.cc:2543 #, fuzzy msgid "remove sync" msgstr "Rimuovi il punto di sincronizzazione" -#: editor_ops.cc:2485 +#: editor_ops.cc:2557 #, fuzzy msgid "naturalize" msgstr "Normalizza" -#: editor_ops.cc:2549 +#: editor_ops.cc:2621 #, fuzzy msgid "align selection (relative)" msgstr "Allinea Realtivo" -#: editor_ops.cc:2577 +#: editor_ops.cc:2649 #, fuzzy msgid "align selection" msgstr "ardour: selezione del colore" -#: editor_ops.cc:2589 +#: editor_ops.cc:2661 #, fuzzy msgid "align region" msgstr "Sposta Regione/i" -#: editor_ops.cc:2636 editor_ops.cc:2661 +#: editor_ops.cc:2708 editor_ops.cc:2733 #, fuzzy msgid "trim to edit" msgstr "Inizio al cursore di modifica" -#: editor_ops.cc:2712 +#: editor_ops.cc:2784 #, fuzzy msgid "ardour: freeze" msgstr "ardour: rinomina la regione" -#: editor_ops.cc:2717 +#: editor_ops.cc:2789 #, fuzzy msgid "Cancel Freeze" msgstr "Cancella" -#: editor_ops.cc:2754 +#: editor_ops.cc:2826 #, fuzzy msgid "bounce range" msgstr "Fai il Bounce dell'intervallo" -#: editor_ops.cc:2807 +#: editor_ops.cc:2879 msgid "cut" msgstr "taglia" -#: editor_ops.cc:2810 +#: editor_ops.cc:2882 msgid "copy" msgstr "copia" -#: editor_ops.cc:2823 +#: editor_ops.cc:2895 msgid " objects" msgstr "oggetti" -#: editor_ops.cc:2849 +#: editor_ops.cc:2921 msgid " range" msgstr " intervallo" -#: editor_ops.cc:3006 +#: editor_ops.cc:3078 #, fuzzy msgid "paste" msgstr "Incolla" -#: editor_ops.cc:3044 +#: editor_ops.cc:3116 #, fuzzy msgid "paste chunk" msgstr "Crea uno Spezzone" #. clear (below) will clear the argument list -#: editor_ops.cc:3085 +#: editor_ops.cc:3157 #, fuzzy msgid "duplicate region" msgstr "Esegui la regione selezionata come loop" -#: editor_ops.cc:3130 +#: editor_ops.cc:3202 #, fuzzy msgid "duplicate selection" msgstr "ardour: selezione del colore" -#: editor_ops.cc:3170 +#: editor_ops.cc:3259 #, fuzzy msgid "clear playlist" msgstr "azzera le posizioni" -#: editor_ops.cc:3199 +#: editor_ops.cc:3288 #, fuzzy msgid "nudge track" msgstr "Nascondi traccia" -#: editor_ops.cc:3226 +#: editor_ops.cc:3315 msgid "" "Do you really want to destroy the last capture?\n" "(This is destructive and cannot be undone)" @@ -4069,163 +4053,160 @@ msgstr "" "Si vuole realmente rimuovere l'ultima registrazione?\n" "(questa azione non potrà essere annullata)" -#: editor_ops.cc:3254 +#: editor_ops.cc:3343 #, fuzzy msgid "normalize" msgstr "Normalizza" -#: editor_ops.cc:3301 +#: editor_ops.cc:3390 msgid "reverse regions" msgstr "fai il Reverse della regione" -#: editor_region_list.cc:93 editor_region_list.cc:98 editor_region_list.cc:101 -#: location_ui.cc:55 +#: editor_region_list.cc:98 editor_region_list.cc:103 +#: editor_region_list.cc:106 location_ui.cc:56 msgid "Hidden" msgstr "Nascosto" #. added a new fresh one at the end -#: editor_route_list.cc:101 editor_route_list.cc:102 editor_route_list.cc:246 +#: editor_route_list.cc:102 editor_route_list.cc:103 editor_route_list.cc:247 msgid "editor" msgstr "" -#: editor_route_list.cc:309 mixer_ui.cc:695 +#: editor_route_list.cc:310 mixer_ui.cc:699 msgid "Show All" msgstr "Mostra Tutto" -#: editor_route_list.cc:310 mixer_ui.cc:696 +#: editor_route_list.cc:311 mixer_ui.cc:700 msgid "Hide All" msgstr "Nascondi tutto" -#: editor_route_list.cc:311 mixer_ui.cc:697 +#: editor_route_list.cc:312 mixer_ui.cc:701 #, fuzzy msgid "Show All Audio Tracks" msgstr "Mostra tutti i Bus Audio" -#: editor_route_list.cc:312 mixer_ui.cc:698 +#: editor_route_list.cc:313 mixer_ui.cc:702 #, fuzzy msgid "Hide All Audio Tracks" msgstr "Nascondi tutti i Bus Audio" -#: editor_route_list.cc:313 mixer_ui.cc:699 +#: editor_route_list.cc:314 mixer_ui.cc:703 #, fuzzy msgid "Show All Audio Busses" msgstr "Mostra tutti i Bus Audio" -#: editor_route_list.cc:314 mixer_ui.cc:700 +#: editor_route_list.cc:315 mixer_ui.cc:704 #, fuzzy msgid "Hide All Audio Busses" msgstr "Nascondi tutti i Bus Audio" -#: editor_rulers.cc:311 +#: editor_rulers.cc:312 msgid "New location marker" msgstr "Marcatore di nuova posizione" -#: editor_rulers.cc:312 +#: editor_rulers.cc:313 msgid "Clear all locations" msgstr "Pulisci tutte le posizioni" #. ruler_items.push_back (MenuElem (_("New Range"))); -#: editor_rulers.cc:317 +#: editor_rulers.cc:318 msgid "Clear all ranges" msgstr "Pulisci tutti gli intervalli" -#: editor_rulers.cc:326 +#: editor_rulers.cc:327 msgid "New Tempo" msgstr "Nuovo tempo" -#: editor_rulers.cc:327 +#: editor_rulers.cc:328 msgid "Clear tempo" msgstr "Pulisci tempo" -#: editor_rulers.cc:332 +#: editor_rulers.cc:333 msgid "New Meter" msgstr "Nuovo Meter" -#: editor_rulers.cc:333 +#: editor_rulers.cc:334 msgid "Clear meter" msgstr "Pulisci Meter" -#: editor_rulers.cc:341 +#: editor_rulers.cc:342 msgid "Min:Secs" msgstr "Min:Sec" -#: editor_selection_list.cc:110 +#: editor_selection_list.cc:108 #, fuzzy msgid "Name for Chunk:" msgstr "Nome dello Spezzone" -#: editor_selection_list.cc:113 +#: editor_selection_list.cc:111 #, fuzzy msgid "Create Chunk" msgstr "Crea uno Spezzone" -#: editor_selection_list.cc:113 +#: editor_selection_list.cc:111 msgid "Forget it" msgstr "Annulla" -#: editor_tempodisplay.cc:249 editor_tempodisplay.cc:289 +#: editor_tempodisplay.cc:253 editor_tempodisplay.cc:293 msgid "add" msgstr "Aggiungi" -#: editor_tempodisplay.cc:271 +#: editor_tempodisplay.cc:275 #, fuzzy msgid "add tempo mark" msgstr "agggiungi marcatore di intervallo" -#: editor_tempodisplay.cc:311 +#: editor_tempodisplay.cc:315 #, fuzzy msgid "add meter mark" msgstr "agggiungi marcatore di intervallo" -#: editor_tempodisplay.cc:344 editor_tempodisplay.cc:375 +#: editor_tempodisplay.cc:348 editor_tempodisplay.cc:376 msgid "done" msgstr "fatto" -#: editor_tempodisplay.cc:365 editor_tempodisplay.cc:396 +#: editor_tempodisplay.cc:366 editor_tempodisplay.cc:394 msgid "replace tempo mark" msgstr "" -#: editor_tempodisplay.cc:435 editor_tempodisplay.cc:466 +#: editor_tempodisplay.cc:433 editor_tempodisplay.cc:464 msgid "programming error: marker for meter is not a meter marker!" msgstr "" -#: editor_tempodisplay.cc:445 editor_tempodisplay.cc:478 +#: editor_tempodisplay.cc:443 editor_tempodisplay.cc:476 #, fuzzy msgid "remove tempo mark" msgstr "rimuovi marcatore" -#: editor_timefx.cc:50 +#: editor_timefx.cc:51 msgid "Quick but Ugly" msgstr "Rapido ma inaccurato" -#: editor_timefx.cc:51 +#: editor_timefx.cc:52 msgid "Skip Anti-aliasing" msgstr "Salta l'Anti-aliasing" -#: editor_timefx.cc:53 -msgid "Stretch/Shrink it" -msgstr "Allunga/Restringi" - -#: editor_timefx.cc:57 +#: editor_timefx.cc:56 msgid "ardour: timestretch" msgstr "" -#: editor_timefx.cc:58 +#: editor_timefx.cc:57 msgid "TimeStretchDialog" msgstr "" -#: editor_timefx.cc:80 editor_timefx.cc:81 editor_timefx.cc:82 -#: editor_timefx.cc:83 +#: editor_timefx.cc:70 +msgid "Stretch/Shrink it" +msgstr "Allunga/Restringi" + +#: editor_timefx.cc:73 editor_timefx.cc:74 msgid "TimeStretchButton" msgstr "" -#: editor_timefx.cc:84 +#: editor_timefx.cc:75 msgid "TimeStretchProgress" msgstr "" -#. GTK2FIX -#. current_timestretch->close (); -#: editor_timefx.cc:153 +#: editor_timefx.cc:139 msgid "timestretch cannot be started - thread creation error" msgstr "" @@ -4359,7 +4340,7 @@ msgstr "" msgid "Export to File" msgstr "Esporta a CD" -#: export_dialog.cc:113 option_editor.cc:82 option_editor.cc:83 +#: export_dialog.cc:113 option_editor.cc:83 option_editor.cc:84 msgid "Browse" msgstr "Naviga" @@ -4376,7 +4357,8 @@ msgstr "ardour: esportazione" msgid "ardour_export" msgstr "ardour: esportazione" -#: export_dialog.cc:139 export_dialog.cc:155 +#: export_dialog.cc:139 export_dialog.cc:155 mixer_strip.cc:124 +#: mixer_strip.cc:767 #, fuzzy msgid "Output" msgstr "Uscite" @@ -4415,144 +4397,73 @@ msgstr "" msgid "File already exists, do you want to overwrite it?" msgstr "" -#: export_dialog.cc:1159 export_range_markers_dialog.cc:154 +#: export_dialog.cc:1159 export_range_markers_dialog.cc:153 msgid "Cannot write file in: " msgstr "" #. warning dialog -#: export_range_markers_dialog.cc:136 +#: export_range_markers_dialog.cc:135 msgid "Please enter a valid target directory." msgstr "" -#: export_range_markers_dialog.cc:144 +#: export_range_markers_dialog.cc:143 msgid "" "Please select an existing target directory. Files\n" "are not allowed!" msgstr "" -#: gain_automation_time_axis.cc:61 +#: gain_automation_time_axis.cc:62 #, fuzzy msgid "add gain automation event" msgstr "aggiungi evento di automazione a " -#: gain_meter.cc:66 +#: gain_meter.cc:67 msgid "cannot find images for fader slider" msgstr "" -#: gain_meter.cc:73 +#: gain_meter.cc:74 msgid "cannot find images for fader rail" msgstr "" -#: gain_meter.cc:88 -msgid "dbFS" -msgstr "" - -#: gain_meter.cc:89 gain_meter.cc:143 gain_meter.cc:704 -msgid "pre" -msgstr "" - -#: gain_meter.cc:139 gain_meter.cc:700 -#, fuzzy -msgid "input" -msgstr "entrata %1" - -#: gain_meter.cc:147 gain_meter.cc:708 -#, fuzzy -msgid "post" -msgstr "entrata" - -#. TRANSLATORS: this string should be longest of the strings -#. used to describe meter points. In english, its "input". -#. -#: gain_meter.cc:155 -msgid "tupni" -msgstr "" - -#: gain_meter.cc:174 gain_meter.cc:458 gain_meter.cc:480 gain_meter.cc:525 +#: gain_meter.cc:130 gain_meter.cc:339 gain_meter.cc:494 gain_meter.cc:539 msgid "-inf" msgstr "" -#: glade/new_session_dialog.glade.h:1 +#: gain_meter.cc:140 #, fuzzy -msgid "Advanced" -msgstr "Avanzate..." +msgid "Fader automation mode" +msgstr "modalita' di automazione pan" -#: glade/new_session_dialog.glade.h:2 -msgid "Input" +#: gain_meter.cc:141 +#, fuzzy +msgid "Fader automation type" +msgstr "Tipo di automazione pan" + +#. XXX it might different in different languages +#: gain_meter.cc:182 gain_meter.cc:817 panner_ui.cc:99 panner_ui.cc:807 +msgid "Abs" msgstr "" -#: glade/new_session_dialog.glade.h:3 -#, fuzzy -msgid "Output" -msgstr "Uscite" - -#: glade/new_session_dialog.glade.h:4 -#, fuzzy -msgid "Automatically connect inputs" -msgstr "autoconnetti le entrate delle tracce alle entrate fisiche" - -#: glade/new_session_dialog.glade.h:5 -#, fuzzy -msgid "Automatically connect outputs" -msgstr "connetti manualmente le uscite delle tracce" - -#: glade/new_session_dialog.glade.h:6 -#, fuzzy -msgid "Channel Count" -msgstr "Annullare l'importazione" - -#: glade/new_session_dialog.glade.h:7 -msgid "Connect to Master Bus" +#: gain_meter.cc:472 +msgid "-Inf" msgstr "" -#: glade/new_session_dialog.glade.h:8 -msgid "Connect to physical outputs" +#: gain_meter.cc:781 mixer_strip.cc:770 panner_ui.cc:771 +#, fuzzy +msgid "O" +msgstr "O" + +#: gain_meter.cc:784 panner_ui.cc:774 +msgid "P" msgstr "" -#: glade/new_session_dialog.glade.h:9 -#, fuzzy -msgid "Create Control Bus" -msgstr "Uscite di Controllo" +#: gain_meter.cc:787 panner_ui.cc:777 +msgid "T" +msgstr "" -#: glade/new_session_dialog.glade.h:10 -#, fuzzy -msgid "Create Master Bus" -msgstr "utilizza le uscite master" - -#: glade/new_session_dialog.glade.h:11 -#, fuzzy -msgid "New Session" -msgstr "Sessione" - -#: glade/new_session_dialog.glade.h:12 -#, fuzzy -msgid "Open Recent Session" -msgstr "apri sessione" - -#: glade/new_session_dialog.glade.h:13 -#, fuzzy -msgid "Open Session" -msgstr "apri sessione" - -#: glade/new_session_dialog.glade.h:14 -#, fuzzy -msgid "Port limit" -msgstr "Annulla" - -#: glade/new_session_dialog.glade.h:15 -#, fuzzy -msgid "Select a File" -msgstr "Seleziona tutto" - -#: glade/new_session_dialog.glade.h:16 -#, fuzzy -msgid "Select a Session" -msgstr "Esegui la regione selezionata come loop" - -#: glade/new_session_dialog.glade.h:17 -#, fuzzy -msgid "Track/Bus connection options" -msgstr "Tracce/Bus" +#: gain_meter.cc:790 panner_ui.cc:780 +msgid "W" +msgstr "" #: gtk-custom-ruler.c:126 #, fuzzy @@ -4599,236 +4510,236 @@ msgid "Draw current ruler position" msgstr "" #. end-of-file, other end closed or shutdown? -#: imageframe_socket_handler.cc:126 +#: imageframe_socket_handler.cc:127 msgid "Image Compositor Socket has been shutdown/closed" msgstr "" -#: imageframe_time_axis.cc:287 +#: imageframe_time_axis.cc:286 #, fuzzy msgid "0.5 seconds" msgstr "Secondi" -#: imageframe_time_axis.cc:288 marker_time_axis.cc:241 +#: imageframe_time_axis.cc:287 marker_time_axis.cc:242 #, fuzzy msgid "1 seconds" msgstr "Secondi" -#: imageframe_time_axis.cc:289 marker_time_axis.cc:242 +#: imageframe_time_axis.cc:288 marker_time_axis.cc:243 #, fuzzy msgid "1.5 seconds" msgstr "Secondi" -#: imageframe_time_axis.cc:290 marker_time_axis.cc:243 +#: imageframe_time_axis.cc:289 marker_time_axis.cc:244 #, fuzzy msgid "2 seconds" msgstr "Secondi" -#: imageframe_time_axis.cc:291 marker_time_axis.cc:244 +#: imageframe_time_axis.cc:290 marker_time_axis.cc:245 #, fuzzy msgid "2.5 seconds" msgstr "Secondi" -#: imageframe_time_axis.cc:292 marker_time_axis.cc:245 +#: imageframe_time_axis.cc:291 marker_time_axis.cc:246 #, fuzzy msgid "3 seconds" msgstr "Secondi" #. duration_items.push_back(SeparatorElem()) ; #. duration_items.push_back(MenuElem (_("custom"), mem_fun(*this, &ImageFrameTimeAxis::set_marker_duration_custom))) ; -#: imageframe_time_axis.cc:297 marker_time_axis.cc:250 +#: imageframe_time_axis.cc:296 marker_time_axis.cc:251 #, fuzzy msgid "Duration (sec)" msgstr "Sposta Regione/i" -#: imageframe_time_axis.cc:302 +#: imageframe_time_axis.cc:301 #, fuzzy msgid "Remove Frame" msgstr "Rimuovi Campo" -#: imageframe_time_axis.cc:305 +#: imageframe_time_axis.cc:304 msgid "Image Frame" msgstr "" -#: imageframe_time_axis.cc:306 marker_time_axis.cc:256 +#: imageframe_time_axis.cc:305 marker_time_axis.cc:257 #, fuzzy msgid "Rename Track" msgstr "Rinomina" -#: io_selector.cc:59 io_selector.cc:793 +#: io_selector.cc:60 io_selector.cc:794 #, fuzzy msgid "Rescan" msgstr "Aggiorna" -#: io_selector.cc:67 +#: io_selector.cc:68 msgid "%1 input" msgstr "entrata %1" -#: io_selector.cc:69 +#: io_selector.cc:70 msgid "%1 output" msgstr "uscita %1" -#: io_selector.cc:141 route_params_ui.cc:106 +#: io_selector.cc:142 route_params_ui.cc:107 msgid "Inputs" msgstr "Entrate" -#: io_selector.cc:141 route_params_ui.cc:107 +#: io_selector.cc:142 route_params_ui.cc:108 msgid "Outputs" msgstr "Uscite" -#: io_selector.cc:142 +#: io_selector.cc:143 #, fuzzy msgid "Add Input" msgstr "aggiungi una entrata" -#: io_selector.cc:142 +#: io_selector.cc:143 #, fuzzy msgid "Add Output" msgstr "aggiungi una uscita" -#: io_selector.cc:143 +#: io_selector.cc:144 #, fuzzy msgid "Remove Input" msgstr "Rimuovi il punto di sincronizzazione" -#: io_selector.cc:143 +#: io_selector.cc:144 #, fuzzy msgid "Remove Output" msgstr "# Uscite" -#: io_selector.cc:144 +#: io_selector.cc:145 #, fuzzy msgid "Disconnect All" msgstr "Disconnetti" -#: io_selector.cc:158 +#: io_selector.cc:159 msgid "Available connections" msgstr "Connessioni disponibili" -#: io_selector.cc:554 io_selector.cc:573 +#: io_selector.cc:555 io_selector.cc:574 msgid "There are no more JACK ports available." msgstr "" -#: io_selector.cc:648 io_selector.cc:675 io_selector.cc:728 +#: io_selector.cc:649 io_selector.cc:676 io_selector.cc:729 msgid "port" msgstr "entrata" -#: io_selector.cc:797 +#: io_selector.cc:798 msgid "ardour: " msgstr "" -#: keyboard.cc:297 +#: keyboard.cc:299 msgid "KeyboardTarget: keyname \"%1\" is unknown." msgstr "KeyboardTarget: il keyname \"%1\" è sconosciuto" -#: keyboard.cc:523 +#: keyboard.cc:525 msgid "" "Your system is completely broken - NumLock uses \"%1\"as its modifier. This " "is madness - see the man page for xmodmap to find out how to fix this." msgstr "" -#: keyboard.cc:531 +#: keyboard.cc:533 msgid "" "Your system generates \"%1\" when the NumLock key is pressed. This can cause " "problems when editing so Ardour will use %2 to mean Meta rather than %1" msgstr "" -#: keyboard.cc:592 +#: keyboard.cc:594 msgid "You have %1 keys bound to \"mod1\"" msgstr "" -#: keyboard.cc:607 +#: keyboard.cc:609 msgid "You have %1 keys bound to \"mod2\"" msgstr "" -#: keyboard.cc:622 +#: keyboard.cc:624 msgid "You have %1 keys bound to \"mod3\"" msgstr "" -#: keyboard.cc:637 +#: keyboard.cc:639 msgid "You have %1 keys bound to \"mod4\"" msgstr "" -#: keyboard.cc:652 +#: keyboard.cc:654 msgid "You have %1 keys bound to \"mod5\"" msgstr "" -#: location_ui.cc:47 location_ui.cc:50 +#: location_ui.cc:48 location_ui.cc:51 msgid "Set" msgstr "Imposta" -#: location_ui.cc:48 location_ui.cc:51 +#: location_ui.cc:49 location_ui.cc:52 msgid "Go" msgstr "Vai" -#: location_ui.cc:54 +#: location_ui.cc:55 msgid "CD" msgstr "" -#: location_ui.cc:57 +#: location_ui.cc:58 msgid "SCMS" msgstr "" -#: location_ui.cc:58 +#: location_ui.cc:59 msgid "Pre-Emphasis" msgstr "" -#: location_ui.cc:569 +#: location_ui.cc:570 msgid "Add New Location" msgstr "Aggiungi una nuova Posizione" -#: location_ui.cc:570 +#: location_ui.cc:571 msgid "Add New Range" msgstr "Aggiungi un nuovo Intervallo" -#: location_ui.cc:574 +#: location_ui.cc:575 msgid "ardour: locations" msgstr "ardour: posizioni" -#: location_ui.cc:575 +#: location_ui.cc:576 msgid "ardour_locations" msgstr "ardour_posizioni" -#: location_ui.cc:603 +#: location_ui.cc:604 #, fuzzy msgid "Location (CD Index) Markers" msgstr "Marcatori di posizione" -#: location_ui.cc:623 +#: location_ui.cc:624 #, fuzzy msgid "Range (CD Track) Markers" msgstr "Marcatori di intervallo" -#: location_ui.cc:789 +#: location_ui.cc:790 msgid "add range marker" msgstr "agggiungi marcatore di intervallo" -#: main.cc:71 +#: main.cc:72 msgid "ardour is killing itself for a clean exit\n" msgstr "ardour sta forzando la chiusura per un'uscita pulita\n" -#: main.cc:80 +#: main.cc:81 msgid "stopping user interface\n" msgstr "chiusura dell'interfaccia\n" #. XXX its doubtful that snprintf() is async-safe -#: main.cc:99 +#: main.cc:100 #, fuzzy, c-format msgid "%d(%d): received signal %d\n" msgstr "%d: ricevuto segnale %d\n" -#: main.cc:185 +#: main.cc:186 msgid "cannot become new process group leader (%1)" msgstr "" -#: main.cc:212 +#: main.cc:213 msgid "cannot setup signal handling for %1" msgstr "" -#: main.cc:223 +#: main.cc:224 msgid "cannot set default signal mask (%1)" msgstr "" -#: main.cc:253 +#: main.cc:254 #, fuzzy msgid "" "Without a UI style file, ardour will look strange.\n" @@ -4837,11 +4748,11 @@ msgstr "" "Senza uno Stile per l'Interfaccia, ardour apparirà strano\n" "Impostare la variabile ARDOUR_UI_RC per puntare ad uno Stile" -#: main.cc:273 +#: main.cc:276 msgid "Ardour could not connect to JACK." msgstr "" -#: main.cc:277 +#: main.cc:280 msgid "" "There are several possible reasons:\n" "\n" @@ -4852,69 +4763,12 @@ msgid "" "Please consider the possibilities, and perhaps (re)start JACK." msgstr "" -#: main.cc:324 -msgid "Ardour/GTK " -msgstr "" - -#: main.cc:326 -msgid "" -"\n" -" (built using " -msgstr "" - -#: main.cc:330 -#, fuzzy -msgid " with libardour " -msgstr " con libardour " - -#: main.cc:335 -msgid " and GCC version " -msgstr "" - -#: main.cc:345 -msgid "Copyright (C) 1999-2005 Paul Davis" -msgstr "" - -#: main.cc:346 -msgid "" -"Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " -"Baker" -msgstr "" - -#: main.cc:348 -msgid "Ardour comes with ABSOLUTELY NO WARRANTY" -msgstr "" - -#: main.cc:349 -msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." -msgstr "" - -#: main.cc:350 -msgid "This is free software, and you are welcome to redistribute it " -msgstr "" - -#: main.cc:351 -msgid "under certain conditions; see the source for copying conditions." -msgstr "" - -#: main.cc:360 -msgid "could not create ARDOUR GUI" -msgstr "Impossibile creare l'interfaccia di Ardour" - -#: main.cc:378 -msgid "Could not connect to JACK server as \"%1\"" -msgstr "" - -#: main.cc:381 -msgid "could not initialize Ardour." -msgstr "impossibile avviare Ardour" - -#: main.cc:392 +#: main.cc:310 msgid "could not load command line session \"%1\"" msgstr "Impossibile caricare la sessione \"%1\" da linea di comando" #. it wasn't new, but we require a new session -#: main.cc:412 +#: main.cc:330 msgid "" "\n" "\n" @@ -4922,7 +4776,7 @@ msgid "" "To avoid this message, start ardour as \"ardour %1" msgstr "" -#: main.cc:423 +#: main.cc:341 msgid "" "\n" "\n" @@ -4930,297 +4784,441 @@ msgid "" "To create it from the command line, start ardour as \"ardour --new %1" msgstr "" +#: main.cc:405 +msgid "Ardour/GTK " +msgstr "" + +#: main.cc:407 +msgid "" +"\n" +" (built using " +msgstr "" + +#: main.cc:411 +#, fuzzy +msgid " with libardour " +msgstr " con libardour " + +#: main.cc:416 +msgid " and GCC version " +msgstr "" + +#: main.cc:426 +msgid "Copyright (C) 1999-2006 Paul Davis" +msgstr "" + +#: main.cc:427 +msgid "" +"Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " +"Baker" +msgstr "" + +#: main.cc:429 +msgid "Ardour comes with ABSOLUTELY NO WARRANTY" +msgstr "" + +#: main.cc:430 +msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." +msgstr "" + +#: main.cc:431 +msgid "This is free software, and you are welcome to redistribute it " +msgstr "" + +#: main.cc:432 +msgid "under certain conditions; see the source for copying conditions." +msgstr "" + +#: main.cc:441 +msgid "could not create ARDOUR GUI" +msgstr "Impossibile creare l'interfaccia di Ardour" + +#: main.cc:459 +msgid "Could not connect to JACK server as \"%1\"" +msgstr "" + +#: main.cc:462 +msgid "could not initialize Ardour." +msgstr "impossibile avviare Ardour" + #: marker.cc:244 #, fuzzy msgid "MarkerText" msgstr "Marcatori" -#: marker_time_axis.cc:253 +#: marker_time_axis.cc:254 #, fuzzy msgid "Remove Marker" msgstr "rimuovi marcatore" -#: marker_time_axis.cc:255 +#: marker_time_axis.cc:256 #, fuzzy msgid "Marker" msgstr "Marcatori" -#: meter_bridge.cc:77 +#: meter_bridge.cc:78 msgid "ardour: meter bridge" msgstr "" -#: meter_bridge.cc:78 +#: meter_bridge.cc:79 msgid "ardour_meter_bridge" msgstr "" -#: meter_bridge_strip.cc:79 meter_bridge_strip.cc:93 +#: meter_bridge_strip.cc:80 meter_bridge_strip.cc:94 #, c-format msgid "# of %u-sample overs" msgstr "" -#: meter_bridge_strip.cc:221 +#: meter_bridge_strip.cc:222 #, fuzzy msgid "New Name for Meter:" msgstr "Nuovo nome per il meter:" -#: mixer_strip.cc:85 mixer_strip.cc:437 region_editor.cc:46 -msgid "mute" -msgstr "muto" - -#: mixer_strip.cc:85 mixer_strip.cc:438 -msgid "solo" +#: mixer_strip.cc:95 mixer_strip.cc:140 mixer_strip.cc:1227 +msgid "pre" msgstr "" -#: mixer_strip.cc:85 mixer_strip.cc:436 -msgid "RECORD" -msgstr "REGISTRA" - -#: mixer_strip.cc:96 mixer_strip.cc:441 mixer_strip.cc:1064 +#: mixer_strip.cc:96 mixer_strip.cc:822 msgid "Comments" msgstr "" -#: mixer_strip.cc:120 mixer_strip.cc:752 -msgid "INPUT" -msgstr "ENTRATA" +#: mixer_strip.cc:119 +#, fuzzy +msgid "Input" +msgstr "Entrate" -#: mixer_strip.cc:125 mixer_strip.cc:773 -msgid "OUTPUT" -msgstr "USCITA" +#: mixer_strip.cc:136 mixer_strip.cc:1223 +#, fuzzy +msgid "input" +msgstr "entrata %1" -#: mixer_strip.cc:140 -msgid "Pan automation mode" -msgstr "Modalita' automazione pan" +#: mixer_strip.cc:144 mixer_strip.cc:1231 +#, fuzzy +msgid "post" +msgstr "entrata" -#: mixer_strip.cc:141 -msgid "Gain automation mode" -msgstr "Modalita' automazione gain" - -#: mixer_strip.cc:143 -msgid "Pan automation type" -msgstr "Tipo di automazione pan" - -#: mixer_strip.cc:144 -msgid "Gain automation type" -msgstr "Tipo di automazione gain" - -#: mixer_strip.cc:183 mixer_strip.cc:195 mixer_strip.cc:913 -msgid "trim" +#. TRANSLATORS: this string should be longest of the strings +#. used to describe meter points. In english, its "input". +#. +#: mixer_strip.cc:152 +msgid "tupni" msgstr "" -#. XXX it might different in different languages -#: mixer_strip.cc:184 mixer_strip.cc:196 mixer_strip.cc:917 -msgid "abs" +#: mixer_strip.cc:207 +msgid "Varispeed" msgstr "" -#: mixer_strip.cc:203 -msgid "gain automation mode" -msgstr "modalita' di automazione gain" - -#: mixer_strip.cc:204 -msgid "pan automation mode" -msgstr "modalita' di automazione pan" - -#: mixer_strip.cc:205 -msgid "gain automation state" -msgstr "stato dell'automazione gain" - -#: mixer_strip.cc:206 -msgid "pan automation state" -msgstr "stato dell'automazione pan" - -#: mixer_strip.cc:223 -msgid "varispeed" -msgstr "" - -#: mixer_strip.cc:245 mixer_strip.cc:1078 +#: mixer_strip.cc:233 mixer_strip.cc:836 msgid "Click to Add/Edit Comments" msgstr "" -#: mixer_strip.cc:393 +#: mixer_strip.cc:374 msgid "unknown strip width \"%1\" in XML GUI information" msgstr "" -#: mixer_strip.cc:443 mixer_strip.cc:1062 -msgid "*Comments*" +#: mixer_strip.cc:417 +#, fuzzy +msgid "record" +msgstr "Registra" + +#: mixer_strip.cc:418 region_editor.cc:47 +msgid "mute" +msgstr "muto" + +#: mixer_strip.cc:419 +msgid "solo" msgstr "" -#: mixer_strip.cc:457 -msgid "REC" +#: mixer_strip.cc:422 +msgid "comments" msgstr "" -#: mixer_strip.cc:462 mixer_strip.cc:1072 +#: mixer_strip.cc:424 +msgid "*comments*" +msgstr "" + +#: mixer_strip.cc:438 +#, fuzzy +msgid "Rec" +msgstr "Aggiorna" + +#: mixer_strip.cc:439 +msgid "M" +msgstr "" + +#: mixer_strip.cc:440 +msgid "S" +msgstr "" + +#: mixer_strip.cc:443 mixer_strip.cc:830 #, fuzzy msgid "Cmt" msgstr "taglia" -#: mixer_strip.cc:464 mixer_strip.cc:1070 +#: mixer_strip.cc:445 mixer_strip.cc:828 msgid "*Cmt*" msgstr "" -#: mixer_strip.cc:503 mixer_strip.cc:562 redirect_box.cc:1004 +#: mixer_strip.cc:483 mixer_strip.cc:549 redirect_box.cc:1006 msgid "Not connected to JACK - no I/O changes are possible" msgstr "" -#: mixer_strip.cc:569 +#: mixer_strip.cc:560 msgid "Track" msgstr "Traccia" -#: mixer_strip.cc:593 mixer_strip.cc:609 +#: mixer_strip.cc:588 mixer_strip.cc:604 msgid "could not register new ports required for that connection" msgstr "" -#: mixer_strip.cc:755 -msgid "IN" +#: mixer_strip.cc:747 +#, fuzzy +msgid " Input" +msgstr "# Entrate" + +#: mixer_strip.cc:750 +msgid "I" msgstr "" -#: mixer_strip.cc:776 -msgid "OUT" +#: mixer_strip.cc:820 +msgid "*Comments*" msgstr "" -#: mixer_strip.cc:884 -msgid "aplay" -msgstr "" - -#: mixer_strip.cc:890 -msgid "awrite" -msgstr "" - -#: mixer_strip.cc:1095 +#: mixer_strip.cc:859 #, fuzzy msgid ": comment editor" msgstr "IU: impossibile avviare l'editor" -#: mixer_strip.cc:1157 mixer_strip.cc:1178 -msgid "no group" -msgstr "nessun gruppo" +#: mixer_strip.cc:953 +msgid "Grp" +msgstr "" -#: mixer_strip.cc:1181 +#: mixer_strip.cc:956 msgid "~G" msgstr "" -#: mixer_strip.cc:1229 +#: mixer_strip.cc:1004 #, fuzzy msgid "Invert Polarity" msgstr "polarità" -#: mixer_ui.cc:84 +#: mixer_ui.cc:85 msgid "Strips" msgstr "Strisce" -#: mixer_ui.cc:108 -msgid "groupname" -msgstr "" +#: mixer_ui.cc:110 +#, fuzzy +msgid "Group" +msgstr "Gruppi di mixaggio" -#: mixer_ui.cc:109 region_editor.cc:48 region_editor.cc:191 -#: region_editor.cc:225 -msgid "active" -msgstr "attivo" - -#: mixer_ui.cc:110 region_editor.cc:49 -msgid "visible" -msgstr "visibile" - -#: mixer_ui.cc:207 mixer_ui.cc:366 +#: mixer_ui.cc:211 mixer_ui.cc:370 msgid "ardour: mixer" msgstr "" -#: mixer_ui.cc:208 +#: mixer_ui.cc:212 msgid "ardour_mixer" msgstr "" -#: mixer_ui.cc:342 +#: mixer_ui.cc:346 msgid "ardour: mixer: " msgstr "" -#: mixer_ui.cc:569 +#: mixer_ui.cc:573 msgid "signal" msgstr "segnale" -#: mixer_ui.cc:719 +#: mixer_ui.cc:723 msgid "track display list item for renamed strip not found!" msgstr "" -#: option_editor.cc:75 +#: new_session_dialog.cc:39 +#, fuzzy +msgid "New Session Name :" +msgstr "Nome della sessione:" + +#: new_session_dialog.cc:41 +msgid "Create Session Directory In :" +msgstr "" + +#: new_session_dialog.cc:43 +#, fuzzy +msgid "Use Session Template :" +msgstr "usa un modello esistente" + +#: new_session_dialog.cc:45 +#, fuzzy +msgid "Channel Count" +msgstr "Annullare l'importazione" + +#: new_session_dialog.cc:46 +#, fuzzy +msgid "Create Monitor Bus" +msgstr "Uscite di Controllo" + +#: new_session_dialog.cc:53 +#, fuzzy +msgid "Create Master Bus" +msgstr "utilizza le uscite master" + +#: new_session_dialog.cc:55 +#, fuzzy +msgid "Automatically Connect Inputs" +msgstr "autoconnetti le entrate delle tracce alle entrate fisiche" + +#: new_session_dialog.cc:56 new_session_dialog.cc:67 +#, fuzzy +msgid "Port Limit" +msgstr "Annulla" + +#: new_session_dialog.cc:64 +#, fuzzy +msgid "Track/Bus Inputs" +msgstr "Tracce/Bus" + +#: new_session_dialog.cc:66 +#, fuzzy +msgid "Automatically Connect Outputs" +msgstr "connetti manualmente le uscite delle tracce" + +#: new_session_dialog.cc:75 +msgid "Connect to Master Bus" +msgstr "" + +#: new_session_dialog.cc:76 +msgid "Connect to Physical Outputs" +msgstr "" + +#: new_session_dialog.cc:80 +#, fuzzy +msgid "Track/Bus Outputs" +msgstr "Uscite" + +#: new_session_dialog.cc:83 +#, fuzzy +msgid "Advanced Options" +msgstr "Editor delle Opzioni" + +#: new_session_dialog.cc:91 +#, fuzzy +msgid "Open Recent Session" +msgstr "apri sessione" + +#: new_session_dialog.cc:127 +#, fuzzy +msgid "Open Session File :" +msgstr "apri sessione" + +#: new_session_dialog.cc:274 +#, fuzzy +msgid "New Session" +msgstr "Sessione" + +#: new_session_dialog.cc:276 +#, fuzzy +msgid "Open Session" +msgstr "apri sessione" + +#: new_session_dialog.cc:281 +#, fuzzy +msgid "ardour: session control" +msgstr "ardour_nuova_sessione" + +#: new_session_dialog.cc:310 +#, fuzzy +msgid "select template" +msgstr "-modello" + +#: new_session_dialog.cc:316 +#, fuzzy +msgid "select session file" +msgstr "Esegui la regione selezionata come loop" + +#: new_session_dialog.cc:325 +#, fuzzy +msgid "select directory" +msgstr "Esegui la regione selezionata come loop" + +#: option_editor.cc:76 msgid "SMPTE offset is negative" msgstr "" -#: option_editor.cc:101 +#: option_editor.cc:102 msgid "ardour: options editor" msgstr "ardour: editor delle opzioni" -#: option_editor.cc:102 +#: option_editor.cc:103 msgid "ardour_option_editor" msgstr "ardour_editor_delle_opzioni" -#: option_editor.cc:126 +#: option_editor.cc:127 msgid "Paths/Files" msgstr "Percorsi/File" -#: option_editor.cc:127 +#: option_editor.cc:128 msgid "Kbd/Mouse" msgstr "Tastiera/Mouse" -#: option_editor.cc:130 +#: option_editor.cc:131 msgid "Layers & Fades" msgstr "" -#: option_editor.cc:134 +#: option_editor.cc:135 msgid "MIDI" msgstr "" -#: option_editor.cc:176 +#: option_editor.cc:177 msgid "24 FPS" msgstr "" -#: option_editor.cc:178 +#: option_editor.cc:179 msgid "25 FPS" msgstr "" -#: option_editor.cc:180 +#: option_editor.cc:181 msgid "30 FPS" msgstr "" -#: option_editor.cc:186 +#: option_editor.cc:187 msgid "30 FPS drop" msgstr "" -#: option_editor.cc:243 +#: option_editor.cc:244 msgid "session RAID path" msgstr "Percorso RAID della sessione" -#: option_editor.cc:248 +#: option_editor.cc:249 #, fuzzy msgid "Soundfile Search Paths" msgstr "Libreria Audio" -#: option_editor.cc:253 +#: option_editor.cc:254 #, fuzzy msgid "Paths" msgstr "Percorsi/File" -#: option_editor.cc:267 option_editor.cc:273 option_editor.cc:724 -#: option_editor.cc:751 +#: option_editor.cc:268 option_editor.cc:274 option_editor.cc:723 +#: option_editor.cc:750 msgid "internal" msgstr "interno" -#: option_editor.cc:286 +#: option_editor.cc:287 msgid "Short crossfade length (msecs)" msgstr "" -#: option_editor.cc:298 +#: option_editor.cc:299 msgid "Destructive crossfade length (msecs)" msgstr "" -#: option_editor.cc:366 +#: option_editor.cc:367 msgid "SMPTE Frames/second" msgstr "" -#: option_editor.cc:367 +#: option_editor.cc:368 msgid "SMPTE Offset" msgstr "" -#: option_editor.cc:461 option_editor.cc:468 option_editor.cc:471 -#: option_editor.cc:617 +#: option_editor.cc:462 option_editor.cc:469 option_editor.cc:472 +#: option_editor.cc:618 #, fuzzy msgid "online" msgstr "lineare" @@ -5228,12 +5226,12 @@ msgstr "lineare" #. remember, we have to handle the i18n case where the relative #. lengths of the strings in language N is different than in english. #. -#: option_editor.cc:468 option_editor.cc:469 option_editor.cc:614 +#: option_editor.cc:469 option_editor.cc:470 option_editor.cc:615 #, fuzzy msgid "offline" msgstr "lineare" -#: option_editor.cc:669 +#: option_editor.cc:670 msgid "Choose Click" msgstr "" @@ -5242,15 +5240,15 @@ msgstr "" msgid "Choose Click Emphasis" msgstr "Usa come enfasi del click" -#: option_editor.cc:804 +#: option_editor.cc:803 msgid "Click audio file" msgstr "File audio del click" -#: option_editor.cc:810 +#: option_editor.cc:809 msgid "Click emphasis audiofile" msgstr "Pecorso del file di enfasi click" -#: option_editor.cc:847 +#: option_editor.cc:846 msgid "" "The auditioner is a dedicated mixer strip used\n" "for listening to specific regions outside the context\n" @@ -5262,35 +5260,35 @@ msgstr "" "del contesto del mixaggio. Può essere connessa proprio\n" "come ogni altra striscia del mixer." -#: option_editor.cc:920 +#: option_editor.cc:919 msgid "Edit using" msgstr "Modifica usando" -#: option_editor.cc:927 option_editor.cc:954 +#: option_editor.cc:926 option_editor.cc:953 msgid "+ button" msgstr "+ pulsante" -#: option_editor.cc:947 +#: option_editor.cc:946 msgid "Delete using" msgstr "Elimina usando" -#: option_editor.cc:974 +#: option_editor.cc:973 msgid "Ignore snap using" msgstr "Ignora l'allineamento automatico usando" -#: opts.cc:47 +#: opts.cc:46 msgid "Usage: " msgstr "Utilizzo: " -#: opts.cc:48 +#: opts.cc:47 msgid " -v, --version Show version information\n" msgstr " -v, --versione Mostra info sulla versione\n" -#: opts.cc:49 +#: opts.cc:48 msgid " -h, --help Print this message\n" msgstr " -h, --help Mostra questo messaggio\n" -#: opts.cc:50 +#: opts.cc:49 msgid "" " -b, --bindings Print all possible keyboard binding " "names\n" @@ -5298,13 +5296,13 @@ msgstr "" " -b, --bindings Mostra tutte le possibili combinazioni di " "tasti\n" -#: opts.cc:51 +#: opts.cc:50 #, fuzzy msgid " -n, --show-splash Show splash screen\n" msgstr "" " -n, --no-splash Non mostrare la schermata d'avvio\n" -#: opts.cc:52 +#: opts.cc:51 #, fuzzy msgid "" " -c, --name name Use a specific jack client name, default " @@ -5313,152 +5311,165 @@ msgstr "" " -c, --jack-client-name name Utilizza nome specifico per jack, " "predefinito e' ardour\n" -#: opts.cc:53 +#: opts.cc:52 #, fuzzy msgid "" " -N, --new session-name Create a new session from the command " "line\n" msgstr " [nome sessione] Nome della sessione da caricare\n" -#: opts.cc:54 +#: opts.cc:53 msgid "" " -o, --use-hw-optimizations Try to use h/w specific optimizations\n" msgstr "" -#: opts.cc:56 +#: opts.cc:55 #, fuzzy msgid " -V, --novst Do not use VST support\n" msgstr "" " -n, --no-splash Non mostrare la schermata d'avvio\n" -#: opts.cc:58 +#: opts.cc:57 msgid " [session-name] Name of session to load\n" msgstr " [nome sessione] Nome della sessione da caricare\n" -#: opts.cc:59 +#: opts.cc:58 msgid " -C, --curvetest filename Curve algorithm debugger\n" msgstr "" -#: opts.cc:60 +#: opts.cc:59 #, fuzzy msgid " -g, --gtktheme Allow GTK to load a theme\n" msgstr " -h, --help Mostra questo messaggio\n" -#: pan_automation_time_axis.cc:59 +#: pan_automation_time_axis.cc:60 msgid "You can't graphically edit panning of more than stream" msgstr "" -#: pan_automation_time_axis.cc:79 +#: pan_automation_time_axis.cc:80 #, fuzzy msgid "add pan automation event" msgstr "aggiungi evento di automazione a " -#: panner2d.cc:588 panner_ui.cc:393 plugin_ui.cc:833 +#: panner2d.cc:589 panner_ui.cc:435 plugin_ui.cc:834 #, fuzzy msgid "Bypass" msgstr "Battute" -#: panner_ui.cc:57 panner_ui.cc:187 +#: panner_ui.cc:58 panner_ui.cc:225 #, fuzzy msgid "link" msgstr "vuoto" +#: panner_ui.cc:69 +msgid "Pan automation mode" +msgstr "Modalita' automazione pan" + #: panner_ui.cc:70 +msgid "Pan automation type" +msgstr "Tipo di automazione pan" + +#: panner_ui.cc:81 msgid "panning link control" msgstr "" -#: panner_ui.cc:72 +#: panner_ui.cc:83 msgid "panning link direction" msgstr "" -#: panner_ui.cc:197 +#: panner_ui.cc:235 msgid "L" msgstr "" -#: panner_ui.cc:296 +#: panner_ui.cc:335 +#, c-format +msgid "panner for channel %lu" +msgstr "" + +#: panner_ui.cc:337 #, c-format msgid "panner for channel %u" msgstr "" -#: panner_ui.cc:403 +#: panner_ui.cc:445 #, fuzzy msgid "Reset all" msgstr "azzera" -#: playlist_selector.cc:51 +#: playlist_selector.cc:52 #, fuzzy msgid "ardour: playlists" msgstr "azzera le posizioni" -#: playlist_selector.cc:58 +#: playlist_selector.cc:59 msgid "Playlists grouped by track" msgstr "" -#: playlist_selector.cc:97 +#: playlist_selector.cc:98 #, fuzzy msgid "ardour: playlist for " msgstr "ardour: editor delle opzioni" -#: playlist_selector.cc:113 +#: playlist_selector.cc:114 #, fuzzy msgid "Other tracks" msgstr "Nascondi traccia" -#: playlist_selector.cc:129 +#: playlist_selector.cc:130 msgid "unassigned" msgstr "" -#: plugin_selector.cc:42 +#: plugin_selector.cc:43 msgid "ardour: plugins" msgstr "" -#: plugin_selector.cc:55 +#: plugin_selector.cc:56 #, fuzzy msgid "Available LADSPA Plugins" msgstr "Plugin LADSPA disponibili" -#: plugin_selector.cc:56 +#: plugin_selector.cc:57 msgid "Type" msgstr "Tipo" -#: plugin_selector.cc:57 plugin_selector.cc:80 +#: plugin_selector.cc:58 plugin_selector.cc:81 msgid "# Inputs" msgstr "# Entrate" -#: plugin_selector.cc:58 plugin_selector.cc:81 +#: plugin_selector.cc:59 plugin_selector.cc:82 msgid "# Outputs" msgstr "# Uscite" -#: plugin_selector.cc:67 +#: plugin_selector.cc:68 msgid "Plugins to be Connected to Insert" msgstr "" -#: plugin_selector.cc:79 +#: plugin_selector.cc:80 #, fuzzy msgid "Available plugins" msgstr "Plugin VST disponibili" -#: plugin_selector.cc:97 +#: plugin_selector.cc:98 msgid "Add a plugin to the effect list" msgstr "Aggiungi un plugin alla lista degli effetti" -#: plugin_selector.cc:99 +#: plugin_selector.cc:102 msgid "Remove a plugin from the effect list" msgstr "Rimuovi un plugin dalla lista degli effetti" -#: plugin_selector.cc:101 +#: plugin_selector.cc:104 msgid "Update available plugins" msgstr "Aggiorna i plugin disponibili" -#: plugin_selector.cc:123 +#: plugin_selector.cc:126 msgid "LADSPA" msgstr "" -#: plugin_selector.cc:126 +#: plugin_selector.cc:129 msgid "VST" msgstr "VST" -#: plugin_ui.cc:83 +#: plugin_ui.cc:84 msgid "" "unknown type of editor-supplying plugin (note: no VST support in this " "version of ardour)" @@ -5466,51 +5477,52 @@ msgstr "" "tipo di plugin fornito sconosciuto (nota: nessun supporto a VST in questa " "versione di ardour)" -#: plugin_ui.cc:138 +#: plugin_ui.cc:139 msgid "Presets" msgstr "" -#: plugin_ui.cc:229 +#: plugin_ui.cc:230 #, fuzzy msgid "Controls" msgstr "Uscite di Controllo" -#: plugin_ui.cc:266 +#: plugin_ui.cc:267 msgid "Plugin Editor: could not build control element for port %1" msgstr "" "Plugin Editor: impossibile creare elemento di controllo per la porta %1" -#: plugin_ui.cc:357 -msgid "automation control" +#: plugin_ui.cc:358 +#, fuzzy +msgid "Automation control" msgstr "controllo di automazione" -#: plugin_ui.cc:853 +#: plugin_ui.cc:854 msgid "Plugin preset %1 not found" msgstr "Preset per plugin %1 non trovato" -#: plugin_ui.cc:863 +#: plugin_ui.cc:864 #, fuzzy msgid "Name of New Preset:" msgstr "Nome della nuova connessione" -#: redirect_automation_line.cc:53 +#: redirect_automation_line.cc:54 msgid "redirect automation created for non-plugin" msgstr "automazione di redirect creata per non-plugin" -#: redirect_automation_time_axis.cc:93 +#: redirect_automation_time_axis.cc:94 msgid "add automation event to " msgstr "aggiungi evento di automazione a " -#: redirect_box.cc:222 +#: redirect_box.cc:223 msgid "New send" msgstr "" -#: redirect_box.cc:223 +#: redirect_box.cc:224 #, fuzzy msgid "Show send controls" msgstr "utilizza le uscite di controllo" -#: redirect_box.cc:377 +#: redirect_box.cc:383 msgid "" "You attempted to add a plugin (%1).\n" "The plugin has %2 inputs\n" @@ -5521,7 +5533,7 @@ msgid "" "part of the signal." msgstr "" -#: redirect_box.cc:389 +#: redirect_box.cc:395 msgid "" "You attempted to add a plugin (%1).\n" "The plugin has %2 inputs\n" @@ -5533,7 +5545,7 @@ msgid "" "support this type of configuration." msgstr "" -#: redirect_box.cc:402 +#: redirect_box.cc:408 msgid "" "You attempted to add a plugin (%1).\n" "\n" @@ -5546,34 +5558,34 @@ msgid "" "Ardour does not understand what to do in such situations.\n" msgstr "" -#: redirect_box.cc:493 +#: redirect_box.cc:495 msgid "Pre-fader inserts, sends & plugins:" msgstr "" -#: redirect_box.cc:496 +#: redirect_box.cc:498 msgid "Post-fader inserts, sends & plugins:" msgstr "" -#: redirect_box.cc:642 +#: redirect_box.cc:644 msgid "" "You cannot reorder this set of redirects\n" "in that way because the inputs and\n" "outputs do not work correctly." msgstr "" -#: redirect_box.cc:747 +#: redirect_box.cc:749 #, fuzzy msgid "rename redirect" msgstr "ardour: rinomina la regione" -#: redirect_box.cc:824 redirect_box.cc:872 +#: redirect_box.cc:826 redirect_box.cc:874 msgid "" "Copying the set of redirects on the clipboard failed,\n" "probably because the I/O configuration of the plugins\n" "could not match the configuration of this track." msgstr "" -#: redirect_box.cc:894 +#: redirect_box.cc:896 #, fuzzy msgid "" "Do you really want to remove all redirects from this track?\n" @@ -5582,7 +5594,7 @@ msgstr "" "Si vuole realmente rimuovere la traccia \"%1\" ?\n" "(questa azione non potrà essere annullata)" -#: redirect_box.cc:897 +#: redirect_box.cc:899 #, fuzzy msgid "" "Do you really want to remove all redirects from this bus?\n" @@ -5591,246 +5603,258 @@ msgstr "" "Si vuole realmente rimuovere la traccia \"%1\" ?\n" "(questa azione non potrà essere annullata)" -#: redirect_box.cc:902 +#: redirect_box.cc:904 #, fuzzy msgid "Yes, remove them all" msgstr "Si, rimuovi." -#: redirect_box.cc:938 +#: redirect_box.cc:940 #, fuzzy msgid "ardour: %1" msgstr "ardour: orologio" -#: redirect_box.cc:980 +#: redirect_box.cc:982 #, fuzzy msgid "ardour: %1: %2 (by %3)" msgstr "ardour: regione" #. new stuff -#: redirect_box.cc:1052 +#: redirect_box.cc:1054 msgid "New Plugin ..." msgstr "" -#: redirect_box.cc:1053 +#: redirect_box.cc:1055 #, fuzzy msgid "New Insert" msgstr "Nuova entrata" -#: redirect_box.cc:1054 +#: redirect_box.cc:1056 msgid "New Send ..." msgstr "" -#: redirect_box.cc:1066 +#: redirect_box.cc:1068 #, fuzzy msgid "Deselect All" msgstr "Seleziona tutto" -#: redirect_box.cc:1073 +#: redirect_box.cc:1075 #, fuzzy msgid "Activate all" msgstr "Attiva" -#: redirect_box.cc:1074 +#: redirect_box.cc:1076 #, fuzzy msgid "Deactivate all" msgstr "Disattiva" -#: region_editor.cc:44 +#: region_editor.cc:45 msgid "NAME:" msgstr "NOME:" -#: region_editor.cc:45 +#: region_editor.cc:46 msgid "lock" msgstr "blocca" -#: region_editor.cc:47 +#: region_editor.cc:48 msgid "opaque" msgstr "opaco" -#: region_editor.cc:52 +#: region_editor.cc:49 region_editor.cc:192 region_editor.cc:226 +msgid "active" +msgstr "attivo" + +#: region_editor.cc:50 +msgid "visible" +msgstr "visibile" + +#: region_editor.cc:53 msgid "Layer" msgstr "Livello" -#: region_editor.cc:60 +#: region_editor.cc:54 +msgid "play" +msgstr "suona" + +#: region_editor.cc:61 msgid "ENVELOPE" msgstr "" -#: region_editor.cc:106 +#: region_editor.cc:107 msgid "mute this region" msgstr "Metti in muto questa regione" -#: region_editor.cc:107 +#: region_editor.cc:108 msgid "regions underneath this one cannot be heard" msgstr "le regioni al di sotto di questa non posssono essere udite" -#: region_editor.cc:108 +#: region_editor.cc:109 msgid "prevent any changes to this region" msgstr "impedisci qualsiasi cambio a questa regione" -#: region_editor.cc:109 +#: region_editor.cc:110 msgid "use the gain envelope during playback" msgstr "usa la curva di gain suonando" -#: region_editor.cc:110 +#: region_editor.cc:111 msgid "show the gain envelope" msgstr "mostra la curva di gain" -#: region_editor.cc:111 +#: region_editor.cc:112 msgid "use fade in curve during playback" msgstr "usa la curva di smorzamento in entrata, suonando" -#: region_editor.cc:112 +#: region_editor.cc:113 msgid "use fade out curve during playback" msgstr "usa la curva di smorzamento in uscita, suonando" -#: region_editor.cc:113 +#: region_editor.cc:114 msgid "audition this region" msgstr "fai l'audition di questa regione" -#: region_editor.cc:146 +#: region_editor.cc:147 msgid "START:" msgstr "INIZIO:" -#: region_editor.cc:148 +#: region_editor.cc:149 msgid "END:" msgstr "FINE" -#: region_editor.cc:150 +#: region_editor.cc:151 msgid "LENGTH:" msgstr "LUNGHEZZA" -#: region_editor.cc:190 +#: region_editor.cc:191 msgid "FADE IN" msgstr "SMORZA ENTRATA" -#: region_editor.cc:192 region_editor.cc:226 +#: region_editor.cc:193 region_editor.cc:227 msgid "msecs" msgstr "msec" -#: region_editor.cc:224 +#: region_editor.cc:225 msgid "FADE OUT" msgstr "SMORZA USCITA" -#: region_editor.cc:264 +#: region_editor.cc:265 msgid "ardour: region " msgstr "ardour: regione" -#: region_editor.cc:401 +#: region_editor.cc:402 msgid "fade in edit" msgstr "modifica lo smorzamento in entrata" -#: region_editor.cc:413 +#: region_editor.cc:414 msgid "fade out edit" msgstr "modifica lo smorzamento in uscita" -#: regionview.cc:1140 +#: regionview.cc:1146 #, fuzzy msgid "add gain control point" msgstr "Rimuovi il punto di sincronizzazione" -#: route_params_ui.cc:88 +#: route_params_ui.cc:89 msgid "Tracks/Buses" msgstr "Tracce/Bus" -#: route_params_ui.cc:108 +#: route_params_ui.cc:109 #, fuzzy msgid "Pre-fader Redirects" msgstr "Pre Redirezionamenti" -#: route_params_ui.cc:109 +#: route_params_ui.cc:110 #, fuzzy msgid "Post-fader Redirects" msgstr "Post Redirezionamenti" -#: route_params_ui.cc:141 +#: route_params_ui.cc:144 #, fuzzy msgid "ardour: track/bus inspector" msgstr "ardour: aggiungi traccia/bus" -#: route_params_ui.cc:142 +#: route_params_ui.cc:145 msgid "ardour_route_parameters" msgstr "" -#: route_params_ui.cc:199 +#: route_params_ui.cc:202 msgid "route display list item for renamed route not found!" msgstr "" -#: route_params_ui.cc:451 +#: route_params_ui.cc:453 msgid "NO TRACK" msgstr "NESSUNA TRACCIA" -#: route_params_ui.cc:693 +#: route_params_ui.cc:695 #, fuzzy msgid "ardour: track/bus inspector: " msgstr "ardour: aggiungi traccia/bus" -#: route_params_ui.cc:697 +#: route_params_ui.cc:699 msgid "No Route Selected" msgstr "Nessun Route Selezionato" -#: route_params_ui.cc:698 +#: route_params_ui.cc:700 #, fuzzy msgid "ardour: track/bus/inspector: no route selected" msgstr "ardour: parametri di route: nessun route selezionato" #. ctrl-shift-click applies change to all routes -#: route_ui.cc:133 +#: route_ui.cc:134 #, fuzzy msgid "mute change" msgstr "Imposta l'intervallo di Punch" #. ctrl-shift-click applies change to all routes #. ctrl-alt-click: exclusively solo this track, not a toggle */ -#: route_ui.cc:208 route_ui.cc:218 +#: route_ui.cc:209 route_ui.cc:219 #, fuzzy msgid "solo change" msgstr "Intervallo di loop" -#: route_ui.cc:281 +#: route_ui.cc:282 msgid "rec-enable change" msgstr "" -#: route_ui.cc:472 +#: route_ui.cc:479 msgid "Solo-safe" msgstr "" -#: route_ui.cc:480 route_ui.cc:523 +#: route_ui.cc:487 route_ui.cc:530 msgid "MIDI Bind" msgstr "" -#: route_ui.cc:494 +#: route_ui.cc:501 msgid "Pre Fader" msgstr "" -#: route_ui.cc:501 +#: route_ui.cc:508 msgid "Post Fader" msgstr "" -#: route_ui.cc:508 +#: route_ui.cc:515 msgid "Control Outs" msgstr "Uscite di Controllo" -#: route_ui.cc:515 +#: route_ui.cc:522 msgid "Main Outs" msgstr "Uscite Principali" -#: route_ui.cc:552 +#: route_ui.cc:559 msgid "mix group solo change" msgstr "" -#: route_ui.cc:586 +#: route_ui.cc:593 msgid "mix group mute change" msgstr "" -#: route_ui.cc:602 +#: route_ui.cc:609 msgid "mix group rec-enable change" msgstr "" -#: route_ui.cc:619 visual_time_axis.cc:236 +#: route_ui.cc:626 visual_time_axis.cc:237 msgid "ardour: color selection" msgstr "ardour: selezione del colore" -#: route_ui.cc:695 +#: route_ui.cc:702 #, fuzzy msgid "" "Do you really want to remove track \"%1\" ?\n" @@ -5841,7 +5865,7 @@ msgstr "" "Si vuole realmente rimuovere la traccia \"%1\" ?\n" "(questa azione non potrà essere annullata)" -#: route_ui.cc:697 +#: route_ui.cc:704 msgid "" "Do you really want to remove bus \"%1\" ?\n" "(cannot be undone)" @@ -5849,11 +5873,11 @@ msgstr "" "Si vuole realmente rimuovere il bus \"%1\" ?\n" "(questa azione non potrà essere annullata)" -#: route_ui.cc:701 visual_time_axis.cc:278 +#: route_ui.cc:708 visual_time_axis.cc:279 msgid "Yes, remove it." msgstr "Si, rimuovi." -#: route_ui.cc:730 +#: route_ui.cc:737 #, fuzzy msgid "New Name: " msgstr "nuovo nome: " @@ -5911,148 +5935,149 @@ msgstr "Impossibile accedere al file audio" msgid "Name for Field" msgstr "Nome per la Regione" -#: sfdb_ui.cc:333 +#: sfdb_ui.cc:335 msgid "Split Channels" msgstr "Dividi i Canali" -#: sfdb_ui.cc:340 +#: sfdb_ui.cc:342 msgid "Create a region for each channel" msgstr "" -#: sfdb_ui.cc:342 +#: sfdb_ui.cc:344 msgid "Embed" msgstr "" -#: sfdb_ui.cc:344 +#: sfdb_ui.cc:346 #, fuzzy msgid "Link to an external file" msgstr "Inserisci un file audio esterno" -#: sfdb_ui.cc:346 +#: sfdb_ui.cc:348 msgid "Import" msgstr "Importa" -#: sfdb_ui.cc:348 +#: sfdb_ui.cc:350 msgid "Copy a file to the session folder" msgstr "" -#: sfdb_ui.cc:412 +#: sfdb_ui.cc:414 #, fuzzy msgid "programming error: %1" msgstr "errore di programmazione: " -#: tempo_dialog.cc:17 tempo_dialog.cc:34 +#: tempo_dialog.cc:18 tempo_dialog.cc:35 msgid "Beats per minute" msgstr "Battiti al minuto" -#: tempo_dialog.cc:20 tempo_dialog.cc:37 tempo_dialog.cc:153 -#: tempo_dialog.cc:171 +#: tempo_dialog.cc:21 tempo_dialog.cc:38 tempo_dialog.cc:203 +#: tempo_dialog.cc:221 msgid "Bar" msgstr "Battuta" -#: tempo_dialog.cc:21 tempo_dialog.cc:38 tempo_dialog.cc:154 -#: tempo_dialog.cc:172 +#: tempo_dialog.cc:22 tempo_dialog.cc:39 tempo_dialog.cc:204 +#: tempo_dialog.cc:222 msgid "Beat" msgstr "Battito" -#: tempo_dialog.cc:23 tempo_dialog.cc:40 tempo_dialog.cc:155 -#: tempo_dialog.cc:173 +#: tempo_dialog.cc:24 tempo_dialog.cc:41 tempo_dialog.cc:205 +#: tempo_dialog.cc:223 msgid "Location" msgstr "Posizione" -#: tempo_dialog.cc:149 tempo_dialog.cc:167 +#: tempo_dialog.cc:199 tempo_dialog.cc:217 msgid "Meter denominator" msgstr "Denominatore per il Meter" -#: tempo_dialog.cc:150 tempo_dialog.cc:168 +#: tempo_dialog.cc:200 tempo_dialog.cc:218 msgid "Beats per bar" msgstr "Battiti per battuta" -#: tempo_dialog.cc:186 tempo_dialog.cc:197 +#: tempo_dialog.cc:236 tempo_dialog.cc:247 msgid "whole (1)" msgstr "intero (1)" -#: tempo_dialog.cc:187 tempo_dialog.cc:199 +#: tempo_dialog.cc:237 tempo_dialog.cc:249 msgid "second (2)" msgstr "mezzo (2)" -#: tempo_dialog.cc:188 tempo_dialog.cc:201 +#: tempo_dialog.cc:238 tempo_dialog.cc:251 msgid "third (3)" msgstr "terzo (3)" -#: tempo_dialog.cc:189 tempo_dialog.cc:203 tempo_dialog.cc:211 +#: tempo_dialog.cc:239 tempo_dialog.cc:253 tempo_dialog.cc:261 msgid "quarter (4)" msgstr "quarto (4)" -#: tempo_dialog.cc:190 tempo_dialog.cc:205 +#: tempo_dialog.cc:240 tempo_dialog.cc:255 msgid "eighth (8)" msgstr "ottavo (8)" -#: tempo_dialog.cc:191 tempo_dialog.cc:207 +#: tempo_dialog.cc:241 tempo_dialog.cc:257 msgid "sixteenth (16)" msgstr "sedicesimo (16)" -#: tempo_dialog.cc:192 tempo_dialog.cc:209 +#: tempo_dialog.cc:242 tempo_dialog.cc:259 msgid "thirty-second (32)" msgstr "trentaduesimo (32)" -#: tempo_dialog.cc:321 +#: tempo_dialog.cc:420 msgid "garbaged note type entry (%1)" msgstr "" -#: tempo_dialog.cc:331 +#: tempo_dialog.cc:430 msgid "incomprehensible note type entry (%1)" msgstr "" -#: time_axis_view.cc:111 +#: time_axis_view.cc:112 msgid "gTortnam" msgstr "" -#: time_axis_view.cc:548 +#: time_axis_view.cc:549 msgid "Largest" msgstr "Ampissimo" -#: time_axis_view.cc:549 +#: time_axis_view.cc:550 msgid "Large" msgstr "Più ampio" -#: time_axis_view.cc:550 +#: time_axis_view.cc:551 msgid "Larger" msgstr "Ampio" -#: time_axis_view.cc:552 +#: time_axis_view.cc:553 msgid "Smaller" msgstr "Piccolo" -#: time_axis_view.cc:553 +#: time_axis_view.cc:554 msgid "Small" msgstr "Più piccolo" -#: time_axis_view.cc:869 +#: time_axis_view.cc:870 msgid "unknown track height name \"%1\" in XML GUI information" msgstr "" -#: time_axis_view_item.cc:71 +#. first constructed item sets up font info +#: time_axis_view_item.cc:79 msgid "TimeAxisViewItemName" msgstr "" -#: time_axis_view_item.cc:271 +#: time_axis_view_item.cc:298 msgid "new duration %1 frames is out of bounds for %2" msgstr "" -#: time_selection.cc:40 +#: time_selection.cc:41 msgid "programming error: request for non-existent audio range (%1)!" msgstr "" -#: utils.cc:106 utils.cc:149 +#: utils.cc:107 utils.cc:150 msgid "bad XPM header %1" msgstr "" -#: utils.cc:331 +#: utils.cc:332 msgid "missing RGBA style for \"%1\"" msgstr "" -#: visual_time_axis.cc:275 +#: visual_time_axis.cc:276 msgid "" "Do you really want to remove track \"%1\" ?\n" "(cannot be undone)" @@ -6060,14 +6085,71 @@ msgstr "" "Si vuole realmente rimuovere la traccia \"%1\" ?\n" "(questa azione non potrà essere annullata)" -#: visual_time_axis.cc:324 +#: visual_time_axis.cc:325 msgid "new name: " msgstr "nuovo nome: " -#: visual_time_axis.cc:335 +#: visual_time_axis.cc:336 msgid "A track already exists with that name" msgstr "esiste già una traccia con quel nome" +#, fuzzy +#~ msgid "set selected trackview" +#~ msgstr "Inserisci selezione" + +#, fuzzy +#~ msgid "set selected control point" +#~ msgstr "Rimuovi il punto di sincronizzazione" + +#, fuzzy +#~ msgid "set selected regionview" +#~ msgstr "Esegui la regione selezionata come loop" + +#~ msgid "Start a new session\n" +#~ msgstr "Inizia una nuova sessione\n" + +#~ msgid "via Session menu" +#~ msgstr "tramite il menu Sessione" + +#, fuzzy +#~ msgid "Advanced" +#~ msgstr "Avanzate..." + +#, fuzzy +#~ msgid "Select a File" +#~ msgstr "Seleziona tutto" + +#, fuzzy +#~ msgid "Track/Bus connection options" +#~ msgstr "Tracce/Bus" + +#~ msgid "RECORD" +#~ msgstr "REGISTRA" + +#~ msgid "INPUT" +#~ msgstr "ENTRATA" + +#~ msgid "OUTPUT" +#~ msgstr "USCITA" + +#~ msgid "Gain automation mode" +#~ msgstr "Modalita' automazione gain" + +#~ msgid "Gain automation type" +#~ msgstr "Tipo di automazione gain" + +#~ msgid "gain automation mode" +#~ msgstr "modalita' di automazione gain" + +#~ msgid "gain automation state" +#~ msgstr "stato dell'automazione gain" + +#~ msgid "pan automation state" +#~ msgstr "stato dell'automazione pan" + +#~ msgid "no group" +#~ msgstr "nessun gruppo" + #, fuzzy #~ msgid "normal" #~ msgstr "Normale" @@ -6310,9 +6392,6 @@ msgstr "esiste già una traccia con quel nome" #~ msgid "AND" #~ msgstr "E" -#~ msgid "OR" -#~ msgstr "O" - #~ msgid "ardour: locate soundfiles" #~ msgstr "ardour: localizza file audio" @@ -6328,9 +6407,6 @@ msgstr "esiste già una traccia con quel nome" #~ msgid "Ardour: Search Results" #~ msgstr "Ardour: Risultati della Ricerca" -#~ msgid "Mix Groups" -#~ msgstr "Gruppi di mixaggio" - #~ msgid "Hide All AudioTrack MixerStrips" #~ msgstr "Nascondi tutte le Tracce del Mixer" @@ -6343,9 +6419,6 @@ msgstr "esiste già una traccia con quel nome" #~ msgid "Name for new mix group" #~ msgstr "Nome del nuovo gruppo di mixaggio" -#~ msgid "Session name:" -#~ msgstr "Nome della sessione:" - #~ msgid "Create" #~ msgstr "Crea" @@ -6378,17 +6451,9 @@ msgstr "esiste già una traccia con quel nome" #~ "Se si vuole utilizzare un sample rate differente\n" #~ "bisogna chiudere e riavviare JACK" -#, fuzzy -#~ msgid "Session template" -#~ msgstr "usa un modello esistente" - #~ msgid "blank" #~ msgstr "vuoto" -#, fuzzy -#~ msgid "No template" -#~ msgstr "-modello" - #, fuzzy #~ msgid "Slave to MTC" #~ msgstr "Invia MTC" @@ -6402,9 +6467,6 @@ msgstr "esiste già una traccia con quel nome" #~ msgid "Display" #~ msgstr "Interfaccia" -#~ msgid "Use as click" -#~ msgstr "Usa come click" - #~ msgid "--unknown--" #~ msgstr "--sconosciuto--" diff --git a/gtk2_ardour/po/pt_BR.po b/gtk2_ardour/po/pt_BR.po index da0bb8b2e3..92c0d7934a 100644 --- a/gtk2_ardour/po/pt_BR.po +++ b/gtk2_ardour/po/pt_BR.po @@ -10,7 +10,7 @@ msgid "" msgstr "" "Project-Id-Version: ardour 0.688.4\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-04-25 17:46-0400\n" +"POT-Creation-Date: 2006-06-21 18:09-0400\n" "PO-Revision-Date: 2005-08-15 21:50-0000\n" "Last-Translator: Chris Ross, Alexander Franca & Leandro Marco\n" "Language-Team: Portuguese\n" @@ -18,150 +18,150 @@ msgstr "" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" -#: about.cc:119 +#: about.cc:120 msgid "Paul Davis" msgstr "" -#: about.cc:120 +#: about.cc:121 #, fuzzy msgid "Jesse Chappell" msgstr "reiniciar todos" -#: about.cc:121 +#: about.cc:122 msgid "Taybin Rutkin" msgstr "" -#: about.cc:122 +#: about.cc:123 msgid "Marcus Andersson" msgstr "" -#: about.cc:123 +#: about.cc:124 msgid "Jeremy Hall" msgstr "" -#: about.cc:124 +#: about.cc:125 msgid "Steve Harris" msgstr "" -#: about.cc:125 +#: about.cc:126 msgid "Tim Mayberry" msgstr "" -#: about.cc:126 +#: about.cc:127 msgid "Mark Stewart" msgstr "" -#: about.cc:127 +#: about.cc:128 msgid "Sam Chessman" msgstr "" -#: about.cc:128 +#: about.cc:129 msgid "Jack O'Quin" msgstr "" -#: about.cc:129 +#: about.cc:130 msgid "Matt Krai" msgstr "" -#: about.cc:130 +#: about.cc:131 msgid "Ben Bell" msgstr "" -#: about.cc:131 +#: about.cc:132 msgid "Gerard van Dongen" msgstr "" -#: about.cc:132 +#: about.cc:133 msgid "Thomas Charbonnel" msgstr "" -#: about.cc:133 +#: about.cc:134 msgid "Nick Mainsbridge" msgstr "" -#: about.cc:134 +#: about.cc:135 msgid "Colin Law" msgstr "" -#: about.cc:135 +#: about.cc:136 msgid "Sampo Savolainen" msgstr "" -#: about.cc:136 +#: about.cc:137 msgid "Joshua Leach" msgstr "" -#: about.cc:137 +#: about.cc:138 msgid "Rob Holland" msgstr "" -#: about.cc:138 +#: about.cc:139 msgid "Per Sigmond" msgstr "" -#: about.cc:139 +#: about.cc:140 msgid "Doug Mclain" msgstr "" -#: about.cc:140 +#: about.cc:141 msgid "Petter Sundlöf" msgstr "" -#: about.cc:145 +#: about.cc:146 msgid "" "French:\n" "\tAlain Fréhel \n" msgstr "" -#: about.cc:146 +#: about.cc:147 msgid "" "German:\n" "\tKarsten Petersen \n" msgstr "" -#: about.cc:147 +#: about.cc:148 msgid "" "Italian:\n" "\tFilippo Pappalardo \n" msgstr "" -#: about.cc:148 +#: about.cc:149 msgid "" "Portuguese:\n" "\tRui Nuno Capela \n" msgstr "" -#: about.cc:149 +#: about.cc:150 msgid "" "Brazilian Portuguese:\n" "\tAlexander da Franca Fernandes \n" "\tChris Ross \n" msgstr "" -#: about.cc:151 +#: about.cc:152 msgid "" "Spanish:\n" "\t Alex Krohn \n" msgstr "" -#: about.cc:152 +#: about.cc:153 msgid "" "Russian:\n" "\t Igor Blinov \n" msgstr "" -#: about.cc:180 +#: about.cc:181 msgid "Copyright (C) 1999-2005 Paul Davis\n" msgstr "" -#: about.cc:181 +#: about.cc:182 msgid "" "Ardour comes with ABSOLUTELY NO WARRANTY\n" "This is free software, and you are welcome to redistribute it\n" "under certain conditions; see the file COPYING for details.\n" msgstr "" -#: about.cc:187 +#: about.cc:188 #, fuzzy msgid "" "%1\n" @@ -170,52 +170,52 @@ msgstr "" "Ardour: %1\n" "(construído com ardour/gtk %2.%3.%4 libardour: %5.%6.%7)" -#: actions.cc:260 +#: actions.cc:261 msgid "programmer error: %1 %2" msgstr "" -#: add_route_dialog.cc:61 +#: add_route_dialog.cc:62 msgid "ardour: add track/bus" msgstr "ardour: adicionar trilhas/barramento" #. path = "1" -#: add_route_dialog.cc:62 editor_route_list.cc:72 +#: add_route_dialog.cc:63 editor_route_list.cc:73 msgid "Tracks" msgstr "Trilhas" #. path = "0" -#: add_route_dialog.cc:63 editor_route_list.cc:69 +#: add_route_dialog.cc:64 editor_route_list.cc:70 msgid "Busses" msgstr "Barramentos" -#: add_route_dialog.cc:95 plugin_ui.cc:832 +#: add_route_dialog.cc:96 plugin_ui.cc:833 msgid "Add" msgstr "Adicionar" -#: add_route_dialog.cc:113 +#: add_route_dialog.cc:114 msgid "Name (template)" msgstr "Nome (esquema)" -#: add_route_dialog.cc:119 +#: add_route_dialog.cc:120 #, fuzzy msgid "Channel Configuration" msgstr "Cancelar importação" -#: add_route_dialog.cc:176 editor.cc:131 editor.cc:3660 time_axis_view.cc:551 +#: add_route_dialog.cc:177 editor.cc:134 editor.cc:3688 time_axis_view.cc:552 msgid "Normal" msgstr "Normal" -#: add_route_dialog.cc:178 +#: add_route_dialog.cc:179 #, fuzzy msgid "Tape" msgstr "Estado" -#: add_route_dialog.cc:195 +#: add_route_dialog.cc:196 #, fuzzy msgid "Mono" msgstr "mono" -#: add_route_dialog.cc:197 +#: add_route_dialog.cc:198 #, fuzzy msgid "Stereo" msgstr "estéreo" @@ -301,31 +301,11 @@ msgstr "AUDIÇÃO" msgid "SOLO" msgstr "SOLO" -#: ardour_ui.cc:207 -msgid "" -"You cannot record-enable\n" -"track %1\n" -"because it has no input connections.\n" -"You would be wasting space recording silence." -msgstr "" -"Vocãonão pode habilitar para gravaãoo\n" -"a trilha %1\n" -"porque ela não tem conexãos de entrada.\n" -"Você estaria desperdiçando espaço gravando silêncio." - -#: ardour_ui.cc:236 -msgid "no vertical meter strip image found" -msgstr "" - -#: ardour_ui.cc:243 -msgid "no horizontal meter strip image found" -msgstr "" - -#: ardour_ui.cc:410 +#: ardour_ui.cc:375 msgid "quit" msgstr "sair" -#: ardour_ui.cc:419 +#: ardour_ui.cc:384 msgid "" "Ardour was unable to save your session.\n" "\n" @@ -338,31 +318,31 @@ msgstr "" "Se mesmo assim você deseja sair, por favor utilize\n" "a opção \"Apenas Sair\"." -#: ardour_ui.cc:438 +#: ardour_ui.cc:403 msgid "ardour: save session?" msgstr "ardour: salvar sessão?" -#: ardour_ui.cc:445 +#: ardour_ui.cc:410 msgid "Don't %1" msgstr "Não %1" -#: ardour_ui.cc:447 +#: ardour_ui.cc:412 msgid "Just %1" msgstr "Apenas %1" -#: ardour_ui.cc:449 +#: ardour_ui.cc:414 msgid "Save and %1" msgstr "Salvar e %1" -#: ardour_ui.cc:461 +#: ardour_ui.cc:426 msgid "session" msgstr "sessão" -#: ardour_ui.cc:463 +#: ardour_ui.cc:428 msgid "snapshot" msgstr "capturar instantâneo" -#: ardour_ui.cc:465 +#: ardour_ui.cc:430 #, fuzzy msgid "" "The %1\"%2\"\n" @@ -382,83 +362,83 @@ msgstr "" "\n" "O que você quer fazer?" -#: ardour_ui.cc:479 +#: ardour_ui.cc:444 msgid "Prompter" msgstr "" -#: ardour_ui.cc:538 +#: ardour_ui.cc:503 #, c-format msgid "disconnected" msgstr "desconectado" -#: ardour_ui.cc:545 +#: ardour_ui.cc:510 #, c-format msgid "SR: %.1f kHz / %4.1f msecs" msgstr "" -#: ardour_ui.cc:549 +#: ardour_ui.cc:514 #, c-format msgid "SR: %u kHz / %4.1f msecs" msgstr "" -#: ardour_ui.cc:562 +#: ardour_ui.cc:527 #, c-format msgid "DSP Load: %.1f%%" msgstr "DSP Carregada: %.1f%%" -#: ardour_ui.cc:572 +#: ardour_ui.cc:537 #, c-format msgid "Buffers p:%%% c:%%%" msgstr "" -#: ardour_ui.cc:599 +#: ardour_ui.cc:564 msgid "space: 24hrs+" msgstr "espaço: 24hrs+" -#: ardour_ui.cc:629 +#: ardour_ui.cc:594 #, c-format msgid "space: %02dh:%02dm:%02ds" msgstr "espaço: %02dh:%02dm:%02ds" -#: ardour_ui.cc:668 +#: ardour_ui.cc:633 msgid "programming error: impossible control method" msgstr "" # -#: ardour_ui.cc:776 new_session_dialog.cc:89 +#: ardour_ui.cc:741 new_session_dialog.cc:294 #, fuzzy msgid "Recent Sessions" msgstr "abrir sessão" # #. ardour sessions are folders -#: ardour_ui.cc:867 +#: ardour_ui.cc:834 msgid "open session" msgstr "abrir sessão" -#: ardour_ui.cc:873 +#: ardour_ui.cc:840 #, fuzzy msgid "Ardour sessions" msgstr "ardour: salvar sessão?" -#: ardour_ui.cc:906 +#: ardour_ui.cc:873 msgid "Patience is a virtue.\n" msgstr "Paciência é uma virtude.\n" -#: ardour_ui.cc:915 +#: ardour_ui.cc:882 msgid "You cannot add a track without a session already loaded." msgstr "" "Você não pode adicionar uma trilha se uma sessão não estiver carregada." -#: ardour_ui.cc:922 +#: ardour_ui.cc:889 msgid "could not create new audio track" msgstr "não pôde criar uma nova trilha de áudio" -#: ardour_ui.cc:926 +#: ardour_ui.cc:893 msgid "could not create new audio bus" msgstr "não foi possível criar um novo barramento de áudio" -#: ardour_ui.cc:945 +#: ardour_ui.cc:912 msgid "" "There are insufficient JACK ports available\n" "to create a new track or bus.\n" @@ -470,7 +450,7 @@ msgstr "" "Você deve salvar Ardour, sair e\n" "reiniciar o JACK com mais portas." -#: ardour_ui.cc:1069 +#: ardour_ui.cc:1036 msgid "" "Please create 1 or more track\n" "before trying to record.\n" @@ -480,7 +460,7 @@ msgstr "" "antes de tentar gravar.\n" "Vir o menu de Sessão." -#: ardour_ui.cc:1298 +#: ardour_ui.cc:1265 msgid "" "JACK has either been shutdown or it\n" "disconnected Ardour because Ardour\n" @@ -493,42 +473,40 @@ msgstr "" "A sessão corrente deverá ser salva e\n" "o serviço JACK reiniciado, tal como o Ardour." -#: ardour_ui.cc:1315 +#: ardour_ui.cc:1282 msgid "Unable to create all required ports" msgstr "Impossível criar todas as portas solicitadas" -#: ardour_ui.cc:1323 +#: ardour_ui.cc:1290 msgid "Unable to start the session running" msgstr "Impossível iniciar a sessão" -#: ardour_ui.cc:1459 +#: ardour_ui.cc:1426 msgid "No Stream" msgstr "Sem fluxo" -#: ardour_ui.cc:1486 ardour_ui.cc:1505 +#: ardour_ui.cc:1453 ardour_ui.cc:1472 msgid "none" msgstr "nenhum" -#: ardour_ui.cc:1495 ardour_ui.cc:1514 automation_time_axis.cc:183 -#: automation_time_axis.cc:212 automation_time_axis.cc:459 mixer_strip.cc:174 -#: mixer_strip.cc:186 mixer_strip.cc:881 plugin_ui.cc:391 plugin_ui.cc:634 +#: ardour_ui.cc:1462 ardour_ui.cc:1481 msgid "off" msgstr "desligado" -#: ardour_ui.cc:1538 +#: ardour_ui.cc:1505 #, fuzzy msgid "Name of New Snapshot" msgstr "Nome para a imagem capturada" -#: ardour_ui.cc:1684 +#: ardour_ui.cc:1651 msgid "Name for mix template:" msgstr "Nome para o esquema de mixer" -#: ardour_ui.cc:1685 +#: ardour_ui.cc:1652 msgid "-template" msgstr "-esquema/template" -#: ardour_ui.cc:1836 +#: ardour_ui.cc:1809 msgid "" "You do not have write access to this session.\n" "This prevents the session from being loaded." @@ -536,15 +514,15 @@ msgstr "" "Você não tem permissão de escrita nesta sessão\n" "Isto impede que a sessão seja aberta." -#: ardour_ui.cc:1849 ardour_ui.cc:1904 +#: ardour_ui.cc:1822 ardour_ui.cc:1877 msgid "Session \"%1 (snapshot %2)\" did not load successfully" msgstr "A sessão \"%1 (instantâneo %2)\" não pôde ser carregada" -#: ardour_ui.cc:1960 +#: ardour_ui.cc:1933 msgid "No audio files were ready for cleanup" msgstr "" -#: ardour_ui.cc:1964 +#: ardour_ui.cc:1937 #, fuzzy msgid "" "If this seems suprising, \n" @@ -557,23 +535,23 @@ msgstr "" "Eles podem conter regiões que requeiram a existência\n" "de arquivos não utlizados." -#: ardour_ui.cc:1973 +#: ardour_ui.cc:1946 msgid "ardour: cleanup" msgstr "ardour: limpar" -#: ardour_ui.cc:2009 ardour_ui.cc:2015 +#: ardour_ui.cc:1982 ardour_ui.cc:1988 msgid "files were" msgstr "" -#: ardour_ui.cc:2011 ardour_ui.cc:2017 +#: ardour_ui.cc:1984 ardour_ui.cc:1990 msgid "file was" msgstr "" -#: ardour_ui.cc:2058 +#: ardour_ui.cc:2031 msgid "Are you sure you want to cleanup?" msgstr "" -#: ardour_ui.cc:2063 +#: ardour_ui.cc:2036 #, fuzzy msgid "" "Cleanup is a destructive operation.\n" @@ -586,24 +564,24 @@ msgstr "" "você continuar. Arquivos de audio não usados serão movidos\n" "para \"dead sounds\"" -#: ardour_ui.cc:2069 +#: ardour_ui.cc:2042 #, fuzzy msgid "Clean Up" msgstr "Limpar" -#: ardour_ui.cc:2072 +#: ardour_ui.cc:2045 msgid "CleanupDialog" msgstr "Limpar" -#: ardour_ui.cc:2073 +#: ardour_ui.cc:2046 msgid "ardour_cleanup" msgstr "ardour_limpar" -#: ardour_ui.cc:2092 +#: ardour_ui.cc:2065 msgid "cleaned files" msgstr "arquivos limpos" -#: ardour_ui.cc:2093 +#: ardour_ui.cc:2066 #, fuzzy msgid "" "The following %1 %2 not in use and \n" @@ -619,11 +597,11 @@ msgstr "" "isto vai liberar %3 %4bytes\n" "de espaço no disco rígido" -#: ardour_ui.cc:2118 +#: ardour_ui.cc:2091 msgid "deleted file" msgstr "arquivo removido" -#: ardour_ui.cc:2119 +#: ardour_ui.cc:2092 #, fuzzy msgid "" "The following %1 %2 deleted from\n" @@ -633,11 +611,11 @@ msgstr "" "Os seguintes %1 arquivo%2 foram deletados, liberando %3 %4bytes de espaço no " "disco rígido" -#: ardour_ui.cc:2242 +#: ardour_ui.cc:2215 msgid "Recording was stopped because your system could not keep up." msgstr "A gravação foi encerrada porque seu sistema não consegue acompanhar" -#: ardour_ui.cc:2265 +#: ardour_ui.cc:2238 msgid "" "The disk system on your computer\n" "was not able to keep up with Ardour.\n" @@ -646,7 +624,7 @@ msgid "" "quickly enough to keep up with recording.\n" msgstr "" -#: ardour_ui.cc:2284 +#: ardour_ui.cc:2257 msgid "" "The disk system on your computer\n" "was not able to keep up with Ardour.\n" @@ -655,7 +633,7 @@ msgid "" "quickly enough to keep up with playback.\n" msgstr "" -#: ardour_ui.cc:2310 +#: ardour_ui.cc:2283 msgid "" "This session appears to have been in\n" "middle of recording when ardour or\n" @@ -666,362 +644,362 @@ msgid "" "what you would like to do.\n" msgstr "" -#: ardour_ui.cc:2320 +#: ardour_ui.cc:2293 msgid "Recover from crash" msgstr "" -#: ardour_ui.cc:2321 +#: ardour_ui.cc:2294 msgid "Ignore crash data" msgstr "" -#: ardour_ui.cc:2339 +#: ardour_ui.cc:2312 msgid "Could not disconnect from JACK" msgstr "Não foi possível se desconectar ao servidor JACK" -#: ardour_ui.cc:2352 +#: ardour_ui.cc:2325 #, fuzzy msgid "Could not reconnect to JACK" msgstr "Não foi possível se conectar ao servidor JACK" -#: ardour_ui2.cc:59 +#: ardour_ui2.cc:60 msgid "UI: cannot setup editor" msgstr "não foi possível iniciar o editor" -#: ardour_ui2.cc:64 +#: ardour_ui2.cc:65 msgid "UI: cannot setup mixer" msgstr "não foi possível iniciar o mixer" -#: ardour_ui2.cc:90 +#: ardour_ui2.cc:91 msgid "MMC + Local" msgstr "" -#: ardour_ui2.cc:91 +#: ardour_ui2.cc:92 msgid "MMC" msgstr "" -#: ardour_ui2.cc:92 +#: ardour_ui2.cc:93 msgid "Local" msgstr "" -#: ardour_ui2.cc:109 +#: ardour_ui2.cc:110 msgid "MMC ID" msgstr "" -#: ardour_ui2.cc:290 +#: ardour_ui2.cc:291 msgid "Play from playhead" msgstr "Reproduzir a partir do início" -#: ardour_ui2.cc:291 +#: ardour_ui2.cc:292 msgid "Stop playback" msgstr "Parar reprodução" -#: ardour_ui2.cc:292 +#: ardour_ui2.cc:293 msgid "Play range/selection" msgstr "Reproduzir intervalo/seleção" -#: ardour_ui2.cc:293 +#: ardour_ui2.cc:294 msgid "Go to start of session" msgstr "Ir para o início da sessão" -#: ardour_ui2.cc:294 +#: ardour_ui2.cc:295 msgid "Go to end of session" msgstr "Ir para o fim da sessão" -#: ardour_ui2.cc:295 +#: ardour_ui2.cc:296 msgid "Play loop range" msgstr "Reproduzir intervalo" -#: ardour_ui2.cc:296 +#: ardour_ui2.cc:297 msgid "Return to last playback start when stopped" msgstr "Ir para o início da última reprodução quando parar" -#: ardour_ui2.cc:297 +#: ardour_ui2.cc:298 msgid "Start playback after any locate" msgstr "Iniciar reprodução após qualquer localização" -#: ardour_ui2.cc:298 +#: ardour_ui2.cc:299 msgid "Be sensible about input monitoring" msgstr "Sensível à monitoração na entrada" -#: ardour_ui2.cc:299 +#: ardour_ui2.cc:300 msgid "Start recording at auto-punch start" msgstr "Iniciar gravação no início do ponto-automático" -#: ardour_ui2.cc:300 +#: ardour_ui2.cc:301 msgid "Stop recording at auto-punch end" msgstr "Parar gravação no final do ponto-automático" -#: ardour_ui2.cc:301 +#: ardour_ui2.cc:302 msgid "Enable/Disable audio click" msgstr "Habilitar/desabilitar metrônomo" -#: ardour_ui2.cc:302 +#: ardour_ui2.cc:303 msgid "Positional sync source" msgstr "" -#: ardour_ui2.cc:303 +#: ardour_ui2.cc:304 msgid "Does Ardour control the time?" msgstr "" -#: ardour_ui2.cc:304 +#: ardour_ui2.cc:305 msgid "Shuttle speed control" msgstr "Velocidade do controle" -#: ardour_ui2.cc:305 +#: ardour_ui2.cc:306 #, c-format msgid "Select semitones or %%-age for speed display" msgstr "Selecionar semitons ou percentual para a velocidade da tela" -#: ardour_ui2.cc:306 +#: ardour_ui2.cc:307 msgid "Current transport speed" msgstr "Velocidade atual do transporte" -#: ardour_ui2.cc:329 +#: ardour_ui2.cc:330 msgid "Primary clock" msgstr "Relógio primeiramente" -#: ardour_ui2.cc:330 +#: ardour_ui2.cc:331 msgid "secondary clock" msgstr "Relógio secundário" #. XXX: this should really be saved in instant.xml or something similar and restored from there #. Combo's are stupid - they steal space from the entry for the button -#: ardour_ui2.cc:387 ardour_ui2.cc:823 ardour_ui2.cc:836 ardour_ui2.cc:899 -#: ardour_ui2.cc:901 +#: ardour_ui2.cc:388 ardour_ui2.cc:833 ardour_ui2.cc:846 ardour_ui2.cc:909 +#: ardour_ui2.cc:911 msgid "sprung" msgstr "retornável" -#: ardour_ui2.cc:388 ardour_ui2.cc:825 ardour_ui2.cc:847 +#: ardour_ui2.cc:389 ardour_ui2.cc:835 ardour_ui2.cc:857 msgid "wheel" msgstr "fixo" -#: ardour_ui2.cc:450 +#: ardour_ui2.cc:451 msgid "ardour: clock" msgstr "ardour: relógio" -#: ardour_ui2.cc:595 +#: ardour_ui2.cc:596 #, fuzzy msgid "Maximum speed" msgstr "velocidade variável" -#: ardour_ui2.cc:813 +#: ardour_ui2.cc:823 msgid "st" msgstr "o." -#: ardour_ui2.cc:857 ardour_ui2.cc:880 ardour_ui2.cc:897 +#: ardour_ui2.cc:867 ardour_ui2.cc:890 ardour_ui2.cc:907 msgid "stopped" msgstr "parado" -#: ardour_ui_dialogs.cc:152 playlist_selector.cc:69 +#: ardour_ui_dialogs.cc:153 playlist_selector.cc:70 msgid "close" msgstr "fechar" -#: ardour_ui_dialogs.cc:359 ardour_ui_ed.cc:181 +#: ardour_ui_dialogs.cc:360 ardour_ui_ed.cc:184 #, fuzzy msgid "Sound File Browser" msgstr "Biblioteca de Ãudio" #. menus + submenus that need action items -#: ardour_ui_ed.cc:69 +#: ardour_ui_ed.cc:72 msgid "Session" msgstr "Sessão" -#: ardour_ui_ed.cc:70 ardour_ui_ed.cc:127 editor.cc:1843 export_dialog.cc:350 +#: ardour_ui_ed.cc:73 ardour_ui_ed.cc:130 editor.cc:1836 export_dialog.cc:350 #: export_dialog.cc:1059 export_dialog.cc:1063 msgid "Export" msgstr "Exportar" -#: ardour_ui_ed.cc:71 +#: ardour_ui_ed.cc:74 msgid "Cleanup" msgstr "Limpar" -#: ardour_ui_ed.cc:72 option_editor.cc:125 +#: ardour_ui_ed.cc:75 option_editor.cc:126 msgid "Sync" msgstr "Sincronia" -#: ardour_ui_ed.cc:73 ardour_ui_ed.cc:74 +#: ardour_ui_ed.cc:76 ardour_ui_ed.cc:77 #, fuzzy msgid "Options" msgstr "Preferências" -#: ardour_ui_ed.cc:75 +#: ardour_ui_ed.cc:78 msgid "Help" msgstr "" -#: ardour_ui_ed.cc:76 +#: ardour_ui_ed.cc:79 msgid "KeyMouse Actions" msgstr "" -#: ardour_ui_ed.cc:77 +#: ardour_ui_ed.cc:80 #, fuzzy msgid "Audio File Format" msgstr "Quadros de Ãudio" -#: ardour_ui_ed.cc:78 +#: ardour_ui_ed.cc:81 #, fuzzy msgid "Header" msgstr "Pré Fade" -#: ardour_ui_ed.cc:79 +#: ardour_ui_ed.cc:82 msgid "Data" msgstr "" -#: ardour_ui_ed.cc:80 +#: ardour_ui_ed.cc:83 #, fuzzy msgid "Control Surfaces" msgstr "Controle de Saídas" #. the real actions -#: ardour_ui_ed.cc:84 audio_time_axis.cc:1856 new_session_dialog.cc:342 +#: ardour_ui_ed.cc:87 audio_time_axis.cc:1854 new_session_dialog.cc:529 msgid "New" msgstr "Novo" -#: ardour_ui_ed.cc:86 new_session_dialog.cc:334 +#: ardour_ui_ed.cc:89 new_session_dialog.cc:517 msgid "Open" msgstr "Abrir" -#: ardour_ui_ed.cc:87 +#: ardour_ui_ed.cc:90 msgid "Recent" msgstr "Recente" -#: ardour_ui_ed.cc:88 io_selector.cc:57 io_selector.cc:791 +#: ardour_ui_ed.cc:91 io_selector.cc:58 io_selector.cc:792 msgid "Close" msgstr "Fechar" -#: ardour_ui_ed.cc:91 route_params_ui.cc:512 +#: ardour_ui_ed.cc:94 route_params_ui.cc:514 msgid "Add Track/Bus" msgstr "Adicionar Trilha/Barramento" -#: ardour_ui_ed.cc:102 +#: ardour_ui_ed.cc:105 msgid "Connect" msgstr "Conectar" #. -#: ardour_ui_ed.cc:110 +#: ardour_ui_ed.cc:113 msgid "Snapshot" msgstr "Capturar instantâneo" -#: ardour_ui_ed.cc:113 +#: ardour_ui_ed.cc:116 msgid "Save Template..." msgstr "Salvar Esquema..." -#: ardour_ui_ed.cc:116 +#: ardour_ui_ed.cc:119 msgid "Export session to audiofile..." msgstr "Exportar sessão para arquivo de áudio" -#: ardour_ui_ed.cc:119 +#: ardour_ui_ed.cc:122 #, fuzzy msgid "Export selection to audiofile..." msgstr "Exportar sessão para arquivo de áudio" -#: ardour_ui_ed.cc:123 +#: ardour_ui_ed.cc:126 #, fuzzy msgid "Export range markers to audiofile..." msgstr "Exportar intervalo para arquivo de áudio" -#: ardour_ui_ed.cc:130 +#: ardour_ui_ed.cc:133 msgid "Cleanup unused sources" msgstr "Limpar fontes não usadas" -#: ardour_ui_ed.cc:132 +#: ardour_ui_ed.cc:135 msgid "Flush wastebasket" msgstr "Esvaziar lixeira" -#: ardour_ui_ed.cc:138 ardour_ui_options.cc:381 ardour_ui_options.cc:390 -#: ardour_ui_options.cc:462 +#: ardour_ui_ed.cc:141 ardour_ui_options.cc:408 ardour_ui_options.cc:417 +#: ardour_ui_options.cc:489 msgid "JACK" msgstr "JACK" -#: ardour_ui_ed.cc:139 +#: ardour_ui_ed.cc:142 msgid "Latency" msgstr "" -#: ardour_ui_ed.cc:141 +#: ardour_ui_ed.cc:144 #, fuzzy msgid "Reconnect" msgstr "Conectar" -#: ardour_ui_ed.cc:144 mixer_strip.cc:514 mixer_strip.cc:574 +#: ardour_ui_ed.cc:147 mixer_strip.cc:497 mixer_strip.cc:565 msgid "Disconnect" msgstr "Desconectar" -#: ardour_ui_ed.cc:171 +#: ardour_ui_ed.cc:174 msgid "Windows" msgstr "Janelas" -#: ardour_ui_ed.cc:172 +#: ardour_ui_ed.cc:175 msgid "start prefix" msgstr "" -#: ardour_ui_ed.cc:173 +#: ardour_ui_ed.cc:176 msgid "Quit" msgstr "Sair" #. windows visibility actions -#: ardour_ui_ed.cc:177 +#: ardour_ui_ed.cc:180 msgid "Maximise Editor Space" msgstr "" -#: ardour_ui_ed.cc:179 +#: ardour_ui_ed.cc:182 #, fuzzy msgid "Show Editor" msgstr "Editor" -#: ardour_ui_ed.cc:180 +#: ardour_ui_ed.cc:183 #, fuzzy msgid "Show Mixer" msgstr "Mixer" -#: ardour_ui_ed.cc:182 +#: ardour_ui_ed.cc:185 msgid "Options Editor" msgstr "Preferências" -#: ardour_ui_ed.cc:183 +#: ardour_ui_ed.cc:186 msgid "Track/Bus Inspector" msgstr "Inspetador de Trilhas/Barramentos" -#: ardour_ui_ed.cc:185 +#: ardour_ui_ed.cc:188 msgid "Connections" msgstr "Conexões" -#: ardour_ui_ed.cc:187 +#: ardour_ui_ed.cc:190 msgid "Locations" msgstr "Localizações" -#: ardour_ui_ed.cc:189 +#: ardour_ui_ed.cc:192 msgid "Big Clock" msgstr "Metrônomo" -#: ardour_ui_ed.cc:191 +#: ardour_ui_ed.cc:194 msgid "About" msgstr "Sobre" -#: ardour_ui_ed.cc:192 +#: ardour_ui_ed.cc:195 #, fuzzy msgid "Colors" msgstr "Cor" -#: ardour_ui_ed.cc:194 +#: ardour_ui_ed.cc:197 #, fuzzy msgid "Add Audio Track" msgstr "Adicionar Trilha/Barramento" -#: ardour_ui_ed.cc:196 +#: ardour_ui_ed.cc:199 #, fuzzy msgid "Add Audio Bus" msgstr "Ocultar todos os barramentos de áudio" -#: ardour_ui_ed.cc:198 +#: ardour_ui_ed.cc:201 msgid "Save" msgstr "Salvar" -#: ardour_ui_ed.cc:200 editor_actions.cc:254 +#: ardour_ui_ed.cc:203 editor_actions.cc:255 #, fuzzy msgid "Remove Last Capture" msgstr "Remover última captura" #. do-nothing action for the "transport" menu bar item -#: ardour_ui_ed.cc:207 +#: ardour_ui_ed.cc:210 #, fuzzy msgid "Transport" msgstr "Tradutores" @@ -1029,73 +1007,73 @@ msgstr "Tradutores" #. these two are not used by key bindings, instead use ToggleRoll for that. these two do show up in #. menus and via button proxies. #. -#: ardour_ui_ed.cc:213 sfdb_ui.cc:57 +#: ardour_ui_ed.cc:216 sfdb_ui.cc:57 msgid "Stop" msgstr "Parar" -#: ardour_ui_ed.cc:216 +#: ardour_ui_ed.cc:219 msgid "Roll" msgstr "" -#: ardour_ui_ed.cc:220 +#: ardour_ui_ed.cc:223 #, fuzzy msgid "Start/Stop" msgstr "Inicio:" -#: ardour_ui_ed.cc:223 +#: ardour_ui_ed.cc:226 msgid "Stop + Forget Capture" msgstr "" -#: ardour_ui_ed.cc:226 +#: ardour_ui_ed.cc:229 #, fuzzy msgid "Play Loop Range" msgstr "Reproduzir intervalo" -#: ardour_ui_ed.cc:229 +#: ardour_ui_ed.cc:232 #, fuzzy msgid "Play Selection" msgstr "Reproduzir região selecionada" -#: ardour_ui_ed.cc:233 +#: ardour_ui_ed.cc:236 #, fuzzy msgid "Enable Record" msgstr "Gravar" -#: ardour_ui_ed.cc:236 +#: ardour_ui_ed.cc:239 #, fuzzy msgid "Rewind" msgstr "Região" -#: ardour_ui_ed.cc:239 +#: ardour_ui_ed.cc:242 msgid "Rewind (Slow)" msgstr "" -#: ardour_ui_ed.cc:242 +#: ardour_ui_ed.cc:245 msgid "Rewind (Fast)" msgstr "" -#: ardour_ui_ed.cc:245 +#: ardour_ui_ed.cc:248 msgid "Forward" msgstr "" -#: ardour_ui_ed.cc:248 +#: ardour_ui_ed.cc:251 msgid "Forward (Slow)" msgstr "" -#: ardour_ui_ed.cc:251 +#: ardour_ui_ed.cc:254 msgid "Forward (Fast)" msgstr "" -#: ardour_ui_ed.cc:254 +#: ardour_ui_ed.cc:257 msgid "Goto Zero" msgstr "" -#: ardour_ui_ed.cc:257 +#: ardour_ui_ed.cc:260 #, fuzzy msgid "Goto Start" msgstr "Inicio:" -#: ardour_ui_ed.cc:260 +#: ardour_ui_ed.cc:263 msgid "Goto End" msgstr "" @@ -1103,7 +1081,7 @@ msgstr "" #. that proxies for these action to be more compact. It would be nice to find a way to override the action #. name appearance on the buttons. #. -#: ardour_ui_ed.cc:269 +#: ardour_ui_ed.cc:272 #, fuzzy msgid "" "Punch\n" @@ -1112,7 +1090,7 @@ msgstr "" "iniciar\n" "inserção" -#: ardour_ui_ed.cc:272 +#: ardour_ui_ed.cc:275 #, fuzzy msgid "" "Punch\n" @@ -1121,11 +1099,11 @@ msgstr "" "finalizar\n" "inserção" -#: ardour_ui_ed.cc:275 option_editor.cc:128 +#: ardour_ui_ed.cc:278 option_editor.cc:129 msgid "Click" msgstr "Metrônomo" -#: ardour_ui_ed.cc:278 +#: ardour_ui_ed.cc:281 #, fuzzy msgid "" "Auto\n" @@ -1134,7 +1112,7 @@ msgstr "" "entrada\n" "automática" -#: ardour_ui_ed.cc:281 +#: ardour_ui_ed.cc:284 #, fuzzy msgid "" "Auto\n" @@ -1143,7 +1121,7 @@ msgstr "" "reprodução\n" "automática" -#: ardour_ui_ed.cc:284 +#: ardour_ui_ed.cc:287 #, fuzzy msgid "" "Auto\n" @@ -1152,283 +1130,283 @@ msgstr "" "retorno\n" "automático" -#: ardour_ui_ed.cc:288 +#: ardour_ui_ed.cc:291 #, fuzzy msgid "" "Time\n" "master" msgstr "Modo supervisor de tempo (JACK)" -#: ardour_ui_ed.cc:291 +#: ardour_ui_ed.cc:294 msgid "Toggle Record Enable Track1" msgstr "" -#: ardour_ui_ed.cc:293 +#: ardour_ui_ed.cc:296 msgid "Toggle Record Enable Track2" msgstr "" -#: ardour_ui_ed.cc:295 +#: ardour_ui_ed.cc:298 msgid "Toggle Record Enable Track3" msgstr "" -#: ardour_ui_ed.cc:297 +#: ardour_ui_ed.cc:300 msgid "Toggle Record Enable Track4" msgstr "" -#: ardour_ui_ed.cc:299 +#: ardour_ui_ed.cc:302 msgid "Toggle Record Enable Track5" msgstr "" -#: ardour_ui_ed.cc:301 +#: ardour_ui_ed.cc:304 msgid "Toggle Record Enable Track6" msgstr "" -#: ardour_ui_ed.cc:303 +#: ardour_ui_ed.cc:306 msgid "Toggle Record Enable Track7" msgstr "" -#: ardour_ui_ed.cc:305 +#: ardour_ui_ed.cc:308 msgid "Toggle Record Enable Track8" msgstr "" -#: ardour_ui_ed.cc:307 +#: ardour_ui_ed.cc:310 msgid "Toggle Record Enable Track9" msgstr "" -#: ardour_ui_ed.cc:309 +#: ardour_ui_ed.cc:312 msgid "Toggle Record Enable Track10" msgstr "" -#: ardour_ui_ed.cc:311 +#: ardour_ui_ed.cc:314 msgid "Toggle Record Enable Track11" msgstr "" -#: ardour_ui_ed.cc:313 +#: ardour_ui_ed.cc:316 msgid "Toggle Record Enable Track12" msgstr "" -#: ardour_ui_ed.cc:315 +#: ardour_ui_ed.cc:318 msgid "Toggle Record Enable Track13" msgstr "" -#: ardour_ui_ed.cc:317 +#: ardour_ui_ed.cc:320 msgid "Toggle Record Enable Track14" msgstr "" -#: ardour_ui_ed.cc:319 +#: ardour_ui_ed.cc:322 msgid "Toggle Record Enable Track15" msgstr "" -#: ardour_ui_ed.cc:321 +#: ardour_ui_ed.cc:324 msgid "Toggle Record Enable Track16" msgstr "" -#: ardour_ui_ed.cc:323 +#: ardour_ui_ed.cc:326 msgid "Toggle Record Enable Track17" msgstr "" -#: ardour_ui_ed.cc:325 +#: ardour_ui_ed.cc:328 msgid "Toggle Record Enable Track18" msgstr "" -#: ardour_ui_ed.cc:327 +#: ardour_ui_ed.cc:330 msgid "Toggle Record Enable Track19" msgstr "" -#: ardour_ui_ed.cc:329 +#: ardour_ui_ed.cc:332 msgid "Toggle Record Enable Track20" msgstr "" -#: ardour_ui_ed.cc:331 +#: ardour_ui_ed.cc:334 msgid "Toggle Record Enable Track21" msgstr "" -#: ardour_ui_ed.cc:333 +#: ardour_ui_ed.cc:336 msgid "Toggle Record Enable Track22" msgstr "" -#: ardour_ui_ed.cc:335 +#: ardour_ui_ed.cc:338 msgid "Toggle Record Enable Track23" msgstr "" -#: ardour_ui_ed.cc:337 +#: ardour_ui_ed.cc:340 msgid "Toggle Record Enable Track24" msgstr "" -#: ardour_ui_ed.cc:339 +#: ardour_ui_ed.cc:342 msgid "Toggle Record Enable Track25" msgstr "" -#: ardour_ui_ed.cc:341 +#: ardour_ui_ed.cc:344 msgid "Toggle Record Enable Track26" msgstr "" -#: ardour_ui_ed.cc:343 +#: ardour_ui_ed.cc:346 msgid "Toggle Record Enable Track27" msgstr "" -#: ardour_ui_ed.cc:345 +#: ardour_ui_ed.cc:348 msgid "Toggle Record Enable Track28" msgstr "" -#: ardour_ui_ed.cc:347 +#: ardour_ui_ed.cc:350 msgid "Toggle Record Enable Track29" msgstr "" -#: ardour_ui_ed.cc:349 +#: ardour_ui_ed.cc:352 msgid "Toggle Record Enable Track30" msgstr "" -#: ardour_ui_ed.cc:351 +#: ardour_ui_ed.cc:354 msgid "Toggle Record Enable Track31" msgstr "" -#: ardour_ui_ed.cc:353 +#: ardour_ui_ed.cc:356 msgid "Toggle Record Enable Track32" msgstr "" -#: ardour_ui_ed.cc:358 +#: ardour_ui_ed.cc:361 msgid "Percentage" msgstr "Percentual" -#: ardour_ui_ed.cc:359 +#: ardour_ui_ed.cc:362 msgid "Semitones" msgstr "Semitons" -#: ardour_ui_ed.cc:363 +#: ardour_ui_ed.cc:366 msgid "Send MTC" msgstr "Enviar MTC" -#: ardour_ui_ed.cc:365 +#: ardour_ui_ed.cc:368 msgid "Send MMC" msgstr "Enviar MMC" -#: ardour_ui_ed.cc:367 +#: ardour_ui_ed.cc:370 #, fuzzy msgid "Use MMC" msgstr "Enviar MMC" -#: ardour_ui_ed.cc:369 +#: ardour_ui_ed.cc:372 msgid "Send MIDI feedback" msgstr "" -#: ardour_ui_ed.cc:371 +#: ardour_ui_ed.cc:374 #, fuzzy msgid "Use MIDI control" msgstr "Porta MMC" -#: ardour_ui_ed.cc:374 +#: ardour_ui_ed.cc:377 #, fuzzy -msgid "Connect newtrack inputs to hardware" +msgid "Connect new track inputs to hardware" msgstr "Conectar novas faixas automaticamente" -#: ardour_ui_ed.cc:392 +#: ardour_ui_ed.cc:396 #, fuzzy msgid "Connect new track outputs to hardware" msgstr "Conectar novas faixas automaticamente" -#: ardour_ui_ed.cc:394 +#: ardour_ui_ed.cc:398 #, fuzzy msgid "Connect new track outputs to master" msgstr "concetar automaticamente saídas das trilhas com as saídas master" -#: ardour_ui_ed.cc:396 +#: ardour_ui_ed.cc:400 #, fuzzy msgid "Manually connect new track outputs" msgstr "conectar manualmente saídas das trilhas" -#: ardour_ui_ed.cc:401 +#: ardour_ui_ed.cc:405 #, fuzzy msgid "Hardware monitoring" msgstr "Usar Monitoração de Hardware" -#: ardour_ui_ed.cc:402 +#: ardour_ui_ed.cc:406 #, fuzzy msgid "Software monitoring" msgstr "Usar Monitoração de Software" -#: ardour_ui_ed.cc:403 +#: ardour_ui_ed.cc:407 #, fuzzy msgid "External monitoring" msgstr "Usar Monitoração de Hardware" #. Configuration object options (i.e. not session specific) -#: ardour_ui_ed.cc:407 +#: ardour_ui_ed.cc:411 msgid "Stop plugins with transport" msgstr "Suspender efeitos/plugins em transporte" -#: ardour_ui_ed.cc:408 +#: ardour_ui_ed.cc:412 #, fuzzy msgid "Verify remove last capture" msgstr "Remover última captura" -#: ardour_ui_ed.cc:409 +#: ardour_ui_ed.cc:413 msgid "Stop recording on xrun" msgstr "Suspender gravaçãoo em caso de falha sincrônica (XRUN)" -#: ardour_ui_ed.cc:410 +#: ardour_ui_ed.cc:414 #, fuzzy msgid "Stop transport at session end" msgstr "Suspender o transporte no final da sessão" -#: ardour_ui_ed.cc:411 +#: ardour_ui_ed.cc:415 msgid "-12dB gain reduce ffwd/rewind" msgstr "" -#: ardour_ui_ed.cc:412 +#: ardour_ui_ed.cc:416 msgid "Rec-enable stays engaged at stop" msgstr "" #. session options -#: ardour_ui_ed.cc:416 +#: ardour_ui_ed.cc:420 #, fuzzy msgid "Do not run plugins while recording" msgstr "Executar plugins enquanto grava" -#: ardour_ui_ed.cc:419 +#: ardour_ui_ed.cc:423 msgid "Latched solo" msgstr "Solo alternado" -#: ardour_ui_ed.cc:424 +#: ardour_ui_ed.cc:428 #, fuzzy msgid "Solo in-place" msgstr "Solo" -#: ardour_ui_ed.cc:426 +#: ardour_ui_ed.cc:430 msgid "Solo via bus" msgstr "" -#: ardour_ui_ed.cc:429 +#: ardour_ui_ed.cc:433 #, fuzzy msgid "Automatically create crossfades" msgstr "Fade cruzado automático no intervalo sobreposto" -#: ardour_ui_ed.cc:431 +#: ardour_ui_ed.cc:435 msgid "Unmute new full crossfades" msgstr "" -#: ardour_ui_options.cc:379 ardour_ui_options.cc:389 ardour_ui_options.cc:456 +#: ardour_ui_options.cc:406 ardour_ui_options.cc:416 ardour_ui_options.cc:483 #, fuzzy msgid "Internal" msgstr "interno" -#: ardour_ui_options.cc:380 ardour_ui_options.cc:459 +#: ardour_ui_options.cc:407 ardour_ui_options.cc:486 msgid "MTC" msgstr "" -#: audio_clock.cc:1719 editor.cc:185 +#: audio_clock.cc:1742 editor.cc:188 msgid "SMPTE" msgstr "" -#: audio_clock.cc:1720 editor.cc:184 editor_rulers.cc:359 +#: audio_clock.cc:1743 editor.cc:187 editor_rulers.cc:360 msgid "Bars:Beats" msgstr "Compassos:Batimentos" -#: audio_clock.cc:1721 +#: audio_clock.cc:1744 msgid "Minutes:Seconds" msgstr "Minutos:Segundos" -#: audio_clock.cc:1722 +#: audio_clock.cc:1745 msgid "Audio Frames" msgstr "Quadros de Ãudio" @@ -1436,285 +1414,307 @@ msgstr "Quadros de Ãudio" #. Slowest = 6.6dB/sec falloff at update rate of 40ms #. Slow = 6.8dB/sec falloff at update rate of 40ms #. -#: audio_clock.cc:1723 editor_actions.cc:374 editor_actions.cc:382 +#: audio_clock.cc:1746 editor_actions.cc:375 editor_actions.cc:383 +#: gain_meter.cc:172 panner_ui.cc:89 plugin_ui.cc:392 plugin_ui.cc:635 msgid "Off" msgstr "Desligar" -#: audio_clock.cc:1725 +#: audio_clock.cc:1748 msgid "Mode" msgstr "Modo" -#: audio_time_axis.cc:90 mixer_strip.cc:458 +#: audio_time_axis.cc:91 msgid "m" msgstr "" -#: audio_time_axis.cc:90 mixer_strip.cc:459 +#: audio_time_axis.cc:91 msgid "s" msgstr "" -#: audio_time_axis.cc:90 +#: audio_time_axis.cc:91 msgid "r" msgstr "" -#: audio_time_axis.cc:94 +#: audio_time_axis.cc:95 msgid "g" msgstr "" #. group -#: audio_time_axis.cc:95 +#: audio_time_axis.cc:96 msgid "p" msgstr "" -#: audio_time_axis.cc:96 automation_time_axis.cc:31 visual_time_axis.cc:73 +#: audio_time_axis.cc:97 automation_time_axis.cc:32 visual_time_axis.cc:74 msgid "h" msgstr "" #. height -#: audio_time_axis.cc:97 +#: audio_time_axis.cc:98 msgid "a" msgstr "" -#: audio_time_axis.cc:98 visual_time_axis.cc:72 +#: audio_time_axis.cc:99 visual_time_axis.cc:73 msgid "v" msgstr "" -#: audio_time_axis.cc:173 +#: audio_time_axis.cc:168 mixer_strip.cc:86 msgid "Record" msgstr "Gravar" -#: audio_time_axis.cc:174 editor_actions.cc:36 +#: audio_time_axis.cc:169 editor_actions.cc:37 mixer_strip.cc:86 msgid "Solo" msgstr "Solo" -#: audio_time_axis.cc:175 editor.cc:1767 editor.cc:1866 panner_ui.cc:385 +#: audio_time_axis.cc:170 editor.cc:1760 editor.cc:1859 mixer_strip.cc:86 +#: panner_ui.cc:427 msgid "Mute" msgstr "Mutar" -#: audio_time_axis.cc:176 +#: audio_time_axis.cc:171 msgid "Edit Group" msgstr "Editar Grupo" -#: audio_time_axis.cc:177 visual_time_axis.cc:91 +#: audio_time_axis.cc:172 visual_time_axis.cc:92 msgid "Display Height" msgstr "Altura" -#: audio_time_axis.cc:178 +#: audio_time_axis.cc:173 msgid "Playlist" msgstr "Lista de reprodução" -#: audio_time_axis.cc:179 audio_time_axis.cc:743 +#: audio_time_axis.cc:174 audio_time_axis.cc:741 msgid "Automation" msgstr "Automação" -#: audio_time_axis.cc:180 visual_time_axis.cc:92 +#: audio_time_axis.cc:175 visual_time_axis.cc:93 msgid "Visual options" msgstr "Opções de aparência" -#: audio_time_axis.cc:181 visual_time_axis.cc:93 +#: audio_time_axis.cc:176 visual_time_axis.cc:94 msgid "Hide this track" msgstr "Ocultar esta trilha" -#: audio_time_axis.cc:337 +#: audio_time_axis.cc:333 mixer_strip.cc:927 msgid "No group" msgstr "Sem grupo" -#: audio_time_axis.cc:704 automation_time_axis.cc:448 -#: imageframe_time_axis.cc:256 marker_time_axis.cc:210 +#: audio_time_axis.cc:702 automation_time_axis.cc:450 +#: imageframe_time_axis.cc:255 marker_time_axis.cc:211 msgid "Height" msgstr "Altura" -#: audio_time_axis.cc:705 color_manager.cc:40 imageframe_time_axis.cc:257 -#: marker_time_axis.cc:211 +#: audio_time_axis.cc:703 color_manager.cc:41 imageframe_time_axis.cc:256 +#: marker_time_axis.cc:212 msgid "Color" msgstr "Cor" -#: audio_time_axis.cc:709 +#: audio_time_axis.cc:707 msgid "Hide all crossfades" msgstr "" -#: audio_time_axis.cc:710 +#: audio_time_axis.cc:708 msgid "Show all crossfades" msgstr "" -#: audio_time_axis.cc:714 mixer_strip.cc:1236 +#: audio_time_axis.cc:712 mixer_strip.cc:1011 #, fuzzy msgid "Remote Control ID" msgstr "Remover ponto de controlo" -#: audio_time_axis.cc:720 -msgid "show all automation" +#: audio_time_axis.cc:718 +#, fuzzy +msgid "Show all automation" msgstr "mostra toda a automação" -#: audio_time_axis.cc:723 -msgid "show existing automation" +#: audio_time_axis.cc:721 +#, fuzzy +msgid "Show existing automation" msgstr "mostra a automação existente" -#: audio_time_axis.cc:726 -msgid "hide all automation" +#: audio_time_axis.cc:724 +#, fuzzy +msgid "Hide all automation" msgstr "ocultar toda a automação" -#: audio_time_axis.cc:731 audio_time_axis.cc:1169 editor.cc:215 -msgid "gain" -msgstr "ganho" +#: audio_time_axis.cc:729 +#, fuzzy +msgid "Fader" +msgstr "Fade" -#: audio_time_axis.cc:736 audio_time_axis.cc:1209 -msgid "pan" +#: audio_time_axis.cc:734 +#, fuzzy +msgid "Pan" msgstr "pan" -#: audio_time_axis.cc:741 +#: audio_time_axis.cc:739 msgid "Plugins" msgstr "Entradas" -#: audio_time_axis.cc:749 +#: audio_time_axis.cc:747 msgid "Show waveforms" msgstr "Mostrar formas de onda áudio" -#: audio_time_axis.cc:757 +#: audio_time_axis.cc:755 msgid "Traditional" msgstr "Tradicional" -#: audio_time_axis.cc:760 +#: audio_time_axis.cc:758 msgid "Rectified" msgstr "Corrigido" -#: audio_time_axis.cc:763 +#: audio_time_axis.cc:761 msgid "Waveform" msgstr "Forma de onda" -#: audio_time_axis.cc:773 +#: audio_time_axis.cc:771 #, fuzzy -msgid "align with existing material" +msgid "Align with existing material" msgstr "Material existente" -#: audio_time_axis.cc:778 +#: audio_time_axis.cc:776 #, fuzzy -msgid "align with capture time" +msgid "Align with capture time" msgstr "Tempo de captura" -#: audio_time_axis.cc:784 +#: audio_time_axis.cc:782 #, fuzzy msgid "Alignment" msgstr "Alinhamento" -#: audio_time_axis.cc:790 editor.cc:523 editor_actions.cc:59 -#: mixer_strip.cc:1225 +#: audio_time_axis.cc:788 editor.cc:527 editor_actions.cc:60 +#: mixer_strip.cc:1000 mixer_ui.cc:111 msgid "Active" msgstr "Ativar" -#: audio_time_axis.cc:795 editor.cc:1929 editor_actions.cc:319 -#: editor_markers.cc:507 imageframe_time_axis.cc:260 location_ui.cc:56 -#: marker_time_axis.cc:214 mixer_strip.cc:1239 +#: audio_time_axis.cc:793 editor.cc:1922 editor_actions.cc:320 +#: editor_markers.cc:508 imageframe_time_axis.cc:259 location_ui.cc:57 +#: marker_time_axis.cc:215 mixer_strip.cc:1014 msgid "Remove" msgstr "Remover" -#: audio_time_axis.cc:835 +#: audio_time_axis.cc:833 msgid "Name for playlist" msgstr "Nome para a lista de reprodução" -#: audio_time_axis.cc:837 audio_time_axis.cc:1853 editor_markers.cc:826 -#: editor_mouse.cc:4609 imageframe_time_axis.cc:249 marker_time_axis.cc:207 -#: meter_bridge_strip.cc:223 mixer_strip.cc:1223 redirect_box.cc:749 -#: redirect_box.cc:1063 route_ui.cc:732 visual_time_axis.cc:325 +#: audio_time_axis.cc:835 audio_time_axis.cc:1851 editor_markers.cc:827 +#: editor_mouse.cc:4673 imageframe_time_axis.cc:248 marker_time_axis.cc:208 +#: meter_bridge_strip.cc:224 mixer_strip.cc:998 redirect_box.cc:751 +#: redirect_box.cc:1065 route_ui.cc:739 visual_time_axis.cc:326 msgid "Rename" msgstr "Renomear" -#: audio_time_axis.cc:870 audio_time_axis.cc:910 +#: audio_time_axis.cc:868 audio_time_axis.cc:908 #, fuzzy msgid "Name for Playlist" msgstr "Nome para a lista de reprodução" -#: audio_time_axis.cc:1128 visual_time_axis.cc:382 +#: audio_time_axis.cc:1126 visual_time_axis.cc:383 msgid "a track already exists with that name" msgstr "já existe uma trilha com este nome" -#: audio_time_axis.cc:1412 editor.cc:1490 selection.cc:622 +#: audio_time_axis.cc:1167 editor.cc:218 +msgid "gain" +msgstr "ganho" + +#: audio_time_axis.cc:1207 +msgid "pan" +msgstr "pan" + +#: audio_time_axis.cc:1410 editor.cc:1483 selection.cc:634 msgid "programming error: " msgstr "" -#: audio_time_axis.cc:1850 +#: audio_time_axis.cc:1848 msgid "Current: %1" msgstr "Atual: %1" -#: audio_time_axis.cc:1857 +#: audio_time_axis.cc:1855 msgid "New Copy" msgstr "Nova Cópia" -#: audio_time_axis.cc:1859 +#: audio_time_axis.cc:1857 msgid "Clear Current" msgstr "Limpar Atual" -#: audio_time_axis.cc:1861 editor.cc:2031 editor.cc:2107 +#: audio_time_axis.cc:1859 editor.cc:2024 editor.cc:2100 msgid "Select" msgstr "Selecionar" -#: automation_line.cc:883 +#: automation_line.cc:884 msgid "automation event move" msgstr "mover evento de automação" -#: automation_line.cc:885 +#: automation_line.cc:886 msgid "automation range drag" msgstr "arrastar intervalo de automação" -#: automation_line.cc:1014 region_gain_line.cc:61 +#: automation_line.cc:1015 region_gain_line.cc:62 msgid "remove control point" msgstr "Remover ponto de controlo" -#: automation_time_axis.cc:32 editor_ops.cc:2813 +#: automation_time_axis.cc:33 editor_ops.cc:2885 msgid "clear" msgstr "limpar" -#: automation_time_axis.cc:74 +#: automation_time_axis.cc:75 msgid "track height" msgstr "" -#: automation_time_axis.cc:75 +#: automation_time_axis.cc:76 msgid "automation state" msgstr "estado do automação" -#: automation_time_axis.cc:76 +#: automation_time_axis.cc:77 msgid "clear track" msgstr "limpar trilha" -#: automation_time_axis.cc:77 +#: automation_time_axis.cc:78 msgid "hide track" msgstr "ocultar esta trilha" -#: automation_time_axis.cc:185 automation_time_axis.cc:223 -#: automation_time_axis.cc:463 mixer_strip.cc:176 mixer_strip.cc:188 -#: plugin_ui.cc:394 plugin_ui.cc:636 region_editor.cc:53 -msgid "play" -msgstr "reproduzir" +#: automation_time_axis.cc:184 automation_time_axis.cc:213 +#: automation_time_axis.cc:461 +msgid "Manual" +msgstr "" -#: automation_time_axis.cc:187 automation_time_axis.cc:234 -#: automation_time_axis.cc:467 mixer_strip.cc:178 mixer_strip.cc:190 -#: plugin_ui.cc:397 plugin_ui.cc:638 -msgid "write" +#: automation_time_axis.cc:186 automation_time_axis.cc:224 +#: automation_time_axis.cc:465 editor.cc:2001 editor.cc:2082 gain_meter.cc:174 +#: panner_ui.cc:91 plugin_ui.cc:395 plugin_ui.cc:637 sfdb_ui.cc:56 +msgid "Play" +msgstr "Reproduzir" + +#: automation_time_axis.cc:188 automation_time_axis.cc:235 +#: automation_time_axis.cc:469 gain_meter.cc:176 panner_ui.cc:93 +#: plugin_ui.cc:398 plugin_ui.cc:639 +#, fuzzy +msgid "Write" msgstr "escrever" -#: automation_time_axis.cc:189 automation_time_axis.cc:245 -#: automation_time_axis.cc:471 mixer_strip.cc:180 mixer_strip.cc:192 -#: mixer_strip.cc:887 plugin_ui.cc:400 plugin_ui.cc:640 -msgid "touch" +#: automation_time_axis.cc:190 automation_time_axis.cc:246 +#: automation_time_axis.cc:473 gain_meter.cc:178 panner_ui.cc:95 +#: plugin_ui.cc:401 plugin_ui.cc:641 +#, fuzzy +msgid "Touch" msgstr "marca como novo" -#: automation_time_axis.cc:256 option_editor.cc:182 option_editor.cc:188 -#: plugin_ui.cc:403 +#: automation_time_axis.cc:257 option_editor.cc:183 option_editor.cc:189 +#: plugin_ui.cc:404 msgid "???" msgstr "" -#: automation_time_axis.cc:270 +#: automation_time_axis.cc:271 msgid "clear automation" msgstr "limpar automação" -#: automation_time_axis.cc:450 editor_actions.cc:317 +#: automation_time_axis.cc:452 editor_actions.cc:318 msgid "Hide" msgstr "Ocultar" -#: automation_time_axis.cc:452 crossfade_edit.cc:76 redirect_box.cc:1055 +#: automation_time_axis.cc:454 crossfade_edit.cc:78 redirect_box.cc:1057 msgid "Clear" msgstr "Limpar" -#: automation_time_axis.cc:475 +#: automation_time_axis.cc:477 msgid "State" msgstr "Estado" @@ -1860,1574 +1860,1561 @@ msgstr "" msgid "color of fill" msgstr "" -#: color_manager.cc:39 +#: color_manager.cc:40 #, fuzzy msgid "Object" msgstr "objeto" -#: color_manager.cc:77 +#: color_manager.cc:78 #, fuzzy msgid "cannot open color definition file %1: %2" msgstr "não foi possível abrir o arquivo de imagem \"%1\"" -#: crossfade_edit.cc:73 +#: crossfade_edit.cc:75 msgid "ardour: x-fade edit" msgstr "ardour: editar cross fade" -#: crossfade_edit.cc:77 panner_ui.cc:401 +#: crossfade_edit.cc:79 panner_ui.cc:443 msgid "Reset" msgstr "Reiniciar" -#: crossfade_edit.cc:78 +#: crossfade_edit.cc:80 msgid "Fade" msgstr "Fade" -#: crossfade_edit.cc:79 +#: crossfade_edit.cc:81 msgid "Out (dry)" msgstr "Saída (flat)" -#: crossfade_edit.cc:80 +#: crossfade_edit.cc:82 msgid "Out" msgstr "Saídas" -#: crossfade_edit.cc:81 +#: crossfade_edit.cc:83 msgid "In (dry)" msgstr "Entrada (flat)" -#: crossfade_edit.cc:82 +#: crossfade_edit.cc:84 msgid "In" msgstr "Entrada" -#: crossfade_edit.cc:84 +#: crossfade_edit.cc:86 msgid "With Pre-roll" msgstr "Com pré-rolagem" -#: crossfade_edit.cc:85 +#: crossfade_edit.cc:87 msgid "With Post-roll" msgstr "Com pós-rolagem" -#: crossfade_edit.cc:93 +#: crossfade_edit.cc:95 msgid "Fade In" msgstr "Fade In" -#: crossfade_edit.cc:94 +#: crossfade_edit.cc:96 msgid "Fade Out" msgstr "Fade Out" -#: crossfade_edit.cc:170 editor.cc:1842 editor_actions.cc:315 -#: option_editor.cc:129 +#: crossfade_edit.cc:172 editor.cc:1835 editor_actions.cc:316 +#: option_editor.cc:130 msgid "Audition" msgstr "Audição" -#: editor.cc:101 editor.cc:3588 +#: editor.cc:104 editor.cc:3616 msgid "Slide" msgstr "Deslizar" -#: editor.cc:102 editor.cc:3586 +#: editor.cc:105 editor.cc:3614 msgid "Splice" msgstr "Reunir" -#: editor.cc:107 editor.cc:3643 export_dialog.cc:78 export_dialog.cc:92 -#: export_dialog.cc:893 export_dialog.cc:1225 +#. note that this menu list starts at zero, not 1, because zero +#. is a valid, if useless, ID. +#. +#. leave some breathing room +#: editor.cc:110 editor.cc:3671 export_dialog.cc:78 export_dialog.cc:92 +#: export_dialog.cc:893 export_dialog.cc:1225 route_ui.cc:437 msgid "None" msgstr "Nenhum" -#: editor.cc:108 editor.cc:3631 +#: editor.cc:111 editor.cc:3659 msgid "CD Frames" msgstr "Quadros de CD" -#: editor.cc:109 editor.cc:3633 +#: editor.cc:112 editor.cc:3661 msgid "SMPTE Frames" msgstr "SMPTE Frames" -#: editor.cc:110 editor.cc:3635 +#: editor.cc:113 editor.cc:3663 msgid "SMPTE Seconds" msgstr "SMPTE segundo" -#: editor.cc:111 editor.cc:3637 +#: editor.cc:114 editor.cc:3665 msgid "SMPTE Minutes" msgstr "SMPTE Minutos" -#: editor.cc:112 editor.cc:3639 +#: editor.cc:115 editor.cc:3667 msgid "Seconds" msgstr "Segundos" -#: editor.cc:113 editor.cc:3641 +#: editor.cc:116 editor.cc:3669 msgid "Minutes" msgstr "Minutos" # ## msgstr "Saídas Principais" -#: editor.cc:114 editor.cc:3613 +#: editor.cc:117 editor.cc:3641 msgid "Beats/32" msgstr "Batimentos/32" -#: editor.cc:115 editor.cc:3611 +#: editor.cc:118 editor.cc:3639 msgid "Beats/16" msgstr "Batimentos/16" -#: editor.cc:116 editor.cc:3609 +#: editor.cc:119 editor.cc:3637 msgid "Beats/8" msgstr "Batimentos/8" -#: editor.cc:117 editor.cc:3607 +#: editor.cc:120 editor.cc:3635 msgid "Beats/4" msgstr "Batimentos/4" -#: editor.cc:118 editor.cc:3605 +#: editor.cc:121 editor.cc:3633 msgid "Beats/3" msgstr "Batimentos/3" -#: editor.cc:119 editor.cc:3615 +#: editor.cc:122 editor.cc:3643 msgid "Beats" msgstr "Batimentos" -#: editor.cc:120 editor.cc:3617 +#: editor.cc:123 editor.cc:3645 msgid "Bars" msgstr "Compassos" -#: editor.cc:121 editor.cc:3619 +#: editor.cc:124 editor.cc:3647 msgid "Marks" msgstr "Marcas" -#: editor.cc:122 editor.cc:141 editor.cc:3621 editor.cc:3687 +#: editor.cc:125 editor.cc:144 editor.cc:3649 editor.cc:3715 msgid "Edit Cursor" msgstr "Cursor de Edição" -#: editor.cc:123 editor.cc:3623 +#: editor.cc:126 editor.cc:3651 msgid "Region starts" msgstr "Começo de regiões" -#: editor.cc:124 editor.cc:3625 +#: editor.cc:127 editor.cc:3653 msgid "Region ends" msgstr "Fim de regiões" -#: editor.cc:125 editor.cc:3629 +#: editor.cc:128 editor.cc:3657 msgid "Region syncs" msgstr "Sincronizações de região" -#: editor.cc:126 editor.cc:3627 +#: editor.cc:129 editor.cc:3655 msgid "Region bounds" msgstr "Divisas de região" -#: editor.cc:132 editor.cc:3662 +#: editor.cc:135 editor.cc:3690 msgid "Magnetic" msgstr "Magnético" -#: editor.cc:137 editor.cc:3679 export_dialog.cc:140 export_dialog.cc:156 +#: editor.cc:140 editor.cc:3707 export_dialog.cc:140 export_dialog.cc:156 #: export_dialog.cc:1068 export_dialog.cc:1072 msgid "Left" msgstr "Esquerdo" -#: editor.cc:138 editor.cc:3681 export_dialog.cc:141 export_dialog.cc:157 +#: editor.cc:141 editor.cc:3709 export_dialog.cc:141 export_dialog.cc:157 msgid "Right" msgstr "Direito" -#: editor.cc:139 editor.cc:3683 +#: editor.cc:142 editor.cc:3711 msgid "Center" msgstr "Centro" -#: editor.cc:140 editor.cc:3685 +#: editor.cc:143 editor.cc:3713 msgid "Playhead" msgstr "Início" #. time display buttons -#: editor.cc:183 +#: editor.cc:186 msgid "Mins:Secs" msgstr "Mins:Segs" -#: editor.cc:186 editor_rulers.cc:353 +#: editor.cc:189 editor_rulers.cc:354 msgid "Frames" msgstr "Quadros" -#: editor.cc:187 editor_rulers.cc:373 +#: editor.cc:190 editor_rulers.cc:374 msgid "Tempo" msgstr "Tempo" -#: editor.cc:188 editor_rulers.cc:367 +#: editor.cc:191 editor_rulers.cc:368 msgid "Meter" msgstr "VU (medidor volumétrico)" -#: editor.cc:189 editor_rulers.cc:379 +#: editor.cc:192 editor_rulers.cc:380 msgid "Location Markers" msgstr "Marcas de Localização" -#: editor.cc:190 editor_rulers.cc:385 +#: editor.cc:193 editor_rulers.cc:386 msgid "Range Markers" msgstr "Marcas de Intervalos" -#: editor.cc:191 editor_rulers.cc:391 +#: editor.cc:194 editor_rulers.cc:392 msgid "Loop/Punch Ranges" msgstr "Intervalos Loop/Insersão" -#: editor.cc:213 +#: editor.cc:216 msgid "range" msgstr "intervalo" -#: editor.cc:214 +#: editor.cc:217 msgid "object" msgstr "objeto" -#: editor.cc:216 +#: editor.cc:219 msgid "zoom" msgstr "zoom" -#: editor.cc:217 +#: editor.cc:220 msgid "timefx" msgstr "" -#: editor.cc:218 +#: editor.cc:221 msgid "listen" msgstr "" -#: editor.cc:220 +#: editor.cc:223 msgid "mode" msgstr "modo" -#: editor.cc:221 +#: editor.cc:224 msgid "automation" msgstr "automação" -#: editor.cc:223 +#: editor.cc:226 msgid "Edit Mode" msgstr "Modo de edição" -#: editor.cc:224 editor_actions.cc:283 +#: editor.cc:227 editor_actions.cc:284 msgid "Snap To" msgstr "Ajustar a" -#: editor.cc:225 +#: editor.cc:228 msgid "Snap Mode" msgstr "Modo de Ajuste" -#: editor.cc:226 +#: editor.cc:229 msgid "Zoom Focus" msgstr "Foco de Zoom" #. #. nudge -#: editor.cc:234 editor.cc:1907 editor.cc:2073 editor.cc:2129 +#: editor.cc:237 editor.cc:1900 editor.cc:2066 editor.cc:2122 msgid "Nudge" msgstr "Retocar" -#: editor.cc:466 +#: editor.cc:470 msgid "Zoom in" msgstr "Mais Zoom" -#: editor.cc:467 +#: editor.cc:471 msgid "Zoom out" msgstr "Menos Zoom" -#: editor.cc:470 +#: editor.cc:474 msgid "Zoom to session" msgstr "Zoom na sessão" -#: editor.cc:485 +#: editor.cc:489 msgid "Zoom Span" msgstr "Alcance de zoom" -#: editor.cc:498 editor.cc:524 editor_actions.cc:61 mixer_ui.cc:85 +#: editor.cc:502 editor.cc:528 editor_actions.cc:62 mixer_ui.cc:86 +#: mixer_ui.cc:112 #, fuzzy msgid "Visible" msgstr "visível" -#: editor.cc:499 editor.cc:522 +#: editor.cc:503 editor.cc:526 #, fuzzy msgid "Name" msgstr "Quadros" -#: editor.cc:595 editor.cc:661 +#: editor.cc:602 editor.cc:669 #, fuzzy msgid "Regions" msgstr "Região" -#: editor.cc:634 editor.cc:673 +#: editor.cc:642 editor.cc:681 msgid "Chunks" msgstr "Trechos" -#: editor.cc:664 +#: editor.cc:672 #, fuzzy msgid "Tracks/Busses" msgstr "Trilhas/Barramentos" -#: editor.cc:667 +#: editor.cc:675 msgid "Snapshots" msgstr "Capturas" -#: editor.cc:670 +#: editor.cc:678 msgid "Edit Groups" msgstr "Editar Grupos" -#: editor.cc:719 +#: editor.cc:727 msgid "Nudge region/selection forwards" msgstr "Avançar o mínimo região/seleção" -#: editor.cc:720 +#: editor.cc:728 msgid "Nudge region/selection backwards" msgstr "Voltar o mínimo região/seleção" -#: editor.cc:727 editor_mixer.cc:298 +#: editor.cc:735 editor_mixer.cc:299 msgid "ardour: editor" msgstr "" -#: editor.cc:728 +#: editor.cc:736 msgid "ardour_editor" msgstr "" -#: editor.cc:1190 +#: editor.cc:1183 msgid "ardour: editor: " msgstr "" #. force name -#: editor.cc:1275 editor.cc:1284 editor_markers.cc:869 +#: editor.cc:1268 editor.cc:1277 editor_markers.cc:870 msgid "Loop" msgstr "Ciclo" #. force name -#: editor.cc:1289 editor.cc:1298 editor_markers.cc:895 +#: editor.cc:1282 editor.cc:1291 editor_markers.cc:896 msgid "Punch" msgstr "Inserção" -#: editor.cc:1446 editor_mouse.cc:1721 +#: editor.cc:1439 editor_mouse.cc:1742 msgid "programming error: fade in canvas item has no regionview data pointer!" msgstr "" -#: editor.cc:1458 editor.cc:1475 redirect_box.cc:1071 +#: editor.cc:1451 editor.cc:1468 redirect_box.cc:1073 msgid "Deactivate" msgstr "Desativar" #. activation -#: editor.cc:1460 editor.cc:1477 redirect_box.cc:1069 +#: editor.cc:1453 editor.cc:1470 redirect_box.cc:1071 msgid "Activate" msgstr "Ativar" -#: editor.cc:1465 editor.cc:1482 +#: editor.cc:1458 editor.cc:1475 msgid "Linear" msgstr "Linear" -#: editor.cc:1466 editor.cc:1483 editor_actions.cc:375 +#: editor.cc:1459 editor.cc:1476 editor_actions.cc:376 msgid "Slowest" msgstr "Menor" -#: editor.cc:1467 editor.cc:1484 editor_actions.cc:376 +#: editor.cc:1460 editor.cc:1477 editor_actions.cc:377 msgid "Slow" msgstr "Devegar" -#: editor.cc:1468 editor.cc:1485 editor_actions.cc:378 +#: editor.cc:1461 editor.cc:1478 editor_actions.cc:379 msgid "Fast" msgstr "Rapido" -#: editor.cc:1469 editor.cc:1486 editor_actions.cc:380 +#: editor.cc:1462 editor.cc:1479 editor_actions.cc:381 msgid "Fastest" msgstr "Rapidamente" -#: editor.cc:1596 editor.cc:1604 +#: editor.cc:1589 editor.cc:1597 msgid "Freeze" msgstr "Congelar" -#: editor.cc:1600 +#: editor.cc:1593 msgid "Unfreeze" msgstr "Descongelar" -#: editor.cc:1769 editor.cc:1864 +#: editor.cc:1762 editor.cc:1857 msgid "Unmute" msgstr "Desmudo" #. non-operative menu items for menu bar #. show editors -#: editor.cc:1773 editor.cc:2053 editor.cc:2755 editor_actions.cc:26 -#: editor_markers.cc:506 mixer_strip.cc:512 mixer_strip.cc:572 -#: redirect_box.cc:1077 +#: editor.cc:1766 editor.cc:2046 editor.cc:2748 editor_actions.cc:27 +#: editor_markers.cc:507 mixer_strip.cc:495 mixer_strip.cc:563 +#: redirect_box.cc:1079 msgid "Edit" msgstr "Editar" -#: editor.cc:1778 +#: editor.cc:1771 msgid "Convert to short" msgstr "" -#: editor.cc:1780 +#: editor.cc:1773 msgid "Convert to full" msgstr "" -#: editor.cc:1791 +#: editor.cc:1784 msgid "Crossfade" msgstr "Fade cruzado" -#: editor.cc:1834 +#: editor.cc:1827 msgid "Popup region editor" msgstr "Editor de região" -#: editor.cc:1835 +#: editor.cc:1828 msgid "Raise to top layer" msgstr "Trazer região para frente, primeira camada" -#: editor.cc:1836 +#: editor.cc:1829 msgid "Lower to bottom layer" msgstr "Enviar região para a trás, última camada" -#: editor.cc:1838 +#: editor.cc:1831 msgid "Define sync point" msgstr "Definir ponto de sincronia" -#: editor.cc:1839 +#: editor.cc:1832 msgid "Remove sync point" msgstr "Remover ponto de sincronia" -#: editor.cc:1844 +#: editor.cc:1837 msgid "Bounce" msgstr "" -#: editor.cc:1847 +#: editor.cc:1840 #, fuzzy msgid "Analyze region" msgstr "Reproduzir região" -#: editor.cc:1859 +#: editor.cc:1852 msgid "Lock" msgstr "Trancar" -#: editor.cc:1860 +#: editor.cc:1853 msgid "Unlock" msgstr "Destrancar" -#: editor.cc:1870 +#: editor.cc:1863 msgid "Original position" msgstr "Posição original" -#: editor.cc:1876 +#: editor.cc:1869 msgid "Toggle envelope visibility" msgstr "" -#: editor.cc:1877 +#: editor.cc:1870 #, fuzzy msgid "Toggle envelope active" msgstr "ativo" -#: editor.cc:1881 +#: editor.cc:1874 msgid "DeNormalize" msgstr "Desnormalizar" -#: editor.cc:1883 +#: editor.cc:1876 msgid "Normalize" msgstr "Normalizar" -#: editor.cc:1886 +#: editor.cc:1879 msgid "Reverse" msgstr "Inverter horizontalmente" #. range related stuff -#: editor.cc:1892 +#: editor.cc:1885 #, fuzzy msgid "Add Range Markers" msgstr "Marcas de Intervalos" -#: editor.cc:1893 +#: editor.cc:1886 #, fuzzy msgid "Set Range" msgstr "Separar intervalo" -#: editor.cc:1902 +#: editor.cc:1895 #, fuzzy msgid "Nudge fwd" msgstr "Retocar" -#: editor.cc:1903 +#: editor.cc:1896 #, fuzzy msgid "Nudge bwd" msgstr "Retocar" -#: editor.cc:1904 +#: editor.cc:1897 msgid "Nudge fwd by capture offset" msgstr "" -#: editor.cc:1905 +#: editor.cc:1898 msgid "Nudge bwd by capture offset" msgstr "" -#: editor.cc:1914 +#: editor.cc:1907 msgid "Start to edit cursor" msgstr "Do início ao cursor de edição" -#: editor.cc:1915 +#: editor.cc:1908 msgid "Edit cursor to end" msgstr "Do cursor de edição ao final" -#: editor.cc:1917 +#: editor.cc:1910 gain_meter.cc:181 gain_meter.cc:813 panner_ui.cc:98 +#: panner_ui.cc:803 msgid "Trim" msgstr "Cortar" -#: editor.cc:1920 +#: editor.cc:1913 msgid "Split" msgstr "Separar" -#: editor.cc:1923 +#: editor.cc:1916 msgid "Make mono regions" msgstr "Criar regiões mono" -#: editor.cc:1926 +#: editor.cc:1919 msgid "Duplicate" msgstr "Duplicar" -#: editor.cc:1927 +#: editor.cc:1920 msgid "Fill Track" msgstr "Preencher Trilha" -#: editor.cc:1931 +#: editor.cc:1924 msgid "Destroy" msgstr "Remover definitavente" -#: editor.cc:1961 +#: editor.cc:1954 msgid "Play range" msgstr "Reproduzir intervalo" -#: editor.cc:1962 +#: editor.cc:1955 msgid "Loop range" msgstr "Loop no intervalo" -#: editor.cc:1966 +#: editor.cc:1959 #, fuzzy msgid "Analyze range" msgstr "Reproduzir intervalo" -#: editor.cc:1970 +#: editor.cc:1963 #, fuzzy msgid "Separate range to track" msgstr "Separar intervalo" -#: editor.cc:1971 +#: editor.cc:1964 #, fuzzy msgid "Separate range to region list" msgstr "Loop região selecionada" -#: editor.cc:1974 +#: editor.cc:1967 #, fuzzy msgid "Select all in range" msgstr "Selecionar tudo na trilha" -#: editor.cc:1976 editor.cc:2021 +#: editor.cc:1969 editor.cc:2014 #, fuzzy msgid "Set range to loop range" msgstr "Selecionar intervalo de loop" -#: editor.cc:1977 editor.cc:2022 +#: editor.cc:1970 editor.cc:2015 #, fuzzy msgid "Set range to punch range" msgstr "Selecionar intervalo de inserção" -#: editor.cc:1979 +#: editor.cc:1972 #, fuzzy msgid "Crop region to range" msgstr "Cortar região pela intervalo" -#: editor.cc:1980 +#: editor.cc:1973 #, fuzzy msgid "Fill range with region" msgstr "Preencher intervalo com região" -#: editor.cc:1981 +#: editor.cc:1974 #, fuzzy msgid "Duplicate range" msgstr "Duplicar" -#: editor.cc:1982 +#: editor.cc:1975 msgid "Create chunk from range" msgstr "Criar trecho a partir da intervalo" -#: editor.cc:1984 +#: editor.cc:1977 #, fuzzy msgid "Bounce range" msgstr "região" -#: editor.cc:1985 +#: editor.cc:1978 #, fuzzy msgid "Export range" msgstr "Exportar região" -#: editor.cc:1987 +#: editor.cc:1980 msgid "Range" msgstr "Intervalo" -#: editor.cc:2002 editor.cc:2087 +#: editor.cc:1995 editor.cc:2080 msgid "Play from edit cursor" msgstr "Reproduzir a partir do cursor" -#: editor.cc:2003 editor.cc:2088 +#: editor.cc:1996 editor.cc:2081 msgid "Play from start" msgstr "Reproduzir do início" -#: editor.cc:2004 +#: editor.cc:1997 msgid "Play region" msgstr "Reproduzir região" -#: editor.cc:2006 +#: editor.cc:1999 msgid "Loop Region" msgstr "Região de loop" -#: editor.cc:2008 editor.cc:2089 sfdb_ui.cc:56 -msgid "Play" -msgstr "Reproduzir" - -#: editor.cc:2016 editor.cc:2097 +#: editor.cc:2009 editor.cc:2090 msgid "Select All in track" msgstr "Selecionar tudo na trilha" -#: editor.cc:2017 editor.cc:2098 redirect_box.cc:1065 +#: editor.cc:2010 editor.cc:2091 redirect_box.cc:1067 msgid "Select All" msgstr "Selecionar Tudo" -#: editor.cc:2018 editor.cc:2099 +#: editor.cc:2011 editor.cc:2092 #, fuzzy msgid "Invert selection in track" msgstr "Inverter verticalmente na trilha" -#: editor.cc:2019 editor.cc:2100 +#: editor.cc:2012 editor.cc:2093 #, fuzzy msgid "Invert selection" msgstr "Saltar Seleção" -#: editor.cc:2024 editor.cc:2102 +#: editor.cc:2017 editor.cc:2095 #, fuzzy msgid "Select all after edit cursor" msgstr "Do início ao cursor de edição" -#: editor.cc:2025 editor.cc:2103 +#: editor.cc:2018 editor.cc:2096 #, fuzzy msgid "Select all before edit cursor" msgstr "Do início ao cursor de edição" -#: editor.cc:2026 editor.cc:2104 +#: editor.cc:2019 editor.cc:2097 #, fuzzy msgid "Select all after playhead" msgstr "Marcar aqui" -#: editor.cc:2027 editor.cc:2105 +#: editor.cc:2020 editor.cc:2098 #, fuzzy msgid "Select all before playhead" msgstr "Marcar aqui" -#: editor.cc:2028 +#: editor.cc:2021 #, fuzzy msgid "Select all between cursors" msgstr "Do início ao cursor de edição" #. standard editing stuff -#: editor.cc:2039 editor.cc:2115 editor.cc:3455 editor_actions.cc:213 -#: redirect_box.cc:1058 +#: editor.cc:2032 editor.cc:2108 editor.cc:3483 editor_actions.cc:214 +#: redirect_box.cc:1060 msgid "Cut" msgstr "Cortar" -#: editor.cc:2040 editor.cc:2116 editor.cc:3457 editor_actions.cc:218 -#: redirect_box.cc:1060 +#: editor.cc:2033 editor.cc:2109 editor.cc:3485 editor_actions.cc:219 +#: redirect_box.cc:1062 msgid "Copy" msgstr "Copiar" -#: editor.cc:2041 +#: editor.cc:2034 msgid "Paste at edit cursor" msgstr "Colar à cursor de edição" -#: editor.cc:2042 +#: editor.cc:2035 msgid "Paste at mouse" msgstr "Colar à mouse" -#: editor.cc:2046 editor.cc:3462 +#: editor.cc:2039 editor.cc:3490 msgid "Align" msgstr "Alinhamento" -#: editor.cc:2047 editor.cc:3464 +#: editor.cc:2040 editor.cc:3492 msgid "Align Relative" msgstr "Alinhamento Relativo" -#: editor.cc:2051 +#: editor.cc:2044 msgid "Insert chunk" msgstr "Inserir trecho" -#: editor.cc:2058 +#: editor.cc:2051 #, fuzzy msgid "Insert Selected Region" msgstr "Loop região selecionada" -#: editor.cc:2059 +#: editor.cc:2052 msgid "Insert Existing Audio" msgstr "" -#: editor.cc:2068 editor.cc:2124 +#: editor.cc:2061 editor.cc:2117 msgid "Nudge entire track fwd" msgstr "Retorcar toda a trilha para frente" -#: editor.cc:2069 editor.cc:2125 +#: editor.cc:2062 editor.cc:2118 msgid "Nudge track after edit cursor fwd" msgstr "Retocar trilha após o cursor de edição" -#: editor.cc:2070 editor.cc:2126 +#: editor.cc:2063 editor.cc:2119 msgid "Nudge entire track bwd" msgstr "Retorcar toda a trilha para trás" -#: editor.cc:2071 editor.cc:2127 +#: editor.cc:2064 editor.cc:2120 msgid "Nudge track after edit cursor bwd" msgstr "Retocar toda a trilha, do cursor de edição para trás" -#: editor.cc:2117 editor.cc:3459 editor_actions.cc:220 redirect_box.cc:1062 +#: editor.cc:2110 editor.cc:3487 editor_actions.cc:221 redirect_box.cc:1064 msgid "Paste" msgstr "Colar" -#: editor.cc:2637 +#: editor.cc:2630 msgid "select/move objects" msgstr "selecionar/mover objetos" -#: editor.cc:2638 +#: editor.cc:2631 msgid "select/move ranges" msgstr "selecionar/mover intervalos" -#: editor.cc:2639 +#: editor.cc:2632 msgid "draw gain automation" msgstr "desenhar ganho automático" -#: editor.cc:2640 +#: editor.cc:2633 msgid "select zoom range" msgstr "selecionar intervalo de zoom" -#: editor.cc:2641 +#: editor.cc:2634 msgid "stretch/shrink regions" msgstr "esticar/encolher regiões" -#: editor.cc:2642 +#: editor.cc:2635 #, fuzzy msgid "listen to specific regions" msgstr "Ouça no região especifica" -#: editor.cc:2753 +#: editor.cc:2746 msgid "Start:" msgstr "Inicio:" -#: editor.cc:2754 +#: editor.cc:2747 msgid "End:" msgstr "Final:" -#: editor.cc:3097 -#, fuzzy -msgid "set selected trackview" -msgstr "Inserir seleção" - -#: editor.cc:3137 -#, fuzzy -msgid "set selected control point" -msgstr "Remover ponto de controlo" - -#: editor.cc:3246 -#, fuzzy -msgid "set selected regionview" -msgstr "Loop região selecionada" - -#: editor.cc:3334 editor.cc:3374 +#: editor.cc:3362 editor.cc:3402 #, fuzzy msgid "set selected regions" msgstr "Loop região selecionada" -#: editor.cc:3430 editor_actions.cc:203 +#: editor.cc:3458 editor_actions.cc:204 msgid "Undo" msgstr "Desfazer" -#: editor.cc:3432 +#: editor.cc:3460 msgid "Undo (%1)" msgstr "Desfazer (%1)" -#: editor.cc:3442 editor_actions.cc:205 +#: editor.cc:3470 editor_actions.cc:206 msgid "Redo" msgstr "Refazer" -#: editor.cc:3444 +#: editor.cc:3472 msgid "Redo (%1)" msgstr "Refazer (%1)" -#: editor.cc:3478 +#: editor.cc:3506 msgid "... as new track" msgstr "" -#: editor.cc:3479 +#: editor.cc:3507 #, fuzzy msgid "... as new region" msgstr "normalizar região" -#: editor.cc:3481 +#: editor.cc:3509 msgid "Import audio (copy)" msgstr "Importar áudio (copiar)" -#: editor.cc:3484 +#: editor.cc:3512 msgid "Remove last capture" msgstr "Remover última captura" -#: editor.cc:3508 +#: editor.cc:3536 msgid "Duplicate how many times?" msgstr "Duplicar quantas vezes?" -#: editor.cc:3994 +#: editor.cc:4022 msgid "" "Playlist %1 is currently unused.\n" "If left alone, no audio files used by it will be cleaned.\n" "If deleted, audio files used by it alone by will cleaned." msgstr "" -#: editor.cc:4002 +#: editor.cc:4030 #, fuzzy msgid "Delete playlist" msgstr "Nome para a imagem capturada" -#: editor.cc:4003 +#: editor.cc:4031 #, fuzzy msgid "Keep playlist" msgstr "Nome para a imagem capturada" -#: editor.cc:4004 editor_audio_import.cc:237 editor_ops.cc:1976 -#: editor_timefx.cc:52 export_dialog.cc:971 io_selector.cc:58 -#: io_selector.cc:792 redirect_box.cc:901 tempo_dialog.cc:19 -#: tempo_dialog.cc:36 tempo_dialog.cc:152 tempo_dialog.cc:170 +#: editor.cc:4032 editor_audio_import.cc:236 editor_ops.cc:2048 +#: editor_timefx.cc:71 export_dialog.cc:971 io_selector.cc:59 +#: io_selector.cc:793 redirect_box.cc:903 tempo_dialog.cc:20 +#: tempo_dialog.cc:37 tempo_dialog.cc:202 tempo_dialog.cc:220 msgid "Cancel" msgstr "Cancelar" -#: editor.cc:4171 +#: editor.cc:4199 #, fuzzy msgid "new playlists" msgstr "Nome para a imagem capturada" -#: editor.cc:4179 +#: editor.cc:4207 #, fuzzy msgid "copy playlists" msgstr "Nome para a imagem capturada" -#: editor.cc:4187 +#: editor.cc:4215 #, fuzzy msgid "clear playlists" msgstr "Nome para a imagem capturada" -#: editor_actions.cc:27 +#: editor_actions.cc:28 #, fuzzy msgid "Select regions" msgstr "Loop região selecionada" -#: editor_actions.cc:28 +#: editor_actions.cc:29 #, fuzzy msgid "Select range operations" msgstr "Loop região selecionada" -#: editor_actions.cc:29 +#: editor_actions.cc:30 #, fuzzy msgid "Move edit cursor" msgstr "Colar à cursor de edição" -#: editor_actions.cc:30 +#: editor_actions.cc:31 #, fuzzy msgid "Region operations" msgstr "Regiões/criação" -#: editor_actions.cc:31 +#: editor_actions.cc:32 msgid "Tools" msgstr "" -#: editor_actions.cc:32 +#: editor_actions.cc:33 msgid "View" msgstr "" -#: editor_actions.cc:33 +#: editor_actions.cc:34 #, fuzzy msgid "ZoomFocus" msgstr "Foco de Zoom" -#: editor_actions.cc:34 +#: editor_actions.cc:35 #, fuzzy msgid "Meter hold" msgstr "VU (medidor volumétrico)" -#: editor_actions.cc:35 +#: editor_actions.cc:36 msgid "Meter falloff" msgstr "" -#: editor_actions.cc:37 +#: editor_actions.cc:38 #, fuzzy msgid "Crossfades" msgstr "Fade cruzado" -#: editor_actions.cc:38 +#: editor_actions.cc:39 #, fuzzy msgid "Monitoring" msgstr "Usar Monitoração de Hardware" -#: editor_actions.cc:39 +#: editor_actions.cc:40 #, fuzzy msgid "Autoconnect" msgstr "Conectar" -#: editor_actions.cc:40 +#: editor_actions.cc:41 #, fuzzy msgid "Layering" msgstr "Camada" -#: editor_actions.cc:41 +#: editor_actions.cc:42 #, fuzzy msgid "Metering" msgstr "VU (medidor volumétrico)" -#: editor_actions.cc:42 +#: editor_actions.cc:43 msgid "Fall off rate" msgstr "" -#: editor_actions.cc:43 +#: editor_actions.cc:44 msgid "Hold Time" msgstr "" -#: editor_actions.cc:44 +#: editor_actions.cc:45 msgid "Add Existing Audio" msgstr "" #. add named actions for the editor -#: editor_actions.cc:49 +#: editor_actions.cc:50 #, fuzzy msgid "Show Editor Mixer" msgstr "Mostrar painéis de mixer de todas as trilhas de áudio" -#: editor_actions.cc:54 +#: editor_actions.cc:55 #, fuzzy msgid "Span Entire Overlap" msgstr "Trazer região uma camada para frente" -#: editor_actions.cc:56 editor_actions.cc:383 +#: editor_actions.cc:57 editor_actions.cc:384 #, fuzzy msgid "Short" msgstr "porta" -#: editor_actions.cc:63 +#: editor_actions.cc:64 msgid "Created Automatically" msgstr "" -#: editor_actions.cc:66 +#: editor_actions.cc:67 msgid "Playhead to Next Region Start" msgstr "" -#: editor_actions.cc:68 +#: editor_actions.cc:69 msgid "Playhead to Next Region End" msgstr "" -#: editor_actions.cc:70 +#: editor_actions.cc:71 msgid "Playhead to Next Region Sync" msgstr "" -#: editor_actions.cc:73 +#: editor_actions.cc:74 msgid "Playhead to Previous Region Start" msgstr "" -#: editor_actions.cc:75 +#: editor_actions.cc:76 msgid "Playhead to Previous Region End" msgstr "" -#: editor_actions.cc:77 +#: editor_actions.cc:78 msgid "Playhead to Previous Region Sync" msgstr "" -#: editor_actions.cc:80 +#: editor_actions.cc:81 #, fuzzy msgid "Edit Cursor to Next Region Start" msgstr "Do cursor de edição ao final" -#: editor_actions.cc:82 +#: editor_actions.cc:83 #, fuzzy msgid "Edit Cursor to Next Region End" msgstr "Do cursor de edição ao final" -#: editor_actions.cc:84 +#: editor_actions.cc:85 #, fuzzy msgid "Edit Cursor to Next Region Sync" msgstr "Do cursor de edição ao final" -#: editor_actions.cc:87 +#: editor_actions.cc:88 msgid "Edit Cursor to Previous Region Start" msgstr "" -#: editor_actions.cc:89 +#: editor_actions.cc:90 #, fuzzy msgid "Edit Cursor to Previous Region End" msgstr "Do cursor de edição ao final" -#: editor_actions.cc:91 +#: editor_actions.cc:92 #, fuzzy msgid "Edit Cursor to Previous Region Sync" msgstr "Do cursor de edição ao final" -#: editor_actions.cc:94 +#: editor_actions.cc:95 msgid "Playhead to Range Start" msgstr "" -#: editor_actions.cc:96 +#: editor_actions.cc:97 #, fuzzy msgid "Playhead to Range End" msgstr "Reproduzir intervalo" -#: editor_actions.cc:99 +#: editor_actions.cc:100 #, fuzzy msgid "Edit Cursor to Range Start" msgstr "Do cursor de edição ao final" -#: editor_actions.cc:101 +#: editor_actions.cc:102 #, fuzzy msgid "Edit Cursor to Range End" msgstr "Do cursor de edição ao final" -#: editor_actions.cc:104 editor_ops.cc:1300 +#: editor_actions.cc:105 editor_ops.cc:1363 #, fuzzy msgid "select all" msgstr "Selecionar Tudo" -#: editor_actions.cc:106 +#: editor_actions.cc:107 #, fuzzy msgid "Select All After Edit Cursor" msgstr "Reproduzir a partir do cursor" -#: editor_actions.cc:108 +#: editor_actions.cc:109 msgid "Select All Before Edit Cursor" msgstr "" -#: editor_actions.cc:111 +#: editor_actions.cc:112 #, fuzzy msgid "Select All After Playhead" msgstr "Marcar aqui" -#: editor_actions.cc:113 +#: editor_actions.cc:114 #, fuzzy msgid "Select All Before Playhead" msgstr "Marcar aqui" -#: editor_actions.cc:115 +#: editor_actions.cc:116 #, fuzzy msgid "Select All Between Cursors" msgstr "Reproduzir a partir do cursor" -#: editor_actions.cc:118 +#: editor_actions.cc:119 #, fuzzy msgid "Select All in Punch Range" msgstr "Fazer intervalo de inserção" -#: editor_actions.cc:120 +#: editor_actions.cc:121 #, fuzzy msgid "Select All in Loop Range" msgstr "Selecionar intervalo de loop" -#: editor_actions.cc:123 +#: editor_actions.cc:124 msgid "Jump Forward to Mark" msgstr "" -#: editor_actions.cc:125 +#: editor_actions.cc:126 msgid "Jump Backward to Mark" msgstr "" -#: editor_actions.cc:127 +#: editor_actions.cc:128 #, fuzzy msgid "Add Location from Playhead" msgstr "Marcar aqui" -#: editor_actions.cc:130 +#: editor_actions.cc:131 #, fuzzy msgid "Nudge Forward" msgstr "Retocar" -#: editor_actions.cc:132 +#: editor_actions.cc:133 #, fuzzy msgid "Nudge Next Forward" msgstr "Avançar o mínimo região/seleção" -#: editor_actions.cc:134 +#: editor_actions.cc:135 #, fuzzy msgid "Nudge Backward" msgstr "Retocar" -#: editor_actions.cc:136 +#: editor_actions.cc:137 #, fuzzy msgid "Nudge Next Backward" msgstr "Retorcar toda a trilha para frente" -#: editor_actions.cc:139 +#: editor_actions.cc:140 #, fuzzy msgid "Zoom Out" msgstr "Menos Zoom" -#: editor_actions.cc:141 +#: editor_actions.cc:142 #, fuzzy msgid "Zoom In" msgstr "Mais Zoom" -#: editor_actions.cc:143 +#: editor_actions.cc:144 #, fuzzy msgid "Zoom to Session" msgstr "Zoom na sessão" -#: editor_actions.cc:146 +#: editor_actions.cc:147 #, fuzzy msgid "Scroll Tracks Up" msgstr "Preencher Trilha" -#: editor_actions.cc:148 +#: editor_actions.cc:149 msgid "Scroll Tracks Down" msgstr "" -#: editor_actions.cc:150 +#: editor_actions.cc:151 #, fuzzy msgid "Step Tracks Up" msgstr "Outras trilhas" -#: editor_actions.cc:152 +#: editor_actions.cc:153 msgid "Step Tracks Down" msgstr "" -#: editor_actions.cc:155 +#: editor_actions.cc:156 msgid "Scroll Backward" msgstr "" -#: editor_actions.cc:157 +#: editor_actions.cc:158 msgid "Scroll Forward" msgstr "" -#: editor_actions.cc:159 +#: editor_actions.cc:160 msgid "goto" msgstr "" -#: editor_actions.cc:161 +#: editor_actions.cc:162 #, fuzzy msgid "Center Playhead" msgstr "Início" -#: editor_actions.cc:163 +#: editor_actions.cc:164 #, fuzzy msgid "Center Edit Cursor" msgstr "Cursor de Edição" -#: editor_actions.cc:165 +#: editor_actions.cc:166 #, fuzzy msgid "Playhead Forward" msgstr "Início" -#: editor_actions.cc:167 +#: editor_actions.cc:168 #, fuzzy msgid "Playhead Backward" msgstr "Início" -#: editor_actions.cc:169 +#: editor_actions.cc:170 #, fuzzy msgid "Playhead to Edit" msgstr "Início" -#: editor_actions.cc:171 +#: editor_actions.cc:172 #, fuzzy msgid "Edit to Playhead" msgstr "Marcar aqui" -#: editor_actions.cc:174 +#: editor_actions.cc:175 #, fuzzy msgid "Align Regions Start" msgstr "Começo de regiões" -#: editor_actions.cc:176 +#: editor_actions.cc:177 #, fuzzy msgid "Align Regions Start Relative" msgstr "Alinhamento Relativo" -#: editor_actions.cc:178 +#: editor_actions.cc:179 #, fuzzy msgid "Align Regions End" msgstr "normalizar região" -#: editor_actions.cc:180 +#: editor_actions.cc:181 #, fuzzy msgid "Align Regions End Relative" msgstr "Alinhamento Relativo" -#: editor_actions.cc:183 +#: editor_actions.cc:184 #, fuzzy msgid "Align Regions Sync" msgstr "normalizar região" -#: editor_actions.cc:185 +#: editor_actions.cc:186 #, fuzzy msgid "Align Regions Sync Relative" msgstr "Alinhamento Relativo" -#: editor_actions.cc:188 +#: editor_actions.cc:189 #, fuzzy msgid "Audition at Mouse" msgstr "Audição" -#: editor_actions.cc:190 +#: editor_actions.cc:191 #, fuzzy msgid "Brush at Mouse" msgstr "Colar à mouse" -#: editor_actions.cc:192 +#: editor_actions.cc:193 #, fuzzy msgid "Set Edit Cursor" msgstr "Cursor de Edição" -#: editor_actions.cc:194 +#: editor_actions.cc:195 #, fuzzy msgid "Mute/Unmute Region" msgstr "Criar Região" -#: editor_actions.cc:196 +#: editor_actions.cc:197 #, fuzzy msgid "Set Playhead" msgstr "Início" -#: editor_actions.cc:198 +#: editor_actions.cc:199 #, fuzzy msgid "Split Region" msgstr "Separar Região" -#: editor_actions.cc:200 +#: editor_actions.cc:201 #, fuzzy msgid "Set Region Sync Position" msgstr "Por Posição da Região" -#: editor_actions.cc:208 +#: editor_actions.cc:209 #, fuzzy msgid "Export Session" msgstr "Exportar região" -#: editor_actions.cc:210 +#: editor_actions.cc:211 #, fuzzy msgid "Export Range" msgstr "Separar intervalo" #. Note: for now, editor-delete does the exact same thing as editor-cut -#: editor_actions.cc:216 +#: editor_actions.cc:217 msgid "Delete" msgstr "Apagar" -#: editor_actions.cc:222 +#: editor_actions.cc:223 #, fuzzy msgid "Duplicate Region" msgstr "Loop região selecionada" -#: editor_actions.cc:224 +#: editor_actions.cc:225 #, fuzzy msgid "Duplicate Range" msgstr "Duplicar" -#: editor_actions.cc:226 +#: editor_actions.cc:227 msgid "Insert Region" msgstr "Inserir região" -#: editor_actions.cc:228 +#: editor_actions.cc:229 #, fuzzy msgid "Reverse Region" msgstr "inverter horizontalmente as regiões" -#: editor_actions.cc:230 +#: editor_actions.cc:231 #, fuzzy msgid "Normalize Region" msgstr "Normalizar" -#: editor_actions.cc:232 +#: editor_actions.cc:233 #, fuzzy msgid "crop" msgstr "copiar" -#: editor_actions.cc:234 +#: editor_actions.cc:235 #, fuzzy msgid "Insert Chunk" msgstr "Inserir trecho" -#: editor_actions.cc:237 +#: editor_actions.cc:238 #, fuzzy msgid "Split at edit cursor" msgstr "Do início ao cursor de edição" -#: editor_actions.cc:240 +#: editor_actions.cc:241 #, fuzzy msgid "Start Range" msgstr "Separar intervalo" -#: editor_actions.cc:242 +#: editor_actions.cc:243 msgid "Finish Range" msgstr "" -#: editor_actions.cc:244 +#: editor_actions.cc:245 msgid "Finish add Range" msgstr "" -#: editor_actions.cc:247 +#: editor_actions.cc:248 msgid "Extend Range to End of Region" msgstr "" -#: editor_actions.cc:249 +#: editor_actions.cc:250 #, fuzzy msgid "Extend Range to Start of Region" msgstr "Ir para o início da sessão" -#: editor_actions.cc:252 +#: editor_actions.cc:253 #, fuzzy msgid "Follow Playhead" msgstr "Reproduzir a partir do início" -#: editor_actions.cc:260 +#: editor_actions.cc:261 #, fuzzy msgid "Zoom Focus Left" msgstr "Foco de Zoom" -#: editor_actions.cc:262 +#: editor_actions.cc:263 #, fuzzy msgid "Zoom Focus Right" msgstr "Foco de Zoom" -#: editor_actions.cc:264 +#: editor_actions.cc:265 #, fuzzy msgid "Zoom Focus Center" msgstr "Foco de Zoom" -#: editor_actions.cc:266 +#: editor_actions.cc:267 #, fuzzy msgid "Zoom Focus Playhead" msgstr "Foco de Zoom" -#: editor_actions.cc:268 +#: editor_actions.cc:269 #, fuzzy msgid "Zoom Focus Edit" msgstr "Foco de Zoom" -#: editor_actions.cc:274 +#: editor_actions.cc:275 msgid "Object Tool" msgstr "" -#: editor_actions.cc:275 +#: editor_actions.cc:276 #, fuzzy msgid "Range Tool" msgstr "Intervalo" -#: editor_actions.cc:276 +#: editor_actions.cc:277 msgid "Gain Tool" msgstr "" -#: editor_actions.cc:277 +#: editor_actions.cc:278 #, fuzzy msgid "Zoom Tool" msgstr "Menos Zoom" -#: editor_actions.cc:278 +#: editor_actions.cc:279 msgid "Timefx Tool" msgstr "" -#: editor_actions.cc:285 +#: editor_actions.cc:286 #, fuzzy msgid "Snap to frame" msgstr "Modo de Ajuste" -#: editor_actions.cc:286 +#: editor_actions.cc:287 #, fuzzy msgid "Snap to cd frame" msgstr "Modo de Ajuste" -#: editor_actions.cc:287 +#: editor_actions.cc:288 #, fuzzy msgid "Snap to SMPTE frame" msgstr "SMPTE Frames" -#: editor_actions.cc:288 +#: editor_actions.cc:289 #, fuzzy msgid "Snap to SMPTE seconds" msgstr "SMPTE segundo" -#: editor_actions.cc:289 +#: editor_actions.cc:290 #, fuzzy msgid "Snap to SMPTE minutes" msgstr "SMPTE Minutos" -#: editor_actions.cc:290 +#: editor_actions.cc:291 #, fuzzy msgid "Snap to seconds" msgstr "Segundos" -#: editor_actions.cc:291 +#: editor_actions.cc:292 msgid "Snap to minutes" msgstr "" -#: editor_actions.cc:292 +#: editor_actions.cc:293 #, fuzzy msgid "Snap to thirtyseconds" msgstr "trigésima segunda (32)" -#: editor_actions.cc:293 +#: editor_actions.cc:294 msgid "Snap to asixteenthbeat" msgstr "" -#: editor_actions.cc:294 +#: editor_actions.cc:295 msgid "Snap to eighths" msgstr "" -#: editor_actions.cc:295 +#: editor_actions.cc:296 msgid "Snap to quarters" msgstr "" -#: editor_actions.cc:296 +#: editor_actions.cc:297 #, fuzzy msgid "Snap to thirds" msgstr "Modo de Ajuste" -#: editor_actions.cc:297 +#: editor_actions.cc:298 #, fuzzy msgid "Snap to beat" msgstr "Modo de Ajuste" -#: editor_actions.cc:298 +#: editor_actions.cc:299 #, fuzzy msgid "Snap to bar" msgstr "Ajustar a" -#: editor_actions.cc:299 +#: editor_actions.cc:300 #, fuzzy msgid "Snap to mark" msgstr "adicionar marca de intervalo" -#: editor_actions.cc:300 +#: editor_actions.cc:301 #, fuzzy msgid "Snap to edit cursor" msgstr "Do início ao cursor de edição" -#: editor_actions.cc:301 +#: editor_actions.cc:302 #, fuzzy msgid "Snap to region start" msgstr "Começo de regiões" -#: editor_actions.cc:302 +#: editor_actions.cc:303 #, fuzzy msgid "Snap to region end" msgstr "Fim de regiões" -#: editor_actions.cc:303 +#: editor_actions.cc:304 #, fuzzy msgid "Snap to region sync" msgstr "Sincronizações de região" -#: editor_actions.cc:304 +#: editor_actions.cc:305 #, fuzzy msgid "Snap to region boundary" msgstr "Divisas de região" #. the region list popup menu -#: editor_actions.cc:313 +#: editor_actions.cc:314 #, fuzzy msgid "Sort" msgstr "porta" -#: editor_actions.cc:321 +#: editor_actions.cc:322 msgid "Show all" msgstr "Mostrar tudo" -#: editor_actions.cc:322 +#: editor_actions.cc:323 #, fuzzy msgid "Show automatic regions" msgstr "mostra toda a automação" -#: editor_actions.cc:324 +#: editor_actions.cc:325 msgid "Ascending" msgstr "Ascendente" -#: editor_actions.cc:326 +#: editor_actions.cc:327 msgid "Descending" msgstr "Descendente" -#: editor_actions.cc:329 +#: editor_actions.cc:330 msgid "By Region Name" msgstr "Por Nome da Região" -#: editor_actions.cc:331 +#: editor_actions.cc:332 msgid "By Region Length" msgstr "Por Tamanho da Região" -#: editor_actions.cc:333 +#: editor_actions.cc:334 msgid "By Region Position" msgstr "Por Posição da Região" -#: editor_actions.cc:335 +#: editor_actions.cc:336 msgid "By Region Timestamp" msgstr "Por tempo data/hora da Região" -#: editor_actions.cc:337 +#: editor_actions.cc:338 msgid "By Region Start in File" msgstr "Por posição inicial da Região no arquivo" -#: editor_actions.cc:339 +#: editor_actions.cc:340 msgid "By Region End in File" msgstr "Por posição final da Região no arquivo" -#: editor_actions.cc:341 +#: editor_actions.cc:342 msgid "By Source File Name" msgstr "Por nome original do arquivo" -#: editor_actions.cc:343 +#: editor_actions.cc:344 msgid "By Source File Length" msgstr "Por tamanho do arquivo original" -#: editor_actions.cc:345 +#: editor_actions.cc:346 msgid "By Source File Creation Date" msgstr "Por data de criação do arquivo original" -#: editor_actions.cc:347 +#: editor_actions.cc:348 msgid "By Source Filesystem" msgstr "Por sistema de arquivos original" #. the next two are duplicate items with different names for use in two different contexts -#: editor_actions.cc:353 +#: editor_actions.cc:354 #, fuzzy msgid "Add External Audio" msgstr "Adicionar na lista de regiões" -#: editor_actions.cc:355 +#: editor_actions.cc:356 #, fuzzy msgid "as Region(s)" msgstr "normalizar região" -#: editor_actions.cc:357 +#: editor_actions.cc:358 #, fuzzy msgid "as Tracks" msgstr "Trilhas" -#: editor_actions.cc:359 +#: editor_actions.cc:360 #, fuzzy msgid "to Tracks" msgstr "Trilhas" -#: editor_actions.cc:362 +#: editor_actions.cc:363 #, fuzzy msgid "Show Waveforms" msgstr "Mostrar formas de onda áudio" -#: editor_actions.cc:363 +#: editor_actions.cc:364 #, fuzzy msgid "Show Waveforms While Recording" msgstr "Mostrar formas de onda áudio quando gravando" -#: editor_actions.cc:364 +#: editor_actions.cc:365 #, fuzzy msgid "Show Measures" msgstr "Mostrar linhas de medida" -#: editor_actions.cc:377 editor_actions.cc:384 +#: editor_actions.cc:378 editor_actions.cc:385 msgid "Medium" msgstr "" -#: editor_actions.cc:379 +#: editor_actions.cc:380 #, fuzzy msgid "Faster" msgstr "Fades" -#: editor_actions.cc:385 +#: editor_actions.cc:386 msgid "Long" msgstr "" -#: editor_actions.cc:389 +#: editor_actions.cc:390 #, fuzzy msgid "Later is Higher" msgstr "Enviar região uma camada para trás" -#: editor_actions.cc:390 +#: editor_actions.cc:391 #, fuzzy msgid "Most Recently Moved/Added is Higher" msgstr "Enviar região uma camada para trás" -#: editor_actions.cc:391 +#: editor_actions.cc:392 #, fuzzy msgid "Most Recently Added is Higher" msgstr "Enviar região uma camada para trás" @@ -3443,40 +3430,40 @@ msgstr "" msgid "Add existing audio to session" msgstr "mostra a automação existente" -#: editor_audio_import.cc:143 +#: editor_audio_import.cc:142 #, fuzzy msgid "ardour: importing %1" msgstr "ardour: exportar" -#: editor_audio_import.cc:147 +#: editor_audio_import.cc:146 msgid "Cancel Import" msgstr "Cancelar importação" -#: editor_audio_import.cc:225 +#: editor_audio_import.cc:224 #, fuzzy msgid "Editor: cannot open file \"%1\", (%2)" msgstr "Editor: não foi possível abrir o arquivo \"%1\" (%2)" -#: editor_audio_import.cc:233 +#: editor_audio_import.cc:232 #, fuzzy msgid "Cancel entire import" msgstr "Cancelar importação" -#: editor_audio_import.cc:234 +#: editor_audio_import.cc:233 #, fuzzy msgid "Don't embed it" msgstr "Não %1" -#: editor_audio_import.cc:235 +#: editor_audio_import.cc:234 msgid "Embed all without questions" msgstr "" -#: editor_audio_import.cc:240 +#: editor_audio_import.cc:239 #, fuzzy msgid "Embed it anyway" msgstr "Embutir mesmo assim" -#: editor_audio_import.cc:243 +#: editor_audio_import.cc:242 #, fuzzy msgid "" "%1\n" @@ -3484,75 +3471,63 @@ msgid "" msgstr "" "A freqüência de áudio deste arquivo não corresponde à freqüência da sessão!" -#: editor_audio_import.cc:276 +#: editor_audio_import.cc:275 msgid "could not open %1" msgstr "não foi possível abrir %1" -#: editor_audio_import.cc:321 +#: editor_audio_import.cc:320 #, fuzzy msgid "insert sndfile" msgstr "Inserir arquivo de áudio externo" #. stuff for the verbose canvas cursor -#: editor_canvas.cc:117 +#: editor_canvas.cc:118 msgid "VerboseCanvasCursor" msgstr "" -#: editor_canvas.cc:285 -msgid "Start a new session\n" -msgstr "Iniciar uma nova sessão\n" - -#: editor_canvas.cc:285 -msgid "via Session menu" -msgstr "via menu de Sessão" - -#: editor_canvas.cc:288 -msgid "FirstActionMessage" -msgstr "" - -#: editor_edit_groups.cc:52 mixer_ui.cc:732 +#: editor_edit_groups.cc:53 mixer_ui.cc:736 #, fuzzy msgid "Activate All" msgstr "Ativar" -#: editor_edit_groups.cc:53 mixer_ui.cc:733 +#: editor_edit_groups.cc:54 mixer_ui.cc:737 #, fuzzy msgid "Disable All" msgstr "Desconectar" -#: editor_edit_groups.cc:55 mixer_ui.cc:735 +#: editor_edit_groups.cc:56 mixer_ui.cc:739 #, fuzzy msgid "Add group" msgstr "Sem grupo" -#: editor_edit_groups.cc:225 mixer_ui.cc:964 +#: editor_edit_groups.cc:229 mixer_ui.cc:970 #, fuzzy msgid "unnamed" msgstr "Renomear" -#: editor_edit_groups.cc:252 mixer_ui.cc:830 +#: editor_edit_groups.cc:258 mixer_ui.cc:834 msgid "-all-" msgstr "-tudo-" -#: editor_export_audio.cc:64 +#: editor_export_audio.cc:65 msgid "" "There is no selection to export.\n" "\n" "Select a selection using the range mouse mode" msgstr "" -#: editor_export_audio.cc:109 +#: editor_export_audio.cc:110 msgid "" "There are no ranges to export.\n" "\n" "Create 1 or more ranges by dragging the mouse in the range bar" msgstr "" -#: editor_imageframe.cc:624 editor_imageframe.cc:654 +#: editor_imageframe.cc:625 editor_imageframe.cc:655 msgid "programming error: no ImageFrameView selected" msgstr "" -#: editor_imageframe.cc:847 editor_imageframe.cc:869 +#: editor_imageframe.cc:848 editor_imageframe.cc:870 msgid "programming error: no MarkerView selected" msgstr "" @@ -3561,141 +3536,141 @@ msgstr "" msgid "mute region" msgstr "mutar esta região" -#: editor_keys.cc:45 +#: editor_keys.cc:46 #, fuzzy msgid "keyboard selection" msgstr "Separar Seleção" -#: editor_markers.cc:291 editor_ops.cc:1227 editor_ops.cc:1240 -#: editor_ops.cc:1258 location_ui.cc:773 +#: editor_markers.cc:292 editor_ops.cc:1290 editor_ops.cc:1303 +#: editor_ops.cc:1321 location_ui.cc:774 msgid "add marker" msgstr "adicionar marca" -#: editor_markers.cc:306 editor_markers.cc:379 editor_markers.cc:551 -#: editor_markers.cc:569 editor_markers.cc:588 editor_markers.cc:607 -#: editor_markers.cc:637 editor_markers.cc:665 editor_markers.cc:693 -#: editor_markers.cc:731 editor_markers.cc:758 editor_markers.cc:781 -#: editor_markers.cc:800 editor_mouse.cc:1994 editor_mouse.cc:4237 +#: editor_markers.cc:307 editor_markers.cc:380 editor_markers.cc:552 +#: editor_markers.cc:570 editor_markers.cc:589 editor_markers.cc:608 +#: editor_markers.cc:638 editor_markers.cc:666 editor_markers.cc:694 +#: editor_markers.cc:732 editor_markers.cc:759 editor_markers.cc:782 +#: editor_markers.cc:801 editor_mouse.cc:2015 editor_mouse.cc:4275 msgid "programming error: marker canvas item has no marker object pointer!" msgstr "" -#: editor_markers.cc:330 location_ui.cc:655 +#: editor_markers.cc:331 location_ui.cc:656 msgid "remove marker" msgstr "remover marca" -#: editor_markers.cc:457 +#: editor_markers.cc:458 #, fuzzy msgid "Locate to Mark" msgstr "Ir para" -#: editor_markers.cc:458 +#: editor_markers.cc:459 #, fuzzy msgid "Play from Mark" msgstr "Reproduzir do início" -#: editor_markers.cc:459 +#: editor_markers.cc:460 #, fuzzy msgid "Set Mark from Playhead" msgstr "Marcar aqui" -#: editor_markers.cc:463 +#: editor_markers.cc:464 #, fuzzy msgid "Rename Mark" msgstr "Renomear" -#: editor_markers.cc:464 +#: editor_markers.cc:465 #, fuzzy msgid "Hide Mark" msgstr "ocultar esta trilha" -#: editor_markers.cc:465 +#: editor_markers.cc:466 #, fuzzy msgid "Remove Mark" msgstr "Remover Marca" -#: editor_markers.cc:478 editor_markers.cc:534 +#: editor_markers.cc:479 editor_markers.cc:535 #, fuzzy msgid "Locate to Range Mark" msgstr "Marcas de Localização" -#: editor_markers.cc:479 editor_markers.cc:535 +#: editor_markers.cc:480 editor_markers.cc:536 #, fuzzy msgid "Play from Range Mark" msgstr "Reproduzir intervalo" -#: editor_markers.cc:480 +#: editor_markers.cc:481 #, fuzzy msgid "Loop Range" msgstr "Loop no intervalo" -#: editor_markers.cc:481 editor_markers.cc:536 +#: editor_markers.cc:482 editor_markers.cc:537 #, fuzzy msgid "Set Range Mark from Playhead" msgstr "Marcar aqui" -#: editor_markers.cc:482 editor_markers.cc:537 +#: editor_markers.cc:483 editor_markers.cc:538 #, fuzzy msgid "Set Range from Range Selection" msgstr "Reproduzir seleção" -#: editor_markers.cc:486 +#: editor_markers.cc:487 #, fuzzy msgid "Rename Range" msgstr "Renomear" -#: editor_markers.cc:487 editor_markers.cc:539 +#: editor_markers.cc:488 editor_markers.cc:540 #, fuzzy msgid "Hide Range" msgstr "Adicionar Novo Intervalo" -#: editor_markers.cc:488 +#: editor_markers.cc:489 #, fuzzy msgid "Remove Range" msgstr "Remover Campo" -#: editor_markers.cc:492 editor_markers.cc:541 +#: editor_markers.cc:493 editor_markers.cc:542 #, fuzzy msgid "Separate Regions in Range" msgstr "Nova região a partir da intervalo" -#: editor_markers.cc:493 editor_markers.cc:542 +#: editor_markers.cc:494 editor_markers.cc:543 #, fuzzy msgid "Select All in Range" msgstr "Selecionar tudo na trilha" -#: editor_markers.cc:519 +#: editor_markers.cc:520 msgid "Set Loop Range" msgstr "Marcar um intervalo de loop" -#: editor_markers.cc:520 +#: editor_markers.cc:521 msgid "Set Punch Range" msgstr "Fazer intervalo de inserção" -#: editor_markers.cc:814 +#: editor_markers.cc:815 #, fuzzy msgid "New Name:" msgstr "novo nome: " -#: editor_markers.cc:817 +#: editor_markers.cc:818 msgid "ardour: rename mark" msgstr "ardour: renomear marca" -#: editor_markers.cc:819 +#: editor_markers.cc:820 #, fuzzy msgid "ardour: rename range" msgstr "ardour: renomear região" -#: editor_markers.cc:839 +#: editor_markers.cc:840 #, fuzzy msgid "rename marker" msgstr "remover marca" -#: editor_markers.cc:864 +#: editor_markers.cc:865 #, fuzzy msgid "set loop range" msgstr "selecionar intervalo de zoom" -#: editor_markers.cc:890 +#: editor_markers.cc:891 #, fuzzy msgid "set punch range" msgstr "Selecionar intervalo atual" @@ -3704,418 +3679,424 @@ msgstr "Selecionar intervalo atual" msgid "Editor::event_frame() used on unhandled event type %1" msgstr "" -#: editor_mouse.cc:1589 +#: editor_mouse.cc:313 +#, fuzzy +msgid "select on click" +msgstr "Usar com metrônomo" + +#: editor_mouse.cc:1590 msgid "programming error: start_grab called without drag item" msgstr "" -#: editor_mouse.cc:1793 +#: editor_mouse.cc:1814 #, fuzzy msgid "change fade in length" msgstr "fade in na edição" -#: editor_mouse.cc:1811 +#: editor_mouse.cc:1832 msgid "programming error: fade out canvas item has no regionview data pointer!" msgstr "" -#: editor_mouse.cc:1885 +#: editor_mouse.cc:1906 #, fuzzy msgid "change fade out length" msgstr "fade out na edição" -#: editor_mouse.cc:1904 +#: editor_mouse.cc:1925 msgid "programming error: cursor canvas item has no cursor data pointer!" msgstr "" -#: editor_mouse.cc:2119 +#: editor_mouse.cc:2142 #, fuzzy msgid "move marker" msgstr "remover marca" -#: editor_mouse.cc:2142 editor_mouse.cc:2173 editor_tempodisplay.cc:461 +#: editor_mouse.cc:2165 editor_mouse.cc:2196 editor_tempodisplay.cc:459 msgid "" "programming error: meter marker canvas item has no marker object pointer!" msgstr "" -#: editor_mouse.cc:2241 +#: editor_mouse.cc:2264 #, fuzzy msgid "copy meter mark" msgstr "remover marca" -#: editor_mouse.cc:2251 +#: editor_mouse.cc:2274 #, fuzzy msgid "move meter mark" msgstr "remover marca" -#: editor_mouse.cc:2266 editor_mouse.cc:2299 editor_tempodisplay.cc:327 -#: editor_tempodisplay.cc:411 editor_tempodisplay.cc:430 +#: editor_mouse.cc:2289 editor_mouse.cc:2322 editor_tempodisplay.cc:331 +#: editor_tempodisplay.cc:409 editor_tempodisplay.cc:428 msgid "" "programming error: tempo marker canvas item has no marker object pointer!" msgstr "" -#: editor_mouse.cc:2271 editor_mouse.cc:2304 editor_tempodisplay.cc:332 -#: editor_tempodisplay.cc:416 +#: editor_mouse.cc:2294 editor_mouse.cc:2327 editor_tempodisplay.cc:336 +#: editor_tempodisplay.cc:414 msgid "programming error: marker for tempo is not a tempo marker!" msgstr "" -#: editor_mouse.cc:2371 +#: editor_mouse.cc:2394 #, fuzzy msgid "copy tempo mark" msgstr "remover marca" -#: editor_mouse.cc:2381 +#: editor_mouse.cc:2404 #, fuzzy msgid "move tempo mark" msgstr "remover marca" -#: editor_mouse.cc:2395 editor_mouse.cc:2414 editor_mouse.cc:2427 +#: editor_mouse.cc:2418 editor_mouse.cc:2437 editor_mouse.cc:2450 msgid "" "programming error: control point canvas item has no control point object " "pointer!" msgstr "" -#: editor_mouse.cc:2525 +#: editor_mouse.cc:2555 msgid "programming error: line canvas item has no line pointer!" msgstr "" -#: editor_mouse.cc:2634 +#: editor_mouse.cc:2664 #, fuzzy msgid "move region(s)" msgstr "inverter horizontalmente as regiões" -#. this is committed in the grab finished callback. -#: editor_mouse.cc:2646 -msgid "Drag region copy" -msgstr "" - -#: editor_mouse.cc:2758 +#: editor_mouse.cc:2727 #, fuzzy msgid "Drag region brush" msgstr "normalizar região" +#. don't copy again +#. this is committed in the grab finished callback. +#: editor_mouse.cc:2751 +msgid "Drag region copy" +msgstr "" + #. A selection grab currently creates two undo/redo operations, one for #. creating the new region and another for moving it. #. -#: editor_mouse.cc:3574 +#: editor_mouse.cc:3609 #, fuzzy msgid "selection grab" msgstr "Seleção" -#: editor_mouse.cc:3615 +#: editor_mouse.cc:3650 #, fuzzy msgid "cancel selection" msgstr "Reproduzir seleção" -#: editor_mouse.cc:3722 +#: editor_mouse.cc:3760 #, fuzzy msgid "range selection" msgstr "Reproduzir seleção" -#: editor_mouse.cc:3738 +#: editor_mouse.cc:3776 #, fuzzy msgid "trim selection start" msgstr "Desde a localização" -#: editor_mouse.cc:3754 +#: editor_mouse.cc:3792 #, fuzzy msgid "trim selection end" msgstr "Desde a localização" -#: editor_mouse.cc:3771 +#: editor_mouse.cc:3809 #, fuzzy msgid "move selection" msgstr "Saltar Seleção" -#: editor_mouse.cc:4157 +#: editor_mouse.cc:4195 #, fuzzy msgid "Start point trim" msgstr "Do início ao cursor de edição" -#: editor_mouse.cc:4185 +#: editor_mouse.cc:4223 msgid "End point trim" msgstr "" -#: editor_mouse.cc:4224 +#: editor_mouse.cc:4262 msgid "trimmed region" msgstr "região aparado" -#: editor_mouse.cc:4363 +#: editor_mouse.cc:4400 #, fuzzy msgid "new range marker" msgstr "adicionar marca de intervalo" -#: editor_mouse.cc:4578 +#: editor_mouse.cc:4642 #, fuzzy msgid "select regions" msgstr "Loop região selecionada" -#: editor_mouse.cc:4607 +#: editor_mouse.cc:4671 msgid "Name for region:" msgstr "Nome para a região:" -#: editor_mouse.cc:4671 +#: editor_mouse.cc:4735 #, fuzzy msgid "timestretch" msgstr "ardour: esticar no tempo" -#: editor_ops.cc:132 +#: editor_ops.cc:195 #, fuzzy msgid "split" msgstr "Separar" -#: editor_ops.cc:168 +#: editor_ops.cc:231 #, fuzzy msgid "remove region" msgstr "inverter horizontalmente as regiões" -#: editor_ops.cc:187 +#: editor_ops.cc:250 msgid "" " This is destructive, will possibly delete audio files\n" "It cannot be undone\n" "Do you really want to destroy %1 ?" msgstr "" -#: editor_ops.cc:191 +#: editor_ops.cc:254 #, fuzzy msgid "these regions" msgstr "inverter horizontalmente as regiões" -#: editor_ops.cc:191 +#: editor_ops.cc:254 #, fuzzy msgid "this region" msgstr "mutar esta região" -#: editor_ops.cc:193 editor_ops.cc:3229 route_ui.cc:700 -#: visual_time_axis.cc:277 +#: editor_ops.cc:256 editor_ops.cc:3318 route_ui.cc:707 +#: visual_time_axis.cc:278 msgid "No, do nothing." msgstr "Não, não faça nada." -#: editor_ops.cc:196 +#: editor_ops.cc:259 #, fuzzy msgid "Yes, destroy them." msgstr "Sim, remova definitivamente isto." -#: editor_ops.cc:198 editor_ops.cc:3230 +#: editor_ops.cc:261 editor_ops.cc:3319 msgid "Yes, destroy it." msgstr "Sim, remova definitivamente isto." -#: editor_ops.cc:289 editor_ops.cc:317 +#: editor_ops.cc:352 editor_ops.cc:380 #, fuzzy msgid "extend selection" msgstr "Separar Seleção" -#: editor_ops.cc:333 editor_ops.cc:367 editor_ops.cc:411 editor_ops.cc:437 +#: editor_ops.cc:396 editor_ops.cc:430 editor_ops.cc:474 editor_ops.cc:500 msgid "nudge forward" msgstr "" -#: editor_ops.cc:501 +#: editor_ops.cc:564 msgid "build_region_boundary_cache called with snap_type = %1" msgstr "" -#: editor_ops.cc:1354 +#: editor_ops.cc:1420 #, fuzzy msgid "select all within" msgstr "Selecionar Tudo" -#: editor_ops.cc:1380 +#: editor_ops.cc:1452 #, fuzzy msgid "set selection from region" msgstr "Nova região a partir da seleção" -#: editor_ops.cc:1413 +#: editor_ops.cc:1485 #, fuzzy msgid "set selection from range" msgstr "Nova região a partir da seleção" -#: editor_ops.cc:1443 +#: editor_ops.cc:1515 #, fuzzy msgid "select all from range" msgstr "selecionar intervalo de zoom" -#: editor_ops.cc:1465 +#: editor_ops.cc:1537 #, fuzzy msgid "select all from punch" msgstr "Selecionar Tudo" -#: editor_ops.cc:1487 +#: editor_ops.cc:1559 #, fuzzy msgid "select all from loop" msgstr "Selecionar Tudo" -#: editor_ops.cc:1501 +#: editor_ops.cc:1573 #, fuzzy msgid "select all after cursor" msgstr "Colar à cursor de edição" -#: editor_ops.cc:1506 +#: editor_ops.cc:1578 #, fuzzy msgid "select all before cursor" msgstr "Reproduzir a partir do cursor" -#: editor_ops.cc:1536 +#: editor_ops.cc:1608 #, fuzzy msgid "select all between cursors" msgstr "Reproduzir a partir do cursor" -#: editor_ops.cc:1667 +#: editor_ops.cc:1739 msgid "clear markers" msgstr "limpar marcas" -#: editor_ops.cc:1679 +#: editor_ops.cc:1751 msgid "clear ranges" msgstr "limpar intervalos" -#: editor_ops.cc:1698 +#: editor_ops.cc:1770 msgid "clear locations" msgstr "limpar localizações" -#: editor_ops.cc:1748 +#: editor_ops.cc:1820 #, fuzzy msgid "insert dragged region" msgstr "Inserir Região" -#: editor_ops.cc:1784 +#: editor_ops.cc:1856 #, fuzzy msgid "insert region" msgstr "Inserir Região" -#: editor_ops.cc:1975 io_selector.cc:57 io_selector.cc:791 +#: editor_ops.cc:2047 io_selector.cc:58 io_selector.cc:792 msgid "OK" msgstr "OK" -#: editor_ops.cc:1982 +#: editor_ops.cc:2054 msgid "ardour: rename region" msgstr "ardour: renomear região" -#: editor_ops.cc:2205 editor_ops.cc:2254 +#: editor_ops.cc:2277 editor_ops.cc:2326 #, fuzzy msgid "separate" msgstr "Separar Região" -#: editor_ops.cc:2316 +#: editor_ops.cc:2388 #, fuzzy msgid "trim to selection" msgstr "Desde a localização" -#: editor_ops.cc:2356 +#: editor_ops.cc:2428 msgid "region fill" msgstr "" -#: editor_ops.cc:2415 +#: editor_ops.cc:2487 #, fuzzy msgid "fill selection" msgstr "Reproduzir seleção continuamente" -#: editor_ops.cc:2436 +#: editor_ops.cc:2508 msgid "Programming error. that region doesn't cover that position" msgstr "" -#: editor_ops.cc:2439 +#: editor_ops.cc:2511 #, fuzzy msgid "set region sync position" msgstr "Regiões/posição" -#: editor_ops.cc:2454 +#: editor_ops.cc:2526 msgid "Place the edit cursor at the desired sync point" msgstr "Coloque o cursor de edição no ponto de sincronia desejado" -#: editor_ops.cc:2459 +#: editor_ops.cc:2531 #, fuzzy msgid "set sync from edit cursor" msgstr "Reproduzir a partir do cursor" -#: editor_ops.cc:2471 +#: editor_ops.cc:2543 #, fuzzy msgid "remove sync" msgstr "Remover ponto de sincronia" -#: editor_ops.cc:2485 +#: editor_ops.cc:2557 #, fuzzy msgid "naturalize" msgstr "Normalizar" -#: editor_ops.cc:2549 +#: editor_ops.cc:2621 #, fuzzy msgid "align selection (relative)" msgstr "Alinhamento Relativo" -#: editor_ops.cc:2577 +#: editor_ops.cc:2649 #, fuzzy msgid "align selection" msgstr "Saltar Seleção" -#: editor_ops.cc:2589 +#: editor_ops.cc:2661 #, fuzzy msgid "align region" msgstr "normalizar região" -#: editor_ops.cc:2636 editor_ops.cc:2661 +#: editor_ops.cc:2708 editor_ops.cc:2733 #, fuzzy msgid "trim to edit" msgstr "Do início ao cursor de edição" -#: editor_ops.cc:2712 +#: editor_ops.cc:2784 #, fuzzy msgid "ardour: freeze" msgstr "ardour: renomear região" -#: editor_ops.cc:2717 +#: editor_ops.cc:2789 #, fuzzy msgid "Cancel Freeze" msgstr "Cancelar" -#: editor_ops.cc:2754 +#: editor_ops.cc:2826 #, fuzzy msgid "bounce range" msgstr "intervalo" -#: editor_ops.cc:2807 +#: editor_ops.cc:2879 msgid "cut" msgstr "cortar" -#: editor_ops.cc:2810 +#: editor_ops.cc:2882 msgid "copy" msgstr "copiar" -#: editor_ops.cc:2823 +#: editor_ops.cc:2895 msgid " objects" msgstr "objetos" -#: editor_ops.cc:2849 +#: editor_ops.cc:2921 msgid " range" msgstr "intervalo" -#: editor_ops.cc:3006 +#: editor_ops.cc:3078 #, fuzzy msgid "paste" msgstr "Colar" -#: editor_ops.cc:3044 +#: editor_ops.cc:3116 #, fuzzy msgid "paste chunk" msgstr "Criar trecho" #. clear (below) will clear the argument list -#: editor_ops.cc:3085 +#: editor_ops.cc:3157 #, fuzzy msgid "duplicate region" msgstr "Loop região selecionada" -#: editor_ops.cc:3130 +#: editor_ops.cc:3202 #, fuzzy msgid "duplicate selection" msgstr "Saltar Seleção" -#: editor_ops.cc:3170 +#: editor_ops.cc:3259 #, fuzzy msgid "clear playlist" msgstr "Nome para a imagem capturada" -#: editor_ops.cc:3199 +#: editor_ops.cc:3288 #, fuzzy msgid "nudge track" msgstr "Ocultar esta trilha" -#: editor_ops.cc:3226 +#: editor_ops.cc:3315 msgid "" "Do you really want to destroy the last capture?\n" "(This is destructive and cannot be undone)" @@ -4123,163 +4104,160 @@ msgstr "" "Você quer realmente remover definitivamente a última captura?\n" "(Isto não poderá ser desfeito)" -#: editor_ops.cc:3254 +#: editor_ops.cc:3343 #, fuzzy msgid "normalize" msgstr "Normalizar" -#: editor_ops.cc:3301 +#: editor_ops.cc:3390 msgid "reverse regions" msgstr "inverter horizontalmente as regiões" -#: editor_region_list.cc:93 editor_region_list.cc:98 editor_region_list.cc:101 -#: location_ui.cc:55 +#: editor_region_list.cc:98 editor_region_list.cc:103 +#: editor_region_list.cc:106 location_ui.cc:56 msgid "Hidden" msgstr "Oculto" #. added a new fresh one at the end -#: editor_route_list.cc:101 editor_route_list.cc:102 editor_route_list.cc:246 +#: editor_route_list.cc:102 editor_route_list.cc:103 editor_route_list.cc:247 msgid "editor" msgstr "editor" -#: editor_route_list.cc:309 mixer_ui.cc:695 +#: editor_route_list.cc:310 mixer_ui.cc:699 msgid "Show All" msgstr "Mostrar Tudo" -#: editor_route_list.cc:310 mixer_ui.cc:696 +#: editor_route_list.cc:311 mixer_ui.cc:700 msgid "Hide All" msgstr "Ocultar Tudo" -#: editor_route_list.cc:311 mixer_ui.cc:697 +#: editor_route_list.cc:312 mixer_ui.cc:701 #, fuzzy msgid "Show All Audio Tracks" msgstr "Mostrar todos os barramentos de áudio" -#: editor_route_list.cc:312 mixer_ui.cc:698 +#: editor_route_list.cc:313 mixer_ui.cc:702 #, fuzzy msgid "Hide All Audio Tracks" msgstr "Ocultar todos os barramentos de áudio" -#: editor_route_list.cc:313 mixer_ui.cc:699 +#: editor_route_list.cc:314 mixer_ui.cc:703 #, fuzzy msgid "Show All Audio Busses" msgstr "Mostrar todos os barramentos de áudio" -#: editor_route_list.cc:314 mixer_ui.cc:700 +#: editor_route_list.cc:315 mixer_ui.cc:704 #, fuzzy msgid "Hide All Audio Busses" msgstr "Ocultar todos os barramentos de áudio" -#: editor_rulers.cc:311 +#: editor_rulers.cc:312 msgid "New location marker" msgstr "Nova marca de localização" -#: editor_rulers.cc:312 +#: editor_rulers.cc:313 msgid "Clear all locations" msgstr "Apagar todas as localizações" #. ruler_items.push_back (MenuElem (_("New Range"))); -#: editor_rulers.cc:317 +#: editor_rulers.cc:318 msgid "Clear all ranges" msgstr "Remover todos os intervalos" -#: editor_rulers.cc:326 +#: editor_rulers.cc:327 msgid "New Tempo" msgstr "Novo Andamento" -#: editor_rulers.cc:327 +#: editor_rulers.cc:328 msgid "Clear tempo" msgstr "Apagar andamento" -#: editor_rulers.cc:332 +#: editor_rulers.cc:333 msgid "New Meter" msgstr "Novo Meter" -#: editor_rulers.cc:333 +#: editor_rulers.cc:334 msgid "Clear meter" msgstr "Apagar meter" -#: editor_rulers.cc:341 +#: editor_rulers.cc:342 msgid "Min:Secs" msgstr "Min:Segs" -#: editor_selection_list.cc:110 +#: editor_selection_list.cc:108 #, fuzzy msgid "Name for Chunk:" msgstr "nome para o trecho" -#: editor_selection_list.cc:113 +#: editor_selection_list.cc:111 #, fuzzy msgid "Create Chunk" msgstr "Criar trecho" -#: editor_selection_list.cc:113 +#: editor_selection_list.cc:111 msgid "Forget it" msgstr "Esqueça isto" -#: editor_tempodisplay.cc:249 editor_tempodisplay.cc:289 +#: editor_tempodisplay.cc:253 editor_tempodisplay.cc:293 msgid "add" msgstr "adicionar" -#: editor_tempodisplay.cc:271 +#: editor_tempodisplay.cc:275 #, fuzzy msgid "add tempo mark" msgstr "adicionar marca de intervalo" -#: editor_tempodisplay.cc:311 +#: editor_tempodisplay.cc:315 #, fuzzy msgid "add meter mark" msgstr "adicionar marca de intervalo" -#: editor_tempodisplay.cc:344 editor_tempodisplay.cc:375 +#: editor_tempodisplay.cc:348 editor_tempodisplay.cc:376 msgid "done" msgstr "pronto" -#: editor_tempodisplay.cc:365 editor_tempodisplay.cc:396 +#: editor_tempodisplay.cc:366 editor_tempodisplay.cc:394 msgid "replace tempo mark" msgstr "" -#: editor_tempodisplay.cc:435 editor_tempodisplay.cc:466 +#: editor_tempodisplay.cc:433 editor_tempodisplay.cc:464 msgid "programming error: marker for meter is not a meter marker!" msgstr "" -#: editor_tempodisplay.cc:445 editor_tempodisplay.cc:478 +#: editor_tempodisplay.cc:443 editor_tempodisplay.cc:476 #, fuzzy msgid "remove tempo mark" msgstr "remover marca" -#: editor_timefx.cc:50 +#: editor_timefx.cc:51 msgid "Quick but Ugly" msgstr "Rápido mas Feio" -#: editor_timefx.cc:51 +#: editor_timefx.cc:52 msgid "Skip Anti-aliasing" msgstr "Pular Anti-aliasing" -#: editor_timefx.cc:53 -msgid "Stretch/Shrink it" -msgstr "Esticar/Encolher isto" - -#: editor_timefx.cc:57 +#: editor_timefx.cc:56 msgid "ardour: timestretch" msgstr "ardour: esticar no tempo" -#: editor_timefx.cc:58 +#: editor_timefx.cc:57 msgid "TimeStretchDialog" msgstr "Diálogo esticar no tempo" -#: editor_timefx.cc:80 editor_timefx.cc:81 editor_timefx.cc:82 -#: editor_timefx.cc:83 +#: editor_timefx.cc:70 +msgid "Stretch/Shrink it" +msgstr "Esticar/Encolher isto" + +#: editor_timefx.cc:73 editor_timefx.cc:74 msgid "TimeStretchButton" msgstr "Botão esticar no tempo" -#: editor_timefx.cc:84 +#: editor_timefx.cc:75 msgid "TimeStretchProgress" msgstr "Progresso esticar no tempo" -#. GTK2FIX -#. current_timestretch->close (); -#: editor_timefx.cc:153 +#: editor_timefx.cc:139 msgid "timestretch cannot be started - thread creation error" msgstr "" @@ -4413,7 +4391,7 @@ msgstr "" msgid "Export to File" msgstr "Exportar para CD" -#: export_dialog.cc:113 option_editor.cc:82 option_editor.cc:83 +#: export_dialog.cc:113 option_editor.cc:83 option_editor.cc:84 msgid "Browse" msgstr "Localizar" @@ -4429,7 +4407,8 @@ msgstr "ardour: exportar" msgid "ardour_export" msgstr "" -#: export_dialog.cc:139 export_dialog.cc:155 +#: export_dialog.cc:139 export_dialog.cc:155 mixer_strip.cc:124 +#: mixer_strip.cc:767 #, fuzzy msgid "Output" msgstr "Saídas" @@ -4468,147 +4447,75 @@ msgstr "" msgid "File already exists, do you want to overwrite it?" msgstr "" -#: export_dialog.cc:1159 export_range_markers_dialog.cc:154 +#: export_dialog.cc:1159 export_range_markers_dialog.cc:153 msgid "Cannot write file in: " msgstr "" #. warning dialog -#: export_range_markers_dialog.cc:136 +#: export_range_markers_dialog.cc:135 msgid "Please enter a valid target directory." msgstr "" -#: export_range_markers_dialog.cc:144 +#: export_range_markers_dialog.cc:143 msgid "" "Please select an existing target directory. Files\n" "are not allowed!" msgstr "" -#: gain_automation_time_axis.cc:61 +#: gain_automation_time_axis.cc:62 #, fuzzy msgid "add gain automation event" msgstr "adicionar evento de automação para " -#: gain_meter.cc:66 +#: gain_meter.cc:67 msgid "cannot find images for fader slider" msgstr "" -#: gain_meter.cc:73 +#: gain_meter.cc:74 msgid "cannot find images for fader rail" msgstr "" -#: gain_meter.cc:88 -msgid "dbFS" -msgstr "" - -#: gain_meter.cc:89 gain_meter.cc:143 gain_meter.cc:704 -msgid "pre" -msgstr "" - -#: gain_meter.cc:139 gain_meter.cc:700 -#, fuzzy -msgid "input" -msgstr "%1 entrada" - -#: gain_meter.cc:147 gain_meter.cc:708 -#, fuzzy -msgid "post" -msgstr "porta" - -#. TRANSLATORS: this string should be longest of the strings -#. used to describe meter points. In english, its "input". -#. -#: gain_meter.cc:155 -msgid "tupni" -msgstr "" - -#: gain_meter.cc:174 gain_meter.cc:458 gain_meter.cc:480 gain_meter.cc:525 +#: gain_meter.cc:130 gain_meter.cc:339 gain_meter.cc:494 gain_meter.cc:539 #, fuzzy msgid "-inf" msgstr "entrada" -#: glade/new_session_dialog.glade.h:1 +#: gain_meter.cc:140 #, fuzzy -msgid "Advanced" -msgstr "Avançado ..." +msgid "Fader automation mode" +msgstr "modo automático de pan" -#: glade/new_session_dialog.glade.h:2 -msgid "Input" +#: gain_meter.cc:141 +#, fuzzy +msgid "Fader automation type" +msgstr "Tipo do pan automático" + +#. XXX it might different in different languages +#: gain_meter.cc:182 gain_meter.cc:817 panner_ui.cc:99 panner_ui.cc:807 +msgid "Abs" msgstr "" -#: glade/new_session_dialog.glade.h:3 +#: gain_meter.cc:472 #, fuzzy -msgid "Output" -msgstr "Saídas" +msgid "-Inf" +msgstr "entrada" -#: glade/new_session_dialog.glade.h:4 +#: gain_meter.cc:781 mixer_strip.cc:770 panner_ui.cc:771 #, fuzzy -msgid "Automatically connect inputs" -msgstr "conectar automaticamente entradas das trilhas com as portas físicas" +msgid "O" +msgstr "OU" -#: glade/new_session_dialog.glade.h:5 -#, fuzzy -msgid "Automatically connect outputs" -msgstr "conectar manualmente saídas das trilhas" - -#: glade/new_session_dialog.glade.h:6 -#, fuzzy -msgid "Channel Count" -msgstr "Cancelar importação" - -#: glade/new_session_dialog.glade.h:7 -msgid "Connect to Master Bus" +#: gain_meter.cc:784 panner_ui.cc:774 +msgid "P" msgstr "" -#: glade/new_session_dialog.glade.h:8 -msgid "Connect to physical outputs" +#: gain_meter.cc:787 panner_ui.cc:777 +msgid "T" msgstr "" -#: glade/new_session_dialog.glade.h:9 -#, fuzzy -msgid "Create Control Bus" -msgstr "Controle de Saídas" - -#: glade/new_session_dialog.glade.h:10 -#, fuzzy -msgid "Create Master Bus" -msgstr "usar saída master" - -#: glade/new_session_dialog.glade.h:11 -#, fuzzy -msgid "New Session" -msgstr "Sessão" - -# -#: glade/new_session_dialog.glade.h:12 -#, fuzzy -msgid "Open Recent Session" -msgstr "abrir sessão" - -# -#: glade/new_session_dialog.glade.h:13 -#, fuzzy -msgid "Open Session" -msgstr "abrir sessão" - -#: glade/new_session_dialog.glade.h:14 -#, fuzzy -msgid "Port limit" -msgstr "Esqueça isto" - -#: glade/new_session_dialog.glade.h:15 -#, fuzzy -msgid "Select a File" -msgstr "Selecionar Tudo" - -#: glade/new_session_dialog.glade.h:16 -#, fuzzy -msgid "Select a Session" -msgstr "Loop região selecionada" - -#: glade/new_session_dialog.glade.h:17 -#, fuzzy -msgid "Track/Bus connection options" -msgstr "Inspetador de Trilhas/Barramentos" +#: gain_meter.cc:790 panner_ui.cc:780 +msgid "W" +msgstr "" #: gtk-custom-ruler.c:126 #, fuzzy @@ -4655,236 +4562,236 @@ msgid "Draw current ruler position" msgstr "" #. end-of-file, other end closed or shutdown? -#: imageframe_socket_handler.cc:126 +#: imageframe_socket_handler.cc:127 msgid "Image Compositor Socket has been shutdown/closed" msgstr "" -#: imageframe_time_axis.cc:287 +#: imageframe_time_axis.cc:286 #, fuzzy msgid "0.5 seconds" msgstr "Segundos" -#: imageframe_time_axis.cc:288 marker_time_axis.cc:241 +#: imageframe_time_axis.cc:287 marker_time_axis.cc:242 #, fuzzy msgid "1 seconds" msgstr "Segundos" -#: imageframe_time_axis.cc:289 marker_time_axis.cc:242 +#: imageframe_time_axis.cc:288 marker_time_axis.cc:243 #, fuzzy msgid "1.5 seconds" msgstr "Segundos" -#: imageframe_time_axis.cc:290 marker_time_axis.cc:243 +#: imageframe_time_axis.cc:289 marker_time_axis.cc:244 #, fuzzy msgid "2 seconds" msgstr "Segundos" -#: imageframe_time_axis.cc:291 marker_time_axis.cc:244 +#: imageframe_time_axis.cc:290 marker_time_axis.cc:245 #, fuzzy msgid "2.5 seconds" msgstr "Segundos" -#: imageframe_time_axis.cc:292 marker_time_axis.cc:245 +#: imageframe_time_axis.cc:291 marker_time_axis.cc:246 #, fuzzy msgid "3 seconds" msgstr "Segundos" #. duration_items.push_back(SeparatorElem()) ; #. duration_items.push_back(MenuElem (_("custom"), mem_fun(*this, &ImageFrameTimeAxis::set_marker_duration_custom))) ; -#: imageframe_time_axis.cc:297 marker_time_axis.cc:250 +#: imageframe_time_axis.cc:296 marker_time_axis.cc:251 #, fuzzy msgid "Duration (sec)" msgstr "normalizar região" -#: imageframe_time_axis.cc:302 +#: imageframe_time_axis.cc:301 #, fuzzy msgid "Remove Frame" msgstr "Remover Campo" -#: imageframe_time_axis.cc:305 +#: imageframe_time_axis.cc:304 #, fuzzy msgid "Image Frame" msgstr "Quadros" -#: imageframe_time_axis.cc:306 marker_time_axis.cc:256 +#: imageframe_time_axis.cc:305 marker_time_axis.cc:257 #, fuzzy msgid "Rename Track" msgstr "Renomear" -#: io_selector.cc:59 io_selector.cc:793 +#: io_selector.cc:60 io_selector.cc:794 msgid "Rescan" msgstr "Rescanear" -#: io_selector.cc:67 +#: io_selector.cc:68 msgid "%1 input" msgstr "%1 entrada" -#: io_selector.cc:69 +#: io_selector.cc:70 msgid "%1 output" msgstr "%1 saída" -#: io_selector.cc:141 route_params_ui.cc:106 +#: io_selector.cc:142 route_params_ui.cc:107 msgid "Inputs" msgstr "Entradas" -#: io_selector.cc:141 route_params_ui.cc:107 +#: io_selector.cc:142 route_params_ui.cc:108 msgid "Outputs" msgstr "Saídas" -#: io_selector.cc:142 +#: io_selector.cc:143 #, fuzzy msgid "Add Input" msgstr "adicionar entrada" -#: io_selector.cc:142 +#: io_selector.cc:143 #, fuzzy msgid "Add Output" msgstr "adicionar saída" -#: io_selector.cc:143 +#: io_selector.cc:144 #, fuzzy msgid "Remove Input" msgstr "Remover ponto de sincronia" -#: io_selector.cc:143 +#: io_selector.cc:144 #, fuzzy msgid "Remove Output" msgstr "# Saídas" -#: io_selector.cc:144 +#: io_selector.cc:145 #, fuzzy msgid "Disconnect All" msgstr "Desconectar" -#: io_selector.cc:158 +#: io_selector.cc:159 msgid "Available connections" msgstr "Conexões disponíveis" -#: io_selector.cc:554 io_selector.cc:573 +#: io_selector.cc:555 io_selector.cc:574 msgid "There are no more JACK ports available." msgstr "" -#: io_selector.cc:648 io_selector.cc:675 io_selector.cc:728 +#: io_selector.cc:649 io_selector.cc:676 io_selector.cc:729 msgid "port" msgstr "porta" -#: io_selector.cc:797 +#: io_selector.cc:798 msgid "ardour: " msgstr "" -#: keyboard.cc:297 +#: keyboard.cc:299 msgid "KeyboardTarget: keyname \"%1\" is unknown." msgstr "KeyboardTarget: nome da tecla \"%1\" é desconhecido." -#: keyboard.cc:523 +#: keyboard.cc:525 msgid "" "Your system is completely broken - NumLock uses \"%1\"as its modifier. This " "is madness - see the man page for xmodmap to find out how to fix this." msgstr "" -#: keyboard.cc:531 +#: keyboard.cc:533 msgid "" "Your system generates \"%1\" when the NumLock key is pressed. This can cause " "problems when editing so Ardour will use %2 to mean Meta rather than %1" msgstr "" -#: keyboard.cc:592 +#: keyboard.cc:594 msgid "You have %1 keys bound to \"mod1\"" msgstr "Você já tem %1 atalho de teclado para \"mod1\"" -#: keyboard.cc:607 +#: keyboard.cc:609 msgid "You have %1 keys bound to \"mod2\"" msgstr "Você já tem %1 atalho de teclado para \"mod2\"" -#: keyboard.cc:622 +#: keyboard.cc:624 msgid "You have %1 keys bound to \"mod3\"" msgstr "Você já tem %1 atalho de teclado para \"mod3\"" -#: keyboard.cc:637 +#: keyboard.cc:639 msgid "You have %1 keys bound to \"mod4\"" msgstr "Você já tem %1 atalho de teclado para \"mod4\"" -#: keyboard.cc:652 +#: keyboard.cc:654 msgid "You have %1 keys bound to \"mod5\"" msgstr "Você já tem %1 atalho de teclado para \"mod5\"" -#: location_ui.cc:47 location_ui.cc:50 +#: location_ui.cc:48 location_ui.cc:51 msgid "Set" msgstr "Fazer" -#: location_ui.cc:48 location_ui.cc:51 +#: location_ui.cc:49 location_ui.cc:52 msgid "Go" msgstr "Ir" -#: location_ui.cc:54 +#: location_ui.cc:55 msgid "CD" msgstr "CD" -#: location_ui.cc:57 +#: location_ui.cc:58 msgid "SCMS" msgstr "" -#: location_ui.cc:58 +#: location_ui.cc:59 msgid "Pre-Emphasis" msgstr "" -#: location_ui.cc:569 +#: location_ui.cc:570 msgid "Add New Location" msgstr "Adicionar Nova Localização" -#: location_ui.cc:570 +#: location_ui.cc:571 msgid "Add New Range" msgstr "Adicionar Novo Intervalo" -#: location_ui.cc:574 +#: location_ui.cc:575 msgid "ardour: locations" msgstr "ardour: localizações" -#: location_ui.cc:575 +#: location_ui.cc:576 msgid "ardour_locations" msgstr "" -#: location_ui.cc:603 +#: location_ui.cc:604 #, fuzzy msgid "Location (CD Index) Markers" msgstr "Marcas de Localização" -#: location_ui.cc:623 +#: location_ui.cc:624 #, fuzzy msgid "Range (CD Track) Markers" msgstr "Marcas de Intervalos" -#: location_ui.cc:789 +#: location_ui.cc:790 msgid "add range marker" msgstr "adicionar marca de intervalo" -#: main.cc:71 +#: main.cc:72 msgid "ardour is killing itself for a clean exit\n" msgstr "o ardour está se matando para uma saída limpa\n" -#: main.cc:80 +#: main.cc:81 msgid "stopping user interface\n" msgstr "interrompendo a interface do usuário\n" #. XXX its doubtful that snprintf() is async-safe -#: main.cc:99 +#: main.cc:100 #, c-format msgid "%d(%d): received signal %d\n" msgstr "" -#: main.cc:185 +#: main.cc:186 msgid "cannot become new process group leader (%1)" msgstr "" -#: main.cc:212 +#: main.cc:213 msgid "cannot setup signal handling for %1" msgstr "" -#: main.cc:223 +#: main.cc:224 msgid "cannot set default signal mask (%1)" msgstr "" -#: main.cc:253 +#: main.cc:254 #, fuzzy msgid "" "Without a UI style file, ardour will look strange.\n" @@ -4893,12 +4800,12 @@ msgstr "" "Sem um arquivo de estilo o ardour vai ficar meio esquisito.\n" "Por favor, configure a variável ambiente ARDOUR_UI_RC para um arquivo válido" -#: main.cc:273 +#: main.cc:276 #, fuzzy msgid "Ardour could not connect to JACK." msgstr "Não foi possível se conectar ao servidor JACK" -#: main.cc:277 +#: main.cc:280 #, fuzzy msgid "" "There are several possible reasons:\n" @@ -4918,69 +4825,12 @@ msgstr "" "\n" "Por favor, considere essas razões, e talvez (re)inicie o JACK." -#: main.cc:324 -msgid "Ardour/GTK " -msgstr "" - -#: main.cc:326 -msgid "" -"\n" -" (built using " -msgstr "" - -#: main.cc:330 -#, fuzzy -msgid " with libardour " -msgstr " executando com libardour " - -#: main.cc:335 -msgid " and GCC version " -msgstr "" - -#: main.cc:345 -msgid "Copyright (C) 1999-2005 Paul Davis" -msgstr "" - -#: main.cc:346 -msgid "" -"Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " -"Baker" -msgstr "" - -#: main.cc:348 -msgid "Ardour comes with ABSOLUTELY NO WARRANTY" -msgstr "Ardour não oferece ABSOLUTAMENTE NENHUMA GARANTIA" - -#: main.cc:349 -msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." -msgstr "" - -#: main.cc:350 -msgid "This is free software, and you are welcome to redistribute it " -msgstr "Isto é um Software Livre. Fique à vontade para redistribuí-lo " - -#: main.cc:351 -msgid "under certain conditions; see the source for copying conditions." -msgstr "com algumas condições; veja o fonte para mais detalhes" - -#: main.cc:360 -msgid "could not create ARDOUR GUI" -msgstr "não foi possível criar a INTERFACE ARDOUR" - -#: main.cc:378 -msgid "Could not connect to JACK server as \"%1\"" -msgstr "Não foi possível se conectar ao servidor JACK com \"%1\"" - -#: main.cc:381 -msgid "could not initialize Ardour." -msgstr "não foi possível iniciar o Ardour." - -#: main.cc:392 +#: main.cc:310 msgid "could not load command line session \"%1\"" msgstr "não foi possível carregar a sessão da linha de comando \"%1\"" #. it wasn't new, but we require a new session -#: main.cc:412 +#: main.cc:330 msgid "" "\n" "\n" @@ -4988,7 +4838,7 @@ msgid "" "To avoid this message, start ardour as \"ardour %1" msgstr "" -#: main.cc:423 +#: main.cc:341 msgid "" "\n" "\n" @@ -4996,296 +4846,445 @@ msgid "" "To create it from the command line, start ardour as \"ardour --new %1" msgstr "" +#: main.cc:405 +msgid "Ardour/GTK " +msgstr "" + +#: main.cc:407 +msgid "" +"\n" +" (built using " +msgstr "" + +#: main.cc:411 +#, fuzzy +msgid " with libardour " +msgstr " executando com libardour " + +#: main.cc:416 +msgid " and GCC version " +msgstr "" + +#: main.cc:426 +msgid "Copyright (C) 1999-2006 Paul Davis" +msgstr "" + +#: main.cc:427 +msgid "" +"Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " +"Baker" +msgstr "" + +#: main.cc:429 +msgid "Ardour comes with ABSOLUTELY NO WARRANTY" +msgstr "Ardour não oferece ABSOLUTAMENTE NENHUMA GARANTIA" + +#: main.cc:430 +msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." +msgstr "" + +#: main.cc:431 +msgid "This is free software, and you are welcome to redistribute it " +msgstr "Isto é um Software Livre. Fique à vontade para redistribuí-lo " + +#: main.cc:432 +msgid "under certain conditions; see the source for copying conditions." +msgstr "com algumas condições; veja o fonte para mais detalhes" + +#: main.cc:441 +msgid "could not create ARDOUR GUI" +msgstr "não foi possível criar a INTERFACE ARDOUR" + +#: main.cc:459 +msgid "Could not connect to JACK server as \"%1\"" +msgstr "Não foi possível se conectar ao servidor JACK com \"%1\"" + +#: main.cc:462 +msgid "could not initialize Ardour." +msgstr "não foi possível iniciar o Ardour." + #: marker.cc:244 #, fuzzy msgid "MarkerText" msgstr "Marcas" -#: marker_time_axis.cc:253 +#: marker_time_axis.cc:254 msgid "Remove Marker" msgstr "Remover Marca" -#: marker_time_axis.cc:255 +#: marker_time_axis.cc:256 msgid "Marker" msgstr "Marca" -#: meter_bridge.cc:77 +#: meter_bridge.cc:78 msgid "ardour: meter bridge" msgstr "ardour: VU (medidor volumétrico)" -#: meter_bridge.cc:78 +#: meter_bridge.cc:79 msgid "ardour_meter_bridge" msgstr "" -#: meter_bridge_strip.cc:79 meter_bridge_strip.cc:93 +#: meter_bridge_strip.cc:80 meter_bridge_strip.cc:94 #, c-format msgid "# of %u-sample overs" msgstr "" -#: meter_bridge_strip.cc:221 +#: meter_bridge_strip.cc:222 #, fuzzy msgid "New Name for Meter:" msgstr "Novo nome para VU (medidor volumétrico)" -#: mixer_strip.cc:85 mixer_strip.cc:437 region_editor.cc:46 -msgid "mute" -msgstr "mudo" +#: mixer_strip.cc:95 mixer_strip.cc:140 mixer_strip.cc:1227 +msgid "pre" +msgstr "" -#: mixer_strip.cc:85 mixer_strip.cc:438 -msgid "solo" -msgstr "solo" - -#: mixer_strip.cc:85 mixer_strip.cc:436 -msgid "RECORD" -msgstr "GRAVAR" - -#: mixer_strip.cc:96 mixer_strip.cc:441 mixer_strip.cc:1064 +#: mixer_strip.cc:96 mixer_strip.cc:822 msgid "Comments" msgstr "" -#: mixer_strip.cc:120 mixer_strip.cc:752 -msgid "INPUT" -msgstr "ENTRADA" +#: mixer_strip.cc:119 +#, fuzzy +msgid "Input" +msgstr "Entradas" -#: mixer_strip.cc:125 mixer_strip.cc:773 -msgid "OUTPUT" -msgstr "SAÃDA" +#: mixer_strip.cc:136 mixer_strip.cc:1223 +#, fuzzy +msgid "input" +msgstr "%1 entrada" -#: mixer_strip.cc:140 -msgid "Pan automation mode" -msgstr "modo automático de pan" +#: mixer_strip.cc:144 mixer_strip.cc:1231 +#, fuzzy +msgid "post" +msgstr "porta" -#: mixer_strip.cc:141 -msgid "Gain automation mode" -msgstr "modo automático de ganho" - -#: mixer_strip.cc:143 -msgid "Pan automation type" -msgstr "Tipo do pan automático" - -#: mixer_strip.cc:144 -msgid "Gain automation type" -msgstr "Tipo do ganho automático" - -#: mixer_strip.cc:183 mixer_strip.cc:195 mixer_strip.cc:913 -msgid "trim" -msgstr "cortar" - -#. XXX it might different in different languages -#: mixer_strip.cc:184 mixer_strip.cc:196 mixer_strip.cc:917 -msgid "abs" +#. TRANSLATORS: this string should be longest of the strings +#. used to describe meter points. In english, its "input". +#. +#: mixer_strip.cc:152 +msgid "tupni" msgstr "" -#: mixer_strip.cc:203 -msgid "gain automation mode" -msgstr "modo automático de ganho" - -#: mixer_strip.cc:204 -msgid "pan automation mode" -msgstr "modo automático de pan" - -#: mixer_strip.cc:205 -msgid "gain automation state" -msgstr "estado do ganho automático" - -#: mixer_strip.cc:206 -msgid "pan automation state" -msgstr "estado do pan automático" - -#: mixer_strip.cc:223 -msgid "varispeed" +#: mixer_strip.cc:207 +#, fuzzy +msgid "Varispeed" msgstr "velocidade variável" -#: mixer_strip.cc:245 mixer_strip.cc:1078 +#: mixer_strip.cc:233 mixer_strip.cc:836 msgid "Click to Add/Edit Comments" msgstr "" -#: mixer_strip.cc:393 +#: mixer_strip.cc:374 msgid "unknown strip width \"%1\" in XML GUI information" msgstr "" -#: mixer_strip.cc:443 mixer_strip.cc:1062 -msgid "*Comments*" +#: mixer_strip.cc:417 +#, fuzzy +msgid "record" +msgstr "Gravar" + +#: mixer_strip.cc:418 region_editor.cc:47 +msgid "mute" +msgstr "mudo" + +#: mixer_strip.cc:419 +msgid "solo" +msgstr "solo" + +#: mixer_strip.cc:422 +msgid "comments" msgstr "" -#: mixer_strip.cc:457 -msgid "REC" -msgstr "GRAV" +#: mixer_strip.cc:424 +msgid "*comments*" +msgstr "" -#: mixer_strip.cc:462 mixer_strip.cc:1072 +#: mixer_strip.cc:438 +#, fuzzy +msgid "Rec" +msgstr "Rescanear" + +#: mixer_strip.cc:439 +msgid "M" +msgstr "" + +#: mixer_strip.cc:440 +msgid "S" +msgstr "" + +#: mixer_strip.cc:443 mixer_strip.cc:830 #, fuzzy msgid "Cmt" msgstr "cortar" -#: mixer_strip.cc:464 mixer_strip.cc:1070 +#: mixer_strip.cc:445 mixer_strip.cc:828 msgid "*Cmt*" msgstr "" -#: mixer_strip.cc:503 mixer_strip.cc:562 redirect_box.cc:1004 +#: mixer_strip.cc:483 mixer_strip.cc:549 redirect_box.cc:1006 msgid "Not connected to JACK - no I/O changes are possible" msgstr "" -#: mixer_strip.cc:569 +#: mixer_strip.cc:560 msgid "Track" msgstr "Trilha" -#: mixer_strip.cc:593 mixer_strip.cc:609 +#: mixer_strip.cc:588 mixer_strip.cc:604 msgid "could not register new ports required for that connection" msgstr "não foi posível registrar portas novas solicitadas por este conneção" -#: mixer_strip.cc:755 -msgid "IN" +#: mixer_strip.cc:747 +#, fuzzy +msgid " Input" +msgstr "# Entradas" + +#: mixer_strip.cc:750 +#, fuzzy +msgid "I" msgstr "ENTRADA" -#: mixer_strip.cc:776 -msgid "OUT" -msgstr "SAÃDA" - -#: mixer_strip.cc:884 -msgid "aplay" +#: mixer_strip.cc:820 +msgid "*Comments*" msgstr "" -#: mixer_strip.cc:890 -msgid "awrite" -msgstr "" - -#: mixer_strip.cc:1095 +#: mixer_strip.cc:859 #, fuzzy msgid ": comment editor" msgstr "não foi possível iniciar o editor" -#: mixer_strip.cc:1157 mixer_strip.cc:1178 -msgid "no group" -msgstr "sem grupo" +#: mixer_strip.cc:953 +msgid "Grp" +msgstr "" -#: mixer_strip.cc:1181 +#: mixer_strip.cc:956 msgid "~G" msgstr "" -#: mixer_strip.cc:1229 +#: mixer_strip.cc:1004 #, fuzzy msgid "Invert Polarity" msgstr "polaridade" -#: mixer_ui.cc:84 +#: mixer_ui.cc:85 msgid "Strips" msgstr "Painéis" -#: mixer_ui.cc:108 -msgid "groupname" -msgstr "" +#: mixer_ui.cc:110 +#, fuzzy +msgid "Group" +msgstr "Grupos de Mixer" -#: mixer_ui.cc:109 region_editor.cc:48 region_editor.cc:191 -#: region_editor.cc:225 -msgid "active" -msgstr "ativo" - -#: mixer_ui.cc:110 region_editor.cc:49 -msgid "visible" -msgstr "visível" - -#: mixer_ui.cc:207 mixer_ui.cc:366 +#: mixer_ui.cc:211 mixer_ui.cc:370 msgid "ardour: mixer" msgstr "" -#: mixer_ui.cc:208 +#: mixer_ui.cc:212 msgid "ardour_mixer" msgstr "ardour_mixer" -#: mixer_ui.cc:342 +#: mixer_ui.cc:346 msgid "ardour: mixer: " msgstr "" -#: mixer_ui.cc:569 +#: mixer_ui.cc:573 msgid "signal" msgstr "sinal" -#: mixer_ui.cc:719 +#: mixer_ui.cc:723 msgid "track display list item for renamed strip not found!" msgstr "não foi encontrada qualquer trilha para o painel de mixer" -#: option_editor.cc:75 +#: new_session_dialog.cc:39 +#, fuzzy +msgid "New Session Name :" +msgstr "Nome da sessão:" + +#: new_session_dialog.cc:41 +msgid "Create Session Directory In :" +msgstr "" + +#: new_session_dialog.cc:43 +#, fuzzy +msgid "Use Session Template :" +msgstr "usar esquema existente" + +#: new_session_dialog.cc:45 +#, fuzzy +msgid "Channel Count" +msgstr "Cancelar importação" + +#: new_session_dialog.cc:46 +#, fuzzy +msgid "Create Monitor Bus" +msgstr "Controle de Saídas" + +#: new_session_dialog.cc:53 +#, fuzzy +msgid "Create Master Bus" +msgstr "usar saída master" + +#: new_session_dialog.cc:55 +#, fuzzy +msgid "Automatically Connect Inputs" +msgstr "conectar automaticamente entradas das trilhas com as portas físicas" + +#: new_session_dialog.cc:56 new_session_dialog.cc:67 +#, fuzzy +msgid "Port Limit" +msgstr "Esqueça isto" + +#: new_session_dialog.cc:64 +#, fuzzy +msgid "Track/Bus Inputs" +msgstr "Inspetador de Trilhas/Barramentos" + +#: new_session_dialog.cc:66 +#, fuzzy +msgid "Automatically Connect Outputs" +msgstr "conectar manualmente saídas das trilhas" + +#: new_session_dialog.cc:75 +msgid "Connect to Master Bus" +msgstr "" + +#: new_session_dialog.cc:76 +msgid "Connect to Physical Outputs" +msgstr "" + +#: new_session_dialog.cc:80 +#, fuzzy +msgid "Track/Bus Outputs" +msgstr "Saídas" + +#: new_session_dialog.cc:83 +#, fuzzy +msgid "Advanced Options" +msgstr "Preferências" + +# +#: new_session_dialog.cc:91 +#, fuzzy +msgid "Open Recent Session" +msgstr "abrir sessão" + +# +#: new_session_dialog.cc:127 +#, fuzzy +msgid "Open Session File :" +msgstr "abrir sessão" + +#: new_session_dialog.cc:274 +#, fuzzy +msgid "New Session" +msgstr "Sessão" + +# +#: new_session_dialog.cc:276 +#, fuzzy +msgid "Open Session" +msgstr "abrir sessão" + +#: new_session_dialog.cc:281 +#, fuzzy +msgid "ardour: session control" +msgstr "ardour: salvar sessão?" + +#: new_session_dialog.cc:310 +#, fuzzy +msgid "select template" +msgstr "-esquema/template" + +#: new_session_dialog.cc:316 +#, fuzzy +msgid "select session file" +msgstr "Loop região selecionada" + +#: new_session_dialog.cc:325 +#, fuzzy +msgid "select directory" +msgstr "Loop região selecionada" + +#: option_editor.cc:76 #, fuzzy msgid "SMPTE offset is negative" msgstr "Compensar SMPTE" -#: option_editor.cc:101 +#: option_editor.cc:102 msgid "ardour: options editor" msgstr "ardour: preferências" -#: option_editor.cc:102 +#: option_editor.cc:103 msgid "ardour_option_editor" msgstr "" -#: option_editor.cc:126 +#: option_editor.cc:127 msgid "Paths/Files" msgstr "Diretórios/Arquivos" -#: option_editor.cc:127 +#: option_editor.cc:128 msgid "Kbd/Mouse" msgstr "Teclado/Mouse" -#: option_editor.cc:130 +#: option_editor.cc:131 msgid "Layers & Fades" msgstr "" -#: option_editor.cc:134 +#: option_editor.cc:135 msgid "MIDI" msgstr "MIDI" -#: option_editor.cc:176 +#: option_editor.cc:177 msgid "24 FPS" msgstr "" -#: option_editor.cc:178 +#: option_editor.cc:179 msgid "25 FPS" msgstr "" -#: option_editor.cc:180 +#: option_editor.cc:181 msgid "30 FPS" msgstr "" -#: option_editor.cc:186 +#: option_editor.cc:187 msgid "30 FPS drop" msgstr "" -#: option_editor.cc:243 +#: option_editor.cc:244 msgid "session RAID path" msgstr "diretório para sessão RAID" -#: option_editor.cc:248 +#: option_editor.cc:249 #, fuzzy msgid "Soundfile Search Paths" msgstr "Biblioteca de Ãudio" -#: option_editor.cc:253 +#: option_editor.cc:254 #, fuzzy msgid "Paths" msgstr "Diretórios/Arquivos" -#: option_editor.cc:267 option_editor.cc:273 option_editor.cc:724 -#: option_editor.cc:751 +#: option_editor.cc:268 option_editor.cc:274 option_editor.cc:723 +#: option_editor.cc:750 msgid "internal" msgstr "interno" -#: option_editor.cc:286 +#: option_editor.cc:287 msgid "Short crossfade length (msecs)" msgstr "" -#: option_editor.cc:298 +#: option_editor.cc:299 msgid "Destructive crossfade length (msecs)" msgstr "" -#: option_editor.cc:366 +#: option_editor.cc:367 msgid "SMPTE Frames/second" msgstr "SMPTE Frames/segundo" -#: option_editor.cc:367 +#: option_editor.cc:368 msgid "SMPTE Offset" msgstr "Compensar SMPTE" -#: option_editor.cc:461 option_editor.cc:468 option_editor.cc:471 -#: option_editor.cc:617 +#: option_editor.cc:462 option_editor.cc:469 option_editor.cc:472 +#: option_editor.cc:618 #, fuzzy msgid "online" msgstr "linear" @@ -5293,12 +5292,12 @@ msgstr "linear" #. remember, we have to handle the i18n case where the relative #. lengths of the strings in language N is different than in english. #. -#: option_editor.cc:468 option_editor.cc:469 option_editor.cc:614 +#: option_editor.cc:469 option_editor.cc:470 option_editor.cc:615 #, fuzzy msgid "offline" msgstr "linear" -#: option_editor.cc:669 +#: option_editor.cc:670 msgid "Choose Click" msgstr "" @@ -5307,15 +5306,15 @@ msgstr "" msgid "Choose Click Emphasis" msgstr "Usar com metrônomo acentuado" -#: option_editor.cc:804 +#: option_editor.cc:803 msgid "Click audio file" msgstr "Metrônomo no arquivo de áudio" -#: option_editor.cc:810 +#: option_editor.cc:809 msgid "Click emphasis audiofile" msgstr "Metrônomo acentuado no arquivo de áudio" -#: option_editor.cc:847 +#: option_editor.cc:846 msgid "" "The auditioner is a dedicated mixer strip used\n" "for listening to specific regions outside the context\n" @@ -5327,35 +5326,35 @@ msgstr "" "da mistura geral. Pode ser interconectado tal como\n" "qualquer outro painel de mistura." -#: option_editor.cc:920 +#: option_editor.cc:919 msgid "Edit using" msgstr "Editar com" -#: option_editor.cc:927 option_editor.cc:954 +#: option_editor.cc:926 option_editor.cc:953 msgid "+ button" msgstr "+ button" -#: option_editor.cc:947 +#: option_editor.cc:946 msgid "Delete using" msgstr "Apagar com" -#: option_editor.cc:974 +#: option_editor.cc:973 msgid "Ignore snap using" msgstr "Ignorar ajuste com" -#: opts.cc:47 +#: opts.cc:46 msgid "Usage: " msgstr "Usual: " -#: opts.cc:48 +#: opts.cc:47 msgid " -v, --version Show version information\n" msgstr " -v, --version Mostra informação sobre a versão\n" -#: opts.cc:49 +#: opts.cc:48 msgid " -h, --help Print this message\n" msgstr " -h, --help Mostra esta mensagem\n" -#: opts.cc:50 +#: opts.cc:49 msgid "" " -b, --bindings Print all possible keyboard binding " "names\n" @@ -5363,12 +5362,12 @@ msgstr "" " -b, --bindings Mostra todos os atalhos de teclado " "possíveis nomes\n" -#: opts.cc:51 +#: opts.cc:50 #, fuzzy msgid " -n, --show-splash Show splash screen\n" msgstr " -n, --no-splash Não mostra imagem de abertura\n" -#: opts.cc:52 +#: opts.cc:51 #, fuzzy msgid "" " -c, --name name Use a specific jack client name, default " @@ -5377,149 +5376,162 @@ msgstr "" " -c, --jack-client-name nome Use o cliente jack especificado por nome. " "O padrão é o ardour\n" -#: opts.cc:53 +#: opts.cc:52 #, fuzzy msgid "" " -N, --new session-name Create a new session from the command " "line\n" msgstr " [session-name] Nome da sessão para carregar\n" -#: opts.cc:54 +#: opts.cc:53 msgid "" " -o, --use-hw-optimizations Try to use h/w specific optimizations\n" msgstr "" -#: opts.cc:56 +#: opts.cc:55 #, fuzzy msgid " -V, --novst Do not use VST support\n" msgstr " -n, --no-splash Não mostra imagem de abertura\n" -#: opts.cc:58 +#: opts.cc:57 msgid " [session-name] Name of session to load\n" msgstr " [session-name] Nome da sessão para carregar\n" -#: opts.cc:59 +#: opts.cc:58 msgid " -C, --curvetest filename Curve algorithm debugger\n" msgstr "" -#: opts.cc:60 +#: opts.cc:59 #, fuzzy msgid " -g, --gtktheme Allow GTK to load a theme\n" msgstr " -h, --help Mostra esta mensagem\n" -#: pan_automation_time_axis.cc:59 +#: pan_automation_time_axis.cc:60 msgid "You can't graphically edit panning of more than stream" msgstr "" -#: pan_automation_time_axis.cc:79 +#: pan_automation_time_axis.cc:80 #, fuzzy msgid "add pan automation event" msgstr "adicionar evento de automação para " -#: panner2d.cc:588 panner_ui.cc:393 plugin_ui.cc:833 +#: panner2d.cc:589 panner_ui.cc:435 plugin_ui.cc:834 msgid "Bypass" msgstr "Ignorar" -#: panner_ui.cc:57 panner_ui.cc:187 +#: panner_ui.cc:58 panner_ui.cc:225 #, fuzzy msgid "link" msgstr "entrada" +#: panner_ui.cc:69 +msgid "Pan automation mode" +msgstr "modo automático de pan" + #: panner_ui.cc:70 +msgid "Pan automation type" +msgstr "Tipo do pan automático" + +#: panner_ui.cc:81 msgid "panning link control" msgstr "" -#: panner_ui.cc:72 +#: panner_ui.cc:83 msgid "panning link direction" msgstr "" -#: panner_ui.cc:197 +#: panner_ui.cc:235 msgid "L" msgstr "" -#: panner_ui.cc:296 +#: panner_ui.cc:335 +#, c-format +msgid "panner for channel %lu" +msgstr "" + +#: panner_ui.cc:337 #, c-format msgid "panner for channel %u" msgstr "" -#: panner_ui.cc:403 +#: panner_ui.cc:445 msgid "Reset all" msgstr "reiniciar todos" -#: playlist_selector.cc:51 +#: playlist_selector.cc:52 #, fuzzy msgid "ardour: playlists" msgstr "ardour: plugins" -#: playlist_selector.cc:58 +#: playlist_selector.cc:59 msgid "Playlists grouped by track" msgstr "" -#: playlist_selector.cc:97 +#: playlist_selector.cc:98 #, fuzzy msgid "ardour: playlist for " msgstr "ardour: plugins" -#: playlist_selector.cc:113 +#: playlist_selector.cc:114 msgid "Other tracks" msgstr "Outras trilhas" # msgstr "Ocultar esta trilha" -#: playlist_selector.cc:129 +#: playlist_selector.cc:130 msgid "unassigned" msgstr "" -#: plugin_selector.cc:42 +#: plugin_selector.cc:43 msgid "ardour: plugins" msgstr "ardour: plugins" -#: plugin_selector.cc:55 +#: plugin_selector.cc:56 #, fuzzy msgid "Available LADSPA Plugins" msgstr "LADSPA plugins disponíveis" -#: plugin_selector.cc:56 +#: plugin_selector.cc:57 msgid "Type" msgstr "Tipo" -#: plugin_selector.cc:57 plugin_selector.cc:80 +#: plugin_selector.cc:58 plugin_selector.cc:81 msgid "# Inputs" msgstr "# Entradas" -#: plugin_selector.cc:58 plugin_selector.cc:81 +#: plugin_selector.cc:59 plugin_selector.cc:82 msgid "# Outputs" msgstr "# Saídas" -#: plugin_selector.cc:67 +#: plugin_selector.cc:68 msgid "Plugins to be Connected to Insert" msgstr "" -#: plugin_selector.cc:79 +#: plugin_selector.cc:80 #, fuzzy msgid "Available plugins" msgstr "VST plugins disponíveis" -#: plugin_selector.cc:97 +#: plugin_selector.cc:98 msgid "Add a plugin to the effect list" msgstr "Adicionar plugin na lista de efeitos" -#: plugin_selector.cc:99 +#: plugin_selector.cc:102 msgid "Remove a plugin from the effect list" msgstr "Remover plugin da lista de efeitos" -#: plugin_selector.cc:101 +#: plugin_selector.cc:104 msgid "Update available plugins" msgstr "Atualizar plugins disponíveis" -#: plugin_selector.cc:123 +#: plugin_selector.cc:126 msgid "LADSPA" msgstr "" -#: plugin_selector.cc:126 +#: plugin_selector.cc:129 msgid "VST" msgstr "" -#: plugin_ui.cc:83 +#: plugin_ui.cc:84 msgid "" "unknown type of editor-supplying plugin (note: no VST support in this " "version of ardour)" @@ -5527,52 +5539,53 @@ msgstr "" "tipo desconhecido do plugin fornecido para o editor (nota: sem suporte VST " "nesta versão do ardour)" -#: plugin_ui.cc:138 +#: plugin_ui.cc:139 msgid "Presets" msgstr "" -#: plugin_ui.cc:229 +#: plugin_ui.cc:230 #, fuzzy msgid "Controls" msgstr "Controle de Saídas" -#: plugin_ui.cc:266 +#: plugin_ui.cc:267 msgid "Plugin Editor: could not build control element for port %1" msgstr "" "Plugin Editor: não foi possível construir elemento de controle para a porta %" "1" -#: plugin_ui.cc:357 -msgid "automation control" +#: plugin_ui.cc:358 +#, fuzzy +msgid "Automation control" msgstr "controle de automação" -#: plugin_ui.cc:853 +#: plugin_ui.cc:854 msgid "Plugin preset %1 not found" msgstr "Pré-seleção do plugin %1 não encontrada" -#: plugin_ui.cc:863 +#: plugin_ui.cc:864 #, fuzzy msgid "Name of New Preset:" msgstr "Nome para a nova conexão:" -#: redirect_automation_line.cc:53 +#: redirect_automation_line.cc:54 msgid "redirect automation created for non-plugin" msgstr "redirecionamento automático criado para um não-efeito/não-plugin" -#: redirect_automation_time_axis.cc:93 +#: redirect_automation_time_axis.cc:94 msgid "add automation event to " msgstr "adicionar evento de automação para " -#: redirect_box.cc:222 +#: redirect_box.cc:223 msgid "New send" msgstr "" -#: redirect_box.cc:223 +#: redirect_box.cc:224 #, fuzzy msgid "Show send controls" msgstr "Velocidade do controle" -#: redirect_box.cc:377 +#: redirect_box.cc:383 msgid "" "You attempted to add a plugin (%1).\n" "The plugin has %2 inputs\n" @@ -5583,7 +5596,7 @@ msgid "" "part of the signal." msgstr "" -#: redirect_box.cc:389 +#: redirect_box.cc:395 msgid "" "You attempted to add a plugin (%1).\n" "The plugin has %2 inputs\n" @@ -5595,7 +5608,7 @@ msgid "" "support this type of configuration." msgstr "" -#: redirect_box.cc:402 +#: redirect_box.cc:408 msgid "" "You attempted to add a plugin (%1).\n" "\n" @@ -5608,34 +5621,34 @@ msgid "" "Ardour does not understand what to do in such situations.\n" msgstr "" -#: redirect_box.cc:493 +#: redirect_box.cc:495 msgid "Pre-fader inserts, sends & plugins:" msgstr "" -#: redirect_box.cc:496 +#: redirect_box.cc:498 msgid "Post-fader inserts, sends & plugins:" msgstr "" -#: redirect_box.cc:642 +#: redirect_box.cc:644 msgid "" "You cannot reorder this set of redirects\n" "in that way because the inputs and\n" "outputs do not work correctly." msgstr "" -#: redirect_box.cc:747 +#: redirect_box.cc:749 #, fuzzy msgid "rename redirect" msgstr "ardour: renomear região" -#: redirect_box.cc:824 redirect_box.cc:872 +#: redirect_box.cc:826 redirect_box.cc:874 msgid "" "Copying the set of redirects on the clipboard failed,\n" "probably because the I/O configuration of the plugins\n" "could not match the configuration of this track." msgstr "" -#: redirect_box.cc:894 +#: redirect_box.cc:896 #, fuzzy msgid "" "Do you really want to remove all redirects from this track?\n" @@ -5644,7 +5657,7 @@ msgstr "" "Tem certeza de que deseja remover a trilha \"%1\" ?\n" "(não será possível voltar)" -#: redirect_box.cc:897 +#: redirect_box.cc:899 #, fuzzy msgid "" "Do you really want to remove all redirects from this bus?\n" @@ -5653,248 +5666,260 @@ msgstr "" "Tem certeza de que deseja remover a trilha \"%1\" ?\n" "(não será possível voltar)" -#: redirect_box.cc:902 +#: redirect_box.cc:904 #, fuzzy msgid "Yes, remove them all" msgstr "Sim, remova isto." -#: redirect_box.cc:938 +#: redirect_box.cc:940 #, fuzzy msgid "ardour: %1" msgstr "ardour: relógio" -#: redirect_box.cc:980 +#: redirect_box.cc:982 #, fuzzy msgid "ardour: %1: %2 (by %3)" msgstr "ardour: região" #. new stuff -#: redirect_box.cc:1052 +#: redirect_box.cc:1054 msgid "New Plugin ..." msgstr "" -#: redirect_box.cc:1053 +#: redirect_box.cc:1055 #, fuzzy msgid "New Insert" msgstr "nova entrada" -#: redirect_box.cc:1054 +#: redirect_box.cc:1056 msgid "New Send ..." msgstr "" -#: redirect_box.cc:1066 +#: redirect_box.cc:1068 #, fuzzy msgid "Deselect All" msgstr "Selecionar Tudo" -#: redirect_box.cc:1073 +#: redirect_box.cc:1075 #, fuzzy msgid "Activate all" msgstr "Ativar" -#: redirect_box.cc:1074 +#: redirect_box.cc:1076 #, fuzzy msgid "Deactivate all" msgstr "Desativar" -#: region_editor.cc:44 +#: region_editor.cc:45 msgid "NAME:" msgstr "NOME:" -#: region_editor.cc:45 +#: region_editor.cc:46 msgid "lock" msgstr "bloquear" -#: region_editor.cc:47 +#: region_editor.cc:48 msgid "opaque" msgstr "opaco" -#: region_editor.cc:52 +#: region_editor.cc:49 region_editor.cc:192 region_editor.cc:226 +msgid "active" +msgstr "ativo" + +#: region_editor.cc:50 +msgid "visible" +msgstr "visível" + +#: region_editor.cc:53 msgid "Layer" msgstr "Camada" -#: region_editor.cc:60 +#: region_editor.cc:54 +msgid "play" +msgstr "reproduzir" + +#: region_editor.cc:61 msgid "ENVELOPE" msgstr "ENVELOPE" -#: region_editor.cc:106 +#: region_editor.cc:107 msgid "mute this region" msgstr "mutar esta região" -#: region_editor.cc:107 +#: region_editor.cc:108 msgid "regions underneath this one cannot be heard" msgstr "regiões abaixo desta não são ouvidas" -#: region_editor.cc:108 +#: region_editor.cc:109 msgid "prevent any changes to this region" msgstr "bloquear qualquer ateração nesta região" -#: region_editor.cc:109 +#: region_editor.cc:110 msgid "use the gain envelope during playback" msgstr "usar envelope de ganho durante a reprodução" -#: region_editor.cc:110 +#: region_editor.cc:111 msgid "show the gain envelope" msgstr "mostrar envelope de ganho" -#: region_editor.cc:111 +#: region_editor.cc:112 msgid "use fade in curve during playback" msgstr "usar curva de fade-in durante reprodução" -#: region_editor.cc:112 +#: region_editor.cc:113 msgid "use fade out curve during playback" msgstr "usar curva de fade-out durante reprodução" -#: region_editor.cc:113 +#: region_editor.cc:114 msgid "audition this region" msgstr "ouvir esta região" -#: region_editor.cc:146 +#: region_editor.cc:147 msgid "START:" msgstr "INICIO" -#: region_editor.cc:148 +#: region_editor.cc:149 msgid "END:" msgstr "FINAL:" -#: region_editor.cc:150 +#: region_editor.cc:151 msgid "LENGTH:" msgstr "TAMANHO:" -#: region_editor.cc:190 +#: region_editor.cc:191 msgid "FADE IN" msgstr "FADE IN" -#: region_editor.cc:192 region_editor.cc:226 +#: region_editor.cc:193 region_editor.cc:227 msgid "msecs" msgstr "milisecs." -#: region_editor.cc:224 +#: region_editor.cc:225 msgid "FADE OUT" msgstr "FADE OUT" -#: region_editor.cc:264 +#: region_editor.cc:265 msgid "ardour: region " msgstr "ardour: região" -#: region_editor.cc:401 +#: region_editor.cc:402 msgid "fade in edit" msgstr "fade in na edição" -#: region_editor.cc:413 +#: region_editor.cc:414 msgid "fade out edit" msgstr "fade out na edição" -#: regionview.cc:1140 +#: regionview.cc:1146 #, fuzzy msgid "add gain control point" msgstr "Remover ponto de controlo" -#: route_params_ui.cc:88 +#: route_params_ui.cc:89 msgid "Tracks/Buses" msgstr "Trilhas/Barramentos" -#: route_params_ui.cc:108 +#: route_params_ui.cc:109 #, fuzzy msgid "Pre-fader Redirects" msgstr "Pré Redirecionamentos" -#: route_params_ui.cc:109 +#: route_params_ui.cc:110 #, fuzzy msgid "Post-fader Redirects" msgstr "Pós Redirecionamentos" -#: route_params_ui.cc:141 +#: route_params_ui.cc:144 #, fuzzy msgid "ardour: track/bus inspector" msgstr "ardour: adicionar trilhas/barramento" -#: route_params_ui.cc:142 +#: route_params_ui.cc:145 msgid "ardour_route_parameters" msgstr "ardour_route_parameters" -#: route_params_ui.cc:199 +#: route_params_ui.cc:202 msgid "route display list item for renamed route not found!" msgstr "não foi encontrada qualquer elemento para encaminhamento" -#: route_params_ui.cc:451 +#: route_params_ui.cc:453 msgid "NO TRACK" msgstr "NENHUMA TRILHA" -#: route_params_ui.cc:693 +#: route_params_ui.cc:695 #, fuzzy msgid "ardour: track/bus inspector: " msgstr "ardour: adicionar trilhas/barramento" -#: route_params_ui.cc:697 +#: route_params_ui.cc:699 msgid "No Route Selected" msgstr "Caminho não selecionado" -#: route_params_ui.cc:698 +#: route_params_ui.cc:700 #, fuzzy msgid "ardour: track/bus/inspector: no route selected" msgstr "ardour: parâmetros de encaminhamento: caminho não seleccionado" #. ctrl-shift-click applies change to all routes -#: route_ui.cc:133 +#: route_ui.cc:134 #, fuzzy msgid "mute change" msgstr "Fazer intervalo de inserção" #. ctrl-shift-click applies change to all routes #. ctrl-alt-click: exclusively solo this track, not a toggle */ -#: route_ui.cc:208 route_ui.cc:218 +#: route_ui.cc:209 route_ui.cc:219 #, fuzzy msgid "solo change" msgstr "Loop no intervalo" -#: route_ui.cc:281 +#: route_ui.cc:282 msgid "rec-enable change" msgstr "" -#: route_ui.cc:472 +#: route_ui.cc:479 #, fuzzy msgid "Solo-safe" msgstr "Solo" -#: route_ui.cc:480 route_ui.cc:523 +#: route_ui.cc:487 route_ui.cc:530 #, fuzzy msgid "MIDI Bind" msgstr "MIDI" -#: route_ui.cc:494 +#: route_ui.cc:501 msgid "Pre Fader" msgstr "Pré Fade" -#: route_ui.cc:501 +#: route_ui.cc:508 msgid "Post Fader" msgstr "Pós Fade" -#: route_ui.cc:508 +#: route_ui.cc:515 msgid "Control Outs" msgstr "Controle de Saídas" -#: route_ui.cc:515 +#: route_ui.cc:522 msgid "Main Outs" msgstr "Saídas Principais" -#: route_ui.cc:552 +#: route_ui.cc:559 msgid "mix group solo change" msgstr "" -#: route_ui.cc:586 +#: route_ui.cc:593 msgid "mix group mute change" msgstr "" -#: route_ui.cc:602 +#: route_ui.cc:609 msgid "mix group rec-enable change" msgstr "" -#: route_ui.cc:619 visual_time_axis.cc:236 +#: route_ui.cc:626 visual_time_axis.cc:237 msgid "ardour: color selection" msgstr "ardour: seleção de cor" -#: route_ui.cc:695 +#: route_ui.cc:702 #, fuzzy msgid "" "Do you really want to remove track \"%1\" ?\n" @@ -5905,7 +5930,7 @@ msgstr "" "Tem certeza de que deseja remover a trilha \"%1\" ?\n" "(não será possível voltar)" -#: route_ui.cc:697 +#: route_ui.cc:704 msgid "" "Do you really want to remove bus \"%1\" ?\n" "(cannot be undone)" @@ -5913,11 +5938,11 @@ msgstr "" "Deseja realmente remover o barramento \"%1\" ?\n" "(esta operação não poderá ser desfeita)" -#: route_ui.cc:701 visual_time_axis.cc:278 +#: route_ui.cc:708 visual_time_axis.cc:279 msgid "Yes, remove it." msgstr "Sim, remova isto." -#: route_ui.cc:730 +#: route_ui.cc:737 #, fuzzy msgid "New Name: " msgstr "novo nome: " @@ -5975,147 +6000,148 @@ msgstr "não foi possível acessar arquivo de áudio" msgid "Name for Field" msgstr "Nome para a região:" -#: sfdb_ui.cc:333 +#: sfdb_ui.cc:335 msgid "Split Channels" msgstr "Separar Canais" -#: sfdb_ui.cc:340 +#: sfdb_ui.cc:342 msgid "Create a region for each channel" msgstr "" -#: sfdb_ui.cc:342 +#: sfdb_ui.cc:344 msgid "Embed" msgstr "" -#: sfdb_ui.cc:344 +#: sfdb_ui.cc:346 #, fuzzy msgid "Link to an external file" msgstr "Inserir arquivo de áudio externo" -#: sfdb_ui.cc:346 +#: sfdb_ui.cc:348 msgid "Import" msgstr "Importar" -#: sfdb_ui.cc:348 +#: sfdb_ui.cc:350 msgid "Copy a file to the session folder" msgstr "" -#: sfdb_ui.cc:412 +#: sfdb_ui.cc:414 msgid "programming error: %1" msgstr "" -#: tempo_dialog.cc:17 tempo_dialog.cc:34 +#: tempo_dialog.cc:18 tempo_dialog.cc:35 msgid "Beats per minute" msgstr "Batimentos por minuto" -#: tempo_dialog.cc:20 tempo_dialog.cc:37 tempo_dialog.cc:153 -#: tempo_dialog.cc:171 +#: tempo_dialog.cc:21 tempo_dialog.cc:38 tempo_dialog.cc:203 +#: tempo_dialog.cc:221 msgid "Bar" msgstr "Compasso" -#: tempo_dialog.cc:21 tempo_dialog.cc:38 tempo_dialog.cc:154 -#: tempo_dialog.cc:172 +#: tempo_dialog.cc:22 tempo_dialog.cc:39 tempo_dialog.cc:204 +#: tempo_dialog.cc:222 msgid "Beat" msgstr "Batimentos" -#: tempo_dialog.cc:23 tempo_dialog.cc:40 tempo_dialog.cc:155 -#: tempo_dialog.cc:173 +#: tempo_dialog.cc:24 tempo_dialog.cc:41 tempo_dialog.cc:205 +#: tempo_dialog.cc:223 msgid "Location" msgstr "Localização" -#: tempo_dialog.cc:149 tempo_dialog.cc:167 +#: tempo_dialog.cc:199 tempo_dialog.cc:217 msgid "Meter denominator" msgstr "Denominador métrico" -#: tempo_dialog.cc:150 tempo_dialog.cc:168 +#: tempo_dialog.cc:200 tempo_dialog.cc:218 msgid "Beats per bar" msgstr "Batimentos por compasso" -#: tempo_dialog.cc:186 tempo_dialog.cc:197 +#: tempo_dialog.cc:236 tempo_dialog.cc:247 msgid "whole (1)" msgstr "toda (1)" -#: tempo_dialog.cc:187 tempo_dialog.cc:199 +#: tempo_dialog.cc:237 tempo_dialog.cc:249 msgid "second (2)" msgstr "segunda (2)" -#: tempo_dialog.cc:188 tempo_dialog.cc:201 +#: tempo_dialog.cc:238 tempo_dialog.cc:251 msgid "third (3)" msgstr "terceira (3)" -#: tempo_dialog.cc:189 tempo_dialog.cc:203 tempo_dialog.cc:211 +#: tempo_dialog.cc:239 tempo_dialog.cc:253 tempo_dialog.cc:261 msgid "quarter (4)" msgstr "quarta (4)" -#: tempo_dialog.cc:190 tempo_dialog.cc:205 +#: tempo_dialog.cc:240 tempo_dialog.cc:255 msgid "eighth (8)" msgstr "oitava (8)" -#: tempo_dialog.cc:191 tempo_dialog.cc:207 +#: tempo_dialog.cc:241 tempo_dialog.cc:257 msgid "sixteenth (16)" msgstr "décima sexta (16)" -#: tempo_dialog.cc:192 tempo_dialog.cc:209 +#: tempo_dialog.cc:242 tempo_dialog.cc:259 msgid "thirty-second (32)" msgstr "trigésima segunda (32)" -#: tempo_dialog.cc:321 +#: tempo_dialog.cc:420 msgid "garbaged note type entry (%1)" msgstr "tipo de nota entrada descartada (%1)" -#: tempo_dialog.cc:331 +#: tempo_dialog.cc:430 msgid "incomprehensible note type entry (%1)" msgstr "tipo de nota entrada incompreensível (%1)" -#: time_axis_view.cc:111 +#: time_axis_view.cc:112 msgid "gTortnam" msgstr "gTortnam" -#: time_axis_view.cc:548 +#: time_axis_view.cc:549 msgid "Largest" msgstr "Enorme" -#: time_axis_view.cc:549 +#: time_axis_view.cc:550 msgid "Large" msgstr "Grande" -#: time_axis_view.cc:550 +#: time_axis_view.cc:551 msgid "Larger" msgstr "Maior" -#: time_axis_view.cc:552 +#: time_axis_view.cc:553 msgid "Smaller" msgstr "Menor" -#: time_axis_view.cc:553 +#: time_axis_view.cc:554 msgid "Small" msgstr "Pequeno" -#: time_axis_view.cc:869 +#: time_axis_view.cc:870 msgid "unknown track height name \"%1\" in XML GUI information" msgstr "" -#: time_axis_view_item.cc:71 +#. first constructed item sets up font info +#: time_axis_view_item.cc:79 msgid "TimeAxisViewItemName" msgstr "" -#: time_axis_view_item.cc:271 +#: time_axis_view_item.cc:298 msgid "new duration %1 frames is out of bounds for %2" msgstr "" -#: time_selection.cc:40 +#: time_selection.cc:41 msgid "programming error: request for non-existent audio range (%1)!" msgstr "" -#: utils.cc:106 utils.cc:149 +#: utils.cc:107 utils.cc:150 msgid "bad XPM header %1" msgstr "" -#: utils.cc:331 +#: utils.cc:332 msgid "missing RGBA style for \"%1\"" msgstr "" -#: visual_time_axis.cc:275 +#: visual_time_axis.cc:276 msgid "" "Do you really want to remove track \"%1\" ?\n" "(cannot be undone)" @@ -6123,14 +6149,91 @@ msgstr "" "Tem certeza de que deseja remover a trilha \"%1\" ?\n" "(não será possível voltar)" -#: visual_time_axis.cc:324 +#: visual_time_axis.cc:325 msgid "new name: " msgstr "novo nome: " -#: visual_time_axis.cc:335 +#: visual_time_axis.cc:336 msgid "A track already exists with that name" msgstr "já existe uma trilha com este nome" +#~ msgid "" +#~ "You cannot record-enable\n" +#~ "track %1\n" +#~ "because it has no input connections.\n" +#~ "You would be wasting space recording silence." +#~ msgstr "" +#~ "Vocãonão pode habilitar para gravaãoo\n" +#~ "a trilha %1\n" +#~ "porque ela não tem conexãos de entrada.\n" +#~ "Você estaria desperdiçando espaço gravando silêncio." + +#, fuzzy +#~ msgid "set selected trackview" +#~ msgstr "Inserir seleção" + +#, fuzzy +#~ msgid "set selected control point" +#~ msgstr "Remover ponto de controlo" + +#, fuzzy +#~ msgid "set selected regionview" +#~ msgstr "Loop região selecionada" + +#~ msgid "Start a new session\n" +#~ msgstr "Iniciar uma nova sessão\n" + +#~ msgid "via Session menu" +#~ msgstr "via menu de Sessão" + +#, fuzzy +#~ msgid "Advanced" +#~ msgstr "Avançado ..." + +#, fuzzy +#~ msgid "Select a File" +#~ msgstr "Selecionar Tudo" + +#, fuzzy +#~ msgid "Track/Bus connection options" +#~ msgstr "Inspetador de Trilhas/Barramentos" + +#~ msgid "RECORD" +#~ msgstr "GRAVAR" + +#~ msgid "INPUT" +#~ msgstr "ENTRADA" + +#~ msgid "OUTPUT" +#~ msgstr "SAÃDA" + +#~ msgid "Gain automation mode" +#~ msgstr "modo automático de ganho" + +#~ msgid "Gain automation type" +#~ msgstr "Tipo do ganho automático" + +#~ msgid "trim" +#~ msgstr "cortar" + +#~ msgid "gain automation mode" +#~ msgstr "modo automático de ganho" + +#~ msgid "gain automation state" +#~ msgstr "estado do ganho automático" + +#~ msgid "pan automation state" +#~ msgstr "estado do pan automático" + +#~ msgid "REC" +#~ msgstr "GRAV" + +#~ msgid "OUT" +#~ msgstr "SAÃDA" + +#~ msgid "no group" +#~ msgstr "sem grupo" + #, fuzzy #~ msgid "normal" #~ msgstr "Normal" @@ -6399,9 +6502,6 @@ msgstr "já existe uma trilha com este nome" #~ msgid "AND" #~ msgstr "E" -#~ msgid "OR" -#~ msgstr "OU" - #~ msgid "ardour: locate soundfiles" #~ msgstr "ardour: localizar arquivos de áudio" @@ -6414,9 +6514,6 @@ msgstr "já existe uma trilha com este nome" #~ msgid "Ardour: Search Results" #~ msgstr "Ardour: Resultado da Busca" -#~ msgid "Mix Groups" -#~ msgstr "Grupos de Mixer" - #~ msgid "Hide All AudioTrack MixerStrips" #~ msgstr "Ocultar os páineis de mixer de todas as trilhas de áudio " @@ -6429,9 +6526,6 @@ msgstr "já existe uma trilha com este nome" #~ msgid "Name for new mix group" #~ msgstr "Nome para o novo grupo de mixer" -#~ msgid "Session name:" -#~ msgstr "Nome da sessão:" - #~ msgid "Create" #~ msgstr "Criar" @@ -6464,17 +6558,9 @@ msgstr "já existe uma trilha com este nome" #~ "Se você quiser usar outra freqüência de áudio\n" #~ "por favor feche o programa e reinicie o JACK" -#, fuzzy -#~ msgid "Session template" -#~ msgstr "usar esquema existente" - #~ msgid "blank" #~ msgstr "vazio" -#, fuzzy -#~ msgid "No template" -#~ msgstr "-esquema/template" - #, fuzzy #~ msgid "Slave to MTC" #~ msgstr "Enviar MTC" @@ -6500,9 +6586,6 @@ msgstr "já existe uma trilha com este nome" #~ msgid "Native Format" #~ msgstr "Formato Nativo" -#~ msgid "Use as click" -#~ msgstr "Usar com metrônomo" - #~ msgid "--unknown--" #~ msgstr "--desconhecido--" diff --git a/gtk2_ardour/po/pt_PT.po b/gtk2_ardour/po/pt_PT.po index 1a8d47b36f..f07f025713 100644 --- a/gtk2_ardour/po/pt_PT.po +++ b/gtk2_ardour/po/pt_PT.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: 0.814.2\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-04-25 17:46-0400\n" +"POT-Creation-Date: 2006-06-21 18:09-0400\n" "PO-Revision-Date: 2004-12-07 13:00+0000\n" "Last-Translator: Rui Nuno Capela \n" "Language-Team: Portuguese\n" @@ -15,143 +15,143 @@ msgstr "" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" -#: about.cc:119 +#: about.cc:120 msgid "Paul Davis" msgstr "" -#: about.cc:120 +#: about.cc:121 #, fuzzy msgid "Jesse Chappell" msgstr "reiniciar" -#: about.cc:121 +#: about.cc:122 msgid "Taybin Rutkin" msgstr "" -#: about.cc:122 +#: about.cc:123 msgid "Marcus Andersson" msgstr "" -#: about.cc:123 +#: about.cc:124 msgid "Jeremy Hall" msgstr "" -#: about.cc:124 +#: about.cc:125 msgid "Steve Harris" msgstr "" -#: about.cc:125 +#: about.cc:126 msgid "Tim Mayberry" msgstr "" -#: about.cc:126 +#: about.cc:127 msgid "Mark Stewart" msgstr "" -#: about.cc:127 +#: about.cc:128 msgid "Sam Chessman" msgstr "" -#: about.cc:128 +#: about.cc:129 msgid "Jack O'Quin" msgstr "" -#: about.cc:129 +#: about.cc:130 msgid "Matt Krai" msgstr "" -#: about.cc:130 +#: about.cc:131 msgid "Ben Bell" msgstr "" -#: about.cc:131 +#: about.cc:132 msgid "Gerard van Dongen" msgstr "" -#: about.cc:132 +#: about.cc:133 msgid "Thomas Charbonnel" msgstr "" -#: about.cc:133 +#: about.cc:134 msgid "Nick Mainsbridge" msgstr "" -#: about.cc:134 +#: about.cc:135 msgid "Colin Law" msgstr "" -#: about.cc:135 +#: about.cc:136 msgid "Sampo Savolainen" msgstr "" -#: about.cc:136 +#: about.cc:137 msgid "Joshua Leach" msgstr "" -#: about.cc:137 +#: about.cc:138 msgid "Rob Holland" msgstr "" -#: about.cc:138 +#: about.cc:139 msgid "Per Sigmond" msgstr "" -#: about.cc:139 +#: about.cc:140 msgid "Doug Mclain" msgstr "" -#: about.cc:140 +#: about.cc:141 msgid "Petter Sundlöf" msgstr "" -#: about.cc:145 +#: about.cc:146 msgid "" "French:\n" "\tAlain Fréhel \n" msgstr "" -#: about.cc:146 +#: about.cc:147 msgid "" "German:\n" "\tKarsten Petersen \n" msgstr "" -#: about.cc:147 +#: about.cc:148 msgid "" "Italian:\n" "\tFilippo Pappalardo \n" msgstr "" -#: about.cc:148 +#: about.cc:149 msgid "" "Portuguese:\n" "\tRui Nuno Capela \n" msgstr "" -#: about.cc:149 +#: about.cc:150 msgid "" "Brazilian Portuguese:\n" "\tAlexander da Franca Fernandes \n" "\tChris Ross \n" msgstr "" -#: about.cc:151 +#: about.cc:152 msgid "" "Spanish:\n" "\t Alex Krohn \n" msgstr "" -#: about.cc:152 +#: about.cc:153 msgid "" "Russian:\n" "\t Igor Blinov \n" msgstr "" -#: about.cc:180 +#: about.cc:181 msgid "Copyright (C) 1999-2005 Paul Davis\n" msgstr "" -#: about.cc:181 +#: about.cc:182 #, fuzzy msgid "" "Ardour comes with ABSOLUTELY NO WARRANTY\n" @@ -164,7 +164,7 @@ msgstr "" "desde que sejam respeitadas algumas condições;\n" "para mais informações, leia por favor o ficheiro COPYING.\n" -#: about.cc:187 +#: about.cc:188 #, fuzzy msgid "" "%1\n" @@ -173,51 +173,51 @@ msgstr "" "Ardour: %1\n" "(compilado com ardour/gtk %2 libardour: %3.%4.%5)" -#: actions.cc:260 +#: actions.cc:261 msgid "programmer error: %1 %2" msgstr "" -#: add_route_dialog.cc:61 +#: add_route_dialog.cc:62 msgid "ardour: add track/bus" msgstr "ardour: acrescentar faixa/barramento" #. path = "1" -#: add_route_dialog.cc:62 editor_route_list.cc:72 +#: add_route_dialog.cc:63 editor_route_list.cc:73 msgid "Tracks" msgstr "Faixas" #. path = "0" -#: add_route_dialog.cc:63 editor_route_list.cc:69 +#: add_route_dialog.cc:64 editor_route_list.cc:70 msgid "Busses" msgstr "Barramentos" -#: add_route_dialog.cc:95 plugin_ui.cc:832 +#: add_route_dialog.cc:96 plugin_ui.cc:833 msgid "Add" msgstr "Acrescentar" -#: add_route_dialog.cc:113 +#: add_route_dialog.cc:114 msgid "Name (template)" msgstr "Nome (modelo)" -#: add_route_dialog.cc:119 +#: add_route_dialog.cc:120 #, fuzzy msgid "Channel Configuration" msgstr "Configuração" -#: add_route_dialog.cc:176 editor.cc:131 editor.cc:3660 time_axis_view.cc:551 +#: add_route_dialog.cc:177 editor.cc:134 editor.cc:3688 time_axis_view.cc:552 msgid "Normal" msgstr "Normal" -#: add_route_dialog.cc:178 +#: add_route_dialog.cc:179 #, fuzzy msgid "Tape" msgstr "Início" -#: add_route_dialog.cc:195 +#: add_route_dialog.cc:196 msgid "Mono" msgstr "" -#: add_route_dialog.cc:197 +#: add_route_dialog.cc:198 #, fuzzy msgid "Stereo" msgstr "Parar" @@ -303,27 +303,11 @@ msgstr "AUDIÇÃO" msgid "SOLO" msgstr "" -#: ardour_ui.cc:207 -msgid "" -"You cannot record-enable\n" -"track %1\n" -"because it has no input connections.\n" -"You would be wasting space recording silence." -msgstr "" - -#: ardour_ui.cc:236 -msgid "no vertical meter strip image found" -msgstr "" - -#: ardour_ui.cc:243 -msgid "no horizontal meter strip image found" -msgstr "" - -#: ardour_ui.cc:410 +#: ardour_ui.cc:375 msgid "quit" msgstr "sair" -#: ardour_ui.cc:419 +#: ardour_ui.cc:384 msgid "" "Ardour was unable to save your session.\n" "\n" @@ -332,33 +316,33 @@ msgid "" "\"Just quit\" option." msgstr "" -#: ardour_ui.cc:438 +#: ardour_ui.cc:403 msgid "ardour: save session?" msgstr "ardour: guardar sessão?" -#: ardour_ui.cc:445 +#: ardour_ui.cc:410 msgid "Don't %1" msgstr "Não %1" -#: ardour_ui.cc:447 +#: ardour_ui.cc:412 msgid "Just %1" msgstr "Apenas %1" -#: ardour_ui.cc:449 +#: ardour_ui.cc:414 msgid "Save and %1" msgstr "Guardar e %1" -#: ardour_ui.cc:461 +#: ardour_ui.cc:426 #, fuzzy msgid "session" msgstr "Sessão" -#: ardour_ui.cc:463 +#: ardour_ui.cc:428 #, fuzzy msgid "snapshot" msgstr "Capturar" -#: ardour_ui.cc:465 +#: ardour_ui.cc:430 #, fuzzy msgid "" "The %1\"%2\"\n" @@ -377,82 +361,82 @@ msgstr "" "\n" "O que pretende fazer?" -#: ardour_ui.cc:479 +#: ardour_ui.cc:444 msgid "Prompter" msgstr "Alerta" -#: ardour_ui.cc:538 +#: ardour_ui.cc:503 #, fuzzy, c-format msgid "disconnected" msgstr "Desligar" -#: ardour_ui.cc:545 +#: ardour_ui.cc:510 #, fuzzy, c-format msgid "SR: %.1f kHz / %4.1f msecs" msgstr "FA: %.1f kHz" -#: ardour_ui.cc:549 +#: ardour_ui.cc:514 #, c-format msgid "SR: %u kHz / %4.1f msecs" msgstr "" -#: ardour_ui.cc:562 +#: ardour_ui.cc:527 #, c-format msgid "DSP Load: %.1f%%" msgstr "Carga DSP: %.1f%%" -#: ardour_ui.cc:572 +#: ardour_ui.cc:537 #, c-format msgid "Buffers p:%%% c:%%%" msgstr "" -#: ardour_ui.cc:599 +#: ardour_ui.cc:564 msgid "space: 24hrs+" msgstr "espaço: 24hrs+" -#: ardour_ui.cc:629 +#: ardour_ui.cc:594 #, c-format msgid "space: %02dh:%02dm:%02ds" msgstr "espaço: %02dh:%02dm:%02ds" -#: ardour_ui.cc:668 +#: ardour_ui.cc:633 msgid "programming error: impossible control method" msgstr "" -#: ardour_ui.cc:776 new_session_dialog.cc:89 +#: ardour_ui.cc:741 new_session_dialog.cc:294 #, fuzzy msgid "Recent Sessions" msgstr "abrir sessão" #. ardour sessions are folders -#: ardour_ui.cc:867 +#: ardour_ui.cc:834 msgid "open session" msgstr "abrir sessão" -#: ardour_ui.cc:873 +#: ardour_ui.cc:840 #, fuzzy msgid "Ardour sessions" msgstr "ardour: guardar sessão?" -#: ardour_ui.cc:906 +#: ardour_ui.cc:873 msgid "Patience is a virtue.\n" msgstr "A paciência é uma virtude.\n" -#: ardour_ui.cc:915 +#: ardour_ui.cc:882 msgid "You cannot add a track without a session already loaded." msgstr "" "Não é possível acrescentar uma faixa sem que haja uma sessão esteja " "carregada." -#: ardour_ui.cc:922 +#: ardour_ui.cc:889 msgid "could not create new audio track" msgstr "não foi possível criar uma nova faixa audio" -#: ardour_ui.cc:926 +#: ardour_ui.cc:893 msgid "could not create new audio bus" msgstr "não foi possível criar um novo barramento audio" -#: ardour_ui.cc:945 +#: ardour_ui.cc:912 msgid "" "There are insufficient JACK ports available\n" "to create a new track or bus.\n" @@ -460,14 +444,14 @@ msgid "" "restart JACK with more ports." msgstr "" -#: ardour_ui.cc:1069 +#: ardour_ui.cc:1036 msgid "" "Please create 1 or more track\n" "before trying to record.\n" "Check the Session menu." msgstr "" -#: ardour_ui.cc:1298 +#: ardour_ui.cc:1265 #, fuzzy msgid "" "JACK has either been shutdown or it\n" @@ -481,57 +465,55 @@ msgstr "" "A sessão corrente deverá ser salvaguardada\n" "e o serviço JACK reiniciado, tal como o Ardour." -#: ardour_ui.cc:1315 +#: ardour_ui.cc:1282 msgid "Unable to create all required ports" msgstr "" -#: ardour_ui.cc:1323 +#: ardour_ui.cc:1290 #, fuzzy msgid "Unable to start the session running" msgstr "Ir para o início da sessão" -#: ardour_ui.cc:1459 +#: ardour_ui.cc:1426 msgid "No Stream" msgstr "Sem Fluxo" -#: ardour_ui.cc:1486 ardour_ui.cc:1505 +#: ardour_ui.cc:1453 ardour_ui.cc:1472 msgid "none" msgstr "nenhum" -#: ardour_ui.cc:1495 ardour_ui.cc:1514 automation_time_axis.cc:183 -#: automation_time_axis.cc:212 automation_time_axis.cc:459 mixer_strip.cc:174 -#: mixer_strip.cc:186 mixer_strip.cc:881 plugin_ui.cc:391 plugin_ui.cc:634 +#: ardour_ui.cc:1462 ardour_ui.cc:1481 msgid "off" msgstr "desligado" -#: ardour_ui.cc:1538 +#: ardour_ui.cc:1505 #, fuzzy msgid "Name of New Snapshot" msgstr "Nome para a imagem capturada" -#: ardour_ui.cc:1684 +#: ardour_ui.cc:1651 msgid "Name for mix template:" msgstr "Nome para o modelo de mistura" -#: ardour_ui.cc:1685 +#: ardour_ui.cc:1652 msgid "-template" msgstr "-modelo" -#: ardour_ui.cc:1836 +#: ardour_ui.cc:1809 msgid "" "You do not have write access to this session.\n" "This prevents the session from being loaded." msgstr "" -#: ardour_ui.cc:1849 ardour_ui.cc:1904 +#: ardour_ui.cc:1822 ardour_ui.cc:1877 msgid "Session \"%1 (snapshot %2)\" did not load successfully" msgstr "Não foi possível carregar a sessão \"%1 (captura %2)\" com sucesso" -#: ardour_ui.cc:1960 +#: ardour_ui.cc:1933 msgid "No audio files were ready for cleanup" msgstr "" -#: ardour_ui.cc:1964 +#: ardour_ui.cc:1937 msgid "" "If this seems suprising, \n" "check for any existing snapshots.\n" @@ -539,25 +521,25 @@ msgid "" "require some unused files to continue to exist." msgstr "" -#: ardour_ui.cc:1973 +#: ardour_ui.cc:1946 msgid "ardour: cleanup" msgstr "ardour: limpeza" -#: ardour_ui.cc:2009 ardour_ui.cc:2015 +#: ardour_ui.cc:1982 ardour_ui.cc:1988 #, fuzzy msgid "files were" msgstr "ficheiros" -#: ardour_ui.cc:2011 ardour_ui.cc:2017 +#: ardour_ui.cc:1984 ardour_ui.cc:1990 #, fuzzy msgid "file was" msgstr "ficheiros" -#: ardour_ui.cc:2058 +#: ardour_ui.cc:2031 msgid "Are you sure you want to cleanup?" msgstr "" -#: ardour_ui.cc:2063 +#: ardour_ui.cc:2036 msgid "" "Cleanup is a destructive operation.\n" "ALL undo/redo information will be lost if you cleanup.\n" @@ -565,26 +547,26 @@ msgid "" "location." msgstr "" -#: ardour_ui.cc:2069 +#: ardour_ui.cc:2042 #, fuzzy msgid "Clean Up" msgstr "Apagar" -#: ardour_ui.cc:2072 +#: ardour_ui.cc:2045 #, fuzzy msgid "CleanupDialog" msgstr "Apagar" -#: ardour_ui.cc:2073 +#: ardour_ui.cc:2046 #, fuzzy msgid "ardour_cleanup" msgstr "ardour: limpeza" -#: ardour_ui.cc:2092 +#: ardour_ui.cc:2065 msgid "cleaned files" msgstr "ficheiros limpos" -#: ardour_ui.cc:2093 +#: ardour_ui.cc:2066 #, fuzzy msgid "" "The following %1 %2 not in use and \n" @@ -599,11 +581,11 @@ msgstr "" "Da próxima vez que efectuar uma limpeza\n" "irão ser libertados %3 %4 de espaço em disco" -#: ardour_ui.cc:2118 +#: ardour_ui.cc:2091 msgid "deleted file" msgstr "ficheiro eliminado" -#: ardour_ui.cc:2119 +#: ardour_ui.cc:2092 #, fuzzy msgid "" "The following %1 %2 deleted from\n" @@ -613,13 +595,13 @@ msgstr "" "Os seguintes %1 ficheiro%2 foram eliminados, libertando %3 %4B de espaço em " "disco" -#: ardour_ui.cc:2242 +#: ardour_ui.cc:2215 msgid "Recording was stopped because your system could not keep up." msgstr "" "A gravação foi interrompida porque o seu sistema não foi capaz de a " "acompanhar." -#: ardour_ui.cc:2265 +#: ardour_ui.cc:2238 msgid "" "The disk system on your computer\n" "was not able to keep up with Ardour.\n" @@ -633,7 +615,7 @@ msgstr "" "Especificamente, a velocidade de escrita de dados em disco\n" "foi insuficiente para acompanhar o ritmo de gravação.\n" -#: ardour_ui.cc:2284 +#: ardour_ui.cc:2257 msgid "" "The disk system on your computer\n" "was not able to keep up with Ardour.\n" @@ -647,7 +629,7 @@ msgstr "" "Especificamente, a velocidade de leitura de dados em disco\n" "foi insuficiente para acompanhar o ritmo de reprodução.\n" -#: ardour_ui.cc:2310 +#: ardour_ui.cc:2283 msgid "" "This session appears to have been in\n" "middle of recording when ardour or\n" @@ -665,367 +647,367 @@ msgstr "" "capturado até então ou simplesmente ignorá-lo.\n" "Por favor decida o que pretende fazer.\n" -#: ardour_ui.cc:2320 +#: ardour_ui.cc:2293 msgid "Recover from crash" msgstr "Recuperação" -#: ardour_ui.cc:2321 +#: ardour_ui.cc:2294 msgid "Ignore crash data" msgstr "Ignorar informação de recuperação" -#: ardour_ui.cc:2339 +#: ardour_ui.cc:2312 #, fuzzy msgid "Could not disconnect from JACK" msgstr "Não foi possível conectar ao serviço JACK como \"%1\"" -#: ardour_ui.cc:2352 +#: ardour_ui.cc:2325 #, fuzzy msgid "Could not reconnect to JACK" msgstr "Não foi possível conectar ao serviço JACK como \"%1\"" -#: ardour_ui2.cc:59 +#: ardour_ui2.cc:60 msgid "UI: cannot setup editor" msgstr "Não foi possível iniciar o painel principal de edição (editor)" -#: ardour_ui2.cc:64 +#: ardour_ui2.cc:65 msgid "UI: cannot setup mixer" msgstr "Não foi posivel iniciar o painel de mistura" -#: ardour_ui2.cc:90 +#: ardour_ui2.cc:91 msgid "MMC + Local" msgstr "" -#: ardour_ui2.cc:91 +#: ardour_ui2.cc:92 msgid "MMC" msgstr "" -#: ardour_ui2.cc:92 +#: ardour_ui2.cc:93 msgid "Local" msgstr "" -#: ardour_ui2.cc:109 +#: ardour_ui2.cc:110 msgid "MMC ID" msgstr "" -#: ardour_ui2.cc:290 +#: ardour_ui2.cc:291 msgid "Play from playhead" msgstr "Reproduzir desde o cursor de reprodução" -#: ardour_ui2.cc:291 +#: ardour_ui2.cc:292 msgid "Stop playback" msgstr "Parar reprodução" -#: ardour_ui2.cc:292 +#: ardour_ui2.cc:293 msgid "Play range/selection" msgstr "Reproduzir selecção" -#: ardour_ui2.cc:293 +#: ardour_ui2.cc:294 msgid "Go to start of session" msgstr "Ir para o início da sessão" -#: ardour_ui2.cc:294 +#: ardour_ui2.cc:295 msgid "Go to end of session" msgstr "Ir para o final da sessão" -#: ardour_ui2.cc:295 +#: ardour_ui2.cc:296 msgid "Play loop range" msgstr "Reproduzir intervalo cíclico" -#: ardour_ui2.cc:296 +#: ardour_ui2.cc:297 msgid "Return to last playback start when stopped" msgstr "Ir para a última posição inicial do cursor de reprodução quando parar" -#: ardour_ui2.cc:297 +#: ardour_ui2.cc:298 msgid "Start playback after any locate" msgstr "Iniciar a reprodução após qualquer localização" -#: ardour_ui2.cc:298 +#: ardour_ui2.cc:299 msgid "Be sensible about input monitoring" msgstr "Seja sensível acerca de monitorização de entradas" -#: ardour_ui2.cc:299 +#: ardour_ui2.cc:300 msgid "Start recording at auto-punch start" msgstr "Iniciar gravação na posição inicial de inserção automática" -#: ardour_ui2.cc:300 +#: ardour_ui2.cc:301 msgid "Stop recording at auto-punch end" msgstr "Parar gravação na posição final de inserção automática" -#: ardour_ui2.cc:301 +#: ardour_ui2.cc:302 msgid "Enable/Disable audio click" msgstr "Ligar/Desligar o metrónomo" -#: ardour_ui2.cc:302 +#: ardour_ui2.cc:303 #, fuzzy msgid "Positional sync source" msgstr "Sicronia de Posição" -#: ardour_ui2.cc:303 +#: ardour_ui2.cc:304 msgid "Does Ardour control the time?" msgstr "" -#: ardour_ui2.cc:304 +#: ardour_ui2.cc:305 msgid "Shuttle speed control" msgstr "Controlo de velocidade" -#: ardour_ui2.cc:305 +#: ardour_ui2.cc:306 #, fuzzy, c-format msgid "Select semitones or %%-age for speed display" msgstr "Seleccionar semitons ou %-agem para visualização de velocidade" -#: ardour_ui2.cc:306 +#: ardour_ui2.cc:307 msgid "Current transport speed" msgstr "Velocidade de transporte actual" -#: ardour_ui2.cc:329 +#: ardour_ui2.cc:330 msgid "Primary clock" msgstr "Cronómetro principal" -#: ardour_ui2.cc:330 +#: ardour_ui2.cc:331 msgid "secondary clock" msgstr "Cronómetro secundário" #. XXX: this should really be saved in instant.xml or something similar and restored from there #. Combo's are stupid - they steal space from the entry for the button -#: ardour_ui2.cc:387 ardour_ui2.cc:823 ardour_ui2.cc:836 ardour_ui2.cc:899 -#: ardour_ui2.cc:901 +#: ardour_ui2.cc:388 ardour_ui2.cc:833 ardour_ui2.cc:846 ardour_ui2.cc:909 +#: ardour_ui2.cc:911 msgid "sprung" msgstr "mola" -#: ardour_ui2.cc:388 ardour_ui2.cc:825 ardour_ui2.cc:847 +#: ardour_ui2.cc:389 ardour_ui2.cc:835 ardour_ui2.cc:857 msgid "wheel" msgstr "roda" -#: ardour_ui2.cc:450 +#: ardour_ui2.cc:451 msgid "ardour: clock" msgstr "ardour: cronómetro" -#: ardour_ui2.cc:595 +#: ardour_ui2.cc:596 #, fuzzy msgid "Maximum speed" msgstr "velocidade variável" -#: ardour_ui2.cc:813 +#: ardour_ui2.cc:823 msgid "st" msgstr "" -#: ardour_ui2.cc:857 ardour_ui2.cc:880 ardour_ui2.cc:897 +#: ardour_ui2.cc:867 ardour_ui2.cc:890 ardour_ui2.cc:907 msgid "stopped" msgstr "parado" -#: ardour_ui_dialogs.cc:152 playlist_selector.cc:69 +#: ardour_ui_dialogs.cc:153 playlist_selector.cc:70 #, fuzzy msgid "close" msgstr "Fechar" -#: ardour_ui_dialogs.cc:359 ardour_ui_ed.cc:181 +#: ardour_ui_dialogs.cc:360 ardour_ui_ed.cc:184 #, fuzzy msgid "Sound File Browser" msgstr "Audioteca" #. menus + submenus that need action items -#: ardour_ui_ed.cc:69 +#: ardour_ui_ed.cc:72 msgid "Session" msgstr "Sessão" -#: ardour_ui_ed.cc:70 ardour_ui_ed.cc:127 editor.cc:1843 export_dialog.cc:350 +#: ardour_ui_ed.cc:73 ardour_ui_ed.cc:130 editor.cc:1836 export_dialog.cc:350 #: export_dialog.cc:1059 export_dialog.cc:1063 msgid "Export" msgstr "Exportar" -#: ardour_ui_ed.cc:71 +#: ardour_ui_ed.cc:74 msgid "Cleanup" msgstr "Apagar" -#: ardour_ui_ed.cc:72 option_editor.cc:125 +#: ardour_ui_ed.cc:75 option_editor.cc:126 msgid "Sync" msgstr "Sincronia" -#: ardour_ui_ed.cc:73 ardour_ui_ed.cc:74 +#: ardour_ui_ed.cc:76 ardour_ui_ed.cc:77 #, fuzzy msgid "Options" msgstr "Opções" -#: ardour_ui_ed.cc:75 +#: ardour_ui_ed.cc:78 msgid "Help" msgstr "" -#: ardour_ui_ed.cc:76 +#: ardour_ui_ed.cc:79 msgid "KeyMouse Actions" msgstr "" -#: ardour_ui_ed.cc:77 +#: ardour_ui_ed.cc:80 #, fuzzy msgid "Audio File Format" msgstr "Quadros Audio" -#: ardour_ui_ed.cc:78 +#: ardour_ui_ed.cc:81 #, fuzzy msgid "Header" msgstr "Pré-Atenuador" -#: ardour_ui_ed.cc:79 +#: ardour_ui_ed.cc:82 msgid "Data" msgstr "" -#: ardour_ui_ed.cc:80 +#: ardour_ui_ed.cc:83 #, fuzzy msgid "Control Surfaces" msgstr "Saídas de Controlo" #. the real actions -#: ardour_ui_ed.cc:84 audio_time_axis.cc:1856 new_session_dialog.cc:342 +#: ardour_ui_ed.cc:87 audio_time_axis.cc:1854 new_session_dialog.cc:529 msgid "New" msgstr "Novo" -#: ardour_ui_ed.cc:86 new_session_dialog.cc:334 +#: ardour_ui_ed.cc:89 new_session_dialog.cc:517 msgid "Open" msgstr "Abrir" -#: ardour_ui_ed.cc:87 +#: ardour_ui_ed.cc:90 msgid "Recent" msgstr "Recente" -#: ardour_ui_ed.cc:88 io_selector.cc:57 io_selector.cc:791 +#: ardour_ui_ed.cc:91 io_selector.cc:58 io_selector.cc:792 msgid "Close" msgstr "Fechar" -#: ardour_ui_ed.cc:91 route_params_ui.cc:512 +#: ardour_ui_ed.cc:94 route_params_ui.cc:514 msgid "Add Track/Bus" msgstr "Acrescentar Faixa/Barramento" -#: ardour_ui_ed.cc:102 +#: ardour_ui_ed.cc:105 msgid "Connect" msgstr "Ligar" #. -#: ardour_ui_ed.cc:110 +#: ardour_ui_ed.cc:113 msgid "Snapshot" msgstr "Capturar" -#: ardour_ui_ed.cc:113 +#: ardour_ui_ed.cc:116 msgid "Save Template..." msgstr "Guardar Modelo..." -#: ardour_ui_ed.cc:116 +#: ardour_ui_ed.cc:119 msgid "Export session to audiofile..." msgstr "Exportar sessão para ficheiro audio..." -#: ardour_ui_ed.cc:119 +#: ardour_ui_ed.cc:122 #, fuzzy msgid "Export selection to audiofile..." msgstr "Exportar sessão para ficheiro audio..." -#: ardour_ui_ed.cc:123 +#: ardour_ui_ed.cc:126 #, fuzzy msgid "Export range markers to audiofile..." msgstr "Exportar intervalo para ficheiro audio..." -#: ardour_ui_ed.cc:130 +#: ardour_ui_ed.cc:133 msgid "Cleanup unused sources" msgstr "Apagar originais em desuso" -#: ardour_ui_ed.cc:132 +#: ardour_ui_ed.cc:135 msgid "Flush wastebasket" msgstr "Limpeza" -#: ardour_ui_ed.cc:138 ardour_ui_options.cc:381 ardour_ui_options.cc:390 -#: ardour_ui_options.cc:462 +#: ardour_ui_ed.cc:141 ardour_ui_options.cc:408 ardour_ui_options.cc:417 +#: ardour_ui_options.cc:489 #, fuzzy msgid "JACK" msgstr "RECUAR" -#: ardour_ui_ed.cc:139 +#: ardour_ui_ed.cc:142 msgid "Latency" msgstr "" -#: ardour_ui_ed.cc:141 +#: ardour_ui_ed.cc:144 #, fuzzy msgid "Reconnect" msgstr "Ligar" -#: ardour_ui_ed.cc:144 mixer_strip.cc:514 mixer_strip.cc:574 +#: ardour_ui_ed.cc:147 mixer_strip.cc:497 mixer_strip.cc:565 msgid "Disconnect" msgstr "Desligar" -#: ardour_ui_ed.cc:171 +#: ardour_ui_ed.cc:174 msgid "Windows" msgstr "Janelas" -#: ardour_ui_ed.cc:172 +#: ardour_ui_ed.cc:175 msgid "start prefix" msgstr "" -#: ardour_ui_ed.cc:173 +#: ardour_ui_ed.cc:176 msgid "Quit" msgstr "Sair" #. windows visibility actions -#: ardour_ui_ed.cc:177 +#: ardour_ui_ed.cc:180 msgid "Maximise Editor Space" msgstr "" -#: ardour_ui_ed.cc:179 +#: ardour_ui_ed.cc:182 #, fuzzy msgid "Show Editor" msgstr "Opções" -#: ardour_ui_ed.cc:180 +#: ardour_ui_ed.cc:183 #, fuzzy msgid "Show Mixer" msgstr "Mistura" -#: ardour_ui_ed.cc:182 +#: ardour_ui_ed.cc:185 msgid "Options Editor" msgstr "Opções" -#: ardour_ui_ed.cc:183 +#: ardour_ui_ed.cc:186 #, fuzzy msgid "Track/Bus Inspector" msgstr "Faixas/Barramentos" -#: ardour_ui_ed.cc:185 +#: ardour_ui_ed.cc:188 msgid "Connections" msgstr "Ligações" -#: ardour_ui_ed.cc:187 +#: ardour_ui_ed.cc:190 msgid "Locations" msgstr "Localizações" -#: ardour_ui_ed.cc:189 +#: ardour_ui_ed.cc:192 msgid "Big Clock" msgstr "Cronómetro Principal" -#: ardour_ui_ed.cc:191 +#: ardour_ui_ed.cc:194 msgid "About" msgstr "Acerca de" -#: ardour_ui_ed.cc:192 +#: ardour_ui_ed.cc:195 #, fuzzy msgid "Colors" msgstr "Cor" -#: ardour_ui_ed.cc:194 +#: ardour_ui_ed.cc:197 #, fuzzy msgid "Add Audio Track" msgstr "Acrescentar Faixa/Barramento" -#: ardour_ui_ed.cc:196 +#: ardour_ui_ed.cc:199 #, fuzzy msgid "Add Audio Bus" msgstr "Esconder todos os barramentos audio" -#: ardour_ui_ed.cc:198 +#: ardour_ui_ed.cc:201 msgid "Save" msgstr "Guardar" -#: ardour_ui_ed.cc:200 editor_actions.cc:254 +#: ardour_ui_ed.cc:203 editor_actions.cc:255 #, fuzzy msgid "Remove Last Capture" msgstr "Remover a última captura" #. do-nothing action for the "transport" menu bar item -#: ardour_ui_ed.cc:207 +#: ardour_ui_ed.cc:210 #, fuzzy msgid "Transport" msgstr "Tradutores" @@ -1033,74 +1015,74 @@ msgstr "Tradutores" #. these two are not used by key bindings, instead use ToggleRoll for that. these two do show up in #. menus and via button proxies. #. -#: ardour_ui_ed.cc:213 sfdb_ui.cc:57 +#: ardour_ui_ed.cc:216 sfdb_ui.cc:57 msgid "Stop" msgstr "Parar" -#: ardour_ui_ed.cc:216 +#: ardour_ui_ed.cc:219 msgid "Roll" msgstr "" -#: ardour_ui_ed.cc:220 +#: ardour_ui_ed.cc:223 #, fuzzy msgid "Start/Stop" msgstr "Início:" -#: ardour_ui_ed.cc:223 +#: ardour_ui_ed.cc:226 msgid "Stop + Forget Capture" msgstr "" -#: ardour_ui_ed.cc:226 +#: ardour_ui_ed.cc:229 #, fuzzy msgid "Play Loop Range" msgstr "Reproduzir intervalo cíclico" -#: ardour_ui_ed.cc:229 +#: ardour_ui_ed.cc:232 #, fuzzy msgid "Play Selection" msgstr "Reproduzir região seleccionada" -#: ardour_ui_ed.cc:233 +#: ardour_ui_ed.cc:236 #, fuzzy msgid "Enable Record" msgstr "Gravar" -#: ardour_ui_ed.cc:236 +#: ardour_ui_ed.cc:239 #, fuzzy msgid "Rewind" msgstr "Região" -#: ardour_ui_ed.cc:239 +#: ardour_ui_ed.cc:242 msgid "Rewind (Slow)" msgstr "" -#: ardour_ui_ed.cc:242 +#: ardour_ui_ed.cc:245 msgid "Rewind (Fast)" msgstr "" -#: ardour_ui_ed.cc:245 +#: ardour_ui_ed.cc:248 #, fuzzy msgid "Forward" msgstr "retocar p/frente" -#: ardour_ui_ed.cc:248 +#: ardour_ui_ed.cc:251 msgid "Forward (Slow)" msgstr "" -#: ardour_ui_ed.cc:251 +#: ardour_ui_ed.cc:254 msgid "Forward (Fast)" msgstr "" -#: ardour_ui_ed.cc:254 +#: ardour_ui_ed.cc:257 msgid "Goto Zero" msgstr "" -#: ardour_ui_ed.cc:257 +#: ardour_ui_ed.cc:260 #, fuzzy msgid "Goto Start" msgstr "Início:" -#: ardour_ui_ed.cc:260 +#: ardour_ui_ed.cc:263 msgid "Goto End" msgstr "" @@ -1108,7 +1090,7 @@ msgstr "" #. that proxies for these action to be more compact. It would be nice to find a way to override the action #. name appearance on the buttons. #. -#: ardour_ui_ed.cc:269 +#: ardour_ui_ed.cc:272 #, fuzzy msgid "" "Punch\n" @@ -1117,7 +1099,7 @@ msgstr "" "início de\n" "inserção" -#: ardour_ui_ed.cc:272 +#: ardour_ui_ed.cc:275 #, fuzzy msgid "" "Punch\n" @@ -1126,11 +1108,11 @@ msgstr "" "final de\n" "inserção" -#: ardour_ui_ed.cc:275 option_editor.cc:128 +#: ardour_ui_ed.cc:278 option_editor.cc:129 msgid "Click" msgstr "Metrónomo" -#: ardour_ui_ed.cc:278 +#: ardour_ui_ed.cc:281 #, fuzzy msgid "" "Auto\n" @@ -1139,7 +1121,7 @@ msgstr "" "entrada\n" "automática" -#: ardour_ui_ed.cc:281 +#: ardour_ui_ed.cc:284 #, fuzzy msgid "" "Auto\n" @@ -1148,7 +1130,7 @@ msgstr "" "reprodução\n" "automática" -#: ardour_ui_ed.cc:284 +#: ardour_ui_ed.cc:287 #, fuzzy msgid "" "Auto\n" @@ -1157,283 +1139,283 @@ msgstr "" "retorno\n" "automático" -#: ardour_ui_ed.cc:288 +#: ardour_ui_ed.cc:291 #, fuzzy msgid "" "Time\n" "master" msgstr "Supervisor de tempo JACK" -#: ardour_ui_ed.cc:291 +#: ardour_ui_ed.cc:294 msgid "Toggle Record Enable Track1" msgstr "" -#: ardour_ui_ed.cc:293 +#: ardour_ui_ed.cc:296 msgid "Toggle Record Enable Track2" msgstr "" -#: ardour_ui_ed.cc:295 +#: ardour_ui_ed.cc:298 msgid "Toggle Record Enable Track3" msgstr "" -#: ardour_ui_ed.cc:297 +#: ardour_ui_ed.cc:300 msgid "Toggle Record Enable Track4" msgstr "" -#: ardour_ui_ed.cc:299 +#: ardour_ui_ed.cc:302 msgid "Toggle Record Enable Track5" msgstr "" -#: ardour_ui_ed.cc:301 +#: ardour_ui_ed.cc:304 msgid "Toggle Record Enable Track6" msgstr "" -#: ardour_ui_ed.cc:303 +#: ardour_ui_ed.cc:306 msgid "Toggle Record Enable Track7" msgstr "" -#: ardour_ui_ed.cc:305 +#: ardour_ui_ed.cc:308 msgid "Toggle Record Enable Track8" msgstr "" -#: ardour_ui_ed.cc:307 +#: ardour_ui_ed.cc:310 msgid "Toggle Record Enable Track9" msgstr "" -#: ardour_ui_ed.cc:309 +#: ardour_ui_ed.cc:312 msgid "Toggle Record Enable Track10" msgstr "" -#: ardour_ui_ed.cc:311 +#: ardour_ui_ed.cc:314 msgid "Toggle Record Enable Track11" msgstr "" -#: ardour_ui_ed.cc:313 +#: ardour_ui_ed.cc:316 msgid "Toggle Record Enable Track12" msgstr "" -#: ardour_ui_ed.cc:315 +#: ardour_ui_ed.cc:318 msgid "Toggle Record Enable Track13" msgstr "" -#: ardour_ui_ed.cc:317 +#: ardour_ui_ed.cc:320 msgid "Toggle Record Enable Track14" msgstr "" -#: ardour_ui_ed.cc:319 +#: ardour_ui_ed.cc:322 msgid "Toggle Record Enable Track15" msgstr "" -#: ardour_ui_ed.cc:321 +#: ardour_ui_ed.cc:324 msgid "Toggle Record Enable Track16" msgstr "" -#: ardour_ui_ed.cc:323 +#: ardour_ui_ed.cc:326 msgid "Toggle Record Enable Track17" msgstr "" -#: ardour_ui_ed.cc:325 +#: ardour_ui_ed.cc:328 msgid "Toggle Record Enable Track18" msgstr "" -#: ardour_ui_ed.cc:327 +#: ardour_ui_ed.cc:330 msgid "Toggle Record Enable Track19" msgstr "" -#: ardour_ui_ed.cc:329 +#: ardour_ui_ed.cc:332 msgid "Toggle Record Enable Track20" msgstr "" -#: ardour_ui_ed.cc:331 +#: ardour_ui_ed.cc:334 msgid "Toggle Record Enable Track21" msgstr "" -#: ardour_ui_ed.cc:333 +#: ardour_ui_ed.cc:336 msgid "Toggle Record Enable Track22" msgstr "" -#: ardour_ui_ed.cc:335 +#: ardour_ui_ed.cc:338 msgid "Toggle Record Enable Track23" msgstr "" -#: ardour_ui_ed.cc:337 +#: ardour_ui_ed.cc:340 msgid "Toggle Record Enable Track24" msgstr "" -#: ardour_ui_ed.cc:339 +#: ardour_ui_ed.cc:342 msgid "Toggle Record Enable Track25" msgstr "" -#: ardour_ui_ed.cc:341 +#: ardour_ui_ed.cc:344 msgid "Toggle Record Enable Track26" msgstr "" -#: ardour_ui_ed.cc:343 +#: ardour_ui_ed.cc:346 msgid "Toggle Record Enable Track27" msgstr "" -#: ardour_ui_ed.cc:345 +#: ardour_ui_ed.cc:348 msgid "Toggle Record Enable Track28" msgstr "" -#: ardour_ui_ed.cc:347 +#: ardour_ui_ed.cc:350 msgid "Toggle Record Enable Track29" msgstr "" -#: ardour_ui_ed.cc:349 +#: ardour_ui_ed.cc:352 msgid "Toggle Record Enable Track30" msgstr "" -#: ardour_ui_ed.cc:351 +#: ardour_ui_ed.cc:354 msgid "Toggle Record Enable Track31" msgstr "" -#: ardour_ui_ed.cc:353 +#: ardour_ui_ed.cc:356 msgid "Toggle Record Enable Track32" msgstr "" -#: ardour_ui_ed.cc:358 +#: ardour_ui_ed.cc:361 msgid "Percentage" msgstr "Percentagem" -#: ardour_ui_ed.cc:359 +#: ardour_ui_ed.cc:362 msgid "Semitones" msgstr "Semitons" -#: ardour_ui_ed.cc:363 +#: ardour_ui_ed.cc:366 msgid "Send MTC" msgstr "Enviar MTC" -#: ardour_ui_ed.cc:365 +#: ardour_ui_ed.cc:368 msgid "Send MMC" msgstr "Enviar MMC" -#: ardour_ui_ed.cc:367 +#: ardour_ui_ed.cc:370 #, fuzzy msgid "Use MMC" msgstr "Enviar MMC" -#: ardour_ui_ed.cc:369 +#: ardour_ui_ed.cc:372 #, fuzzy msgid "Send MIDI feedback" msgstr "Enviar resposta a parametros MIDI" -#: ardour_ui_ed.cc:371 +#: ardour_ui_ed.cc:374 #, fuzzy msgid "Use MIDI control" msgstr "Porta MMC" -#: ardour_ui_ed.cc:374 +#: ardour_ui_ed.cc:377 #, fuzzy -msgid "Connect newtrack inputs to hardware" +msgid "Connect new track inputs to hardware" msgstr "Ligar novas faixas automaticamente" -#: ardour_ui_ed.cc:392 +#: ardour_ui_ed.cc:396 #, fuzzy msgid "Connect new track outputs to hardware" msgstr "Ligar novas faixas automaticamente" -#: ardour_ui_ed.cc:394 +#: ardour_ui_ed.cc:398 #, fuzzy msgid "Connect new track outputs to master" msgstr "ligar saídas principais automaticamente" -#: ardour_ui_ed.cc:396 +#: ardour_ui_ed.cc:400 #, fuzzy msgid "Manually connect new track outputs" msgstr "ligar saídas manualmente" -#: ardour_ui_ed.cc:401 +#: ardour_ui_ed.cc:405 #, fuzzy msgid "Hardware monitoring" msgstr "Usar monitorização física" -#: ardour_ui_ed.cc:402 +#: ardour_ui_ed.cc:406 #, fuzzy msgid "Software monitoring" msgstr "Usar monitorização lógica" -#: ardour_ui_ed.cc:403 +#: ardour_ui_ed.cc:407 #, fuzzy msgid "External monitoring" msgstr "Usar monitorização física" #. Configuration object options (i.e. not session specific) -#: ardour_ui_ed.cc:407 +#: ardour_ui_ed.cc:411 msgid "Stop plugins with transport" msgstr "Suspender efeitos/plug-ins com transporte" -#: ardour_ui_ed.cc:408 +#: ardour_ui_ed.cc:412 #, fuzzy msgid "Verify remove last capture" msgstr "Remover a última captura" -#: ardour_ui_ed.cc:409 +#: ardour_ui_ed.cc:413 msgid "Stop recording on xrun" msgstr "Suspender a gravação em caso de falha sincrónica (XRUN)" -#: ardour_ui_ed.cc:410 +#: ardour_ui_ed.cc:414 #, fuzzy msgid "Stop transport at session end" msgstr "Suspender o transporte no final da sessão" -#: ardour_ui_ed.cc:411 +#: ardour_ui_ed.cc:415 msgid "-12dB gain reduce ffwd/rewind" msgstr "" -#: ardour_ui_ed.cc:412 +#: ardour_ui_ed.cc:416 msgid "Rec-enable stays engaged at stop" msgstr "" #. session options -#: ardour_ui_ed.cc:416 +#: ardour_ui_ed.cc:420 #, fuzzy msgid "Do not run plugins while recording" msgstr "Executar efeitos/plug-ins durante a gravação" -#: ardour_ui_ed.cc:419 +#: ardour_ui_ed.cc:423 msgid "Latched solo" msgstr "Solo retido" -#: ardour_ui_ed.cc:424 +#: ardour_ui_ed.cc:428 #, fuzzy msgid "Solo in-place" msgstr "solo livre" -#: ardour_ui_ed.cc:426 +#: ardour_ui_ed.cc:430 msgid "Solo via bus" msgstr "Solo por barramento" -#: ardour_ui_ed.cc:429 +#: ardour_ui_ed.cc:433 #, fuzzy msgid "Automatically create crossfades" msgstr "Desvanecimento cruzado automático em sobreposição" -#: ardour_ui_ed.cc:431 +#: ardour_ui_ed.cc:435 msgid "Unmute new full crossfades" msgstr "" -#: ardour_ui_options.cc:379 ardour_ui_options.cc:389 ardour_ui_options.cc:456 +#: ardour_ui_options.cc:406 ardour_ui_options.cc:416 ardour_ui_options.cc:483 msgid "Internal" msgstr "Interno" -#: ardour_ui_options.cc:380 ardour_ui_options.cc:459 +#: ardour_ui_options.cc:407 ardour_ui_options.cc:486 msgid "MTC" msgstr "" -#: audio_clock.cc:1719 editor.cc:185 +#: audio_clock.cc:1742 editor.cc:188 msgid "SMPTE" msgstr "" -#: audio_clock.cc:1720 editor.cc:184 editor_rulers.cc:359 +#: audio_clock.cc:1743 editor.cc:187 editor_rulers.cc:360 msgid "Bars:Beats" msgstr "Comp:Bat" -#: audio_clock.cc:1721 +#: audio_clock.cc:1744 msgid "Minutes:Seconds" msgstr "Mins:Segs" -#: audio_clock.cc:1722 +#: audio_clock.cc:1745 msgid "Audio Frames" msgstr "Quadros Audio" @@ -1441,288 +1423,310 @@ msgstr "Quadros Audio" #. Slowest = 6.6dB/sec falloff at update rate of 40ms #. Slow = 6.8dB/sec falloff at update rate of 40ms #. -#: audio_clock.cc:1723 editor_actions.cc:374 editor_actions.cc:382 +#: audio_clock.cc:1746 editor_actions.cc:375 editor_actions.cc:383 +#: gain_meter.cc:172 panner_ui.cc:89 plugin_ui.cc:392 plugin_ui.cc:635 msgid "Off" msgstr "Desligado" -#: audio_clock.cc:1725 +#: audio_clock.cc:1748 msgid "Mode" msgstr "Modo" -#: audio_time_axis.cc:90 mixer_strip.cc:458 +#: audio_time_axis.cc:91 msgid "m" msgstr "" -#: audio_time_axis.cc:90 mixer_strip.cc:459 +#: audio_time_axis.cc:91 msgid "s" msgstr "" -#: audio_time_axis.cc:90 +#: audio_time_axis.cc:91 msgid "r" msgstr "" -#: audio_time_axis.cc:94 +#: audio_time_axis.cc:95 msgid "g" msgstr "" #. group -#: audio_time_axis.cc:95 +#: audio_time_axis.cc:96 msgid "p" msgstr "" -#: audio_time_axis.cc:96 automation_time_axis.cc:31 visual_time_axis.cc:73 +#: audio_time_axis.cc:97 automation_time_axis.cc:32 visual_time_axis.cc:74 msgid "h" msgstr "" #. height -#: audio_time_axis.cc:97 +#: audio_time_axis.cc:98 msgid "a" msgstr "" -#: audio_time_axis.cc:98 visual_time_axis.cc:72 +#: audio_time_axis.cc:99 visual_time_axis.cc:73 msgid "v" msgstr "" -#: audio_time_axis.cc:173 +#: audio_time_axis.cc:168 mixer_strip.cc:86 msgid "Record" msgstr "Gravar" -#: audio_time_axis.cc:174 editor_actions.cc:36 +#: audio_time_axis.cc:169 editor_actions.cc:37 mixer_strip.cc:86 msgid "Solo" msgstr "" -#: audio_time_axis.cc:175 editor.cc:1767 editor.cc:1866 panner_ui.cc:385 +#: audio_time_axis.cc:170 editor.cc:1760 editor.cc:1859 mixer_strip.cc:86 +#: panner_ui.cc:427 msgid "Mute" msgstr "Mudo" -#: audio_time_axis.cc:176 +#: audio_time_axis.cc:171 msgid "Edit Group" msgstr "Grupo" -#: audio_time_axis.cc:177 visual_time_axis.cc:91 +#: audio_time_axis.cc:172 visual_time_axis.cc:92 msgid "Display Height" msgstr "Altura" -#: audio_time_axis.cc:178 +#: audio_time_axis.cc:173 msgid "Playlist" msgstr "Lista de Reprodução" -#: audio_time_axis.cc:179 audio_time_axis.cc:743 +#: audio_time_axis.cc:174 audio_time_axis.cc:741 msgid "Automation" msgstr "Automatização" -#: audio_time_axis.cc:180 visual_time_axis.cc:92 +#: audio_time_axis.cc:175 visual_time_axis.cc:93 msgid "Visual options" msgstr "Opções visuais" -#: audio_time_axis.cc:181 visual_time_axis.cc:93 +#: audio_time_axis.cc:176 visual_time_axis.cc:94 msgid "Hide this track" msgstr "Esconder esta faixa" -#: audio_time_axis.cc:337 +#: audio_time_axis.cc:333 mixer_strip.cc:927 msgid "No group" msgstr "Sem grupo" -#: audio_time_axis.cc:704 automation_time_axis.cc:448 -#: imageframe_time_axis.cc:256 marker_time_axis.cc:210 +#: audio_time_axis.cc:702 automation_time_axis.cc:450 +#: imageframe_time_axis.cc:255 marker_time_axis.cc:211 msgid "Height" msgstr "Altura" -#: audio_time_axis.cc:705 color_manager.cc:40 imageframe_time_axis.cc:257 -#: marker_time_axis.cc:211 +#: audio_time_axis.cc:703 color_manager.cc:41 imageframe_time_axis.cc:256 +#: marker_time_axis.cc:212 msgid "Color" msgstr "Cor" -#: audio_time_axis.cc:709 +#: audio_time_axis.cc:707 msgid "Hide all crossfades" msgstr "" -#: audio_time_axis.cc:710 +#: audio_time_axis.cc:708 msgid "Show all crossfades" msgstr "" -#: audio_time_axis.cc:714 mixer_strip.cc:1236 +#: audio_time_axis.cc:712 mixer_strip.cc:1011 #, fuzzy msgid "Remote Control ID" msgstr "remover ponto de controlo" -#: audio_time_axis.cc:720 -msgid "show all automation" +#: audio_time_axis.cc:718 +#, fuzzy +msgid "Show all automation" msgstr "Mostrar todos as automatizações" -#: audio_time_axis.cc:723 -msgid "show existing automation" +#: audio_time_axis.cc:721 +#, fuzzy +msgid "Show existing automation" msgstr "Mostrar automatizações existentes" -#: audio_time_axis.cc:726 -msgid "hide all automation" +#: audio_time_axis.cc:724 +#, fuzzy +msgid "Hide all automation" msgstr "Esconder todos as automatizações" -#: audio_time_axis.cc:731 audio_time_axis.cc:1169 editor.cc:215 -msgid "gain" -msgstr "ganho" +#: audio_time_axis.cc:729 +#, fuzzy +msgid "Fader" +msgstr "Desvanecimentos" -#: audio_time_axis.cc:736 audio_time_axis.cc:1209 -msgid "pan" +#: audio_time_axis.cc:734 +#, fuzzy +msgid "Pan" msgstr "pan" -#: audio_time_axis.cc:741 +#: audio_time_axis.cc:739 msgid "Plugins" msgstr "" -#: audio_time_axis.cc:749 +#: audio_time_axis.cc:747 msgid "Show waveforms" msgstr "Mostrar formas de onda" -#: audio_time_axis.cc:757 +#: audio_time_axis.cc:755 msgid "Traditional" msgstr "Tradicional" -#: audio_time_axis.cc:760 +#: audio_time_axis.cc:758 msgid "Rectified" msgstr "Rectificado" -#: audio_time_axis.cc:763 +#: audio_time_axis.cc:761 msgid "Waveform" msgstr "Forma de onda" -#: audio_time_axis.cc:773 +#: audio_time_axis.cc:771 #, fuzzy -msgid "align with existing material" +msgid "Align with existing material" msgstr "Material existente" -#: audio_time_axis.cc:778 +#: audio_time_axis.cc:776 #, fuzzy -msgid "align with capture time" +msgid "Align with capture time" msgstr "Tempo de captura" -#: audio_time_axis.cc:784 +#: audio_time_axis.cc:782 #, fuzzy msgid "Alignment" msgstr "Alinhar" -#: audio_time_axis.cc:790 editor.cc:523 editor_actions.cc:59 -#: mixer_strip.cc:1225 +#: audio_time_axis.cc:788 editor.cc:527 editor_actions.cc:60 +#: mixer_strip.cc:1000 mixer_ui.cc:111 msgid "Active" msgstr "Activar" -#: audio_time_axis.cc:795 editor.cc:1929 editor_actions.cc:319 -#: editor_markers.cc:507 imageframe_time_axis.cc:260 location_ui.cc:56 -#: marker_time_axis.cc:214 mixer_strip.cc:1239 +#: audio_time_axis.cc:793 editor.cc:1922 editor_actions.cc:320 +#: editor_markers.cc:508 imageframe_time_axis.cc:259 location_ui.cc:57 +#: marker_time_axis.cc:215 mixer_strip.cc:1014 msgid "Remove" msgstr "Remover" -#: audio_time_axis.cc:835 +#: audio_time_axis.cc:833 msgid "Name for playlist" msgstr "Nome para lista de reprodução" -#: audio_time_axis.cc:837 audio_time_axis.cc:1853 editor_markers.cc:826 -#: editor_mouse.cc:4609 imageframe_time_axis.cc:249 marker_time_axis.cc:207 -#: meter_bridge_strip.cc:223 mixer_strip.cc:1223 redirect_box.cc:749 -#: redirect_box.cc:1063 route_ui.cc:732 visual_time_axis.cc:325 +#: audio_time_axis.cc:835 audio_time_axis.cc:1851 editor_markers.cc:827 +#: editor_mouse.cc:4673 imageframe_time_axis.cc:248 marker_time_axis.cc:208 +#: meter_bridge_strip.cc:224 mixer_strip.cc:998 redirect_box.cc:751 +#: redirect_box.cc:1065 route_ui.cc:739 visual_time_axis.cc:326 msgid "Rename" msgstr "Renomear" -#: audio_time_axis.cc:870 audio_time_axis.cc:910 +#: audio_time_axis.cc:868 audio_time_axis.cc:908 #, fuzzy msgid "Name for Playlist" msgstr "Nome para lista de reprodução" -#: audio_time_axis.cc:1128 visual_time_axis.cc:382 +#: audio_time_axis.cc:1126 visual_time_axis.cc:383 msgid "a track already exists with that name" msgstr "já existe uma faixa com este nome" -#: audio_time_axis.cc:1412 editor.cc:1490 selection.cc:622 +#: audio_time_axis.cc:1167 editor.cc:218 +msgid "gain" +msgstr "ganho" + +#: audio_time_axis.cc:1207 +msgid "pan" +msgstr "pan" + +#: audio_time_axis.cc:1410 editor.cc:1483 selection.cc:634 msgid "programming error: " msgstr "" -#: audio_time_axis.cc:1850 +#: audio_time_axis.cc:1848 msgid "Current: %1" msgstr "Actual: %1" -#: audio_time_axis.cc:1857 +#: audio_time_axis.cc:1855 msgid "New Copy" msgstr "Nova Cópia" -#: audio_time_axis.cc:1859 +#: audio_time_axis.cc:1857 msgid "Clear Current" msgstr "Limpar Actual" -#: audio_time_axis.cc:1861 editor.cc:2031 editor.cc:2107 +#: audio_time_axis.cc:1859 editor.cc:2024 editor.cc:2100 msgid "Select" msgstr "Seleccionar" -#: automation_line.cc:883 +#: automation_line.cc:884 msgid "automation event move" msgstr "mover evento de automatização" -#: automation_line.cc:885 +#: automation_line.cc:886 msgid "automation range drag" msgstr "deslocar intervalo de automatização" -#: automation_line.cc:1014 region_gain_line.cc:61 +#: automation_line.cc:1015 region_gain_line.cc:62 msgid "remove control point" msgstr "remover ponto de controlo" -#: automation_time_axis.cc:32 editor_ops.cc:2813 +#: automation_time_axis.cc:33 editor_ops.cc:2885 msgid "clear" msgstr "apagar" -#: automation_time_axis.cc:74 +#: automation_time_axis.cc:75 msgid "track height" msgstr "" -#: automation_time_axis.cc:75 +#: automation_time_axis.cc:76 #, fuzzy msgid "automation state" msgstr "ponto de automatização de panorâmica" -#: automation_time_axis.cc:76 +#: automation_time_axis.cc:77 #, fuzzy msgid "clear track" msgstr "apagar intervalos" -#: automation_time_axis.cc:77 +#: automation_time_axis.cc:78 #, fuzzy msgid "hide track" msgstr "retocar faixa" -#: automation_time_axis.cc:185 automation_time_axis.cc:223 -#: automation_time_axis.cc:463 mixer_strip.cc:176 mixer_strip.cc:188 -#: plugin_ui.cc:394 plugin_ui.cc:636 region_editor.cc:53 -msgid "play" -msgstr "reproduzir" +#: automation_time_axis.cc:184 automation_time_axis.cc:213 +#: automation_time_axis.cc:461 +msgid "Manual" +msgstr "" -#: automation_time_axis.cc:187 automation_time_axis.cc:234 -#: automation_time_axis.cc:467 mixer_strip.cc:178 mixer_strip.cc:190 -#: plugin_ui.cc:397 plugin_ui.cc:638 -msgid "write" +#: automation_time_axis.cc:186 automation_time_axis.cc:224 +#: automation_time_axis.cc:465 editor.cc:2001 editor.cc:2082 gain_meter.cc:174 +#: panner_ui.cc:91 plugin_ui.cc:395 plugin_ui.cc:637 sfdb_ui.cc:56 +msgid "Play" +msgstr "Reproduzir" + +#: automation_time_axis.cc:188 automation_time_axis.cc:235 +#: automation_time_axis.cc:469 gain_meter.cc:176 panner_ui.cc:93 +#: plugin_ui.cc:398 plugin_ui.cc:639 +#, fuzzy +msgid "Write" msgstr "escrita" -#: automation_time_axis.cc:189 automation_time_axis.cc:245 -#: automation_time_axis.cc:471 mixer_strip.cc:180 mixer_strip.cc:192 -#: mixer_strip.cc:887 plugin_ui.cc:400 plugin_ui.cc:640 -msgid "touch" +#: automation_time_axis.cc:190 automation_time_axis.cc:246 +#: automation_time_axis.cc:473 gain_meter.cc:178 panner_ui.cc:95 +#: plugin_ui.cc:401 plugin_ui.cc:641 +#, fuzzy +msgid "Touch" msgstr "tocar" -#: automation_time_axis.cc:256 option_editor.cc:182 option_editor.cc:188 -#: plugin_ui.cc:403 +#: automation_time_axis.cc:257 option_editor.cc:183 option_editor.cc:189 +#: plugin_ui.cc:404 msgid "???" msgstr "" -#: automation_time_axis.cc:270 +#: automation_time_axis.cc:271 msgid "clear automation" msgstr "apagar automatizações" -#: automation_time_axis.cc:450 editor_actions.cc:317 +#: automation_time_axis.cc:452 editor_actions.cc:318 msgid "Hide" msgstr "Esconder" -#: automation_time_axis.cc:452 crossfade_edit.cc:76 redirect_box.cc:1055 +#: automation_time_axis.cc:454 crossfade_edit.cc:78 redirect_box.cc:1057 msgid "Clear" msgstr "Apagar" -#: automation_time_axis.cc:475 +#: automation_time_axis.cc:477 #, fuzzy msgid "State" msgstr "Início" @@ -1870,816 +1874,804 @@ msgstr "" msgid "color of fill" msgstr "" -#: color_manager.cc:39 +#: color_manager.cc:40 #, fuzzy msgid "Object" msgstr "objecto" -#: color_manager.cc:77 +#: color_manager.cc:78 #, fuzzy msgid "cannot open color definition file %1: %2" msgstr "" "Editor: não foi possível abrir o ficheiro de imagem inicial \"%1\" (%2)" -#: crossfade_edit.cc:73 +#: crossfade_edit.cc:75 msgid "ardour: x-fade edit" msgstr "ardour: desvanecimento cruzado" -#: crossfade_edit.cc:77 panner_ui.cc:401 +#: crossfade_edit.cc:79 panner_ui.cc:443 #, fuzzy msgid "Reset" msgstr "reiniciar" -#: crossfade_edit.cc:78 +#: crossfade_edit.cc:80 #, fuzzy msgid "Fade" msgstr "Desvanecimentos" -#: crossfade_edit.cc:79 +#: crossfade_edit.cc:81 #, fuzzy msgid "Out (dry)" msgstr "saída (limpa)" -#: crossfade_edit.cc:80 +#: crossfade_edit.cc:82 #, fuzzy msgid "Out" msgstr "Saída" -#: crossfade_edit.cc:81 +#: crossfade_edit.cc:83 #, fuzzy msgid "In (dry)" msgstr "entrada (limpa)" -#: crossfade_edit.cc:82 +#: crossfade_edit.cc:84 msgid "In" msgstr "" -#: crossfade_edit.cc:84 +#: crossfade_edit.cc:86 #, fuzzy msgid "With Pre-roll" msgstr "com pré-batimento" -#: crossfade_edit.cc:85 +#: crossfade_edit.cc:87 #, fuzzy msgid "With Post-roll" msgstr "com pós-batimento" -#: crossfade_edit.cc:93 +#: crossfade_edit.cc:95 msgid "Fade In" msgstr "Evanescimento" -#: crossfade_edit.cc:94 +#: crossfade_edit.cc:96 msgid "Fade Out" msgstr "Desvanecimento" -#: crossfade_edit.cc:170 editor.cc:1842 editor_actions.cc:315 -#: option_editor.cc:129 +#: crossfade_edit.cc:172 editor.cc:1835 editor_actions.cc:316 +#: option_editor.cc:130 msgid "Audition" msgstr "Audição" -#: editor.cc:101 editor.cc:3588 +#: editor.cc:104 editor.cc:3616 msgid "Slide" msgstr "Deslizar" -#: editor.cc:102 editor.cc:3586 +#: editor.cc:105 editor.cc:3614 msgid "Splice" msgstr "Reunir" -#: editor.cc:107 editor.cc:3643 export_dialog.cc:78 export_dialog.cc:92 -#: export_dialog.cc:893 export_dialog.cc:1225 +#. note that this menu list starts at zero, not 1, because zero +#. is a valid, if useless, ID. +#. +#. leave some breathing room +#: editor.cc:110 editor.cc:3671 export_dialog.cc:78 export_dialog.cc:92 +#: export_dialog.cc:893 export_dialog.cc:1225 route_ui.cc:437 msgid "None" msgstr "Nenhum" -#: editor.cc:108 editor.cc:3631 +#: editor.cc:111 editor.cc:3659 msgid "CD Frames" msgstr "Quadros CD" -#: editor.cc:109 editor.cc:3633 +#: editor.cc:112 editor.cc:3661 msgid "SMPTE Frames" msgstr "Quadros SMPTE" -#: editor.cc:110 editor.cc:3635 +#: editor.cc:113 editor.cc:3663 msgid "SMPTE Seconds" msgstr "Segundos SMPTE" -#: editor.cc:111 editor.cc:3637 +#: editor.cc:114 editor.cc:3665 msgid "SMPTE Minutes" msgstr "Minutos SMPTE" -#: editor.cc:112 editor.cc:3639 +#: editor.cc:115 editor.cc:3667 msgid "Seconds" msgstr "Segundos" -#: editor.cc:113 editor.cc:3641 +#: editor.cc:116 editor.cc:3669 msgid "Minutes" msgstr "Minutos" -#: editor.cc:114 editor.cc:3613 +#: editor.cc:117 editor.cc:3641 msgid "Beats/32" msgstr "Batimentos/32" -#: editor.cc:115 editor.cc:3611 +#: editor.cc:118 editor.cc:3639 msgid "Beats/16" msgstr "Batimentos/16" -#: editor.cc:116 editor.cc:3609 +#: editor.cc:119 editor.cc:3637 msgid "Beats/8" msgstr "Batimentos/8" -#: editor.cc:117 editor.cc:3607 +#: editor.cc:120 editor.cc:3635 msgid "Beats/4" msgstr "Batimentos/4" -#: editor.cc:118 editor.cc:3605 +#: editor.cc:121 editor.cc:3633 msgid "Beats/3" msgstr "Batimentos/3" -#: editor.cc:119 editor.cc:3615 +#: editor.cc:122 editor.cc:3643 msgid "Beats" msgstr "Batimentos" -#: editor.cc:120 editor.cc:3617 +#: editor.cc:123 editor.cc:3645 msgid "Bars" msgstr "Compassos" -#: editor.cc:121 editor.cc:3619 +#: editor.cc:124 editor.cc:3647 msgid "Marks" msgstr "Marcas" -#: editor.cc:122 editor.cc:141 editor.cc:3621 editor.cc:3687 +#: editor.cc:125 editor.cc:144 editor.cc:3649 editor.cc:3715 msgid "Edit Cursor" msgstr "Cursor de Edição" -#: editor.cc:123 editor.cc:3623 +#: editor.cc:126 editor.cc:3651 msgid "Region starts" msgstr "Inícios de região" -#: editor.cc:124 editor.cc:3625 +#: editor.cc:127 editor.cc:3653 msgid "Region ends" msgstr "Finais de região" -#: editor.cc:125 editor.cc:3629 +#: editor.cc:128 editor.cc:3657 msgid "Region syncs" msgstr "Sincronismos de região" -#: editor.cc:126 editor.cc:3627 +#: editor.cc:129 editor.cc:3655 msgid "Region bounds" msgstr "Extremos de região" -#: editor.cc:132 editor.cc:3662 +#: editor.cc:135 editor.cc:3690 msgid "Magnetic" msgstr "Magnético" -#: editor.cc:137 editor.cc:3679 export_dialog.cc:140 export_dialog.cc:156 +#: editor.cc:140 editor.cc:3707 export_dialog.cc:140 export_dialog.cc:156 #: export_dialog.cc:1068 export_dialog.cc:1072 msgid "Left" msgstr "Esquerda" -#: editor.cc:138 editor.cc:3681 export_dialog.cc:141 export_dialog.cc:157 +#: editor.cc:141 editor.cc:3709 export_dialog.cc:141 export_dialog.cc:157 msgid "Right" msgstr "Direita" -#: editor.cc:139 editor.cc:3683 +#: editor.cc:142 editor.cc:3711 msgid "Center" msgstr "Centro" -#: editor.cc:140 editor.cc:3685 +#: editor.cc:143 editor.cc:3713 msgid "Playhead" msgstr "Cursor de Reprodução" #. time display buttons -#: editor.cc:183 +#: editor.cc:186 msgid "Mins:Secs" msgstr "Mins:Segs" -#: editor.cc:186 editor_rulers.cc:353 +#: editor.cc:189 editor_rulers.cc:354 msgid "Frames" msgstr "Quadros" -#: editor.cc:187 editor_rulers.cc:373 +#: editor.cc:190 editor_rulers.cc:374 msgid "Tempo" msgstr "" -#: editor.cc:188 editor_rulers.cc:367 +#: editor.cc:191 editor_rulers.cc:368 msgid "Meter" msgstr "VUímetro" -#: editor.cc:189 editor_rulers.cc:379 +#: editor.cc:192 editor_rulers.cc:380 msgid "Location Markers" msgstr "Localizações" -#: editor.cc:190 editor_rulers.cc:385 +#: editor.cc:193 editor_rulers.cc:386 msgid "Range Markers" msgstr "Intervalos" -#: editor.cc:191 editor_rulers.cc:391 +#: editor.cc:194 editor_rulers.cc:392 msgid "Loop/Punch Ranges" msgstr "Ciclos/Inserção" -#: editor.cc:213 +#: editor.cc:216 msgid "range" msgstr "intervalo" -#: editor.cc:214 +#: editor.cc:217 msgid "object" msgstr "objecto" -#: editor.cc:216 +#: editor.cc:219 msgid "zoom" msgstr "" -#: editor.cc:217 +#: editor.cc:220 msgid "timefx" msgstr "" -#: editor.cc:218 +#: editor.cc:221 msgid "listen" msgstr "" -#: editor.cc:220 +#: editor.cc:223 msgid "mode" msgstr "modo" -#: editor.cc:221 +#: editor.cc:224 msgid "automation" msgstr "automatização" -#: editor.cc:223 +#: editor.cc:226 msgid "Edit Mode" msgstr "Modo de Edição" -#: editor.cc:224 editor_actions.cc:283 +#: editor.cc:227 editor_actions.cc:284 msgid "Snap To" msgstr "Ajustar a" -#: editor.cc:225 +#: editor.cc:228 msgid "Snap Mode" msgstr "Modo de Ajuste" -#: editor.cc:226 +#: editor.cc:229 msgid "Zoom Focus" msgstr "Zoom(focagem)" #. #. nudge -#: editor.cc:234 editor.cc:1907 editor.cc:2073 editor.cc:2129 +#: editor.cc:237 editor.cc:1900 editor.cc:2066 editor.cc:2122 msgid "Nudge" msgstr "Retocar" -#: editor.cc:466 +#: editor.cc:470 msgid "Zoom in" msgstr "Zoom(+)" -#: editor.cc:467 +#: editor.cc:471 msgid "Zoom out" msgstr "Zoom(-)" -#: editor.cc:470 +#: editor.cc:474 msgid "Zoom to session" msgstr "Zoom(sessão)" -#: editor.cc:485 +#: editor.cc:489 msgid "Zoom Span" msgstr "Zoom(alcance)" -#: editor.cc:498 editor.cc:524 editor_actions.cc:61 mixer_ui.cc:85 +#: editor.cc:502 editor.cc:528 editor_actions.cc:62 mixer_ui.cc:86 +#: mixer_ui.cc:112 #, fuzzy msgid "Visible" msgstr "visível" -#: editor.cc:499 editor.cc:522 +#: editor.cc:503 editor.cc:526 #, fuzzy msgid "Name" msgstr "Quadros" -#: editor.cc:595 editor.cc:661 +#: editor.cc:602 editor.cc:669 #, fuzzy msgid "Regions" msgstr "Região" -#: editor.cc:634 editor.cc:673 +#: editor.cc:642 editor.cc:681 msgid "Chunks" msgstr "Trechos" -#: editor.cc:664 +#: editor.cc:672 #, fuzzy msgid "Tracks/Busses" msgstr "Faixas/Barramentos" -#: editor.cc:667 +#: editor.cc:675 msgid "Snapshots" msgstr "Capturas" -#: editor.cc:670 +#: editor.cc:678 msgid "Edit Groups" msgstr "Grupos" -#: editor.cc:719 +#: editor.cc:727 msgid "Nudge region/selection forwards" msgstr "Retocar região/selecção para a frente" -#: editor.cc:720 +#: editor.cc:728 msgid "Nudge region/selection backwards" msgstr "Retocar região/selecção para trás" -#: editor.cc:727 editor_mixer.cc:298 +#: editor.cc:735 editor_mixer.cc:299 msgid "ardour: editor" msgstr "" -#: editor.cc:728 +#: editor.cc:736 msgid "ardour_editor" msgstr "" -#: editor.cc:1190 +#: editor.cc:1183 msgid "ardour: editor: " msgstr "" #. force name -#: editor.cc:1275 editor.cc:1284 editor_markers.cc:869 +#: editor.cc:1268 editor.cc:1277 editor_markers.cc:870 msgid "Loop" msgstr "Ciclo" #. force name -#: editor.cc:1289 editor.cc:1298 editor_markers.cc:895 +#: editor.cc:1282 editor.cc:1291 editor_markers.cc:896 msgid "Punch" msgstr "Inserção" -#: editor.cc:1446 editor_mouse.cc:1721 +#: editor.cc:1439 editor_mouse.cc:1742 msgid "programming error: fade in canvas item has no regionview data pointer!" msgstr "" -#: editor.cc:1458 editor.cc:1475 redirect_box.cc:1071 +#: editor.cc:1451 editor.cc:1468 redirect_box.cc:1073 msgid "Deactivate" msgstr "Desactivar" #. activation -#: editor.cc:1460 editor.cc:1477 redirect_box.cc:1069 +#: editor.cc:1453 editor.cc:1470 redirect_box.cc:1071 msgid "Activate" msgstr "Activar" -#: editor.cc:1465 editor.cc:1482 +#: editor.cc:1458 editor.cc:1475 msgid "Linear" msgstr "" -#: editor.cc:1466 editor.cc:1483 editor_actions.cc:375 +#: editor.cc:1459 editor.cc:1476 editor_actions.cc:376 msgid "Slowest" msgstr "Mais lento" -#: editor.cc:1467 editor.cc:1484 editor_actions.cc:376 +#: editor.cc:1460 editor.cc:1477 editor_actions.cc:377 msgid "Slow" msgstr "Lento" -#: editor.cc:1468 editor.cc:1485 editor_actions.cc:378 +#: editor.cc:1461 editor.cc:1478 editor_actions.cc:379 msgid "Fast" msgstr "Rápido" -#: editor.cc:1469 editor.cc:1486 editor_actions.cc:380 +#: editor.cc:1462 editor.cc:1479 editor_actions.cc:381 msgid "Fastest" msgstr "Mais Rápido" -#: editor.cc:1596 editor.cc:1604 +#: editor.cc:1589 editor.cc:1597 msgid "Freeze" msgstr "Congelar" -#: editor.cc:1600 +#: editor.cc:1593 msgid "Unfreeze" msgstr "Descongelar" -#: editor.cc:1769 editor.cc:1864 +#: editor.cc:1762 editor.cc:1857 #, fuzzy msgid "Unmute" msgstr "mudo" #. non-operative menu items for menu bar #. show editors -#: editor.cc:1773 editor.cc:2053 editor.cc:2755 editor_actions.cc:26 -#: editor_markers.cc:506 mixer_strip.cc:512 mixer_strip.cc:572 -#: redirect_box.cc:1077 +#: editor.cc:1766 editor.cc:2046 editor.cc:2748 editor_actions.cc:27 +#: editor_markers.cc:507 mixer_strip.cc:495 mixer_strip.cc:563 +#: redirect_box.cc:1079 msgid "Edit" msgstr "Editar" -#: editor.cc:1778 +#: editor.cc:1771 msgid "Convert to short" msgstr "" -#: editor.cc:1780 +#: editor.cc:1773 msgid "Convert to full" msgstr "" -#: editor.cc:1791 +#: editor.cc:1784 #, fuzzy msgid "Crossfade" msgstr "Desvanecimento cruzado" -#: editor.cc:1834 +#: editor.cc:1827 msgid "Popup region editor" msgstr "Editor de região" -#: editor.cc:1835 +#: editor.cc:1828 #, fuzzy msgid "Raise to top layer" msgstr "Elevar a região para o nível de topo" -#: editor.cc:1836 +#: editor.cc:1829 #, fuzzy msgid "Lower to bottom layer" msgstr "Descer a região para o nível de fundo" -#: editor.cc:1838 +#: editor.cc:1831 msgid "Define sync point" msgstr "Definir ponto de sincronia" -#: editor.cc:1839 +#: editor.cc:1832 msgid "Remove sync point" msgstr "Remover ponto de sincronia" -#: editor.cc:1844 +#: editor.cc:1837 #, fuzzy msgid "Bounce" msgstr "Rebater intervalo" -#: editor.cc:1847 +#: editor.cc:1840 #, fuzzy msgid "Analyze region" msgstr "Reproduzir Região" -#: editor.cc:1859 +#: editor.cc:1852 msgid "Lock" msgstr "Bloquear" -#: editor.cc:1860 +#: editor.cc:1853 msgid "Unlock" msgstr "Desbloquear" -#: editor.cc:1870 +#: editor.cc:1863 msgid "Original position" msgstr "Posição original" -#: editor.cc:1876 +#: editor.cc:1869 msgid "Toggle envelope visibility" msgstr "" -#: editor.cc:1877 +#: editor.cc:1870 #, fuzzy msgid "Toggle envelope active" msgstr "Activação" -#: editor.cc:1881 +#: editor.cc:1874 msgid "DeNormalize" msgstr "Denormalizar" -#: editor.cc:1883 +#: editor.cc:1876 msgid "Normalize" msgstr "Normalizar" -#: editor.cc:1886 +#: editor.cc:1879 msgid "Reverse" msgstr "Inverter" #. range related stuff -#: editor.cc:1892 +#: editor.cc:1885 #, fuzzy msgid "Add Range Markers" msgstr "Intervalos" -#: editor.cc:1893 +#: editor.cc:1886 #, fuzzy msgid "Set Range" msgstr "Separar Intervalo" -#: editor.cc:1902 +#: editor.cc:1895 msgid "Nudge fwd" msgstr "Retocar p/frente" -#: editor.cc:1903 +#: editor.cc:1896 msgid "Nudge bwd" msgstr "Retocar p/trás" -#: editor.cc:1904 +#: editor.cc:1897 msgid "Nudge fwd by capture offset" msgstr "Retocar p/frente captura" -#: editor.cc:1905 +#: editor.cc:1898 msgid "Nudge bwd by capture offset" msgstr "Retocar p/trás captura" -#: editor.cc:1914 +#: editor.cc:1907 msgid "Start to edit cursor" msgstr "Do início ao cursor de edição" -#: editor.cc:1915 +#: editor.cc:1908 msgid "Edit cursor to end" msgstr "Do cursor de edição ao final" -#: editor.cc:1917 +#: editor.cc:1910 gain_meter.cc:181 gain_meter.cc:813 panner_ui.cc:98 +#: panner_ui.cc:803 msgid "Trim" msgstr "Cortar" -#: editor.cc:1920 +#: editor.cc:1913 msgid "Split" msgstr "Separar" -#: editor.cc:1923 +#: editor.cc:1916 msgid "Make mono regions" msgstr "Criar regiões mono" -#: editor.cc:1926 +#: editor.cc:1919 msgid "Duplicate" msgstr "Duplicar" -#: editor.cc:1927 +#: editor.cc:1920 msgid "Fill Track" msgstr "Preencher Faixa" -#: editor.cc:1931 +#: editor.cc:1924 msgid "Destroy" msgstr "Destruir" -#: editor.cc:1961 +#: editor.cc:1954 msgid "Play range" msgstr "Reproduzir intervalo" -#: editor.cc:1962 +#: editor.cc:1955 msgid "Loop range" msgstr "Intervalo cíclico" -#: editor.cc:1966 +#: editor.cc:1959 #, fuzzy msgid "Analyze range" msgstr "Reproduzir intervalo" -#: editor.cc:1970 +#: editor.cc:1963 #, fuzzy msgid "Separate range to track" msgstr "Separar Intervalo" -#: editor.cc:1971 +#: editor.cc:1964 #, fuzzy msgid "Separate range to region list" msgstr "seleccionar regiões" -#: editor.cc:1974 +#: editor.cc:1967 #, fuzzy msgid "Select all in range" msgstr "Seleccionar tudo na faixa" -#: editor.cc:1976 editor.cc:2021 +#: editor.cc:1969 editor.cc:2014 #, fuzzy msgid "Set range to loop range" msgstr "Seleccionar intervalo de ciclo" -#: editor.cc:1977 editor.cc:2022 +#: editor.cc:1970 editor.cc:2015 #, fuzzy msgid "Set range to punch range" msgstr "Seleccionar intervalo de inserção" -#: editor.cc:1979 +#: editor.cc:1972 #, fuzzy msgid "Crop region to range" msgstr "Cortar Regão para intervalo" -#: editor.cc:1980 +#: editor.cc:1973 #, fuzzy msgid "Fill range with region" msgstr "Preencher intervalo c/Região" -#: editor.cc:1981 +#: editor.cc:1974 #, fuzzy msgid "Duplicate range" msgstr "Duplicar" -#: editor.cc:1982 +#: editor.cc:1975 msgid "Create chunk from range" msgstr "Criar trecho desde intervalo" -#: editor.cc:1984 +#: editor.cc:1977 msgid "Bounce range" msgstr "Rebater intervalo" -#: editor.cc:1985 +#: editor.cc:1978 #, fuzzy msgid "Export range" msgstr "Exportar região" -#: editor.cc:1987 +#: editor.cc:1980 msgid "Range" msgstr "Intervalo" -#: editor.cc:2002 editor.cc:2087 +#: editor.cc:1995 editor.cc:2080 msgid "Play from edit cursor" msgstr "Reproduzir desde o cursor de edição" -#: editor.cc:2003 editor.cc:2088 +#: editor.cc:1996 editor.cc:2081 msgid "Play from start" msgstr "Reproduzir desde o início" -#: editor.cc:2004 +#: editor.cc:1997 #, fuzzy msgid "Play region" msgstr "Reproduzir Região" -#: editor.cc:2006 +#: editor.cc:1999 msgid "Loop Region" msgstr "Região Cíclica" -#: editor.cc:2008 editor.cc:2089 sfdb_ui.cc:56 -msgid "Play" -msgstr "Reproduzir" - -#: editor.cc:2016 editor.cc:2097 +#: editor.cc:2009 editor.cc:2090 msgid "Select All in track" msgstr "Seleccionar tudo na faixa" -#: editor.cc:2017 editor.cc:2098 redirect_box.cc:1065 +#: editor.cc:2010 editor.cc:2091 redirect_box.cc:1067 msgid "Select All" msgstr "Seleccionar tudo" -#: editor.cc:2018 editor.cc:2099 +#: editor.cc:2011 editor.cc:2092 #, fuzzy msgid "Invert selection in track" msgstr "Inverter na faixa" -#: editor.cc:2019 editor.cc:2100 +#: editor.cc:2012 editor.cc:2093 #, fuzzy msgid "Invert selection" msgstr "mover selecção" -#: editor.cc:2024 editor.cc:2102 +#: editor.cc:2017 editor.cc:2095 #, fuzzy msgid "Select all after edit cursor" msgstr "Do início ao cursor de edição" -#: editor.cc:2025 editor.cc:2103 +#: editor.cc:2018 editor.cc:2096 #, fuzzy msgid "Select all before edit cursor" msgstr "Do início ao cursor de edição" -#: editor.cc:2026 editor.cc:2104 +#: editor.cc:2019 editor.cc:2097 #, fuzzy msgid "Select all after playhead" msgstr "Desde cursor de reprodução" -#: editor.cc:2027 editor.cc:2105 +#: editor.cc:2020 editor.cc:2098 #, fuzzy msgid "Select all before playhead" msgstr "Desde cursor de reprodução" -#: editor.cc:2028 +#: editor.cc:2021 #, fuzzy msgid "Select all between cursors" msgstr "Do início ao cursor de edição" #. standard editing stuff -#: editor.cc:2039 editor.cc:2115 editor.cc:3455 editor_actions.cc:213 -#: redirect_box.cc:1058 +#: editor.cc:2032 editor.cc:2108 editor.cc:3483 editor_actions.cc:214 +#: redirect_box.cc:1060 msgid "Cut" msgstr "Cortar" -#: editor.cc:2040 editor.cc:2116 editor.cc:3457 editor_actions.cc:218 -#: redirect_box.cc:1060 +#: editor.cc:2033 editor.cc:2109 editor.cc:3485 editor_actions.cc:219 +#: redirect_box.cc:1062 msgid "Copy" msgstr "Copiar" -#: editor.cc:2041 +#: editor.cc:2034 #, fuzzy msgid "Paste at edit cursor" msgstr "Do início ao cursor de edição" -#: editor.cc:2042 +#: editor.cc:2035 #, fuzzy msgid "Paste at mouse" msgstr "usar saídas principais" -#: editor.cc:2046 editor.cc:3462 +#: editor.cc:2039 editor.cc:3490 msgid "Align" msgstr "Alinhar" -#: editor.cc:2047 editor.cc:3464 +#: editor.cc:2040 editor.cc:3492 msgid "Align Relative" msgstr "Alinhar Relativamente" -#: editor.cc:2051 +#: editor.cc:2044 msgid "Insert chunk" msgstr "Inserir trecho" -#: editor.cc:2058 +#: editor.cc:2051 #, fuzzy msgid "Insert Selected Region" msgstr "seleccionar regiões" -#: editor.cc:2059 +#: editor.cc:2052 msgid "Insert Existing Audio" msgstr "" -#: editor.cc:2068 editor.cc:2124 +#: editor.cc:2061 editor.cc:2117 msgid "Nudge entire track fwd" msgstr "Retocar toda a faixa p/frente" -#: editor.cc:2069 editor.cc:2125 +#: editor.cc:2062 editor.cc:2118 msgid "Nudge track after edit cursor fwd" msgstr "Retocar a faixa p/frente do cursor de edição" -#: editor.cc:2070 editor.cc:2126 +#: editor.cc:2063 editor.cc:2119 msgid "Nudge entire track bwd" msgstr "Retocar toda a faixa p/trás" -#: editor.cc:2071 editor.cc:2127 +#: editor.cc:2064 editor.cc:2120 msgid "Nudge track after edit cursor bwd" msgstr "Retocar a faixa p/trás do cursor de edição" -#: editor.cc:2117 editor.cc:3459 editor_actions.cc:220 redirect_box.cc:1062 +#: editor.cc:2110 editor.cc:3487 editor_actions.cc:221 redirect_box.cc:1064 msgid "Paste" msgstr "Colar" -#: editor.cc:2637 +#: editor.cc:2630 msgid "select/move objects" msgstr "seleccionar/mover objectos" -#: editor.cc:2638 +#: editor.cc:2631 msgid "select/move ranges" msgstr "seleccionar/mover intervalos" -#: editor.cc:2639 +#: editor.cc:2632 msgid "draw gain automation" msgstr "desenhar automatização de ganho" -#: editor.cc:2640 +#: editor.cc:2633 msgid "select zoom range" msgstr "seleccionar zoom" -#: editor.cc:2641 +#: editor.cc:2634 msgid "stretch/shrink regions" msgstr "alongar/estreitar regiões" -#: editor.cc:2642 +#: editor.cc:2635 #, fuzzy msgid "listen to specific regions" msgstr "seleccionar regiões" -#: editor.cc:2753 +#: editor.cc:2746 msgid "Start:" msgstr "Início:" -#: editor.cc:2754 +#: editor.cc:2747 msgid "End:" msgstr "Final:" -#: editor.cc:3097 -#, fuzzy -msgid "set selected trackview" -msgstr "seleccionar visualização de faixa" - -#: editor.cc:3137 -#, fuzzy -msgid "set selected control point" -msgstr "remover ponto de controlo" - -#: editor.cc:3246 -msgid "set selected regionview" -msgstr "seleccionar visualização de região" - -#: editor.cc:3334 editor.cc:3374 +#: editor.cc:3362 editor.cc:3402 msgid "set selected regions" msgstr "seleccionar regiões" -#: editor.cc:3430 editor_actions.cc:203 +#: editor.cc:3458 editor_actions.cc:204 msgid "Undo" msgstr "Desfazer" -#: editor.cc:3432 +#: editor.cc:3460 msgid "Undo (%1)" msgstr "Desfazer (%1)" -#: editor.cc:3442 editor_actions.cc:205 +#: editor.cc:3470 editor_actions.cc:206 msgid "Redo" msgstr "Refazer" -#: editor.cc:3444 +#: editor.cc:3472 msgid "Redo (%1)" msgstr "Refazer (%1)" -#: editor.cc:3478 +#: editor.cc:3506 msgid "... as new track" msgstr "" -#: editor.cc:3479 +#: editor.cc:3507 #, fuzzy msgid "... as new region" msgstr "alinhar região" -#: editor.cc:3481 +#: editor.cc:3509 msgid "Import audio (copy)" msgstr "Importar audio (copiar)" -#: editor.cc:3484 +#: editor.cc:3512 msgid "Remove last capture" msgstr "Remover a última captura" -#: editor.cc:3508 +#: editor.cc:3536 msgid "Duplicate how many times?" msgstr "Duplicar quantas vezes?" -#: editor.cc:3994 +#: editor.cc:4022 msgid "" "Playlist %1 is currently unused.\n" "If left alone, no audio files used by it will be cleaned.\n" @@ -2691,768 +2683,768 @@ msgstr "" "Se for eliminada, todos os ficheiros de audio serão respectivamente " "eliminados." -#: editor.cc:4002 +#: editor.cc:4030 msgid "Delete playlist" msgstr "Eliminar lista de reprodução" -#: editor.cc:4003 +#: editor.cc:4031 #, fuzzy msgid "Keep playlist" msgstr "Manter lista de reprodução" -#: editor.cc:4004 editor_audio_import.cc:237 editor_ops.cc:1976 -#: editor_timefx.cc:52 export_dialog.cc:971 io_selector.cc:58 -#: io_selector.cc:792 redirect_box.cc:901 tempo_dialog.cc:19 -#: tempo_dialog.cc:36 tempo_dialog.cc:152 tempo_dialog.cc:170 +#: editor.cc:4032 editor_audio_import.cc:236 editor_ops.cc:2048 +#: editor_timefx.cc:71 export_dialog.cc:971 io_selector.cc:59 +#: io_selector.cc:793 redirect_box.cc:903 tempo_dialog.cc:20 +#: tempo_dialog.cc:37 tempo_dialog.cc:202 tempo_dialog.cc:220 msgid "Cancel" msgstr "Cancelar" -#: editor.cc:4171 +#: editor.cc:4199 #, fuzzy msgid "new playlists" msgstr "Manter lista de reprodução" -#: editor.cc:4179 +#: editor.cc:4207 #, fuzzy msgid "copy playlists" msgstr "Manter lista de reprodução" -#: editor.cc:4187 +#: editor.cc:4215 #, fuzzy msgid "clear playlists" msgstr "limpar lista de reprodução" -#: editor_actions.cc:27 +#: editor_actions.cc:28 #, fuzzy msgid "Select regions" msgstr "seleccionar regiões" -#: editor_actions.cc:28 +#: editor_actions.cc:29 #, fuzzy msgid "Select range operations" msgstr "seleccionar regiões" -#: editor_actions.cc:29 +#: editor_actions.cc:30 #, fuzzy msgid "Move edit cursor" msgstr "Do início ao cursor de edição" -#: editor_actions.cc:30 +#: editor_actions.cc:31 #, fuzzy msgid "Region operations" msgstr "Regiões/criação" -#: editor_actions.cc:31 +#: editor_actions.cc:32 msgid "Tools" msgstr "" -#: editor_actions.cc:32 +#: editor_actions.cc:33 msgid "View" msgstr "" -#: editor_actions.cc:33 +#: editor_actions.cc:34 #, fuzzy msgid "ZoomFocus" msgstr "Zoom(focagem)" -#: editor_actions.cc:34 +#: editor_actions.cc:35 #, fuzzy msgid "Meter hold" msgstr "VUímetro" -#: editor_actions.cc:35 +#: editor_actions.cc:36 msgid "Meter falloff" msgstr "" -#: editor_actions.cc:37 +#: editor_actions.cc:38 #, fuzzy msgid "Crossfades" msgstr "Desvanecimento cruzado" -#: editor_actions.cc:38 +#: editor_actions.cc:39 #, fuzzy msgid "Monitoring" msgstr "Usar monitorização física" -#: editor_actions.cc:39 +#: editor_actions.cc:40 #, fuzzy msgid "Autoconnect" msgstr "Ligar" -#: editor_actions.cc:40 +#: editor_actions.cc:41 #, fuzzy msgid "Layering" msgstr "Nível" -#: editor_actions.cc:41 +#: editor_actions.cc:42 #, fuzzy msgid "Metering" msgstr "VUímetro" -#: editor_actions.cc:42 +#: editor_actions.cc:43 msgid "Fall off rate" msgstr "" -#: editor_actions.cc:43 +#: editor_actions.cc:44 msgid "Hold Time" msgstr "" -#: editor_actions.cc:44 +#: editor_actions.cc:45 msgid "Add Existing Audio" msgstr "" #. add named actions for the editor -#: editor_actions.cc:49 +#: editor_actions.cc:50 #, fuzzy msgid "Show Editor Mixer" msgstr "Mostrar painéis de mistura de todas as faixas audio" -#: editor_actions.cc:54 +#: editor_actions.cc:55 #, fuzzy msgid "Span Entire Overlap" msgstr "Elevar a região em um nível" -#: editor_actions.cc:56 editor_actions.cc:383 +#: editor_actions.cc:57 editor_actions.cc:384 #, fuzzy msgid "Short" msgstr "porta" -#: editor_actions.cc:63 +#: editor_actions.cc:64 msgid "Created Automatically" msgstr "" -#: editor_actions.cc:66 +#: editor_actions.cc:67 msgid "Playhead to Next Region Start" msgstr "" -#: editor_actions.cc:68 +#: editor_actions.cc:69 msgid "Playhead to Next Region End" msgstr "" -#: editor_actions.cc:70 +#: editor_actions.cc:71 msgid "Playhead to Next Region Sync" msgstr "" -#: editor_actions.cc:73 +#: editor_actions.cc:74 msgid "Playhead to Previous Region Start" msgstr "" -#: editor_actions.cc:75 +#: editor_actions.cc:76 msgid "Playhead to Previous Region End" msgstr "" -#: editor_actions.cc:77 +#: editor_actions.cc:78 msgid "Playhead to Previous Region Sync" msgstr "" -#: editor_actions.cc:80 +#: editor_actions.cc:81 #, fuzzy msgid "Edit Cursor to Next Region Start" msgstr "Do cursor de edição ao final" -#: editor_actions.cc:82 +#: editor_actions.cc:83 #, fuzzy msgid "Edit Cursor to Next Region End" msgstr "Do cursor de edição ao final" -#: editor_actions.cc:84 +#: editor_actions.cc:85 #, fuzzy msgid "Edit Cursor to Next Region Sync" msgstr "Do cursor de edição ao final" -#: editor_actions.cc:87 +#: editor_actions.cc:88 msgid "Edit Cursor to Previous Region Start" msgstr "" -#: editor_actions.cc:89 +#: editor_actions.cc:90 #, fuzzy msgid "Edit Cursor to Previous Region End" msgstr "Do cursor de edição ao final" -#: editor_actions.cc:91 +#: editor_actions.cc:92 #, fuzzy msgid "Edit Cursor to Previous Region Sync" msgstr "Do cursor de edição ao final" -#: editor_actions.cc:94 +#: editor_actions.cc:95 msgid "Playhead to Range Start" msgstr "" -#: editor_actions.cc:96 +#: editor_actions.cc:97 #, fuzzy msgid "Playhead to Range End" msgstr "Reproduzir intervalo cíclico" -#: editor_actions.cc:99 +#: editor_actions.cc:100 #, fuzzy msgid "Edit Cursor to Range Start" msgstr "Do cursor de edição ao final" -#: editor_actions.cc:101 +#: editor_actions.cc:102 #, fuzzy msgid "Edit Cursor to Range End" msgstr "Do cursor de edição ao final" -#: editor_actions.cc:104 editor_ops.cc:1300 +#: editor_actions.cc:105 editor_ops.cc:1363 #, fuzzy msgid "select all" msgstr "Seleccionar tudo" -#: editor_actions.cc:106 +#: editor_actions.cc:107 #, fuzzy msgid "Select All After Edit Cursor" msgstr "sincronizar pelo cursor de edição" -#: editor_actions.cc:108 +#: editor_actions.cc:109 msgid "Select All Before Edit Cursor" msgstr "" -#: editor_actions.cc:111 +#: editor_actions.cc:112 #, fuzzy msgid "Select All After Playhead" msgstr "Desde cursor de reprodução" -#: editor_actions.cc:113 +#: editor_actions.cc:114 #, fuzzy msgid "Select All Before Playhead" msgstr "Desde cursor de reprodução" -#: editor_actions.cc:115 +#: editor_actions.cc:116 #, fuzzy msgid "Select All Between Cursors" msgstr "sincronizar pelo cursor de edição" -#: editor_actions.cc:118 +#: editor_actions.cc:119 #, fuzzy msgid "Select All in Punch Range" msgstr "Seleccionar Intervalo de Inserção" -#: editor_actions.cc:120 +#: editor_actions.cc:121 #, fuzzy msgid "Select All in Loop Range" msgstr "Seleccionar intervalo de ciclo" -#: editor_actions.cc:123 +#: editor_actions.cc:124 msgid "Jump Forward to Mark" msgstr "" -#: editor_actions.cc:125 +#: editor_actions.cc:126 msgid "Jump Backward to Mark" msgstr "" -#: editor_actions.cc:127 +#: editor_actions.cc:128 #, fuzzy msgid "Add Location from Playhead" msgstr "Desde cursor de reprodução" -#: editor_actions.cc:130 +#: editor_actions.cc:131 #, fuzzy msgid "Nudge Forward" msgstr "retocar p/frente" -#: editor_actions.cc:132 +#: editor_actions.cc:133 #, fuzzy msgid "Nudge Next Forward" msgstr "retocar p/frente" -#: editor_actions.cc:134 +#: editor_actions.cc:135 #, fuzzy msgid "Nudge Backward" msgstr "Retocar p/trás" -#: editor_actions.cc:136 +#: editor_actions.cc:137 #, fuzzy msgid "Nudge Next Backward" msgstr "Retocar toda a faixa p/frente" -#: editor_actions.cc:139 +#: editor_actions.cc:140 #, fuzzy msgid "Zoom Out" msgstr "Zoom(-)" -#: editor_actions.cc:141 +#: editor_actions.cc:142 #, fuzzy msgid "Zoom In" msgstr "Zoom(+)" -#: editor_actions.cc:143 +#: editor_actions.cc:144 #, fuzzy msgid "Zoom to Session" msgstr "Zoom(sessão)" -#: editor_actions.cc:146 +#: editor_actions.cc:147 #, fuzzy msgid "Scroll Tracks Up" msgstr "Preencher Faixa" -#: editor_actions.cc:148 +#: editor_actions.cc:149 msgid "Scroll Tracks Down" msgstr "" -#: editor_actions.cc:150 +#: editor_actions.cc:151 #, fuzzy msgid "Step Tracks Up" msgstr "retocar faixa" -#: editor_actions.cc:152 +#: editor_actions.cc:153 msgid "Step Tracks Down" msgstr "" -#: editor_actions.cc:155 +#: editor_actions.cc:156 msgid "Scroll Backward" msgstr "" -#: editor_actions.cc:157 +#: editor_actions.cc:158 msgid "Scroll Forward" msgstr "" -#: editor_actions.cc:159 +#: editor_actions.cc:160 msgid "goto" msgstr "" -#: editor_actions.cc:161 +#: editor_actions.cc:162 #, fuzzy msgid "Center Playhead" msgstr "Cursor de Reprodução" -#: editor_actions.cc:163 +#: editor_actions.cc:164 #, fuzzy msgid "Center Edit Cursor" msgstr "Cursor de Edição" -#: editor_actions.cc:165 +#: editor_actions.cc:166 #, fuzzy msgid "Playhead Forward" msgstr "Cursor de Reprodução" -#: editor_actions.cc:167 +#: editor_actions.cc:168 #, fuzzy msgid "Playhead Backward" msgstr "Cursor de Reprodução" -#: editor_actions.cc:169 +#: editor_actions.cc:170 #, fuzzy msgid "Playhead to Edit" msgstr "Cursor de Reprodução" -#: editor_actions.cc:171 +#: editor_actions.cc:172 #, fuzzy msgid "Edit to Playhead" msgstr "Desde cursor de reprodução" -#: editor_actions.cc:174 +#: editor_actions.cc:175 #, fuzzy msgid "Align Regions Start" msgstr "Inícios de região" -#: editor_actions.cc:176 +#: editor_actions.cc:177 #, fuzzy msgid "Align Regions Start Relative" msgstr "alinhar selecção (relativamente)" -#: editor_actions.cc:178 +#: editor_actions.cc:179 #, fuzzy msgid "Align Regions End" msgstr "alinhar região" -#: editor_actions.cc:180 +#: editor_actions.cc:181 #, fuzzy msgid "Align Regions End Relative" msgstr "Alinhar Relativamente" -#: editor_actions.cc:183 +#: editor_actions.cc:184 #, fuzzy msgid "Align Regions Sync" msgstr "alinhar região" -#: editor_actions.cc:185 +#: editor_actions.cc:186 #, fuzzy msgid "Align Regions Sync Relative" msgstr "Alinhar Relativamente" -#: editor_actions.cc:188 +#: editor_actions.cc:189 #, fuzzy msgid "Audition at Mouse" msgstr "Audição" -#: editor_actions.cc:190 +#: editor_actions.cc:191 #, fuzzy msgid "Brush at Mouse" msgstr "usar saídas principais" -#: editor_actions.cc:192 +#: editor_actions.cc:193 #, fuzzy msgid "Set Edit Cursor" msgstr "Cursor de Edição" -#: editor_actions.cc:194 +#: editor_actions.cc:195 #, fuzzy msgid "Mute/Unmute Region" msgstr "Criar Região" -#: editor_actions.cc:196 +#: editor_actions.cc:197 #, fuzzy msgid "Set Playhead" msgstr "Cursor de Reprodução" -#: editor_actions.cc:198 +#: editor_actions.cc:199 #, fuzzy msgid "Split Region" msgstr "Separar Região" -#: editor_actions.cc:200 +#: editor_actions.cc:201 #, fuzzy msgid "Set Region Sync Position" msgstr "Por Posição de Região" -#: editor_actions.cc:208 +#: editor_actions.cc:209 #, fuzzy msgid "Export Session" msgstr "Exportar região" -#: editor_actions.cc:210 +#: editor_actions.cc:211 #, fuzzy msgid "Export Range" msgstr "Separar Intervalo" #. Note: for now, editor-delete does the exact same thing as editor-cut -#: editor_actions.cc:216 +#: editor_actions.cc:217 #, fuzzy msgid "Delete" msgstr "eliminar" -#: editor_actions.cc:222 +#: editor_actions.cc:223 #, fuzzy msgid "Duplicate Region" msgstr "duplicar região" -#: editor_actions.cc:224 +#: editor_actions.cc:225 #, fuzzy msgid "Duplicate Range" msgstr "Duplicar" -#: editor_actions.cc:226 +#: editor_actions.cc:227 msgid "Insert Region" msgstr "Inserir Região" -#: editor_actions.cc:228 +#: editor_actions.cc:229 #, fuzzy msgid "Reverse Region" msgstr "inverter regiões" -#: editor_actions.cc:230 +#: editor_actions.cc:231 #, fuzzy msgid "Normalize Region" msgstr "Normalizar" -#: editor_actions.cc:232 +#: editor_actions.cc:233 #, fuzzy msgid "crop" msgstr "cópia" -#: editor_actions.cc:234 +#: editor_actions.cc:235 #, fuzzy msgid "Insert Chunk" msgstr "Inserir trecho" -#: editor_actions.cc:237 +#: editor_actions.cc:238 #, fuzzy msgid "Split at edit cursor" msgstr "Do início ao cursor de edição" -#: editor_actions.cc:240 +#: editor_actions.cc:241 #, fuzzy msgid "Start Range" msgstr "Separar Intervalo" -#: editor_actions.cc:242 +#: editor_actions.cc:243 msgid "Finish Range" msgstr "" -#: editor_actions.cc:244 +#: editor_actions.cc:245 msgid "Finish add Range" msgstr "" -#: editor_actions.cc:247 +#: editor_actions.cc:248 msgid "Extend Range to End of Region" msgstr "" -#: editor_actions.cc:249 +#: editor_actions.cc:250 #, fuzzy msgid "Extend Range to Start of Region" msgstr "Ir para o início da sessão" -#: editor_actions.cc:252 +#: editor_actions.cc:253 #, fuzzy msgid "Follow Playhead" msgstr "Seguir o cursor de reprodução" -#: editor_actions.cc:260 +#: editor_actions.cc:261 #, fuzzy msgid "Zoom Focus Left" msgstr "Zoom(focagem)" -#: editor_actions.cc:262 +#: editor_actions.cc:263 #, fuzzy msgid "Zoom Focus Right" msgstr "Zoom(focagem)" -#: editor_actions.cc:264 +#: editor_actions.cc:265 #, fuzzy msgid "Zoom Focus Center" msgstr "Zoom(focagem)" -#: editor_actions.cc:266 +#: editor_actions.cc:267 #, fuzzy msgid "Zoom Focus Playhead" msgstr "Zoom(focagem)" -#: editor_actions.cc:268 +#: editor_actions.cc:269 #, fuzzy msgid "Zoom Focus Edit" msgstr "Zoom(focagem)" -#: editor_actions.cc:274 +#: editor_actions.cc:275 msgid "Object Tool" msgstr "" -#: editor_actions.cc:275 +#: editor_actions.cc:276 #, fuzzy msgid "Range Tool" msgstr "Intervalo" -#: editor_actions.cc:276 +#: editor_actions.cc:277 msgid "Gain Tool" msgstr "" -#: editor_actions.cc:277 +#: editor_actions.cc:278 #, fuzzy msgid "Zoom Tool" msgstr "Zoom(-)" -#: editor_actions.cc:278 +#: editor_actions.cc:279 msgid "Timefx Tool" msgstr "" -#: editor_actions.cc:285 +#: editor_actions.cc:286 #, fuzzy msgid "Snap to frame" msgstr "Modo de Ajuste" -#: editor_actions.cc:286 +#: editor_actions.cc:287 #, fuzzy msgid "Snap to cd frame" msgstr "Modo de Ajuste" -#: editor_actions.cc:287 +#: editor_actions.cc:288 #, fuzzy msgid "Snap to SMPTE frame" msgstr "Quadros SMPTE" -#: editor_actions.cc:288 +#: editor_actions.cc:289 #, fuzzy msgid "Snap to SMPTE seconds" msgstr "Segundos SMPTE" -#: editor_actions.cc:289 +#: editor_actions.cc:290 #, fuzzy msgid "Snap to SMPTE minutes" msgstr "Minutos SMPTE" -#: editor_actions.cc:290 +#: editor_actions.cc:291 #, fuzzy msgid "Snap to seconds" msgstr "Segundos" -#: editor_actions.cc:291 +#: editor_actions.cc:292 msgid "Snap to minutes" msgstr "" -#: editor_actions.cc:292 +#: editor_actions.cc:293 #, fuzzy msgid "Snap to thirtyseconds" msgstr "trigésima-segunda (32)" -#: editor_actions.cc:293 +#: editor_actions.cc:294 msgid "Snap to asixteenthbeat" msgstr "" -#: editor_actions.cc:294 +#: editor_actions.cc:295 msgid "Snap to eighths" msgstr "" -#: editor_actions.cc:295 +#: editor_actions.cc:296 msgid "Snap to quarters" msgstr "" -#: editor_actions.cc:296 +#: editor_actions.cc:297 #, fuzzy msgid "Snap to thirds" msgstr "Modo de Ajuste" -#: editor_actions.cc:297 +#: editor_actions.cc:298 #, fuzzy msgid "Snap to beat" msgstr "Modo de Ajuste" -#: editor_actions.cc:298 +#: editor_actions.cc:299 #, fuzzy msgid "Snap to bar" msgstr "Ajustar a" -#: editor_actions.cc:299 +#: editor_actions.cc:300 #, fuzzy msgid "Snap to mark" msgstr "acrescentar marcador de região" -#: editor_actions.cc:300 +#: editor_actions.cc:301 #, fuzzy msgid "Snap to edit cursor" msgstr "Do início ao cursor de edição" -#: editor_actions.cc:301 +#: editor_actions.cc:302 #, fuzzy msgid "Snap to region start" msgstr "Inícios de região" -#: editor_actions.cc:302 +#: editor_actions.cc:303 #, fuzzy msgid "Snap to region end" msgstr "Finais de região" -#: editor_actions.cc:303 +#: editor_actions.cc:304 #, fuzzy msgid "Snap to region sync" msgstr "Sincronismos de região" -#: editor_actions.cc:304 +#: editor_actions.cc:305 #, fuzzy msgid "Snap to region boundary" msgstr "Extremos de região" #. the region list popup menu -#: editor_actions.cc:313 +#: editor_actions.cc:314 #, fuzzy msgid "Sort" msgstr "porta" -#: editor_actions.cc:321 +#: editor_actions.cc:322 msgid "Show all" msgstr "Mostrar tudo" -#: editor_actions.cc:322 +#: editor_actions.cc:323 #, fuzzy msgid "Show automatic regions" msgstr "Mostrar todos as automatizações" -#: editor_actions.cc:324 +#: editor_actions.cc:325 msgid "Ascending" msgstr "Crescente" -#: editor_actions.cc:326 +#: editor_actions.cc:327 msgid "Descending" msgstr "Decrescente" -#: editor_actions.cc:329 +#: editor_actions.cc:330 msgid "By Region Name" msgstr "Por Nome de Região" -#: editor_actions.cc:331 +#: editor_actions.cc:332 msgid "By Region Length" msgstr "Por Tamanho de Região" -#: editor_actions.cc:333 +#: editor_actions.cc:334 msgid "By Region Position" msgstr "Por Posição de Região" -#: editor_actions.cc:335 +#: editor_actions.cc:336 msgid "By Region Timestamp" msgstr "Por Instante de Região" -#: editor_actions.cc:337 +#: editor_actions.cc:338 msgid "By Region Start in File" msgstr "Por Posição Inicial da Região no Ficheiro" -#: editor_actions.cc:339 +#: editor_actions.cc:340 msgid "By Region End in File" msgstr "Por Posição Final da Região no Ficheiro" -#: editor_actions.cc:341 +#: editor_actions.cc:342 msgid "By Source File Name" msgstr "Por Nome do Ficheiro Original" -#: editor_actions.cc:343 +#: editor_actions.cc:344 msgid "By Source File Length" msgstr "Por Tamanho do Ficheiro Original" -#: editor_actions.cc:345 +#: editor_actions.cc:346 msgid "By Source File Creation Date" msgstr "Por Data de Criação do Ficheiro Original" -#: editor_actions.cc:347 +#: editor_actions.cc:348 msgid "By Source Filesystem" msgstr "Por Sistema de Ficheiros Original" #. the next two are duplicate items with different names for use in two different contexts -#: editor_actions.cc:353 +#: editor_actions.cc:354 #, fuzzy msgid "Add External Audio" msgstr "Acrescentar à lista de Regiões Externas" -#: editor_actions.cc:355 +#: editor_actions.cc:356 #, fuzzy msgid "as Region(s)" msgstr "Arrastar regiões" -#: editor_actions.cc:357 +#: editor_actions.cc:358 #, fuzzy msgid "as Tracks" msgstr "Faixas" -#: editor_actions.cc:359 +#: editor_actions.cc:360 #, fuzzy msgid "to Tracks" msgstr "Faixas" -#: editor_actions.cc:362 +#: editor_actions.cc:363 #, fuzzy msgid "Show Waveforms" msgstr "Mostrar formas de onda" -#: editor_actions.cc:363 +#: editor_actions.cc:364 #, fuzzy msgid "Show Waveforms While Recording" msgstr "Mostrar formas de onda enquanto grava" -#: editor_actions.cc:364 +#: editor_actions.cc:365 #, fuzzy msgid "Show Measures" msgstr "Mostrar linhas de tempo" -#: editor_actions.cc:377 editor_actions.cc:384 +#: editor_actions.cc:378 editor_actions.cc:385 msgid "Medium" msgstr "" -#: editor_actions.cc:379 +#: editor_actions.cc:380 #, fuzzy msgid "Faster" msgstr "Rápido" -#: editor_actions.cc:385 +#: editor_actions.cc:386 msgid "Long" msgstr "" -#: editor_actions.cc:389 +#: editor_actions.cc:390 #, fuzzy msgid "Later is Higher" msgstr "Descer a região em um nível" -#: editor_actions.cc:390 +#: editor_actions.cc:391 #, fuzzy msgid "Most Recently Moved/Added is Higher" msgstr "Descer a região em um nível" -#: editor_actions.cc:391 +#: editor_actions.cc:392 #, fuzzy msgid "Most Recently Added is Higher" msgstr "Descer a região em um nível" @@ -3468,39 +3460,39 @@ msgstr "" msgid "Add existing audio to session" msgstr "Mostrar automatizações existentes" -#: editor_audio_import.cc:143 +#: editor_audio_import.cc:142 msgid "ardour: importing %1" msgstr "ardour: em importação %1" -#: editor_audio_import.cc:147 +#: editor_audio_import.cc:146 msgid "Cancel Import" msgstr "Cancelar Importação" -#: editor_audio_import.cc:225 +#: editor_audio_import.cc:224 #, fuzzy msgid "Editor: cannot open file \"%1\", (%2)" msgstr "Editor: não foi possível abrir o ficheiro \"%1\" (%2)" -#: editor_audio_import.cc:233 +#: editor_audio_import.cc:232 #, fuzzy msgid "Cancel entire import" msgstr "Cancelar Importação" -#: editor_audio_import.cc:234 +#: editor_audio_import.cc:233 #, fuzzy msgid "Don't embed it" msgstr "Não %1" -#: editor_audio_import.cc:235 +#: editor_audio_import.cc:234 msgid "Embed all without questions" msgstr "" -#: editor_audio_import.cc:240 +#: editor_audio_import.cc:239 #, fuzzy msgid "Embed it anyway" msgstr "%s de qualquer forma" -#: editor_audio_import.cc:243 +#: editor_audio_import.cc:242 #, fuzzy msgid "" "%1\n" @@ -3508,74 +3500,62 @@ msgid "" msgstr "" "A frequência de amostragem deste ficheiro audio não é igual à de sessão" -#: editor_audio_import.cc:276 +#: editor_audio_import.cc:275 msgid "could not open %1" msgstr "não foi possível abrir %1" -#: editor_audio_import.cc:321 +#: editor_audio_import.cc:320 msgid "insert sndfile" msgstr "inserir ficheiro audio" #. stuff for the verbose canvas cursor -#: editor_canvas.cc:117 +#: editor_canvas.cc:118 msgid "VerboseCanvasCursor" msgstr "" -#: editor_canvas.cc:285 -msgid "Start a new session\n" -msgstr "Iniciar uma nova sessão\n" - -#: editor_canvas.cc:285 -msgid "via Session menu" -msgstr "via menu de Sessão" - -#: editor_canvas.cc:288 -msgid "FirstActionMessage" -msgstr "" - -#: editor_edit_groups.cc:52 mixer_ui.cc:732 +#: editor_edit_groups.cc:53 mixer_ui.cc:736 #, fuzzy msgid "Activate All" msgstr "Activar" -#: editor_edit_groups.cc:53 mixer_ui.cc:733 +#: editor_edit_groups.cc:54 mixer_ui.cc:737 #, fuzzy msgid "Disable All" msgstr "Desligar" -#: editor_edit_groups.cc:55 mixer_ui.cc:735 +#: editor_edit_groups.cc:56 mixer_ui.cc:739 #, fuzzy msgid "Add group" msgstr "Sem grupo" -#: editor_edit_groups.cc:225 mixer_ui.cc:964 +#: editor_edit_groups.cc:229 mixer_ui.cc:970 #, fuzzy msgid "unnamed" msgstr "Renomear" -#: editor_edit_groups.cc:252 mixer_ui.cc:830 +#: editor_edit_groups.cc:258 mixer_ui.cc:834 msgid "-all-" msgstr "-tudo-" -#: editor_export_audio.cc:64 +#: editor_export_audio.cc:65 msgid "" "There is no selection to export.\n" "\n" "Select a selection using the range mouse mode" msgstr "" -#: editor_export_audio.cc:109 +#: editor_export_audio.cc:110 msgid "" "There are no ranges to export.\n" "\n" "Create 1 or more ranges by dragging the mouse in the range bar" msgstr "" -#: editor_imageframe.cc:624 editor_imageframe.cc:654 +#: editor_imageframe.cc:625 editor_imageframe.cc:655 msgid "programming error: no ImageFrameView selected" msgstr "" -#: editor_imageframe.cc:847 editor_imageframe.cc:869 +#: editor_imageframe.cc:848 editor_imageframe.cc:870 msgid "programming error: no MarkerView selected" msgstr "" @@ -3584,140 +3564,140 @@ msgstr "" msgid "mute region" msgstr "emudecer esta região" -#: editor_keys.cc:45 +#: editor_keys.cc:46 #, fuzzy msgid "keyboard selection" msgstr "extender selecção" -#: editor_markers.cc:291 editor_ops.cc:1227 editor_ops.cc:1240 -#: editor_ops.cc:1258 location_ui.cc:773 +#: editor_markers.cc:292 editor_ops.cc:1290 editor_ops.cc:1303 +#: editor_ops.cc:1321 location_ui.cc:774 msgid "add marker" msgstr "adicionar marcador" -#: editor_markers.cc:306 editor_markers.cc:379 editor_markers.cc:551 -#: editor_markers.cc:569 editor_markers.cc:588 editor_markers.cc:607 -#: editor_markers.cc:637 editor_markers.cc:665 editor_markers.cc:693 -#: editor_markers.cc:731 editor_markers.cc:758 editor_markers.cc:781 -#: editor_markers.cc:800 editor_mouse.cc:1994 editor_mouse.cc:4237 +#: editor_markers.cc:307 editor_markers.cc:380 editor_markers.cc:552 +#: editor_markers.cc:570 editor_markers.cc:589 editor_markers.cc:608 +#: editor_markers.cc:638 editor_markers.cc:666 editor_markers.cc:694 +#: editor_markers.cc:732 editor_markers.cc:759 editor_markers.cc:782 +#: editor_markers.cc:801 editor_mouse.cc:2015 editor_mouse.cc:4275 msgid "programming error: marker canvas item has no marker object pointer!" msgstr "" -#: editor_markers.cc:330 location_ui.cc:655 +#: editor_markers.cc:331 location_ui.cc:656 msgid "remove marker" msgstr "remover marcador" -#: editor_markers.cc:457 +#: editor_markers.cc:458 #, fuzzy msgid "Locate to Mark" msgstr "Localizar" -#: editor_markers.cc:458 +#: editor_markers.cc:459 #, fuzzy msgid "Play from Mark" msgstr "Reproduzir desde o início" -#: editor_markers.cc:459 +#: editor_markers.cc:460 #, fuzzy msgid "Set Mark from Playhead" msgstr "Desde cursor de reprodução" -#: editor_markers.cc:463 +#: editor_markers.cc:464 #, fuzzy msgid "Rename Mark" msgstr "Renomear" -#: editor_markers.cc:464 +#: editor_markers.cc:465 #, fuzzy msgid "Hide Mark" msgstr "retocar faixa" -#: editor_markers.cc:465 +#: editor_markers.cc:466 #, fuzzy msgid "Remove Mark" msgstr "remover marcador" -#: editor_markers.cc:478 editor_markers.cc:534 +#: editor_markers.cc:479 editor_markers.cc:535 #, fuzzy msgid "Locate to Range Mark" msgstr "Localizações" -#: editor_markers.cc:479 editor_markers.cc:535 +#: editor_markers.cc:480 editor_markers.cc:536 #, fuzzy msgid "Play from Range Mark" msgstr "Reproduzir intervalo cíclico" -#: editor_markers.cc:480 +#: editor_markers.cc:481 #, fuzzy msgid "Loop Range" msgstr "Intervalo cíclico" -#: editor_markers.cc:481 editor_markers.cc:536 +#: editor_markers.cc:482 editor_markers.cc:537 #, fuzzy msgid "Set Range Mark from Playhead" msgstr "Desde cursor de reprodução" -#: editor_markers.cc:482 editor_markers.cc:537 +#: editor_markers.cc:483 editor_markers.cc:538 #, fuzzy msgid "Set Range from Range Selection" msgstr "selecção de intervalo" -#: editor_markers.cc:486 +#: editor_markers.cc:487 #, fuzzy msgid "Rename Range" msgstr "Renomear" -#: editor_markers.cc:487 editor_markers.cc:539 +#: editor_markers.cc:488 editor_markers.cc:540 #, fuzzy msgid "Hide Range" msgstr "Adicionar Novo Intervalo" -#: editor_markers.cc:488 +#: editor_markers.cc:489 #, fuzzy msgid "Remove Range" msgstr "Remover Campo" -#: editor_markers.cc:492 editor_markers.cc:541 +#: editor_markers.cc:493 editor_markers.cc:542 #, fuzzy msgid "Separate Regions in Range" msgstr "Nova região desde a selecção" -#: editor_markers.cc:493 editor_markers.cc:542 +#: editor_markers.cc:494 editor_markers.cc:543 #, fuzzy msgid "Select All in Range" msgstr "Seleccionar tudo na faixa" -#: editor_markers.cc:519 +#: editor_markers.cc:520 msgid "Set Loop Range" msgstr "Seleccionar Intervalo Cíclico" -#: editor_markers.cc:520 +#: editor_markers.cc:521 msgid "Set Punch Range" msgstr "Seleccionar Intervalo de Inserção" -#: editor_markers.cc:814 +#: editor_markers.cc:815 #, fuzzy msgid "New Name:" msgstr "novo nome: " -#: editor_markers.cc:817 +#: editor_markers.cc:818 msgid "ardour: rename mark" msgstr "ardour: renomear marca" -#: editor_markers.cc:819 +#: editor_markers.cc:820 #, fuzzy msgid "ardour: rename range" msgstr "ardour: renomear região" -#: editor_markers.cc:839 +#: editor_markers.cc:840 #, fuzzy msgid "rename marker" msgstr "remover marcador" -#: editor_markers.cc:864 +#: editor_markers.cc:865 msgid "set loop range" msgstr "seleccionar intervalo cíclico" -#: editor_markers.cc:890 +#: editor_markers.cc:891 msgid "set punch range" msgstr "seleccionar intervalo de inserção" @@ -3725,385 +3705,391 @@ msgstr "seleccionar intervalo de inserção" msgid "Editor::event_frame() used on unhandled event type %1" msgstr "" -#: editor_mouse.cc:1589 +#: editor_mouse.cc:313 +#, fuzzy +msgid "select on click" +msgstr "Usar como metrónomo" + +#: editor_mouse.cc:1590 msgid "programming error: start_grab called without drag item" msgstr "" -#: editor_mouse.cc:1793 +#: editor_mouse.cc:1814 msgid "change fade in length" msgstr "alterar duração de evanescimento" -#: editor_mouse.cc:1811 +#: editor_mouse.cc:1832 msgid "programming error: fade out canvas item has no regionview data pointer!" msgstr "" -#: editor_mouse.cc:1885 +#: editor_mouse.cc:1906 msgid "change fade out length" msgstr "alterar duração desvanecimento" -#: editor_mouse.cc:1904 +#: editor_mouse.cc:1925 msgid "programming error: cursor canvas item has no cursor data pointer!" msgstr "" -#: editor_mouse.cc:2119 +#: editor_mouse.cc:2142 #, fuzzy msgid "move marker" msgstr "remover marcador" -#: editor_mouse.cc:2142 editor_mouse.cc:2173 editor_tempodisplay.cc:461 +#: editor_mouse.cc:2165 editor_mouse.cc:2196 editor_tempodisplay.cc:459 msgid "" "programming error: meter marker canvas item has no marker object pointer!" msgstr "" -#: editor_mouse.cc:2241 +#: editor_mouse.cc:2264 #, fuzzy msgid "copy meter mark" msgstr "remover marcador métrico" -#: editor_mouse.cc:2251 +#: editor_mouse.cc:2274 msgid "move meter mark" msgstr "remover marcador métrico" -#: editor_mouse.cc:2266 editor_mouse.cc:2299 editor_tempodisplay.cc:327 -#: editor_tempodisplay.cc:411 editor_tempodisplay.cc:430 +#: editor_mouse.cc:2289 editor_mouse.cc:2322 editor_tempodisplay.cc:331 +#: editor_tempodisplay.cc:409 editor_tempodisplay.cc:428 msgid "" "programming error: tempo marker canvas item has no marker object pointer!" msgstr "" -#: editor_mouse.cc:2271 editor_mouse.cc:2304 editor_tempodisplay.cc:332 -#: editor_tempodisplay.cc:416 +#: editor_mouse.cc:2294 editor_mouse.cc:2327 editor_tempodisplay.cc:336 +#: editor_tempodisplay.cc:414 msgid "programming error: marker for tempo is not a tempo marker!" msgstr "" -#: editor_mouse.cc:2371 +#: editor_mouse.cc:2394 #, fuzzy msgid "copy tempo mark" msgstr "remover marcador de tempo" -#: editor_mouse.cc:2381 +#: editor_mouse.cc:2404 msgid "move tempo mark" msgstr "remover marcador de tempo" -#: editor_mouse.cc:2395 editor_mouse.cc:2414 editor_mouse.cc:2427 +#: editor_mouse.cc:2418 editor_mouse.cc:2437 editor_mouse.cc:2450 msgid "" "programming error: control point canvas item has no control point object " "pointer!" msgstr "" -#: editor_mouse.cc:2525 +#: editor_mouse.cc:2555 msgid "programming error: line canvas item has no line pointer!" msgstr "" -#: editor_mouse.cc:2634 +#: editor_mouse.cc:2664 #, fuzzy msgid "move region(s)" msgstr "remover região" -#. this is committed in the grab finished callback. -#: editor_mouse.cc:2646 -msgid "Drag region copy" -msgstr "Arraster cópia de região" - -#: editor_mouse.cc:2758 +#: editor_mouse.cc:2727 #, fuzzy msgid "Drag region brush" msgstr "Arrastar regiões" +#. don't copy again +#. this is committed in the grab finished callback. +#: editor_mouse.cc:2751 +msgid "Drag region copy" +msgstr "Arraster cópia de região" + #. A selection grab currently creates two undo/redo operations, one for #. creating the new region and another for moving it. #. -#: editor_mouse.cc:3574 +#: editor_mouse.cc:3609 msgid "selection grab" msgstr "selecção" -#: editor_mouse.cc:3615 +#: editor_mouse.cc:3650 #, fuzzy msgid "cancel selection" msgstr "selecção de intervalo" -#: editor_mouse.cc:3722 +#: editor_mouse.cc:3760 msgid "range selection" msgstr "selecção de intervalo" -#: editor_mouse.cc:3738 +#: editor_mouse.cc:3776 msgid "trim selection start" msgstr "recortar início da selecção" -#: editor_mouse.cc:3754 +#: editor_mouse.cc:3792 msgid "trim selection end" msgstr "recortar final da selecção" -#: editor_mouse.cc:3771 +#: editor_mouse.cc:3809 msgid "move selection" msgstr "mover selecção" -#: editor_mouse.cc:4157 +#: editor_mouse.cc:4195 msgid "Start point trim" msgstr "Ponto inicial de recorte" -#: editor_mouse.cc:4185 +#: editor_mouse.cc:4223 msgid "End point trim" msgstr "Ponto final de recorte" -#: editor_mouse.cc:4224 +#: editor_mouse.cc:4262 msgid "trimmed region" msgstr "região recortada" -#: editor_mouse.cc:4363 +#: editor_mouse.cc:4400 msgid "new range marker" msgstr "novo marcador de região" -#: editor_mouse.cc:4578 +#: editor_mouse.cc:4642 msgid "select regions" msgstr "seleccionar regiões" -#: editor_mouse.cc:4607 +#: editor_mouse.cc:4671 msgid "Name for region:" msgstr "Nome para a região:" -#: editor_mouse.cc:4671 +#: editor_mouse.cc:4735 msgid "timestretch" msgstr "alongamento temporal" -#: editor_ops.cc:132 +#: editor_ops.cc:195 msgid "split" msgstr "separar" -#: editor_ops.cc:168 +#: editor_ops.cc:231 msgid "remove region" msgstr "remover região" -#: editor_ops.cc:187 +#: editor_ops.cc:250 msgid "" " This is destructive, will possibly delete audio files\n" "It cannot be undone\n" "Do you really want to destroy %1 ?" msgstr "" -#: editor_ops.cc:191 +#: editor_ops.cc:254 #, fuzzy msgid "these regions" msgstr "inverter regiões" -#: editor_ops.cc:191 +#: editor_ops.cc:254 #, fuzzy msgid "this region" msgstr "emudecer esta região" -#: editor_ops.cc:193 editor_ops.cc:3229 route_ui.cc:700 -#: visual_time_axis.cc:277 +#: editor_ops.cc:256 editor_ops.cc:3318 route_ui.cc:707 +#: visual_time_axis.cc:278 msgid "No, do nothing." msgstr "Não, não fazer nada." -#: editor_ops.cc:196 +#: editor_ops.cc:259 #, fuzzy msgid "Yes, destroy them." msgstr "Sim, elimine-se." -#: editor_ops.cc:198 editor_ops.cc:3230 +#: editor_ops.cc:261 editor_ops.cc:3319 msgid "Yes, destroy it." msgstr "Sim, elimine-se." -#: editor_ops.cc:289 editor_ops.cc:317 +#: editor_ops.cc:352 editor_ops.cc:380 msgid "extend selection" msgstr "extender selecção" -#: editor_ops.cc:333 editor_ops.cc:367 editor_ops.cc:411 editor_ops.cc:437 +#: editor_ops.cc:396 editor_ops.cc:430 editor_ops.cc:474 editor_ops.cc:500 msgid "nudge forward" msgstr "retocar p/frente" -#: editor_ops.cc:501 +#: editor_ops.cc:564 msgid "build_region_boundary_cache called with snap_type = %1" msgstr "" -#: editor_ops.cc:1354 +#: editor_ops.cc:1420 #, fuzzy msgid "select all within" msgstr "Seleccionar tudo" -#: editor_ops.cc:1380 +#: editor_ops.cc:1452 #, fuzzy msgid "set selection from region" msgstr "selecção de intervalo" -#: editor_ops.cc:1413 +#: editor_ops.cc:1485 #, fuzzy msgid "set selection from range" msgstr "selecção de intervalo" -#: editor_ops.cc:1443 +#: editor_ops.cc:1515 #, fuzzy msgid "select all from range" msgstr "seleccionar zoom" -#: editor_ops.cc:1465 +#: editor_ops.cc:1537 #, fuzzy msgid "select all from punch" msgstr "Seleccionar tudo" -#: editor_ops.cc:1487 +#: editor_ops.cc:1559 #, fuzzy msgid "select all from loop" msgstr "Seleccionar tudo" -#: editor_ops.cc:1501 +#: editor_ops.cc:1573 #, fuzzy msgid "select all after cursor" msgstr "Do início ao cursor de edição" -#: editor_ops.cc:1506 +#: editor_ops.cc:1578 #, fuzzy msgid "select all before cursor" msgstr "sincronizar pelo cursor de edição" -#: editor_ops.cc:1536 +#: editor_ops.cc:1608 #, fuzzy msgid "select all between cursors" msgstr "sincronizar pelo cursor de edição" -#: editor_ops.cc:1667 +#: editor_ops.cc:1739 msgid "clear markers" msgstr "apagar marcadores" -#: editor_ops.cc:1679 +#: editor_ops.cc:1751 msgid "clear ranges" msgstr "apagar intervalos" -#: editor_ops.cc:1698 +#: editor_ops.cc:1770 msgid "clear locations" msgstr "apagar localizações" -#: editor_ops.cc:1748 +#: editor_ops.cc:1820 msgid "insert dragged region" msgstr "inserir região arrastada" -#: editor_ops.cc:1784 +#: editor_ops.cc:1856 msgid "insert region" msgstr "inserir região" -#: editor_ops.cc:1975 io_selector.cc:57 io_selector.cc:791 +#: editor_ops.cc:2047 io_selector.cc:58 io_selector.cc:792 msgid "OK" msgstr "" -#: editor_ops.cc:1982 +#: editor_ops.cc:2054 msgid "ardour: rename region" msgstr "ardour: renomear região" -#: editor_ops.cc:2205 editor_ops.cc:2254 +#: editor_ops.cc:2277 editor_ops.cc:2326 #, fuzzy msgid "separate" msgstr "separar" -#: editor_ops.cc:2316 +#: editor_ops.cc:2388 msgid "trim to selection" msgstr "recortar pela selecção" -#: editor_ops.cc:2356 +#: editor_ops.cc:2428 msgid "region fill" msgstr "preencher região" -#: editor_ops.cc:2415 +#: editor_ops.cc:2487 msgid "fill selection" msgstr "preencher selecção" -#: editor_ops.cc:2436 +#: editor_ops.cc:2508 msgid "Programming error. that region doesn't cover that position" msgstr "" -#: editor_ops.cc:2439 +#: editor_ops.cc:2511 #, fuzzy msgid "set region sync position" msgstr "Regiões/posição" -#: editor_ops.cc:2454 +#: editor_ops.cc:2526 msgid "Place the edit cursor at the desired sync point" msgstr "Coloque o cursor de edição sobre o ponto de sincronia desejado" -#: editor_ops.cc:2459 +#: editor_ops.cc:2531 #, fuzzy msgid "set sync from edit cursor" msgstr "sincronizar pelo cursor de edição" -#: editor_ops.cc:2471 +#: editor_ops.cc:2543 msgid "remove sync" msgstr "remover sincronismo" -#: editor_ops.cc:2485 +#: editor_ops.cc:2557 msgid "naturalize" msgstr "naturalizar" -#: editor_ops.cc:2549 +#: editor_ops.cc:2621 msgid "align selection (relative)" msgstr "alinhar selecção (relativamente)" -#: editor_ops.cc:2577 +#: editor_ops.cc:2649 msgid "align selection" msgstr "alinhar selecção" -#: editor_ops.cc:2589 +#: editor_ops.cc:2661 msgid "align region" msgstr "alinhar região" -#: editor_ops.cc:2636 editor_ops.cc:2661 +#: editor_ops.cc:2708 editor_ops.cc:2733 msgid "trim to edit" msgstr "recortar para edição" -#: editor_ops.cc:2712 +#: editor_ops.cc:2784 #, fuzzy msgid "ardour: freeze" msgstr "ardour: renomear região" -#: editor_ops.cc:2717 +#: editor_ops.cc:2789 #, fuzzy msgid "Cancel Freeze" msgstr "Cancelar" -#: editor_ops.cc:2754 +#: editor_ops.cc:2826 msgid "bounce range" msgstr "intervalo de rebatimento" -#: editor_ops.cc:2807 +#: editor_ops.cc:2879 msgid "cut" msgstr "corte" -#: editor_ops.cc:2810 +#: editor_ops.cc:2882 msgid "copy" msgstr "cópia" -#: editor_ops.cc:2823 +#: editor_ops.cc:2895 msgid " objects" msgstr " objectos" -#: editor_ops.cc:2849 +#: editor_ops.cc:2921 msgid " range" msgstr " intervalo" -#: editor_ops.cc:3006 +#: editor_ops.cc:3078 msgid "paste" msgstr "colar" -#: editor_ops.cc:3044 +#: editor_ops.cc:3116 msgid "paste chunk" msgstr "colar trecho" #. clear (below) will clear the argument list -#: editor_ops.cc:3085 +#: editor_ops.cc:3157 msgid "duplicate region" msgstr "duplicar região" -#: editor_ops.cc:3130 +#: editor_ops.cc:3202 msgid "duplicate selection" msgstr "duplicar selecção" -#: editor_ops.cc:3170 +#: editor_ops.cc:3259 msgid "clear playlist" msgstr "limpar lista de reprodução" -#: editor_ops.cc:3199 +#: editor_ops.cc:3288 msgid "nudge track" msgstr "retocar faixa" -#: editor_ops.cc:3226 +#: editor_ops.cc:3315 msgid "" "Do you really want to destroy the last capture?\n" "(This is destructive and cannot be undone)" @@ -4111,161 +4097,158 @@ msgstr "" "Deseja realmente eliminar a última captura?\n" "(esta operação é destrutiva e não pode ser desfeita)" -#: editor_ops.cc:3254 +#: editor_ops.cc:3343 msgid "normalize" msgstr "normalizar" -#: editor_ops.cc:3301 +#: editor_ops.cc:3390 msgid "reverse regions" msgstr "inverter regiões" -#: editor_region_list.cc:93 editor_region_list.cc:98 editor_region_list.cc:101 -#: location_ui.cc:55 +#: editor_region_list.cc:98 editor_region_list.cc:103 +#: editor_region_list.cc:106 location_ui.cc:56 msgid "Hidden" msgstr "Esconder" #. added a new fresh one at the end -#: editor_route_list.cc:101 editor_route_list.cc:102 editor_route_list.cc:246 +#: editor_route_list.cc:102 editor_route_list.cc:103 editor_route_list.cc:247 msgid "editor" msgstr "" -#: editor_route_list.cc:309 mixer_ui.cc:695 +#: editor_route_list.cc:310 mixer_ui.cc:699 msgid "Show All" msgstr "Mostrar tudo" -#: editor_route_list.cc:310 mixer_ui.cc:696 +#: editor_route_list.cc:311 mixer_ui.cc:700 msgid "Hide All" msgstr "Ocultar tudo" -#: editor_route_list.cc:311 mixer_ui.cc:697 +#: editor_route_list.cc:312 mixer_ui.cc:701 #, fuzzy msgid "Show All Audio Tracks" msgstr "Mostrar todos os barramentos audio" -#: editor_route_list.cc:312 mixer_ui.cc:698 +#: editor_route_list.cc:313 mixer_ui.cc:702 #, fuzzy msgid "Hide All Audio Tracks" msgstr "Esconder todos os barramentos audio" -#: editor_route_list.cc:313 mixer_ui.cc:699 +#: editor_route_list.cc:314 mixer_ui.cc:703 #, fuzzy msgid "Show All Audio Busses" msgstr "Mostrar todos os barramentos audio" -#: editor_route_list.cc:314 mixer_ui.cc:700 +#: editor_route_list.cc:315 mixer_ui.cc:704 #, fuzzy msgid "Hide All Audio Busses" msgstr "Esconder todos os barramentos audio" -#: editor_rulers.cc:311 +#: editor_rulers.cc:312 msgid "New location marker" msgstr "Novo marcador de localização" -#: editor_rulers.cc:312 +#: editor_rulers.cc:313 msgid "Clear all locations" msgstr "Apagar todas as localizações" #. ruler_items.push_back (MenuElem (_("New Range"))); -#: editor_rulers.cc:317 +#: editor_rulers.cc:318 msgid "Clear all ranges" msgstr "Apagar todos os intervalos" -#: editor_rulers.cc:326 +#: editor_rulers.cc:327 msgid "New Tempo" msgstr "Novo Tempo" -#: editor_rulers.cc:327 +#: editor_rulers.cc:328 msgid "Clear tempo" msgstr "Apagar tempo" -#: editor_rulers.cc:332 +#: editor_rulers.cc:333 msgid "New Meter" msgstr "Novo VUímetro" -#: editor_rulers.cc:333 +#: editor_rulers.cc:334 msgid "Clear meter" msgstr "Apagar VUímetro" -#: editor_rulers.cc:341 +#: editor_rulers.cc:342 msgid "Min:Secs" msgstr "Min:Segs" -#: editor_selection_list.cc:110 +#: editor_selection_list.cc:108 #, fuzzy msgid "Name for Chunk:" msgstr "Nome para o trecho:" -#: editor_selection_list.cc:113 +#: editor_selection_list.cc:111 #, fuzzy msgid "Create Chunk" msgstr "Criar trecho" -#: editor_selection_list.cc:113 +#: editor_selection_list.cc:111 msgid "Forget it" msgstr "Esquecer" -#: editor_tempodisplay.cc:249 editor_tempodisplay.cc:289 +#: editor_tempodisplay.cc:253 editor_tempodisplay.cc:293 msgid "add" msgstr "acrescentar" -#: editor_tempodisplay.cc:271 +#: editor_tempodisplay.cc:275 #, fuzzy msgid "add tempo mark" msgstr "acrescentar marcador de região" -#: editor_tempodisplay.cc:311 +#: editor_tempodisplay.cc:315 #, fuzzy msgid "add meter mark" msgstr "acrescentar marcador métrico" -#: editor_tempodisplay.cc:344 editor_tempodisplay.cc:375 +#: editor_tempodisplay.cc:348 editor_tempodisplay.cc:376 msgid "done" msgstr "pronto" -#: editor_tempodisplay.cc:365 editor_tempodisplay.cc:396 +#: editor_tempodisplay.cc:366 editor_tempodisplay.cc:394 msgid "replace tempo mark" msgstr "substituir marcador de tempo" -#: editor_tempodisplay.cc:435 editor_tempodisplay.cc:466 +#: editor_tempodisplay.cc:433 editor_tempodisplay.cc:464 msgid "programming error: marker for meter is not a meter marker!" msgstr "" -#: editor_tempodisplay.cc:445 editor_tempodisplay.cc:478 +#: editor_tempodisplay.cc:443 editor_tempodisplay.cc:476 msgid "remove tempo mark" msgstr "remover marcador de tempo" -#: editor_timefx.cc:50 +#: editor_timefx.cc:51 msgid "Quick but Ugly" msgstr "Rápido mas Feio" -#: editor_timefx.cc:51 +#: editor_timefx.cc:52 msgid "Skip Anti-aliasing" msgstr "Ignorar Anti-aliasing" -#: editor_timefx.cc:53 -msgid "Stretch/Shrink it" -msgstr "Alongar/Estreitar" - -#: editor_timefx.cc:57 +#: editor_timefx.cc:56 msgid "ardour: timestretch" msgstr "ardour: alongamento temporal" -#: editor_timefx.cc:58 +#: editor_timefx.cc:57 msgid "TimeStretchDialog" msgstr "" -#: editor_timefx.cc:80 editor_timefx.cc:81 editor_timefx.cc:82 -#: editor_timefx.cc:83 +#: editor_timefx.cc:70 +msgid "Stretch/Shrink it" +msgstr "Alongar/Estreitar" + +#: editor_timefx.cc:73 editor_timefx.cc:74 msgid "TimeStretchButton" msgstr "" -#: editor_timefx.cc:84 +#: editor_timefx.cc:75 msgid "TimeStretchProgress" msgstr "" -#. GTK2FIX -#. current_timestretch->close (); -#: editor_timefx.cc:153 +#: editor_timefx.cc:139 msgid "timestretch cannot be started - thread creation error" msgstr "" @@ -4399,7 +4382,7 @@ msgstr "" msgid "Export to File" msgstr "Exportar para CD" -#: export_dialog.cc:113 option_editor.cc:82 option_editor.cc:83 +#: export_dialog.cc:113 option_editor.cc:83 option_editor.cc:84 msgid "Browse" msgstr "Pesquisar" @@ -4415,7 +4398,8 @@ msgstr "ardour: exportar" msgid "ardour_export" msgstr "" -#: export_dialog.cc:139 export_dialog.cc:155 +#: export_dialog.cc:139 export_dialog.cc:155 mixer_strip.cc:124 +#: mixer_strip.cc:767 msgid "Output" msgstr "Saída" @@ -4451,145 +4435,75 @@ msgstr "" msgid "File already exists, do you want to overwrite it?" msgstr "" -#: export_dialog.cc:1159 export_range_markers_dialog.cc:154 +#: export_dialog.cc:1159 export_range_markers_dialog.cc:153 msgid "Cannot write file in: " msgstr "" #. warning dialog -#: export_range_markers_dialog.cc:136 +#: export_range_markers_dialog.cc:135 msgid "Please enter a valid target directory." msgstr "" -#: export_range_markers_dialog.cc:144 +#: export_range_markers_dialog.cc:143 msgid "" "Please select an existing target directory. Files\n" "are not allowed!" msgstr "" -#: gain_automation_time_axis.cc:61 +#: gain_automation_time_axis.cc:62 #, fuzzy msgid "add gain automation event" msgstr "acrescentar evento de automatização a " -#: gain_meter.cc:66 +#: gain_meter.cc:67 msgid "cannot find images for fader slider" msgstr "" -#: gain_meter.cc:73 +#: gain_meter.cc:74 msgid "cannot find images for fader rail" msgstr "" -#: gain_meter.cc:88 -msgid "dbFS" -msgstr "" - -#: gain_meter.cc:89 gain_meter.cc:143 gain_meter.cc:704 -msgid "pre" -msgstr "" - -#: gain_meter.cc:139 gain_meter.cc:700 -#, fuzzy -msgid "input" -msgstr "%1 entrada" - -#: gain_meter.cc:147 gain_meter.cc:708 -#, fuzzy -msgid "post" -msgstr "porta" - -#. TRANSLATORS: this string should be longest of the strings -#. used to describe meter points. In english, its "input". -#. -#: gain_meter.cc:155 -msgid "tupni" -msgstr "" - -#: gain_meter.cc:174 gain_meter.cc:458 gain_meter.cc:480 gain_meter.cc:525 +#: gain_meter.cc:130 gain_meter.cc:339 gain_meter.cc:494 gain_meter.cc:539 #, fuzzy msgid "-inf" msgstr "entrada" -#: glade/new_session_dialog.glade.h:1 +#: gain_meter.cc:140 #, fuzzy -msgid "Advanced" -msgstr "Avançado..." +msgid "Fader automation mode" +msgstr "modo de automatização de panorâmica" -#: glade/new_session_dialog.glade.h:2 -msgid "Input" +#: gain_meter.cc:141 +#, fuzzy +msgid "Fader automation type" +msgstr "Tipo de automatização de panorâmica" + +#. XXX it might different in different languages +#: gain_meter.cc:182 gain_meter.cc:817 panner_ui.cc:99 panner_ui.cc:807 +msgid "Abs" msgstr "" -#: glade/new_session_dialog.glade.h:3 +#: gain_meter.cc:472 #, fuzzy -msgid "Output" -msgstr "Saída" +msgid "-Inf" +msgstr "entrada" -#: glade/new_session_dialog.glade.h:4 +#: gain_meter.cc:781 mixer_strip.cc:770 panner_ui.cc:771 #, fuzzy -msgid "Automatically connect inputs" -msgstr "ligar entradas físicas automaticamente" +msgid "O" +msgstr "OU" -#: glade/new_session_dialog.glade.h:5 -#, fuzzy -msgid "Automatically connect outputs" -msgstr "ligar saídas manualmente" - -#: glade/new_session_dialog.glade.h:6 -#, fuzzy -msgid "Channel Count" -msgstr "Cancelar Importação" - -#: glade/new_session_dialog.glade.h:7 -msgid "Connect to Master Bus" +#: gain_meter.cc:784 panner_ui.cc:774 +msgid "P" msgstr "" -#: glade/new_session_dialog.glade.h:8 -msgid "Connect to physical outputs" +#: gain_meter.cc:787 panner_ui.cc:777 +msgid "T" msgstr "" -#: glade/new_session_dialog.glade.h:9 -#, fuzzy -msgid "Create Control Bus" -msgstr "Saídas de Controlo" - -#: glade/new_session_dialog.glade.h:10 -#, fuzzy -msgid "Create Master Bus" -msgstr "usar saídas principais" - -#: glade/new_session_dialog.glade.h:11 -#, fuzzy -msgid "New Session" -msgstr "Sessão" - -#: glade/new_session_dialog.glade.h:12 -#, fuzzy -msgid "Open Recent Session" -msgstr "abrir sessão" - -#: glade/new_session_dialog.glade.h:13 -#, fuzzy -msgid "Open Session" -msgstr "abrir sessão" - -#: glade/new_session_dialog.glade.h:14 -#, fuzzy -msgid "Port limit" -msgstr "Esquecer" - -#: glade/new_session_dialog.glade.h:15 -#, fuzzy -msgid "Select a File" -msgstr "Seleccionar tudo" - -#: glade/new_session_dialog.glade.h:16 -#, fuzzy -msgid "Select a Session" -msgstr "seleccionar regiões" - -#: glade/new_session_dialog.glade.h:17 -#, fuzzy -msgid "Track/Bus connection options" -msgstr "Faixas/Barramentos" +#: gain_meter.cc:790 panner_ui.cc:780 +msgid "W" +msgstr "" #: gtk-custom-ruler.c:126 #, fuzzy @@ -4636,237 +4550,237 @@ msgid "Draw current ruler position" msgstr "" #. end-of-file, other end closed or shutdown? -#: imageframe_socket_handler.cc:126 +#: imageframe_socket_handler.cc:127 msgid "Image Compositor Socket has been shutdown/closed" msgstr "O ligação ao Compositor de Imagem foi desligada/fechada" -#: imageframe_time_axis.cc:287 +#: imageframe_time_axis.cc:286 #, fuzzy msgid "0.5 seconds" msgstr "Segundos" -#: imageframe_time_axis.cc:288 marker_time_axis.cc:241 +#: imageframe_time_axis.cc:287 marker_time_axis.cc:242 #, fuzzy msgid "1 seconds" msgstr "Segundos" -#: imageframe_time_axis.cc:289 marker_time_axis.cc:242 +#: imageframe_time_axis.cc:288 marker_time_axis.cc:243 #, fuzzy msgid "1.5 seconds" msgstr "Segundos" -#: imageframe_time_axis.cc:290 marker_time_axis.cc:243 +#: imageframe_time_axis.cc:289 marker_time_axis.cc:244 #, fuzzy msgid "2 seconds" msgstr "Segundos" -#: imageframe_time_axis.cc:291 marker_time_axis.cc:244 +#: imageframe_time_axis.cc:290 marker_time_axis.cc:245 #, fuzzy msgid "2.5 seconds" msgstr "Segundos" -#: imageframe_time_axis.cc:292 marker_time_axis.cc:245 +#: imageframe_time_axis.cc:291 marker_time_axis.cc:246 #, fuzzy msgid "3 seconds" msgstr "Segundos" #. duration_items.push_back(SeparatorElem()) ; #. duration_items.push_back(MenuElem (_("custom"), mem_fun(*this, &ImageFrameTimeAxis::set_marker_duration_custom))) ; -#: imageframe_time_axis.cc:297 marker_time_axis.cc:250 +#: imageframe_time_axis.cc:296 marker_time_axis.cc:251 #, fuzzy msgid "Duration (sec)" msgstr "Arrastar regiões" -#: imageframe_time_axis.cc:302 +#: imageframe_time_axis.cc:301 #, fuzzy msgid "Remove Frame" msgstr "Remover Campo" -#: imageframe_time_axis.cc:305 +#: imageframe_time_axis.cc:304 #, fuzzy msgid "Image Frame" msgstr "Quadros CD" -#: imageframe_time_axis.cc:306 marker_time_axis.cc:256 +#: imageframe_time_axis.cc:305 marker_time_axis.cc:257 #, fuzzy msgid "Rename Track" msgstr "Renomear" -#: io_selector.cc:59 io_selector.cc:793 +#: io_selector.cc:60 io_selector.cc:794 #, fuzzy msgid "Rescan" msgstr "refrescar" -#: io_selector.cc:67 +#: io_selector.cc:68 msgid "%1 input" msgstr "%1 entrada" -#: io_selector.cc:69 +#: io_selector.cc:70 msgid "%1 output" msgstr "%1 saída" -#: io_selector.cc:141 route_params_ui.cc:106 +#: io_selector.cc:142 route_params_ui.cc:107 msgid "Inputs" msgstr "Entradas" -#: io_selector.cc:141 route_params_ui.cc:107 +#: io_selector.cc:142 route_params_ui.cc:108 msgid "Outputs" msgstr "Saídas" -#: io_selector.cc:142 +#: io_selector.cc:143 #, fuzzy msgid "Add Input" msgstr "acrescentar entrada" -#: io_selector.cc:142 +#: io_selector.cc:143 #, fuzzy msgid "Add Output" msgstr "acrescentar saída" -#: io_selector.cc:143 +#: io_selector.cc:144 #, fuzzy msgid "Remove Input" msgstr "Remover ponto de sincronia" -#: io_selector.cc:143 +#: io_selector.cc:144 #, fuzzy msgid "Remove Output" msgstr "No.Saídas" -#: io_selector.cc:144 +#: io_selector.cc:145 #, fuzzy msgid "Disconnect All" msgstr "Desligar" -#: io_selector.cc:158 +#: io_selector.cc:159 msgid "Available connections" msgstr "Ligações disponíveis" -#: io_selector.cc:554 io_selector.cc:573 +#: io_selector.cc:555 io_selector.cc:574 msgid "There are no more JACK ports available." msgstr "" -#: io_selector.cc:648 io_selector.cc:675 io_selector.cc:728 +#: io_selector.cc:649 io_selector.cc:676 io_selector.cc:729 msgid "port" msgstr "porta" -#: io_selector.cc:797 +#: io_selector.cc:798 msgid "ardour: " msgstr "" -#: keyboard.cc:297 +#: keyboard.cc:299 msgid "KeyboardTarget: keyname \"%1\" is unknown." msgstr "" -#: keyboard.cc:523 +#: keyboard.cc:525 msgid "" "Your system is completely broken - NumLock uses \"%1\"as its modifier. This " "is madness - see the man page for xmodmap to find out how to fix this." msgstr "" -#: keyboard.cc:531 +#: keyboard.cc:533 msgid "" "Your system generates \"%1\" when the NumLock key is pressed. This can cause " "problems when editing so Ardour will use %2 to mean Meta rather than %1" msgstr "" -#: keyboard.cc:592 +#: keyboard.cc:594 msgid "You have %1 keys bound to \"mod1\"" msgstr "Existem %1 teclas associadas a \"mod1\"" -#: keyboard.cc:607 +#: keyboard.cc:609 msgid "You have %1 keys bound to \"mod2\"" msgstr "Existem %1 teclas associadas a \"mod2\"" -#: keyboard.cc:622 +#: keyboard.cc:624 msgid "You have %1 keys bound to \"mod3\"" msgstr "Existem %1 teclas associadas a \"mod3\"" -#: keyboard.cc:637 +#: keyboard.cc:639 msgid "You have %1 keys bound to \"mod4\"" msgstr "Existem %1 teclas associadas a \"mod4\"" -#: keyboard.cc:652 +#: keyboard.cc:654 msgid "You have %1 keys bound to \"mod5\"" msgstr "Existem %1 teclas associadas a \"mod5\"" -#: location_ui.cc:47 location_ui.cc:50 +#: location_ui.cc:48 location_ui.cc:51 msgid "Set" msgstr "Seleccionar" -#: location_ui.cc:48 location_ui.cc:51 +#: location_ui.cc:49 location_ui.cc:52 msgid "Go" msgstr "Ir" -#: location_ui.cc:54 +#: location_ui.cc:55 msgid "CD" msgstr "" -#: location_ui.cc:57 +#: location_ui.cc:58 msgid "SCMS" msgstr "" -#: location_ui.cc:58 +#: location_ui.cc:59 msgid "Pre-Emphasis" msgstr "" -#: location_ui.cc:569 +#: location_ui.cc:570 msgid "Add New Location" msgstr "Adicionar Nova Localização" -#: location_ui.cc:570 +#: location_ui.cc:571 msgid "Add New Range" msgstr "Adicionar Novo Intervalo" -#: location_ui.cc:574 +#: location_ui.cc:575 msgid "ardour: locations" msgstr "ardour: localizações" -#: location_ui.cc:575 +#: location_ui.cc:576 msgid "ardour_locations" msgstr "" -#: location_ui.cc:603 +#: location_ui.cc:604 #, fuzzy msgid "Location (CD Index) Markers" msgstr "Localizações" -#: location_ui.cc:623 +#: location_ui.cc:624 #, fuzzy msgid "Range (CD Track) Markers" msgstr "Intervalos" -#: location_ui.cc:789 +#: location_ui.cc:790 msgid "add range marker" msgstr "acrescentar marcador de região" -#: main.cc:71 +#: main.cc:72 msgid "ardour is killing itself for a clean exit\n" msgstr "ardour em modo de auto-destruição para uma saída em beleza\n" -#: main.cc:80 +#: main.cc:81 msgid "stopping user interface\n" msgstr "interface homem-máquina em fase terminal\n" #. XXX its doubtful that snprintf() is async-safe -#: main.cc:99 +#: main.cc:100 #, fuzzy, c-format msgid "%d(%d): received signal %d\n" msgstr "%d: sinal %d recebido\n" -#: main.cc:185 +#: main.cc:186 msgid "cannot become new process group leader (%1)" msgstr "" -#: main.cc:212 +#: main.cc:213 msgid "cannot setup signal handling for %1" msgstr "não foi possível estabelecer receptor de sinal %1" -#: main.cc:223 +#: main.cc:224 msgid "cannot set default signal mask (%1)" msgstr "não foi possível estabelecer máscara de sinal %1" -#: main.cc:253 +#: main.cc:254 #, fuzzy msgid "" "Without a UI style file, ardour will look strange.\n" @@ -4877,12 +4791,12 @@ msgstr "" "Por favor, indique um ficheiro de estilo visual válido em ARDOUR_UI_RC " "(variável de ambiente)" -#: main.cc:273 +#: main.cc:276 #, fuzzy msgid "Ardour could not connect to JACK." msgstr "Não foi possível conectar ao serviço JACK como \"%1\"" -#: main.cc:277 +#: main.cc:280 #, fuzzy msgid "" "There are several possible reasons:\n" @@ -4902,72 +4816,12 @@ msgstr "" "\n" "Por favor, considere estas possibilidades e (re)inicie o serviço JACK." -#: main.cc:324 -msgid "Ardour/GTK " -msgstr "" - -#: main.cc:326 -msgid "" -"\n" -" (built using " -msgstr "" - -#: main.cc:330 -#, fuzzy -msgid " with libardour " -msgstr " em execução com libardour " - -#: main.cc:335 -msgid " and GCC version " -msgstr "" - -#: main.cc:345 -msgid "Copyright (C) 1999-2005 Paul Davis" -msgstr "" - -#: main.cc:346 -msgid "" -"Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " -"Baker" -msgstr "" - -#: main.cc:348 -msgid "Ardour comes with ABSOLUTELY NO WARRANTY" -msgstr "Ardour é fornecido ABSOLUTAMENTE SEM QUALQUER GARANTIA" - -#: main.cc:349 -msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." -msgstr "" - -#: main.cc:350 -msgid "This is free software, and you are welcome to redistribute it " -msgstr "Sendo software livre, é permitida e até encorajada a sua distribuição" - -#: main.cc:351 -#, fuzzy -msgid "under certain conditions; see the source for copying conditions." -msgstr "" -"desde que sejam respeitadas algumas condições; para mais informações, leia " -"por favor o ficheiro COPYING." - -#: main.cc:360 -msgid "could not create ARDOUR GUI" -msgstr "não foi possível criar o interface gráfico (GUI)" - -#: main.cc:378 -msgid "Could not connect to JACK server as \"%1\"" -msgstr "Não foi possível conectar ao serviço JACK como \"%1\"" - -#: main.cc:381 -msgid "could not initialize Ardour." -msgstr "não foi possível inicializar o Ardour" - -#: main.cc:392 +#: main.cc:310 msgid "could not load command line session \"%1\"" msgstr "não foi possível carregar a sessão de linha de comando \"%1\"" #. it wasn't new, but we require a new session -#: main.cc:412 +#: main.cc:330 msgid "" "\n" "\n" @@ -4975,7 +4829,7 @@ msgid "" "To avoid this message, start ardour as \"ardour %1" msgstr "" -#: main.cc:423 +#: main.cc:341 msgid "" "\n" "\n" @@ -4983,299 +4837,448 @@ msgid "" "To create it from the command line, start ardour as \"ardour --new %1" msgstr "" +#: main.cc:405 +msgid "Ardour/GTK " +msgstr "" + +#: main.cc:407 +msgid "" +"\n" +" (built using " +msgstr "" + +#: main.cc:411 +#, fuzzy +msgid " with libardour " +msgstr " em execução com libardour " + +#: main.cc:416 +msgid " and GCC version " +msgstr "" + +#: main.cc:426 +msgid "Copyright (C) 1999-2006 Paul Davis" +msgstr "" + +#: main.cc:427 +msgid "" +"Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " +"Baker" +msgstr "" + +#: main.cc:429 +msgid "Ardour comes with ABSOLUTELY NO WARRANTY" +msgstr "Ardour é fornecido ABSOLUTAMENTE SEM QUALQUER GARANTIA" + +#: main.cc:430 +msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." +msgstr "" + +#: main.cc:431 +msgid "This is free software, and you are welcome to redistribute it " +msgstr "Sendo software livre, é permitida e até encorajada a sua distribuição" + +#: main.cc:432 +#, fuzzy +msgid "under certain conditions; see the source for copying conditions." +msgstr "" +"desde que sejam respeitadas algumas condições; para mais informações, leia " +"por favor o ficheiro COPYING." + +#: main.cc:441 +msgid "could not create ARDOUR GUI" +msgstr "não foi possível criar o interface gráfico (GUI)" + +#: main.cc:459 +msgid "Could not connect to JACK server as \"%1\"" +msgstr "Não foi possível conectar ao serviço JACK como \"%1\"" + +#: main.cc:462 +msgid "could not initialize Ardour." +msgstr "não foi possível inicializar o Ardour" + #: marker.cc:244 #, fuzzy msgid "MarkerText" msgstr "Marcas" -#: marker_time_axis.cc:253 +#: marker_time_axis.cc:254 #, fuzzy msgid "Remove Marker" msgstr "remover marcador" -#: marker_time_axis.cc:255 +#: marker_time_axis.cc:256 #, fuzzy msgid "Marker" msgstr "Marcas" -#: meter_bridge.cc:77 +#: meter_bridge.cc:78 msgid "ardour: meter bridge" msgstr "ardour: VUímetro" -#: meter_bridge.cc:78 +#: meter_bridge.cc:79 msgid "ardour_meter_bridge" msgstr "" -#: meter_bridge_strip.cc:79 meter_bridge_strip.cc:93 +#: meter_bridge_strip.cc:80 meter_bridge_strip.cc:94 #, c-format msgid "# of %u-sample overs" msgstr "# de %u-quadros" -#: meter_bridge_strip.cc:221 +#: meter_bridge_strip.cc:222 #, fuzzy msgid "New Name for Meter:" msgstr "Novo nome para o VUímetro:" -#: mixer_strip.cc:85 mixer_strip.cc:437 region_editor.cc:46 -msgid "mute" -msgstr "mudo" - -#: mixer_strip.cc:85 mixer_strip.cc:438 -msgid "solo" +#: mixer_strip.cc:95 mixer_strip.cc:140 mixer_strip.cc:1227 +msgid "pre" msgstr "" -#: mixer_strip.cc:85 mixer_strip.cc:436 -msgid "RECORD" -msgstr "GRAVAR" - -#: mixer_strip.cc:96 mixer_strip.cc:441 mixer_strip.cc:1064 +#: mixer_strip.cc:96 mixer_strip.cc:822 msgid "Comments" msgstr "" -#: mixer_strip.cc:120 mixer_strip.cc:752 -msgid "INPUT" -msgstr "ENTRADA" +#: mixer_strip.cc:119 +#, fuzzy +msgid "Input" +msgstr "Entradas" -#: mixer_strip.cc:125 mixer_strip.cc:773 -msgid "OUTPUT" -msgstr "SAÃDA" +#: mixer_strip.cc:136 mixer_strip.cc:1223 +#, fuzzy +msgid "input" +msgstr "%1 entrada" -#: mixer_strip.cc:140 -msgid "Pan automation mode" -msgstr "Modo de automatização de panorâmica" +#: mixer_strip.cc:144 mixer_strip.cc:1231 +#, fuzzy +msgid "post" +msgstr "porta" -#: mixer_strip.cc:141 -msgid "Gain automation mode" -msgstr "Modo de automatização de ganho" - -#: mixer_strip.cc:143 -msgid "Pan automation type" -msgstr "Tipo de automatização de panorâmica" - -#: mixer_strip.cc:144 -msgid "Gain automation type" -msgstr "Tipo de automatização de ganho" - -#: mixer_strip.cc:183 mixer_strip.cc:195 mixer_strip.cc:913 -msgid "trim" -msgstr "recorte" - -#. XXX it might different in different languages -#: mixer_strip.cc:184 mixer_strip.cc:196 mixer_strip.cc:917 -msgid "abs" +#. TRANSLATORS: this string should be longest of the strings +#. used to describe meter points. In english, its "input". +#. +#: mixer_strip.cc:152 +msgid "tupni" msgstr "" -#: mixer_strip.cc:203 -msgid "gain automation mode" -msgstr "modo de automatização de ganho" - -#: mixer_strip.cc:204 -msgid "pan automation mode" -msgstr "modo de automatização de panorâmica" - -#: mixer_strip.cc:205 -msgid "gain automation state" -msgstr "ponto de automatização de ganho" - -#: mixer_strip.cc:206 -msgid "pan automation state" -msgstr "ponto de automatização de panorâmica" - -#: mixer_strip.cc:223 -msgid "varispeed" +#: mixer_strip.cc:207 +#, fuzzy +msgid "Varispeed" msgstr "velocidade variável" -#: mixer_strip.cc:245 mixer_strip.cc:1078 +#: mixer_strip.cc:233 mixer_strip.cc:836 msgid "Click to Add/Edit Comments" msgstr "" -#: mixer_strip.cc:393 +#: mixer_strip.cc:374 msgid "unknown strip width \"%1\" in XML GUI information" msgstr "" "largura desconhecida \"%1\" na informação XML para o interface gráfico (GUI)" -#: mixer_strip.cc:443 mixer_strip.cc:1062 -msgid "*Comments*" +#: mixer_strip.cc:417 +#, fuzzy +msgid "record" +msgstr "Gravar" + +#: mixer_strip.cc:418 region_editor.cc:47 +msgid "mute" +msgstr "mudo" + +#: mixer_strip.cc:419 +msgid "solo" msgstr "" -#: mixer_strip.cc:457 -msgid "REC" -msgstr "GRAV" +#: mixer_strip.cc:422 +msgid "comments" +msgstr "" -#: mixer_strip.cc:462 mixer_strip.cc:1072 +#: mixer_strip.cc:424 +msgid "*comments*" +msgstr "" + +#: mixer_strip.cc:438 +#, fuzzy +msgid "Rec" +msgstr "refrescar" + +#: mixer_strip.cc:439 +msgid "M" +msgstr "" + +#: mixer_strip.cc:440 +msgid "S" +msgstr "" + +#: mixer_strip.cc:443 mixer_strip.cc:830 #, fuzzy msgid "Cmt" msgstr "corte" -#: mixer_strip.cc:464 mixer_strip.cc:1070 +#: mixer_strip.cc:445 mixer_strip.cc:828 msgid "*Cmt*" msgstr "" -#: mixer_strip.cc:503 mixer_strip.cc:562 redirect_box.cc:1004 +#: mixer_strip.cc:483 mixer_strip.cc:549 redirect_box.cc:1006 msgid "Not connected to JACK - no I/O changes are possible" msgstr "" -#: mixer_strip.cc:569 +#: mixer_strip.cc:560 msgid "Track" msgstr "Faixa" -#: mixer_strip.cc:593 mixer_strip.cc:609 +#: mixer_strip.cc:588 mixer_strip.cc:604 msgid "could not register new ports required for that connection" msgstr "" -#: mixer_strip.cc:755 -msgid "IN" +#: mixer_strip.cc:747 +#, fuzzy +msgid " Input" +msgstr "No.Entradas" + +#: mixer_strip.cc:750 +#, fuzzy +msgid "I" msgstr "ENTRADA" -#: mixer_strip.cc:776 -msgid "OUT" -msgstr "SAÃDA" +#: mixer_strip.cc:820 +msgid "*Comments*" +msgstr "" -#: mixer_strip.cc:884 -msgid "aplay" -msgstr "aRepr" - -#: mixer_strip.cc:890 -msgid "awrite" -msgstr "aGrav" - -#: mixer_strip.cc:1095 +#: mixer_strip.cc:859 #, fuzzy msgid ": comment editor" msgstr "Não foi possível iniciar o painel principal de edição (editor)" -#: mixer_strip.cc:1157 mixer_strip.cc:1178 -msgid "no group" -msgstr "sem grupo" +#: mixer_strip.cc:953 +msgid "Grp" +msgstr "" -#: mixer_strip.cc:1181 +#: mixer_strip.cc:956 msgid "~G" msgstr "" -#: mixer_strip.cc:1229 +#: mixer_strip.cc:1004 #, fuzzy msgid "Invert Polarity" msgstr "polaridade" -#: mixer_ui.cc:84 +#: mixer_ui.cc:85 msgid "Strips" msgstr "Painéis" -#: mixer_ui.cc:108 -msgid "groupname" -msgstr "" +#: mixer_ui.cc:110 +#, fuzzy +msgid "Group" +msgstr "Grupos" -#: mixer_ui.cc:109 region_editor.cc:48 region_editor.cc:191 -#: region_editor.cc:225 -msgid "active" -msgstr "activo" - -#: mixer_ui.cc:110 region_editor.cc:49 -msgid "visible" -msgstr "visível" - -#: mixer_ui.cc:207 mixer_ui.cc:366 +#: mixer_ui.cc:211 mixer_ui.cc:370 msgid "ardour: mixer" msgstr "ardour: misturador" -#: mixer_ui.cc:208 +#: mixer_ui.cc:212 msgid "ardour_mixer" msgstr "" -#: mixer_ui.cc:342 +#: mixer_ui.cc:346 msgid "ardour: mixer: " msgstr "ardour: misturador: " -#: mixer_ui.cc:569 +#: mixer_ui.cc:573 msgid "signal" msgstr "sinal" -#: mixer_ui.cc:719 +#: mixer_ui.cc:723 msgid "track display list item for renamed strip not found!" msgstr "não foi encontrada qualquer faixa para o painel de mistura" -#: option_editor.cc:75 +#: new_session_dialog.cc:39 +#, fuzzy +msgid "New Session Name :" +msgstr "Nome de sessão:" + +#: new_session_dialog.cc:41 +msgid "Create Session Directory In :" +msgstr "" + +#: new_session_dialog.cc:43 +#, fuzzy +msgid "Use Session Template :" +msgstr "Modelo de sessão" + +#: new_session_dialog.cc:45 +#, fuzzy +msgid "Channel Count" +msgstr "Cancelar Importação" + +#: new_session_dialog.cc:46 +#, fuzzy +msgid "Create Monitor Bus" +msgstr "Saídas de Controlo" + +#: new_session_dialog.cc:53 +#, fuzzy +msgid "Create Master Bus" +msgstr "usar saídas principais" + +#: new_session_dialog.cc:55 +#, fuzzy +msgid "Automatically Connect Inputs" +msgstr "ligar entradas físicas automaticamente" + +#: new_session_dialog.cc:56 new_session_dialog.cc:67 +#, fuzzy +msgid "Port Limit" +msgstr "Esquecer" + +#: new_session_dialog.cc:64 +#, fuzzy +msgid "Track/Bus Inputs" +msgstr "Faixas/Barramentos" + +#: new_session_dialog.cc:66 +#, fuzzy +msgid "Automatically Connect Outputs" +msgstr "ligar saídas manualmente" + +#: new_session_dialog.cc:75 +msgid "Connect to Master Bus" +msgstr "" + +#: new_session_dialog.cc:76 +msgid "Connect to Physical Outputs" +msgstr "" + +#: new_session_dialog.cc:80 +#, fuzzy +msgid "Track/Bus Outputs" +msgstr "Saída" + +#: new_session_dialog.cc:83 +#, fuzzy +msgid "Advanced Options" +msgstr "Opções" + +#: new_session_dialog.cc:91 +#, fuzzy +msgid "Open Recent Session" +msgstr "abrir sessão" + +#: new_session_dialog.cc:127 +#, fuzzy +msgid "Open Session File :" +msgstr "abrir sessão" + +#: new_session_dialog.cc:274 +#, fuzzy +msgid "New Session" +msgstr "Sessão" + +#: new_session_dialog.cc:276 +#, fuzzy +msgid "Open Session" +msgstr "abrir sessão" + +#: new_session_dialog.cc:281 +#, fuzzy +msgid "ardour: session control" +msgstr "ardour: guardar sessão?" + +#: new_session_dialog.cc:310 +#, fuzzy +msgid "select template" +msgstr "Sem modelo" + +#: new_session_dialog.cc:316 +#, fuzzy +msgid "select session file" +msgstr "seleccionar regiões" + +#: new_session_dialog.cc:325 +#, fuzzy +msgid "select directory" +msgstr "seleccionar regiões" + +#: option_editor.cc:76 #, fuzzy msgid "SMPTE offset is negative" msgstr "Deslocamento SMPTE" -#: option_editor.cc:101 +#: option_editor.cc:102 msgid "ardour: options editor" msgstr "ardour: opções" -#: option_editor.cc:102 +#: option_editor.cc:103 msgid "ardour_option_editor" msgstr "" -#: option_editor.cc:126 +#: option_editor.cc:127 msgid "Paths/Files" msgstr "Directórios/Ficheiros" -#: option_editor.cc:127 +#: option_editor.cc:128 msgid "Kbd/Mouse" msgstr "Teclado/Rato" -#: option_editor.cc:130 +#: option_editor.cc:131 msgid "Layers & Fades" msgstr "" -#: option_editor.cc:134 +#: option_editor.cc:135 msgid "MIDI" msgstr "" -#: option_editor.cc:176 +#: option_editor.cc:177 msgid "24 FPS" msgstr "" -#: option_editor.cc:178 +#: option_editor.cc:179 msgid "25 FPS" msgstr "" -#: option_editor.cc:180 +#: option_editor.cc:181 msgid "30 FPS" msgstr "" -#: option_editor.cc:186 +#: option_editor.cc:187 msgid "30 FPS drop" msgstr "" -#: option_editor.cc:243 +#: option_editor.cc:244 msgid "session RAID path" msgstr "directório RAID de sessão" -#: option_editor.cc:248 +#: option_editor.cc:249 #, fuzzy msgid "Soundfile Search Paths" msgstr "Audioteca" -#: option_editor.cc:253 +#: option_editor.cc:254 #, fuzzy msgid "Paths" msgstr "Directórios/Ficheiros" -#: option_editor.cc:267 option_editor.cc:273 option_editor.cc:724 -#: option_editor.cc:751 +#: option_editor.cc:268 option_editor.cc:274 option_editor.cc:723 +#: option_editor.cc:750 msgid "internal" msgstr "interno" -#: option_editor.cc:286 +#: option_editor.cc:287 msgid "Short crossfade length (msecs)" msgstr "" -#: option_editor.cc:298 +#: option_editor.cc:299 msgid "Destructive crossfade length (msecs)" msgstr "" -#: option_editor.cc:366 +#: option_editor.cc:367 msgid "SMPTE Frames/second" msgstr "Quadros SMPTE/segundo" -#: option_editor.cc:367 +#: option_editor.cc:368 msgid "SMPTE Offset" msgstr "Deslocamento SMPTE" -#: option_editor.cc:461 option_editor.cc:468 option_editor.cc:471 -#: option_editor.cc:617 +#: option_editor.cc:462 option_editor.cc:469 option_editor.cc:472 +#: option_editor.cc:618 #, fuzzy msgid "online" msgstr "linear" @@ -5283,12 +5286,12 @@ msgstr "linear" #. remember, we have to handle the i18n case where the relative #. lengths of the strings in language N is different than in english. #. -#: option_editor.cc:468 option_editor.cc:469 option_editor.cc:614 +#: option_editor.cc:469 option_editor.cc:470 option_editor.cc:615 #, fuzzy msgid "offline" msgstr "linear" -#: option_editor.cc:669 +#: option_editor.cc:670 msgid "Choose Click" msgstr "" @@ -5297,15 +5300,15 @@ msgstr "" msgid "Choose Click Emphasis" msgstr "Usar como metrónomo acentuado" -#: option_editor.cc:804 +#: option_editor.cc:803 msgid "Click audio file" msgstr "Ficheiro audio para metrónomo" -#: option_editor.cc:810 +#: option_editor.cc:809 msgid "Click emphasis audiofile" msgstr "Ficheiro audio para metrónomo acentuado" -#: option_editor.cc:847 +#: option_editor.cc:846 msgid "" "The auditioner is a dedicated mixer strip used\n" "for listening to specific regions outside the context\n" @@ -5317,35 +5320,35 @@ msgstr "" "da mistura geral. Pode ser inter-conectado tal como\n" "qualquer outro painel de mistura." -#: option_editor.cc:920 +#: option_editor.cc:919 msgid "Edit using" msgstr "Editar com" -#: option_editor.cc:927 option_editor.cc:954 +#: option_editor.cc:926 option_editor.cc:953 msgid "+ button" msgstr "+ botão" -#: option_editor.cc:947 +#: option_editor.cc:946 msgid "Delete using" msgstr "Eliminar com" -#: option_editor.cc:974 +#: option_editor.cc:973 msgid "Ignore snap using" msgstr "Ignorar ajuste com" -#: opts.cc:47 +#: opts.cc:46 msgid "Usage: " msgstr "Uso: " -#: opts.cc:48 +#: opts.cc:47 msgid " -v, --version Show version information\n" msgstr " -v, --version Mostrar informação sobre versão\n" -#: opts.cc:49 +#: opts.cc:48 msgid " -h, --help Print this message\n" msgstr " -h, --help Mostrar esta mesma mensagem\n" -#: opts.cc:50 +#: opts.cc:49 msgid "" " -b, --bindings Print all possible keyboard binding " "names\n" @@ -5353,14 +5356,14 @@ msgstr "" " -b, --bindings Mostrar todas as associações de teclado " "possíveis\n" -#: opts.cc:51 +#: opts.cc:50 #, fuzzy msgid " -n, --show-splash Show splash screen\n" msgstr "" " -n, --no-splash Não mostrar ecran de apresentação " "inicial\n" -#: opts.cc:52 +#: opts.cc:51 #, fuzzy msgid "" " -c, --name name Use a specific jack client name, default " @@ -5369,150 +5372,163 @@ msgstr "" " -c, --jack-client-name name Empregar um nome de cliente JACK " "específico (ardour)\n" -#: opts.cc:53 +#: opts.cc:52 #, fuzzy msgid "" " -N, --new session-name Create a new session from the command " "line\n" msgstr " [session-name] Nome de sessão a carregar\n" -#: opts.cc:54 +#: opts.cc:53 msgid "" " -o, --use-hw-optimizations Try to use h/w specific optimizations\n" msgstr "" -#: opts.cc:56 +#: opts.cc:55 #, fuzzy msgid " -V, --novst Do not use VST support\n" msgstr " -V, --novst Não usar suporte VST inicial\n" -#: opts.cc:58 +#: opts.cc:57 msgid " [session-name] Name of session to load\n" msgstr " [session-name] Nome de sessão a carregar\n" -#: opts.cc:59 +#: opts.cc:58 msgid " -C, --curvetest filename Curve algorithm debugger\n" msgstr "" -#: opts.cc:60 +#: opts.cc:59 #, fuzzy msgid " -g, --gtktheme Allow GTK to load a theme\n" msgstr " -h, --help Mostrar esta mesma mensagem\n" -#: pan_automation_time_axis.cc:59 +#: pan_automation_time_axis.cc:60 msgid "You can't graphically edit panning of more than stream" msgstr "" -#: pan_automation_time_axis.cc:79 +#: pan_automation_time_axis.cc:80 #, fuzzy msgid "add pan automation event" msgstr "acrescentar evento de automatização a " -#: panner2d.cc:588 panner_ui.cc:393 plugin_ui.cc:833 +#: panner2d.cc:589 panner_ui.cc:435 plugin_ui.cc:834 msgid "Bypass" msgstr "Ignorar" -#: panner_ui.cc:57 panner_ui.cc:187 +#: panner_ui.cc:58 panner_ui.cc:225 #, fuzzy msgid "link" msgstr "entrada" +#: panner_ui.cc:69 +msgid "Pan automation mode" +msgstr "Modo de automatização de panorâmica" + #: panner_ui.cc:70 +msgid "Pan automation type" +msgstr "Tipo de automatização de panorâmica" + +#: panner_ui.cc:81 msgid "panning link control" msgstr "" -#: panner_ui.cc:72 +#: panner_ui.cc:83 msgid "panning link direction" msgstr "" -#: panner_ui.cc:197 +#: panner_ui.cc:235 msgid "L" msgstr "" -#: panner_ui.cc:296 +#: panner_ui.cc:335 +#, c-format +msgid "panner for channel %lu" +msgstr "" + +#: panner_ui.cc:337 #, c-format msgid "panner for channel %u" msgstr "" -#: panner_ui.cc:403 +#: panner_ui.cc:445 #, fuzzy msgid "Reset all" msgstr "reiniciar" -#: playlist_selector.cc:51 +#: playlist_selector.cc:52 #, fuzzy msgid "ardour: playlists" msgstr "ardour: efeitos/plug-ins" -#: playlist_selector.cc:58 +#: playlist_selector.cc:59 msgid "Playlists grouped by track" msgstr "" -#: playlist_selector.cc:97 +#: playlist_selector.cc:98 #, fuzzy msgid "ardour: playlist for " msgstr "ardour: efeitos/plug-ins" -#: playlist_selector.cc:113 +#: playlist_selector.cc:114 #, fuzzy msgid "Other tracks" msgstr "retocar faixa" -#: playlist_selector.cc:129 +#: playlist_selector.cc:130 msgid "unassigned" msgstr "" -#: plugin_selector.cc:42 +#: plugin_selector.cc:43 msgid "ardour: plugins" msgstr "ardour: efeitos/plug-ins" -#: plugin_selector.cc:55 +#: plugin_selector.cc:56 #, fuzzy msgid "Available LADSPA Plugins" msgstr "Efeitos/plug-ins LADSPA disponíveis" -#: plugin_selector.cc:56 +#: plugin_selector.cc:57 msgid "Type" msgstr "Tipo" -#: plugin_selector.cc:57 plugin_selector.cc:80 +#: plugin_selector.cc:58 plugin_selector.cc:81 msgid "# Inputs" msgstr "No.Entradas" -#: plugin_selector.cc:58 plugin_selector.cc:81 +#: plugin_selector.cc:59 plugin_selector.cc:82 msgid "# Outputs" msgstr "No.Saídas" -#: plugin_selector.cc:67 +#: plugin_selector.cc:68 msgid "Plugins to be Connected to Insert" msgstr "" -#: plugin_selector.cc:79 +#: plugin_selector.cc:80 #, fuzzy msgid "Available plugins" msgstr "Efeitos/plug-ins VST disponíveis" -#: plugin_selector.cc:97 +#: plugin_selector.cc:98 msgid "Add a plugin to the effect list" msgstr "Acrescentar à lista de efeitos/plug-ins" -#: plugin_selector.cc:99 +#: plugin_selector.cc:102 msgid "Remove a plugin from the effect list" msgstr "Remover à lista de efeitos/plug-ins" -#: plugin_selector.cc:101 +#: plugin_selector.cc:104 msgid "Update available plugins" msgstr "Actualizar efeitos/plug-ins disponíveis" -#: plugin_selector.cc:123 +#: plugin_selector.cc:126 msgid "LADSPA" msgstr "" -#: plugin_selector.cc:126 +#: plugin_selector.cc:129 msgid "VST" msgstr "" -#: plugin_ui.cc:83 +#: plugin_ui.cc:84 msgid "" "unknown type of editor-supplying plugin (note: no VST support in this " "version of ardour)" @@ -5520,52 +5536,53 @@ msgstr "" "tipo desconhecido de editor de efeito/plug-in (nota: esta versão do ardour " "não suporta VST)" -#: plugin_ui.cc:138 +#: plugin_ui.cc:139 msgid "Presets" msgstr "" -#: plugin_ui.cc:229 +#: plugin_ui.cc:230 #, fuzzy msgid "Controls" msgstr "Saídas de Controlo" -#: plugin_ui.cc:266 +#: plugin_ui.cc:267 msgid "Plugin Editor: could not build control element for port %1" msgstr "" "Editor de efeitos/plug-ins: não foi possível criar elemento de controlo para " "%1" -#: plugin_ui.cc:357 -msgid "automation control" +#: plugin_ui.cc:358 +#, fuzzy +msgid "Automation control" msgstr "controlo de automatização" -#: plugin_ui.cc:853 +#: plugin_ui.cc:854 msgid "Plugin preset %1 not found" msgstr "Parametrização de efeito/plug-in %1 inexistente" -#: plugin_ui.cc:863 +#: plugin_ui.cc:864 #, fuzzy msgid "Name of New Preset:" msgstr "Nome para a nova ligação:" -#: redirect_automation_line.cc:53 +#: redirect_automation_line.cc:54 msgid "redirect automation created for non-plugin" msgstr "automatização de re-encaminhamento criado para um não-efeito/plug-in" -#: redirect_automation_time_axis.cc:93 +#: redirect_automation_time_axis.cc:94 msgid "add automation event to " msgstr "acrescentar evento de automatização a " -#: redirect_box.cc:222 +#: redirect_box.cc:223 msgid "New send" msgstr "" -#: redirect_box.cc:223 +#: redirect_box.cc:224 #, fuzzy msgid "Show send controls" msgstr "Controlo de velocidade" -#: redirect_box.cc:377 +#: redirect_box.cc:383 msgid "" "You attempted to add a plugin (%1).\n" "The plugin has %2 inputs\n" @@ -5576,7 +5593,7 @@ msgid "" "part of the signal." msgstr "" -#: redirect_box.cc:389 +#: redirect_box.cc:395 msgid "" "You attempted to add a plugin (%1).\n" "The plugin has %2 inputs\n" @@ -5588,7 +5605,7 @@ msgid "" "support this type of configuration." msgstr "" -#: redirect_box.cc:402 +#: redirect_box.cc:408 msgid "" "You attempted to add a plugin (%1).\n" "\n" @@ -5601,34 +5618,34 @@ msgid "" "Ardour does not understand what to do in such situations.\n" msgstr "" -#: redirect_box.cc:493 +#: redirect_box.cc:495 msgid "Pre-fader inserts, sends & plugins:" msgstr "" -#: redirect_box.cc:496 +#: redirect_box.cc:498 msgid "Post-fader inserts, sends & plugins:" msgstr "" -#: redirect_box.cc:642 +#: redirect_box.cc:644 msgid "" "You cannot reorder this set of redirects\n" "in that way because the inputs and\n" "outputs do not work correctly." msgstr "" -#: redirect_box.cc:747 +#: redirect_box.cc:749 #, fuzzy msgid "rename redirect" msgstr "ardour: renomear região" -#: redirect_box.cc:824 redirect_box.cc:872 +#: redirect_box.cc:826 redirect_box.cc:874 msgid "" "Copying the set of redirects on the clipboard failed,\n" "probably because the I/O configuration of the plugins\n" "could not match the configuration of this track." msgstr "" -#: redirect_box.cc:894 +#: redirect_box.cc:896 #, fuzzy msgid "" "Do you really want to remove all redirects from this track?\n" @@ -5637,7 +5654,7 @@ msgstr "" "Deseja realmente remover o faixa \"%1\" ?\n" "(esta operação não pode ser desfeita)" -#: redirect_box.cc:897 +#: redirect_box.cc:899 #, fuzzy msgid "" "Do you really want to remove all redirects from this bus?\n" @@ -5646,244 +5663,256 @@ msgstr "" "Deseja realmente remover o faixa \"%1\" ?\n" "(esta operação não pode ser desfeita)" -#: redirect_box.cc:902 +#: redirect_box.cc:904 #, fuzzy msgid "Yes, remove them all" msgstr "Sim, remover." -#: redirect_box.cc:938 +#: redirect_box.cc:940 #, fuzzy msgid "ardour: %1" msgstr "ardour: misturador" -#: redirect_box.cc:980 +#: redirect_box.cc:982 #, fuzzy msgid "ardour: %1: %2 (by %3)" msgstr "ardour: misturador: " #. new stuff -#: redirect_box.cc:1052 +#: redirect_box.cc:1054 msgid "New Plugin ..." msgstr "" -#: redirect_box.cc:1053 +#: redirect_box.cc:1055 #, fuzzy msgid "New Insert" msgstr "nova entrada" -#: redirect_box.cc:1054 +#: redirect_box.cc:1056 msgid "New Send ..." msgstr "" -#: redirect_box.cc:1066 +#: redirect_box.cc:1068 #, fuzzy msgid "Deselect All" msgstr "Seleccionar tudo" -#: redirect_box.cc:1073 +#: redirect_box.cc:1075 #, fuzzy msgid "Activate all" msgstr "Activar" -#: redirect_box.cc:1074 +#: redirect_box.cc:1076 #, fuzzy msgid "Deactivate all" msgstr "Desactivar" -#: region_editor.cc:44 +#: region_editor.cc:45 msgid "NAME:" msgstr "NOME:" -#: region_editor.cc:45 +#: region_editor.cc:46 msgid "lock" msgstr "bloquear" -#: region_editor.cc:47 +#: region_editor.cc:48 msgid "opaque" msgstr "opaco" -#: region_editor.cc:52 +#: region_editor.cc:49 region_editor.cc:192 region_editor.cc:226 +msgid "active" +msgstr "activo" + +#: region_editor.cc:50 +msgid "visible" +msgstr "visível" + +#: region_editor.cc:53 msgid "Layer" msgstr "Nível" -#: region_editor.cc:60 +#: region_editor.cc:54 +msgid "play" +msgstr "reproduzir" + +#: region_editor.cc:61 msgid "ENVELOPE" msgstr "ENVOLVENTE" -#: region_editor.cc:106 +#: region_editor.cc:107 msgid "mute this region" msgstr "emudecer esta região" -#: region_editor.cc:107 +#: region_editor.cc:108 msgid "regions underneath this one cannot be heard" msgstr "regiões abaixo desta não serão ouvidas" -#: region_editor.cc:108 +#: region_editor.cc:109 msgid "prevent any changes to this region" msgstr "evitar qualquer alteração nesta região" -#: region_editor.cc:109 +#: region_editor.cc:110 msgid "use the gain envelope during playback" msgstr "usar a envolvente de ganho durante a reprodução" -#: region_editor.cc:110 +#: region_editor.cc:111 msgid "show the gain envelope" msgstr "mostrar a curva de envolvente de ganho" -#: region_editor.cc:111 +#: region_editor.cc:112 msgid "use fade in curve during playback" msgstr "usar curva de evanescimento durante a reprodução" -#: region_editor.cc:112 +#: region_editor.cc:113 msgid "use fade out curve during playback" msgstr "usar curva de desvanecimento durante a reprodução" -#: region_editor.cc:113 +#: region_editor.cc:114 msgid "audition this region" msgstr "ouvir esta região" -#: region_editor.cc:146 +#: region_editor.cc:147 msgid "START:" msgstr "INÃCIO:" -#: region_editor.cc:148 +#: region_editor.cc:149 msgid "END:" msgstr "FINAL:" -#: region_editor.cc:150 +#: region_editor.cc:151 msgid "LENGTH:" msgstr "TAMANHO:" -#: region_editor.cc:190 +#: region_editor.cc:191 msgid "FADE IN" msgstr "EVANESCER" -#: region_editor.cc:192 region_editor.cc:226 +#: region_editor.cc:193 region_editor.cc:227 msgid "msecs" msgstr "msegs" -#: region_editor.cc:224 +#: region_editor.cc:225 msgid "FADE OUT" msgstr "DESVANECER" -#: region_editor.cc:264 +#: region_editor.cc:265 msgid "ardour: region " msgstr "ardour: região" -#: region_editor.cc:401 +#: region_editor.cc:402 msgid "fade in edit" msgstr "alterar evanescimento" -#: region_editor.cc:413 +#: region_editor.cc:414 msgid "fade out edit" msgstr "alterar desvanecimento" -#: regionview.cc:1140 +#: regionview.cc:1146 #, fuzzy msgid "add gain control point" msgstr "remover ponto de controlo" -#: route_params_ui.cc:88 +#: route_params_ui.cc:89 msgid "Tracks/Buses" msgstr "Faixas/Barramentos" -#: route_params_ui.cc:108 +#: route_params_ui.cc:109 #, fuzzy msgid "Pre-fader Redirects" msgstr "Pré-encaminhamentos" -#: route_params_ui.cc:109 +#: route_params_ui.cc:110 #, fuzzy msgid "Post-fader Redirects" msgstr "Pós-encaminhamentos" -#: route_params_ui.cc:141 +#: route_params_ui.cc:144 #, fuzzy msgid "ardour: track/bus inspector" msgstr "ardour: acrescentar faixa/barramento" -#: route_params_ui.cc:142 +#: route_params_ui.cc:145 msgid "ardour_route_parameters" msgstr "" -#: route_params_ui.cc:199 +#: route_params_ui.cc:202 msgid "route display list item for renamed route not found!" msgstr "não foi encontrado qualquer elemento de encaminhamento" -#: route_params_ui.cc:451 +#: route_params_ui.cc:453 msgid "NO TRACK" msgstr "SEM FAIXA" -#: route_params_ui.cc:693 +#: route_params_ui.cc:695 #, fuzzy msgid "ardour: track/bus inspector: " msgstr "ardour: acrescentar faixa/barramento" -#: route_params_ui.cc:697 +#: route_params_ui.cc:699 msgid "No Route Selected" msgstr "Caminho Não Seleccionado" -#: route_params_ui.cc:698 +#: route_params_ui.cc:700 #, fuzzy msgid "ardour: track/bus/inspector: no route selected" msgstr "ardour: parâmetros de encaminhamento: caminho não seleccionado" #. ctrl-shift-click applies change to all routes -#: route_ui.cc:133 +#: route_ui.cc:134 msgid "mute change" msgstr "mudo alterado" #. ctrl-shift-click applies change to all routes #. ctrl-alt-click: exclusively solo this track, not a toggle */ -#: route_ui.cc:208 route_ui.cc:218 +#: route_ui.cc:209 route_ui.cc:219 msgid "solo change" msgstr "solo alterado" -#: route_ui.cc:281 +#: route_ui.cc:282 msgid "rec-enable change" msgstr "gravar alterado" -#: route_ui.cc:472 +#: route_ui.cc:479 msgid "Solo-safe" msgstr "solo livre" -#: route_ui.cc:480 route_ui.cc:523 +#: route_ui.cc:487 route_ui.cc:530 msgid "MIDI Bind" msgstr "Associação MIDI" -#: route_ui.cc:494 +#: route_ui.cc:501 msgid "Pre Fader" msgstr "Pré-Atenuador" -#: route_ui.cc:501 +#: route_ui.cc:508 msgid "Post Fader" msgstr "Pós-Atenuador" -#: route_ui.cc:508 +#: route_ui.cc:515 msgid "Control Outs" msgstr "Saídas de Controlo" -#: route_ui.cc:515 +#: route_ui.cc:522 msgid "Main Outs" msgstr "Saídas Principais" -#: route_ui.cc:552 +#: route_ui.cc:559 msgid "mix group solo change" msgstr "grupo solo alterado" -#: route_ui.cc:586 +#: route_ui.cc:593 msgid "mix group mute change" msgstr "grupo mudo alterado" -#: route_ui.cc:602 +#: route_ui.cc:609 msgid "mix group rec-enable change" msgstr "grupo gravar alterado" -#: route_ui.cc:619 visual_time_axis.cc:236 +#: route_ui.cc:626 visual_time_axis.cc:237 msgid "ardour: color selection" msgstr "ardor: selecção de cor" -#: route_ui.cc:695 +#: route_ui.cc:702 #, fuzzy msgid "" "Do you really want to remove track \"%1\" ?\n" @@ -5895,7 +5924,7 @@ msgstr "" "A lista de reprodução em uso por esta faixa pode ficar perdida.\n" "(esta operação não pode ser desfeita)" -#: route_ui.cc:697 +#: route_ui.cc:704 msgid "" "Do you really want to remove bus \"%1\" ?\n" "(cannot be undone)" @@ -5903,11 +5932,11 @@ msgstr "" "Deseja realmente remover o barramento \"%1\" ?\n" "(esta operação não pode ser desfeita)" -#: route_ui.cc:701 visual_time_axis.cc:278 +#: route_ui.cc:708 visual_time_axis.cc:279 msgid "Yes, remove it." msgstr "Sim, remover." -#: route_ui.cc:730 +#: route_ui.cc:737 #, fuzzy msgid "New Name: " msgstr "novo nome: " @@ -5965,147 +5994,148 @@ msgstr "Não foi possível aceder ao ficheiros audio: " msgid "Name for Field" msgstr "Nome para a região:" -#: sfdb_ui.cc:333 +#: sfdb_ui.cc:335 msgid "Split Channels" msgstr "Separar Canais" -#: sfdb_ui.cc:340 +#: sfdb_ui.cc:342 msgid "Create a region for each channel" msgstr "" -#: sfdb_ui.cc:342 +#: sfdb_ui.cc:344 msgid "Embed" msgstr "" -#: sfdb_ui.cc:344 +#: sfdb_ui.cc:346 #, fuzzy msgid "Link to an external file" msgstr "Inserir ficheiro audio externo" -#: sfdb_ui.cc:346 +#: sfdb_ui.cc:348 msgid "Import" msgstr "Importar" -#: sfdb_ui.cc:348 +#: sfdb_ui.cc:350 msgid "Copy a file to the session folder" msgstr "" -#: sfdb_ui.cc:412 +#: sfdb_ui.cc:414 msgid "programming error: %1" msgstr "" -#: tempo_dialog.cc:17 tempo_dialog.cc:34 +#: tempo_dialog.cc:18 tempo_dialog.cc:35 msgid "Beats per minute" msgstr "Batimentos por minuto" -#: tempo_dialog.cc:20 tempo_dialog.cc:37 tempo_dialog.cc:153 -#: tempo_dialog.cc:171 +#: tempo_dialog.cc:21 tempo_dialog.cc:38 tempo_dialog.cc:203 +#: tempo_dialog.cc:221 msgid "Bar" msgstr "Compasso" -#: tempo_dialog.cc:21 tempo_dialog.cc:38 tempo_dialog.cc:154 -#: tempo_dialog.cc:172 +#: tempo_dialog.cc:22 tempo_dialog.cc:39 tempo_dialog.cc:204 +#: tempo_dialog.cc:222 msgid "Beat" msgstr "Batimento" -#: tempo_dialog.cc:23 tempo_dialog.cc:40 tempo_dialog.cc:155 -#: tempo_dialog.cc:173 +#: tempo_dialog.cc:24 tempo_dialog.cc:41 tempo_dialog.cc:205 +#: tempo_dialog.cc:223 msgid "Location" msgstr "Localização" -#: tempo_dialog.cc:149 tempo_dialog.cc:167 +#: tempo_dialog.cc:199 tempo_dialog.cc:217 msgid "Meter denominator" msgstr "Denominador métrico" -#: tempo_dialog.cc:150 tempo_dialog.cc:168 +#: tempo_dialog.cc:200 tempo_dialog.cc:218 msgid "Beats per bar" msgstr "Batimentos por compasso" -#: tempo_dialog.cc:186 tempo_dialog.cc:197 +#: tempo_dialog.cc:236 tempo_dialog.cc:247 msgid "whole (1)" msgstr "toda (1)" -#: tempo_dialog.cc:187 tempo_dialog.cc:199 +#: tempo_dialog.cc:237 tempo_dialog.cc:249 msgid "second (2)" msgstr "segunda (2)" -#: tempo_dialog.cc:188 tempo_dialog.cc:201 +#: tempo_dialog.cc:238 tempo_dialog.cc:251 msgid "third (3)" msgstr "terça (3)" -#: tempo_dialog.cc:189 tempo_dialog.cc:203 tempo_dialog.cc:211 +#: tempo_dialog.cc:239 tempo_dialog.cc:253 tempo_dialog.cc:261 msgid "quarter (4)" msgstr "quarta (4)" -#: tempo_dialog.cc:190 tempo_dialog.cc:205 +#: tempo_dialog.cc:240 tempo_dialog.cc:255 msgid "eighth (8)" msgstr "octogésima (8)" -#: tempo_dialog.cc:191 tempo_dialog.cc:207 +#: tempo_dialog.cc:241 tempo_dialog.cc:257 msgid "sixteenth (16)" msgstr "hexodécima (16)" -#: tempo_dialog.cc:192 tempo_dialog.cc:209 +#: tempo_dialog.cc:242 tempo_dialog.cc:259 msgid "thirty-second (32)" msgstr "trigésima-segunda (32)" -#: tempo_dialog.cc:321 +#: tempo_dialog.cc:420 msgid "garbaged note type entry (%1)" msgstr "tipo de nota desconhecido (%1)" -#: tempo_dialog.cc:331 +#: tempo_dialog.cc:430 msgid "incomprehensible note type entry (%1)" msgstr "tipo de nota imcompreensível (%1)" -#: time_axis_view.cc:111 +#: time_axis_view.cc:112 msgid "gTortnam" msgstr "" -#: time_axis_view.cc:548 +#: time_axis_view.cc:549 msgid "Largest" msgstr "Enorme" -#: time_axis_view.cc:549 +#: time_axis_view.cc:550 msgid "Large" msgstr "Grande" -#: time_axis_view.cc:550 +#: time_axis_view.cc:551 msgid "Larger" msgstr "Maior" -#: time_axis_view.cc:552 +#: time_axis_view.cc:553 msgid "Smaller" msgstr "Menor" -#: time_axis_view.cc:553 +#: time_axis_view.cc:554 msgid "Small" msgstr "Pequeno" -#: time_axis_view.cc:869 +#: time_axis_view.cc:870 msgid "unknown track height name \"%1\" in XML GUI information" msgstr "" -#: time_axis_view_item.cc:71 +#. first constructed item sets up font info +#: time_axis_view_item.cc:79 msgid "TimeAxisViewItemName" msgstr "" -#: time_axis_view_item.cc:271 +#: time_axis_view_item.cc:298 msgid "new duration %1 frames is out of bounds for %2" msgstr "" -#: time_selection.cc:40 +#: time_selection.cc:41 msgid "programming error: request for non-existent audio range (%1)!" msgstr "" -#: utils.cc:106 utils.cc:149 +#: utils.cc:107 utils.cc:150 msgid "bad XPM header %1" msgstr "" -#: utils.cc:331 +#: utils.cc:332 msgid "missing RGBA style for \"%1\"" msgstr "" -#: visual_time_axis.cc:275 +#: visual_time_axis.cc:276 msgid "" "Do you really want to remove track \"%1\" ?\n" "(cannot be undone)" @@ -6113,14 +6143,85 @@ msgstr "" "Deseja realmente remover o faixa \"%1\" ?\n" "(esta operação não pode ser desfeita)" -#: visual_time_axis.cc:324 +#: visual_time_axis.cc:325 msgid "new name: " msgstr "novo nome: " -#: visual_time_axis.cc:335 +#: visual_time_axis.cc:336 msgid "A track already exists with that name" msgstr "Já existe uma faixa com este nome" +#, fuzzy +#~ msgid "set selected trackview" +#~ msgstr "seleccionar visualização de faixa" + +#, fuzzy +#~ msgid "set selected control point" +#~ msgstr "remover ponto de controlo" + +#~ msgid "set selected regionview" +#~ msgstr "seleccionar visualização de região" + +#~ msgid "Start a new session\n" +#~ msgstr "Iniciar uma nova sessão\n" + +#~ msgid "via Session menu" +#~ msgstr "via menu de Sessão" + +#, fuzzy +#~ msgid "Advanced" +#~ msgstr "Avançado..." + +#, fuzzy +#~ msgid "Select a File" +#~ msgstr "Seleccionar tudo" + +#, fuzzy +#~ msgid "Track/Bus connection options" +#~ msgstr "Faixas/Barramentos" + +#~ msgid "RECORD" +#~ msgstr "GRAVAR" + +#~ msgid "INPUT" +#~ msgstr "ENTRADA" + +#~ msgid "OUTPUT" +#~ msgstr "SAÃDA" + +#~ msgid "Gain automation mode" +#~ msgstr "Modo de automatização de ganho" + +#~ msgid "Gain automation type" +#~ msgstr "Tipo de automatização de ganho" + +#~ msgid "trim" +#~ msgstr "recorte" + +#~ msgid "gain automation mode" +#~ msgstr "modo de automatização de ganho" + +#~ msgid "gain automation state" +#~ msgstr "ponto de automatização de ganho" + +#~ msgid "pan automation state" +#~ msgstr "ponto de automatização de panorâmica" + +#~ msgid "REC" +#~ msgstr "GRAV" + +#~ msgid "OUT" +#~ msgstr "SAÃDA" + +#~ msgid "aplay" +#~ msgstr "aRepr" + +#~ msgid "awrite" +#~ msgstr "aGrav" + +#~ msgid "no group" +#~ msgstr "sem grupo" + #, fuzzy #~ msgid "normal" #~ msgstr "Normal" @@ -6415,9 +6516,6 @@ msgstr "Já existe uma faixa com este nome" #~ msgid "AND" #~ msgstr "E" -#~ msgid "OR" -#~ msgstr "OU" - #~ msgid "ardour: locate soundfiles" #~ msgstr "ardour: localizar ficheiros audio" @@ -6433,9 +6531,6 @@ msgstr "Já existe uma faixa com este nome" #~ msgid "Ardour: Search Results" #~ msgstr "Ardour: Resultados da Procura" -#~ msgid "Mix Groups" -#~ msgstr "Grupos" - #~ msgid "Hide All AudioTrack MixerStrips" #~ msgstr "Esconder painéis de mistura de todas as faixas audio" @@ -6448,9 +6543,6 @@ msgstr "Já existe uma faixa com este nome" #~ msgid "Name for new mix group" #~ msgstr "Nome para o novo grupo de mistura" -#~ msgid "Session name:" -#~ msgstr "Nome de sessão:" - #~ msgid "Create" #~ msgstr "Criar" @@ -6488,19 +6580,12 @@ msgstr "Já existe uma faixa com este nome" #~ "Se pretende usar uma frequência de amostragem diferente\n" #~ "terá de sair e reiniciar o serviço JACK" -#, fuzzy -#~ msgid "Session template" -#~ msgstr "Modelo de sessão" - #~ msgid "blank" #~ msgstr "vazio" #~ msgid "No template - create tracks/busses manually" #~ msgstr "Sem modelo - criar faixas/barramentos manualmente" -#~ msgid "No template" -#~ msgstr "Sem modelo" - #~ msgid "Slave to MTC" #~ msgstr "Escravo MTC" @@ -6535,9 +6620,6 @@ msgstr "Já existe uma faixa com este nome" #~ msgid "Native Format" #~ msgstr "Formato Nativo" -#~ msgid "Use as click" -#~ msgstr "Usar como metrónomo" - #~ msgid "--unknown--" #~ msgstr "--desconhecido--" diff --git a/gtk2_ardour/po/ru_RU.po b/gtk2_ardour/po/ru_RU.po index 1bf84f864a..7d9e33695c 100644 --- a/gtk2_ardour/po/ru_RU.po +++ b/gtk2_ardour/po/ru_RU.po @@ -6,7 +6,7 @@ msgid "" msgstr "" "Project-Id-Version: gtk-ardour 0.413.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-04-25 17:46-0400\n" +"POT-Creation-Date: 2006-06-21 18:09-0400\n" "PO-Revision-Date: 2004-03-31 00:45+0300\n" "Last-Translator: Igor Blinov pitstop@nm.ru\n" "Language-Team: Russian\n" @@ -14,203 +14,203 @@ msgstr "" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" -#: about.cc:119 +#: about.cc:120 msgid "Paul Davis" msgstr "" -#: about.cc:120 +#: about.cc:121 #, fuzzy msgid "Jesse Chappell" msgstr "ОгромнаÑ" -#: about.cc:121 +#: about.cc:122 msgid "Taybin Rutkin" msgstr "" -#: about.cc:122 +#: about.cc:123 msgid "Marcus Andersson" msgstr "" -#: about.cc:123 +#: about.cc:124 msgid "Jeremy Hall" msgstr "" -#: about.cc:124 +#: about.cc:125 msgid "Steve Harris" msgstr "" -#: about.cc:125 +#: about.cc:126 msgid "Tim Mayberry" msgstr "" -#: about.cc:126 +#: about.cc:127 msgid "Mark Stewart" msgstr "" -#: about.cc:127 +#: about.cc:128 msgid "Sam Chessman" msgstr "" -#: about.cc:128 +#: about.cc:129 msgid "Jack O'Quin" msgstr "" -#: about.cc:129 +#: about.cc:130 msgid "Matt Krai" msgstr "" -#: about.cc:130 +#: about.cc:131 msgid "Ben Bell" msgstr "" -#: about.cc:131 +#: about.cc:132 msgid "Gerard van Dongen" msgstr "" -#: about.cc:132 +#: about.cc:133 msgid "Thomas Charbonnel" msgstr "" -#: about.cc:133 +#: about.cc:134 msgid "Nick Mainsbridge" msgstr "" -#: about.cc:134 +#: about.cc:135 msgid "Colin Law" msgstr "" -#: about.cc:135 +#: about.cc:136 msgid "Sampo Savolainen" msgstr "" -#: about.cc:136 +#: about.cc:137 msgid "Joshua Leach" msgstr "" -#: about.cc:137 +#: about.cc:138 msgid "Rob Holland" msgstr "" -#: about.cc:138 +#: about.cc:139 msgid "Per Sigmond" msgstr "" -#: about.cc:139 +#: about.cc:140 msgid "Doug Mclain" msgstr "" -#: about.cc:140 +#: about.cc:141 msgid "Petter Sundlöf" msgstr "" -#: about.cc:145 +#: about.cc:146 msgid "" "French:\n" "\tAlain Fréhel \n" msgstr "" -#: about.cc:146 +#: about.cc:147 msgid "" "German:\n" "\tKarsten Petersen \n" msgstr "" -#: about.cc:147 +#: about.cc:148 msgid "" "Italian:\n" "\tFilippo Pappalardo \n" msgstr "" -#: about.cc:148 +#: about.cc:149 msgid "" "Portuguese:\n" "\tRui Nuno Capela \n" msgstr "" -#: about.cc:149 +#: about.cc:150 msgid "" "Brazilian Portuguese:\n" "\tAlexander da Franca Fernandes \n" "\tChris Ross \n" msgstr "" -#: about.cc:151 +#: about.cc:152 msgid "" "Spanish:\n" "\t Alex Krohn \n" msgstr "" -#: about.cc:152 +#: about.cc:153 msgid "" "Russian:\n" "\t Igor Blinov \n" msgstr "" -#: about.cc:180 +#: about.cc:181 #, fuzzy msgid "Copyright (C) 1999-2005 Paul Davis\n" msgstr "ÐвторÑкое право 1999-2004 Paul Davis" -#: about.cc:181 +#: about.cc:182 msgid "" "Ardour comes with ABSOLUTELY NO WARRANTY\n" "This is free software, and you are welcome to redistribute it\n" "under certain conditions; see the file COPYING for details.\n" msgstr "" -#: about.cc:187 +#: about.cc:188 msgid "" "%1\n" "(built with ardour/gtk %2.%3.%4 libardour: %5.%6.%7)" msgstr "" -#: actions.cc:260 +#: actions.cc:261 #, fuzzy msgid "programmer error: %1 %2" msgstr "ошибка в программе: " -#: add_route_dialog.cc:61 +#: add_route_dialog.cc:62 msgid "ardour: add track/bus" msgstr "ardour: добавить трек/шину" #. path = "1" -#: add_route_dialog.cc:62 editor_route_list.cc:72 +#: add_route_dialog.cc:63 editor_route_list.cc:73 msgid "Tracks" msgstr "Треки" #. path = "0" -#: add_route_dialog.cc:63 editor_route_list.cc:69 +#: add_route_dialog.cc:64 editor_route_list.cc:70 msgid "Busses" msgstr "Шины" -#: add_route_dialog.cc:95 plugin_ui.cc:832 +#: add_route_dialog.cc:96 plugin_ui.cc:833 msgid "Add" msgstr "Добавить" -#: add_route_dialog.cc:113 +#: add_route_dialog.cc:114 msgid "Name (template)" msgstr "Ð˜Ð¼Ñ (шаблона)" -#: add_route_dialog.cc:119 +#: add_route_dialog.cc:120 #, fuzzy msgid "Channel Configuration" msgstr "Отменить импорт" -#: add_route_dialog.cc:176 editor.cc:131 editor.cc:3660 time_axis_view.cc:551 +#: add_route_dialog.cc:177 editor.cc:134 editor.cc:3688 time_axis_view.cc:552 msgid "Normal" msgstr "Ðорм." -#: add_route_dialog.cc:178 +#: add_route_dialog.cc:179 #, fuzzy msgid "Tape" msgstr "Ðачало" -#: add_route_dialog.cc:195 +#: add_route_dialog.cc:196 #, fuzzy msgid "Mono" msgstr "моно" -#: add_route_dialog.cc:197 +#: add_route_dialog.cc:198 #, fuzzy msgid "Stereo" msgstr "Ñтерео" @@ -292,27 +292,11 @@ msgstr "КОÐТРОЛЬ" msgid "SOLO" msgstr "СОЛО" -#: ardour_ui.cc:207 -msgid "" -"You cannot record-enable\n" -"track %1\n" -"because it has no input connections.\n" -"You would be wasting space recording silence." -msgstr "" - -#: ardour_ui.cc:236 -msgid "no vertical meter strip image found" -msgstr "" - -#: ardour_ui.cc:243 -msgid "no horizontal meter strip image found" -msgstr "" - -#: ardour_ui.cc:410 +#: ardour_ui.cc:375 msgid "quit" msgstr "выйти" -#: ardour_ui.cc:419 +#: ardour_ui.cc:384 msgid "" "Ardour was unable to save your session.\n" "\n" @@ -321,33 +305,33 @@ msgid "" "\"Just quit\" option." msgstr "" -#: ardour_ui.cc:438 +#: ardour_ui.cc:403 msgid "ardour: save session?" msgstr "ardour: Ñохранить ÑеÑÑию?" -#: ardour_ui.cc:445 +#: ardour_ui.cc:410 msgid "Don't %1" msgstr "Отмена" -#: ardour_ui.cc:447 +#: ardour_ui.cc:412 msgid "Just %1" msgstr "Да, %1" -#: ardour_ui.cc:449 +#: ardour_ui.cc:414 msgid "Save and %1" msgstr "Сохранить и %1" -#: ardour_ui.cc:461 +#: ardour_ui.cc:426 #, fuzzy msgid "session" msgstr "СеÑÑиÑ" -#: ardour_ui.cc:463 +#: ardour_ui.cc:428 #, fuzzy msgid "snapshot" msgstr "Снимок" -#: ardour_ui.cc:465 +#: ardour_ui.cc:430 #, fuzzy msgid "" "The %1\"%2\"\n" @@ -366,80 +350,80 @@ msgstr "" "\n" "Что Ð’Ñ‹ хотите Ñделать?" -#: ardour_ui.cc:479 +#: ardour_ui.cc:444 msgid "Prompter" msgstr "" -#: ardour_ui.cc:538 +#: ardour_ui.cc:503 #, fuzzy, c-format msgid "disconnected" msgstr "ОтÑоединить" -#: ardour_ui.cc:545 +#: ardour_ui.cc:510 #, fuzzy, c-format msgid "SR: %.1f kHz / %4.1f msecs" msgstr "SR: %.1f кГц" -#: ardour_ui.cc:549 +#: ardour_ui.cc:514 #, c-format msgid "SR: %u kHz / %4.1f msecs" msgstr "" -#: ardour_ui.cc:562 +#: ardour_ui.cc:527 #, c-format msgid "DSP Load: %.1f%%" msgstr "Загрузка DSP: %.1f%%" -#: ardour_ui.cc:572 +#: ardour_ui.cc:537 #, fuzzy, c-format msgid "Buffers p:%%% c:%%%" msgstr "Буферы p:%5.0f%% c:%5.0f%%" -#: ardour_ui.cc:599 +#: ardour_ui.cc:564 msgid "space: 24hrs+" msgstr "меÑто на диÑке: 24 чаÑа +" -#: ardour_ui.cc:629 +#: ardour_ui.cc:594 #, c-format msgid "space: %02dh:%02dm:%02ds" msgstr "Ñвободное меÑто: %02dч:%02dмин:%02dÑек" -#: ardour_ui.cc:668 +#: ardour_ui.cc:633 msgid "programming error: impossible control method" msgstr "ошибка в программе: impossible control method" -#: ardour_ui.cc:776 new_session_dialog.cc:89 +#: ardour_ui.cc:741 new_session_dialog.cc:294 #, fuzzy msgid "Recent Sessions" msgstr "открыть ÑеÑÑию" #. ardour sessions are folders -#: ardour_ui.cc:867 +#: ardour_ui.cc:834 msgid "open session" msgstr "открыть ÑеÑÑию" -#: ardour_ui.cc:873 +#: ardour_ui.cc:840 #, fuzzy msgid "Ardour sessions" msgstr "ardour_новаÑ_ÑеÑÑиÑ" -#: ardour_ui.cc:906 +#: ardour_ui.cc:873 msgid "Patience is a virtue.\n" msgstr "По нитке дойдёшь и до клубка.\n" -#: ardour_ui.cc:915 +#: ardour_ui.cc:882 msgid "You cannot add a track without a session already loaded." msgstr "Ð’Ñ‹ не можете добавить трек пока ÑеÑÑÐ¸Ñ Ð½Ðµ загружена." -#: ardour_ui.cc:922 +#: ardour_ui.cc:889 msgid "could not create new audio track" msgstr "не удалоÑÑŒ Ñоздать новый аудиотрек" -#: ardour_ui.cc:926 +#: ardour_ui.cc:893 msgid "could not create new audio bus" msgstr "не удалоÑÑŒ Ñоздать новую аудиошину" -#: ardour_ui.cc:945 +#: ardour_ui.cc:912 msgid "" "There are insufficient JACK ports available\n" "to create a new track or bus.\n" @@ -447,14 +431,14 @@ msgid "" "restart JACK with more ports." msgstr "" -#: ardour_ui.cc:1069 +#: ardour_ui.cc:1036 msgid "" "Please create 1 or more track\n" "before trying to record.\n" "Check the Session menu." msgstr "" -#: ardour_ui.cc:1298 +#: ardour_ui.cc:1265 #, fuzzy msgid "" "JACK has either been shutdown or it\n" @@ -467,57 +451,55 @@ msgstr "" "Ðеобходимо Ñохранить ÑеÑÑию и\n" "перезапуÑтить JACK и Ardour." -#: ardour_ui.cc:1315 +#: ardour_ui.cc:1282 msgid "Unable to create all required ports" msgstr "" -#: ardour_ui.cc:1323 +#: ardour_ui.cc:1290 #, fuzzy msgid "Unable to start the session running" msgstr "Ð’ начало ÑеÑÑии" -#: ardour_ui.cc:1459 +#: ardour_ui.cc:1426 msgid "No Stream" msgstr "Ðет потока" -#: ardour_ui.cc:1486 ardour_ui.cc:1505 +#: ardour_ui.cc:1453 ardour_ui.cc:1472 msgid "none" msgstr "нет" -#: ardour_ui.cc:1495 ardour_ui.cc:1514 automation_time_axis.cc:183 -#: automation_time_axis.cc:212 automation_time_axis.cc:459 mixer_strip.cc:174 -#: mixer_strip.cc:186 mixer_strip.cc:881 plugin_ui.cc:391 plugin_ui.cc:634 +#: ardour_ui.cc:1462 ardour_ui.cc:1481 msgid "off" msgstr "выкл" -#: ardour_ui.cc:1538 +#: ardour_ui.cc:1505 #, fuzzy msgid "Name of New Snapshot" msgstr "Ð˜Ð¼Ñ Ñнимка" -#: ardour_ui.cc:1684 +#: ardour_ui.cc:1651 msgid "Name for mix template:" msgstr "Ð˜Ð¼Ñ mix-шаблона:" -#: ardour_ui.cc:1685 +#: ardour_ui.cc:1652 msgid "-template" msgstr "-шаблон" -#: ardour_ui.cc:1836 +#: ardour_ui.cc:1809 msgid "" "You do not have write access to this session.\n" "This prevents the session from being loaded." msgstr "" -#: ardour_ui.cc:1849 ardour_ui.cc:1904 +#: ardour_ui.cc:1822 ardour_ui.cc:1877 msgid "Session \"%1 (snapshot %2)\" did not load successfully" msgstr "Ðе удалоÑÑŒ загрузить ÑеÑÑию \"%1 (Ñнимок %2)\"" -#: ardour_ui.cc:1960 +#: ardour_ui.cc:1933 msgid "No audio files were ready for cleanup" msgstr "" -#: ardour_ui.cc:1964 +#: ardour_ui.cc:1937 msgid "" "If this seems suprising, \n" "check for any existing snapshots.\n" @@ -525,23 +507,23 @@ msgid "" "require some unused files to continue to exist." msgstr "" -#: ardour_ui.cc:1973 +#: ardour_ui.cc:1946 msgid "ardour: cleanup" msgstr "ardour: очиÑтка" -#: ardour_ui.cc:2009 ardour_ui.cc:2015 +#: ardour_ui.cc:1982 ardour_ui.cc:1988 msgid "files were" msgstr "" -#: ardour_ui.cc:2011 ardour_ui.cc:2017 +#: ardour_ui.cc:1984 ardour_ui.cc:1990 msgid "file was" msgstr "" -#: ardour_ui.cc:2058 +#: ardour_ui.cc:2031 msgid "Are you sure you want to cleanup?" msgstr "" -#: ardour_ui.cc:2063 +#: ardour_ui.cc:2036 msgid "" "Cleanup is a destructive operation.\n" "ALL undo/redo information will be lost if you cleanup.\n" @@ -549,26 +531,26 @@ msgid "" "location." msgstr "" -#: ardour_ui.cc:2069 +#: ardour_ui.cc:2042 #, fuzzy msgid "Clean Up" msgstr "ОчиÑтка" -#: ardour_ui.cc:2072 +#: ardour_ui.cc:2045 #, fuzzy msgid "CleanupDialog" msgstr "ОчиÑтка" -#: ardour_ui.cc:2073 +#: ardour_ui.cc:2046 #, fuzzy msgid "ardour_cleanup" msgstr "ardour: очиÑтка" -#: ardour_ui.cc:2092 +#: ardour_ui.cc:2065 msgid "cleaned files" msgstr "" -#: ardour_ui.cc:2093 +#: ardour_ui.cc:2066 #, fuzzy msgid "" "The following %1 %2 not in use and \n" @@ -583,12 +565,12 @@ msgstr "" "ПоÑÐ»ÐµÐ´ÑƒÑŽÑ‰Ð°Ñ Ð¾Ñ‡Ð¸Ñтка корзины оÑвободит\n" "%2 мегабайт меÑта на диÑке." -#: ardour_ui.cc:2118 +#: ardour_ui.cc:2091 #, fuzzy msgid "deleted file" msgstr "удалённые файлы" -#: ardour_ui.cc:2119 +#: ardour_ui.cc:2092 #, fuzzy msgid "" "The following %1 %2 deleted from\n" @@ -597,11 +579,11 @@ msgid "" msgstr "" "Следующие %1 файлов были удалены, оÑвободив при Ñтом %2 Мб меÑта на диÑке" -#: ardour_ui.cc:2242 +#: ardour_ui.cc:2215 msgid "Recording was stopped because your system could not keep up." msgstr "ЗапиÑÑŒ оÑтановлена из-за недоÑтаточного быÑтродейÑÑ‚Ð²Ð¸Ñ ÑиÑтемы" -#: ardour_ui.cc:2265 +#: ardour_ui.cc:2238 msgid "" "The disk system on your computer\n" "was not able to keep up with Ardour.\n" @@ -610,7 +592,7 @@ msgid "" "quickly enough to keep up with recording.\n" msgstr "" -#: ardour_ui.cc:2284 +#: ardour_ui.cc:2257 msgid "" "The disk system on your computer\n" "was not able to keep up with Ardour.\n" @@ -619,7 +601,7 @@ msgid "" "quickly enough to keep up with playback.\n" msgstr "" -#: ardour_ui.cc:2310 +#: ardour_ui.cc:2283 msgid "" "This session appears to have been in\n" "middle of recording when ardour or\n" @@ -630,365 +612,365 @@ msgid "" "what you would like to do.\n" msgstr "" -#: ardour_ui.cc:2320 +#: ardour_ui.cc:2293 msgid "Recover from crash" msgstr "" -#: ardour_ui.cc:2321 +#: ardour_ui.cc:2294 msgid "Ignore crash data" msgstr "" -#: ardour_ui.cc:2339 +#: ardour_ui.cc:2312 #, fuzzy msgid "Could not disconnect from JACK" msgstr "Ðе удалоÑÑŒ ÑоединитьÑÑ Ñ Ñервером JACK как \"%1\"" -#: ardour_ui.cc:2352 +#: ardour_ui.cc:2325 #, fuzzy msgid "Could not reconnect to JACK" msgstr "Ðе удалоÑÑŒ ÑоединитьÑÑ Ñ Ñервером JACK как \"%1\"" -#: ardour_ui2.cc:59 +#: ardour_ui2.cc:60 msgid "UI: cannot setup editor" msgstr "ИнтерфейÑ: не удалоÑÑŒ инициализировать редактор" -#: ardour_ui2.cc:64 +#: ardour_ui2.cc:65 msgid "UI: cannot setup mixer" msgstr "ИнтерфейÑ: не удалоÑÑŒ инициализировать микшер" -#: ardour_ui2.cc:90 +#: ardour_ui2.cc:91 msgid "MMC + Local" msgstr "" -#: ardour_ui2.cc:91 +#: ardour_ui2.cc:92 msgid "MMC" msgstr "MMC" -#: ardour_ui2.cc:92 +#: ardour_ui2.cc:93 msgid "Local" msgstr "" -#: ardour_ui2.cc:109 +#: ardour_ui2.cc:110 msgid "MMC ID" msgstr "MMC идентификатор" -#: ardour_ui2.cc:290 +#: ardour_ui2.cc:291 msgid "Play from playhead" msgstr "ВоÑпроизвеÑти от указателÑ" -#: ardour_ui2.cc:291 +#: ardour_ui2.cc:292 msgid "Stop playback" msgstr "Стоп" -#: ardour_ui2.cc:292 +#: ardour_ui2.cc:293 #, fuzzy msgid "Play range/selection" msgstr "ВоÑпроизвеÑти выделенное" -#: ardour_ui2.cc:293 +#: ardour_ui2.cc:294 msgid "Go to start of session" msgstr "Ð’ начало ÑеÑÑии" -#: ardour_ui2.cc:294 +#: ardour_ui2.cc:295 msgid "Go to end of session" msgstr "Ð’ конец ÑеÑÑии" -#: ardour_ui2.cc:295 +#: ardour_ui2.cc:296 msgid "Play loop range" msgstr "ВоÑпроизвеÑти \"кольцо\"" -#: ardour_ui2.cc:296 +#: ardour_ui2.cc:297 msgid "Return to last playback start when stopped" msgstr "ВернутьÑÑ Ðº точке начала воÑпроизведениÑ" -#: ardour_ui2.cc:297 +#: ardour_ui2.cc:298 msgid "Start playback after any locate" msgstr "" -#: ardour_ui2.cc:298 +#: ardour_ui2.cc:299 msgid "Be sensible about input monitoring" msgstr "" -#: ardour_ui2.cc:299 +#: ardour_ui2.cc:300 msgid "Start recording at auto-punch start" msgstr "Ðачать запиÑÑŒ Ñ Ð½Ð°Ñ‡Ð°Ð»Ð° \"авто-врезки\"" -#: ardour_ui2.cc:300 +#: ardour_ui2.cc:301 msgid "Stop recording at auto-punch end" msgstr "ОÑтановить запиÑÑŒ в конце \"авто-врезки\"" -#: ardour_ui2.cc:301 +#: ardour_ui2.cc:302 msgid "Enable/Disable audio click" msgstr "Вкл./Выкл. метроном" -#: ardour_ui2.cc:302 +#: ardour_ui2.cc:303 msgid "Positional sync source" msgstr "" -#: ardour_ui2.cc:303 +#: ardour_ui2.cc:304 msgid "Does Ardour control the time?" msgstr "" -#: ardour_ui2.cc:304 +#: ardour_ui2.cc:305 msgid "Shuttle speed control" msgstr "" -#: ardour_ui2.cc:305 +#: ardour_ui2.cc:306 #, c-format msgid "Select semitones or %%-age for speed display" msgstr "" -#: ardour_ui2.cc:306 +#: ardour_ui2.cc:307 msgid "Current transport speed" msgstr "ТекщаÑÑ ÑкорÑть транÑпорта" -#: ardour_ui2.cc:329 +#: ardour_ui2.cc:330 msgid "Primary clock" msgstr "ОÑновной Ñчётчик" -#: ardour_ui2.cc:330 +#: ardour_ui2.cc:331 msgid "secondary clock" msgstr "дополнительный Ñчётчик" #. XXX: this should really be saved in instant.xml or something similar and restored from there #. Combo's are stupid - they steal space from the entry for the button -#: ardour_ui2.cc:387 ardour_ui2.cc:823 ardour_ui2.cc:836 ardour_ui2.cc:899 -#: ardour_ui2.cc:901 +#: ardour_ui2.cc:388 ardour_ui2.cc:833 ardour_ui2.cc:846 ardour_ui2.cc:909 +#: ardour_ui2.cc:911 msgid "sprung" msgstr "" -#: ardour_ui2.cc:388 ardour_ui2.cc:825 ardour_ui2.cc:847 +#: ardour_ui2.cc:389 ardour_ui2.cc:835 ardour_ui2.cc:857 msgid "wheel" msgstr "" -#: ardour_ui2.cc:450 +#: ardour_ui2.cc:451 msgid "ardour: clock" msgstr "ardour: Ñчётчик" -#: ardour_ui2.cc:595 +#: ardour_ui2.cc:596 msgid "Maximum speed" msgstr "" -#: ardour_ui2.cc:813 +#: ardour_ui2.cc:823 msgid "st" msgstr "" -#: ardour_ui2.cc:857 ardour_ui2.cc:880 ardour_ui2.cc:897 +#: ardour_ui2.cc:867 ardour_ui2.cc:890 ardour_ui2.cc:907 msgid "stopped" msgstr "оÑтановлено" -#: ardour_ui_dialogs.cc:152 playlist_selector.cc:69 +#: ardour_ui_dialogs.cc:153 playlist_selector.cc:70 #, fuzzy msgid "close" msgstr "Закрыть" -#: ardour_ui_dialogs.cc:359 ardour_ui_ed.cc:181 +#: ardour_ui_dialogs.cc:360 ardour_ui_ed.cc:184 #, fuzzy msgid "Sound File Browser" msgstr "Ðудио-библиотека" #. menus + submenus that need action items -#: ardour_ui_ed.cc:69 +#: ardour_ui_ed.cc:72 msgid "Session" msgstr "СеÑÑиÑ" -#: ardour_ui_ed.cc:70 ardour_ui_ed.cc:127 editor.cc:1843 export_dialog.cc:350 +#: ardour_ui_ed.cc:73 ardour_ui_ed.cc:130 editor.cc:1836 export_dialog.cc:350 #: export_dialog.cc:1059 export_dialog.cc:1063 msgid "Export" msgstr "ЭкÑпорт" -#: ardour_ui_ed.cc:71 +#: ardour_ui_ed.cc:74 msgid "Cleanup" msgstr "ОчиÑтка" -#: ardour_ui_ed.cc:72 option_editor.cc:125 +#: ardour_ui_ed.cc:75 option_editor.cc:126 msgid "Sync" msgstr "Синхр." -#: ardour_ui_ed.cc:73 ardour_ui_ed.cc:74 +#: ardour_ui_ed.cc:76 ardour_ui_ed.cc:77 #, fuzzy msgid "Options" msgstr "Редактор параметров" -#: ardour_ui_ed.cc:75 +#: ardour_ui_ed.cc:78 msgid "Help" msgstr "" -#: ardour_ui_ed.cc:76 +#: ardour_ui_ed.cc:79 msgid "KeyMouse Actions" msgstr "" -#: ardour_ui_ed.cc:77 +#: ardour_ui_ed.cc:80 #, fuzzy msgid "Audio File Format" msgstr "Ðудио кадры" -#: ardour_ui_ed.cc:78 +#: ardour_ui_ed.cc:81 #, fuzzy msgid "Header" msgstr "Пред фейдер" -#: ardour_ui_ed.cc:79 +#: ardour_ui_ed.cc:82 msgid "Data" msgstr "" -#: ardour_ui_ed.cc:80 +#: ardour_ui_ed.cc:83 #, fuzzy msgid "Control Surfaces" msgstr "Контрольные выходы" #. the real actions -#: ardour_ui_ed.cc:84 audio_time_axis.cc:1856 new_session_dialog.cc:342 +#: ardour_ui_ed.cc:87 audio_time_axis.cc:1854 new_session_dialog.cc:529 msgid "New" msgstr "Ðовый" -#: ardour_ui_ed.cc:86 new_session_dialog.cc:334 +#: ardour_ui_ed.cc:89 new_session_dialog.cc:517 msgid "Open" msgstr "Открыть" -#: ardour_ui_ed.cc:87 +#: ardour_ui_ed.cc:90 msgid "Recent" msgstr "ПоÑледние" -#: ardour_ui_ed.cc:88 io_selector.cc:57 io_selector.cc:791 +#: ardour_ui_ed.cc:91 io_selector.cc:58 io_selector.cc:792 msgid "Close" msgstr "Закрыть" -#: ardour_ui_ed.cc:91 route_params_ui.cc:512 +#: ardour_ui_ed.cc:94 route_params_ui.cc:514 msgid "Add Track/Bus" msgstr "Добавить Трек/Шину" -#: ardour_ui_ed.cc:102 +#: ardour_ui_ed.cc:105 msgid "Connect" msgstr "Соединить" #. -#: ardour_ui_ed.cc:110 +#: ardour_ui_ed.cc:113 msgid "Snapshot" msgstr "Снимок" -#: ardour_ui_ed.cc:113 +#: ardour_ui_ed.cc:116 msgid "Save Template..." msgstr "Сохранить шаблон..." -#: ardour_ui_ed.cc:116 +#: ardour_ui_ed.cc:119 msgid "Export session to audiofile..." msgstr "ЭкÑпорт ÑеÑÑии в аудиофайл..." -#: ardour_ui_ed.cc:119 +#: ardour_ui_ed.cc:122 #, fuzzy msgid "Export selection to audiofile..." msgstr "ЭкÑпорт ÑеÑÑии в аудиофайл..." -#: ardour_ui_ed.cc:123 +#: ardour_ui_ed.cc:126 #, fuzzy msgid "Export range markers to audiofile..." msgstr "ЭкÑпорт ÑеÑÑии в аудиофайл..." -#: ardour_ui_ed.cc:130 +#: ardour_ui_ed.cc:133 msgid "Cleanup unused sources" msgstr "" -#: ardour_ui_ed.cc:132 +#: ardour_ui_ed.cc:135 msgid "Flush wastebasket" msgstr "ОчиÑтить корзину" -#: ardour_ui_ed.cc:138 ardour_ui_options.cc:381 ardour_ui_options.cc:390 -#: ardour_ui_options.cc:462 +#: ardour_ui_ed.cc:141 ardour_ui_options.cc:408 ardour_ui_options.cc:417 +#: ardour_ui_options.cc:489 msgid "JACK" msgstr "JACK" -#: ardour_ui_ed.cc:139 +#: ardour_ui_ed.cc:142 msgid "Latency" msgstr "" -#: ardour_ui_ed.cc:141 +#: ardour_ui_ed.cc:144 #, fuzzy msgid "Reconnect" msgstr "Соединить" -#: ardour_ui_ed.cc:144 mixer_strip.cc:514 mixer_strip.cc:574 +#: ardour_ui_ed.cc:147 mixer_strip.cc:497 mixer_strip.cc:565 msgid "Disconnect" msgstr "ОтÑоединить" -#: ardour_ui_ed.cc:171 +#: ardour_ui_ed.cc:174 msgid "Windows" msgstr "Окна" -#: ardour_ui_ed.cc:172 +#: ardour_ui_ed.cc:175 msgid "start prefix" msgstr "" -#: ardour_ui_ed.cc:173 +#: ardour_ui_ed.cc:176 msgid "Quit" msgstr "Выйти" #. windows visibility actions -#: ardour_ui_ed.cc:177 +#: ardour_ui_ed.cc:180 msgid "Maximise Editor Space" msgstr "" -#: ardour_ui_ed.cc:179 +#: ardour_ui_ed.cc:182 #, fuzzy msgid "Show Editor" msgstr "Редактор" -#: ardour_ui_ed.cc:180 +#: ardour_ui_ed.cc:183 #, fuzzy msgid "Show Mixer" msgstr "Микшер" -#: ardour_ui_ed.cc:182 +#: ardour_ui_ed.cc:185 msgid "Options Editor" msgstr "Редактор параметров" -#: ardour_ui_ed.cc:183 +#: ardour_ui_ed.cc:186 #, fuzzy msgid "Track/Bus Inspector" msgstr "Треки/Шины" -#: ardour_ui_ed.cc:185 +#: ardour_ui_ed.cc:188 msgid "Connections" msgstr "СоединениÑ" -#: ardour_ui_ed.cc:187 +#: ardour_ui_ed.cc:190 msgid "Locations" msgstr "Интервалы" -#: ardour_ui_ed.cc:189 +#: ardour_ui_ed.cc:192 msgid "Big Clock" msgstr "Большой Ñчётчик" -#: ardour_ui_ed.cc:191 +#: ardour_ui_ed.cc:194 msgid "About" msgstr "О программе" -#: ardour_ui_ed.cc:192 +#: ardour_ui_ed.cc:195 #, fuzzy msgid "Colors" msgstr "Цвет" -#: ardour_ui_ed.cc:194 +#: ardour_ui_ed.cc:197 #, fuzzy msgid "Add Audio Track" msgstr "Добавить Трек/Шину" -#: ardour_ui_ed.cc:196 +#: ardour_ui_ed.cc:199 #, fuzzy msgid "Add Audio Bus" msgstr "Скрыть вÑе аудиошины" -#: ardour_ui_ed.cc:198 +#: ardour_ui_ed.cc:201 msgid "Save" msgstr "Сохранить" -#: ardour_ui_ed.cc:200 editor_actions.cc:254 +#: ardour_ui_ed.cc:203 editor_actions.cc:255 #, fuzzy msgid "Remove Last Capture" msgstr "Удалить поÑледнюю запиÑÑŒ" #. do-nothing action for the "transport" menu bar item -#: ardour_ui_ed.cc:207 +#: ardour_ui_ed.cc:210 #, fuzzy msgid "Transport" msgstr "Triangular" @@ -996,73 +978,73 @@ msgstr "Triangular" #. these two are not used by key bindings, instead use ToggleRoll for that. these two do show up in #. menus and via button proxies. #. -#: ardour_ui_ed.cc:213 sfdb_ui.cc:57 +#: ardour_ui_ed.cc:216 sfdb_ui.cc:57 msgid "Stop" msgstr "Стоп" -#: ardour_ui_ed.cc:216 +#: ardour_ui_ed.cc:219 msgid "Roll" msgstr "" -#: ardour_ui_ed.cc:220 +#: ardour_ui_ed.cc:223 #, fuzzy msgid "Start/Stop" msgstr "Ðачало:" -#: ardour_ui_ed.cc:223 +#: ardour_ui_ed.cc:226 msgid "Stop + Forget Capture" msgstr "" -#: ardour_ui_ed.cc:226 +#: ardour_ui_ed.cc:229 #, fuzzy msgid "Play Loop Range" msgstr "ВоÑпроизвеÑти \"кольцо\"" -#: ardour_ui_ed.cc:229 +#: ardour_ui_ed.cc:232 #, fuzzy msgid "Play Selection" msgstr "ВоÑпроизвеÑти выделенную облаÑть" -#: ardour_ui_ed.cc:233 +#: ardour_ui_ed.cc:236 #, fuzzy msgid "Enable Record" msgstr "ЗапиÑÑŒ" -#: ardour_ui_ed.cc:236 +#: ardour_ui_ed.cc:239 #, fuzzy msgid "Rewind" msgstr "ОблаÑть" -#: ardour_ui_ed.cc:239 +#: ardour_ui_ed.cc:242 msgid "Rewind (Slow)" msgstr "" -#: ardour_ui_ed.cc:242 +#: ardour_ui_ed.cc:245 msgid "Rewind (Fast)" msgstr "" -#: ardour_ui_ed.cc:245 +#: ardour_ui_ed.cc:248 msgid "Forward" msgstr "" -#: ardour_ui_ed.cc:248 +#: ardour_ui_ed.cc:251 msgid "Forward (Slow)" msgstr "" -#: ardour_ui_ed.cc:251 +#: ardour_ui_ed.cc:254 msgid "Forward (Fast)" msgstr "" -#: ardour_ui_ed.cc:254 +#: ardour_ui_ed.cc:257 msgid "Goto Zero" msgstr "" -#: ardour_ui_ed.cc:257 +#: ardour_ui_ed.cc:260 #, fuzzy msgid "Goto Start" msgstr "Ðачало:" -#: ardour_ui_ed.cc:260 +#: ardour_ui_ed.cc:263 msgid "Goto End" msgstr "" @@ -1070,7 +1052,7 @@ msgstr "" #. that proxies for these action to be more compact. It would be nice to find a way to override the action #. name appearance on the buttons. #. -#: ardour_ui_ed.cc:269 +#: ardour_ui_ed.cc:272 #, fuzzy msgid "" "Punch\n" @@ -1079,7 +1061,7 @@ msgstr "" "врезка\n" "до" -#: ardour_ui_ed.cc:272 +#: ardour_ui_ed.cc:275 #, fuzzy msgid "" "Punch\n" @@ -1088,11 +1070,11 @@ msgstr "" "врезка\n" "поÑле" -#: ardour_ui_ed.cc:275 option_editor.cc:128 +#: ardour_ui_ed.cc:278 option_editor.cc:129 msgid "Click" msgstr "Метроном" -#: ardour_ui_ed.cc:278 +#: ardour_ui_ed.cc:281 #, fuzzy msgid "" "Auto\n" @@ -1101,7 +1083,7 @@ msgstr "" "авто\n" "вход" -#: ardour_ui_ed.cc:281 +#: ardour_ui_ed.cc:284 #, fuzzy msgid "" "Auto\n" @@ -1110,7 +1092,7 @@ msgstr "" "авто\n" "воÑпр." -#: ardour_ui_ed.cc:284 +#: ardour_ui_ed.cc:287 #, fuzzy msgid "" "Auto\n" @@ -1119,284 +1101,284 @@ msgstr "" "авто\n" "возврат" -#: ardour_ui_ed.cc:288 +#: ardour_ui_ed.cc:291 #, fuzzy msgid "" "Time\n" "master" msgstr "JACK-Ñчётчик - маÑтер" -#: ardour_ui_ed.cc:291 +#: ardour_ui_ed.cc:294 msgid "Toggle Record Enable Track1" msgstr "" -#: ardour_ui_ed.cc:293 +#: ardour_ui_ed.cc:296 msgid "Toggle Record Enable Track2" msgstr "" -#: ardour_ui_ed.cc:295 +#: ardour_ui_ed.cc:298 msgid "Toggle Record Enable Track3" msgstr "" -#: ardour_ui_ed.cc:297 +#: ardour_ui_ed.cc:300 msgid "Toggle Record Enable Track4" msgstr "" -#: ardour_ui_ed.cc:299 +#: ardour_ui_ed.cc:302 msgid "Toggle Record Enable Track5" msgstr "" -#: ardour_ui_ed.cc:301 +#: ardour_ui_ed.cc:304 msgid "Toggle Record Enable Track6" msgstr "" -#: ardour_ui_ed.cc:303 +#: ardour_ui_ed.cc:306 msgid "Toggle Record Enable Track7" msgstr "" -#: ardour_ui_ed.cc:305 +#: ardour_ui_ed.cc:308 msgid "Toggle Record Enable Track8" msgstr "" -#: ardour_ui_ed.cc:307 +#: ardour_ui_ed.cc:310 msgid "Toggle Record Enable Track9" msgstr "" -#: ardour_ui_ed.cc:309 +#: ardour_ui_ed.cc:312 msgid "Toggle Record Enable Track10" msgstr "" -#: ardour_ui_ed.cc:311 +#: ardour_ui_ed.cc:314 msgid "Toggle Record Enable Track11" msgstr "" -#: ardour_ui_ed.cc:313 +#: ardour_ui_ed.cc:316 msgid "Toggle Record Enable Track12" msgstr "" -#: ardour_ui_ed.cc:315 +#: ardour_ui_ed.cc:318 msgid "Toggle Record Enable Track13" msgstr "" -#: ardour_ui_ed.cc:317 +#: ardour_ui_ed.cc:320 msgid "Toggle Record Enable Track14" msgstr "" -#: ardour_ui_ed.cc:319 +#: ardour_ui_ed.cc:322 msgid "Toggle Record Enable Track15" msgstr "" -#: ardour_ui_ed.cc:321 +#: ardour_ui_ed.cc:324 msgid "Toggle Record Enable Track16" msgstr "" -#: ardour_ui_ed.cc:323 +#: ardour_ui_ed.cc:326 msgid "Toggle Record Enable Track17" msgstr "" -#: ardour_ui_ed.cc:325 +#: ardour_ui_ed.cc:328 msgid "Toggle Record Enable Track18" msgstr "" -#: ardour_ui_ed.cc:327 +#: ardour_ui_ed.cc:330 msgid "Toggle Record Enable Track19" msgstr "" -#: ardour_ui_ed.cc:329 +#: ardour_ui_ed.cc:332 msgid "Toggle Record Enable Track20" msgstr "" -#: ardour_ui_ed.cc:331 +#: ardour_ui_ed.cc:334 msgid "Toggle Record Enable Track21" msgstr "" -#: ardour_ui_ed.cc:333 +#: ardour_ui_ed.cc:336 msgid "Toggle Record Enable Track22" msgstr "" -#: ardour_ui_ed.cc:335 +#: ardour_ui_ed.cc:338 msgid "Toggle Record Enable Track23" msgstr "" -#: ardour_ui_ed.cc:337 +#: ardour_ui_ed.cc:340 msgid "Toggle Record Enable Track24" msgstr "" -#: ardour_ui_ed.cc:339 +#: ardour_ui_ed.cc:342 msgid "Toggle Record Enable Track25" msgstr "" -#: ardour_ui_ed.cc:341 +#: ardour_ui_ed.cc:344 msgid "Toggle Record Enable Track26" msgstr "" -#: ardour_ui_ed.cc:343 +#: ardour_ui_ed.cc:346 msgid "Toggle Record Enable Track27" msgstr "" -#: ardour_ui_ed.cc:345 +#: ardour_ui_ed.cc:348 msgid "Toggle Record Enable Track28" msgstr "" -#: ardour_ui_ed.cc:347 +#: ardour_ui_ed.cc:350 msgid "Toggle Record Enable Track29" msgstr "" -#: ardour_ui_ed.cc:349 +#: ardour_ui_ed.cc:352 msgid "Toggle Record Enable Track30" msgstr "" -#: ardour_ui_ed.cc:351 +#: ardour_ui_ed.cc:354 msgid "Toggle Record Enable Track31" msgstr "" -#: ardour_ui_ed.cc:353 +#: ardour_ui_ed.cc:356 msgid "Toggle Record Enable Track32" msgstr "" -#: ardour_ui_ed.cc:358 +#: ardour_ui_ed.cc:361 msgid "Percentage" msgstr "Процентов" -#: ardour_ui_ed.cc:359 +#: ardour_ui_ed.cc:362 msgid "Semitones" msgstr "Полутонов" -#: ardour_ui_ed.cc:363 +#: ardour_ui_ed.cc:366 msgid "Send MTC" msgstr "Передача MTC" -#: ardour_ui_ed.cc:365 +#: ardour_ui_ed.cc:368 msgid "Send MMC" msgstr "Передача MMC" -#: ardour_ui_ed.cc:367 +#: ardour_ui_ed.cc:370 #, fuzzy msgid "Use MMC" msgstr "Передача MMC" -#: ardour_ui_ed.cc:369 +#: ardour_ui_ed.cc:372 msgid "Send MIDI feedback" msgstr "" -#: ardour_ui_ed.cc:371 +#: ardour_ui_ed.cc:374 #, fuzzy msgid "Use MIDI control" msgstr "MMC порт" -#: ardour_ui_ed.cc:374 +#: ardour_ui_ed.cc:377 #, fuzzy -msgid "Connect newtrack inputs to hardware" +msgid "Connect new track inputs to hardware" msgstr "ÐвтоподÑоединение новых треков" -#: ardour_ui_ed.cc:392 +#: ardour_ui_ed.cc:396 #, fuzzy msgid "Connect new track outputs to hardware" msgstr "ÐвтоподÑоединение новых треков" -#: ardour_ui_ed.cc:394 +#: ardour_ui_ed.cc:398 #, fuzzy msgid "Connect new track outputs to master" msgstr "автоматичеÑкое подключение треков к маÑтер-выходам" -#: ardour_ui_ed.cc:396 +#: ardour_ui_ed.cc:400 #, fuzzy msgid "Manually connect new track outputs" msgstr "ручное подключение треков к выходам" -#: ardour_ui_ed.cc:401 +#: ardour_ui_ed.cc:405 #, fuzzy msgid "Hardware monitoring" msgstr "Ðппаратный контроль" -#: ardour_ui_ed.cc:402 +#: ardour_ui_ed.cc:406 #, fuzzy msgid "Software monitoring" msgstr "ИÑпользовать программный контроль" -#: ardour_ui_ed.cc:403 +#: ardour_ui_ed.cc:407 #, fuzzy msgid "External monitoring" msgstr "Ðппаратный контроль" #. Configuration object options (i.e. not session specific) -#: ardour_ui_ed.cc:407 +#: ardour_ui_ed.cc:411 msgid "Stop plugins with transport" msgstr "ОÑтанавливать модули (plugins) вмеÑте Ñ Ñ‚Ñ€Ð°Ð½Ñпортом" -#: ardour_ui_ed.cc:408 +#: ardour_ui_ed.cc:412 #, fuzzy msgid "Verify remove last capture" msgstr "Удалить поÑледнюю запиÑÑŒ" -#: ardour_ui_ed.cc:409 +#: ardour_ui_ed.cc:413 msgid "Stop recording on xrun" msgstr "ОÑтановить запиÑÑŒ при потере отÑчётов" -#: ardour_ui_ed.cc:410 +#: ardour_ui_ed.cc:414 #, fuzzy msgid "Stop transport at session end" msgstr "ОÑтанавливать транÑпорт в конце ÑеÑÑии" -#: ardour_ui_ed.cc:411 +#: ardour_ui_ed.cc:415 msgid "-12dB gain reduce ffwd/rewind" msgstr "" -#: ardour_ui_ed.cc:412 +#: ardour_ui_ed.cc:416 msgid "Rec-enable stays engaged at stop" msgstr "" #. session options -#: ardour_ui_ed.cc:416 +#: ardour_ui_ed.cc:420 #, fuzzy msgid "Do not run plugins while recording" msgstr "ИÑпользовать модули (plugins) во Ð²Ñ€ÐµÐ¼Ñ Ð·Ð°Ð¿Ð¸Ñи" -#: ardour_ui_ed.cc:419 +#: ardour_ui_ed.cc:423 msgid "Latched solo" msgstr "" -#: ardour_ui_ed.cc:424 +#: ardour_ui_ed.cc:428 #, fuzzy msgid "Solo in-place" msgstr "Соло" -#: ardour_ui_ed.cc:426 +#: ardour_ui_ed.cc:430 msgid "Solo via bus" msgstr "" -#: ardour_ui_ed.cc:429 +#: ardour_ui_ed.cc:433 #, fuzzy msgid "Automatically create crossfades" msgstr "ÐвтоматичеÑкий кроÑÑфейд на перекрытии" -#: ardour_ui_ed.cc:431 +#: ardour_ui_ed.cc:435 msgid "Unmute new full crossfades" msgstr "" -#: ardour_ui_options.cc:379 ardour_ui_options.cc:389 ardour_ui_options.cc:456 +#: ardour_ui_options.cc:406 ardour_ui_options.cc:416 ardour_ui_options.cc:483 #, fuzzy msgid "Internal" msgstr "внутренний" -#: ardour_ui_options.cc:380 ardour_ui_options.cc:459 +#: ardour_ui_options.cc:407 ardour_ui_options.cc:486 #, fuzzy msgid "MTC" msgstr "MMC" -#: audio_clock.cc:1719 editor.cc:185 +#: audio_clock.cc:1742 editor.cc:188 msgid "SMPTE" msgstr "SMPTE" -#: audio_clock.cc:1720 editor.cc:184 editor_rulers.cc:359 +#: audio_clock.cc:1743 editor.cc:187 editor_rulers.cc:360 msgid "Bars:Beats" msgstr "Такт:ДолÑ" -#: audio_clock.cc:1721 +#: audio_clock.cc:1744 msgid "Minutes:Seconds" msgstr "Минуты:Секунды" -#: audio_clock.cc:1722 +#: audio_clock.cc:1745 msgid "Audio Frames" msgstr "Ðудио кадры" @@ -1404,294 +1386,315 @@ msgstr "Ðудио кадры" #. Slowest = 6.6dB/sec falloff at update rate of 40ms #. Slow = 6.8dB/sec falloff at update rate of 40ms #. -#: audio_clock.cc:1723 editor_actions.cc:374 editor_actions.cc:382 +#: audio_clock.cc:1746 editor_actions.cc:375 editor_actions.cc:383 +#: gain_meter.cc:172 panner_ui.cc:89 plugin_ui.cc:392 plugin_ui.cc:635 msgid "Off" msgstr "Выкл" -#: audio_clock.cc:1725 +#: audio_clock.cc:1748 msgid "Mode" msgstr "Режим" -#: audio_time_axis.cc:90 mixer_strip.cc:458 +#: audio_time_axis.cc:91 msgid "m" msgstr "Ñ‚" -#: audio_time_axis.cc:90 mixer_strip.cc:459 +#: audio_time_axis.cc:91 msgid "s" msgstr "Ñ" -#: audio_time_axis.cc:90 +#: audio_time_axis.cc:91 msgid "r" msgstr "з" -#: audio_time_axis.cc:94 +#: audio_time_axis.cc:95 msgid "g" msgstr "г" #. group -#: audio_time_axis.cc:95 +#: audio_time_axis.cc:96 msgid "p" msgstr "Ñп" -#: audio_time_axis.cc:96 automation_time_axis.cc:31 visual_time_axis.cc:73 +#: audio_time_axis.cc:97 automation_time_axis.cc:32 visual_time_axis.cc:74 msgid "h" msgstr "в" #. height -#: audio_time_axis.cc:97 +#: audio_time_axis.cc:98 msgid "a" msgstr "а" -#: audio_time_axis.cc:98 visual_time_axis.cc:72 +#: audio_time_axis.cc:99 visual_time_axis.cc:73 msgid "v" msgstr "п" -#: audio_time_axis.cc:173 +#: audio_time_axis.cc:168 mixer_strip.cc:86 msgid "Record" msgstr "ЗапиÑÑŒ" -#: audio_time_axis.cc:174 editor_actions.cc:36 +#: audio_time_axis.cc:169 editor_actions.cc:37 mixer_strip.cc:86 msgid "Solo" msgstr "Соло" -#: audio_time_axis.cc:175 editor.cc:1767 editor.cc:1866 panner_ui.cc:385 +#: audio_time_axis.cc:170 editor.cc:1760 editor.cc:1859 mixer_strip.cc:86 +#: panner_ui.cc:427 msgid "Mute" msgstr "Тихо" -#: audio_time_axis.cc:176 +#: audio_time_axis.cc:171 msgid "Edit Group" msgstr "Группы" -#: audio_time_axis.cc:177 visual_time_axis.cc:91 +#: audio_time_axis.cc:172 visual_time_axis.cc:92 msgid "Display Height" msgstr "Ð’Ñ‹Ñота дорожки" -#: audio_time_axis.cc:178 +#: audio_time_axis.cc:173 msgid "Playlist" msgstr "СпиÑок" -#: audio_time_axis.cc:179 audio_time_axis.cc:743 +#: audio_time_axis.cc:174 audio_time_axis.cc:741 msgid "Automation" msgstr "Ðвтомат" -#: audio_time_axis.cc:180 visual_time_axis.cc:92 +#: audio_time_axis.cc:175 visual_time_axis.cc:93 msgid "Visual options" msgstr "Параметры отображениÑ" -#: audio_time_axis.cc:181 visual_time_axis.cc:93 +#: audio_time_axis.cc:176 visual_time_axis.cc:94 msgid "Hide this track" msgstr "Скрыть трек" -#: audio_time_axis.cc:337 +#: audio_time_axis.cc:333 mixer_strip.cc:927 msgid "No group" msgstr "Ðет группы" -#: audio_time_axis.cc:704 automation_time_axis.cc:448 -#: imageframe_time_axis.cc:256 marker_time_axis.cc:210 +#: audio_time_axis.cc:702 automation_time_axis.cc:450 +#: imageframe_time_axis.cc:255 marker_time_axis.cc:211 msgid "Height" msgstr "Ð’Ñ‹Ñота" -#: audio_time_axis.cc:705 color_manager.cc:40 imageframe_time_axis.cc:257 -#: marker_time_axis.cc:211 +#: audio_time_axis.cc:703 color_manager.cc:41 imageframe_time_axis.cc:256 +#: marker_time_axis.cc:212 msgid "Color" msgstr "Цвет" -#: audio_time_axis.cc:709 +#: audio_time_axis.cc:707 msgid "Hide all crossfades" msgstr "" -#: audio_time_axis.cc:710 +#: audio_time_axis.cc:708 msgid "Show all crossfades" msgstr "" -#: audio_time_axis.cc:714 mixer_strip.cc:1236 +#: audio_time_axis.cc:712 mixer_strip.cc:1011 #, fuzzy msgid "Remote Control ID" msgstr "иÑпользовать контрольные выходы" -#: audio_time_axis.cc:720 -msgid "show all automation" -msgstr "" - -#: audio_time_axis.cc:723 +#: audio_time_axis.cc:718 #, fuzzy -msgid "show existing automation" +msgid "Show all automation" +msgstr "автомат" + +#: audio_time_axis.cc:721 +#, fuzzy +msgid "Show existing automation" msgstr "иÑпользовать имеющийÑÑ ÑˆÐ°Ð±Ð»Ð¾Ð½" -#: audio_time_axis.cc:726 -msgid "hide all automation" -msgstr "" +#: audio_time_axis.cc:724 +#, fuzzy +msgid "Hide all automation" +msgstr "очиÑтить интервалы" -#: audio_time_axis.cc:731 audio_time_axis.cc:1169 editor.cc:215 -msgid "gain" -msgstr "уÑил." +#: audio_time_axis.cc:729 +#, fuzzy +msgid "Fader" +msgstr "Затухание" -#: audio_time_axis.cc:736 audio_time_axis.cc:1209 -msgid "pan" +#: audio_time_axis.cc:734 +#, fuzzy +msgid "Pan" msgstr "пан." -#: audio_time_axis.cc:741 +#: audio_time_axis.cc:739 msgid "Plugins" msgstr "Модули (плагины)" -#: audio_time_axis.cc:749 +#: audio_time_axis.cc:747 msgid "Show waveforms" msgstr "Отображать форму Ñигнала" -#: audio_time_axis.cc:757 +#: audio_time_axis.cc:755 msgid "Traditional" msgstr "ОбычнаÑ" -#: audio_time_axis.cc:760 +#: audio_time_axis.cc:758 msgid "Rectified" msgstr "УвеличеннаÑ" -#: audio_time_axis.cc:763 +#: audio_time_axis.cc:761 msgid "Waveform" msgstr "Форма Ñигнала" -#: audio_time_axis.cc:773 +#: audio_time_axis.cc:771 #, fuzzy -msgid "align with existing material" +msgid "Align with existing material" msgstr "СущеÑтвующий материал" -#: audio_time_axis.cc:778 +#: audio_time_axis.cc:776 #, fuzzy -msgid "align with capture time" +msgid "Align with capture time" msgstr "Ð’Ñ€ÐµÐ¼Ñ Ð·Ð°Ð¿Ð¸Ñи" -#: audio_time_axis.cc:784 +#: audio_time_axis.cc:782 #, fuzzy msgid "Alignment" msgstr "ВыровнÑть" -#: audio_time_axis.cc:790 editor.cc:523 editor_actions.cc:59 -#: mixer_strip.cc:1225 +#: audio_time_axis.cc:788 editor.cc:527 editor_actions.cc:60 +#: mixer_strip.cc:1000 mixer_ui.cc:111 msgid "Active" msgstr "Ðктивен" -#: audio_time_axis.cc:795 editor.cc:1929 editor_actions.cc:319 -#: editor_markers.cc:507 imageframe_time_axis.cc:260 location_ui.cc:56 -#: marker_time_axis.cc:214 mixer_strip.cc:1239 +#: audio_time_axis.cc:793 editor.cc:1922 editor_actions.cc:320 +#: editor_markers.cc:508 imageframe_time_axis.cc:259 location_ui.cc:57 +#: marker_time_axis.cc:215 mixer_strip.cc:1014 msgid "Remove" msgstr "Удалить" -#: audio_time_axis.cc:835 +#: audio_time_axis.cc:833 #, fuzzy msgid "Name for playlist" msgstr "Ð˜Ð¼Ñ Ñнимка" -#: audio_time_axis.cc:837 audio_time_axis.cc:1853 editor_markers.cc:826 -#: editor_mouse.cc:4609 imageframe_time_axis.cc:249 marker_time_axis.cc:207 -#: meter_bridge_strip.cc:223 mixer_strip.cc:1223 redirect_box.cc:749 -#: redirect_box.cc:1063 route_ui.cc:732 visual_time_axis.cc:325 +#: audio_time_axis.cc:835 audio_time_axis.cc:1851 editor_markers.cc:827 +#: editor_mouse.cc:4673 imageframe_time_axis.cc:248 marker_time_axis.cc:208 +#: meter_bridge_strip.cc:224 mixer_strip.cc:998 redirect_box.cc:751 +#: redirect_box.cc:1065 route_ui.cc:739 visual_time_axis.cc:326 msgid "Rename" msgstr "Переименовать" -#: audio_time_axis.cc:870 audio_time_axis.cc:910 +#: audio_time_axis.cc:868 audio_time_axis.cc:908 #, fuzzy msgid "Name for Playlist" msgstr "Ð˜Ð¼Ñ Ñнимка" -#: audio_time_axis.cc:1128 visual_time_axis.cc:382 +#: audio_time_axis.cc:1126 visual_time_axis.cc:383 msgid "a track already exists with that name" msgstr "трек Ñ Ñ‚Ð°ÐºÐ¸Ð¼ именем уже ÑущеÑтвует" -#: audio_time_axis.cc:1412 editor.cc:1490 selection.cc:622 +#: audio_time_axis.cc:1167 editor.cc:218 +msgid "gain" +msgstr "уÑил." + +#: audio_time_axis.cc:1207 +msgid "pan" +msgstr "пан." + +#: audio_time_axis.cc:1410 editor.cc:1483 selection.cc:634 msgid "programming error: " msgstr "ошибка в программе: " -#: audio_time_axis.cc:1850 +#: audio_time_axis.cc:1848 msgid "Current: %1" msgstr "" -#: audio_time_axis.cc:1857 +#: audio_time_axis.cc:1855 msgid "New Copy" msgstr "ÐÐ¾Ð²Ð°Ñ ÐºÐ¾Ð¿Ð¸Ñ" -#: audio_time_axis.cc:1859 +#: audio_time_axis.cc:1857 msgid "Clear Current" msgstr "ОчиÑтить текущий" -#: audio_time_axis.cc:1861 editor.cc:2031 editor.cc:2107 +#: audio_time_axis.cc:1859 editor.cc:2024 editor.cc:2100 msgid "Select" msgstr "Выделеннное" -#: automation_line.cc:883 +#: automation_line.cc:884 #, fuzzy msgid "automation event move" msgstr "автомат" -#: automation_line.cc:885 +#: automation_line.cc:886 #, fuzzy msgid "automation range drag" msgstr "автомат" -#: automation_line.cc:1014 region_gain_line.cc:61 +#: automation_line.cc:1015 region_gain_line.cc:62 #, fuzzy msgid "remove control point" msgstr "иÑпользовать контрольные выходы" -#: automation_time_axis.cc:32 editor_ops.cc:2813 +#: automation_time_axis.cc:33 editor_ops.cc:2885 msgid "clear" msgstr "очиÑтить" -#: automation_time_axis.cc:74 +#: automation_time_axis.cc:75 msgid "track height" msgstr "" -#: automation_time_axis.cc:75 +#: automation_time_axis.cc:76 #, fuzzy msgid "automation state" msgstr "автомат" -#: automation_time_axis.cc:76 +#: automation_time_axis.cc:77 #, fuzzy msgid "clear track" msgstr "Скрыть трек" -#: automation_time_axis.cc:77 +#: automation_time_axis.cc:78 #, fuzzy msgid "hide track" msgstr "Скрыть трек" -#: automation_time_axis.cc:185 automation_time_axis.cc:223 -#: automation_time_axis.cc:463 mixer_strip.cc:176 mixer_strip.cc:188 -#: plugin_ui.cc:394 plugin_ui.cc:636 region_editor.cc:53 -msgid "play" -msgstr "воÑпроизвеÑти" - -#: automation_time_axis.cc:187 automation_time_axis.cc:234 -#: automation_time_axis.cc:467 mixer_strip.cc:178 mixer_strip.cc:190 -#: plugin_ui.cc:397 plugin_ui.cc:638 -msgid "write" -msgstr "запиÑÑŒ" - -#: automation_time_axis.cc:189 automation_time_axis.cc:245 -#: automation_time_axis.cc:471 mixer_strip.cc:180 mixer_strip.cc:192 -#: mixer_strip.cc:887 plugin_ui.cc:400 plugin_ui.cc:640 -msgid "touch" +#: automation_time_axis.cc:184 automation_time_axis.cc:213 +#: automation_time_axis.cc:461 +msgid "Manual" msgstr "" -#: automation_time_axis.cc:256 option_editor.cc:182 option_editor.cc:188 -#: plugin_ui.cc:403 +#: automation_time_axis.cc:186 automation_time_axis.cc:224 +#: automation_time_axis.cc:465 editor.cc:2001 editor.cc:2082 gain_meter.cc:174 +#: panner_ui.cc:91 plugin_ui.cc:395 plugin_ui.cc:637 sfdb_ui.cc:56 +msgid "Play" +msgstr "ВоÑпроизвеÑти" + +#: automation_time_axis.cc:188 automation_time_axis.cc:235 +#: automation_time_axis.cc:469 gain_meter.cc:176 panner_ui.cc:93 +#: plugin_ui.cc:398 plugin_ui.cc:639 +#, fuzzy +msgid "Write" +msgstr "запиÑÑŒ" + +#: automation_time_axis.cc:190 automation_time_axis.cc:246 +#: automation_time_axis.cc:473 gain_meter.cc:178 panner_ui.cc:95 +#: plugin_ui.cc:401 plugin_ui.cc:641 +#, fuzzy +msgid "Touch" +msgstr "Врезка" + +#: automation_time_axis.cc:257 option_editor.cc:183 option_editor.cc:189 +#: plugin_ui.cc:404 msgid "???" msgstr "" -#: automation_time_axis.cc:270 +#: automation_time_axis.cc:271 #, fuzzy msgid "clear automation" msgstr "очиÑтить интервалы" -#: automation_time_axis.cc:450 editor_actions.cc:317 +#: automation_time_axis.cc:452 editor_actions.cc:318 msgid "Hide" msgstr "Скрыть" -#: automation_time_axis.cc:452 crossfade_edit.cc:76 redirect_box.cc:1055 +#: automation_time_axis.cc:454 crossfade_edit.cc:78 redirect_box.cc:1057 msgid "Clear" msgstr "ОчиÑтить" -#: automation_time_axis.cc:475 +#: automation_time_axis.cc:477 #, fuzzy msgid "State" msgstr "Ðачало" @@ -1837,1604 +1840,1591 @@ msgstr "" msgid "color of fill" msgstr "" -#: color_manager.cc:39 +#: color_manager.cc:40 #, fuzzy msgid "Object" msgstr "объект" -#: color_manager.cc:77 +#: color_manager.cc:78 #, fuzzy msgid "cannot open color definition file %1: %2" msgstr "не удалоÑÑŒ отобразить заÑтавку (файл \"%1\")" -#: crossfade_edit.cc:73 +#: crossfade_edit.cc:75 #, fuzzy msgid "ardour: x-fade edit" msgstr "ardour: редактор" -#: crossfade_edit.cc:77 panner_ui.cc:401 +#: crossfade_edit.cc:79 panner_ui.cc:443 #, fuzzy msgid "Reset" msgstr "ОгромнаÑ" -#: crossfade_edit.cc:78 +#: crossfade_edit.cc:80 #, fuzzy msgid "Fade" msgstr "Затухание" -#: crossfade_edit.cc:79 +#: crossfade_edit.cc:81 #, fuzzy msgid "Out (dry)" msgstr "в %d" -#: crossfade_edit.cc:80 +#: crossfade_edit.cc:82 #, fuzzy msgid "Out" msgstr "Выходов" -#: crossfade_edit.cc:81 +#: crossfade_edit.cc:83 #, fuzzy msgid "In (dry)" msgstr "в %d" -#: crossfade_edit.cc:82 +#: crossfade_edit.cc:84 msgid "In" msgstr "" -#: crossfade_edit.cc:84 +#: crossfade_edit.cc:86 #, fuzzy msgid "With Pre-roll" msgstr "откат" -#: crossfade_edit.cc:85 +#: crossfade_edit.cc:87 #, fuzzy msgid "With Post-roll" msgstr "накат" -#: crossfade_edit.cc:93 +#: crossfade_edit.cc:95 #, fuzzy msgid "Fade In" msgstr "Затухание" -#: crossfade_edit.cc:94 +#: crossfade_edit.cc:96 #, fuzzy msgid "Fade Out" msgstr "Затухание" -#: crossfade_edit.cc:170 editor.cc:1842 editor_actions.cc:315 -#: option_editor.cc:129 +#: crossfade_edit.cc:172 editor.cc:1835 editor_actions.cc:316 +#: option_editor.cc:130 msgid "Audition" msgstr "Ðудит" -#: editor.cc:101 editor.cc:3588 +#: editor.cc:104 editor.cc:3616 msgid "Slide" msgstr "Скольжение" -#: editor.cc:102 editor.cc:3586 +#: editor.cc:105 editor.cc:3614 msgid "Splice" msgstr "Стыковка" -#: editor.cc:107 editor.cc:3643 export_dialog.cc:78 export_dialog.cc:92 -#: export_dialog.cc:893 export_dialog.cc:1225 +#. note that this menu list starts at zero, not 1, because zero +#. is a valid, if useless, ID. +#. +#. leave some breathing room +#: editor.cc:110 editor.cc:3671 export_dialog.cc:78 export_dialog.cc:92 +#: export_dialog.cc:893 export_dialog.cc:1225 route_ui.cc:437 msgid "None" msgstr "Ðет" -#: editor.cc:108 editor.cc:3631 +#: editor.cc:111 editor.cc:3659 #, fuzzy msgid "CD Frames" msgstr "Кадр" -#: editor.cc:109 editor.cc:3633 +#: editor.cc:112 editor.cc:3661 #, fuzzy msgid "SMPTE Frames" msgstr "SMPTE Кадры/Секунды" -#: editor.cc:110 editor.cc:3635 +#: editor.cc:113 editor.cc:3663 #, fuzzy msgid "SMPTE Seconds" msgstr "SMPTE Кадры/Секунды" -#: editor.cc:111 editor.cc:3637 +#: editor.cc:114 editor.cc:3665 msgid "SMPTE Minutes" msgstr "" -#: editor.cc:112 editor.cc:3639 +#: editor.cc:115 editor.cc:3667 #, fuzzy msgid "Seconds" msgstr "Минуты:Секунды" -#: editor.cc:113 editor.cc:3641 +#: editor.cc:116 editor.cc:3669 #, fuzzy msgid "Minutes" msgstr "Главные выходы" -#: editor.cc:114 editor.cc:3613 +#: editor.cc:117 editor.cc:3641 msgid "Beats/32" msgstr "долÑм/32" -#: editor.cc:115 editor.cc:3611 +#: editor.cc:118 editor.cc:3639 msgid "Beats/16" msgstr "долÑм/16" -#: editor.cc:116 editor.cc:3609 +#: editor.cc:119 editor.cc:3637 msgid "Beats/8" msgstr "долÑм/8" -#: editor.cc:117 editor.cc:3607 +#: editor.cc:120 editor.cc:3635 msgid "Beats/4" msgstr "долÑм/4" -#: editor.cc:118 editor.cc:3605 +#: editor.cc:121 editor.cc:3633 msgid "Beats/3" msgstr "долÑм/3" -#: editor.cc:119 editor.cc:3615 +#: editor.cc:122 editor.cc:3643 msgid "Beats" msgstr "долÑм" -#: editor.cc:120 editor.cc:3617 +#: editor.cc:123 editor.cc:3645 msgid "Bars" msgstr "тактам" -#: editor.cc:121 editor.cc:3619 +#: editor.cc:124 editor.cc:3647 msgid "Marks" msgstr "маркерам" -#: editor.cc:122 editor.cc:141 editor.cc:3621 editor.cc:3687 +#: editor.cc:125 editor.cc:144 editor.cc:3649 editor.cc:3715 msgid "Edit Cursor" msgstr "курÑору" -#: editor.cc:123 editor.cc:3623 +#: editor.cc:126 editor.cc:3651 msgid "Region starts" msgstr "нач. облаÑтей" -#: editor.cc:124 editor.cc:3625 +#: editor.cc:127 editor.cc:3653 msgid "Region ends" msgstr "оконч. облаÑтей" -#: editor.cc:125 editor.cc:3629 +#: editor.cc:128 editor.cc:3657 msgid "Region syncs" msgstr "" -#: editor.cc:126 editor.cc:3627 +#: editor.cc:129 editor.cc:3655 msgid "Region bounds" msgstr "" -#: editor.cc:132 editor.cc:3662 +#: editor.cc:135 editor.cc:3690 msgid "Magnetic" msgstr "Магн." -#: editor.cc:137 editor.cc:3679 export_dialog.cc:140 export_dialog.cc:156 +#: editor.cc:140 editor.cc:3707 export_dialog.cc:140 export_dialog.cc:156 #: export_dialog.cc:1068 export_dialog.cc:1072 msgid "Left" msgstr "лев. краю" -#: editor.cc:138 editor.cc:3681 export_dialog.cc:141 export_dialog.cc:157 +#: editor.cc:141 editor.cc:3709 export_dialog.cc:141 export_dialog.cc:157 msgid "Right" msgstr "прав. краю" -#: editor.cc:139 editor.cc:3683 +#: editor.cc:142 editor.cc:3711 msgid "Center" msgstr "центру" -#: editor.cc:140 editor.cc:3685 +#: editor.cc:143 editor.cc:3713 msgid "Playhead" msgstr "указателю" #. time display buttons -#: editor.cc:183 +#: editor.cc:186 msgid "Mins:Secs" msgstr "Мин:Сек" -#: editor.cc:186 editor_rulers.cc:353 +#: editor.cc:189 editor_rulers.cc:354 msgid "Frames" msgstr "Кадр" -#: editor.cc:187 editor_rulers.cc:373 +#: editor.cc:190 editor_rulers.cc:374 msgid "Tempo" msgstr "Темп" -#: editor.cc:188 editor_rulers.cc:367 +#: editor.cc:191 editor_rulers.cc:368 msgid "Meter" msgstr "Размер" -#: editor.cc:189 editor_rulers.cc:379 +#: editor.cc:192 editor_rulers.cc:380 msgid "Location Markers" msgstr "Маркеры интервалов" -#: editor.cc:190 editor_rulers.cc:385 +#: editor.cc:193 editor_rulers.cc:386 msgid "Range Markers" msgstr "" -#: editor.cc:191 editor_rulers.cc:391 +#: editor.cc:194 editor_rulers.cc:392 msgid "Loop/Punch Ranges" msgstr "" -#: editor.cc:213 +#: editor.cc:216 msgid "range" msgstr "выделÑть" -#: editor.cc:214 +#: editor.cc:217 msgid "object" msgstr "объект" -#: editor.cc:216 +#: editor.cc:219 msgid "zoom" msgstr "маÑштаб" -#: editor.cc:217 +#: editor.cc:220 msgid "timefx" msgstr "Ñффект" -#: editor.cc:218 +#: editor.cc:221 msgid "listen" msgstr "" -#: editor.cc:220 +#: editor.cc:223 msgid "mode" msgstr "режим" -#: editor.cc:221 +#: editor.cc:224 msgid "automation" msgstr "автомат" -#: editor.cc:223 +#: editor.cc:226 msgid "Edit Mode" msgstr "Режим редактированиÑ" -#: editor.cc:224 editor_actions.cc:283 +#: editor.cc:227 editor_actions.cc:284 msgid "Snap To" msgstr "ПривÑзка к" -#: editor.cc:225 +#: editor.cc:228 msgid "Snap Mode" msgstr "ПривÑзка к" -#: editor.cc:226 +#: editor.cc:229 msgid "Zoom Focus" msgstr "МаÑштабировать к" #. #. nudge -#: editor.cc:234 editor.cc:1907 editor.cc:2073 editor.cc:2129 +#: editor.cc:237 editor.cc:1900 editor.cc:2066 editor.cc:2122 msgid "Nudge" msgstr "" -#: editor.cc:466 +#: editor.cc:470 msgid "Zoom in" msgstr "Увеличить" -#: editor.cc:467 +#: editor.cc:471 msgid "Zoom out" msgstr "Уменьшить" -#: editor.cc:470 +#: editor.cc:474 msgid "Zoom to session" msgstr "Показать вÑÑ‘" -#: editor.cc:485 +#: editor.cc:489 msgid "Zoom Span" msgstr "ОблаÑть проÑмотра" -#: editor.cc:498 editor.cc:524 editor_actions.cc:61 mixer_ui.cc:85 +#: editor.cc:502 editor.cc:528 editor_actions.cc:62 mixer_ui.cc:86 +#: mixer_ui.cc:112 #, fuzzy msgid "Visible" msgstr "отображать" -#: editor.cc:499 editor.cc:522 +#: editor.cc:503 editor.cc:526 #, fuzzy msgid "Name" msgstr "Кадр" -#: editor.cc:595 editor.cc:661 +#: editor.cc:602 editor.cc:669 #, fuzzy msgid "Regions" msgstr "ОблаÑть" -#: editor.cc:634 editor.cc:673 +#: editor.cc:642 editor.cc:681 msgid "Chunks" msgstr "Фрагменты" -#: editor.cc:664 +#: editor.cc:672 #, fuzzy msgid "Tracks/Busses" msgstr "Треки/Шины" -#: editor.cc:667 +#: editor.cc:675 msgid "Snapshots" msgstr "Снимки" -#: editor.cc:670 +#: editor.cc:678 msgid "Edit Groups" msgstr "" "Ред.\n" "группы" -#: editor.cc:719 +#: editor.cc:727 msgid "Nudge region/selection forwards" msgstr "" -#: editor.cc:720 +#: editor.cc:728 msgid "Nudge region/selection backwards" msgstr "" -#: editor.cc:727 editor_mixer.cc:298 +#: editor.cc:735 editor_mixer.cc:299 msgid "ardour: editor" msgstr "ardour: редактор" -#: editor.cc:728 +#: editor.cc:736 msgid "ardour_editor" msgstr "ardour_редактор" -#: editor.cc:1190 +#: editor.cc:1183 msgid "ardour: editor: " msgstr "ardour: редактор: " #. force name -#: editor.cc:1275 editor.cc:1284 editor_markers.cc:869 +#: editor.cc:1268 editor.cc:1277 editor_markers.cc:870 msgid "Loop" msgstr "Кольцо" #. force name -#: editor.cc:1289 editor.cc:1298 editor_markers.cc:895 +#: editor.cc:1282 editor.cc:1291 editor_markers.cc:896 msgid "Punch" msgstr "Врезка" -#: editor.cc:1446 editor_mouse.cc:1721 +#: editor.cc:1439 editor_mouse.cc:1742 #, fuzzy msgid "programming error: fade in canvas item has no regionview data pointer!" msgstr "ошибка в программе: line canvas item has no line pointer!" -#: editor.cc:1458 editor.cc:1475 redirect_box.cc:1071 +#: editor.cc:1451 editor.cc:1468 redirect_box.cc:1073 msgid "Deactivate" msgstr "Деактивировать" #. activation -#: editor.cc:1460 editor.cc:1477 redirect_box.cc:1069 +#: editor.cc:1453 editor.cc:1470 redirect_box.cc:1071 msgid "Activate" msgstr "Ðктивировать" -#: editor.cc:1465 editor.cc:1482 +#: editor.cc:1458 editor.cc:1475 #, fuzzy msgid "Linear" msgstr "линейное" -#: editor.cc:1466 editor.cc:1483 editor_actions.cc:375 +#: editor.cc:1459 editor.cc:1476 editor_actions.cc:376 #, fuzzy msgid "Slowest" msgstr "Меньше" -#: editor.cc:1467 editor.cc:1484 editor_actions.cc:376 +#: editor.cc:1460 editor.cc:1477 editor_actions.cc:377 #, fuzzy msgid "Slow" msgstr "Соло" -#: editor.cc:1468 editor.cc:1485 editor_actions.cc:378 +#: editor.cc:1461 editor.cc:1478 editor_actions.cc:379 #, fuzzy msgid "Fast" msgstr "Затухание" -#: editor.cc:1469 editor.cc:1486 editor_actions.cc:380 +#: editor.cc:1462 editor.cc:1479 editor_actions.cc:381 #, fuzzy msgid "Fastest" msgstr "быÑтрое" -#: editor.cc:1596 editor.cc:1604 +#: editor.cc:1589 editor.cc:1597 msgid "Freeze" msgstr "Заморозить" -#: editor.cc:1600 +#: editor.cc:1593 msgid "Unfreeze" msgstr "Разморозить" -#: editor.cc:1769 editor.cc:1864 +#: editor.cc:1762 editor.cc:1857 #, fuzzy msgid "Unmute" msgstr "тихо" #. non-operative menu items for menu bar #. show editors -#: editor.cc:1773 editor.cc:2053 editor.cc:2755 editor_actions.cc:26 -#: editor_markers.cc:506 mixer_strip.cc:512 mixer_strip.cc:572 -#: redirect_box.cc:1077 +#: editor.cc:1766 editor.cc:2046 editor.cc:2748 editor_actions.cc:27 +#: editor_markers.cc:507 mixer_strip.cc:495 mixer_strip.cc:563 +#: redirect_box.cc:1079 msgid "Edit" msgstr "Правка" -#: editor.cc:1778 +#: editor.cc:1771 msgid "Convert to short" msgstr "" -#: editor.cc:1780 +#: editor.cc:1773 msgid "Convert to full" msgstr "" -#: editor.cc:1791 +#: editor.cc:1784 #, fuzzy msgid "Crossfade" msgstr "КроÑÑфейд" -#: editor.cc:1834 +#: editor.cc:1827 msgid "Popup region editor" msgstr "Открыть редактор облаÑти" -#: editor.cc:1835 +#: editor.cc:1828 #, fuzzy msgid "Raise to top layer" msgstr "ПоднÑть облаÑть в верхний Ñлой" -#: editor.cc:1836 +#: editor.cc:1829 #, fuzzy msgid "Lower to bottom layer" msgstr "ОпуÑтить облаÑть в нижний Ñлой" -#: editor.cc:1838 +#: editor.cc:1831 msgid "Define sync point" msgstr "" -#: editor.cc:1839 +#: editor.cc:1832 msgid "Remove sync point" msgstr "" -#: editor.cc:1844 +#: editor.cc:1837 #, fuzzy msgid "Bounce" msgstr "СвеÑти выделенное" -#: editor.cc:1847 +#: editor.cc:1840 #, fuzzy msgid "Analyze region" msgstr "ВоÑпроизвеÑти облаÑть" -#: editor.cc:1859 +#: editor.cc:1852 msgid "Lock" msgstr "" -#: editor.cc:1860 +#: editor.cc:1853 msgid "Unlock" msgstr "" -#: editor.cc:1870 +#: editor.cc:1863 msgid "Original position" msgstr "" -#: editor.cc:1876 +#: editor.cc:1869 msgid "Toggle envelope visibility" msgstr "" -#: editor.cc:1877 +#: editor.cc:1870 msgid "Toggle envelope active" msgstr "" -#: editor.cc:1881 +#: editor.cc:1874 #, fuzzy msgid "DeNormalize" msgstr "Ðорм." -#: editor.cc:1883 +#: editor.cc:1876 msgid "Normalize" msgstr "" -#: editor.cc:1886 +#: editor.cc:1879 msgid "Reverse" msgstr "" #. range related stuff -#: editor.cc:1892 +#: editor.cc:1885 #, fuzzy msgid "Add Range Markers" msgstr "Маркеры интервалов" -#: editor.cc:1893 +#: editor.cc:1886 #, fuzzy msgid "Set Range" msgstr "Разделить облаÑть" -#: editor.cc:1902 +#: editor.cc:1895 msgid "Nudge fwd" msgstr "" -#: editor.cc:1903 +#: editor.cc:1896 msgid "Nudge bwd" msgstr "" -#: editor.cc:1904 +#: editor.cc:1897 msgid "Nudge fwd by capture offset" msgstr "" -#: editor.cc:1905 +#: editor.cc:1898 msgid "Nudge bwd by capture offset" msgstr "" -#: editor.cc:1914 +#: editor.cc:1907 msgid "Start to edit cursor" msgstr "От начала до курÑора" -#: editor.cc:1915 +#: editor.cc:1908 msgid "Edit cursor to end" msgstr "От курÑора до конца" -#: editor.cc:1917 +#: editor.cc:1910 gain_meter.cc:181 gain_meter.cc:813 panner_ui.cc:98 +#: panner_ui.cc:803 msgid "Trim" msgstr "" -#: editor.cc:1920 +#: editor.cc:1913 msgid "Split" msgstr "Склеить" -#: editor.cc:1923 +#: editor.cc:1916 msgid "Make mono regions" msgstr "Создать моно-облаÑти" -#: editor.cc:1926 +#: editor.cc:1919 msgid "Duplicate" msgstr "Размножить" -#: editor.cc:1927 +#: editor.cc:1920 msgid "Fill Track" msgstr "Заполнить трек" -#: editor.cc:1931 +#: editor.cc:1924 msgid "Destroy" msgstr "" -#: editor.cc:1961 +#: editor.cc:1954 #, fuzzy msgid "Play range" msgstr "ВоÑпроизвеÑти \"кольцо\"" -#: editor.cc:1962 +#: editor.cc:1955 msgid "Loop range" msgstr "" -#: editor.cc:1966 +#: editor.cc:1959 #, fuzzy msgid "Analyze range" msgstr "ВоÑпроизвеÑти \"кольцо\"" -#: editor.cc:1970 +#: editor.cc:1963 #, fuzzy msgid "Separate range to track" msgstr "Разделить облаÑть" -#: editor.cc:1971 +#: editor.cc:1964 #, fuzzy msgid "Separate range to region list" msgstr "ВоÑпроизвеÑти выделенную облаÑть" -#: editor.cc:1974 +#: editor.cc:1967 #, fuzzy msgid "Select all in range" msgstr "Выделить вÑÑ‘" -#: editor.cc:1976 editor.cc:2021 +#: editor.cc:1969 editor.cc:2014 #, fuzzy msgid "Set range to loop range" msgstr "выбрать окно проÑмотра" -#: editor.cc:1977 editor.cc:2022 +#: editor.cc:1970 editor.cc:2015 #, fuzzy msgid "Set range to punch range" msgstr "Выбрать текущий интервал" -#: editor.cc:1979 +#: editor.cc:1972 #, fuzzy msgid "Crop region to range" msgstr "Обрезать облаÑть по выделенному" -#: editor.cc:1980 +#: editor.cc:1973 #, fuzzy msgid "Fill range with region" msgstr "Создать облаÑть" -#: editor.cc:1981 +#: editor.cc:1974 #, fuzzy msgid "Duplicate range" msgstr "Размножить" -#: editor.cc:1982 +#: editor.cc:1975 #, fuzzy msgid "Create chunk from range" msgstr "Создать фрагмент из выделенного" -#: editor.cc:1984 +#: editor.cc:1977 msgid "Bounce range" msgstr "" -#: editor.cc:1985 +#: editor.cc:1978 #, fuzzy msgid "Export range" msgstr "ЭкÑпорт облаÑти" -#: editor.cc:1987 +#: editor.cc:1980 #, fuzzy msgid "Range" msgstr "выделÑть" -#: editor.cc:2002 editor.cc:2087 +#: editor.cc:1995 editor.cc:2080 #, fuzzy msgid "Play from edit cursor" msgstr "ВоÑпроизвеÑти от курÑора" -#: editor.cc:2003 editor.cc:2088 +#: editor.cc:1996 editor.cc:2081 msgid "Play from start" msgstr "ВоÑпроизвеÑти Ñ Ð½Ð°Ñ‡Ð°Ð»Ð°" -#: editor.cc:2004 +#: editor.cc:1997 #, fuzzy msgid "Play region" msgstr "ВоÑпроизвеÑти облаÑть" -#: editor.cc:2006 +#: editor.cc:1999 msgid "Loop Region" msgstr "\"Закольцевать\" облаÑть" -#: editor.cc:2008 editor.cc:2089 sfdb_ui.cc:56 -msgid "Play" -msgstr "ВоÑпроизвеÑти" - -#: editor.cc:2016 editor.cc:2097 +#: editor.cc:2009 editor.cc:2090 #, fuzzy msgid "Select All in track" msgstr "Выделить вÑÑ‘" -#: editor.cc:2017 editor.cc:2098 redirect_box.cc:1065 +#: editor.cc:2010 editor.cc:2091 redirect_box.cc:1067 #, fuzzy msgid "Select All" msgstr "Выделить вÑÑ‘" -#: editor.cc:2018 editor.cc:2099 +#: editor.cc:2011 editor.cc:2092 #, fuzzy msgid "Invert selection in track" msgstr "Скрыть трек" -#: editor.cc:2019 editor.cc:2100 +#: editor.cc:2012 editor.cc:2093 #, fuzzy msgid "Invert selection" msgstr "СвеÑти выделенное" -#: editor.cc:2024 editor.cc:2102 +#: editor.cc:2017 editor.cc:2095 #, fuzzy msgid "Select all after edit cursor" msgstr "От начала до курÑора" -#: editor.cc:2025 editor.cc:2103 +#: editor.cc:2018 editor.cc:2096 #, fuzzy msgid "Select all before edit cursor" msgstr "От начала до курÑора" -#: editor.cc:2026 editor.cc:2104 +#: editor.cc:2019 editor.cc:2097 #, fuzzy msgid "Select all after playhead" msgstr "ВоÑпроизвеÑти от указателÑ" -#: editor.cc:2027 editor.cc:2105 +#: editor.cc:2020 editor.cc:2098 #, fuzzy msgid "Select all before playhead" msgstr "ВоÑпроизвеÑти от указателÑ" -#: editor.cc:2028 +#: editor.cc:2021 #, fuzzy msgid "Select all between cursors" msgstr "От начала до курÑора" #. standard editing stuff -#: editor.cc:2039 editor.cc:2115 editor.cc:3455 editor_actions.cc:213 -#: redirect_box.cc:1058 +#: editor.cc:2032 editor.cc:2108 editor.cc:3483 editor_actions.cc:214 +#: redirect_box.cc:1060 msgid "Cut" msgstr "Вырезать" -#: editor.cc:2040 editor.cc:2116 editor.cc:3457 editor_actions.cc:218 -#: redirect_box.cc:1060 +#: editor.cc:2033 editor.cc:2109 editor.cc:3485 editor_actions.cc:219 +#: redirect_box.cc:1062 msgid "Copy" msgstr "Копировать" -#: editor.cc:2041 +#: editor.cc:2034 #, fuzzy msgid "Paste at edit cursor" msgstr "От начала до курÑора" -#: editor.cc:2042 +#: editor.cc:2035 #, fuzzy msgid "Paste at mouse" msgstr "иÑпользовать маÑтер-выходы" -#: editor.cc:2046 editor.cc:3462 +#: editor.cc:2039 editor.cc:3490 msgid "Align" msgstr "ВыровнÑть" -#: editor.cc:2047 editor.cc:3464 +#: editor.cc:2040 editor.cc:3492 msgid "Align Relative" msgstr "ВыровнÑть отноÑительно" -#: editor.cc:2051 +#: editor.cc:2044 msgid "Insert chunk" msgstr "Ð’Ñтавить фрагмент" -#: editor.cc:2058 +#: editor.cc:2051 #, fuzzy msgid "Insert Selected Region" msgstr "ВоÑпроизвеÑти выделенную облаÑть" -#: editor.cc:2059 +#: editor.cc:2052 msgid "Insert Existing Audio" msgstr "" -#: editor.cc:2068 editor.cc:2124 +#: editor.cc:2061 editor.cc:2117 msgid "Nudge entire track fwd" msgstr "" -#: editor.cc:2069 editor.cc:2125 +#: editor.cc:2062 editor.cc:2118 msgid "Nudge track after edit cursor fwd" msgstr "" -#: editor.cc:2070 editor.cc:2126 +#: editor.cc:2063 editor.cc:2119 msgid "Nudge entire track bwd" msgstr "" -#: editor.cc:2071 editor.cc:2127 +#: editor.cc:2064 editor.cc:2120 msgid "Nudge track after edit cursor bwd" msgstr "" -#: editor.cc:2117 editor.cc:3459 editor_actions.cc:220 redirect_box.cc:1062 +#: editor.cc:2110 editor.cc:3487 editor_actions.cc:221 redirect_box.cc:1064 msgid "Paste" msgstr "Ð’Ñтавить" -#: editor.cc:2637 +#: editor.cc:2630 msgid "select/move objects" msgstr "выбирать/двигать объекты" -#: editor.cc:2638 +#: editor.cc:2631 msgid "select/move ranges" msgstr "выбирать/двигать диапазоны" -#: editor.cc:2639 +#: editor.cc:2632 msgid "draw gain automation" msgstr "" -#: editor.cc:2640 +#: editor.cc:2633 msgid "select zoom range" msgstr "выбрать окно проÑмотра" -#: editor.cc:2641 +#: editor.cc:2634 msgid "stretch/shrink regions" msgstr "раÑÑ‚Ñнуть/Ñжать облаÑти" -#: editor.cc:2642 +#: editor.cc:2635 #, fuzzy msgid "listen to specific regions" msgstr "ВоÑпроизвеÑти выделенную облаÑть" -#: editor.cc:2753 +#: editor.cc:2746 msgid "Start:" msgstr "Ðачало:" -#: editor.cc:2754 +#: editor.cc:2747 msgid "End:" msgstr "Конец:" -#: editor.cc:3097 -#, fuzzy -msgid "set selected trackview" -msgstr "Ð’Ñтавить выбранное" - -#: editor.cc:3137 -#, fuzzy -msgid "set selected control point" -msgstr "иÑпользовать контрольные выходы" - -#: editor.cc:3246 -#, fuzzy -msgid "set selected regionview" -msgstr "ВоÑпроизвеÑти выделенную облаÑть" - -#: editor.cc:3334 editor.cc:3374 +#: editor.cc:3362 editor.cc:3402 #, fuzzy msgid "set selected regions" msgstr "ВоÑпроизвеÑти выделенную облаÑть" -#: editor.cc:3430 editor_actions.cc:203 +#: editor.cc:3458 editor_actions.cc:204 msgid "Undo" msgstr "Отменить" -#: editor.cc:3432 +#: editor.cc:3460 msgid "Undo (%1)" msgstr "Отменить (%1)" -#: editor.cc:3442 editor_actions.cc:205 +#: editor.cc:3470 editor_actions.cc:206 msgid "Redo" msgstr "Вернуть" -#: editor.cc:3444 +#: editor.cc:3472 msgid "Redo (%1)" msgstr "Вернуть (%1)" -#: editor.cc:3478 +#: editor.cc:3506 msgid "... as new track" msgstr "" -#: editor.cc:3479 +#: editor.cc:3507 #, fuzzy msgid "... as new region" msgstr "проÑлушать облаÑть" -#: editor.cc:3481 +#: editor.cc:3509 msgid "Import audio (copy)" msgstr "Импортировать аудио (копировать)" -#: editor.cc:3484 +#: editor.cc:3512 msgid "Remove last capture" msgstr "Удалить поÑледнюю запиÑÑŒ" -#: editor.cc:3508 +#: editor.cc:3536 msgid "Duplicate how many times?" msgstr "КоличеÑтво повторов?" -#: editor.cc:3994 +#: editor.cc:4022 msgid "" "Playlist %1 is currently unused.\n" "If left alone, no audio files used by it will be cleaned.\n" "If deleted, audio files used by it alone by will cleaned." msgstr "" -#: editor.cc:4002 +#: editor.cc:4030 #, fuzzy msgid "Delete playlist" msgstr "Ð˜Ð¼Ñ Ñнимка" -#: editor.cc:4003 +#: editor.cc:4031 #, fuzzy msgid "Keep playlist" msgstr "Ð˜Ð¼Ñ Ñнимка" -#: editor.cc:4004 editor_audio_import.cc:237 editor_ops.cc:1976 -#: editor_timefx.cc:52 export_dialog.cc:971 io_selector.cc:58 -#: io_selector.cc:792 redirect_box.cc:901 tempo_dialog.cc:19 -#: tempo_dialog.cc:36 tempo_dialog.cc:152 tempo_dialog.cc:170 +#: editor.cc:4032 editor_audio_import.cc:236 editor_ops.cc:2048 +#: editor_timefx.cc:71 export_dialog.cc:971 io_selector.cc:59 +#: io_selector.cc:793 redirect_box.cc:903 tempo_dialog.cc:20 +#: tempo_dialog.cc:37 tempo_dialog.cc:202 tempo_dialog.cc:220 msgid "Cancel" msgstr "Отмена" -#: editor.cc:4171 +#: editor.cc:4199 #, fuzzy msgid "new playlists" msgstr "Ð˜Ð¼Ñ Ñнимка" -#: editor.cc:4179 +#: editor.cc:4207 #, fuzzy msgid "copy playlists" msgstr "Ð˜Ð¼Ñ Ñнимка" -#: editor.cc:4187 +#: editor.cc:4215 #, fuzzy msgid "clear playlists" msgstr "Ð˜Ð¼Ñ Ñнимка" -#: editor_actions.cc:27 +#: editor_actions.cc:28 #, fuzzy msgid "Select regions" msgstr "ВоÑпроизвеÑти выделенную облаÑть" -#: editor_actions.cc:28 +#: editor_actions.cc:29 #, fuzzy msgid "Select range operations" msgstr "ВоÑпроизвеÑти выделенную облаÑть" -#: editor_actions.cc:29 +#: editor_actions.cc:30 #, fuzzy msgid "Move edit cursor" msgstr "От начала до курÑора" -#: editor_actions.cc:30 +#: editor_actions.cc:31 #, fuzzy msgid "Region operations" msgstr "ОблаÑти/Ñоздание" -#: editor_actions.cc:31 +#: editor_actions.cc:32 msgid "Tools" msgstr "" -#: editor_actions.cc:32 +#: editor_actions.cc:33 msgid "View" msgstr "" -#: editor_actions.cc:33 +#: editor_actions.cc:34 #, fuzzy msgid "ZoomFocus" msgstr "МаÑштабировать к" -#: editor_actions.cc:34 +#: editor_actions.cc:35 #, fuzzy msgid "Meter hold" msgstr "Размер" -#: editor_actions.cc:35 +#: editor_actions.cc:36 msgid "Meter falloff" msgstr "" -#: editor_actions.cc:37 +#: editor_actions.cc:38 #, fuzzy msgid "Crossfades" msgstr "КроÑÑфейд" -#: editor_actions.cc:38 +#: editor_actions.cc:39 #, fuzzy msgid "Monitoring" msgstr "Ðппаратный контроль" -#: editor_actions.cc:39 +#: editor_actions.cc:40 #, fuzzy msgid "Autoconnect" msgstr "Соединить" -#: editor_actions.cc:40 +#: editor_actions.cc:41 #, fuzzy msgid "Layering" msgstr "Слой" -#: editor_actions.cc:41 +#: editor_actions.cc:42 #, fuzzy msgid "Metering" msgstr "Размер" -#: editor_actions.cc:42 +#: editor_actions.cc:43 msgid "Fall off rate" msgstr "" -#: editor_actions.cc:43 +#: editor_actions.cc:44 msgid "Hold Time" msgstr "" -#: editor_actions.cc:44 +#: editor_actions.cc:45 msgid "Add Existing Audio" msgstr "" #. add named actions for the editor -#: editor_actions.cc:49 +#: editor_actions.cc:50 #, fuzzy msgid "Show Editor Mixer" msgstr "Показать вÑе каналы аудиотреков" -#: editor_actions.cc:54 +#: editor_actions.cc:55 #, fuzzy msgid "Span Entire Overlap" msgstr "ПоднÑть облаÑть на один Ñлой" -#: editor_actions.cc:56 editor_actions.cc:383 +#: editor_actions.cc:57 editor_actions.cc:384 #, fuzzy msgid "Short" msgstr "порт" -#: editor_actions.cc:63 +#: editor_actions.cc:64 msgid "Created Automatically" msgstr "" -#: editor_actions.cc:66 +#: editor_actions.cc:67 msgid "Playhead to Next Region Start" msgstr "" -#: editor_actions.cc:68 +#: editor_actions.cc:69 msgid "Playhead to Next Region End" msgstr "" -#: editor_actions.cc:70 +#: editor_actions.cc:71 msgid "Playhead to Next Region Sync" msgstr "" -#: editor_actions.cc:73 +#: editor_actions.cc:74 msgid "Playhead to Previous Region Start" msgstr "" -#: editor_actions.cc:75 +#: editor_actions.cc:76 msgid "Playhead to Previous Region End" msgstr "" -#: editor_actions.cc:77 +#: editor_actions.cc:78 msgid "Playhead to Previous Region Sync" msgstr "" -#: editor_actions.cc:80 +#: editor_actions.cc:81 #, fuzzy msgid "Edit Cursor to Next Region Start" msgstr "От курÑора до конца" -#: editor_actions.cc:82 +#: editor_actions.cc:83 #, fuzzy msgid "Edit Cursor to Next Region End" msgstr "От курÑора до конца" -#: editor_actions.cc:84 +#: editor_actions.cc:85 #, fuzzy msgid "Edit Cursor to Next Region Sync" msgstr "От курÑора до конца" -#: editor_actions.cc:87 +#: editor_actions.cc:88 msgid "Edit Cursor to Previous Region Start" msgstr "" -#: editor_actions.cc:89 +#: editor_actions.cc:90 #, fuzzy msgid "Edit Cursor to Previous Region End" msgstr "От курÑора до конца" -#: editor_actions.cc:91 +#: editor_actions.cc:92 #, fuzzy msgid "Edit Cursor to Previous Region Sync" msgstr "От курÑора до конца" -#: editor_actions.cc:94 +#: editor_actions.cc:95 msgid "Playhead to Range Start" msgstr "" -#: editor_actions.cc:96 +#: editor_actions.cc:97 #, fuzzy msgid "Playhead to Range End" msgstr "ВоÑпроизвеÑти \"кольцо\"" -#: editor_actions.cc:99 +#: editor_actions.cc:100 #, fuzzy msgid "Edit Cursor to Range Start" msgstr "От курÑора до конца" -#: editor_actions.cc:101 +#: editor_actions.cc:102 #, fuzzy msgid "Edit Cursor to Range End" msgstr "От курÑора до конца" -#: editor_actions.cc:104 editor_ops.cc:1300 +#: editor_actions.cc:105 editor_ops.cc:1363 #, fuzzy msgid "select all" msgstr "Выделить вÑÑ‘" -#: editor_actions.cc:106 +#: editor_actions.cc:107 #, fuzzy msgid "Select All After Edit Cursor" msgstr "ВоÑпроизвеÑти от курÑора" -#: editor_actions.cc:108 +#: editor_actions.cc:109 msgid "Select All Before Edit Cursor" msgstr "" -#: editor_actions.cc:111 +#: editor_actions.cc:112 #, fuzzy msgid "Select All After Playhead" msgstr "ВоÑпроизвеÑти от указателÑ" -#: editor_actions.cc:113 +#: editor_actions.cc:114 #, fuzzy msgid "Select All Before Playhead" msgstr "ВоÑпроизвеÑти от указателÑ" -#: editor_actions.cc:115 +#: editor_actions.cc:116 #, fuzzy msgid "Select All Between Cursors" msgstr "ВоÑпроизвеÑти от курÑора" -#: editor_actions.cc:118 +#: editor_actions.cc:119 #, fuzzy msgid "Select All in Punch Range" msgstr "Выбрать текущий интервал" -#: editor_actions.cc:120 +#: editor_actions.cc:121 #, fuzzy msgid "Select All in Loop Range" msgstr "выбрать окно проÑмотра" -#: editor_actions.cc:123 +#: editor_actions.cc:124 msgid "Jump Forward to Mark" msgstr "" -#: editor_actions.cc:125 +#: editor_actions.cc:126 msgid "Jump Backward to Mark" msgstr "" -#: editor_actions.cc:127 +#: editor_actions.cc:128 #, fuzzy msgid "Add Location from Playhead" msgstr "ВоÑпроизвеÑти от указателÑ" -#: editor_actions.cc:130 +#: editor_actions.cc:131 msgid "Nudge Forward" msgstr "" -#: editor_actions.cc:132 +#: editor_actions.cc:133 msgid "Nudge Next Forward" msgstr "" -#: editor_actions.cc:134 +#: editor_actions.cc:135 #, fuzzy msgid "Nudge Backward" msgstr "Скрыть трек" -#: editor_actions.cc:136 +#: editor_actions.cc:137 #, fuzzy msgid "Nudge Next Backward" msgstr "Скрыть трек" -#: editor_actions.cc:139 +#: editor_actions.cc:140 #, fuzzy msgid "Zoom Out" msgstr "Уменьшить" -#: editor_actions.cc:141 +#: editor_actions.cc:142 #, fuzzy msgid "Zoom In" msgstr "Увеличить" -#: editor_actions.cc:143 +#: editor_actions.cc:144 #, fuzzy msgid "Zoom to Session" msgstr "Показать вÑÑ‘" -#: editor_actions.cc:146 +#: editor_actions.cc:147 #, fuzzy msgid "Scroll Tracks Up" msgstr "Заполнить трек" -#: editor_actions.cc:148 +#: editor_actions.cc:149 msgid "Scroll Tracks Down" msgstr "" -#: editor_actions.cc:150 +#: editor_actions.cc:151 #, fuzzy msgid "Step Tracks Up" msgstr "Скрыть трек" -#: editor_actions.cc:152 +#: editor_actions.cc:153 msgid "Step Tracks Down" msgstr "" -#: editor_actions.cc:155 +#: editor_actions.cc:156 msgid "Scroll Backward" msgstr "" -#: editor_actions.cc:157 +#: editor_actions.cc:158 msgid "Scroll Forward" msgstr "" -#: editor_actions.cc:159 +#: editor_actions.cc:160 msgid "goto" msgstr "" -#: editor_actions.cc:161 +#: editor_actions.cc:162 #, fuzzy msgid "Center Playhead" msgstr "указателю" -#: editor_actions.cc:163 +#: editor_actions.cc:164 #, fuzzy msgid "Center Edit Cursor" msgstr "курÑору" -#: editor_actions.cc:165 +#: editor_actions.cc:166 #, fuzzy msgid "Playhead Forward" msgstr "указателю" -#: editor_actions.cc:167 +#: editor_actions.cc:168 #, fuzzy msgid "Playhead Backward" msgstr "указателю" -#: editor_actions.cc:169 +#: editor_actions.cc:170 #, fuzzy msgid "Playhead to Edit" msgstr "указателю" -#: editor_actions.cc:171 +#: editor_actions.cc:172 #, fuzzy msgid "Edit to Playhead" msgstr "ВоÑпроизвеÑти от указателÑ" -#: editor_actions.cc:174 +#: editor_actions.cc:175 #, fuzzy msgid "Align Regions Start" msgstr "нач. облаÑтей" -#: editor_actions.cc:176 +#: editor_actions.cc:177 #, fuzzy msgid "Align Regions Start Relative" msgstr "ВыровнÑть отноÑительно" -#: editor_actions.cc:178 +#: editor_actions.cc:179 #, fuzzy msgid "Align Regions End" msgstr "проÑлушать облаÑть" -#: editor_actions.cc:180 +#: editor_actions.cc:181 #, fuzzy msgid "Align Regions End Relative" msgstr "ВыровнÑть отноÑительно" -#: editor_actions.cc:183 +#: editor_actions.cc:184 #, fuzzy msgid "Align Regions Sync" msgstr "проÑлушать облаÑть" -#: editor_actions.cc:185 +#: editor_actions.cc:186 #, fuzzy msgid "Align Regions Sync Relative" msgstr "ВыровнÑть отноÑительно" -#: editor_actions.cc:188 +#: editor_actions.cc:189 #, fuzzy msgid "Audition at Mouse" msgstr "Ðудит" -#: editor_actions.cc:190 +#: editor_actions.cc:191 #, fuzzy msgid "Brush at Mouse" msgstr "иÑпользовать маÑтер-выходы" -#: editor_actions.cc:192 +#: editor_actions.cc:193 #, fuzzy msgid "Set Edit Cursor" msgstr "курÑору" -#: editor_actions.cc:194 +#: editor_actions.cc:195 #, fuzzy msgid "Mute/Unmute Region" msgstr "Создать облаÑть" -#: editor_actions.cc:196 +#: editor_actions.cc:197 #, fuzzy msgid "Set Playhead" msgstr "указателю" -#: editor_actions.cc:198 +#: editor_actions.cc:199 #, fuzzy msgid "Split Region" msgstr "Разделить облаÑть" -#: editor_actions.cc:200 +#: editor_actions.cc:201 #, fuzzy msgid "Set Region Sync Position" msgstr "по раÑположению облаÑти" -#: editor_actions.cc:208 +#: editor_actions.cc:209 #, fuzzy msgid "Export Session" msgstr "ЭкÑпорт облаÑти" -#: editor_actions.cc:210 +#: editor_actions.cc:211 #, fuzzy msgid "Export Range" msgstr "Разделить облаÑть" #. Note: for now, editor-delete does the exact same thing as editor-cut -#: editor_actions.cc:216 +#: editor_actions.cc:217 #, fuzzy msgid "Delete" msgstr "удалить" -#: editor_actions.cc:222 +#: editor_actions.cc:223 #, fuzzy msgid "Duplicate Region" msgstr "Разделить облаÑть" -#: editor_actions.cc:224 +#: editor_actions.cc:225 #, fuzzy msgid "Duplicate Range" msgstr "Размножить" -#: editor_actions.cc:226 +#: editor_actions.cc:227 msgid "Insert Region" msgstr "Ð’Ñтавить облаÑть" -#: editor_actions.cc:228 +#: editor_actions.cc:229 #, fuzzy msgid "Reverse Region" msgstr "Разделить облаÑть" -#: editor_actions.cc:230 +#: editor_actions.cc:231 #, fuzzy msgid "Normalize Region" msgstr "Создать облаÑть" -#: editor_actions.cc:232 +#: editor_actions.cc:233 #, fuzzy msgid "crop" msgstr "копировать" -#: editor_actions.cc:234 +#: editor_actions.cc:235 #, fuzzy msgid "Insert Chunk" msgstr "Ð’Ñтавить фрагмент" -#: editor_actions.cc:237 +#: editor_actions.cc:238 #, fuzzy msgid "Split at edit cursor" msgstr "От начала до курÑора" -#: editor_actions.cc:240 +#: editor_actions.cc:241 #, fuzzy msgid "Start Range" msgstr "Разделить облаÑть" -#: editor_actions.cc:242 +#: editor_actions.cc:243 msgid "Finish Range" msgstr "" -#: editor_actions.cc:244 +#: editor_actions.cc:245 msgid "Finish add Range" msgstr "" -#: editor_actions.cc:247 +#: editor_actions.cc:248 msgid "Extend Range to End of Region" msgstr "" -#: editor_actions.cc:249 +#: editor_actions.cc:250 #, fuzzy msgid "Extend Range to Start of Region" msgstr "Ð’ начало ÑеÑÑии" -#: editor_actions.cc:252 +#: editor_actions.cc:253 #, fuzzy msgid "Follow Playhead" msgstr "Следовать за указателем" -#: editor_actions.cc:260 +#: editor_actions.cc:261 #, fuzzy msgid "Zoom Focus Left" msgstr "МаÑштабировать к" -#: editor_actions.cc:262 +#: editor_actions.cc:263 #, fuzzy msgid "Zoom Focus Right" msgstr "МаÑштабировать к" -#: editor_actions.cc:264 +#: editor_actions.cc:265 #, fuzzy msgid "Zoom Focus Center" msgstr "МаÑштабировать к" -#: editor_actions.cc:266 +#: editor_actions.cc:267 #, fuzzy msgid "Zoom Focus Playhead" msgstr "МаÑштабировать к" -#: editor_actions.cc:268 +#: editor_actions.cc:269 #, fuzzy msgid "Zoom Focus Edit" msgstr "МаÑштабировать к" -#: editor_actions.cc:274 +#: editor_actions.cc:275 msgid "Object Tool" msgstr "" -#: editor_actions.cc:275 +#: editor_actions.cc:276 #, fuzzy msgid "Range Tool" msgstr "выделÑть" -#: editor_actions.cc:276 +#: editor_actions.cc:277 msgid "Gain Tool" msgstr "" -#: editor_actions.cc:277 +#: editor_actions.cc:278 #, fuzzy msgid "Zoom Tool" msgstr "Уменьшить" -#: editor_actions.cc:278 +#: editor_actions.cc:279 msgid "Timefx Tool" msgstr "" -#: editor_actions.cc:285 +#: editor_actions.cc:286 #, fuzzy msgid "Snap to frame" msgstr "ПривÑзка к" -#: editor_actions.cc:286 +#: editor_actions.cc:287 #, fuzzy msgid "Snap to cd frame" msgstr "ПривÑзка к" -#: editor_actions.cc:287 +#: editor_actions.cc:288 #, fuzzy msgid "Snap to SMPTE frame" msgstr "SMPTE Кадры/Секунды" -#: editor_actions.cc:288 +#: editor_actions.cc:289 #, fuzzy msgid "Snap to SMPTE seconds" msgstr "SMPTE Кадры/Секунды" -#: editor_actions.cc:289 +#: editor_actions.cc:290 msgid "Snap to SMPTE minutes" msgstr "" -#: editor_actions.cc:290 +#: editor_actions.cc:291 #, fuzzy msgid "Snap to seconds" msgstr "Минуты:Секунды" -#: editor_actions.cc:291 +#: editor_actions.cc:292 msgid "Snap to minutes" msgstr "" -#: editor_actions.cc:292 +#: editor_actions.cc:293 #, fuzzy msgid "Snap to thirtyseconds" msgstr "тридцать-вторых (32)" -#: editor_actions.cc:293 +#: editor_actions.cc:294 msgid "Snap to asixteenthbeat" msgstr "" -#: editor_actions.cc:294 +#: editor_actions.cc:295 msgid "Snap to eighths" msgstr "" -#: editor_actions.cc:295 +#: editor_actions.cc:296 msgid "Snap to quarters" msgstr "" -#: editor_actions.cc:296 +#: editor_actions.cc:297 #, fuzzy msgid "Snap to thirds" msgstr "ПривÑзка к" -#: editor_actions.cc:297 +#: editor_actions.cc:298 #, fuzzy msgid "Snap to beat" msgstr "ПривÑзка к" -#: editor_actions.cc:298 +#: editor_actions.cc:299 #, fuzzy msgid "Snap to bar" msgstr "ПривÑзка к" -#: editor_actions.cc:299 +#: editor_actions.cc:300 #, fuzzy msgid "Snap to mark" msgstr "добавить маркер" -#: editor_actions.cc:300 +#: editor_actions.cc:301 #, fuzzy msgid "Snap to edit cursor" msgstr "От начала до курÑора" -#: editor_actions.cc:301 +#: editor_actions.cc:302 #, fuzzy msgid "Snap to region start" msgstr "нач. облаÑтей" -#: editor_actions.cc:302 +#: editor_actions.cc:303 #, fuzzy msgid "Snap to region end" msgstr "оконч. облаÑтей" -#: editor_actions.cc:303 +#: editor_actions.cc:304 #, fuzzy msgid "Snap to region sync" msgstr "Создать моно-облаÑти" -#: editor_actions.cc:304 +#: editor_actions.cc:305 msgid "Snap to region boundary" msgstr "" #. the region list popup menu -#: editor_actions.cc:313 +#: editor_actions.cc:314 #, fuzzy msgid "Sort" msgstr "порт" -#: editor_actions.cc:321 +#: editor_actions.cc:322 msgid "Show all" msgstr "Показать вÑÑ‘" -#: editor_actions.cc:322 +#: editor_actions.cc:323 #, fuzzy msgid "Show automatic regions" msgstr "автомат" -#: editor_actions.cc:324 +#: editor_actions.cc:325 msgid "Ascending" msgstr "по возраÑтанию" -#: editor_actions.cc:326 +#: editor_actions.cc:327 msgid "Descending" msgstr "по убыванию" -#: editor_actions.cc:329 +#: editor_actions.cc:330 msgid "By Region Name" msgstr "по имени облаÑти" -#: editor_actions.cc:331 +#: editor_actions.cc:332 msgid "By Region Length" msgstr "по длине облаÑти" -#: editor_actions.cc:333 +#: editor_actions.cc:334 msgid "By Region Position" msgstr "по раÑположению облаÑти" -#: editor_actions.cc:335 +#: editor_actions.cc:336 msgid "By Region Timestamp" msgstr "по времени ÑÐ¾Ð·Ð´Ð°Ð½Ð¸Ñ Ð¾Ð±Ð»Ð°Ñти" -#: editor_actions.cc:337 +#: editor_actions.cc:338 msgid "By Region Start in File" msgstr "по началу облаÑти в файле" -#: editor_actions.cc:339 +#: editor_actions.cc:340 msgid "By Region End in File" msgstr "по концу облаÑти в файле" -#: editor_actions.cc:341 +#: editor_actions.cc:342 msgid "By Source File Name" msgstr "по имени файла" -#: editor_actions.cc:343 +#: editor_actions.cc:344 msgid "By Source File Length" msgstr "по размеру файла" -#: editor_actions.cc:345 +#: editor_actions.cc:346 msgid "By Source File Creation Date" msgstr "по дате ÑÐ¾Ð·Ð´Ð°Ð½Ð¸Ñ Ð¸Ñходного файла" -#: editor_actions.cc:347 +#: editor_actions.cc:348 msgid "By Source Filesystem" msgstr "по раÑположению файла" #. the next two are duplicate items with different names for use in two different contexts -#: editor_actions.cc:353 +#: editor_actions.cc:354 #, fuzzy msgid "Add External Audio" msgstr "Добавить во внешний ÑпиÑок облаÑтей" -#: editor_actions.cc:355 +#: editor_actions.cc:356 #, fuzzy msgid "as Region(s)" msgstr "ВоÑпроизвеÑти выделенную облаÑть" -#: editor_actions.cc:357 +#: editor_actions.cc:358 #, fuzzy msgid "as Tracks" msgstr "Треки" -#: editor_actions.cc:359 +#: editor_actions.cc:360 #, fuzzy msgid "to Tracks" msgstr "Треки" -#: editor_actions.cc:362 +#: editor_actions.cc:363 #, fuzzy msgid "Show Waveforms" msgstr "Отображать форму Ñигнала" -#: editor_actions.cc:363 +#: editor_actions.cc:364 #, fuzzy msgid "Show Waveforms While Recording" msgstr "Отображать форму Ñигнала" -#: editor_actions.cc:364 +#: editor_actions.cc:365 #, fuzzy msgid "Show Measures" msgstr "Показывать линии тактов" -#: editor_actions.cc:377 editor_actions.cc:384 +#: editor_actions.cc:378 editor_actions.cc:385 msgid "Medium" msgstr "" -#: editor_actions.cc:379 +#: editor_actions.cc:380 #, fuzzy msgid "Faster" msgstr "Затухание" -#: editor_actions.cc:385 +#: editor_actions.cc:386 msgid "Long" msgstr "" -#: editor_actions.cc:389 +#: editor_actions.cc:390 #, fuzzy msgid "Later is Higher" msgstr "ОпуÑтить облаÑть на один Ñлой" -#: editor_actions.cc:390 +#: editor_actions.cc:391 #, fuzzy msgid "Most Recently Moved/Added is Higher" msgstr "ОпуÑтить облаÑть на один Ñлой" -#: editor_actions.cc:391 +#: editor_actions.cc:392 #, fuzzy msgid "Most Recently Added is Higher" msgstr "ОпуÑтить облаÑть на один Ñлой" @@ -3449,39 +3439,39 @@ msgstr "Ð’Ñ‹ не можете импортировать аудиофайл п msgid "Add existing audio to session" msgstr "иÑпользовать имеющийÑÑ ÑˆÐ°Ð±Ð»Ð¾Ð½" -#: editor_audio_import.cc:143 +#: editor_audio_import.cc:142 #, fuzzy msgid "ardour: importing %1" msgstr "ardour: ÑкÑпорт" -#: editor_audio_import.cc:147 +#: editor_audio_import.cc:146 msgid "Cancel Import" msgstr "Отменить импорт" -#: editor_audio_import.cc:225 +#: editor_audio_import.cc:224 #, fuzzy msgid "Editor: cannot open file \"%1\", (%2)" msgstr "Редактор: не удалоÑÑŒ открыть файл \"%1\" (%2)" -#: editor_audio_import.cc:233 +#: editor_audio_import.cc:232 #, fuzzy msgid "Cancel entire import" msgstr "Отменить импорт" -#: editor_audio_import.cc:234 +#: editor_audio_import.cc:233 #, fuzzy msgid "Don't embed it" msgstr "Отмена" -#: editor_audio_import.cc:235 +#: editor_audio_import.cc:234 msgid "Embed all without questions" msgstr "" -#: editor_audio_import.cc:240 +#: editor_audio_import.cc:239 msgid "Embed it anyway" msgstr "" -#: editor_audio_import.cc:243 +#: editor_audio_import.cc:242 #, fuzzy msgid "" "%1\n" @@ -3490,75 +3480,63 @@ msgstr "" "Выбранный аудиофайл имеет чаÑтоту диÑкретизации данных\n" "отличную от текущей ÑеÑÑии!" -#: editor_audio_import.cc:276 +#: editor_audio_import.cc:275 msgid "could not open %1" msgstr "не удалоÑÑŒ открыть %1" -#: editor_audio_import.cc:321 +#: editor_audio_import.cc:320 #, fuzzy msgid "insert sndfile" msgstr "Ð’Ñтавить внешний аудиофайл" #. stuff for the verbose canvas cursor -#: editor_canvas.cc:117 +#: editor_canvas.cc:118 msgid "VerboseCanvasCursor" msgstr "" -#: editor_canvas.cc:285 -msgid "Start a new session\n" -msgstr "Ðачать новую ÑеÑÑию\n" - -#: editor_canvas.cc:285 -msgid "via Session menu" -msgstr "в меню \"СеÑÑиÑ\"" - -#: editor_canvas.cc:288 -msgid "FirstActionMessage" -msgstr "" - -#: editor_edit_groups.cc:52 mixer_ui.cc:732 +#: editor_edit_groups.cc:53 mixer_ui.cc:736 #, fuzzy msgid "Activate All" msgstr "Ðктивировать" -#: editor_edit_groups.cc:53 mixer_ui.cc:733 +#: editor_edit_groups.cc:54 mixer_ui.cc:737 #, fuzzy msgid "Disable All" msgstr "ОтÑоединить" -#: editor_edit_groups.cc:55 mixer_ui.cc:735 +#: editor_edit_groups.cc:56 mixer_ui.cc:739 #, fuzzy msgid "Add group" msgstr "Ðет группы" -#: editor_edit_groups.cc:225 mixer_ui.cc:964 +#: editor_edit_groups.cc:229 mixer_ui.cc:970 #, fuzzy msgid "unnamed" msgstr "Переименовать" -#: editor_edit_groups.cc:252 mixer_ui.cc:830 +#: editor_edit_groups.cc:258 mixer_ui.cc:834 msgid "-all-" msgstr "-вÑе-" -#: editor_export_audio.cc:64 +#: editor_export_audio.cc:65 msgid "" "There is no selection to export.\n" "\n" "Select a selection using the range mouse mode" msgstr "" -#: editor_export_audio.cc:109 +#: editor_export_audio.cc:110 msgid "" "There are no ranges to export.\n" "\n" "Create 1 or more ranges by dragging the mouse in the range bar" msgstr "" -#: editor_imageframe.cc:624 editor_imageframe.cc:654 +#: editor_imageframe.cc:625 editor_imageframe.cc:655 msgid "programming error: no ImageFrameView selected" msgstr "ошибка в программе: no ImageFrameView selected" -#: editor_imageframe.cc:847 editor_imageframe.cc:869 +#: editor_imageframe.cc:848 editor_imageframe.cc:870 msgid "programming error: no MarkerView selected" msgstr "ошибка в программе: no MarkerView selected" @@ -3567,141 +3545,141 @@ msgstr "ошибка в программе: no MarkerView selected" msgid "mute region" msgstr "отключить воÑпроизведение Ñтой облаÑти" -#: editor_keys.cc:45 +#: editor_keys.cc:46 #, fuzzy msgid "keyboard selection" msgstr "Выделить по интервалу" -#: editor_markers.cc:291 editor_ops.cc:1227 editor_ops.cc:1240 -#: editor_ops.cc:1258 location_ui.cc:773 +#: editor_markers.cc:292 editor_ops.cc:1290 editor_ops.cc:1303 +#: editor_ops.cc:1321 location_ui.cc:774 msgid "add marker" msgstr "добавить маркер" -#: editor_markers.cc:306 editor_markers.cc:379 editor_markers.cc:551 -#: editor_markers.cc:569 editor_markers.cc:588 editor_markers.cc:607 -#: editor_markers.cc:637 editor_markers.cc:665 editor_markers.cc:693 -#: editor_markers.cc:731 editor_markers.cc:758 editor_markers.cc:781 -#: editor_markers.cc:800 editor_mouse.cc:1994 editor_mouse.cc:4237 +#: editor_markers.cc:307 editor_markers.cc:380 editor_markers.cc:552 +#: editor_markers.cc:570 editor_markers.cc:589 editor_markers.cc:608 +#: editor_markers.cc:638 editor_markers.cc:666 editor_markers.cc:694 +#: editor_markers.cc:732 editor_markers.cc:759 editor_markers.cc:782 +#: editor_markers.cc:801 editor_mouse.cc:2015 editor_mouse.cc:4275 msgid "programming error: marker canvas item has no marker object pointer!" msgstr "ошибка в программе: marker canvas item has no marker object pointer!" -#: editor_markers.cc:330 location_ui.cc:655 +#: editor_markers.cc:331 location_ui.cc:656 msgid "remove marker" msgstr "" -#: editor_markers.cc:457 +#: editor_markers.cc:458 #, fuzzy msgid "Locate to Mark" msgstr "Маркеры интервалов" -#: editor_markers.cc:458 +#: editor_markers.cc:459 #, fuzzy msgid "Play from Mark" msgstr "ВоÑпроизвеÑти Ñ Ð½Ð°Ñ‡Ð°Ð»Ð°" -#: editor_markers.cc:459 +#: editor_markers.cc:460 #, fuzzy msgid "Set Mark from Playhead" msgstr "ВоÑпроизвеÑти от указателÑ" -#: editor_markers.cc:463 +#: editor_markers.cc:464 #, fuzzy msgid "Rename Mark" msgstr "Переименовать" -#: editor_markers.cc:464 +#: editor_markers.cc:465 #, fuzzy msgid "Hide Mark" msgstr "Скрыть трек" -#: editor_markers.cc:465 +#: editor_markers.cc:466 #, fuzzy msgid "Remove Mark" msgstr "Удалить поле" -#: editor_markers.cc:478 editor_markers.cc:534 +#: editor_markers.cc:479 editor_markers.cc:535 #, fuzzy msgid "Locate to Range Mark" msgstr "Маркеры интервалов" -#: editor_markers.cc:479 editor_markers.cc:535 +#: editor_markers.cc:480 editor_markers.cc:536 #, fuzzy msgid "Play from Range Mark" msgstr "ВоÑпроизвеÑти \"кольцо\"" -#: editor_markers.cc:480 +#: editor_markers.cc:481 #, fuzzy msgid "Loop Range" msgstr "ВоÑпроизвеÑти \"кольцо\"" -#: editor_markers.cc:481 editor_markers.cc:536 +#: editor_markers.cc:482 editor_markers.cc:537 #, fuzzy msgid "Set Range Mark from Playhead" msgstr "ВоÑпроизвеÑти от указателÑ" -#: editor_markers.cc:482 editor_markers.cc:537 +#: editor_markers.cc:483 editor_markers.cc:538 #, fuzzy msgid "Set Range from Range Selection" msgstr "ВоÑпроизвеÑти выделенное" -#: editor_markers.cc:486 +#: editor_markers.cc:487 #, fuzzy msgid "Rename Range" msgstr "Переименовать" -#: editor_markers.cc:487 editor_markers.cc:539 +#: editor_markers.cc:488 editor_markers.cc:540 #, fuzzy msgid "Hide Range" msgstr "выделÑть" -#: editor_markers.cc:488 +#: editor_markers.cc:489 #, fuzzy msgid "Remove Range" msgstr "Удалить поле" -#: editor_markers.cc:492 editor_markers.cc:541 +#: editor_markers.cc:493 editor_markers.cc:542 #, fuzzy msgid "Separate Regions in Range" msgstr "Создать облаÑть из выделенного" -#: editor_markers.cc:493 editor_markers.cc:542 +#: editor_markers.cc:494 editor_markers.cc:543 #, fuzzy msgid "Select All in Range" msgstr "Выделить вÑÑ‘" -#: editor_markers.cc:519 +#: editor_markers.cc:520 msgid "Set Loop Range" msgstr "" -#: editor_markers.cc:520 +#: editor_markers.cc:521 msgid "Set Punch Range" msgstr "" -#: editor_markers.cc:814 +#: editor_markers.cc:815 #, fuzzy msgid "New Name:" msgstr "новое имÑ: " -#: editor_markers.cc:817 +#: editor_markers.cc:818 msgid "ardour: rename mark" msgstr "ardour: переименовать маркер" -#: editor_markers.cc:819 +#: editor_markers.cc:820 #, fuzzy msgid "ardour: rename range" msgstr "ardour: переименовать облаÑть" -#: editor_markers.cc:839 +#: editor_markers.cc:840 #, fuzzy msgid "rename marker" msgstr "добавить маркер" -#: editor_markers.cc:864 +#: editor_markers.cc:865 #, fuzzy msgid "set loop range" msgstr "выбрать окно проÑмотра" -#: editor_markers.cc:890 +#: editor_markers.cc:891 #, fuzzy msgid "set punch range" msgstr "Выбрать текущий интервал" @@ -3710,71 +3688,76 @@ msgstr "Выбрать текущий интервал" msgid "Editor::event_frame() used on unhandled event type %1" msgstr "Editor::event_frame() used on unhandled event type %1" -#: editor_mouse.cc:1589 +#: editor_mouse.cc:313 +#, fuzzy +msgid "select on click" +msgstr "ИÑпользовать как щелчок метронома" + +#: editor_mouse.cc:1590 msgid "programming error: start_grab called without drag item" msgstr "ошибка в программе: start_grab called without drag item" -#: editor_mouse.cc:1793 +#: editor_mouse.cc:1814 #, fuzzy msgid "change fade in length" msgstr "редактировать введение в уровень" -#: editor_mouse.cc:1811 +#: editor_mouse.cc:1832 #, fuzzy msgid "programming error: fade out canvas item has no regionview data pointer!" msgstr "ошибка в программе: cursor canvas item has no cursor data pointer!" -#: editor_mouse.cc:1885 +#: editor_mouse.cc:1906 #, fuzzy msgid "change fade out length" msgstr "редактировать Ñведение в ноль" -#: editor_mouse.cc:1904 +#: editor_mouse.cc:1925 msgid "programming error: cursor canvas item has no cursor data pointer!" msgstr "ошибка в программе: cursor canvas item has no cursor data pointer!" -#: editor_mouse.cc:2119 +#: editor_mouse.cc:2142 #, fuzzy msgid "move marker" msgstr "Удалить поле" -#: editor_mouse.cc:2142 editor_mouse.cc:2173 editor_tempodisplay.cc:461 +#: editor_mouse.cc:2165 editor_mouse.cc:2196 editor_tempodisplay.cc:459 msgid "" "programming error: meter marker canvas item has no marker object pointer!" msgstr "" "ошибка в программе: meter marker canvas item has no marker object pointer!" -#: editor_mouse.cc:2241 +#: editor_mouse.cc:2264 #, fuzzy msgid "copy meter mark" msgstr "добавить маркер" -#: editor_mouse.cc:2251 +#: editor_mouse.cc:2274 msgid "move meter mark" msgstr "" -#: editor_mouse.cc:2266 editor_mouse.cc:2299 editor_tempodisplay.cc:327 -#: editor_tempodisplay.cc:411 editor_tempodisplay.cc:430 +#: editor_mouse.cc:2289 editor_mouse.cc:2322 editor_tempodisplay.cc:331 +#: editor_tempodisplay.cc:409 editor_tempodisplay.cc:428 msgid "" "programming error: tempo marker canvas item has no marker object pointer!" msgstr "" "ошибка в программе: tempo marker canvas item has no marker object pointer!" -#: editor_mouse.cc:2271 editor_mouse.cc:2304 editor_tempodisplay.cc:332 -#: editor_tempodisplay.cc:416 +#: editor_mouse.cc:2294 editor_mouse.cc:2327 editor_tempodisplay.cc:336 +#: editor_tempodisplay.cc:414 msgid "programming error: marker for tempo is not a tempo marker!" msgstr "ошибка в программе: marker for tempo is not a tempo marker!" -#: editor_mouse.cc:2371 +#: editor_mouse.cc:2394 #, fuzzy msgid "copy tempo mark" msgstr "добавить маркер" -#: editor_mouse.cc:2381 +#: editor_mouse.cc:2404 msgid "move tempo mark" msgstr "" -#: editor_mouse.cc:2395 editor_mouse.cc:2414 editor_mouse.cc:2427 +#: editor_mouse.cc:2418 editor_mouse.cc:2437 editor_mouse.cc:2450 msgid "" "programming error: control point canvas item has no control point object " "pointer!" @@ -3782,348 +3765,349 @@ msgstr "" "ошибка в программе: control point canvas item has no control point object " "pointer!" -#: editor_mouse.cc:2525 +#: editor_mouse.cc:2555 msgid "programming error: line canvas item has no line pointer!" msgstr "ошибка в программе: line canvas item has no line pointer!" -#: editor_mouse.cc:2634 +#: editor_mouse.cc:2664 #, fuzzy msgid "move region(s)" msgstr "Создать облаÑть" -#. this is committed in the grab finished callback. -#: editor_mouse.cc:2646 -msgid "Drag region copy" -msgstr "" - -#: editor_mouse.cc:2758 +#: editor_mouse.cc:2727 #, fuzzy msgid "Drag region brush" msgstr "проÑлушать облаÑть" +#. don't copy again +#. this is committed in the grab finished callback. +#: editor_mouse.cc:2751 +msgid "Drag region copy" +msgstr "" + #. A selection grab currently creates two undo/redo operations, one for #. creating the new region and another for moving it. #. -#: editor_mouse.cc:3574 +#: editor_mouse.cc:3609 #, fuzzy msgid "selection grab" msgstr "Выделенное" -#: editor_mouse.cc:3615 +#: editor_mouse.cc:3650 #, fuzzy msgid "cancel selection" msgstr "ВоÑпроизвеÑти выделенное" -#: editor_mouse.cc:3722 +#: editor_mouse.cc:3760 #, fuzzy msgid "range selection" msgstr "ВоÑпроизвеÑти выделенное" -#: editor_mouse.cc:3738 +#: editor_mouse.cc:3776 #, fuzzy msgid "trim selection start" msgstr "Выделить по интервалу" -#: editor_mouse.cc:3754 +#: editor_mouse.cc:3792 #, fuzzy msgid "trim selection end" msgstr "Выделить по интервалу" -#: editor_mouse.cc:3771 +#: editor_mouse.cc:3809 #, fuzzy msgid "move selection" msgstr "СвеÑти выделенное" -#: editor_mouse.cc:4157 +#: editor_mouse.cc:4195 #, fuzzy msgid "Start point trim" msgstr "От начала до курÑора" -#: editor_mouse.cc:4185 +#: editor_mouse.cc:4223 msgid "End point trim" msgstr "" -#: editor_mouse.cc:4224 +#: editor_mouse.cc:4262 msgid "trimmed region" msgstr "" -#: editor_mouse.cc:4363 +#: editor_mouse.cc:4400 #, fuzzy msgid "new range marker" msgstr "Маркеры интервалов" -#: editor_mouse.cc:4578 +#: editor_mouse.cc:4642 #, fuzzy msgid "select regions" msgstr "ВоÑпроизвеÑти выделенную облаÑть" -#: editor_mouse.cc:4607 +#: editor_mouse.cc:4671 msgid "Name for region:" msgstr "Ð˜Ð¼Ñ Ð¾Ð±Ð»Ð°Ñти: " -#: editor_mouse.cc:4671 +#: editor_mouse.cc:4735 #, fuzzy msgid "timestretch" msgstr "ardour: Ñффект timestretch" -#: editor_ops.cc:132 +#: editor_ops.cc:195 #, fuzzy msgid "split" msgstr "Склеить" -#: editor_ops.cc:168 +#: editor_ops.cc:231 #, fuzzy msgid "remove region" msgstr "Создать облаÑть" -#: editor_ops.cc:187 +#: editor_ops.cc:250 msgid "" " This is destructive, will possibly delete audio files\n" "It cannot be undone\n" "Do you really want to destroy %1 ?" msgstr "" -#: editor_ops.cc:191 +#: editor_ops.cc:254 #, fuzzy msgid "these regions" msgstr "ВоÑпроизвеÑти выделенную облаÑть" -#: editor_ops.cc:191 +#: editor_ops.cc:254 #, fuzzy msgid "this region" msgstr "отключить воÑпроизведение Ñтой облаÑти" -#: editor_ops.cc:193 editor_ops.cc:3229 route_ui.cc:700 -#: visual_time_axis.cc:277 +#: editor_ops.cc:256 editor_ops.cc:3318 route_ui.cc:707 +#: visual_time_axis.cc:278 msgid "No, do nothing." msgstr "Ðет" -#: editor_ops.cc:196 +#: editor_ops.cc:259 #, fuzzy msgid "Yes, destroy them." msgstr "Да" -#: editor_ops.cc:198 editor_ops.cc:3230 +#: editor_ops.cc:261 editor_ops.cc:3319 msgid "Yes, destroy it." msgstr "Да" -#: editor_ops.cc:289 editor_ops.cc:317 +#: editor_ops.cc:352 editor_ops.cc:380 #, fuzzy msgid "extend selection" msgstr "Выделить по интервалу" -#: editor_ops.cc:333 editor_ops.cc:367 editor_ops.cc:411 editor_ops.cc:437 +#: editor_ops.cc:396 editor_ops.cc:430 editor_ops.cc:474 editor_ops.cc:500 msgid "nudge forward" msgstr "" -#: editor_ops.cc:501 +#: editor_ops.cc:564 msgid "build_region_boundary_cache called with snap_type = %1" msgstr "build_region_boundary_cache called with snap_type = %1" -#: editor_ops.cc:1354 +#: editor_ops.cc:1420 #, fuzzy msgid "select all within" msgstr "Выделить вÑÑ‘" -#: editor_ops.cc:1380 +#: editor_ops.cc:1452 #, fuzzy msgid "set selection from region" msgstr "Создать облаÑть из выделенного" -#: editor_ops.cc:1413 +#: editor_ops.cc:1485 #, fuzzy msgid "set selection from range" msgstr "Создать облаÑть из выделенного" -#: editor_ops.cc:1443 +#: editor_ops.cc:1515 #, fuzzy msgid "select all from range" msgstr "выбрать окно проÑмотра" -#: editor_ops.cc:1465 +#: editor_ops.cc:1537 #, fuzzy msgid "select all from punch" msgstr "Выделить вÑÑ‘" -#: editor_ops.cc:1487 +#: editor_ops.cc:1559 #, fuzzy msgid "select all from loop" msgstr "Выделить вÑÑ‘" -#: editor_ops.cc:1501 +#: editor_ops.cc:1573 #, fuzzy msgid "select all after cursor" msgstr "От начала до курÑора" -#: editor_ops.cc:1506 +#: editor_ops.cc:1578 #, fuzzy msgid "select all before cursor" msgstr "ВоÑпроизвеÑти от курÑора" -#: editor_ops.cc:1536 +#: editor_ops.cc:1608 #, fuzzy msgid "select all between cursors" msgstr "ВоÑпроизвеÑти от курÑора" -#: editor_ops.cc:1667 +#: editor_ops.cc:1739 msgid "clear markers" msgstr "очиÑтить маркеры" -#: editor_ops.cc:1679 +#: editor_ops.cc:1751 msgid "clear ranges" msgstr "" -#: editor_ops.cc:1698 +#: editor_ops.cc:1770 msgid "clear locations" msgstr "очиÑтить интервалы" -#: editor_ops.cc:1748 +#: editor_ops.cc:1820 #, fuzzy msgid "insert dragged region" msgstr "Ð’Ñтавить облаÑть" -#: editor_ops.cc:1784 +#: editor_ops.cc:1856 #, fuzzy msgid "insert region" msgstr "Ð’Ñтавить облаÑть" -#: editor_ops.cc:1975 io_selector.cc:57 io_selector.cc:791 +#: editor_ops.cc:2047 io_selector.cc:58 io_selector.cc:792 msgid "OK" msgstr "ОК" -#: editor_ops.cc:1982 +#: editor_ops.cc:2054 msgid "ardour: rename region" msgstr "ardour: переименовать облаÑть" -#: editor_ops.cc:2205 editor_ops.cc:2254 +#: editor_ops.cc:2277 editor_ops.cc:2326 #, fuzzy msgid "separate" msgstr "Разделить облаÑть" -#: editor_ops.cc:2316 +#: editor_ops.cc:2388 #, fuzzy msgid "trim to selection" msgstr "Выделить по интервалу" -#: editor_ops.cc:2356 +#: editor_ops.cc:2428 msgid "region fill" msgstr "" -#: editor_ops.cc:2415 +#: editor_ops.cc:2487 #, fuzzy msgid "fill selection" msgstr "Закольцевать выделенное" -#: editor_ops.cc:2436 +#: editor_ops.cc:2508 #, fuzzy msgid "Programming error. that region doesn't cover that position" msgstr "ошибка в программе: location/marker map does not contain location!" -#: editor_ops.cc:2439 +#: editor_ops.cc:2511 #, fuzzy msgid "set region sync position" msgstr "ОблаÑти/положение" -#: editor_ops.cc:2454 +#: editor_ops.cc:2526 msgid "Place the edit cursor at the desired sync point" msgstr "ПомеÑтите курÑор на точку Ñинхронизации" -#: editor_ops.cc:2459 +#: editor_ops.cc:2531 #, fuzzy msgid "set sync from edit cursor" msgstr "ВоÑпроизвеÑти от курÑора" -#: editor_ops.cc:2471 +#: editor_ops.cc:2543 msgid "remove sync" msgstr "" -#: editor_ops.cc:2485 +#: editor_ops.cc:2557 msgid "naturalize" msgstr "" -#: editor_ops.cc:2549 +#: editor_ops.cc:2621 #, fuzzy msgid "align selection (relative)" msgstr "ВыровнÑть отноÑительно" -#: editor_ops.cc:2577 +#: editor_ops.cc:2649 #, fuzzy msgid "align selection" msgstr "СвеÑти выделенное" -#: editor_ops.cc:2589 +#: editor_ops.cc:2661 #, fuzzy msgid "align region" msgstr "проÑлушать облаÑть" -#: editor_ops.cc:2636 editor_ops.cc:2661 +#: editor_ops.cc:2708 editor_ops.cc:2733 #, fuzzy msgid "trim to edit" msgstr "От начала до курÑора" -#: editor_ops.cc:2712 +#: editor_ops.cc:2784 #, fuzzy msgid "ardour: freeze" msgstr "ardour: " -#: editor_ops.cc:2717 +#: editor_ops.cc:2789 #, fuzzy msgid "Cancel Freeze" msgstr "Отмена" -#: editor_ops.cc:2754 +#: editor_ops.cc:2826 #, fuzzy msgid "bounce range" msgstr "Выбрать текущий интервал" -#: editor_ops.cc:2807 +#: editor_ops.cc:2879 msgid "cut" msgstr "вырезать" -#: editor_ops.cc:2810 +#: editor_ops.cc:2882 msgid "copy" msgstr "копировать" -#: editor_ops.cc:2823 +#: editor_ops.cc:2895 msgid " objects" msgstr "объекты" -#: editor_ops.cc:2849 +#: editor_ops.cc:2921 msgid " range" msgstr "" -#: editor_ops.cc:3006 +#: editor_ops.cc:3078 #, fuzzy msgid "paste" msgstr "Ð’Ñтавить" -#: editor_ops.cc:3044 +#: editor_ops.cc:3116 #, fuzzy msgid "paste chunk" msgstr "Создать фрагмент" #. clear (below) will clear the argument list -#: editor_ops.cc:3085 +#: editor_ops.cc:3157 #, fuzzy msgid "duplicate region" msgstr "Разделить облаÑть" -#: editor_ops.cc:3130 +#: editor_ops.cc:3202 #, fuzzy msgid "duplicate selection" msgstr "СвеÑти выделенное" -#: editor_ops.cc:3170 +#: editor_ops.cc:3259 #, fuzzy msgid "clear playlist" msgstr "Ð˜Ð¼Ñ Ñнимка" -#: editor_ops.cc:3199 +#: editor_ops.cc:3288 #, fuzzy msgid "nudge track" msgstr "Скрыть трек" -#: editor_ops.cc:3226 +#: editor_ops.cc:3315 msgid "" "Do you really want to destroy the last capture?\n" "(This is destructive and cannot be undone)" @@ -4131,171 +4115,168 @@ msgstr "" "ПоÑледнюю запиÑÑŒ будет удалена. Ð’Ñ‹ уверены?\n" "(отмена операции невозможна)" -#: editor_ops.cc:3254 +#: editor_ops.cc:3343 #, fuzzy msgid "normalize" msgstr "Ðорм." -#: editor_ops.cc:3301 +#: editor_ops.cc:3390 msgid "reverse regions" msgstr "" -#: editor_region_list.cc:93 editor_region_list.cc:98 editor_region_list.cc:101 -#: location_ui.cc:55 +#: editor_region_list.cc:98 editor_region_list.cc:103 +#: editor_region_list.cc:106 location_ui.cc:56 msgid "Hidden" msgstr "Скрытый" #. added a new fresh one at the end -#: editor_route_list.cc:101 editor_route_list.cc:102 editor_route_list.cc:246 +#: editor_route_list.cc:102 editor_route_list.cc:103 editor_route_list.cc:247 msgid "editor" msgstr "редактор" -#: editor_route_list.cc:309 mixer_ui.cc:695 +#: editor_route_list.cc:310 mixer_ui.cc:699 msgid "Show All" msgstr "Показать вÑÑ‘" -#: editor_route_list.cc:310 mixer_ui.cc:696 +#: editor_route_list.cc:311 mixer_ui.cc:700 msgid "Hide All" msgstr "Скрыть вÑÑ‘" -#: editor_route_list.cc:311 mixer_ui.cc:697 +#: editor_route_list.cc:312 mixer_ui.cc:701 #, fuzzy msgid "Show All Audio Tracks" msgstr "Показать вÑе аудиошины" -#: editor_route_list.cc:312 mixer_ui.cc:698 +#: editor_route_list.cc:313 mixer_ui.cc:702 #, fuzzy msgid "Hide All Audio Tracks" msgstr "Скрыть вÑе аудиошины" -#: editor_route_list.cc:313 mixer_ui.cc:699 +#: editor_route_list.cc:314 mixer_ui.cc:703 #, fuzzy msgid "Show All Audio Busses" msgstr "Показать вÑе аудиошины" -#: editor_route_list.cc:314 mixer_ui.cc:700 +#: editor_route_list.cc:315 mixer_ui.cc:704 #, fuzzy msgid "Hide All Audio Busses" msgstr "Скрыть вÑе аудиошины" -#: editor_rulers.cc:311 +#: editor_rulers.cc:312 #, fuzzy msgid "New location marker" msgstr "Маркеры интервалов" -#: editor_rulers.cc:312 +#: editor_rulers.cc:313 #, fuzzy msgid "Clear all locations" msgstr "очиÑтить интервалы" #. ruler_items.push_back (MenuElem (_("New Range"))); -#: editor_rulers.cc:317 +#: editor_rulers.cc:318 #, fuzzy msgid "Clear all ranges" msgstr "ВоÑпроизвеÑти \"кольцо\"" -#: editor_rulers.cc:326 +#: editor_rulers.cc:327 #, fuzzy msgid "New Tempo" msgstr "Ðовый темп" -#: editor_rulers.cc:327 +#: editor_rulers.cc:328 #, fuzzy msgid "Clear tempo" msgstr "Ðовый темп" -#: editor_rulers.cc:332 +#: editor_rulers.cc:333 #, fuzzy msgid "New Meter" msgstr "Размер" -#: editor_rulers.cc:333 +#: editor_rulers.cc:334 #, fuzzy msgid "Clear meter" msgstr "очиÑтить маркеры" -#: editor_rulers.cc:341 +#: editor_rulers.cc:342 #, fuzzy msgid "Min:Secs" msgstr "Мин:Сек" -#: editor_selection_list.cc:110 +#: editor_selection_list.cc:108 #, fuzzy msgid "Name for Chunk:" msgstr "Ð¸Ð¼Ñ Ñ„Ñ€Ð°Ð³Ð¼ÐµÐ½Ñ‚Ð°:" -#: editor_selection_list.cc:113 +#: editor_selection_list.cc:111 #, fuzzy msgid "Create Chunk" msgstr "Создать фрагмент" -#: editor_selection_list.cc:113 +#: editor_selection_list.cc:111 msgid "Forget it" msgstr "Забыть" -#: editor_tempodisplay.cc:249 editor_tempodisplay.cc:289 +#: editor_tempodisplay.cc:253 editor_tempodisplay.cc:293 msgid "add" msgstr "добавить" -#: editor_tempodisplay.cc:271 +#: editor_tempodisplay.cc:275 #, fuzzy msgid "add tempo mark" msgstr "добавить маркер" -#: editor_tempodisplay.cc:311 +#: editor_tempodisplay.cc:315 #, fuzzy msgid "add meter mark" msgstr "добавить маркер" -#: editor_tempodisplay.cc:344 editor_tempodisplay.cc:375 +#: editor_tempodisplay.cc:348 editor_tempodisplay.cc:376 msgid "done" msgstr "готово" -#: editor_tempodisplay.cc:365 editor_tempodisplay.cc:396 +#: editor_tempodisplay.cc:366 editor_tempodisplay.cc:394 msgid "replace tempo mark" msgstr "" -#: editor_tempodisplay.cc:435 editor_tempodisplay.cc:466 +#: editor_tempodisplay.cc:433 editor_tempodisplay.cc:464 msgid "programming error: marker for meter is not a meter marker!" msgstr "ошибка в программе: marker for meter is not a meter marker!" -#: editor_tempodisplay.cc:445 editor_tempodisplay.cc:478 +#: editor_tempodisplay.cc:443 editor_tempodisplay.cc:476 #, fuzzy msgid "remove tempo mark" msgstr "Да, удалить вÑÑ‘" -#: editor_timefx.cc:50 +#: editor_timefx.cc:51 msgid "Quick but Ugly" msgstr "БыÑтро и грубо" -#: editor_timefx.cc:51 +#: editor_timefx.cc:52 msgid "Skip Anti-aliasing" msgstr "Без фильтрации" -#: editor_timefx.cc:53 -msgid "Stretch/Shrink it" -msgstr "РаÑÑ‚Ñнуть/Сжать" - -#: editor_timefx.cc:57 +#: editor_timefx.cc:56 msgid "ardour: timestretch" msgstr "ardour: Ñффект timestretch" -#: editor_timefx.cc:58 +#: editor_timefx.cc:57 msgid "TimeStretchDialog" msgstr "TimeStretchDialog" -#: editor_timefx.cc:80 editor_timefx.cc:81 editor_timefx.cc:82 -#: editor_timefx.cc:83 +#: editor_timefx.cc:70 +msgid "Stretch/Shrink it" +msgstr "РаÑÑ‚Ñнуть/Сжать" + +#: editor_timefx.cc:73 editor_timefx.cc:74 msgid "TimeStretchButton" msgstr "TimeStretchButton" -#: editor_timefx.cc:84 +#: editor_timefx.cc:75 msgid "TimeStretchProgress" msgstr "TimeStretchProgress" -#. GTK2FIX -#. current_timestretch->close (); -#: editor_timefx.cc:153 +#: editor_timefx.cc:139 msgid "timestretch cannot be started - thread creation error" msgstr "" @@ -4429,7 +4410,7 @@ msgstr "" msgid "Export to File" msgstr "ЭкÑпорт на CD" -#: export_dialog.cc:113 option_editor.cc:82 option_editor.cc:83 +#: export_dialog.cc:113 option_editor.cc:83 option_editor.cc:84 msgid "Browse" msgstr "Обзор" @@ -4445,7 +4426,8 @@ msgstr "ardour: ÑкÑпорт" msgid "ardour_export" msgstr "ardour_ÑкÑпорт" -#: export_dialog.cc:139 export_dialog.cc:155 +#: export_dialog.cc:139 export_dialog.cc:155 mixer_strip.cc:124 +#: mixer_strip.cc:767 #, fuzzy msgid "Output" msgstr "Выходов" @@ -4482,145 +4464,75 @@ msgstr "" msgid "File already exists, do you want to overwrite it?" msgstr "" -#: export_dialog.cc:1159 export_range_markers_dialog.cc:154 +#: export_dialog.cc:1159 export_range_markers_dialog.cc:153 msgid "Cannot write file in: " msgstr "" #. warning dialog -#: export_range_markers_dialog.cc:136 +#: export_range_markers_dialog.cc:135 msgid "Please enter a valid target directory." msgstr "" -#: export_range_markers_dialog.cc:144 +#: export_range_markers_dialog.cc:143 msgid "" "Please select an existing target directory. Files\n" "are not allowed!" msgstr "" -#: gain_automation_time_axis.cc:61 +#: gain_automation_time_axis.cc:62 #, fuzzy msgid "add gain automation event" msgstr "автомат" -#: gain_meter.cc:66 +#: gain_meter.cc:67 msgid "cannot find images for fader slider" msgstr "" -#: gain_meter.cc:73 +#: gain_meter.cc:74 msgid "cannot find images for fader rail" msgstr "" -#: gain_meter.cc:88 -msgid "dbFS" -msgstr "" - -#: gain_meter.cc:89 gain_meter.cc:143 gain_meter.cc:704 -msgid "pre" -msgstr "" - -#: gain_meter.cc:139 gain_meter.cc:700 -#, fuzzy -msgid "input" -msgstr "%1 вход" - -#: gain_meter.cc:147 gain_meter.cc:708 -#, fuzzy -msgid "post" -msgstr "порт" - -#. TRANSLATORS: this string should be longest of the strings -#. used to describe meter points. In english, its "input". -#. -#: gain_meter.cc:155 -msgid "tupni" -msgstr "" - -#: gain_meter.cc:174 gain_meter.cc:458 gain_meter.cc:480 gain_meter.cc:525 +#: gain_meter.cc:130 gain_meter.cc:339 gain_meter.cc:494 gain_meter.cc:539 #, fuzzy msgid "-inf" msgstr "в" -#: glade/new_session_dialog.glade.h:1 +#: gain_meter.cc:140 #, fuzzy -msgid "Advanced" -msgstr "Дополнительно..." +msgid "Fader automation mode" +msgstr "автомат" -#: glade/new_session_dialog.glade.h:2 -msgid "Input" +#: gain_meter.cc:141 +#, fuzzy +msgid "Fader automation type" +msgstr "автомат" + +#. XXX it might different in different languages +#: gain_meter.cc:182 gain_meter.cc:817 panner_ui.cc:99 panner_ui.cc:807 +msgid "Abs" msgstr "" -#: glade/new_session_dialog.glade.h:3 +#: gain_meter.cc:472 #, fuzzy -msgid "Output" -msgstr "Выходов" +msgid "-Inf" +msgstr "в" -#: glade/new_session_dialog.glade.h:4 +#: gain_meter.cc:781 mixer_strip.cc:770 panner_ui.cc:771 #, fuzzy -msgid "Automatically connect inputs" -msgstr "автоматичеÑкое подключение треков ко входам" +msgid "O" +msgstr "ИЛИ" -#: glade/new_session_dialog.glade.h:5 -#, fuzzy -msgid "Automatically connect outputs" -msgstr "ручное подключение треков к выходам" - -#: glade/new_session_dialog.glade.h:6 -#, fuzzy -msgid "Channel Count" -msgstr "Отменить импорт" - -#: glade/new_session_dialog.glade.h:7 -msgid "Connect to Master Bus" +#: gain_meter.cc:784 panner_ui.cc:774 +msgid "P" msgstr "" -#: glade/new_session_dialog.glade.h:8 -msgid "Connect to physical outputs" +#: gain_meter.cc:787 panner_ui.cc:777 +msgid "T" msgstr "" -#: glade/new_session_dialog.glade.h:9 -#, fuzzy -msgid "Create Control Bus" -msgstr "Контрольные выходы" - -#: glade/new_session_dialog.glade.h:10 -#, fuzzy -msgid "Create Master Bus" -msgstr "иÑпользовать маÑтер-выходы" - -#: glade/new_session_dialog.glade.h:11 -#, fuzzy -msgid "New Session" -msgstr "СеÑÑиÑ" - -#: glade/new_session_dialog.glade.h:12 -#, fuzzy -msgid "Open Recent Session" -msgstr "открыть ÑеÑÑию" - -#: glade/new_session_dialog.glade.h:13 -#, fuzzy -msgid "Open Session" -msgstr "открыть ÑеÑÑию" - -#: glade/new_session_dialog.glade.h:14 -#, fuzzy -msgid "Port limit" -msgstr "Забыть" - -#: glade/new_session_dialog.glade.h:15 -#, fuzzy -msgid "Select a File" -msgstr "Выделить вÑÑ‘" - -#: glade/new_session_dialog.glade.h:16 -#, fuzzy -msgid "Select a Session" -msgstr "ВоÑпроизвеÑти выделенную облаÑть" - -#: glade/new_session_dialog.glade.h:17 -#, fuzzy -msgid "Track/Bus connection options" -msgstr "Треки/Шины" +#: gain_meter.cc:790 panner_ui.cc:780 +msgid "W" +msgstr "" #: gtk-custom-ruler.c:126 #, fuzzy @@ -4667,235 +4579,235 @@ msgid "Draw current ruler position" msgstr "" #. end-of-file, other end closed or shutdown? -#: imageframe_socket_handler.cc:126 +#: imageframe_socket_handler.cc:127 msgid "Image Compositor Socket has been shutdown/closed" msgstr "" -#: imageframe_time_axis.cc:287 +#: imageframe_time_axis.cc:286 #, fuzzy msgid "0.5 seconds" msgstr "Минуты:Секунды" -#: imageframe_time_axis.cc:288 marker_time_axis.cc:241 +#: imageframe_time_axis.cc:287 marker_time_axis.cc:242 #, fuzzy msgid "1 seconds" msgstr "Минуты:Секунды" -#: imageframe_time_axis.cc:289 marker_time_axis.cc:242 +#: imageframe_time_axis.cc:288 marker_time_axis.cc:243 #, fuzzy msgid "1.5 seconds" msgstr "Минуты:Секунды" -#: imageframe_time_axis.cc:290 marker_time_axis.cc:243 +#: imageframe_time_axis.cc:289 marker_time_axis.cc:244 #, fuzzy msgid "2 seconds" msgstr "Минуты:Секунды" -#: imageframe_time_axis.cc:291 marker_time_axis.cc:244 +#: imageframe_time_axis.cc:290 marker_time_axis.cc:245 #, fuzzy msgid "2.5 seconds" msgstr "Минуты:Секунды" -#: imageframe_time_axis.cc:292 marker_time_axis.cc:245 +#: imageframe_time_axis.cc:291 marker_time_axis.cc:246 #, fuzzy msgid "3 seconds" msgstr "Минуты:Секунды" #. duration_items.push_back(SeparatorElem()) ; #. duration_items.push_back(MenuElem (_("custom"), mem_fun(*this, &ImageFrameTimeAxis::set_marker_duration_custom))) ; -#: imageframe_time_axis.cc:297 marker_time_axis.cc:250 +#: imageframe_time_axis.cc:296 marker_time_axis.cc:251 msgid "Duration (sec)" msgstr "" -#: imageframe_time_axis.cc:302 +#: imageframe_time_axis.cc:301 #, fuzzy msgid "Remove Frame" msgstr "Удалить поле" -#: imageframe_time_axis.cc:305 +#: imageframe_time_axis.cc:304 #, fuzzy msgid "Image Frame" msgstr "Кадр" -#: imageframe_time_axis.cc:306 marker_time_axis.cc:256 +#: imageframe_time_axis.cc:305 marker_time_axis.cc:257 #, fuzzy msgid "Rename Track" msgstr "Переименовать" -#: io_selector.cc:59 io_selector.cc:793 +#: io_selector.cc:60 io_selector.cc:794 #, fuzzy msgid "Rescan" msgstr "обновить" -#: io_selector.cc:67 +#: io_selector.cc:68 msgid "%1 input" msgstr "%1 вход" -#: io_selector.cc:69 +#: io_selector.cc:70 msgid "%1 output" msgstr "%1 выход" -#: io_selector.cc:141 route_params_ui.cc:106 +#: io_selector.cc:142 route_params_ui.cc:107 msgid "Inputs" msgstr "Входов" -#: io_selector.cc:141 route_params_ui.cc:107 +#: io_selector.cc:142 route_params_ui.cc:108 msgid "Outputs" msgstr "Выходов" -#: io_selector.cc:142 +#: io_selector.cc:143 #, fuzzy msgid "Add Input" msgstr "добавить вход" -#: io_selector.cc:142 +#: io_selector.cc:143 #, fuzzy msgid "Add Output" msgstr "добавить выход" -#: io_selector.cc:143 +#: io_selector.cc:144 #, fuzzy msgid "Remove Input" msgstr "Удалить" -#: io_selector.cc:143 +#: io_selector.cc:144 #, fuzzy msgid "Remove Output" msgstr "# Выходов" -#: io_selector.cc:144 +#: io_selector.cc:145 #, fuzzy msgid "Disconnect All" msgstr "ОтÑоединить" -#: io_selector.cc:158 +#: io_selector.cc:159 msgid "Available connections" msgstr "ДоÑтупные ÑоединениÑ" -#: io_selector.cc:554 io_selector.cc:573 +#: io_selector.cc:555 io_selector.cc:574 msgid "There are no more JACK ports available." msgstr "" -#: io_selector.cc:648 io_selector.cc:675 io_selector.cc:728 +#: io_selector.cc:649 io_selector.cc:676 io_selector.cc:729 msgid "port" msgstr "порт" -#: io_selector.cc:797 +#: io_selector.cc:798 msgid "ardour: " msgstr "ardour: " -#: keyboard.cc:297 +#: keyboard.cc:299 msgid "KeyboardTarget: keyname \"%1\" is unknown." msgstr "KeyboardTarget: \"%1\" - неизвеÑтное имÑ." -#: keyboard.cc:523 +#: keyboard.cc:525 msgid "" "Your system is completely broken - NumLock uses \"%1\"as its modifier. This " "is madness - see the man page for xmodmap to find out how to fix this." msgstr "" -#: keyboard.cc:531 +#: keyboard.cc:533 msgid "" "Your system generates \"%1\" when the NumLock key is pressed. This can cause " "problems when editing so Ardour will use %2 to mean Meta rather than %1" msgstr "" -#: keyboard.cc:592 +#: keyboard.cc:594 msgid "You have %1 keys bound to \"mod1\"" msgstr "Ð”Ð»Ñ \"mod1\" назначено кнопок: %1" -#: keyboard.cc:607 +#: keyboard.cc:609 msgid "You have %1 keys bound to \"mod2\"" msgstr "Ð”Ð»Ñ \"mod2\" назначено кнопок: %1" -#: keyboard.cc:622 +#: keyboard.cc:624 msgid "You have %1 keys bound to \"mod3\"" msgstr "Ð”Ð»Ñ \"mod3\" назначено кнопок: %1" -#: keyboard.cc:637 +#: keyboard.cc:639 msgid "You have %1 keys bound to \"mod4\"" msgstr "Ð”Ð»Ñ \"mod4\" назначено кнопок: %1" -#: keyboard.cc:652 +#: keyboard.cc:654 msgid "You have %1 keys bound to \"mod5\"" msgstr "Ð”Ð»Ñ \"mod5\" назначено кнопок: %1" -#: location_ui.cc:47 location_ui.cc:50 +#: location_ui.cc:48 location_ui.cc:51 msgid "Set" msgstr "" -#: location_ui.cc:48 location_ui.cc:51 +#: location_ui.cc:49 location_ui.cc:52 msgid "Go" msgstr "" -#: location_ui.cc:54 +#: location_ui.cc:55 msgid "CD" msgstr "CD" -#: location_ui.cc:57 +#: location_ui.cc:58 msgid "SCMS" msgstr "" -#: location_ui.cc:58 +#: location_ui.cc:59 msgid "Pre-Emphasis" msgstr "" -#: location_ui.cc:569 +#: location_ui.cc:570 msgid "Add New Location" msgstr "Добавить новый интервал" -#: location_ui.cc:570 +#: location_ui.cc:571 msgid "Add New Range" msgstr "" -#: location_ui.cc:574 +#: location_ui.cc:575 msgid "ardour: locations" msgstr "ardour: интервалы" -#: location_ui.cc:575 +#: location_ui.cc:576 msgid "ardour_locations" msgstr "ardour_интервалы" -#: location_ui.cc:603 +#: location_ui.cc:604 #, fuzzy msgid "Location (CD Index) Markers" msgstr "Маркеры интервалов" -#: location_ui.cc:623 +#: location_ui.cc:624 msgid "Range (CD Track) Markers" msgstr "" -#: location_ui.cc:789 +#: location_ui.cc:790 msgid "add range marker" msgstr "" -#: main.cc:71 +#: main.cc:72 msgid "ardour is killing itself for a clean exit\n" msgstr "ardour: принудительное завершение работы\n" -#: main.cc:80 +#: main.cc:81 msgid "stopping user interface\n" msgstr "завершение работы...\n" #. XXX its doubtful that snprintf() is async-safe -#: main.cc:99 +#: main.cc:100 #, fuzzy, c-format msgid "%d(%d): received signal %d\n" msgstr "%d: принÑÑ‚ Ñигнал %d\n" -#: main.cc:185 +#: main.cc:186 msgid "cannot become new process group leader (%1)" msgstr "" -#: main.cc:212 +#: main.cc:213 msgid "cannot setup signal handling for %1" msgstr "cannot setup signal handling for %1" -#: main.cc:223 +#: main.cc:224 msgid "cannot set default signal mask (%1)" msgstr "cannot set default signal mask (%1)" -#: main.cc:253 +#: main.cc:254 #, fuzzy msgid "" "Without a UI style file, ardour will look strange.\n" @@ -4905,12 +4817,12 @@ msgstr "" "без файла определÑющего Ñтиль отображениÑ.\n" "ПожалуйÑта, укажите его (файл) в переменной Ð¾ÐºÑ€ÑƒÐ¶ÐµÐ½Ð¸Ñ ARDOUR_UI_RC" -#: main.cc:273 +#: main.cc:276 #, fuzzy msgid "Ardour could not connect to JACK." msgstr "Ðе удалоÑÑŒ ÑоединитьÑÑ Ñ Ñервером JACK как \"%1\"" -#: main.cc:277 +#: main.cc:280 #, fuzzy msgid "" "There are several possible reasons:\n" @@ -4930,71 +4842,12 @@ msgstr "" "\n" "ПожалуйÑта, проверьте вÑе варианты, возможно потребуетÑÑ (пере)запуÑк JACK." -#: main.cc:324 -msgid "Ardour/GTK " -msgstr "Ardour/GTK " - -#: main.cc:326 -msgid "" -"\n" -" (built using " -msgstr "" - -#: main.cc:330 -#, fuzzy -msgid " with libardour " -msgstr " работает Ñ libardour " - -#: main.cc:335 -msgid " and GCC version " -msgstr "" - -#: main.cc:345 -#, fuzzy -msgid "Copyright (C) 1999-2005 Paul Davis" -msgstr "ÐвторÑкое право 1999-2004 Paul Davis" - -#: main.cc:346 -msgid "" -"Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " -"Baker" -msgstr "" - -#: main.cc:348 -msgid "Ardour comes with ABSOLUTELY NO WARRANTY" -msgstr "Ardour раÑпроÑтранÑетÑÑ Ð‘Ð•Ð— ВСЯКИХ ГÐРÐÐТИЙ" - -#: main.cc:349 -msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." -msgstr "" - -#: main.cc:350 -msgid "This is free software, and you are welcome to redistribute it " -msgstr "Это Ñвободное программное обеÑпечение, Ð’Ñ‹ можете раÑпроÑтранÑть его" - -#: main.cc:351 -#, fuzzy -msgid "under certain conditions; see the source for copying conditions." -msgstr "на определённых уÑловиÑÑ…; подробнее об Ñтом читайте в файле COPYING." - -#: main.cc:360 -msgid "could not create ARDOUR GUI" -msgstr "не удалоÑÑŒ Ñоздать графичеÑкий Ð¸Ð½Ñ‚ÐµÑ€Ñ„ÐµÐ¹Ñ Ð´Ð»Ñ ARDOUR" - -#: main.cc:378 -msgid "Could not connect to JACK server as \"%1\"" -msgstr "Ðе удалоÑÑŒ ÑоединитьÑÑ Ñ Ñервером JACK как \"%1\"" - -#: main.cc:381 -msgid "could not initialize Ardour." -msgstr "не удалоÑÑŒ запуÑтить Ardour." - -#: main.cc:392 +#: main.cc:310 msgid "could not load command line session \"%1\"" msgstr "не удалоÑÑŒ загрузить ÑеÑÑию \"%1\", указанную в командной Ñтроке" #. it wasn't new, but we require a new session -#: main.cc:412 +#: main.cc:330 msgid "" "\n" "\n" @@ -5002,7 +4855,7 @@ msgid "" "To avoid this message, start ardour as \"ardour %1" msgstr "" -#: main.cc:423 +#: main.cc:341 msgid "" "\n" "\n" @@ -5010,307 +4863,445 @@ msgid "" "To create it from the command line, start ardour as \"ardour --new %1" msgstr "" +#: main.cc:405 +msgid "Ardour/GTK " +msgstr "Ardour/GTK " + +#: main.cc:407 +msgid "" +"\n" +" (built using " +msgstr "" + +#: main.cc:411 +#, fuzzy +msgid " with libardour " +msgstr " работает Ñ libardour " + +#: main.cc:416 +msgid " and GCC version " +msgstr "" + +#: main.cc:426 +#, fuzzy +msgid "Copyright (C) 1999-2006 Paul Davis" +msgstr "ÐвторÑкое право 1999-2004 Paul Davis" + +#: main.cc:427 +msgid "" +"Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " +"Baker" +msgstr "" + +#: main.cc:429 +msgid "Ardour comes with ABSOLUTELY NO WARRANTY" +msgstr "Ardour раÑпроÑтранÑетÑÑ Ð‘Ð•Ð— ВСЯКИХ ГÐРÐÐТИЙ" + +#: main.cc:430 +msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." +msgstr "" + +#: main.cc:431 +msgid "This is free software, and you are welcome to redistribute it " +msgstr "Это Ñвободное программное обеÑпечение, Ð’Ñ‹ можете раÑпроÑтранÑть его" + +#: main.cc:432 +#, fuzzy +msgid "under certain conditions; see the source for copying conditions." +msgstr "на определённых уÑловиÑÑ…; подробнее об Ñтом читайте в файле COPYING." + +#: main.cc:441 +msgid "could not create ARDOUR GUI" +msgstr "не удалоÑÑŒ Ñоздать графичеÑкий Ð¸Ð½Ñ‚ÐµÑ€Ñ„ÐµÐ¹Ñ Ð´Ð»Ñ ARDOUR" + +#: main.cc:459 +msgid "Could not connect to JACK server as \"%1\"" +msgstr "Ðе удалоÑÑŒ ÑоединитьÑÑ Ñ Ñервером JACK как \"%1\"" + +#: main.cc:462 +msgid "could not initialize Ardour." +msgstr "не удалоÑÑŒ запуÑтить Ardour." + #: marker.cc:244 #, fuzzy msgid "MarkerText" msgstr "маркерам" -#: marker_time_axis.cc:253 +#: marker_time_axis.cc:254 #, fuzzy msgid "Remove Marker" msgstr "Удалить поле" -#: marker_time_axis.cc:255 +#: marker_time_axis.cc:256 #, fuzzy msgid "Marker" msgstr "маркерам" -#: meter_bridge.cc:77 +#: meter_bridge.cc:78 msgid "ardour: meter bridge" msgstr "ardour: индикатор уровнÑ" -#: meter_bridge.cc:78 +#: meter_bridge.cc:79 msgid "ardour_meter_bridge" msgstr "ardour_индикатор_уровнÑ" -#: meter_bridge_strip.cc:79 meter_bridge_strip.cc:93 +#: meter_bridge_strip.cc:80 meter_bridge_strip.cc:94 #, c-format msgid "# of %u-sample overs" msgstr "" -#: meter_bridge_strip.cc:221 +#: meter_bridge_strip.cc:222 #, fuzzy msgid "New Name for Meter:" msgstr "Ðовое Ð¸Ð¼Ñ Ð¸Ð½Ð´Ð¸ÐºÐ°Ñ‚Ð¾Ñ€Ð°:" -#: mixer_strip.cc:85 mixer_strip.cc:437 region_editor.cc:46 -msgid "mute" -msgstr "тихо" +#: mixer_strip.cc:95 mixer_strip.cc:140 mixer_strip.cc:1227 +msgid "pre" +msgstr "" -#: mixer_strip.cc:85 mixer_strip.cc:438 -msgid "solo" -msgstr "Ñоло" - -#: mixer_strip.cc:85 mixer_strip.cc:436 -msgid "RECORD" -msgstr "ЗÐПИСЬ" - -#: mixer_strip.cc:96 mixer_strip.cc:441 mixer_strip.cc:1064 +#: mixer_strip.cc:96 mixer_strip.cc:822 msgid "Comments" msgstr "" -#: mixer_strip.cc:120 mixer_strip.cc:752 -msgid "INPUT" -msgstr "ВХОД" - -#: mixer_strip.cc:125 mixer_strip.cc:773 -msgid "OUTPUT" -msgstr "ВЫХОД" - -#: mixer_strip.cc:140 +#: mixer_strip.cc:119 #, fuzzy -msgid "Pan automation mode" -msgstr "автомат" +msgid "Input" +msgstr "Входов" -#: mixer_strip.cc:141 +#: mixer_strip.cc:136 mixer_strip.cc:1223 #, fuzzy -msgid "Gain automation mode" -msgstr "автомат" +msgid "input" +msgstr "%1 вход" -#: mixer_strip.cc:143 +#: mixer_strip.cc:144 mixer_strip.cc:1231 #, fuzzy -msgid "Pan automation type" -msgstr "автомат" +msgid "post" +msgstr "порт" -#: mixer_strip.cc:144 -#, fuzzy -msgid "Gain automation type" -msgstr "автомат" - -#: mixer_strip.cc:183 mixer_strip.cc:195 mixer_strip.cc:913 -msgid "trim" +#. TRANSLATORS: this string should be longest of the strings +#. used to describe meter points. In english, its "input". +#. +#: mixer_strip.cc:152 +msgid "tupni" msgstr "" -#. XXX it might different in different languages -#: mixer_strip.cc:184 mixer_strip.cc:196 mixer_strip.cc:917 -msgid "abs" +#: mixer_strip.cc:207 +msgid "Varispeed" msgstr "" -#: mixer_strip.cc:203 -#, fuzzy -msgid "gain automation mode" -msgstr "автомат" - -#: mixer_strip.cc:204 -#, fuzzy -msgid "pan automation mode" -msgstr "автомат" - -#: mixer_strip.cc:205 -#, fuzzy -msgid "gain automation state" -msgstr "автомат" - -#: mixer_strip.cc:206 -#, fuzzy -msgid "pan automation state" -msgstr "автомат" - -#: mixer_strip.cc:223 -msgid "varispeed" -msgstr "" - -#: mixer_strip.cc:245 mixer_strip.cc:1078 +#: mixer_strip.cc:233 mixer_strip.cc:836 msgid "Click to Add/Edit Comments" msgstr "" -#: mixer_strip.cc:393 +#: mixer_strip.cc:374 msgid "unknown strip width \"%1\" in XML GUI information" msgstr "неизвеÑÑ‚Ð½Ð°Ñ ÑˆÐ¸Ñ€Ð¸Ð½Ð° трека \"%1\" в XML опиÑании" -#: mixer_strip.cc:443 mixer_strip.cc:1062 -msgid "*Comments*" +#: mixer_strip.cc:417 +#, fuzzy +msgid "record" +msgstr "ЗапиÑÑŒ" + +#: mixer_strip.cc:418 region_editor.cc:47 +msgid "mute" +msgstr "тихо" + +#: mixer_strip.cc:419 +msgid "solo" +msgstr "Ñоло" + +#: mixer_strip.cc:422 +msgid "comments" msgstr "" -#: mixer_strip.cc:457 -msgid "REC" -msgstr "ЗÐП" +#: mixer_strip.cc:424 +msgid "*comments*" +msgstr "" -#: mixer_strip.cc:462 mixer_strip.cc:1072 +#: mixer_strip.cc:438 +#, fuzzy +msgid "Rec" +msgstr "обновить" + +#: mixer_strip.cc:439 +msgid "M" +msgstr "" + +#: mixer_strip.cc:440 +msgid "S" +msgstr "" + +#: mixer_strip.cc:443 mixer_strip.cc:830 #, fuzzy msgid "Cmt" msgstr "вырезать" -#: mixer_strip.cc:464 mixer_strip.cc:1070 +#: mixer_strip.cc:445 mixer_strip.cc:828 msgid "*Cmt*" msgstr "" -#: mixer_strip.cc:503 mixer_strip.cc:562 redirect_box.cc:1004 +#: mixer_strip.cc:483 mixer_strip.cc:549 redirect_box.cc:1006 msgid "Not connected to JACK - no I/O changes are possible" msgstr "" -#: mixer_strip.cc:569 +#: mixer_strip.cc:560 msgid "Track" msgstr "Трек" -#: mixer_strip.cc:593 mixer_strip.cc:609 +#: mixer_strip.cc:588 mixer_strip.cc:604 msgid "could not register new ports required for that connection" msgstr "" -#: mixer_strip.cc:755 -msgid "IN" +#: mixer_strip.cc:747 +#, fuzzy +msgid " Input" +msgstr "# Входов" + +#: mixer_strip.cc:750 +#, fuzzy +msgid "I" msgstr "Ð’Ð¥" -#: mixer_strip.cc:776 -msgid "OUT" -msgstr "ВЫХ" +#: mixer_strip.cc:820 +msgid "*Comments*" +msgstr "" -#: mixer_strip.cc:884 -msgid "aplay" -msgstr "авоÑпр" - -#: mixer_strip.cc:890 -#, fuzzy -msgid "awrite" -msgstr "запиÑÑŒ" - -#: mixer_strip.cc:1095 +#: mixer_strip.cc:859 #, fuzzy msgid ": comment editor" msgstr "ИнтерфейÑ: не удалоÑÑŒ инициализировать редактор" -#: mixer_strip.cc:1157 mixer_strip.cc:1178 -msgid "no group" -msgstr "нет группы" +#: mixer_strip.cc:953 +msgid "Grp" +msgstr "" -#: mixer_strip.cc:1181 +#: mixer_strip.cc:956 msgid "~G" msgstr "нГр" -#: mixer_strip.cc:1229 +#: mixer_strip.cc:1004 #, fuzzy msgid "Invert Polarity" msgstr "полÑрноÑть" -#: mixer_ui.cc:84 +#: mixer_ui.cc:85 msgid "Strips" msgstr "Каналы" -#: mixer_ui.cc:108 -msgid "groupname" -msgstr "" +#: mixer_ui.cc:110 +#, fuzzy +msgid "Group" +msgstr "Mix группы" -#: mixer_ui.cc:109 region_editor.cc:48 region_editor.cc:191 -#: region_editor.cc:225 -msgid "active" -msgstr "активно" - -#: mixer_ui.cc:110 region_editor.cc:49 -msgid "visible" -msgstr "отображать" - -#: mixer_ui.cc:207 mixer_ui.cc:366 +#: mixer_ui.cc:211 mixer_ui.cc:370 msgid "ardour: mixer" msgstr "ardour: микшер" -#: mixer_ui.cc:208 +#: mixer_ui.cc:212 msgid "ardour_mixer" msgstr "ardour_микшер" -#: mixer_ui.cc:342 +#: mixer_ui.cc:346 msgid "ardour: mixer: " msgstr "ardour: микшер: " -#: mixer_ui.cc:569 +#: mixer_ui.cc:573 msgid "signal" msgstr "Ñигнал" -#: mixer_ui.cc:719 +#: mixer_ui.cc:723 msgid "track display list item for renamed strip not found!" msgstr "" -#: option_editor.cc:75 +#: new_session_dialog.cc:39 +#, fuzzy +msgid "New Session Name :" +msgstr "Ð˜Ð¼Ñ ÑеÑÑии:" + +#: new_session_dialog.cc:41 +msgid "Create Session Directory In :" +msgstr "" + +#: new_session_dialog.cc:43 +#, fuzzy +msgid "Use Session Template :" +msgstr "иÑпользовать имеющийÑÑ ÑˆÐ°Ð±Ð»Ð¾Ð½" + +#: new_session_dialog.cc:45 +#, fuzzy +msgid "Channel Count" +msgstr "Отменить импорт" + +#: new_session_dialog.cc:46 +#, fuzzy +msgid "Create Monitor Bus" +msgstr "Контрольные выходы" + +#: new_session_dialog.cc:53 +#, fuzzy +msgid "Create Master Bus" +msgstr "иÑпользовать маÑтер-выходы" + +#: new_session_dialog.cc:55 +#, fuzzy +msgid "Automatically Connect Inputs" +msgstr "автоматичеÑкое подключение треков ко входам" + +#: new_session_dialog.cc:56 new_session_dialog.cc:67 +#, fuzzy +msgid "Port Limit" +msgstr "Забыть" + +#: new_session_dialog.cc:64 +#, fuzzy +msgid "Track/Bus Inputs" +msgstr "Треки/Шины" + +#: new_session_dialog.cc:66 +#, fuzzy +msgid "Automatically Connect Outputs" +msgstr "ручное подключение треков к выходам" + +#: new_session_dialog.cc:75 +msgid "Connect to Master Bus" +msgstr "" + +#: new_session_dialog.cc:76 +msgid "Connect to Physical Outputs" +msgstr "" + +#: new_session_dialog.cc:80 +#, fuzzy +msgid "Track/Bus Outputs" +msgstr "Выходов" + +#: new_session_dialog.cc:83 +#, fuzzy +msgid "Advanced Options" +msgstr "Редактор параметров" + +#: new_session_dialog.cc:91 +#, fuzzy +msgid "Open Recent Session" +msgstr "открыть ÑеÑÑию" + +#: new_session_dialog.cc:127 +#, fuzzy +msgid "Open Session File :" +msgstr "открыть ÑеÑÑию" + +#: new_session_dialog.cc:274 +#, fuzzy +msgid "New Session" +msgstr "СеÑÑиÑ" + +#: new_session_dialog.cc:276 +#, fuzzy +msgid "Open Session" +msgstr "открыть ÑеÑÑию" + +#: new_session_dialog.cc:281 +#, fuzzy +msgid "ardour: session control" +msgstr "ardour_новаÑ_ÑеÑÑиÑ" + +#: new_session_dialog.cc:310 +#, fuzzy +msgid "select template" +msgstr "-шаблон" + +#: new_session_dialog.cc:316 +#, fuzzy +msgid "select session file" +msgstr "ВоÑпроизвеÑти выделенную облаÑть" + +#: new_session_dialog.cc:325 +#, fuzzy +msgid "select directory" +msgstr "ВоÑпроизвеÑти выделенную облаÑть" + +#: option_editor.cc:76 #, fuzzy msgid "SMPTE offset is negative" msgstr "Смещение SMPTE" -#: option_editor.cc:101 +#: option_editor.cc:102 msgid "ardour: options editor" msgstr "adour: редактор параметров" -#: option_editor.cc:102 +#: option_editor.cc:103 msgid "ardour_option_editor" msgstr "adour_редактор_параметров" -#: option_editor.cc:126 +#: option_editor.cc:127 msgid "Paths/Files" msgstr "Пути/Файлы" -#: option_editor.cc:127 +#: option_editor.cc:128 msgid "Kbd/Mouse" msgstr "Клавиатура/Мышь" -#: option_editor.cc:130 +#: option_editor.cc:131 msgid "Layers & Fades" msgstr "" -#: option_editor.cc:134 +#: option_editor.cc:135 msgid "MIDI" msgstr "MIDI" -#: option_editor.cc:176 +#: option_editor.cc:177 msgid "24 FPS" msgstr "" -#: option_editor.cc:178 +#: option_editor.cc:179 msgid "25 FPS" msgstr "" -#: option_editor.cc:180 +#: option_editor.cc:181 msgid "30 FPS" msgstr "" -#: option_editor.cc:186 +#: option_editor.cc:187 msgid "30 FPS drop" msgstr "" -#: option_editor.cc:243 +#: option_editor.cc:244 msgid "session RAID path" msgstr "путь к файлам RAID ÑеÑÑий" -#: option_editor.cc:248 +#: option_editor.cc:249 #, fuzzy msgid "Soundfile Search Paths" msgstr "Ðудио-библиотека" -#: option_editor.cc:253 +#: option_editor.cc:254 #, fuzzy msgid "Paths" msgstr "Пути/Файлы" -#: option_editor.cc:267 option_editor.cc:273 option_editor.cc:724 -#: option_editor.cc:751 +#: option_editor.cc:268 option_editor.cc:274 option_editor.cc:723 +#: option_editor.cc:750 msgid "internal" msgstr "внутренний" -#: option_editor.cc:286 +#: option_editor.cc:287 msgid "Short crossfade length (msecs)" msgstr "" -#: option_editor.cc:298 +#: option_editor.cc:299 msgid "Destructive crossfade length (msecs)" msgstr "" -#: option_editor.cc:366 +#: option_editor.cc:367 msgid "SMPTE Frames/second" msgstr "SMPTE Кадры/Секунды" -#: option_editor.cc:367 +#: option_editor.cc:368 msgid "SMPTE Offset" msgstr "Смещение SMPTE" -#: option_editor.cc:461 option_editor.cc:468 option_editor.cc:471 -#: option_editor.cc:617 +#: option_editor.cc:462 option_editor.cc:469 option_editor.cc:472 +#: option_editor.cc:618 #, fuzzy msgid "online" msgstr "линейное" @@ -5318,12 +5309,12 @@ msgstr "линейное" #. remember, we have to handle the i18n case where the relative #. lengths of the strings in language N is different than in english. #. -#: option_editor.cc:468 option_editor.cc:469 option_editor.cc:614 +#: option_editor.cc:469 option_editor.cc:470 option_editor.cc:615 #, fuzzy msgid "offline" msgstr "линейное" -#: option_editor.cc:669 +#: option_editor.cc:670 msgid "Choose Click" msgstr "" @@ -5332,15 +5323,15 @@ msgstr "" msgid "Choose Click Emphasis" msgstr "ИÑпользовать как акцентирующий щелчок метронома" -#: option_editor.cc:804 +#: option_editor.cc:803 msgid "Click audio file" msgstr "Файл щелчков метронома" -#: option_editor.cc:810 +#: option_editor.cc:809 msgid "Click emphasis audiofile" msgstr "Файл акцентирующих щелчков метронома" -#: option_editor.cc:847 +#: option_editor.cc:846 msgid "" "The auditioner is a dedicated mixer strip used\n" "for listening to specific regions outside the context\n" @@ -5352,35 +5343,35 @@ msgstr "" "вне общего контекÑта микÑа. Его можно Ñоединить как любой\n" "другой канал микшера." -#: option_editor.cc:920 +#: option_editor.cc:919 msgid "Edit using" msgstr "Редактировать Ñочетание" -#: option_editor.cc:927 option_editor.cc:954 +#: option_editor.cc:926 option_editor.cc:953 msgid "+ button" msgstr "+ клавиша" -#: option_editor.cc:947 +#: option_editor.cc:946 msgid "Delete using" msgstr "Удалить Ñочетание" -#: option_editor.cc:974 +#: option_editor.cc:973 msgid "Ignore snap using" msgstr "Ðе иÑпользовать \"Ñнимки\"" -#: opts.cc:47 +#: opts.cc:46 msgid "Usage: " msgstr "ИÑпользование: " -#: opts.cc:48 +#: opts.cc:47 msgid " -v, --version Show version information\n" msgstr " -v, --version Ð˜Ð½Ñ„Ð¾Ñ€Ð¼Ð°Ñ†Ð¸Ñ Ð¾ верÑии программы\n" -#: opts.cc:49 +#: opts.cc:48 msgid " -h, --help Print this message\n" msgstr " -h, --help Показать Ñто Ñообщение\n" -#: opts.cc:50 +#: opts.cc:49 msgid "" " -b, --bindings Print all possible keyboard binding " "names\n" @@ -5388,12 +5379,12 @@ msgstr "" " -b, --bindings Показать вÑе доÑтупные \"горÑчие\" " "клавиши\n" -#: opts.cc:51 +#: opts.cc:50 #, fuzzy msgid " -n, --show-splash Show splash screen\n" msgstr " -n, --no-splash Ðе показывать заÑтавку\n" -#: opts.cc:52 +#: opts.cc:51 #, fuzzy msgid "" " -c, --name name Use a specific jack client name, default " @@ -5402,7 +5393,7 @@ msgstr "" " -c, --jack-client-name Ð¸Ð¼Ñ Ð˜Ñпользовать другое Ð¸Ð¼Ñ jack-клиента, " "ardour по умолчанию\n" -#: opts.cc:53 +#: opts.cc:52 #, fuzzy msgid "" " -N, --new session-name Create a new session from the command " @@ -5410,197 +5401,212 @@ msgid "" msgstr "" " [имÑ-ÑеÑÑии] Загрузить ÑеÑÑию Ñ ÑƒÐºÐ°Ð·Ð°Ð½Ð½Ñ‹Ð¼ именем\n" -#: opts.cc:54 +#: opts.cc:53 msgid "" " -o, --use-hw-optimizations Try to use h/w specific optimizations\n" msgstr "" -#: opts.cc:56 +#: opts.cc:55 #, fuzzy msgid " -V, --novst Do not use VST support\n" msgstr " -n, --no-splash Ðе показывать заÑтавку\n" -#: opts.cc:58 +#: opts.cc:57 msgid " [session-name] Name of session to load\n" msgstr "" " [имÑ-ÑеÑÑии] Загрузить ÑеÑÑию Ñ ÑƒÐºÐ°Ð·Ð°Ð½Ð½Ñ‹Ð¼ именем\n" -#: opts.cc:59 +#: opts.cc:58 msgid " -C, --curvetest filename Curve algorithm debugger\n" msgstr "" -#: opts.cc:60 +#: opts.cc:59 #, fuzzy msgid " -g, --gtktheme Allow GTK to load a theme\n" msgstr " -h, --help Показать Ñто Ñообщение\n" -#: pan_automation_time_axis.cc:59 +#: pan_automation_time_axis.cc:60 msgid "You can't graphically edit panning of more than stream" msgstr "" -#: pan_automation_time_axis.cc:79 +#: pan_automation_time_axis.cc:80 #, fuzzy msgid "add pan automation event" msgstr "автомат" -#: panner2d.cc:588 panner_ui.cc:393 plugin_ui.cc:833 +#: panner2d.cc:589 panner_ui.cc:435 plugin_ui.cc:834 #, fuzzy msgid "Bypass" msgstr "обход" -#: panner_ui.cc:57 panner_ui.cc:187 +#: panner_ui.cc:58 panner_ui.cc:225 #, fuzzy msgid "link" msgstr "в" +#: panner_ui.cc:69 +#, fuzzy +msgid "Pan automation mode" +msgstr "автомат" + #: panner_ui.cc:70 +#, fuzzy +msgid "Pan automation type" +msgstr "автомат" + +#: panner_ui.cc:81 msgid "panning link control" msgstr "" -#: panner_ui.cc:72 +#: panner_ui.cc:83 msgid "panning link direction" msgstr "" -#: panner_ui.cc:197 +#: panner_ui.cc:235 msgid "L" msgstr "" -#: panner_ui.cc:296 +#: panner_ui.cc:335 +#, c-format +msgid "panner for channel %lu" +msgstr "" + +#: panner_ui.cc:337 #, c-format msgid "panner for channel %u" msgstr "" -#: panner_ui.cc:403 +#: panner_ui.cc:445 #, fuzzy msgid "Reset all" msgstr "ОгромнаÑ" -#: playlist_selector.cc:51 +#: playlist_selector.cc:52 #, fuzzy msgid "ardour: playlists" msgstr "ardour: модули (plugins)" -#: playlist_selector.cc:58 +#: playlist_selector.cc:59 msgid "Playlists grouped by track" msgstr "" -#: playlist_selector.cc:97 +#: playlist_selector.cc:98 #, fuzzy msgid "ardour: playlist for " msgstr "ardour: редактор: " -#: playlist_selector.cc:113 +#: playlist_selector.cc:114 #, fuzzy msgid "Other tracks" msgstr "Скрыть трек" -#: playlist_selector.cc:129 +#: playlist_selector.cc:130 msgid "unassigned" msgstr "" -#: plugin_selector.cc:42 +#: plugin_selector.cc:43 msgid "ardour: plugins" msgstr "ardour: модули (plugins)" -#: plugin_selector.cc:55 +#: plugin_selector.cc:56 #, fuzzy msgid "Available LADSPA Plugins" msgstr "ДоÑтупные LADSPA модули" -#: plugin_selector.cc:56 +#: plugin_selector.cc:57 msgid "Type" msgstr "Тип" -#: plugin_selector.cc:57 plugin_selector.cc:80 +#: plugin_selector.cc:58 plugin_selector.cc:81 msgid "# Inputs" msgstr "# Входов" -#: plugin_selector.cc:58 plugin_selector.cc:81 +#: plugin_selector.cc:59 plugin_selector.cc:82 msgid "# Outputs" msgstr "# Выходов" -#: plugin_selector.cc:67 +#: plugin_selector.cc:68 msgid "Plugins to be Connected to Insert" msgstr "" -#: plugin_selector.cc:79 +#: plugin_selector.cc:80 #, fuzzy msgid "Available plugins" msgstr "ДоÑтупные LADSPA модули" -#: plugin_selector.cc:97 +#: plugin_selector.cc:98 msgid "Add a plugin to the effect list" msgstr "Добавить модуль в ÑпиÑок Ñффектов" -#: plugin_selector.cc:99 +#: plugin_selector.cc:102 msgid "Remove a plugin from the effect list" msgstr "Удалить модуль из ÑпиÑка Ñффектов" -#: plugin_selector.cc:101 +#: plugin_selector.cc:104 msgid "Update available plugins" msgstr "Обновить доÑтупные модули" -#: plugin_selector.cc:123 +#: plugin_selector.cc:126 #, fuzzy msgid "LADSPA" msgstr "ADAT" -#: plugin_selector.cc:126 +#: plugin_selector.cc:129 #, fuzzy msgid "VST" msgstr "УСТÐÐОВИТЬ" -#: plugin_ui.cc:83 +#: plugin_ui.cc:84 msgid "" "unknown type of editor-supplying plugin (note: no VST support in this " "version of ardour)" msgstr "" -#: plugin_ui.cc:138 +#: plugin_ui.cc:139 msgid "Presets" msgstr "" -#: plugin_ui.cc:229 +#: plugin_ui.cc:230 #, fuzzy msgid "Controls" msgstr "Контрольные выходы" -#: plugin_ui.cc:266 +#: plugin_ui.cc:267 msgid "Plugin Editor: could not build control element for port %1" msgstr "Редактор модулей: невозможно Ñоздать Ñффект Ð´Ð»Ñ Ð¿Ð¾Ñ€Ñ‚Ð° %1" -#: plugin_ui.cc:357 +#: plugin_ui.cc:358 #, fuzzy -msgid "automation control" +msgid "Automation control" msgstr "автомат" -#: plugin_ui.cc:853 +#: plugin_ui.cc:854 msgid "Plugin preset %1 not found" msgstr "" -#: plugin_ui.cc:863 +#: plugin_ui.cc:864 #, fuzzy msgid "Name of New Preset:" msgstr "Ð˜Ð¼Ñ Ð½Ð¾Ð²Ð¾Ð³Ð¾ ÑоединениÑ:" -#: redirect_automation_line.cc:53 +#: redirect_automation_line.cc:54 msgid "redirect automation created for non-plugin" msgstr "" -#: redirect_automation_time_axis.cc:93 +#: redirect_automation_time_axis.cc:94 msgid "add automation event to " msgstr "" -#: redirect_box.cc:222 +#: redirect_box.cc:223 msgid "New send" msgstr "" -#: redirect_box.cc:223 +#: redirect_box.cc:224 #, fuzzy msgid "Show send controls" msgstr "иÑпользовать контрольные выходы" -#: redirect_box.cc:377 +#: redirect_box.cc:383 msgid "" "You attempted to add a plugin (%1).\n" "The plugin has %2 inputs\n" @@ -5611,7 +5617,7 @@ msgid "" "part of the signal." msgstr "" -#: redirect_box.cc:389 +#: redirect_box.cc:395 msgid "" "You attempted to add a plugin (%1).\n" "The plugin has %2 inputs\n" @@ -5623,7 +5629,7 @@ msgid "" "support this type of configuration." msgstr "" -#: redirect_box.cc:402 +#: redirect_box.cc:408 msgid "" "You attempted to add a plugin (%1).\n" "\n" @@ -5636,34 +5642,34 @@ msgid "" "Ardour does not understand what to do in such situations.\n" msgstr "" -#: redirect_box.cc:493 +#: redirect_box.cc:495 msgid "Pre-fader inserts, sends & plugins:" msgstr "" -#: redirect_box.cc:496 +#: redirect_box.cc:498 msgid "Post-fader inserts, sends & plugins:" msgstr "" -#: redirect_box.cc:642 +#: redirect_box.cc:644 msgid "" "You cannot reorder this set of redirects\n" "in that way because the inputs and\n" "outputs do not work correctly." msgstr "" -#: redirect_box.cc:747 +#: redirect_box.cc:749 #, fuzzy msgid "rename redirect" msgstr "ardour: переименовать облаÑть" -#: redirect_box.cc:824 redirect_box.cc:872 +#: redirect_box.cc:826 redirect_box.cc:874 msgid "" "Copying the set of redirects on the clipboard failed,\n" "probably because the I/O configuration of the plugins\n" "could not match the configuration of this track." msgstr "" -#: redirect_box.cc:894 +#: redirect_box.cc:896 #, fuzzy msgid "" "Do you really want to remove all redirects from this track?\n" @@ -5672,7 +5678,7 @@ msgstr "" "Ð’Ñ‹ дейÑтвительно хотите удалить трек \"%1\" ?\n" "(отмена невозможна)" -#: redirect_box.cc:897 +#: redirect_box.cc:899 #, fuzzy msgid "" "Do you really want to remove all redirects from this bus?\n" @@ -5681,246 +5687,258 @@ msgstr "" "Ð’Ñ‹ дейÑтвительно хотите удалить трек \"%1\" ?\n" "(отмена невозможна)" -#: redirect_box.cc:902 +#: redirect_box.cc:904 #, fuzzy msgid "Yes, remove them all" msgstr "Да, удалить." -#: redirect_box.cc:938 +#: redirect_box.cc:940 #, fuzzy msgid "ardour: %1" msgstr "ardour: " -#: redirect_box.cc:980 +#: redirect_box.cc:982 #, fuzzy msgid "ardour: %1: %2 (by %3)" msgstr "ardour: " #. new stuff -#: redirect_box.cc:1052 +#: redirect_box.cc:1054 msgid "New Plugin ..." msgstr "" -#: redirect_box.cc:1053 +#: redirect_box.cc:1055 #, fuzzy msgid "New Insert" msgstr "новый вход" -#: redirect_box.cc:1054 +#: redirect_box.cc:1056 msgid "New Send ..." msgstr "" -#: redirect_box.cc:1066 +#: redirect_box.cc:1068 #, fuzzy msgid "Deselect All" msgstr "Выделить вÑÑ‘" -#: redirect_box.cc:1073 +#: redirect_box.cc:1075 #, fuzzy msgid "Activate all" msgstr "Ðктивировать" -#: redirect_box.cc:1074 +#: redirect_box.cc:1076 #, fuzzy msgid "Deactivate all" msgstr "Деактивировать" -#: region_editor.cc:44 +#: region_editor.cc:45 msgid "NAME:" msgstr "ИМЯ:" -#: region_editor.cc:45 +#: region_editor.cc:46 msgid "lock" msgstr "фикÑ." -#: region_editor.cc:47 +#: region_editor.cc:48 msgid "opaque" msgstr "затенить" -#: region_editor.cc:52 +#: region_editor.cc:49 region_editor.cc:192 region_editor.cc:226 +msgid "active" +msgstr "активно" + +#: region_editor.cc:50 +msgid "visible" +msgstr "отображать" + +#: region_editor.cc:53 msgid "Layer" msgstr "Слой" -#: region_editor.cc:60 +#: region_editor.cc:54 +msgid "play" +msgstr "воÑпроизвеÑти" + +#: region_editor.cc:61 msgid "ENVELOPE" msgstr "ОГИБÐЮЩÐЯ" -#: region_editor.cc:106 +#: region_editor.cc:107 msgid "mute this region" msgstr "отключить воÑпроизведение Ñтой облаÑти" -#: region_editor.cc:107 +#: region_editor.cc:108 msgid "regions underneath this one cannot be heard" msgstr "облаÑти ниже Ñтой не могут быть проÑлушаны" -#: region_editor.cc:108 +#: region_editor.cc:109 msgid "prevent any changes to this region" msgstr "запретить любые Ð¸Ð·Ð¼ÐµÐ½ÐµÐ½Ð¸Ñ Ñтой облаÑти" -#: region_editor.cc:109 +#: region_editor.cc:110 msgid "use the gain envelope during playback" msgstr "иÑпользовать огибающую при воÑпроизведении" -#: region_editor.cc:110 +#: region_editor.cc:111 msgid "show the gain envelope" msgstr "отображать огибающую" -#: region_editor.cc:111 +#: region_editor.cc:112 msgid "use fade in curve during playback" msgstr "иÑпользовать вводную кривую при воÑпроизведении" -#: region_editor.cc:112 +#: region_editor.cc:113 msgid "use fade out curve during playback" msgstr "иÑпользовать выводную кривую при воÑпроизведении" -#: region_editor.cc:113 +#: region_editor.cc:114 msgid "audition this region" msgstr "проÑлушать облаÑть" -#: region_editor.cc:146 +#: region_editor.cc:147 msgid "START:" msgstr "ÐÐЧÐЛО:" -#: region_editor.cc:148 +#: region_editor.cc:149 msgid "END:" msgstr "КОÐЕЦ:" -#: region_editor.cc:150 +#: region_editor.cc:151 msgid "LENGTH:" msgstr "ДЛИÐÐ:" -#: region_editor.cc:190 +#: region_editor.cc:191 msgid "FADE IN" msgstr "ВВЕДЕÐИЕ Ð’ УРОВЕÐЬ" -#: region_editor.cc:192 region_editor.cc:226 +#: region_editor.cc:193 region_editor.cc:227 msgid "msecs" msgstr "мÑек" -#: region_editor.cc:224 +#: region_editor.cc:225 msgid "FADE OUT" msgstr "СВЕДЕÐИЕ Ð’ ÐОЛЬ" -#: region_editor.cc:264 +#: region_editor.cc:265 msgid "ardour: region " msgstr "ardour: облаÑть " -#: region_editor.cc:401 +#: region_editor.cc:402 msgid "fade in edit" msgstr "редактировать введение в уровень" -#: region_editor.cc:413 +#: region_editor.cc:414 msgid "fade out edit" msgstr "редактировать Ñведение в ноль" -#: regionview.cc:1140 +#: regionview.cc:1146 #, fuzzy msgid "add gain control point" msgstr "иÑпользовать контрольные выходы" -#: route_params_ui.cc:88 +#: route_params_ui.cc:89 msgid "Tracks/Buses" msgstr "Треки/Шины" -#: route_params_ui.cc:108 +#: route_params_ui.cc:109 #, fuzzy msgid "Pre-fader Redirects" msgstr "Предобработка" -#: route_params_ui.cc:109 +#: route_params_ui.cc:110 #, fuzzy msgid "Post-fader Redirects" msgstr "ПоÑтобработка" -#: route_params_ui.cc:141 +#: route_params_ui.cc:144 #, fuzzy msgid "ardour: track/bus inspector" msgstr "ardour: добавить трек/шину" -#: route_params_ui.cc:142 +#: route_params_ui.cc:145 msgid "ardour_route_parameters" msgstr "ardour_параметры_маршрутов" -#: route_params_ui.cc:199 +#: route_params_ui.cc:202 msgid "route display list item for renamed route not found!" msgstr "" -#: route_params_ui.cc:451 +#: route_params_ui.cc:453 msgid "NO TRACK" msgstr "ÐЕТ ТРЕКОВ" -#: route_params_ui.cc:693 +#: route_params_ui.cc:695 #, fuzzy msgid "ardour: track/bus inspector: " msgstr "ardour: добавить трек/шину" -#: route_params_ui.cc:697 +#: route_params_ui.cc:699 msgid "No Route Selected" msgstr "Ðет выбранных маршрутов" -#: route_params_ui.cc:698 +#: route_params_ui.cc:700 #, fuzzy msgid "ardour: track/bus/inspector: no route selected" msgstr "ardour: параметры маршрутов: нет выбранных маршрутов" #. ctrl-shift-click applies change to all routes -#: route_ui.cc:133 +#: route_ui.cc:134 msgid "mute change" msgstr "" #. ctrl-shift-click applies change to all routes #. ctrl-alt-click: exclusively solo this track, not a toggle */ -#: route_ui.cc:208 route_ui.cc:218 +#: route_ui.cc:209 route_ui.cc:219 msgid "solo change" msgstr "" -#: route_ui.cc:281 +#: route_ui.cc:282 msgid "rec-enable change" msgstr "" -#: route_ui.cc:472 +#: route_ui.cc:479 #, fuzzy msgid "Solo-safe" msgstr "Соло" -#: route_ui.cc:480 route_ui.cc:523 +#: route_ui.cc:487 route_ui.cc:530 #, fuzzy msgid "MIDI Bind" msgstr "MIDI" -#: route_ui.cc:494 +#: route_ui.cc:501 msgid "Pre Fader" msgstr "Пред фейдер" -#: route_ui.cc:501 +#: route_ui.cc:508 msgid "Post Fader" msgstr "ПоÑÑ‚ фейдер" -#: route_ui.cc:508 +#: route_ui.cc:515 msgid "Control Outs" msgstr "Контрольные выходы" -#: route_ui.cc:515 +#: route_ui.cc:522 msgid "Main Outs" msgstr "Главные выходы" -#: route_ui.cc:552 +#: route_ui.cc:559 msgid "mix group solo change" msgstr "" -#: route_ui.cc:586 +#: route_ui.cc:593 msgid "mix group mute change" msgstr "" -#: route_ui.cc:602 +#: route_ui.cc:609 msgid "mix group rec-enable change" msgstr "" -#: route_ui.cc:619 visual_time_axis.cc:236 +#: route_ui.cc:626 visual_time_axis.cc:237 msgid "ardour: color selection" msgstr "ardour: выбор цвета" -#: route_ui.cc:695 +#: route_ui.cc:702 #, fuzzy msgid "" "Do you really want to remove track \"%1\" ?\n" @@ -5931,7 +5949,7 @@ msgstr "" "Ð’Ñ‹ дейÑтвительно хотите удалить трек \"%1\" ?\n" "(отмена невозможна)" -#: route_ui.cc:697 +#: route_ui.cc:704 msgid "" "Do you really want to remove bus \"%1\" ?\n" "(cannot be undone)" @@ -5939,11 +5957,11 @@ msgstr "" "Ð’Ñ‹ дейÑтвительно хотите удалить шину \"%1\" ?\n" "(отмена невозможна)" -#: route_ui.cc:701 visual_time_axis.cc:278 +#: route_ui.cc:708 visual_time_axis.cc:279 msgid "Yes, remove it." msgstr "Да, удалить." -#: route_ui.cc:730 +#: route_ui.cc:737 #, fuzzy msgid "New Name: " msgstr "новое имÑ: " @@ -6002,148 +6020,149 @@ msgstr "Файл недоÑтупен: " msgid "Name for Field" msgstr "Ð˜Ð¼Ñ Ð¾Ð±Ð»Ð°Ñти: " -#: sfdb_ui.cc:333 +#: sfdb_ui.cc:335 msgid "Split Channels" msgstr "" -#: sfdb_ui.cc:340 +#: sfdb_ui.cc:342 msgid "Create a region for each channel" msgstr "" -#: sfdb_ui.cc:342 +#: sfdb_ui.cc:344 msgid "Embed" msgstr "" -#: sfdb_ui.cc:344 +#: sfdb_ui.cc:346 #, fuzzy msgid "Link to an external file" msgstr "Ð’Ñтавить внешний аудиофайл" -#: sfdb_ui.cc:346 +#: sfdb_ui.cc:348 msgid "Import" msgstr "Импорт" -#: sfdb_ui.cc:348 +#: sfdb_ui.cc:350 msgid "Copy a file to the session folder" msgstr "" -#: sfdb_ui.cc:412 +#: sfdb_ui.cc:414 #, fuzzy msgid "programming error: %1" msgstr "ошибка в программе: " -#: tempo_dialog.cc:17 tempo_dialog.cc:34 +#: tempo_dialog.cc:18 tempo_dialog.cc:35 msgid "Beats per minute" msgstr "Ударов в минуту" -#: tempo_dialog.cc:20 tempo_dialog.cc:37 tempo_dialog.cc:153 -#: tempo_dialog.cc:171 +#: tempo_dialog.cc:21 tempo_dialog.cc:38 tempo_dialog.cc:203 +#: tempo_dialog.cc:221 msgid "Bar" msgstr "Такт" -#: tempo_dialog.cc:21 tempo_dialog.cc:38 tempo_dialog.cc:154 -#: tempo_dialog.cc:172 +#: tempo_dialog.cc:22 tempo_dialog.cc:39 tempo_dialog.cc:204 +#: tempo_dialog.cc:222 msgid "Beat" msgstr "ДолÑ" -#: tempo_dialog.cc:23 tempo_dialog.cc:40 tempo_dialog.cc:155 -#: tempo_dialog.cc:173 +#: tempo_dialog.cc:24 tempo_dialog.cc:41 tempo_dialog.cc:205 +#: tempo_dialog.cc:223 msgid "Location" msgstr "РаÑположение" -#: tempo_dialog.cc:149 tempo_dialog.cc:167 +#: tempo_dialog.cc:199 tempo_dialog.cc:217 msgid "Meter denominator" msgstr "Знаменатель размера" -#: tempo_dialog.cc:150 tempo_dialog.cc:168 +#: tempo_dialog.cc:200 tempo_dialog.cc:218 msgid "Beats per bar" msgstr "Долей на такт" -#: tempo_dialog.cc:186 tempo_dialog.cc:197 +#: tempo_dialog.cc:236 tempo_dialog.cc:247 msgid "whole (1)" msgstr "целых (1)" -#: tempo_dialog.cc:187 tempo_dialog.cc:199 +#: tempo_dialog.cc:237 tempo_dialog.cc:249 msgid "second (2)" msgstr "половины (2)" -#: tempo_dialog.cc:188 tempo_dialog.cc:201 +#: tempo_dialog.cc:238 tempo_dialog.cc:251 msgid "third (3)" msgstr "трети (3)" -#: tempo_dialog.cc:189 tempo_dialog.cc:203 tempo_dialog.cc:211 +#: tempo_dialog.cc:239 tempo_dialog.cc:253 tempo_dialog.cc:261 msgid "quarter (4)" msgstr "четверти (4)" -#: tempo_dialog.cc:190 tempo_dialog.cc:205 +#: tempo_dialog.cc:240 tempo_dialog.cc:255 msgid "eighth (8)" msgstr "воÑьмых (8)" -#: tempo_dialog.cc:191 tempo_dialog.cc:207 +#: tempo_dialog.cc:241 tempo_dialog.cc:257 msgid "sixteenth (16)" msgstr "шеÑтьнадцатых (16)" -#: tempo_dialog.cc:192 tempo_dialog.cc:209 +#: tempo_dialog.cc:242 tempo_dialog.cc:259 msgid "thirty-second (32)" msgstr "тридцать-вторых (32)" -#: tempo_dialog.cc:321 +#: tempo_dialog.cc:420 msgid "garbaged note type entry (%1)" msgstr "неÑÑное определение ноты (%1)" -#: tempo_dialog.cc:331 +#: tempo_dialog.cc:430 msgid "incomprehensible note type entry (%1)" msgstr "некорректное определение ноты (%1)" -#: time_axis_view.cc:111 +#: time_axis_view.cc:112 msgid "gTortnam" msgstr "" -#: time_axis_view.cc:548 +#: time_axis_view.cc:549 msgid "Largest" msgstr "ОгромнаÑ" -#: time_axis_view.cc:549 +#: time_axis_view.cc:550 msgid "Large" msgstr "БольшаÑ" -#: time_axis_view.cc:550 +#: time_axis_view.cc:551 msgid "Larger" msgstr "Больше" -#: time_axis_view.cc:552 +#: time_axis_view.cc:553 msgid "Smaller" msgstr "Меньше" -#: time_axis_view.cc:553 +#: time_axis_view.cc:554 msgid "Small" msgstr "МаленькаÑ" -#: time_axis_view.cc:869 +#: time_axis_view.cc:870 msgid "unknown track height name \"%1\" in XML GUI information" msgstr "неизвеÑтное Ð¸Ð¼Ñ ÑˆÐ¸Ñ€Ð¸Ð½Ñ‹ трека \"%1\" в XML опиÑании" -#: time_axis_view_item.cc:71 +#. first constructed item sets up font info +#: time_axis_view_item.cc:79 msgid "TimeAxisViewItemName" msgstr "" -#: time_axis_view_item.cc:271 +#: time_axis_view_item.cc:298 msgid "new duration %1 frames is out of bounds for %2" msgstr "" -#: time_selection.cc:40 +#: time_selection.cc:41 msgid "programming error: request for non-existent audio range (%1)!" msgstr "ошибка в программе: request for non-existent audio range (%1)!" -#: utils.cc:106 utils.cc:149 +#: utils.cc:107 utils.cc:150 msgid "bad XPM header %1" msgstr "ошибка в XPM заголовке %1" -#: utils.cc:331 +#: utils.cc:332 msgid "missing RGBA style for \"%1\"" msgstr "" -#: visual_time_axis.cc:275 +#: visual_time_axis.cc:276 msgid "" "Do you really want to remove track \"%1\" ?\n" "(cannot be undone)" @@ -6151,14 +6170,89 @@ msgstr "" "Ð’Ñ‹ дейÑтвительно хотите удалить трек \"%1\" ?\n" "(отмена невозможна)" -#: visual_time_axis.cc:324 +#: visual_time_axis.cc:325 msgid "new name: " msgstr "новое имÑ: " -#: visual_time_axis.cc:335 +#: visual_time_axis.cc:336 msgid "A track already exists with that name" msgstr "Трек Ñ Ñ‚Ð°ÐºÐ¸Ð¼ именем уже ÑущеÑтвует" +#, fuzzy +#~ msgid "set selected trackview" +#~ msgstr "Ð’Ñтавить выбранное" + +#, fuzzy +#~ msgid "set selected control point" +#~ msgstr "иÑпользовать контрольные выходы" + +#, fuzzy +#~ msgid "set selected regionview" +#~ msgstr "ВоÑпроизвеÑти выделенную облаÑть" + +#~ msgid "Start a new session\n" +#~ msgstr "Ðачать новую ÑеÑÑию\n" + +#~ msgid "via Session menu" +#~ msgstr "в меню \"СеÑÑиÑ\"" + +#, fuzzy +#~ msgid "Advanced" +#~ msgstr "Дополнительно..." + +#, fuzzy +#~ msgid "Select a File" +#~ msgstr "Выделить вÑÑ‘" + +#, fuzzy +#~ msgid "Track/Bus connection options" +#~ msgstr "Треки/Шины" + +#~ msgid "RECORD" +#~ msgstr "ЗÐПИСЬ" + +#~ msgid "INPUT" +#~ msgstr "ВХОД" + +#~ msgid "OUTPUT" +#~ msgstr "ВЫХОД" + +#, fuzzy +#~ msgid "Gain automation mode" +#~ msgstr "автомат" + +#, fuzzy +#~ msgid "Gain automation type" +#~ msgstr "автомат" + +#, fuzzy +#~ msgid "gain automation mode" +#~ msgstr "автомат" + +#, fuzzy +#~ msgid "gain automation state" +#~ msgstr "автомат" + +#, fuzzy +#~ msgid "pan automation state" +#~ msgstr "автомат" + +#~ msgid "REC" +#~ msgstr "ЗÐП" + +#~ msgid "OUT" +#~ msgstr "ВЫХ" + +#~ msgid "aplay" +#~ msgstr "авоÑпр" + +#, fuzzy +#~ msgid "awrite" +#~ msgstr "запиÑÑŒ" + +#~ msgid "no group" +#~ msgstr "нет группы" + #, fuzzy #~ msgid "normal" #~ msgstr "Ðорм." @@ -6438,9 +6532,6 @@ msgstr "Трек Ñ Ñ‚Ð°ÐºÐ¸Ð¼ именем уже ÑущеÑтвует" #~ msgid "AND" #~ msgstr "И" -#~ msgid "OR" -#~ msgstr "ИЛИ" - #~ msgid "ardour: locate soundfiles" #~ msgstr "ardour: раÑположение звуковых файлов" @@ -6461,9 +6552,6 @@ msgstr "Трек Ñ Ñ‚Ð°ÐºÐ¸Ð¼ именем уже ÑущеÑтвует" #~ msgid "***" #~ msgstr "***" -#~ msgid "Mix Groups" -#~ msgstr "Mix группы" - #~ msgid "Hide All AudioTrack MixerStrips" #~ msgstr "Скрыть вÑе каналы аудиотреков" @@ -6476,9 +6564,6 @@ msgstr "Трек Ñ Ñ‚Ð°ÐºÐ¸Ð¼ именем уже ÑущеÑтвует" #~ msgid "Name for new mix group" #~ msgstr "Ð˜Ð¼Ñ Ð½Ð¾Ð²Ð¾Ð¹ mix группы" -#~ msgid "Session name:" -#~ msgstr "Ð˜Ð¼Ñ ÑеÑÑии:" - #~ msgid "Create" #~ msgstr "Создать" @@ -6510,17 +6595,9 @@ msgstr "Трек Ñ Ñ‚Ð°ÐºÐ¸Ð¼ именем уже ÑущеÑтвует" #~ "ЕÑли вы хотите иÑпользовать другую чаÑтоту диÑкретизации,\n" #~ "вам необходимо закрыть Ardour и перезапуÑтить JACK" -#, fuzzy -#~ msgid "Session template" -#~ msgstr "иÑпользовать имеющийÑÑ ÑˆÐ°Ð±Ð»Ð¾Ð½" - #~ msgid "blank" #~ msgstr "пуÑтой" -#, fuzzy -#~ msgid "No template" -#~ msgstr "-шаблон" - #, fuzzy #~ msgid "Slave to MTC" #~ msgstr "Передача MTC" @@ -6546,9 +6623,6 @@ msgstr "Трек Ñ Ñ‚Ð°ÐºÐ¸Ð¼ именем уже ÑущеÑтвует" #~ msgid "Native Format" #~ msgstr "Внутренний формат" -#~ msgid "Use as click" -#~ msgstr "ИÑпользовать как щелчок метронома" - #~ msgid "--unknown--" #~ msgstr "--неизвеÑтный--" diff --git a/gtk2_ardour/redirect_automation_line.cc b/gtk2_ardour/redirect_automation_line.cc index 57b1c07967..8971e8ff10 100644 --- a/gtk2_ardour/redirect_automation_line.cc +++ b/gtk2_ardour/redirect_automation_line.cc @@ -32,6 +32,7 @@ using namespace std; using namespace ARDOUR; +using namespace PBD; RedirectAutomationLine::RedirectAutomationLine (const string & name, Redirect& rd, uint32_t port, Session& s, diff --git a/gtk2_ardour/redirect_automation_line.h b/gtk2_ardour/redirect_automation_line.h index 3933359db0..ad39f6625c 100644 --- a/gtk2_ardour/redirect_automation_line.h +++ b/gtk2_ardour/redirect_automation_line.h @@ -53,8 +53,6 @@ class RedirectAutomationLine : public AutomationLine void view_to_model_y (double&); void model_to_view_y (double&); - void change_model (uint32_t, double x, double y); - void change_model_range (uint32_t, uint32_t, double delta); }; #endif /* __ardour_gtk_region_gain_line_h__ */ diff --git a/gtk2_ardour/redirect_automation_time_axis.cc b/gtk2_ardour/redirect_automation_time_axis.cc index 798d132a4a..e1b71310ac 100644 --- a/gtk2_ardour/redirect_automation_time_axis.cc +++ b/gtk2_ardour/redirect_automation_time_axis.cc @@ -29,6 +29,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace Gtk; RedirectAutomationTimeAxisView::RedirectAutomationTimeAxisView (Session& s, Route& r, PublicEditor& e, TimeAxisView& parent, Canvas& canvas, std::string n, diff --git a/gtk2_ardour/redirect_box.cc b/gtk2_ardour/redirect_box.cc index f186fab2d5..f5cb9522e0 100644 --- a/gtk2_ardour/redirect_box.cc +++ b/gtk2_ardour/redirect_box.cc @@ -38,7 +38,7 @@ #include #include #include -#include +#include #include #include #include @@ -65,6 +65,7 @@ using namespace sigc; using namespace ARDOUR; +using namespace PBD; using namespace Gtk; using namespace Glib; using namespace Gtkmm2ext; diff --git a/gtk2_ardour/region_editor.cc b/gtk2_ardour/region_editor.cc index 73aa3465d9..413ff01753 100644 --- a/gtk2_ardour/region_editor.cc +++ b/gtk2_ardour/region_editor.cc @@ -33,6 +33,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace sigc; using namespace std; diff --git a/gtk2_ardour/region_gain_line.cc b/gtk2_ardour/region_gain_line.cc index 059289acd4..bba9410ffb 100644 --- a/gtk2_ardour/region_gain_line.cc +++ b/gtk2_ardour/region_gain_line.cc @@ -16,6 +16,7 @@ using namespace std; using namespace ARDOUR; +using namespace PBD; AudioRegionGainLine::AudioRegionGainLine (const string & name, Session& s, AudioRegionView& r, ArdourCanvas::Group& parent, Curve& c) : AutomationLine (name, r.get_time_axis_view(), parent, c), diff --git a/gtk2_ardour/region_selection.cc b/gtk2_ardour/region_selection.cc index b3ceb8516f..751584cab7 100644 --- a/gtk2_ardour/region_selection.cc +++ b/gtk2_ardour/region_selection.cc @@ -6,6 +6,7 @@ #include "region_selection.h" using namespace ARDOUR; +using namespace PBD; using namespace sigc; diff --git a/gtk2_ardour/regionview.cc b/gtk2_ardour/regionview.cc index dbca103239..114aaf5da3 100644 --- a/gtk2_ardour/regionview.cc +++ b/gtk2_ardour/regionview.cc @@ -27,7 +27,8 @@ #include #include -#include +#include +#include #include "streamview.h" #include "regionview.h" @@ -48,6 +49,7 @@ using namespace sigc; using namespace ARDOUR; +using namespace PBD; using namespace Editing; using namespace ArdourCanvas; @@ -1233,12 +1235,6 @@ AudioRegionView::set_waveform_shape (WaveformShape shape) } } -std::string -AudioRegionView::get_item_name () -{ - return region.name(); -} - void AudioRegionView::move (double x_delta, double y_delta) { diff --git a/gtk2_ardour/regionview.h b/gtk2_ardour/regionview.h index cb71a8f3a7..f49b46aea4 100644 --- a/gtk2_ardour/regionview.h +++ b/gtk2_ardour/regionview.h @@ -63,7 +63,6 @@ class AudioRegionView : public TimeAxisViewItem bool is_valid() const { return valid; } void set_valid (bool yn) { valid = yn; } - std::string get_item_name(); void set_height (double); void set_samples_per_unit (double); bool set_duration (jack_nframes_t, void*); diff --git a/gtk2_ardour/route_params_ui.cc b/gtk2_ardour/route_params_ui.cc index aee247df02..d6ec7eab6c 100644 --- a/gtk2_ardour/route_params_ui.cc +++ b/gtk2_ardour/route_params_ui.cc @@ -26,7 +26,7 @@ #include #include -#include +#include #include #include #include @@ -52,6 +52,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace Gtk; using namespace sigc; diff --git a/gtk2_ardour/route_redirect_selection.cc b/gtk2_ardour/route_redirect_selection.cc index cefe7985cb..6d315e0aae 100644 --- a/gtk2_ardour/route_redirect_selection.cc +++ b/gtk2_ardour/route_redirect_selection.cc @@ -31,6 +31,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace sigc; RouteRedirectSelection& diff --git a/gtk2_ardour/route_ui.cc b/gtk2_ardour/route_ui.cc index 05f3683175..4559058b8d 100644 --- a/gtk2_ardour/route_ui.cc +++ b/gtk2_ardour/route_ui.cc @@ -34,13 +34,14 @@ #include #include -#include +#include #include "i18n.h" using namespace sigc; using namespace Gtk; using namespace Gtkmm2ext; using namespace ARDOUR; +using namespace PBD; RouteUI::RouteUI (ARDOUR::Route& rt, ARDOUR::Session& sess, const char* m_name, @@ -433,7 +434,13 @@ RouteUI::refresh_remote_control_menu () limit += 4; /* leave some breathing room */ - for (uint32_t i = 0; i < limit; ++i) { + rc_items.push_back (RadioMenuElem (rc_group, _("None"))); + if (_route.remote_control_id() == 0) { + rc_active = dynamic_cast (&rc_items.back()); + rc_active->set_active (); + } + + for (uint32_t i = 1; i < limit; ++i) { snprintf (buf, sizeof (buf), "%u", i); rc_items.push_back (RadioMenuElem (rc_group, buf)); rc_active = dynamic_cast(&rc_items.back()); @@ -872,7 +879,7 @@ RouteUI::is_audio_track () const return dynamic_cast(&_route) != 0; } -DiskStream* +AudioDiskstream* RouteUI::get_diskstream () const { AudioTrack *at; diff --git a/gtk2_ardour/route_ui.h b/gtk2_ardour/route_ui.h index b7a5b059f0..69c9b7f5a9 100644 --- a/gtk2_ardour/route_ui.h +++ b/gtk2_ardour/route_ui.h @@ -50,7 +50,7 @@ class RouteUI : public virtual AxisView virtual ~RouteUI(); bool is_audio_track() const; - ARDOUR::DiskStream* get_diskstream() const; + ARDOUR::AudioDiskstream* get_diskstream() const; ARDOUR::Route& route() const { return _route; } ARDOUR::AudioTrack* audio_track() const; @@ -116,7 +116,7 @@ class RouteUI : public virtual AxisView sigc::connection blink_connection; - void rec_enable_button_blink (bool onoff, ARDOUR::DiskStream *, Gtk::Widget *w); + void rec_enable_button_blink (bool onoff, ARDOUR::AudioDiskstream *, Gtk::Widget *w); void remove_this_route (); static gint idle_remove_this_route (RouteUI *); diff --git a/gtk2_ardour/selectable.h b/gtk2_ardour/selectable.h index fdd6f7ff9f..b4be7090e2 100644 --- a/gtk2_ardour/selectable.h +++ b/gtk2_ardour/selectable.h @@ -21,7 +21,9 @@ #ifndef __ardour_gtk_selectable_h__ #define __ardour_gtk_selectable_h__ -class Selectable +#include + +class Selectable : public virtual sigc::trackable { public: Selectable() { @@ -30,10 +32,20 @@ class Selectable virtual ~Selectable() {} - virtual void set_selected (bool) { - _selected = true; + virtual void set_selected (bool yn) { + if (yn != _selected) { + _selected = true; + Selected (_selected); /* EMIT_SIGNAL */ + } } + bool get_selected() const { + return _selected; + } + + /** Emitted when the selected status of this Selectable changes */ + sigc::signal Selected ; + protected: bool _selected; }; diff --git a/gtk2_ardour/selection.cc b/gtk2_ardour/selection.cc index 3c1aea1ec8..2e4ed8a117 100644 --- a/gtk2_ardour/selection.cc +++ b/gtk2_ardour/selection.cc @@ -33,6 +33,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace sigc; struct AudioRangeComparator { diff --git a/gtk2_ardour/send_ui.cc b/gtk2_ardour/send_ui.cc index 8ce3838176..be95f753e7 100644 --- a/gtk2_ardour/send_ui.cc +++ b/gtk2_ardour/send_ui.cc @@ -28,6 +28,7 @@ #include "gui_thread.h" using namespace ARDOUR; +using namespace PBD; SendUI::SendUI (Send& s, Session& se) : _send (s), diff --git a/gtk2_ardour/sfdb_ui.cc b/gtk2_ardour/sfdb_ui.cc index 947f470ac8..79546880de 100644 --- a/gtk2_ardour/sfdb_ui.cc +++ b/gtk2_ardour/sfdb_ui.cc @@ -31,7 +31,7 @@ #include #include -#include +#include #include "ardour_ui.h" #include "gui_thread.h" @@ -42,6 +42,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace std; SoundFileBox::SoundFileBox () @@ -122,7 +123,7 @@ SoundFileBox::setup_labels (string filename) path = filename; string error_msg; - if(!ExternalSource::get_soundfile_info (filename, sf_info, error_msg)) { + if(!AudioFileSource::get_soundfile_info (filename, sf_info, error_msg)) { return false; } @@ -187,12 +188,12 @@ SoundFileBox::play_btn_clicked () if (region_cache.find (path) == region_cache.end()) { AudioRegion::SourceList srclist; - ExternalSource* sfs; + AudioFileSource* afs; for (int n = 0; n < sf_info.channels; ++n) { try { - sfs = ExternalSource::create (path+":"+string_compose("%1", n), false); - srclist.push_back(sfs); + afs = AudioFileSource::create (path+":"+string_compose("%1", n)); + srclist.push_back(afs); } catch (failed_constructor& err) { error << _("Could not access soundfile: ") << path << endmsg; diff --git a/gtk2_ardour/sfdb_ui.h b/gtk2_ardour/sfdb_ui.h index 769e4ff02d..79c73b97ac 100644 --- a/gtk2_ardour/sfdb_ui.h +++ b/gtk2_ardour/sfdb_ui.h @@ -40,7 +40,7 @@ #include #include -#include +#include #include "ardour_dialog.h" #include "editing.h" @@ -69,7 +69,7 @@ class SoundFileBox : public Gtk::VBox LabelModelColumns label_columns; - ARDOUR::SoundFileInfo sf_info; + ARDOUR::SoundFileInfo sf_info; pid_t current_pid; diff --git a/gtk2_ardour/streamview.cc b/gtk2_ardour/streamview.cc index bceaf09f99..a60e0d59e7 100644 --- a/gtk2_ardour/streamview.cc +++ b/gtk2_ardour/streamview.cc @@ -6,7 +6,8 @@ #include #include -#include +#include +#include #include #include #include @@ -28,6 +29,7 @@ #include "color.h" using namespace ARDOUR; +using namespace PBD; using namespace Editing; StreamView::StreamView (AudioTimeAxisView& tv) @@ -311,7 +313,7 @@ StreamView::undisplay_diskstream () } void -StreamView::display_diskstream (DiskStream *ds) +StreamView::display_diskstream (AudioDiskstream *ds) { playlist_change_connection.disconnect(); playlist_changed (ds); @@ -337,7 +339,7 @@ StreamView::playlist_modified () } void -StreamView::playlist_changed (DiskStream *ds) +StreamView::playlist_changed (AudioDiskstream *ds) { ENSURE_GUI_THREAD (bind (mem_fun (*this, &StreamView::playlist_changed), ds)); @@ -491,7 +493,7 @@ StreamView::diskstream_changed (void *src_ignored) AudioTrack *at; if ((at = _trackview.audio_track()) != 0) { - DiskStream& ds = at->disk_stream(); + AudioDiskstream& ds = at->disk_stream(); /* XXX grrr: when will SigC++ allow me to bind references? */ Gtkmm2ext::UI::instance()->call_slot (bind (mem_fun (*this, &StreamView::display_diskstream), &ds)); } else { @@ -547,7 +549,7 @@ StreamView::set_selected_regionviews (AudioRegionSelection& regions) } // cerr << "\tregion " << (*i)->region.name() << " selected = " << selected << endl; - (*i)->set_selected (selected, this); + (*i)->set_selected (selected); } } @@ -634,7 +636,7 @@ StreamView::setup_rec_box () peak_ready_connections.clear(); for (uint32_t n=0; n < _trackview.get_diskstream()->n_channels(); ++n) { - Source *src = (Source *) _trackview.get_diskstream()->write_source (n); + AudioSource *src = (AudioSource *) _trackview.get_diskstream()->write_source (n); if (src) { sources.push_back (src); peak_ready_connections.push_back (src->PeakRangeReady.connect (bind (mem_fun (*this, &StreamView::rec_peak_range_ready), src))); @@ -662,7 +664,7 @@ StreamView::setup_rec_box () AudioTrack* at; at = _trackview.audio_track(); /* we know what it is already */ - DiskStream& ds = at->disk_stream(); + AudioDiskstream& ds = at->disk_stream(); jack_nframes_t frame_pos = ds.current_capture_start (); gdouble xstart = _trackview.editor.frame_to_pixel (frame_pos); gdouble xend; diff --git a/gtk2_ardour/streamview.h b/gtk2_ardour/streamview.h index eb17083de1..00ec2d93f2 100644 --- a/gtk2_ardour/streamview.h +++ b/gtk2_ardour/streamview.h @@ -37,7 +37,7 @@ namespace Gdk { namespace ARDOUR { class Route; - class DiskStream; + class AudioDiskstream; class Crossfade; class PeakData; class AudioRegion; @@ -151,12 +151,12 @@ class StreamView : public sigc::trackable void remove_audio_region_view (ARDOUR::AudioRegion* ); void remove_audio_rec_region (ARDOUR::AudioRegion*); - void display_diskstream (ARDOUR::DiskStream* ); + void display_diskstream (ARDOUR::AudioDiskstream* ); void undisplay_diskstream (); void redisplay_diskstream (); void diskstream_changed (void* ); void playlist_state_changed (ARDOUR::Change); - void playlist_changed (ARDOUR::DiskStream* ); + void playlist_changed (ARDOUR::AudioDiskstream* ); void playlist_modified (); bool crossfades_visible; diff --git a/gtk2_ardour/taperegionview.cc b/gtk2_ardour/taperegionview.cc index 19276223ef..641d067350 100644 --- a/gtk2_ardour/taperegionview.cc +++ b/gtk2_ardour/taperegionview.cc @@ -27,7 +27,8 @@ #include #include -#include +#include +#include #include "taperegionview.h" #include "audio_time_axis.h" @@ -37,6 +38,7 @@ using namespace sigc; using namespace ARDOUR; +using namespace PBD; using namespace Editing; using namespace ArdourCanvas; diff --git a/gtk2_ardour/tempo_dialog.cc b/gtk2_ardour/tempo_dialog.cc index 9f5fbda13f..7eb0362580 100644 --- a/gtk2_ardour/tempo_dialog.cc +++ b/gtk2_ardour/tempo_dialog.cc @@ -11,6 +11,7 @@ using namespace Gtk; using namespace Gtkmm2ext; using namespace ARDOUR; +using namespace PBD; TempoDialog::TempoDialog (TempoMap& map, jack_nframes_t frame, const string & action) : ArdourDialog ("tempo dialog"), diff --git a/gtk2_ardour/time_axis_view.cc b/gtk2_ardour/time_axis_view.cc index 1b6c1f390c..b5ab5baa10 100644 --- a/gtk2_ardour/time_axis_view.cc +++ b/gtk2_ardour/time_axis_view.cc @@ -55,6 +55,7 @@ using namespace Gtk; using namespace Gdk; using namespace sigc; using namespace ARDOUR; +using namespace PBD; using namespace Editing; using namespace ArdourCanvas; diff --git a/gtk2_ardour/time_axis_view_item.cc b/gtk2_ardour/time_axis_view_item.cc index f54688ddfb..abab306a84 100644 --- a/gtk2_ardour/time_axis_view_item.cc +++ b/gtk2_ardour/time_axis_view_item.cc @@ -38,6 +38,7 @@ using namespace std; using namespace Editing; using namespace Glib; +using namespace PBD; //------------------------------------------------------------------------------ /** Initialize const static memeber data */ @@ -484,26 +485,14 @@ TimeAxisViewItem::get_item_name() const * @param src the identity of the object that initiated the change */ void -TimeAxisViewItem::set_selected(bool yn, void* src) +TimeAxisViewItem::set_selected(bool yn) { if (_selected != yn) { - _selected = yn ; + Selectable::set_selected (yn); set_frame_color (); - Selected (_selected) ; /* EMIT_SIGNAL */ } } -/** - * Returns whether this item is currently selected. - * - * @return true if this item is currently selected, false otherwise - */ -bool -TimeAxisViewItem::get_selected() const -{ - return (_selected) ; -} - void TimeAxisViewItem::set_should_show_selection (bool yn) { diff --git a/gtk2_ardour/time_axis_view_item.h b/gtk2_ardour/time_axis_view_item.h index c9e4fd5dd5..b23350eef7 100644 --- a/gtk2_ardour/time_axis_view_item.h +++ b/gtk2_ardour/time_axis_view_item.h @@ -21,8 +21,6 @@ #ifndef __gtk_ardour_time_axis_view_item_h__ #define __gtk_ardour_time_axis_view_item_h__ -#include - #include #include @@ -38,7 +36,7 @@ class TimeAxisView; * A base class for 'items' that may appear upon a TimeAxisView * */ -class TimeAxisViewItem : public sigc::trackable, public Selectable +class TimeAxisViewItem : public Selectable { public: virtual ~TimeAxisViewItem() ; @@ -170,9 +168,8 @@ class TimeAxisViewItem : public sigc::trackable, public Selectable * Set to true to indicate that this item is currently selected * * @param yn true if this item is currently selected - * @param src the identity of the object that initiated the change */ - virtual void set_selected(bool yn, void* src) ; + virtual void set_selected(bool yn) ; /** * Set to true to indicate that this item should show its selection status @@ -181,13 +178,6 @@ class TimeAxisViewItem : public sigc::trackable, public Selectable */ virtual void set_should_show_selection (bool yn) ; - /** - * Returns whether this item is currently selected. - * - * @return true if this item is currently selected, false otherwise - */ - bool get_selected() const ; - //---------------------------------------------------------------------------------------// // Parent Component Methods @@ -319,10 +309,6 @@ class TimeAxisViewItem : public sigc::trackable, public Selectable /** Emitted when the mionimum item duration is changed */ sigc::signal MinDurationChanged ; - /** Emitted when the selected status of this item changes */ - sigc::signal Selected ; - - protected: enum Visibility { diff --git a/gtk2_ardour/time_selection.cc b/gtk2_ardour/time_selection.cc index 0d1b94e8a0..518e04cccb 100644 --- a/gtk2_ardour/time_selection.cc +++ b/gtk2_ardour/time_selection.cc @@ -28,6 +28,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; AudioRange& TimeSelection::operator[] (uint32_t which) diff --git a/gtk2_ardour/utils.cc b/gtk2_ardour/utils.cc index c1ad4f6ca7..91cb7ad58b 100644 --- a/gtk2_ardour/utils.cc +++ b/gtk2_ardour/utils.cc @@ -43,6 +43,7 @@ using namespace std; using namespace Gtk; using namespace sigc; using namespace Glib; +using namespace PBD; ustring fit_to_pixels (const ustring& str, int pixel_width, Pango::FontDescription& font, int& actual_width) diff --git a/gtk2_ardour/visual_time_axis.cc b/gtk2_ardour/visual_time_axis.cc index b6c96c55ab..c27ed33089 100644 --- a/gtk2_ardour/visual_time_axis.cc +++ b/gtk2_ardour/visual_time_axis.cc @@ -55,6 +55,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; using namespace sigc; using namespace Gtk; diff --git a/gtk2_ardour/vst_pluginui.cc b/gtk2_ardour/vst_pluginui.cc index 8b40e27070..7adf702f4d 100644 --- a/gtk2_ardour/vst_pluginui.cc +++ b/gtk2_ardour/vst_pluginui.cc @@ -19,7 +19,7 @@ */ #include - +#include #include #include @@ -29,6 +29,7 @@ using namespace Gtk; using namespace ARDOUR; +using namespace PBD; VSTPluginUI::VSTPluginUI (PluginInsert& pi, VSTPlugin& vp) : PlugUIBase (pi), @@ -60,16 +61,12 @@ VSTPluginUI::get_preferred_height () int VSTPluginUI::package (Gtk::Window& win) { - /* for GTK+2, remove this: you cannot add to a realized socket */ - - //socket.realize (); - /* forward configure events to plugin window */ - win.signal_configure_event().connect (bind (mem_fun (*this, &VSTPluginUI::configure_handler), &socket)); + win.signal_configure_event().connect (bind (mem_fun (*this, &VSTPluginUI::configure_handler), &socket), false); - /* XXX in GTK2, use add_id() instead of steal, although add_id() - assumes that the window's owner understands the XEmbed protocol. + /* + this assumes that the window's owner understands the XEmbed protocol. */ socket.add_id (fst_get_XID (vst.fst())); @@ -77,45 +74,42 @@ VSTPluginUI::package (Gtk::Window& win) return 0; } -gboolean +bool VSTPluginUI::configure_handler (GdkEventConfigure* ev, Gtk::Socket *socket) { XEvent event; - gint x, y; + GdkWindow* w; - if (socket->gobj() == NULL) { - return FALSE; + if (socket == 0 || ((w = socket->gobj()->plug_window) == 0)) { + return false; } event.xconfigure.type = ConfigureNotify; - event.xconfigure.event = GDK_WINDOW_XWINDOW (socket->get_window()->gobj()); - event.xconfigure.window = GDK_WINDOW_XWINDOW (socket->get_window()->gobj()); + event.xconfigure.event = GDK_WINDOW_XWINDOW (w); + event.xconfigure.window = GDK_WINDOW_XWINDOW (w); /* The ICCCM says that synthetic events should have root relative * coordinates. We still aren't really ICCCM compliant, since * we don't send events when the real toplevel is moved. */ gdk_error_trap_push (); - gdk_window_get_origin (socket->get_window()->gobj(), &x, &y); + gdk_window_get_origin (w, &x, &y); gdk_error_trap_pop (); event.xconfigure.x = x; event.xconfigure.y = y; - event.xconfigure.width = GTK_WIDGET(socket)->allocation.width; - event.xconfigure.height = GTK_WIDGET(socket)->allocation.height; + event.xconfigure.width = GTK_WIDGET(socket->gobj())->allocation.width; + event.xconfigure.height = GTK_WIDGET(socket->gobj())->allocation.height; event.xconfigure.border_width = 0; event.xconfigure.above = None; event.xconfigure.override_redirect = False; gdk_error_trap_push (); - XSendEvent (GDK_WINDOW_XDISPLAY (socket->get_window()->gobj()), - GDK_WINDOW_XWINDOW (socket->get_window()->gobj()), - False, StructureNotifyMask, &event); - // gdk_display_sync (GDK_WINDOW_XDISPLAY (socket->plug_window)); + XSendEvent (GDK_WINDOW_XDISPLAY (w), GDK_WINDOW_XWINDOW (w), False, StructureNotifyMask, &event); gdk_error_trap_pop (); - return FALSE; + return false; } diff --git a/libs/ardour/SConscript b/libs/ardour/SConscript index 0fb5cfc788..605911d7ef 100644 --- a/libs/ardour/SConscript +++ b/libs/ardour/SConscript @@ -27,12 +27,15 @@ ardour.Append(POTFILE = domain + '.pot') ardour.Append(CPPPATH = '#libs/surfaces/control_protocol') ardour_files=Split(""" +audio_diskstream.cc audio_library.cc audio_playlist.cc audio_track.cc audioengine.cc +audiofilesource.cc audiofilter.cc audioregion.cc +audiosource.cc auditioner.cc automation.cc automation_event.cc @@ -44,9 +47,6 @@ curve.cc cycle_timer.cc default_click.cc destructive_filesource.cc -diskstream.cc -externalsource.cc -filesource.cc gain.cc gdither.cc globals.cc @@ -103,6 +103,7 @@ extra_sources = [ ] if ardour['VST']: extra_sources += vst_files + ardour.Append(CCFLAGS="-DVST_SUPPORT", CPPPATH="#libs/fst") if ardour['LIBLO']: extra_sources += osc_files @@ -178,15 +179,14 @@ if conf.CheckCHeader('/System/Library/Frameworks/CoreMIDI.framework/Headers/Core if conf.CheckCHeader('/System/Library/Frameworks/AudioToolbox.framework/Headers/ExtendedAudioFile.h') and ardour['COREAUDIO'] == 1: ardour.Append(CXXFLAGS="-DHAVE_COREAUDIO") ardour.Append(LINKFLAGS="-framework AudioToolbox") + extra_sources += coreaudio_files if env['CONFIG_ARCH'] == 'apple': # this next line avoids issues with circular dependencies between libardour and libardour_cp. # it is based on the (entirely reasonable) assumption that a system with CoreAudio is OS X # - print 'APPLE CONFIG' ardour.Append(LINKFLAGS='-undefined suppress -flat_namespace') - extra_sources += coreaudio_files ardour = conf.Finish () @@ -201,8 +201,8 @@ ardour.Merge ([ libraries['pbd3'], libraries['soundtouch'], libraries['midi++2'], - libraries['glib2'], - libraries['glibmm2'] + libraries['glib2'], + libraries['glibmm2'] ]) if ardour['LIBLO']: diff --git a/libs/ardour/ardour/ardour.h b/libs/ardour/ardour/ardour.h index fee6c601a2..c0dfea9a95 100644 --- a/libs/ardour/ardour/ardour.h +++ b/libs/ardour/ardour/ardour.h @@ -45,7 +45,7 @@ namespace ARDOUR { static const jack_nframes_t max_frames = JACK_MAX_FRAMES; - int init (AudioEngine&, bool with_vst, bool try_optimization, void (*sighandler)(int,siginfo_t*,void*) = 0); + int init (AudioEngine&, bool with_vst, bool try_optimization); int cleanup (); diff --git a/libs/ardour/ardour/diskstream.h b/libs/ardour/ardour/audio_diskstream.h similarity index 94% rename from libs/ardour/ardour/diskstream.h rename to libs/ardour/ardour/audio_diskstream.h index 316daba52f..9355a3fccb 100644 --- a/libs/ardour/ardour/diskstream.h +++ b/libs/ardour/ardour/audio_diskstream.h @@ -15,7 +15,7 @@ along with this program; if not, write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - $Id$ + $Id: diskstream.h 579 2006-06-12 19:56:37Z essej $ */ #ifndef __ardour_diskstream_h__ @@ -52,10 +52,10 @@ class AudioEngine; class Send; class Session; class AudioPlaylist; -class FileSource; +class AudioFileSource; class IO; -class DiskStream : public Stateful, public sigc::trackable +class AudioDiskstream : public Stateful, public sigc::trackable { public: enum Flag { @@ -64,15 +64,15 @@ class DiskStream : public Stateful, public sigc::trackable Destructive = 0x4 }; - DiskStream (Session &, const string& name, Flag f = Recordable); - DiskStream (Session &, const XMLNode&); + AudioDiskstream (Session &, const string& name, Flag f = Recordable); + AudioDiskstream (Session &, const XMLNode&); string name() const { return _name; } ARDOUR::IO* io() const { return _io; } void set_io (ARDOUR::IO& io); - DiskStream& ref() { _refcnt++; return *this; } + AudioDiskstream& ref() { _refcnt++; return *this; } void unref() { if (_refcnt) _refcnt--; if (_refcnt == 0) delete this; } uint32_t refcnt() const { return _refcnt; } @@ -154,7 +154,7 @@ class DiskStream : public Stateful, public sigc::trackable AudioPlaylist *playlist () { return _playlist; } - FileSource *write_source (uint32_t n=0) { + AudioFileSource *write_source (uint32_t n=0) { if (n < channels.size()) return channels[n].write_source; return 0; @@ -184,8 +184,8 @@ class DiskStream : public Stateful, public sigc::trackable static sigc::signal DiskOverrun; static sigc::signal DiskUnderrun; - static sigc::signal DiskStreamCreated; // XXX use a ref with sigc2 - static sigc::signal*> DeleteSources; + static sigc::signal AudioDiskstreamCreated; // XXX use a ref with sigc2 + static sigc::signal*> DeleteSources; /* stateful */ @@ -266,7 +266,7 @@ class DiskStream : public Stateful, public sigc::trackable /* use unref() to destroy a diskstream */ - ~DiskStream(); + ~AudioDiskstream(); enum TransitionType { CaptureStart = 0, @@ -288,8 +288,8 @@ class DiskStream : public Stateful, public sigc::trackable float peak_power; - FileSource *fades_source; - FileSource *write_source; + AudioFileSource *fades_source; + AudioFileSource *write_source; Port *source; Sample *current_capture_buffer; @@ -432,7 +432,7 @@ class DiskStream : public Stateful, public sigc::trackable void non_realtime_set_speed (); std::list _last_capture_regions; - std::vector capturing_sources; + std::vector capturing_sources; int use_pending_capture_data (XMLNode& node); void get_input_sources (); diff --git a/libs/ardour/ardour/audio_track.h b/libs/ardour/ardour/audio_track.h index c7af9fc5d8..1c17cbc859 100644 --- a/libs/ardour/ardour/audio_track.h +++ b/libs/ardour/ardour/audio_track.h @@ -26,7 +26,7 @@ namespace ARDOUR { class Session; -class DiskStream; +class AudioDiskstream; class AudioPlaylist; class RouteGroup; @@ -52,8 +52,8 @@ class AudioTrack : public Route bool can_record() const { return true; } void set_record_enable (bool yn, void *src); - DiskStream& disk_stream() const { return *diskstream; } - int set_diskstream (DiskStream&, void *); + AudioDiskstream& disk_stream() const { return *diskstream; } + int set_diskstream (AudioDiskstream&, void *); int use_diskstream (string name); int use_diskstream (id_t id); @@ -99,7 +99,7 @@ class AudioTrack : public Route void set_meter_point (MeterPoint, void* src); protected: - DiskStream *diskstream; + AudioDiskstream *diskstream; MeterPoint _saved_meter_point; TrackMode _mode; diff --git a/libs/ardour/ardour/audiofilesource.h b/libs/ardour/ardour/audiofilesource.h new file mode 100644 index 0000000000..ecbac569d5 --- /dev/null +++ b/libs/ardour/ardour/audiofilesource.h @@ -0,0 +1,157 @@ +/* + Copyright (C) 2006 Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + +*/ + +#ifndef __ardour_audiofilesource_h__ +#define __ardour_audiofilesource_h__ + +#include + +#include + +namespace ARDOUR { + +struct SoundFileInfo { + float samplerate; + uint16_t channels; + int64_t length; + std::string format_name; +}; + +class AudioFileSource : public AudioSource { + public: + enum Flag { + Writable = 0x1, + CanRename = 0x2, + Broadcast = 0x4, + Removable = 0x8, + RemovableIfEmpty = 0x10, + RemoveAtDestroy = 0x20, + BuildPeaks = 0x40 + }; + + virtual ~AudioFileSource (); + + int set_name (string newname, bool destructive); + + string path() const { return _path; } + string peak_path (string audio_path); + string old_peak_path (string audio_path); + + static void set_peak_dir (string dir) { peak_dir = dir; } + + /* factory for an existing but not-used-in-session audio file. this exists + because there maybe multiple back-end derivations of AudioFileSource, + some of which can handle formats that cannot be handled by others. + For example, CoreAudioFileSource can handle MP3 files, which SndFileSource + cannot. + */ + + static AudioFileSource* create (string path_plus_channel); + static AudioFileSource* create (const XMLNode&); + + static bool get_soundfile_info (string path, SoundFileInfo& _info, string& error); + + void set_allow_remove_if_empty (bool yn); + void mark_for_remove(); + + /* this block of methods do nothing for regular file sources, but are significant + for files used in destructive recording. + */ + + virtual jack_nframes_t last_capture_start_frame() const { return 0; } + virtual void mark_capture_start (jack_nframes_t) {} + virtual void mark_capture_end () {} + virtual void clear_capture_marks() {} + + virtual int update_header (jack_nframes_t when, struct tm&, time_t) = 0; + virtual int flush_header () = 0; + + int move_to_trash (const string trash_dir_name); + + static bool is_empty (string path); + void mark_streaming_write_completed (); + + void mark_take (string); + string take_id() const { return _take_id; } + + static void set_bwf_country_code (string x); + static void set_bwf_organization_code (string x); + static void set_bwf_serial_number (int); + + static void set_search_path (string); + static void set_header_position_offset (jack_nframes_t offset, bool negative); + + static sigc::signal HeaderPositionOffsetChanged; + + XMLNode& get_state (); + int set_state (const XMLNode&); + + /* this should really be protected, but C++ is getting stricter + and creating slots from protected member functions is starting + to cause issues. + */ + + void handle_header_position_change (struct tm*, time_t tnow); + + protected: + + /* constructor to be called for existing external-to-session files */ + + AudioFileSource (std::string path, Flag flags); + + /* constructor to be called for new in-session files */ + + AudioFileSource (std::string path, Flag flags, + SampleFormat samp_format, HeaderFormat hdr_format); + + /* constructor to be called for existing in-session files */ + + AudioFileSource (const XMLNode&); + + int init (string idstr, bool must_exist); + + uint16_t channel; + string _path; + Flag _flags; + string _take_id; + bool allow_remove_if_empty; + uint64_t timeline_position; + + static string peak_dir; + static string search_path; + + static char bwf_country_code[3]; + static char bwf_organization_code[4]; + static char bwf_serial_number[13]; + + static uint64_t header_position_offset; + static bool header_position_negative; + + virtual void set_timeline_position (jack_nframes_t pos); + virtual void set_header_timeline_position () = 0; + + bool find (std::string path, bool must_exist, bool& is_new); + bool removable() const; + bool writable() const { return _flags & Writable; } +}; + +}; /* namespace ARDOUR */ + +#endif /* __ardour_audiofilesource_h__ */ + diff --git a/libs/ardour/ardour/audiofilter.h b/libs/ardour/ardour/audiofilter.h index d0fc275cf6..02e5e6f061 100644 --- a/libs/ardour/ardour/audiofilter.h +++ b/libs/ardour/ardour/audiofilter.h @@ -28,7 +28,6 @@ namespace ARDOUR { class AudioRegion; class Session; -class FileSource; class AudioFilter { @@ -37,7 +36,6 @@ class AudioFilter { : session (s){} virtual ~AudioFilter() {} - virtual int run (ARDOUR::AudioRegion&) = 0; std::vector results; diff --git a/libs/ardour/ardour/audioregion.h b/libs/ardour/ardour/audioregion.h index f210fa595b..009aa4b5b0 100644 --- a/libs/ardour/ardour/audioregion.h +++ b/libs/ardour/ardour/audioregion.h @@ -27,7 +27,6 @@ #include #include -#include #include #include #include @@ -40,6 +39,7 @@ class Route; class Playlist; class Session; class AudioFilter; +class AudioSource; struct AudioRegionState : public RegionState { @@ -56,7 +56,7 @@ struct AudioRegionState : public RegionState class AudioRegion : public Region { public: - typedef vector SourceList; + typedef vector SourceList; static Change FadeInChanged; static Change FadeOutChanged; @@ -66,12 +66,12 @@ class AudioRegion : public Region static Change ScaleAmplitudeChanged; static Change EnvelopeChanged; - AudioRegion (Source&, jack_nframes_t start, jack_nframes_t length, bool announce = true); - AudioRegion (Source&, jack_nframes_t start, jack_nframes_t length, const string& name, layer_t = 0, Region::Flag flags = Region::DefaultFlags, bool announce = true); + AudioRegion (AudioSource&, jack_nframes_t start, jack_nframes_t length, bool announce = true); + AudioRegion (AudioSource&, jack_nframes_t start, jack_nframes_t length, const string& name, layer_t = 0, Region::Flag flags = Region::DefaultFlags, bool announce = true); AudioRegion (SourceList &, jack_nframes_t start, jack_nframes_t length, const string& name, layer_t = 0, Region::Flag flags = Region::DefaultFlags, bool announce = true); AudioRegion (const AudioRegion&, jack_nframes_t start, jack_nframes_t length, const string& name, layer_t = 0, Region::Flag flags = Region::DefaultFlags, bool announce = true); AudioRegion (const AudioRegion&); - AudioRegion (Source&, const XMLNode&); + AudioRegion (AudioSource&, const XMLNode&); AudioRegion (SourceList &, const XMLNode&); ~AudioRegion(); @@ -85,7 +85,7 @@ class AudioRegion : public Region void lock_sources (); void unlock_sources (); - Source& source (uint32_t n=0) const { if (n < sources.size()) return *sources[n]; else return *sources[0]; } + AudioSource& source (uint32_t n=0) const { if (n < sources.size()) return *sources[n]; else return *sources[0]; } void set_scale_amplitude (gain_t); gain_t scale_amplitude() const { return _scale_amplitude; } diff --git a/libs/ardour/ardour/audiosource.h b/libs/ardour/ardour/audiosource.h new file mode 100644 index 0000000000..1dcf5b42f3 --- /dev/null +++ b/libs/ardour/ardour/audiosource.h @@ -0,0 +1,166 @@ +/* + Copyright (C) 2000 Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + + $Id: audio_source.h 486 2006-04-27 09:04:24Z pauld $ +*/ + +#ifndef __ardour_audio_source_h__ +#define __ardour_audio_source_h__ + +#include +#include +#include + +#include + +#include + +#include + +#include +#include +#include +#include + +using std::list; +using std::vector; +using std::string; + +namespace ARDOUR { + +const jack_nframes_t frames_per_peak = 256; + +class AudioSource : public Source +{ + public: + AudioSource (string name); + AudioSource (const XMLNode&); + virtual ~AudioSource (); + + /* returns the number of items in this `audio_source' */ + + virtual jack_nframes_t length() const { + return _length; + } + + virtual jack_nframes_t available_peaks (double zoom) const; + + virtual jack_nframes_t read (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const; + virtual jack_nframes_t write (Sample *src, jack_nframes_t cnt, char * workbuf); + + virtual float sample_rate () const = 0; + + virtual void mark_for_remove() = 0; + virtual void mark_streaming_write_completed () {} + + void set_captured_for (string str) { _captured_for = str; } + string captured_for() const { return _captured_for; } + + uint32_t read_data_count() const { return _read_data_count; } + uint32_t write_data_count() const { return _write_data_count; } + + int read_peaks (PeakData *peaks, jack_nframes_t npeaks, jack_nframes_t start, jack_nframes_t cnt, double samples_per_unit) const; + int build_peaks (); + bool peaks_ready (sigc::slot, sigc::connection&) const; + + static sigc::signal AudioSourceCreated; + + mutable sigc::signal PeaksReady; + mutable sigc::signal PeakRangeReady; + + XMLNode& get_state (); + int set_state (const XMLNode&); + + static int start_peak_thread (); + static void stop_peak_thread (); + + int rename_peakfile (std::string newpath); + + static void set_build_missing_peakfiles (bool yn) { + _build_missing_peakfiles = yn; + } + + static void set_build_peakfiles (bool yn) { + _build_peakfiles = yn; + } + + protected: + static bool _build_missing_peakfiles; + static bool _build_peakfiles; + + bool _peaks_built; + mutable Glib::Mutex _lock; + jack_nframes_t _length; + bool next_peak_clear_should_notify; + string peakpath; + string _captured_for; + + mutable uint32_t _read_data_count; // modified in read() + mutable uint32_t _write_data_count; // modified in write() + + int initialize_peakfile (bool newfile, string path); + void build_peaks_from_scratch (); + + int do_build_peak (jack_nframes_t, jack_nframes_t); + + virtual jack_nframes_t read_unlocked (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const = 0; + virtual jack_nframes_t write_unlocked (Sample *dst, jack_nframes_t cnt, char * workbuf) = 0; + virtual string peak_path(string audio_path) = 0; + virtual string old_peak_path(string audio_path) = 0; + + void update_length (jack_nframes_t pos, jack_nframes_t cnt); + + static pthread_t peak_thread; + static bool have_peak_thread; + static void* peak_thread_work(void*); + + static int peak_request_pipe[2]; + + struct PeakRequest { + enum Type { + Build, + Quit + }; + }; + + static vector pending_peak_sources; + static Glib::Mutex* pending_peak_sources_lock; + + static void queue_for_peaks (AudioSource&); + static void clear_queue_for_peaks (); + + struct PeakBuildRecord { + jack_nframes_t frame; + jack_nframes_t cnt; + + PeakBuildRecord (jack_nframes_t f, jack_nframes_t c) + : frame (f), cnt (c) {} + PeakBuildRecord (const PeakBuildRecord& other) { + frame = other.frame; + cnt = other.cnt; + } + }; + + list pending_peak_builds; + + private: + bool file_changed (string path); +}; + +} + +#endif /* __ardour_audio_source_h__ */ diff --git a/libs/ardour/ardour/constsource.h b/libs/ardour/ardour/constsource.h deleted file mode 100644 index d000afb347..0000000000 --- a/libs/ardour/ardour/constsource.h +++ /dev/null @@ -1,60 +0,0 @@ -/* - Copyright (C) 2000 Paul Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ - -#ifndef __playlist_const_buffer_h__ -#define __playlist_const_buffer_h__ - -#include -#include - -#include "edl.h" - -namespace EDL { - -class ConstSource : public Source { - public: - ConstSource (const gchar *id) { - _type = Source::Const; - value = strtod (id, 0); - strncpy (idstr, id, 15); - idstr[15] = '\0'; - } - - const gchar * const id() { return idstr; } - - uint32_t length() { return ~0U; } - - uint32_t read (Source::Data *dst, uint32_t start, uint32_t cnt) { - uint32_t n = cnt; - while (n--) *dst++ = value; - return cnt; - } - void peak (guint8 *max, guint8 *min, uint32_t start, uint32_t cnt) { - *max = *min = (guint8) value; - } - - private: - Source::Data value; - gchar idstr[16]; -}; - -}; /* namespace EDL */ - -#endif /* __playlist_const_buffer_h__ */ diff --git a/libs/ardour/ardour/coreaudio_source.h b/libs/ardour/ardour/coreaudio_source.h index 736ea32df7..81f1a14050 100644 --- a/libs/ardour/ardour/coreaudio_source.h +++ b/libs/ardour/ardour/coreaudio_source.h @@ -20,19 +20,22 @@ #ifndef __coreaudio_source_h__ #define __coreaudio_source_h__ -#include +#include #include namespace ARDOUR { -class CoreAudioSource : public ExternalSource { +class CoreAudioSource : public AudioFileSource { public: CoreAudioSource (const string& path_plus_channel, bool build_peak = true); CoreAudioSource (const XMLNode&); ~CoreAudioSource (); - jack_nframes_t read (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const; float sample_rate() const; + int update_header (jack_nframes_t when, struct tm&, time_t); + + protected: + jack_nframes_t read_unlocked (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const; private: ExtAudioFileRef af; diff --git a/libs/ardour/ardour/cycle_timer.h b/libs/ardour/ardour/cycle_timer.h index 1ec7c74903..b9cbbbf0a8 100644 --- a/libs/ardour/ardour/cycle_timer.h +++ b/libs/ardour/ardour/cycle_timer.h @@ -22,29 +22,27 @@ #define __ardour_cycle_timer_h__ #include -#include +#include #include -using std::string; - class CycleTimer { private: static float cycles_per_usec; - uint32_t long entry; - uint32_t long exit; - string _name; + cycles_t _entry; + cycles_t _exit; + std::string _name; public: - CycleTimer(string name) : _name (name){ + CycleTimer(std::string name) : _name (name){ if (cycles_per_usec == 0) { cycles_per_usec = get_mhz (); } - entry = get_cycles(); + _entry = get_cycles(); } ~CycleTimer() { - exit = get_cycles(); - printf ("%s: %.9f usecs (%lu-%lu)\n", _name.c_str(), (float) (exit - entry) / cycles_per_usec, entry, exit); + _exit = get_cycles(); + std::cerr << _name << ": " << (float) (_exit - _entry) / cycles_per_usec << " (" << _entry << ", " << _exit << ')' << endl; } static float get_mhz (); diff --git a/libs/ardour/ardour/destructive_filesource.h b/libs/ardour/ardour/destructive_filesource.h index dbaf379257..c92a0762ee 100644 --- a/libs/ardour/ardour/destructive_filesource.h +++ b/libs/ardour/ardour/destructive_filesource.h @@ -23,30 +23,33 @@ #include -#include +#include struct tm; namespace ARDOUR { -class DestructiveFileSource : public FileSource { +class DestructiveFileSource : public SndFileSource { public: - DestructiveFileSource (std::string path, jack_nframes_t rate, bool repair_first = false, SampleFormat samp_format=FormatInt24); - DestructiveFileSource (const XMLNode&, jack_nframes_t rate); + DestructiveFileSource (std::string path, SampleFormat samp_format, HeaderFormat hdr_format, jack_nframes_t rate, + Flag flags = AudioFileSource::Flag (AudioFileSource::Writable| + AudioFileSource::BuildPeaks)); + + DestructiveFileSource (const XMLNode&); ~DestructiveFileSource (); - int seek (jack_nframes_t frame); jack_nframes_t last_capture_start_frame() const; void mark_capture_start (jack_nframes_t); void mark_capture_end (); void clear_capture_marks(); - jack_nframes_t write (Sample *src, jack_nframes_t cnt, char * workbuf); - XMLNode& get_state (); static void setup_standard_crossfades (jack_nframes_t sample_rate); + protected: + jack_nframes_t write_unlocked (Sample *src, jack_nframes_t cnt, char * workbuf); + private: static jack_nframes_t xfade_frames; static gain_t* out_coefficient; @@ -59,7 +62,7 @@ class DestructiveFileSource : public FileSource { Sample* xfade_buf; jack_nframes_t crossfade (Sample* data, jack_nframes_t cnt, int dir, char * workbuf); - + void set_timeline_position (jack_nframes_t); }; } diff --git a/libs/ardour/ardour/externalsource.h b/libs/ardour/ardour/externalsource.h deleted file mode 100644 index 17504d0afc..0000000000 --- a/libs/ardour/ardour/externalsource.h +++ /dev/null @@ -1,67 +0,0 @@ -/* - Copyright (C) 2006 Paul Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - -*/ - -#ifndef __external_source_h__ -#define __external_source_h__ - -#include - -namespace ARDOUR { - -struct SoundFileInfo { - float samplerate; - uint16_t channels; - int64_t length; - std::string format_name; -}; - -class ExternalSource : public Source { - public: - virtual ~ExternalSource (); - - string path() const { return _path; } - - virtual jack_nframes_t read (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const = 0; - - void mark_for_remove() {} // we never remove external sndfiles - string peak_path(string audio_path); - string old_peak_path(string audio_path); - - static void set_peak_dir (string dir) { peak_dir = dir; } - - static ExternalSource* create (const string& path_plus_channel, bool build_peak = true); - static ExternalSource* create (const XMLNode& node); - static bool get_soundfile_info (string path, SoundFileInfo& _info, string& error); - - protected: - ExternalSource (const string& path_plus_channel, bool build_peak = true); - ExternalSource (const XMLNode&); - - static string peak_dir; - - uint16_t channel; - string _path; - - jack_nframes_t read_unlocked (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const; -}; - -}; /* namespace ARDOUR */ - -#endif /* __external_source_h__ */ - diff --git a/libs/ardour/ardour/filesource.h b/libs/ardour/ardour/filesource.h deleted file mode 100644 index 28a01f0a78..0000000000 --- a/libs/ardour/ardour/filesource.h +++ /dev/null @@ -1,201 +0,0 @@ -/* - Copyright (C) 2000 Paul Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ - -#ifndef __playlist_file_buffer_h__ -#define __playlist_file_buffer_h__ - -// darwin supports 64 by default and doesn't provide wrapper functions. -#if defined (__APPLE__) -typedef off_t off64_t; -#define open64 open -#define close64 close -#define lseek64 lseek -#define pread64 pread -#define pwrite64 pwrite -#endif - -#include -#include - -#include - -struct tm; - -using std::string; - -namespace ARDOUR { - -class FileSource : public Source { - public: - FileSource (string path, jack_nframes_t rate, bool repair_first = false, SampleFormat samp_format=FormatFloat); - FileSource (const XMLNode&, jack_nframes_t rate); - ~FileSource (); - - int set_name (std::string str, bool destructive); - - void set_allow_remove_if_empty (bool yn); - - jack_nframes_t length() const { return _length; } - jack_nframes_t read (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const; - jack_nframes_t write (Sample *src, jack_nframes_t cnt, char * workbuf); - void mark_for_remove(); - string peak_path(string audio_path); - string path() const { return _path; } - float sample_rate () const; - - virtual int seek (jack_nframes_t frame) {return 0; } - virtual jack_nframes_t last_capture_start_frame() const { return 0; } - virtual void mark_capture_start (jack_nframes_t) {} - virtual void mark_capture_end () {} - virtual void clear_capture_marks() {} - - int update_header (jack_nframes_t when, struct tm&, time_t); - - int move_to_trash (const string trash_dir_name); - - static bool is_empty (string path); - void mark_streaming_write_completed (); - - void mark_take (string); - string take_id() const { return _take_id; } - - static void set_bwf_country_code (string x); - static void set_bwf_organization_code (string x); - static void set_bwf_serial_number (int); - - static void set_search_path (string); - - protected: - int fd; - string _path; - bool remove_at_unref; - bool is_bwf; - off64_t data_offset; - string _take_id; - SampleFormat _sample_format; - int _sample_size; - bool allow_remove_if_empty; - - static char bwf_country_code[3]; - static char bwf_organization_code[4]; - static char bwf_serial_number[13]; - - struct GenericChunk { - char id[4]; - int32_t size; - }; - - struct WAVEChunk : public GenericChunk { - char text[4]; /* wave pseudo-chunk id "WAVE" */ - }; - - struct FMTChunk : public GenericChunk { - int16_t formatTag; /* format tag; currently pcm */ - int16_t nChannels; /* number of channels */ - uint32_t nSamplesPerSec; /* sample rate in hz */ - int32_t nAvgBytesPerSec; /* average bytes per second */ - int16_t nBlockAlign; /* number of bytes per sample */ - int16_t nBitsPerSample; /* number of bits in a sample */ - }; - - struct BroadcastChunk : public GenericChunk { - char description[256]; - char originator[32]; - char originator_reference[32]; - char origination_date[10]; - char origination_time[8]; - int32_t time_reference_low; - int32_t time_reference_high; - int16_t version; /* 1.0 because we have umid and 190 bytes of "reserved" */ - char umid[64]; - char reserved[190]; - /* we don't treat coding history as part of the struct */ - }; - - struct ChunkInfo { - std::string name; - uint32_t size; - off64_t offset; - - ChunkInfo (string s, uint32_t sz, off64_t o) - : name (s), size (sz), offset (o) {} - }; - - vector chunk_info; - - struct { - WAVEChunk wave; - FMTChunk format; - GenericChunk data; - BroadcastChunk bext; - vector coding_history; - bool bigendian; - } header; - - int init (string, bool must_exist, jack_nframes_t); - jack_nframes_t read_unlocked (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const; - - ssize_t file_write (Sample *src, jack_nframes_t framepos, jack_nframes_t cnt, char * workbuf) { - switch (_sample_format) { - case FormatInt24: return write_pcm_24(src, framepos, cnt, workbuf); - default: return write_float(src, framepos, cnt, workbuf); - }; - } - - ssize_t file_read (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const { - switch (_sample_format) { - case FormatInt24: return read_pcm_24(dst, start, cnt, workbuf); - default: return read_float(dst, start, cnt, workbuf); - }; - } - - ssize_t write_float(Sample *src, jack_nframes_t framepos, jack_nframes_t cnt, char * workbuf); - ssize_t read_float (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const; - ssize_t write_pcm_24(Sample *src, jack_nframes_t framepos, jack_nframes_t cnt, char * workbuf); - ssize_t read_pcm_24 (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const; - - int discover_chunks (bool silent); - ChunkInfo* lookup_chunk (string name); - - int write_header (); - int read_header (bool silent); - - int check_header (jack_nframes_t rate, bool silent); - int fill_header (jack_nframes_t rate); - - int read_broadcast_data (ChunkInfo&); - void compute_header_size (); - - static const int32_t wave_header_size = sizeof (WAVEChunk) + sizeof (FMTChunk) + sizeof (GenericChunk); - static const int32_t bwf_header_size = wave_header_size + sizeof (BroadcastChunk); - - static string search_path; - - int repair (string, jack_nframes_t); - - void swap_endian (GenericChunk & chunk) const; - void swap_endian (FMTChunk & chunk) const; - void swap_endian (BroadcastChunk & chunk) const; - void swap_endian (Sample *buf, jack_nframes_t cnt) const; -}; - -} - -#endif /* __playlist_file_buffer_h__ */ diff --git a/libs/ardour/ardour/io.h b/libs/ardour/ardour/io.h index c80a7abfaa..8ae45fe65c 100644 --- a/libs/ardour/ardour/io.h +++ b/libs/ardour/ardour/io.h @@ -321,7 +321,6 @@ public: Change restore_state (State&); StateManager::State* state_factory (std::string why) const; - void send_state_changed(); bool get_midi_node_info (XMLNode * node, MIDI::eventType & ev, MIDI::channel_t & chan, MIDI::byte & additional); bool set_midi_node_info (XMLNode * node, MIDI::eventType ev, MIDI::channel_t chan, MIDI::byte additional); diff --git a/libs/ardour/ardour/osc.h b/libs/ardour/ardour/osc.h index 69ec76eac6..0a34f44a41 100644 --- a/libs/ardour/ardour/osc.h +++ b/libs/ardour/ardour/osc.h @@ -32,7 +32,7 @@ #include -#include "basic_ui.h" +#include namespace ARDOUR { class Session; diff --git a/libs/ardour/ardour/playlist.h b/libs/ardour/ardour/playlist.h index d322f564ee..c653c8502e 100644 --- a/libs/ardour/ardour/playlist.h +++ b/libs/ardour/ardour/playlist.h @@ -37,7 +37,6 @@ #include #include #include -#include #include namespace ARDOUR { diff --git a/libs/ardour/ardour/region.h b/libs/ardour/ardour/region.h index 3c94dad6fd..aae776625e 100644 --- a/libs/ardour/ardour/region.h +++ b/libs/ardour/ardour/region.h @@ -233,7 +233,6 @@ class Region : public Stateful, public StateManager /* state management */ void send_change (Change); - void send_state_changed (); /* derived classes need these during their own state management calls */ diff --git a/libs/ardour/ardour/route.h b/libs/ardour/ardour/route.h index 5699d9ef14..5686dfc908 100644 --- a/libs/ardour/ardour/route.h +++ b/libs/ardour/ardour/route.h @@ -95,7 +95,7 @@ class Route : public IO virtual bool can_record() const { return false; } virtual void set_record_enable (bool yn, void *src) {} virtual bool record_enabled() const { return false; } - virtual void transport_stopped (bool abort, bool did_locate, bool flush_redirects); + virtual void handle_transport_stopped (bool abort, bool did_locate, bool flush_redirects); virtual void set_pending_declick (int); /* end of vfunc-based API */ diff --git a/libs/ardour/ardour/seqsource.h b/libs/ardour/ardour/seqsource.h deleted file mode 100644 index 7e38d27915..0000000000 --- a/libs/ardour/ardour/seqsource.h +++ /dev/null @@ -1,55 +0,0 @@ -/* - Copyright (C) 2000 Paul Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ - -#ifndef __playlist_seqsource_h__ -#define __playlist_seqsource_h__ - -#include - -#include "edl.h" - -namespace EDL { - -class PlaylistSource : public Source { - public: - PlaylistSource (Playlist&); - ~PlaylistSource (); - - const gchar * const id() { return playlist.name().c_str(); } - uint32_t length() { return playlist.length(); } - uint32_t read (Source::Data *dst, uint32_t start, uint32_t cnt) { - return playlist.read (dst, start, cnt, false); - } - uint32_t write (Source::Data *src, uint32_t where, uint32_t cnt) { - return playlist.write (src, where, cnt); - } - -// int read_peaks (peak_data_t *, uint32_t npeaks, uint32_t start, uint32_t cnt); -// int build_peak (uint32_t first_frame, uint32_t cnt); - - protected: - - private: - Playlist& playlist; -}; - -}; /* namespace EDL */ - -#endif /* __playlist_seqsource_h__ */ diff --git a/libs/ardour/ardour/session.h b/libs/ardour/ardour/session.h index 3d164a4b05..971e141363 100644 --- a/libs/ardour/ardour/session.h +++ b/libs/ardour/ardour/session.h @@ -60,11 +60,12 @@ namespace ARDOUR { class Port; class AudioEngine; class Slave; -class DiskStream; +class AudioDiskstream; class Route; class AuxInput; class Source; -class FileSource; +class AudioSource; +class AudioFileSource; class Auditioner; class Insert; class Send; @@ -261,25 +262,30 @@ class Session : public sigc::trackable, public Stateful vector& get_silent_buffers (uint32_t howmany); vector& get_send_buffers () { return _send_buffers; } - DiskStream *diskstream_by_id (id_t id); - DiskStream *diskstream_by_name (string name); + AudioDiskstream *diskstream_by_id (id_t id); + AudioDiskstream *diskstream_by_name (string name); bool have_captured() const { return _have_captured; } void refill_all_diskstream_buffers (); uint32_t diskstream_buffer_size() const { return dstream_buffer_size; } - uint32_t get_next_diskstream_id() const { return n_diskstreams(); } - uint32_t n_diskstreams() const; - typedef list DiskStreamList; + /* XXX fix required here when we get new diskstream types *, but + not sure of the direction to take this in until then. + */ - Session::DiskStreamList disk_streams() const { + uint32_t get_next_diskstream_id() const { return n_audio_diskstreams(); } + uint32_t n_audio_diskstreams() const; + + typedef list AudioDiskstreamList; + + Session::AudioDiskstreamList audio_disk_streams() const { Glib::RWLock::ReaderLock lm (diskstream_lock); - return diskstreams; /* XXX yes, force a copy */ + return audio_diskstreams; /* XXX yes, force a copy */ } - void foreach_diskstream (void (DiskStream::*func)(void)); - template void foreach_diskstream (T *obj, void (T::*func)(DiskStream&)); + void foreach_audio_diskstream (void (AudioDiskstream::*func)(void)); + template void foreach_audio_diskstream (T *obj, void (T::*func)(AudioDiskstream&)); typedef list RouteList; @@ -344,7 +350,7 @@ class Session : public sigc::trackable, public Stateful sigc::signal HaltOnXrun; sigc::signal RouteAdded; - sigc::signal DiskStreamAdded; + sigc::signal AudioDiskstreamAdded; void request_roll (); void request_bounded_roll (jack_nframes_t start, jack_nframes_t end); @@ -356,15 +362,15 @@ class Session : public sigc::trackable, public Stateful void goto_start () { request_locate (start_location->start(), false); } void use_rf_shuttle_speed (); void request_transport_speed (float speed); - void request_overwrite_buffer (DiskStream*); - void request_diskstream_speed (DiskStream&, float speed); + void request_overwrite_buffer (AudioDiskstream*); + void request_diskstream_speed (AudioDiskstream&, float speed); void request_input_change_handling (); bool locate_pending() const { return static_cast(post_transport_work&PostTransportLocate); } bool transport_locked () const; int wipe (); - int wipe_diskstream (DiskStream *); + int wipe_diskstream (AudioDiskstream *); int remove_region_from_region_list (Region&); @@ -584,25 +590,13 @@ class Session : public sigc::trackable, public Stateful int set_smpte_type (float fps, bool drop_frames); void bbt_time (jack_nframes_t when, BBT_Time&); + void smpte_to_sample( SMPTE::Time& smpte, jack_nframes_t& sample, bool use_offset, bool use_subframes ) const; + void sample_to_smpte( jack_nframes_t sample, SMPTE::Time& smpte, bool use_offset, bool use_subframes ) const; + void smpte_time (SMPTE::Time &); + void smpte_time (jack_nframes_t when, SMPTE::Time&); + void smpte_time_subframes (jack_nframes_t when, SMPTE::Time&); - ARDOUR::smpte_wrap_t smpte_increment( SMPTE_Time& smpte ) const; - ARDOUR::smpte_wrap_t smpte_decrement( SMPTE_Time& smpte ) const; - ARDOUR::smpte_wrap_t smpte_increment_subframes( SMPTE_Time& smpte ) const; - ARDOUR::smpte_wrap_t smpte_decrement_subframes( SMPTE_Time& smpte ) const; - ARDOUR::smpte_wrap_t smpte_increment_seconds( SMPTE_Time& smpte ) const; - ARDOUR::smpte_wrap_t smpte_increment_minutes( SMPTE_Time& smpte ) const; - ARDOUR::smpte_wrap_t smpte_increment_hours( SMPTE_Time& smpte ) const; - void smpte_frames_floor( SMPTE_Time& smpte ) const; - void smpte_seconds_floor( SMPTE_Time& smpte ) const; - void smpte_minutes_floor( SMPTE_Time& smpte ) const; - void smpte_hours_floor( SMPTE_Time& smpte ) const; - void smpte_to_sample( SMPTE_Time& smpte, jack_nframes_t& sample, bool use_offset, bool use_subframes ) const; - void sample_to_smpte( jack_nframes_t sample, SMPTE_Time& smpte, bool use_offset, bool use_subframes ) const; - void smpte_time (SMPTE_Time &); - void smpte_time (jack_nframes_t when, SMPTE_Time&); - void smpte_time_subframes (jack_nframes_t when, SMPTE_Time&); - - void smpte_duration (jack_nframes_t, SMPTE_Time&) const; + void smpte_duration (jack_nframes_t, SMPTE::Time&) const; void smpte_duration_string (char *, jack_nframes_t) const; void set_smpte_offset (jack_nframes_t); @@ -612,7 +606,7 @@ class Session : public sigc::trackable, public Stateful jack_nframes_t convert_to_frames_at (jack_nframes_t position, AnyTime&); - sigc::signal SMPTEOffsetChanged; + static sigc::signal SMPTEOffsetChanged; sigc::signal SMPTETypeChanged; void request_slave_source (SlaveSource, jack_nframes_t pos = 0); @@ -668,8 +662,9 @@ class Session : public sigc::trackable, public Stateful int start_audio_export (ARDOUR::AudioExportSpecification&); int stop_audio_export (ARDOUR::AudioExportSpecification&); - void add_source (Source *); - int remove_file_source (FileSource&); + void add_audio_source (AudioSource *); + void remove_source (Source *); + int cleanup_audio_file_source (AudioFileSource&); struct cleanup_report { vector paths; @@ -701,7 +696,8 @@ class Session : public sigc::trackable, public Stateful sigc::signal SourceAdded; sigc::signal SourceRemoved; - FileSource *create_file_source (ARDOUR::DiskStream&, int32_t chan, bool destructive); + AudioFileSource *create_audio_source_for_session (ARDOUR::AudioDiskstream&, uint32_t which_channel, bool destructive); + Source *get_source (ARDOUR::id_t); /* playlist management */ @@ -745,8 +741,8 @@ class Session : public sigc::trackable, public Stateful /* flattening stuff */ - int write_one_track (AudioTrack&, jack_nframes_t start, jack_nframes_t cnt, bool overwrite, vector&, - InterThreadInfo& wot); + int write_one_audio_track (AudioTrack&, jack_nframes_t start, jack_nframes_t cnt, bool overwrite, vector&, + InterThreadInfo& wot); int freeze (InterThreadInfo&); /* session-wide solo/mute/rec-enable */ @@ -972,7 +968,7 @@ class Session : public sigc::trackable, public Stateful void set_frame_rate (jack_nframes_t nframes); protected: - friend class DiskStream; + friend class AudioDiskstream; void stop_butler (); void wait_till_butler_finished(); @@ -1338,7 +1334,7 @@ class Session : public sigc::trackable, public Stateful MIDI::byte mtc_smpte_bits; /* encoding of SMTPE type for MTC */ MIDI::byte midi_msg[16]; jack_nframes_t outbound_mtc_smpte_frame; - SMPTE_Time transmitting_smpte_time; + SMPTE::Time transmitting_smpte_time; int next_quarter_frame_to_send; double _frames_per_smpte_frame; /* has to be floating point because of drop frame */ @@ -1354,7 +1350,7 @@ class Session : public sigc::trackable, public Stateful bool last_smpte_valid; jack_nframes_t last_smpte_when; - SMPTE_Time last_smpte; + SMPTE::Time last_smpte; int send_full_time_code (); int send_midi_time_code (); @@ -1434,12 +1430,12 @@ class Session : public sigc::trackable, public Stateful bool waiting_to_start; void set_auto_loop (bool yn); - void overwrite_some_buffers (DiskStream*); + void overwrite_some_buffers (AudioDiskstream*); void flush_all_redirects (); void locate (jack_nframes_t, bool with_roll, bool with_flush, bool with_loop=false); void start_locate (jack_nframes_t, bool with_roll, bool with_flush, bool with_loop=false); void force_locate (jack_nframes_t frame, bool with_roll = false); - void set_diskstream_speed (DiskStream*, float speed); + void set_diskstream_speed (AudioDiskstream*, float speed); void set_transport_speed (float speed, bool abort = false); void stop_transport (bool abort = false); void start_transport (); @@ -1470,10 +1466,10 @@ class Session : public sigc::trackable, public Stateful /* disk-streams */ - DiskStreamList diskstreams; + AudioDiskstreamList audio_diskstreams; mutable Glib::RWLock diskstream_lock; uint32_t dstream_buffer_size; - void add_diskstream (DiskStream*); + void add_diskstream (AudioDiskstream*); int load_diskstreams (const XMLNode&); /* routes stuff */ @@ -1515,16 +1511,14 @@ class Session : public sigc::trackable, public Stateful /* SOURCES */ - mutable Glib::Mutex source_lock; - typedef std::map SourceList; + mutable Glib::Mutex audio_source_lock; + typedef std::map AudioSourceList; - SourceList sources; + AudioSourceList audio_sources; int load_sources (const XMLNode& node); XMLNode& get_sources_as_xml (); - void remove_source (Source *); - Source *XMLSourceFactory (const XMLNode&); /* PLAYLISTS */ @@ -1543,7 +1537,7 @@ class Session : public sigc::trackable, public Stateful Playlist *XMLPlaylistFactory (const XMLNode&); void playlist_length_changed (Playlist *); - void diskstream_playlist_changed (DiskStream *); + void diskstream_playlist_changed (AudioDiskstream *); /* NAMED SELECTIONS */ diff --git a/libs/ardour/ardour/session_diskstream.h b/libs/ardour/ardour/session_diskstream.h index 3c888c92c3..33fc5419ba 100644 --- a/libs/ardour/ardour/session_diskstream.h +++ b/libs/ardour/ardour/session_diskstream.h @@ -22,15 +22,15 @@ #define __ardour_session_diskstream_h__ #include -#include +#include namespace ARDOUR { template void -Session::foreach_diskstream (T *obj, void (T::*func)(DiskStream&)) +Session::foreach_audio_diskstream (T *obj, void (T::*func)(AudioDiskstream&)) { Glib::RWLock::ReaderLock lm (diskstream_lock); - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); i++) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); i++) { if (!(*i)->hidden()) { (obj->*func) (**i); } diff --git a/libs/ardour/ardour/silentsource.h b/libs/ardour/ardour/silentsource.h deleted file mode 100644 index 0079e5f103..0000000000 --- a/libs/ardour/ardour/silentsource.h +++ /dev/null @@ -1,56 +0,0 @@ -/* - Copyright (C) 2000 Paul Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ - -#ifndef __playlist_const_buffer_h__ -#define __playlist_const_buffer_h__ - -#include -#include - -#include "source.h" - -namespace ARDOUR { - -class SilentSource : public Source { - public: - SilentSource () { - _name = "Silent Source"; - } - - static bool is_silent_source (const string& name) { - return name == "Silent Source"; - } - - jack_nframes_t length() { return ~0U; } - - jack_nframes_t read (Source::Data *dst, jack_nframes_t start, jack_nframes_t cnt) { - jack_nframes_t n = cnt; - while (n--) *dst++ = 0; - return cnt; - } - - void peak (guint8 *max, guint8 *min, jack_nframes_t start, jack_nframes_t cnt) { - *max = *min = 0; - } -}; - -} - -#endif /* __playlist_const_buffer_h__ */ diff --git a/libs/ardour/ardour/sndfilesource.h b/libs/ardour/ardour/sndfilesource.h index 5d11c9ef09..d146bb5793 100644 --- a/libs/ardour/ardour/sndfilesource.h +++ b/libs/ardour/ardour/sndfilesource.h @@ -23,29 +23,57 @@ #include -#include +#include namespace ARDOUR { -class SndFileSource : public ExternalSource { +class SndFileSource : public AudioFileSource { public: - SndFileSource (const string& path_plus_channel, bool build_peak = true); + /* constructor to be called for existing external-to-session files */ + + SndFileSource (std::string path, Flag flags); + + /* constructor to be called for new in-session files */ + + SndFileSource (std::string path, SampleFormat samp_format, HeaderFormat hdr_format, jack_nframes_t rate, + Flag flags = AudioFileSource::Flag (AudioFileSource::Writable| + AudioFileSource::Removable| + AudioFileSource::RemovableIfEmpty| + AudioFileSource::CanRename| + AudioFileSource::BuildPeaks)); + + /* constructor to be called for existing in-session files */ + SndFileSource (const XMLNode&); + ~SndFileSource (); - jack_nframes_t length() const { return _info.frames; } - jack_nframes_t read (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const; float sample_rate () const; + int update_header (jack_nframes_t when, struct tm&, time_t); + int flush_header (); + + static Flag default_in_session_flags(); + + protected: + void set_header_timeline_position (); + + jack_nframes_t read_unlocked (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const; + jack_nframes_t write_unlocked (Sample *dst, jack_nframes_t cnt, char * workbuf); + + jack_nframes_t write_float (Sample* data, jack_nframes_t pos, jack_nframes_t cnt); private: SNDFILE *sf; SF_INFO _info; + SF_BROADCAST_INFO *_broadcast_info; - mutable float *tmpbuf; - mutable jack_nframes_t tmpbufsize; - mutable Glib::Mutex _tmpbuf_lock; + mutable float *interleave_buf; + mutable jack_nframes_t interleave_bufsize; - void init (const string &str, bool build_peak); + void init (const string &str); + int open(); + void close(); + int setup_broadcast_info (jack_nframes_t when, struct tm&, time_t); }; }; /* namespace ARDOUR */ diff --git a/libs/ardour/ardour/source.h b/libs/ardour/ardour/source.h index 3781950fbf..f3133c71cd 100644 --- a/libs/ardour/ardour/source.h +++ b/libs/ardour/ardour/source.h @@ -21,166 +21,46 @@ #ifndef __ardour_source_h__ #define __ardour_source_h__ -#include -#include #include -#include - #include -#include - #include #include -#include - -using std::list; -using std::vector; -using std::string; namespace ARDOUR { -struct PeakData { - typedef Sample PeakDatum; - - PeakDatum min; - PeakDatum max; -}; - -const jack_nframes_t frames_per_peak = 256; - class Source : public Stateful, public sigc::trackable { public: - Source (bool announce=true); + Source (std::string name); Source (const XMLNode&); virtual ~Source (); - const string& name() const { return _name; } + std::string name() const { return _name; } + int set_name (std::string str, bool destructive); ARDOUR::id_t id() const { return _id; } - /* returns the number of items in this `source' */ - - virtual jack_nframes_t length() const { - return _length; - } - - virtual jack_nframes_t available_peaks (double zoom) const; - - virtual jack_nframes_t read (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const { - return 0; - } - - virtual jack_nframes_t write (Sample *src, jack_nframes_t cnt, char * workbuf) { - return 0; - } - - virtual float sample_rate () const { return 0; } - uint32_t use_cnt() const { return _use_cnt; } void use (); void release (); - virtual void mark_for_remove() = 0; - virtual void mark_streaming_write_completed () {} - time_t timestamp() const { return _timestamp; } void stamp (time_t when) { _timestamp = when; } - void set_captured_for (string str) { _captured_for = str; } - string captured_for() const { return _captured_for; } - - uint32_t read_data_count() const { return _read_data_count; } - uint32_t write_data_count() const { return _write_data_count; } - - int read_peaks (PeakData *peaks, jack_nframes_t npeaks, jack_nframes_t start, jack_nframes_t cnt, double samples_per_unit) const; - int build_peaks (); - bool peaks_ready (sigc::slot, sigc::connection&) const; - - static sigc::signal SourceCreated; - - sigc::signal GoingAway; - mutable sigc::signal PeaksReady; - mutable sigc::signal PeakRangeReady; - XMLNode& get_state (); int set_state (const XMLNode&); - static int start_peak_thread (); - static void stop_peak_thread (); - - int rename_peakfile (std::string newpath); - - static void set_build_missing_peakfiles (bool yn) { - _build_missing_peakfiles = yn; - } - static void set_build_peakfiles (bool yn) { - _build_peakfiles = yn; - } + sigc::signal GoingAway; protected: - static bool _build_missing_peakfiles; - static bool _build_peakfiles; - string _name; - uint32_t _use_cnt; - bool _peaks_built; - mutable Glib::Mutex _lock; - jack_nframes_t _length; - bool next_peak_clear_should_notify; - string peakpath; + uint32_t _use_cnt; time_t _timestamp; - string _captured_for; - - mutable uint32_t _read_data_count; // modified in read() - mutable uint32_t _write_data_count; // modified in write() - - int initialize_peakfile (bool newfile, string path); - void build_peaks_from_scratch (); - - int do_build_peak (jack_nframes_t, jack_nframes_t); - virtual jack_nframes_t read_unlocked (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const = 0; - virtual string peak_path(string audio_path) = 0; - - static pthread_t peak_thread; - static bool have_peak_thread; - static void* peak_thread_work(void*); - - static int peak_request_pipe[2]; - - struct PeakRequest { - enum Type { - Build, - Quit - }; - }; - - static vector pending_peak_sources; - static Glib::StaticMutex pending_peak_sources_lock; - - static void queue_for_peaks (Source&); - static void clear_queue_for_peaks (); - - struct PeakBuildRecord { - jack_nframes_t frame; - jack_nframes_t cnt; - - PeakBuildRecord (jack_nframes_t f, jack_nframes_t c) - : frame (f), cnt (c) {} - PeakBuildRecord (const PeakBuildRecord& other) { - frame = other.frame; - cnt = other.cnt; - } - }; - - list pending_peak_builds; private: ARDOUR::id_t _id; - - bool file_changed (string path); }; } diff --git a/libs/ardour/ardour/types.h b/libs/ardour/ardour/types.h index 3d7ab4b59a..a0a209b569 100644 --- a/libs/ardour/ardour/types.h +++ b/libs/ardour/ardour/types.h @@ -29,6 +29,7 @@ #include #include +#include #include #if __GNUC__ < 3 @@ -98,34 +99,7 @@ namespace ARDOUR { Normal, Destructive }; - - enum smpte_wrap_t { - smpte_wrap_none = 0, - smpte_wrap_frames, - smpte_wrap_seconds, - smpte_wrap_minutes, - smpte_wrap_hours - }; - - struct SMPTE_Time { - bool negative; - uint32_t hours; - uint32_t minutes; - uint32_t seconds; - uint32_t frames; - uint32_t subframes; // mostly not used - - SMPTE_Time() { - negative = false; - hours = 0; - minutes = 0; - seconds = 0; - frames = 0; - subframes = 0; - } - - }; - + struct BBT_Time { uint32_t bars; uint32_t beats; @@ -164,7 +138,7 @@ namespace ARDOUR { Type type; - SMPTE_Time smpte; + SMPTE::Time smpte; BBT_Time bbt; union { @@ -255,10 +229,18 @@ namespace ARDOUR { BWF, WAVE, WAVE64, + CAF, + AIFF, iXML, RF64 }; + struct PeakData { + typedef Sample PeakDatum; + + PeakDatum min; + PeakDatum max; + }; }; std::istream& operator>>(std::istream& o, ARDOUR::SampleFormat& sf); diff --git a/libs/ardour/diskstream.cc b/libs/ardour/audio_diskstream.cc similarity index 89% rename from libs/ardour/diskstream.cc rename to libs/ardour/audio_diskstream.cc index 90e8387f3f..69f00efe68 100644 --- a/libs/ardour/diskstream.cc +++ b/libs/ardour/audio_diskstream.cc @@ -15,7 +15,7 @@ along with this program; if not, write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - $Id$ + $Id: diskstream.cc 567 2006-06-07 14:54:12Z trutkin $ */ #include @@ -38,10 +38,10 @@ #include #include -#include +#include #include #include -#include +#include #include #include #include @@ -53,15 +53,16 @@ using namespace std; using namespace ARDOUR; +using namespace PBD; -jack_nframes_t DiskStream::disk_io_chunk_frames; +jack_nframes_t AudioDiskstream::disk_io_chunk_frames; -sigc::signal DiskStream::DiskStreamCreated; -sigc::signal*> DiskStream::DeleteSources; -sigc::signal DiskStream::DiskOverrun; -sigc::signal DiskStream::DiskUnderrun; +sigc::signal AudioDiskstream::AudioDiskstreamCreated; +sigc::signal*> AudioDiskstream::DeleteSources; +sigc::signal AudioDiskstream::DiskOverrun; +sigc::signal AudioDiskstream::DiskUnderrun; -DiskStream::DiskStream (Session &sess, const string &name, Flag flag) +AudioDiskstream::AudioDiskstream (Session &sess, const string &name, Flag flag) : _name (name), _session (sess) { @@ -74,10 +75,10 @@ DiskStream::DiskStream (Session &sess, const string &name, Flag flag) in_set_state = false; - DiskStreamCreated (this); /* EMIT SIGNAL */ + AudioDiskstreamCreated (this); /* EMIT SIGNAL */ } -DiskStream::DiskStream (Session& sess, const XMLNode& node) +AudioDiskstream::AudioDiskstream (Session& sess, const XMLNode& node) : _session (sess) { @@ -95,11 +96,11 @@ DiskStream::DiskStream (Session& sess, const XMLNode& node) use_destructive_playlist (); } - DiskStreamCreated (this); /* EMIT SIGNAL */ + AudioDiskstreamCreated (this); /* EMIT SIGNAL */ } void -DiskStream::init_channel (ChannelInfo &chan) +AudioDiskstream::init_channel (ChannelInfo &chan) { chan.playback_wrap_buffer = 0; chan.capture_wrap_buffer = 0; @@ -128,7 +129,7 @@ DiskStream::init_channel (ChannelInfo &chan) void -DiskStream::init (Flag f) +AudioDiskstream::init (Flag f) { _id = new_id(); _refcnt = 0; @@ -185,7 +186,7 @@ DiskStream::init (Flag f) } void -DiskStream::destroy_channel (ChannelInfo &chan) +AudioDiskstream::destroy_channel (ChannelInfo &chan) { if (chan.write_source) { chan.write_source->release (); @@ -211,7 +212,7 @@ DiskStream::destroy_channel (ChannelInfo &chan) chan.capture_buf = 0; } -DiskStream::~DiskStream () +AudioDiskstream::~AudioDiskstream () { Glib::Mutex::Lock lm (state_lock); @@ -227,7 +228,7 @@ DiskStream::~DiskStream () } void -DiskStream::handle_input_change (IOChange change, void *src) +AudioDiskstream::handle_input_change (IOChange change, void *src) { Glib::Mutex::Lock lm (state_lock); @@ -238,7 +239,7 @@ DiskStream::handle_input_change (IOChange change, void *src) } void -DiskStream::non_realtime_input_change () +AudioDiskstream::non_realtime_input_change () { { Glib::Mutex::Lock lm (state_lock); @@ -299,7 +300,7 @@ DiskStream::non_realtime_input_change () } void -DiskStream::get_input_sources () +AudioDiskstream::get_input_sources () { uint32_t ni = _io->n_inputs(); @@ -327,18 +328,18 @@ DiskStream::get_input_sources () } int -DiskStream::find_and_use_playlist (const string& name) +AudioDiskstream::find_and_use_playlist (const string& name) { Playlist* pl; AudioPlaylist* playlist; if ((pl = _session.get_playlist (name)) == 0) { - error << string_compose(_("DiskStream: Session doesn't know about a Playlist called \"%1\""), name) << endmsg; + error << string_compose(_("AudioDiskstream: Session doesn't know about a Playlist called \"%1\""), name) << endmsg; return -1; } if ((playlist = dynamic_cast (pl)) == 0) { - error << string_compose(_("DiskStream: Playlist \"%1\" isn't an audio playlist"), name) << endmsg; + error << string_compose(_("AudioDiskstream: Playlist \"%1\" isn't an audio playlist"), name) << endmsg; return -1; } @@ -346,7 +347,7 @@ DiskStream::find_and_use_playlist (const string& name) } int -DiskStream::use_playlist (AudioPlaylist* playlist) +AudioDiskstream::use_playlist (AudioPlaylist* playlist) { { Glib::Mutex::Lock lm (state_lock); @@ -370,9 +371,9 @@ DiskStream::use_playlist (AudioPlaylist* playlist) reset_write_sources (false); } - plstate_connection = _playlist->StateChanged.connect (mem_fun (*this, &DiskStream::playlist_changed)); - plmod_connection = _playlist->Modified.connect (mem_fun (*this, &DiskStream::playlist_modified)); - plgone_connection = _playlist->GoingAway.connect (mem_fun (*this, &DiskStream::playlist_deleted)); + plstate_connection = _playlist->StateChanged.connect (mem_fun (*this, &AudioDiskstream::playlist_changed)); + plmod_connection = _playlist->Modified.connect (mem_fun (*this, &AudioDiskstream::playlist_modified)); + plgone_connection = _playlist->GoingAway.connect (mem_fun (*this, &AudioDiskstream::playlist_deleted)); } if (!overwrite_queued) { @@ -387,7 +388,7 @@ DiskStream::use_playlist (AudioPlaylist* playlist) } void -DiskStream::playlist_deleted (Playlist* pl) +AudioDiskstream::playlist_deleted (Playlist* pl) { /* this catches an ordering issue with session destruction. playlists are destroyed before diskstreams. we have to invalidate any handles @@ -398,7 +399,7 @@ DiskStream::playlist_deleted (Playlist* pl) } int -DiskStream::use_new_playlist () +AudioDiskstream::use_new_playlist () { string newname; AudioPlaylist* playlist; @@ -422,14 +423,14 @@ DiskStream::use_new_playlist () } int -DiskStream::use_copy_playlist () +AudioDiskstream::use_copy_playlist () { if (destructive()) { return 0; } if (_playlist == 0) { - error << string_compose(_("DiskStream %1: there is no existing playlist to make a copy of!"), _name) << endmsg; + error << string_compose(_("AudioDiskstream %1: there is no existing playlist to make a copy of!"), _name) << endmsg; return -1; } @@ -447,7 +448,7 @@ DiskStream::use_copy_playlist () } void -DiskStream::setup_destructive_playlist () +AudioDiskstream::setup_destructive_playlist () { AudioRegion::SourceList srcs; @@ -462,7 +463,7 @@ DiskStream::setup_destructive_playlist () } void -DiskStream::use_destructive_playlist () +AudioDiskstream::use_destructive_playlist () { /* use the sources associated with the single full-extent region */ @@ -485,7 +486,7 @@ DiskStream::use_destructive_playlist () ChannelList::iterator chan; for (n = 0, chan = channels.begin(); chan != channels.end(); ++chan, ++n) { - (*chan).write_source = dynamic_cast(®ion->source (n)); + (*chan).write_source = dynamic_cast(®ion->source (n)); (*chan).write_source->set_allow_remove_if_empty (false); } @@ -493,14 +494,14 @@ DiskStream::use_destructive_playlist () } void -DiskStream::set_io (IO& io) +AudioDiskstream::set_io (IO& io) { _io = &io; set_align_style_from_io (); } int -DiskStream::set_name (string str, void *src) +AudioDiskstream::set_name (string str, void *src) { if (str != _name) { _playlist->set_name (str); @@ -518,7 +519,7 @@ DiskStream::set_name (string str, void *src) } void -DiskStream::set_speed (double sp) +AudioDiskstream::set_speed (double sp) { _session.request_diskstream_speed (*this, sp); @@ -527,7 +528,7 @@ DiskStream::set_speed (double sp) } bool -DiskStream::realtime_set_speed (double sp, bool global) +AudioDiskstream::realtime_set_speed (double sp, bool global) { bool changed = false; double new_speed = sp * _session.transport_speed(); @@ -561,7 +562,7 @@ DiskStream::realtime_set_speed (double sp, bool global) } void -DiskStream::non_realtime_set_speed () +AudioDiskstream::non_realtime_set_speed () { if (_buffer_reallocation_required) { @@ -584,14 +585,14 @@ DiskStream::non_realtime_set_speed () } void -DiskStream::prepare () +AudioDiskstream::prepare () { _processed = false; playback_distance = 0; } void -DiskStream::check_record_status (jack_nframes_t transport_frame, jack_nframes_t nframes, bool can_record) +AudioDiskstream::check_record_status (jack_nframes_t transport_frame, jack_nframes_t nframes, bool can_record) { int possibly_recording; int rolling; @@ -716,7 +717,7 @@ DiskStream::check_record_status (jack_nframes_t transport_frame, jack_nframes_t } int -DiskStream::process (jack_nframes_t transport_frame, jack_nframes_t nframes, jack_nframes_t offset, bool can_record, bool rec_monitors_input) +AudioDiskstream::process (jack_nframes_t transport_frame, jack_nframes_t nframes, jack_nframes_t offset, bool can_record, bool rec_monitors_input) { uint32_t n; ChannelList::iterator c; @@ -731,7 +732,7 @@ DiskStream::process (jack_nframes_t transport_frame, jack_nframes_t nframes, jac just return. this allows multiple routes that are taking input from this diskstream to call our ::process() method, but have this stuff only happen once. more commonly, it allows both - the AudioTrack that is using this DiskStream *and* the Session + the AudioTrack that is using this AudioDiskstream *and* the Session to call process() without problems. */ @@ -748,7 +749,7 @@ DiskStream::process (jack_nframes_t transport_frame, jack_nframes_t nframes, jac return 0; } - /* This lock is held until the end of DiskStream::commit, so these two functions + /* This lock is held until the end of AudioDiskstream::commit, so these two functions must always be called as a pair. The only exception is if this function returns a non-zero value, in which case, ::commit should not be called. */ @@ -1010,14 +1011,14 @@ DiskStream::process (jack_nframes_t transport_frame, jack_nframes_t nframes, jac } void -DiskStream::recover () +AudioDiskstream::recover () { state_lock.unlock(); _processed = false; } bool -DiskStream::commit (jack_nframes_t nframes) +AudioDiskstream::commit (jack_nframes_t nframes) { bool need_butler = false; @@ -1056,7 +1057,7 @@ DiskStream::commit (jack_nframes_t nframes) } void -DiskStream::set_pending_overwrite (bool yn) +AudioDiskstream::set_pending_overwrite (bool yn) { /* called from audio thread, so we can use the read ptr and playback sample as we wish */ @@ -1067,7 +1068,7 @@ DiskStream::set_pending_overwrite (bool yn) } int -DiskStream::overwrite_existing_buffers () +AudioDiskstream::overwrite_existing_buffers () { Sample* mixdown_buffer; float* gain_buffer; @@ -1110,7 +1111,7 @@ DiskStream::overwrite_existing_buffers () if (read ((*chan).playback_buf->buffer() + overwrite_offset, mixdown_buffer, gain_buffer, workbuf, start, to_read, *chan, n, reversed)) { - error << string_compose(_("DiskStream %1: when refilling, cannot read %2 from playlist at frame %3"), + error << string_compose(_("AudioDiskstream %1: when refilling, cannot read %2 from playlist at frame %3"), _id, size, playback_sample) << endmsg; goto out; } @@ -1121,7 +1122,7 @@ DiskStream::overwrite_existing_buffers () if (read ((*chan).playback_buf->buffer(), mixdown_buffer, gain_buffer, workbuf, start, cnt, *chan, n, reversed)) { - error << string_compose(_("DiskStream %1: when refilling, cannot read %2 from playlist at frame %3"), + error << string_compose(_("AudioDiskstream %1: when refilling, cannot read %2 from playlist at frame %3"), _id, size, playback_sample) << endmsg; goto out; } @@ -1139,7 +1140,7 @@ DiskStream::overwrite_existing_buffers () } int -DiskStream::seek (jack_nframes_t frame, bool complete_refill) +AudioDiskstream::seek (jack_nframes_t frame, bool complete_refill) { Glib::Mutex::Lock lm (state_lock); uint32_t n; @@ -1149,9 +1150,6 @@ DiskStream::seek (jack_nframes_t frame, bool complete_refill) for (n = 0, chan = channels.begin(); chan != channels.end(); ++chan, ++n) { (*chan).playback_buf->reset (); (*chan).capture_buf->reset (); - if ((*chan).write_source) { - (*chan).write_source->seek (frame); - } } playback_sample = frame; @@ -1167,7 +1165,7 @@ DiskStream::seek (jack_nframes_t frame, bool complete_refill) } int -DiskStream::can_internal_playback_seek (jack_nframes_t distance) +AudioDiskstream::can_internal_playback_seek (jack_nframes_t distance) { ChannelList::iterator chan; @@ -1180,7 +1178,7 @@ DiskStream::can_internal_playback_seek (jack_nframes_t distance) } int -DiskStream::internal_playback_seek (jack_nframes_t distance) +AudioDiskstream::internal_playback_seek (jack_nframes_t distance) { ChannelList::iterator chan; @@ -1195,7 +1193,7 @@ DiskStream::internal_playback_seek (jack_nframes_t distance) } int -DiskStream::read (Sample* buf, Sample* mixdown_buffer, float* gain_buffer, char * workbuf, jack_nframes_t& start, jack_nframes_t cnt, +AudioDiskstream::read (Sample* buf, Sample* mixdown_buffer, float* gain_buffer, char * workbuf, jack_nframes_t& start, jack_nframes_t cnt, ChannelInfo& channel_info, int channel, bool reversed) { jack_nframes_t this_read = 0; @@ -1253,7 +1251,7 @@ DiskStream::read (Sample* buf, Sample* mixdown_buffer, float* gain_buffer, char this_read = min(cnt,this_read); if (_playlist->read (buf+offset, mixdown_buffer, gain_buffer, workbuf, start, this_read, channel) != this_read) { - error << string_compose(_("DiskStream %1: cannot read %2 from playlist at frame %3"), _id, this_read, + error << string_compose(_("AudioDiskstream %1: cannot read %2 from playlist at frame %3"), _id, this_read, start) << endmsg; return -1; } @@ -1286,7 +1284,7 @@ DiskStream::read (Sample* buf, Sample* mixdown_buffer, float* gain_buffer, char } int -DiskStream::do_refill (Sample* mixdown_buffer, float* gain_buffer, char * workbuf) +AudioDiskstream::do_refill (Sample* mixdown_buffer, float* gain_buffer, char * workbuf) { int32_t ret = 0; jack_nframes_t to_read; @@ -1516,7 +1514,7 @@ DiskStream::do_refill (Sample* mixdown_buffer, float* gain_buffer, char * workbu } int -DiskStream::do_flush (char * workbuf, bool force_flush) +AudioDiskstream::do_flush (char * workbuf, bool force_flush) { uint32_t to_write; int32_t ret = 0; @@ -1620,7 +1618,7 @@ DiskStream::do_flush (char * workbuf, bool force_flush) } if ((!(*chan).write_source) || (*chan).write_source->write (vector.buf[0], to_write, workbuf) != to_write) { - error << string_compose(_("DiskStream %1: cannot write to disk"), _id) << endmsg; + error << string_compose(_("AudioDiskstream %1: cannot write to disk"), _id) << endmsg; return -1; } @@ -1637,7 +1635,7 @@ DiskStream::do_flush (char * workbuf, bool force_flush) to_write = min ((jack_nframes_t)(disk_io_chunk_frames - to_write), (jack_nframes_t) vector.len[1]); if ((*chan).write_source->write (vector.buf[1], to_write, workbuf) != to_write) { - error << string_compose(_("DiskStream %1: cannot write to disk"), _id) << endmsg; + error << string_compose(_("AudioDiskstream %1: cannot write to disk"), _id) << endmsg; return -1; } @@ -1653,13 +1651,13 @@ DiskStream::do_flush (char * workbuf, bool force_flush) } void -DiskStream::playlist_changed (Change ignored) +AudioDiskstream::playlist_changed (Change ignored) { playlist_modified (); } void -DiskStream::playlist_modified () +AudioDiskstream::playlist_modified () { if (!i_am_the_modifier && !overwrite_queued) { _session.request_overwrite_buffer (this); @@ -1668,7 +1666,7 @@ DiskStream::playlist_modified () } void -DiskStream::transport_stopped (struct tm& when, time_t twhen, bool abort_capture) +AudioDiskstream::transport_stopped (struct tm& when, time_t twhen, bool abort_capture) { uint32_t buffer_position; bool more_work = true; @@ -1680,7 +1678,7 @@ DiskStream::transport_stopped (struct tm& when, time_t twhen, bool abort_capture ChannelList::iterator chan; vector::iterator ci; uint32_t n = 0; - list* deletion_list; + list* deletion_list; bool mark_write_completed = false; finish_capture (true); @@ -1697,7 +1695,7 @@ DiskStream::transport_stopped (struct tm& when, time_t twhen, bool abort_capture case 1: break; case -1: - error << string_compose(_("DiskStream \"%1\": cannot flush captured data to disk!"), _name) << endmsg; + error << string_compose(_("AudioDiskstream \"%1\": cannot flush captured data to disk!"), _name) << endmsg; err++; } } @@ -1713,7 +1711,7 @@ DiskStream::transport_stopped (struct tm& when, time_t twhen, bool abort_capture ChannelList::iterator chan; - deletion_list = new list; + deletion_list = new list; for ( chan = channels.begin(); chan != channels.end(); ++chan) { @@ -1747,15 +1745,15 @@ DiskStream::transport_stopped (struct tm& when, time_t twhen, bool abort_capture for (n = 0, chan = channels.begin(); chan != channels.end(); ++chan, ++n) { - Source* s = (*chan).write_source; + AudioFileSource* s = (*chan).write_source; if (s) { - FileSource* fsrc; + AudioFileSource* fsrc; srcs.push_back (s); - if ((fsrc = dynamic_cast(s)) != 0) { + if ((fsrc = dynamic_cast(s)) != 0) { fsrc->update_header (capture_info.front()->start, when, twhen); } @@ -1817,7 +1815,7 @@ DiskStream::transport_stopped (struct tm& when, time_t twhen, bool abort_capture } catch (failed_constructor& err) { - error << _("DiskStream: could not create region for captured audio!") << endmsg; + error << _("AudioDiskstream: could not create region for captured audio!") << endmsg; continue; /* XXX is this OK? */ } @@ -1850,7 +1848,7 @@ DiskStream::transport_stopped (struct tm& when, time_t twhen, bool abort_capture } void -DiskStream::finish_capture (bool rec_monitors_input) +AudioDiskstream::finish_capture (bool rec_monitors_input) { was_recording = false; @@ -1899,7 +1897,7 @@ DiskStream::finish_capture (bool rec_monitors_input) } void -DiskStream::set_record_enabled (bool yn, void* src) +AudioDiskstream::set_record_enabled (bool yn, void* src) { bool rolling = _session.transport_speed() != 0.0f; @@ -1958,9 +1956,9 @@ DiskStream::set_record_enabled (bool yn, void* src) } XMLNode& -DiskStream::get_state () +AudioDiskstream::get_state () { - XMLNode* node = new XMLNode ("DiskStream"); + XMLNode* node = new XMLNode ("AudioDiskstream"); char buf[64]; LocaleGuard lg (X_("POSIX")); @@ -1984,7 +1982,7 @@ DiskStream::get_state () XMLNode* cs_child = new XMLNode (X_("CapturingSources")); XMLNode* cs_grandchild; - for (vector::iterator i = capturing_sources.begin(); i != capturing_sources.end(); ++i) { + for (vector::iterator i = capturing_sources.begin(); i != capturing_sources.end(); ++i) { cs_grandchild = new XMLNode (X_("file")); cs_grandchild->add_property (X_("path"), (*i)->path()); cs_child->add_child_nocopy (*cs_grandchild); @@ -2012,7 +2010,7 @@ DiskStream::get_state () } int -DiskStream::set_state (const XMLNode& node) +AudioDiskstream::set_state (const XMLNode& node) { const XMLProperty* prop; XMLNodeList nlist = node.children(); @@ -2137,14 +2135,14 @@ DiskStream::set_state (const XMLNode& node) } int -DiskStream::use_new_write_source (uint32_t n) +AudioDiskstream::use_new_write_source (uint32_t n) { if (!recordable()) { return 1; } if (n >= channels.size()) { - error << string_compose (_("DiskStream: channel %1 out of range"), n) << endmsg; + error << string_compose (_("AudioDiskstream: channel %1 out of range"), n) << endmsg; return -1; } @@ -2152,7 +2150,7 @@ DiskStream::use_new_write_source (uint32_t n) if (chan.write_source) { - if (FileSource::is_empty (chan.write_source->path())) { + if (AudioFileSource::is_empty (chan.write_source->path())) { chan.write_source->mark_for_remove (); chan.write_source->release(); delete chan.write_source; @@ -2163,7 +2161,7 @@ DiskStream::use_new_write_source (uint32_t n) } try { - if ((chan.write_source = _session.create_file_source (*this, n, destructive())) == 0) { + if ((chan.write_source = _session.create_audio_source_for_session (*this, n, destructive())) == 0) { throw failed_constructor(); } } @@ -2184,7 +2182,7 @@ DiskStream::use_new_write_source (uint32_t n) } void -DiskStream::reset_write_sources (bool mark_write_complete, bool force) +AudioDiskstream::reset_write_sources (bool mark_write_complete, bool force) { ChannelList::iterator chan; uint32_t n; @@ -2227,7 +2225,7 @@ DiskStream::reset_write_sources (bool mark_write_complete, bool force) } int -DiskStream::rename_write_sources () +AudioDiskstream::rename_write_sources () { ChannelList::iterator chan; uint32_t n; @@ -2243,7 +2241,7 @@ DiskStream::rename_write_sources () } void -DiskStream::set_block_size (jack_nframes_t nframes) +AudioDiskstream::set_block_size (jack_nframes_t nframes) { if (_session.get_block_size() > speed_buffer_size) { speed_buffer_size = _session.get_block_size(); @@ -2257,7 +2255,7 @@ DiskStream::set_block_size (jack_nframes_t nframes) } void -DiskStream::allocate_temporary_buffers () +AudioDiskstream::allocate_temporary_buffers () { /* make sure the wrap buffer is at least large enough to deal with the speeds up to 1.2, to allow for micro-variation @@ -2281,7 +2279,7 @@ DiskStream::allocate_temporary_buffers () } void -DiskStream::monitor_input (bool yn) +AudioDiskstream::monitor_input (bool yn) { for (ChannelList::iterator chan = channels.begin(); chan != channels.end(); ++chan) { @@ -2292,7 +2290,7 @@ DiskStream::monitor_input (bool yn) } void -DiskStream::set_capture_offset () +AudioDiskstream::set_capture_offset () { if (_io == 0) { /* can't capture, so forget it */ @@ -2303,13 +2301,13 @@ DiskStream::set_capture_offset () } void -DiskStream::set_persistent_align_style (AlignStyle a) +AudioDiskstream::set_persistent_align_style (AlignStyle a) { _persistent_alignment_style = a; } void -DiskStream::set_align_style_from_io () +AudioDiskstream::set_align_style_from_io () { bool have_physical = false; @@ -2334,7 +2332,7 @@ DiskStream::set_align_style_from_io () } void -DiskStream::set_align_style (AlignStyle a) +AudioDiskstream::set_align_style (AlignStyle a) { if (record_enabled() && _session.actively_recording()) { return; @@ -2348,7 +2346,7 @@ DiskStream::set_align_style (AlignStyle a) } int -DiskStream::add_channel () +AudioDiskstream::add_channel () { /* XXX need to take lock??? */ @@ -2368,7 +2366,7 @@ DiskStream::add_channel () } int -DiskStream::remove_channel () +AudioDiskstream::remove_channel () { if (channels.size() > 1) { /* XXX need to take lock??? */ @@ -2384,21 +2382,21 @@ DiskStream::remove_channel () } float -DiskStream::playback_buffer_load () const +AudioDiskstream::playback_buffer_load () const { return (float) ((double) channels.front().playback_buf->read_space()/ (double) channels.front().playback_buf->bufsize()); } float -DiskStream::capture_buffer_load () const +AudioDiskstream::capture_buffer_load () const { return (float) ((double) channels.front().capture_buf->write_space()/ (double) channels.front().capture_buf->bufsize()); } int -DiskStream::set_loop (Location *location) +AudioDiskstream::set_loop (Location *location) { if (location) { if (location->start() >= location->end()) { @@ -2414,7 +2412,7 @@ DiskStream::set_loop (Location *location) } jack_nframes_t -DiskStream::get_capture_start_frame (uint32_t n) +AudioDiskstream::get_capture_start_frame (uint32_t n) { Glib::Mutex::Lock lm (capture_info_lock); @@ -2427,7 +2425,7 @@ DiskStream::get_capture_start_frame (uint32_t n) } jack_nframes_t -DiskStream::get_captured_frames (uint32_t n) +AudioDiskstream::get_captured_frames (uint32_t n) { Glib::Mutex::Lock lm (capture_info_lock); @@ -2440,23 +2438,23 @@ DiskStream::get_captured_frames (uint32_t n) } void -DiskStream::punch_in () +AudioDiskstream::punch_in () { } void -DiskStream::punch_out () +AudioDiskstream::punch_out () { } int -DiskStream::use_pending_capture_data (XMLNode& node) +AudioDiskstream::use_pending_capture_data (XMLNode& node) { const XMLProperty* prop; XMLNodeList nlist = node.children(); XMLNodeIterator niter; - FileSource* fs; - FileSource* first_fs = 0; + AudioFileSource* fs; + AudioFileSource* first_fs = 0; AudioRegion::SourceList pending_sources; jack_nframes_t position; @@ -2476,7 +2474,10 @@ DiskStream::use_pending_capture_data (XMLNode& node) } try { - fs = new FileSource (prop->value(), _session.frame_rate(), true, Config->get_native_file_data_format()); + fs = new SndFileSource (prop->value(), + Config->get_native_file_data_format(), + Config->get_native_file_header_format(), + _session.frame_rate()); } catch (failed_constructor& err) { @@ -2543,13 +2544,13 @@ DiskStream::use_pending_capture_data (XMLNode& node) } void -DiskStream::set_roll_delay (jack_nframes_t nframes) +AudioDiskstream::set_roll_delay (jack_nframes_t nframes) { _roll_delay = nframes; } void -DiskStream::set_destructive (bool yn) +AudioDiskstream::set_destructive (bool yn) { if (yn != destructive()) { reset_write_sources (true, true); diff --git a/libs/ardour/audio_library.cc b/libs/ardour/audio_library.cc index bf462f7128..7f421e86c8 100644 --- a/libs/ardour/audio_library.cc +++ b/libs/ardour/audio_library.cc @@ -42,6 +42,7 @@ using namespace std; using namespace ARDOUR; +using namespace PBD; static char* SOUNDFILE = "http://ardour.org/ontology/Soundfile"; diff --git a/libs/ardour/audio_playlist.cc b/libs/ardour/audio_playlist.cc index 9f3c02ce43..bbbaf42fef 100644 --- a/libs/ardour/audio_playlist.cc +++ b/libs/ardour/audio_playlist.cc @@ -37,6 +37,7 @@ using namespace ARDOUR; using namespace sigc; using namespace std; +using namespace PBD; AudioPlaylist::State::~State () { diff --git a/libs/ardour/audio_track.cc b/libs/ardour/audio_track.cc index 30adc54d1a..ae24d3a577 100644 --- a/libs/ardour/audio_track.cc +++ b/libs/ardour/audio_track.cc @@ -23,10 +23,11 @@ #include #include -#include +#include #include #include #include +#include #include #include #include @@ -37,25 +38,26 @@ using namespace std; using namespace ARDOUR; +using namespace PBD; AudioTrack::AudioTrack (Session& sess, string name, Route::Flag flag, TrackMode mode) : Route (sess, name, 1, -1, -1, -1, flag), diskstream (0), _midi_rec_enable_control (*this, _session.midi_port()) { - DiskStream::Flag dflags = DiskStream::Flag (0); + AudioDiskstream::Flag dflags = AudioDiskstream::Flag (0); if (_flags & Hidden) { - dflags = DiskStream::Flag (dflags | DiskStream::Hidden); + dflags = AudioDiskstream::Flag (dflags | AudioDiskstream::Hidden); } else { - dflags = DiskStream::Flag (dflags | DiskStream::Recordable); + dflags = AudioDiskstream::Flag (dflags | AudioDiskstream::Recordable); } if (mode == Destructive) { - dflags = DiskStream::Flag (dflags | DiskStream::Destructive); + dflags = AudioDiskstream::Flag (dflags | AudioDiskstream::Destructive); } - DiskStream* ds = new DiskStream (_session, name, dflags); + AudioDiskstream* ds = new AudioDiskstream (_session, name, dflags); _declickable = true; _freeze_record.state = NoFreeze; @@ -64,6 +66,8 @@ AudioTrack::AudioTrack (Session& sess, string name, Route::Flag flag, TrackMode set_diskstream (*ds, this); + // session.SMPTEOffsetChanged.connect (mem_fun (*this, &AudioTrack::handle_smpte_offset_change)); + // we do this even though Route already did it in it's init reset_midi_control (_session.midi_port(), _session.get_midi_control()); @@ -90,6 +94,14 @@ AudioTrack::~AudioTrack () } } +#if 0 +void +AudioTrack::handle_smpte_offset_change () +{ + diskstream +} +#endif + int AudioTrack::deprecated_use_diskstream_connections () { @@ -143,7 +155,7 @@ AudioTrack::deprecated_use_diskstream_connections () } int -AudioTrack::set_diskstream (DiskStream& ds, void *src) +AudioTrack::set_diskstream (AudioDiskstream& ds, void *src) { if (diskstream) { diskstream->unref(); @@ -166,7 +178,7 @@ AudioTrack::set_diskstream (DiskStream& ds, void *src) diskstream->monitor_input (false); ic_connection.disconnect(); - ic_connection = input_changed.connect (mem_fun (*diskstream, &DiskStream::handle_input_change)); + ic_connection = input_changed.connect (mem_fun (*diskstream, &AudioDiskstream::handle_input_change)); diskstream_changed (src); /* EMIT SIGNAL */ @@ -176,7 +188,7 @@ AudioTrack::set_diskstream (DiskStream& ds, void *src) int AudioTrack::use_diskstream (string name) { - DiskStream *dstream; + AudioDiskstream *dstream; if ((dstream = _session.diskstream_by_name (name)) == 0) { error << string_compose(_("AudioTrack: diskstream \"%1\" not known by session"), name) << endmsg; @@ -189,7 +201,7 @@ AudioTrack::use_diskstream (string name) int AudioTrack::use_diskstream (id_t id) { - DiskStream *dstream; + AudioDiskstream *dstream; if ((dstream = _session.diskstream_by_id (id)) == 0) { error << string_compose(_("AudioTrack: diskstream \"%1\" not known by session"), id) << endmsg; @@ -899,23 +911,23 @@ AudioTrack::update_total_latency () void AudioTrack::bounce (InterThreadInfo& itt) { - vector srcs; - _session.write_one_track (*this, 0, _session.current_end_frame(), false, srcs, itt); + vector srcs; + _session.write_one_audio_track (*this, 0, _session.current_end_frame(), false, srcs, itt); } void AudioTrack::bounce_range (jack_nframes_t start, jack_nframes_t end, InterThreadInfo& itt) { - vector srcs; - _session.write_one_track (*this, start, end, false, srcs, itt); + vector srcs; + _session.write_one_audio_track (*this, start, end, false, srcs, itt); } void AudioTrack::freeze (InterThreadInfo& itt) { Insert* insert; - vector srcs; + vector srcs; string new_playlist_name; Playlist* new_playlist; string dir; @@ -950,7 +962,7 @@ AudioTrack::freeze (InterThreadInfo& itt) return; } - if (_session.write_one_track (*this, 0, _session.current_end_frame(), true, srcs, itt)) { + if (_session.write_one_audio_track (*this, 0, _session.current_end_frame(), true, srcs, itt)) { return; } diff --git a/libs/ardour/audioengine.cc b/libs/ardour/audioengine.cc index 87866e7b31..5a5e200531 100644 --- a/libs/ardour/audioengine.cc +++ b/libs/ardour/audioengine.cc @@ -40,6 +40,7 @@ using namespace std; using namespace ARDOUR; +using namespace PBD; jack_nframes_t Port::short_over_length = 2; jack_nframes_t Port::long_over_length = 10; @@ -91,12 +92,6 @@ _thread_init_callback (void *arg) */ PBD::ThreadCreatedWithRequestSize (pthread_self(), X_("Audioengine"), 4096); - -#ifdef VST_SUPPORT - if (Config->get_use_vst()) { - fst_adopt_thread (); - } -#endif } int @@ -229,9 +224,10 @@ AudioEngine::_freewheel_callback (int onoff, void *arg) int AudioEngine::process_callback (jack_nframes_t nframes) { + // CycleTimer ct ("AudioEngine::process"); Glib::Mutex::Lock tm (_process_lock, Glib::TRY_LOCK); jack_nframes_t next_processed_frames; - + /* handle wrap around of total frames counter */ if (max_frames - _processed_frames < nframes) { diff --git a/libs/ardour/audiofilesource.cc b/libs/ardour/audiofilesource.cc new file mode 100644 index 0000000000..1e13a29acc --- /dev/null +++ b/libs/ardour/audiofilesource.cc @@ -0,0 +1,662 @@ +/* + Copyright (C) 2006 Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + +*/ + +#include + +#include +#include +#include +#include + +#include +#include +#include +#include + +#include + +#include + +#include +#include +#include +#include +#include + +// if these headers come before sigc++ is included +// the parser throws ObjC++ errors. (nil is a keyword) +#ifdef HAVE_COREAUDIO +#include +#include +#include +#endif // HAVE_COREAUDIO + +#include "i18n.h" + +using namespace ARDOUR; +using namespace PBD; + +string AudioFileSource::peak_dir = ""; +string AudioFileSource::search_path; + +sigc::signal AudioFileSource::HeaderPositionOffsetChanged; +bool AudioFileSource::header_position_negative; +uint64_t AudioFileSource::header_position_offset; + +char AudioFileSource::bwf_country_code[3] = "US"; +char AudioFileSource::bwf_organization_code[4] = "LAS"; +char AudioFileSource::bwf_serial_number[13] = "000000000000"; + +AudioFileSource::AudioFileSource (string idstr, Flag flags) + : AudioSource (idstr), _flags (flags) +{ + /* constructor used for existing external to session files. file must exist already */ + + if (init (idstr, true)) { + throw failed_constructor (); + } + +} + +AudioFileSource::AudioFileSource (std::string path, Flag flags, SampleFormat samp_format, HeaderFormat hdr_format) + : AudioSource (path), _flags (flags) +{ + /* constructor used for new internal-to-session files. file cannot exist */ + + if (init (path, false)) { + throw failed_constructor (); + } +} + +AudioFileSource::AudioFileSource (const XMLNode& node) + : AudioSource (node), _flags (Flag (Writable|CanRename)) +{ + /* constructor used for existing internal-to-session files. file must exist */ + + if (set_state (node)) { + throw failed_constructor (); + } + + if (init (_name, true)) { + throw failed_constructor (); + } +} + +AudioFileSource::~AudioFileSource () +{ + if (removable()) { + unlink (_path.c_str()); + unlink (peakpath.c_str()); + } +} + +bool +AudioFileSource::removable () const +{ + return (_flags & Removable) && ((_flags & RemoveAtDestroy) || + ((_flags & RemovableIfEmpty) && is_empty (_path))); +} + +int +AudioFileSource::init (string pathstr, bool must_exist) +{ + bool is_new = false; + + _length = 0; + next_peak_clear_should_notify = false; + + if (!find (pathstr, must_exist, is_new)) { + cerr << "cannot find " << pathstr << " with me = " << must_exist << endl; + return -1; + } + + if (is_new && must_exist) { + return -1; + } + + return 0; +} + + +string +AudioFileSource::peak_path (string audio_path) +{ + return Session::peak_path_from_audio_path (audio_path); +} + +string +AudioFileSource::old_peak_path (string audio_path) +{ + /* XXX hardly bombproof! fix me */ + + struct stat stat_file; + struct stat stat_mount; + + string mp = mountpoint (audio_path); + + stat (audio_path.c_str(), &stat_file); + stat (mp.c_str(), &stat_mount); + + char buf[32]; +#ifdef __APPLE__ + snprintf (buf, sizeof (buf), "%u-%u-%d.peak", stat_mount.st_ino, stat_file.st_ino, channel); +#else + snprintf (buf, sizeof (buf), "%ld-%ld-%d.peak", stat_mount.st_ino, stat_file.st_ino, channel); +#endif + + string res = peak_dir; + res += buf; + + return res; +} + +#ifdef HAVE_COREAUDIO + +AudioFileSource* +AudioFileSource::create (const XMLNode& node) +{ + AudioFileSource* es = 0; + + if (node.property (X_("destructive")) != 0) { + + es = new DestructiveFileSource (node); + + } else { + + try { + es = new CoreAudioSource (node); + } + + + catch (failed_constructor& err) { + es = new SndFileSource (node); + } + } + + return es; +} + +#else + +AudioFileSource* +AudioFileSource::create (const XMLNode& node) +{ + if (node.property (X_("destructive")) != 0) { + + return new DestructiveFileSource (node); + + } else { + + return new SndFileSource (node); + } +} + +#endif // HAVE_COREAUDIO + +#ifdef HAVE_COREAUDIO +AudioFileSource* +AudioFileSource::create (const string& idstr) +{ + AudioFileSource* es = 0; + + try { + es = new CoreAudioSource (idstr); + } + + catch (failed_constructor& err) { + es = new SndFileSource (idstr); + } + + return es; +} + +#else + +AudioFileSource* +AudioFileSource::create (string idstr) +{ + return new SndFileSource (idstr); +} + +#endif // HAVE_COREAUDIO + +#ifdef HAVE_COREAUDIO +std::string +CFStringRefToStdString(CFStringRef stringRef) +{ + CFIndex size = + CFStringGetMaximumSizeForEncoding(CFStringGetLength(stringRef) , + kCFStringEncodingASCII); + char *buf = new char[size]; + + std::string result; + + if(CFStringGetCString(stringRef, buf, size, kCFStringEncodingASCII)) { + result = buf; + } + delete [] buf; + return result; +} +#endif // HAVE_COREAUDIO + +bool +AudioFileSource::get_soundfile_info (string path, SoundFileInfo& _info, string& error_msg) +{ +#ifdef HAVE_COREAUDIO + OSStatus err = noErr; + FSRef ref; + ExtAudioFileRef af = 0; + size_t size; + CFStringRef name; + + err = FSPathMakeRef ((UInt8*)path.c_str(), &ref, 0); + if (err != noErr) { + ExtAudioFileDispose (af); + goto libsndfile; + } + + err = ExtAudioFileOpen(&ref, &af); + if (err != noErr) { + ExtAudioFileDispose (af); + goto libsndfile; + } + + AudioStreamBasicDescription absd; + memset(&absd, 0, sizeof(absd)); + size = sizeof(AudioStreamBasicDescription); + err = ExtAudioFileGetProperty(af, + kExtAudioFileProperty_FileDataFormat, &size, &absd); + if (err != noErr) { + ExtAudioFileDispose (af); + goto libsndfile; + } + + _info.samplerate = absd.mSampleRate; + _info.channels = absd.mChannelsPerFrame; + + size = sizeof(_info.length); + err = ExtAudioFileGetProperty(af, kExtAudioFileProperty_FileLengthFrames, &size, &_info.length); + if (err != noErr) { + ExtAudioFileDispose (af); + goto libsndfile; + } + + size = sizeof(CFStringRef); + err = AudioFormatGetProperty( + kAudioFormatProperty_FormatName, sizeof(absd), &absd, &size, &name); + if (err != noErr) { + ExtAudioFileDispose (af); + goto libsndfile; + } + + _info.format_name = CFStringRefToStdString(name); + + ExtAudioFileDispose (af); + return true; + +libsndfile: +#endif // HAVE_COREAUDIO + + SNDFILE *sf; + SF_INFO sf_info; + + sf_info.format = 0; // libsndfile says to clear this before sf_open(). + + if ((sf = sf_open ((char*) path.c_str(), SFM_READ, &sf_info)) == 0) { + char errbuf[256]; + error_msg = sf_error_str (0, errbuf, sizeof (errbuf) - 1); + return false; + } + + sf_close (sf); + + _info.samplerate = sf_info.samplerate; + _info.channels = sf_info.channels; + _info.length = sf_info.frames; + _info.format_name = string_compose("Format: %1, %2", + sndfile_major_format(sf_info.format), + sndfile_minor_format(sf_info.format)); + return true; +} + +XMLNode& +AudioFileSource::get_state () +{ + XMLNode& root (AudioSource::get_state()); + char buf[16]; + snprintf (buf, sizeof (buf), "0x%x", (int)_flags); + root.add_property ("flags", buf); + return root; +} + +int +AudioFileSource::set_state (const XMLNode& node) +{ + const XMLProperty* prop; + + if (AudioSource::set_state (node)) { + return -1; + } + + if ((prop = node.property (X_("flags"))) != 0) { + + int ival; + sscanf (prop->value().c_str(), "0x%x", &ival); + _flags = Flag (ival); + + } else { + + _flags = Flag (0); + + } + + return 0; +} + +void +AudioFileSource::mark_for_remove () +{ + if (!writable()) { + return; + } + _flags = Flag (_flags | RemoveAtDestroy); +} + +void +AudioFileSource::mark_streaming_write_completed () +{ + if (!writable()) { + return; + } + + Glib::Mutex::Lock lm (_lock); + + next_peak_clear_should_notify = true; + + if (_peaks_built || pending_peak_builds.empty()) { + _peaks_built = true; + PeaksReady (); /* EMIT SIGNAL */ + } +} + +void +AudioFileSource::mark_take (string id) +{ + if (writable()) { + _take_id = id; + } +} + +int +AudioFileSource::move_to_trash (const string trash_dir_name) +{ + string newpath; + + if (!writable()) { + return -1; + } + + /* don't move the file across filesystems, just + stick it in the `trash_dir_name' directory + on whichever filesystem it was already on. + */ + + newpath = Glib::path_get_dirname (_path); + newpath = Glib::path_get_dirname (newpath); + + newpath += '/'; + newpath += trash_dir_name; + newpath += '/'; + newpath += Glib::path_get_basename (_path); + + if (access (newpath.c_str(), F_OK) == 0) { + + /* the new path already exists, try versioning */ + + char buf[PATH_MAX+1]; + int version = 1; + string newpath_v; + + snprintf (buf, sizeof (buf), "%s.%d", newpath.c_str(), version); + newpath_v = buf; + + while (access (newpath_v.c_str(), F_OK) == 0 && version < 999) { + snprintf (buf, sizeof (buf), "%s.%d", newpath.c_str(), ++version); + newpath_v = buf; + } + + if (version == 999) { + error << string_compose (_("there are already 1000 files with names like %1; versioning discontinued"), + newpath) + << endmsg; + } else { + newpath = newpath_v; + } + + } else { + + /* it doesn't exist, or we can't read it or something */ + + } + + if (::rename (_path.c_str(), newpath.c_str()) != 0) { + error << string_compose (_("cannot rename audio file source from %1 to %2 (%3)"), + _path, newpath, strerror (errno)) + << endmsg; + return -1; + } + + if (::unlink (peakpath.c_str()) != 0) { + error << string_compose (_("cannot remove peakfile %1 for %2 (%3)"), + peakpath, _path, strerror (errno)) + << endmsg; + /* try to back out */ + rename (newpath.c_str(), _path.c_str()); + return -1; + } + + _path = newpath; + peakpath = ""; + + /* file can not be removed twice, since the operation is not idempotent */ + + _flags = Flag (_flags & ~(RemoveAtDestroy|Removable|RemovableIfEmpty)); + + return 0; +} + +bool +AudioFileSource::find (string pathstr, bool must_exist, bool& isnew) +{ + string::size_type pos; + bool ret = false; + + isnew = false; + + /* clean up PATH:CHANNEL notation so that we are looking for the correct path */ + + if ((pos = pathstr.find_last_of (':')) == string::npos) { + pathstr = pathstr; + } else { + pathstr = pathstr.substr (0, pos); + } + + if (pathstr[0] != '/') { + + /* non-absolute pathname: find pathstr in search path */ + + vector dirs; + int cnt; + string fullpath; + string keeppath; + + if (search_path.length() == 0) { + error << _("FileSource: search path not set") << endmsg; + goto out; + } + + split (search_path, dirs, ':'); + + cnt = 0; + + for (vector::iterator i = dirs.begin(); i != dirs.end(); ++i) { + + fullpath = *i; + if (fullpath[fullpath.length()-1] != '/') { + fullpath += '/'; + } + fullpath += pathstr; + + if (access (fullpath.c_str(), R_OK) == 0) { + keeppath = fullpath; + ++cnt; + } + } + + if (cnt > 1) { + + error << string_compose (_("FileSource: \"%1\" is ambigous when searching %2\n\t"), pathstr, search_path) << endmsg; + goto out; + + } else if (cnt == 0) { + + if (must_exist) { + error << string_compose(_("Filesource: cannot find required file (%1): while searching %2"), pathstr, search_path) << endmsg; + goto out; + } else { + isnew = true; + } + } + + _name = pathstr; + _path = keeppath; + ret = true; + + } else { + + /* external files and/or very very old style sessions include full paths */ + + _path = pathstr; + _name = pathstr.substr (pathstr.find_last_of ('/') + 1); + + if (access (_path.c_str(), R_OK) != 0) { + + /* file does not exist or we cannot read it */ + + if (must_exist) { + error << string_compose(_("Filesource: cannot find required file (%1): %2"), _path, strerror (errno)) << endmsg; + goto out; + } + + if (errno != ENOENT) { + error << string_compose(_("Filesource: cannot check for existing file (%1): %2"), _path, strerror (errno)) << endmsg; + goto out; + } + + /* a new file */ + + isnew = true; + ret = true; + + } else { + + /* already exists */ + + ret = true; + } + } + + out: + return ret; +} + +void +AudioFileSource::set_search_path (string p) +{ + search_path = p; +} + +void +AudioFileSource::set_header_position_offset (jack_nframes_t offset, bool negative) +{ + time_t tnow; + + time (&tnow); + + header_position_offset = offset; + header_position_negative = negative; + HeaderPositionOffsetChanged (localtime (&tnow), tnow); /* EMIT SIGNAL */ +} + +void +AudioFileSource::set_timeline_position (jack_nframes_t pos) +{ + timeline_position = pos; +} + +void +AudioFileSource::handle_header_position_change (struct tm* now, time_t tnow) +{ + /* don't do this if the file has never had its header flushed to disk yet */ + + if (writable() && _timestamp) { + set_header_timeline_position (); + flush_header (); + } +} + +void +AudioFileSource::set_allow_remove_if_empty (bool yn) +{ + if (writable()) { + allow_remove_if_empty = yn; + } +} + +int +AudioFileSource::set_name (string newname, bool destructive) +{ + Glib::Mutex::Lock lm (_lock); + string oldpath = _path; + string newpath = Session::change_audio_path_by_name (oldpath, _name, newname, destructive); + + if (newpath.empty()) { + error << string_compose (_("programming error: %1"), "cannot generate a changed audio path") << endmsg; + return -1; + } + + if (rename (oldpath.c_str(), newpath.c_str()) != 0) { + error << string_compose (_("cannot rename audio file for %1 to %2"), _name, newpath) << endmsg; + return -1; + } + + _name = Glib::path_get_basename (newpath); + _path = newpath; + + return rename_peakfile (peak_path (_path)); +} + +bool +AudioFileSource::is_empty (string path) +{ + /* XXX fix me */ + + return false; +} + diff --git a/libs/ardour/audiofilter.cc b/libs/ardour/audiofilter.cc index c340bccb2c..a26d9674bd 100644 --- a/libs/ardour/audiofilter.cc +++ b/libs/ardour/audiofilter.cc @@ -22,7 +22,7 @@ #include #include -#include +#include #include #include #include @@ -30,6 +30,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; int AudioFilter::make_new_sources (AudioRegion& region, AudioRegion::SourceList& nsrcs) @@ -47,7 +48,10 @@ AudioFilter::make_new_sources (AudioRegion& region, AudioRegion::SourceList& nsr } try { - nsrcs.push_back (new FileSource (path, session.frame_rate(), false, Config->get_native_file_data_format())); + nsrcs.push_back (new SndFileSource (path, + Config->get_native_file_data_format(), + Config->get_native_file_header_format(), + session.frame_rate())); } catch (failed_constructor& err) { @@ -73,7 +77,10 @@ AudioFilter::finish (AudioRegion& region, AudioRegion::SourceList& nsrcs) now = localtime (&xnow); for (AudioRegion::SourceList::iterator si = nsrcs.begin(); si != nsrcs.end(); ++si) { - dynamic_cast((*si))->update_header (region.position(), *now, xnow); + AudioFileSource* afs = dynamic_cast(*si); + if (afs) { + afs->update_header (region.position(), *now, xnow); + } } /* create a new region */ diff --git a/libs/ardour/audioregion.cc b/libs/ardour/audioregion.cc index 21773d9222..6b118faa51 100644 --- a/libs/ardour/audioregion.cc +++ b/libs/ardour/audioregion.cc @@ -38,6 +38,7 @@ #include #include #include +#include #include "i18n.h" #include @@ -63,7 +64,7 @@ AudioRegionState::AudioRegionState (string why) { } -AudioRegion::AudioRegion (Source& src, jack_nframes_t start, jack_nframes_t length, bool announce) +AudioRegion::AudioRegion (AudioSource& src, jack_nframes_t start, jack_nframes_t length, bool announce) : Region (start, length, PBD::basename_nosuffix(src.name()), 0, Region::Flag(Region::DefaultFlags|Region::External)), _fade_in (0.0, 2.0, 1.0, false), _fade_out (0.0, 2.0, 1.0, false), @@ -89,7 +90,7 @@ AudioRegion::AudioRegion (Source& src, jack_nframes_t start, jack_nframes_t leng } } -AudioRegion::AudioRegion (Source& src, jack_nframes_t start, jack_nframes_t length, const string& name, layer_t layer, Flag flags, bool announce) +AudioRegion::AudioRegion (AudioSource& src, jack_nframes_t start, jack_nframes_t length, const string& name, layer_t layer, Flag flags, bool announce) : Region (start, length, name, layer, flags), _fade_in (0.0, 2.0, 1.0, false), _fade_out (0.0, 2.0, 1.0, false), @@ -150,7 +151,7 @@ AudioRegion::AudioRegion (const AudioRegion& other, jack_nframes_t offset, jack_ { /* create a new AudioRegion, that is part of an existing one */ - set unique_srcs; + set unique_srcs; for (SourceList::const_iterator i= other.sources.begin(); i != other.sources.end(); ++i) { sources.push_back (*i); @@ -209,7 +210,7 @@ AudioRegion::AudioRegion (const AudioRegion &other) { /* Pure copy constructor */ - set unique_srcs; + set unique_srcs; for (SourceList::const_iterator i = other.sources.begin(); i != other.sources.end(); ++i) { sources.push_back (*i); @@ -237,7 +238,7 @@ AudioRegion::AudioRegion (const AudioRegion &other) /* NOTE: no CheckNewRegion signal emitted here. This is the copy constructor */ } -AudioRegion::AudioRegion (Source& src, const XMLNode& node) +AudioRegion::AudioRegion (AudioSource& src, const XMLNode& node) : Region (node), _fade_in (0.0, 2.0, 1.0, false), _fade_out (0.0, 2.0, 1.0, false), @@ -268,7 +269,7 @@ AudioRegion::AudioRegion (SourceList& srcs, const XMLNode& node) { /* basic AudioRegion constructor */ - set unique_srcs; + set unique_srcs; for (SourceList::iterator i=srcs.begin(); i != srcs.end(); ++i) { sources.push_back (*i); @@ -1094,7 +1095,7 @@ void AudioRegion::lock_sources () { SourceList::iterator i; - set unique_srcs; + set unique_srcs; for (i = sources.begin(); i != sources.end(); ++i) { unique_srcs.insert (*i); @@ -1112,7 +1113,7 @@ void AudioRegion::unlock_sources () { SourceList::iterator i; - set unique_srcs; + set unique_srcs; for (i = sources.begin(); i != sources.end(); ++i) { unique_srcs.insert (*i); diff --git a/libs/ardour/audiosource.cc b/libs/ardour/audiosource.cc new file mode 100644 index 0000000000..add9364cad --- /dev/null +++ b/libs/ardour/audiosource.cc @@ -0,0 +1,899 @@ +/* + Copyright (C) 2000 Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + + $Id: source.cc 404 2006-03-17 17:39:21Z pauld $ +*/ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include + +#include + +#include "i18n.h" + +using namespace std; +using namespace ARDOUR; +using namespace PBD; + +sigc::signal AudioSource::AudioSourceCreated; +pthread_t AudioSource::peak_thread; +bool AudioSource::have_peak_thread = false; +vector AudioSource::pending_peak_sources; +Glib::Mutex* AudioSource::pending_peak_sources_lock = 0; +int AudioSource::peak_request_pipe[2]; + +bool AudioSource::_build_missing_peakfiles = false; +bool AudioSource::_build_peakfiles = false; + +AudioSource::AudioSource (string name) + : Source (name) +{ + if (pending_peak_sources_lock == 0) { + pending_peak_sources_lock = new Glib::Mutex; + } + + _peaks_built = false; + next_peak_clear_should_notify = true; + _read_data_count = 0; + _write_data_count = 0; +} + +AudioSource::AudioSource (const XMLNode& node) + : Source (node) +{ + if (pending_peak_sources_lock == 0) { + pending_peak_sources_lock = new Glib::Mutex; + } + + _peaks_built = false; + next_peak_clear_should_notify = true; + _read_data_count = 0; + _write_data_count = 0; + + if (set_state (node)) { + throw failed_constructor(); + } +} + +AudioSource::~AudioSource () +{ +} + +XMLNode& +AudioSource::get_state () +{ + XMLNode& node (Source::get_state()); + + if (_captured_for.length()) { + node.add_property ("captured-for", _captured_for); + } + + return node; +} + +int +AudioSource::set_state (const XMLNode& node) +{ + const XMLProperty* prop; + + Source::set_state (node); + + if ((prop = node.property ("captured-for")) != 0) { + _captured_for = prop->value(); + } + + return 0; +} + +/*********************************************************************** + PEAK FILE STUFF + ***********************************************************************/ + +void* +AudioSource::peak_thread_work (void* arg) +{ + PBD::ThreadCreated (pthread_self(), X_("Peak")); + struct pollfd pfd[1]; + + if (pending_peak_sources_lock == 0) { + pending_peak_sources_lock = new Glib::Mutex; + } + + Glib::Mutex::Lock lm (*pending_peak_sources_lock); + + while (true) { + + pfd[0].fd = peak_request_pipe[0]; + pfd[0].events = POLLIN|POLLERR|POLLHUP; + + pending_peak_sources_lock->unlock (); + + if (poll (pfd, 1, -1) < 0) { + + if (errno == EINTR) { + pending_peak_sources_lock->lock (); + continue; + } + + error << string_compose (_("poll on peak request pipe failed (%1)"), + strerror (errno)) + << endmsg; + break; + } + + if (pfd[0].revents & ~POLLIN) { + error << _("Error on peak thread request pipe") << endmsg; + break; + } + + if (pfd[0].revents & POLLIN) { + + char req; + + /* empty the pipe of all current requests */ + + while (1) { + size_t nread = ::read (peak_request_pipe[0], &req, sizeof (req)); + + if (nread == 1) { + switch ((PeakRequest::Type) req) { + + case PeakRequest::Build: + break; + + case PeakRequest::Quit: + pthread_exit_pbd (0); + /*NOTREACHED*/ + break; + + default: + break; + } + + } else if (nread == 0) { + break; + } else if (errno == EAGAIN) { + break; + } else { + fatal << _("Error reading from peak request pipe") << endmsg; + /*NOTREACHED*/ + } + } + } + + pending_peak_sources_lock->lock (); + + while (!pending_peak_sources.empty()) { + + AudioSource* s = pending_peak_sources.front(); + pending_peak_sources.erase (pending_peak_sources.begin()); + + pending_peak_sources_lock->unlock (); + s->build_peaks(); + pending_peak_sources_lock->lock (); + } + } + + pthread_exit_pbd (0); + /*NOTREACHED*/ + return 0; +} + +int +AudioSource::start_peak_thread () +{ + if (!_build_peakfiles) { + return 0; + } + + if (pipe (peak_request_pipe)) { + error << string_compose(_("Cannot create transport request signal pipe (%1)"), strerror (errno)) << endmsg; + return -1; + } + + if (fcntl (peak_request_pipe[0], F_SETFL, O_NONBLOCK)) { + error << string_compose(_("UI: cannot set O_NONBLOCK on peak request pipe (%1)"), strerror (errno)) << endmsg; + return -1; + } + + if (fcntl (peak_request_pipe[1], F_SETFL, O_NONBLOCK)) { + error << string_compose(_("UI: cannot set O_NONBLOCK on peak request pipe (%1)"), strerror (errno)) << endmsg; + return -1; + } + + if (pthread_create_and_store ("peak file builder", &peak_thread, 0, peak_thread_work, 0)) { + error << _("AudioSource: could not create peak thread") << endmsg; + return -1; + } + + have_peak_thread = true; + return 0; +} + +void +AudioSource::stop_peak_thread () +{ + if (!have_peak_thread) { + return; + } + + void* status; + + char c = (char) PeakRequest::Quit; + ::write (peak_request_pipe[1], &c, 1); + pthread_join (peak_thread, &status); +} + +void +AudioSource::queue_for_peaks (AudioSource& source) +{ + if (have_peak_thread) { + + Glib::Mutex::Lock lm (*pending_peak_sources_lock); + + source.next_peak_clear_should_notify = true; + + if (find (pending_peak_sources.begin(), + pending_peak_sources.end(), + &source) == pending_peak_sources.end()) { + pending_peak_sources.push_back (&source); + } + + char c = (char) PeakRequest::Build; + ::write (peak_request_pipe[1], &c, 1); + } +} + +void AudioSource::clear_queue_for_peaks () +{ + /* this is done to cancel a group of running peak builds */ + if (have_peak_thread) { + Glib::Mutex::Lock lm (*pending_peak_sources_lock); + pending_peak_sources.clear (); + } +} + + +bool +AudioSource::peaks_ready (sigc::slot the_slot, sigc::connection& conn) const +{ + bool ret; + Glib::Mutex::Lock lm (_lock); + + /* check to see if the peak data is ready. if not + connect the slot while still holding the lock. + */ + + if (!(ret = _peaks_built)) { + conn = PeaksReady.connect (the_slot); + } + + return ret; +} + +int +AudioSource::rename_peakfile (string newpath) +{ + /* caller must hold _lock */ + + string oldpath = peakpath; + + if (access (oldpath.c_str(), F_OK) == 0) { + if (rename (oldpath.c_str(), newpath.c_str()) != 0) { + error << string_compose (_("cannot rename peakfile for %1 from %2 to %3 (%4)"), _name, oldpath, newpath, strerror (errno)) << endmsg; + return -1; + } + } + + peakpath = newpath; + + return 0; +} + +int +AudioSource::initialize_peakfile (bool newfile, string audio_path) +{ + struct stat statbuf; + + peakpath = peak_path (audio_path); + + /* Nasty band-aid for older sessions that were created before we + used libsndfile for all audio files. + */ + + if (!newfile && access (peakpath.c_str(), R_OK) != 0) { + string str = old_peak_path (audio_path); + if (access (str.c_str(), R_OK) == 0) { + peakpath = str; + } + } + + if (newfile) { + + if (!_build_peakfiles) { + return 0; + } + + _peaks_built = false; + + } else { + + if (stat (peakpath.c_str(), &statbuf)) { + if (errno != ENOENT) { + /* it exists in the peaks dir, but there is some kind of error */ + + error << string_compose(_("AudioSource: cannot stat peakfile \"%1\""), peakpath) << endmsg; + return -1; + } + + } else { + + /* we found it in the peaks dir */ + } + + if (statbuf.st_size == 0) { + _peaks_built = false; + } else { + // Check if the audio file has changed since the peakfile was built. + struct stat stat_file; + int err = stat (audio_path.c_str(), &stat_file); + + if (!err && stat_file.st_mtime > statbuf.st_mtime){ + _peaks_built = false; + } else { + _peaks_built = true; + } + } + } + + if (!newfile && !_peaks_built && _build_missing_peakfiles && _build_peakfiles) { + build_peaks_from_scratch (); + } + + return 0; +} + +jack_nframes_t +AudioSource::read (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const +{ + Glib::Mutex::Lock lm (_lock); + return read_unlocked (dst, start, cnt, workbuf); +} + +jack_nframes_t +AudioSource::write (Sample *dst, jack_nframes_t cnt, char * workbuf) +{ + Glib::Mutex::Lock lm (_lock); + return write_unlocked (dst, cnt, workbuf); +} + +int +AudioSource::read_peaks (PeakData *peaks, jack_nframes_t npeaks, jack_nframes_t start, jack_nframes_t cnt, double samples_per_visual_peak) const +{ + Glib::Mutex::Lock lm (_lock); + double scale; + double expected_peaks; + PeakData::PeakDatum xmax; + PeakData::PeakDatum xmin; + int32_t to_read; + uint32_t nread; + jack_nframes_t zero_fill = 0; + int ret = -1; + PeakData* staging = 0; + Sample* raw_staging = 0; + char * workbuf = 0; + int peakfile = -1; + + expected_peaks = (cnt / (double) frames_per_peak); + scale = npeaks/expected_peaks; + +#if 0 + cerr << "======>RP: npeaks = " << npeaks + << " start = " << start + << " cnt = " << cnt + << " len = " << _length + << " samples_per_visual_peak =" << samples_per_visual_peak + << " expected was " << expected_peaks << " ... scale = " << scale + << " PD ptr = " << peaks + < _length - start) { + // cerr << "too close to end @ " << _length << " given " << start << " + " << cnt << endl; + cnt = _length - start; + jack_nframes_t old = npeaks; + npeaks = min ((jack_nframes_t) floor (cnt / samples_per_visual_peak), npeaks); + zero_fill = old - npeaks; + } + + // cerr << "actual npeaks = " << npeaks << " zf = " << zero_fill << endl; + + if (npeaks == cnt) { + + // cerr << "RAW DATA\n"; + + /* no scaling at all, just get the sample data and duplicate it for + both max and min peak values. + */ + + Sample* raw_staging = new Sample[cnt]; + workbuf = new char[cnt*4]; + + if (read_unlocked (raw_staging, start, cnt, workbuf) != cnt) { + error << _("cannot read sample data for unscaled peak computation") << endmsg; + return -1; + } + + for (jack_nframes_t i = 0; i < npeaks; ++i) { + peaks[i].max = raw_staging[i]; + peaks[i].min = raw_staging[i]; + } + + delete [] raw_staging; + delete [] workbuf; + return 0; + } + + if (scale == 1.0) { + + off_t first_peak_byte = (start / frames_per_peak) * sizeof (PeakData); + + /* open, read, close */ + + if ((peakfile = ::open (peakpath.c_str(), O_RDWR|O_CREAT, 0664)) < 0) { + error << string_compose(_("AudioSource: cannot open peakpath \"%1\" (%2)"), peakpath, strerror (errno)) << endmsg; + return -1; + } + + // cerr << "DIRECT PEAKS\n"; + + nread = ::pread (peakfile, peaks, sizeof (PeakData)* npeaks, first_peak_byte); + close (peakfile); + + if (nread != sizeof (PeakData) * npeaks) { + cerr << "AudioSource[" + << _name + << "]: cannot read peaks from peakfile! (read only " + << nread + << " not " + << npeaks + << "at sample " + << start + << " = byte " + << first_peak_byte + << ')' + << endl; + return -1; + } + + if (zero_fill) { + memset (&peaks[npeaks], 0, sizeof (PeakData) * zero_fill); + } + + return 0; + } + + + jack_nframes_t tnp; + + if (scale < 1.0) { + + // cerr << "DOWNSAMPLE\n"; + + /* the caller wants: + + - more frames-per-peak (lower resolution) than the peakfile, or to put it another way, + - less peaks than the peakfile holds for the same range + + So, read a block into a staging area, and then downsample from there. + + to avoid confusion, I'll refer to the requested peaks as visual_peaks and the peakfile peaks as stored_peaks + */ + + const uint32_t chunksize = (uint32_t) min (expected_peaks, 4096.0); + + staging = new PeakData[chunksize]; + + /* compute the rounded up frame position */ + + jack_nframes_t current_frame = start; + jack_nframes_t current_stored_peak = (jack_nframes_t) ceil (current_frame / (double) frames_per_peak); + uint32_t next_visual_peak = (uint32_t) ceil (current_frame / samples_per_visual_peak); + double next_visual_peak_frame = next_visual_peak * samples_per_visual_peak; + uint32_t stored_peak_before_next_visual_peak = (jack_nframes_t) next_visual_peak_frame / frames_per_peak; + uint32_t nvisual_peaks = 0; + uint32_t stored_peaks_read = 0; + uint32_t i = 0; + + /* handle the case where the initial visual peak is on a pixel boundary */ + + current_stored_peak = min (current_stored_peak, stored_peak_before_next_visual_peak); + + /* open ... close during out: handling */ + + if ((peakfile = ::open (peakpath.c_str(), O_RDWR|O_CREAT, 0664)) < 0) { + error << string_compose(_("AudioSource: cannot open peakpath \"%1\" (%2)"), peakpath, strerror (errno)) << endmsg; + return 0; + } + + while (nvisual_peaks < npeaks) { + + if (i == stored_peaks_read) { + + uint32_t start_byte = current_stored_peak * sizeof(PeakData); + tnp = min ((_length/frames_per_peak - current_stored_peak), (jack_nframes_t) expected_peaks); + to_read = min (chunksize, tnp); + + off_t fend = lseek (peakfile, 0, SEEK_END); + + if ((nread = ::pread (peakfile, staging, sizeof (PeakData) * to_read, start_byte)) + != sizeof (PeakData) * to_read) { + cerr << "AudioSource[" + << _name + << "]: cannot read peak data from peakfile (" + << (nread / sizeof(PeakData)) + << " peaks instead of " + << to_read + << ") (" + << strerror (errno) + << ')' + << " at start_byte = " << start_byte + << " _length = " << _length << " versus len = " << fend + << " expected maxpeaks = " << (_length - current_frame)/frames_per_peak + << " npeaks was " << npeaks + << endl; + goto out; + } + + i = 0; + stored_peaks_read = nread / sizeof(PeakData); + } + + xmax = -1.0; + xmin = 1.0; + + while ((i < stored_peaks_read) && (current_stored_peak <= stored_peak_before_next_visual_peak)) { + + xmax = max (xmax, staging[i].max); + xmin = min (xmin, staging[i].min); + ++i; + ++current_stored_peak; + --expected_peaks; + } + + peaks[nvisual_peaks].max = xmax; + peaks[nvisual_peaks].min = xmin; + ++nvisual_peaks; + ++next_visual_peak; + + //next_visual_peak_frame = min ((next_visual_peak * samples_per_visual_peak), (next_visual_peak_frame+samples_per_visual_peak) ); + next_visual_peak_frame = min ((double) start+cnt, (next_visual_peak_frame+samples_per_visual_peak) ); + stored_peak_before_next_visual_peak = (uint32_t) next_visual_peak_frame / frames_per_peak; + } + + if (zero_fill) { + memset (&peaks[npeaks], 0, sizeof (PeakData) * zero_fill); + } + + ret = 0; + + } else { + + // cerr << "UPSAMPLE\n"; + + /* the caller wants + + - less frames-per-peak (more resolution) + - more peaks than stored in the Peakfile + + So, fetch data from the raw source, and generate peak + data on the fly. + */ + + jack_nframes_t frames_read = 0; + jack_nframes_t current_frame = start; + jack_nframes_t i = 0; + jack_nframes_t nvisual_peaks = 0; + jack_nframes_t chunksize = (jack_nframes_t) min (cnt, (jack_nframes_t) 4096); + raw_staging = new Sample[chunksize]; + workbuf = new char[chunksize *4]; + + jack_nframes_t frame_pos = start; + double pixel_pos = floor (frame_pos / samples_per_visual_peak); + double next_pixel_pos = ceil (frame_pos / samples_per_visual_peak); + double pixels_per_frame = 1.0 / samples_per_visual_peak; + + xmin = 1.0; + xmax = -1.0; + + while (nvisual_peaks < npeaks) { + + if (i == frames_read) { + + to_read = min (chunksize, (_length - current_frame)); + + if ((frames_read = read_unlocked (raw_staging, current_frame, to_read, workbuf)) < 0) { + error << string_compose(_("AudioSource[%1]: peak read - cannot read %2 samples at offset %3") + , _name, to_read, current_frame) + << endmsg; + goto out; + } + + i = 0; + } + + xmax = max (xmax, raw_staging[i]); + xmin = min (xmin, raw_staging[i]); + ++i; + ++current_frame; + pixel_pos += pixels_per_frame; + + if (pixel_pos >= next_pixel_pos) { + + peaks[nvisual_peaks].max = xmax; + peaks[nvisual_peaks].min = xmin; + ++nvisual_peaks; + xmin = 1.0; + xmax = -1.0; + + next_pixel_pos = ceil (pixel_pos + 0.5); + } + } + + if (zero_fill) { + memset (&peaks[npeaks], 0, sizeof (PeakData) * zero_fill); + } + + ret = 0; + } + + out: + if (peakfile >= 0) { + close (peakfile); + } + + if (staging) { + delete [] staging; + } + + if (raw_staging) { + delete [] raw_staging; + } + + if (workbuf) { + delete [] workbuf; + } + + return ret; +} + +#undef DEBUG_PEAK_BUILD + +int +AudioSource::build_peaks () +{ + vector built; + int status = -1; + bool pr_signal = false; + list copy; + + { + Glib::Mutex::Lock lm (_lock); + copy = pending_peak_builds; + pending_peak_builds.clear (); + } + +#ifdef DEBUG_PEAK_BUILD + cerr << "build peaks with " << copy.size() << " requests pending\n"; +#endif + + for (list::iterator i = copy.begin(); i != copy.end(); ++i) { + + if ((status = do_build_peak ((*i)->frame, (*i)->cnt)) != 0) { + unlink (peakpath.c_str()); + break; + } + built.push_back (new PeakBuildRecord (*(*i))); + delete *i; + } + + { + Glib::Mutex::Lock lm (_lock); + + if (status == 0) { + _peaks_built = true; + + if (next_peak_clear_should_notify) { + next_peak_clear_should_notify = false; + pr_signal = true; + } + } + } + + if (status == 0) { + for (vector::iterator i = built.begin(); i != built.end(); ++i) { + PeakRangeReady ((*i)->frame, (*i)->cnt); /* EMIT SIGNAL */ + delete *i; + } + + if (pr_signal) { + PeaksReady (); /* EMIT SIGNAL */ + } + } + + return status; +} + +int +AudioSource::do_build_peak (jack_nframes_t first_frame, jack_nframes_t cnt) +{ + jack_nframes_t current_frame; + Sample buf[frames_per_peak]; + Sample xmin, xmax; + uint32_t peaki; + PeakData* peakbuf; + char * workbuf = 0; + jack_nframes_t frames_read; + jack_nframes_t frames_to_read; + off_t first_peak_byte; + int peakfile = -1; + int ret = -1; + +#ifdef DEBUG_PEAK_BUILD + cerr << pthread_self() << ": " << _name << ": building peaks for " << first_frame << " to " << first_frame + cnt - 1 << endl; +#endif + + first_peak_byte = (first_frame / frames_per_peak) * sizeof (PeakData); + +#ifdef DEBUG_PEAK_BUILD + cerr << "seeking to " << first_peak_byte << " before writing new peak data\n"; +#endif + + current_frame = first_frame; + peakbuf = new PeakData[(cnt/frames_per_peak)+1]; + peaki = 0; + + workbuf = new char[max(frames_per_peak, cnt) * 4]; + + if ((peakfile = ::open (peakpath.c_str(), O_RDWR|O_CREAT, 0664)) < 0) { + error << string_compose(_("AudioSource: cannot open peakpath \"%1\" (%2)"), peakpath, strerror (errno)) << endmsg; + return -1; + } + + while (cnt) { + + frames_to_read = min (frames_per_peak, cnt); + + /* lock for every read */ + + if ((frames_read = read (buf, current_frame, frames_to_read, workbuf)) != frames_to_read) { + error << string_compose(_("%1: could not write read raw data for peak computation (%2)"), _name, strerror (errno)) << endmsg; + goto out; + } + + xmin = buf[0]; + xmax = buf[0]; + + for (jack_nframes_t n = 1; n < frames_read; ++n) { + xmax = max (xmax, buf[n]); + xmin = min (xmin, buf[n]); + +// if (current_frame < frames_read) { +// cerr << "sample = " << buf[n] << " max = " << xmax << " min = " << xmin << " max of 2 = " << max (xmax, buf[n]) << endl; +// } + } + + peakbuf[peaki].max = xmax; + peakbuf[peaki].min = xmin; + peaki++; + + current_frame += frames_read; + cnt -= frames_read; + } + + if (::pwrite (peakfile, peakbuf, sizeof (PeakData) * peaki, first_peak_byte) != (ssize_t) (sizeof (PeakData) * peaki)) { + error << string_compose(_("%1: could not write peak file data (%2)"), _name, strerror (errno)) << endmsg; + goto out; + } + + ret = 0; + + out: + delete [] peakbuf; + if (peakfile >= 0) { + close (peakfile); + } + if (workbuf) + delete [] workbuf; + return ret; +} + +void +AudioSource::build_peaks_from_scratch () +{ + Glib::Mutex::Lock lp (_lock); + + next_peak_clear_should_notify = true; + pending_peak_builds.push_back (new PeakBuildRecord (0, _length)); + queue_for_peaks (*this); +} + +bool +AudioSource::file_changed (string path) +{ + struct stat stat_file; + struct stat stat_peak; + + int e1 = stat (path.c_str(), &stat_file); + int e2 = stat (peak_path(path).c_str(), &stat_peak); + + if (!e1 && !e2 && stat_file.st_mtime > stat_peak.st_mtime){ + return true; + } else { + return false; + } +} + +jack_nframes_t +AudioSource::available_peaks (double zoom_factor) const +{ + int peakfile; + off_t end; + + if (zoom_factor < frames_per_peak) { + return length(); // peak data will come from the audio file + } + + /* peak data comes from peakfile */ + + if ((peakfile = ::open (peakpath.c_str(), O_RDONLY)) < 0) { + error << string_compose(_("AudioSource: cannot open peakpath \"%1\" (%2)"), peakpath, strerror (errno)) << endmsg; + return 0; + } + + { + Glib::Mutex::Lock lm (_lock); + end = lseek (peakfile, 0, SEEK_END); + } + + close (peakfile); + + return (end/sizeof(PeakData)) * frames_per_peak; +} + +void +AudioSource::update_length (jack_nframes_t pos, jack_nframes_t cnt) +{ + if (pos + cnt > _length) { + _length = pos+cnt; + } +} + diff --git a/libs/ardour/auditioner.cc b/libs/ardour/auditioner.cc index ce7b9a3e6f..2f0b943c0e 100644 --- a/libs/ardour/auditioner.cc +++ b/libs/ardour/auditioner.cc @@ -20,7 +20,7 @@ #include -#include +#include #include #include #include diff --git a/libs/ardour/automation_event.cc b/libs/ardour/automation_event.cc index 17888c4a7c..3df7dd94f7 100644 --- a/libs/ardour/automation_event.cc +++ b/libs/ardour/automation_event.cc @@ -31,6 +31,7 @@ using namespace std; using namespace ARDOUR; using namespace sigc; +using namespace PBD; #if 0 static void dumpit (const AutomationList& al, string prefix = "") diff --git a/libs/ardour/configuration.cc b/libs/ardour/configuration.cc index b7b1d65815..fc708f805d 100644 --- a/libs/ardour/configuration.cc +++ b/libs/ardour/configuration.cc @@ -26,7 +26,7 @@ #include #include -#include +#include #include #include @@ -34,6 +34,7 @@ using namespace ARDOUR; using namespace std; +using namespace PBD; /* this is global so that we do not have to indirect through an object pointer to reference it. @@ -231,7 +232,7 @@ Configuration::set_state (const XMLNode& root) } } - DiskStream::set_disk_io_chunk_frames (minimum_disk_io_bytes.get() / sizeof (Sample)); + AudioDiskstream::set_disk_io_chunk_frames (minimum_disk_io_bytes.get() / sizeof (Sample)); return 0; } diff --git a/libs/ardour/connection.cc b/libs/ardour/connection.cc index 719751f7ba..fbfd02d509 100644 --- a/libs/ardour/connection.cc +++ b/libs/ardour/connection.cc @@ -28,6 +28,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; Connection::Connection (const XMLNode& node) { diff --git a/libs/ardour/control_protocol_manager.cc b/libs/ardour/control_protocol_manager.cc index 57a89cc2d9..c2fb188953 100644 --- a/libs/ardour/control_protocol_manager.cc +++ b/libs/ardour/control_protocol_manager.cc @@ -4,16 +4,14 @@ #include #include -#include "control_protocol.h" +#include #include #include - - - using namespace ARDOUR; using namespace std; +using namespace PBD; #include "i18n.h" diff --git a/libs/ardour/coreaudio_source.cc b/libs/ardour/coreaudio_source.cc index 67aaabfb88..1b0ee565e7 100644 --- a/libs/ardour/coreaudio_source.cc +++ b/libs/ardour/coreaudio_source.cc @@ -26,21 +26,22 @@ #include using namespace ARDOUR; +using namespace PBD; CoreAudioSource::CoreAudioSource (const XMLNode& node) - : ExternalSource (node) + : AudioFileSource (node) { init (_name, true); - SourceCreated (this); /* EMIT SIGNAL */ + AudioSourceCreated (this); /* EMIT SIGNAL */ } CoreAudioSource::CoreAudioSource (const string& idstr, bool build_peak) - : ExternalSource(idstr, build_peak) + : AudioFileSource(idstr, build_peak) { init (idstr, build_peak); if (build_peak) { - SourceCreated (this); /* EMIT SIGNAL */ + AudioSourceCreated (this); /* EMIT SIGNAL */ } } diff --git a/libs/ardour/crossfade.cc b/libs/ardour/crossfade.cc index 767fdd85e6..5d36c63f01 100644 --- a/libs/ardour/crossfade.cc +++ b/libs/ardour/crossfade.cc @@ -33,7 +33,7 @@ using namespace std; using namespace ARDOUR; -//using namespace sigc; +using namespace PBD; jack_nframes_t Crossfade::_short_xfade_length = 0; Change Crossfade::ActiveChanged = ARDOUR::new_change(); diff --git a/libs/ardour/curve.cc b/libs/ardour/curve.cc index a515c3a39a..977b6dfd7b 100644 --- a/libs/ardour/curve.cc +++ b/libs/ardour/curve.cc @@ -38,6 +38,7 @@ using namespace std; using namespace ARDOUR; using namespace sigc; +using namespace PBD; Curve::Curve (double minv, double maxv, double canv, bool nostate) : AutomationList (canv, nostate) diff --git a/libs/ardour/cycle_timer.cc b/libs/ardour/cycle_timer.cc index c48b7fb861..3031d5a7ec 100644 --- a/libs/ardour/cycle_timer.cc +++ b/libs/ardour/cycle_timer.cc @@ -24,6 +24,8 @@ #include "i18n.h" +using namespace PBD; + float CycleTimer::cycles_per_usec = 0; float diff --git a/libs/ardour/destructive_filesource.cc b/libs/ardour/destructive_filesource.cc index 9a4c2425e9..cce757509a 100644 --- a/libs/ardour/destructive_filesource.cc +++ b/libs/ardour/destructive_filesource.cc @@ -61,18 +61,15 @@ typedef off_t off64_t; using namespace std; using namespace ARDOUR; +using namespace PBD; gain_t* DestructiveFileSource::out_coefficient = 0; gain_t* DestructiveFileSource::in_coefficient = 0; jack_nframes_t DestructiveFileSource::xfade_frames = 64; -DestructiveFileSource::DestructiveFileSource (string path, jack_nframes_t rate, bool repair_first, SampleFormat samp_format) - : FileSource (path, rate, repair_first, samp_format) +DestructiveFileSource::DestructiveFileSource (string path, SampleFormat samp_format, HeaderFormat hdr_format, jack_nframes_t rate, Flag flags) + : SndFileSource (path, samp_format, hdr_format, rate, flags) { - if (out_coefficient == 0) { - setup_standard_crossfades (rate); - } - xfade_buf = new Sample[xfade_frames]; _capture_start = false; @@ -80,13 +77,9 @@ DestructiveFileSource::DestructiveFileSource (string path, jack_nframes_t rate, file_pos = 0; } -DestructiveFileSource::DestructiveFileSource (const XMLNode& node, jack_nframes_t rate) - : FileSource (node, rate) +DestructiveFileSource::DestructiveFileSource (const XMLNode& node) + : SndFileSource (node) { - if (out_coefficient == 0) { - setup_standard_crossfades (rate); - } - xfade_buf = new Sample[xfade_frames]; _capture_start = false; @@ -102,6 +95,10 @@ DestructiveFileSource::~DestructiveFileSource() void DestructiveFileSource::setup_standard_crossfades (jack_nframes_t rate) { + /* This static method is assumed to have been called by the Session + before any DFS's are created. + */ + xfade_frames = (jack_nframes_t) floor ((Config->get_destructive_xfade_msecs () / 1000.0) * rate); if (out_coefficient) { @@ -124,12 +121,6 @@ DestructiveFileSource::setup_standard_crossfades (jack_nframes_t rate) } } -int -DestructiveFileSource::seek (jack_nframes_t frame) -{ - return 0; -} - void DestructiveFileSource::mark_capture_start (jack_nframes_t pos) { @@ -188,7 +179,7 @@ DestructiveFileSource::crossfade (Sample* data, jack_nframes_t cnt, int fade_in, } if (file_cnt) { - if ((retval = file_read (xfade_buf, fade_position, file_cnt, workbuf)) != (ssize_t) file_cnt) { + if ((retval = write_float (xfade_buf, fade_position, file_cnt)) != (ssize_t) file_cnt) { if (retval >= 0 && errno == EAGAIN) { /* XXX - can we really trust that errno is meaningful here? yes POSIX, i'm talking to you. * short or no data there */ @@ -206,7 +197,7 @@ DestructiveFileSource::crossfade (Sample* data, jack_nframes_t cnt, int fade_in, } if (nofade && !fade_in) { - if (file_write (data, file_pos, nofade, workbuf) != (ssize_t) nofade) { + if (write_float (data, file_pos, nofade) != nofade) { error << string_compose(_("DestructiveFileSource: \"%1\" bad write (%2)"), _path, strerror (errno)) << endmsg; return 0; } @@ -248,14 +239,14 @@ DestructiveFileSource::crossfade (Sample* data, jack_nframes_t cnt, int fade_in, } if (xfade) { - if (file_write (xfade_buf, fade_position, xfade, workbuf) != (ssize_t) xfade) { + if (write_float (xfade_buf, fade_position, xfade) != xfade) { error << string_compose(_("DestructiveFileSource: \"%1\" bad write (%2)"), _path, strerror (errno)) << endmsg; return 0; } } if (fade_in && nofade) { - if (file_write (data + xfade, file_pos + xfade, nofade, workbuf) != (ssize_t) nofade) { + if (write_float (data + xfade, file_pos + xfade, nofade) != nofade) { error << string_compose(_("DestructiveFileSource: \"%1\" bad write (%2)"), _path, strerror (errno)) << endmsg; return 0; } @@ -265,96 +256,98 @@ DestructiveFileSource::crossfade (Sample* data, jack_nframes_t cnt, int fade_in, } jack_nframes_t -DestructiveFileSource::write (Sample* data, jack_nframes_t cnt, char * workbuf) +DestructiveFileSource::write_unlocked (Sample* data, jack_nframes_t cnt, char * workbuf) { - { - Glib::Mutex::Lock lm (_lock); + jack_nframes_t old_file_pos; + + if (!writable()) { + return 0; + } + + if (_capture_start && _capture_end) { + _capture_start = false; + _capture_end = false; - jack_nframes_t old_file_pos; - - if (_capture_start && _capture_end) { - _capture_start = false; - _capture_end = false; - - /* move to the correct location place */ - file_pos = capture_start_frame; - - // split cnt in half - jack_nframes_t subcnt = cnt / 2; - jack_nframes_t ofilepos = file_pos; - - // fade in - if (crossfade (data, subcnt, 1, workbuf) != subcnt) { - return 0; - } - - file_pos += subcnt; - Sample * tmpdata = data + subcnt; - - // fade out - subcnt = cnt - subcnt; - if (crossfade (tmpdata, subcnt, 0, workbuf) != subcnt) { - return 0; - } - - file_pos = ofilepos; // adjusted below + /* move to the correct location place */ + file_pos = capture_start_frame; + + // split cnt in half + jack_nframes_t subcnt = cnt / 2; + jack_nframes_t ofilepos = file_pos; + + // fade in + if (crossfade (data, subcnt, 1, workbuf) != subcnt) { + return 0; } - else if (_capture_start) { - _capture_start = false; - _capture_end = false; + + file_pos += subcnt; + Sample * tmpdata = data + subcnt; + + // fade out + subcnt = cnt - subcnt; + if (crossfade (tmpdata, subcnt, 0, workbuf) != subcnt) { + return 0; + } + + file_pos = ofilepos; // adjusted below + } + else if (_capture_start) { - /* move to the correct location place */ - file_pos = capture_start_frame; + _capture_start = false; + _capture_end = false; + + /* move to the correct location place */ + file_pos = capture_start_frame; + + if (crossfade (data, cnt, 1, workbuf) != cnt) { + return 0; + } + + } else if (_capture_end) { + + _capture_start = false; + _capture_end = false; + + if (crossfade (data, cnt, 0, workbuf) != cnt) { + return 0; + } + + } else { + + if (write_float (data, file_pos, cnt) != cnt) { + return 0; + } + } + + old_file_pos = file_pos; + update_length (file_pos, cnt); + file_pos += cnt; + + if (_build_peakfiles) { + PeakBuildRecord *pbr = 0; + + if (pending_peak_builds.size()) { + pbr = pending_peak_builds.back(); + } + + if (pbr && pbr->frame + pbr->cnt == old_file_pos) { - if (crossfade (data, cnt, 1, workbuf) != cnt) { - return 0; - } - - } else if (_capture_end) { - _capture_start = false; - _capture_end = false; - - if (crossfade (data, cnt, 0, workbuf) != cnt) { - return 0; - } + /* the last PBR extended to the start of the current write, + so just extend it again. + */ + + pbr->cnt += cnt; } else { - if (file_write(data, file_pos, cnt, workbuf) != (ssize_t) cnt) { - return 0; - } + pending_peak_builds.push_back (new PeakBuildRecord (old_file_pos, cnt)); } - - old_file_pos = file_pos; - if (file_pos + cnt > _length) { - _length = file_pos + cnt; - } - file_pos += cnt; - if (_build_peakfiles) { - PeakBuildRecord *pbr = 0; - - if (pending_peak_builds.size()) { - pbr = pending_peak_builds.back(); - } - - if (pbr && pbr->frame + pbr->cnt == old_file_pos) { - - /* the last PBR extended to the start of the current write, - so just extend it again. - */ - - pbr->cnt += cnt; - } else { - pending_peak_builds.push_back (new PeakBuildRecord (old_file_pos, cnt)); - } - - _peaks_built = false; - } + _peaks_built = false; } if (_build_peakfiles) { queue_for_peaks (*this); } - + return cnt; } @@ -367,7 +360,14 @@ DestructiveFileSource::last_capture_start_frame () const XMLNode& DestructiveFileSource::get_state () { - XMLNode& node = FileSource::get_state (); + XMLNode& node = AudioFileSource::get_state (); node.add_property (X_("destructive"), "true"); return node; } + +void +DestructiveFileSource::set_timeline_position (jack_nframes_t pos) +{ + /* destructive tracks always start at where our reference frame zero is */ + timeline_position = 0; +} diff --git a/libs/ardour/externalsource.cc b/libs/ardour/externalsource.cc deleted file mode 100644 index 7f478b6f53..0000000000 --- a/libs/ardour/externalsource.cc +++ /dev/null @@ -1,246 +0,0 @@ -/* - Copyright (C) 2006 Paul Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - -*/ - -#include -#include -#include - -#include - -#include -#include -#include -#include - -// if these headers come before sigc++ is included -// the parser throws ObjC++ errors. (nil is a keyword) -#ifdef HAVE_COREAUDIO -#include -#include -#include -#endif // HAVE_COREAUDIO - -#include "i18n.h" - -using namespace ARDOUR; - -string ExternalSource::peak_dir = ""; - -ExternalSource::ExternalSource (const XMLNode& node) - : Source (node) -{ -} - -ExternalSource::ExternalSource (const string& idstr, bool build_peak) - : Source(build_peak) -{ -} - -ExternalSource::~ExternalSource () -{ -} - -jack_nframes_t -ExternalSource::read_unlocked (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const -{ - return read (dst, start, cnt, workbuf); -} - -string -ExternalSource::peak_path (string audio_path) -{ - /* XXX hardly bombproof! fix me */ - - struct stat stat_file; - struct stat stat_mount; - - string mp = mountpoint (audio_path); - - stat (audio_path.c_str(), &stat_file); - stat (mp.c_str(), &stat_mount); - - char buf[32]; -#ifdef __APPLE__ - snprintf (buf, sizeof (buf), "%u-%u-%d.peak", stat_mount.st_ino, stat_file.st_ino, channel); -#else - snprintf (buf, sizeof (buf), "%ld-%ld-%d.peak", stat_mount.st_ino, stat_file.st_ino, channel); -#endif - - string res = peak_dir; - res += buf; - - return res; -} - -#ifdef HAVE_COREAUDIO - -ExternalSource* -ExternalSource::create (const XMLNode& node) -{ - ExternalSource* es = 0; - - try { - es = new CoreAudioSource (node); - } - - catch (failed_constructor& err) { - es = new SndFileSource (node); - } - - es = new SndFileSource (node); - - return es; -} - -#else - -ExternalSource* -ExternalSource::create (const XMLNode& node) -{ - return new SndFileSource (node); -} - -#endif // HAVE_COREAUDIO - -#ifdef HAVE_COREAUDIO -ExternalSource* -ExternalSource::create (const string& idstr, bool build_peak) -{ - ExternalSource* es = 0; - - try { - es = new CoreAudioSource (idstr, build_peak); - } - - catch (failed_constructor& err) { - es = new SndFileSource (idstr, build_peak); - } - - return es; -} - -#else - -ExternalSource* -ExternalSource::create (const string& idstr, bool build_peak) -{ - return new SndFileSource (idstr, build_peak); -} - -#endif // HAVE_COREAUDIO - -#ifdef HAVE_COREAUDIO -std::string -CFStringRefToStdString(CFStringRef stringRef) -{ - CFIndex size = - CFStringGetMaximumSizeForEncoding(CFStringGetLength(stringRef) , - kCFStringEncodingASCII); - char *buf = new char[size]; - - std::string result; - - if(CFStringGetCString(stringRef, buf, size, kCFStringEncodingASCII)) { - result = buf; - } - delete [] buf; - return result; -} -#endif // HAVE_COREAUDIO - -bool -ExternalSource::get_soundfile_info (string path, SoundFileInfo& _info, string& error_msg) -{ -#ifdef HAVE_COREAUDIO - OSStatus err = noErr; - FSRef ref; - ExtAudioFileRef af = 0; - size_t size; - CFStringRef name; - - err = FSPathMakeRef ((UInt8*)path.c_str(), &ref, 0); - if (err != noErr) { - ExtAudioFileDispose (af); - goto libsndfile; - } - - err = ExtAudioFileOpen(&ref, &af); - if (err != noErr) { - ExtAudioFileDispose (af); - goto libsndfile; - } - - AudioStreamBasicDescription absd; - memset(&absd, 0, sizeof(absd)); - size = sizeof(AudioStreamBasicDescription); - err = ExtAudioFileGetProperty(af, - kExtAudioFileProperty_FileDataFormat, &size, &absd); - if (err != noErr) { - ExtAudioFileDispose (af); - goto libsndfile; - } - - _info.samplerate = absd.mSampleRate; - _info.channels = absd.mChannelsPerFrame; - - size = sizeof(_info.length); - err = ExtAudioFileGetProperty(af, kExtAudioFileProperty_FileLengthFrames, &size, &_info.length); - if (err != noErr) { - ExtAudioFileDispose (af); - goto libsndfile; - } - - size = sizeof(CFStringRef); - err = AudioFormatGetProperty( - kAudioFormatProperty_FormatName, sizeof(absd), &absd, &size, &name); - if (err != noErr) { - ExtAudioFileDispose (af); - goto libsndfile; - } - - _info.format_name = CFStringRefToStdString(name); - - ExtAudioFileDispose (af); - return true; - -libsndfile: -#endif // HAVE_COREAUDIO - - SNDFILE *sf; - SF_INFO sf_info; - - sf_info.format = 0; // libsndfile says to clear this before sf_open(). - - if ((sf = sf_open ((char*) path.c_str(), SFM_READ, &sf_info)) == 0) { - char errbuf[256]; - error_msg = sf_error_str (0, errbuf, sizeof (errbuf) - 1); - return false; - } - - sf_close (sf); - - _info.samplerate = sf_info.samplerate; - _info.channels = sf_info.channels; - _info.length = sf_info.frames; - _info.format_name = string_compose("Format: %1, %2", - sndfile_major_format(sf_info.format), - sndfile_minor_format(sf_info.format)); - - return true; -} diff --git a/libs/ardour/filesource.cc b/libs/ardour/filesource.cc deleted file mode 100644 index 63a9a3d014..0000000000 --- a/libs/ardour/filesource.cc +++ /dev/null @@ -1,1513 +0,0 @@ -/* - Copyright (C) 2000 Paul Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ -*/ - -#include - -/* This is is very hacky way to get pread and pwrite declarations. - First, include so that we can avoid its #undef __USE_UNIX98. - Then define __USE_UNIX98, include , and then undef it - again. If #define _XOPEN_SOURCE actually worked, I'd use that, but - despite claims in the header that it does, it doesn't. - - features.h isn't available on osx and it compiles fine without it. -*/ - -#ifdef HAVE_FEATURES_H -#include -#endif - -#if __GNUC__ >= 3 -// #define _XOPEN_SOURCE 500 -#include -#else -#define __USE_UNIX98 -#include -#undef __USE_UNIX98 -#endif - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include /* for rename(2) */ - -#include - -#include - -#include -#include - -#include -#include -#include -#include -#include -#include -#include - -#include "i18n.h" - -using namespace ARDOUR; - -string prepare_string(string& regex); - -char FileSource::bwf_country_code[3] = "us"; -char FileSource::bwf_organization_code[4] = "las"; -char FileSource::bwf_serial_number[13] = "000000000000"; -string FileSource::search_path; - -#undef WE_ARE_BIGENDIAN -#ifdef __BIG_ENDIAN__ -#define WE_ARE_BIGENDIAN true -#else -#define WE_ARE_BIGENDIAN false -#endif - -#define Swap_32(value) \ - (((((uint32_t)value)<<24) & 0xFF000000) | \ - ((((uint32_t)value)<< 8) & 0x00FF0000) | \ - ((((uint32_t)value)>> 8) & 0x0000FF00) | \ - ((((uint32_t)value)>>24) & 0x000000FF)) - -#define Swap_16(value) \ - (((((uint16_t)value)>> 8) & 0x000000FF) | \ - ((((uint16_t)value)<< 8) & 0x0000FF00)) - - -void -FileSource::set_search_path (string p) -{ - search_path = p; -} - -FileSource::FileSource (string pathstr, jack_nframes_t rate, bool repair_first, SampleFormat samp_format) -{ - /* constructor used when the file cannot already exist or might be damaged */ - _sample_format = samp_format; - if (samp_format == FormatInt24) { - _sample_size = 3; - } else { - _sample_size = sizeof(float); - } - - if (repair_first && repair (pathstr, rate)) { - throw failed_constructor (); - } - - if (init (pathstr, false, rate)) { - throw failed_constructor (); - } - - SourceCreated (this); /* EMIT SIGNAL */ -} - -FileSource::FileSource (const XMLNode& node, jack_nframes_t rate) - : Source (node) -{ - _sample_format = FormatFloat; - _sample_size = sizeof(float); - - if (set_state (node)) { - throw failed_constructor(); - } - - /* constructor used when the file must already exist */ - - if (init (_name, true, rate)) { - throw failed_constructor (); - } - - SourceCreated (this); /* EMIT SIGNAL */ -} - -int -FileSource::init (string pathstr, bool must_exist, jack_nframes_t rate) -{ - bool new_file = false; - int ret = -1; - PathScanner scanner; - - /* all native files end in .wav. this lets us discard - SndFileSource paths, which have ":N" at the end to - indicate which channel to read from, as well as any - other kind of non-native file. obviously, there - are more subtle checks later on. - */ - - if (pathstr.length() < 4 || pathstr.rfind (".wav") != pathstr.length() - 4) { - return ret; - } - - is_bwf = false; - _length = 0; - fd = -1; - remove_at_unref = false; - next_peak_clear_should_notify = false; - allow_remove_if_empty = true; - - if (pathstr[0] != '/') { - - /* find pathstr in search path */ - - if (search_path.length() == 0) { - error << _("FileSource: search path not set") << endmsg; - goto out; - } - - /* force exact match on the filename component by prefixing the regexp. - otherwise, "Drums-2.wav" matches "Comp_Drums-2.wav". - */ - - string regexp = "^"; - regexp += prepare_string(pathstr); - regexp += '$'; - - vector* result = scanner (search_path, regexp, false, true, -1); - - if (result == 0 || result->size() == 0) { - error << string_compose (_("FileSource: \"%1\" not found when searching %2 using %3"), - pathstr, search_path, regexp) << endmsg; - goto out; - } - - if (result->size() > 1) { - string msg = string_compose (_("FileSource: \"%1\" is ambigous when searching %2\n\t"), pathstr, search_path); - vector::iterator x = result->begin(); - - while (true) { - msg += *(*x); - ++x; - - if (x == result->end()) { - break; - } - - msg += "\n\t"; - } - - error << msg << endmsg; - goto out; - } - - _name = pathstr; - _path = *(result->front()); - - vector_delete (result); - delete result; - - } else { - - /* old style sessions include full paths */ - - _path = pathstr; - _name = pathstr.substr (pathstr.find_last_of ('/') + 1); - - } - - if (access (_path.c_str(), F_OK) != 0) { - if (must_exist) { - error << string_compose(_("Filesource: cannot find required file (%1): %2"), _path, strerror (errno)) << endmsg; - goto out; - - } - - if (errno == ENOENT) { - new_file = true; - } else { - error << string_compose(_("Filesource: cannot check for existing file (%1): %2"), _path, strerror (errno)) << endmsg; - goto out; - } - } - - if ((fd = open64 (_path.c_str(), O_RDWR|O_CREAT, 0644)) < 0) { - error << string_compose(_("FileSource: could not open \"%1\": (%2)"), _path, strerror (errno)) << endmsg; - goto out; - } - - /* if there was no timestamp available via XML, - then get it from the filesystem. - */ - - if (_timestamp == 0) { - struct stat statbuf; - - fstat (fd, &statbuf); - _timestamp = statbuf.st_mtime; - } - - if (lseek (fd, 0, SEEK_END) == 0) { - new_file = true; - } - - /* check that its a RIFF/WAVE format file */ - - if (new_file) { - - switch (Config->get_native_file_header_format()) { - case BWF: - is_bwf = true; - break; - default: - is_bwf = false; - break; - } - - if (fill_header (rate)) { - error << string_compose (_("FileSource: cannot write header in %1"), _path) << endmsg; - goto out; - } - - struct tm* now; - time_t xnow; - - time (&xnow); - now = localtime (&xnow); - - update_header (0, *now, xnow); - - } else { - - if (discover_chunks (must_exist)) { - error << string_compose (_("FileSource: cannot locate chunks in %1"), _path) << endmsg; - goto out; - } - - if (read_header (must_exist)) { - error << string_compose (_("FileSource: cannot read header in %1"), _path) << endmsg; - goto out; - } - - if (check_header (rate, must_exist)) { - error << string_compose (_("FileSource: cannot check header in %1"), _path) << endmsg; - goto out; - } - - compute_header_size (); - } - - if ((ret = initialize_peakfile (new_file, _path))) { - error << string_compose (_("FileSource: cannot initialize peakfile for %1 as %2"), _path, peakpath) << endmsg; - } - - out: - if (ret) { - - if (fd >= 0) { - close (fd); - } - - if (new_file) { - unlink (_path.c_str()); - } - } - - return ret; - -} - -FileSource::~FileSource () -{ - GoingAway (this); /* EMIT SIGNAL */ - - if (fd >= 0) { - - if (remove_at_unref || (is_empty (_path) && allow_remove_if_empty)) { - unlink (_path.c_str()); - unlink (peakpath.c_str()); - } - - close (fd); - } -} - -void -FileSource::set_allow_remove_if_empty (bool yn) -{ - allow_remove_if_empty = yn; -} - -int -FileSource::set_name (string newname, bool destructive) -{ - Glib::Mutex::Lock lm (_lock); - string oldpath = _path; - string newpath = Session::change_audio_path_by_name (oldpath, _name, newname, destructive); - - if (newpath.empty()) { - error << string_compose (_("programming error: %1"), "cannot generate a changed audio path") << endmsg; - return -1; - } - - if (rename (oldpath.c_str(), newpath.c_str()) != 0) { - error << string_compose (_("cannot rename audio file for %1 to %2"), _name, newpath) << endmsg; - return -1; - } - - _name = Glib::path_get_basename (newpath); - _path = newpath; - - return rename_peakfile (peak_path (_path)); -} - -string -FileSource::peak_path (string audio_path) -{ - return Session::peak_path_from_audio_path (audio_path); -} - -int -FileSource::discover_chunks (bool silent) -{ - WAVEChunk rw; - off64_t end; - off64_t offset; - char null_terminated_id[5]; - bool doswap = false; - - if ((end = lseek (fd, 0, SEEK_END)) < 0) { - error << _("FileSource: cannot seek to end of file") << endmsg; - return -1; - } - - if (::pread64 (fd, &rw, sizeof (rw), 0) != sizeof (rw)) { - error << _("FileSource: cannot read RIFF/WAVE chunk from file") << endmsg; - return -1; - } - - if (memcmp (rw.id, "RIFF", 4) == 0 && memcmp (rw.text, "WAVE", 4) == 0) { - header.bigendian = false; - } - else if (memcmp(rw.id, "RIFX", 4) == 0 && memcmp (rw.text, "WAVE", 4) == 0) { - header.bigendian = true; - } - else { - if (!silent) { - error << string_compose (_("FileSource %1: not a RIFF/WAVE file"), _path) << endmsg; - } - return -1; - } - - null_terminated_id[4] = '\0'; - - /* OK, its a RIFF/WAVE file. Find each chunk */ - - doswap = header.bigendian != WE_ARE_BIGENDIAN; - - if (doswap) { - swap_endian(rw); - } - - - - memcpy (null_terminated_id, rw.id, 4); - chunk_info.push_back (ChunkInfo (null_terminated_id, rw.size, 0)); - - offset = sizeof (rw); - - while (offset < end) { - - GenericChunk this_chunk; - - if (::pread64 (fd, &this_chunk, sizeof (this_chunk), offset) != sizeof (this_chunk)) { - error << _("FileSource: can't read a chunk") << endmsg; - return -1; - } - - if (doswap) { - swap_endian(this_chunk); - } - - memcpy (null_terminated_id, this_chunk.id, 4); - - /* do sanity check and possible correction to legacy ardour RIFF wavs - created on big endian platforms. after swapping, the size field will not be - in range for the fmt chunk - */ - if ((memcmp(null_terminated_id, "fmt ", 4) == 0 || memcmp(null_terminated_id, "bext", 4) == 0) - && !header.bigendian && (this_chunk.size > 700 || this_chunk.size < 0)) - { - warning << _("filesource: correcting mis-written RIFF file to become a RIFX: ") << name() << endmsg; - - memcpy (&rw.id, "RIFX", 4); - ::pwrite64 (fd, &rw.id, 4, 0); - header.bigendian = true; - // fix wave chunk already read - swap_endian(rw); - - doswap = header.bigendian != WE_ARE_BIGENDIAN; - - // now reset offset and continue the loop - // to reread all the chunks - chunk_info.clear(); - memcpy (null_terminated_id, rw.id, 4); - chunk_info.push_back (ChunkInfo (null_terminated_id, rw.size, 0)); - offset = sizeof (rw); - continue; - } - - - if (end != 44) - if ((memcmp(null_terminated_id, "data", 4) == 0)) - if ((this_chunk.size == 0) || (this_chunk.size > (end - offset))) - this_chunk.size = end - offset; - - chunk_info.push_back (ChunkInfo (null_terminated_id, this_chunk.size, offset)); - - /* skip to the next chunk */ - - offset += sizeof(GenericChunk) + this_chunk.size; - } - - return 0; -} - -void -FileSource::swap_endian (GenericChunk & chunk) const -{ - chunk.size = Swap_32(chunk.size); -} - -void -FileSource::swap_endian (FMTChunk & chunk) const -{ - chunk.size = Swap_32(chunk.size); - - chunk.formatTag = Swap_16(chunk.formatTag); - chunk.nChannels = Swap_16(chunk.nChannels); - chunk.nSamplesPerSec = Swap_32(chunk.nSamplesPerSec); - chunk.nAvgBytesPerSec = Swap_32(chunk.nAvgBytesPerSec); - chunk.nBlockAlign = Swap_16(chunk.nBlockAlign); - chunk.nBitsPerSample = Swap_16(chunk.nBitsPerSample); -} - -void -FileSource::swap_endian (BroadcastChunk & chunk) const -{ - chunk.size = Swap_32(chunk.size); - - chunk.time_reference_low = Swap_32(chunk.time_reference_low); - chunk.time_reference_high = Swap_32(chunk.time_reference_high); - chunk.version = Swap_16(chunk.version); -} - -void FileSource::swap_endian (Sample *buf, jack_nframes_t cnt) const -{ - for (jack_nframes_t n=0; n < cnt; ++n) { - uint32_t * tmp = (uint32_t *) &buf[n]; - *tmp = Swap_32(*tmp); - } -} - - -FileSource::ChunkInfo* -FileSource::lookup_chunk (string what) -{ - for (vector::iterator i = chunk_info.begin(); i != chunk_info.end(); ++i) { - if ((*i).name == what) { - return &*i; - } - } - return 0; -} - -int -FileSource::fill_header (jack_nframes_t rate) -{ - /* RIFF/WAVE */ - - if (WE_ARE_BIGENDIAN) { - memcpy (header.wave.id, "RIFX", 4); - header.bigendian = true; - } - else { - memcpy (header.wave.id, "RIFF", 4); - header.bigendian = false; - } - header.wave.size = 0; /* file size */ - memcpy (header.wave.text, "WAVE", 4); - - /* BROADCAST WAVE EXTENSION */ - - if (is_bwf) { - - /* fill the entire BWF header with nulls */ - - memset (&header.bext, 0, sizeof (header.bext)); - - memcpy (header.bext.id, "bext", 4); - - snprintf (header.bext.description, sizeof (header.bext.description), "%s", "ambiguity is clearer than precision."); - - struct passwd *pwinfo; - struct utsname utsinfo; - - if ((pwinfo = getpwuid (getuid())) == 0) { - error << string_compose(_("FileSource: cannot get user information for BWF header (%1)"), strerror(errno)) << endmsg; - return -1; - } - if (uname (&utsinfo)) { - error << string_compose(_("FileSource: cannot get host information for BWF header (%1)"), strerror(errno)) << endmsg; - return -1; - } - - snprintf (header.bext.originator, sizeof (header.bext.originator), "ardour:%s:%s:%s:%s:%s)", - pwinfo->pw_gecos, - utsinfo.nodename, - utsinfo.sysname, - utsinfo.release, - utsinfo.version); - - header.bext.version = 1; - - /* XXX do something about this field */ - - snprintf (header.bext.umid, sizeof (header.bext.umid), "%s", "fnord"); - - /* add some coding history */ - - char buf[64]; - - /* encode: PCM,rate,mono,24bit,ardour-version - - Note that because we use JACK, there is no way to tell - what the original bit depth of the signal was. - */ - - snprintf (buf, sizeof(buf), "F=%u,A=PCM,M=mono,W=24,T=ardour-%d.%d.%d", - rate, - libardour_major_version, - libardour_minor_version, - libardour_micro_version); - - header.coding_history.push_back (buf); - - /* initial size reflects coding history + "\r\n" */ - - header.bext.size = sizeof (BroadcastChunk) - sizeof (GenericChunk) + strlen (buf) + 2; - } - - memcpy (header.format.id, "fmt ", 4); - header.format.size = sizeof (FMTChunk) - sizeof (GenericChunk); - - if (_sample_format == FormatInt24) { - header.format.formatTag = 1; // PCM - header.format.nBlockAlign = 3; - header.format.nBitsPerSample = 24; - } - else { - header.format.formatTag = 3; /* little-endian IEEE float format */ - header.format.nBlockAlign = 4; - header.format.nBitsPerSample = 32; - } - header.format.nChannels = 1; /* mono */ - header.format.nSamplesPerSec = rate; - header.format.nAvgBytesPerSec = rate * _sample_size; - - /* DATA */ - - memcpy (header.data.id, "data", 4); - header.data.size = 0; - - return 0; -} - -void -FileSource::compute_header_size () -{ - off64_t end_of_file; - int32_t coding_history_size = 0; - - end_of_file = lseek (fd, 0, SEEK_END); - - if (is_bwf) { - - /* include the coding history */ - - for (vector::iterator i = header.coding_history.begin(); i != header.coding_history.end(); ++i) { - coding_history_size += (*i).length() + 2; // include "\r\n"; - } - - header.bext.size = sizeof (BroadcastChunk) - sizeof (GenericChunk) + coding_history_size; - data_offset = bwf_header_size + coding_history_size; - - } else { - data_offset = wave_header_size; - } - - if (end_of_file == 0) { - - /* newfile condition */ - - if (is_bwf) { - /* include "WAVE" then all the chunk sizes (bext, fmt, data) */ - header.wave.size = 4 + sizeof (BroadcastChunk) + coding_history_size + sizeof (FMTChunk) + sizeof (GenericChunk); - } else { - /* include "WAVE" then all the chunk sizes (fmt, data) */ - header.wave.size = 4 + sizeof (FMTChunk) + sizeof (GenericChunk); - } - - header.data.size = 0; - - } else { - - header.wave.size = end_of_file - 8; /* size of initial RIFF+size pseudo-chunk */ - header.data.size = end_of_file - data_offset; - } -} - -int -FileSource::update_header (jack_nframes_t when, struct tm& now, time_t tnow) -{ - Glib::Mutex::Lock lm (_lock); - - if (is_bwf) { - /* random code is 9 digits */ - - int random_code = random() % 999999999; - - snprintf (header.bext.originator_reference, sizeof (header.bext.originator_reference), "%2s%3s%12s%02d%02d%02d%9d", - bwf_country_code, - bwf_organization_code, - bwf_serial_number, - now.tm_hour, - now.tm_min, - now.tm_sec, - random_code); - - snprintf (header.bext.origination_date, sizeof (header.bext.origination_date), "%4d-%02d-%02d", - 1900 + now.tm_year, - now.tm_mon, - now.tm_mday); - - snprintf (header.bext.origination_time, sizeof (header.bext.origination_time), "%02d-%02d-%02d", - now.tm_hour, - now.tm_min, - now.tm_sec); - - header.bext.time_reference_high = 0; - header.bext.time_reference_low = when; - } - - compute_header_size (); - - if (write_header()) { - error << string_compose(_("FileSource[%1]: cannot update data size: %2"), _path, strerror (errno)) << endmsg; - return -1; - } - - stamp (tnow); - - return 0; -} - -int -FileSource::read_header (bool silent) -{ - /* we already have the chunk info, so just load up whatever we have */ - - ChunkInfo* info; - - if (header.bigendian == false && (info = lookup_chunk ("RIFF")) == 0) { - error << _("FileSource: can't find RIFF chunk info") << endmsg; - return -1; - } - else if (header.bigendian == true && (info = lookup_chunk ("RIFX")) == 0) { - error << _("FileSource: can't find RIFX chunk info") << endmsg; - return -1; - } - - - /* just fill this chunk/header ourselves, disk i/o is stupid */ - - if (header.bigendian) { - memcpy (header.wave.id, "RIFX", 4); - } - else { - memcpy (header.wave.id, "RIFF", 4); - } - header.wave.size = 0; - memcpy (header.wave.text, "WAVE", 4); - - if ((info = lookup_chunk ("bext")) != 0) { - - is_bwf = true; - - if (::pread64 (fd, &header.bext, sizeof (header.bext), info->offset) != sizeof (header.bext)) { - error << _("FileSource: can't read RIFF chunk") << endmsg; - return -1; - } - - if (read_broadcast_data (*info)) { - return -1; - } - } - - if ((info = lookup_chunk ("fmt ")) == 0) { - error << _("FileSource: can't find format chunk info") << endmsg; - return -1; - } - - if (::pread64 (fd, &header.format, sizeof (header.format), info->offset) != sizeof (header.format)) { - error << _("FileSource: can't read format chunk") << endmsg; - return -1; - } - - if (header.bigendian != WE_ARE_BIGENDIAN) { - swap_endian (header.format); - } - - if ((info = lookup_chunk ("data")) == 0) { - error << _("FileSource: can't find data chunk info") << endmsg; - return -1; - } - - if (::pread64 (fd, &header.data, sizeof (header.data), info->offset) != sizeof (header.data)) { - error << _("FileSource: can't read data chunk") << endmsg; - return -1; - } - - if (header.bigendian != WE_ARE_BIGENDIAN) { - swap_endian (header.data); - } - - return 0; -} - -int -FileSource::read_broadcast_data (ChunkInfo& info) -{ - int32_t coding_history_size; - - if (::pread64 (fd, (char *) &header.bext, sizeof (header.bext), info.offset + sizeof (GenericChunk)) != sizeof (header.bext)) { - error << string_compose(_("FileSource: cannot read Broadcast Wave data from existing audio file \"%1\" (%2)"), - _path, strerror (errno)) << endmsg; - return -1; - } - - if (header.bigendian != WE_ARE_BIGENDIAN) { - swap_endian (header.bext); - } - - if (info.size > sizeof (header.bext)) { - - coding_history_size = info.size - (sizeof (header.bext) - sizeof (GenericChunk)); - - char data[coding_history_size]; - - if (::pread64 (fd, data, coding_history_size, info.offset + sizeof (BroadcastChunk)) != coding_history_size) { - error << string_compose(_("FileSource: cannot read Broadcast Wave coding history from audio file \"%1\" (%2)"), - _path, strerror (errno)) << endmsg; - return -1; - } - - /* elements of the coding history are divided by \r\n */ - - char *p = data; - char *end = data + coding_history_size; - string tmp; - - while (p < end) { - if (*p == '\r' && (p+1) != end && *(p+1) == '\n') { - if (tmp.length()) { - header.coding_history.push_back (tmp); - tmp = ""; - } - p += 2; - } else { - tmp += *p; - p++; - } - } - } - - return 0; -} - -int -FileSource::check_header (jack_nframes_t rate, bool silent) -{ - if (header.format.formatTag == 1 && header.format.nBitsPerSample == 24) { - // 24 bit PCM - _sample_format = FormatInt24; - _sample_size = 3; - } else if (header.format.formatTag == 3) { - /* IEEE float */ - _sample_format = FormatFloat; - _sample_size = 4; - } - else { - if (!silent) { - error << string_compose(_("FileSource \"%1\" does not use valid sample format.\n" - "This is probably a programming error."), _path) << endmsg; - } - return -1; - } - - /* compute the apparent length of the data */ - - data_offset = 0; - - for (vector::iterator i = chunk_info.begin(); i != chunk_info.end();) { - vector::iterator n; - - n = i; - ++n; - - if ((*i).name == "data") { - - data_offset = (*i).offset + sizeof (GenericChunk); - - if (n == chunk_info.end()) { - off64_t end_of_file; - end_of_file = lseek (fd, 0, SEEK_END); - - _length = end_of_file - data_offset; - - } else { - _length = (*n).offset - data_offset; - } - - _length /= sizeof (Sample); - - break; - } - - i = n; - } - - if (data_offset == 0) { - error << string_compose(_("FileSource \"%1\" has no \"data\" chunk"), _path) << endmsg; - return -1; - } - - if (_length * sizeof (Sample) != (jack_nframes_t) header.data.size) { - warning << string_compose(_("%1: data length in header (%2) differs from implicit size in file (%3)"), - _path, header.data.size, _length * sizeof (Sample)) << endmsg; - } - -// if ((jack_nframes_t) header.format.nSamplesPerSec != rate) { -// warning << string_compose(_("\"%1\" has a sample rate of %2 instead of %3 as used by this session"), -// _path, header.format.nSamplesPerSec, rate) << endmsg; -// } - - return 0; -} - -float -FileSource::sample_rate () const -{ - return header.format.nSamplesPerSec; -} - -int -FileSource::write_header() -{ - off64_t pos; - - /* write RIFF/WAVE boilerplate */ - - pos = 0; - - WAVEChunk wchunk = header.wave; - - if (header.bigendian != WE_ARE_BIGENDIAN) { - swap_endian(wchunk); - } - - if (::pwrite64 (fd, (char *) &wchunk, sizeof (wchunk), pos) != sizeof (wchunk)) { - error << string_compose(_("FileSource: cannot write WAVE chunk: %1"), strerror (errno)) << endmsg; - return -1; - } - - pos += sizeof (header.wave); - - if (is_bwf) { - - /* write broadcast chunk data without copy history */ - - BroadcastChunk bchunk = header.bext; - if (header.bigendian != WE_ARE_BIGENDIAN) { - swap_endian (bchunk); - } - - if (::pwrite64 (fd, (char *) &bchunk, sizeof (bchunk), pos) != sizeof (bchunk)) { - return -1; - } - - pos += sizeof (header.bext); - - /* write copy history */ - - for (vector::iterator i = header.coding_history.begin(); i != header.coding_history.end(); ++i) { - string x; - - x = *i; - x += "\r\n"; - - if (::pwrite64 (fd, x.c_str(), x.length(), pos) != (int32_t) x.length()) { - return -1; - } - - pos += x.length(); - } - } - - /* write fmt and data chunks */ - FMTChunk fchunk = header.format; - if (header.bigendian != WE_ARE_BIGENDIAN) { - swap_endian (fchunk); - } - - if (::pwrite64 (fd, (char *) &fchunk, sizeof (fchunk), pos) != sizeof (fchunk)) { - error << string_compose(_("FileSource: cannot write format chunk: %1"), strerror (errno)) << endmsg; - return -1; - } - - pos += sizeof (header.format); - - GenericChunk dchunk = header.data; - if (header.bigendian != WE_ARE_BIGENDIAN) { - swap_endian (dchunk); - } - - if (::pwrite64 (fd, (char *) &dchunk, sizeof (dchunk), pos) != sizeof (dchunk)) { - error << string_compose(_("FileSource: cannot data chunk: %1"), strerror (errno)) << endmsg; - return -1; - } - - return 0; -} - -void -FileSource::mark_for_remove () -{ - remove_at_unref = true; -} - -jack_nframes_t -FileSource::read (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const -{ - Glib::Mutex::Lock lm (_lock); - return read_unlocked (dst, start, cnt, workbuf); -} - -jack_nframes_t -FileSource::read_unlocked (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const -{ - jack_nframes_t file_cnt; - - if (start > _length) { - - /* read starts beyond end of data, just memset to zero */ - - file_cnt = 0; - - } else if (start + cnt > _length) { - - /* read ends beyond end of data, read some, memset the rest */ - - file_cnt = _length - start; - - } else { - - /* read is entirely within data */ - - file_cnt = cnt; - } - - if (file_cnt) { - if (file_read(dst, start, file_cnt, workbuf) != (ssize_t) file_cnt) { - return 0; - } - } - - if (file_cnt != cnt) { - jack_nframes_t delta = cnt - file_cnt; - memset (dst+file_cnt, 0, sizeof (Sample) * delta); - } - - return cnt; -} - -jack_nframes_t -FileSource::write (Sample *data, jack_nframes_t cnt, char * workbuf) -{ - { - Glib::Mutex::Lock lm (_lock); - - jack_nframes_t oldlen; - int32_t frame_pos = _length; - - if (file_write(data, frame_pos, cnt, workbuf) != (ssize_t) cnt) { - return 0; - } - - oldlen = _length; - _length += cnt; - - if (_build_peakfiles) { - PeakBuildRecord *pbr = 0; - - if (pending_peak_builds.size()) { - pbr = pending_peak_builds.back(); - } - - if (pbr && pbr->frame + pbr->cnt == oldlen) { - - /* the last PBR extended to the start of the current write, - so just extend it again. - */ - - pbr->cnt += cnt; - } else { - pending_peak_builds.push_back (new PeakBuildRecord (oldlen, cnt)); - } - - _peaks_built = false; - } - - } - - - if (_build_peakfiles) { - queue_for_peaks (*this); - } - - return cnt; -} - -ssize_t -FileSource::write_float(Sample *data, jack_nframes_t framepos, jack_nframes_t cnt, char * workbuf) -{ - int32_t byte_cnt = cnt * _sample_size; - int32_t byte_pos = data_offset + (framepos * _sample_size); - ssize_t retval; - - if ((retval = ::pwrite64 (fd, (char *) data, byte_cnt, byte_pos)) != (ssize_t) byte_cnt) { - error << string_compose(_("FileSource: \"%1\" bad write (%2)"), _path, strerror (errno)) << endmsg; - if (retval > 0) { - return retval / _sample_size; - } - else { - return retval; - } - } - - _write_data_count = byte_cnt; - - return cnt; -} - -ssize_t -FileSource::read_float (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const -{ - ssize_t nread; - ssize_t byte_cnt = (ssize_t) cnt * sizeof (Sample); - int readfd; - - /* open, read, close */ - - if ((readfd = open64 (_path.c_str(), O_RDONLY)) < 0) { - error << string_compose(_("FileSource: could not open \"%1\": (%2)"), _path, strerror (errno)) << endmsg; - return 0; - } - - nread = ::pread64 (readfd, (char *) dst, byte_cnt, data_offset + (start * _sample_size)); - close (readfd); - - if (nread != byte_cnt) { - - cerr << "FileSource: \"" - << _path - << "\" bad read at frame " - << start - << ", of " - << cnt - << " (bytes=" - << byte_cnt - << ") frames [length = " << _length - << " eor = " << start + cnt << "] (" - << strerror (errno) - << ") (read " - << nread / sizeof (Sample) - << " (bytes=" < 0) { - return retval / _sample_size; - } - else { - return retval; - } - } - - return (ssize_t) cnt; -} - -ssize_t -FileSource::read_pcm_24 (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const -{ - ssize_t nread; - ssize_t byte_cnt = (ssize_t) cnt * _sample_size; - int readfd; - - /* open, read, close */ - - if ((readfd = open64 (_path.c_str(), O_RDONLY)) < 0) { - error << string_compose(_("FileSource: could not open \"%1\": (%2)"), _path, strerror (errno)) << endmsg; - return 0; - } - - nread = ::pread64 (readfd, (char *) workbuf, byte_cnt, data_offset + (start * _sample_size)); - close (readfd); - - if (nread != byte_cnt) { - - cerr << "May be OK - FileSource: \"" - << _path - << "\" bad 24bit read at frame " - << start - << ", of " - << cnt - << " (bytes=" - << byte_cnt - << ") frames [length = " << _length - << " eor = " << start + cnt << "] (" - << strerror (errno) - << ") (read " - << nread / sizeof (Sample) - << " (bytes=" < #include #include -#include +#include #include #include #include @@ -69,6 +69,7 @@ ARDOUR::OSC* ARDOUR::osc = 0; using namespace ARDOUR; using namespace std; +using namespace PBD; MIDI::Port *default_mmc_port = 0; MIDI::Port *default_mtc_port = 0; @@ -188,7 +189,7 @@ setup_midi () } int -ARDOUR::init (AudioEngine& engine, bool use_vst, bool try_optimization, void (*sighandler)(int,siginfo_t*,void*)) +ARDOUR::init (AudioEngine& engine, bool use_vst, bool try_optimization) { bool generic_mix_functions = true; @@ -213,7 +214,7 @@ ARDOUR::init (AudioEngine& engine, bool use_vst, bool try_optimization, void (*s #endif #ifdef VST_SUPPORT - if (Config->get_use_vst() && fst_init (sighandler)) { + if (Config->get_use_vst() && fst_init ()) { return -1; } #endif diff --git a/libs/ardour/import.cc b/libs/ardour/import.cc index c13816e648..b70a7bbc9c 100644 --- a/libs/ardour/import.cc +++ b/libs/ardour/import.cc @@ -36,14 +36,15 @@ #include #include -#include -#include +#include +#include #include #include #include "i18n.h" using namespace ARDOUR; +using namespace PBD; #define BLOCKSIZE 4096U @@ -51,8 +52,8 @@ int Session::import_audiofile (import_status& status) { SNDFILE *in; - FileSource **newfiles = 0; - ARDOUR::AudioRegion::SourceList sources; + AudioFileSource **newfiles = 0; + AudioRegion::SourceList sources; SF_INFO info; float *data = 0; Sample **channel_data = 0; @@ -94,7 +95,7 @@ Session::import_audiofile (import_status& status) } } - newfiles = new FileSource *[info.channels]; + newfiles = new AudioFileSource *[info.channels]; for (n = 0; n < info.channels; ++n) { newfiles[n] = 0; } @@ -137,7 +138,10 @@ Session::import_audiofile (import_status& status) try { - newfiles[n] = new FileSource (buf, frame_rate(), false, Config->get_native_file_data_format()); + newfiles[n] = new SndFileSource (buf, + Config->get_native_file_data_format(), + Config->get_native_file_header_format(), + frame_rate ()); } catch (failed_constructor& err) { diff --git a/libs/ardour/insert.cc b/libs/ardour/insert.cc index c3c3462016..fc05355d4a 100644 --- a/libs/ardour/insert.cc +++ b/libs/ardour/insert.cc @@ -38,7 +38,7 @@ using namespace std; using namespace ARDOUR; -//using namespace sigc; +using namespace PBD; Insert::Insert(Session& s, Placement p) : Redirect (s, s.next_insert_name(), p) diff --git a/libs/ardour/io.cc b/libs/ardour/io.cc index fa30463bd4..87c03c6b70 100644 --- a/libs/ardour/io.cc +++ b/libs/ardour/io.cc @@ -55,7 +55,8 @@ extern "C" int isinf (double); using namespace std; using namespace ARDOUR; -//using namespace sigc; +using namespace PBD; + static float current_automation_version_number = 1.0; @@ -2443,12 +2444,6 @@ IO::state_factory (std::string why) const return state; } -void -IO::send_state_changed () -{ - return; -} - /** Update the peak meters. @@ -2493,7 +2488,7 @@ IO::meter () } else { // do falloff new_peak = _visible_peak_power[n] - _session.meter_falloff(); - _visible_peak_power[n] = max (new_peak, -200.0f); + _visible_peak_power[n] = max (new_peak, -INFINITY); } } } diff --git a/libs/ardour/jack_slave.cc b/libs/ardour/jack_slave.cc index be8d585aaa..352bcaeee5 100644 --- a/libs/ardour/jack_slave.cc +++ b/libs/ardour/jack_slave.cc @@ -23,7 +23,6 @@ #include #include #include -#include #include #include diff --git a/libs/ardour/ladspa_plugin.cc b/libs/ardour/ladspa_plugin.cc index 50757f9acd..11001655d2 100644 --- a/libs/ardour/ladspa_plugin.cc +++ b/libs/ardour/ladspa_plugin.cc @@ -49,6 +49,7 @@ using namespace std; using namespace ARDOUR; +using namespace PBD; LadspaPlugin::LadspaPlugin (void *mod, AudioEngine& e, Session& session, uint32_t index, jack_nframes_t rate) : Plugin (e, session) diff --git a/libs/ardour/location.cc b/libs/ardour/location.cc index 28ec42a394..b2af52284e 100644 --- a/libs/ardour/location.cc +++ b/libs/ardour/location.cc @@ -36,6 +36,7 @@ using namespace std; using namespace ARDOUR; using namespace sigc; +using namespace PBD; Location::Location (const Location& other) : _name (other._name), diff --git a/libs/ardour/mtc_slave.cc b/libs/ardour/mtc_slave.cc index cb35c0c785..32642d570d 100644 --- a/libs/ardour/mtc_slave.cc +++ b/libs/ardour/mtc_slave.cc @@ -37,6 +37,7 @@ using namespace ARDOUR; using namespace sigc; using namespace MIDI; +using namespace PBD; MTC_Slave::MTC_Slave (Session& s, MIDI::Port& p) : session (s) @@ -87,7 +88,7 @@ void MTC_Slave::update_mtc_time (const byte *msg, bool was_full) { jack_nframes_t now = session.engine().frame_time(); - SMPTE_Time smpte; + SMPTE::Time smpte; smpte.hours = msg[3]; smpte.minutes = msg[2]; diff --git a/libs/ardour/named_selection.cc b/libs/ardour/named_selection.cc index 9c5830dfc1..605d7cae13 100644 --- a/libs/ardour/named_selection.cc +++ b/libs/ardour/named_selection.cc @@ -29,6 +29,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; sigc::signal NamedSelection::NamedSelectionCreated; diff --git a/libs/ardour/osc.cc b/libs/ardour/osc.cc index 67b70fba0c..5aaf9d5591 100644 --- a/libs/ardour/osc.cc +++ b/libs/ardour/osc.cc @@ -309,7 +309,6 @@ OSC::osc_receiver() if ((ret = poll (pfd, nfds, timeout)) < 0) { if (errno == EINTR) { /* gdb at work, perhaps */ - cerr << "EINTR hit " << endl; goto again; } diff --git a/libs/ardour/panner.cc b/libs/ardour/panner.cc index bc7b472732..83c9e6eb4d 100644 --- a/libs/ardour/panner.cc +++ b/libs/ardour/panner.cc @@ -44,9 +44,9 @@ #include - using namespace std; using namespace ARDOUR; +using namespace PBD; float Panner::current_automation_version_number = 1.0; diff --git a/libs/ardour/playlist.cc b/libs/ardour/playlist.cc index 1bc6ccac6d..7dee866767 100644 --- a/libs/ardour/playlist.cc +++ b/libs/ardour/playlist.cc @@ -41,7 +41,7 @@ using namespace std; using namespace ARDOUR; -//using namespace sigc; +using namespace PBD; sigc::signal Playlist::PlaylistCreated; diff --git a/libs/ardour/playlist_factory.cc b/libs/ardour/playlist_factory.cc index fc4618d1dc..7c7060dae8 100644 --- a/libs/ardour/playlist_factory.cc +++ b/libs/ardour/playlist_factory.cc @@ -1,3 +1,25 @@ +/* + Copyright (C) 2000-2006 Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + + $Id$ +*/ + +#include + #include #include @@ -10,6 +32,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; Region* ARDOUR::createRegion (const Region& region, jack_nframes_t start, diff --git a/libs/ardour/plugin.cc b/libs/ardour/plugin.cc index e9665908a3..2d1f8ffcbd 100644 --- a/libs/ardour/plugin.cc +++ b/libs/ardour/plugin.cc @@ -48,6 +48,7 @@ #include using namespace ARDOUR; +using namespace PBD; Plugin::Plugin (AudioEngine& e, Session& s) : _engine (e), _session (s) diff --git a/libs/ardour/plugin_manager.cc b/libs/ardour/plugin_manager.cc index e1f34199d6..b096e81785 100644 --- a/libs/ardour/plugin_manager.cc +++ b/libs/ardour/plugin_manager.cc @@ -44,6 +44,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; PluginManager* PluginManager::_manager = 0; diff --git a/libs/ardour/po/el_GR.po b/libs/ardour/po/el_GR.po index 9a36b31c83..fb235155f3 100644 --- a/libs/ardour/po/el_GR.po +++ b/libs/ardour/po/el_GR.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: libardour 0.664.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-04-25 17:46-0400\n" +"POT-Creation-Date: 2006-06-21 15:09-0400\n" "PO-Revision-Date: 2003-05-21 12:50+0500\n" "Last-Translator: Muadibas\n" "Language-Team: Hellenic(Greek)\n" @@ -15,38 +15,124 @@ msgstr "" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" -#: libs/ardour/audio_library.cc:91 +#: libs/ardour/audio_diskstream.cc:337 +#, fuzzy +msgid "AudioDiskstream: Session doesn't know about a Playlist called \"%1\"" +msgstr "" +"DiskStream: Η ΣυνεδÏία δεν γνωÏίζει για την λίστα ΑναπαÏ/γής με όνομα \"%1\"" + +#: libs/ardour/audio_diskstream.cc:342 +#, fuzzy +msgid "AudioDiskstream: Playlist \"%1\" isn't an audio playlist" +msgstr "DiskStream: Η Λίστα \"%1\" δεν είναι ηχητική λίστα αναπαÏ/γής" + +#: libs/ardour/audio_diskstream.cc:433 +#, fuzzy +msgid "AudioDiskstream %1: there is no existing playlist to make a copy of!" +msgstr "DiskStream %1: δεν υπάÏχει λίστα αναπαÏ/γής για να γίνει αντιγÏαφή!" + +#: libs/ardour/audio_diskstream.cc:1114 libs/ardour/audio_diskstream.cc:1125 +#, fuzzy +msgid "" +"AudioDiskstream %1: when refilling, cannot read %2 from playlist at frame %3" +msgstr "" +"DiskStream %1: κατα την αναγόμωση, δεν μπόÏεσα να διαβάσω %2 από τη λίστα " +"αναπαÏ/γής στο frame %3" + +#: libs/ardour/audio_diskstream.cc:1254 +#, fuzzy +msgid "AudioDiskstream %1: cannot read %2 from playlist at frame %3" +msgstr "" +"DiskStream %1: δεν μπόÏεσα να διαβάσω %2 από τη λίστα αναπαÏ/γής στο frame %3" + +#: libs/ardour/audio_diskstream.cc:1621 libs/ardour/audio_diskstream.cc:1638 +#, fuzzy +msgid "AudioDiskstream %1: cannot write to disk" +msgstr "DiskStream %1: δεν μποÏÏŽ να γÏάψω στο δίσκο" + +#: libs/ardour/audio_diskstream.cc:1698 +#, fuzzy +msgid "AudioDiskstream \"%1\": cannot flush captured data to disk!" +msgstr "" +"DiskStream \"%1\": δεν γίνεται να αποÏÏιφθοÏν δειγματοληψίες στο δίσκο!" + +#: libs/ardour/audio_diskstream.cc:1795 +msgid "%1: could not create region for complete audio file" +msgstr "%1: δεν μπόÏεσα να δημιουÏγήσω πεÏιοχή για ολόκληÏο audio file" + +#: libs/ardour/audio_diskstream.cc:1818 +#, fuzzy +msgid "AudioDiskstream: could not create region for captured audio!" +msgstr "DiskStream: δεν μπόÏεσα να δημιουÏγήσω πεÏιοχή για δειγματοληψίες!" + +#: libs/ardour/audio_diskstream.cc:1873 +#, fuzzy +msgid "programmer error: %1" +msgstr "σφάλμα Ï€ÏογÏαμματισμοÏ: %1" + +#: libs/ardour/audio_diskstream.cc:2145 +#, fuzzy +msgid "AudioDiskstream: channel %1 out of range" +msgstr "DiskStream: κανάλι εκτός διαστήματος" + +#: libs/ardour/audio_diskstream.cc:2170 +msgid "%1:%2 new capture file not initialized correctly" +msgstr "%1:%2 νέα δειγματοληψία δεν εκκινήθη σωστά" + +#: libs/ardour/audio_diskstream.cc:2403 +msgid "Location \"%1\" not valid for track loop (start >= end)" +msgstr "Η Τοποθεσία \"%1\" δεν είναι ικανή για track loop (αÏχή >= τέλος)" + +#: libs/ardour/audio_diskstream.cc:2484 +#, fuzzy +msgid "%1: cannot restore pending capture source file %2" +msgstr "Εισαγωγή: δεν μποÏÏŽ να ανοίξω το εισαγμένο αÏχείο ήχου \"%1\"" + +#: libs/ardour/audio_diskstream.cc:2506 +msgid "%1: incorrect number of pending sources listed - ignoring them all" +msgstr "" + +#: libs/ardour/audio_diskstream.cc:2522 +msgid "%1: cannot create whole-file region from pending capture sources" +msgstr "" + +#: libs/ardour/audio_diskstream.cc:2534 +#, fuzzy +msgid "%1: cannot create region from pending capture sources" +msgstr "%1: δεν μπόÏεσα να δημιουÏγήσω πεÏιοχή για ολόκληÏο audio file" + +#: libs/ardour/audio_library.cc:92 msgid "channels" msgstr "" -#: libs/ardour/audio_library.cc:92 +#: libs/ardour/audio_library.cc:93 #, fuzzy msgid "samplerate" msgstr "ξεχωÏιστό" -#: libs/ardour/audio_library.cc:93 +#: libs/ardour/audio_library.cc:94 msgid "resolution" msgstr "" -#: libs/ardour/audio_library.cc:94 +#: libs/ardour/audio_library.cc:95 #, fuzzy msgid "format" msgstr "float" -#: libs/ardour/audio_library.cc:101 +#: libs/ardour/audio_library.cc:102 msgid "Could not open %1. Audio Library not saved" msgstr "Δεν μπόÏεσα να ανοίξω το %1. Η Audio Library δεν αποθηκεÏθηκε" -#: libs/ardour/audio_playlist.cc:52 libs/ardour/audio_playlist.cc:62 -#: libs/ardour/audio_playlist.cc:73 libs/ardour/audio_playlist.cc:120 +#: libs/ardour/audio_playlist.cc:53 libs/ardour/audio_playlist.cc:63 +#: libs/ardour/audio_playlist.cc:74 libs/ardour/audio_playlist.cc:121 #: libs/ardour/insert.cc:76 libs/ardour/insert.cc:95 libs/ardour/insert.cc:120 -#: libs/ardour/insert.cc:838 libs/ardour/insert.cc:846 libs/ardour/send.cc:38 -#: libs/ardour/send.cc:52 libs/ardour/send.cc:61 -#: libs/ardour/session_state.cc:1620 libs/ardour/session_state.cc:1666 +#: libs/ardour/insert.cc:838 libs/ardour/insert.cc:846 libs/ardour/send.cc:39 +#: libs/ardour/send.cc:53 libs/ardour/send.cc:62 +#: libs/ardour/session_state.cc:1621 libs/ardour/session_state.cc:1667 msgid "initial state" msgstr "Ï€ÏωταÏχική κατάσταση" -#: libs/ardour/audio_playlist.cc:274 libs/ardour/audio_playlist.cc:768 +#: libs/ardour/audio_playlist.cc:275 libs/ardour/audio_playlist.cc:769 msgid "" "programming error: non-audio Region passed to remove_overlap in audio " "playlist" @@ -54,51 +140,51 @@ msgstr "" "σφάλμα Ï€ÏογÏαμματισμοÏ: μη-ηχητική ΠεÏιοχή πέÏασε σε remove_overlap στην " "audio playlist" -#: libs/ardour/audio_playlist.cc:401 +#: libs/ardour/audio_playlist.cc:402 msgid "" "programming error: non-audio Region tested for overlap in audio playlist" msgstr "" "σφάλμα Ï€ÏογÏαμματισμοÏ: μη-ηχητική ΠεÏιοχή ελέγχθη για υπεÏπήδηση(overlap) " "στην λίστα αναπαÏ/γής του ήχου" -#: libs/ardour/audio_playlist.cc:877 +#: libs/ardour/audio_playlist.cc:878 msgid "xfade change" msgstr "αλλαγή xfade" -#: libs/ardour/audio_playlist.cc:926 +#: libs/ardour/audio_playlist.cc:933 msgid "region modified" msgstr "η πεÏιοχή μετεβλήθη" -#: libs/ardour/audio_track.cc:121 libs/ardour/io.cc:1703 -#: libs/ardour/io.cc:1813 +#: libs/ardour/audio_track.cc:133 libs/ardour/io.cc:1716 +#: libs/ardour/io.cc:1826 msgid "Unknown connection \"%1\" listed for input of %2" msgstr "Άγνωστη σÏνδεση \"%1\" στη λίστα εισόδου του %2" -#: libs/ardour/audio_track.cc:123 libs/ardour/io.cc:1705 -#: libs/ardour/io.cc:1815 +#: libs/ardour/audio_track.cc:135 libs/ardour/io.cc:1718 +#: libs/ardour/io.cc:1828 #, fuzzy msgid "in 1" msgstr "in %lu" -#: libs/ardour/audio_track.cc:124 libs/ardour/io.cc:1706 -#: libs/ardour/io.cc:1816 +#: libs/ardour/audio_track.cc:136 libs/ardour/io.cc:1719 +#: libs/ardour/io.cc:1829 msgid "No input connections available as a replacement" msgstr "" -#: libs/ardour/audio_track.cc:128 libs/ardour/io.cc:1710 -#: libs/ardour/io.cc:1820 +#: libs/ardour/audio_track.cc:140 libs/ardour/io.cc:1723 +#: libs/ardour/io.cc:1833 msgid "Connection %1 was not available - \"in 1\" used instead" msgstr "" -#: libs/ardour/audio_track.cc:137 libs/ardour/io.cc:1829 +#: libs/ardour/audio_track.cc:149 libs/ardour/io.cc:1842 msgid "improper input channel list in XML node (%1)" msgstr "ακατάλληλη λίστα καναλιών εισόδου στον κόμβο XML (%1)" -#: libs/ardour/audio_track.cc:182 libs/ardour/audio_track.cc:195 +#: libs/ardour/audio_track.cc:194 libs/ardour/audio_track.cc:207 msgid "AudioTrack: diskstream \"%1\" not known by session" msgstr "AudioTrack: το diskstream \"%1\" είναι μή αναγνωÏίσιμο από τη συνεδÏία" -#: libs/ardour/audio_track.cc:293 +#: libs/ardour/audio_track.cc:305 #, fuzzy msgid "" "MIDI rec_enable control specification for %1 is incomplete, so it has been " @@ -107,214 +193,325 @@ msgstr "" "Η Ï€ÏοδιαγÏαφή ελέγχου του MIDI gain για το %1 είναι ημιτελής, με αποτέλεσμα " "να αγνοηθεί" -#: libs/ardour/audio_track.cc:305 +#: libs/ardour/audio_track.cc:317 msgid "programming error: AudioTrack given state without diskstream!" msgstr "" "σφάλμα Ï€ÏογÏαμματισμοÏ: εδόθη κατάσταση στην AudioTrack δίχως diskstream!" -#: libs/ardour/audioengine.cc:147 +#: libs/ardour/audioengine.cc:150 msgid "cannot activate JACK client" msgstr "Ο JACK δεν μποÏεί να ενεÏγοποιηθεί" -#: libs/ardour/audioengine.cc:432 +#: libs/ardour/audioengine.cc:401 msgid "register audio input port called before engine was started" msgstr "η register audio input port εκλήθη Ï€Ïιν να εκκινηθεί η engine" -#: libs/ardour/audioengine.cc:463 +#: libs/ardour/audioengine.cc:432 msgid "register audio output port called before engine was started" msgstr "η register audio output port εκλήθη Ï€Ïίν να εκκινηθεί η engine" -#: libs/ardour/audioengine.cc:524 +#: libs/ardour/audioengine.cc:493 msgid "connect called before engine was started" msgstr "η σÏνδεση εκλήθη Ï€Ïιν να εκκινηθεί η engine" -#: libs/ardour/audioengine.cc:540 +#: libs/ardour/audioengine.cc:509 msgid "AudioEngine: cannot connect %1 (%2) to %3 (%4)" msgstr "" -#: libs/ardour/audioengine.cc:553 libs/ardour/audioengine.cc:582 +#: libs/ardour/audioengine.cc:522 libs/ardour/audioengine.cc:551 msgid "disconnect called before engine was started" msgstr "η αποσÏνδεση εκλήθη Ï€Ïιν να εκκινηθεί η engine" -#: libs/ardour/audioengine.cc:640 +#: libs/ardour/audioengine.cc:609 msgid "get_port_by_name() called before engine was started" msgstr "η Ïουτίνα get_port_by_name() εκλήθη Ï€Ïιν να εκκινηθεί η engine" -#: libs/ardour/audioengine.cc:673 +#: libs/ardour/audioengine.cc:642 msgid "get_ports called before engine was started" msgstr "η Ïουτίνα get_ports εκλήθη Ï€Ïιν να εκκινηθεί η engine" -#: libs/ardour/audioengine.cc:748 +#: libs/ardour/audioengine.cc:717 msgid "get_nth_physical called before engine was started" msgstr "η Ïουτίνα get_nth_physical εκλήθη Ï€Ïιν να εκκινηθεί η engine" -#: libs/ardour/audioengine.cc:776 +#: libs/ardour/audioengine.cc:745 #, fuzzy msgid "get_port_total_latency() called with no JACK client connection" msgstr "η Ïουτίνα get_port_total_latency() εκλήθη Ï€Ïιν να εκκινηθεί η engine" -#: libs/ardour/audioengine.cc:782 +#: libs/ardour/audioengine.cc:751 msgid "get_port_total_latency() called before engine was started" msgstr "η Ïουτίνα get_port_total_latency() εκλήθη Ï€Ïιν να εκκινηθεί η engine" -#: libs/ardour/audioengine.cc:906 +#: libs/ardour/audioengine.cc:875 msgid "Unable to connect to JACK server" msgstr "" -#: libs/ardour/audioengine.cc:909 +#: libs/ardour/audioengine.cc:878 msgid "Could not connect to JACK server as \"%1\"" msgstr "" -#: libs/ardour/audioengine.cc:914 +#: libs/ardour/audioengine.cc:883 msgid "JACK server started" msgstr "" -#: libs/ardour/audioengine.cc:948 +#: libs/ardour/audioengine.cc:917 msgid "cannot shutdown connection to JACK" msgstr "" -#: libs/ardour/audioengine.cc:973 +#: libs/ardour/audioengine.cc:942 msgid "failed to connect to JACK" msgstr "" -#: libs/ardour/audioengine.cc:989 +#: libs/ardour/audioengine.cc:958 #, fuzzy msgid "could not reregister %1" msgstr "Σφάλμα: δεν μπόÏεσα να γÏάψω %1" -#: libs/ardour/audioengine.cc:1046 +#: libs/ardour/audioengine.cc:1015 msgid "could not reconnect %1 and %2 (err = %3)" msgstr "" -#: libs/ardour/audiofilter.cc:44 +#: libs/ardour/audiofilesource.cc:445 libs/ardour/session_state.cc:3095 +msgid "" +"there are already 1000 files with names like %1; versioning discontinued" +msgstr "ΥπάÏχουν ήδη 1000 αÏχεία με ονόματα όπως %1; μη-συνεχές versioning" + +#: libs/ardour/audiofilesource.cc:459 libs/ardour/session_state.cc:3109 +msgid "cannot rename audio file source from %1 to %2 (%3)" +msgstr "δεν μποÏÏŽ να μετονομάσω την πηγή του audio file από %1 σε %2 (%3)" + +#: libs/ardour/audiofilesource.cc:466 libs/ardour/session_state.cc:3124 +msgid "cannot remove peakfile %1 for %2 (%3)" +msgstr "δεν μποÏÏŽ να απαλοίψω το peakfile %1 για %2 (%3)" + +#: libs/ardour/audiofilesource.cc:510 +msgid "FileSource: search path not set" +msgstr "FileSource: μονοπάτι αναζητήσεως δεν ετέθη" + +#: libs/ardour/audiofilesource.cc:534 +msgid "" +"FileSource: \"%1\" is ambigous when searching %2\n" +"\t" +msgstr "" +"FileSource: \"%1\" είναι αμφίβολο κατά την αναζήτηση του %2\n" +"\t" + +#: libs/ardour/audiofilesource.cc:540 +#, fuzzy +msgid "Filesource: cannot find required file (%1): while searching %2" +msgstr "Filesource: δεν ευÏέθη το απαιτοÏμενο αÏχείο (%1): %2" + +#: libs/ardour/audiofilesource.cc:563 +msgid "Filesource: cannot find required file (%1): %2" +msgstr "Filesource: δεν ευÏέθη το απαιτοÏμενο αÏχείο (%1): %2" + +#: libs/ardour/audiofilesource.cc:568 +msgid "Filesource: cannot check for existing file (%1): %2" +msgstr "Filesource: δεν μποÏÏŽ να ελέγξω για το υπάÏχον αÏχείο (%1): %2" + +#: libs/ardour/audiofilesource.cc:640 libs/ardour/insert.cc:525 +#: libs/ardour/sndfilesource.cc:112 +msgid "programming error: %1" +msgstr "σφάλμα Ï€ÏογÏαμματισμοÏ: %1" + +#: libs/ardour/audiofilesource.cc:645 +#, fuzzy +msgid "cannot rename audio file for %1 to %2" +msgstr "δεν μποÏÏŽ να μετονομάσω την πηγή του audio file από %1 σε %2 (%3)" + +#: libs/ardour/audiofilter.cc:45 msgid "audiofilter: error creating name for new audio file based on %1" msgstr "" "audiofilter: σφάλμα στη δημιουÏγία ονόματος για νέο audio file βασισμένο σε %" "1" -#: libs/ardour/audiofilter.cc:54 +#: libs/ardour/audiofilter.cc:58 msgid "audiofilter: error creating new audio file %1 (%2)" msgstr "audiofilter: σφάλμα στη δημιουÏγία νέου audio file %1 (%2)" -#: libs/ardour/audioregion.cc:855 libs/ardour/audioregion.cc:917 +#: libs/ardour/audioregion.cc:857 libs/ardour/audioregion.cc:919 #, fuzzy msgid "fade in change" msgstr "αλλαγή xfade" -#: libs/ardour/audioregion.cc:1341 +#: libs/ardour/audioregion.cc:1349 #, c-format msgid "normalized to %.2fdB" msgstr "εξομαλÏνθηκε στα %.2fdB" -#: libs/ardour/audioregion.cc:1359 +#: libs/ardour/audioregion.cc:1367 #, fuzzy msgid "envelope change" msgstr "αλλαγή ενεÏγοÏ" -#: libs/ardour/automation_event.cc:64 libs/ardour/location.cc:344 -#: libs/ardour/tempo.cc:225 +#: libs/ardour/audiosource.cc:143 +msgid "poll on peak request pipe failed (%1)" +msgstr "" + +#: libs/ardour/audiosource.cc:150 +#, fuzzy +msgid "Error on peak thread request pipe" +msgstr "Σφάλμα στο transport thread request pipe" + +#: libs/ardour/audiosource.cc:183 +#, fuzzy +msgid "Error reading from peak request pipe" +msgstr "Σφάλμα στην ανάγνωση από transport request pipe" + +#: libs/ardour/audiosource.cc:215 libs/ardour/session_butler.cc:80 +#: libs/ardour/session_midi.cc:1183 +msgid "Cannot create transport request signal pipe (%1)" +msgstr "Δεν μποÏÏŽ να δημιουÏγήσω transport request signal pipe (%1)" + +#: libs/ardour/audiosource.cc:220 libs/ardour/audiosource.cc:225 +#, fuzzy +msgid "UI: cannot set O_NONBLOCK on peak request pipe (%1)" +msgstr "UI: δεν μποÏÏŽ να θέσω O_NONBLOCK στο signal read pipe (%1)" + +#: libs/ardour/audiosource.cc:230 +#, fuzzy +msgid "AudioSource: could not create peak thread" +msgstr "Source: δεν μπόÏεσα να δημιουÏγήσω peak δέσμη" + +#: libs/ardour/audiosource.cc:308 +#, fuzzy +msgid "cannot rename peakfile for %1 from %2 to %3 (%4)" +msgstr "δεν μποÏÏŽ να απαλοίψω το peakfile %1 για %2 (%3)" + +#: libs/ardour/audiosource.cc:350 +#, fuzzy +msgid "AudioSource: cannot stat peakfile \"%1\"" +msgstr "Source: δεν μποÏÏŽ να μετÏήσω το αυτοστιγμεί peakfile \"%1\"" + +#: libs/ardour/audiosource.cc:451 +msgid "cannot read sample data for unscaled peak computation" +msgstr "" +"δεν μποÏÏŽ να διαβάσω δεδομένα δείγματος για υπολογισμό μη-κλιμακώτου peak" + +#: libs/ardour/audiosource.cc:472 libs/ardour/audiosource.cc:543 +#: libs/ardour/audiosource.cc:787 libs/ardour/audiosource.cc:878 +#, fuzzy +msgid "AudioSource: cannot open peakpath \"%1\" (%2)" +msgstr "Source: δεν μποÏÏŽ να ανοίξω το peakpath \"%1\" (%2)" + +#: libs/ardour/audiosource.cc:644 +#, fuzzy +msgid "AudioSource[%1]: peak read - cannot read %2 samples at offset %3" +msgstr "" +"Source[%1]: ανάγνωση peak - δεν μποÏÏŽ να διαβάσω %2 δείγματα στην αÏχή" +"(offset) %3" + +#: libs/ardour/audiosource.cc:798 +msgid "%1: could not write read raw data for peak computation (%2)" +msgstr "" +"%1: δεν μποÏεσα να γÏάψω ανεγνωσμένα raw δεδομένα για τον υπολογισμό του " +"peak (%2)" + +#: libs/ardour/audiosource.cc:823 +msgid "%1: could not write peak file data (%2)" +msgstr "%1: δεν μπόÏεσα να γÏάψω δεδομένα του αÏχείου peak (%2)" + +#: libs/ardour/automation_event.cc:65 libs/ardour/location.cc:345 +#: libs/ardour/tempo.cc:226 msgid "initial" msgstr "Ï€ÏωταÏχικό" -#: libs/ardour/automation_event.cc:231 +#: libs/ardour/automation_event.cc:232 msgid "cleared" msgstr "εκκαθαÏίσθη" -#: libs/ardour/automation_event.cc:403 +#: libs/ardour/automation_event.cc:404 msgid "added event" msgstr "συμβάν Ï€Ïοστέθηκε" -#: libs/ardour/automation_event.cc:420 +#: libs/ardour/automation_event.cc:421 msgid "removed event" msgstr "συμβάν απαλοίφθηκε" -#: libs/ardour/automation_event.cc:435 +#: libs/ardour/automation_event.cc:436 msgid "removed multiple events" msgstr "πολλαπλά συμβάντα απαλοίφθηκαν" -#: libs/ardour/automation_event.cc:461 +#: libs/ardour/automation_event.cc:467 libs/ardour/automation_event.cc:498 msgid "removed range" msgstr "διάστημα απαλοίφθηκε" -#: libs/ardour/automation_event.cc:491 +#: libs/ardour/automation_event.cc:528 msgid "event range adjusted" msgstr "διάστημα συμβάντων Ïυθμίστηκε" -#: libs/ardour/automation_event.cc:513 +#: libs/ardour/automation_event.cc:550 msgid "event adjusted" msgstr "συμβάν Ïυθμίστηκε" -#: libs/ardour/automation_event.cc:628 libs/ardour/automation_event.cc:733 -#: libs/ardour/panner.cc:1040 +#: libs/ardour/automation_event.cc:665 libs/ardour/automation_event.cc:770 +#: libs/ardour/panner.cc:1041 msgid "programming error:" msgstr "σφάλμα Ï€ÏογÏαμματισμοÏ:" -#: libs/ardour/automation_event.cc:1042 +#: libs/ardour/automation_event.cc:1079 msgid "cut/copy/clear" msgstr "κοπή/αντιγÏαφή/εκκαθάÏιση" -#: libs/ardour/automation_event.cc:1075 +#: libs/ardour/automation_event.cc:1112 msgid "copy" msgstr "αντιγÏαφή" -#: libs/ardour/automation_event.cc:1143 libs/ardour/playlist.cc:939 +#: libs/ardour/automation_event.cc:1180 libs/ardour/playlist.cc:939 msgid "paste" msgstr "επικόλληση" -#: libs/ardour/automation_event.cc:1198 +#: libs/ardour/automation_event.cc:1235 msgid "" "automation list: no x-coordinate stored for control point (point ignored)" msgstr "" "λίστα αυτοματισμοÏ: καμία x-συντεταγμένη αποθηκευμένη για σημείο ελέγχου (το " "σημείο αγνοήθηκε)" -#: libs/ardour/automation_event.cc:1204 +#: libs/ardour/automation_event.cc:1241 msgid "" "automation list: no y-coordinate stored for control point (point ignored)" msgstr "" "λίστα αυτοματισμοÏ: καμία y-συντεταγμένη αποθηκευμένη για σημείο ελέγχου (το " "σημείο αγνοήθηκε)" -#: libs/ardour/basic_ui.cc:68 -msgid "unnamed" -msgstr "" - -#: libs/ardour/configuration.cc:79 +#: libs/ardour/configuration.cc:80 #, fuzzy msgid "loading system configuration file %1" msgstr "" "Ardour: δεν μποÏÏŽ να διαβάσω το αÏχείο διαÏÏυθμίσεως του συστήματος \"%1\"" -#: libs/ardour/configuration.cc:82 +#: libs/ardour/configuration.cc:83 msgid "Ardour: cannot read system configuration file \"%1\"" msgstr "" "Ardour: δεν μποÏÏŽ να διαβάσω το αÏχείο διαÏÏυθμίσεως του συστήματος \"%1\"" -#: libs/ardour/configuration.cc:87 +#: libs/ardour/configuration.cc:88 msgid "Ardour: system configuration file \"%1\" not loaded successfully." msgstr "" "Ardour: το αÏχείο διαÏÏυθμίσεως του συστήματος \"%1\" δεν φοÏτώθηκε επιτυχώς." -#: libs/ardour/configuration.cc:104 +#: libs/ardour/configuration.cc:105 #, fuzzy msgid "loading user configuration file %1" msgstr "Ardour: αÏχείο διαÏÏυθμίσεως μή αναγνώσιμο \"%1\"" -#: libs/ardour/configuration.cc:107 +#: libs/ardour/configuration.cc:108 msgid "Ardour: cannot read configuration file \"%1\"" msgstr "Ardour: αÏχείο διαÏÏυθμίσεως μή αναγνώσιμο \"%1\"" -#: libs/ardour/configuration.cc:112 +#: libs/ardour/configuration.cc:113 #, fuzzy msgid "Ardour: user configuration file \"%1\" not loaded successfully." msgstr "Ardour: αÏχείο διαÏÏυθμίσεως \"%1\" δεν φοÏτώθηκε επιτυχώς." -#: libs/ardour/configuration.cc:136 +#: libs/ardour/configuration.cc:137 #, fuzzy msgid "Config file %1 not saved" msgstr "ΑÏχείο διαÏÏυθμίσεως δεν αποθηκεÏθηκε" -#: libs/ardour/configuration.cc:209 +#: libs/ardour/configuration.cc:210 msgid "ill-formed MIDI port specification in ardour rcfile (ignored)" msgstr "κακοσχηματισμένος καθοÏισμός MIDI θÏÏας στο ardour rcfile (αγνοήθηκε)" @@ -326,28 +523,41 @@ msgstr "Κόμβος Ï€Ïος ΣÏνδεση δεν έχει \"όνομα\" ιδ msgid "Node for Connection has no \"connections\" property" msgstr "Κόμβος Ï€Ïος ΣÏνδεση δεν έχει \"συνδέσεις\" ιδιότητα" -#: libs/ardour/connection.cc:227 libs/ardour/io.cc:1889 +#: libs/ardour/connection.cc:227 libs/ardour/io.cc:1902 msgid "IO: badly formed string in XML node for inputs \"%1\"" msgstr "IO: κακοφτιαγμένη γÏαμμή στον XML κόμβο για εισόδους \"%1\"" -#: libs/ardour/connection.cc:232 libs/ardour/io.cc:1894 +#: libs/ardour/connection.cc:232 libs/ardour/io.cc:1907 msgid "bad input string in XML node \"%1\"" msgstr "κακή γÏαμμή εισόδου στον XML κόμβο \"%1\"" -#: libs/ardour/control_protocol_manager.cc:79 +#: libs/ardour/control_protocol_manager.cc:80 msgid "control protocol name \"%1\" has no descriptor" msgstr "" -#: libs/ardour/control_protocol_manager.cc:84 +#: libs/ardour/control_protocol_manager.cc:85 msgid "control protocol name \"%1\" could not be initialized" msgstr "" -#: libs/ardour/control_protocol_manager.cc:180 +#: libs/ardour/control_protocol_manager.cc:141 +msgid "Instantiating mandatory control protocol %1" +msgstr "" + +#: libs/ardour/control_protocol_manager.cc:175 +#, fuzzy +msgid "Control protocol %1 not usable" +msgstr "ΧωÏίς έλεγχο MMC (θÏÏα MIDI \"%1\" μη διαθέσιμη)" + +#: libs/ardour/control_protocol_manager.cc:187 +msgid "Control surface protocol discovered: \"%1\"" +msgstr "" + +#: libs/ardour/control_protocol_manager.cc:205 #, fuzzy msgid "ControlProtocolManager: cannot load module \"%1\" (%2)" msgstr "LADSPA: δεν μποÏÏŽ να φοÏτώσω το module \"%1\" (%2)" -#: libs/ardour/control_protocol_manager.cc:188 +#: libs/ardour/control_protocol_manager.cc:213 #, fuzzy msgid "ControlProtocolManager: module \"%1\" has no descriptor function." msgstr "LADSPA: το module \"%1\" δεν έχει λειτουÏγία πεÏιγÏαφής." @@ -381,372 +591,104 @@ msgstr "αλλαγή ενεÏγοÏ" msgid "old-style crossfade information - no position information" msgstr "Ο κόμβος XML για την Τοποθεσία δεν έχει πληÏοφοÏίες ενάÏξεως" -#: libs/ardour/curve.cc:112 libs/ardour/insert.cc:454 -#: libs/ardour/session.cc:2452 libs/ardour/session.cc:2504 +#: libs/ardour/curve.cc:112 libs/ardour/globals.cc:340 +#: libs/ardour/insert.cc:454 libs/ardour/session.cc:2466 +#: libs/ardour/session.cc:2518 msgid "programming error: " msgstr "σφάλμα Ï€ÏογÏαμματισμοÏ: " -#: libs/ardour/cycle_timer.cc:35 +#: libs/ardour/cycle_timer.cc:37 msgid "CycleTimer::get_mhz(): can't open /proc/cpuinfo" msgstr "CycleTimer::get_mhz(): δεν ανοίγει το /proc/cpuinfo" -#: libs/ardour/cycle_timer.cc:47 +#: libs/ardour/cycle_timer.cc:49 msgid "CycleTimer::get_mhz(): cannot locate cpu MHz in /proc/cpuinfo" msgstr "CycleTimer::get_mhz(): δεν ευÏέθη το cpu MHz στο /proc/cpuinfo" -#: libs/ardour/cycle_timer.cc:70 +#: libs/ardour/cycle_timer.cc:72 msgid "cannot locate cpu MHz in /proc/cpuinfo" msgstr "δεν ευÏέθη το cpu MHz στο /proc/cpuinfo" -#: libs/ardour/destructive_filesource.cc:197 +#: libs/ardour/destructive_filesource.cc:188 msgid "DestructiveFileSource: \"%1\" bad read retval: %2 of %5 (%3: %4)" msgstr "" -#: libs/ardour/destructive_filesource.cc:210 -#: libs/ardour/destructive_filesource.cc:252 -#: libs/ardour/destructive_filesource.cc:259 +#: libs/ardour/destructive_filesource.cc:201 +#: libs/ardour/destructive_filesource.cc:243 +#: libs/ardour/destructive_filesource.cc:250 #, fuzzy msgid "DestructiveFileSource: \"%1\" bad write (%2)" msgstr "FileSource: \"%1\" κακή εγγÏαφή (%2)" -#: libs/ardour/diskstream.cc:337 -msgid "DiskStream: Session doesn't know about a Playlist called \"%1\"" -msgstr "" -"DiskStream: Η ΣυνεδÏία δεν γνωÏίζει για την λίστα ΑναπαÏ/γής με όνομα \"%1\"" - -#: libs/ardour/diskstream.cc:342 -msgid "DiskStream: Playlist \"%1\" isn't an audio playlist" -msgstr "DiskStream: Η Λίστα \"%1\" δεν είναι ηχητική λίστα αναπαÏ/γής" - -#: libs/ardour/diskstream.cc:433 -msgid "DiskStream %1: there is no existing playlist to make a copy of!" -msgstr "DiskStream %1: δεν υπάÏχει λίστα αναπαÏ/γής για να γίνει αντιγÏαφή!" - -#: libs/ardour/diskstream.cc:1113 libs/ardour/diskstream.cc:1124 -msgid "DiskStream %1: when refilling, cannot read %2 from playlist at frame %3" -msgstr "" -"DiskStream %1: κατα την αναγόμωση, δεν μπόÏεσα να διαβάσω %2 από τη λίστα " -"αναπαÏ/γής στο frame %3" - -#: libs/ardour/diskstream.cc:1256 -msgid "DiskStream %1: cannot read %2 from playlist at frame %3" -msgstr "" -"DiskStream %1: δεν μπόÏεσα να διαβάσω %2 από τη λίστα αναπαÏ/γής στο frame %3" - -#: libs/ardour/diskstream.cc:1623 libs/ardour/diskstream.cc:1640 -msgid "DiskStream %1: cannot write to disk" -msgstr "DiskStream %1: δεν μποÏÏŽ να γÏάψω στο δίσκο" - -#: libs/ardour/diskstream.cc:1700 -msgid "DiskStream \"%1\": cannot flush captured data to disk!" -msgstr "" -"DiskStream \"%1\": δεν γίνεται να αποÏÏιφθοÏν δειγματοληψίες στο δίσκο!" - -#: libs/ardour/diskstream.cc:1797 -msgid "%1: could not create region for complete audio file" -msgstr "%1: δεν μπόÏεσα να δημιουÏγήσω πεÏιοχή για ολόκληÏο audio file" - -#: libs/ardour/diskstream.cc:1820 -msgid "DiskStream: could not create region for captured audio!" -msgstr "DiskStream: δεν μπόÏεσα να δημιουÏγήσω πεÏιοχή για δειγματοληψίες!" - -#: libs/ardour/diskstream.cc:1875 -#, fuzzy -msgid "programmer error: %1" -msgstr "σφάλμα Ï€ÏογÏαμματισμοÏ: %1" - -#: libs/ardour/diskstream.cc:2155 -#, fuzzy -msgid "DiskStream: channel %1 out of range" -msgstr "DiskStream: κανάλι εκτός διαστήματος" - -#: libs/ardour/diskstream.cc:2180 -msgid "%1:%2 new capture file not initialized correctly" -msgstr "%1:%2 νέα δειγματοληψία δεν εκκινήθη σωστά" - -#: libs/ardour/diskstream.cc:2413 -msgid "Location \"%1\" not valid for track loop (start >= end)" -msgstr "Η Τοποθεσία \"%1\" δεν είναι ικανή για track loop (αÏχή >= τέλος)" - -#: libs/ardour/diskstream.cc:2491 -#, fuzzy -msgid "%1: cannot restore pending capture source file %2" -msgstr "Εισαγωγή: δεν μποÏÏŽ να ανοίξω το εισαγμένο αÏχείο ήχου \"%1\"" - -#: libs/ardour/diskstream.cc:2513 -msgid "%1: incorrect number of pending sources listed - ignoring them all" -msgstr "" - -#: libs/ardour/diskstream.cc:2529 -msgid "%1: cannot create whole-file region from pending capture sources" -msgstr "" - -#: libs/ardour/diskstream.cc:2541 -#, fuzzy -msgid "%1: cannot create region from pending capture sources" -msgstr "%1: δεν μπόÏεσα να δημιουÏγήσω πεÏιοχή για ολόκληÏο audio file" - -#: libs/ardour/filesource.cc:175 -msgid "FileSource: search path not set" -msgstr "FileSource: μονοπάτι αναζητήσεως δεν ετέθη" - -#: libs/ardour/filesource.cc:190 -msgid "FileSource: \"%1\" not found when searching %2 using %3" -msgstr "FileSource: \"%1\" δεν ευÏέθη όταν αναζητείτο %2 χÏησιμοποιώντας %3" - -#: libs/ardour/filesource.cc:196 -msgid "" -"FileSource: \"%1\" is ambigous when searching %2\n" -"\t" -msgstr "" -"FileSource: \"%1\" είναι αμφίβολο κατά την αναζήτηση του %2\n" -"\t" - -#: libs/ardour/filesource.cc:231 -msgid "Filesource: cannot find required file (%1): %2" -msgstr "Filesource: δεν ευÏέθη το απαιτοÏμενο αÏχείο (%1): %2" - -#: libs/ardour/filesource.cc:239 -msgid "Filesource: cannot check for existing file (%1): %2" -msgstr "Filesource: δεν μποÏÏŽ να ελέγξω για το υπάÏχον αÏχείο (%1): %2" - -#: libs/ardour/filesource.cc:245 libs/ardour/filesource.cc:1127 -#: libs/ardour/filesource.cc:1210 -msgid "FileSource: could not open \"%1\": (%2)" -msgstr "FileSource: δεν μπόÏεσα να ανοίξω \"%1\": (%2)" - -#: libs/ardour/filesource.cc:278 -msgid "FileSource: cannot write header in %1" -msgstr "FileSource: δεν μποÏÏŽ να γÏάψω επικεφαλίδα στο %1" - -#: libs/ardour/filesource.cc:293 -msgid "FileSource: cannot locate chunks in %1" -msgstr "FileSource: δεν μποÏÏŽ να ανιχνεÏσω κομμάτια στο %1" - -#: libs/ardour/filesource.cc:298 -msgid "FileSource: cannot read header in %1" -msgstr "FileSource: δεν μποÏÏŽ να διαβάσω επικεφαλίδα στο %1" - -#: libs/ardour/filesource.cc:303 -msgid "FileSource: cannot check header in %1" -msgstr "FileSource: δεν μποÏÏŽ να ελέγξω επικεφαλίδα στο %1" - -#: libs/ardour/filesource.cc:311 -#, fuzzy -msgid "FileSource: cannot initialize peakfile for %1 as %2" -msgstr "FileSource: δεν μποÏÏŽ να εκκινήσω το peakfile για %1" - -#: libs/ardour/filesource.cc:359 libs/ardour/insert.cc:525 -msgid "programming error: %1" -msgstr "σφάλμα Ï€ÏογÏαμματισμοÏ: %1" - -#: libs/ardour/filesource.cc:364 -#, fuzzy -msgid "cannot rename audio file for %1 to %2" -msgstr "δεν μποÏÏŽ να μετονομάσω την πηγή του audio file από %1 σε %2 (%3)" - -#: libs/ardour/filesource.cc:390 -msgid "FileSource: cannot seek to end of file" -msgstr "FileSource: δεν μποÏÏŽ να ανιχνεÏσω το τέλος του αÏχείου" - -#: libs/ardour/filesource.cc:395 -msgid "FileSource: cannot read RIFF/WAVE chunk from file" -msgstr "FileSource: δεν μποÏÏŽ να διαβάσω κομμάτι RIFF/WAVE από το αÏχείο" - -#: libs/ardour/filesource.cc:407 -msgid "FileSource %1: not a RIFF/WAVE file" -msgstr "FileSource %1: δεν είναι RIFF/WAVE αÏχείο" - -#: libs/ardour/filesource.cc:434 -msgid "FileSource: can't read a chunk" -msgstr "FileSource: δεν μποÏÏŽ να διαβάσω κομμάτι" - -#: libs/ardour/filesource.cc:451 -msgid "filesource: correcting mis-written RIFF file to become a RIFX: " -msgstr "" - -#: libs/ardour/filesource.cc:567 -msgid "FileSource: cannot get user information for BWF header (%1)" -msgstr "" -"FileSource: δεν μποÏÏŽ να βÏÏŽ πληÏοφοÏίες χÏήστη για επικεφαλίδα BWF (%1)" - -#: libs/ardour/filesource.cc:571 -msgid "FileSource: cannot get host information for BWF header (%1)" -msgstr "" -"FileSource: δεν μποÏÏŽ να βÏÏŽ πληÏοφοÏίες οικοδεσπότη(host) για επικεφαλίδα " -"BWF (%1)" - -#: libs/ardour/filesource.cc:716 -msgid "FileSource[%1]: cannot update data size: %2" -msgstr "FileSource[%1]: δεν μποÏÏŽ να ανανεώσω το μέγεθος δεδομένων: %2" - -#: libs/ardour/filesource.cc:733 -msgid "FileSource: can't find RIFF chunk info" -msgstr "FileSource: δεν ευÏέθησαν πληÏοφοÏίες για RIFF κομμάτι" - -#: libs/ardour/filesource.cc:737 -#, fuzzy -msgid "FileSource: can't find RIFX chunk info" -msgstr "FileSource: δεν ευÏέθησαν πληÏοφοÏίες για RIFF κομμάτι" - -#: libs/ardour/filesource.cc:758 -msgid "FileSource: can't read RIFF chunk" -msgstr "FileSource: δεν μποÏÏŽ να διαβάσω RIFF κομμάτι" - -#: libs/ardour/filesource.cc:768 -msgid "FileSource: can't find format chunk info" -msgstr "FileSource: δεν ευÏέθησαν πληÏοφοÏίες για το κομμάτι φοÏμαÏίσματος" - -#: libs/ardour/filesource.cc:773 -msgid "FileSource: can't read format chunk" -msgstr "FileSource: δεν μποÏÏŽ να διαβάσω το κομμάτι φοÏμαÏίσματος" - -#: libs/ardour/filesource.cc:782 -msgid "FileSource: can't find data chunk info" -msgstr "FileSource: δεν μποÏÏŽ να βÏÏŽ πληÏοφοÏίες για το κομμάτι δεδομένων" - -#: libs/ardour/filesource.cc:787 -msgid "FileSource: can't read data chunk" -msgstr "FileSource: δεν μποÏÏŽ να διαβάσω το κομμάτι δεδομένων" - -#: libs/ardour/filesource.cc:804 -msgid "" -"FileSource: cannot read Broadcast Wave data from existing audio file \"%1" -"\" (%2)" -msgstr "" -"FileSource: δεν μποÏÏŽ να διαβάσω δεδομένα Broadcast Wave από το υπάÏχον " -"αÏχείο \"%1\" (%2)" - -#: libs/ardour/filesource.cc:820 -msgid "" -"FileSource: cannot read Broadcast Wave coding history from audio file \"%1" -"\" (%2)" -msgstr "" -"FileSource: δεν μποÏÏŽ να διαβάσω το ιστοÏικό του κώδικα Broadcast Wave από " -"το αÏχείο \"%1\" (%2)" - -#: libs/ardour/filesource.cc:862 -#, fuzzy -msgid "" -"FileSource \"%1\" does not use valid sample format.\n" -"This is probably a programming error." -msgstr "" -"FileSource \"%1\" δεν χÏησιμοποιεί format μεταβλητής υποδιαστολής.\n" -"Αυτό πιθανόν να είναι σφάλμα Ï€ÏογÏαμματισμοÏ." - -#: libs/ardour/filesource.cc:901 -msgid "FileSource \"%1\" has no \"data\" chunk" -msgstr "FileSource \"%1\" δεν έχει \"data\" κομμάτι" - -#: libs/ardour/filesource.cc:906 -msgid "%1: data length in header (%2) differs from implicit size in file (%3)" -msgstr "" -"%1: το μέγεθος δεδομένων της επικεφαλίδας (%2) διαφέÏει από το δεδηλωμένο " -"μέγεθος στο αÏχείο (%3)" - -#: libs/ardour/filesource.cc:911 -msgid "\"%1\" has a sample rate of %2 instead of %3 as used by this session" -msgstr "" -"\"%1\" έχει Ïυθμό δειγματοληψίας %2 αντί του %3 όπως στην παÏοÏσα συνεδÏία" - -#: libs/ardour/filesource.cc:934 -msgid "FileSource: cannot write WAVE chunk: %1" -msgstr "FileSource: δεν μποÏÏŽ να γÏάψω WAVE κομμάτι: %1" - -#: libs/ardour/filesource.cc:978 -msgid "FileSource: cannot write format chunk: %1" -msgstr "FileSource: δεν μποÏÏŽ να γÏάψω format κομμάτι: %1" - -#: libs/ardour/filesource.cc:990 -msgid "FileSource: cannot data chunk: %1" -msgstr "FileSource: cδεν μποÏÏŽ να γÏάψω κομμάτι δεδομένων: %1" - -#: libs/ardour/filesource.cc:1103 libs/ardour/filesource.cc:1188 -msgid "FileSource: \"%1\" bad write (%2)" -msgstr "FileSource: \"%1\" κακή εγγÏαφή (%2)" - -#: libs/ardour/filesource.cc:1335 libs/ardour/session_state.cc:3093 -msgid "" -"there are already 1000 files with names like %1; versioning discontinued" -msgstr "ΥπάÏχουν ήδη 1000 αÏχεία με ονόματα όπως %1; μη-συνεχές versioning" - -#: libs/ardour/filesource.cc:1349 libs/ardour/session_state.cc:3107 -msgid "cannot rename audio file source from %1 to %2 (%3)" -msgstr "δεν μποÏÏŽ να μετονομάσω την πηγή του audio file από %1 σε %2 (%3)" - -#: libs/ardour/filesource.cc:1356 libs/ardour/session_state.cc:3122 -msgid "cannot remove peakfile %1 for %2 (%3)" -msgstr "δεν μποÏÏŽ να απαλοίψω το peakfile %1 για %2 (%3)" - -#: libs/ardour/globals.cc:82 +#: libs/ardour/globals.cc:109 msgid "no MIDI ports specified: no MMC or MTC control possible" msgstr "καμία MIDI θÏÏα δεν επελέχθη: έλεγχος MMC ή MTC αδÏνατος" -#: libs/ardour/globals.cc:97 +#: libs/ardour/globals.cc:124 msgid "MIDI port specifications for \"%1\" are not understandable." msgstr "Οι Ï€ÏοδιαγÏαφές της θÏÏας MIDI για το \"%1\" δεν είναι κατανοητές." -#: libs/ardour/globals.cc:110 libs/ardour/globals.cc:114 -#: libs/ardour/globals.cc:118 +#: libs/ardour/globals.cc:137 libs/ardour/globals.cc:141 +#: libs/ardour/globals.cc:145 msgid "default" msgstr "Ï€ÏοκαθοÏισμένο" -#: libs/ardour/globals.cc:146 +#: libs/ardour/globals.cc:173 msgid "No MMC control (MIDI port \"%1\" not available)" msgstr "ΧωÏίς έλεγχο MMC (θÏÏα MIDI \"%1\" μη διαθέσιμη)" -#: libs/ardour/globals.cc:152 +#: libs/ardour/globals.cc:179 msgid "No MTC support (MIDI port \"%1\" not available)" msgstr "ΧωÏίς έλεγχο MTC (θÏÏα MIDI \"%1\" μη διαθέσιμη)" -#: libs/ardour/globals.cc:157 +#: libs/ardour/globals.cc:184 #, fuzzy msgid "No MIDI parameter support (MIDI port \"%1\" not available)" msgstr "ΧωÏίς έλεγχο MTC (θÏÏα MIDI \"%1\" μη διαθέσιμη)" -#: libs/ardour/import.cc:71 +#: libs/ardour/import.cc:75 msgid "Import: cannot open input sound file \"%1\"" msgstr "Εισαγωγή: δεν μποÏÏŽ να ανοίξω το εισαγμένο αÏχείο ήχου \"%1\"" -#: libs/ardour/import.cc:76 +#: libs/ardour/import.cc:80 msgid "resampling audio" msgstr "επανά-ληψη(resampling) ήχου" -#: libs/ardour/import.cc:80 +#: libs/ardour/import.cc:84 msgid "Import: cannot open converted sound file \"%1\"" msgstr "Εισαγωγή: δεν μποÏÏŽ να ανοίξω το Ï„Ïοποποιημένο αÏχείο ήχου \"%1\"" -#: libs/ardour/import.cc:85 +#: libs/ardour/import.cc:89 msgid "Import: error while resampling sound file \"%1\"" msgstr "Εισαγωγή: σφάλμα κατά την Ï„Ïοποποίηση αÏχείου \"%1\"" -#: libs/ardour/import.cc:141 +#: libs/ardour/import.cc:148 msgid "Session::import_audiofile: cannot open new file source for channel %1" msgstr "" "ΣυνεδÏία::εισαγωγή_αÏχείου: δεν μποÏÏŽ να ανοίξω νέα πηγή αÏχείου για το " "κανάλι %1" -#: libs/ardour/import.cc:160 +#: libs/ardour/import.cc:167 msgid "converting audio" msgstr "μετατÏοπή ήχου" -#: libs/ardour/import.cc:192 +#: libs/ardour/import.cc:199 msgid "building region" msgstr "χτίσιμο πεÏιοχής" -#: libs/ardour/import.cc:194 +#: libs/ardour/import.cc:201 msgid "building regions" msgstr "χτίσιμο πεÏιοχών" -#: libs/ardour/import.cc:318 +#: libs/ardour/import.cc:325 msgid "Import: could not open temp file: %1" msgstr "Εισαγωγή: δεν μπόÏεσα να ανοίξω το temp αÏχείο: %1" -#: libs/ardour/import.cc:327 +#: libs/ardour/import.cc:334 msgid "Import: src_new() failed : %1" msgstr "Εισαγωγή: src_new() απέτυχε : %1" -#: libs/ardour/import.cc:355 +#: libs/ardour/import.cc:362 msgid "Import: %1" msgstr "Εισαγωγή: %1" @@ -805,153 +747,153 @@ msgstr "PortInsert: δεν μποÏεί να Ï€Ïοστεθεί θÏÏα εξό msgid "non-port insert XML used for port plugin insert" msgstr "εισαγωγή μη-θÏÏας XML για χÏήση σε εισαγωγή plugin θÏÏας" -#: libs/ardour/io.cc:585 +#: libs/ardour/io.cc:598 msgid "IO: cannot disconnect input port %1 from %2" msgstr "IO: δεν μποÏει να αποσυνδεθεί η θÏÏα εισόδου %1 από %2" -#: libs/ardour/io.cc:653 +#: libs/ardour/io.cc:666 msgid "IO: cannot disconnect output port %1 from %2" msgstr "IO: δεν μποÏεί να αποσυνδεθεί η θÏÏα εξόδου %1 από %2" -#: libs/ardour/io.cc:794 libs/ardour/io.cc:1138 libs/ardour/io.cc:1264 +#: libs/ardour/io.cc:807 libs/ardour/io.cc:1151 libs/ardour/io.cc:1277 #, c-format msgid "%s/out" msgstr "%s/out" -#: libs/ardour/io.cc:796 libs/ardour/io.cc:1140 libs/ardour/io.cc:1266 -#: libs/ardour/io.cc:2826 +#: libs/ardour/io.cc:809 libs/ardour/io.cc:1153 libs/ardour/io.cc:1279 +#: libs/ardour/io.cc:2849 #, c-format msgid "%s/out %u" msgstr "%s/out %u" -#: libs/ardour/io.cc:800 libs/ardour/io.cc:1145 libs/ardour/io.cc:1270 +#: libs/ardour/io.cc:813 libs/ardour/io.cc:1158 libs/ardour/io.cc:1283 msgid "IO: cannot register output port %1" msgstr "IO: δεν μποÏει να καταχώÏηθεί η θÏÏα εξόδου %1" -#: libs/ardour/io.cc:895 libs/ardour/io.cc:998 libs/ardour/io.cc:1104 +#: libs/ardour/io.cc:908 libs/ardour/io.cc:1011 libs/ardour/io.cc:1117 #, c-format msgid "%s/in" msgstr "%s/in" -#: libs/ardour/io.cc:897 libs/ardour/io.cc:1001 libs/ardour/io.cc:1107 -#: libs/ardour/io.cc:2796 +#: libs/ardour/io.cc:910 libs/ardour/io.cc:1014 libs/ardour/io.cc:1120 +#: libs/ardour/io.cc:2819 #, c-format msgid "%s/in %u" msgstr "%s/in %u" -#: libs/ardour/io.cc:901 libs/ardour/io.cc:1007 libs/ardour/io.cc:1112 +#: libs/ardour/io.cc:914 libs/ardour/io.cc:1020 libs/ardour/io.cc:1125 msgid "IO: cannot register input port %1" msgstr "IO: δεν μποÏεί να καταχώÏηθεί η θÏÏα εισόδου %1" -#: libs/ardour/io.cc:1528 +#: libs/ardour/io.cc:1541 msgid "IO::connecting_became_legal() called without a pending state node" msgstr "" "IO::connecting_became_legal() εκλήθη χωÏίς κόμβο καταστάσεως εν αναμονή" -#: libs/ardour/io.cc:1551 +#: libs/ardour/io.cc:1564 msgid "IO::ports_became_legal() called without a pending state node" msgstr "IO::ports_became_legal() εκλήθη χωÏίς κόμβο καταστάσεως εν αναμονή" -#: libs/ardour/io.cc:1581 +#: libs/ardour/io.cc:1594 msgid "incorrect XML node \"%1\" passed to IO object" msgstr "μη-σωστός κόμβος XML \"%1\" πέÏασε στο IO αντικείμενο" -#: libs/ardour/io.cc:1636 +#: libs/ardour/io.cc:1649 msgid "" "MIDI gain control specification for %1 is incomplete, so it has been ignored" msgstr "" "Η Ï€ÏοδιαγÏαφή ελέγχου του MIDI gain για το %1 είναι ημιτελής, με αποτέλεσμα " "να αγνοηθεί" -#: libs/ardour/io.cc:1726 libs/ardour/io.cc:1838 +#: libs/ardour/io.cc:1739 libs/ardour/io.cc:1851 msgid "Unknown connection \"%1\" listed for output of %2" msgstr "Άγνωστη σÏνδεση \"%1\" καταχωÏήθη για την έξοδο του %2" -#: libs/ardour/io.cc:1728 libs/ardour/io.cc:1840 +#: libs/ardour/io.cc:1741 libs/ardour/io.cc:1853 #, fuzzy msgid "out 1" msgstr "out %lu" -#: libs/ardour/io.cc:1729 libs/ardour/io.cc:1841 +#: libs/ardour/io.cc:1742 libs/ardour/io.cc:1854 msgid "No output connections available as a replacement" msgstr "" -#: libs/ardour/io.cc:1733 libs/ardour/io.cc:1845 +#: libs/ardour/io.cc:1746 libs/ardour/io.cc:1858 msgid "Connection %1 was not available - \"out 1\" used instead" msgstr "" -#: libs/ardour/io.cc:1747 +#: libs/ardour/io.cc:1760 msgid "%1: cannot create I/O ports" msgstr "%1: θÏÏες I/O δεν μποÏοÏν να δημιουÏγηθοÏν" -#: libs/ardour/io.cc:1854 +#: libs/ardour/io.cc:1867 msgid "improper output channel list in XML node (%1)" msgstr "ασαφής λίστα καναλιών εξόδου στον κόμβο XML (%1)" -#: libs/ardour/io.cc:1939 +#: libs/ardour/io.cc:1952 msgid "IO: badly formed string in XML node for outputs \"%1\"" msgstr "IO: δÏσμοÏφη γÏαμμή στον κόμβο XML για τις εξόδους \"%1\"" -#: libs/ardour/io.cc:1944 +#: libs/ardour/io.cc:1957 msgid "IO: bad output string in XML node \"%1\"" msgstr "IO: κακή γÏαμμή εξόδουστον κόμβο XML \"%1\"" -#: libs/ardour/io.cc:2502 +#: libs/ardour/io.cc:2525 msgid "%1: could not open automation event file \"%2\"" msgstr "%1: δεν μπόÏεσα να ανοίξω το αÏχείο συμβάντων Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï \"%2\"" -#: libs/ardour/io.cc:2541 +#: libs/ardour/io.cc:2564 msgid "%1: cannot open automation event file \"%2\"" msgstr "%1: δεν μποÏÏŽ να ανοίξω το αÏχείο συμβάντων Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï \"%2\"" -#: libs/ardour/io.cc:2556 +#: libs/ardour/io.cc:2579 msgid "badly formed version number in automation event file \"%1\"" msgstr "δÏσμοÏφος αÏιθμός εκδόσεως στο αÏχείο συμβάντων Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï \"%1\"" -#: libs/ardour/io.cc:2560 +#: libs/ardour/io.cc:2583 msgid "no version information in automation event file \"%1\"" msgstr "" "δεν υπάÏχουν πληÏοφοÏίες πεÏί εκδόσεων στο αÏχείο συμβάντων Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï \"%1" "\"" -#: libs/ardour/io.cc:2565 +#: libs/ardour/io.cc:2588 msgid "mismatched automation event file version (%1)" msgstr "αταίÏιαστη έκδοση αÏχείου συμβάντων Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï (%1)" -#: libs/ardour/io.cc:2573 +#: libs/ardour/io.cc:2596 msgid "badly formatted automation event record at line %1 of %2 (ignored)" msgstr "" "κακώς φοÏμαÏισμένη καταγÏαφή συμβάντων Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï ÏƒÏ„Î· γÏαμμή %1 of %2 " "(αγνοήθηκε)" -#: libs/ardour/io.cc:2593 +#: libs/ardour/io.cc:2616 msgid "dubious automation event found (and ignored)" msgstr "αβέβαιο συμβάν Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï ÎµÏ…Ïέθηκε (και αγνοήθηκε)" -#: libs/ardour/io.cc:2597 libs/ardour/panner.cc:437 +#: libs/ardour/io.cc:2620 libs/ardour/panner.cc:438 #: libs/ardour/redirect.cc:148 msgid "loaded from disk" msgstr "φοÏτώθηκε από το δίσκο" -#: libs/ardour/io.cc:2768 +#: libs/ardour/io.cc:2791 msgid "automation write/touch" msgstr "αυτοματισμός εγγÏαφή/αφή(write/touch)" -#: libs/ardour/ladspa_plugin.cc:86 +#: libs/ardour/ladspa_plugin.cc:87 msgid "LADSPA: module has no descriptor function." msgstr "LADSPA: το module δεν έχει ενδεικτική λειτουÏγία." -#: libs/ardour/ladspa_plugin.cc:91 +#: libs/ardour/ladspa_plugin.cc:92 msgid "LADSPA: plugin has gone away since discovery!" msgstr "LADSPA: το plugin την 'κοπάνισε' μετά την ανακάλυψη του!" -#: libs/ardour/ladspa_plugin.cc:98 +#: libs/ardour/ladspa_plugin.cc:99 msgid "LADSPA: \"%1\" cannot be used, since it cannot do inplace processing" msgstr "" "LADSPA: \"%1\" δεν μποÏεί να χÏησιμοποιηθεί, εφ'όσον δεν μποÏεί να κάνει επι " "τόπου επεξεÏγασία" -#: libs/ardour/ladspa_plugin.cc:328 +#: libs/ardour/ladspa_plugin.cc:329 msgid "" "illegal parameter number used with plugin \"%1\". This mayindicate a change " "in the plugin design, and presets may beinvalid" @@ -960,20 +902,20 @@ msgstr "" "ενδείκνυται αλλαγή στο σχεδιασμό του plugin, και οι Ïυθμίσεις ίσως να είναι " "άκυÏες" -#: libs/ardour/ladspa_plugin.cc:429 +#: libs/ardour/ladspa_plugin.cc:430 #, fuzzy msgid "Bad node sent to LadspaPlugin::set_state" msgstr "Κακή αποστολή κόμβου εστάλη στο LadspaPlugin::set_state" -#: libs/ardour/ladspa_plugin.cc:442 +#: libs/ardour/ladspa_plugin.cc:443 msgid "LADSPA: no ladspa port number" msgstr "LADSPA: κανείς αÏιθμός θÏÏας ladspa" -#: libs/ardour/ladspa_plugin.cc:448 +#: libs/ardour/ladspa_plugin.cc:449 msgid "LADSPA: no ladspa port data" msgstr "LADSPA: κανένα δεδομένο θÏÏας ladspa" -#: libs/ardour/ladspa_plugin.cc:497 +#: libs/ardour/ladspa_plugin.cc:498 msgid "" "LADSPA LadspaPlugin MIDI control specification for port %1 is incomplete, so " "it has been ignored" @@ -981,131 +923,131 @@ msgstr "" "Ο καθοÏισμός ελέγχου LADSPA LadspaPlugin για MIDI για την θÏÏα %1 είναι " "ημιτελής, έτσι αγνοήθηκε." -#: libs/ardour/location.cc:268 +#: libs/ardour/location.cc:269 msgid "incorrect XML node passed to Location::set_state" msgstr "λανθασμένος κόμβος XML πέÏασε στην Τοποθεσία::set_state" -#: libs/ardour/location.cc:275 +#: libs/ardour/location.cc:276 msgid "XML node for Location has no name information" msgstr "Ο κόμβος XML για την Τοποθεσία δεν έχει πληÏοφοÏίες ονόματος" -#: libs/ardour/location.cc:282 +#: libs/ardour/location.cc:283 msgid "XML node for Location has no start information" msgstr "Ο κόμβος XML για την Τοποθεσία δεν έχει πληÏοφοÏίες ενάÏξεως" -#: libs/ardour/location.cc:293 +#: libs/ardour/location.cc:294 msgid "XML node for Location has no end information" msgstr "Ο κόμβος XML για την Τοποθεσία δεν έχει πληÏοφοÏίες τέλους" -#: libs/ardour/location.cc:302 +#: libs/ardour/location.cc:303 msgid "XML node for Location has no flags information" msgstr "Ο κόμβος XML για την Τοποθεσία δεν έχει πληÏοφοÏίες για σημαίες(flags)" -#: libs/ardour/location.cc:390 +#: libs/ardour/location.cc:391 msgid "Locations: attempt to use unknown location as selected location" msgstr "" "Τοποθεσίες: απόπειÏα να χÏησιμοποιηθεί άγνωστη τοποθεσία σαν επιλεγμένη " "τοποθεσία" -#: libs/ardour/location.cc:417 libs/ardour/playlist.cc:1187 +#: libs/ardour/location.cc:418 libs/ardour/playlist.cc:1187 msgid "clear" msgstr "εκκαθάÏιση" -#: libs/ardour/location.cc:442 +#: libs/ardour/location.cc:443 msgid "clear markers" msgstr "εκκαθάÏιση στιγμάτων" -#: libs/ardour/location.cc:470 +#: libs/ardour/location.cc:471 msgid "clear ranges" msgstr "εκκαθάÏιση διαστημάτων" -#: libs/ardour/location.cc:488 +#: libs/ardour/location.cc:489 msgid "add" msgstr "Ï€Ïόσθεση" -#: libs/ardour/location.cc:526 +#: libs/ardour/location.cc:527 msgid "remove" msgstr "απαλοιφή" -#: libs/ardour/location.cc:566 +#: libs/ardour/location.cc:567 msgid "incorrect XML mode passed to Locations::set_state" msgstr "λανθασμένο XML mode πέÏασε στις Τοποθεσίες::set_state" -#: libs/ardour/mtc_slave.cc:195 +#: libs/ardour/mtc_slave.cc:196 msgid "MTC Slave: atomic read of current time failed, sleeping!" msgstr "" "MTC Slave: ατομική ανάγνωση του Ï„Ïέχοντος χÏόνου απέτυχε, πίσω για Ïπνο!" -#: libs/ardour/named_selection.cc:76 +#: libs/ardour/named_selection.cc:77 msgid "Chunk %1 uses an unknown playlist \"%2\"" msgstr "Το κομμάτι %1 χÏησιμοποιεί άγνωστη λίστα αναπαÏ/γής \"%2\"" -#: libs/ardour/named_selection.cc:79 +#: libs/ardour/named_selection.cc:80 msgid "Chunk %1 contains misformed playlist information" msgstr "Το κομμάτι %1 πεÏιέχει δÏσμοÏφες πληÏοφοÏίες για τη λίστα αναπαÏ/γής" -#: libs/ardour/panner.cc:255 +#: libs/ardour/panner.cc:256 #, fuzzy msgid "MIDI pan control specification is incomplete, so it has been ignored" msgstr "" "Η Ï€ÏοδιαγÏαφή ελέγχου του MIDI gain για το %1 είναι ημιτελής, με αποτέλεσμα " "να αγνοηθεί" -#: libs/ardour/panner.cc:360 +#: libs/ardour/panner.cc:361 msgid "automation write pass" msgstr "πέÏασμα εγγÏαφής αυτοματισμοÏ" -#: libs/ardour/panner.cc:400 +#: libs/ardour/panner.cc:401 #, c-format msgid "error writing pan automation file (%s)" msgstr "σφάλμα στην εγγÏαφή του pan στο αÏχείο Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï (%s)" -#: libs/ardour/panner.cc:428 +#: libs/ardour/panner.cc:429 msgid "" "badly formatted pan automation event record at line %1 of %2 (ignored) [%3]" msgstr "" "δÏσμοÏφη εγγÏαφή συμβάντος pan Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï ÏƒÏ„Î· γÏαμμή %1 of %2 (αγνοήθηκε) " "[%3]" -#: libs/ardour/panner.cc:943 +#: libs/ardour/panner.cc:944 msgid "badly-formed positional data for Multi2dPanner - ignored" msgstr "δÏσμοÏφα δεδομένα θέσεως για το Multi2dPanner - αγνοήθηκε" -#: libs/ardour/panner.cc:1236 +#: libs/ardour/panner.cc:1237 msgid "cannot open pan automation file \"%1\" for saving (%s)" msgstr "" "δεν μποÏÏŽ να ανοίξω αÏχείο Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï Ï„Î¿Ï… pan \"%1\" για αποθήκευση (%s)" -#: libs/ardour/panner.cc:1272 +#: libs/ardour/panner.cc:1273 msgid "cannot open pan automation file %1 (%2)" msgstr "δεν μποÏÏŽ να ανοίξω αÏχείο Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï Ï„Î¿Ï… pan %1 (%2)" -#: libs/ardour/panner.cc:1285 +#: libs/ardour/panner.cc:1286 msgid "badly formed version number in pan automation event file \"%1\"" msgstr "" "δÏσμοÏφος αÏιθμός εκδόσεως στο αÏχείο συμβάντων Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï Ï„Î¿Ï… pan \"%1\"" -#: libs/ardour/panner.cc:1289 +#: libs/ardour/panner.cc:1290 msgid "" "no version information in pan automation event file \"%1\" (first line = %2)" msgstr "" "καμία πληÏοφοÏία εκδόσεως στο αÏχείο συμβάντων Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï Ï„Î¿Ï… pan \"%1" "\" (Ï€Ïώτη γÏαμμή = %2)" -#: libs/ardour/panner.cc:1295 +#: libs/ardour/panner.cc:1296 msgid "mismatched pan automation event file version (%1)" msgstr "αταίÏιαστη έκδοση αÏχείου συμβάντων Î±Ï…Ï„Î¿Î¼Î±Ï„Î¹ÏƒÎ¼Î¿Ï Î³Î¹Î± το pan (%1)" -#: libs/ardour/panner.cc:1309 +#: libs/ardour/panner.cc:1310 msgid "too many panner states found in pan automation file %1" msgstr "" "πάÏα πολλές καταστάσεις panner ευÏέθησαν στο αÏχείο των αυτοματισμών pan %1" -#: libs/ardour/panner.cc:1450 +#: libs/ardour/panner.cc:1451 msgid "Unknown panner plugin \"%1\" found in pan state - ignored" msgstr "Άγνωστο plugin για panner \"%1\" ευÏέθη στην κατάσταση pan - αγνοήθηκε" -#: libs/ardour/panner.cc:1456 +#: libs/ardour/panner.cc:1457 msgid "panner plugin node has no type information!" msgstr "ο κόμβος για τα plugin του panner δεν έχει πληÏοφοÏίες Ï„Ïπου!" @@ -1160,63 +1102,63 @@ msgstr "Playlist: δεν μποÏÏŽ να δημιουÏγήσω ΠεÏιοχή msgid "nudged" msgstr "νυχθέν" -#: libs/ardour/playlist_factory.cc:26 libs/ardour/playlist_factory.cc:41 +#: libs/ardour/playlist_factory.cc:49 libs/ardour/playlist_factory.cc:64 msgid "" "programming error: Playlist::createRegion called with unknown Region type" msgstr "" "σφάλμα Ï€ÏογÏαμματισμοÏ: Playlist::createRegion εκλήθη με άγνωστο Ï„Ïπο Πε" -#: libs/ardour/playlist_factory.cc:63 +#: libs/ardour/playlist_factory.cc:86 msgid "" "programming error: Playlist::copyPlaylist called with unknown Playlist type" msgstr "" "σφάλμα Ï€ÏογÏαμματισμοÏ: Playlist::copyPlaylist με άγνωστο Ï„Ïπο Playlist" -#: libs/ardour/plugin.cc:327 +#: libs/ardour/plugin.cc:328 msgid "Could not locate HOME. Preset not saved." msgstr "Δεν μπόÏεσα να βÏÏŽ το HOME. ΠÏο-ÏÏθμιση δεν αποθηκεÏθηκε." -#: libs/ardour/plugin.cc:337 libs/ardour/plugin.cc:343 +#: libs/ardour/plugin.cc:338 libs/ardour/plugin.cc:344 msgid "Could not create %1. Preset not saved. (%2)" msgstr "Δεν μπόÏεσα να δημιουÏγήσω το %1. ΠÏο-ÏÏθμιση δεν αποθηκεÏθηκε. (%2)" -#: libs/ardour/plugin.cc:348 +#: libs/ardour/plugin.cc:349 msgid "Error saving presets file %1." msgstr "Σφάλμα στην αποθήκευση αÏχείου Ï€Ïο-Ïυθμίσεων %1." -#: libs/ardour/plugin_manager.cc:193 +#: libs/ardour/plugin_manager.cc:194 msgid "Could not parse rdf file: %1" msgstr "Δεν μπόÏεσα να αναλÏσω το αÏχείο rdf: %1" -#: libs/ardour/plugin_manager.cc:234 +#: libs/ardour/plugin_manager.cc:235 msgid "LADSPA: cannot load module \"%1\" (%2)" msgstr "LADSPA: δεν μποÏÏŽ να φοÏτώσω το module \"%1\" (%2)" -#: libs/ardour/plugin_manager.cc:241 +#: libs/ardour/plugin_manager.cc:242 msgid "LADSPA: module \"%1\" has no descriptor function." msgstr "LADSPA: το module \"%1\" δεν έχει λειτουÏγία πεÏιγÏαφής." -#: libs/ardour/plugin_manager.cc:296 +#: libs/ardour/plugin_manager.cc:297 msgid "VST: cannot load module from \"%1\"" msgstr "VST: δεν μποÏÏŽ να φοÏτώσω module από \"%1\"" -#: libs/ardour/plugin_manager.cc:301 +#: libs/ardour/plugin_manager.cc:302 msgid "You asked ardour to not use any VST plugins" msgstr "" -#: libs/ardour/plugin_manager.cc:304 +#: libs/ardour/plugin_manager.cc:305 msgid "This version of ardour has no support for VST plugins" msgstr "Η παÏοÏσα έκδοση του ardour δεν υποστηÏίζει VST plugins" -#: libs/ardour/plugin_manager.cc:311 +#: libs/ardour/plugin_manager.cc:312 msgid "LADSPA: cannot load module from \"%1\"" msgstr "LADSPA: δεν μποÏÏŽ να φοÏτώσω module από \"%1\"" -#: libs/ardour/plugin_manager.cc:373 libs/ardour/plugin_manager.cc:385 +#: libs/ardour/plugin_manager.cc:374 libs/ardour/plugin_manager.cc:386 msgid "Unknown" msgstr "Άγνωστο" -#: libs/ardour/plugin_manager.cc:463 +#: libs/ardour/plugin_manager.cc:464 msgid "" "VST plugin %1 does not support processReplacing, and so cannot be used in " "ardour at this time" @@ -1232,11 +1174,11 @@ msgstr "δεν μποÏÏŽ να ανοίξω το Ï€Ïόσφατο αÏχείο msgid "programming error: unknown Redirect type in Redirect::Clone!\n" msgstr "σφάλμα Ï€ÏογÏαμματισμοÏ: άγνωστος Ï„Ïπος Redirect στο Redirect::Clone!\n" -#: libs/ardour/redirect.cc:102 libs/ardour/utils.cc:199 +#: libs/ardour/redirect.cc:102 libs/ardour/utils.cc:203 msgid "pre" msgstr "pre" -#: libs/ardour/redirect.cc:104 libs/ardour/utils.cc:202 +#: libs/ardour/redirect.cc:104 libs/ardour/utils.cc:206 msgid "post" msgstr "post" @@ -1293,67 +1235,67 @@ msgstr "" msgid "active_changed" msgstr "αλλαγή_ενεÏγοÏ" -#: libs/ardour/region.cc:884 +#: libs/ardour/region.cc:885 msgid "Session: XMLNode describing a Region is incomplete (no id)" msgstr "ΣυνεδÏία: XMLΚόμβος που πεÏιγÏάφει ΠεÏιοχή είναι ημιτελής (χωÏίς id)" -#: libs/ardour/region.cc:891 +#: libs/ardour/region.cc:892 msgid "Session: XMLNode describing a Region is incomplete (no name)" msgstr "" "ΣυνεδÏία: XMLΚόμβος που πεÏιγÏάφει ΠεÏιοχή είναι ημιτελής (χωÏίς όνομα)" -#: libs/ardour/route.cc:79 libs/ardour/session.cc:1541 -#: libs/ardour/session.cc:1547 libs/ardour/session.cc:3064 +#: libs/ardour/route.cc:79 libs/ardour/session.cc:1554 +#: libs/ardour/session.cc:1560 libs/ardour/session.cc:3093 msgid "signal" msgstr "σήμα" -#: libs/ardour/route.cc:1433 +#: libs/ardour/route.cc:1430 msgid "Could not get state of route. Problem with save_automation" msgstr "" "Δεν μπόÏεσα να πάÏω κατάσταση διαδÏομής. ΠÏόβλημα με αποθήκευση_αυτοματισμοÏ" -#: libs/ardour/route.cc:1485 +#: libs/ardour/route.cc:1482 msgid "Send construction failed" msgstr "Αποστολή κατασκευής απέτυχε" -#: libs/ardour/route.cc:1507 +#: libs/ardour/route.cc:1504 msgid "unknown Insert type \"%1\"; ignored" msgstr "άγνωστος Ï„Ïπος Λήψης(Insert) \"%1\"... αγνοήθηκε" -#: libs/ardour/route.cc:1513 +#: libs/ardour/route.cc:1510 msgid "Insert XML node has no type property" msgstr "Εισηχθέντας κόμβος XML δεν έχει στοιχεία Ï„Ïπου" -#: libs/ardour/route.cc:1518 +#: libs/ardour/route.cc:1515 msgid "insert could not be created. Ignored." msgstr "εισαγωγή δεν μπόÏεσε να δημιουÏγηθεί. Αγνοήθηκε." -#: libs/ardour/route.cc:1536 +#: libs/ardour/route.cc:1533 msgid "Bad node sent to Route::set_state() [%1]" msgstr "Κακός κόμβος εστάλη στο Route::set_state() [%1]" -#: libs/ardour/route.cc:1595 +#: libs/ardour/route.cc:1592 msgid "Route %1: unknown edit group \"%2 in saved state (ignored)" msgstr "" "Route %1: άγνωστη ομάδα επεξεÏγασίας \"%2 στην αποθηκευμένη κατάσταση " "(αγνοήθηκε)" -#: libs/ardour/route.cc:1611 libs/ardour/route.cc:1615 +#: libs/ardour/route.cc:1608 libs/ardour/route.cc:1612 msgid "badly formed order key string in state file! [%1] ... ignored." msgstr "" "δÏσμοÏφη γÏαμμή ÎºÎ»ÎµÎ¹Î´Î¹Î¿Ï Ï„Î±Î¾Î¹Î½Î¿Î¼Î®ÏƒÎµÏ‰Ï‚ στο αÏχείο καταστάσεως ! [%1] ... " "αγνοήθηκε." -#: libs/ardour/route.cc:1696 libs/ardour/route.cc:1823 +#: libs/ardour/route.cc:1693 libs/ardour/route.cc:1820 msgid "[control]" msgstr "[έλεγχος]" -#: libs/ardour/route.cc:1716 +#: libs/ardour/route.cc:1713 msgid "Route %1: unknown mix group \"%2 in saved state (ignored)" msgstr "" "Route %1: άγνωστη ομάδα μίξεως \"%2 στην αποθηκευμένη κατάσταση (αγνοήθηκε)" -#: libs/ardour/route.cc:1745 libs/ardour/route.cc:1753 +#: libs/ardour/route.cc:1742 libs/ardour/route.cc:1750 #, fuzzy msgid "" "MIDI mute control specification for %1 is incomplete, so it has been ignored" @@ -1361,207 +1303,202 @@ msgstr "" "Η Ï€ÏοδιαγÏαφή ελέγχου του MIDI gain για το %1 είναι ημιτελής, με αποτέλεσμα " "να αγνοηθεί" -#: libs/ardour/send.cc:98 +#: libs/ardour/send.cc:99 msgid "XML node describing a send is missing a Redirect node" msgstr "Στον κόμβο XML όπου πεÏιγÏάφεται ένα send λείπει ένας κόμβος Redirect" -#: libs/ardour/session.cc:99 +#: libs/ardour/session.cc:103 #, fuzzy msgid "Could not resolve path: %1 (%2)" msgstr "Source: δεν μποÏÏŽ να ανοίξω το peakpath \"%1\" (%2)" -#: libs/ardour/session.cc:111 +#: libs/ardour/session.cc:115 msgid "cannot check session path %1 (%2)" msgstr "δεν μποÏÏŽ να ελέγξω το μονοπάτι συνεδÏίας %1 (%2)" -#: libs/ardour/session.cc:141 +#: libs/ardour/session.cc:145 msgid "cannot check statefile %1 (%2)" msgstr "δεν μποÏÏŽ να ελέγξω το αÏχείο κατάστασεως %1 (%2)" -#: libs/ardour/session.cc:177 +#: libs/ardour/session.cc:181 msgid "%1 is not an Ardour snapshot file" msgstr "Το %1 δεν έιναι αÏχείο-στιγμιότυπο του Ardour" -#: libs/ardour/session.cc:194 +#: libs/ardour/session.cc:198 msgid "cannot determine current working directory (%1)" msgstr "δεν μποÏÏŽ να καθοÏίσω τον Ï„Ïέχοντα ενεÏγό φάκελο(directory) (%1)" -#: libs/ardour/session.cc:211 +#: libs/ardour/session.cc:215 msgid "unknown file type for session %1" msgstr "άγνωστος Ï„Ïπος αÏχείου για την συνεδÏία %1" -#: libs/ardour/session.cc:316 +#: libs/ardour/session.cc:320 msgid "monitor" msgstr "monitor" -#: libs/ardour/session.cc:323 +#: libs/ardour/session.cc:327 msgid "master" msgstr "master" -#: libs/ardour/session.cc:607 +#: libs/ardour/session.cc:611 msgid "could not setup Click I/O" msgstr "Δεν μπόÏεσα να διαμοÏφώσω το I/O του ΜετÏονόμου(click)" -#: libs/ardour/session.cc:628 +#: libs/ardour/session.cc:632 msgid "cannot setup Click I/O" msgstr "Δεν μποÏÏŽ να διαμοÏφώσω το I/O του ΜετÏονόμου(click)" -#: libs/ardour/session.cc:650 +#: libs/ardour/session.cc:654 msgid "cannot create Auditioner: no auditioning of regions possible" msgstr "δεν μποÏÏŽ να δημιουÏγήσω τον ΑκÏοατή: καμία ακÏόαση πεÏιοχών δυνατή" -#: libs/ardour/session.cc:662 +#: libs/ardour/session.cc:666 #, fuzzy, c-format msgid "out %" msgstr "out %lu" -#: libs/ardour/session.cc:674 +#: libs/ardour/session.cc:678 #, c-format msgid "in %" msgstr "" -#: libs/ardour/session.cc:688 +#: libs/ardour/session.cc:692 #, c-format msgid "out %+%" msgstr "" -#: libs/ardour/session.cc:702 +#: libs/ardour/session.cc:706 #, c-format msgid "in %+%" msgstr "" -#: libs/ardour/session.cc:735 +#: libs/ardour/session.cc:739 msgid "cannot setup master inputs" msgstr "δεν μποÏÏŽ να διαμοÏφώσω τις master εισόδους" -#: libs/ardour/session.cc:743 +#: libs/ardour/session.cc:747 msgid "cannot setup master outputs" msgstr "δεν μποÏÏŽ να διαμοÏφώσω τις master εξόδους" -#: libs/ardour/session.cc:754 +#: libs/ardour/session.cc:758 #, fuzzy msgid "Master Out" msgstr "master" -#: libs/ardour/session.cc:820 +#: libs/ardour/session.cc:830 msgid "cannot setup control inputs" msgstr "δεν μποÏÏŽ να διαμοÏφώσω τις εισόδους ελέγχου" -#: libs/ardour/session.cc:828 +#: libs/ardour/session.cc:838 msgid "cannot set up master outputs" msgstr "δεν μποÏÏŽ να διαμοÏφώσω τις εξόδους ελέγχου" -#: libs/ardour/session.cc:1100 +#: libs/ardour/session.cc:1110 msgid "Session: you can't use that location for auto punch (start <= end)" msgstr "" "ΣυνεδÏία: δεν μποÏείτε να χÏησιμοποιήσετε αυτήν την τοποθεσία για auto punch " "(αÏχή <= τέλος)" -#: libs/ardour/session.cc:1179 +#: libs/ardour/session.cc:1189 msgid "Session: you can't use a mark for auto loop" msgstr "ΣυνεδÏία: δεν μποÏείτε να χÏησιμοποιήσετε στίγμα για auto loop" -#: libs/ardour/session.cc:1559 +#: libs/ardour/session.cc:1572 msgid "feedback loop setup between %1 and %2" msgstr "διαμόÏφωση feedback loop ανάμεσα σε %1 και %2" -#: libs/ardour/session.cc:1711 libs/ardour/session.cc:1808 +#: libs/ardour/session.cc:1724 libs/ardour/session.cc:1821 msgid "cannot configure %1 in/%2 out configuration for new audio track" msgstr "δεν μποÏÏŽ να διαμοÏφώσω %1 in/%2 out διάταξη για νέο κανάλι ήχου" -#: libs/ardour/session.cc:1767 +#: libs/ardour/session.cc:1780 msgid "Session: could not create new audio track." msgstr "ΣυνεδÏία: δεν μπόÏεσα να δημιουÏγήσω νέο κανάλι ήχου." -#: libs/ardour/session.cc:1857 +#: libs/ardour/session.cc:1870 msgid "Session: could not create new route." msgstr "ΣυνεδÏία: δεν μπόÏεσα να δημιουÏγήσω διαδÏομή." -#: libs/ardour/session.cc:2340 +#: libs/ardour/session.cc:2354 msgid "cannot create new name for region \"%1\"" msgstr "δεν μποÏÏŽ να δημιουÏγήσω νέο όνομα για την πεÏιοχή \"%1\"" -#: libs/ardour/session.cc:2404 +#: libs/ardour/session.cc:2418 msgid "too many regions with names like %1" msgstr "πάÏα πολλές πεÏιοχές με ονόματα σαν %1" -#: libs/ardour/session.cc:2860 +#: libs/ardour/session.cc:2883 msgid "There are already %1 recordings for %2, which I consider too many." msgstr "ΥπάÏχουν ήδη %1 εγγÏαφές για %2, τις οποίες θεωÏÏŽ πάÏα πολλές." -#: libs/ardour/session.cc:3229 +#: libs/ardour/session.cc:3258 msgid "programming error: unknown type of Insert created!" msgstr "σφάλμα Ï€ÏογÏαμματισμοÏ: άγνωστος Ï„Ïπος Εισόδου εδημιουÏγήθη!" -#: libs/ardour/session.cc:3235 +#: libs/ardour/session.cc:3264 msgid "programming error: unknown type of Redirect created!" msgstr "σφάλμα Ï€ÏογÏαμματισμοÏ: άγνωστος Ï„Ïπος Redirect εδημιουÏγήθη!" -#: libs/ardour/session.cc:3258 +#: libs/ardour/session.cc:3287 msgid "programming error: unknown type of Insert deleted!" msgstr "σφάλμα Ï€ÏογÏαμματισμοÏ: άγνωστος Ï„Ïπος of Insert διεγÏάφη!" -#: libs/ardour/session.cc:3264 +#: libs/ardour/session.cc:3293 msgid "programming error: unknown type of Redirect deleted!" msgstr "σφάλμα Ï€ÏογÏαμματισμοÏ: άγνωστος Ï„Ïπος of Redirect διεγÏάφη!" -#: libs/ardour/session.cc:3605 +#: libs/ardour/session.cc:3636 msgid "too many bounced versions of playlist \"%1\"" msgstr "πάÏα πολλές bounced εκδόσεις της Playlist \"%1\"" -#: libs/ardour/session.cc:3614 +#: libs/ardour/session.cc:3649 msgid "cannot create new audio file \"%1\" for %2" msgstr "δεν μποÏÏŽ να δημιουÏγήσω νέο αÏχείο ήχου \"%1\" για %2" -#: libs/ardour/session_butler.cc:81 libs/ardour/session_midi.cc:1183 -#: libs/ardour/source.cc:233 -msgid "Cannot create transport request signal pipe (%1)" -msgstr "Δεν μποÏÏŽ να δημιουÏγήσω transport request signal pipe (%1)" - -#: libs/ardour/session_butler.cc:86 libs/ardour/session_butler.cc:91 +#: libs/ardour/session_butler.cc:85 libs/ardour/session_butler.cc:90 #, fuzzy msgid "UI: cannot set O_NONBLOCK on butler request pipe (%1)" msgstr "UI: δεν μποÏÏŽ να θέσω O_NONBLOCK στο signal read pipe (%1)" -#: libs/ardour/session_butler.cc:96 +#: libs/ardour/session_butler.cc:95 msgid "Session: could not create butler thread" msgstr "ΣυνεδÏία: δεν μπόÏεσα να δημιουÏγήσω δέσμη με τον butler" -#: libs/ardour/session_butler.cc:190 +#: libs/ardour/session_butler.cc:189 msgid "poll on butler request pipe failed (%1)" msgstr "" -#: libs/ardour/session_butler.cc:197 +#: libs/ardour/session_butler.cc:196 #, fuzzy msgid "Error on butler thread request pipe" msgstr "Σφάλμα στο transport thread request pipe" -#: libs/ardour/session_butler.cc:239 +#: libs/ardour/session_butler.cc:238 #, fuzzy msgid "Error reading from butler request pipe" msgstr "Σφάλμα στην ανάγνωση από transport request pipe" -#: libs/ardour/session_butler.cc:276 +#: libs/ardour/session_butler.cc:275 msgid "Butler read ahead failure on dstream %1" msgstr "Αποτυχία Ï€Ïοανάγνωσης Butler στο dstream %1" -#: libs/ardour/session_butler.cc:320 +#: libs/ardour/session_butler.cc:319 msgid "Butler write-behind failure on dstream %1" msgstr "Αποτυχία οπισθεγγÏαφής Butler στο dstream %1" -#: libs/ardour/session_click.cc:157 +#: libs/ardour/session_click.cc:158 msgid "cannot open click soundfile %1 (%2)" msgstr "δεν μποÏÏŽ να ανοίξω τοsoundfile μετÏονόμου%1 (%2)" -#: libs/ardour/session_click.cc:166 +#: libs/ardour/session_click.cc:167 msgid "cannot read data from click soundfile" msgstr "δεν μποÏÏŽ να διαβάσω δεδομένα από το soundfile μετÏονόμου" -#: libs/ardour/session_click.cc:191 +#: libs/ardour/session_click.cc:192 msgid "cannot open click emphasis soundfile %1 (%2)" msgstr "δεν μποÏÏŽ να ανοίξω το soundfile εμφάσεως μετÏονόμου %1 (%2)" -#: libs/ardour/session_click.cc:199 +#: libs/ardour/session_click.cc:200 msgid "cannot read data from click emphasis soundfile" msgstr "δεν μποÏÏŽ να διαβάσω δεδομένα από το soundfile εμφάσεως μετÏονόμου" @@ -1666,7 +1603,7 @@ msgstr "Σφάλμα στο transport thread request pipe" msgid "Error reading from transport request pipe" msgstr "Σφάλμα στην ανάγνωση από transport request pipe" -#: libs/ardour/session_process.cc:105 +#: libs/ardour/session_process.cc:104 msgid "Session: error in no roll for %1" msgstr "ΣυνεδÏία: σφάλμα στο no roll για %1" @@ -1684,212 +1621,223 @@ msgstr "τέλος" msgid "start" msgstr "ξεχωÏιστό" -#: libs/ardour/session_state.cc:501 +#: libs/ardour/session_state.cc:502 msgid "Session: cannot create session dir \"%1\" (%2)" msgstr "ΣυνεδÏία: δεν μποÏÏŽ να δημιουÏγήσω φάκελο συνεδÏίας \"%1\" (%2)" -#: libs/ardour/session_state.cc:512 +#: libs/ardour/session_state.cc:513 #, fuzzy msgid "Session: cannot create session peakfile dir \"%1\" (%2)" msgstr "ΣυνεδÏία: δεν μποÏÏŽ να δημιουÏγήσω φάκελο συνεδÏίας \"%1\" (%2)" -#: libs/ardour/session_state.cc:521 +#: libs/ardour/session_state.cc:522 msgid "Session: cannot create session sounds dir \"%1\" (%2)" msgstr "ΣυνεδÏία: δεν μποÏÏŽ να δημιουÏγήσω φάκελο ήχων συνεδÏίας \"%1\" (%2)" -#: libs/ardour/session_state.cc:530 +#: libs/ardour/session_state.cc:531 #, fuzzy msgid "Session: cannot create session tape dir \"%1\" (%2)" msgstr "ΣυνεδÏία: δεν μποÏÏŽ να δημιουÏγήσω φάκελο συνεδÏίας \"%1\" (%2)" -#: libs/ardour/session_state.cc:539 +#: libs/ardour/session_state.cc:540 msgid "Session: cannot create session dead sounds dir \"%1\" (%2)" msgstr "" "ΣυνεδÏία: δεν μποÏÏŽ να δημιουÏγήσω φάκελο 'νεκÏών' ήχων συνεδÏίας \"%1\" (%2)" -#: libs/ardour/session_state.cc:548 +#: libs/ardour/session_state.cc:549 msgid "Session: cannot create session automation dir \"%1\" (%2)" msgstr "" "ΣυνεδÏία: δεν μποÏÏŽ να δημιουÏγήσω φάκελο αυτοματισμών της συνεδÏίας \"%1" "\" (%2)" -#: libs/ardour/session_state.cc:579 +#: libs/ardour/session_state.cc:580 msgid "Could not open %1 for writing mix template" msgstr "Δεν μπόÏεσα να ανοίξω %1 για γÏάψιμο του Ï€Ïοσχεδίου μίξεως" -#: libs/ardour/session_state.cc:585 +#: libs/ardour/session_state.cc:586 msgid "Could not open mix template %1 for reading" msgstr "Δεν μπόÏεσα να ανοίξω Ï€Ïοσχέδιο μίξεως %1 για ανάγνωση" -#: libs/ardour/session_state.cc:592 +#: libs/ardour/session_state.cc:593 msgid "Session already exists. Not overwriting" msgstr "Η ΣυνεδÏία ήδη υπάÏχει. ΑκÏÏωση overwriting" -#: libs/ardour/session_state.cc:635 +#: libs/ardour/session_state.cc:636 msgid "Session: could not load diskstream via XML state" msgstr "ΣυνεδÏία: δεν μπόÏεσα να φοÏτώσω diskstream μέσω καταστάσεως XML" -#: libs/ardour/session_state.cc:684 +#: libs/ardour/session_state.cc:685 msgid "could not backup old state file, current state not saved." msgstr "" "δεν μπόÏεσα να διασώσω το παλαιό αÏχείο καταστάσεως, η Ï„Ïέχουσα κατάσταση " "δεν αποθηκεÏτηκε." -#: libs/ardour/session_state.cc:697 +#: libs/ardour/session_state.cc:698 msgid "state could not be saved to %1" msgstr "η κατάσταση δεν μποÏοÏσε να σωθεί στο %1" -#: libs/ardour/session_state.cc:704 +#: libs/ardour/session_state.cc:705 #, fuzzy msgid "could not remove corrupt state file %1" msgstr "Δεν μπόÏεσα να αναλÏσω το αÏχείο rdf: %1" -#: libs/ardour/session_state.cc:708 +#: libs/ardour/session_state.cc:709 #, fuzzy msgid "could not restore state file from backup %1" msgstr "Σφάλμα: δεν μπόÏεσα να γÏάψω %1" -#: libs/ardour/session_state.cc:777 +#: libs/ardour/session_state.cc:778 msgid "%1: session state information file \"%2\" doesn't exist!" msgstr "%1: το αÏχείο πληÏοφοÏιών καταστάσεως συνεδÏίας \"%2\" δεν υπάÏχει!" -#: libs/ardour/session_state.cc:788 +#: libs/ardour/session_state.cc:789 msgid "Could not understand ardour file %1" msgstr "Δεν μπόÏεσα να κατανοήσω το ardour αÏχείο %1" -#: libs/ardour/session_state.cc:1492 +#: libs/ardour/session_state.cc:1493 msgid "programming error: Session: incorrect XML node sent to set_state()" msgstr "" "σφάλμα Ï€ÏογÏαμματισμοÏ: ΣυνεδÏία: λανθασμένος κόμβος XML εστάλη στην " "set_state()" -#: libs/ardour/session_state.cc:1538 +#: libs/ardour/session_state.cc:1539 msgid "Session: XML state has no options section" msgstr "ΣυνεδÏία: η XML κατάσταση δεν έχει τομέα επιλογών(options)" -#: libs/ardour/session_state.cc:1543 +#: libs/ardour/session_state.cc:1544 msgid "Session: XML state has no sources section" msgstr "ΣυνεδÏία: η XML κατάσταση δεν έχει τομέα πηγών" -#: libs/ardour/session_state.cc:1550 +#: libs/ardour/session_state.cc:1551 msgid "Session: XML state has no Regions section" msgstr "ΣυνεδÏία: η XML κατάσταση δεν έχει τομέα ΠεÏιοχών" -#: libs/ardour/session_state.cc:1557 +#: libs/ardour/session_state.cc:1558 msgid "Session: XML state has no playlists section" msgstr "ΣυνεδÏία: η XML κατάσταση δεν έχει τομέα playlists" -#: libs/ardour/session_state.cc:1576 +#: libs/ardour/session_state.cc:1577 msgid "Session: XML state has no diskstreams section" msgstr "ΣυνεδÏία: η XML κατάσταση δεν έχει τομέα diskstreams" -#: libs/ardour/session_state.cc:1583 +#: libs/ardour/session_state.cc:1584 msgid "Session: XML state has no connections section" msgstr "ΣυνεδÏία: η XML κατάσταση δεν έχει τομέα συνδέσεων" -#: libs/ardour/session_state.cc:1590 +#: libs/ardour/session_state.cc:1591 msgid "Session: XML state has no locations section" msgstr "ΣυνεδÏία: η XML κατάσταση δεν έχει τομέα τοποθεσιών" -#: libs/ardour/session_state.cc:1623 +#: libs/ardour/session_state.cc:1624 msgid "Session: XML state has no edit groups section" msgstr "ΣυνεδÏία: η XML κατάσταση δεν έχει τομέα επεξεÏ/σίας ομάδων" -#: libs/ardour/session_state.cc:1630 +#: libs/ardour/session_state.cc:1631 msgid "Session: XML state has no mix groups section" msgstr "ΣυνεδÏία: η XML κατάσταση δεν έχει τομέα μίξεως ομάδων" -#: libs/ardour/session_state.cc:1637 +#: libs/ardour/session_state.cc:1638 msgid "Session: XML state has no Tempo Map section" msgstr "ΣυνεδÏία: η XML κατάσταση δεν έχει τομέα Tempo Map" -#: libs/ardour/session_state.cc:1644 +#: libs/ardour/session_state.cc:1645 msgid "Session: XML state has no routes section" msgstr "ΣυνεδÏία: η XML κατάσταση δεν έχει τομέα διαδÏομών" -#: libs/ardour/session_state.cc:1651 +#: libs/ardour/session_state.cc:1652 msgid "Session: XML state has no click section" msgstr "ΣυνεδÏία: η XML κατάσταση δεν έχει τομέα μετÏονόμου" -#: libs/ardour/session_state.cc:1696 +#: libs/ardour/session_state.cc:1697 msgid "Session: cannot create Route from XML description." msgstr "ΣυνεδÏία: δεν μποÏÏŽ να δημιουÏγήσω ΔιαδÏομή από XML πεÏιγÏαφή." -#: libs/ardour/session_state.cc:1734 +#: libs/ardour/session_state.cc:1735 msgid "Session: cannot create Region from XML description." msgstr "ΣυνεδÏία: δεν μποÏÏŽ να δημιουÏγήσω ΠεÏιοχή από XML πεÏιγÏαφή." -#: libs/ardour/session_state.cc:1762 +#: libs/ardour/session_state.cc:1764 msgid "Session: XMLNode describing a AudioRegion is incomplete (no source)" msgstr "" "ΣυνεδÏία: Ο XMLΚόμβος που πεÏιγÏάφει AudioΠεÏιοχή είναι ημιτελής (δίχως πηγή)" -#: libs/ardour/session_state.cc:1770 libs/ardour/session_state.cc:1784 +#: libs/ardour/session_state.cc:1772 libs/ardour/session_state.cc:1792 msgid "" "Session: XMLNode describing a AudioRegion references an unknown source id =%1" msgstr "" "ΣυνεδÏία: Ο XMLΚόμβος που πεÏιγÏάφει AudioΠεÏιοχή αναφέÏει άγνωστο id πηγής =" "%1" -#: libs/ardour/session_state.cc:1852 +#: libs/ardour/session_state.cc:1778 libs/ardour/session_state.cc:1798 +#, fuzzy +msgid "" +"Session: XMLNode describing a AudioRegion references a non-audio source id =%" +"1" +msgstr "" +"ΣυνεδÏία: Ο XMLΚόμβος που πεÏιγÏάφει AudioΠεÏιοχή αναφέÏει άγνωστο id πηγής =" +"%1" + +#: libs/ardour/session_state.cc:1868 msgid "Session: cannot create Source from XML description." msgstr "ΣυνεδÏία: δεν μποÏÏŽ να δημιουÏγήσω Πηγή από XML πεÏιγÏαφή." -#: libs/ardour/session_state.cc:1883 -msgid "Found a sound file that cannot be used by Ardour. See the progammers." +#: libs/ardour/session_state.cc:1889 +#, fuzzy +msgid "" +"Found a sound file that cannot be used by Ardour. Talk to the progammers." msgstr "" "Î’Ïήκα ένα sound file που δεν μποÏεί να χÏησιμοποιηθεί από τον Ardour. " "Επικοινωνήστε με τους Ï€ÏογÏαμματιστές." -#: libs/ardour/session_state.cc:1908 +#: libs/ardour/session_state.cc:1913 msgid "Could not create mix templates directory \"%1\" (%2)" msgstr "Δεν μπόÏεσα να δημιουÏγήσω φάκελο Ï€Ïοσχεδίων μίξεως \"%1\" (%2)" -#: libs/ardour/session_state.cc:1922 +#: libs/ardour/session_state.cc:1927 msgid "Template \"%1\" already exists - new version not created" msgstr "Το Ï€Ïοσχέδιο \"%1\" ήδη υπάÏχει - νέα έκδοση δεν δημιουÏγήθηκε" -#: libs/ardour/session_state.cc:1929 +#: libs/ardour/session_state.cc:1934 msgid "mix template not saved" msgstr "Ï€Ïοσχέδιο μίξεως δεν αποθηκεÏτηκε" -#: libs/ardour/session_state.cc:1989 +#: libs/ardour/session_state.cc:1994 msgid "cannot create session directory \"%1\"; ignored" msgstr "δεν μποÏÏŽ να δημιουÏγήσω φάκελο συνεδÏίας \"%1\"; αγνοήθηκε" -#: libs/ardour/session_state.cc:2002 +#: libs/ardour/session_state.cc:2007 msgid "cannot create sounds directory \"%1\"; ignored" msgstr "δεν μποÏÏŽ να δημιουÏγήσω τον φάκελο 'sounds' \"%1\"; αγνοήθηκε" -#: libs/ardour/session_state.cc:2013 +#: libs/ardour/session_state.cc:2018 msgid "cannot create dead sounds directory \"%1\"; ignored" msgstr "δεν μποÏÏŽ να δημιουÏγήσω τον φάκελο 'dead sounds' \"%1\"; αγνοήθηκε" -#: libs/ardour/session_state.cc:2024 +#: libs/ardour/session_state.cc:2029 #, fuzzy msgid "cannot create peak file directory \"%1\"; ignored" msgstr "δεν μποÏÏŽ να δημιουÏγήσω φάκελο συνεδÏίας \"%1\"; αγνοήθηκε" -#: libs/ardour/session_state.cc:2163 libs/ardour/session_state.cc:2184 +#: libs/ardour/session_state.cc:2168 libs/ardour/session_state.cc:2189 msgid "Session: cannot create Playlist from XML description." msgstr "ΣυνεδÏία: δεν μποÏÏŽ να δημιουÏγήσω την Playlist από την XML πεÏιγÏαφή." -#: libs/ardour/session_state.cc:2223 +#: libs/ardour/session_state.cc:2228 msgid "Session: cannot create Named Selection from XML description." msgstr "" "ΣυνεδÏία: δεν μποÏÏŽ να δημιουÏγήσω την ονομασμένη επιλογή από την XML " "πεÏιγÏαφή." -#: libs/ardour/session_state.cc:2355 +#: libs/ardour/session_state.cc:2360 msgid "Unknown node \"%1\" found in Connections list from state file" msgstr "" "Άγνωστος κόμβος \"%1\" ευÏέθη στη λίστα 'Συνδέσεις' από το αÏχείο καταστάσεως" -#: libs/ardour/session_state.cc:3195 +#: libs/ardour/session_state.cc:3197 msgid "cannot remove dead sound file %1 (%2)" msgstr "δεν μποÏÏŽ να απαλοίψω το 'νεκÏο' ηχο-αÏχείο %1 (%2)" -#: libs/ardour/session_time.cc:736 +#: libs/ardour/session_time.cc:375 msgid "Unknown JACK transport state %1 in sync callback" msgstr "Άγνωστη κατάσταση του JACK transport %1 στην ανάκληση sync" @@ -1898,28 +1846,28 @@ msgid "tempoize: error creating name for new audio file based on %1" msgstr "" "tempoize: σφάλμα στη δημιουÏγία ονόματος για νέο αÏχείο ήχου βασισμένο σε %1" -#: libs/ardour/session_timefx.cc:85 +#: libs/ardour/session_timefx.cc:88 msgid "tempoize: error creating new audio file %1 (%2)" msgstr "tempoize: σφάλμα στη δημιουÏγία νέου αÏχείου ήχου %1 (%2)" -#: libs/ardour/session_timefx.cc:111 +#: libs/ardour/session_timefx.cc:114 msgid "tempoize: error reading data from %1" msgstr "tempoize: σφάλμα στην ανάγνωση δεδομένων από %1" -#: libs/ardour/session_timefx.cc:124 libs/ardour/session_timefx.cc:136 +#: libs/ardour/session_timefx.cc:127 libs/ardour/session_timefx.cc:139 msgid "error writing tempo-adjusted data to %1" msgstr "σφάλμα στην εγγÏαφή χÏονο-Ïυθμισμένων δεδομένων στο %1" -#: libs/ardour/session_timefx.cc:142 +#: libs/ardour/session_timefx.cc:145 msgid "timefx code failure. please notify ardour-developers." msgstr "" "αποτυχία κώδικα timefx. παÏακαλώ ειδοποιήστε τους Ï€ÏογÏαμματιστές του ardour." -#: libs/ardour/session_transport.cc:116 +#: libs/ardour/session_transport.cc:117 msgid "Cannot loop - no loop range defined" msgstr "Δεν γίνεται loop - κανένα διάστημα loop δεν Ï€ÏοσδιοÏίστηκε" -#: libs/ardour/session_transport.cc:478 +#: libs/ardour/session_transport.cc:479 msgid "" "Seamless looping cannot be supported while Ardour is using JACK transport.\n" "Recommend changing the configured options" @@ -1928,7 +1876,7 @@ msgstr "" "transport.\n" "ΣυνιστοÏμε την αλλαγή των διαμοÏφωμένων Ïυθμίσεων" -#: libs/ardour/session_transport.cc:754 +#: libs/ardour/session_transport.cc:755 msgid "" "Global varispeed cannot be supported while Ardour is connected to JACK " "transport control" @@ -1936,12 +1884,12 @@ msgstr "" "Η Global varispeed δεν μποÏεί να υποστηÏιχθεί ενώ ο Ardour είναι " "συνδεδεμένος με τον JACK transport control" -#: libs/ardour/session_transport.cc:954 +#: libs/ardour/session_transport.cc:955 msgid "please stop the transport before adjusting slave settings" msgstr "" "παÏακαλώ σταματήστε το transport Ï€Ïιν την ÏÏθμιση των επιλογων εξαÏτήσεως" -#: libs/ardour/session_transport.cc:990 +#: libs/ardour/session_transport.cc:991 msgid "No MTC port defined: MTC slaving is impossible." msgstr "" "Καμμία θÏÏα MTC δεν Ï€ÏοσδιοÏίστηκε: η εξάÏτηση του MTC (slaving) είναι " @@ -2031,11 +1979,24 @@ msgstr "Little-endian (Intel)" msgid "Big-endian (Mac)" msgstr "Big-endian (Mac)" -#: libs/ardour/sndfilesource.cc:75 -msgid "SndFileSource: cannot open file \"%1\" (%2)" +#: libs/ardour/sndfilesource.cc:146 +msgid "FileSource: cannot get host information for BWF header (%1)" +msgstr "" +"FileSource: δεν μποÏÏŽ να βÏÏŽ πληÏοφοÏίες οικοδεσπότη(host) για επικεφαλίδα " +"BWF (%1)" + +#: libs/ardour/sndfilesource.cc:168 +msgid "" +"cannot set broadcast info for audio file %1 (%2); dropping broadcast info " +"for this file" +msgstr "" + +#: libs/ardour/sndfilesource.cc:224 +#, fuzzy +msgid "SndFileSource: cannot open file \"%1\" for %2 (%3)" msgstr "SndFileSource: δεν μποÏÏŽ να ανοίξω το αÏχείο \"%1\" (%2)" -#: libs/ardour/sndfilesource.cc:80 +#: libs/ardour/sndfilesource.cc:230 msgid "" "SndFileSource: file only contains %1 channels; %2 is invalid as a channel " "number" @@ -2043,74 +2004,32 @@ msgstr "" "SndFileSource: το αÏχείο πεÏιέχει μόνο %1 κανάλια; %2 δεν έχει αξία σαν " "κανάλι number" -#: libs/ardour/sndfilesource.cc:122 +#: libs/ardour/sndfilesource.cc:307 msgid "SndFileSource: could not seek to frame %1 within %2 (%3)" msgstr "SndFileSource: δεν μποÏοÏσα να αναζητήσω στο frame %1 μέσα στο %2 (%3)" -#: libs/ardour/source.cc:161 -msgid "poll on peak request pipe failed (%1)" +#: libs/ardour/sndfilesource.cc:358 +#, fuzzy +msgid "programming error: %1 %2" +msgstr "σφάλμα Ï€ÏογÏαμματισμοÏ: %1" + +#: libs/ardour/sndfilesource.cc:458 +msgid "" +"cannot set broadcast info for audio file %1; Dropping broadcast info for " +"this file" msgstr "" -#: libs/ardour/source.cc:168 +#: libs/ardour/sndfilesource.cc:500 #, fuzzy -msgid "Error on peak thread request pipe" -msgstr "Σφάλμα στο transport thread request pipe" +msgid "%1: cannot seek to %2" +msgstr "%1: δεν μποÏÏŽ να αναζητήσω στο %2 για εξαγωγή" -#: libs/ardour/source.cc:201 -#, fuzzy -msgid "Error reading from peak request pipe" -msgstr "Σφάλμα στην ανάγνωση από transport request pipe" - -#: libs/ardour/source.cc:238 libs/ardour/source.cc:243 -#, fuzzy -msgid "UI: cannot set O_NONBLOCK on peak request pipe (%1)" -msgstr "UI: δεν μποÏÏŽ να θέσω O_NONBLOCK στο signal read pipe (%1)" - -#: libs/ardour/source.cc:248 -msgid "Source: could not create peak thread" -msgstr "Source: δεν μπόÏεσα να δημιουÏγήσω peak δέσμη" - -#: libs/ardour/source.cc:326 -#, fuzzy -msgid "cannot rename peakfile for %1 from %2 to %3 (%4)" -msgstr "δεν μποÏÏŽ να απαλοίψω το peakfile %1 για %2 (%3)" - -#: libs/ardour/source.cc:357 -msgid "Source: cannot stat peakfile \"%1\"" -msgstr "Source: δεν μποÏÏŽ να μετÏήσω το αυτοστιγμεί peakfile \"%1\"" - -#: libs/ardour/source.cc:444 -msgid "cannot read sample data for unscaled peak computation" -msgstr "" -"δεν μποÏÏŽ να διαβάσω δεδομένα δείγματος για υπολογισμό μη-κλιμακώτου peak" - -#: libs/ardour/source.cc:465 libs/ardour/source.cc:536 -#: libs/ardour/source.cc:780 libs/ardour/source.cc:881 -msgid "Source: cannot open peakpath \"%1\" (%2)" -msgstr "Source: δεν μποÏÏŽ να ανοίξω το peakpath \"%1\" (%2)" - -#: libs/ardour/source.cc:637 -msgid "Source[%1]: peak read - cannot read %2 samples at offset %3" -msgstr "" -"Source[%1]: ανάγνωση peak - δεν μποÏÏŽ να διαβάσω %2 δείγματα στην αÏχή" -"(offset) %3" - -#: libs/ardour/source.cc:789 -msgid "%1: could not write read raw data for peak computation (%2)" -msgstr "" -"%1: δεν μποÏεσα να γÏάψω ανεγνωσμένα raw δεδομένα για τον υπολογισμό του " -"peak (%2)" - -#: libs/ardour/source.cc:814 -msgid "%1: could not write peak file data (%2)" -msgstr "%1: δεν μπόÏεσα να γÏάψω δεδομένα του αÏχείου peak (%2)" - -#: libs/ardour/state_manager.cc:46 +#: libs/ardour/state_manager.cc:47 #, fuzzy msgid "cleared history" msgstr "εκκαθαÏίσθη" -#: libs/ardour/state_manager.cc:59 +#: libs/ardour/state_manager.cc:60 #, fuzzy msgid "" "programming error: illegal state ID (%1) passed to StateManager::set_state() " @@ -2119,135 +2038,135 @@ msgstr "" "σφάλμα Ï€ÏογÏαμματισμοÏ: αθέμιτη κατάσταση ID (%1) πέÏασε στον StateManager::" "set_state() (range = 0-%3)" -#: libs/ardour/stateful.cc:100 +#: libs/ardour/stateful.cc:102 msgid "Error: could not write %1" msgstr "Σφάλμα: δεν μπόÏεσα να γÏάψω %1" -#: libs/ardour/stateful.cc:114 +#: libs/ardour/stateful.cc:116 msgid "Could not understand XML file %1" msgstr "Δεν μπόÏεσα να κατανοήσω το XML αÏχείο %1" -#: libs/ardour/tempo.cc:66 +#: libs/ardour/tempo.cc:67 msgid "TempoSection XML node has no \"start\" property" msgstr "Κόμβος του TempoSection XML δεν έχει ιδιότητα \"έναÏξη\"" -#: libs/ardour/tempo.cc:74 +#: libs/ardour/tempo.cc:75 msgid "TempoSection XML node has an illegal \"start\" value" msgstr "Κόμβος του TempoSection XML έχει αθέμιτη αξία \"έναÏξη\"" -#: libs/ardour/tempo.cc:81 +#: libs/ardour/tempo.cc:82 msgid "TempoSection XML node has no \"beats-per-minute\" property" msgstr "Κόμβος του TempoSection XML δεν έχει \"κτÏπων-ανά-λεπτό\" ιδιότητα" -#: libs/ardour/tempo.cc:86 +#: libs/ardour/tempo.cc:87 msgid "TempoSection XML node has an illegal \"beats_per_minute\" value" msgstr "Κόμβος του TempoSection XML έχει αθέμιτη \"κτÏπων_ανά_λεπτό\" αξία" -#: libs/ardour/tempo.cc:91 +#: libs/ardour/tempo.cc:92 msgid "TempoSection XML node has no \"movable\" property" msgstr "Κόμβος του TempoSection XML δεν έχει \"κινητή\" ιδιότητα" -#: libs/ardour/tempo.cc:130 +#: libs/ardour/tempo.cc:131 msgid "MeterSection XML node has no \"start\" property" msgstr "Κόμβος του MeterSection XML δεν έχει \"έναÏξη\" ιδιότητα" -#: libs/ardour/tempo.cc:138 +#: libs/ardour/tempo.cc:139 msgid "MeterSection XML node has an illegal \"start\" value" msgstr "Κόμβος του MeterSection XML έχει αθέμιτη \"έναÏξη\" αξία" -#: libs/ardour/tempo.cc:145 +#: libs/ardour/tempo.cc:146 msgid "MeterSection XML node has no \"beats-per-bar\" property" msgstr "Κόμβος του MeterSection XML δεν έχει \"κτÏπων-ανά-μπάÏα\" ιδιότητα" -#: libs/ardour/tempo.cc:150 +#: libs/ardour/tempo.cc:151 msgid "MeterSection XML node has an illegal \"beats-per-bar\" value" msgstr "Κόμβος του MeterSection XML έχει αθέμιτη \"κτÏπων-ανά-μπάÏα\" αξία" -#: libs/ardour/tempo.cc:155 +#: libs/ardour/tempo.cc:156 msgid "MeterSection XML node has no \"note-type\" property" msgstr "Κόμβος του MeterSection XML δεν έχει \"Ï„Ïπος-νότας\" ιδιότητα" -#: libs/ardour/tempo.cc:160 +#: libs/ardour/tempo.cc:161 msgid "MeterSection XML node has an illegal \"note-type\" value" msgstr "Κόμβος του MeterSection XML έχει αθέμιτη \"Ï„Ïπος-νότας\" αξία" -#: libs/ardour/tempo.cc:165 +#: libs/ardour/tempo.cc:166 msgid "MeterSection XML node has no \"movable\" property" msgstr "Κόμβος του MeterSection XML δεν έχει \"κινητή\" ιδιότητα" -#: libs/ardour/tempo.cc:258 +#: libs/ardour/tempo.cc:259 msgid "move metric" msgstr "μετακίνηση μετÏικοÏ" -#: libs/ardour/tempo.cc:329 +#: libs/ardour/tempo.cc:330 msgid "metric removed" msgstr "μετÏικό απεσÏÏθη" -#: libs/ardour/tempo.cc:372 +#: libs/ardour/tempo.cc:373 msgid "add tempo" msgstr "Ï€Ïόσθεση ÏυθμοÏ" -#: libs/ardour/tempo.cc:401 +#: libs/ardour/tempo.cc:402 msgid "replace tempo" msgstr "αντικατάσταση ÏυθμοÏ" -#: libs/ardour/tempo.cc:434 +#: libs/ardour/tempo.cc:435 msgid "add meter" msgstr "Ï€Ïόσθεση μετÏητή" -#: libs/ardour/tempo.cc:462 +#: libs/ardour/tempo.cc:463 msgid "replaced meter" msgstr "αντικατεστημένος μετÏητής" -#: libs/ardour/tempo.cc:482 libs/ardour/tempo.cc:498 +#: libs/ardour/tempo.cc:483 libs/ardour/tempo.cc:499 msgid "programming error: no tempo section in tempo map!" msgstr "σφάλμα Ï€ÏογÏαμματισμοÏ: κανένας τομέας ÏÏ…Î¸Î¼Î¿Ï ÏƒÏ„Î¿ χάÏτη Ïυθμών!" -#: libs/ardour/tempo.cc:537 +#: libs/ardour/tempo.cc:538 msgid "programming error: unhandled MetricSection type" msgstr "σφάλμα Ï€ÏογÏαμματισμοÏ: αχείÏιστος Ï„Ïπος MetricSection" -#: libs/ardour/tempo.cc:1225 libs/ardour/tempo.cc:1237 +#: libs/ardour/tempo.cc:1226 libs/ardour/tempo.cc:1238 msgid "Tempo map: could not set new state, restoring old one." msgstr "" "ΧάÏτης Ïυθμών: δεν μπόÏεσα να θέσω νέα κατάσταση, επιστÏοφή Ï€ÏοηγοÏμενης." -#: libs/ardour/tempo.cc:1261 +#: libs/ardour/tempo.cc:1262 msgid "load XML data" msgstr "" -#: libs/ardour/utils.cc:242 +#: libs/ardour/utils.cc:246 #, fuzzy msgid "illegal or badly-formed string used for path (%1)" msgstr "παÏάνομη ή κακοσχηματισμένη γÏαμμή για το μονοπάτι RAID" -#: libs/ardour/utils.cc:247 +#: libs/ardour/utils.cc:251 #, fuzzy msgid "path (%1) is ambiguous" msgstr "Το μονοπάτι αναζήτησης του RAID είναι αμφίβολο" -#: libs/ardour/vst_plugin.cc:186 +#: libs/ardour/vst_plugin.cc:187 msgid "cannot create VST chunk directory: %1" msgstr "δεν μποÏÏŽ να δημιουÏγήσω φάκελο κομματιών VST: %1" -#: libs/ardour/vst_plugin.cc:194 +#: libs/ardour/vst_plugin.cc:195 msgid "cannot check VST chunk directory: %1" msgstr "δεν μποÏÏŽ να ελέγξω το φάκελο κομματιών VST: %1" -#: libs/ardour/vst_plugin.cc:201 +#: libs/ardour/vst_plugin.cc:202 msgid "%1 exists but is not a directory" msgstr "%1 υπάÏχει αλλά δεν είναι φάκελος" -#: libs/ardour/vst_plugin.cc:239 +#: libs/ardour/vst_plugin.cc:240 msgid "Bad node sent to VSTPlugin::set_state" msgstr "Κακός κόμβος εστάλη στο VSTPlugin::set_state" -#: libs/ardour/vst_plugin.cc:342 libs/ardour/vst_plugin.cc:353 +#: libs/ardour/vst_plugin.cc:343 libs/ardour/vst_plugin.cc:354 msgid "no support for presets using chunks at this time" msgstr "" "καμμία υποστήÏιξη αυτή τη στιγμή για Ïυθμίσεις που χÏησιμοποιοÏν κομμάτια" -#: libs/ardour/coreaudio_source.cc:93 +#: libs/ardour/coreaudio_source.cc:99 #, fuzzy msgid "" "CoreAudioSource: file only contains %1 channels; %2 is invalid as a channel " @@ -2256,11 +2175,121 @@ msgstr "" "SndFileSource: το αÏχείο πεÏιέχει μόνο %1 κανάλια; %2 δεν έχει αξία σαν " "κανάλι number" -#: libs/ardour/coreaudio_source.cc:157 +#: libs/ardour/coreaudio_source.cc:164 #, fuzzy msgid "CoreAudioSource: could not seek to frame %1 within %2 (%3)" msgstr "SndFileSource: δεν μποÏοÏσα να αναζητήσω στο frame %1 μέσα στο %2 (%3)" +#~ msgid "FileSource: \"%1\" not found when searching %2 using %3" +#~ msgstr "FileSource: \"%1\" δεν ευÏέθη όταν αναζητείτο %2 χÏησιμοποιώντας %3" + +#~ msgid "FileSource: could not open \"%1\": (%2)" +#~ msgstr "FileSource: δεν μπόÏεσα να ανοίξω \"%1\": (%2)" + +#~ msgid "FileSource: cannot write header in %1" +#~ msgstr "FileSource: δεν μποÏÏŽ να γÏάψω επικεφαλίδα στο %1" + +#~ msgid "FileSource: cannot locate chunks in %1" +#~ msgstr "FileSource: δεν μποÏÏŽ να ανιχνεÏσω κομμάτια στο %1" + +#~ msgid "FileSource: cannot read header in %1" +#~ msgstr "FileSource: δεν μποÏÏŽ να διαβάσω επικεφαλίδα στο %1" + +#~ msgid "FileSource: cannot check header in %1" +#~ msgstr "FileSource: δεν μποÏÏŽ να ελέγξω επικεφαλίδα στο %1" + +#, fuzzy +#~ msgid "FileSource: cannot initialize peakfile for %1 as %2" +#~ msgstr "FileSource: δεν μποÏÏŽ να εκκινήσω το peakfile για %1" + +#~ msgid "FileSource: cannot seek to end of file" +#~ msgstr "FileSource: δεν μποÏÏŽ να ανιχνεÏσω το τέλος του αÏχείου" + +#~ msgid "FileSource: cannot read RIFF/WAVE chunk from file" +#~ msgstr "FileSource: δεν μποÏÏŽ να διαβάσω κομμάτι RIFF/WAVE από το αÏχείο" + +#~ msgid "FileSource %1: not a RIFF/WAVE file" +#~ msgstr "FileSource %1: δεν είναι RIFF/WAVE αÏχείο" + +#~ msgid "FileSource: can't read a chunk" +#~ msgstr "FileSource: δεν μποÏÏŽ να διαβάσω κομμάτι" + +#~ msgid "FileSource: cannot get user information for BWF header (%1)" +#~ msgstr "" +#~ "FileSource: δεν μποÏÏŽ να βÏÏŽ πληÏοφοÏίες χÏήστη για επικεφαλίδα BWF (%1)" + +#~ msgid "FileSource[%1]: cannot update data size: %2" +#~ msgstr "FileSource[%1]: δεν μποÏÏŽ να ανανεώσω το μέγεθος δεδομένων: %2" + +#~ msgid "FileSource: can't find RIFF chunk info" +#~ msgstr "FileSource: δεν ευÏέθησαν πληÏοφοÏίες για RIFF κομμάτι" + +#, fuzzy +#~ msgid "FileSource: can't find RIFX chunk info" +#~ msgstr "FileSource: δεν ευÏέθησαν πληÏοφοÏίες για RIFF κομμάτι" + +#~ msgid "FileSource: can't read RIFF chunk" +#~ msgstr "FileSource: δεν μποÏÏŽ να διαβάσω RIFF κομμάτι" + +#~ msgid "FileSource: can't find format chunk info" +#~ msgstr "FileSource: δεν ευÏέθησαν πληÏοφοÏίες για το κομμάτι φοÏμαÏίσματος" + +#~ msgid "FileSource: can't read format chunk" +#~ msgstr "FileSource: δεν μποÏÏŽ να διαβάσω το κομμάτι φοÏμαÏίσματος" + +#~ msgid "FileSource: can't find data chunk info" +#~ msgstr "FileSource: δεν μποÏÏŽ να βÏÏŽ πληÏοφοÏίες για το κομμάτι δεδομένων" + +#~ msgid "FileSource: can't read data chunk" +#~ msgstr "FileSource: δεν μποÏÏŽ να διαβάσω το κομμάτι δεδομένων" + +#~ msgid "" +#~ "FileSource: cannot read Broadcast Wave data from existing audio file \"%1" +#~ "\" (%2)" +#~ msgstr "" +#~ "FileSource: δεν μποÏÏŽ να διαβάσω δεδομένα Broadcast Wave από το υπάÏχον " +#~ "αÏχείο \"%1\" (%2)" + +#~ msgid "" +#~ "FileSource: cannot read Broadcast Wave coding history from audio file \"%1" +#~ "\" (%2)" +#~ msgstr "" +#~ "FileSource: δεν μποÏÏŽ να διαβάσω το ιστοÏικό του κώδικα Broadcast Wave " +#~ "από το αÏχείο \"%1\" (%2)" + +#, fuzzy +#~ msgid "" +#~ "FileSource \"%1\" does not use valid sample format.\n" +#~ "This is probably a programming error." +#~ msgstr "" +#~ "FileSource \"%1\" δεν χÏησιμοποιεί format μεταβλητής υποδιαστολής.\n" +#~ "Αυτό πιθανόν να είναι σφάλμα Ï€ÏογÏαμματισμοÏ." + +#~ msgid "FileSource \"%1\" has no \"data\" chunk" +#~ msgstr "FileSource \"%1\" δεν έχει \"data\" κομμάτι" + +#~ msgid "" +#~ "%1: data length in header (%2) differs from implicit size in file (%3)" +#~ msgstr "" +#~ "%1: το μέγεθος δεδομένων της επικεφαλίδας (%2) διαφέÏει από το δεδηλωμένο " +#~ "μέγεθος στο αÏχείο (%3)" + +#~ msgid "\"%1\" has a sample rate of %2 instead of %3 as used by this session" +#~ msgstr "" +#~ "\"%1\" έχει Ïυθμό δειγματοληψίας %2 αντί του %3 όπως στην παÏοÏσα συνεδÏία" + +#~ msgid "FileSource: cannot write WAVE chunk: %1" +#~ msgstr "FileSource: δεν μποÏÏŽ να γÏάψω WAVE κομμάτι: %1" + +#~ msgid "FileSource: cannot write format chunk: %1" +#~ msgstr "FileSource: δεν μποÏÏŽ να γÏάψω format κομμάτι: %1" + +#~ msgid "FileSource: cannot data chunk: %1" +#~ msgstr "FileSource: cδεν μποÏÏŽ να γÏάψω κομμάτι δεδομένων: %1" + +#~ msgid "FileSource: \"%1\" bad write (%2)" +#~ msgstr "FileSource: \"%1\" κακή εγγÏαφή (%2)" + #, fuzzy #~ msgid "cannot create feedback request pipe (%1)" #~ msgstr "Δεν μποÏÏŽ να δημιουÏγήσω transport request signal pipe (%1)" diff --git a/libs/ardour/po/it_IT.po b/libs/ardour/po/it_IT.po index 7f2412e5d2..55368c2d5a 100644 --- a/libs/ardour/po/it_IT.po +++ b/libs/ardour/po/it_IT.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: libardour 0.664.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-04-25 17:46-0400\n" +"POT-Creation-Date: 2006-06-21 15:09-0400\n" "PO-Revision-Date: 2003-05-21 12:50+0500\n" "Last-Translator: Filippo Pappalardo \n" "Language-Team: Italian\n" @@ -15,308 +15,494 @@ msgstr "" "Content-Type: text/plain; charset=ISO-8859-1\n" "Content-Transfer-Encoding: 8bit\n" -#: libs/ardour/audio_library.cc:91 +#: libs/ardour/audio_diskstream.cc:337 +#, fuzzy +msgid "AudioDiskstream: Session doesn't know about a Playlist called \"%1\"" +msgstr "DiskStream: La sessione non riconosce la Playlist chiamata \"%1\"" + +#: libs/ardour/audio_diskstream.cc:342 +msgid "AudioDiskstream: Playlist \"%1\" isn't an audio playlist" +msgstr "" + +#: libs/ardour/audio_diskstream.cc:433 +#, fuzzy +msgid "AudioDiskstream %1: there is no existing playlist to make a copy of!" +msgstr "DiskStream %1: non esiste alcuna playlist di cui fare una copia!" + +#: libs/ardour/audio_diskstream.cc:1114 libs/ardour/audio_diskstream.cc:1125 +#, fuzzy +msgid "" +"AudioDiskstream %1: when refilling, cannot read %2 from playlist at frame %3" +msgstr "DiskStream %1: impossibile leggere %2 dalla playlista al frame %3" + +#: libs/ardour/audio_diskstream.cc:1254 +#, fuzzy +msgid "AudioDiskstream %1: cannot read %2 from playlist at frame %3" +msgstr "DiskStream %1: impossibile leggere %2 dalla playlista al frame %3" + +#: libs/ardour/audio_diskstream.cc:1621 libs/ardour/audio_diskstream.cc:1638 +#, fuzzy +msgid "AudioDiskstream %1: cannot write to disk" +msgstr "DiskStream %1: impossibile scrivere sul disco" + +#: libs/ardour/audio_diskstream.cc:1698 +#, fuzzy +msgid "AudioDiskstream \"%1\": cannot flush captured data to disk!" +msgstr "DiskStream \"%1\": impossibile scaricare i dati acquisiti sul disco!" + +#: libs/ardour/audio_diskstream.cc:1795 +msgid "%1: could not create region for complete audio file" +msgstr "%1: impossibile creare una regione per il file audio completo" + +#: libs/ardour/audio_diskstream.cc:1818 +#, fuzzy +msgid "AudioDiskstream: could not create region for captured audio!" +msgstr "DiskStream: impossibile creare una regione per l'audio registrato!" + +#: libs/ardour/audio_diskstream.cc:1873 +#, fuzzy +msgid "programmer error: %1" +msgstr "errore di programmazione: %1" + +#: libs/ardour/audio_diskstream.cc:2145 +#, fuzzy +msgid "AudioDiskstream: channel %1 out of range" +msgstr "DiskStream: canale fuori margine" + +#: libs/ardour/audio_diskstream.cc:2170 +msgid "%1:%2 new capture file not initialized correctly" +msgstr "%1:%2 nuovo file di registrazione non è stato avviato correttamente" + +#: libs/ardour/audio_diskstream.cc:2403 +msgid "Location \"%1\" not valid for track loop (start >= end)" +msgstr "La Location \"%1\" non valida per il loop (inizio >= fine)" + +#: libs/ardour/audio_diskstream.cc:2484 +#, fuzzy +msgid "%1: cannot restore pending capture source file %2" +msgstr "Import: impossibile aprire il file audio di input \"%1\"" + +#: libs/ardour/audio_diskstream.cc:2506 +msgid "%1: incorrect number of pending sources listed - ignoring them all" +msgstr "" + +#: libs/ardour/audio_diskstream.cc:2522 +#, fuzzy +msgid "%1: cannot create whole-file region from pending capture sources" +msgstr "Playlist: impossibile creare la Regione dal file di stato" + +#: libs/ardour/audio_diskstream.cc:2534 +#, fuzzy +msgid "%1: cannot create region from pending capture sources" +msgstr "Playlist: impossibile creare la Regione dal file di stato" + +#: libs/ardour/audio_library.cc:92 msgid "channels" msgstr "" -#: libs/ardour/audio_library.cc:92 +#: libs/ardour/audio_library.cc:93 #, fuzzy msgid "samplerate" msgstr "separa" -#: libs/ardour/audio_library.cc:93 +#: libs/ardour/audio_library.cc:94 msgid "resolution" msgstr "" -#: libs/ardour/audio_library.cc:94 +#: libs/ardour/audio_library.cc:95 msgid "format" msgstr "" -#: libs/ardour/audio_library.cc:101 +#: libs/ardour/audio_library.cc:102 msgid "Could not open %1. Audio Library not saved" msgstr "Impossibile accedere a %1. Libreria Audio non salvata" -#: libs/ardour/audio_playlist.cc:52 libs/ardour/audio_playlist.cc:62 -#: libs/ardour/audio_playlist.cc:73 libs/ardour/audio_playlist.cc:120 +#: libs/ardour/audio_playlist.cc:53 libs/ardour/audio_playlist.cc:63 +#: libs/ardour/audio_playlist.cc:74 libs/ardour/audio_playlist.cc:121 #: libs/ardour/insert.cc:76 libs/ardour/insert.cc:95 libs/ardour/insert.cc:120 -#: libs/ardour/insert.cc:838 libs/ardour/insert.cc:846 libs/ardour/send.cc:38 -#: libs/ardour/send.cc:52 libs/ardour/send.cc:61 -#: libs/ardour/session_state.cc:1620 libs/ardour/session_state.cc:1666 +#: libs/ardour/insert.cc:838 libs/ardour/insert.cc:846 libs/ardour/send.cc:39 +#: libs/ardour/send.cc:53 libs/ardour/send.cc:62 +#: libs/ardour/session_state.cc:1621 libs/ardour/session_state.cc:1667 msgid "initial state" msgstr "stato iniziale" -#: libs/ardour/audio_playlist.cc:274 libs/ardour/audio_playlist.cc:768 +#: libs/ardour/audio_playlist.cc:275 libs/ardour/audio_playlist.cc:769 msgid "" "programming error: non-audio Region passed to remove_overlap in audio " "playlist" msgstr "" -#: libs/ardour/audio_playlist.cc:401 +#: libs/ardour/audio_playlist.cc:402 msgid "" "programming error: non-audio Region tested for overlap in audio playlist" msgstr "" -#: libs/ardour/audio_playlist.cc:877 +#: libs/ardour/audio_playlist.cc:878 msgid "xfade change" msgstr "cambio dello smorzamento incrociato" -#: libs/ardour/audio_playlist.cc:926 +#: libs/ardour/audio_playlist.cc:933 msgid "region modified" msgstr "regione modificata" -#: libs/ardour/audio_track.cc:121 libs/ardour/io.cc:1703 -#: libs/ardour/io.cc:1813 +#: libs/ardour/audio_track.cc:133 libs/ardour/io.cc:1716 +#: libs/ardour/io.cc:1826 msgid "Unknown connection \"%1\" listed for input of %2" msgstr "Connessione sconosciuta \"%1\" come input di %2" -#: libs/ardour/audio_track.cc:123 libs/ardour/io.cc:1705 -#: libs/ardour/io.cc:1815 +#: libs/ardour/audio_track.cc:135 libs/ardour/io.cc:1718 +#: libs/ardour/io.cc:1828 msgid "in 1" msgstr "" -#: libs/ardour/audio_track.cc:124 libs/ardour/io.cc:1706 -#: libs/ardour/io.cc:1816 +#: libs/ardour/audio_track.cc:136 libs/ardour/io.cc:1719 +#: libs/ardour/io.cc:1829 msgid "No input connections available as a replacement" msgstr "" -#: libs/ardour/audio_track.cc:128 libs/ardour/io.cc:1710 -#: libs/ardour/io.cc:1820 +#: libs/ardour/audio_track.cc:140 libs/ardour/io.cc:1723 +#: libs/ardour/io.cc:1833 msgid "Connection %1 was not available - \"in 1\" used instead" msgstr "" -#: libs/ardour/audio_track.cc:137 libs/ardour/io.cc:1829 +#: libs/ardour/audio_track.cc:149 libs/ardour/io.cc:1842 msgid "improper input channel list in XML node (%1)" msgstr "" -#: libs/ardour/audio_track.cc:182 libs/ardour/audio_track.cc:195 +#: libs/ardour/audio_track.cc:194 libs/ardour/audio_track.cc:207 msgid "AudioTrack: diskstream \"%1\" not known by session" msgstr "AudioTrack: diskstream \"%1\" non riconosciuto dalla sessione" -#: libs/ardour/audio_track.cc:293 +#: libs/ardour/audio_track.cc:305 msgid "" "MIDI rec_enable control specification for %1 is incomplete, so it has been " "ignored" msgstr "" -#: libs/ardour/audio_track.cc:305 +#: libs/ardour/audio_track.cc:317 msgid "programming error: AudioTrack given state without diskstream!" msgstr "" -#: libs/ardour/audioengine.cc:147 +#: libs/ardour/audioengine.cc:150 msgid "cannot activate JACK client" msgstr "impossibile attivare il client JACK" -#: libs/ardour/audioengine.cc:432 +#: libs/ardour/audioengine.cc:401 msgid "register audio input port called before engine was started" msgstr "" "la richiesta di registrazione di una porta di entrata avvenuta prima " "dell'avvio dell'applicazione" -#: libs/ardour/audioengine.cc:463 +#: libs/ardour/audioengine.cc:432 msgid "register audio output port called before engine was started" msgstr "" "la richiesta di registrazione di una porta di uscita avvenuta prima " "dell'avvio dell'applicazione" -#: libs/ardour/audioengine.cc:524 +#: libs/ardour/audioengine.cc:493 msgid "connect called before engine was started" msgstr "richiesta di connessione avvenuta prima dell'avvio dell'applicazione" -#: libs/ardour/audioengine.cc:540 +#: libs/ardour/audioengine.cc:509 msgid "AudioEngine: cannot connect %1 (%2) to %3 (%4)" msgstr "" -#: libs/ardour/audioengine.cc:553 libs/ardour/audioengine.cc:582 +#: libs/ardour/audioengine.cc:522 libs/ardour/audioengine.cc:551 msgid "disconnect called before engine was started" msgstr "" "richiesta di disconnessione avvenuta prima dell'avvio dell'applicazione" -#: libs/ardour/audioengine.cc:640 +#: libs/ardour/audioengine.cc:609 msgid "get_port_by_name() called before engine was started" msgstr "" "richiesta get_port_by_name() avvenuta prima dell'avvio dell'applicazione" -#: libs/ardour/audioengine.cc:673 +#: libs/ardour/audioengine.cc:642 msgid "get_ports called before engine was started" msgstr "richiesta di get_ports avvenuta prima dell'avvio dell'applicazione" -#: libs/ardour/audioengine.cc:748 +#: libs/ardour/audioengine.cc:717 msgid "get_nth_physical called before engine was started" msgstr "" "richiesta di get_nth_physical avvenuta prima dell'avvio dell'applicazione" -#: libs/ardour/audioengine.cc:776 +#: libs/ardour/audioengine.cc:745 #, fuzzy msgid "get_port_total_latency() called with no JACK client connection" msgstr "" "richiesta di get_port_total_latency() avvenuta prima dell'avvio " "dell'applicazione" -#: libs/ardour/audioengine.cc:782 +#: libs/ardour/audioengine.cc:751 msgid "get_port_total_latency() called before engine was started" msgstr "" "richiesta di get_port_total_latency() avvenuta prima dell'avvio " "dell'applicazione" -#: libs/ardour/audioengine.cc:906 +#: libs/ardour/audioengine.cc:875 msgid "Unable to connect to JACK server" msgstr "" -#: libs/ardour/audioengine.cc:909 +#: libs/ardour/audioengine.cc:878 msgid "Could not connect to JACK server as \"%1\"" msgstr "" -#: libs/ardour/audioengine.cc:914 +#: libs/ardour/audioengine.cc:883 msgid "JACK server started" msgstr "" -#: libs/ardour/audioengine.cc:948 +#: libs/ardour/audioengine.cc:917 msgid "cannot shutdown connection to JACK" msgstr "" -#: libs/ardour/audioengine.cc:973 +#: libs/ardour/audioengine.cc:942 msgid "failed to connect to JACK" msgstr "" -#: libs/ardour/audioengine.cc:989 +#: libs/ardour/audioengine.cc:958 #, fuzzy msgid "could not reregister %1" msgstr "Esportazione: impossibile scrivere dati sul file di output (%1)" -#: libs/ardour/audioengine.cc:1046 +#: libs/ardour/audioengine.cc:1015 msgid "could not reconnect %1 and %2 (err = %3)" msgstr "" -#: libs/ardour/audiofilter.cc:44 +#: libs/ardour/audiofilesource.cc:445 libs/ardour/session_state.cc:3095 +msgid "" +"there are already 1000 files with names like %1; versioning discontinued" +msgstr "" +"ci sono gia' 1000 file con nomi come %1; tracciamento di versione interrotto" + +#: libs/ardour/audiofilesource.cc:459 libs/ardour/session_state.cc:3109 +msgid "cannot rename audio file source from %1 to %2 (%3)" +msgstr "impossibile rinominare file audio sorgente da %1 a %2 (%3)" + +#: libs/ardour/audiofilesource.cc:466 libs/ardour/session_state.cc:3124 +msgid "cannot remove peakfile %1 for %2 (%3)" +msgstr "impossibile eliminare il peakfile %1 per %2 (%3)" + +#: libs/ardour/audiofilesource.cc:510 +msgid "FileSource: search path not set" +msgstr "FileSource: percorso di ricerca non specificato" + +#: libs/ardour/audiofilesource.cc:534 +msgid "" +"FileSource: \"%1\" is ambigous when searching %2\n" +"\t" +msgstr "" +"FileSource: \"%1\" è risultato ambiguo nel cercare %2\n" +"\t" + +#: libs/ardour/audiofilesource.cc:540 +#, fuzzy +msgid "Filesource: cannot find required file (%1): while searching %2" +msgstr "FileSource: impossibile trovare il file richiesto (%1): %2" + +#: libs/ardour/audiofilesource.cc:563 +msgid "Filesource: cannot find required file (%1): %2" +msgstr "FileSource: impossibile trovare il file richiesto (%1): %2" + +#: libs/ardour/audiofilesource.cc:568 +msgid "Filesource: cannot check for existing file (%1): %2" +msgstr "FileSource: impossibile controllare il file esistente (%1): %2" + +#: libs/ardour/audiofilesource.cc:640 libs/ardour/insert.cc:525 +#: libs/ardour/sndfilesource.cc:112 +msgid "programming error: %1" +msgstr "errore di programmazione: %1" + +#: libs/ardour/audiofilesource.cc:645 +#, fuzzy +msgid "cannot rename audio file for %1 to %2" +msgstr "impossibile rinominare file audio sorgente da %1 a %2 (%3)" + +#: libs/ardour/audiofilter.cc:45 msgid "audiofilter: error creating name for new audio file based on %1" msgstr "" "audiofilter: errore nel creare il nome per il nuovo file audio basato su %1" -#: libs/ardour/audiofilter.cc:54 +#: libs/ardour/audiofilter.cc:58 msgid "audiofilter: error creating new audio file %1 (%2)" msgstr "audiofilter: errore nel creare un nuovo file audio %1 (%2)" -#: libs/ardour/audioregion.cc:855 libs/ardour/audioregion.cc:917 +#: libs/ardour/audioregion.cc:857 libs/ardour/audioregion.cc:919 #, fuzzy msgid "fade in change" msgstr "cambio dello smorzamento incrociato" -#: libs/ardour/audioregion.cc:1341 +#: libs/ardour/audioregion.cc:1349 #, c-format msgid "normalized to %.2fdB" msgstr "normalizzato a %.2fdB" -#: libs/ardour/audioregion.cc:1359 +#: libs/ardour/audioregion.cc:1367 #, fuzzy msgid "envelope change" msgstr "livello cambiato" -#: libs/ardour/automation_event.cc:64 libs/ardour/location.cc:344 -#: libs/ardour/tempo.cc:225 +#: libs/ardour/audiosource.cc:143 +msgid "poll on peak request pipe failed (%1)" +msgstr "" + +#: libs/ardour/audiosource.cc:150 +msgid "Error on peak thread request pipe" +msgstr "" + +#: libs/ardour/audiosource.cc:183 +#, fuzzy +msgid "Error reading from peak request pipe" +msgstr "Errore nel leggere dalla porta MIDI %1" + +#: libs/ardour/audiosource.cc:215 libs/ardour/session_butler.cc:80 +#: libs/ardour/session_midi.cc:1183 +msgid "Cannot create transport request signal pipe (%1)" +msgstr "" + +#: libs/ardour/audiosource.cc:220 libs/ardour/audiosource.cc:225 +msgid "UI: cannot set O_NONBLOCK on peak request pipe (%1)" +msgstr "" + +#: libs/ardour/audiosource.cc:230 +#, fuzzy +msgid "AudioSource: could not create peak thread" +msgstr "Sessione: impossibile creare un nuovo route" + +#: libs/ardour/audiosource.cc:308 +#, fuzzy +msgid "cannot rename peakfile for %1 from %2 to %3 (%4)" +msgstr "impossibile eliminare il peakfile %1 per %2 (%3)" + +#: libs/ardour/audiosource.cc:350 +#, fuzzy +msgid "AudioSource: cannot stat peakfile \"%1\"" +msgstr "FileSource: impossibile avviare il peakfile per %1" + +#: libs/ardour/audiosource.cc:451 +msgid "cannot read sample data for unscaled peak computation" +msgstr "" + +#: libs/ardour/audiosource.cc:472 libs/ardour/audiosource.cc:543 +#: libs/ardour/audiosource.cc:787 libs/ardour/audiosource.cc:878 +#, fuzzy +msgid "AudioSource: cannot open peakpath \"%1\" (%2)" +msgstr "SndFileSource: impossibile accedere al file \"%1\" (%2)" + +#: libs/ardour/audiosource.cc:644 +#, fuzzy +msgid "AudioSource[%1]: peak read - cannot read %2 samples at offset %3" +msgstr "DiskStream %1: impossibile leggere %2 dalla playlista al frame %3" + +#: libs/ardour/audiosource.cc:798 +msgid "%1: could not write read raw data for peak computation (%2)" +msgstr "" + +#: libs/ardour/audiosource.cc:823 +msgid "%1: could not write peak file data (%2)" +msgstr "" + +#: libs/ardour/automation_event.cc:65 libs/ardour/location.cc:345 +#: libs/ardour/tempo.cc:226 msgid "initial" msgstr "iniziale" -#: libs/ardour/automation_event.cc:231 +#: libs/ardour/automation_event.cc:232 msgid "cleared" msgstr "pulito" -#: libs/ardour/automation_event.cc:403 +#: libs/ardour/automation_event.cc:404 msgid "added event" msgstr "aggiunto evento" -#: libs/ardour/automation_event.cc:420 +#: libs/ardour/automation_event.cc:421 msgid "removed event" msgstr "rimosso evento" -#: libs/ardour/automation_event.cc:435 +#: libs/ardour/automation_event.cc:436 msgid "removed multiple events" msgstr "rimossi molteplici eventi" -#: libs/ardour/automation_event.cc:461 +#: libs/ardour/automation_event.cc:467 libs/ardour/automation_event.cc:498 msgid "removed range" msgstr "rimosso intervallo" -#: libs/ardour/automation_event.cc:491 +#: libs/ardour/automation_event.cc:528 msgid "event range adjusted" msgstr "" -#: libs/ardour/automation_event.cc:513 +#: libs/ardour/automation_event.cc:550 msgid "event adjusted" msgstr "" -#: libs/ardour/automation_event.cc:628 libs/ardour/automation_event.cc:733 -#: libs/ardour/panner.cc:1040 +#: libs/ardour/automation_event.cc:665 libs/ardour/automation_event.cc:770 +#: libs/ardour/panner.cc:1041 msgid "programming error:" msgstr "errore di programmazione:" -#: libs/ardour/automation_event.cc:1042 +#: libs/ardour/automation_event.cc:1079 msgid "cut/copy/clear" msgstr "taglia/copia/pulisci" -#: libs/ardour/automation_event.cc:1075 +#: libs/ardour/automation_event.cc:1112 msgid "copy" msgstr "copia" -#: libs/ardour/automation_event.cc:1143 libs/ardour/playlist.cc:939 +#: libs/ardour/automation_event.cc:1180 libs/ardour/playlist.cc:939 msgid "paste" msgstr "incolla" -#: libs/ardour/automation_event.cc:1198 +#: libs/ardour/automation_event.cc:1235 msgid "" "automation list: no x-coordinate stored for control point (point ignored)" msgstr "" "lista automazione: nessuna coordinata X salvata per punto di controllo " "(ignorato)" -#: libs/ardour/automation_event.cc:1204 +#: libs/ardour/automation_event.cc:1241 msgid "" "automation list: no y-coordinate stored for control point (point ignored)" msgstr "" "lista automazione: nessuna coordinata Y salvata per punto di controllo " "(ignorato)" -#: libs/ardour/basic_ui.cc:68 -msgid "unnamed" -msgstr "" - -#: libs/ardour/configuration.cc:79 +#: libs/ardour/configuration.cc:80 #, fuzzy msgid "loading system configuration file %1" msgstr "" "Ardour: impossibile leggere il file di configurazione di sistema \"%1\"" -#: libs/ardour/configuration.cc:82 +#: libs/ardour/configuration.cc:83 msgid "Ardour: cannot read system configuration file \"%1\"" msgstr "" "Ardour: impossibile leggere il file di configurazione di sistema \"%1\"" -#: libs/ardour/configuration.cc:87 +#: libs/ardour/configuration.cc:88 msgid "Ardour: system configuration file \"%1\" not loaded successfully." msgstr "" "Ardour: il file di configurazione di sistema \"%1\" non stato caricato con " "successo" -#: libs/ardour/configuration.cc:104 +#: libs/ardour/configuration.cc:105 #, fuzzy msgid "loading user configuration file %1" msgstr "Ardour: impossibile la lettura del file di configurazione \"%1\"" -#: libs/ardour/configuration.cc:107 +#: libs/ardour/configuration.cc:108 msgid "Ardour: cannot read configuration file \"%1\"" msgstr "Ardour: impossibile la lettura del file di configurazione \"%1\"" -#: libs/ardour/configuration.cc:112 +#: libs/ardour/configuration.cc:113 #, fuzzy msgid "Ardour: user configuration file \"%1\" not loaded successfully." msgstr "" "Ardour: il file di configurazione \"%1\" non stato caricato con successo" -#: libs/ardour/configuration.cc:136 +#: libs/ardour/configuration.cc:137 #, fuzzy msgid "Config file %1 not saved" msgstr "File di configurazione non salvato" -#: libs/ardour/configuration.cc:209 +#: libs/ardour/configuration.cc:210 msgid "ill-formed MIDI port specification in ardour rcfile (ignored)" msgstr "" "porta MIDI mal configurata nel file di configurazione di ardour (ignorato)" @@ -329,28 +515,41 @@ msgstr "Il nodo per la connessione non possiede l'attributo \"nome\"" msgid "Node for Connection has no \"connections\" property" msgstr "Il nodo per la connessione non ha l'attributo \"connessioni\"" -#: libs/ardour/connection.cc:227 libs/ardour/io.cc:1889 +#: libs/ardour/connection.cc:227 libs/ardour/io.cc:1902 msgid "IO: badly formed string in XML node for inputs \"%1\"" msgstr "IO: stringa malformata nel nodo XML per le entrate \"%1\"" -#: libs/ardour/connection.cc:232 libs/ardour/io.cc:1894 +#: libs/ardour/connection.cc:232 libs/ardour/io.cc:1907 msgid "bad input string in XML node \"%1\"" msgstr "stringa malformata nel nodo XML \"%1\"" -#: libs/ardour/control_protocol_manager.cc:79 +#: libs/ardour/control_protocol_manager.cc:80 msgid "control protocol name \"%1\" has no descriptor" msgstr "" -#: libs/ardour/control_protocol_manager.cc:84 +#: libs/ardour/control_protocol_manager.cc:85 msgid "control protocol name \"%1\" could not be initialized" msgstr "" -#: libs/ardour/control_protocol_manager.cc:180 +#: libs/ardour/control_protocol_manager.cc:141 +msgid "Instantiating mandatory control protocol %1" +msgstr "" + +#: libs/ardour/control_protocol_manager.cc:175 +#, fuzzy +msgid "Control protocol %1 not usable" +msgstr "La porta MIDI \"%1\" non disponibile: nessun controllo MTC possibile" + +#: libs/ardour/control_protocol_manager.cc:187 +msgid "Control surface protocol discovered: \"%1\"" +msgstr "" + +#: libs/ardour/control_protocol_manager.cc:205 #, fuzzy msgid "ControlProtocolManager: cannot load module \"%1\" (%2)" msgstr "LADSPA: impossibile caricare il modulo \"%1\" (%2)" -#: libs/ardour/control_protocol_manager.cc:188 +#: libs/ardour/control_protocol_manager.cc:213 #, fuzzy msgid "ControlProtocolManager: module \"%1\" has no descriptor function." msgstr "LADSPA: il modulo \"%1\" non ha alcuna funzione descriptor." @@ -381,365 +580,103 @@ msgstr "livello cambiato" msgid "old-style crossfade information - no position information" msgstr "il nodo XML per la Location non ha informazioni sull'inizio" -#: libs/ardour/curve.cc:112 libs/ardour/insert.cc:454 -#: libs/ardour/session.cc:2452 libs/ardour/session.cc:2504 +#: libs/ardour/curve.cc:112 libs/ardour/globals.cc:340 +#: libs/ardour/insert.cc:454 libs/ardour/session.cc:2466 +#: libs/ardour/session.cc:2518 msgid "programming error: " msgstr "errore di programmazione: " -#: libs/ardour/cycle_timer.cc:35 +#: libs/ardour/cycle_timer.cc:37 msgid "CycleTimer::get_mhz(): can't open /proc/cpuinfo" msgstr "CycleTimer::get_mhz(): impossibile accedere a /proc/cpuinfo" -#: libs/ardour/cycle_timer.cc:47 +#: libs/ardour/cycle_timer.cc:49 msgid "CycleTimer::get_mhz(): cannot locate cpu MHz in /proc/cpuinfo" msgstr "" "CycleTimer::get_mhz(): impossibile localizzare \"cpu MHz\" in /proc/cpuinfo" -#: libs/ardour/cycle_timer.cc:70 +#: libs/ardour/cycle_timer.cc:72 msgid "cannot locate cpu MHz in /proc/cpuinfo" msgstr "impossibile localizzare \"cpu MHz\" in /proc/cpuinfo" -#: libs/ardour/destructive_filesource.cc:197 +#: libs/ardour/destructive_filesource.cc:188 msgid "DestructiveFileSource: \"%1\" bad read retval: %2 of %5 (%3: %4)" msgstr "" -#: libs/ardour/destructive_filesource.cc:210 -#: libs/ardour/destructive_filesource.cc:252 -#: libs/ardour/destructive_filesource.cc:259 +#: libs/ardour/destructive_filesource.cc:201 +#: libs/ardour/destructive_filesource.cc:243 +#: libs/ardour/destructive_filesource.cc:250 msgid "DestructiveFileSource: \"%1\" bad write (%2)" msgstr "" -#: libs/ardour/diskstream.cc:337 -msgid "DiskStream: Session doesn't know about a Playlist called \"%1\"" -msgstr "DiskStream: La sessione non riconosce la Playlist chiamata \"%1\"" - -#: libs/ardour/diskstream.cc:342 -msgid "DiskStream: Playlist \"%1\" isn't an audio playlist" -msgstr "" - -#: libs/ardour/diskstream.cc:433 -msgid "DiskStream %1: there is no existing playlist to make a copy of!" -msgstr "DiskStream %1: non esiste alcuna playlist di cui fare una copia!" - -#: libs/ardour/diskstream.cc:1113 libs/ardour/diskstream.cc:1124 -msgid "DiskStream %1: when refilling, cannot read %2 from playlist at frame %3" -msgstr "DiskStream %1: impossibile leggere %2 dalla playlista al frame %3" - -#: libs/ardour/diskstream.cc:1256 -msgid "DiskStream %1: cannot read %2 from playlist at frame %3" -msgstr "DiskStream %1: impossibile leggere %2 dalla playlista al frame %3" - -#: libs/ardour/diskstream.cc:1623 libs/ardour/diskstream.cc:1640 -msgid "DiskStream %1: cannot write to disk" -msgstr "DiskStream %1: impossibile scrivere sul disco" - -#: libs/ardour/diskstream.cc:1700 -msgid "DiskStream \"%1\": cannot flush captured data to disk!" -msgstr "DiskStream \"%1\": impossibile scaricare i dati acquisiti sul disco!" - -#: libs/ardour/diskstream.cc:1797 -msgid "%1: could not create region for complete audio file" -msgstr "%1: impossibile creare una regione per il file audio completo" - -#: libs/ardour/diskstream.cc:1820 -msgid "DiskStream: could not create region for captured audio!" -msgstr "DiskStream: impossibile creare una regione per l'audio registrato!" - -#: libs/ardour/diskstream.cc:1875 -#, fuzzy -msgid "programmer error: %1" -msgstr "errore di programmazione: %1" - -#: libs/ardour/diskstream.cc:2155 -#, fuzzy -msgid "DiskStream: channel %1 out of range" -msgstr "DiskStream: canale fuori margine" - -#: libs/ardour/diskstream.cc:2180 -msgid "%1:%2 new capture file not initialized correctly" -msgstr "%1:%2 nuovo file di registrazione non è stato avviato correttamente" - -#: libs/ardour/diskstream.cc:2413 -msgid "Location \"%1\" not valid for track loop (start >= end)" -msgstr "La Location \"%1\" non valida per il loop (inizio >= fine)" - -#: libs/ardour/diskstream.cc:2491 -#, fuzzy -msgid "%1: cannot restore pending capture source file %2" -msgstr "Import: impossibile aprire il file audio di input \"%1\"" - -#: libs/ardour/diskstream.cc:2513 -msgid "%1: incorrect number of pending sources listed - ignoring them all" -msgstr "" - -#: libs/ardour/diskstream.cc:2529 -#, fuzzy -msgid "%1: cannot create whole-file region from pending capture sources" -msgstr "Playlist: impossibile creare la Regione dal file di stato" - -#: libs/ardour/diskstream.cc:2541 -#, fuzzy -msgid "%1: cannot create region from pending capture sources" -msgstr "Playlist: impossibile creare la Regione dal file di stato" - -#: libs/ardour/filesource.cc:175 -msgid "FileSource: search path not set" -msgstr "FileSource: percorso di ricerca non specificato" - -#: libs/ardour/filesource.cc:190 -msgid "FileSource: \"%1\" not found when searching %2 using %3" -msgstr "FileSource: \"%1\" non trovato nel cercare %2 utilizzando %3" - -#: libs/ardour/filesource.cc:196 -msgid "" -"FileSource: \"%1\" is ambigous when searching %2\n" -"\t" -msgstr "" -"FileSource: \"%1\" è risultato ambiguo nel cercare %2\n" -"\t" - -#: libs/ardour/filesource.cc:231 -msgid "Filesource: cannot find required file (%1): %2" -msgstr "FileSource: impossibile trovare il file richiesto (%1): %2" - -#: libs/ardour/filesource.cc:239 -msgid "Filesource: cannot check for existing file (%1): %2" -msgstr "FileSource: impossibile controllare il file esistente (%1): %2" - -#: libs/ardour/filesource.cc:245 libs/ardour/filesource.cc:1127 -#: libs/ardour/filesource.cc:1210 -msgid "FileSource: could not open \"%1\": (%2)" -msgstr "FileSource: impossibile aprire \"%1\": (%2)" - -#: libs/ardour/filesource.cc:278 -msgid "FileSource: cannot write header in %1" -msgstr "FileSource: impossibile scrivere header in %1" - -#: libs/ardour/filesource.cc:293 -msgid "FileSource: cannot locate chunks in %1" -msgstr "FileSource: impossibile trovare spezzoni in %1" - -#: libs/ardour/filesource.cc:298 -msgid "FileSource: cannot read header in %1" -msgstr "FileSource: impossibile leggere header in %1" - -#: libs/ardour/filesource.cc:303 -msgid "FileSource: cannot check header in %1" -msgstr "FileSource: impossibile controllare header in %1" - -#: libs/ardour/filesource.cc:311 -#, fuzzy -msgid "FileSource: cannot initialize peakfile for %1 as %2" -msgstr "FileSource: impossibile avviare il peakfile per %1" - -#: libs/ardour/filesource.cc:359 libs/ardour/insert.cc:525 -msgid "programming error: %1" -msgstr "errore di programmazione: %1" - -#: libs/ardour/filesource.cc:364 -#, fuzzy -msgid "cannot rename audio file for %1 to %2" -msgstr "impossibile rinominare file audio sorgente da %1 a %2 (%3)" - -#: libs/ardour/filesource.cc:390 -msgid "FileSource: cannot seek to end of file" -msgstr "FileSource: impossibile cercare fino alla fine del file" - -#: libs/ardour/filesource.cc:395 -msgid "FileSource: cannot read RIFF/WAVE chunk from file" -msgstr "FileSource: impossibile accedere allo spezzone RIFF/WAVE dal file" - -#: libs/ardour/filesource.cc:407 -msgid "FileSource %1: not a RIFF/WAVE file" -msgstr "FileSource %1: il file non un file RIFF/WAVE" - -#: libs/ardour/filesource.cc:434 -msgid "FileSource: can't read a chunk" -msgstr "FileSource: impossibile accedere ad uno spezzone" - -#: libs/ardour/filesource.cc:451 -msgid "filesource: correcting mis-written RIFF file to become a RIFX: " -msgstr "" - -#: libs/ardour/filesource.cc:567 -msgid "FileSource: cannot get user information for BWF header (%1)" -msgstr "FileSource: impossibile otterene info utente dall'header BWF (%1)" - -#: libs/ardour/filesource.cc:571 -msgid "FileSource: cannot get host information for BWF header (%1)" -msgstr "FileSource: impossibile ottenere info sull'host dall'header BWF (%1)" - -#: libs/ardour/filesource.cc:716 -msgid "FileSource[%1]: cannot update data size: %2" -msgstr "FileSource[%1]: impossibile aggiornare la dimensione dei dati: %2" - -#: libs/ardour/filesource.cc:733 -msgid "FileSource: can't find RIFF chunk info" -msgstr "FileSource: impossibile trovare info sullo spezzone RIFF" - -#: libs/ardour/filesource.cc:737 -#, fuzzy -msgid "FileSource: can't find RIFX chunk info" -msgstr "FileSource: impossibile trovare info sullo spezzone RIFF" - -#: libs/ardour/filesource.cc:758 -msgid "FileSource: can't read RIFF chunk" -msgstr "FileSource: impossibile accedere allo spezzone RIFF" - -#: libs/ardour/filesource.cc:768 -msgid "FileSource: can't find format chunk info" -msgstr "FileSource: impossibile trovare info sul formato dello spezzone" - -#: libs/ardour/filesource.cc:773 -msgid "FileSource: can't read format chunk" -msgstr "FileSource: impossibile leggere il formato dello spezzone" - -#: libs/ardour/filesource.cc:782 -msgid "FileSource: can't find data chunk info" -msgstr "FileSource: impossibile trovare info sui dati dello spezzone" - -#: libs/ardour/filesource.cc:787 -msgid "FileSource: can't read data chunk" -msgstr "FileSource: impossibile leggere dati dello spezzone" - -#: libs/ardour/filesource.cc:804 -msgid "" -"FileSource: cannot read Broadcast Wave data from existing audio file \"%1" -"\" (%2)" -msgstr "" -"FileSource: impossibile leggere dati Broadcast Wave dal file audio esistente " -"\"%1\" (%2) " - -#: libs/ardour/filesource.cc:820 -msgid "" -"FileSource: cannot read Broadcast Wave coding history from audio file \"%1" -"\" (%2)" -msgstr "" -"FileSource: impossibile leggere lo storico del Broadcast Wave dal file audio " -"\"%1\" (%2)" - -#: libs/ardour/filesource.cc:862 -#, fuzzy -msgid "" -"FileSource \"%1\" does not use valid sample format.\n" -"This is probably a programming error." -msgstr "" -"FileSource \"%1\" non usa il formato floating point.\n" -"Questo probabilmente un errore di programmazione." - -#: libs/ardour/filesource.cc:901 -msgid "FileSource \"%1\" has no \"data\" chunk" -msgstr "FileSource \"%1\" non ha uno spezzone di \"dati\"" - -#: libs/ardour/filesource.cc:906 -msgid "%1: data length in header (%2) differs from implicit size in file (%3)" -msgstr "" -"%1: la lunghezza dei dati nell'header (%2) diversa dalla dimensione " -"implicita nel file (%3)" - -#: libs/ardour/filesource.cc:911 -msgid "\"%1\" has a sample rate of %2 instead of %3 as used by this session" -msgstr "" -"\"%1\" ha una sample rate di %2 anzicch di %3 come il resto della sessione" - -#: libs/ardour/filesource.cc:934 -msgid "FileSource: cannot write WAVE chunk: %1" -msgstr "FileSource: impossibile scrivere lo spezzone WAVE: %1" - -#: libs/ardour/filesource.cc:978 -msgid "FileSource: cannot write format chunk: %1" -msgstr "FileSource: impossibile scrivere il formato dello spezzone: %1" - -#: libs/ardour/filesource.cc:990 -msgid "FileSource: cannot data chunk: %1" -msgstr "" - -#: libs/ardour/filesource.cc:1103 libs/ardour/filesource.cc:1188 -msgid "FileSource: \"%1\" bad write (%2)" -msgstr "" - -#: libs/ardour/filesource.cc:1335 libs/ardour/session_state.cc:3093 -msgid "" -"there are already 1000 files with names like %1; versioning discontinued" -msgstr "" -"ci sono gia' 1000 file con nomi come %1; tracciamento di versione interrotto" - -#: libs/ardour/filesource.cc:1349 libs/ardour/session_state.cc:3107 -msgid "cannot rename audio file source from %1 to %2 (%3)" -msgstr "impossibile rinominare file audio sorgente da %1 a %2 (%3)" - -#: libs/ardour/filesource.cc:1356 libs/ardour/session_state.cc:3122 -msgid "cannot remove peakfile %1 for %2 (%3)" -msgstr "impossibile eliminare il peakfile %1 per %2 (%3)" - -#: libs/ardour/globals.cc:82 +#: libs/ardour/globals.cc:109 msgid "no MIDI ports specified: no MMC or MTC control possible" msgstr "Nessuna porta MIDI specificata: impossibile alcun controllo MMC o MTC" -#: libs/ardour/globals.cc:97 +#: libs/ardour/globals.cc:124 msgid "MIDI port specifications for \"%1\" are not understandable." msgstr "Le specifiche per la porta MIDI \"%1\" non sono state capite" -#: libs/ardour/globals.cc:110 libs/ardour/globals.cc:114 -#: libs/ardour/globals.cc:118 +#: libs/ardour/globals.cc:137 libs/ardour/globals.cc:141 +#: libs/ardour/globals.cc:145 msgid "default" msgstr "" -#: libs/ardour/globals.cc:146 +#: libs/ardour/globals.cc:173 msgid "No MMC control (MIDI port \"%1\" not available)" msgstr "La porta MIDI \"%1\" non disponibile: nessun controllo MTC possibile" -#: libs/ardour/globals.cc:152 +#: libs/ardour/globals.cc:179 msgid "No MTC support (MIDI port \"%1\" not available)" msgstr "La porta MIDI \"%1\" non disponibile: nessun controllo MTC possibile" -#: libs/ardour/globals.cc:157 +#: libs/ardour/globals.cc:184 #, fuzzy msgid "No MIDI parameter support (MIDI port \"%1\" not available)" msgstr "La porta MIDI \"%1\" non disponibile: nessun controllo MTC possibile" -#: libs/ardour/import.cc:71 +#: libs/ardour/import.cc:75 msgid "Import: cannot open input sound file \"%1\"" msgstr "Import: impossibile aprire il file audio di input \"%1\"" -#: libs/ardour/import.cc:76 +#: libs/ardour/import.cc:80 msgid "resampling audio" msgstr "" -#: libs/ardour/import.cc:80 +#: libs/ardour/import.cc:84 msgid "Import: cannot open converted sound file \"%1\"" msgstr "Import: impossibile aprire il file audio convertito \"%1\"" -#: libs/ardour/import.cc:85 +#: libs/ardour/import.cc:89 msgid "Import: error while resampling sound file \"%1\"" msgstr "Import: errore nel resampling deil file audio \"%1\"" -#: libs/ardour/import.cc:141 +#: libs/ardour/import.cc:148 msgid "Session::import_audiofile: cannot open new file source for channel %1" msgstr "" "Session::import_audiofile: impossibile aprire il nuovo file per il canale %1" -#: libs/ardour/import.cc:160 +#: libs/ardour/import.cc:167 msgid "converting audio" msgstr "conversione dell'audio" -#: libs/ardour/import.cc:192 +#: libs/ardour/import.cc:199 msgid "building region" msgstr "costruzione della regione" -#: libs/ardour/import.cc:194 +#: libs/ardour/import.cc:201 msgid "building regions" msgstr "costruzione delle regioni" -#: libs/ardour/import.cc:318 +#: libs/ardour/import.cc:325 msgid "Import: could not open temp file: %1" msgstr "Import: impossibile aprire il file audio temporaneo \"%1\"" -#: libs/ardour/import.cc:327 +#: libs/ardour/import.cc:334 msgid "Import: src_new() failed : %1" msgstr "" -#: libs/ardour/import.cc:355 +#: libs/ardour/import.cc:362 msgid "Import: %1" msgstr "" @@ -796,280 +733,280 @@ msgstr "PortInsert: impossibile aggiungere una porta d'uscita" msgid "non-port insert XML used for port plugin insert" msgstr "insert non-port XML usato per insert di plugin di porta" -#: libs/ardour/io.cc:585 +#: libs/ardour/io.cc:598 msgid "IO: cannot disconnect input port %1 from %2" msgstr "IO: impossibile disconnettere la porta d'entrata %1 da %2" -#: libs/ardour/io.cc:653 +#: libs/ardour/io.cc:666 msgid "IO: cannot disconnect output port %1 from %2" msgstr "IO: impossibile disconnettere la porta d'uscita %1 da %2" -#: libs/ardour/io.cc:794 libs/ardour/io.cc:1138 libs/ardour/io.cc:1264 +#: libs/ardour/io.cc:807 libs/ardour/io.cc:1151 libs/ardour/io.cc:1277 #, c-format msgid "%s/out" msgstr "" -#: libs/ardour/io.cc:796 libs/ardour/io.cc:1140 libs/ardour/io.cc:1266 -#: libs/ardour/io.cc:2826 +#: libs/ardour/io.cc:809 libs/ardour/io.cc:1153 libs/ardour/io.cc:1279 +#: libs/ardour/io.cc:2849 #, c-format msgid "%s/out %u" msgstr "" -#: libs/ardour/io.cc:800 libs/ardour/io.cc:1145 libs/ardour/io.cc:1270 +#: libs/ardour/io.cc:813 libs/ardour/io.cc:1158 libs/ardour/io.cc:1283 msgid "IO: cannot register output port %1" msgstr "IO: impossibile registrare la porta %1" -#: libs/ardour/io.cc:895 libs/ardour/io.cc:998 libs/ardour/io.cc:1104 +#: libs/ardour/io.cc:908 libs/ardour/io.cc:1011 libs/ardour/io.cc:1117 #, c-format msgid "%s/in" msgstr "" -#: libs/ardour/io.cc:897 libs/ardour/io.cc:1001 libs/ardour/io.cc:1107 -#: libs/ardour/io.cc:2796 +#: libs/ardour/io.cc:910 libs/ardour/io.cc:1014 libs/ardour/io.cc:1120 +#: libs/ardour/io.cc:2819 #, c-format msgid "%s/in %u" msgstr "" -#: libs/ardour/io.cc:901 libs/ardour/io.cc:1007 libs/ardour/io.cc:1112 +#: libs/ardour/io.cc:914 libs/ardour/io.cc:1020 libs/ardour/io.cc:1125 msgid "IO: cannot register input port %1" msgstr "IO: impossibile registrare la porta %1" -#: libs/ardour/io.cc:1528 +#: libs/ardour/io.cc:1541 msgid "IO::connecting_became_legal() called without a pending state node" msgstr "" -#: libs/ardour/io.cc:1551 +#: libs/ardour/io.cc:1564 msgid "IO::ports_became_legal() called without a pending state node" msgstr "" -#: libs/ardour/io.cc:1581 +#: libs/ardour/io.cc:1594 msgid "incorrect XML node \"%1\" passed to IO object" msgstr "" -#: libs/ardour/io.cc:1636 +#: libs/ardour/io.cc:1649 msgid "" "MIDI gain control specification for %1 is incomplete, so it has been ignored" msgstr "" -#: libs/ardour/io.cc:1726 libs/ardour/io.cc:1838 +#: libs/ardour/io.cc:1739 libs/ardour/io.cc:1851 msgid "Unknown connection \"%1\" listed for output of %2" msgstr "" -#: libs/ardour/io.cc:1728 libs/ardour/io.cc:1840 +#: libs/ardour/io.cc:1741 libs/ardour/io.cc:1853 msgid "out 1" msgstr "" -#: libs/ardour/io.cc:1729 libs/ardour/io.cc:1841 +#: libs/ardour/io.cc:1742 libs/ardour/io.cc:1854 msgid "No output connections available as a replacement" msgstr "" -#: libs/ardour/io.cc:1733 libs/ardour/io.cc:1845 +#: libs/ardour/io.cc:1746 libs/ardour/io.cc:1858 msgid "Connection %1 was not available - \"out 1\" used instead" msgstr "" -#: libs/ardour/io.cc:1747 +#: libs/ardour/io.cc:1760 msgid "%1: cannot create I/O ports" msgstr "" -#: libs/ardour/io.cc:1854 +#: libs/ardour/io.cc:1867 msgid "improper output channel list in XML node (%1)" msgstr "" -#: libs/ardour/io.cc:1939 +#: libs/ardour/io.cc:1952 msgid "IO: badly formed string in XML node for outputs \"%1\"" msgstr "IO: stringa mal formata nel nodo XML per le uscite \"%1\"" -#: libs/ardour/io.cc:1944 +#: libs/ardour/io.cc:1957 msgid "IO: bad output string in XML node \"%1\"" msgstr "IO: stringa mal formata nel nodo XML \"%1\"" -#: libs/ardour/io.cc:2502 +#: libs/ardour/io.cc:2525 msgid "%1: could not open automation event file \"%2\"" msgstr "" -#: libs/ardour/io.cc:2541 +#: libs/ardour/io.cc:2564 msgid "%1: cannot open automation event file \"%2\"" msgstr "" -#: libs/ardour/io.cc:2556 +#: libs/ardour/io.cc:2579 msgid "badly formed version number in automation event file \"%1\"" msgstr "" -#: libs/ardour/io.cc:2560 +#: libs/ardour/io.cc:2583 msgid "no version information in automation event file \"%1\"" msgstr "" -#: libs/ardour/io.cc:2565 +#: libs/ardour/io.cc:2588 msgid "mismatched automation event file version (%1)" msgstr "" -#: libs/ardour/io.cc:2573 +#: libs/ardour/io.cc:2596 msgid "badly formatted automation event record at line %1 of %2 (ignored)" msgstr "" -#: libs/ardour/io.cc:2593 +#: libs/ardour/io.cc:2616 msgid "dubious automation event found (and ignored)" msgstr "" -#: libs/ardour/io.cc:2597 libs/ardour/panner.cc:437 +#: libs/ardour/io.cc:2620 libs/ardour/panner.cc:438 #: libs/ardour/redirect.cc:148 msgid "loaded from disk" msgstr "" -#: libs/ardour/io.cc:2768 +#: libs/ardour/io.cc:2791 msgid "automation write/touch" msgstr "" -#: libs/ardour/ladspa_plugin.cc:86 +#: libs/ardour/ladspa_plugin.cc:87 msgid "LADSPA: module has no descriptor function." msgstr "LADSPA: il modulo non ha alcuna funzione descriptor." -#: libs/ardour/ladspa_plugin.cc:91 +#: libs/ardour/ladspa_plugin.cc:92 msgid "LADSPA: plugin has gone away since discovery!" msgstr "LADSPA: il plugin è stato rimosso" -#: libs/ardour/ladspa_plugin.cc:98 +#: libs/ardour/ladspa_plugin.cc:99 msgid "LADSPA: \"%1\" cannot be used, since it cannot do inplace processing" msgstr "" -#: libs/ardour/ladspa_plugin.cc:328 +#: libs/ardour/ladspa_plugin.cc:329 msgid "" "illegal parameter number used with plugin \"%1\". This mayindicate a change " "in the plugin design, and presets may beinvalid" msgstr "" -#: libs/ardour/ladspa_plugin.cc:429 +#: libs/ardour/ladspa_plugin.cc:430 msgid "Bad node sent to LadspaPlugin::set_state" msgstr "" -#: libs/ardour/ladspa_plugin.cc:442 +#: libs/ardour/ladspa_plugin.cc:443 msgid "LADSPA: no ladspa port number" msgstr "" -#: libs/ardour/ladspa_plugin.cc:448 +#: libs/ardour/ladspa_plugin.cc:449 msgid "LADSPA: no ladspa port data" msgstr "" -#: libs/ardour/ladspa_plugin.cc:497 +#: libs/ardour/ladspa_plugin.cc:498 msgid "" "LADSPA LadspaPlugin MIDI control specification for port %1 is incomplete, so " "it has been ignored" msgstr "" -#: libs/ardour/location.cc:268 +#: libs/ardour/location.cc:269 msgid "incorrect XML node passed to Location::set_state" msgstr "" -#: libs/ardour/location.cc:275 +#: libs/ardour/location.cc:276 msgid "XML node for Location has no name information" msgstr "il nodo XML per la Location non ha informazioni sul nome" -#: libs/ardour/location.cc:282 +#: libs/ardour/location.cc:283 msgid "XML node for Location has no start information" msgstr "il nodo XML per la Location non ha informazioni sull'inizio" -#: libs/ardour/location.cc:293 +#: libs/ardour/location.cc:294 msgid "XML node for Location has no end information" msgstr "il nodo XML per la Location non ha informazioni sulla fine" -#: libs/ardour/location.cc:302 +#: libs/ardour/location.cc:303 msgid "XML node for Location has no flags information" msgstr "il nodo XML per la Location non ha informazioni sui flags" -#: libs/ardour/location.cc:390 +#: libs/ardour/location.cc:391 msgid "Locations: attempt to use unknown location as selected location" msgstr "" -#: libs/ardour/location.cc:417 libs/ardour/playlist.cc:1187 +#: libs/ardour/location.cc:418 libs/ardour/playlist.cc:1187 msgid "clear" msgstr "pulisci" -#: libs/ardour/location.cc:442 +#: libs/ardour/location.cc:443 msgid "clear markers" msgstr "" -#: libs/ardour/location.cc:470 +#: libs/ardour/location.cc:471 msgid "clear ranges" msgstr "" -#: libs/ardour/location.cc:488 +#: libs/ardour/location.cc:489 msgid "add" msgstr "" -#: libs/ardour/location.cc:526 +#: libs/ardour/location.cc:527 msgid "remove" msgstr "rimuovi" -#: libs/ardour/location.cc:566 +#: libs/ardour/location.cc:567 msgid "incorrect XML mode passed to Locations::set_state" msgstr "" -#: libs/ardour/mtc_slave.cc:195 +#: libs/ardour/mtc_slave.cc:196 msgid "MTC Slave: atomic read of current time failed, sleeping!" msgstr "" -#: libs/ardour/named_selection.cc:76 +#: libs/ardour/named_selection.cc:77 msgid "Chunk %1 uses an unknown playlist \"%2\"" msgstr "Lo spezzone %1 usa una playlist sconosciuta \"%2\"" -#: libs/ardour/named_selection.cc:79 +#: libs/ardour/named_selection.cc:80 msgid "Chunk %1 contains misformed playlist information" msgstr "Lo spezzone %1 contiene informazioni sulla playlist mal formate" -#: libs/ardour/panner.cc:255 +#: libs/ardour/panner.cc:256 msgid "MIDI pan control specification is incomplete, so it has been ignored" msgstr "" -#: libs/ardour/panner.cc:360 +#: libs/ardour/panner.cc:361 msgid "automation write pass" msgstr "" -#: libs/ardour/panner.cc:400 +#: libs/ardour/panner.cc:401 #, c-format msgid "error writing pan automation file (%s)" msgstr "errore nello scrivere il file per l'automazione pan (%s)" -#: libs/ardour/panner.cc:428 +#: libs/ardour/panner.cc:429 msgid "" "badly formatted pan automation event record at line %1 of %2 (ignored) [%3]" msgstr "" -#: libs/ardour/panner.cc:943 +#: libs/ardour/panner.cc:944 msgid "badly-formed positional data for Multi2dPanner - ignored" msgstr "" -#: libs/ardour/panner.cc:1236 +#: libs/ardour/panner.cc:1237 msgid "cannot open pan automation file \"%1\" for saving (%s)" msgstr "" "impossibile aprire il file dell'automazione pan \"%1\" per salvare (%s)" -#: libs/ardour/panner.cc:1272 +#: libs/ardour/panner.cc:1273 msgid "cannot open pan automation file %1 (%2)" msgstr "impossibile accedere al file dell'automazione pan %1 (%2)" -#: libs/ardour/panner.cc:1285 +#: libs/ardour/panner.cc:1286 msgid "badly formed version number in pan automation event file \"%1\"" msgstr "" -#: libs/ardour/panner.cc:1289 +#: libs/ardour/panner.cc:1290 msgid "" "no version information in pan automation event file \"%1\" (first line = %2)" msgstr "" -#: libs/ardour/panner.cc:1295 +#: libs/ardour/panner.cc:1296 msgid "mismatched pan automation event file version (%1)" msgstr "" -#: libs/ardour/panner.cc:1309 +#: libs/ardour/panner.cc:1310 msgid "too many panner states found in pan automation file %1" msgstr "" -#: libs/ardour/panner.cc:1450 +#: libs/ardour/panner.cc:1451 #, fuzzy msgid "Unknown panner plugin \"%1\" found in pan state - ignored" msgstr "Nodo sconosciuto \"%1\" trovato in Connections list dal file di stato" -#: libs/ardour/panner.cc:1456 +#: libs/ardour/panner.cc:1457 #, fuzzy msgid "panner plugin node has no type information!" msgstr "il nodo XML per la Location non ha informazioni sulla fine" @@ -1123,63 +1060,63 @@ msgstr "Playlist: impossibile creare la Regione dal file di stato" msgid "nudged" msgstr "spostato" -#: libs/ardour/playlist_factory.cc:26 libs/ardour/playlist_factory.cc:41 +#: libs/ardour/playlist_factory.cc:49 libs/ardour/playlist_factory.cc:64 msgid "" "programming error: Playlist::createRegion called with unknown Region type" msgstr "" -#: libs/ardour/playlist_factory.cc:63 +#: libs/ardour/playlist_factory.cc:86 msgid "" "programming error: Playlist::copyPlaylist called with unknown Playlist type" msgstr "" -#: libs/ardour/plugin.cc:327 +#: libs/ardour/plugin.cc:328 msgid "Could not locate HOME. Preset not saved." msgstr "impossibile localizzare HOME. Preset non salvato." -#: libs/ardour/plugin.cc:337 libs/ardour/plugin.cc:343 +#: libs/ardour/plugin.cc:338 libs/ardour/plugin.cc:344 msgid "Could not create %1. Preset not saved. (%2)" msgstr "Impossibile creare %1 . Preset non salvato. (%2)" -#: libs/ardour/plugin.cc:348 +#: libs/ardour/plugin.cc:349 msgid "Error saving presets file %1." msgstr "Errore nel salvare il file di preset %1." -#: libs/ardour/plugin_manager.cc:193 +#: libs/ardour/plugin_manager.cc:194 #, fuzzy msgid "Could not parse rdf file: %1" msgstr "IO: impossibile registrare la porta %1" -#: libs/ardour/plugin_manager.cc:234 +#: libs/ardour/plugin_manager.cc:235 msgid "LADSPA: cannot load module \"%1\" (%2)" msgstr "LADSPA: impossibile caricare il modulo \"%1\" (%2)" -#: libs/ardour/plugin_manager.cc:241 +#: libs/ardour/plugin_manager.cc:242 msgid "LADSPA: module \"%1\" has no descriptor function." msgstr "LADSPA: il modulo \"%1\" non ha alcuna funzione descriptor." -#: libs/ardour/plugin_manager.cc:296 +#: libs/ardour/plugin_manager.cc:297 #, fuzzy msgid "VST: cannot load module from \"%1\"" msgstr "LADPSA: impossibile caricare il modulo da \"%1\"" -#: libs/ardour/plugin_manager.cc:301 +#: libs/ardour/plugin_manager.cc:302 msgid "You asked ardour to not use any VST plugins" msgstr "" -#: libs/ardour/plugin_manager.cc:304 +#: libs/ardour/plugin_manager.cc:305 msgid "This version of ardour has no support for VST plugins" msgstr "" -#: libs/ardour/plugin_manager.cc:311 +#: libs/ardour/plugin_manager.cc:312 msgid "LADSPA: cannot load module from \"%1\"" msgstr "LADPSA: impossibile caricare il modulo da \"%1\"" -#: libs/ardour/plugin_manager.cc:373 libs/ardour/plugin_manager.cc:385 +#: libs/ardour/plugin_manager.cc:374 libs/ardour/plugin_manager.cc:386 msgid "Unknown" msgstr "" -#: libs/ardour/plugin_manager.cc:463 +#: libs/ardour/plugin_manager.cc:464 msgid "" "VST plugin %1 does not support processReplacing, and so cannot be used in " "ardour at this time" @@ -1194,11 +1131,11 @@ msgstr "impossibile accedere al file di sessione recente %1 (%2)" msgid "programming error: unknown Redirect type in Redirect::Clone!\n" msgstr "" -#: libs/ardour/redirect.cc:102 libs/ardour/utils.cc:199 +#: libs/ardour/redirect.cc:102 libs/ardour/utils.cc:203 msgid "pre" msgstr "" -#: libs/ardour/redirect.cc:104 libs/ardour/utils.cc:202 +#: libs/ardour/redirect.cc:104 libs/ardour/utils.cc:206 #, fuzzy msgid "post" msgstr "incolla" @@ -1253,265 +1190,260 @@ msgstr "" msgid "active_changed" msgstr "livello cambiato" -#: libs/ardour/region.cc:884 +#: libs/ardour/region.cc:885 msgid "Session: XMLNode describing a Region is incomplete (no id)" msgstr "" -#: libs/ardour/region.cc:891 +#: libs/ardour/region.cc:892 msgid "Session: XMLNode describing a Region is incomplete (no name)" msgstr "" -#: libs/ardour/route.cc:79 libs/ardour/session.cc:1541 -#: libs/ardour/session.cc:1547 libs/ardour/session.cc:3064 +#: libs/ardour/route.cc:79 libs/ardour/session.cc:1554 +#: libs/ardour/session.cc:1560 libs/ardour/session.cc:3093 msgid "signal" msgstr "segnale" -#: libs/ardour/route.cc:1433 +#: libs/ardour/route.cc:1430 msgid "Could not get state of route. Problem with save_automation" msgstr "" -#: libs/ardour/route.cc:1485 +#: libs/ardour/route.cc:1482 msgid "Send construction failed" msgstr "" -#: libs/ardour/route.cc:1507 +#: libs/ardour/route.cc:1504 msgid "unknown Insert type \"%1\"; ignored" msgstr "" -#: libs/ardour/route.cc:1513 +#: libs/ardour/route.cc:1510 msgid "Insert XML node has no type property" msgstr "" -#: libs/ardour/route.cc:1518 +#: libs/ardour/route.cc:1515 msgid "insert could not be created. Ignored." msgstr "" -#: libs/ardour/route.cc:1536 +#: libs/ardour/route.cc:1533 msgid "Bad node sent to Route::set_state() [%1]" msgstr "" -#: libs/ardour/route.cc:1595 +#: libs/ardour/route.cc:1592 msgid "Route %1: unknown edit group \"%2 in saved state (ignored)" msgstr "" -#: libs/ardour/route.cc:1611 libs/ardour/route.cc:1615 +#: libs/ardour/route.cc:1608 libs/ardour/route.cc:1612 msgid "badly formed order key string in state file! [%1] ... ignored." msgstr "" -#: libs/ardour/route.cc:1696 libs/ardour/route.cc:1823 +#: libs/ardour/route.cc:1693 libs/ardour/route.cc:1820 msgid "[control]" msgstr "" -#: libs/ardour/route.cc:1716 +#: libs/ardour/route.cc:1713 msgid "Route %1: unknown mix group \"%2 in saved state (ignored)" msgstr "" -#: libs/ardour/route.cc:1745 libs/ardour/route.cc:1753 +#: libs/ardour/route.cc:1742 libs/ardour/route.cc:1750 msgid "" "MIDI mute control specification for %1 is incomplete, so it has been ignored" msgstr "" -#: libs/ardour/send.cc:98 +#: libs/ardour/send.cc:99 msgid "XML node describing a send is missing a Redirect node" msgstr "" -#: libs/ardour/session.cc:99 +#: libs/ardour/session.cc:103 #, fuzzy msgid "Could not resolve path: %1 (%2)" msgstr "impossibile controllare il percorso %1 (%2)" -#: libs/ardour/session.cc:111 +#: libs/ardour/session.cc:115 msgid "cannot check session path %1 (%2)" msgstr "impossibile controllare il percorso %1 (%2)" -#: libs/ardour/session.cc:141 +#: libs/ardour/session.cc:145 msgid "cannot check statefile %1 (%2)" msgstr "impossibile controllare il file di stato %1 (%2)" -#: libs/ardour/session.cc:177 +#: libs/ardour/session.cc:181 msgid "%1 is not an Ardour snapshot file" msgstr "%1 non è un file di istantanea di Ardour" -#: libs/ardour/session.cc:194 +#: libs/ardour/session.cc:198 msgid "cannot determine current working directory (%1)" msgstr "impossibile determinare la cartella di lavoro corrente (%1)" -#: libs/ardour/session.cc:211 +#: libs/ardour/session.cc:215 msgid "unknown file type for session %1" msgstr "tipo di fle sconosciuto per la sessione %1" -#: libs/ardour/session.cc:316 +#: libs/ardour/session.cc:320 msgid "monitor" msgstr "" -#: libs/ardour/session.cc:323 +#: libs/ardour/session.cc:327 msgid "master" msgstr "" -#: libs/ardour/session.cc:607 +#: libs/ardour/session.cc:611 msgid "could not setup Click I/O" msgstr "impossibile impostare entrata/uscita del click" -#: libs/ardour/session.cc:628 +#: libs/ardour/session.cc:632 msgid "cannot setup Click I/O" msgstr "impossibile impostare entrata/uscita del click" -#: libs/ardour/session.cc:650 +#: libs/ardour/session.cc:654 msgid "cannot create Auditioner: no auditioning of regions possible" msgstr "impossibile creare l'Auditioner" -#: libs/ardour/session.cc:662 +#: libs/ardour/session.cc:666 #, c-format msgid "out %" msgstr "" -#: libs/ardour/session.cc:674 +#: libs/ardour/session.cc:678 #, c-format msgid "in %" msgstr "" -#: libs/ardour/session.cc:688 +#: libs/ardour/session.cc:692 #, c-format msgid "out %+%" msgstr "" -#: libs/ardour/session.cc:702 +#: libs/ardour/session.cc:706 #, c-format msgid "in %+%" msgstr "" -#: libs/ardour/session.cc:735 +#: libs/ardour/session.cc:739 #, fuzzy msgid "cannot setup master inputs" msgstr "IO: impossibile registrare la porta %1" -#: libs/ardour/session.cc:743 +#: libs/ardour/session.cc:747 #, fuzzy msgid "cannot setup master outputs" msgstr "IO: impossibile registrare la porta %1" -#: libs/ardour/session.cc:754 +#: libs/ardour/session.cc:758 msgid "Master Out" msgstr "" -#: libs/ardour/session.cc:820 +#: libs/ardour/session.cc:830 #, fuzzy msgid "cannot setup control inputs" msgstr "impossibile impostare entrata/uscita del click" -#: libs/ardour/session.cc:828 +#: libs/ardour/session.cc:838 #, fuzzy msgid "cannot set up master outputs" msgstr "IO: impossibile registrare la porta %1" -#: libs/ardour/session.cc:1100 +#: libs/ardour/session.cc:1110 msgid "Session: you can't use that location for auto punch (start <= end)" msgstr "" "Sessione: non si può usare quella location per l'auto punch (inizio <= fine)" -#: libs/ardour/session.cc:1179 +#: libs/ardour/session.cc:1189 msgid "Session: you can't use a mark for auto loop" msgstr "Sessione: non si può usare un marcatore per l'auto loop" -#: libs/ardour/session.cc:1559 +#: libs/ardour/session.cc:1572 msgid "feedback loop setup between %1 and %2" msgstr "" -#: libs/ardour/session.cc:1711 libs/ardour/session.cc:1808 +#: libs/ardour/session.cc:1724 libs/ardour/session.cc:1821 msgid "cannot configure %1 in/%2 out configuration for new audio track" msgstr "" -#: libs/ardour/session.cc:1767 +#: libs/ardour/session.cc:1780 msgid "Session: could not create new audio track." msgstr "Sessione: impossibile creare una nuova traccia audio" -#: libs/ardour/session.cc:1857 +#: libs/ardour/session.cc:1870 msgid "Session: could not create new route." msgstr "Sessione: impossibile creare un nuovo route" -#: libs/ardour/session.cc:2340 +#: libs/ardour/session.cc:2354 msgid "cannot create new name for region \"%1\"" msgstr "impossibile creare un nuovo nome per la regione \"%1\"" -#: libs/ardour/session.cc:2404 +#: libs/ardour/session.cc:2418 msgid "too many regions with names like %1" msgstr "troppe regioni con nomi come %1" -#: libs/ardour/session.cc:2860 +#: libs/ardour/session.cc:2883 msgid "There are already %1 recordings for %2, which I consider too many." msgstr "Ci sono già %1 registrazioni per %2, che io considero troppe" -#: libs/ardour/session.cc:3229 +#: libs/ardour/session.cc:3258 msgid "programming error: unknown type of Insert created!" msgstr "" -#: libs/ardour/session.cc:3235 +#: libs/ardour/session.cc:3264 msgid "programming error: unknown type of Redirect created!" msgstr "" -#: libs/ardour/session.cc:3258 +#: libs/ardour/session.cc:3287 msgid "programming error: unknown type of Insert deleted!" msgstr "" -#: libs/ardour/session.cc:3264 +#: libs/ardour/session.cc:3293 msgid "programming error: unknown type of Redirect deleted!" msgstr "" -#: libs/ardour/session.cc:3605 +#: libs/ardour/session.cc:3636 msgid "too many bounced versions of playlist \"%1\"" msgstr "" -#: libs/ardour/session.cc:3614 +#: libs/ardour/session.cc:3649 msgid "cannot create new audio file \"%1\" for %2" msgstr "impossibile creare un nuovo file audio \"%1\" per %2" -#: libs/ardour/session_butler.cc:81 libs/ardour/session_midi.cc:1183 -#: libs/ardour/source.cc:233 -msgid "Cannot create transport request signal pipe (%1)" -msgstr "" - -#: libs/ardour/session_butler.cc:86 libs/ardour/session_butler.cc:91 +#: libs/ardour/session_butler.cc:85 libs/ardour/session_butler.cc:90 msgid "UI: cannot set O_NONBLOCK on butler request pipe (%1)" msgstr "" -#: libs/ardour/session_butler.cc:96 +#: libs/ardour/session_butler.cc:95 msgid "Session: could not create butler thread" msgstr "" -#: libs/ardour/session_butler.cc:190 +#: libs/ardour/session_butler.cc:189 msgid "poll on butler request pipe failed (%1)" msgstr "" -#: libs/ardour/session_butler.cc:197 +#: libs/ardour/session_butler.cc:196 msgid "Error on butler thread request pipe" msgstr "" -#: libs/ardour/session_butler.cc:239 +#: libs/ardour/session_butler.cc:238 #, fuzzy msgid "Error reading from butler request pipe" msgstr "Errore nel leggere dalla porta MIDI %1" -#: libs/ardour/session_butler.cc:276 +#: libs/ardour/session_butler.cc:275 msgid "Butler read ahead failure on dstream %1" msgstr "" -#: libs/ardour/session_butler.cc:320 +#: libs/ardour/session_butler.cc:319 msgid "Butler write-behind failure on dstream %1" msgstr "" -#: libs/ardour/session_click.cc:157 +#: libs/ardour/session_click.cc:158 msgid "cannot open click soundfile %1 (%2)" msgstr "impossibile accedere al file audio per il click %1 (%2)" -#: libs/ardour/session_click.cc:166 +#: libs/ardour/session_click.cc:167 msgid "cannot read data from click soundfile" msgstr "impossibile leggere dati dal file audio per il click" -#: libs/ardour/session_click.cc:191 +#: libs/ardour/session_click.cc:192 msgid "cannot open click emphasis soundfile %1 (%2)" msgstr "impossibile accedere al file audio di enfasi per il click %1 (%2)" -#: libs/ardour/session_click.cc:199 +#: libs/ardour/session_click.cc:200 msgid "cannot read data from click emphasis soundfile" msgstr "impossibile leggere dati dal file audio di enfasi per il click" @@ -1611,7 +1543,7 @@ msgstr "" msgid "Error reading from transport request pipe" msgstr "" -#: libs/ardour/session_process.cc:105 +#: libs/ardour/session_process.cc:104 msgid "Session: error in no roll for %1" msgstr "" @@ -1629,154 +1561,154 @@ msgstr "" msgid "start" msgstr "separa" -#: libs/ardour/session_state.cc:501 +#: libs/ardour/session_state.cc:502 msgid "Session: cannot create session dir \"%1\" (%2)" msgstr "Sessione: impossibile creare la cartella per la sessione \"%1\" (%2)" -#: libs/ardour/session_state.cc:512 +#: libs/ardour/session_state.cc:513 #, fuzzy msgid "Session: cannot create session peakfile dir \"%1\" (%2)" msgstr "Sessione: impossibile creare la cartella per la sessione \"%1\" (%2)" -#: libs/ardour/session_state.cc:521 +#: libs/ardour/session_state.cc:522 msgid "Session: cannot create session sounds dir \"%1\" (%2)" msgstr "" "Sessione: impossibile creare la cartella sounds per la sessione \"%1\" (%2)" -#: libs/ardour/session_state.cc:530 +#: libs/ardour/session_state.cc:531 #, fuzzy msgid "Session: cannot create session tape dir \"%1\" (%2)" msgstr "Sessione: impossibile creare la cartella per la sessione \"%1\" (%2)" -#: libs/ardour/session_state.cc:539 +#: libs/ardour/session_state.cc:540 #, fuzzy msgid "Session: cannot create session dead sounds dir \"%1\" (%2)" msgstr "" "Sessione: impossibile creare la cartella sounds per la sessione \"%1\" (%2)" -#: libs/ardour/session_state.cc:548 +#: libs/ardour/session_state.cc:549 msgid "Session: cannot create session automation dir \"%1\" (%2)" msgstr "" "Sessione: impossibile creare la cartella automation per la sessione \"%1\" (%" "2)" -#: libs/ardour/session_state.cc:579 +#: libs/ardour/session_state.cc:580 #, fuzzy msgid "Could not open %1 for writing mix template" msgstr "Impossibile accedere a %1 per scrivere il modello di mixaggio" -#: libs/ardour/session_state.cc:585 +#: libs/ardour/session_state.cc:586 #, fuzzy msgid "Could not open mix template %1 for reading" msgstr "Impossibile aprire il modello di mixaggio %1 per leggere" -#: libs/ardour/session_state.cc:592 +#: libs/ardour/session_state.cc:593 msgid "Session already exists. Not overwriting" msgstr "La sessione esiste già. Non sovrascrivo" -#: libs/ardour/session_state.cc:635 +#: libs/ardour/session_state.cc:636 msgid "Session: could not load diskstream via XML state" msgstr "" -#: libs/ardour/session_state.cc:684 +#: libs/ardour/session_state.cc:685 msgid "could not backup old state file, current state not saved." msgstr "" "impossibile fare copia di sicurezza del file di stato, stato attuale non " "salvato" -#: libs/ardour/session_state.cc:697 +#: libs/ardour/session_state.cc:698 #, fuzzy msgid "state could not be saved to %1" msgstr "stato non salvato" -#: libs/ardour/session_state.cc:704 +#: libs/ardour/session_state.cc:705 #, fuzzy msgid "could not remove corrupt state file %1" msgstr "IO: impossibile registrare la porta %1" -#: libs/ardour/session_state.cc:708 +#: libs/ardour/session_state.cc:709 #, fuzzy msgid "could not restore state file from backup %1" msgstr "Esportazione: impossibile scrivere dati sul file di output (%1)" -#: libs/ardour/session_state.cc:777 +#: libs/ardour/session_state.cc:778 msgid "%1: session state information file \"%2\" doesn't exist!" msgstr "" "%1: il file di informazioni sullo stato della sessione \"%2\" non esiste!" -#: libs/ardour/session_state.cc:788 +#: libs/ardour/session_state.cc:789 #, fuzzy msgid "Could not understand ardour file %1" msgstr "IO: impossibile registrare la porta %1" -#: libs/ardour/session_state.cc:1492 +#: libs/ardour/session_state.cc:1493 msgid "programming error: Session: incorrect XML node sent to set_state()" msgstr "" -#: libs/ardour/session_state.cc:1538 +#: libs/ardour/session_state.cc:1539 msgid "Session: XML state has no options section" msgstr "Sessione: il file di stato XML non ha alcuna sezione option" -#: libs/ardour/session_state.cc:1543 +#: libs/ardour/session_state.cc:1544 msgid "Session: XML state has no sources section" msgstr "Sessione: il file di stato XML non ha alcuna sezione sources" -#: libs/ardour/session_state.cc:1550 +#: libs/ardour/session_state.cc:1551 msgid "Session: XML state has no Regions section" msgstr "Sessione: il file di stato XML non ha alcuna sezione Regions" -#: libs/ardour/session_state.cc:1557 +#: libs/ardour/session_state.cc:1558 msgid "Session: XML state has no playlists section" msgstr "Sessione: il file di stato XML non ha alcuna sezione playlist" -#: libs/ardour/session_state.cc:1576 +#: libs/ardour/session_state.cc:1577 msgid "Session: XML state has no diskstreams section" msgstr "Sessione: il file di stato XML non ha alcuna sezione diskstream" -#: libs/ardour/session_state.cc:1583 +#: libs/ardour/session_state.cc:1584 msgid "Session: XML state has no connections section" msgstr "Sessione: il file di stato XML non ha alcuna sezione connections" -#: libs/ardour/session_state.cc:1590 +#: libs/ardour/session_state.cc:1591 msgid "Session: XML state has no locations section" msgstr "Sessione: il file di stato XML non ha alcuna sezione locations" -#: libs/ardour/session_state.cc:1623 +#: libs/ardour/session_state.cc:1624 msgid "Session: XML state has no edit groups section" msgstr "Sessione: il file di stato XML non ha alcuna sezione edit groups" -#: libs/ardour/session_state.cc:1630 +#: libs/ardour/session_state.cc:1631 msgid "Session: XML state has no mix groups section" msgstr "Sessione: il file di stato XML non ha alcuna sezione mix groups" -#: libs/ardour/session_state.cc:1637 +#: libs/ardour/session_state.cc:1638 msgid "Session: XML state has no Tempo Map section" msgstr "Sessione: il file di stato XML non ha alcuna sezione Tempo Map" -#: libs/ardour/session_state.cc:1644 +#: libs/ardour/session_state.cc:1645 msgid "Session: XML state has no routes section" msgstr "Sessione: il file di stato XML non ha alcuna sezione routes" -#: libs/ardour/session_state.cc:1651 +#: libs/ardour/session_state.cc:1652 #, fuzzy msgid "Session: XML state has no click section" msgstr "Sessione: il file di stato XML non ha alcuna sezione click" -#: libs/ardour/session_state.cc:1696 +#: libs/ardour/session_state.cc:1697 msgid "Session: cannot create Route from XML description." msgstr "Sessione: impossibile creare Route dalla descrizione XML" -#: libs/ardour/session_state.cc:1734 +#: libs/ardour/session_state.cc:1735 msgid "Session: cannot create Region from XML description." msgstr "Sessione: impossibile creare regione dalla descrizione XML" -#: libs/ardour/session_state.cc:1762 +#: libs/ardour/session_state.cc:1764 #, fuzzy msgid "Session: XMLNode describing a AudioRegion is incomplete (no source)" msgstr "" "Sessione: il nodo XML descrivente una Regione è incompleto (nessun source)" -#: libs/ardour/session_state.cc:1770 libs/ardour/session_state.cc:1784 +#: libs/ardour/session_state.cc:1772 libs/ardour/session_state.cc:1792 #, fuzzy msgid "" "Session: XMLNode describing a AudioRegion references an unknown source id =%1" @@ -1784,62 +1716,73 @@ msgstr "" "Sessione: il nodo XML descrivente una Regione fa riferimento ad un source " "con id sconosciuto =%1" -#: libs/ardour/session_state.cc:1852 +#: libs/ardour/session_state.cc:1778 libs/ardour/session_state.cc:1798 +#, fuzzy +msgid "" +"Session: XMLNode describing a AudioRegion references a non-audio source id =%" +"1" +msgstr "" +"Sessione: il nodo XML descrivente una Regione fa riferimento ad un source " +"con id sconosciuto =%1" + +#: libs/ardour/session_state.cc:1868 msgid "Session: cannot create Source from XML description." msgstr "Sessione: impossibile creare Source dalla descrizione XML" -#: libs/ardour/session_state.cc:1883 -msgid "Found a sound file that cannot be used by Ardour. See the progammers." +#: libs/ardour/session_state.cc:1889 +#, fuzzy +msgid "" +"Found a sound file that cannot be used by Ardour. Talk to the progammers." msgstr "E' stato trovato un file audio che non può essere usato da Ardour." -#: libs/ardour/session_state.cc:1908 +#: libs/ardour/session_state.cc:1913 msgid "Could not create mix templates directory \"%1\" (%2)" msgstr "Impossibile creare la cartella per i modelli di mixaggio \"%1\" (%2)" -#: libs/ardour/session_state.cc:1922 +#: libs/ardour/session_state.cc:1927 msgid "Template \"%1\" already exists - new version not created" msgstr "Il modello \"%1\" esiste già - non è stata creata una nuova versione" -#: libs/ardour/session_state.cc:1929 +#: libs/ardour/session_state.cc:1934 msgid "mix template not saved" msgstr "modello di mixaggio non salvato" -#: libs/ardour/session_state.cc:1989 +#: libs/ardour/session_state.cc:1994 msgid "cannot create session directory \"%1\"; ignored" msgstr "impossibile creare la cartella per la sessione %1; ignorato" -#: libs/ardour/session_state.cc:2002 +#: libs/ardour/session_state.cc:2007 msgid "cannot create sounds directory \"%1\"; ignored" msgstr "impossibile creare la cartella sounds \"%1\"; ignorato" -#: libs/ardour/session_state.cc:2013 +#: libs/ardour/session_state.cc:2018 #, fuzzy msgid "cannot create dead sounds directory \"%1\"; ignored" msgstr "impossibile creare la cartella sounds \"%1\"; ignorato" -#: libs/ardour/session_state.cc:2024 +#: libs/ardour/session_state.cc:2029 #, fuzzy msgid "cannot create peak file directory \"%1\"; ignored" msgstr "impossibile creare la cartella per la sessione %1; ignorato" -#: libs/ardour/session_state.cc:2163 libs/ardour/session_state.cc:2184 +#: libs/ardour/session_state.cc:2168 libs/ardour/session_state.cc:2189 msgid "Session: cannot create Playlist from XML description." msgstr "Sessione: impossibile creare Playlist dalla descrizione XML" -#: libs/ardour/session_state.cc:2223 +#: libs/ardour/session_state.cc:2228 msgid "Session: cannot create Named Selection from XML description." msgstr "Sessione: impossibile creare Named Selection dalla descizione XML" -#: libs/ardour/session_state.cc:2355 +#: libs/ardour/session_state.cc:2360 msgid "Unknown node \"%1\" found in Connections list from state file" msgstr "Nodo sconosciuto \"%1\" trovato in Connections list dal file di stato" -#: libs/ardour/session_state.cc:3195 +#: libs/ardour/session_state.cc:3197 #, fuzzy msgid "cannot remove dead sound file %1 (%2)" msgstr "impossibile accedere al file audio per il click %1 (%2)" -#: libs/ardour/session_time.cc:736 +#: libs/ardour/session_time.cc:375 msgid "Unknown JACK transport state %1 in sync callback" msgstr "" @@ -1848,43 +1791,43 @@ msgid "tempoize: error creating name for new audio file based on %1" msgstr "" "tempoize: errore nel creare il nome per il nuovo file audio basato su %1" -#: libs/ardour/session_timefx.cc:85 +#: libs/ardour/session_timefx.cc:88 msgid "tempoize: error creating new audio file %1 (%2)" msgstr "tempoize: errore nel creare un nuovo file audio %1 (%2)" -#: libs/ardour/session_timefx.cc:111 +#: libs/ardour/session_timefx.cc:114 msgid "tempoize: error reading data from %1" msgstr "tempoize: errore nel leggere dati da %1" -#: libs/ardour/session_timefx.cc:124 libs/ardour/session_timefx.cc:136 +#: libs/ardour/session_timefx.cc:127 libs/ardour/session_timefx.cc:139 msgid "error writing tempo-adjusted data to %1" msgstr "" -#: libs/ardour/session_timefx.cc:142 +#: libs/ardour/session_timefx.cc:145 msgid "timefx code failure. please notify ardour-developers." msgstr "" -#: libs/ardour/session_transport.cc:116 +#: libs/ardour/session_transport.cc:117 msgid "Cannot loop - no loop range defined" msgstr "" -#: libs/ardour/session_transport.cc:478 +#: libs/ardour/session_transport.cc:479 msgid "" "Seamless looping cannot be supported while Ardour is using JACK transport.\n" "Recommend changing the configured options" msgstr "" -#: libs/ardour/session_transport.cc:754 +#: libs/ardour/session_transport.cc:755 msgid "" "Global varispeed cannot be supported while Ardour is connected to JACK " "transport control" msgstr "" -#: libs/ardour/session_transport.cc:954 +#: libs/ardour/session_transport.cc:955 msgid "please stop the transport before adjusting slave settings" msgstr "" -#: libs/ardour/session_transport.cc:990 +#: libs/ardour/session_transport.cc:991 msgid "No MTC port defined: MTC slaving is impossible." msgstr "" @@ -1972,11 +1915,22 @@ msgstr "" msgid "Big-endian (Mac)" msgstr "" -#: libs/ardour/sndfilesource.cc:75 -msgid "SndFileSource: cannot open file \"%1\" (%2)" +#: libs/ardour/sndfilesource.cc:146 +msgid "FileSource: cannot get host information for BWF header (%1)" +msgstr "FileSource: impossibile ottenere info sull'host dall'header BWF (%1)" + +#: libs/ardour/sndfilesource.cc:168 +msgid "" +"cannot set broadcast info for audio file %1 (%2); dropping broadcast info " +"for this file" +msgstr "" + +#: libs/ardour/sndfilesource.cc:224 +#, fuzzy +msgid "SndFileSource: cannot open file \"%1\" for %2 (%3)" msgstr "SndFileSource: impossibile accedere al file \"%1\" (%2)" -#: libs/ardour/sndfilesource.cc:80 +#: libs/ardour/sndfilesource.cc:230 msgid "" "SndFileSource: file only contains %1 channels; %2 is invalid as a channel " "number" @@ -1984,205 +1938,169 @@ msgstr "" "SndFileSource: il file contiene solo %1 canali; %2 non è valido come numero " "di canale" -#: libs/ardour/sndfilesource.cc:122 +#: libs/ardour/sndfilesource.cc:307 msgid "SndFileSource: could not seek to frame %1 within %2 (%3)" msgstr "" -#: libs/ardour/source.cc:161 -msgid "poll on peak request pipe failed (%1)" -msgstr "" - -#: libs/ardour/source.cc:168 -msgid "Error on peak thread request pipe" -msgstr "" - -#: libs/ardour/source.cc:201 +#: libs/ardour/sndfilesource.cc:358 #, fuzzy -msgid "Error reading from peak request pipe" -msgstr "Errore nel leggere dalla porta MIDI %1" +msgid "programming error: %1 %2" +msgstr "errore di programmazione: %1" -#: libs/ardour/source.cc:238 libs/ardour/source.cc:243 -msgid "UI: cannot set O_NONBLOCK on peak request pipe (%1)" +#: libs/ardour/sndfilesource.cc:458 +msgid "" +"cannot set broadcast info for audio file %1; Dropping broadcast info for " +"this file" msgstr "" -#: libs/ardour/source.cc:248 -msgid "Source: could not create peak thread" +#: libs/ardour/sndfilesource.cc:500 +msgid "%1: cannot seek to %2" msgstr "" -#: libs/ardour/source.cc:326 -#, fuzzy -msgid "cannot rename peakfile for %1 from %2 to %3 (%4)" -msgstr "impossibile eliminare il peakfile %1 per %2 (%3)" - -#: libs/ardour/source.cc:357 -msgid "Source: cannot stat peakfile \"%1\"" -msgstr "" - -#: libs/ardour/source.cc:444 -msgid "cannot read sample data for unscaled peak computation" -msgstr "" - -#: libs/ardour/source.cc:465 libs/ardour/source.cc:536 -#: libs/ardour/source.cc:780 libs/ardour/source.cc:881 -msgid "Source: cannot open peakpath \"%1\" (%2)" -msgstr "" - -#: libs/ardour/source.cc:637 -msgid "Source[%1]: peak read - cannot read %2 samples at offset %3" -msgstr "" - -#: libs/ardour/source.cc:789 -msgid "%1: could not write read raw data for peak computation (%2)" -msgstr "" - -#: libs/ardour/source.cc:814 -msgid "%1: could not write peak file data (%2)" -msgstr "" - -#: libs/ardour/state_manager.cc:46 +#: libs/ardour/state_manager.cc:47 #, fuzzy msgid "cleared history" msgstr "pulito" -#: libs/ardour/state_manager.cc:59 +#: libs/ardour/state_manager.cc:60 msgid "" "programming error: illegal state ID (%1) passed to StateManager::set_state() " "(range = 0-%2)" msgstr "" -#: libs/ardour/stateful.cc:100 +#: libs/ardour/stateful.cc:102 #, fuzzy msgid "Error: could not write %1" msgstr "Esportazione: impossibile scrivere dati sul file di output (%1)" -#: libs/ardour/stateful.cc:114 +#: libs/ardour/stateful.cc:116 msgid "Could not understand XML file %1" msgstr "" -#: libs/ardour/tempo.cc:66 +#: libs/ardour/tempo.cc:67 msgid "TempoSection XML node has no \"start\" property" msgstr "" -#: libs/ardour/tempo.cc:74 +#: libs/ardour/tempo.cc:75 msgid "TempoSection XML node has an illegal \"start\" value" msgstr "" -#: libs/ardour/tempo.cc:81 +#: libs/ardour/tempo.cc:82 msgid "TempoSection XML node has no \"beats-per-minute\" property" msgstr "" -#: libs/ardour/tempo.cc:86 +#: libs/ardour/tempo.cc:87 msgid "TempoSection XML node has an illegal \"beats_per_minute\" value" msgstr "" -#: libs/ardour/tempo.cc:91 +#: libs/ardour/tempo.cc:92 msgid "TempoSection XML node has no \"movable\" property" msgstr "" -#: libs/ardour/tempo.cc:130 +#: libs/ardour/tempo.cc:131 msgid "MeterSection XML node has no \"start\" property" msgstr "" -#: libs/ardour/tempo.cc:138 +#: libs/ardour/tempo.cc:139 msgid "MeterSection XML node has an illegal \"start\" value" msgstr "" -#: libs/ardour/tempo.cc:145 +#: libs/ardour/tempo.cc:146 msgid "MeterSection XML node has no \"beats-per-bar\" property" msgstr "" -#: libs/ardour/tempo.cc:150 +#: libs/ardour/tempo.cc:151 msgid "MeterSection XML node has an illegal \"beats-per-bar\" value" msgstr "" -#: libs/ardour/tempo.cc:155 +#: libs/ardour/tempo.cc:156 msgid "MeterSection XML node has no \"note-type\" property" msgstr "" -#: libs/ardour/tempo.cc:160 +#: libs/ardour/tempo.cc:161 msgid "MeterSection XML node has an illegal \"note-type\" value" msgstr "" -#: libs/ardour/tempo.cc:165 +#: libs/ardour/tempo.cc:166 msgid "MeterSection XML node has no \"movable\" property" msgstr "" -#: libs/ardour/tempo.cc:258 +#: libs/ardour/tempo.cc:259 msgid "move metric" msgstr "" -#: libs/ardour/tempo.cc:329 +#: libs/ardour/tempo.cc:330 msgid "metric removed" msgstr "" -#: libs/ardour/tempo.cc:372 +#: libs/ardour/tempo.cc:373 #, fuzzy msgid "add tempo" msgstr "aggiungi regione" -#: libs/ardour/tempo.cc:401 +#: libs/ardour/tempo.cc:402 #, fuzzy msgid "replace tempo" msgstr "sostituisci la regione" -#: libs/ardour/tempo.cc:434 +#: libs/ardour/tempo.cc:435 msgid "add meter" msgstr "" -#: libs/ardour/tempo.cc:462 +#: libs/ardour/tempo.cc:463 #, fuzzy msgid "replaced meter" msgstr "sostituisci la regione" -#: libs/ardour/tempo.cc:482 libs/ardour/tempo.cc:498 +#: libs/ardour/tempo.cc:483 libs/ardour/tempo.cc:499 msgid "programming error: no tempo section in tempo map!" msgstr "" -#: libs/ardour/tempo.cc:537 +#: libs/ardour/tempo.cc:538 msgid "programming error: unhandled MetricSection type" msgstr "" -#: libs/ardour/tempo.cc:1225 libs/ardour/tempo.cc:1237 +#: libs/ardour/tempo.cc:1226 libs/ardour/tempo.cc:1238 msgid "Tempo map: could not set new state, restoring old one." msgstr "" -#: libs/ardour/tempo.cc:1261 +#: libs/ardour/tempo.cc:1262 msgid "load XML data" msgstr "" -#: libs/ardour/utils.cc:242 +#: libs/ardour/utils.cc:246 #, fuzzy msgid "illegal or badly-formed string used for path (%1)" msgstr "il percorso indicato per il RAID è non valido o malformato" -#: libs/ardour/utils.cc:247 +#: libs/ardour/utils.cc:251 #, fuzzy msgid "path (%1) is ambiguous" msgstr "il percorso indicato per la ricerca RAID è ambiguo" -#: libs/ardour/vst_plugin.cc:186 +#: libs/ardour/vst_plugin.cc:187 #, fuzzy msgid "cannot create VST chunk directory: %1" msgstr "impossibile creare la cartella sounds \"%1\"; ignorato" -#: libs/ardour/vst_plugin.cc:194 +#: libs/ardour/vst_plugin.cc:195 #, fuzzy msgid "cannot check VST chunk directory: %1" msgstr "impossibile determinare la cartella di lavoro corrente (%1)" -#: libs/ardour/vst_plugin.cc:201 +#: libs/ardour/vst_plugin.cc:202 msgid "%1 exists but is not a directory" msgstr "" -#: libs/ardour/vst_plugin.cc:239 +#: libs/ardour/vst_plugin.cc:240 msgid "Bad node sent to VSTPlugin::set_state" msgstr "" -#: libs/ardour/vst_plugin.cc:342 libs/ardour/vst_plugin.cc:353 +#: libs/ardour/vst_plugin.cc:343 libs/ardour/vst_plugin.cc:354 msgid "no support for presets using chunks at this time" msgstr "" -#: libs/ardour/coreaudio_source.cc:93 +#: libs/ardour/coreaudio_source.cc:99 #, fuzzy msgid "" "CoreAudioSource: file only contains %1 channels; %2 is invalid as a channel " @@ -2191,18 +2109,117 @@ msgstr "" "SndFileSource: il file contiene solo %1 canali; %2 non è valido come numero " "di canale" -#: libs/ardour/coreaudio_source.cc:157 +#: libs/ardour/coreaudio_source.cc:164 msgid "CoreAudioSource: could not seek to frame %1 within %2 (%3)" msgstr "" +#~ msgid "FileSource: \"%1\" not found when searching %2 using %3" +#~ msgstr "FileSource: \"%1\" non trovato nel cercare %2 utilizzando %3" + +#~ msgid "FileSource: could not open \"%1\": (%2)" +#~ msgstr "FileSource: impossibile aprire \"%1\": (%2)" + +#~ msgid "FileSource: cannot write header in %1" +#~ msgstr "FileSource: impossibile scrivere header in %1" + +#~ msgid "FileSource: cannot locate chunks in %1" +#~ msgstr "FileSource: impossibile trovare spezzoni in %1" + +#~ msgid "FileSource: cannot read header in %1" +#~ msgstr "FileSource: impossibile leggere header in %1" + +#~ msgid "FileSource: cannot check header in %1" +#~ msgstr "FileSource: impossibile controllare header in %1" + +#, fuzzy +#~ msgid "FileSource: cannot initialize peakfile for %1 as %2" +#~ msgstr "FileSource: impossibile avviare il peakfile per %1" + +#~ msgid "FileSource: cannot seek to end of file" +#~ msgstr "FileSource: impossibile cercare fino alla fine del file" + +#~ msgid "FileSource: cannot read RIFF/WAVE chunk from file" +#~ msgstr "FileSource: impossibile accedere allo spezzone RIFF/WAVE dal file" + +#~ msgid "FileSource %1: not a RIFF/WAVE file" +#~ msgstr "FileSource %1: il file non un file RIFF/WAVE" + +#~ msgid "FileSource: can't read a chunk" +#~ msgstr "FileSource: impossibile accedere ad uno spezzone" + +#~ msgid "FileSource: cannot get user information for BWF header (%1)" +#~ msgstr "FileSource: impossibile otterene info utente dall'header BWF (%1)" + +#~ msgid "FileSource[%1]: cannot update data size: %2" +#~ msgstr "FileSource[%1]: impossibile aggiornare la dimensione dei dati: %2" + +#~ msgid "FileSource: can't find RIFF chunk info" +#~ msgstr "FileSource: impossibile trovare info sullo spezzone RIFF" + +#, fuzzy +#~ msgid "FileSource: can't find RIFX chunk info" +#~ msgstr "FileSource: impossibile trovare info sullo spezzone RIFF" + +#~ msgid "FileSource: can't read RIFF chunk" +#~ msgstr "FileSource: impossibile accedere allo spezzone RIFF" + +#~ msgid "FileSource: can't find format chunk info" +#~ msgstr "FileSource: impossibile trovare info sul formato dello spezzone" + +#~ msgid "FileSource: can't read format chunk" +#~ msgstr "FileSource: impossibile leggere il formato dello spezzone" + +#~ msgid "FileSource: can't find data chunk info" +#~ msgstr "FileSource: impossibile trovare info sui dati dello spezzone" + +#~ msgid "FileSource: can't read data chunk" +#~ msgstr "FileSource: impossibile leggere dati dello spezzone" + +#~ msgid "" +#~ "FileSource: cannot read Broadcast Wave data from existing audio file \"%1" +#~ "\" (%2)" +#~ msgstr "" +#~ "FileSource: impossibile leggere dati Broadcast Wave dal file audio " +#~ "esistente \"%1\" (%2) " + +#~ msgid "" +#~ "FileSource: cannot read Broadcast Wave coding history from audio file \"%1" +#~ "\" (%2)" +#~ msgstr "" +#~ "FileSource: impossibile leggere lo storico del Broadcast Wave dal file " +#~ "audio \"%1\" (%2)" + +#, fuzzy +#~ msgid "" +#~ "FileSource \"%1\" does not use valid sample format.\n" +#~ "This is probably a programming error." +#~ msgstr "" +#~ "FileSource \"%1\" non usa il formato floating point.\n" +#~ "Questo probabilmente un errore di programmazione." + +#~ msgid "FileSource \"%1\" has no \"data\" chunk" +#~ msgstr "FileSource \"%1\" non ha uno spezzone di \"dati\"" + +#~ msgid "" +#~ "%1: data length in header (%2) differs from implicit size in file (%3)" +#~ msgstr "" +#~ "%1: la lunghezza dei dati nell'header (%2) diversa dalla dimensione " +#~ "implicita nel file (%3)" + +#~ msgid "\"%1\" has a sample rate of %2 instead of %3 as used by this session" +#~ msgstr "" +#~ "\"%1\" ha una sample rate di %2 anzicch di %3 come il resto della sessione" + +#~ msgid "FileSource: cannot write WAVE chunk: %1" +#~ msgstr "FileSource: impossibile scrivere lo spezzone WAVE: %1" + +#~ msgid "FileSource: cannot write format chunk: %1" +#~ msgstr "FileSource: impossibile scrivere il formato dello spezzone: %1" + #, fuzzy #~ msgid "cannot create feedback request pipe (%1)" #~ msgstr "Errore nel leggere dalla porta MIDI %1" -#, fuzzy -#~ msgid "Session: could not create feedback thread" -#~ msgstr "Sessione: impossibile creare un nuovo route" - #, fuzzy #~ msgid "Error on feedback thread request pipe" #~ msgstr "Errore nel leggere dalla porta MIDI %1" @@ -2217,7 +2234,3 @@ msgstr "" #, fuzzy #~ msgid "Could not find a template called %1 in %2" #~ msgstr "Impossibile aprire il modello di mixaggio %1 per leggere" - -#, fuzzy -#~ msgid "Source: cannot stat peakfile \"%1\" or \"%2\"" -#~ msgstr "FileSource: impossibile avviare il peakfile per %1" diff --git a/libs/ardour/po/ru_RU.po b/libs/ardour/po/ru_RU.po index e21d70b371..922d304e2d 100644 --- a/libs/ardour/po/ru_RU.po +++ b/libs/ardour/po/ru_RU.po @@ -6,7 +6,7 @@ msgid "" msgstr "" "Project-Id-Version: libardour 0.716.1\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-04-25 17:46-0400\n" +"POT-Creation-Date: 2006-06-21 15:09-0400\n" "PO-Revision-Date: 2004-03-31 00:55+0300\n" "Last-Translator: Igor Blinov pitstop@nm.ru\n" "Language-Team: Russian\n" @@ -14,286 +14,453 @@ msgstr "" "Content-Type: text/plain; charset=koi8-r\n" "Content-Transfer-Encoding: 8bit\n" -#: libs/ardour/audio_library.cc:91 -msgid "channels" +#: libs/ardour/audio_diskstream.cc:337 +msgid "AudioDiskstream: Session doesn't know about a Playlist called \"%1\"" +msgstr "" + +#: libs/ardour/audio_diskstream.cc:342 +msgid "AudioDiskstream: Playlist \"%1\" isn't an audio playlist" +msgstr "" + +#: libs/ardour/audio_diskstream.cc:433 +msgid "AudioDiskstream %1: there is no existing playlist to make a copy of!" +msgstr "" + +#: libs/ardour/audio_diskstream.cc:1114 libs/ardour/audio_diskstream.cc:1125 +msgid "" +"AudioDiskstream %1: when refilling, cannot read %2 from playlist at frame %3" +msgstr "" + +#: libs/ardour/audio_diskstream.cc:1254 +msgid "AudioDiskstream %1: cannot read %2 from playlist at frame %3" +msgstr "" + +#: libs/ardour/audio_diskstream.cc:1621 libs/ardour/audio_diskstream.cc:1638 +msgid "AudioDiskstream %1: cannot write to disk" +msgstr "" + +#: libs/ardour/audio_diskstream.cc:1698 +msgid "AudioDiskstream \"%1\": cannot flush captured data to disk!" +msgstr "" + +#: libs/ardour/audio_diskstream.cc:1795 +msgid "%1: could not create region for complete audio file" +msgstr "" + +#: libs/ardour/audio_diskstream.cc:1818 +msgid "AudioDiskstream: could not create region for captured audio!" +msgstr "" + +#: libs/ardour/audio_diskstream.cc:1873 +#, fuzzy +msgid "programmer error: %1" +msgstr "ÏÛÉÂËÁ ÐÒÏÇÒÁÍÍÙ: " + +#: libs/ardour/audio_diskstream.cc:2145 +msgid "AudioDiskstream: channel %1 out of range" +msgstr "" + +#: libs/ardour/audio_diskstream.cc:2170 +msgid "%1:%2 new capture file not initialized correctly" +msgstr "" + +#: libs/ardour/audio_diskstream.cc:2403 +msgid "Location \"%1\" not valid for track loop (start >= end)" +msgstr "" + +#: libs/ardour/audio_diskstream.cc:2484 +msgid "%1: cannot restore pending capture source file %2" +msgstr "" + +#: libs/ardour/audio_diskstream.cc:2506 +msgid "%1: incorrect number of pending sources listed - ignoring them all" +msgstr "" + +#: libs/ardour/audio_diskstream.cc:2522 +msgid "%1: cannot create whole-file region from pending capture sources" +msgstr "" + +#: libs/ardour/audio_diskstream.cc:2534 +msgid "%1: cannot create region from pending capture sources" msgstr "" #: libs/ardour/audio_library.cc:92 +msgid "channels" +msgstr "" + +#: libs/ardour/audio_library.cc:93 #, fuzzy msgid "samplerate" msgstr "ÒÁÚÄÅÌÉÔØ" -#: libs/ardour/audio_library.cc:93 +#: libs/ardour/audio_library.cc:94 msgid "resolution" msgstr "" -#: libs/ardour/audio_library.cc:94 +#: libs/ardour/audio_library.cc:95 msgid "format" msgstr "" -#: libs/ardour/audio_library.cc:101 +#: libs/ardour/audio_library.cc:102 msgid "Could not open %1. Audio Library not saved" msgstr "" -#: libs/ardour/audio_playlist.cc:52 libs/ardour/audio_playlist.cc:62 -#: libs/ardour/audio_playlist.cc:73 libs/ardour/audio_playlist.cc:120 +#: libs/ardour/audio_playlist.cc:53 libs/ardour/audio_playlist.cc:63 +#: libs/ardour/audio_playlist.cc:74 libs/ardour/audio_playlist.cc:121 #: libs/ardour/insert.cc:76 libs/ardour/insert.cc:95 libs/ardour/insert.cc:120 -#: libs/ardour/insert.cc:838 libs/ardour/insert.cc:846 libs/ardour/send.cc:38 -#: libs/ardour/send.cc:52 libs/ardour/send.cc:61 -#: libs/ardour/session_state.cc:1620 libs/ardour/session_state.cc:1666 +#: libs/ardour/insert.cc:838 libs/ardour/insert.cc:846 libs/ardour/send.cc:39 +#: libs/ardour/send.cc:53 libs/ardour/send.cc:62 +#: libs/ardour/session_state.cc:1621 libs/ardour/session_state.cc:1667 msgid "initial state" msgstr "" -#: libs/ardour/audio_playlist.cc:274 libs/ardour/audio_playlist.cc:768 +#: libs/ardour/audio_playlist.cc:275 libs/ardour/audio_playlist.cc:769 msgid "" "programming error: non-audio Region passed to remove_overlap in audio " "playlist" msgstr "" -#: libs/ardour/audio_playlist.cc:401 +#: libs/ardour/audio_playlist.cc:402 msgid "" "programming error: non-audio Region tested for overlap in audio playlist" msgstr "" -#: libs/ardour/audio_playlist.cc:877 +#: libs/ardour/audio_playlist.cc:878 msgid "xfade change" msgstr "" -#: libs/ardour/audio_playlist.cc:926 +#: libs/ardour/audio_playlist.cc:933 msgid "region modified" msgstr "" -#: libs/ardour/audio_track.cc:121 libs/ardour/io.cc:1703 -#: libs/ardour/io.cc:1813 +#: libs/ardour/audio_track.cc:133 libs/ardour/io.cc:1716 +#: libs/ardour/io.cc:1826 msgid "Unknown connection \"%1\" listed for input of %2" msgstr "" -#: libs/ardour/audio_track.cc:123 libs/ardour/io.cc:1705 -#: libs/ardour/io.cc:1815 +#: libs/ardour/audio_track.cc:135 libs/ardour/io.cc:1718 +#: libs/ardour/io.cc:1828 msgid "in 1" msgstr "" -#: libs/ardour/audio_track.cc:124 libs/ardour/io.cc:1706 -#: libs/ardour/io.cc:1816 +#: libs/ardour/audio_track.cc:136 libs/ardour/io.cc:1719 +#: libs/ardour/io.cc:1829 msgid "No input connections available as a replacement" msgstr "" -#: libs/ardour/audio_track.cc:128 libs/ardour/io.cc:1710 -#: libs/ardour/io.cc:1820 +#: libs/ardour/audio_track.cc:140 libs/ardour/io.cc:1723 +#: libs/ardour/io.cc:1833 msgid "Connection %1 was not available - \"in 1\" used instead" msgstr "" -#: libs/ardour/audio_track.cc:137 libs/ardour/io.cc:1829 +#: libs/ardour/audio_track.cc:149 libs/ardour/io.cc:1842 msgid "improper input channel list in XML node (%1)" msgstr "" -#: libs/ardour/audio_track.cc:182 libs/ardour/audio_track.cc:195 +#: libs/ardour/audio_track.cc:194 libs/ardour/audio_track.cc:207 msgid "AudioTrack: diskstream \"%1\" not known by session" msgstr "" -#: libs/ardour/audio_track.cc:293 +#: libs/ardour/audio_track.cc:305 msgid "" "MIDI rec_enable control specification for %1 is incomplete, so it has been " "ignored" msgstr "" -#: libs/ardour/audio_track.cc:305 +#: libs/ardour/audio_track.cc:317 msgid "programming error: AudioTrack given state without diskstream!" msgstr "" -#: libs/ardour/audioengine.cc:147 +#: libs/ardour/audioengine.cc:150 msgid "cannot activate JACK client" msgstr "ÎÅ ÕÄÁÌÏÓØ ÁËÔÉ×ÉÒÏ×ÁÔØ ËÌÉÅÎÔÁ JACK ÓÅÒ×ÅÒÁ" -#: libs/ardour/audioengine.cc:432 +#: libs/ardour/audioengine.cc:401 msgid "register audio input port called before engine was started" msgstr "" -#: libs/ardour/audioengine.cc:463 +#: libs/ardour/audioengine.cc:432 msgid "register audio output port called before engine was started" msgstr "" -#: libs/ardour/audioengine.cc:524 +#: libs/ardour/audioengine.cc:493 msgid "connect called before engine was started" msgstr "" -#: libs/ardour/audioengine.cc:540 +#: libs/ardour/audioengine.cc:509 msgid "AudioEngine: cannot connect %1 (%2) to %3 (%4)" msgstr "" -#: libs/ardour/audioengine.cc:553 libs/ardour/audioengine.cc:582 +#: libs/ardour/audioengine.cc:522 libs/ardour/audioengine.cc:551 msgid "disconnect called before engine was started" msgstr "" -#: libs/ardour/audioengine.cc:640 +#: libs/ardour/audioengine.cc:609 msgid "get_port_by_name() called before engine was started" msgstr "" -#: libs/ardour/audioengine.cc:673 +#: libs/ardour/audioengine.cc:642 msgid "get_ports called before engine was started" msgstr "" -#: libs/ardour/audioengine.cc:748 +#: libs/ardour/audioengine.cc:717 msgid "get_nth_physical called before engine was started" msgstr "" -#: libs/ardour/audioengine.cc:776 +#: libs/ardour/audioengine.cc:745 msgid "get_port_total_latency() called with no JACK client connection" msgstr "" -#: libs/ardour/audioengine.cc:782 +#: libs/ardour/audioengine.cc:751 msgid "get_port_total_latency() called before engine was started" msgstr "" -#: libs/ardour/audioengine.cc:906 +#: libs/ardour/audioengine.cc:875 msgid "Unable to connect to JACK server" msgstr "" -#: libs/ardour/audioengine.cc:909 +#: libs/ardour/audioengine.cc:878 msgid "Could not connect to JACK server as \"%1\"" msgstr "" -#: libs/ardour/audioengine.cc:914 +#: libs/ardour/audioengine.cc:883 msgid "JACK server started" msgstr "" -#: libs/ardour/audioengine.cc:948 +#: libs/ardour/audioengine.cc:917 msgid "cannot shutdown connection to JACK" msgstr "" -#: libs/ardour/audioengine.cc:973 +#: libs/ardour/audioengine.cc:942 msgid "failed to connect to JACK" msgstr "" -#: libs/ardour/audioengine.cc:989 +#: libs/ardour/audioengine.cc:958 msgid "could not reregister %1" msgstr "" -#: libs/ardour/audioengine.cc:1046 +#: libs/ardour/audioengine.cc:1015 msgid "could not reconnect %1 and %2 (err = %3)" msgstr "" -#: libs/ardour/audiofilter.cc:44 +#: libs/ardour/audiofilesource.cc:445 libs/ardour/session_state.cc:3095 +msgid "" +"there are already 1000 files with names like %1; versioning discontinued" +msgstr "" + +#: libs/ardour/audiofilesource.cc:459 libs/ardour/session_state.cc:3109 +msgid "cannot rename audio file source from %1 to %2 (%3)" +msgstr "" + +#: libs/ardour/audiofilesource.cc:466 libs/ardour/session_state.cc:3124 +msgid "cannot remove peakfile %1 for %2 (%3)" +msgstr "" + +#: libs/ardour/audiofilesource.cc:510 +msgid "FileSource: search path not set" +msgstr "" + +#: libs/ardour/audiofilesource.cc:534 +msgid "" +"FileSource: \"%1\" is ambigous when searching %2\n" +"\t" +msgstr "" + +#: libs/ardour/audiofilesource.cc:540 +msgid "Filesource: cannot find required file (%1): while searching %2" +msgstr "" + +#: libs/ardour/audiofilesource.cc:563 +msgid "Filesource: cannot find required file (%1): %2" +msgstr "" + +#: libs/ardour/audiofilesource.cc:568 +msgid "Filesource: cannot check for existing file (%1): %2" +msgstr "" + +#: libs/ardour/audiofilesource.cc:640 libs/ardour/insert.cc:525 +#: libs/ardour/sndfilesource.cc:112 +#, fuzzy +msgid "programming error: %1" +msgstr "ÏÛÉÂËÁ ÐÒÏÇÒÁÍÍÙ: " + +#: libs/ardour/audiofilesource.cc:645 +msgid "cannot rename audio file for %1 to %2" +msgstr "" + +#: libs/ardour/audiofilter.cc:45 msgid "audiofilter: error creating name for new audio file based on %1" msgstr "" -#: libs/ardour/audiofilter.cc:54 +#: libs/ardour/audiofilter.cc:58 msgid "audiofilter: error creating new audio file %1 (%2)" msgstr "" -#: libs/ardour/audioregion.cc:855 libs/ardour/audioregion.cc:917 +#: libs/ardour/audioregion.cc:857 libs/ardour/audioregion.cc:919 msgid "fade in change" msgstr "" -#: libs/ardour/audioregion.cc:1341 +#: libs/ardour/audioregion.cc:1349 #, c-format msgid "normalized to %.2fdB" msgstr "" -#: libs/ardour/audioregion.cc:1359 +#: libs/ardour/audioregion.cc:1367 msgid "envelope change" msgstr "" -#: libs/ardour/automation_event.cc:64 libs/ardour/location.cc:344 -#: libs/ardour/tempo.cc:225 +#: libs/ardour/audiosource.cc:143 +msgid "poll on peak request pipe failed (%1)" +msgstr "" + +#: libs/ardour/audiosource.cc:150 +msgid "Error on peak thread request pipe" +msgstr "" + +#: libs/ardour/audiosource.cc:183 +msgid "Error reading from peak request pipe" +msgstr "" + +#: libs/ardour/audiosource.cc:215 libs/ardour/session_butler.cc:80 +#: libs/ardour/session_midi.cc:1183 +msgid "Cannot create transport request signal pipe (%1)" +msgstr "" + +#: libs/ardour/audiosource.cc:220 libs/ardour/audiosource.cc:225 +msgid "UI: cannot set O_NONBLOCK on peak request pipe (%1)" +msgstr "" + +#: libs/ardour/audiosource.cc:230 +msgid "AudioSource: could not create peak thread" +msgstr "" + +#: libs/ardour/audiosource.cc:308 +msgid "cannot rename peakfile for %1 from %2 to %3 (%4)" +msgstr "" + +#: libs/ardour/audiosource.cc:350 +#, fuzzy +msgid "AudioSource: cannot stat peakfile \"%1\"" +msgstr "Ardour: ÎÅ ÕÄÁÌÏÓØ ÐÒÏÞÉÔÁÔØ ÆÁÊÌ ËÏÎÆÉÇÕÒÁÃÉÉ ÐÏÌØÚÏ×ÁÔÅÌÑ \"%1\"" + +#: libs/ardour/audiosource.cc:451 +msgid "cannot read sample data for unscaled peak computation" +msgstr "" + +#: libs/ardour/audiosource.cc:472 libs/ardour/audiosource.cc:543 +#: libs/ardour/audiosource.cc:787 libs/ardour/audiosource.cc:878 +#, fuzzy +msgid "AudioSource: cannot open peakpath \"%1\" (%2)" +msgstr "LADSPA: ÎÅ ÕÄÁÌÏÓØ ÚÁÇÒÕÚÉÔØ ÍÏÄÕÌØ \"%1\" (%2)" + +#: libs/ardour/audiosource.cc:644 +msgid "AudioSource[%1]: peak read - cannot read %2 samples at offset %3" +msgstr "" + +#: libs/ardour/audiosource.cc:798 +msgid "%1: could not write read raw data for peak computation (%2)" +msgstr "" + +#: libs/ardour/audiosource.cc:823 +msgid "%1: could not write peak file data (%2)" +msgstr "" + +#: libs/ardour/automation_event.cc:65 libs/ardour/location.cc:345 +#: libs/ardour/tempo.cc:226 msgid "initial" msgstr "" -#: libs/ardour/automation_event.cc:231 +#: libs/ardour/automation_event.cc:232 msgid "cleared" msgstr "" -#: libs/ardour/automation_event.cc:403 +#: libs/ardour/automation_event.cc:404 msgid "added event" msgstr "" -#: libs/ardour/automation_event.cc:420 +#: libs/ardour/automation_event.cc:421 #, fuzzy msgid "removed event" msgstr "ÕÄÁÌÉÔØ ÏÂÌÁÓÔØ" -#: libs/ardour/automation_event.cc:435 +#: libs/ardour/automation_event.cc:436 msgid "removed multiple events" msgstr "" -#: libs/ardour/automation_event.cc:461 +#: libs/ardour/automation_event.cc:467 libs/ardour/automation_event.cc:498 #, fuzzy msgid "removed range" msgstr "ÕÄÁÌÉÔØ ÏÂÌÁÓÔØ" -#: libs/ardour/automation_event.cc:491 +#: libs/ardour/automation_event.cc:528 msgid "event range adjusted" msgstr "" -#: libs/ardour/automation_event.cc:513 +#: libs/ardour/automation_event.cc:550 msgid "event adjusted" msgstr "" -#: libs/ardour/automation_event.cc:628 libs/ardour/automation_event.cc:733 -#: libs/ardour/panner.cc:1040 +#: libs/ardour/automation_event.cc:665 libs/ardour/automation_event.cc:770 +#: libs/ardour/panner.cc:1041 #, fuzzy msgid "programming error:" msgstr "ÏÛÉÂËÁ ÐÒÏÇÒÁÍÍÙ: " -#: libs/ardour/automation_event.cc:1042 +#: libs/ardour/automation_event.cc:1079 msgid "cut/copy/clear" msgstr "" -#: libs/ardour/automation_event.cc:1075 +#: libs/ardour/automation_event.cc:1112 msgid "copy" msgstr "" -#: libs/ardour/automation_event.cc:1143 libs/ardour/playlist.cc:939 +#: libs/ardour/automation_event.cc:1180 libs/ardour/playlist.cc:939 msgid "paste" msgstr "×ÓÔÁ×ÉÔØ" -#: libs/ardour/automation_event.cc:1198 +#: libs/ardour/automation_event.cc:1235 msgid "" "automation list: no x-coordinate stored for control point (point ignored)" msgstr "" -#: libs/ardour/automation_event.cc:1204 +#: libs/ardour/automation_event.cc:1241 msgid "" "automation list: no y-coordinate stored for control point (point ignored)" msgstr "" -#: libs/ardour/basic_ui.cc:68 -msgid "unnamed" -msgstr "" - -#: libs/ardour/configuration.cc:79 +#: libs/ardour/configuration.cc:80 #, fuzzy msgid "loading system configuration file %1" msgstr "Ardour: ÎÅ ÕÄÁÌÏÓØ ÐÒÏÞÉÔÁÔØ ÆÁÊÌ ËÏÎÆÉÇÕÒÁÃÉÉ ÐÒÏÇÒÁÍÍÙ \"%1\"" -#: libs/ardour/configuration.cc:82 +#: libs/ardour/configuration.cc:83 msgid "Ardour: cannot read system configuration file \"%1\"" msgstr "Ardour: ÎÅ ÕÄÁÌÏÓØ ÐÒÏÞÉÔÁÔØ ÆÁÊÌ ËÏÎÆÉÇÕÒÁÃÉÉ ÐÒÏÇÒÁÍÍÙ \"%1\"" -#: libs/ardour/configuration.cc:87 +#: libs/ardour/configuration.cc:88 msgid "Ardour: system configuration file \"%1\" not loaded successfully." msgstr "Ardour: ÎÅ ÕÄÁÌÏÓØ ÚÁÇÒÕÚÉÔØ ÆÁÊÌ ËÏÎÆÉÇÕÒÁÃÉÉ ÐÒÏÇÒÁÍÍÙ \"%1\"." -#: libs/ardour/configuration.cc:104 +#: libs/ardour/configuration.cc:105 #, fuzzy msgid "loading user configuration file %1" msgstr "Ardour: ÎÅ ÕÄÁÌÏÓØ ÐÒÏÞÉÔÁÔØ ÆÁÊÌ ËÏÎÆÉÇÕÒÁÃÉÉ ÐÏÌØÚÏ×ÁÔÅÌÑ \"%1\"" -#: libs/ardour/configuration.cc:107 +#: libs/ardour/configuration.cc:108 msgid "Ardour: cannot read configuration file \"%1\"" msgstr "Ardour: ÎÅ ÕÄÁÌÏÓØ ÐÒÏÞÉÔÁÔØ ÆÁÊÌ ËÏÎÆÉÇÕÒÁÃÉÉ ÐÏÌØÚÏ×ÁÔÅÌÑ \"%1\"" -#: libs/ardour/configuration.cc:112 +#: libs/ardour/configuration.cc:113 #, fuzzy msgid "Ardour: user configuration file \"%1\" not loaded successfully." msgstr "Ardour: ÎÅ ÕÄÁÌÏÓØ ÚÁÇÒÕÚÉÔØ ÆÁÊÌ ËÏÎÆÉÇÕÒÁÃÉÉ ÐÏÌØÚÏ×ÁÔÅÌÑ \"%1\"." -#: libs/ardour/configuration.cc:136 +#: libs/ardour/configuration.cc:137 #, fuzzy msgid "Config file %1 not saved" msgstr "æÁÊÌ ËÏÎÆÉÇÕÒÁÃÉÉ ÎÅ ÓÏÈÒÁΣÎ" -#: libs/ardour/configuration.cc:209 +#: libs/ardour/configuration.cc:210 msgid "ill-formed MIDI port specification in ardour rcfile (ignored)" msgstr "" @@ -305,28 +472,40 @@ msgstr "" msgid "Node for Connection has no \"connections\" property" msgstr "" -#: libs/ardour/connection.cc:227 libs/ardour/io.cc:1889 +#: libs/ardour/connection.cc:227 libs/ardour/io.cc:1902 msgid "IO: badly formed string in XML node for inputs \"%1\"" msgstr "" -#: libs/ardour/connection.cc:232 libs/ardour/io.cc:1894 +#: libs/ardour/connection.cc:232 libs/ardour/io.cc:1907 msgid "bad input string in XML node \"%1\"" msgstr "" -#: libs/ardour/control_protocol_manager.cc:79 +#: libs/ardour/control_protocol_manager.cc:80 msgid "control protocol name \"%1\" has no descriptor" msgstr "" -#: libs/ardour/control_protocol_manager.cc:84 +#: libs/ardour/control_protocol_manager.cc:85 msgid "control protocol name \"%1\" could not be initialized" msgstr "" -#: libs/ardour/control_protocol_manager.cc:180 +#: libs/ardour/control_protocol_manager.cc:141 +msgid "Instantiating mandatory control protocol %1" +msgstr "" + +#: libs/ardour/control_protocol_manager.cc:175 +msgid "Control protocol %1 not usable" +msgstr "" + +#: libs/ardour/control_protocol_manager.cc:187 +msgid "Control surface protocol discovered: \"%1\"" +msgstr "" + +#: libs/ardour/control_protocol_manager.cc:205 #, fuzzy msgid "ControlProtocolManager: cannot load module \"%1\" (%2)" msgstr "LADSPA: ÎÅ ÕÄÁÌÏÓØ ÚÁÇÒÕÚÉÔØ ÍÏÄÕÌØ \"%1\" (%2)" -#: libs/ardour/control_protocol_manager.cc:188 +#: libs/ardour/control_protocol_manager.cc:213 msgid "ControlProtocolManager: module \"%1\" has no descriptor function." msgstr "" @@ -354,343 +533,100 @@ msgstr "" msgid "old-style crossfade information - no position information" msgstr "" -#: libs/ardour/curve.cc:112 libs/ardour/insert.cc:454 -#: libs/ardour/session.cc:2452 libs/ardour/session.cc:2504 +#: libs/ardour/curve.cc:112 libs/ardour/globals.cc:340 +#: libs/ardour/insert.cc:454 libs/ardour/session.cc:2466 +#: libs/ardour/session.cc:2518 msgid "programming error: " msgstr "ÏÛÉÂËÁ ÐÒÏÇÒÁÍÍÙ: " -#: libs/ardour/cycle_timer.cc:35 +#: libs/ardour/cycle_timer.cc:37 msgid "CycleTimer::get_mhz(): can't open /proc/cpuinfo" msgstr "" -#: libs/ardour/cycle_timer.cc:47 +#: libs/ardour/cycle_timer.cc:49 msgid "CycleTimer::get_mhz(): cannot locate cpu MHz in /proc/cpuinfo" msgstr "" -#: libs/ardour/cycle_timer.cc:70 +#: libs/ardour/cycle_timer.cc:72 msgid "cannot locate cpu MHz in /proc/cpuinfo" msgstr "" -#: libs/ardour/destructive_filesource.cc:197 +#: libs/ardour/destructive_filesource.cc:188 msgid "DestructiveFileSource: \"%1\" bad read retval: %2 of %5 (%3: %4)" msgstr "" -#: libs/ardour/destructive_filesource.cc:210 -#: libs/ardour/destructive_filesource.cc:252 -#: libs/ardour/destructive_filesource.cc:259 +#: libs/ardour/destructive_filesource.cc:201 +#: libs/ardour/destructive_filesource.cc:243 +#: libs/ardour/destructive_filesource.cc:250 msgid "DestructiveFileSource: \"%1\" bad write (%2)" msgstr "" -#: libs/ardour/diskstream.cc:337 -msgid "DiskStream: Session doesn't know about a Playlist called \"%1\"" -msgstr "" - -#: libs/ardour/diskstream.cc:342 -msgid "DiskStream: Playlist \"%1\" isn't an audio playlist" -msgstr "" - -#: libs/ardour/diskstream.cc:433 -msgid "DiskStream %1: there is no existing playlist to make a copy of!" -msgstr "" - -#: libs/ardour/diskstream.cc:1113 libs/ardour/diskstream.cc:1124 -msgid "DiskStream %1: when refilling, cannot read %2 from playlist at frame %3" -msgstr "" - -#: libs/ardour/diskstream.cc:1256 -msgid "DiskStream %1: cannot read %2 from playlist at frame %3" -msgstr "" - -#: libs/ardour/diskstream.cc:1623 libs/ardour/diskstream.cc:1640 -msgid "DiskStream %1: cannot write to disk" -msgstr "" - -#: libs/ardour/diskstream.cc:1700 -msgid "DiskStream \"%1\": cannot flush captured data to disk!" -msgstr "" - -#: libs/ardour/diskstream.cc:1797 -msgid "%1: could not create region for complete audio file" -msgstr "" - -#: libs/ardour/diskstream.cc:1820 -msgid "DiskStream: could not create region for captured audio!" -msgstr "" - -#: libs/ardour/diskstream.cc:1875 -#, fuzzy -msgid "programmer error: %1" -msgstr "ÏÛÉÂËÁ ÐÒÏÇÒÁÍÍÙ: " - -#: libs/ardour/diskstream.cc:2155 -msgid "DiskStream: channel %1 out of range" -msgstr "" - -#: libs/ardour/diskstream.cc:2180 -msgid "%1:%2 new capture file not initialized correctly" -msgstr "" - -#: libs/ardour/diskstream.cc:2413 -msgid "Location \"%1\" not valid for track loop (start >= end)" -msgstr "" - -#: libs/ardour/diskstream.cc:2491 -msgid "%1: cannot restore pending capture source file %2" -msgstr "" - -#: libs/ardour/diskstream.cc:2513 -msgid "%1: incorrect number of pending sources listed - ignoring them all" -msgstr "" - -#: libs/ardour/diskstream.cc:2529 -msgid "%1: cannot create whole-file region from pending capture sources" -msgstr "" - -#: libs/ardour/diskstream.cc:2541 -msgid "%1: cannot create region from pending capture sources" -msgstr "" - -#: libs/ardour/filesource.cc:175 -msgid "FileSource: search path not set" -msgstr "" - -#: libs/ardour/filesource.cc:190 -msgid "FileSource: \"%1\" not found when searching %2 using %3" -msgstr "" - -#: libs/ardour/filesource.cc:196 -msgid "" -"FileSource: \"%1\" is ambigous when searching %2\n" -"\t" -msgstr "" - -#: libs/ardour/filesource.cc:231 -msgid "Filesource: cannot find required file (%1): %2" -msgstr "" - -#: libs/ardour/filesource.cc:239 -msgid "Filesource: cannot check for existing file (%1): %2" -msgstr "" - -#: libs/ardour/filesource.cc:245 libs/ardour/filesource.cc:1127 -#: libs/ardour/filesource.cc:1210 -msgid "FileSource: could not open \"%1\": (%2)" -msgstr "" - -#: libs/ardour/filesource.cc:278 -msgid "FileSource: cannot write header in %1" -msgstr "" - -#: libs/ardour/filesource.cc:293 -msgid "FileSource: cannot locate chunks in %1" -msgstr "" - -#: libs/ardour/filesource.cc:298 -msgid "FileSource: cannot read header in %1" -msgstr "" - -#: libs/ardour/filesource.cc:303 -msgid "FileSource: cannot check header in %1" -msgstr "" - -#: libs/ardour/filesource.cc:311 -msgid "FileSource: cannot initialize peakfile for %1 as %2" -msgstr "" - -#: libs/ardour/filesource.cc:359 libs/ardour/insert.cc:525 -#, fuzzy -msgid "programming error: %1" -msgstr "ÏÛÉÂËÁ ÐÒÏÇÒÁÍÍÙ: " - -#: libs/ardour/filesource.cc:364 -msgid "cannot rename audio file for %1 to %2" -msgstr "" - -#: libs/ardour/filesource.cc:390 -msgid "FileSource: cannot seek to end of file" -msgstr "" - -#: libs/ardour/filesource.cc:395 -msgid "FileSource: cannot read RIFF/WAVE chunk from file" -msgstr "" - -#: libs/ardour/filesource.cc:407 -msgid "FileSource %1: not a RIFF/WAVE file" -msgstr "" - -#: libs/ardour/filesource.cc:434 -msgid "FileSource: can't read a chunk" -msgstr "" - -#: libs/ardour/filesource.cc:451 -msgid "filesource: correcting mis-written RIFF file to become a RIFX: " -msgstr "" - -#: libs/ardour/filesource.cc:567 -msgid "FileSource: cannot get user information for BWF header (%1)" -msgstr "" - -#: libs/ardour/filesource.cc:571 -msgid "FileSource: cannot get host information for BWF header (%1)" -msgstr "" - -#: libs/ardour/filesource.cc:716 -msgid "FileSource[%1]: cannot update data size: %2" -msgstr "" - -#: libs/ardour/filesource.cc:733 -msgid "FileSource: can't find RIFF chunk info" -msgstr "" - -#: libs/ardour/filesource.cc:737 -msgid "FileSource: can't find RIFX chunk info" -msgstr "" - -#: libs/ardour/filesource.cc:758 -msgid "FileSource: can't read RIFF chunk" -msgstr "" - -#: libs/ardour/filesource.cc:768 -msgid "FileSource: can't find format chunk info" -msgstr "" - -#: libs/ardour/filesource.cc:773 -msgid "FileSource: can't read format chunk" -msgstr "" - -#: libs/ardour/filesource.cc:782 -msgid "FileSource: can't find data chunk info" -msgstr "" - -#: libs/ardour/filesource.cc:787 -msgid "FileSource: can't read data chunk" -msgstr "" - -#: libs/ardour/filesource.cc:804 -msgid "" -"FileSource: cannot read Broadcast Wave data from existing audio file \"%1" -"\" (%2)" -msgstr "" - -#: libs/ardour/filesource.cc:820 -msgid "" -"FileSource: cannot read Broadcast Wave coding history from audio file \"%1" -"\" (%2)" -msgstr "" - -#: libs/ardour/filesource.cc:862 -msgid "" -"FileSource \"%1\" does not use valid sample format.\n" -"This is probably a programming error." -msgstr "" - -#: libs/ardour/filesource.cc:901 -msgid "FileSource \"%1\" has no \"data\" chunk" -msgstr "" - -#: libs/ardour/filesource.cc:906 -msgid "%1: data length in header (%2) differs from implicit size in file (%3)" -msgstr "" - -#: libs/ardour/filesource.cc:911 -msgid "\"%1\" has a sample rate of %2 instead of %3 as used by this session" -msgstr "" - -#: libs/ardour/filesource.cc:934 -msgid "FileSource: cannot write WAVE chunk: %1" -msgstr "" - -#: libs/ardour/filesource.cc:978 -msgid "FileSource: cannot write format chunk: %1" -msgstr "" - -#: libs/ardour/filesource.cc:990 -msgid "FileSource: cannot data chunk: %1" -msgstr "" - -#: libs/ardour/filesource.cc:1103 libs/ardour/filesource.cc:1188 -msgid "FileSource: \"%1\" bad write (%2)" -msgstr "" - -#: libs/ardour/filesource.cc:1335 libs/ardour/session_state.cc:3093 -msgid "" -"there are already 1000 files with names like %1; versioning discontinued" -msgstr "" - -#: libs/ardour/filesource.cc:1349 libs/ardour/session_state.cc:3107 -msgid "cannot rename audio file source from %1 to %2 (%3)" -msgstr "" - -#: libs/ardour/filesource.cc:1356 libs/ardour/session_state.cc:3122 -msgid "cannot remove peakfile %1 for %2 (%3)" -msgstr "" - -#: libs/ardour/globals.cc:82 +#: libs/ardour/globals.cc:109 msgid "no MIDI ports specified: no MMC or MTC control possible" msgstr "" -#: libs/ardour/globals.cc:97 +#: libs/ardour/globals.cc:124 msgid "MIDI port specifications for \"%1\" are not understandable." msgstr "" -#: libs/ardour/globals.cc:110 libs/ardour/globals.cc:114 -#: libs/ardour/globals.cc:118 +#: libs/ardour/globals.cc:137 libs/ardour/globals.cc:141 +#: libs/ardour/globals.cc:145 msgid "default" msgstr "" -#: libs/ardour/globals.cc:146 +#: libs/ardour/globals.cc:173 msgid "No MMC control (MIDI port \"%1\" not available)" msgstr "" -#: libs/ardour/globals.cc:152 +#: libs/ardour/globals.cc:179 msgid "No MTC support (MIDI port \"%1\" not available)" msgstr "" -#: libs/ardour/globals.cc:157 +#: libs/ardour/globals.cc:184 msgid "No MIDI parameter support (MIDI port \"%1\" not available)" msgstr "" -#: libs/ardour/import.cc:71 +#: libs/ardour/import.cc:75 msgid "Import: cannot open input sound file \"%1\"" msgstr "" -#: libs/ardour/import.cc:76 +#: libs/ardour/import.cc:80 msgid "resampling audio" msgstr "" -#: libs/ardour/import.cc:80 +#: libs/ardour/import.cc:84 msgid "Import: cannot open converted sound file \"%1\"" msgstr "" -#: libs/ardour/import.cc:85 +#: libs/ardour/import.cc:89 msgid "Import: error while resampling sound file \"%1\"" msgstr "" -#: libs/ardour/import.cc:141 +#: libs/ardour/import.cc:148 msgid "Session::import_audiofile: cannot open new file source for channel %1" msgstr "" -#: libs/ardour/import.cc:160 +#: libs/ardour/import.cc:167 msgid "converting audio" msgstr "" -#: libs/ardour/import.cc:192 +#: libs/ardour/import.cc:199 msgid "building region" msgstr "" -#: libs/ardour/import.cc:194 +#: libs/ardour/import.cc:201 msgid "building regions" msgstr "" -#: libs/ardour/import.cc:318 +#: libs/ardour/import.cc:325 msgid "Import: could not open temp file: %1" msgstr "" -#: libs/ardour/import.cc:327 +#: libs/ardour/import.cc:334 msgid "Import: src_new() failed : %1" msgstr "" -#: libs/ardour/import.cc:355 +#: libs/ardour/import.cc:362 msgid "Import: %1" msgstr "éÍÐÏÒÔ: %1" @@ -744,278 +680,278 @@ msgstr "" msgid "non-port insert XML used for port plugin insert" msgstr "" -#: libs/ardour/io.cc:585 +#: libs/ardour/io.cc:598 msgid "IO: cannot disconnect input port %1 from %2" msgstr "" -#: libs/ardour/io.cc:653 +#: libs/ardour/io.cc:666 msgid "IO: cannot disconnect output port %1 from %2" msgstr "" -#: libs/ardour/io.cc:794 libs/ardour/io.cc:1138 libs/ardour/io.cc:1264 +#: libs/ardour/io.cc:807 libs/ardour/io.cc:1151 libs/ardour/io.cc:1277 #, c-format msgid "%s/out" msgstr "" -#: libs/ardour/io.cc:796 libs/ardour/io.cc:1140 libs/ardour/io.cc:1266 -#: libs/ardour/io.cc:2826 +#: libs/ardour/io.cc:809 libs/ardour/io.cc:1153 libs/ardour/io.cc:1279 +#: libs/ardour/io.cc:2849 #, c-format msgid "%s/out %u" msgstr "" -#: libs/ardour/io.cc:800 libs/ardour/io.cc:1145 libs/ardour/io.cc:1270 +#: libs/ardour/io.cc:813 libs/ardour/io.cc:1158 libs/ardour/io.cc:1283 msgid "IO: cannot register output port %1" msgstr "" -#: libs/ardour/io.cc:895 libs/ardour/io.cc:998 libs/ardour/io.cc:1104 +#: libs/ardour/io.cc:908 libs/ardour/io.cc:1011 libs/ardour/io.cc:1117 #, c-format msgid "%s/in" msgstr "" -#: libs/ardour/io.cc:897 libs/ardour/io.cc:1001 libs/ardour/io.cc:1107 -#: libs/ardour/io.cc:2796 +#: libs/ardour/io.cc:910 libs/ardour/io.cc:1014 libs/ardour/io.cc:1120 +#: libs/ardour/io.cc:2819 #, c-format msgid "%s/in %u" msgstr "" -#: libs/ardour/io.cc:901 libs/ardour/io.cc:1007 libs/ardour/io.cc:1112 +#: libs/ardour/io.cc:914 libs/ardour/io.cc:1020 libs/ardour/io.cc:1125 msgid "IO: cannot register input port %1" msgstr "" -#: libs/ardour/io.cc:1528 +#: libs/ardour/io.cc:1541 msgid "IO::connecting_became_legal() called without a pending state node" msgstr "" -#: libs/ardour/io.cc:1551 +#: libs/ardour/io.cc:1564 msgid "IO::ports_became_legal() called without a pending state node" msgstr "" -#: libs/ardour/io.cc:1581 +#: libs/ardour/io.cc:1594 msgid "incorrect XML node \"%1\" passed to IO object" msgstr "" -#: libs/ardour/io.cc:1636 +#: libs/ardour/io.cc:1649 msgid "" "MIDI gain control specification for %1 is incomplete, so it has been ignored" msgstr "" -#: libs/ardour/io.cc:1726 libs/ardour/io.cc:1838 +#: libs/ardour/io.cc:1739 libs/ardour/io.cc:1851 msgid "Unknown connection \"%1\" listed for output of %2" msgstr "" -#: libs/ardour/io.cc:1728 libs/ardour/io.cc:1840 +#: libs/ardour/io.cc:1741 libs/ardour/io.cc:1853 msgid "out 1" msgstr "" -#: libs/ardour/io.cc:1729 libs/ardour/io.cc:1841 +#: libs/ardour/io.cc:1742 libs/ardour/io.cc:1854 msgid "No output connections available as a replacement" msgstr "" -#: libs/ardour/io.cc:1733 libs/ardour/io.cc:1845 +#: libs/ardour/io.cc:1746 libs/ardour/io.cc:1858 msgid "Connection %1 was not available - \"out 1\" used instead" msgstr "" -#: libs/ardour/io.cc:1747 +#: libs/ardour/io.cc:1760 msgid "%1: cannot create I/O ports" msgstr "" -#: libs/ardour/io.cc:1854 +#: libs/ardour/io.cc:1867 msgid "improper output channel list in XML node (%1)" msgstr "" -#: libs/ardour/io.cc:1939 +#: libs/ardour/io.cc:1952 msgid "IO: badly formed string in XML node for outputs \"%1\"" msgstr "" -#: libs/ardour/io.cc:1944 +#: libs/ardour/io.cc:1957 msgid "IO: bad output string in XML node \"%1\"" msgstr "" -#: libs/ardour/io.cc:2502 +#: libs/ardour/io.cc:2525 msgid "%1: could not open automation event file \"%2\"" msgstr "" -#: libs/ardour/io.cc:2541 +#: libs/ardour/io.cc:2564 msgid "%1: cannot open automation event file \"%2\"" msgstr "" -#: libs/ardour/io.cc:2556 +#: libs/ardour/io.cc:2579 msgid "badly formed version number in automation event file \"%1\"" msgstr "" -#: libs/ardour/io.cc:2560 +#: libs/ardour/io.cc:2583 msgid "no version information in automation event file \"%1\"" msgstr "" -#: libs/ardour/io.cc:2565 +#: libs/ardour/io.cc:2588 msgid "mismatched automation event file version (%1)" msgstr "" -#: libs/ardour/io.cc:2573 +#: libs/ardour/io.cc:2596 msgid "badly formatted automation event record at line %1 of %2 (ignored)" msgstr "" -#: libs/ardour/io.cc:2593 +#: libs/ardour/io.cc:2616 msgid "dubious automation event found (and ignored)" msgstr "" -#: libs/ardour/io.cc:2597 libs/ardour/panner.cc:437 +#: libs/ardour/io.cc:2620 libs/ardour/panner.cc:438 #: libs/ardour/redirect.cc:148 msgid "loaded from disk" msgstr "" -#: libs/ardour/io.cc:2768 +#: libs/ardour/io.cc:2791 msgid "automation write/touch" msgstr "" -#: libs/ardour/ladspa_plugin.cc:86 +#: libs/ardour/ladspa_plugin.cc:87 msgid "LADSPA: module has no descriptor function." msgstr "" -#: libs/ardour/ladspa_plugin.cc:91 +#: libs/ardour/ladspa_plugin.cc:92 msgid "LADSPA: plugin has gone away since discovery!" msgstr "" -#: libs/ardour/ladspa_plugin.cc:98 +#: libs/ardour/ladspa_plugin.cc:99 msgid "LADSPA: \"%1\" cannot be used, since it cannot do inplace processing" msgstr "" -#: libs/ardour/ladspa_plugin.cc:328 +#: libs/ardour/ladspa_plugin.cc:329 msgid "" "illegal parameter number used with plugin \"%1\". This mayindicate a change " "in the plugin design, and presets may beinvalid" msgstr "" -#: libs/ardour/ladspa_plugin.cc:429 +#: libs/ardour/ladspa_plugin.cc:430 msgid "Bad node sent to LadspaPlugin::set_state" msgstr "" -#: libs/ardour/ladspa_plugin.cc:442 +#: libs/ardour/ladspa_plugin.cc:443 msgid "LADSPA: no ladspa port number" msgstr "" -#: libs/ardour/ladspa_plugin.cc:448 +#: libs/ardour/ladspa_plugin.cc:449 msgid "LADSPA: no ladspa port data" msgstr "" -#: libs/ardour/ladspa_plugin.cc:497 +#: libs/ardour/ladspa_plugin.cc:498 msgid "" "LADSPA LadspaPlugin MIDI control specification for port %1 is incomplete, so " "it has been ignored" msgstr "" -#: libs/ardour/location.cc:268 +#: libs/ardour/location.cc:269 msgid "incorrect XML node passed to Location::set_state" msgstr "" -#: libs/ardour/location.cc:275 +#: libs/ardour/location.cc:276 msgid "XML node for Location has no name information" msgstr "" -#: libs/ardour/location.cc:282 +#: libs/ardour/location.cc:283 msgid "XML node for Location has no start information" msgstr "" -#: libs/ardour/location.cc:293 +#: libs/ardour/location.cc:294 msgid "XML node for Location has no end information" msgstr "" -#: libs/ardour/location.cc:302 +#: libs/ardour/location.cc:303 msgid "XML node for Location has no flags information" msgstr "" -#: libs/ardour/location.cc:390 +#: libs/ardour/location.cc:391 msgid "Locations: attempt to use unknown location as selected location" msgstr "" -#: libs/ardour/location.cc:417 libs/ardour/playlist.cc:1187 +#: libs/ardour/location.cc:418 libs/ardour/playlist.cc:1187 msgid "clear" msgstr "" -#: libs/ardour/location.cc:442 +#: libs/ardour/location.cc:443 msgid "clear markers" msgstr "" -#: libs/ardour/location.cc:470 +#: libs/ardour/location.cc:471 msgid "clear ranges" msgstr "" -#: libs/ardour/location.cc:488 +#: libs/ardour/location.cc:489 msgid "add" msgstr "ÄÏÂÁ×ÉÔØ" -#: libs/ardour/location.cc:526 +#: libs/ardour/location.cc:527 msgid "remove" msgstr "ÕÄÁÌÉÔØ" -#: libs/ardour/location.cc:566 +#: libs/ardour/location.cc:567 msgid "incorrect XML mode passed to Locations::set_state" msgstr "" -#: libs/ardour/mtc_slave.cc:195 +#: libs/ardour/mtc_slave.cc:196 msgid "MTC Slave: atomic read of current time failed, sleeping!" msgstr "" -#: libs/ardour/named_selection.cc:76 +#: libs/ardour/named_selection.cc:77 msgid "Chunk %1 uses an unknown playlist \"%2\"" msgstr "" -#: libs/ardour/named_selection.cc:79 +#: libs/ardour/named_selection.cc:80 msgid "Chunk %1 contains misformed playlist information" msgstr "" -#: libs/ardour/panner.cc:255 +#: libs/ardour/panner.cc:256 msgid "MIDI pan control specification is incomplete, so it has been ignored" msgstr "" -#: libs/ardour/panner.cc:360 +#: libs/ardour/panner.cc:361 msgid "automation write pass" msgstr "" -#: libs/ardour/panner.cc:400 +#: libs/ardour/panner.cc:401 #, c-format msgid "error writing pan automation file (%s)" msgstr "" -#: libs/ardour/panner.cc:428 +#: libs/ardour/panner.cc:429 msgid "" "badly formatted pan automation event record at line %1 of %2 (ignored) [%3]" msgstr "" -#: libs/ardour/panner.cc:943 +#: libs/ardour/panner.cc:944 msgid "badly-formed positional data for Multi2dPanner - ignored" msgstr "" -#: libs/ardour/panner.cc:1236 +#: libs/ardour/panner.cc:1237 msgid "cannot open pan automation file \"%1\" for saving (%s)" msgstr "" -#: libs/ardour/panner.cc:1272 +#: libs/ardour/panner.cc:1273 msgid "cannot open pan automation file %1 (%2)" msgstr "" -#: libs/ardour/panner.cc:1285 +#: libs/ardour/panner.cc:1286 msgid "badly formed version number in pan automation event file \"%1\"" msgstr "" -#: libs/ardour/panner.cc:1289 +#: libs/ardour/panner.cc:1290 msgid "" "no version information in pan automation event file \"%1\" (first line = %2)" msgstr "" -#: libs/ardour/panner.cc:1295 +#: libs/ardour/panner.cc:1296 msgid "mismatched pan automation event file version (%1)" msgstr "" -#: libs/ardour/panner.cc:1309 +#: libs/ardour/panner.cc:1310 msgid "too many panner states found in pan automation file %1" msgstr "" -#: libs/ardour/panner.cc:1450 +#: libs/ardour/panner.cc:1451 msgid "Unknown panner plugin \"%1\" found in pan state - ignored" msgstr "" -#: libs/ardour/panner.cc:1456 +#: libs/ardour/panner.cc:1457 msgid "panner plugin node has no type information!" msgstr "" @@ -1067,62 +1003,62 @@ msgstr "" msgid "nudged" msgstr "" -#: libs/ardour/playlist_factory.cc:26 libs/ardour/playlist_factory.cc:41 +#: libs/ardour/playlist_factory.cc:49 libs/ardour/playlist_factory.cc:64 msgid "" "programming error: Playlist::createRegion called with unknown Region type" msgstr "" -#: libs/ardour/playlist_factory.cc:63 +#: libs/ardour/playlist_factory.cc:86 msgid "" "programming error: Playlist::copyPlaylist called with unknown Playlist type" msgstr "" -#: libs/ardour/plugin.cc:327 +#: libs/ardour/plugin.cc:328 msgid "Could not locate HOME. Preset not saved." msgstr "" -#: libs/ardour/plugin.cc:337 libs/ardour/plugin.cc:343 +#: libs/ardour/plugin.cc:338 libs/ardour/plugin.cc:344 msgid "Could not create %1. Preset not saved. (%2)" msgstr "" -#: libs/ardour/plugin.cc:348 +#: libs/ardour/plugin.cc:349 msgid "Error saving presets file %1." msgstr "" -#: libs/ardour/plugin_manager.cc:193 +#: libs/ardour/plugin_manager.cc:194 msgid "Could not parse rdf file: %1" msgstr "" -#: libs/ardour/plugin_manager.cc:234 +#: libs/ardour/plugin_manager.cc:235 msgid "LADSPA: cannot load module \"%1\" (%2)" msgstr "LADSPA: ÎÅ ÕÄÁÌÏÓØ ÚÁÇÒÕÚÉÔØ ÍÏÄÕÌØ \"%1\" (%2)" -#: libs/ardour/plugin_manager.cc:241 +#: libs/ardour/plugin_manager.cc:242 msgid "LADSPA: module \"%1\" has no descriptor function." msgstr "" -#: libs/ardour/plugin_manager.cc:296 +#: libs/ardour/plugin_manager.cc:297 #, fuzzy msgid "VST: cannot load module from \"%1\"" msgstr "LADSPA: ÎÅ ÕÄÁÌÏÓØ ÚÁÇÒÕÚÉÔØ ÍÏÄÕÌØ \"%1\" (%2)" -#: libs/ardour/plugin_manager.cc:301 +#: libs/ardour/plugin_manager.cc:302 msgid "You asked ardour to not use any VST plugins" msgstr "" -#: libs/ardour/plugin_manager.cc:304 +#: libs/ardour/plugin_manager.cc:305 msgid "This version of ardour has no support for VST plugins" msgstr "" -#: libs/ardour/plugin_manager.cc:311 +#: libs/ardour/plugin_manager.cc:312 msgid "LADSPA: cannot load module from \"%1\"" msgstr "" -#: libs/ardour/plugin_manager.cc:373 libs/ardour/plugin_manager.cc:385 +#: libs/ardour/plugin_manager.cc:374 libs/ardour/plugin_manager.cc:386 msgid "Unknown" msgstr "" -#: libs/ardour/plugin_manager.cc:463 +#: libs/ardour/plugin_manager.cc:464 msgid "" "VST plugin %1 does not support processReplacing, and so cannot be used in " "ardour at this time" @@ -1136,11 +1072,11 @@ msgstr "" msgid "programming error: unknown Redirect type in Redirect::Clone!\n" msgstr "" -#: libs/ardour/redirect.cc:102 libs/ardour/utils.cc:199 +#: libs/ardour/redirect.cc:102 libs/ardour/utils.cc:203 msgid "pre" msgstr "ÐÒÅ" -#: libs/ardour/redirect.cc:104 libs/ardour/utils.cc:202 +#: libs/ardour/redirect.cc:104 libs/ardour/utils.cc:206 msgid "post" msgstr "ÐÏÓÔ" @@ -1192,259 +1128,254 @@ msgstr "" msgid "active_changed" msgstr "" -#: libs/ardour/region.cc:884 +#: libs/ardour/region.cc:885 msgid "Session: XMLNode describing a Region is incomplete (no id)" msgstr "" -#: libs/ardour/region.cc:891 +#: libs/ardour/region.cc:892 msgid "Session: XMLNode describing a Region is incomplete (no name)" msgstr "" -#: libs/ardour/route.cc:79 libs/ardour/session.cc:1541 -#: libs/ardour/session.cc:1547 libs/ardour/session.cc:3064 +#: libs/ardour/route.cc:79 libs/ardour/session.cc:1554 +#: libs/ardour/session.cc:1560 libs/ardour/session.cc:3093 msgid "signal" msgstr "" -#: libs/ardour/route.cc:1433 +#: libs/ardour/route.cc:1430 msgid "Could not get state of route. Problem with save_automation" msgstr "" -#: libs/ardour/route.cc:1485 +#: libs/ardour/route.cc:1482 msgid "Send construction failed" msgstr "" -#: libs/ardour/route.cc:1507 +#: libs/ardour/route.cc:1504 msgid "unknown Insert type \"%1\"; ignored" msgstr "" -#: libs/ardour/route.cc:1513 +#: libs/ardour/route.cc:1510 msgid "Insert XML node has no type property" msgstr "" -#: libs/ardour/route.cc:1518 +#: libs/ardour/route.cc:1515 msgid "insert could not be created. Ignored." msgstr "" -#: libs/ardour/route.cc:1536 +#: libs/ardour/route.cc:1533 msgid "Bad node sent to Route::set_state() [%1]" msgstr "" -#: libs/ardour/route.cc:1595 +#: libs/ardour/route.cc:1592 msgid "Route %1: unknown edit group \"%2 in saved state (ignored)" msgstr "" -#: libs/ardour/route.cc:1611 libs/ardour/route.cc:1615 +#: libs/ardour/route.cc:1608 libs/ardour/route.cc:1612 msgid "badly formed order key string in state file! [%1] ... ignored." msgstr "" -#: libs/ardour/route.cc:1696 libs/ardour/route.cc:1823 +#: libs/ardour/route.cc:1693 libs/ardour/route.cc:1820 msgid "[control]" msgstr "" -#: libs/ardour/route.cc:1716 +#: libs/ardour/route.cc:1713 msgid "Route %1: unknown mix group \"%2 in saved state (ignored)" msgstr "" -#: libs/ardour/route.cc:1745 libs/ardour/route.cc:1753 +#: libs/ardour/route.cc:1742 libs/ardour/route.cc:1750 msgid "" "MIDI mute control specification for %1 is incomplete, so it has been ignored" msgstr "" -#: libs/ardour/send.cc:98 +#: libs/ardour/send.cc:99 msgid "XML node describing a send is missing a Redirect node" msgstr "" -#: libs/ardour/session.cc:99 +#: libs/ardour/session.cc:103 msgid "Could not resolve path: %1 (%2)" msgstr "" -#: libs/ardour/session.cc:111 +#: libs/ardour/session.cc:115 msgid "cannot check session path %1 (%2)" msgstr "" -#: libs/ardour/session.cc:141 +#: libs/ardour/session.cc:145 msgid "cannot check statefile %1 (%2)" msgstr "" -#: libs/ardour/session.cc:177 +#: libs/ardour/session.cc:181 msgid "%1 is not an Ardour snapshot file" msgstr "" -#: libs/ardour/session.cc:194 +#: libs/ardour/session.cc:198 msgid "cannot determine current working directory (%1)" msgstr "" -#: libs/ardour/session.cc:211 +#: libs/ardour/session.cc:215 msgid "unknown file type for session %1" msgstr "" -#: libs/ardour/session.cc:316 +#: libs/ardour/session.cc:320 msgid "monitor" msgstr "ÍÏÎÉÔÏÒ" -#: libs/ardour/session.cc:323 +#: libs/ardour/session.cc:327 msgid "master" msgstr "ÍÁÓÔÅÒ" -#: libs/ardour/session.cc:607 +#: libs/ardour/session.cc:611 msgid "could not setup Click I/O" msgstr "" -#: libs/ardour/session.cc:628 +#: libs/ardour/session.cc:632 msgid "cannot setup Click I/O" msgstr "" -#: libs/ardour/session.cc:650 +#: libs/ardour/session.cc:654 msgid "cannot create Auditioner: no auditioning of regions possible" msgstr "" -#: libs/ardour/session.cc:662 +#: libs/ardour/session.cc:666 #, c-format msgid "out %" msgstr "" -#: libs/ardour/session.cc:674 +#: libs/ardour/session.cc:678 #, c-format msgid "in %" msgstr "" -#: libs/ardour/session.cc:688 +#: libs/ardour/session.cc:692 #, c-format msgid "out %+%" msgstr "" -#: libs/ardour/session.cc:702 +#: libs/ardour/session.cc:706 #, c-format msgid "in %+%" msgstr "" -#: libs/ardour/session.cc:735 +#: libs/ardour/session.cc:739 msgid "cannot setup master inputs" msgstr "" -#: libs/ardour/session.cc:743 +#: libs/ardour/session.cc:747 msgid "cannot setup master outputs" msgstr "" -#: libs/ardour/session.cc:754 +#: libs/ardour/session.cc:758 #, fuzzy msgid "Master Out" msgstr "ÍÁÓÔÅÒ" -#: libs/ardour/session.cc:820 +#: libs/ardour/session.cc:830 msgid "cannot setup control inputs" msgstr "" -#: libs/ardour/session.cc:828 +#: libs/ardour/session.cc:838 msgid "cannot set up master outputs" msgstr "" -#: libs/ardour/session.cc:1100 +#: libs/ardour/session.cc:1110 msgid "Session: you can't use that location for auto punch (start <= end)" msgstr "" -#: libs/ardour/session.cc:1179 +#: libs/ardour/session.cc:1189 msgid "Session: you can't use a mark for auto loop" msgstr "" -#: libs/ardour/session.cc:1559 +#: libs/ardour/session.cc:1572 msgid "feedback loop setup between %1 and %2" msgstr "" -#: libs/ardour/session.cc:1711 libs/ardour/session.cc:1808 +#: libs/ardour/session.cc:1724 libs/ardour/session.cc:1821 msgid "cannot configure %1 in/%2 out configuration for new audio track" msgstr "" -#: libs/ardour/session.cc:1767 +#: libs/ardour/session.cc:1780 msgid "Session: could not create new audio track." msgstr "" -#: libs/ardour/session.cc:1857 +#: libs/ardour/session.cc:1870 msgid "Session: could not create new route." msgstr "" -#: libs/ardour/session.cc:2340 +#: libs/ardour/session.cc:2354 msgid "cannot create new name for region \"%1\"" msgstr "" -#: libs/ardour/session.cc:2404 +#: libs/ardour/session.cc:2418 msgid "too many regions with names like %1" msgstr "" -#: libs/ardour/session.cc:2860 +#: libs/ardour/session.cc:2883 msgid "There are already %1 recordings for %2, which I consider too many." msgstr "" -#: libs/ardour/session.cc:3229 +#: libs/ardour/session.cc:3258 msgid "programming error: unknown type of Insert created!" msgstr "" -#: libs/ardour/session.cc:3235 +#: libs/ardour/session.cc:3264 msgid "programming error: unknown type of Redirect created!" msgstr "" -#: libs/ardour/session.cc:3258 +#: libs/ardour/session.cc:3287 msgid "programming error: unknown type of Insert deleted!" msgstr "" -#: libs/ardour/session.cc:3264 +#: libs/ardour/session.cc:3293 msgid "programming error: unknown type of Redirect deleted!" msgstr "" -#: libs/ardour/session.cc:3605 +#: libs/ardour/session.cc:3636 msgid "too many bounced versions of playlist \"%1\"" msgstr "" -#: libs/ardour/session.cc:3614 +#: libs/ardour/session.cc:3649 msgid "cannot create new audio file \"%1\" for %2" msgstr "" -#: libs/ardour/session_butler.cc:81 libs/ardour/session_midi.cc:1183 -#: libs/ardour/source.cc:233 -msgid "Cannot create transport request signal pipe (%1)" -msgstr "" - -#: libs/ardour/session_butler.cc:86 libs/ardour/session_butler.cc:91 +#: libs/ardour/session_butler.cc:85 libs/ardour/session_butler.cc:90 msgid "UI: cannot set O_NONBLOCK on butler request pipe (%1)" msgstr "" -#: libs/ardour/session_butler.cc:96 +#: libs/ardour/session_butler.cc:95 msgid "Session: could not create butler thread" msgstr "" -#: libs/ardour/session_butler.cc:190 +#: libs/ardour/session_butler.cc:189 msgid "poll on butler request pipe failed (%1)" msgstr "" -#: libs/ardour/session_butler.cc:197 +#: libs/ardour/session_butler.cc:196 msgid "Error on butler thread request pipe" msgstr "" -#: libs/ardour/session_butler.cc:239 +#: libs/ardour/session_butler.cc:238 msgid "Error reading from butler request pipe" msgstr "" -#: libs/ardour/session_butler.cc:276 +#: libs/ardour/session_butler.cc:275 msgid "Butler read ahead failure on dstream %1" msgstr "" -#: libs/ardour/session_butler.cc:320 +#: libs/ardour/session_butler.cc:319 msgid "Butler write-behind failure on dstream %1" msgstr "" -#: libs/ardour/session_click.cc:157 +#: libs/ardour/session_click.cc:158 msgid "cannot open click soundfile %1 (%2)" msgstr "" -#: libs/ardour/session_click.cc:166 +#: libs/ardour/session_click.cc:167 msgid "cannot read data from click soundfile" msgstr "" -#: libs/ardour/session_click.cc:191 +#: libs/ardour/session_click.cc:192 msgid "cannot open click emphasis soundfile %1 (%2)" msgstr "" -#: libs/ardour/session_click.cc:199 +#: libs/ardour/session_click.cc:200 msgid "cannot read data from click emphasis soundfile" msgstr "" @@ -1544,7 +1475,7 @@ msgstr "" msgid "Error reading from transport request pipe" msgstr "" -#: libs/ardour/session_process.cc:105 +#: libs/ardour/session_process.cc:104 msgid "Session: error in no roll for %1" msgstr "" @@ -1561,192 +1492,199 @@ msgstr "" msgid "start" msgstr "ÒÁÚÄÅÌÉÔØ" -#: libs/ardour/session_state.cc:501 +#: libs/ardour/session_state.cc:502 msgid "Session: cannot create session dir \"%1\" (%2)" msgstr "" -#: libs/ardour/session_state.cc:512 +#: libs/ardour/session_state.cc:513 msgid "Session: cannot create session peakfile dir \"%1\" (%2)" msgstr "" -#: libs/ardour/session_state.cc:521 +#: libs/ardour/session_state.cc:522 msgid "Session: cannot create session sounds dir \"%1\" (%2)" msgstr "" -#: libs/ardour/session_state.cc:530 +#: libs/ardour/session_state.cc:531 msgid "Session: cannot create session tape dir \"%1\" (%2)" msgstr "" -#: libs/ardour/session_state.cc:539 +#: libs/ardour/session_state.cc:540 msgid "Session: cannot create session dead sounds dir \"%1\" (%2)" msgstr "" -#: libs/ardour/session_state.cc:548 +#: libs/ardour/session_state.cc:549 msgid "Session: cannot create session automation dir \"%1\" (%2)" msgstr "" -#: libs/ardour/session_state.cc:579 +#: libs/ardour/session_state.cc:580 msgid "Could not open %1 for writing mix template" msgstr "" -#: libs/ardour/session_state.cc:585 +#: libs/ardour/session_state.cc:586 msgid "Could not open mix template %1 for reading" msgstr "" -#: libs/ardour/session_state.cc:592 +#: libs/ardour/session_state.cc:593 msgid "Session already exists. Not overwriting" msgstr "" -#: libs/ardour/session_state.cc:635 +#: libs/ardour/session_state.cc:636 msgid "Session: could not load diskstream via XML state" msgstr "" -#: libs/ardour/session_state.cc:684 +#: libs/ardour/session_state.cc:685 msgid "could not backup old state file, current state not saved." msgstr "" -#: libs/ardour/session_state.cc:697 +#: libs/ardour/session_state.cc:698 msgid "state could not be saved to %1" msgstr "" -#: libs/ardour/session_state.cc:704 +#: libs/ardour/session_state.cc:705 msgid "could not remove corrupt state file %1" msgstr "" -#: libs/ardour/session_state.cc:708 +#: libs/ardour/session_state.cc:709 msgid "could not restore state file from backup %1" msgstr "" -#: libs/ardour/session_state.cc:777 +#: libs/ardour/session_state.cc:778 msgid "%1: session state information file \"%2\" doesn't exist!" msgstr "" -#: libs/ardour/session_state.cc:788 +#: libs/ardour/session_state.cc:789 msgid "Could not understand ardour file %1" msgstr "" -#: libs/ardour/session_state.cc:1492 +#: libs/ardour/session_state.cc:1493 msgid "programming error: Session: incorrect XML node sent to set_state()" msgstr "" -#: libs/ardour/session_state.cc:1538 +#: libs/ardour/session_state.cc:1539 msgid "Session: XML state has no options section" msgstr "" -#: libs/ardour/session_state.cc:1543 +#: libs/ardour/session_state.cc:1544 msgid "Session: XML state has no sources section" msgstr "" -#: libs/ardour/session_state.cc:1550 +#: libs/ardour/session_state.cc:1551 msgid "Session: XML state has no Regions section" msgstr "" -#: libs/ardour/session_state.cc:1557 +#: libs/ardour/session_state.cc:1558 msgid "Session: XML state has no playlists section" msgstr "" -#: libs/ardour/session_state.cc:1576 +#: libs/ardour/session_state.cc:1577 msgid "Session: XML state has no diskstreams section" msgstr "" -#: libs/ardour/session_state.cc:1583 +#: libs/ardour/session_state.cc:1584 msgid "Session: XML state has no connections section" msgstr "" -#: libs/ardour/session_state.cc:1590 +#: libs/ardour/session_state.cc:1591 msgid "Session: XML state has no locations section" msgstr "" -#: libs/ardour/session_state.cc:1623 +#: libs/ardour/session_state.cc:1624 msgid "Session: XML state has no edit groups section" msgstr "" -#: libs/ardour/session_state.cc:1630 +#: libs/ardour/session_state.cc:1631 msgid "Session: XML state has no mix groups section" msgstr "" -#: libs/ardour/session_state.cc:1637 +#: libs/ardour/session_state.cc:1638 msgid "Session: XML state has no Tempo Map section" msgstr "" -#: libs/ardour/session_state.cc:1644 +#: libs/ardour/session_state.cc:1645 msgid "Session: XML state has no routes section" msgstr "" -#: libs/ardour/session_state.cc:1651 +#: libs/ardour/session_state.cc:1652 msgid "Session: XML state has no click section" msgstr "" -#: libs/ardour/session_state.cc:1696 +#: libs/ardour/session_state.cc:1697 msgid "Session: cannot create Route from XML description." msgstr "" -#: libs/ardour/session_state.cc:1734 +#: libs/ardour/session_state.cc:1735 msgid "Session: cannot create Region from XML description." msgstr "" -#: libs/ardour/session_state.cc:1762 +#: libs/ardour/session_state.cc:1764 msgid "Session: XMLNode describing a AudioRegion is incomplete (no source)" msgstr "" -#: libs/ardour/session_state.cc:1770 libs/ardour/session_state.cc:1784 +#: libs/ardour/session_state.cc:1772 libs/ardour/session_state.cc:1792 msgid "" "Session: XMLNode describing a AudioRegion references an unknown source id =%1" msgstr "" -#: libs/ardour/session_state.cc:1852 +#: libs/ardour/session_state.cc:1778 libs/ardour/session_state.cc:1798 +msgid "" +"Session: XMLNode describing a AudioRegion references a non-audio source id =%" +"1" +msgstr "" + +#: libs/ardour/session_state.cc:1868 msgid "Session: cannot create Source from XML description." msgstr "" -#: libs/ardour/session_state.cc:1883 -msgid "Found a sound file that cannot be used by Ardour. See the progammers." +#: libs/ardour/session_state.cc:1889 +msgid "" +"Found a sound file that cannot be used by Ardour. Talk to the progammers." msgstr "" -#: libs/ardour/session_state.cc:1908 +#: libs/ardour/session_state.cc:1913 msgid "Could not create mix templates directory \"%1\" (%2)" msgstr "" -#: libs/ardour/session_state.cc:1922 +#: libs/ardour/session_state.cc:1927 msgid "Template \"%1\" already exists - new version not created" msgstr "" -#: libs/ardour/session_state.cc:1929 +#: libs/ardour/session_state.cc:1934 msgid "mix template not saved" msgstr "" -#: libs/ardour/session_state.cc:1989 +#: libs/ardour/session_state.cc:1994 msgid "cannot create session directory \"%1\"; ignored" msgstr "" -#: libs/ardour/session_state.cc:2002 +#: libs/ardour/session_state.cc:2007 msgid "cannot create sounds directory \"%1\"; ignored" msgstr "" -#: libs/ardour/session_state.cc:2013 +#: libs/ardour/session_state.cc:2018 msgid "cannot create dead sounds directory \"%1\"; ignored" msgstr "" -#: libs/ardour/session_state.cc:2024 +#: libs/ardour/session_state.cc:2029 msgid "cannot create peak file directory \"%1\"; ignored" msgstr "" -#: libs/ardour/session_state.cc:2163 libs/ardour/session_state.cc:2184 +#: libs/ardour/session_state.cc:2168 libs/ardour/session_state.cc:2189 msgid "Session: cannot create Playlist from XML description." msgstr "" -#: libs/ardour/session_state.cc:2223 +#: libs/ardour/session_state.cc:2228 msgid "Session: cannot create Named Selection from XML description." msgstr "" -#: libs/ardour/session_state.cc:2355 +#: libs/ardour/session_state.cc:2360 msgid "Unknown node \"%1\" found in Connections list from state file" msgstr "" -#: libs/ardour/session_state.cc:3195 +#: libs/ardour/session_state.cc:3197 msgid "cannot remove dead sound file %1 (%2)" msgstr "" -#: libs/ardour/session_time.cc:736 +#: libs/ardour/session_time.cc:375 msgid "Unknown JACK transport state %1 in sync callback" msgstr "" @@ -1754,43 +1692,43 @@ msgstr "" msgid "tempoize: error creating name for new audio file based on %1" msgstr "" -#: libs/ardour/session_timefx.cc:85 +#: libs/ardour/session_timefx.cc:88 msgid "tempoize: error creating new audio file %1 (%2)" msgstr "" -#: libs/ardour/session_timefx.cc:111 +#: libs/ardour/session_timefx.cc:114 msgid "tempoize: error reading data from %1" msgstr "" -#: libs/ardour/session_timefx.cc:124 libs/ardour/session_timefx.cc:136 +#: libs/ardour/session_timefx.cc:127 libs/ardour/session_timefx.cc:139 msgid "error writing tempo-adjusted data to %1" msgstr "" -#: libs/ardour/session_timefx.cc:142 +#: libs/ardour/session_timefx.cc:145 msgid "timefx code failure. please notify ardour-developers." msgstr "" -#: libs/ardour/session_transport.cc:116 +#: libs/ardour/session_transport.cc:117 msgid "Cannot loop - no loop range defined" msgstr "" -#: libs/ardour/session_transport.cc:478 +#: libs/ardour/session_transport.cc:479 msgid "" "Seamless looping cannot be supported while Ardour is using JACK transport.\n" "Recommend changing the configured options" msgstr "" -#: libs/ardour/session_transport.cc:754 +#: libs/ardour/session_transport.cc:755 msgid "" "Global varispeed cannot be supported while Ardour is connected to JACK " "transport control" msgstr "" -#: libs/ardour/session_transport.cc:954 +#: libs/ardour/session_transport.cc:955 msgid "please stop the transport before adjusting slave settings" msgstr "" -#: libs/ardour/session_transport.cc:990 +#: libs/ardour/session_transport.cc:991 msgid "No MTC port defined: MTC slaving is impossible." msgstr "" @@ -1878,209 +1816,185 @@ msgstr "" msgid "Big-endian (Mac)" msgstr "" -#: libs/ardour/sndfilesource.cc:75 -msgid "SndFileSource: cannot open file \"%1\" (%2)" +#: libs/ardour/sndfilesource.cc:146 +msgid "FileSource: cannot get host information for BWF header (%1)" msgstr "" -#: libs/ardour/sndfilesource.cc:80 +#: libs/ardour/sndfilesource.cc:168 +msgid "" +"cannot set broadcast info for audio file %1 (%2); dropping broadcast info " +"for this file" +msgstr "" + +#: libs/ardour/sndfilesource.cc:224 +msgid "SndFileSource: cannot open file \"%1\" for %2 (%3)" +msgstr "" + +#: libs/ardour/sndfilesource.cc:230 msgid "" "SndFileSource: file only contains %1 channels; %2 is invalid as a channel " "number" msgstr "" -#: libs/ardour/sndfilesource.cc:122 +#: libs/ardour/sndfilesource.cc:307 msgid "SndFileSource: could not seek to frame %1 within %2 (%3)" msgstr "" -#: libs/ardour/source.cc:161 -msgid "poll on peak request pipe failed (%1)" +#: libs/ardour/sndfilesource.cc:358 +#, fuzzy +msgid "programming error: %1 %2" +msgstr "ÏÛÉÂËÁ ÐÒÏÇÒÁÍÍÙ: " + +#: libs/ardour/sndfilesource.cc:458 +msgid "" +"cannot set broadcast info for audio file %1; Dropping broadcast info for " +"this file" msgstr "" -#: libs/ardour/source.cc:168 -msgid "Error on peak thread request pipe" +#: libs/ardour/sndfilesource.cc:500 +msgid "%1: cannot seek to %2" msgstr "" -#: libs/ardour/source.cc:201 -msgid "Error reading from peak request pipe" -msgstr "" - -#: libs/ardour/source.cc:238 libs/ardour/source.cc:243 -msgid "UI: cannot set O_NONBLOCK on peak request pipe (%1)" -msgstr "" - -#: libs/ardour/source.cc:248 -msgid "Source: could not create peak thread" -msgstr "" - -#: libs/ardour/source.cc:326 -msgid "cannot rename peakfile for %1 from %2 to %3 (%4)" -msgstr "" - -#: libs/ardour/source.cc:357 -msgid "Source: cannot stat peakfile \"%1\"" -msgstr "" - -#: libs/ardour/source.cc:444 -msgid "cannot read sample data for unscaled peak computation" -msgstr "" - -#: libs/ardour/source.cc:465 libs/ardour/source.cc:536 -#: libs/ardour/source.cc:780 libs/ardour/source.cc:881 -msgid "Source: cannot open peakpath \"%1\" (%2)" -msgstr "" - -#: libs/ardour/source.cc:637 -msgid "Source[%1]: peak read - cannot read %2 samples at offset %3" -msgstr "" - -#: libs/ardour/source.cc:789 -msgid "%1: could not write read raw data for peak computation (%2)" -msgstr "" - -#: libs/ardour/source.cc:814 -msgid "%1: could not write peak file data (%2)" -msgstr "" - -#: libs/ardour/state_manager.cc:46 +#: libs/ardour/state_manager.cc:47 msgid "cleared history" msgstr "" -#: libs/ardour/state_manager.cc:59 +#: libs/ardour/state_manager.cc:60 msgid "" "programming error: illegal state ID (%1) passed to StateManager::set_state() " "(range = 0-%2)" msgstr "" -#: libs/ardour/stateful.cc:100 +#: libs/ardour/stateful.cc:102 msgid "Error: could not write %1" msgstr "" -#: libs/ardour/stateful.cc:114 +#: libs/ardour/stateful.cc:116 msgid "Could not understand XML file %1" msgstr "" -#: libs/ardour/tempo.cc:66 +#: libs/ardour/tempo.cc:67 msgid "TempoSection XML node has no \"start\" property" msgstr "" -#: libs/ardour/tempo.cc:74 +#: libs/ardour/tempo.cc:75 msgid "TempoSection XML node has an illegal \"start\" value" msgstr "" -#: libs/ardour/tempo.cc:81 +#: libs/ardour/tempo.cc:82 msgid "TempoSection XML node has no \"beats-per-minute\" property" msgstr "" -#: libs/ardour/tempo.cc:86 +#: libs/ardour/tempo.cc:87 msgid "TempoSection XML node has an illegal \"beats_per_minute\" value" msgstr "" -#: libs/ardour/tempo.cc:91 +#: libs/ardour/tempo.cc:92 msgid "TempoSection XML node has no \"movable\" property" msgstr "" -#: libs/ardour/tempo.cc:130 +#: libs/ardour/tempo.cc:131 msgid "MeterSection XML node has no \"start\" property" msgstr "" -#: libs/ardour/tempo.cc:138 +#: libs/ardour/tempo.cc:139 msgid "MeterSection XML node has an illegal \"start\" value" msgstr "" -#: libs/ardour/tempo.cc:145 +#: libs/ardour/tempo.cc:146 msgid "MeterSection XML node has no \"beats-per-bar\" property" msgstr "" -#: libs/ardour/tempo.cc:150 +#: libs/ardour/tempo.cc:151 msgid "MeterSection XML node has an illegal \"beats-per-bar\" value" msgstr "" -#: libs/ardour/tempo.cc:155 +#: libs/ardour/tempo.cc:156 msgid "MeterSection XML node has no \"note-type\" property" msgstr "" -#: libs/ardour/tempo.cc:160 +#: libs/ardour/tempo.cc:161 msgid "MeterSection XML node has an illegal \"note-type\" value" msgstr "" -#: libs/ardour/tempo.cc:165 +#: libs/ardour/tempo.cc:166 msgid "MeterSection XML node has no \"movable\" property" msgstr "" -#: libs/ardour/tempo.cc:258 +#: libs/ardour/tempo.cc:259 msgid "move metric" msgstr "" -#: libs/ardour/tempo.cc:329 +#: libs/ardour/tempo.cc:330 msgid "metric removed" msgstr "" -#: libs/ardour/tempo.cc:372 +#: libs/ardour/tempo.cc:373 msgid "add tempo" msgstr "" -#: libs/ardour/tempo.cc:401 +#: libs/ardour/tempo.cc:402 msgid "replace tempo" msgstr "" -#: libs/ardour/tempo.cc:434 +#: libs/ardour/tempo.cc:435 msgid "add meter" msgstr "" -#: libs/ardour/tempo.cc:462 +#: libs/ardour/tempo.cc:463 msgid "replaced meter" msgstr "" -#: libs/ardour/tempo.cc:482 libs/ardour/tempo.cc:498 +#: libs/ardour/tempo.cc:483 libs/ardour/tempo.cc:499 msgid "programming error: no tempo section in tempo map!" msgstr "" -#: libs/ardour/tempo.cc:537 +#: libs/ardour/tempo.cc:538 msgid "programming error: unhandled MetricSection type" msgstr "" -#: libs/ardour/tempo.cc:1225 libs/ardour/tempo.cc:1237 +#: libs/ardour/tempo.cc:1226 libs/ardour/tempo.cc:1238 msgid "Tempo map: could not set new state, restoring old one." msgstr "" -#: libs/ardour/tempo.cc:1261 +#: libs/ardour/tempo.cc:1262 msgid "load XML data" msgstr "" -#: libs/ardour/utils.cc:242 +#: libs/ardour/utils.cc:246 msgid "illegal or badly-formed string used for path (%1)" msgstr "" -#: libs/ardour/utils.cc:247 +#: libs/ardour/utils.cc:251 msgid "path (%1) is ambiguous" msgstr "" -#: libs/ardour/vst_plugin.cc:186 +#: libs/ardour/vst_plugin.cc:187 msgid "cannot create VST chunk directory: %1" msgstr "" -#: libs/ardour/vst_plugin.cc:194 +#: libs/ardour/vst_plugin.cc:195 msgid "cannot check VST chunk directory: %1" msgstr "" -#: libs/ardour/vst_plugin.cc:201 +#: libs/ardour/vst_plugin.cc:202 msgid "%1 exists but is not a directory" msgstr "" -#: libs/ardour/vst_plugin.cc:239 +#: libs/ardour/vst_plugin.cc:240 msgid "Bad node sent to VSTPlugin::set_state" msgstr "" -#: libs/ardour/vst_plugin.cc:342 libs/ardour/vst_plugin.cc:353 +#: libs/ardour/vst_plugin.cc:343 libs/ardour/vst_plugin.cc:354 msgid "no support for presets using chunks at this time" msgstr "" -#: libs/ardour/coreaudio_source.cc:93 +#: libs/ardour/coreaudio_source.cc:99 msgid "" "CoreAudioSource: file only contains %1 channels; %2 is invalid as a channel " "number" msgstr "" -#: libs/ardour/coreaudio_source.cc:157 +#: libs/ardour/coreaudio_source.cc:164 msgid "CoreAudioSource: could not seek to frame %1 within %2 (%3)" msgstr "" diff --git a/libs/ardour/recent_sessions.cc b/libs/ardour/recent_sessions.cc index efbdb807f7..954162dd18 100644 --- a/libs/ardour/recent_sessions.cc +++ b/libs/ardour/recent_sessions.cc @@ -27,9 +27,9 @@ #include #include "i18n.h" - using namespace std; using namespace ARDOUR; +using namespace PBD; int ARDOUR::read_recent_sessions (RecentSessions& rs) diff --git a/libs/ardour/redirect.cc b/libs/ardour/redirect.cc index 746d2790e2..33fec5088f 100644 --- a/libs/ardour/redirect.cc +++ b/libs/ardour/redirect.cc @@ -39,7 +39,7 @@ using namespace std; using namespace ARDOUR; -//using namespace sigc; +using namespace PBD; const string Redirect::state_node_name = "Redirect"; sigc::signal Redirect::RedirectCreated; diff --git a/libs/ardour/region.cc b/libs/ardour/region.cc index 08df23146b..8c27a3bebc 100644 --- a/libs/ardour/region.cc +++ b/libs/ardour/region.cc @@ -37,6 +37,7 @@ using namespace std; using namespace ARDOUR; +using namespace PBD; Change Region::FadeChanged = ARDOUR::new_change (); Change Region::SyncOffsetChanged = ARDOUR::new_change (); diff --git a/libs/ardour/reverse.cc b/libs/ardour/reverse.cc index 335dacad6e..13dd531bac 100644 --- a/libs/ardour/reverse.cc +++ b/libs/ardour/reverse.cc @@ -24,7 +24,7 @@ #include #include -#include +#include #include #include diff --git a/libs/ardour/route.cc b/libs/ardour/route.cc index 93fbb85e49..3f51b2f140 100644 --- a/libs/ardour/route.cc +++ b/libs/ardour/route.cc @@ -44,7 +44,7 @@ using namespace std; using namespace ARDOUR; -//using namespace sigc; +using namespace PBD; uint32_t Route::order_key_cnt = 0; @@ -2002,7 +2002,7 @@ Route::set_active (bool yn) } void -Route::transport_stopped (bool abort_ignored, bool did_locate, bool can_flush_redirects) +Route::handle_transport_stopped (bool abort_ignored, bool did_locate, bool can_flush_redirects) { jack_nframes_t now = _session.transport_frame(); diff --git a/libs/ardour/route_group.cc b/libs/ardour/route_group.cc index ae807e66e1..5730623742 100644 --- a/libs/ardour/route_group.cc +++ b/libs/ardour/route_group.cc @@ -29,7 +29,7 @@ #include #include -#include +#include #include using namespace ARDOUR; diff --git a/libs/ardour/send.cc b/libs/ardour/send.cc index 50fdd4a96a..2b72fb9bdb 100644 --- a/libs/ardour/send.cc +++ b/libs/ardour/send.cc @@ -29,6 +29,7 @@ #include "i18n.h" using namespace ARDOUR; +using namespace PBD; Send::Send (Session& s, Placement p) : Redirect (s, s.next_send_name(), p) diff --git a/libs/ardour/session.cc b/libs/ardour/session.cc index d729b5d7f7..864e6178d2 100644 --- a/libs/ardour/session.cc +++ b/libs/ardour/session.cc @@ -32,7 +32,8 @@ #include #include -#include +#include +#include #include #include @@ -43,14 +44,12 @@ #include #include #include -#include +#include #include #include #include -#include -#include +#include #include -#include #include #include #include @@ -74,7 +73,7 @@ using namespace std; using namespace ARDOUR; -//using namespace sigc; +using namespace PBD; const char* Session::_template_suffix = X_(".template"); const char* Session::_statefile_suffix = X_(".ardour"); @@ -90,6 +89,7 @@ Session::mix_buffers_with_gain_t Session::mix_buffers_with_gain = 0; Session::mix_buffers_no_gain_t Session::mix_buffers_no_gain = 0; sigc::signal Session::AskAboutPendingState; +sigc::signal Session::SMPTEOffsetChanged; int Session::find_session (string str, string& path, string& snapshot, bool& isnew) @@ -455,10 +455,10 @@ Session::~Session () } #ifdef TRACK_DESTRUCTION - cerr << "delete diskstreams\n"; + cerr << "delete audio_diskstreams\n"; #endif /* TRACK_DESTRUCTION */ - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ) { - DiskStreamList::iterator tmp; + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ) { + AudioDiskstreamList::iterator tmp; tmp = i; ++tmp; @@ -469,10 +469,10 @@ Session::~Session () } #ifdef TRACK_DESTRUCTION - cerr << "delete sources\n"; + cerr << "delete audio sources\n"; #endif /* TRACK_DESTRUCTION */ - for (SourceList::iterator i = sources.begin(); i != sources.end(); ) { - SourceList::iterator tmp; + for (AudioSourceList::iterator i = audio_sources.begin(); i != audio_sources.end(); ) { + AudioSourceList::iterator tmp; tmp = i; ++tmp; @@ -881,7 +881,7 @@ Session::playlist_length_changed (Playlist* pl) } void -Session::diskstream_playlist_changed (DiskStream* dstream) +Session::diskstream_playlist_changed (AudioDiskstream* dstream) { Playlist *playlist; @@ -961,7 +961,7 @@ Session::set_auto_input (bool yn) The rarity and short potential lock duration makes this "OK" */ Glib::RWLock::ReaderLock dsm (diskstream_lock); - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if ((*i)->record_enabled ()) { //cerr << "switching to input = " << !auto_input << __FILE__ << __LINE__ << endl << endl; (*i)->monitor_input (!auto_input); @@ -979,7 +979,7 @@ Session::reset_input_monitor_state () { if (transport_rolling()) { Glib::RWLock::ReaderLock dsm (diskstream_lock); - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if ((*i)->record_enabled ()) { //cerr << "switching to input = " << !auto_input << __FILE__ << __LINE__ << endl << endl; (*i)->monitor_input (Config->get_use_hardware_monitoring() && !auto_input); @@ -987,7 +987,7 @@ Session::reset_input_monitor_state () } } else { Glib::RWLock::ReaderLock dsm (diskstream_lock); - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if ((*i)->record_enabled ()) { //cerr << "switching to input = " << !auto_input << __FILE__ << __LINE__ << endl << endl; (*i)->monitor_input (Config->get_use_hardware_monitoring()); @@ -1068,7 +1068,7 @@ Session::auto_loop_changed (Location* location) } else if (seamless_loop && !loop_changing) { - // schedule a locate-roll to refill the diskstreams at the + // schedule a locate-roll to refill the audio_diskstreams at the // previous loop end loop_changing = true; @@ -1265,7 +1265,7 @@ Session::enable_record () */ Glib::RWLock::ReaderLock dsm (diskstream_lock); - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if ((*i)->record_enabled ()) { (*i)->monitor_input (true); } @@ -1300,7 +1300,7 @@ Session::disable_record (bool rt_context, bool force) */ Glib::RWLock::ReaderLock dsm (diskstream_lock); - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if ((*i)->record_enabled ()) { (*i)->monitor_input (false); } @@ -1327,7 +1327,7 @@ Session::step_back_from_record () */ Glib::RWLock::ReaderLock dsm (diskstream_lock); - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if (auto_input && (*i)->record_enabled ()) { //cerr << "switching from input" << __FILE__ << __LINE__ << endl << endl; (*i)->monitor_input (false); @@ -1432,6 +1432,9 @@ Session::set_frame_rate (jack_nframes_t frames_per_second) Route::set_automation_interval ((jack_nframes_t) ceil ((double) frames_per_second * 0.25)); + // XXX we need some equivalent to this, somehow + // DestructiveFileSource::setup_standard_crossfades (frames_per_second); + set_dirty(); /* XXX need to reset/reinstantiate all LADSPA plugins */ @@ -1493,7 +1496,7 @@ Session::set_block_size (jack_nframes_t nframes) (*i)->set_block_size (nframes); } - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { (*i)->set_block_size (nframes); } @@ -1900,14 +1903,14 @@ Session::add_route (Route* route) } void -Session::add_diskstream (DiskStream* dstream) +Session::add_diskstream (AudioDiskstream* dstream) { /* need to do this in case we're rolling at the time, to prevent false underruns */ dstream->do_refill(0, 0, 0); { Glib::RWLock::WriterLock lm (diskstream_lock); - diskstreams.push_back (dstream); + audio_diskstreams.push_back (dstream); } /* take a reference to the diskstream, preventing it from @@ -1927,7 +1930,7 @@ Session::add_diskstream (DiskStream* dstream) set_dirty(); save_state (_current_snapshot_name); - DiskStreamAdded (dstream); /* EMIT SIGNAL */ + AudioDiskstreamAdded (dstream); /* EMIT SIGNAL */ } void @@ -1961,18 +1964,24 @@ Session::remove_route (Route& route) update_route_solo_state (); } - { - Glib::RWLock::WriterLock lm (diskstream_lock); + AudioTrack* at; + AudioDiskstream* ds = 0; + + if ((at = dynamic_cast(&route)) != 0) { + ds = &at->disk_stream(); + } + + if (ds) { - AudioTrack* at; - - if ((at = dynamic_cast(&route)) != 0) { - diskstreams.remove (&at->disk_stream()); - at->disk_stream().unref (); + { + Glib::RWLock::WriterLock lm (diskstream_lock); + audio_diskstreams.remove (ds); } - find_current_end (); + ds->unref (); } + + find_current_end (); update_latency_compensation (false, false); set_dirty(); @@ -2255,7 +2264,7 @@ Session::get_maximum_extent () const ensure atomicity. */ - for (DiskStreamList::const_iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::const_iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { Playlist* pl = (*i)->playlist(); if ((me = pl->get_maximum_extent()) > max) { max = me; @@ -2265,12 +2274,12 @@ Session::get_maximum_extent () const return max; } -DiskStream * +AudioDiskstream * Session::diskstream_by_name (string name) { Glib::RWLock::ReaderLock lm (diskstream_lock); - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if ((*i)->name() == name) { return* i; } @@ -2279,12 +2288,12 @@ Session::diskstream_by_name (string name) return 0; } -DiskStream * +AudioDiskstream * Session::diskstream_by_id (id_t id) { Glib::RWLock::ReaderLock lm (diskstream_lock); - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if ((*i)->id() == id) { return *i; } @@ -2583,7 +2592,10 @@ Session::destroy_region (Region* region) for (vector::iterator i = srcs.begin(); i != srcs.end(); ++i) { if ((*i)->use_cnt() == 0) { - (*i)->mark_for_remove (); + AudioFileSource* afs = dynamic_cast(*i); + if (afs) { + (afs)->mark_for_remove (); + } delete *i; } } @@ -2607,7 +2619,7 @@ Session::remove_last_capture () Glib::RWLock::ReaderLock lm (diskstream_lock); - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { list& l = (*i)->last_capture_regions(); if (!l.empty()) { @@ -2630,15 +2642,15 @@ Session::remove_region_from_region_list (Region& r) /* Source Management */ void -Session::add_source (Source* source) +Session::add_audio_source (AudioSource* source) { - pair entry; + pair entry; { - Glib::Mutex::Lock lm (source_lock); + Glib::Mutex::Lock lm (audio_source_lock); entry.first = source->id(); entry.second = source; - sources.insert (entry); + audio_sources.insert (entry); } source->GoingAway.connect (mem_fun (this, &Session::remove_source)); @@ -2650,13 +2662,13 @@ Session::add_source (Source* source) void Session::remove_source (Source* source) { - SourceList::iterator i; + AudioSourceList::iterator i; { - Glib::Mutex::Lock lm (source_lock); + Glib::Mutex::Lock lm (audio_source_lock); - if ((i = sources.find (source->id())) != sources.end()) { - sources.erase (i); + if ((i = audio_sources.find (source->id())) != audio_sources.end()) { + audio_sources.erase (i); } } @@ -2675,15 +2687,21 @@ Session::remove_source (Source* source) Source * Session::get_source (ARDOUR::id_t id) { - Glib::Mutex::Lock lm (source_lock); - SourceList::iterator i; + Glib::Mutex::Lock lm (audio_source_lock); + AudioSourceList::iterator i; Source* source = 0; - if ((i = sources.find (id)) != sources.end()) { + if ((i = audio_sources.find (id)) != audio_sources.end()) { source = (*i).second; } - return source; + if (source) { + return source; + } + + /* XXX search MIDI or other searches here */ + + return 0; } string @@ -2890,17 +2908,23 @@ Session::audio_path_from_name (string name, uint32_t nchan, uint32_t chan, bool return spath; } -FileSource * -Session::create_file_source (DiskStream& ds, int32_t chan, bool destructive) +AudioFileSource * +Session::create_audio_source_for_session (AudioDiskstream& ds, uint32_t chan, bool destructive) { string spath = audio_path_from_name (ds.name(), ds.n_channels(), chan, destructive); /* this might throw failed_constructor(), which is OK */ - + if (destructive) { - return new DestructiveFileSource (spath, frame_rate(), false, Config->get_native_file_data_format()); + return new DestructiveFileSource (spath, + Config->get_native_file_data_format(), + Config->get_native_file_header_format(), + frame_rate()); } else { - return new FileSource (spath, frame_rate(), false, Config->get_native_file_data_format()); + return new SndFileSource (spath, + Config->get_native_file_data_format(), + Config->get_native_file_header_format(), + frame_rate()); } } @@ -3082,7 +3106,7 @@ Session::remove_empty_sounds () for (vector::iterator i = possible_audiofiles->begin(); i != possible_audiofiles->end(); ++i) { - if (FileSource::is_empty (*(*i))) { + if (AudioFileSource::is_empty (*(*i))) { unlink ((*i)->c_str()); @@ -3140,12 +3164,12 @@ Session::set_all_mute (bool yn) } uint32_t -Session::n_diskstreams () const +Session::n_audio_diskstreams () const { Glib::RWLock::ReaderLock lm (diskstream_lock); uint32_t n = 0; - for (DiskStreamList::const_iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::const_iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if (!(*i)->hidden()) { n++; } @@ -3154,10 +3178,10 @@ Session::n_diskstreams () const } void -Session::foreach_diskstream (void (DiskStream::*func)(void)) +Session::foreach_audio_diskstream (void (AudioDiskstream::*func)(void)) { Glib::RWLock::ReaderLock lm (diskstream_lock); - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if (!(*i)->hidden()) { ((*i)->*func)(); } @@ -3184,7 +3208,7 @@ Session::graph_reordered () reflect any changes in latencies within the graph. */ - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { (*i)->set_capture_offset (); } } @@ -3467,7 +3491,7 @@ Session::reset_native_file_format () //RWLockMonitor lm1 (route_lock, true, __LINE__, __FILE__); Glib::RWLock::ReaderLock lm2 (diskstream_lock); - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { (*i)->reset_write_sources (false); } } @@ -3487,7 +3511,7 @@ Session::route_name_unique (string n) const } int -Session::remove_file_source (FileSource& fs) +Session::cleanup_audio_file_source (AudioFileSource& fs) { return fs.move_to_trash (dead_sound_dir_name); } @@ -3562,12 +3586,12 @@ Session::freeze (InterThreadInfo& itt) } int -Session::write_one_track (AudioTrack& track, jack_nframes_t start, jack_nframes_t len, bool overwrite, vector& srcs, - InterThreadInfo& itt) +Session::write_one_audio_track (AudioTrack& track, jack_nframes_t start, jack_nframes_t len, + bool overwrite, vector& srcs, InterThreadInfo& itt) { int ret = -1; Playlist* playlist; - FileSource* fsource; + AudioFileSource* fsource; uint32_t x; char buf[PATH_MAX+1]; string dir; @@ -3577,7 +3601,9 @@ Session::write_one_track (AudioTrack& track, jack_nframes_t start, jack_nframes_ jack_nframes_t to_do; vector buffers; char * workbuf = 0; - const jack_nframes_t chunk_size = (256 * 1024)/4; + + // any bigger than this seems to cause stack overflows in called functions + const jack_nframes_t chunk_size = (128 * 1024)/4; g_atomic_int_set (&processing_prohibited, 1); @@ -3612,7 +3638,11 @@ Session::write_one_track (AudioTrack& track, jack_nframes_t start, jack_nframes_ } try { - fsource = new FileSource (buf, frame_rate(), false, Config->get_native_file_data_format()); + fsource = new SndFileSource (buf, + Config->get_native_file_data_format(), + Config->get_native_file_header_format(), + frame_rate()); + } catch (failed_constructor& err) { @@ -3651,9 +3681,13 @@ Session::write_one_track (AudioTrack& track, jack_nframes_t start, jack_nframes_ } uint32_t n = 0; - for (vector::iterator src=srcs.begin(); src != srcs.end(); ++src, ++n) { - if ((*src)->write (buffers[n], this_chunk, workbuf) != this_chunk) { - goto out; + for (vector::iterator src=srcs.begin(); src != srcs.end(); ++src, ++n) { + AudioFileSource* afs = dynamic_cast(*src); + + if (afs) { + if (afs->write (buffers[n], this_chunk, workbuf) != this_chunk) { + goto out; + } } } @@ -3671,14 +3705,20 @@ Session::write_one_track (AudioTrack& track, jack_nframes_t start, jack_nframes_ time (&now); xnow = localtime (&now); - for (vector::iterator src=srcs.begin(); src != srcs.end(); ++src) { - dynamic_cast((*src))->update_header (position, *xnow, now); + for (vector::iterator src=srcs.begin(); src != srcs.end(); ++src) { + AudioFileSource* afs = dynamic_cast(*src); + if (afs) { + afs->update_header (position, *xnow, now); + } } /* build peakfile for new source */ - for (vector::iterator src=srcs.begin(); src != srcs.end(); ++src) { - dynamic_cast(*src)->build_peaks (); + for (vector::iterator src=srcs.begin(); src != srcs.end(); ++src) { + AudioFileSource* afs = dynamic_cast(*src); + if (afs) { + afs->build_peaks (); + } } ret = 0; @@ -3686,8 +3726,11 @@ Session::write_one_track (AudioTrack& track, jack_nframes_t start, jack_nframes_ out: if (ret) { - for (vector::iterator src=srcs.begin(); src != srcs.end(); ++src) { - dynamic_cast(*src)->mark_for_remove (); + for (vector::iterator src=srcs.begin(); src != srcs.end(); ++src) { + AudioFileSource* afs = dynamic_cast(*src); + if (afs) { + afs->mark_for_remove (); + } delete *src; } } diff --git a/libs/ardour/session_butler.cc b/libs/ardour/session_butler.cc index ebe0d64548..4613bfccf9 100644 --- a/libs/ardour/session_butler.cc +++ b/libs/ardour/session_butler.cc @@ -34,7 +34,7 @@ #include #include #include -#include +#include #include #include @@ -42,7 +42,7 @@ using namespace std; using namespace ARDOUR; -//using namespace sigc; +using namespace PBD; static float _read_data_rate; static float _write_data_rate; @@ -168,10 +168,10 @@ Session::butler_thread_work () struct timeval begin, end; struct pollfd pfd[1]; bool disk_work_outstanding = false; - DiskStreamList::iterator i; + AudioDiskstreamList::iterator i; - butler_mixdown_buffer = new Sample[DiskStream::disk_io_frames()]; - butler_gain_buffer = new gain_t[DiskStream::disk_io_frames()]; + butler_mixdown_buffer = new Sample[AudioDiskstream::disk_io_frames()]; + butler_gain_buffer = new gain_t[AudioDiskstream::disk_io_frames()]; // this buffer is used for temp conversion purposes in filesources char * conv_buffer = conversion_buffer(ButlerContext); @@ -241,7 +241,7 @@ Session::butler_thread_work () } } - for (i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { // cerr << "BEFORE " << (*i)->name() << ": pb = " << (*i)->playback_buffer_load() << " cp = " << (*i)->capture_buffer_load() << endl; } @@ -257,7 +257,7 @@ Session::butler_thread_work () Glib::RWLock::ReaderLock dsm (diskstream_lock); - for (i = diskstreams.begin(); !transport_work_requested() && butler_should_run && i != diskstreams.end(); ++i) { + for (i = audio_diskstreams.begin(); !transport_work_requested() && butler_should_run && i != audio_diskstreams.end(); ++i) { // cerr << "rah fondr " << (*i)->io()->name () << endl; @@ -278,7 +278,7 @@ Session::butler_thread_work () } - if (i != diskstreams.end()) { + if (i != audio_diskstreams.end()) { /* we didn't get to all the streams */ disk_work_outstanding = true; } @@ -300,7 +300,7 @@ Session::butler_thread_work () compute_io = true; gettimeofday (&begin, 0); - for (i = diskstreams.begin(); !transport_work_requested() && butler_should_run && i != diskstreams.end(); ++i) { + for (i = audio_diskstreams.begin(); !transport_work_requested() && butler_should_run && i != audio_diskstreams.end(); ++i) { // cerr << "write behind for " << (*i)->name () << endl; @@ -330,7 +330,7 @@ Session::butler_thread_work () request_stop (); } - if (i != diskstreams.end()) { + if (i != audio_diskstreams.end()) { /* we didn't get to all the streams */ disk_work_outstanding = true; } @@ -357,7 +357,7 @@ Session::butler_thread_work () Glib::Mutex::Lock lm (butler_request_lock); if (butler_should_run && (disk_work_outstanding || transport_work_requested())) { -// for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { +// for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { // cerr << "AFTER " << (*i)->name() << ": pb = " << (*i)->playback_buffer_load() << " cp = " << (*i)->capture_buffer_load() << endl; // } @@ -375,7 +375,7 @@ Session::butler_thread_work () void -Session::request_overwrite_buffer (DiskStream* stream) +Session::request_overwrite_buffer (AudioDiskstream* stream) { Event *ev = new Event (Event::Overwrite, Event::Add, Event::Immediate, 0, 0, 0.0); ev->set_ptr (stream); @@ -383,7 +383,7 @@ Session::request_overwrite_buffer (DiskStream* stream) } void -Session::overwrite_some_buffers (DiskStream* ds) +Session::overwrite_some_buffers (AudioDiskstream* ds) { /* executed by the audio thread */ @@ -398,7 +398,7 @@ Session::overwrite_some_buffers (DiskStream* ds) } else { Glib::RWLock::ReaderLock dm (diskstream_lock); - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { (*i)->set_pending_overwrite (true); } } diff --git a/libs/ardour/session_click.cc b/libs/ardour/session_click.cc index 4503287da1..1d14fd4a80 100644 --- a/libs/ardour/session_click.cc +++ b/libs/ardour/session_click.cc @@ -32,6 +32,7 @@ using namespace std; using namespace ARDOUR; +using namespace PBD; Pool Session::Click::pool ("click", sizeof (Click), 128); diff --git a/libs/ardour/session_control.cc b/libs/ardour/session_control.cc index 8e0a3e99a1..afecc146b7 100644 --- a/libs/ardour/session_control.cc +++ b/libs/ardour/session_control.cc @@ -1,8 +1,8 @@ #include -#include -#include -#include +#include +#include +#include using namespace ARDOUR; diff --git a/libs/ardour/session_events.cc b/libs/ardour/session_events.cc index d48bbe3053..e918e0383f 100644 --- a/libs/ardour/session_events.cc +++ b/libs/ardour/session_events.cc @@ -28,12 +28,12 @@ #include #include -#include +#include #include "i18n.h" using namespace ARDOUR; -//using namespace sigc; +using namespace PBD; MultiAllocSingleReleasePool Session::Event::pool ("event", sizeof (Session::Event), 512); @@ -389,11 +389,11 @@ Session::process_event (Event* ev) break; case Event::Overwrite: - overwrite_some_buffers (static_cast(ev->ptr)); + overwrite_some_buffers (static_cast(ev->ptr)); break; case Event::SetDiskstreamSpeed: - set_diskstream_speed (static_cast (ev->ptr), ev->speed); + set_diskstream_speed (static_cast (ev->ptr), ev->speed); break; case Event::SetSlaveSource: diff --git a/libs/ardour/session_export.cc b/libs/ardour/session_export.cc index 183b6df237..ddced9cc5f 100644 --- a/libs/ardour/session_export.cc +++ b/libs/ardour/session_export.cc @@ -47,14 +47,14 @@ #include #include #include -#include +#include #include #include "i18n.h" using namespace std; using namespace ARDOUR; -//using namespace sigc; +using namespace PBD; static int convert_spec_to_info (AudioExportSpecification& spec, SF_INFO& sfinfo) @@ -495,7 +495,7 @@ Session::prepare_to_export (AudioExportSpecification& spec) { Glib::RWLock::ReaderLock lm (diskstream_lock); - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if ((*i)-> seek (spec.start_frame, true)) { error << string_compose (_("%1: cannot seek to %2 for export"), (*i)->name(), spec.start_frame) diff --git a/libs/ardour/session_feedback.cc b/libs/ardour/session_feedback.cc index ea8580b3c2..1fd8389e11 100644 --- a/libs/ardour/session_feedback.cc +++ b/libs/ardour/session_feedback.cc @@ -31,15 +31,14 @@ #include -#include #include #include #include #include #include -#include -#include +#include +#include #include "i18n.h" diff --git a/libs/ardour/session_midi.cc b/libs/ardour/session_midi.cc index d8382c69a4..60bd95464f 100644 --- a/libs/ardour/session_midi.cc +++ b/libs/ardour/session_midi.cc @@ -37,7 +37,7 @@ #include #include #include -#include +#include #include #include @@ -45,7 +45,7 @@ using namespace std; using namespace ARDOUR; -//using namespace sigc; +using namespace PBD; using namespace MIDI; MachineControl::CommandSignature MMC_CommandSignature; @@ -724,7 +724,7 @@ Session::mmc_locate (MIDI::MachineControl &mmc, const MIDI::byte* mmc_tc) } jack_nframes_t target_frame; - SMPTE_Time smpte; + SMPTE::Time smpte; smpte.hours = mmc_tc[0] & 0xf; smpte.minutes = mmc_tc[1]; @@ -858,7 +858,7 @@ Session::send_full_time_code () { MIDI::byte msg[10]; - SMPTE_Time smpte; + SMPTE::Time smpte; if (_mtc_port == 0 || !send_mtc) { return 0; @@ -884,7 +884,7 @@ Session::send_full_time_code () outbound_mtc_smpte_frame = _transport_frame; if (((mtc_smpte_bits >> 5) != MIDI::MTC_25_FPS) && (transmitting_smpte_time.frames % 2)) { // start MTC quarter frame transmission on an even frame - smpte_increment( transmitting_smpte_time ); + SMPTE::increment( transmitting_smpte_time ); outbound_mtc_smpte_frame += (jack_nframes_t) _frames_per_smpte_frame; } } @@ -985,8 +985,8 @@ Session::send_midi_time_code () // Wrap quarter frame counter next_quarter_frame_to_send = 0; // Increment smpte time twice - smpte_increment( transmitting_smpte_time ); - smpte_increment( transmitting_smpte_time ); + SMPTE::increment( transmitting_smpte_time ); + SMPTE::increment( transmitting_smpte_time ); // Re-calculate timing of first quarter frame smpte_to_sample( transmitting_smpte_time, outbound_mtc_smpte_frame, true /* use_offset */, false ); // Compensate for audio latency @@ -1024,7 +1024,7 @@ Session::deliver_mmc (MIDI::MachineControl::Command cmd, jack_nframes_t where) { using namespace MIDI; int nbytes = 4; - SMPTE_Time smpte; + SMPTE::Time smpte; if (_mmc_port == 0 || !send_mmc) { return; diff --git a/libs/ardour/session_process.cc b/libs/ardour/session_process.cc index 2f098a384f..ad4e9a64bb 100644 --- a/libs/ardour/session_process.cc +++ b/libs/ardour/session_process.cc @@ -30,7 +30,7 @@ #include #include #include -#include +#include #include #include #include @@ -40,7 +40,7 @@ #include "i18n.h" using namespace ARDOUR; -//using namespace sigc; +using namespace PBD; using namespace std; void @@ -64,7 +64,7 @@ Session::process (jack_nframes_t nframes) void Session::prepare_diskstreams () { - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { (*i)->prepare (); } } @@ -136,12 +136,12 @@ Session::process_routes (jack_nframes_t nframes, jack_nframes_t offset) if ((ret = (*i)->roll (nframes, _transport_frame, _transport_frame + nframes, offset, declick, record_active, rec_monitors)) < 0) { - /* we have to do this here. Route::roll() for an AudioTrack will have called DiskStream::process(), - and the DS will expect DiskStream::commit() to be called. but we're aborting from that + /* we have to do this here. Route::roll() for an AudioTrack will have called AudioDiskstream::process(), + and the DS will expect AudioDiskstream::commit() to be called. but we're aborting from that call path, so make sure we release any outstanding locks here before we return failure. */ - for (DiskStreamList::iterator ids = diskstreams.begin(); ids != diskstreams.end(); ++ids) { + for (AudioDiskstreamList::iterator ids = audio_diskstreams.begin(); ids != audio_diskstreams.end(); ++ids) { (*ids)->recover (); } @@ -175,12 +175,12 @@ Session::silent_process_routes (jack_nframes_t nframes, jack_nframes_t offset) if ((ret = (*i)->silent_roll (nframes, _transport_frame, _transport_frame + nframes, offset, record_active, rec_monitors)) < 0) { - /* we have to do this here. Route::roll() for an AudioTrack will have called DiskStream::process(), - and the DS will expect DiskStream::commit() to be called. but we're aborting from that + /* we have to do this here. Route::roll() for an AudioTrack will have called AudioDiskstream::process(), + and the DS will expect AudioDiskstream::commit() to be called. but we're aborting from that call path, so make sure we release any outstanding locks here before we return failure. */ - for (DiskStreamList::iterator ids = diskstreams.begin(); ids != diskstreams.end(); ++ids) { + for (AudioDiskstreamList::iterator ids = audio_diskstreams.begin(); ids != audio_diskstreams.end(); ++ids) { (*ids)->recover (); } @@ -199,7 +199,7 @@ Session::commit_diskstreams (jack_nframes_t nframes, bool &needs_butler) float pworst = 1.0f; float cworst = 1.0f; - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if ((*i)->hidden()) { continue; @@ -566,7 +566,7 @@ Session::follow_slave (jack_nframes_t nframes, jack_nframes_t offset) bool ok = true; jack_nframes_t frame_delta = slave_transport_frame - _transport_frame; - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if (!(*i)->can_internal_playback_seek (frame_delta)) { ok = false; break; @@ -574,7 +574,7 @@ Session::follow_slave (jack_nframes_t nframes, jack_nframes_t offset) } if (ok) { - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { (*i)->internal_playback_seek (frame_delta); } _transport_frame += frame_delta; diff --git a/libs/ardour/session_state.cc b/libs/ardour/session_state.cc index 5ef717de8a..92a21ea794 100644 --- a/libs/ardour/session_state.cc +++ b/libs/ardour/session_state.cc @@ -58,13 +58,11 @@ #include #include #include -#include +#include #include #include -#include -#include +#include #include -#include #include #include #include @@ -89,6 +87,7 @@ using namespace std; using namespace ARDOUR; +using namespace PBD; void Session::first_stage_init (string fullpath, string snapshot_name) @@ -196,12 +195,13 @@ Session::first_stage_init (string fullpath, string snapshot_name) destructive_index = 0; /* allocate conversion buffers */ - _conversion_buffers[ButlerContext] = new char[DiskStream::disk_io_frames() * 4]; - _conversion_buffers[TransportContext] = new char[DiskStream::disk_io_frames() * 4]; + _conversion_buffers[ButlerContext] = new char[AudioDiskstream::disk_io_frames() * 4]; + _conversion_buffers[TransportContext] = new char[AudioDiskstream::disk_io_frames() * 4]; /* default short fade = 15ms */ Crossfade::set_short_xfade_length ((jack_nframes_t) floor ((15.0 * frame_rate()) / 1000.0)); + DestructiveFileSource::setup_standard_crossfades (frame_rate()); last_mmc_step.tv_sec = 0; last_mmc_step.tv_usec = 0; @@ -267,10 +267,10 @@ Session::first_stage_init (string fullpath, string snapshot_name) /* These are all static "per-class" signals */ Region::CheckNewRegion.connect (mem_fun (*this, &Session::add_region)); - Source::SourceCreated.connect (mem_fun (*this, &Session::add_source)); + AudioSource::AudioSourceCreated.connect (mem_fun (*this, &Session::add_audio_source)); Playlist::PlaylistCreated.connect (mem_fun (*this, &Session::add_playlist)); Redirect::RedirectCreated.connect (mem_fun (*this, &Session::add_redirect)); - DiskStream::DiskStreamCreated.connect (mem_fun (*this, &Session::add_diskstream)); + AudioDiskstream::AudioDiskstreamCreated.connect (mem_fun (*this, &Session::add_diskstream)); NamedSelection::NamedSelectionCreated.connect (mem_fun (*this, &Session::add_named_selection)); IO::MoreOutputs.connect (mem_fun (*this, &Session::ensure_passthru_buffers)); @@ -285,7 +285,7 @@ Session::first_stage_init (string fullpath, string snapshot_name) int Session::second_stage_init (bool new_session) { - ExternalSource::set_peak_dir (peak_dir()); + AudioFileSource::set_peak_dir (peak_dir()); if (!new_session) { if (load_state (_current_snapshot_name)) { @@ -425,7 +425,7 @@ Session::setup_raid_path (string path) } fspath += tape_dir_name; - FileSource::set_search_path (fspath); + AudioFileSource::set_search_path (fspath); return; } @@ -481,9 +481,9 @@ Session::setup_raid_path (string path) session_dirs.push_back (sp); } - /* set the FileSource search path */ + /* set the AudioFileSource search path */ - FileSource::set_search_path (fspath); + AudioFileSource::set_search_path (fspath); /* reset the round-robin soundfile path thingie */ @@ -625,11 +625,11 @@ Session::load_diskstreams (const XMLNode& node) for (citer = clist.begin(); citer != clist.end(); ++citer) { - DiskStream* dstream; + AudioDiskstream* dstream; try { - dstream = new DiskStream (*this, **citer); - /* added automatically by DiskStreamCreated handler */ + dstream = new AudioDiskstream (*this, **citer); + /* added automatically by AudioDiskstreamCreated handler */ } catch (failed_constructor& err) { @@ -1335,15 +1335,15 @@ Session::state(bool full_state) child = node->add_child ("Sources"); if (full_state) { - Glib::Mutex::Lock sl (source_lock); + Glib::Mutex::Lock sl (audio_source_lock); - for (SourceList::iterator siter = sources.begin(); siter != sources.end(); ++siter) { + for (AudioSourceList::iterator siter = audio_sources.begin(); siter != audio_sources.end(); ++siter) { - /* Don't save information about FileSources that are empty */ + /* Don't save information about AudioFileSources that are empty */ - FileSource* fs; + AudioFileSource* fs; - if ((fs = dynamic_cast ((*siter).second)) != 0) { + if ((fs = dynamic_cast ((*siter).second)) != 0) { DestructiveFileSource* dfs = dynamic_cast (fs); /* destructive file sources are OK if they are empty, because @@ -1380,7 +1380,7 @@ Session::state(bool full_state) { Glib::RWLock::ReaderLock dl (diskstream_lock); - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if (!(*i)->hidden()) { child->add_child_nocopy ((*i)->get_state()); } @@ -1511,7 +1511,7 @@ Session::set_state (const XMLNode& node) Options Sources AudioRegions - DiskStreams + AudioDiskstreams Connections Locations Routes @@ -1745,6 +1745,7 @@ Session::XMLRegionFactory (const XMLNode& node, bool full) const XMLProperty* prop; id_t s_id; Source* source; + AudioSource* as; AudioRegion::SourceList sources; uint32_t nchans = 1; char buf[128]; @@ -1772,7 +1773,13 @@ Session::XMLRegionFactory (const XMLNode& node, bool full) return 0; } - sources.push_back(source); + as = dynamic_cast(source); + if (!as) { + error << string_compose(_("Session: XMLNode describing a AudioRegion references a non-audio source id =%1"), s_id) << endmsg; + return 0; + } + + sources.push_back (as); /* pickup other channels */ @@ -1785,7 +1792,13 @@ Session::XMLRegionFactory (const XMLNode& node, bool full) error << string_compose(_("Session: XMLNode describing a AudioRegion references an unknown source id =%1"), s_id) << endmsg; return 0; } - sources.push_back(source); + + as = dynamic_cast(source); + if (!as) { + error << string_compose(_("Session: XMLNode describing a AudioRegion references a non-audio source id =%1"), s_id) << endmsg; + return 0; + } + sources.push_back (as); } } @@ -1804,12 +1817,14 @@ Session::get_sources_as_xml () { XMLNode* node = new XMLNode (X_("Sources")); - Glib::Mutex::Lock lm (source_lock); + Glib::Mutex::Lock lm (audio_source_lock); - for (SourceList::iterator i = sources.begin(); i != sources.end(); ++i) { + for (AudioSourceList::iterator i = audio_sources.begin(); i != audio_sources.end(); ++i) { node->add_child_nocopy ((*i).second->get_state()); } + /* XXX get MIDI and other sources here */ + return *node; } @@ -1867,23 +1882,12 @@ Session::XMLSourceFactory (const XMLNode& node) } try { - if (node.property (X_("destructive")) != 0) { - src = new DestructiveFileSource (node, frame_rate()); - } else { - src = new FileSource (node, frame_rate()); - } + src = AudioFileSource::create (node); } catch (failed_constructor& err) { - - try { - src = ExternalSource::create (node); - } - - catch (failed_constructor& err) { - error << _("Found a sound file that cannot be used by Ardour. See the progammers.") << endmsg; - return 0; - } + error << _("Found a sound file that cannot be used by Ardour. Talk to the progammers.") << endmsg; + return 0; } return src; @@ -2930,9 +2934,9 @@ Session::cleanup_sources (Session::cleanup_report& rep) rep.paths.clear (); rep.space = 0; - for (SourceList::iterator i = sources.begin(); i != sources.end(); ) { + for (AudioSourceList::iterator i = audio_sources.begin(); i != audio_sources.end(); ) { - SourceList::iterator tmp; + AudioSourceList::iterator tmp; tmp = i; ++tmp; @@ -2949,7 +2953,7 @@ Session::cleanup_sources (Session::cleanup_report& rep) adding it to the list of all sources below */ - sources.erase (i); + audio_sources.erase (i); } i = tmp; @@ -3013,20 +3017,17 @@ Session::cleanup_sources (Session::cleanup_report& rep) state file on disk still references sources we may have already dropped. */ - + find_all_sources_across_snapshots (all_sources, true); - /* add our current source list + /* add our current source list */ - - for (SourceList::iterator i = sources.begin(); i != sources.end(); ++i) { - FileSource* fs; - ExternalSource* sfs; + + for (AudioSourceList::iterator i = audio_sources.begin(); i != audio_sources.end(); ++i) { + AudioFileSource* fs; - if ((fs = dynamic_cast ((*i).second)) != 0) { + if ((fs = dynamic_cast ((*i).second)) != 0) { all_sources.insert (fs->path()); - } else if ((sfs = dynamic_cast ((*i).second)) != 0) { - all_sources.insert (sfs->path()); } } diff --git a/libs/ardour/session_time.cc b/libs/ardour/session_time.cc index e3badc5b11..07b702618e 100644 --- a/libs/ardour/session_time.cc +++ b/libs/ardour/session_time.cc @@ -32,11 +32,12 @@ #include #include #include +#include #include "i18n.h" using namespace ARDOUR; -//using namespace sigc; +using namespace PBD; /* BBT TIME*/ @@ -91,6 +92,9 @@ Session::set_smpte_offset (jack_nframes_t off) { _smpte_offset = off; last_smpte_valid = false; + + AudioFileSource::set_header_position_offset (_smpte_offset, _smpte_offset_negative); + SMPTEOffsetChanged (); /* EMIT SIGNAL */ } @@ -99,380 +103,15 @@ Session::set_smpte_offset_negative (bool neg) { _smpte_offset_negative = neg; last_smpte_valid = false; + + AudioFileSource::set_header_position_offset (_smpte_offset, _smpte_offset_negative); + SMPTEOffsetChanged (); /* EMIT SIGNAL */ } -#define SMPTE_IS_AROUND_ZERO( sm ) (!(sm).frames && !(sm).seconds && !(sm).minutes && !(sm).hours) -#define SMPTE_IS_ZERO( sm ) (!(sm).frames && !(sm).seconds && !(sm).minutes && !(sm).hours && !(sm.subframes)) - -// Increment by exactly one frame (keep subframes value) -// Return true if seconds wrap -smpte_wrap_t -Session::smpte_increment( SMPTE_Time& smpte ) const -{ - smpte_wrap_t wrap = smpte_wrap_none; - - if (smpte.negative) { - if (SMPTE_IS_AROUND_ZERO(smpte) && smpte.subframes) { - // We have a zero transition involving only subframes - smpte.subframes = 80 - smpte.subframes; - smpte.negative = false; - return smpte_wrap_seconds; - } - - smpte.negative = false; - wrap = smpte_decrement( smpte ); - if (!SMPTE_IS_ZERO( smpte )) { - smpte.negative = true; - } - return wrap; - } - - switch (mtc_smpte_bits >> 5) { - case MIDI::MTC_24_FPS: - if (smpte.frames == 23) { - smpte.frames = 0; - wrap = smpte_wrap_seconds; - } - break; - case MIDI::MTC_25_FPS: - if (smpte.frames == 24) { - smpte.frames = 0; - wrap = smpte_wrap_seconds; - } - break; - case MIDI::MTC_30_FPS_DROP: - if (smpte.frames == 29) { - if ( ((smpte.minutes + 1) % 10) && (smpte.seconds == 59) ) { - smpte.frames = 2; - } - else { - smpte.frames = 0; - } - wrap = smpte_wrap_seconds; - } - break; - case MIDI::MTC_30_FPS: - if (smpte.frames == 29) { - smpte.frames = 0; - wrap = smpte_wrap_seconds; - } - break; - } - - if (wrap == smpte_wrap_seconds) { - if (smpte.seconds == 59) { - smpte.seconds = 0; - wrap = smpte_wrap_minutes; - if (smpte.minutes == 59) { - smpte.minutes = 0; - wrap = smpte_wrap_hours; - smpte.hours++; - } else { - smpte.minutes++; - } - } else { - smpte.seconds++; - } - } else { - smpte.frames++; - } - - return wrap; -} - -// Decrement by exactly one frame (keep subframes value) -smpte_wrap_t -Session::smpte_decrement( SMPTE_Time& smpte ) const -{ - smpte_wrap_t wrap = smpte_wrap_none; - - - if (smpte.negative || SMPTE_IS_ZERO(smpte)) { - smpte.negative = false; - wrap = smpte_increment( smpte ); - smpte.negative = true; - return wrap; - } else if (SMPTE_IS_AROUND_ZERO(smpte) && smpte.subframes) { - // We have a zero transition involving only subframes - smpte.subframes = 80 - smpte.subframes; - smpte.negative = true; - return smpte_wrap_seconds; - } - - switch (mtc_smpte_bits >> 5) { - case MIDI::MTC_24_FPS: - if (smpte.frames == 0) { - smpte.frames = 23; - wrap = smpte_wrap_seconds; - } - break; - case MIDI::MTC_25_FPS: - if (smpte.frames == 0) { - smpte.frames = 24; - wrap = smpte_wrap_seconds; - } - break; - case MIDI::MTC_30_FPS_DROP: - if ((smpte.minutes % 10) && (smpte.seconds == 0)) { - if (smpte.frames <= 2) { - smpte.frames = 29; - wrap = smpte_wrap_seconds; - } - } else if (smpte.frames == 0) { - smpte.frames = 29; - wrap = smpte_wrap_seconds; - } - break; - case MIDI::MTC_30_FPS: - if (smpte.frames == 0) { - smpte.frames = 29; - wrap = smpte_wrap_seconds; - } - break; - } - - if (wrap == smpte_wrap_seconds) { - if (smpte.seconds == 0) { - smpte.seconds = 59; - wrap = smpte_wrap_minutes; - if (smpte.minutes == 0) { - smpte.minutes = 59; - wrap = smpte_wrap_hours; - smpte.hours--; - } - else { - smpte.minutes--; - } - } else { - smpte.seconds--; - } - } else { - smpte.frames--; - } - - if (SMPTE_IS_ZERO( smpte )) { - smpte.negative = false; - } - - return wrap; -} - -// Go to lowest absolute subframe value in this frame (set to 0 :-) -void -Session::smpte_frames_floor( SMPTE_Time& smpte ) const -{ - smpte.subframes = 0; - if (SMPTE_IS_ZERO(smpte)) { - smpte.negative = false; - } -} - -// Increment by one subframe -smpte_wrap_t -Session::smpte_increment_subframes( SMPTE_Time& smpte ) const -{ - smpte_wrap_t wrap = smpte_wrap_none; - - if (smpte.negative) { - smpte.negative = false; - wrap = smpte_decrement_subframes( smpte ); - if (!SMPTE_IS_ZERO(smpte)) { - smpte.negative = true; - } - return wrap; - } - - smpte.subframes++; - if (smpte.subframes >= 80) { - smpte.subframes = 0; - smpte_increment( smpte ); - return smpte_wrap_frames; - } - return smpte_wrap_none; -} - - -// Decrement by one subframe -smpte_wrap_t -Session::smpte_decrement_subframes( SMPTE_Time& smpte ) const -{ - smpte_wrap_t wrap = smpte_wrap_none; - - if (smpte.negative) { - smpte.negative = false; - wrap = smpte_increment_subframes( smpte ); - smpte.negative = true; - return wrap; - } - - if (smpte.subframes <= 0) { - smpte.subframes = 0; - if (SMPTE_IS_ZERO(smpte)) { - smpte.negative = true; - smpte.subframes = 1; - return smpte_wrap_frames; - } else { - smpte_decrement( smpte ); - smpte.subframes = 79; - return smpte_wrap_frames; - } - } else { - smpte.subframes--; - if (SMPTE_IS_ZERO(smpte)) { - smpte.negative = false; - } - return smpte_wrap_none; - } -} - - -// Go to next whole second (frames == 0 or frames == 2) -smpte_wrap_t -Session::smpte_increment_seconds( SMPTE_Time& smpte ) const -{ - smpte_wrap_t wrap = smpte_wrap_none; - - // Clear subframes - smpte_frames_floor( smpte ); - - if (smpte.negative) { - // Wrap second if on second boundary - wrap = smpte_increment(smpte); - // Go to lowest absolute frame value - smpte_seconds_floor( smpte ); - if (SMPTE_IS_ZERO(smpte)) { - smpte.negative = false; - } - } else { - // Go to highest possible frame in this second - switch (mtc_smpte_bits >> 5) { - case MIDI::MTC_24_FPS: - smpte.frames = 23; - break; - case MIDI::MTC_25_FPS: - smpte.frames = 24; - break; - case MIDI::MTC_30_FPS_DROP: - case MIDI::MTC_30_FPS: - smpte.frames = 29; - break; - } - - // Increment by one frame - wrap = smpte_increment( smpte ); - } - - return wrap; -} - -// Go to lowest (absolute) frame value in this second -// Doesn't care about positive/negative -void -Session::smpte_seconds_floor( SMPTE_Time& smpte ) const -{ - // Clear subframes - smpte_frames_floor( smpte ); - - // Go to lowest possible frame in this second - switch (mtc_smpte_bits >> 5) { - case MIDI::MTC_24_FPS: - case MIDI::MTC_25_FPS: - case MIDI::MTC_30_FPS: - smpte.frames = 0; - break; - case MIDI::MTC_30_FPS_DROP: - if ((smpte.minutes % 10) && (smpte.seconds == 0)) { - smpte.frames = 2; - } else { - smpte.frames = 0; - } - break; - } - - if (SMPTE_IS_ZERO(smpte)) { - smpte.negative = false; - } -} - - -// Go to next whole minute (seconds == 0, frames == 0 or frames == 2) -smpte_wrap_t -Session::smpte_increment_minutes( SMPTE_Time& smpte ) const -{ - smpte_wrap_t wrap = smpte_wrap_none; - - // Clear subframes - smpte_frames_floor( smpte ); - - if (smpte.negative) { - // Wrap if on minute boundary - wrap = smpte_increment_seconds( smpte ); - // Go to lowest possible value in this minute - smpte_minutes_floor( smpte ); - } else { - // Go to highest possible second - smpte.seconds = 59; - // Wrap minute by incrementing second - wrap = smpte_increment_seconds( smpte ); - } - - return wrap; -} - -// Go to lowest absolute value in this minute -void -Session::smpte_minutes_floor( SMPTE_Time& smpte ) const -{ - // Go to lowest possible second - smpte.seconds = 0; - // Go to lowest possible frame - smpte_seconds_floor( smpte ); - - if (SMPTE_IS_ZERO(smpte)) { - smpte.negative = false; - } -} - -// Go to next whole hour (minute = 0, second = 0, frame = 0) -smpte_wrap_t -Session::smpte_increment_hours( SMPTE_Time& smpte ) const -{ - smpte_wrap_t wrap = smpte_wrap_none; - - // Clear subframes - smpte_frames_floor(smpte); - - if (smpte.negative) { - // Wrap if on hour boundary - wrap = smpte_increment_minutes( smpte ); - // Go to lowest possible value in this hour - smpte_hours_floor( smpte ); - } else { - smpte.minutes = 59; - wrap = smpte_increment_minutes( smpte ); - } - - return wrap; -} - -// Go to lowest absolute value in this hour -void -Session::smpte_hours_floor( SMPTE_Time& smpte ) const -{ - smpte.minutes = 0; - smpte.seconds = 0; - smpte.frames = 0; - smpte.subframes = 0; - - if (SMPTE_IS_ZERO(smpte)) { - smpte.negative = false; - } -} - void -Session::smpte_to_sample( SMPTE_Time& smpte, jack_nframes_t& sample, bool use_offset, bool use_subframes ) const +Session::smpte_to_sample( SMPTE::Time& smpte, jack_nframes_t& sample, bool use_offset, bool use_subframes ) const { if (smpte_drop_frames) { // The drop frame format was created to better approximate the 30000/1001 = 29.97002997002997.... @@ -555,10 +194,10 @@ Session::smpte_to_sample( SMPTE_Time& smpte, jack_nframes_t& sample, bool use_of void -Session::sample_to_smpte( jack_nframes_t sample, SMPTE_Time& smpte, bool use_offset, bool use_subframes ) const +Session::sample_to_smpte( jack_nframes_t sample, SMPTE::Time& smpte, bool use_offset, bool use_subframes ) const { jack_nframes_t offset_sample; - + if (!use_offset) { offset_sample = sample; smpte.negative = false; @@ -649,7 +288,7 @@ Session::sample_to_smpte( jack_nframes_t sample, SMPTE_Time& smpte, bool use_off } void -Session::smpte_time (jack_nframes_t when, SMPTE_Time& smpte) +Session::smpte_time (jack_nframes_t when, SMPTE::Time& smpte) { if (last_smpte_valid && when == last_smpte_when) { smpte = last_smpte; @@ -664,7 +303,7 @@ Session::smpte_time (jack_nframes_t when, SMPTE_Time& smpte) } void -Session::smpte_time_subframes (jack_nframes_t when, SMPTE_Time& smpte) +Session::smpte_time_subframes (jack_nframes_t when, SMPTE::Time& smpte) { if (last_smpte_valid && when == last_smpte_when) { smpte = last_smpte; @@ -679,7 +318,7 @@ Session::smpte_time_subframes (jack_nframes_t when, SMPTE_Time& smpte) } void -Session::smpte_duration (jack_nframes_t when, SMPTE_Time& smpte) const +Session::smpte_duration (jack_nframes_t when, SMPTE::Time& smpte) const { sample_to_smpte( when, smpte, false /* use_offset */, true /* use_subframes */ ); } @@ -687,14 +326,14 @@ Session::smpte_duration (jack_nframes_t when, SMPTE_Time& smpte) const void Session::smpte_duration_string (char* buf, jack_nframes_t when) const { - SMPTE_Time smpte; + SMPTE::Time smpte; smpte_duration (when, smpte); - snprintf (buf, sizeof (buf), "%02ld:%02ld:%02ld:%02ld", smpte.hours, smpte.minutes, smpte.seconds, smpte.frames); + snprintf (buf, sizeof (buf), "%02" PRIu32 ":%02" PRIu32 ":%02" PRIu32 ":%02" PRIu32, smpte.hours, smpte.minutes, smpte.seconds, smpte.frames); } void -Session::smpte_time (SMPTE_Time &t) +Session::smpte_time (SMPTE::Time &t) { smpte_time (_transport_frame, t); diff --git a/libs/ardour/session_timefx.cc b/libs/ardour/session_timefx.cc index 6351aa9825..7eec1e578b 100644 --- a/libs/ardour/session_timefx.cc +++ b/libs/ardour/session_timefx.cc @@ -27,13 +27,13 @@ #include #include -#include #include #include "i18n.h" using namespace std; using namespace ARDOUR; +using namespace PBD; using namespace soundtouch; AudioRegion* @@ -80,7 +80,10 @@ Session::tempoize_region (TimeStretchRequest& tsr) } try { - sources.push_back(new FileSource (path, frame_rate(), false, Config->get_native_file_data_format())); + sources.push_back (new SndFileSource (path, + Config->get_native_file_data_format(), + Config->get_native_file_header_format(), + frame_rate())); } catch (failed_constructor& err) { error << string_compose (_("tempoize: error creating new audio file %1 (%2)"), path, strerror (errno)) << endmsg; goto out; @@ -150,13 +153,16 @@ Session::tempoize_region (TimeStretchRequest& tsr) xnow = localtime (&now); for (it = sources.begin(); it != sources.end(); ++it) { - dynamic_cast(*it)->update_header (tsr.region->position(), *xnow, now); + AudioFileSource* afs = dynamic_cast(*it); + if (afs) { + afs->update_header (tsr.region->position(), *xnow, now); + } } region_name = tsr.region->name() + X_(".t"); r = new AudioRegion (sources, 0, sources.front()->length(), region_name, - 0, AudioRegion::Flag (AudioRegion::DefaultFlags | AudioRegion::WholeFile)); + 0, AudioRegion::Flag (AudioRegion::DefaultFlags | AudioRegion::WholeFile)); out: diff --git a/libs/ardour/session_transport.cc b/libs/ardour/session_transport.cc index db15b64c32..376dee11a2 100644 --- a/libs/ardour/session_transport.cc +++ b/libs/ardour/session_transport.cc @@ -36,7 +36,7 @@ #include #include #include -#include +#include #include #include #include @@ -46,6 +46,7 @@ using namespace std; using namespace ARDOUR; using namespace sigc; +using namespace PBD; void Session::request_input_change_handling () @@ -78,7 +79,7 @@ Session::request_transport_speed (float speed) } void -Session::request_diskstream_speed (DiskStream& ds, float speed) +Session::request_diskstream_speed (AudioDiskstream& ds, float speed) { Event* ev = new Event (Event::SetDiskstreamSpeed, Event::Add, Event::Immediate, 0, speed); ev->set_ptr (&ds); @@ -200,7 +201,7 @@ Session::butler_transport_work () } if (post_transport_work & PostTransportInputChange) { - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { (*i)->non_realtime_input_change (); } } @@ -216,7 +217,7 @@ Session::butler_transport_work () cumulative_rf_motion = 0; reset_rf_scale (0); - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if (!(*i)->hidden()) { if ((*i)->speed() != 1.0f || (*i)->speed() != -1.0f) { (*i)->seek ((jack_nframes_t) (_transport_frame * (double) (*i)->speed())); @@ -248,7 +249,7 @@ Session::non_realtime_set_speed () { Glib::RWLock::ReaderLock lm (diskstream_lock); - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { (*i)->non_realtime_set_speed (); } } @@ -258,7 +259,7 @@ Session::non_realtime_overwrite () { Glib::RWLock::ReaderLock lm (diskstream_lock); - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if ((*i)->pending_overwrite) { (*i)->overwrite_existing_buffers (); } @@ -274,7 +275,7 @@ Session::non_realtime_stop (bool abort) did_record = false; - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if ((*i)->get_captured_frames () != 0) { did_record = true; break; @@ -327,7 +328,7 @@ Session::non_realtime_stop (bool abort) _have_captured = true; } - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { (*i)->transport_stopped (*now, xnow, abort); } @@ -364,7 +365,7 @@ Session::non_realtime_stop (bool abort) } #endif - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if (!(*i)->hidden()) { if ((*i)->speed() != 1.0f || (*i)->speed() != -1.0f) { (*i)->seek ((jack_nframes_t) (_transport_frame * (double) (*i)->speed())); @@ -491,7 +492,7 @@ Session::set_auto_loop (bool yn) if (seamless_loop) { // set all diskstreams to use internal looping - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if (!(*i)->hidden()) { (*i)->set_loop (loc); } @@ -499,7 +500,7 @@ Session::set_auto_loop (bool yn) } else { // set all diskstreams to NOT use internal looping - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if (!(*i)->hidden()) { (*i)->set_loop (0); } @@ -529,7 +530,7 @@ Session::set_auto_loop (bool yn) clear_events (Event::AutoLoop); // set all diskstreams to NOT use internal looping - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if (!(*i)->hidden()) { (*i)->set_loop (0); } @@ -645,7 +646,7 @@ Session::locate (jack_nframes_t target_frame, bool with_roll, bool with_flush, b The rarity and short potential lock duration makes this "OK" */ Glib::RWLock::ReaderLock dsm (diskstream_lock); - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if ((*i)->record_enabled ()) { //cerr << "switching from input" << __FILE__ << __LINE__ << endl << endl; (*i)->monitor_input (!auto_input); @@ -660,7 +661,7 @@ Session::locate (jack_nframes_t target_frame, bool with_roll, bool with_flush, b The rarity and short potential lock duration makes this "OK" */ Glib::RWLock::ReaderLock dsm (diskstream_lock); - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if ((*i)->record_enabled ()) { //cerr << "switching to input" << __FILE__ << __LINE__ << endl << endl; (*i)->monitor_input (true); @@ -704,7 +705,7 @@ Session::set_transport_speed (float speed, bool abort) The rarity and short potential lock duration makes this "OK" */ Glib::RWLock::ReaderLock dsm (diskstream_lock); - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if ((*i)->record_enabled ()) { //cerr << "switching to input" << __FILE__ << __LINE__ << endl << endl; (*i)->monitor_input (true); @@ -730,7 +731,7 @@ Session::set_transport_speed (float speed, bool abort) The rarity and short potential lock duration makes this "OK" */ Glib::RWLock::ReaderLock dsm (diskstream_lock); - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if (auto_input && (*i)->record_enabled ()) { //cerr << "switching from input" << __FILE__ << __LINE__ << endl << endl; (*i)->monitor_input (false); @@ -781,7 +782,7 @@ Session::set_transport_speed (float speed, bool abort) _last_transport_speed = _transport_speed; _transport_speed = speed; - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if ((*i)->realtime_set_speed ((*i)->speed(), true)) { post_transport_work = PostTransportWork (post_transport_work | PostTransportSpeed); } @@ -871,7 +872,7 @@ Session::actually_start_transport () transport_sub_state |= PendingDeclickIn; _transport_speed = 1.0; - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { (*i)->realtime_set_speed ((*i)->speed(), true); } @@ -1001,7 +1002,7 @@ Session::set_slave_source (SlaveSource src, jack_nframes_t frame) _slave_type = src; - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { if (!(*i)->hidden()) { if ((*i)->realtime_set_speed ((*i)->speed(), true)) { non_rt_required = true; @@ -1033,7 +1034,7 @@ Session::reverse_diskstream_buffers () } void -Session::set_diskstream_speed (DiskStream* stream, float speed) +Session::set_diskstream_speed (AudioDiskstream* stream, float speed) { if (stream->realtime_set_speed (speed, false)) { post_transport_work = PostTransportWork (post_transport_work | PostTransportSpeed); @@ -1198,8 +1199,8 @@ Session::update_latency_compensation (bool with_stop, bool abort) for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) { if (with_stop) { - (*i)->transport_stopped (abort, (post_transport_work & PostTransportLocate), - (!(post_transport_work & PostTransportLocate) || pending_locate_flush)); + (*i)->handle_transport_stopped (abort, (post_transport_work & PostTransportLocate), + (!(post_transport_work & PostTransportLocate) || pending_locate_flush)); } jack_nframes_t old_latency = (*i)->signal_latency (); @@ -1229,7 +1230,7 @@ Session::update_latency_compensation (bool with_stop, bool abort) /* reflect any changes in latencies into capture offsets */ - for (DiskStreamList::iterator i = diskstreams.begin(); i != diskstreams.end(); ++i) { + for (AudioDiskstreamList::iterator i = audio_diskstreams.begin(); i != audio_diskstreams.end(); ++i) { (*i)->set_capture_offset (); } } diff --git a/libs/ardour/sndfilesource.cc b/libs/ardour/sndfilesource.cc index 87f7faf423..24a70f636b 100644 --- a/libs/ardour/sndfilesource.cc +++ b/libs/ardour/sndfilesource.cc @@ -18,47 +18,194 @@ $Id$ */ +#include +#include + +#include +#include + +#include + #include #include "i18n.h" +using namespace std; using namespace ARDOUR; +using namespace PBD; SndFileSource::SndFileSource (const XMLNode& node) - : ExternalSource (node) + : AudioFileSource (node) { - init (_name, true); - SourceCreated (this); /* EMIT SIGNAL */ + init (_name); + + if (open()) { + throw failed_constructor (); + } + + if (_build_peakfiles) { + if (initialize_peakfile (false, _path)) { + sf_close (sf); + sf = 0; + throw failed_constructor (); + } + } + + AudioSourceCreated (this); /* EMIT SIGNAL */ } -SndFileSource::SndFileSource (const string& idstr, bool build_peak) - : ExternalSource(idstr, build_peak) +SndFileSource::SndFileSource (string idstr, Flag flags) + : AudioFileSource (idstr, Flag (flags & ~(Writable|Removable|RemovableIfEmpty|RemoveAtDestroy))) { - init (idstr, build_peak); + init (idstr); - if (build_peak) { - SourceCreated (this); /* EMIT SIGNAL */ + if (open()) { + throw failed_constructor (); } + + if (_build_peakfiles) { + if (initialize_peakfile (false, _path)) { + sf_close (sf); + sf = 0; + throw failed_constructor (); + } + } + + + AudioSourceCreated (this); /* EMIT SIGNAL */ +} + +SndFileSource::SndFileSource (string idstr, SampleFormat sfmt, HeaderFormat hf, jack_nframes_t rate, Flag flags) + : AudioFileSource(idstr, flags, sfmt, hf) +{ + int fmt = 0; + + init (idstr); + + switch (hf) { + case CAF: + fmt = SF_FORMAT_CAF; + _flags = Flag (_flags & ~Broadcast); + break; + + case AIFF: + fmt = SF_FORMAT_AIFF; + _flags = Flag (_flags & ~Broadcast); + break; + + case BWF: + fmt = SF_FORMAT_WAV; + _flags = Flag (_flags | Broadcast); + break; + + case WAVE: + fmt = SF_FORMAT_WAV; + _flags = Flag (_flags & ~Broadcast); + break; + + case WAVE64: + fmt = SF_FORMAT_W64; + _flags = Flag (_flags & ~Broadcast); + break; + + default: + fatal << string_compose (_("programming error: %1"), X_("unsupported audio header format requested")) << endmsg; + /*NOTREACHED*/ + break; + + } + + switch (sfmt) { + case FormatFloat: + fmt |= SF_FORMAT_FLOAT; + break; + + case FormatInt24: + fmt |= SF_FORMAT_PCM_24; + break; + } + + _info.channels = 1; + _info.samplerate = rate; + _info.format = fmt; + + if (open()) { + throw failed_constructor(); + } + + if (writable() && (_flags & Broadcast)) { + + _broadcast_info = new SF_BROADCAST_INFO; + memset (_broadcast_info, 0, sizeof (*_broadcast_info)); + + snprintf (_broadcast_info->description, sizeof (_broadcast_info->description), "BWF %s", _name.c_str()); + + struct utsname utsinfo; + + if (uname (&utsinfo)) { + error << string_compose(_("FileSource: cannot get host information for BWF header (%1)"), strerror(errno)) << endmsg; + return; + } + + snprintf (_broadcast_info->originator, sizeof (_broadcast_info->originator), "ardour:%s:%s:%s:%s:%s)", + Glib::get_real_name().c_str(), + utsinfo.nodename, + utsinfo.sysname, + utsinfo.release, + utsinfo.version); + + _broadcast_info->version = 1; + + /* XXX do something about this field */ + + snprintf (_broadcast_info->umid, sizeof (_broadcast_info->umid), "%s", "fnord"); + + /* coding history is added by libsndfile */ + + if (sf_command (sf, SFC_SET_BROADCAST_INFO, _broadcast_info, sizeof (_broadcast_info)) != SF_TRUE) { + char errbuf[256]; + sf_error_str (0, errbuf, sizeof (errbuf) - 1); + error << string_compose (_("cannot set broadcast info for audio file %1 (%2); dropping broadcast info for this file"), _path, errbuf) << endmsg; + _flags = Flag (_flags & ~Broadcast); + delete _broadcast_info; + _broadcast_info = 0; + } + } + + if (_build_peakfiles) { + if (initialize_peakfile (true, _path)) { + sf_close (sf); + sf = 0; + throw failed_constructor (); + } + } + + /* since SndFileSource's constructed with this constructor can be writable, make sure we update if the header info changes */ + + if (writable()) { + HeaderPositionOffsetChanged.connect (mem_fun (*this, &AudioFileSource::handle_header_position_change)); + } + + AudioSourceCreated (this); /* EMIT SIGNAL */ } void -SndFileSource::init (const string& idstr, bool build_peak) +SndFileSource::init (const string& idstr) { string::size_type pos; string file; - tmpbuf = 0; - tmpbufsize = 0; + interleave_buf = 0; + interleave_bufsize = 0; sf = 0; - - _name = idstr; + _broadcast_info = 0; if ((pos = idstr.find_last_of (':')) == string::npos) { channel = 0; - file = idstr; + _name = Glib::path_get_basename (idstr); } else { channel = atoi (idstr.substr (pos+1).c_str()); - file = idstr.substr (0, pos); + _name = Glib::path_get_basename (idstr.substr (0, pos)); } /* although libsndfile says we don't need to set this, @@ -66,46 +213,56 @@ SndFileSource::init (const string& idstr, bool build_peak) */ memset (&_info, 0, sizeof(_info)); +} - /* note that we temporarily truncated _id at the colon */ - - if ((sf = sf_open (file.c_str(), SFM_READ, &_info)) == 0) { +int +SndFileSource::open () +{ + if ((sf = sf_open (_path.c_str(), (writable() ? SFM_RDWR : SFM_READ), &_info)) == 0) { char errbuf[256]; sf_error_str (0, errbuf, sizeof (errbuf) - 1); - error << string_compose(_("SndFileSource: cannot open file \"%1\" (%2)"), file, errbuf) << endmsg; - throw failed_constructor(); + error << string_compose(_("SndFileSource: cannot open file \"%1\" for %2 (%3)"), + _path, (writable() ? "read+write" : "reading"), errbuf) << endmsg; + return -1; } if (channel >= _info.channels) { error << string_compose(_("SndFileSource: file only contains %1 channels; %2 is invalid as a channel number"), _info.channels, channel) << endmsg; sf_close (sf); sf = 0; - throw failed_constructor(); + return -1; } _length = _info.frames; - _path = file; - if (build_peak) { - if (initialize_peakfile (false, _path)) { - sf_close (sf); - sf = 0; - throw failed_constructor (); - } + if (writable()) { + sf_command (sf, SFC_SET_UPDATE_HEADER_AUTO, 0, SF_FALSE); + } + + return 0; +} + +void +SndFileSource::close () +{ + if (sf) { + sf_close (sf); + sf = 0; } } SndFileSource::~SndFileSource () - { GoingAway (this); /* EMIT SIGNAL */ - if (sf) { - sf_close (sf); + close (); + + if (interleave_buf) { + delete [] interleave_buf; } - if (tmpbuf) { - delete [] tmpbuf; + if (_broadcast_info) { + delete [] _broadcast_info; } } @@ -116,49 +273,73 @@ SndFileSource::sample_rate () const } jack_nframes_t -SndFileSource::read (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const +SndFileSource::read_unlocked (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const { int32_t nread; float *ptr; uint32_t real_cnt; + jack_nframes_t file_cnt; - if (sf_seek (sf, (off_t) start, SEEK_SET) < 0) { - char errbuf[256]; - sf_error_str (0, errbuf, sizeof (errbuf) - 1); - error << string_compose(_("SndFileSource: could not seek to frame %1 within %2 (%3)"), start, _name.substr (1), errbuf) << endmsg; - return 0; + if (start > _length) { + + /* read starts beyond end of data, just memset to zero */ + + file_cnt = 0; + + } else if (start + cnt > _length) { + + /* read ends beyond end of data, read some, memset the rest */ + + file_cnt = _length - start; + + } else { + + /* read is entirely within data */ + + file_cnt = cnt; + } + + if (file_cnt) { + + if (sf_seek (sf, (sf_count_t) start, SEEK_SET|SFM_READ) != (sf_count_t) start) { + char errbuf[256]; + sf_error_str (0, errbuf, sizeof (errbuf) - 1); + error << string_compose(_("SndFileSource: could not seek to frame %1 within %2 (%3)"), start, _name.substr (1), errbuf) << endmsg; + return 0; + } + + if (_info.channels == 1) { + jack_nframes_t ret = sf_read_float (sf, dst, file_cnt); + _read_data_count = cnt * sizeof(float); + return ret; + } } - if (_info.channels == 1) { - jack_nframes_t ret = sf_read_float (sf, dst, cnt); - _read_data_count = cnt * sizeof(float); - return ret; + if (file_cnt != cnt) { + jack_nframes_t delta = cnt - file_cnt; + memset (dst+file_cnt, 0, sizeof (Sample) * delta); } real_cnt = cnt * _info.channels; - { - Glib::Mutex::Lock lm (_tmpbuf_lock); + if (interleave_bufsize < real_cnt) { - if (tmpbufsize < real_cnt) { - - if (tmpbuf) { - delete [] tmpbuf; - } - tmpbufsize = real_cnt; - tmpbuf = new float[tmpbufsize]; - } - - nread = sf_read_float (sf, tmpbuf, real_cnt); - ptr = tmpbuf + channel; - nread /= _info.channels; - - /* stride through the interleaved data */ - - for (int32_t n = 0; n < nread; ++n) { - dst[n] = *ptr; - ptr += _info.channels; + if (interleave_buf) { + delete [] interleave_buf; } + interleave_bufsize = real_cnt; + interleave_buf = new float[interleave_bufsize]; + } + + nread = sf_read_float (sf, interleave_buf, real_cnt); + ptr = interleave_buf + channel; + nread /= _info.channels; + + /* stride through the interleaved data */ + + for (int32_t n = 0; n < nread; ++n) { + dst[n] = *ptr; + ptr += _info.channels; } _read_data_count = cnt * sizeof(float); @@ -166,3 +347,163 @@ SndFileSource::read (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char return nread; } +jack_nframes_t +SndFileSource::write_unlocked (Sample *data, jack_nframes_t cnt, char * workbuf) +{ + if (!writable()) { + return 0; + } + + if (_info.channels != 1) { + fatal << string_compose (_("programming error: %1 %2"), X_("SndFileSource::write called on non-mono file"), _path) << endmsg; + /*NOTREACHED*/ + return 0; + } + + jack_nframes_t oldlen; + int32_t frame_pos = _length; + + if (write_float (data, frame_pos, cnt) != cnt) { + return 0; + } + + oldlen = _length; + update_length (oldlen, cnt); + + if (_build_peakfiles) { + PeakBuildRecord *pbr = 0; + + if (pending_peak_builds.size()) { + pbr = pending_peak_builds.back(); + } + + if (pbr && pbr->frame + pbr->cnt == oldlen) { + + /* the last PBR extended to the start of the current write, + so just extend it again. + */ + + pbr->cnt += cnt; + } else { + pending_peak_builds.push_back (new PeakBuildRecord (oldlen, cnt)); + } + + _peaks_built = false; + } + + + if (_build_peakfiles) { + queue_for_peaks (*this); + } + + _write_data_count = cnt; + + return cnt; +} + +int +SndFileSource::update_header (jack_nframes_t when, struct tm& now, time_t tnow) +{ + /* allow derived classes to override how this is done */ + + set_timeline_position (when); + + if (_flags & Broadcast) { + /* this will flush the header implicitly */ + return setup_broadcast_info (when, now, tnow); + } else { + return flush_header (); + } +} + +int +SndFileSource::flush_header () +{ + return (sf_command (sf, SFC_UPDATE_HEADER_NOW, 0, 0) != SF_TRUE); +} + +int +SndFileSource::setup_broadcast_info (jack_nframes_t when, struct tm& now, time_t tnow) +{ + /* random code is 9 digits */ + + int random_code = random() % 999999999; + + snprintf (_broadcast_info->originator_reference, sizeof (_broadcast_info->originator_reference), "%2s%3s%12s%02d%02d%02d%9d", + bwf_country_code, + bwf_organization_code, + bwf_serial_number, + now.tm_hour, + now.tm_min, + now.tm_sec, + random_code); + + snprintf (_broadcast_info->origination_date, sizeof (_broadcast_info->origination_date), "%4d-%02d-%02d", + 1900 + now.tm_year, + now.tm_mon, + now.tm_mday); + + snprintf (_broadcast_info->origination_time, sizeof (_broadcast_info->origination_time), "%02d-%02d-%02d", + now.tm_hour, + now.tm_min, + now.tm_sec); + + /* now update header position taking header offset into account */ + + set_header_timeline_position (); + + /* note that libsndfile flushes the header to disk when resetting the broadcast info */ + + if (sf_command (sf, SFC_SET_BROADCAST_INFO, _broadcast_info, sizeof (*_broadcast_info)) != SF_TRUE) { + error << string_compose (_("cannot set broadcast info for audio file %1; Dropping broadcast info for this file"), _path) << endmsg; + _flags = Flag (_flags & ~Broadcast); + delete _broadcast_info; + _broadcast_info = 0; + return -1; + } + + return 0; +} + +void +SndFileSource::set_header_timeline_position () +{ + uint64_t pos; + + _broadcast_info->time_reference_high = 0; + + if (header_position_negative) { + + if (ULONG_LONG_MAX - header_position_offset < timeline_position) { + pos = ULONG_LONG_MAX; // impossible + } else { + pos = timeline_position + header_position_offset; + } + + } else { + + if (timeline_position < header_position_offset) { + pos = 0; + } else { + pos = timeline_position - header_position_offset; + } + } + + _broadcast_info->time_reference_high = (pos >> 32); + _broadcast_info->time_reference_low = (pos & 0xffffffff); +} + +jack_nframes_t +SndFileSource::write_float (Sample* data, jack_nframes_t frame_pos, jack_nframes_t cnt) +{ + if (sf_seek (sf, frame_pos, SEEK_SET|SFM_WRITE) != frame_pos) { + error << string_compose (_("%1: cannot seek to %2"), _path, frame_pos) << endmsg; + return 0; + } + + if (sf_writef_float (sf, data, cnt) != (ssize_t) cnt) { + return 0; + } + + return cnt; +} diff --git a/libs/ardour/source.cc b/libs/ardour/source.cc index 7d790a036d..0d32ea4a21 100644 --- a/libs/ardour/source.cc +++ b/libs/ardour/source.cc @@ -42,35 +42,18 @@ using std::max; using namespace ARDOUR; -sigc::signal Source::SourceCreated; -pthread_t Source::peak_thread; -bool Source::have_peak_thread = false; -vector Source::pending_peak_sources; -Glib::StaticMutex Source::pending_peak_sources_lock = GLIBMM_STATIC_MUTEX_INIT; -int Source::peak_request_pipe[2]; - -bool Source::_build_missing_peakfiles = false; -bool Source::_build_peakfiles = false; - -Source::Source (bool announce) +Source::Source (string name) { + _name = name; _id = ARDOUR::new_id(); _use_cnt = 0; - _peaks_built = false; - next_peak_clear_should_notify = true; _timestamp = 0; - _read_data_count = 0; - _write_data_count = 0; } Source::Source (const XMLNode& node) { _use_cnt = 0; - _peaks_built = false; - next_peak_clear_should_notify = true; _timestamp = 0; - _read_data_count = 0; - _write_data_count = 0; if (set_state (node)) { throw failed_constructor(); @@ -96,10 +79,6 @@ Source::get_state () node->add_property ("timestamp", buf); } - if (_captured_for.length()) { - node->add_property ("captured-for", _captured_for); - } - return *node; } @@ -124,734 +103,9 @@ Source::set_state (const XMLNode& node) sscanf (prop->value().c_str(), "%ld", &_timestamp); } - if ((prop = node.property ("captured-for")) != 0) { - _captured_for = prop->value(); - } - return 0; } -/*********************************************************************** - PEAK FILE STUFF - ***********************************************************************/ - -void* -Source::peak_thread_work (void* arg) -{ - PBD::ThreadCreated (pthread_self(), X_("Peak")); - struct pollfd pfd[1]; - - Glib::Mutex::Lock lm (pending_peak_sources_lock); - - while (true) { - - pfd[0].fd = peak_request_pipe[0]; - pfd[0].events = POLLIN|POLLERR|POLLHUP; - - pending_peak_sources_lock.unlock(); - - if (poll (pfd, 1, -1) < 0) { - - if (errno == EINTR) { - pending_peak_sources_lock.lock(); - continue; - } - - error << string_compose (_("poll on peak request pipe failed (%1)"), - strerror (errno)) - << endmsg; - break; - } - - if (pfd[0].revents & ~POLLIN) { - error << _("Error on peak thread request pipe") << endmsg; - break; - } - - if (pfd[0].revents & POLLIN) { - - char req; - - /* empty the pipe of all current requests */ - - while (1) { - size_t nread = ::read (peak_request_pipe[0], &req, sizeof (req)); - - if (nread == 1) { - switch ((PeakRequest::Type) req) { - - case PeakRequest::Build: - break; - - case PeakRequest::Quit: - pthread_exit_pbd (0); - /*NOTREACHED*/ - break; - - default: - break; - } - - } else if (nread == 0) { - break; - } else if (errno == EAGAIN) { - break; - } else { - fatal << _("Error reading from peak request pipe") << endmsg; - /*NOTREACHED*/ - } - } - } - - pending_peak_sources_lock.lock(); - - while (!pending_peak_sources.empty()) { - - Source* s = pending_peak_sources.front(); - pending_peak_sources.erase (pending_peak_sources.begin()); - - pending_peak_sources_lock.unlock(); - s->build_peaks(); - pending_peak_sources_lock.lock(); - } - } - - pthread_exit_pbd (0); - /*NOTREACHED*/ - return 0; -} - -int -Source::start_peak_thread () -{ - if (!_build_peakfiles) { - return 0; - } - - if (pipe (peak_request_pipe)) { - error << string_compose(_("Cannot create transport request signal pipe (%1)"), strerror (errno)) << endmsg; - return -1; - } - - if (fcntl (peak_request_pipe[0], F_SETFL, O_NONBLOCK)) { - error << string_compose(_("UI: cannot set O_NONBLOCK on peak request pipe (%1)"), strerror (errno)) << endmsg; - return -1; - } - - if (fcntl (peak_request_pipe[1], F_SETFL, O_NONBLOCK)) { - error << string_compose(_("UI: cannot set O_NONBLOCK on peak request pipe (%1)"), strerror (errno)) << endmsg; - return -1; - } - - if (pthread_create_and_store ("peak file builder", &peak_thread, 0, peak_thread_work, 0)) { - error << _("Source: could not create peak thread") << endmsg; - return -1; - } - - have_peak_thread = true; - return 0; -} - -void -Source::stop_peak_thread () -{ - if (!have_peak_thread) { - return; - } - - void* status; - - char c = (char) PeakRequest::Quit; - ::write (peak_request_pipe[1], &c, 1); - pthread_join (peak_thread, &status); -} - -void -Source::queue_for_peaks (Source& source) -{ - if (have_peak_thread) { - - Glib::Mutex::Lock lm (pending_peak_sources_lock); - - source.next_peak_clear_should_notify = true; - - if (find (pending_peak_sources.begin(), - pending_peak_sources.end(), - &source) == pending_peak_sources.end()) { - pending_peak_sources.push_back (&source); - } - - char c = (char) PeakRequest::Build; - ::write (peak_request_pipe[1], &c, 1); - } -} - -void Source::clear_queue_for_peaks () -{ - /* this is done to cancel a group of running peak builds */ - if (have_peak_thread) { - Glib::Mutex::Lock lm (pending_peak_sources_lock); - pending_peak_sources.clear (); - } -} - - -bool -Source::peaks_ready (sigc::slot the_slot, sigc::connection& conn) const -{ - bool ret; - Glib::Mutex::Lock lm (_lock); - - /* check to see if the peak data is ready. if not - connect the slot while still holding the lock. - */ - - if (!(ret = _peaks_built)) { - conn = PeaksReady.connect (the_slot); - } - - return ret; -} - -int -Source::rename_peakfile (string newpath) -{ - /* caller must hold _lock */ - - string oldpath = peakpath; - - if (access (oldpath.c_str(), F_OK) == 0) { - if (rename (oldpath.c_str(), newpath.c_str()) != 0) { - error << string_compose (_("cannot rename peakfile for %1 from %2 to %3 (%4)"), _name, oldpath, newpath, strerror (errno)) << endmsg; - return -1; - } - } - - peakpath = newpath; - - return 0; -} - -int -Source::initialize_peakfile (bool newfile, string audio_path) -{ - struct stat statbuf; - - peakpath = peak_path (audio_path); - - if (newfile) { - - if (!_build_peakfiles) { - return 0; - } - - _peaks_built = false; - - } else { - - if (stat (peakpath.c_str(), &statbuf)) { - if (errno != ENOENT) { - /* it exists in the peaks dir, but there is some kind of error */ - - error << string_compose(_("Source: cannot stat peakfile \"%1\""), peakpath) << endmsg; - return -1; - } - - } else { - - /* we found it in the peaks dir */ - } - - if (statbuf.st_size == 0) { - _peaks_built = false; - } else { - // Check if the audio file has changed since the peakfile was built. - struct stat stat_file; - int err = stat (audio_path.c_str(), &stat_file); - - if (!err && stat_file.st_mtime > statbuf.st_mtime){ - _peaks_built = false; - } else { - _peaks_built = true; - } - } - } - - if (!newfile && !_peaks_built && _build_missing_peakfiles && _build_peakfiles) { - build_peaks_from_scratch (); - } - - return 0; -} - -int -Source::read_peaks (PeakData *peaks, jack_nframes_t npeaks, jack_nframes_t start, jack_nframes_t cnt, double samples_per_visual_peak) const -{ - Glib::Mutex::Lock lm (_lock); - double scale; - double expected_peaks; - PeakData::PeakDatum xmax; - PeakData::PeakDatum xmin; - int32_t to_read; - uint32_t nread; - jack_nframes_t zero_fill = 0; - int ret = -1; - PeakData* staging = 0; - Sample* raw_staging = 0; - char * workbuf = 0; - int peakfile = -1; - - expected_peaks = (cnt / (double) frames_per_peak); - scale = npeaks/expected_peaks; - -#if 0 - cerr << "======>RP: npeaks = " << npeaks - << " start = " << start - << " cnt = " << cnt - << " len = " << _length - << " samples_per_visual_peak =" << samples_per_visual_peak - << " expected was " << expected_peaks << " ... scale = " << scale - << " PD ptr = " << peaks - < _length - start) { - // cerr << "too close to end @ " << _length << " given " << start << " + " << cnt << endl; - cnt = _length - start; - jack_nframes_t old = npeaks; - npeaks = min ((jack_nframes_t) floor (cnt / samples_per_visual_peak), npeaks); - zero_fill = old - npeaks; - } - - // cerr << "actual npeaks = " << npeaks << " zf = " << zero_fill << endl; - - if (npeaks == cnt) { - - // cerr << "RAW DATA\n"; - - /* no scaling at all, just get the sample data and duplicate it for - both max and min peak values. - */ - - Sample* raw_staging = new Sample[cnt]; - workbuf = new char[cnt*4]; - - if (read_unlocked (raw_staging, start, cnt, workbuf) != cnt) { - error << _("cannot read sample data for unscaled peak computation") << endmsg; - return -1; - } - - for (jack_nframes_t i = 0; i < npeaks; ++i) { - peaks[i].max = raw_staging[i]; - peaks[i].min = raw_staging[i]; - } - - delete [] raw_staging; - delete [] workbuf; - return 0; - } - - if (scale == 1.0) { - - off_t first_peak_byte = (start / frames_per_peak) * sizeof (PeakData); - - /* open, read, close */ - - if ((peakfile = ::open (peakpath.c_str(), O_RDWR|O_CREAT, 0664)) < 0) { - error << string_compose(_("Source: cannot open peakpath \"%1\" (%2)"), peakpath, strerror (errno)) << endmsg; - return -1; - } - - // cerr << "DIRECT PEAKS\n"; - - nread = ::pread (peakfile, peaks, sizeof (PeakData)* npeaks, first_peak_byte); - close (peakfile); - - if (nread != sizeof (PeakData) * npeaks) { - cerr << "Source[" - << _name - << "]: cannot read peaks from peakfile! (read only " - << nread - << " not " - << npeaks - << "at sample " - << start - << " = byte " - << first_peak_byte - << ')' - << endl; - return -1; - } - - if (zero_fill) { - memset (&peaks[npeaks], 0, sizeof (PeakData) * zero_fill); - } - - return 0; - } - - - jack_nframes_t tnp; - - if (scale < 1.0) { - - // cerr << "DOWNSAMPLE\n"; - - /* the caller wants: - - - more frames-per-peak (lower resolution) than the peakfile, or to put it another way, - - less peaks than the peakfile holds for the same range - - So, read a block into a staging area, and then downsample from there. - - to avoid confusion, I'll refer to the requested peaks as visual_peaks and the peakfile peaks as stored_peaks - */ - - const uint32_t chunksize = (uint32_t) min (expected_peaks, 4096.0); - - staging = new PeakData[chunksize]; - - /* compute the rounded up frame position */ - - jack_nframes_t current_frame = start; - jack_nframes_t current_stored_peak = (jack_nframes_t) ceil (current_frame / (double) frames_per_peak); - uint32_t next_visual_peak = (uint32_t) ceil (current_frame / samples_per_visual_peak); - double next_visual_peak_frame = next_visual_peak * samples_per_visual_peak; - uint32_t stored_peak_before_next_visual_peak = (jack_nframes_t) next_visual_peak_frame / frames_per_peak; - uint32_t nvisual_peaks = 0; - uint32_t stored_peaks_read = 0; - uint32_t i = 0; - - /* handle the case where the initial visual peak is on a pixel boundary */ - - current_stored_peak = min (current_stored_peak, stored_peak_before_next_visual_peak); - - /* open ... close during out: handling */ - - if ((peakfile = ::open (peakpath.c_str(), O_RDWR|O_CREAT, 0664)) < 0) { - error << string_compose(_("Source: cannot open peakpath \"%1\" (%2)"), peakpath, strerror (errno)) << endmsg; - return 0; - } - - while (nvisual_peaks < npeaks) { - - if (i == stored_peaks_read) { - - uint32_t start_byte = current_stored_peak * sizeof(PeakData); - tnp = min ((_length/frames_per_peak - current_stored_peak), (jack_nframes_t) expected_peaks); - to_read = min (chunksize, tnp); - - off_t fend = lseek (peakfile, 0, SEEK_END); - - if ((nread = ::pread (peakfile, staging, sizeof (PeakData) * to_read, start_byte)) - != sizeof (PeakData) * to_read) { - cerr << "Source[" - << _name - << "]: cannot read peak data from peakfile (" - << (nread / sizeof(PeakData)) - << " peaks instead of " - << to_read - << ") (" - << strerror (errno) - << ')' - << " at start_byte = " << start_byte - << " _length = " << _length << " versus len = " << fend - << " expected maxpeaks = " << (_length - current_frame)/frames_per_peak - << " npeaks was " << npeaks - << endl; - goto out; - } - - i = 0; - stored_peaks_read = nread / sizeof(PeakData); - } - - xmax = -1.0; - xmin = 1.0; - - while ((i < stored_peaks_read) && (current_stored_peak <= stored_peak_before_next_visual_peak)) { - - xmax = max (xmax, staging[i].max); - xmin = min (xmin, staging[i].min); - ++i; - ++current_stored_peak; - --expected_peaks; - } - - peaks[nvisual_peaks].max = xmax; - peaks[nvisual_peaks].min = xmin; - ++nvisual_peaks; - ++next_visual_peak; - - //next_visual_peak_frame = min ((next_visual_peak * samples_per_visual_peak), (next_visual_peak_frame+samples_per_visual_peak) ); - next_visual_peak_frame = min ((double) start+cnt, (next_visual_peak_frame+samples_per_visual_peak) ); - stored_peak_before_next_visual_peak = (uint32_t) next_visual_peak_frame / frames_per_peak; - } - - if (zero_fill) { - memset (&peaks[npeaks], 0, sizeof (PeakData) * zero_fill); - } - - ret = 0; - - } else { - - // cerr << "UPSAMPLE\n"; - - /* the caller wants - - - less frames-per-peak (more resolution) - - more peaks than stored in the Peakfile - - So, fetch data from the raw source, and generate peak - data on the fly. - */ - - jack_nframes_t frames_read = 0; - jack_nframes_t current_frame = start; - jack_nframes_t i = 0; - jack_nframes_t nvisual_peaks = 0; - jack_nframes_t chunksize = (jack_nframes_t) min (cnt, (jack_nframes_t) 4096); - raw_staging = new Sample[chunksize]; - workbuf = new char[chunksize *4]; - - jack_nframes_t frame_pos = start; - double pixel_pos = floor (frame_pos / samples_per_visual_peak); - double next_pixel_pos = ceil (frame_pos / samples_per_visual_peak); - double pixels_per_frame = 1.0 / samples_per_visual_peak; - - xmin = 1.0; - xmax = -1.0; - - while (nvisual_peaks < npeaks) { - - if (i == frames_read) { - - to_read = min (chunksize, (_length - current_frame)); - - if ((frames_read = read_unlocked (raw_staging, current_frame, to_read, workbuf)) < 0) { - error << string_compose(_("Source[%1]: peak read - cannot read %2 samples at offset %3") - , _name, to_read, current_frame) - << endmsg; - goto out; - } - - i = 0; - } - - xmax = max (xmax, raw_staging[i]); - xmin = min (xmin, raw_staging[i]); - ++i; - ++current_frame; - pixel_pos += pixels_per_frame; - - if (pixel_pos >= next_pixel_pos) { - - peaks[nvisual_peaks].max = xmax; - peaks[nvisual_peaks].min = xmin; - ++nvisual_peaks; - xmin = 1.0; - xmax = -1.0; - - next_pixel_pos = ceil (pixel_pos + 0.5); - } - } - - if (zero_fill) { - memset (&peaks[npeaks], 0, sizeof (PeakData) * zero_fill); - } - - ret = 0; - } - - out: - if (peakfile >= 0) { - close (peakfile); - } - - if (staging) { - delete [] staging; - } - - if (raw_staging) { - delete [] raw_staging; - } - - if (workbuf) { - delete [] workbuf; - } - - return ret; -} - -#undef DEBUG_PEAK_BUILD - -int -Source::build_peaks () -{ - vector built; - int status = -1; - bool pr_signal = false; - list copy; - - { - Glib::Mutex::Lock lm (_lock); - copy = pending_peak_builds; - pending_peak_builds.clear (); - } - -#ifdef DEBUG_PEAK_BUILD - cerr << "build peaks with " << copy.size() << " requests pending\n"; -#endif - - for (list::iterator i = copy.begin(); i != copy.end(); ++i) { - - if ((status = do_build_peak ((*i)->frame, (*i)->cnt)) != 0) { - unlink (peakpath.c_str()); - break; - } - built.push_back (new PeakBuildRecord (*(*i))); - delete *i; - } - - { - Glib::Mutex::Lock lm (_lock); - - if (status == 0) { - _peaks_built = true; - - if (next_peak_clear_should_notify) { - next_peak_clear_should_notify = false; - pr_signal = true; - } - } - } - - if (status == 0) { - for (vector::iterator i = built.begin(); i != built.end(); ++i) { - PeakRangeReady ((*i)->frame, (*i)->cnt); /* EMIT SIGNAL */ - delete *i; - } - - if (pr_signal) { - PeaksReady (); /* EMIT SIGNAL */ - } - } - - return status; -} - -int -Source::do_build_peak (jack_nframes_t first_frame, jack_nframes_t cnt) -{ - jack_nframes_t current_frame; - Sample buf[frames_per_peak]; - Sample xmin, xmax; - uint32_t peaki; - PeakData* peakbuf; - char * workbuf = 0; - jack_nframes_t frames_read; - jack_nframes_t frames_to_read; - off_t first_peak_byte; - int peakfile = -1; - int ret = -1; - -#ifdef DEBUG_PEAK_BUILD - cerr << pthread_self() << ": " << _name << ": building peaks for " << first_frame << " to " << first_frame + cnt - 1 << endl; -#endif - - first_peak_byte = (first_frame / frames_per_peak) * sizeof (PeakData); - -#ifdef DEBUG_PEAK_BUILD - cerr << "seeking to " << first_peak_byte << " before writing new peak data\n"; -#endif - - current_frame = first_frame; - peakbuf = new PeakData[(cnt/frames_per_peak)+1]; - peaki = 0; - - workbuf = new char[max(frames_per_peak, cnt) * 4]; - - if ((peakfile = ::open (peakpath.c_str(), O_RDWR|O_CREAT, 0664)) < 0) { - error << string_compose(_("Source: cannot open peakpath \"%1\" (%2)"), peakpath, strerror (errno)) << endmsg; - return -1; - } - - while (cnt) { - - frames_to_read = min (frames_per_peak, cnt); - - if ((frames_read = read_unlocked (buf, current_frame, frames_to_read, workbuf)) != frames_to_read) { - error << string_compose(_("%1: could not write read raw data for peak computation (%2)"), _name, strerror (errno)) << endmsg; - goto out; - } - - xmin = buf[0]; - xmax = buf[0]; - - for (jack_nframes_t n = 1; n < frames_read; ++n) { - xmax = max (xmax, buf[n]); - xmin = min (xmin, buf[n]); - -// if (current_frame < frames_read) { -// cerr << "sample = " << buf[n] << " max = " << xmax << " min = " << xmin << " max of 2 = " << max (xmax, buf[n]) << endl; -// } - } - - peakbuf[peaki].max = xmax; - peakbuf[peaki].min = xmin; - peaki++; - - current_frame += frames_read; - cnt -= frames_read; - } - - if (::pwrite (peakfile, peakbuf, sizeof (PeakData) * peaki, first_peak_byte) != (ssize_t) (sizeof (PeakData) * peaki)) { - error << string_compose(_("%1: could not write peak file data (%2)"), _name, strerror (errno)) << endmsg; - goto out; - } - - ret = 0; - - out: - delete [] peakbuf; - if (peakfile >= 0) { - close (peakfile); - } - if (workbuf) - delete [] workbuf; - return ret; -} - -void -Source::build_peaks_from_scratch () -{ - Glib::Mutex::Lock lp (_lock); - - next_peak_clear_should_notify = true; - pending_peak_builds.push_back (new PeakBuildRecord (0, _length)); - queue_for_peaks (*this); -} - -bool -Source::file_changed (string path) -{ - struct stat stat_file; - struct stat stat_peak; - - int e1 = stat (path.c_str(), &stat_file); - int e2 = stat (peak_path(path).c_str(), &stat_peak); - - if (!e1 && !e2 && stat_file.st_mtime > stat_peak.st_mtime){ - return true; - } else { - return false; - } -} - void Source::use () { @@ -864,30 +118,3 @@ Source::release () if (_use_cnt) --_use_cnt; } -jack_nframes_t -Source::available_peaks (double zoom_factor) const -{ - int peakfile; - off_t end; - - if (zoom_factor < frames_per_peak) { - return length(); // peak data will come from the audio file - } - - /* peak data comes from peakfile */ - - if ((peakfile = ::open (peakpath.c_str(), O_RDONLY)) < 0) { - error << string_compose(_("Source: cannot open peakpath \"%1\" (%2)"), peakpath, strerror (errno)) << endmsg; - return 0; - } - - { - Glib::Mutex::Lock lm (_lock); - end = lseek (peakfile, 0, SEEK_END); - } - - close (peakfile); - - return (end/sizeof(PeakData)) * frames_per_peak; -} - diff --git a/libs/ardour/state_manager.cc b/libs/ardour/state_manager.cc index bb24c8eb58..bcffe381c3 100644 --- a/libs/ardour/state_manager.cc +++ b/libs/ardour/state_manager.cc @@ -5,6 +5,7 @@ using namespace ARDOUR; using namespace std; +using namespace PBD; bool StateManager::_allow_save = true; sigc::signal StateManager::SaveAllowed; diff --git a/libs/ardour/stateful.cc b/libs/ardour/stateful.cc index d08be38ecd..b8e301b273 100644 --- a/libs/ardour/stateful.cc +++ b/libs/ardour/stateful.cc @@ -27,6 +27,8 @@ #include "i18n.h" +using namespace PBD; + Stateful::Stateful () { _extra_xml = 0; diff --git a/libs/ardour/tempo.cc b/libs/ardour/tempo.cc index 64964b29dd..c0e52279e1 100644 --- a/libs/ardour/tempo.cc +++ b/libs/ardour/tempo.cc @@ -35,6 +35,7 @@ using namespace std; using namespace ARDOUR; +using namespace PBD; /* _default tempo is 4/4 qtr=120 */ diff --git a/libs/ardour/utils.cc b/libs/ardour/utils.cc index 15d0c6be81..9adc7c72cd 100644 --- a/libs/ardour/utils.cc +++ b/libs/ardour/utils.cc @@ -42,6 +42,7 @@ using namespace ARDOUR; using namespace std; +using namespace PBD; void elapsed_time_to_str (char *buf, uint32_t seconds) @@ -177,7 +178,7 @@ tokenize_fullpath (string fullpath, string& path, string& name) int touch_file (string path) { - int fd = open (path.c_str(), O_RDONLY|O_CREAT); + int fd = open (path.c_str(), O_RDWR|O_CREAT, 0660); if (fd >= 0) { close (fd); return 0; diff --git a/libs/ardour/vst_plugin.cc b/libs/ardour/vst_plugin.cc index 2f3653a16a..80c36dab95 100644 --- a/libs/ardour/vst_plugin.cc +++ b/libs/ardour/vst_plugin.cc @@ -54,6 +54,7 @@ #include using namespace ARDOUR; +using namespace PBD; using std::min; using std::max; diff --git a/libs/fst/SConscript b/libs/fst/SConscript new file mode 100644 index 0000000000..0499f11c61 --- /dev/null +++ b/libs/fst/SConscript @@ -0,0 +1,27 @@ +# -*- python -*- + +import os +import os.path +import glob + +fst_src = glob.glob('*.c') + +Import('env install_prefix') +fst = env.Copy(CC="winegcc") +fst.Append (CPPPATH=".") + +hackSDK = fst.Command('vst/aeffectx.h', 'vstsdk2.3/source/common/aeffectx.h', [ + Delete ('${TARGET.dir}'), + Copy ('${TARGET.dir}', '${SOURCE.dir}'), + "sed -i '/struct VstFileType\|struct VstFileSelect/,/};/d' $TARGET" +]) + +a = fst.Object ('fst', 'fst.c') +b = fst.Object ('fstinfofile', 'fstinfofile.c') +c = fst.Object ('vstwin', 'vstwin.c') +d = fst.Object ('vsti', 'vsti.c') + +Default([hackSDK,a,b,c,d]) + +env.Alias('tarball', env.Distribute (env['DISTTREE'], fst_src + ['SConscript'] )) + diff --git a/libs/fst/fst.c b/libs/fst/fst.c new file mode 100644 index 0000000000..85473578d2 --- /dev/null +++ b/libs/fst/fst.c @@ -0,0 +1,27 @@ +#include +#include + +#include "fst.h" + + +void +default_fst_error_callback (const char *desc) +{ + fprintf(stderr, "%s\n", desc); +} + +void (*fst_error_callback)(const char *desc) = &default_fst_error_callback; + +void +fst_error (const char *fmt, ...) +{ + va_list ap; + char buffer[512]; + + va_start (ap, fmt); + vsnprintf (buffer, sizeof(buffer), fmt, ap); + fst_error_callback (buffer); + va_end (ap); +} + + diff --git a/libs/fst/fst.h b/libs/fst/fst.h new file mode 100644 index 0000000000..9055eac620 --- /dev/null +++ b/libs/fst/fst.h @@ -0,0 +1,108 @@ +#ifndef __fst_fst_h__ +#define __fst_fst_h__ + +#include +#include +#include + +/** + * Display FST error message. + * + * @param fmt printf-style formatting specification + */ +extern void fst_error (const char *fmt, ...); + +/** + * Set the @ref fst_error_callback for error message display. + * + * The FST library provides two built-in callbacks for this purpose: + * default_fst_error_callback(). + * + * The default will print the message (plus a newline) to stderr. + * + */ +void fst_set_error_function (void (*func)(const char *)); + +#include + +typedef struct _FST FST; +typedef struct _FSTHandle FSTHandle; +typedef struct _FSTInfo FSTInfo; + +struct _FSTInfo +{ + char *name; + int UniqueID; + char *Category; + + int numInputs; + int numOutputs; + int numParams; + + int wantMidi; + int wantEvents; + int hasEditor; + int canProcessReplacing; // what do we need this for ? + + // i think we should save the parameter Info Stuff soon. + // struct VstParameterInfo *infos; + char **ParamNames; + char **ParamLabels; +}; + +struct _FSTHandle +{ + void* dll; + char* name; + char* nameptr; /* ptr returned from strdup() etc. */ + AEffect* (*main_entry)(audioMasterCallback); + + int plugincnt; +}; + +struct _FST +{ + AEffect* plugin; + void* window; /* win32 HWND */ + int xid; /* X11 XWindow */ + FSTHandle* handle; + int width; + int height; + int destroy; + + struct _FST* next; + + pthread_mutex_t lock; + pthread_cond_t window_status_change; + int been_activated; +}; + +#ifdef __cplusplus +extern "C" { +#endif + +extern int fst_init (); + +extern FSTHandle* fst_load (const char*); +extern int fst_unload (FSTHandle*); + +extern FST* fst_instantiate (FSTHandle*, audioMasterCallback amc, void* userptr); +extern void fst_close (FST*); + +extern void fst_event_loop_remove_plugin (FST* fst); +extern void fst_event_loop_add_plugin (FST* fst); + +extern int fst_run_editor (FST*); +extern void fst_destroy_editor (FST*); +extern int fst_get_XID (FST*); + +extern void fst_signal_handler (int sig, siginfo_t* info, void* context); + +extern FSTInfo *fst_get_info( char *dllpathname ); +extern void fst_free_info( FSTInfo *info ); + +#ifdef __cplusplus +} +#endif + +#endif /* __fst_fst_h__ */ diff --git a/libs/fst/fstinfofile.c b/libs/fst/fstinfofile.c new file mode 100644 index 0000000000..7cc98d2233 --- /dev/null +++ b/libs/fst/fstinfofile.c @@ -0,0 +1,266 @@ + +#include "fst.h" +#include "vst/aeffectx.h" + +#include +#include +#include + +#include +#include +#include +#include + +#define MAX_STRING_LEN 256 + +#define FALSE 0 +#define TRUE !FALSE + +static char *read_string( FILE *fp ) { + char buf[MAX_STRING_LEN]; + + fgets( buf, MAX_STRING_LEN, fp ); + if( strlen( buf ) < MAX_STRING_LEN ) { + + if( strlen(buf) ) + buf[strlen(buf)-1] = 0; + + return strdup( buf ); + } else { + return NULL; + } +} + +static FSTInfo *load_fst_info_file( char *filename ) { + + FSTInfo *info = (FSTInfo *) malloc( sizeof( FSTInfo ) ); + FILE *fp; + int i; + + + if( info == NULL ) + return NULL; + + fp = fopen( filename, "r" ); + + if( fp == NULL ) { + free( info ); + return NULL; + } + + if( (info->name = read_string( fp )) == NULL ) goto error; + if( 1 != fscanf( fp, "%d\n", &info->UniqueID ) ) goto error; + if( (info->Category = read_string( fp )) == NULL ) goto error; + if( 1 != fscanf( fp, "%d\n", &info->numInputs ) ) goto error; + if( 1 != fscanf( fp, "%d\n", &info->numOutputs ) ) goto error; + if( 1 != fscanf( fp, "%d\n", &info->numParams ) ) goto error; + if( 1 != fscanf( fp, "%d\n", &info->wantMidi ) ) goto error; + if( 1 != fscanf( fp, "%d\n", &info->hasEditor ) ) goto error; + if( 1 != fscanf( fp, "%d\n", &info->canProcessReplacing ) ) goto error; + + if( (info->ParamNames = (char **) malloc( sizeof( char * ) * info->numParams )) == NULL ) goto error; + for( i=0; inumParams; i++ ) { + if( (info->ParamNames[i] = read_string( fp )) == NULL ) goto error; + } + if( (info->ParamLabels = (char **) malloc( sizeof( char * ) * info->numParams )) == NULL ) goto error; + for( i=0; inumParams; i++ ) { + if( (info->ParamLabels[i] = read_string( fp )) == NULL ) goto error; + } + + + fclose( fp ); + return info; + +error: + fclose( fp ); + free( info ); + return NULL; +} + +static int save_fst_info_file( FSTInfo *info, char *filename ) { + + FILE *fp; + int i; + + + if( info == NULL ) { + fst_error( "info is NULL\n" ); + return TRUE; + } + + fp = fopen( filename, "w" ); + + if( fp == NULL ) { + fst_error( "Cant write info file %s\n", filename ); + return TRUE; + } + + fprintf( fp, "%s\n", info->name ); + fprintf( fp, "%d\n", info->UniqueID ); + fprintf( fp, "%s\n", info->Category ); + fprintf( fp, "%d\n", info->numInputs ); + fprintf( fp, "%d\n", info->numOutputs ); + fprintf( fp, "%d\n", info->numParams ); + fprintf( fp, "%d\n", info->wantMidi ); + fprintf( fp, "%d\n", info->hasEditor ); + fprintf( fp, "%d\n", info->canProcessReplacing ); + + for( i=0; inumParams; i++ ) { + fprintf( fp, "%s\n", info->ParamNames[i] ); + } + for( i=0; inumParams; i++ ) { + fprintf( fp, "%s\n", info->ParamLabels[i] ); + } + + + fclose( fp ); + + return FALSE; +} + +static char *fst_dllpath_to_infopath( char *dllpath ) { + char *retval; + if( strstr( dllpath, ".dll" ) == NULL ) return NULL; + + retval = strdup( dllpath ); + sprintf( retval + strlen(retval) - 4, ".fst" ); + return retval; +} + +static int fst_info_file_is_valid( char *dllpath ) { + struct stat dllstat, fststat; + char *fstpath = fst_dllpath_to_infopath( dllpath ); + + if( !fstpath ) return FALSE; + + if( stat( dllpath, &dllstat ) ){ fst_error( "dll path %s invalid\n", dllpath ); return TRUE; } + if( stat( fstpath, &fststat ) ) return FALSE; + + free( fstpath ); + if( dllstat.st_mtime > fststat.st_mtime ) + return FALSE; + else + return TRUE; +} + +static int fst_can_midi( FST *fst ) { + AEffect *plugin = fst->plugin; + int vst_version = plugin->dispatcher (plugin, effGetVstVersion, 0, 0, NULL, 0.0f); + + if (vst_version >= 2) { + + /* should we send it VST events (i.e. MIDI) */ + + if ((plugin->flags & effFlagsIsSynth) || + (plugin->dispatcher (plugin, effCanDo, 0, 0,(void*) "receiveVstEvents", 0.0f) > 0)) + return TRUE; + } + return FALSE; + +} +static FSTInfo *fst_info_from_plugin( FST *fst ) { + FSTInfo *info = (FSTInfo *) malloc( sizeof( FSTInfo ) ); + AEffect *plugin; + int i; + + if( ! fst ) { + fst_error( "fst is NULL\n" ); + return NULL; + } + + if( ! info ) return NULL; + + plugin = fst->plugin; + + + info->name = strdup(fst->handle->name ); + info->UniqueID = plugin->uniqueID; + info->Category = strdup( "None" ); // FIXME: + info->numInputs = plugin->numInputs; + info->numOutputs = plugin->numOutputs; + info->numParams = plugin->numParams; + info->wantMidi = fst_can_midi( fst ); + info->hasEditor = plugin->flags & effFlagsHasEditor ? TRUE : FALSE; + info->canProcessReplacing = plugin->flags & effFlagsCanReplacing ? TRUE : FALSE; + + info->ParamNames = (char **) malloc( sizeof( char * ) * info->numParams ); + info->ParamLabels = (char **) malloc( sizeof( char * ) * info->numParams ); + for( i=0; inumParams; i++ ) { + char name[20]; + char label[9]; + plugin->dispatcher (plugin, + effGetParamName, + i, 0, name, 0); + + plugin->dispatcher (plugin, + effGetParamLabel, + i, 0, label, 0); + + info->ParamNames[i] = strdup( name ); + info->ParamLabels[i] = strdup( label ); + } + return info; +} + +// most simple one :) could be sufficient.... +static long simple_master_callback( AEffect *fx, long opcode, long index, long value, void *ptr, float opt ) { + if( opcode == audioMasterVersion ) + return 2; + else + return 0; +} + +FSTInfo *fst_get_info( char *dllpath ) { + + if( fst_info_file_is_valid( dllpath ) ) { + FSTInfo *info; + char *fstpath = fst_dllpath_to_infopath( dllpath ); + + info = load_fst_info_file( fstpath ); + free( fstpath ); + return info; + + } else { + + FSTHandle *h; + FST *fst; + FSTInfo *info; + char *fstpath; + + if( !(h = fst_load( dllpath )) ) return NULL; + if( !(fst = fst_instantiate( h, simple_master_callback, NULL )) ) { + fst_unload( h ); + fst_error( "instantiate failed\n" ); + return NULL; + } + fstpath = fst_dllpath_to_infopath( dllpath ); + if( !fstpath ) { + fst_close( fst ); + fst_unload( h ); + fst_error( "get fst filename failed\n" ); + return NULL; + } + info = fst_info_from_plugin( fst ); + save_fst_info_file( info, fstpath ); + + free( fstpath ); + fst_close( fst ); + fst_unload( h ); + return info; + } +} + +void fst_free_info( FSTInfo *info ) { + + int i; + + for( i=0; inumParams; i++ ) { + free( info->ParamNames[i] ); + free( info->ParamLabels[i] ); + } + free( info->name ); + free( info->Category ); + free( info ); +} + + diff --git a/libs/fst/jackvst.h b/libs/fst/jackvst.h new file mode 100644 index 0000000000..abb9e22e12 --- /dev/null +++ b/libs/fst/jackvst.h @@ -0,0 +1,35 @@ +#ifndef __jack_vst_h__ +#define __jack_vst_h__ + +#include +#include +#include +#include +#include +#include + +typedef struct _JackVST JackVST; + +struct _JackVST { + jack_client_t *client; + FSTHandle* handle; + FST* fst; + float **ins; + float **outs; + jack_port_t **inports; + jack_port_t **outports; + void* userdata; + int bypassed; + int muted; + + int resume_called; + /* For VST/i support */ + + pthread_t midi_thread; + snd_seq_t* seq; + int midiquit; + jack_ringbuffer_t* event_queue; + struct VstEvents* events; +}; + +#endif /* __jack_vst_h__ */ diff --git a/libs/fst/vsti.c b/libs/fst/vsti.c new file mode 100644 index 0000000000..f6d8725ddf --- /dev/null +++ b/libs/fst/vsti.c @@ -0,0 +1,181 @@ +/* + * VST instrument support + * + * Derived from code that was marked: + * Copyright (C) Kjetil S. Matheussen 2004 (k.s.matheussen@notam02.no) + * Alsa-seq midi-code made by looking at the jack-rack source made by Bob Ham. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id: vsti.c,v 1.2 2004/04/07 01:56:23 pauld Exp $ + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include + +snd_seq_t * +create_sequencer (const char* client_name, bool isinput) +{ + snd_seq_t * seq; + int err; + + if ((err = snd_seq_open (&seq, "default", SND_SEQ_OPEN_DUPLEX, 0)) != 0) { + fst_error ("Could not open ALSA sequencer, aborting\n\n%s\n\n" + "Make sure you have configure ALSA properly and that\n" + "/proc/asound/seq/clients exists and contains relevant\n" + "devices (%s).", + snd_strerror (err)); + return NULL; + } + + snd_seq_set_client_name (seq, client_name); + + if ((err = snd_seq_create_simple_port (seq, isinput? "Input" : "Output", + (isinput? SND_SEQ_PORT_CAP_WRITE: SND_SEQ_PORT_CAP_READ)| SND_SEQ_PORT_CAP_DUPLEX | + SND_SEQ_PORT_CAP_SUBS_READ|SND_SEQ_PORT_CAP_SUBS_WRITE, + SND_SEQ_PORT_TYPE_APPLICATION|SND_SEQ_PORT_TYPE_SPECIFIC)) != 0) { + fst_error ("Could not create ALSA port: %s", snd_strerror (err)); + snd_seq_close(seq); + return NULL; + } + + return seq; +} + +static void +queue_midi (JackVST *jvst, int val1, int val2, int val3) +{ + struct VstMidiEvent *pevent; + jack_ringbuffer_data_t vec[2]; + + jack_ringbuffer_get_write_vector (jvst->event_queue, vec); + + if (vec[0].len < sizeof (struct VstMidiEvent)) { + fst_error ("event queue has no write space"); + return; + } + + pevent = (struct VstMidiEevent *) vec[0].buf; + + // printf("note: %d\n",note); + + pevent->type = kVstMidiType; + pevent->byteSize = 24; + pevent->deltaFrames = 0; + pevent->flags = 0; + pevent->detune = 0; + pevent->noteLength = 0; + pevent->noteOffset = 0; + pevent->reserved1 = 0; + pevent->reserved2 = 0; + pevent->noteOffVelocity = 0; + pevent->midiData[0] = val1; + pevent->midiData[1] = val2; + pevent->midiData[2] = val3; + pevent->midiData[3] = 0; + + //printf("Sending: %x %x %x\n",val1,val2,val3); + + jack_ringbuffer_write_advance (jvst->event_queue, sizeof (struct VstMidiEvent)); +} + +void *midireceiver(void *arg) +{ + snd_seq_event_t *event; + JackVST *jvst = (JackVST* )arg; + int val; + + while (1) { + + snd_seq_event_input (jvst->seq, &event); + + if (jvst->midiquit) { + break; + } + + switch(event->type){ + case SND_SEQ_EVENT_NOTEON: + queue_midi(jvst,0x90+event->data.note.channel,event->data.note.note,event->data.note.velocity); + //printf("Noteon, channel: %d note: %d vol: %d\n",event->data.note.channel,event->data.note.note,event->data.note.velocity); + break; + case SND_SEQ_EVENT_NOTEOFF: + queue_midi(jvst,0x80+event->data.note.channel,event->data.note.note,0); + //printf("Noteoff, channel: %d note: %d vol: %d\n",event->data.note.channel,event->data.note.note,event->data.note.velocity); + break; + case SND_SEQ_EVENT_KEYPRESS: + //printf("Keypress, channel: %d note: %d vol: %d\n",event->data.note.channel,event->data.note.note,event->data.note.velocity); + queue_midi(jvst,0xa0+event->data.note.channel,event->data.note.note,event->data.note.velocity); + break; + case SND_SEQ_EVENT_CONTROLLER: + queue_midi(jvst,0xb0+event->data.control.channel,event->data.control.param,event->data.control.value); + //printf("Control: %d %d %d\n",event->data.control.channel,event->data.control.param,event->data.control.value); + break; + case SND_SEQ_EVENT_PITCHBEND: + val=event->data.control.value + 0x2000; + queue_midi(jvst,0xe0+event->data.control.channel,val&127,val>>7); + //printf("Pitch: %d %d %d\n",event->data.control.channel,event->data.control.param,event->data.control.value); + break; + case SND_SEQ_EVENT_CHANPRESS: + //printf("chanpress: %d %d %d\n",event->data.control.channel,event->data.control.param,event->data.control.value); + queue_midi(jvst,0xd0+event->data.control.channel,event->data.control.value,0); + break; + case SND_SEQ_EVENT_PGMCHANGE: + //printf("pgmchange: %d %d %d\n",event->data.control.channel,event->data.control.param,event->data.control.value); + queue_midi(jvst,0xc0+event->data.control.channel,event->data.control.value,0); + break; + default: + //printf("Unknown type: %d\n",event->type); + break; + } + } + + return NULL; +} + +void stop_midireceiver (JackVST *jvst) +{ + int err; + snd_seq_event_t event; + snd_seq_t *seq2 = create_sequencer ("jfstquit", true); + + jvst->midiquit = 1; + + snd_seq_connect_to (seq2, 0, snd_seq_client_id (jvst->seq),0); + snd_seq_ev_clear (&event); + snd_seq_ev_set_direct (&event); + snd_seq_ev_set_subs (&event); + snd_seq_ev_set_source (&event, 0); + snd_seq_ev_set_controller (&event,1,0x80,50); + + if ((err = snd_seq_event_output (seq2, &event)) < 0) { + fst_error ("cannot send stop event to midi thread: %s\n", + snd_strerror (err)); + } + + snd_seq_drain_output (seq2); + snd_seq_close (seq2); + pthread_join (jvst->midi_thread,NULL); + snd_seq_close (jvst->seq); +} + + + diff --git a/libs/fst/vstwin.c b/libs/fst/vstwin.c new file mode 100644 index 0000000000..8911ff4a01 --- /dev/null +++ b/libs/fst/vstwin.c @@ -0,0 +1,583 @@ +#include +#include +#include +#include +#include +#include +#include + +//#include +//#include +//#include +//#include + +#include "fst.h" + + +struct ERect{ + short top; + short left; + short bottom; + short right; +}; + +static pthread_mutex_t plugin_mutex = PTHREAD_MUTEX_INITIALIZER; +static FST* fst_first = NULL; + +DWORD gui_thread_id = 0; + +static char* message_name (int message) +{ + switch (message) { + case 0x0000: + return "WM_NULL"; + + case 0x0001: + return "WM_CREATE"; + + case 0x0002: + return "WM_DESTROY"; + + case 0x0003: + return "WM_MOVE"; + + case 0x0004: + return "WM_SIZEWAIT"; + + case 0x0005: + return "WM_SIZE"; + + case 0x0006: + return "WM_ACTIVATE"; + + case 0x0007: + return "WM_SETFOCUS"; + + case 0x0008: + return "WM_KILLFOCUS"; + + case 0x0009: + return "WM_SETVISIBLE"; + + case 0x000a: + return "WM_ENABLE"; + + case 0x000b: + return "WM_SETREDRAW"; + + case 0x000c: + return "WM_SETTEXT"; + + case 0x000d: + return "WM_GETTEXT"; + + case 0x000e: + return "WM_GETTEXTLENGTH"; + + case 0x000f: + return "WM_PAINT"; + + case 0x0010: + return "WM_CLOSE"; + + case 0x0011: + return "WM_QUERYENDSESSION"; + + case 0x0012: + return "WM_QUIT"; + + case 0x0013: + return "WM_QUERYOPEN"; + + case 0x0014: + return "WM_ERASEBKGND"; + + case 0x0015: + return "WM_SYSCOLORCHANGE"; + + case 0x0016: + return "WM_ENDSESSION"; + + case 0x0017: + return "WM_SYSTEMERROR"; + + case 0x0018: + return "WM_SHOWWINDOW"; + + case 0x0019: + return "WM_CTLCOLOR"; + + case 0x001a: + return "WM_WININICHANGE"; + + case 0x001b: + return "WM_DEVMODECHANGE"; + + case 0x001c: + return "WM_ACTIVATEAPP"; + + case 0x001d: + return "WM_FONTCHANGE"; + + case 0x001e: + return "WM_TIMECHANGE"; + + case 0x001f: + return "WM_CANCELMODE"; + + case 0x0020: + return "WM_SETCURSOR"; + + case 0x0021: + return "WM_MOUSEACTIVATE"; + + case 0x0022: + return "WM_CHILDACTIVATE"; + + case 0x0023: + return "WM_QUEUESYNC"; + + case 0x0024: + return "WM_GETMINMAXINFO"; + + default: + break; + } + return "--- OTHER ---"; +} + +static LRESULT WINAPI +my_window_proc (HWND w, UINT msg, WPARAM wp, LPARAM lp) +{ + FST* fst; + +// if (msg != WM_TIMER) { +// fst_error ("window callback handler, msg = 0x%x (%s) win=%p\n", msg, message_name (msg), w); +// } + + switch (msg) { + case WM_KEYUP: + case WM_KEYDOWN: + break; + + case WM_CLOSE: + PostQuitMessage (0); + + case WM_DESTROY: + case WM_NCDESTROY: + /* we should never get these */ + //return 0; + break; + + case WM_PAINT: + if ((fst = GetPropA (w, "fst_ptr")) != NULL) { + if (fst->window && !fst->been_activated) { + fst->been_activated = TRUE; + pthread_cond_signal (&fst->window_status_change); + pthread_mutex_unlock (&fst->lock); + } + } + break; + + default: + break; + } + + return DefWindowProcA (w, msg, wp, lp ); +} + +static FST* +fst_new () +{ + FST* fst = (FST*) calloc (1, sizeof (FST)); + + pthread_mutex_init (&fst->lock, NULL); + pthread_cond_init (&fst->window_status_change, NULL); + + return fst; +} + +static FSTHandle* +fst_handle_new () +{ + FSTHandle* fst = (FSTHandle*) calloc (1, sizeof (FSTHandle)); + return fst; +} + +int +fst_create_editor (FST* fst) +{ + HMODULE hInst; + HWND window; + + /* "guard point" to trap errors that occur during plugin loading */ + + /* Note: fst->lock is held while this function is called */ + + if (!(fst->plugin->flags & effFlagsHasEditor)) { + fst_error ("Plugin \"%s\" has no editor", fst->handle->name); + return -1; + } + + if ((hInst = GetModuleHandleA (NULL)) == NULL) { + fst_error ("can't get module handle"); + return 1; + } + +// if ((window = CreateWindowExA (WS_EX_TOOLWINDOW | WS_EX_TRAYWINDOW, "FST", fst->handle->name, + if ((window = CreateWindowExA (0, "FST", fst->handle->name, + (WS_OVERLAPPEDWINDOW & ~WS_THICKFRAME & ~WS_MAXIMIZEBOX), + 0, 0, 1, 1, + NULL, NULL, + hInst, + NULL)) == NULL) { + fst_error ("cannot create editor window"); + return 1; + } + + if (!SetPropA (window, "fst_ptr", fst)) { + fst_error ("cannot set fst_ptr on window"); + } + + fst->window = window; + fst->xid = (int) GetPropA (window, "__wine_x11_whole_window"); + + { + struct ERect* er; + + ShowWindow (fst->window, SW_SHOW); + + fst->plugin->dispatcher (fst->plugin, effEditOpen, 0, 0, fst->window, 0 ); + fst->plugin->dispatcher (fst->plugin, effEditGetRect, 0, 0, &er, 0 ); + + fst->width = er->right-er->left; + fst->height = er->bottom-er->top; + + SetWindowPos (fst->window, 0, 0, 0, er->right-er->left+8, er->bottom-er->top+26, SWP_SHOWWINDOW|SWP_NOMOVE|SWP_NOZORDER); + } + + return 0; +} + +void +fst_destroy_editor (FST* fst) +{ + pthread_mutex_lock (&fst->lock); + if (fst->window) { + fst->destroy = TRUE; + if (!PostThreadMessageA (gui_thread_id, WM_USER, 0, 0)) { + fst_error ("could not post message to gui thread"); + } + pthread_cond_wait (&fst->window_status_change, &fst->lock); + + } + pthread_mutex_unlock (&fst->lock); +} + +void +fst_event_loop_remove_plugin (FST* fst) +{ + FST* p; + FST* prev; + + for (p = fst_first, prev = NULL; p->next; prev = p, p = p->next) { + if (p == fst) { + if (prev) { + prev->next = p->next; + } + } + } + + if (fst_first == fst) { + fst_first = fst_first->next; + } + +} + +void debreak( void ) { printf( "debreak\n" ); } + +DWORD WINAPI gui_event_loop (LPVOID param) +{ + MSG msg; + FST* fst; + HMODULE hInst; + HWND window; + + gui_thread_id = GetCurrentThreadId (); + + /* create a dummy window for timer events */ + + if ((hInst = GetModuleHandleA (NULL)) == NULL) { + fst_error ("can't get module handle"); + return 1; + } + + if ((window = CreateWindowExA (0, "FST", "dummy", + WS_OVERLAPPEDWINDOW & ~WS_THICKFRAME & ~WS_MAXIMIZEBOX, + CW_USEDEFAULT, CW_USEDEFAULT, + CW_USEDEFAULT, CW_USEDEFAULT, + NULL, NULL, + hInst, + NULL )) == NULL) { + fst_error ("cannot create dummy timer window"); + } + + if (!SetTimer (window, 1000, 100, NULL)) { + fst_error ("cannot set timer on dummy window"); + } + + while (GetMessageA (&msg, NULL, 0,0)) { + + if( msg.message == WM_KEYDOWN ) debreak(); + TranslateMessage( &msg ); + DispatchMessageA (&msg); + + /* handle window creation requests, destroy requests, + and run idle callbacks + */ + + + if( msg.message == WM_TIMER ) { + pthread_mutex_lock (&plugin_mutex); +again: + for (fst = fst_first; fst; fst = fst->next) { + + if (fst->destroy) { + if (fst->window) { + fst->plugin->dispatcher( fst->plugin, effEditClose, 0, 0, NULL, 0.0 ); + CloseWindow (fst->window); + fst->window = NULL; + fst->destroy = FALSE; + } + fst_event_loop_remove_plugin (fst); + fst->been_activated = FALSE; + pthread_mutex_lock (&fst->lock); + pthread_cond_signal (&fst->window_status_change); + pthread_mutex_unlock (&fst->lock); + goto again; + } + + if (fst->window == NULL) { + pthread_mutex_lock (&fst->lock); + if (fst_create_editor (fst)) { + fst_error ("cannot create editor for plugin %s", fst->handle->name); + fst_event_loop_remove_plugin (fst); + pthread_cond_signal (&fst->window_status_change); + pthread_mutex_unlock (&fst->lock); + goto again; + } + /* condition/unlock handled when we receive WM_ACTIVATE */ + } + + fst->plugin->dispatcher (fst->plugin, effEditIdle, 0, 0, NULL, 0); + } + pthread_mutex_unlock (&plugin_mutex); + } + } + fst_error ("FST GUI event loop has quit!"); + return 0; +} + +int +fst_init () +{ + WNDCLASSA wc; + HMODULE hInst; + + if ((hInst = GetModuleHandleA (NULL)) == NULL) { + fst_error ("can't get module handle"); + return -1; + } + wc.style = 0; + wc.lpfnWndProc = my_window_proc; + wc.cbClsExtra = 0; + wc.cbWndExtra = 0; + wc.hInstance = hInst; + wc.hIcon = LoadIconA( hInst, "FST"); + wc.hCursor = LoadCursorA( NULL, IDI_APPLICATION ); + wc.hbrBackground = GetStockObject( BLACK_BRUSH ); + wc.lpszMenuName = "MENU_FST"; + wc.lpszClassName = "FST"; + + if (!RegisterClassA(&wc)){ + return 1; + } + + if (CreateThread (NULL, 0, gui_event_loop, NULL, 0, NULL) == NULL) { + fst_error ("could not create new thread proxy"); + return -1; + } + + return 0; +} + +int +fst_run_editor (FST* fst) +{ + /* Add the FST to the list of all that should be handled by the GUI thread */ + + pthread_mutex_lock (&plugin_mutex); + + if (fst_first == NULL) { + fst_first = fst; + } else { + FST* p = fst_first; + while (p->next) { + p = p->next; + } + p->next = fst; + } + + if (!PostThreadMessageA (gui_thread_id, WM_USER, 0, 0)) { + fst_error ("could not post message to gui thread"); + return -1; + } + + pthread_mutex_unlock (&plugin_mutex); + + /* wait for the plugin editor window to be created (or not) */ + + pthread_mutex_lock (&fst->lock); + if (!fst->window) { + pthread_cond_wait (&fst->window_status_change, &fst->lock); + } + pthread_mutex_unlock (&fst->lock); + + if (!fst->window) { + fst_error ("no window created for VST plugin editor"); + return -1; + } + + return 0; +} + +FSTHandle* +fst_load (const char *path) +{ + char* buf; + FSTHandle* fhandle; + char* period; + + fhandle = fst_handle_new (); + + // XXX: Would be nice to find the correct call for this. + // if the user does not configure Z: to be / we are doomed :( + + if (strstr (path, ".dll") == NULL) { + + buf = (char *) malloc (strlen (path) + 7); + + if( path[0] == '/' ) { + sprintf (buf, "Z:%s.dll", path); + } else { + sprintf (buf, "%s.dll", path); + } + + fhandle->nameptr = strdup (path); + + } else { + + buf = (char *) malloc (strlen (path) + 3); + + if( path[0] == '/' ) { + sprintf (buf, "Z:%s", path); + } else { + sprintf (buf, "%s", path); + } + + fhandle->nameptr = strdup (path); + } + + fhandle->name = basename (fhandle->nameptr); + + /* strip off .dll */ + + if ((period = strrchr (fhandle->name, '.')) != NULL) { + *period = '\0'; + } + + if ((fhandle->dll = LoadLibraryA (buf)) == NULL) { + fst_unload (fhandle); + return NULL; + } + + if ((fhandle->main_entry = GetProcAddress (fhandle->dll, "main")) == NULL) { + fst_unload (fhandle); + return NULL; + } + + return fhandle; +} + +int +fst_unload (FSTHandle* fhandle) +{ + if (fhandle->plugincnt) { + return -1; + } + + if (fhandle->dll) { + FreeLibrary (fhandle->dll); + fhandle->dll = NULL; + } + + if (fhandle->nameptr) { + free (fhandle->nameptr); + fhandle->name = NULL; + } + + free (fhandle); + return 0; +} + +FST* +fst_instantiate (FSTHandle* fhandle, audioMasterCallback amc, void* userptr) +{ + FST* fst = fst_new (); + + if( fhandle == NULL ) { + fst_error( "the handle was NULL\n" ); + return NULL; + } + + if ((fst->plugin = fhandle->main_entry (amc)) == NULL) { + fst_error ("%s could not be instantiated\n", fhandle->name); + free (fst); + return NULL; + } + + fst->handle = fhandle; + fst->plugin->user = userptr; + + if (fst->plugin->magic != kEffectMagic) { + fst_error ("%s is not a VST plugin\n", fhandle->name); + free (fst); + return NULL; + } + + fst->plugin->dispatcher (fst->plugin, effOpen, 0, 0, 0, 0); + //fst->plugin->dispatcher (fst->plugin, effMainsChanged, 0, 0, NULL, 0); + + fst->handle->plugincnt++; + + return fst; +} + +void +fst_close (FST* fst) +{ + fst_destroy_editor (fst); + + fst->plugin->dispatcher (fst->plugin, effMainsChanged, 0, 0, NULL, 0); + fst->plugin->dispatcher (fst->plugin, effClose, 0, 0, 0, 0); + + if (fst->handle->plugincnt) { + --fst->handle->plugincnt; + } +} + +int +fst_get_XID (FST* fst) +{ + return fst->xid; +} diff --git a/libs/gtkmm2ext/fastmeter.cc b/libs/gtkmm2ext/fastmeter.cc index f0ee0ddea1..3c489e08ff 100644 --- a/libs/gtkmm2ext/fastmeter.cc +++ b/libs/gtkmm2ext/fastmeter.cc @@ -354,11 +354,12 @@ FastMeter::vertical_expose (GdkEventExpose* ev) // draw peak bar if (hold_state && intersection.width > 0) { gint y = pixheight - (gint) floor (pixheight * current_peak); + int h = min(3, pixheight - y); get_window()->draw_pixbuf (get_style()->get_fg_gc(get_state()), pixbuf, intersection.x, y, intersection.x, y, - intersection.width, 3, + intersection.width, h, Gdk::RGB_DITHER_NONE, 0, 0); } diff --git a/libs/gtkmm2ext/gtk_ui.cc b/libs/gtkmm2ext/gtk_ui.cc index 50d6114dee..55a6bebb02 100644 --- a/libs/gtkmm2ext/gtk_ui.cc +++ b/libs/gtkmm2ext/gtk_ui.cc @@ -43,6 +43,7 @@ using namespace Gtkmm2ext; using namespace Gtk; using namespace Glib; +using namespace PBD; using std::map; pthread_t UI::gui_thread; diff --git a/libs/gtkmm2ext/po/el_GR.po b/libs/gtkmm2ext/po/el_GR.po index 9329e844f9..cc10981aa8 100644 --- a/libs/gtkmm2ext/po/el_GR.po +++ b/libs/gtkmm2ext/po/el_GR.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: 0.99beta23\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-04-25 17:46-0400\n" +"POT-Creation-Date: 2006-06-21 15:09-0400\n" "PO-Revision-Date: 2005-01-11\n" "Last-Translator: Muadibas\n" "Language-Team: Hellenic(Greek) \n" @@ -15,12 +15,12 @@ msgstr "" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" -#: libs/gtkmm2ext/barcontroller.cc:431 libs/gtkmm2ext/bindable_button.cc:131 +#: libs/gtkmm2ext/barcontroller.cc:432 libs/gtkmm2ext/bindable_button.cc:131 #: libs/gtkmm2ext/controller.cc:50 libs/gtkmm2ext/slider_controller.cc:132 msgid "operate MIDI controller now" msgstr "λειτουÏγία ελεγκτή MIDI τώÏα" -#: libs/gtkmm2ext/gtk_ui.cc:509 +#: libs/gtkmm2ext/gtk_ui.cc:510 msgid "Press To Exit" msgstr "" diff --git a/libs/gtkmm2ext/po/es_ES.po b/libs/gtkmm2ext/po/es_ES.po index a51e058090..8b7dc8804d 100644 --- a/libs/gtkmm2ext/po/es_ES.po +++ b/libs/gtkmm2ext/po/es_ES.po @@ -6,7 +6,7 @@ msgid "" msgstr "" "Project-Id-Version: gtkmm2ext\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-04-25 17:46-0400\n" +"POT-Creation-Date: 2006-06-21 15:09-0400\n" "PO-Revision-Date: 2004-02-13 00:35+0300\n" "Last-Translator: Alex Krohn alexkrohn@fastmail.fm\n" "Language-Team: Spanish\n" @@ -14,12 +14,12 @@ msgstr "" "Content-Type: text/plain; charset=ISO-8859-1\n" "Content-Transfer-Encoding: 8bit\n" -#: libs/gtkmm2ext/barcontroller.cc:431 libs/gtkmm2ext/bindable_button.cc:131 +#: libs/gtkmm2ext/barcontroller.cc:432 libs/gtkmm2ext/bindable_button.cc:131 #: libs/gtkmm2ext/controller.cc:50 libs/gtkmm2ext/slider_controller.cc:132 msgid "operate MIDI controller now" msgstr "Operar controladora de MIDI ahora" -#: libs/gtkmm2ext/gtk_ui.cc:509 +#: libs/gtkmm2ext/gtk_ui.cc:510 msgid "Press To Exit" msgstr "" diff --git a/libs/gtkmm2ext/po/pt_BR.po b/libs/gtkmm2ext/po/pt_BR.po index 3cd751eb73..66381c2d37 100644 --- a/libs/gtkmm2ext/po/pt_BR.po +++ b/libs/gtkmm2ext/po/pt_BR.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: gtkmm2ext\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-04-25 17:46-0400\n" +"POT-Creation-Date: 2006-06-21 15:09-0400\n" "PO-Revision-Date: 2004-05-17 20:36+0200\n" "Last-Translator: Chris Ross \n" "Language-Team: Portuguese\n" @@ -15,12 +15,12 @@ msgstr "" "Content-Type: text/plain; charset=ISO-8859-15\n" "Content-Transfer-Encoding: 8bit\n" -#: libs/gtkmm2ext/barcontroller.cc:431 libs/gtkmm2ext/bindable_button.cc:131 +#: libs/gtkmm2ext/barcontroller.cc:432 libs/gtkmm2ext/bindable_button.cc:131 #: libs/gtkmm2ext/controller.cc:50 libs/gtkmm2ext/slider_controller.cc:132 msgid "operate MIDI controller now" msgstr "Operar controladora de MIDI agora" -#: libs/gtkmm2ext/gtk_ui.cc:509 +#: libs/gtkmm2ext/gtk_ui.cc:510 msgid "Press To Exit" msgstr "" diff --git a/libs/gtkmm2ext/po/ru_RU.po b/libs/gtkmm2ext/po/ru_RU.po index 7de883d439..4a3edcef5c 100644 --- a/libs/gtkmm2ext/po/ru_RU.po +++ b/libs/gtkmm2ext/po/ru_RU.po @@ -6,7 +6,7 @@ msgid "" msgstr "" "Project-Id-Version: gtkmm2ext\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-04-25 17:46-0400\n" +"POT-Creation-Date: 2006-06-21 15:09-0400\n" "PO-Revision-Date: 2004-02-13 00:35+0300\n" "Last-Translator: Igor Blinov pitstop@nm.ru\n" "Language-Team: Russian\n" @@ -14,12 +14,12 @@ msgstr "" "Content-Type: text/plain; charset=koi8-r\n" "Content-Transfer-Encoding: 8bit\n" -#: libs/gtkmm2ext/barcontroller.cc:431 libs/gtkmm2ext/bindable_button.cc:131 +#: libs/gtkmm2ext/barcontroller.cc:432 libs/gtkmm2ext/bindable_button.cc:131 #: libs/gtkmm2ext/controller.cc:50 libs/gtkmm2ext/slider_controller.cc:132 msgid "operate MIDI controller now" msgstr "×ËÌÀÞÉÔØ MIDI-ËÏÎÔÒÏÌÌÅÒ" -#: libs/gtkmm2ext/gtk_ui.cc:509 +#: libs/gtkmm2ext/gtk_ui.cc:510 msgid "Press To Exit" msgstr "" diff --git a/libs/gtkmm2ext/selector.cc b/libs/gtkmm2ext/selector.cc index 00db129d6b..7302de66e7 100644 --- a/libs/gtkmm2ext/selector.cc +++ b/libs/gtkmm2ext/selector.cc @@ -25,7 +25,6 @@ #include #include #include -#include using namespace std; using namespace Gtkmm2ext; diff --git a/libs/libsndfile/src/sndfile.c b/libs/libsndfile/src/sndfile.c index c30d7b61b4..b627c88ffe 100644 --- a/libs/libsndfile/src/sndfile.c +++ b/libs/libsndfile/src/sndfile.c @@ -1150,7 +1150,7 @@ sf_seek (SNDFILE *sndfile, sf_count_t offset, int whence) ** it makes sense. */ if (((whence & SFM_MASK) == SFM_WRITE && psf->mode == SFM_READ) || - ((whence & SFM_MASK) == SFM_WRITE && psf->mode == SFM_WRITE)) + ((whence & SFM_MASK) == SFM_READ && psf->mode == SFM_WRITE)) { psf->error = SFE_WRONG_SEEK ; return PSF_SEEK_ERROR ; } ; @@ -1210,10 +1210,25 @@ sf_seek (SNDFILE *sndfile, sf_count_t offset, int whence) if (psf->error) return PSF_SEEK_ERROR ; +#ifdef ECDL_ORIGINAL# if (seek_from_start < 0 || seek_from_start > psf->sf.frames) { psf->error = SFE_BAD_SEEK ; return PSF_SEEK_ERROR ; } ; +#else + if (((whence & SFM_MASK) == SFM_WRITE) || (psf->mode == SFM_WRITE || psf->mode == SFM_RDWR)) + { if (seek_from_start < 0 /* || (seek_from_start > psf->sf.frames && post-audio chunks exist) */ ) + { psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; + } + } + else /* seek for reading */ + { if (seek_from_start < 0 || seek_from_start > psf->sf.frames) + { psf->error = SFE_BAD_SEEK ; + return PSF_SEEK_ERROR ; + } + } +#endif if (psf->seek) { int new_mode = (whence & SFM_MASK) ? (whence & SFM_MASK) : psf->mode ; @@ -1234,6 +1249,7 @@ sf_seek (SNDFILE *sndfile, sf_count_t offset, int whence) break ; } ; + psf->last_op = new_mode ; return retval ; diff --git a/libs/libsndfile/src/wav.c b/libs/libsndfile/src/wav.c index f2fbcd7b50..c627738c39 100644 --- a/libs/libsndfile/src/wav.c +++ b/libs/libsndfile/src/wav.c @@ -539,7 +539,6 @@ wav_read_header (SF_PRIVATE *psf, int *blockalign, int *framesperblock) break ; case bext_MARKER : - parsestage |= HAVE_other ; psf_binheader_readf (psf, "4", &dword) ; if (dword < WAV_BEXT_CHUNK_SIZE) diff --git a/libs/midi++2/fd_midiport.cc b/libs/midi++2/fd_midiport.cc index 2ced63c259..1d21642a00 100644 --- a/libs/midi++2/fd_midiport.cc +++ b/libs/midi++2/fd_midiport.cc @@ -29,6 +29,7 @@ using namespace std; using namespace MIDI; +using namespace PBD; string *FD_MidiPort::midi_dirpath = 0; string *FD_MidiPort::midi_filename_pattern = 0; diff --git a/libs/midi++2/midicontrollable.cc b/libs/midi++2/midicontrollable.cc index f17782f3c4..f0dbd9cb77 100644 --- a/libs/midi++2/midicontrollable.cc +++ b/libs/midi++2/midicontrollable.cc @@ -26,6 +26,7 @@ using namespace sigc; using namespace MIDI; +using namespace PBD; Controllable::Controllable (Port *p, bool is_bistate) { diff --git a/libs/midi++2/midimanager.cc b/libs/midi++2/midimanager.cc index 692c06fe92..e25a2737ba 100644 --- a/libs/midi++2/midimanager.cc +++ b/libs/midi++2/midimanager.cc @@ -31,6 +31,7 @@ using namespace std; using namespace MIDI; +using namespace PBD; /* XXX check for strdup leaks */ diff --git a/libs/midi++2/mmc.cc b/libs/midi++2/mmc.cc index 3e1aefd4eb..61c47e856f 100644 --- a/libs/midi++2/mmc.cc +++ b/libs/midi++2/mmc.cc @@ -27,6 +27,7 @@ using namespace std; using namespace MIDI; +using namespace PBD; static std::map mmc_cmd_map; static void build_mmc_cmd_map () diff --git a/libs/midi++2/mmctest.cc b/libs/midi++2/mmctest.cc index 25ea964ded..36fbd61124 100644 --- a/libs/midi++2/mmctest.cc +++ b/libs/midi++2/mmctest.cc @@ -16,6 +16,7 @@ TextReceiver text_receiver ("mmctest"); #include "midi++/mmc.h" using namespace MIDI; +using namespace PBD; Port *port; PortRequest midi_device; diff --git a/libs/pbd3/SConscript b/libs/pbd3/SConscript index 4e64f12d43..2766b3c5ed 100644 --- a/libs/pbd3/SConscript +++ b/libs/pbd3/SConscript @@ -22,6 +22,7 @@ basename.cc base_ui.cc convert.cc dmalloc.cc +error.cc mountpoint.cc pathscanner.cc pool.cc diff --git a/libs/pbd3/base_ui.cc b/libs/pbd3/base_ui.cc index 5598b20021..d3c8d5e4c7 100644 --- a/libs/pbd3/base_ui.cc +++ b/libs/pbd3/base_ui.cc @@ -11,6 +11,7 @@ #include "i18n.h" using namespace std; +using namespace PBD; uint32_t BaseUI::rt_bit = 1; BaseUI::RequestType BaseUI::CallSlot = BaseUI::new_request_type(); diff --git a/libs/pbd3/error.cc b/libs/pbd3/error.cc new file mode 100644 index 0000000000..a6f8fb7f8f --- /dev/null +++ b/libs/pbd3/error.cc @@ -0,0 +1,7 @@ +#include + +Transmitter PBD::error (Transmitter::Error); +Transmitter PBD::info (Transmitter::Info); +Transmitter PBD::fatal (Transmitter::Fatal); +Transmitter PBD::warning (Transmitter::Warning); + diff --git a/libs/pbd3/pathscanner.cc b/libs/pbd3/pathscanner.cc index 5b96284a90..2af227a3a0 100644 --- a/libs/pbd3/pathscanner.cc +++ b/libs/pbd3/pathscanner.cc @@ -27,6 +27,8 @@ #include #include +using namespace PBD; + vector * PathScanner::operator() (const string &dirpath, const string ®exp, bool match_fullpath, bool return_fullpath, diff --git a/libs/pbd3/pbd/error.h b/libs/pbd3/pbd/error.h index cb822e6210..4136f02ee2 100644 --- a/libs/pbd3/pbd/error.h +++ b/libs/pbd3/pbd/error.h @@ -1,5 +1,5 @@ /* - Copyright (C) 1998-99 Paul Barton-Davis + Copyright (C) 1998-2006 Paul Davis This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -17,14 +17,16 @@ $Id$ */ -#ifndef __libmisc_error_h__ -#define __libmisc_error_h__ +#ifndef __libpbd_error_h__ +#define __libpbd_error_h__ #include "transmitter.h" -extern Transmitter error; -extern Transmitter info; -extern Transmitter warning; -extern Transmitter fatal; +namespace PBD { + extern Transmitter error; + extern Transmitter info; + extern Transmitter warning; + extern Transmitter fatal; +} -#endif // __libmisc_error_h__ +#endif // __libpbd_error_h__ diff --git a/libs/pbd3/pbd/transmitter.h b/libs/pbd3/pbd/transmitter.h index 07fc266bce..357cb9965f 100644 --- a/libs/pbd3/pbd/transmitter.h +++ b/libs/pbd3/pbd/transmitter.h @@ -104,6 +104,7 @@ endmsg (std::ostream &ostr) return ostr; } + extern "C" { void pbd_c_error (const char *); } #endif // __libmisc_transmitter_h__ diff --git a/libs/pbd3/pool.cc b/libs/pbd3/pool.cc index 7318bd4398..089766482d 100644 --- a/libs/pbd3/pool.cc +++ b/libs/pbd3/pool.cc @@ -25,6 +25,7 @@ #include using namespace std; +using namespace PBD; Pool::Pool (string n, unsigned long item_size, unsigned long nitems) { diff --git a/libs/pbd3/transmitter.cc b/libs/pbd3/transmitter.cc index 63f676a04f..876a9d86e5 100644 --- a/libs/pbd3/transmitter.cc +++ b/libs/pbd3/transmitter.cc @@ -24,17 +24,12 @@ #include #include +#include using std::string; using std::ios; -Transmitter error (Transmitter::Error); -Transmitter info (Transmitter::Info); -Transmitter fatal (Transmitter::Fatal); -Transmitter warning (Transmitter::Warning); - Transmitter::Transmitter (Channel c) - { channel = c; switch (c) { @@ -110,11 +105,11 @@ Transmitter::does_not_return () } } + extern "C" { void pbd_c_error (const char *str) { - extern Transmitter error; - error << str << endmsg; + PBD::error << str << endmsg; } } diff --git a/libs/surfaces/control_protocol/SConscript b/libs/surfaces/control_protocol/SConscript index 38ff95d9f0..f8a7d574f5 100644 --- a/libs/surfaces/control_protocol/SConscript +++ b/libs/surfaces/control_protocol/SConscript @@ -23,6 +23,7 @@ cp.Append(POTFILE = domain + '.pot') cp_files=Split(""" basic_ui.cc control_protocol.cc +smpte.cc """) cp.Append(CCFLAGS="-D_REENTRANT -D_LARGEFILE_SOURCE -D_LARGEFILE64_SOURCE") @@ -53,4 +54,4 @@ env.Alias('install', env.Install(os.path.join(install_prefix, 'lib/ardour2'), li env.Alias('tarball', env.Distribute (env['DISTTREE'], [ 'SConscript' ] + cp_files + - glob.glob('po/*.po') + glob.glob('*.h'))) + glob.glob('po/*.po') + glob.glob('*.h') + glob.glob('control_protocol/*.h'))) diff --git a/libs/surfaces/control_protocol/basic_ui.cc b/libs/surfaces/control_protocol/basic_ui.cc index 8cf157c26c..3dc93cc64a 100644 --- a/libs/surfaces/control_protocol/basic_ui.cc +++ b/libs/surfaces/control_protocol/basic_ui.cc @@ -24,7 +24,8 @@ #include #include -#include "basic_ui.h" +#include + #include "i18n.h" using namespace ARDOUR; @@ -263,19 +264,19 @@ BasicUI::smpte_frames_per_hour () } void -BasicUI::smpte_time (jack_nframes_t where, SMPTE_t& smpte) +BasicUI::smpte_time (jack_nframes_t where, SMPTE::Time& smpte) { - session->smpte_time (where, *((SMPTE_Time *) &smpte)); + session->smpte_time (where, *((SMPTE::Time *) &smpte)); } void -BasicUI::smpte_to_sample (SMPTE_t& smpte, jack_nframes_t& sample, bool use_offset, bool use_subframes) const +BasicUI::smpte_to_sample (SMPTE::Time& smpte, jack_nframes_t& sample, bool use_offset, bool use_subframes) const { - session->smpte_to_sample (*((SMPTE_Time*)&smpte), sample, use_offset, use_subframes); + session->smpte_to_sample (*((SMPTE::Time*)&smpte), sample, use_offset, use_subframes); } void -BasicUI::sample_to_smpte (jack_nframes_t sample, SMPTE_t& smpte, bool use_offset, bool use_subframes) const +BasicUI::sample_to_smpte (jack_nframes_t sample, SMPTE::Time& smpte, bool use_offset, bool use_subframes) const { - session->sample_to_smpte (sample, *((SMPTE_Time*)&smpte), use_offset, use_subframes); + session->sample_to_smpte (sample, *((SMPTE::Time*)&smpte), use_offset, use_subframes); } diff --git a/libs/surfaces/control_protocol/control_protocol.cc b/libs/surfaces/control_protocol/control_protocol.cc index 6407c64385..10295bc698 100644 --- a/libs/surfaces/control_protocol/control_protocol.cc +++ b/libs/surfaces/control_protocol/control_protocol.cc @@ -23,7 +23,7 @@ #include #include -#include "control_protocol.h" +#include using namespace ARDOUR; using namespace std; diff --git a/libs/surfaces/control_protocol/basic_ui.h b/libs/surfaces/control_protocol/control_protocol/basic_ui.h similarity index 77% rename from libs/surfaces/control_protocol/basic_ui.h rename to libs/surfaces/control_protocol/control_protocol/basic_ui.h index 81f2727264..23b274ca01 100644 --- a/libs/surfaces/control_protocol/basic_ui.h +++ b/libs/surfaces/control_protocol/control_protocol/basic_ui.h @@ -25,6 +25,7 @@ #include #include +#include namespace ARDOUR { class Session; @@ -72,27 +73,9 @@ class BasicUI { jack_nframes_t smpte_frames_per_hour (); - struct SMPTE_t { - bool negative; - uint32_t hours; - uint32_t minutes; - uint32_t seconds; - uint32_t frames; - uint32_t subframes; // mostly not used - - SMPTE_t () { - negative = false; - hours = 0; - minutes = 0; - seconds = 0; - frames = 0; - subframes = 0; - } - }; - - void smpte_time (jack_nframes_t where, SMPTE_t&); - void smpte_to_sample (SMPTE_t& smpte, jack_nframes_t& sample, bool use_offset, bool use_subframes) const; - void sample_to_smpte (jack_nframes_t sample, SMPTE_t& smpte, bool use_offset, bool use_subframes) const; + void smpte_time (jack_nframes_t where, SMPTE::Time&); + void smpte_to_sample (SMPTE::Time& smpte, jack_nframes_t& sample, bool use_offset, bool use_subframes) const; + void sample_to_smpte (jack_nframes_t sample, SMPTE::Time& smpte, bool use_offset, bool use_subframes) const; protected: BasicUI (); diff --git a/libs/surfaces/control_protocol/control_protocol.h b/libs/surfaces/control_protocol/control_protocol/control_protocol.h similarity index 98% rename from libs/surfaces/control_protocol/control_protocol.h rename to libs/surfaces/control_protocol/control_protocol/control_protocol.h index 720188c666..69135f2b4b 100644 --- a/libs/surfaces/control_protocol/control_protocol.h +++ b/libs/surfaces/control_protocol/control_protocol/control_protocol.h @@ -27,7 +27,7 @@ #include #include -#include "basic_ui.h" +#include namespace ARDOUR { diff --git a/libs/surfaces/control_protocol/control_protocol/smpte.h b/libs/surfaces/control_protocol/control_protocol/smpte.h new file mode 100644 index 0000000000..09c1c9616a --- /dev/null +++ b/libs/surfaces/control_protocol/control_protocol/smpte.h @@ -0,0 +1,80 @@ +/* + Copyright (C) 2006 Paul Davis + + This program is free software; you can redistribute it and/or modify it + under the terms of the GNU Lesser General Public License as published + by the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License along + with this program; if not, write to the Free Software Foundation, Inc., + 675 Mass Ave, Cambridge, MA 02139, USA. +*/ + +#ifndef __ardour_smpte_h__ +#define __ardour_smpte_h__ + +#include + +namespace SMPTE { + +enum Wrap { + NONE = 0, + FRAMES, + SECONDS, + MINUTES, + HOURS +}; + +/** SMPTE frame rate (in frames per second). + * + * This should be eliminated in favour of a float to support arbitrary rates. + */ +enum FPS { + MTC_24_FPS = 0, + MTC_25_FPS = 1, + MTC_30_FPS_DROP = 2, + MTC_30_FPS = 3 +}; + +struct Time { + bool negative; + uint32_t hours; + uint32_t minutes; + uint32_t seconds; + uint32_t frames; ///< SMPTE frames (not audio samples) + uint32_t subframes; ///< Typically unused + FPS rate; ///< Frame rate of this Time + static FPS default_rate; ///< Rate to use for default constructor + + Time(FPS a_rate = default_rate) { + negative = false; + hours = 0; + minutes = 0; + seconds = 0; + frames = 0; + subframes = 0; + rate = a_rate; + } +}; + +Wrap increment( Time& smpte ); +Wrap decrement( Time& smpte ); +Wrap increment_subframes( Time& smpte ); +Wrap decrement_subframes( Time& smpte ); +Wrap increment_seconds( Time& smpte ); +Wrap increment_minutes( Time& smpte ); +Wrap increment_hours( Time& smpte ); +void frames_floor( Time& smpte ); +void seconds_floor( Time& smpte ); +void minutes_floor( Time& smpte ); +void hours_floor( Time& smpte ); + +} // namespace SMPTE + +#endif // __ardour_smpte_h__ diff --git a/libs/surfaces/control_protocol/smpte.cc b/libs/surfaces/control_protocol/smpte.cc new file mode 100644 index 0000000000..55d0660c59 --- /dev/null +++ b/libs/surfaces/control_protocol/smpte.cc @@ -0,0 +1,406 @@ +/* + Copyright (C) 2006 Paul Davis + + This program is free software; you can redistribute it and/or modify it + under the terms of the GNU Lesser General Public License as published + by the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License along + with this program; if not, write to the Free Software Foundation, Inc., + 675 Mass Ave, Cambridge, MA 02139, USA. +*/ + +#define SMPTE_IS_AROUND_ZERO( sm ) (!(sm).frames && !(sm).seconds && !(sm).minutes && !(sm).hours) +#define SMPTE_IS_ZERO( sm ) (!(sm).frames && !(sm).seconds && !(sm).minutes && !(sm).hours && !(sm.subframes)) + +#include + +namespace SMPTE { + +FPS Time::default_rate = MTC_30_FPS; + + +/** Increment @a smpte by exactly one frame (keep subframes value). + * Realtime safe. + * @return true if seconds wrap. + */ +Wrap +increment( Time& smpte ) +{ + Wrap wrap = NONE; + + if (smpte.negative) { + if (SMPTE_IS_AROUND_ZERO(smpte) && smpte.subframes) { + // We have a zero transition involving only subframes + smpte.subframes = 80 - smpte.subframes; + smpte.negative = false; + return SECONDS; + } + + smpte.negative = false; + wrap = decrement( smpte ); + if (!SMPTE_IS_ZERO( smpte )) { + smpte.negative = true; + } + return wrap; + } + + switch (smpte.rate) { + case MTC_24_FPS: + if (smpte.frames == 23) { + smpte.frames = 0; + wrap = SECONDS; + } + break; + case MTC_25_FPS: + if (smpte.frames == 24) { + smpte.frames = 0; + wrap = SECONDS; + } + break; + case MTC_30_FPS_DROP: + if (smpte.frames == 29) { + if ( ((smpte.minutes + 1) % 10) && (smpte.seconds == 59) ) { + smpte.frames = 2; + } + else { + smpte.frames = 0; + } + wrap = SECONDS; + } + break; + case MTC_30_FPS: + if (smpte.frames == 29) { + smpte.frames = 0; + wrap = SECONDS; + } + break; + } + + if (wrap == SECONDS) { + if (smpte.seconds == 59) { + smpte.seconds = 0; + wrap = MINUTES; + if (smpte.minutes == 59) { + smpte.minutes = 0; + wrap = HOURS; + smpte.hours++; + } else { + smpte.minutes++; + } + } else { + smpte.seconds++; + } + } else { + smpte.frames++; + } + + return wrap; +} + + +/** Decrement @a smpte by exactly one frame (keep subframes value) + * Realtime safe. + * @return true if seconds wrap. */ +Wrap +decrement( Time& smpte ) +{ + Wrap wrap = NONE; + + + if (smpte.negative || SMPTE_IS_ZERO(smpte)) { + smpte.negative = false; + wrap = increment( smpte ); + smpte.negative = true; + return wrap; + } else if (SMPTE_IS_AROUND_ZERO(smpte) && smpte.subframes) { + // We have a zero transition involving only subframes + smpte.subframes = 80 - smpte.subframes; + smpte.negative = true; + return SECONDS; + } + + switch (smpte.rate) { + case MTC_24_FPS: + if (smpte.frames == 0) { + smpte.frames = 23; + wrap = SECONDS; + } + break; + case MTC_25_FPS: + if (smpte.frames == 0) { + smpte.frames = 24; + wrap = SECONDS; + } + break; + case MTC_30_FPS_DROP: + if ((smpte.minutes % 10) && (smpte.seconds == 0)) { + if (smpte.frames <= 2) { + smpte.frames = 29; + wrap = SECONDS; + } + } else if (smpte.frames == 0) { + smpte.frames = 29; + wrap = SECONDS; + } + break; + case MTC_30_FPS: + if (smpte.frames == 0) { + smpte.frames = 29; + wrap = SECONDS; + } + break; + } + + if (wrap == SECONDS) { + if (smpte.seconds == 0) { + smpte.seconds = 59; + wrap = MINUTES; + if (smpte.minutes == 0) { + smpte.minutes = 59; + wrap = HOURS; + smpte.hours--; + } + else { + smpte.minutes--; + } + } else { + smpte.seconds--; + } + } else { + smpte.frames--; + } + + if (SMPTE_IS_ZERO( smpte )) { + smpte.negative = false; + } + + return wrap; +} + + +/** Go to lowest absolute subframe value in this frame (set to 0 :-) ) */ +void +frames_floor( Time& smpte ) +{ + smpte.subframes = 0; + if (SMPTE_IS_ZERO(smpte)) { + smpte.negative = false; + } +} + + +/** Increment @a smpte by one subframe */ +Wrap +increment_subframes( Time& smpte ) +{ + Wrap wrap = NONE; + + if (smpte.negative) { + smpte.negative = false; + wrap = decrement_subframes( smpte ); + if (!SMPTE_IS_ZERO(smpte)) { + smpte.negative = true; + } + return wrap; + } + + smpte.subframes++; + if (smpte.subframes >= 80) { + smpte.subframes = 0; + increment( smpte ); + return FRAMES; + } + return NONE; +} + + +/** Decrement @a smpte by one subframe */ +Wrap +decrement_subframes( Time& smpte ) +{ + Wrap wrap = NONE; + + if (smpte.negative) { + smpte.negative = false; + wrap = increment_subframes( smpte ); + smpte.negative = true; + return wrap; + } + + if (smpte.subframes <= 0) { + smpte.subframes = 0; + if (SMPTE_IS_ZERO(smpte)) { + smpte.negative = true; + smpte.subframes = 1; + return FRAMES; + } else { + decrement( smpte ); + smpte.subframes = 79; + return FRAMES; + } + } else { + smpte.subframes--; + if (SMPTE_IS_ZERO(smpte)) { + smpte.negative = false; + } + return NONE; + } +} + + +/** Go to next whole second (frames == 0 or frames == 2) */ +Wrap +increment_seconds( Time& smpte ) +{ + Wrap wrap = NONE; + + // Clear subframes + frames_floor( smpte ); + + if (smpte.negative) { + // Wrap second if on second boundary + wrap = increment(smpte); + // Go to lowest absolute frame value + seconds_floor( smpte ); + if (SMPTE_IS_ZERO(smpte)) { + smpte.negative = false; + } + } else { + // Go to highest possible frame in this second + switch (smpte.rate) { + case MTC_24_FPS: + smpte.frames = 23; + break; + case MTC_25_FPS: + smpte.frames = 24; + break; + case MTC_30_FPS_DROP: + case MTC_30_FPS: + smpte.frames = 29; + break; + } + + // Increment by one frame + wrap = increment( smpte ); + } + + return wrap; +} + + +/** Go to lowest (absolute) frame value in this second + * Doesn't care about positive/negative */ +void +seconds_floor( Time& smpte ) +{ + // Clear subframes + frames_floor( smpte ); + + // Go to lowest possible frame in this second + switch (smpte.rate) { + case MTC_24_FPS: + case MTC_25_FPS: + case MTC_30_FPS: + smpte.frames = 0; + break; + case MTC_30_FPS_DROP: + if ((smpte.minutes % 10) && (smpte.seconds == 0)) { + smpte.frames = 2; + } else { + smpte.frames = 0; + } + break; + } + + if (SMPTE_IS_ZERO(smpte)) { + smpte.negative = false; + } +} + + +/** Go to next whole minute (seconds == 0, frames == 0 or frames == 2) */ +Wrap +increment_minutes( Time& smpte ) +{ + Wrap wrap = NONE; + + // Clear subframes + frames_floor( smpte ); + + if (smpte.negative) { + // Wrap if on minute boundary + wrap = increment_seconds( smpte ); + // Go to lowest possible value in this minute + minutes_floor( smpte ); + } else { + // Go to highest possible second + smpte.seconds = 59; + // Wrap minute by incrementing second + wrap = increment_seconds( smpte ); + } + + return wrap; +} + + +/** Go to lowest absolute value in this minute */ +void +minutes_floor( Time& smpte ) +{ + // Go to lowest possible second + smpte.seconds = 0; + // Go to lowest possible frame + seconds_floor( smpte ); + + if (SMPTE_IS_ZERO(smpte)) { + smpte.negative = false; + } +} + + +/** Go to next whole hour (minute = 0, second = 0, frame = 0) */ +Wrap +increment_hours( Time& smpte ) +{ + Wrap wrap = NONE; + + // Clear subframes + frames_floor(smpte); + + if (smpte.negative) { + // Wrap if on hour boundary + wrap = increment_minutes( smpte ); + // Go to lowest possible value in this hour + hours_floor( smpte ); + } else { + smpte.minutes = 59; + wrap = increment_minutes( smpte ); + } + + return wrap; +} + + +/** Go to lowest absolute value in this hour */ +void +hours_floor( Time& smpte ) +{ + smpte.minutes = 0; + smpte.seconds = 0; + smpte.frames = 0; + smpte.subframes = 0; + + if (SMPTE_IS_ZERO(smpte)) { + smpte.negative = false; + } +} + + +} // namespace SMPTE diff --git a/libs/surfaces/generic_midi/generic_midi_control_protocol.h b/libs/surfaces/generic_midi/generic_midi_control_protocol.h index 77a4dca805..70cbd181c8 100644 --- a/libs/surfaces/generic_midi/generic_midi_control_protocol.h +++ b/libs/surfaces/generic_midi/generic_midi_control_protocol.h @@ -1,7 +1,7 @@ #ifndef ardour_generic_midi_control_protocol_h #define ardour_generic_midi_control_protocol_h -#include "control_protocol.h" +#include namespace MIDI { class Port; diff --git a/libs/surfaces/generic_midi/interface.cc b/libs/surfaces/generic_midi/interface.cc index 625ac65273..c6c59c6589 100644 --- a/libs/surfaces/generic_midi/interface.cc +++ b/libs/surfaces/generic_midi/interface.cc @@ -1,5 +1,4 @@ -#include "control_protocol.h" - +#include #include "generic_midi_control_protocol.h" using namespace ARDOUR; diff --git a/libs/surfaces/tranzport/interface.cc b/libs/surfaces/tranzport/interface.cc index 20f38dce08..29a0fde043 100644 --- a/libs/surfaces/tranzport/interface.cc +++ b/libs/surfaces/tranzport/interface.cc @@ -1,5 +1,4 @@ -#include "control_protocol.h" - +#include #include "tranzport_control_protocol.h" using namespace ARDOUR; diff --git a/libs/surfaces/tranzport/tranzport_control_protocol.cc b/libs/surfaces/tranzport/tranzport_control_protocol.cc index 4fad413d24..ee8fa95bc2 100644 --- a/libs/surfaces/tranzport/tranzport_control_protocol.cc +++ b/libs/surfaces/tranzport/tranzport_control_protocol.cc @@ -41,6 +41,7 @@ using namespace ARDOUR; using namespace std; using namespace sigc; +using namespace PBD; #include "i18n.h" @@ -324,7 +325,7 @@ TranzportControlProtocol::show_transport_time () if (where != last_where) { char buf[5]; - SMPTE_Time smpte; + SMPTE::Time smpte; session->smpte_time (where, smpte); @@ -395,10 +396,7 @@ TranzportControlProtocol::open_core (struct usb_device* dev) } if (usb_set_configuration (udev, 1) < 0) { - error << _("Tranzport: cannot configure USB interface") << endmsg; - usb_close (udev); - udev = 0; - return -1; + cerr << _("Tranzport: cannot configure USB interface") << endmsg; } return 0; diff --git a/libs/surfaces/tranzport/tranzport_control_protocol.h b/libs/surfaces/tranzport/tranzport_control_protocol.h index 44045f6834..546cc2f2af 100644 --- a/libs/surfaces/tranzport/tranzport_control_protocol.h +++ b/libs/surfaces/tranzport/tranzport_control_protocol.h @@ -11,7 +11,7 @@ #include -#include "control_protocol.h" +#include class TranzportControlProtocol : public ARDOUR::ControlProtocol { diff --git a/templates/SConscript b/templates/SConscript index b5410ad7a5..7fa556530b 100644 --- a/templates/SConscript +++ b/templates/SConscript @@ -13,5 +13,5 @@ for template in template_files: Default(template_build) -env.Alias('install', env.Install(os.path.join(install_prefix, 'share/ardour/templates'), template_build)) +env.Alias('install', env.Install(os.path.join(install_prefix, 'share/ardour2/templates'), template_build)) env.Alias('tarball', env.Distribute (env['DISTTREE'], [ 'SConscript' ] + template_build)) diff --git a/vst/SConscript b/vst/SConscript new file mode 100644 index 0000000000..fead9ba512 --- /dev/null +++ b/vst/SConscript @@ -0,0 +1,54 @@ +# -*- python -*- + +import os +import os.path +import glob + +Import('env install_prefix final_prefix config_prefix libraries') + +ardour_vst = env.Copy() + +sources = Split (""" +winmain.c +#libs/fst/fst.o +#libs/fst/fstinfofile.o +#libs/fst/vstwin.o +#libs/fst/vsti.o +""" +) + +ardour_vst.Append (CCFLAGS="-DVST_SUPPORT", CPPPATH="#libs/fst", LIBPATH='#gtk2_ardour') +ardour_vst.Append (LINKFLAGS='-L/usr/X11R6/lib -lasound -lardourgtk -lX11 -lpthread') +ardour_vst["CC"] ="winegcc" +ardour_vst["LINK"] ="wineg++ -mwindows" + +ardour_vst.Merge ([ + libraries['ardour'], + libraries['ardour_cp'], + libraries['gtkmm2ext'], + libraries['midi++2'], + libraries['pbd3'], + libraries['gtkmm2'], + libraries['glib2'], + libraries['libgnomecanvas2'], + libraries['libgnomecanvasmm'], + libraries['sysmidi'], + libraries['sndfile'], + libraries['flac'], + libraries['lrdf'], + libraries['glibmm2'], + libraries['pangomm'], + libraries['atkmm'], + libraries['gdkmm2'], + libraries['sigc2'], + libraries['gtk2'], + libraries['xml'], + libraries['xslt'], + libraries['soundtouch'], + libraries['samplerate'], + libraries['jack'] +]) + +wine_executable = ardour_vst.Program (target = 'ardour_vst', source = sources) + +Default(wine_executable) diff --git a/vst/winmain.c b/vst/winmain.c new file mode 100644 index 0000000000..c2ad5fc6bd --- /dev/null +++ b/vst/winmain.c @@ -0,0 +1,17 @@ +#include +#include +#include + +extern int ardour_main(int argc, char* argv[]); + +int +main (int argc, char* argv[]) +{ + // call the user specified main function + + int result = ardour_main(argc, argv); + printf ("main returned %d\n", result); + + return result; + +} From 7968974c01040801c858e8d9192607df49b7996a Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Thu, 29 Jun 2006 14:19:37 +0000 Subject: [PATCH 08/27] merging trunk git-svn-id: svn://localhost/ardour2/branches/undo@652 d708f5d6-7413-0410-9779-e7cbd77b26cf --- SConstruct | 5 + gtk2_ardour/SConscript | 2 +- gtk2_ardour/po/de_DE.po | 46 +- gtk2_ardour/po/el_GR.po | 46 +- gtk2_ardour/po/es_ES.po | 46 +- gtk2_ardour/po/fr_FR.po | 46 +- gtk2_ardour/po/it_IT.po | 46 +- gtk2_ardour/po/pt_BR.po | 46 +- gtk2_ardour/po/pt_PT.po | 46 +- gtk2_ardour/po/ru_RU.po | 46 +- libs/ardour/SConscript | 2 +- libs/ardour/ardour/audiofilesource.h | 8 +- .../{coreaudio_source.h => coreaudiosource.h} | 11 +- libs/ardour/ardour/destructive_filesource.h | 3 +- libs/ardour/ardour/sndfilesource.h | 5 +- libs/ardour/audio_diskstream.cc | 1 + libs/ardour/audio_playlist.cc | 2 +- libs/ardour/audio_track.cc | 8 - libs/ardour/audiofilesource.cc | 56 +- ...coreaudio_source.cc => coreaudiosource.cc} | 22 +- libs/ardour/po/el_GR.po | 38 +- libs/ardour/po/it_IT.po | 38 +- libs/ardour/po/ru_RU.po | 38 +- libs/ardour/session_time.cc | 1 - libs/ardour/sndfilesource.cc | 96 +- libs/cassowary/.cvsignore | 3 - libs/cassowary/ANNOUNCE | 37 - libs/cassowary/AUTHORS | 12 - libs/cassowary/COPYING | 340 --- libs/cassowary/COPYING.LGPL | 444 ---- libs/cassowary/ChangeLog | 2005 ----------------- libs/cassowary/ClAbstractVariable.cc | 23 - libs/cassowary/ClBug0.cc | 102 - libs/cassowary/ClBug1.cc | 21 - libs/cassowary/ClBug2.cc | 130 -- libs/cassowary/ClConstraint.cc | 32 - libs/cassowary/ClDummyVariable.cc | 12 - libs/cassowary/ClFDBinaryOneWayConstraint.cc | 140 -- libs/cassowary/ClFDConnectorVariable.cc | 29 - libs/cassowary/ClFDSolver.cc | 364 --- libs/cassowary/ClFDVariable.cc | 27 - libs/cassowary/ClFloatVariable.cc | 25 - libs/cassowary/ClLinearExpression.cc | 473 ---- libs/cassowary/ClReader.ll | 87 - libs/cassowary/ClReader.yy | 154 -- libs/cassowary/ClSimplexSolver.cc | 1631 -------------- libs/cassowary/ClSlackVariable.cc | 12 - libs/cassowary/ClSolver.cc | 59 - libs/cassowary/ClStrength.cc | 52 - libs/cassowary/ClSymbolicWeight.cc | 149 -- libs/cassowary/ClTableau.cc | 297 --- libs/cassowary/ClTests.cc | 884 -------- libs/cassowary/ClVariable.cc | 21 - libs/cassowary/IMPORTANT | 26 - libs/cassowary/LICENSE | 18 - libs/cassowary/NEWS | 229 -- libs/cassowary/README | 241 -- libs/cassowary/SConscript | 32 - libs/cassowary/THANKS | 30 - libs/cassowary/cassowary-config.in | 102 - libs/cassowary/cassowary-nofd.spec2.in | 84 - libs/cassowary/cassowary.spec.in | 78 - libs/cassowary/cassowary/.cvsignore | 0 libs/cassowary/cassowary/Cassowary.h | 40 - libs/cassowary/cassowary/Cl.h | 49 - libs/cassowary/cassowary/ClAbstractVariable.h | 161 -- libs/cassowary/cassowary/ClConstraint.h | 198 -- libs/cassowary/cassowary/ClConstraintHash.h | 39 - libs/cassowary/cassowary/ClDummyVariable.h | 88 - libs/cassowary/cassowary/ClEditConstraint.h | 45 - .../cassowary/ClEditOrStayConstraint.h | 51 - libs/cassowary/cassowary/ClErrors.h | 179 -- .../cassowary/ClFDBinaryOneWayConstraint.h | 94 - .../cassowary/ClFDConnectorVariable.h | 89 - libs/cassowary/cassowary/ClFDConstraint.h | 40 - libs/cassowary/cassowary/ClFDSolver.h | 120 - libs/cassowary/cassowary/ClFDVariable.h | 126 -- libs/cassowary/cassowary/ClFloatVariable.h | 119 - libs/cassowary/cassowary/ClLinearConstraint.h | 61 - libs/cassowary/cassowary/ClLinearEquation.h | 74 - libs/cassowary/cassowary/ClLinearExpression.h | 298 --- .../cassowary/ClLinearExpression_fwd.h | 26 - libs/cassowary/cassowary/ClLinearInequality.h | 167 -- .../cassowary/cassowary/ClObjectiveVariable.h | 63 - libs/cassowary/cassowary/ClPoint.h | 74 - libs/cassowary/cassowary/ClReader.h | 120 - libs/cassowary/cassowary/ClSimplexSolver.h | 588 ----- libs/cassowary/cassowary/ClSlackVariable.h | 75 - libs/cassowary/cassowary/ClSolver.h | 167 -- libs/cassowary/cassowary/ClStayConstraint.h | 43 - libs/cassowary/cassowary/ClStrength.h | 91 - libs/cassowary/cassowary/ClSymbolicWeight.h | 197 -- libs/cassowary/cassowary/ClTableau.h | 230 -- libs/cassowary/cassowary/ClTypedefs.h | 48 - libs/cassowary/cassowary/ClVariable.h | 169 -- libs/cassowary/cassowary/cl_auto_ptr.h | 69 - libs/cassowary/cassowary/config-inline.h | 1 - libs/cassowary/cassowary/debug.h | 48 - libs/cassowary/cassowary/timer.h | 176 -- libs/libsndfile/src/sndfile.c | 4 +- tools/osx_packaging/Ardour2.icns | Bin 0 -> 53885 bytes tools/osx_packaging/MenuBar.nib/classes.nib | 4 + tools/osx_packaging/MenuBar.nib/info.nib | 23 + tools/osx_packaging/MenuBar.nib/objects.xib | 73 + .../ProgressWindow.nib/classes.nib | 4 + .../osx_packaging/ProgressWindow.nib/info.nib | 18 + .../ProgressWindow.nib/objects.xib | 53 + tools/osx_packaging/README.rtf | 68 + tools/osx_packaging/app_build.rb | 22 + tools/osx_packaging/bin/cache-fonts | Bin 0 -> 9516 bytes tools/osx_packaging/bin/exporter | 39 + tools/osx_packaging/bin/getdisplay.sh | 9 + tools/osx_packaging/bin/gs | Bin 0 -> 6527252 bytes tools/osx_packaging/init | 16 + tools/osx_packaging/openDoc | 6 + tools/osx_packaging/script | 27 + 116 files changed, 735 insertions(+), 12963 deletions(-) rename libs/ardour/ardour/{coreaudio_source.h => coreaudiosource.h} (84%) rename libs/ardour/{coreaudio_source.cc => coreaudiosource.cc} (92%) delete mode 100644 libs/cassowary/.cvsignore delete mode 100644 libs/cassowary/ANNOUNCE delete mode 100644 libs/cassowary/AUTHORS delete mode 100644 libs/cassowary/COPYING delete mode 100644 libs/cassowary/COPYING.LGPL delete mode 100644 libs/cassowary/ChangeLog delete mode 100644 libs/cassowary/ClAbstractVariable.cc delete mode 100644 libs/cassowary/ClBug0.cc delete mode 100644 libs/cassowary/ClBug1.cc delete mode 100644 libs/cassowary/ClBug2.cc delete mode 100644 libs/cassowary/ClConstraint.cc delete mode 100644 libs/cassowary/ClDummyVariable.cc delete mode 100644 libs/cassowary/ClFDBinaryOneWayConstraint.cc delete mode 100644 libs/cassowary/ClFDConnectorVariable.cc delete mode 100644 libs/cassowary/ClFDSolver.cc delete mode 100644 libs/cassowary/ClFDVariable.cc delete mode 100644 libs/cassowary/ClFloatVariable.cc delete mode 100644 libs/cassowary/ClLinearExpression.cc delete mode 100644 libs/cassowary/ClReader.ll delete mode 100644 libs/cassowary/ClReader.yy delete mode 100644 libs/cassowary/ClSimplexSolver.cc delete mode 100644 libs/cassowary/ClSlackVariable.cc delete mode 100644 libs/cassowary/ClSolver.cc delete mode 100644 libs/cassowary/ClStrength.cc delete mode 100644 libs/cassowary/ClSymbolicWeight.cc delete mode 100644 libs/cassowary/ClTableau.cc delete mode 100644 libs/cassowary/ClTests.cc delete mode 100644 libs/cassowary/ClVariable.cc delete mode 100644 libs/cassowary/IMPORTANT delete mode 100644 libs/cassowary/LICENSE delete mode 100644 libs/cassowary/NEWS delete mode 100644 libs/cassowary/README delete mode 100644 libs/cassowary/SConscript delete mode 100644 libs/cassowary/THANKS delete mode 100755 libs/cassowary/cassowary-config.in delete mode 100644 libs/cassowary/cassowary-nofd.spec2.in delete mode 100644 libs/cassowary/cassowary.spec.in delete mode 100644 libs/cassowary/cassowary/.cvsignore delete mode 100644 libs/cassowary/cassowary/Cassowary.h delete mode 100644 libs/cassowary/cassowary/Cl.h delete mode 100644 libs/cassowary/cassowary/ClAbstractVariable.h delete mode 100644 libs/cassowary/cassowary/ClConstraint.h delete mode 100644 libs/cassowary/cassowary/ClConstraintHash.h delete mode 100644 libs/cassowary/cassowary/ClDummyVariable.h delete mode 100644 libs/cassowary/cassowary/ClEditConstraint.h delete mode 100644 libs/cassowary/cassowary/ClEditOrStayConstraint.h delete mode 100644 libs/cassowary/cassowary/ClErrors.h delete mode 100644 libs/cassowary/cassowary/ClFDBinaryOneWayConstraint.h delete mode 100644 libs/cassowary/cassowary/ClFDConnectorVariable.h delete mode 100644 libs/cassowary/cassowary/ClFDConstraint.h delete mode 100644 libs/cassowary/cassowary/ClFDSolver.h delete mode 100644 libs/cassowary/cassowary/ClFDVariable.h delete mode 100644 libs/cassowary/cassowary/ClFloatVariable.h delete mode 100644 libs/cassowary/cassowary/ClLinearConstraint.h delete mode 100644 libs/cassowary/cassowary/ClLinearEquation.h delete mode 100644 libs/cassowary/cassowary/ClLinearExpression.h delete mode 100644 libs/cassowary/cassowary/ClLinearExpression_fwd.h delete mode 100644 libs/cassowary/cassowary/ClLinearInequality.h delete mode 100644 libs/cassowary/cassowary/ClObjectiveVariable.h delete mode 100644 libs/cassowary/cassowary/ClPoint.h delete mode 100644 libs/cassowary/cassowary/ClReader.h delete mode 100644 libs/cassowary/cassowary/ClSimplexSolver.h delete mode 100644 libs/cassowary/cassowary/ClSlackVariable.h delete mode 100644 libs/cassowary/cassowary/ClSolver.h delete mode 100644 libs/cassowary/cassowary/ClStayConstraint.h delete mode 100644 libs/cassowary/cassowary/ClStrength.h delete mode 100644 libs/cassowary/cassowary/ClSymbolicWeight.h delete mode 100644 libs/cassowary/cassowary/ClTableau.h delete mode 100644 libs/cassowary/cassowary/ClTypedefs.h delete mode 100644 libs/cassowary/cassowary/ClVariable.h delete mode 100644 libs/cassowary/cassowary/cl_auto_ptr.h delete mode 100644 libs/cassowary/cassowary/config-inline.h delete mode 100644 libs/cassowary/cassowary/debug.h delete mode 100644 libs/cassowary/cassowary/timer.h create mode 100644 tools/osx_packaging/Ardour2.icns create mode 100644 tools/osx_packaging/MenuBar.nib/classes.nib create mode 100644 tools/osx_packaging/MenuBar.nib/info.nib create mode 100644 tools/osx_packaging/MenuBar.nib/objects.xib create mode 100644 tools/osx_packaging/ProgressWindow.nib/classes.nib create mode 100644 tools/osx_packaging/ProgressWindow.nib/info.nib create mode 100644 tools/osx_packaging/ProgressWindow.nib/objects.xib create mode 100644 tools/osx_packaging/README.rtf create mode 100755 tools/osx_packaging/app_build.rb create mode 100755 tools/osx_packaging/bin/cache-fonts create mode 100755 tools/osx_packaging/bin/exporter create mode 100755 tools/osx_packaging/bin/getdisplay.sh create mode 100755 tools/osx_packaging/bin/gs create mode 100755 tools/osx_packaging/init create mode 100755 tools/osx_packaging/openDoc create mode 100755 tools/osx_packaging/script diff --git a/SConstruct b/SConstruct index 65dfd3b06e..1dd250edfb 100644 --- a/SConstruct +++ b/SConstruct @@ -838,6 +838,11 @@ if env['NLS']: print 'This system is not configured for internationalized applications (no libintl.h). An english-only version will be built\n' env['NLS'] = 0 + have_intltool = conf.TryAction(Action('intltool-update --version')) + if have_intltool[0] != 1: + print 'This system is not configured for internationalized applications (no intltool-update command). An english-only version will be built\n' + env['NLS'] = 0 + env = conf.Finish() diff --git a/gtk2_ardour/SConscript b/gtk2_ardour/SConscript index 55fa26ec85..65f8dfca73 100644 --- a/gtk2_ardour/SConscript +++ b/gtk2_ardour/SConscript @@ -255,7 +255,7 @@ else: env.Alias('install', env.InstallAs(os.path.join(install_prefix, 'bin')+'/ardour2', ardoursh)) if env['NLS']: - Export('gtkardour', 'intl_files') + Export('gtkardour', 'intl_files') SConscript ('po/SConscript') # configuration files diff --git a/gtk2_ardour/po/de_DE.po b/gtk2_ardour/po/de_DE.po index a51f6108bc..edd8394611 100644 --- a/gtk2_ardour/po/de_DE.po +++ b/gtk2_ardour/po/de_DE.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: gtk-ardour 0.347.2\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-06-21 18:09-0400\n" +"POT-Creation-Date: 2006-06-27 13:00-0400\n" "PO-Revision-Date: 2003-05-11 17:36+0200\n" "Last-Translator: Karsten Petersen \n" "Language-Team: Deutsch \n" @@ -4773,29 +4773,29 @@ msgstr "" msgid "%d(%d): received signal %d\n" msgstr "" -#: main.cc:186 +#: main.cc:180 msgid "cannot become new process group leader (%1)" msgstr "" -#: main.cc:213 +#: main.cc:207 msgid "cannot setup signal handling for %1" msgstr "" -#: main.cc:224 +#: main.cc:218 msgid "cannot set default signal mask (%1)" msgstr "" -#: main.cc:254 +#: main.cc:248 msgid "" "Without a UI style file, ardour will look strange.\n" " Please set ARDOUR2_UI_RC to point to a valid UI style file" msgstr "" -#: main.cc:276 +#: main.cc:270 msgid "Ardour could not connect to JACK." msgstr "" -#: main.cc:280 +#: main.cc:274 msgid "" "There are several possible reasons:\n" "\n" @@ -4806,12 +4806,12 @@ msgid "" "Please consider the possibilities, and perhaps (re)start JACK." msgstr "" -#: main.cc:310 +#: main.cc:304 msgid "could not load command line session \"%1\"" msgstr "" #. it wasn't new, but we require a new session -#: main.cc:330 +#: main.cc:324 msgid "" "\n" "\n" @@ -4819,7 +4819,7 @@ msgid "" "To avoid this message, start ardour as \"ardour %1" msgstr "" -#: main.cc:341 +#: main.cc:335 msgid "" "\n" "\n" @@ -4827,60 +4827,60 @@ msgid "" "To create it from the command line, start ardour as \"ardour --new %1" msgstr "" -#: main.cc:405 +#: main.cc:399 msgid "Ardour/GTK " msgstr "" -#: main.cc:407 +#: main.cc:401 msgid "" "\n" " (built using " msgstr "" -#: main.cc:411 +#: main.cc:405 msgid " with libardour " msgstr "" -#: main.cc:416 +#: main.cc:410 msgid " and GCC version " msgstr "" -#: main.cc:426 +#: main.cc:420 msgid "Copyright (C) 1999-2006 Paul Davis" msgstr "" -#: main.cc:427 +#: main.cc:421 msgid "" "Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " "Baker" msgstr "" -#: main.cc:429 +#: main.cc:423 msgid "Ardour comes with ABSOLUTELY NO WARRANTY" msgstr "Achtung: Es gibt zu Ardour KEINERLEI Gewährleistung!" -#: main.cc:430 +#: main.cc:424 msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." msgstr "" -#: main.cc:431 +#: main.cc:425 msgid "This is free software, and you are welcome to redistribute it " msgstr "Dies ist freie Software und Sie dürfen sie gerne weiterverbreiten," -#: main.cc:432 +#: main.cc:426 #, fuzzy msgid "under certain conditions; see the source for copying conditions." msgstr "solange Sie sich an die Spielregeln aus der Datei COPYING halten." -#: main.cc:441 +#: main.cc:435 msgid "could not create ARDOUR GUI" msgstr "" -#: main.cc:459 +#: main.cc:453 msgid "Could not connect to JACK server as \"%1\"" msgstr "" -#: main.cc:462 +#: main.cc:456 msgid "could not initialize Ardour." msgstr "" diff --git a/gtk2_ardour/po/el_GR.po b/gtk2_ardour/po/el_GR.po index e737aa7ca0..4a6545d282 100644 --- a/gtk2_ardour/po/el_GR.po +++ b/gtk2_ardour/po/el_GR.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: 0.99beta23\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-06-21 18:09-0400\n" +"POT-Creation-Date: 2006-06-27 13:00-0400\n" "PO-Revision-Date: 2005-01-11\n" "Last-Translator: Muadibas \n" "Language-Team: Hellenic(Greek) \n" @@ -4776,19 +4776,19 @@ msgstr "παÏση του user interface\n" msgid "%d(%d): received signal %d\n" msgstr "%d: εδέχθη σήμα %d\n" -#: main.cc:186 +#: main.cc:180 msgid "cannot become new process group leader (%1)" msgstr "" -#: main.cc:213 +#: main.cc:207 msgid "cannot setup signal handling for %1" msgstr "δεν γίνεται να διαμοÏφώθεί η διαχείÏηση σημάτων για %1" -#: main.cc:224 +#: main.cc:218 msgid "cannot set default signal mask (%1)" msgstr "δεν γίνεται να διαμοÏφώθεί η Ï€ÏοκαθοÏισμένη μάσκα σημάτων (%1)" -#: main.cc:254 +#: main.cc:248 #, fuzzy msgid "" "Without a UI style file, ardour will look strange.\n" @@ -4797,12 +4797,12 @@ msgstr "" "Δίχως αÏχείο εμφάνισεως UI, ο ardour θα φαίνεται παÏάξενα.\n" "ΠαÏακαλώ θέστε το ARDOUR_UI_RC να δείχνει σε ενεÏγό αÏχείο εμφανίσεως UI" -#: main.cc:276 +#: main.cc:270 #, fuzzy msgid "Ardour could not connect to JACK." msgstr "Δεν γινόταν να συνδεθώ στον JACK server σαν \"%1\"" -#: main.cc:280 +#: main.cc:274 #, fuzzy msgid "" "There are several possible reasons:\n" @@ -4822,12 +4822,12 @@ msgstr "" "\n" "ΠαÏακαλώ αναλογιστείτε τις πιθανότητες, και ίσως (ξανα)ξεκινήστε τον JACK." -#: main.cc:310 +#: main.cc:304 msgid "could not load command line session \"%1\"" msgstr "δεν γινόταν να φοÏτωθεί η συνεδÏία γÏαμμής εντολών \"%1\"" #. it wasn't new, but we require a new session -#: main.cc:330 +#: main.cc:324 msgid "" "\n" "\n" @@ -4835,7 +4835,7 @@ msgid "" "To avoid this message, start ardour as \"ardour %1" msgstr "" -#: main.cc:341 +#: main.cc:335 msgid "" "\n" "\n" @@ -4843,63 +4843,63 @@ msgid "" "To create it from the command line, start ardour as \"ardour --new %1" msgstr "" -#: main.cc:405 +#: main.cc:399 msgid "Ardour/GTK " msgstr "Ardour/GTK " -#: main.cc:407 +#: main.cc:401 msgid "" "\n" " (built using " msgstr "" -#: main.cc:411 +#: main.cc:405 #, fuzzy msgid " with libardour " msgstr " Ï„Ïέχοντας με libardour " -#: main.cc:416 +#: main.cc:410 msgid " and GCC version " msgstr "" -#: main.cc:426 +#: main.cc:420 #, fuzzy msgid "Copyright (C) 1999-2006 Paul Davis" msgstr "Πνευματικα Δικαιώματα 1999-2004 Paul Davis" -#: main.cc:427 +#: main.cc:421 msgid "" "Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " "Baker" msgstr "" -#: main.cc:429 +#: main.cc:423 msgid "Ardour comes with ABSOLUTELY NO WARRANTY" msgstr "Ο Ardour έÏχεται με απολÏτως ΚΑΜΙΑ ΕΓΓΥΗΣΗ" -#: main.cc:430 +#: main.cc:424 msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." msgstr "" -#: main.cc:431 +#: main.cc:425 msgid "This is free software, and you are welcome to redistribute it " msgstr "" "Το παÏόν είναι ελεÏθεÏο λογισμικό, είστε ελεÏθεÏοι να το επαναδιανείμετε " -#: main.cc:432 +#: main.cc:426 #, fuzzy msgid "under certain conditions; see the source for copying conditions." msgstr "υπό οÏισμένους ÏŒÏους, ανατÏέξτε στο αÏχείο COPYING για λεπτομέÏειες" -#: main.cc:441 +#: main.cc:435 msgid "could not create ARDOUR GUI" msgstr "δεν γινόταν να δημιουÏγηθεί ARDOUR GUI" -#: main.cc:459 +#: main.cc:453 msgid "Could not connect to JACK server as \"%1\"" msgstr "Δεν γινόταν να συνδεθώ στον JACK server σαν \"%1\"" -#: main.cc:462 +#: main.cc:456 msgid "could not initialize Ardour." msgstr "δεν γινόταν να εκκινηθεί ο Ardour." diff --git a/gtk2_ardour/po/es_ES.po b/gtk2_ardour/po/es_ES.po index 10468d6ab8..88ba699420 100644 --- a/gtk2_ardour/po/es_ES.po +++ b/gtk2_ardour/po/es_ES.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: ardour 0.688.4\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-06-21 18:09-0400\n" +"POT-Creation-Date: 2006-06-27 13:00-0400\n" "PO-Revision-Date: 2004-01-21 12:45+0100\n" "Last-Translator: Alex Krohn \n" "Language-Team: Spanish\n" @@ -4827,19 +4827,19 @@ msgstr "deteniendo interfase visual\n" msgid "%d(%d): received signal %d\n" msgstr "" -#: main.cc:186 +#: main.cc:180 msgid "cannot become new process group leader (%1)" msgstr "" -#: main.cc:213 +#: main.cc:207 msgid "cannot setup signal handling for %1" msgstr "" -#: main.cc:224 +#: main.cc:218 msgid "cannot set default signal mask (%1)" msgstr "" -#: main.cc:254 +#: main.cc:248 #, fuzzy msgid "" "Without a UI style file, ardour will look strange.\n" @@ -4848,12 +4848,12 @@ msgstr "" "Sin un archivo de interfase visual, Ardour no se \n" "ver�correctamente. Apunte ARDOUR_UI_RC a un archivo v�ido" -#: main.cc:276 +#: main.cc:270 #, fuzzy msgid "Ardour could not connect to JACK." msgstr "No se pudo conectar a JACK con el nombre \"%1\"" -#: main.cc:280 +#: main.cc:274 #, fuzzy msgid "" "There are several possible reasons:\n" @@ -4873,12 +4873,12 @@ msgstr "" "\n" "Considere estas posibilidades y o reinicie a JACK.\n" -#: main.cc:310 +#: main.cc:304 msgid "could not load command line session \"%1\"" msgstr "no se pudo cargar desde l�ea de comando a la sesin \"%1\"" #. it wasn't new, but we require a new session -#: main.cc:330 +#: main.cc:324 msgid "" "\n" "\n" @@ -4886,7 +4886,7 @@ msgid "" "To avoid this message, start ardour as \"ardour %1" msgstr "" -#: main.cc:341 +#: main.cc:335 msgid "" "\n" "\n" @@ -4894,61 +4894,61 @@ msgid "" "To create it from the command line, start ardour as \"ardour --new %1" msgstr "" -#: main.cc:405 +#: main.cc:399 msgid "Ardour/GTK " msgstr "" -#: main.cc:407 +#: main.cc:401 msgid "" "\n" " (built using " msgstr "" -#: main.cc:411 +#: main.cc:405 #, fuzzy msgid " with libardour " msgstr " corriendo con libardour " -#: main.cc:416 +#: main.cc:410 msgid " and GCC version " msgstr "" -#: main.cc:426 +#: main.cc:420 msgid "Copyright (C) 1999-2006 Paul Davis" msgstr "" -#: main.cc:427 +#: main.cc:421 msgid "" "Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " "Baker" msgstr "" -#: main.cc:429 +#: main.cc:423 msgid "Ardour comes with ABSOLUTELY NO WARRANTY" msgstr "Ardour no ofrece ningn tipo de garant�" -#: main.cc:430 +#: main.cc:424 msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." msgstr "" -#: main.cc:431 +#: main.cc:425 msgid "This is free software, and you are welcome to redistribute it " msgstr "Este software es gratuito.Usted puede distribuirlo " -#: main.cc:432 +#: main.cc:426 #, fuzzy msgid "under certain conditions; see the source for copying conditions." msgstr "bajo ciertas condiciones; lea el archivo COPYING para m� detalles" -#: main.cc:441 +#: main.cc:435 msgid "could not create ARDOUR GUI" msgstr "no se pudo crear la interfase visual de Ardour" -#: main.cc:459 +#: main.cc:453 msgid "Could not connect to JACK server as \"%1\"" msgstr "No se pudo conectar a JACK con el nombre \"%1\"" -#: main.cc:462 +#: main.cc:456 msgid "could not initialize Ardour." msgstr "no se pudo iniciar a Ardour." diff --git a/gtk2_ardour/po/fr_FR.po b/gtk2_ardour/po/fr_FR.po index 4875e57712..c6911e89c6 100644 --- a/gtk2_ardour/po/fr_FR.po +++ b/gtk2_ardour/po/fr_FR.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: gtk-ardour 0.334.5\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-06-21 18:09-0400\n" +"POT-Creation-Date: 2006-06-27 13:00-0400\n" "PO-Revision-Date: 2005-02-14 11:19-0500\n" "Last-Translator: Alain Fréhel \n" "Language-Team: French \n" @@ -4809,19 +4809,19 @@ msgstr "en train d'arrêter l'interface utilisateur\n" msgid "%d(%d): received signal %d\n" msgstr "%d(%d) : reçu le signal %d\n" -#: main.cc:186 +#: main.cc:180 msgid "cannot become new process group leader (%1)" msgstr "" -#: main.cc:213 +#: main.cc:207 msgid "cannot setup signal handling for %1" msgstr "impossible d'installer le gestionnaire de signaux pour %1" -#: main.cc:224 +#: main.cc:218 msgid "cannot set default signal mask (%1)" msgstr "impossible de définir le masque de signalisation" -#: main.cc:254 +#: main.cc:248 #, fuzzy msgid "" "Without a UI style file, ardour will look strange.\n" @@ -4830,12 +4830,12 @@ msgstr "" "Sans un fichier de style pour son IHM, ardour aura une apparence bizarre.\n" "Veuillez faire pointer ARDOUR_UI_RC vers un fichier de style d'IHM valide" -#: main.cc:276 +#: main.cc:270 #, fuzzy msgid "Ardour could not connect to JACK." msgstr "Impossible de se reconnecter à JACK" -#: main.cc:280 +#: main.cc:274 #, fuzzy msgid "" "There are several possible reasons:\n" @@ -4855,12 +4855,12 @@ msgstr "" "\n" "Veuillez étudier les possibilités, et peut-être (re)lancer JACK." -#: main.cc:310 +#: main.cc:304 msgid "could not load command line session \"%1\"" msgstr "impossible de charger la session indiqué en ligne de commande \"%1\"" #. it wasn't new, but we require a new session -#: main.cc:330 +#: main.cc:324 msgid "" "\n" "\n" @@ -4872,7 +4872,7 @@ msgstr "" "Une session nommé \"%1\" existe déjà.\n" "Pour éviter ce message, lancez ardour comme cela : \"ardour %1" -#: main.cc:341 +#: main.cc:335 msgid "" "\n" "\n" @@ -4885,11 +4885,11 @@ msgstr "" "Pour la créer depuis la ligne de commande, lancez ardour comme cela : " "\"ardour --new %1" -#: main.cc:405 +#: main.cc:399 msgid "Ardour/GTK " msgstr "Ardour/GTK" -#: main.cc:407 +#: main.cc:401 msgid "" "\n" " (built using " @@ -4897,20 +4897,20 @@ msgstr "" "\n" " (fonctionnant avec " -#: main.cc:411 +#: main.cc:405 msgid " with libardour " msgstr " avec libardour " -#: main.cc:416 +#: main.cc:410 msgid " and GCC version " msgstr "" -#: main.cc:426 +#: main.cc:420 #, fuzzy msgid "Copyright (C) 1999-2006 Paul Davis" msgstr "Copyright (C) 1999-2005 Paul Davis" -#: main.cc:427 +#: main.cc:421 msgid "" "Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " "Baker" @@ -4918,33 +4918,33 @@ msgstr "" "Certaines parties Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " "Baker" -#: main.cc:429 +#: main.cc:423 msgid "Ardour comes with ABSOLUTELY NO WARRANTY" msgstr "Ardour est distribué sans AUCUNE GARANTIE" -#: main.cc:430 +#: main.cc:424 msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." msgstr "ni même pour la COMMERCIALISATION ou pour UN BUT PARTICULIER." -#: main.cc:431 +#: main.cc:425 msgid "This is free software, and you are welcome to redistribute it " msgstr "Ceci est un logiciel libre, et vous êtes encouragé à le distribuer " -#: main.cc:432 +#: main.cc:426 msgid "under certain conditions; see the source for copying conditions." msgstr "" "sous certaines conditions ; voir le fichier source pour les conditions de " "distribution." -#: main.cc:441 +#: main.cc:435 msgid "could not create ARDOUR GUI" msgstr "impossible de créer l'interface utilisateur d'ARDOUR" -#: main.cc:459 +#: main.cc:453 msgid "Could not connect to JACK server as \"%1\"" msgstr "Impossible de se connecter au serveur JACK en tant que \"%1\"" -#: main.cc:462 +#: main.cc:456 msgid "could not initialize Ardour." msgstr "impossible d'initialiser Ardour." diff --git a/gtk2_ardour/po/it_IT.po b/gtk2_ardour/po/it_IT.po index f283f846da..ef2a1b3e58 100644 --- a/gtk2_ardour/po/it_IT.po +++ b/gtk2_ardour/po/it_IT.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: ardour 0.354.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-06-21 18:09-0400\n" +"POT-Creation-Date: 2006-06-27 13:00-0400\n" "PO-Revision-Date: 2003-05-20 13:03-0500\n" "Last-Translator: Filippo Pappalardo \n" "Language-Team: Italian\n" @@ -4727,19 +4727,19 @@ msgstr "chiusura dell'interfaccia\n" msgid "%d(%d): received signal %d\n" msgstr "%d: ricevuto segnale %d\n" -#: main.cc:186 +#: main.cc:180 msgid "cannot become new process group leader (%1)" msgstr "" -#: main.cc:213 +#: main.cc:207 msgid "cannot setup signal handling for %1" msgstr "" -#: main.cc:224 +#: main.cc:218 msgid "cannot set default signal mask (%1)" msgstr "" -#: main.cc:254 +#: main.cc:248 #, fuzzy msgid "" "Without a UI style file, ardour will look strange.\n" @@ -4748,11 +4748,11 @@ msgstr "" "Senza uno Stile per l'Interfaccia, ardour apparirà strano\n" "Impostare la variabile ARDOUR_UI_RC per puntare ad uno Stile" -#: main.cc:276 +#: main.cc:270 msgid "Ardour could not connect to JACK." msgstr "" -#: main.cc:280 +#: main.cc:274 msgid "" "There are several possible reasons:\n" "\n" @@ -4763,12 +4763,12 @@ msgid "" "Please consider the possibilities, and perhaps (re)start JACK." msgstr "" -#: main.cc:310 +#: main.cc:304 msgid "could not load command line session \"%1\"" msgstr "Impossibile caricare la sessione \"%1\" da linea di comando" #. it wasn't new, but we require a new session -#: main.cc:330 +#: main.cc:324 msgid "" "\n" "\n" @@ -4776,7 +4776,7 @@ msgid "" "To avoid this message, start ardour as \"ardour %1" msgstr "" -#: main.cc:341 +#: main.cc:335 msgid "" "\n" "\n" @@ -4784,60 +4784,60 @@ msgid "" "To create it from the command line, start ardour as \"ardour --new %1" msgstr "" -#: main.cc:405 +#: main.cc:399 msgid "Ardour/GTK " msgstr "" -#: main.cc:407 +#: main.cc:401 msgid "" "\n" " (built using " msgstr "" -#: main.cc:411 +#: main.cc:405 #, fuzzy msgid " with libardour " msgstr " con libardour " -#: main.cc:416 +#: main.cc:410 msgid " and GCC version " msgstr "" -#: main.cc:426 +#: main.cc:420 msgid "Copyright (C) 1999-2006 Paul Davis" msgstr "" -#: main.cc:427 +#: main.cc:421 msgid "" "Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " "Baker" msgstr "" -#: main.cc:429 +#: main.cc:423 msgid "Ardour comes with ABSOLUTELY NO WARRANTY" msgstr "" -#: main.cc:430 +#: main.cc:424 msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." msgstr "" -#: main.cc:431 +#: main.cc:425 msgid "This is free software, and you are welcome to redistribute it " msgstr "" -#: main.cc:432 +#: main.cc:426 msgid "under certain conditions; see the source for copying conditions." msgstr "" -#: main.cc:441 +#: main.cc:435 msgid "could not create ARDOUR GUI" msgstr "Impossibile creare l'interfaccia di Ardour" -#: main.cc:459 +#: main.cc:453 msgid "Could not connect to JACK server as \"%1\"" msgstr "" -#: main.cc:462 +#: main.cc:456 msgid "could not initialize Ardour." msgstr "impossibile avviare Ardour" diff --git a/gtk2_ardour/po/pt_BR.po b/gtk2_ardour/po/pt_BR.po index 92c0d7934a..1a10e8abcd 100644 --- a/gtk2_ardour/po/pt_BR.po +++ b/gtk2_ardour/po/pt_BR.po @@ -10,7 +10,7 @@ msgid "" msgstr "" "Project-Id-Version: ardour 0.688.4\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-06-21 18:09-0400\n" +"POT-Creation-Date: 2006-06-27 13:00-0400\n" "PO-Revision-Date: 2005-08-15 21:50-0000\n" "Last-Translator: Chris Ross, Alexander Franca & Leandro Marco\n" "Language-Team: Portuguese\n" @@ -4779,19 +4779,19 @@ msgstr "interrompendo a interface do usuário\n" msgid "%d(%d): received signal %d\n" msgstr "" -#: main.cc:186 +#: main.cc:180 msgid "cannot become new process group leader (%1)" msgstr "" -#: main.cc:213 +#: main.cc:207 msgid "cannot setup signal handling for %1" msgstr "" -#: main.cc:224 +#: main.cc:218 msgid "cannot set default signal mask (%1)" msgstr "" -#: main.cc:254 +#: main.cc:248 #, fuzzy msgid "" "Without a UI style file, ardour will look strange.\n" @@ -4800,12 +4800,12 @@ msgstr "" "Sem um arquivo de estilo o ardour vai ficar meio esquisito.\n" "Por favor, configure a variável ambiente ARDOUR_UI_RC para um arquivo válido" -#: main.cc:276 +#: main.cc:270 #, fuzzy msgid "Ardour could not connect to JACK." msgstr "Não foi possível se conectar ao servidor JACK" -#: main.cc:280 +#: main.cc:274 #, fuzzy msgid "" "There are several possible reasons:\n" @@ -4825,12 +4825,12 @@ msgstr "" "\n" "Por favor, considere essas razões, e talvez (re)inicie o JACK." -#: main.cc:310 +#: main.cc:304 msgid "could not load command line session \"%1\"" msgstr "não foi possível carregar a sessão da linha de comando \"%1\"" #. it wasn't new, but we require a new session -#: main.cc:330 +#: main.cc:324 msgid "" "\n" "\n" @@ -4838,7 +4838,7 @@ msgid "" "To avoid this message, start ardour as \"ardour %1" msgstr "" -#: main.cc:341 +#: main.cc:335 msgid "" "\n" "\n" @@ -4846,60 +4846,60 @@ msgid "" "To create it from the command line, start ardour as \"ardour --new %1" msgstr "" -#: main.cc:405 +#: main.cc:399 msgid "Ardour/GTK " msgstr "" -#: main.cc:407 +#: main.cc:401 msgid "" "\n" " (built using " msgstr "" -#: main.cc:411 +#: main.cc:405 #, fuzzy msgid " with libardour " msgstr " executando com libardour " -#: main.cc:416 +#: main.cc:410 msgid " and GCC version " msgstr "" -#: main.cc:426 +#: main.cc:420 msgid "Copyright (C) 1999-2006 Paul Davis" msgstr "" -#: main.cc:427 +#: main.cc:421 msgid "" "Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " "Baker" msgstr "" -#: main.cc:429 +#: main.cc:423 msgid "Ardour comes with ABSOLUTELY NO WARRANTY" msgstr "Ardour não oferece ABSOLUTAMENTE NENHUMA GARANTIA" -#: main.cc:430 +#: main.cc:424 msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." msgstr "" -#: main.cc:431 +#: main.cc:425 msgid "This is free software, and you are welcome to redistribute it " msgstr "Isto é um Software Livre. Fique à vontade para redistribuí-lo " -#: main.cc:432 +#: main.cc:426 msgid "under certain conditions; see the source for copying conditions." msgstr "com algumas condições; veja o fonte para mais detalhes" -#: main.cc:441 +#: main.cc:435 msgid "could not create ARDOUR GUI" msgstr "não foi possível criar a INTERFACE ARDOUR" -#: main.cc:459 +#: main.cc:453 msgid "Could not connect to JACK server as \"%1\"" msgstr "Não foi possível se conectar ao servidor JACK com \"%1\"" -#: main.cc:462 +#: main.cc:456 msgid "could not initialize Ardour." msgstr "não foi possível iniciar o Ardour." diff --git a/gtk2_ardour/po/pt_PT.po b/gtk2_ardour/po/pt_PT.po index f07f025713..9499f4b29c 100644 --- a/gtk2_ardour/po/pt_PT.po +++ b/gtk2_ardour/po/pt_PT.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: 0.814.2\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-06-21 18:09-0400\n" +"POT-Creation-Date: 2006-06-27 13:00-0400\n" "PO-Revision-Date: 2004-12-07 13:00+0000\n" "Last-Translator: Rui Nuno Capela \n" "Language-Team: Portuguese\n" @@ -4768,19 +4768,19 @@ msgstr "interface homem-máquina em fase terminal\n" msgid "%d(%d): received signal %d\n" msgstr "%d: sinal %d recebido\n" -#: main.cc:186 +#: main.cc:180 msgid "cannot become new process group leader (%1)" msgstr "" -#: main.cc:213 +#: main.cc:207 msgid "cannot setup signal handling for %1" msgstr "não foi possível estabelecer receptor de sinal %1" -#: main.cc:224 +#: main.cc:218 msgid "cannot set default signal mask (%1)" msgstr "não foi possível estabelecer máscara de sinal %1" -#: main.cc:254 +#: main.cc:248 #, fuzzy msgid "" "Without a UI style file, ardour will look strange.\n" @@ -4791,12 +4791,12 @@ msgstr "" "Por favor, indique um ficheiro de estilo visual válido em ARDOUR_UI_RC " "(variável de ambiente)" -#: main.cc:276 +#: main.cc:270 #, fuzzy msgid "Ardour could not connect to JACK." msgstr "Não foi possível conectar ao serviço JACK como \"%1\"" -#: main.cc:280 +#: main.cc:274 #, fuzzy msgid "" "There are several possible reasons:\n" @@ -4816,12 +4816,12 @@ msgstr "" "\n" "Por favor, considere estas possibilidades e (re)inicie o serviço JACK." -#: main.cc:310 +#: main.cc:304 msgid "could not load command line session \"%1\"" msgstr "não foi possível carregar a sessão de linha de comando \"%1\"" #. it wasn't new, but we require a new session -#: main.cc:330 +#: main.cc:324 msgid "" "\n" "\n" @@ -4829,7 +4829,7 @@ msgid "" "To avoid this message, start ardour as \"ardour %1" msgstr "" -#: main.cc:341 +#: main.cc:335 msgid "" "\n" "\n" @@ -4837,63 +4837,63 @@ msgid "" "To create it from the command line, start ardour as \"ardour --new %1" msgstr "" -#: main.cc:405 +#: main.cc:399 msgid "Ardour/GTK " msgstr "" -#: main.cc:407 +#: main.cc:401 msgid "" "\n" " (built using " msgstr "" -#: main.cc:411 +#: main.cc:405 #, fuzzy msgid " with libardour " msgstr " em execução com libardour " -#: main.cc:416 +#: main.cc:410 msgid " and GCC version " msgstr "" -#: main.cc:426 +#: main.cc:420 msgid "Copyright (C) 1999-2006 Paul Davis" msgstr "" -#: main.cc:427 +#: main.cc:421 msgid "" "Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " "Baker" msgstr "" -#: main.cc:429 +#: main.cc:423 msgid "Ardour comes with ABSOLUTELY NO WARRANTY" msgstr "Ardour é fornecido ABSOLUTAMENTE SEM QUALQUER GARANTIA" -#: main.cc:430 +#: main.cc:424 msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." msgstr "" -#: main.cc:431 +#: main.cc:425 msgid "This is free software, and you are welcome to redistribute it " msgstr "Sendo software livre, é permitida e até encorajada a sua distribuição" -#: main.cc:432 +#: main.cc:426 #, fuzzy msgid "under certain conditions; see the source for copying conditions." msgstr "" "desde que sejam respeitadas algumas condições; para mais informações, leia " "por favor o ficheiro COPYING." -#: main.cc:441 +#: main.cc:435 msgid "could not create ARDOUR GUI" msgstr "não foi possível criar o interface gráfico (GUI)" -#: main.cc:459 +#: main.cc:453 msgid "Could not connect to JACK server as \"%1\"" msgstr "Não foi possível conectar ao serviço JACK como \"%1\"" -#: main.cc:462 +#: main.cc:456 msgid "could not initialize Ardour." msgstr "não foi possível inicializar o Ardour" diff --git a/gtk2_ardour/po/ru_RU.po b/gtk2_ardour/po/ru_RU.po index 7d9e33695c..2a7183442f 100644 --- a/gtk2_ardour/po/ru_RU.po +++ b/gtk2_ardour/po/ru_RU.po @@ -6,7 +6,7 @@ msgid "" msgstr "" "Project-Id-Version: gtk-ardour 0.413.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-06-21 18:09-0400\n" +"POT-Creation-Date: 2006-06-27 13:00-0400\n" "PO-Revision-Date: 2004-03-31 00:45+0300\n" "Last-Translator: Igor Blinov pitstop@nm.ru\n" "Language-Team: Russian\n" @@ -4795,19 +4795,19 @@ msgstr "завершение работы...\n" msgid "%d(%d): received signal %d\n" msgstr "%d: принÑÑ‚ Ñигнал %d\n" -#: main.cc:186 +#: main.cc:180 msgid "cannot become new process group leader (%1)" msgstr "" -#: main.cc:213 +#: main.cc:207 msgid "cannot setup signal handling for %1" msgstr "cannot setup signal handling for %1" -#: main.cc:224 +#: main.cc:218 msgid "cannot set default signal mask (%1)" msgstr "cannot set default signal mask (%1)" -#: main.cc:254 +#: main.cc:248 #, fuzzy msgid "" "Without a UI style file, ardour will look strange.\n" @@ -4817,12 +4817,12 @@ msgstr "" "без файла определÑющего Ñтиль отображениÑ.\n" "ПожалуйÑта, укажите его (файл) в переменной Ð¾ÐºÑ€ÑƒÐ¶ÐµÐ½Ð¸Ñ ARDOUR_UI_RC" -#: main.cc:276 +#: main.cc:270 #, fuzzy msgid "Ardour could not connect to JACK." msgstr "Ðе удалоÑÑŒ ÑоединитьÑÑ Ñ Ñервером JACK как \"%1\"" -#: main.cc:280 +#: main.cc:274 #, fuzzy msgid "" "There are several possible reasons:\n" @@ -4842,12 +4842,12 @@ msgstr "" "\n" "ПожалуйÑта, проверьте вÑе варианты, возможно потребуетÑÑ (пере)запуÑк JACK." -#: main.cc:310 +#: main.cc:304 msgid "could not load command line session \"%1\"" msgstr "не удалоÑÑŒ загрузить ÑеÑÑию \"%1\", указанную в командной Ñтроке" #. it wasn't new, but we require a new session -#: main.cc:330 +#: main.cc:324 msgid "" "\n" "\n" @@ -4855,7 +4855,7 @@ msgid "" "To avoid this message, start ardour as \"ardour %1" msgstr "" -#: main.cc:341 +#: main.cc:335 msgid "" "\n" "\n" @@ -4863,62 +4863,62 @@ msgid "" "To create it from the command line, start ardour as \"ardour --new %1" msgstr "" -#: main.cc:405 +#: main.cc:399 msgid "Ardour/GTK " msgstr "Ardour/GTK " -#: main.cc:407 +#: main.cc:401 msgid "" "\n" " (built using " msgstr "" -#: main.cc:411 +#: main.cc:405 #, fuzzy msgid " with libardour " msgstr " работает Ñ libardour " -#: main.cc:416 +#: main.cc:410 msgid " and GCC version " msgstr "" -#: main.cc:426 +#: main.cc:420 #, fuzzy msgid "Copyright (C) 1999-2006 Paul Davis" msgstr "ÐвторÑкое право 1999-2004 Paul Davis" -#: main.cc:427 +#: main.cc:421 msgid "" "Some portions Copyright (C) Steve Harris, Ari Johnson, Brett Viren, Joel " "Baker" msgstr "" -#: main.cc:429 +#: main.cc:423 msgid "Ardour comes with ABSOLUTELY NO WARRANTY" msgstr "Ardour раÑпроÑтранÑетÑÑ Ð‘Ð•Ð— ВСЯКИХ ГÐРÐÐТИЙ" -#: main.cc:430 +#: main.cc:424 msgid "not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE." msgstr "" -#: main.cc:431 +#: main.cc:425 msgid "This is free software, and you are welcome to redistribute it " msgstr "Это Ñвободное программное обеÑпечение, Ð’Ñ‹ можете раÑпроÑтранÑть его" -#: main.cc:432 +#: main.cc:426 #, fuzzy msgid "under certain conditions; see the source for copying conditions." msgstr "на определённых уÑловиÑÑ…; подробнее об Ñтом читайте в файле COPYING." -#: main.cc:441 +#: main.cc:435 msgid "could not create ARDOUR GUI" msgstr "не удалоÑÑŒ Ñоздать графичеÑкий Ð¸Ð½Ñ‚ÐµÑ€Ñ„ÐµÐ¹Ñ Ð´Ð»Ñ ARDOUR" -#: main.cc:459 +#: main.cc:453 msgid "Could not connect to JACK server as \"%1\"" msgstr "Ðе удалоÑÑŒ ÑоединитьÑÑ Ñ Ñервером JACK как \"%1\"" -#: main.cc:462 +#: main.cc:456 msgid "could not initialize Ardour." msgstr "не удалоÑÑŒ запуÑтить Ardour." diff --git a/libs/ardour/SConscript b/libs/ardour/SConscript index 605911d7ef..f5f1272fb8 100644 --- a/libs/ardour/SConscript +++ b/libs/ardour/SConscript @@ -98,7 +98,7 @@ arch_specific_objects = [ ] osc_files = [ 'osc.cc' ] vst_files = [ 'vst_plugin.cc', 'session_vst.cc' ] -coreaudio_files = [ 'coreaudio_source.cc' ] +coreaudio_files = [ 'coreaudiosource.cc' ] extra_sources = [ ] if ardour['VST']: diff --git a/libs/ardour/ardour/audiofilesource.h b/libs/ardour/ardour/audiofilesource.h index ecbac569d5..36251c07ff 100644 --- a/libs/ardour/ardour/audiofilesource.h +++ b/libs/ardour/ardour/audiofilesource.h @@ -42,7 +42,7 @@ class AudioFileSource : public AudioSource { Removable = 0x8, RemovableIfEmpty = 0x10, RemoveAtDestroy = 0x20, - BuildPeaks = 0x40 + NoPeakFile = 0x40 }; virtual ~AudioFileSource (); @@ -62,7 +62,7 @@ class AudioFileSource : public AudioSource { cannot. */ - static AudioFileSource* create (string path_plus_channel); + static AudioFileSource* create (const string& path_plus_channel, Flag flags = Flag (0)); static AudioFileSource* create (const XMLNode&); static bool get_soundfile_info (string path, SoundFileInfo& _info, string& error); @@ -97,7 +97,7 @@ class AudioFileSource : public AudioSource { static void set_search_path (string); static void set_header_position_offset (jack_nframes_t offset, bool negative); - static sigc::signal HeaderPositionOffsetChanged; + static sigc::signal HeaderPositionOffsetChanged; XMLNode& get_state (); int set_state (const XMLNode&); @@ -107,7 +107,7 @@ class AudioFileSource : public AudioSource { to cause issues. */ - void handle_header_position_change (struct tm*, time_t tnow); + void handle_header_position_change (); protected: diff --git a/libs/ardour/ardour/coreaudio_source.h b/libs/ardour/ardour/coreaudiosource.h similarity index 84% rename from libs/ardour/ardour/coreaudio_source.h rename to libs/ardour/ardour/coreaudiosource.h index 81f1a14050..ba9f122fc9 100644 --- a/libs/ardour/ardour/coreaudio_source.h +++ b/libs/ardour/ardour/coreaudiosource.h @@ -27,15 +27,22 @@ namespace ARDOUR { class CoreAudioSource : public AudioFileSource { public: - CoreAudioSource (const string& path_plus_channel, bool build_peak = true); CoreAudioSource (const XMLNode&); + CoreAudioSource (const string& path_plus_channel, Flag); ~CoreAudioSource (); float sample_rate() const; int update_header (jack_nframes_t when, struct tm&, time_t); + int flush_header () {return 0;}; + void set_header_timeline_position () {}; + protected: jack_nframes_t read_unlocked (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const; + + jack_nframes_t write_unlocked (Sample *dst, jack_nframes_t cnt, char * workbuf) + { return 0; } + private: ExtAudioFileRef af; @@ -45,7 +52,7 @@ class CoreAudioSource : public AudioFileSource { mutable jack_nframes_t tmpbufsize; mutable Glib::Mutex _tmpbuf_lock; - void init (const string &str, bool build_peak); + void init (const string &str); }; }; /* namespace ARDOUR */ diff --git a/libs/ardour/ardour/destructive_filesource.h b/libs/ardour/ardour/destructive_filesource.h index c92a0762ee..2d10528ac8 100644 --- a/libs/ardour/ardour/destructive_filesource.h +++ b/libs/ardour/ardour/destructive_filesource.h @@ -32,8 +32,7 @@ namespace ARDOUR { class DestructiveFileSource : public SndFileSource { public: DestructiveFileSource (std::string path, SampleFormat samp_format, HeaderFormat hdr_format, jack_nframes_t rate, - Flag flags = AudioFileSource::Flag (AudioFileSource::Writable| - AudioFileSource::BuildPeaks)); + Flag flags = AudioFileSource::Flag (AudioFileSource::Writable)); DestructiveFileSource (const XMLNode&); ~DestructiveFileSource (); diff --git a/libs/ardour/ardour/sndfilesource.h b/libs/ardour/ardour/sndfilesource.h index d146bb5793..5e3c1f621d 100644 --- a/libs/ardour/ardour/sndfilesource.h +++ b/libs/ardour/ardour/sndfilesource.h @@ -39,8 +39,7 @@ class SndFileSource : public AudioFileSource { Flag flags = AudioFileSource::Flag (AudioFileSource::Writable| AudioFileSource::Removable| AudioFileSource::RemovableIfEmpty| - AudioFileSource::CanRename| - AudioFileSource::BuildPeaks)); + AudioFileSource::CanRename)); /* constructor to be called for existing in-session files */ @@ -52,7 +51,7 @@ class SndFileSource : public AudioFileSource { int update_header (jack_nframes_t when, struct tm&, time_t); int flush_header (); - static Flag default_in_session_flags(); + void handle_smpte_offset_change (jack_nframes_t offset, bool negative); protected: void set_header_timeline_position (); diff --git a/libs/ardour/audio_diskstream.cc b/libs/ardour/audio_diskstream.cc index 69f00efe68..96615fd077 100644 --- a/libs/ardour/audio_diskstream.cc +++ b/libs/ardour/audio_diskstream.cc @@ -1754,6 +1754,7 @@ AudioDiskstream::transport_stopped (struct tm& when, time_t twhen, bool abort_ca srcs.push_back (s); if ((fsrc = dynamic_cast(s)) != 0) { + cerr << "updating source after capture\n"; fsrc->update_header (capture_info.front()->start, when, twhen); } diff --git a/libs/ardour/audio_playlist.cc b/libs/ardour/audio_playlist.cc index bbbaf42fef..85c11647f4 100644 --- a/libs/ardour/audio_playlist.cc +++ b/libs/ardour/audio_playlist.cc @@ -20,7 +20,7 @@ #include -#include +#include #include diff --git a/libs/ardour/audio_track.cc b/libs/ardour/audio_track.cc index ae24d3a577..74b7dd071c 100644 --- a/libs/ardour/audio_track.cc +++ b/libs/ardour/audio_track.cc @@ -94,14 +94,6 @@ AudioTrack::~AudioTrack () } } -#if 0 -void -AudioTrack::handle_smpte_offset_change () -{ - diskstream -} -#endif - int AudioTrack::deprecated_use_diskstream_connections () { diff --git a/libs/ardour/audiofilesource.cc b/libs/ardour/audiofilesource.cc index 1e13a29acc..0663f5f9b1 100644 --- a/libs/ardour/audiofilesource.cc +++ b/libs/ardour/audiofilesource.cc @@ -42,7 +42,7 @@ // if these headers come before sigc++ is included // the parser throws ObjC++ errors. (nil is a keyword) #ifdef HAVE_COREAUDIO -#include +#include #include #include #endif // HAVE_COREAUDIO @@ -55,9 +55,9 @@ using namespace PBD; string AudioFileSource::peak_dir = ""; string AudioFileSource::search_path; -sigc::signal AudioFileSource::HeaderPositionOffsetChanged; -bool AudioFileSource::header_position_negative; -uint64_t AudioFileSource::header_position_offset; +sigc::signal AudioFileSource::HeaderPositionOffsetChanged; +bool AudioFileSource::header_position_negative; +uint64_t AudioFileSource::header_position_offset; char AudioFileSource::bwf_country_code[3] = "US"; char AudioFileSource::bwf_organization_code[4] = "LAS"; @@ -122,7 +122,6 @@ AudioFileSource::init (string pathstr, bool must_exist) next_peak_clear_should_notify = false; if (!find (pathstr, must_exist, is_new)) { - cerr << "cannot find " << pathstr << " with me = " << must_exist << endl; return -1; } @@ -211,16 +210,16 @@ AudioFileSource::create (const XMLNode& node) #ifdef HAVE_COREAUDIO AudioFileSource* -AudioFileSource::create (const string& idstr) +AudioFileSource::create (const string& idstr, Flag flags) { AudioFileSource* es = 0; try { - es = new CoreAudioSource (idstr); + es = new CoreAudioSource (idstr, flags); } catch (failed_constructor& err) { - es = new SndFileSource (idstr); + es = new SndFileSource (idstr, flags); } return es; @@ -229,9 +228,9 @@ AudioFileSource::create (const string& idstr) #else AudioFileSource* -AudioFileSource::create (string idstr) +AudioFileSource::create (const string& idstr, Flag flags) { - return new SndFileSource (idstr); + return new SndFileSource (idstr, flags); } #endif // HAVE_COREAUDIO @@ -595,13 +594,19 @@ AudioFileSource::set_search_path (string p) void AudioFileSource::set_header_position_offset (jack_nframes_t offset, bool negative) { - time_t tnow; - - time (&tnow); - header_position_offset = offset; header_position_negative = negative; - HeaderPositionOffsetChanged (localtime (&tnow), tnow); /* EMIT SIGNAL */ + + HeaderPositionOffsetChanged (); +} + +void +AudioFileSource::handle_header_position_change () +{ + if (writable()) { + set_header_timeline_position (); + flush_header (); + } } void @@ -610,17 +615,6 @@ AudioFileSource::set_timeline_position (jack_nframes_t pos) timeline_position = pos; } -void -AudioFileSource::handle_header_position_change (struct tm* now, time_t tnow) -{ - /* don't do this if the file has never had its header flushed to disk yet */ - - if (writable() && _timestamp) { - set_header_timeline_position (); - flush_header (); - } -} - void AudioFileSource::set_allow_remove_if_empty (bool yn) { @@ -655,8 +649,14 @@ AudioFileSource::set_name (string newname, bool destructive) bool AudioFileSource::is_empty (string path) { - /* XXX fix me */ + bool ret = false; + AudioFileSource* afs = create (path, NoPeakFile); - return false; + if (afs) { + ret = (afs->length() == 0); + delete afs; + } + + return ret; } diff --git a/libs/ardour/coreaudio_source.cc b/libs/ardour/coreaudiosource.cc similarity index 92% rename from libs/ardour/coreaudio_source.cc rename to libs/ardour/coreaudiosource.cc index 1b0ee565e7..55409a8524 100644 --- a/libs/ardour/coreaudio_source.cc +++ b/libs/ardour/coreaudiosource.cc @@ -18,8 +18,7 @@ */ #include - -#include +#include #include "i18n.h" @@ -31,22 +30,21 @@ using namespace PBD; CoreAudioSource::CoreAudioSource (const XMLNode& node) : AudioFileSource (node) { - init (_name, true); + init (_name); + AudioSourceCreated (this); /* EMIT SIGNAL */ } -CoreAudioSource::CoreAudioSource (const string& idstr, bool build_peak) - : AudioFileSource(idstr, build_peak) +CoreAudioSource::CoreAudioSource (const string& idstr, Flag flags) + : AudioFileSource(idstr, flags) { - init (idstr, build_peak); + init (idstr); - if (build_peak) { - AudioSourceCreated (this); /* EMIT SIGNAL */ - } + AudioSourceCreated (this); /* EMIT SIGNAL */ } void -CoreAudioSource::init (const string& idstr, bool build_peak) +CoreAudioSource::init (const string& idstr) { string::size_type pos; string file; @@ -132,7 +130,7 @@ CoreAudioSource::init (const string& idstr, bool build_peak) throw failed_constructor (); } - if (build_peak) { + if (_build_peakfiles) { if (initialize_peakfile (false, file)) { error << "initialize peakfile failed" << endmsg; ExtAudioFileDispose (af); @@ -155,7 +153,7 @@ CoreAudioSource::~CoreAudioSource () } jack_nframes_t -CoreAudioSource::read (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const +CoreAudioSource::read_unlocked (Sample *dst, jack_nframes_t start, jack_nframes_t cnt, char * workbuf) const { OSStatus err = noErr; diff --git a/libs/ardour/po/el_GR.po b/libs/ardour/po/el_GR.po index fb235155f3..33c1bb6e85 100644 --- a/libs/ardour/po/el_GR.po +++ b/libs/ardour/po/el_GR.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: libardour 0.664.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-06-21 15:09-0400\n" +"POT-Creation-Date: 2006-06-27 13:00-0400\n" "PO-Revision-Date: 2003-05-21 12:50+0500\n" "Last-Translator: Muadibas\n" "Language-Team: Hellenic(Greek)\n" @@ -198,77 +198,77 @@ msgid "programming error: AudioTrack given state without diskstream!" msgstr "" "σφάλμα Ï€ÏογÏαμματισμοÏ: εδόθη κατάσταση στην AudioTrack δίχως diskstream!" -#: libs/ardour/audioengine.cc:150 +#: libs/ardour/audioengine.cc:144 msgid "cannot activate JACK client" msgstr "Ο JACK δεν μποÏεί να ενεÏγοποιηθεί" -#: libs/ardour/audioengine.cc:401 +#: libs/ardour/audioengine.cc:395 msgid "register audio input port called before engine was started" msgstr "η register audio input port εκλήθη Ï€Ïιν να εκκινηθεί η engine" -#: libs/ardour/audioengine.cc:432 +#: libs/ardour/audioengine.cc:426 msgid "register audio output port called before engine was started" msgstr "η register audio output port εκλήθη Ï€Ïίν να εκκινηθεί η engine" -#: libs/ardour/audioengine.cc:493 +#: libs/ardour/audioengine.cc:487 msgid "connect called before engine was started" msgstr "η σÏνδεση εκλήθη Ï€Ïιν να εκκινηθεί η engine" -#: libs/ardour/audioengine.cc:509 +#: libs/ardour/audioengine.cc:503 msgid "AudioEngine: cannot connect %1 (%2) to %3 (%4)" msgstr "" -#: libs/ardour/audioengine.cc:522 libs/ardour/audioengine.cc:551 +#: libs/ardour/audioengine.cc:516 libs/ardour/audioengine.cc:545 msgid "disconnect called before engine was started" msgstr "η αποσÏνδεση εκλήθη Ï€Ïιν να εκκινηθεί η engine" -#: libs/ardour/audioengine.cc:609 +#: libs/ardour/audioengine.cc:603 msgid "get_port_by_name() called before engine was started" msgstr "η Ïουτίνα get_port_by_name() εκλήθη Ï€Ïιν να εκκινηθεί η engine" -#: libs/ardour/audioengine.cc:642 +#: libs/ardour/audioengine.cc:636 msgid "get_ports called before engine was started" msgstr "η Ïουτίνα get_ports εκλήθη Ï€Ïιν να εκκινηθεί η engine" -#: libs/ardour/audioengine.cc:717 +#: libs/ardour/audioengine.cc:711 msgid "get_nth_physical called before engine was started" msgstr "η Ïουτίνα get_nth_physical εκλήθη Ï€Ïιν να εκκινηθεί η engine" -#: libs/ardour/audioengine.cc:745 +#: libs/ardour/audioengine.cc:739 #, fuzzy msgid "get_port_total_latency() called with no JACK client connection" msgstr "η Ïουτίνα get_port_total_latency() εκλήθη Ï€Ïιν να εκκινηθεί η engine" -#: libs/ardour/audioengine.cc:751 +#: libs/ardour/audioengine.cc:745 msgid "get_port_total_latency() called before engine was started" msgstr "η Ïουτίνα get_port_total_latency() εκλήθη Ï€Ïιν να εκκινηθεί η engine" -#: libs/ardour/audioengine.cc:875 +#: libs/ardour/audioengine.cc:869 msgid "Unable to connect to JACK server" msgstr "" -#: libs/ardour/audioengine.cc:878 +#: libs/ardour/audioengine.cc:872 msgid "Could not connect to JACK server as \"%1\"" msgstr "" -#: libs/ardour/audioengine.cc:883 +#: libs/ardour/audioengine.cc:877 msgid "JACK server started" msgstr "" -#: libs/ardour/audioengine.cc:917 +#: libs/ardour/audioengine.cc:911 msgid "cannot shutdown connection to JACK" msgstr "" -#: libs/ardour/audioengine.cc:942 +#: libs/ardour/audioengine.cc:936 msgid "failed to connect to JACK" msgstr "" -#: libs/ardour/audioengine.cc:958 +#: libs/ardour/audioengine.cc:952 #, fuzzy msgid "could not reregister %1" msgstr "Σφάλμα: δεν μπόÏεσα να γÏάψω %1" -#: libs/ardour/audioengine.cc:1015 +#: libs/ardour/audioengine.cc:1009 msgid "could not reconnect %1 and %2 (err = %3)" msgstr "" diff --git a/libs/ardour/po/it_IT.po b/libs/ardour/po/it_IT.po index 55368c2d5a..63089ea77f 100644 --- a/libs/ardour/po/it_IT.po +++ b/libs/ardour/po/it_IT.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: libardour 0.664.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-06-21 15:09-0400\n" +"POT-Creation-Date: 2006-06-27 13:00-0400\n" "PO-Revision-Date: 2003-05-21 12:50+0500\n" "Last-Translator: Filippo Pappalardo \n" "Language-Team: Italian\n" @@ -183,88 +183,88 @@ msgstr "" msgid "programming error: AudioTrack given state without diskstream!" msgstr "" -#: libs/ardour/audioengine.cc:150 +#: libs/ardour/audioengine.cc:144 msgid "cannot activate JACK client" msgstr "impossibile attivare il client JACK" -#: libs/ardour/audioengine.cc:401 +#: libs/ardour/audioengine.cc:395 msgid "register audio input port called before engine was started" msgstr "" "la richiesta di registrazione di una porta di entrata avvenuta prima " "dell'avvio dell'applicazione" -#: libs/ardour/audioengine.cc:432 +#: libs/ardour/audioengine.cc:426 msgid "register audio output port called before engine was started" msgstr "" "la richiesta di registrazione di una porta di uscita avvenuta prima " "dell'avvio dell'applicazione" -#: libs/ardour/audioengine.cc:493 +#: libs/ardour/audioengine.cc:487 msgid "connect called before engine was started" msgstr "richiesta di connessione avvenuta prima dell'avvio dell'applicazione" -#: libs/ardour/audioengine.cc:509 +#: libs/ardour/audioengine.cc:503 msgid "AudioEngine: cannot connect %1 (%2) to %3 (%4)" msgstr "" -#: libs/ardour/audioengine.cc:522 libs/ardour/audioengine.cc:551 +#: libs/ardour/audioengine.cc:516 libs/ardour/audioengine.cc:545 msgid "disconnect called before engine was started" msgstr "" "richiesta di disconnessione avvenuta prima dell'avvio dell'applicazione" -#: libs/ardour/audioengine.cc:609 +#: libs/ardour/audioengine.cc:603 msgid "get_port_by_name() called before engine was started" msgstr "" "richiesta get_port_by_name() avvenuta prima dell'avvio dell'applicazione" -#: libs/ardour/audioengine.cc:642 +#: libs/ardour/audioengine.cc:636 msgid "get_ports called before engine was started" msgstr "richiesta di get_ports avvenuta prima dell'avvio dell'applicazione" -#: libs/ardour/audioengine.cc:717 +#: libs/ardour/audioengine.cc:711 msgid "get_nth_physical called before engine was started" msgstr "" "richiesta di get_nth_physical avvenuta prima dell'avvio dell'applicazione" -#: libs/ardour/audioengine.cc:745 +#: libs/ardour/audioengine.cc:739 #, fuzzy msgid "get_port_total_latency() called with no JACK client connection" msgstr "" "richiesta di get_port_total_latency() avvenuta prima dell'avvio " "dell'applicazione" -#: libs/ardour/audioengine.cc:751 +#: libs/ardour/audioengine.cc:745 msgid "get_port_total_latency() called before engine was started" msgstr "" "richiesta di get_port_total_latency() avvenuta prima dell'avvio " "dell'applicazione" -#: libs/ardour/audioengine.cc:875 +#: libs/ardour/audioengine.cc:869 msgid "Unable to connect to JACK server" msgstr "" -#: libs/ardour/audioengine.cc:878 +#: libs/ardour/audioengine.cc:872 msgid "Could not connect to JACK server as \"%1\"" msgstr "" -#: libs/ardour/audioengine.cc:883 +#: libs/ardour/audioengine.cc:877 msgid "JACK server started" msgstr "" -#: libs/ardour/audioengine.cc:917 +#: libs/ardour/audioengine.cc:911 msgid "cannot shutdown connection to JACK" msgstr "" -#: libs/ardour/audioengine.cc:942 +#: libs/ardour/audioengine.cc:936 msgid "failed to connect to JACK" msgstr "" -#: libs/ardour/audioengine.cc:958 +#: libs/ardour/audioengine.cc:952 #, fuzzy msgid "could not reregister %1" msgstr "Esportazione: impossibile scrivere dati sul file di output (%1)" -#: libs/ardour/audioengine.cc:1015 +#: libs/ardour/audioengine.cc:1009 msgid "could not reconnect %1 and %2 (err = %3)" msgstr "" diff --git a/libs/ardour/po/ru_RU.po b/libs/ardour/po/ru_RU.po index 922d304e2d..2ca30cba55 100644 --- a/libs/ardour/po/ru_RU.po +++ b/libs/ardour/po/ru_RU.po @@ -6,7 +6,7 @@ msgid "" msgstr "" "Project-Id-Version: libardour 0.716.1\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2006-06-21 15:09-0400\n" +"POT-Creation-Date: 2006-06-27 13:00-0400\n" "PO-Revision-Date: 2004-03-31 00:55+0300\n" "Last-Translator: Igor Blinov pitstop@nm.ru\n" "Language-Team: Russian\n" @@ -171,75 +171,75 @@ msgstr "" msgid "programming error: AudioTrack given state without diskstream!" msgstr "" -#: libs/ardour/audioengine.cc:150 +#: libs/ardour/audioengine.cc:144 msgid "cannot activate JACK client" msgstr "ÎÅ ÕÄÁÌÏÓØ ÁËÔÉ×ÉÒÏ×ÁÔØ ËÌÉÅÎÔÁ JACK ÓÅÒ×ÅÒÁ" -#: libs/ardour/audioengine.cc:401 +#: libs/ardour/audioengine.cc:395 msgid "register audio input port called before engine was started" msgstr "" -#: libs/ardour/audioengine.cc:432 +#: libs/ardour/audioengine.cc:426 msgid "register audio output port called before engine was started" msgstr "" -#: libs/ardour/audioengine.cc:493 +#: libs/ardour/audioengine.cc:487 msgid "connect called before engine was started" msgstr "" -#: libs/ardour/audioengine.cc:509 +#: libs/ardour/audioengine.cc:503 msgid "AudioEngine: cannot connect %1 (%2) to %3 (%4)" msgstr "" -#: libs/ardour/audioengine.cc:522 libs/ardour/audioengine.cc:551 +#: libs/ardour/audioengine.cc:516 libs/ardour/audioengine.cc:545 msgid "disconnect called before engine was started" msgstr "" -#: libs/ardour/audioengine.cc:609 +#: libs/ardour/audioengine.cc:603 msgid "get_port_by_name() called before engine was started" msgstr "" -#: libs/ardour/audioengine.cc:642 +#: libs/ardour/audioengine.cc:636 msgid "get_ports called before engine was started" msgstr "" -#: libs/ardour/audioengine.cc:717 +#: libs/ardour/audioengine.cc:711 msgid "get_nth_physical called before engine was started" msgstr "" -#: libs/ardour/audioengine.cc:745 +#: libs/ardour/audioengine.cc:739 msgid "get_port_total_latency() called with no JACK client connection" msgstr "" -#: libs/ardour/audioengine.cc:751 +#: libs/ardour/audioengine.cc:745 msgid "get_port_total_latency() called before engine was started" msgstr "" -#: libs/ardour/audioengine.cc:875 +#: libs/ardour/audioengine.cc:869 msgid "Unable to connect to JACK server" msgstr "" -#: libs/ardour/audioengine.cc:878 +#: libs/ardour/audioengine.cc:872 msgid "Could not connect to JACK server as \"%1\"" msgstr "" -#: libs/ardour/audioengine.cc:883 +#: libs/ardour/audioengine.cc:877 msgid "JACK server started" msgstr "" -#: libs/ardour/audioengine.cc:917 +#: libs/ardour/audioengine.cc:911 msgid "cannot shutdown connection to JACK" msgstr "" -#: libs/ardour/audioengine.cc:942 +#: libs/ardour/audioengine.cc:936 msgid "failed to connect to JACK" msgstr "" -#: libs/ardour/audioengine.cc:958 +#: libs/ardour/audioengine.cc:952 msgid "could not reregister %1" msgstr "" -#: libs/ardour/audioengine.cc:1015 +#: libs/ardour/audioengine.cc:1009 msgid "could not reconnect %1 and %2 (err = %3)" msgstr "" diff --git a/libs/ardour/session_time.cc b/libs/ardour/session_time.cc index 07b702618e..0e52c926fe 100644 --- a/libs/ardour/session_time.cc +++ b/libs/ardour/session_time.cc @@ -109,7 +109,6 @@ Session::set_smpte_offset_negative (bool neg) SMPTEOffsetChanged (); /* EMIT SIGNAL */ } - void Session::smpte_to_sample( SMPTE::Time& smpte, jack_nframes_t& sample, bool use_offset, bool use_subframes ) const { diff --git a/libs/ardour/sndfilesource.cc b/libs/ardour/sndfilesource.cc index 24a70f636b..443a24e3c2 100644 --- a/libs/ardour/sndfilesource.cc +++ b/libs/ardour/sndfilesource.cc @@ -55,6 +55,7 @@ SndFileSource::SndFileSource (const XMLNode& node) } SndFileSource::SndFileSource (string idstr, Flag flags) + /* files created this way are never writable or removable */ : AudioFileSource (idstr, Flag (flags & ~(Writable|Removable|RemovableIfEmpty|RemoveAtDestroy))) { init (idstr); @@ -63,7 +64,7 @@ SndFileSource::SndFileSource (string idstr, Flag flags) throw failed_constructor (); } - if (_build_peakfiles) { + if (!(_flags & NoPeakFile) && _build_peakfiles) { if (initialize_peakfile (false, _path)) { sf_close (sf); sf = 0; @@ -170,9 +171,10 @@ SndFileSource::SndFileSource (string idstr, SampleFormat sfmt, HeaderFormat hf, delete _broadcast_info; _broadcast_info = 0; } + } - if (_build_peakfiles) { + if (!(_flags & NoPeakFile) && _build_peakfiles) { if (initialize_peakfile (true, _path)) { sf_close (sf); sf = 0; @@ -180,12 +182,6 @@ SndFileSource::SndFileSource (string idstr, SampleFormat sfmt, HeaderFormat hf, } } - /* since SndFileSource's constructed with this constructor can be writable, make sure we update if the header info changes */ - - if (writable()) { - HeaderPositionOffsetChanged.connect (mem_fun (*this, &AudioFileSource::handle_header_position_change)); - } - AudioSourceCreated (this); /* EMIT SIGNAL */ } @@ -235,34 +231,56 @@ SndFileSource::open () _length = _info.frames; + + _broadcast_info = (SF_BROADCAST_INFO*) calloc (1, sizeof (SF_BROADCAST_INFO)); + + /* lookup broadcast info */ + + if (sf_command (sf, SFC_GET_BROADCAST_INFO, _broadcast_info, sizeof (*_broadcast_info)) != SF_TRUE) { + + /* if the file has data but no broadcast info, then clearly, there is no broadcast info */ + + if (_length) { + free (_broadcast_info); + _broadcast_info = 0; + _flags = Flag (_flags & ~Broadcast); + } + + } else { + + /* XXX 64 bit alert: when JACK switches to a 64 bit frame count, this needs to use the high bits + of the time reference. + */ + + set_timeline_position (_broadcast_info->time_reference_low); + } + if (writable()) { sf_command (sf, SFC_SET_UPDATE_HEADER_AUTO, 0, SF_FALSE); + + /* update header if header offset info changes */ + + AudioFileSource::HeaderPositionOffsetChanged.connect (mem_fun (*this, &AudioFileSource::handle_header_position_change)); } return 0; } -void -SndFileSource::close () -{ - if (sf) { - sf_close (sf); - sf = 0; - } -} - SndFileSource::~SndFileSource () { GoingAway (this); /* EMIT SIGNAL */ - close (); + if (sf) { + sf_close (sf); + sf = 0; + } if (interleave_buf) { delete [] interleave_buf; } if (_broadcast_info) { - delete [] _broadcast_info; + free (_broadcast_info); } } @@ -404,27 +422,38 @@ SndFileSource::write_unlocked (Sample *data, jack_nframes_t cnt, char * workbuf) int SndFileSource::update_header (jack_nframes_t when, struct tm& now, time_t tnow) { - /* allow derived classes to override how this is done */ - set_timeline_position (when); if (_flags & Broadcast) { - /* this will flush the header implicitly */ - return setup_broadcast_info (when, now, tnow); - } else { - return flush_header (); - } + if (setup_broadcast_info (when, now, tnow)) { + return -1; + } + } + + return flush_header (); } int SndFileSource::flush_header () { + if (!writable() || (sf == 0)) { + return -1; + } + return (sf_command (sf, SFC_UPDATE_HEADER_NOW, 0, 0) != SF_TRUE); } int SndFileSource::setup_broadcast_info (jack_nframes_t when, struct tm& now, time_t tnow) { + if (!writable()) { + return -1; + } + + if (!(_flags & Broadcast)) { + return 0; + } + /* random code is 9 digits */ int random_code = random() % 999999999; @@ -452,12 +481,10 @@ SndFileSource::setup_broadcast_info (jack_nframes_t when, struct tm& now, time_t set_header_timeline_position (); - /* note that libsndfile flushes the header to disk when resetting the broadcast info */ - if (sf_command (sf, SFC_SET_BROADCAST_INFO, _broadcast_info, sizeof (*_broadcast_info)) != SF_TRUE) { error << string_compose (_("cannot set broadcast info for audio file %1; Dropping broadcast info for this file"), _path) << endmsg; _flags = Flag (_flags & ~Broadcast); - delete _broadcast_info; + free (_broadcast_info); _broadcast_info = 0; return -1; } @@ -470,6 +497,10 @@ SndFileSource::set_header_timeline_position () { uint64_t pos; + if (!(_flags & Broadcast)) { + return; + } + _broadcast_info->time_reference_high = 0; if (header_position_negative) { @@ -491,6 +522,13 @@ SndFileSource::set_header_timeline_position () _broadcast_info->time_reference_high = (pos >> 32); _broadcast_info->time_reference_low = (pos & 0xffffffff); + + if (sf_command (sf, SFC_SET_BROADCAST_INFO, _broadcast_info, sizeof (*_broadcast_info)) != SF_TRUE) { + error << string_compose (_("cannot set broadcast info for audio file %1; Dropping broadcast info for this file"), _path) << endmsg; + _flags = Flag (_flags & ~Broadcast); + free (_broadcast_info); + _broadcast_info = 0; + } } jack_nframes_t diff --git a/libs/cassowary/.cvsignore b/libs/cassowary/.cvsignore deleted file mode 100644 index 532f703477..0000000000 --- a/libs/cassowary/.cvsignore +++ /dev/null @@ -1,3 +0,0 @@ -ClReader-lex.cc -ClReader.cc -ClReader.cc.h diff --git a/libs/cassowary/ANNOUNCE b/libs/cassowary/ANNOUNCE deleted file mode 100644 index e0137fa643..0000000000 --- a/libs/cassowary/ANNOUNCE +++ /dev/null @@ -1,37 +0,0 @@ -Announcing the release of a free (for research use) constraint solver: - -Cassowary Constraint Solver for Smalltalk, C++, and Java -Version 0.60 - -Web Page: http://www.cs.washington.edu/research/constraints/cassowary -Distribution: ftp://ftp.cs.washington.edu:/pub/constraints/code/cassowary/ -Contact: cassowary@cs.washington.edu - -Greg J. Badros and -Alan Borning -University of Washington -Computer Science and Engineering -15-December-1999 - -with Constraint Drawing Applet (CDA) by Michael Noth - -Cassowary is an incremental constraint solving toolkit that efficiently -solves systems of linear equalities and inequalities. Constraints may -be either requirements or preferences. Client code specifies the -constraints to be maintained, and the solver updates the constrained -variables to have values that satisfy the constraints. - -A technical report is included in the distribution that describes the -algorithm, interface, and implementation of the Cassowary solver. -Additionally, the distribution contains toy sample applications written -in Smalltalk, C++, Java, and Python, and a more complex example Java -applet, the "Constraint Drawing Application". - -More information is available on our web page: - -http://www.cs.washington.edu/research/constraints/cassowary - -See README for more details on getting started using these packages. -See NEWS for a history of user-visible changes. -See LICENSE for legalese regarding use of this distribution. - diff --git a/libs/cassowary/AUTHORS b/libs/cassowary/AUTHORS deleted file mode 100644 index 51d8592e6f..0000000000 --- a/libs/cassowary/AUTHORS +++ /dev/null @@ -1,12 +0,0 @@ -Cassowary Constraint Solving Toolkit was -Implemented by: - -Greg J. Badros and -Alan Borning -University of Washington -Computer Science and Engineering -Seattle, WA 98195-2350 - -with Constraint Drawing Applet (CDA) by Michael Noth - -Please send bug reports to cassowary@cs.washington.edu diff --git a/libs/cassowary/COPYING b/libs/cassowary/COPYING deleted file mode 100644 index d60c31a97a..0000000000 --- a/libs/cassowary/COPYING +++ /dev/null @@ -1,340 +0,0 @@ - GNU GENERAL PUBLIC LICENSE - Version 2, June 1991 - - Copyright (C) 1989, 1991 Free Software Foundation, Inc. - 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - Everyone is permitted to copy and distribute verbatim copies - of this license document, but changing it is not allowed. - - Preamble - - The licenses for most software are designed to take away your -freedom to share and change it. By contrast, the GNU General Public -License is intended to guarantee your freedom to share and change free -software--to make sure the software is free for all its users. This -General Public License applies to most of the Free Software -Foundation's software and to any other program whose authors commit to -using it. (Some other Free Software Foundation software is covered by -the GNU Library General Public License instead.) You can apply it to -your programs, too. - - When we speak of free software, we are referring to freedom, not -price. Our General Public Licenses are designed to make sure that you -have the freedom to distribute copies of free software (and charge for -this service if you wish), that you receive source code or can get it -if you want it, that you can change the software or use pieces of it -in new free programs; and that you know you can do these things. - - To protect your rights, we need to make restrictions that forbid -anyone to deny you these rights or to ask you to surrender the rights. -These restrictions translate to certain responsibilities for you if you -distribute copies of the software, or if you modify it. - - For example, if you distribute copies of such a program, whether -gratis or for a fee, you must give the recipients all the rights that -you have. You must make sure that they, too, receive or can get the -source code. And you must show them these terms so they know their -rights. - - We protect your rights with two steps: (1) copyright the software, and -(2) offer you this license which gives you legal permission to copy, -distribute and/or modify the software. - - Also, for each author's protection and ours, we want to make certain -that everyone understands that there is no warranty for this free -software. If the software is modified by someone else and passed on, we -want its recipients to know that what they have is not the original, so -that any problems introduced by others will not reflect on the original -authors' reputations. - - Finally, any free program is threatened constantly by software -patents. We wish to avoid the danger that redistributors of a free -program will individually obtain patent licenses, in effect making the -program proprietary. To prevent this, we have made it clear that any -patent must be licensed for everyone's free use or not licensed at all. - - The precise terms and conditions for copying, distribution and -modification follow. - - GNU GENERAL PUBLIC LICENSE - TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION - - 0. This License applies to any program or other work which contains -a notice placed by the copyright holder saying it may be distributed -under the terms of this General Public License. The "Program", below, -refers to any such program or work, and a "work based on the Program" -means either the Program or any derivative work under copyright law: -that is to say, a work containing the Program or a portion of it, -either verbatim or with modifications and/or translated into another -language. (Hereinafter, translation is included without limitation in -the term "modification".) Each licensee is addressed as "you". - -Activities other than copying, distribution and modification are not -covered by this License; they are outside its scope. The act of -running the Program is not restricted, and the output from the Program -is covered only if its contents constitute a work based on the -Program (independent of having been made by running the Program). -Whether that is true depends on what the Program does. - - 1. You may copy and distribute verbatim copies of the Program's -source code as you receive it, in any medium, provided that you -conspicuously and appropriately publish on each copy an appropriate -copyright notice and disclaimer of warranty; keep intact all the -notices that refer to this License and to the absence of any warranty; -and give any other recipients of the Program a copy of this License -along with the Program. - -You may charge a fee for the physical act of transferring a copy, and -you may at your option offer warranty protection in exchange for a fee. - - 2. You may modify your copy or copies of the Program or any portion -of it, thus forming a work based on the Program, and copy and -distribute such modifications or work under the terms of Section 1 -above, provided that you also meet all of these conditions: - - a) You must cause the modified files to carry prominent notices - stating that you changed the files and the date of any change. - - b) You must cause any work that you distribute or publish, that in - whole or in part contains or is derived from the Program or any - part thereof, to be licensed as a whole at no charge to all third - parties under the terms of this License. - - c) If the modified program normally reads commands interactively - when run, you must cause it, when started running for such - interactive use in the most ordinary way, to print or display an - announcement including an appropriate copyright notice and a - notice that there is no warranty (or else, saying that you provide - a warranty) and that users may redistribute the program under - these conditions, and telling the user how to view a copy of this - License. (Exception: if the Program itself is interactive but - does not normally print such an announcement, your work based on - the Program is not required to print an announcement.) - -These requirements apply to the modified work as a whole. If -identifiable sections of that work are not derived from the Program, -and can be reasonably considered independent and separate works in -themselves, then this License, and its terms, do not apply to those -sections when you distribute them as separate works. But when you -distribute the same sections as part of a whole which is a work based -on the Program, the distribution of the whole must be on the terms of -this License, whose permissions for other licensees extend to the -entire whole, and thus to each and every part regardless of who wrote it. - -Thus, it is not the intent of this section to claim rights or contest -your rights to work written entirely by you; rather, the intent is to -exercise the right to control the distribution of derivative or -collective works based on the Program. - -In addition, mere aggregation of another work not based on the Program -with the Program (or with a work based on the Program) on a volume of -a storage or distribution medium does not bring the other work under -the scope of this License. - - 3. You may copy and distribute the Program (or a work based on it, -under Section 2) in object code or executable form under the terms of -Sections 1 and 2 above provided that you also do one of the following: - - a) Accompany it with the complete corresponding machine-readable - source code, which must be distributed under the terms of Sections - 1 and 2 above on a medium customarily used for software interchange; or, - - b) Accompany it with a written offer, valid for at least three - years, to give any third party, for a charge no more than your - cost of physically performing source distribution, a complete - machine-readable copy of the corresponding source code, to be - distributed under the terms of Sections 1 and 2 above on a medium - customarily used for software interchange; or, - - c) Accompany it with the information you received as to the offer - to distribute corresponding source code. (This alternative is - allowed only for noncommercial distribution and only if you - received the program in object code or executable form with such - an offer, in accord with Subsection b above.) - -The source code for a work means the preferred form of the work for -making modifications to it. For an executable work, complete source -code means all the source code for all modules it contains, plus any -associated interface definition files, plus the scripts used to -control compilation and installation of the executable. However, as a -special exception, the source code distributed need not include -anything that is normally distributed (in either source or binary -form) with the major components (compiler, kernel, and so on) of the -operating system on which the executable runs, unless that component -itself accompanies the executable. - -If distribution of executable or object code is made by offering -access to copy from a designated place, then offering equivalent -access to copy the source code from the same place counts as -distribution of the source code, even though third parties are not -compelled to copy the source along with the object code. - - 4. You may not copy, modify, sublicense, or distribute the Program -except as expressly provided under this License. Any attempt -otherwise to copy, modify, sublicense or distribute the Program is -void, and will automatically terminate your rights under this License. -However, parties who have received copies, or rights, from you under -this License will not have their licenses terminated so long as such -parties remain in full compliance. - - 5. You are not required to accept this License, since you have not -signed it. However, nothing else grants you permission to modify or -distribute the Program or its derivative works. These actions are -prohibited by law if you do not accept this License. Therefore, by -modifying or distributing the Program (or any work based on the -Program), you indicate your acceptance of this License to do so, and -all its terms and conditions for copying, distributing or modifying -the Program or works based on it. - - 6. Each time you redistribute the Program (or any work based on the -Program), the recipient automatically receives a license from the -original licensor to copy, distribute or modify the Program subject to -these terms and conditions. You may not impose any further -restrictions on the recipients' exercise of the rights granted herein. -You are not responsible for enforcing compliance by third parties to -this License. - - 7. If, as a consequence of a court judgment or allegation of patent -infringement or for any other reason (not limited to patent issues), -conditions are imposed on you (whether by court order, agreement or -otherwise) that contradict the conditions of this License, they do not -excuse you from the conditions of this License. If you cannot -distribute so as to satisfy simultaneously your obligations under this -License and any other pertinent obligations, then as a consequence you -may not distribute the Program at all. For example, if a patent -license would not permit royalty-free redistribution of the Program by -all those who receive copies directly or indirectly through you, then -the only way you could satisfy both it and this License would be to -refrain entirely from distribution of the Program. - -If any portion of this section is held invalid or unenforceable under -any particular circumstance, the balance of the section is intended to -apply and the section as a whole is intended to apply in other -circumstances. - -It is not the purpose of this section to induce you to infringe any -patents or other property right claims or to contest validity of any -such claims; this section has the sole purpose of protecting the -integrity of the free software distribution system, which is -implemented by public license practices. Many people have made -generous contributions to the wide range of software distributed -through that system in reliance on consistent application of that -system; it is up to the author/donor to decide if he or she is willing -to distribute software through any other system and a licensee cannot -impose that choice. - -This section is intended to make thoroughly clear what is believed to -be a consequence of the rest of this License. - - 8. If the distribution and/or use of the Program is restricted in -certain countries either by patents or by copyrighted interfaces, the -original copyright holder who places the Program under this License -may add an explicit geographical distribution limitation excluding -those countries, so that distribution is permitted only in or among -countries not thus excluded. In such case, this License incorporates -the limitation as if written in the body of this License. - - 9. The Free Software Foundation may publish revised and/or new versions -of the General Public License from time to time. Such new versions will -be similar in spirit to the present version, but may differ in detail to -address new problems or concerns. - -Each version is given a distinguishing version number. If the Program -specifies a version number of this License which applies to it and "any -later version", you have the option of following the terms and conditions -either of that version or of any later version published by the Free -Software Foundation. If the Program does not specify a version number of -this License, you may choose any version ever published by the Free Software -Foundation. - - 10. If you wish to incorporate parts of the Program into other free -programs whose distribution conditions are different, write to the author -to ask for permission. For software which is copyrighted by the Free -Software Foundation, write to the Free Software Foundation; we sometimes -make exceptions for this. Our decision will be guided by the two goals -of preserving the free status of all derivatives of our free software and -of promoting the sharing and reuse of software generally. - - NO WARRANTY - - 11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY -FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN -OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES -PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED -OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF -MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS -TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE -PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, -REPAIR OR CORRECTION. - - 12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING -WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR -REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, -INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING -OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED -TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY -YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER -PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE -POSSIBILITY OF SUCH DAMAGES. - - END OF TERMS AND CONDITIONS - - How to Apply These Terms to Your New Programs - - If you develop a new program, and you want it to be of the greatest -possible use to the public, the best way to achieve this is to make it -free software which everyone can redistribute and change under these terms. - - To do so, attach the following notices to the program. It is safest -to attach them to the start of each source file to most effectively -convey the exclusion of warranty; and each file should have at least -the "copyright" line and a pointer to where the full notice is found. - - - Copyright (C) - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - - -Also add information on how to contact you by electronic and paper mail. - -If the program is interactive, make it output a short notice like this -when it starts in an interactive mode: - - Gnomovision version 69, Copyright (C) year name of author - Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'. - This is free software, and you are welcome to redistribute it - under certain conditions; type `show c' for details. - -The hypothetical commands `show w' and `show c' should show the appropriate -parts of the General Public License. Of course, the commands you use may -be called something other than `show w' and `show c'; they could even be -mouse-clicks or menu items--whatever suits your program. - -You should also get your employer (if you work as a programmer) or your -school, if any, to sign a "copyright disclaimer" for the program, if -necessary. Here is a sample; alter the names: - - Yoyodyne, Inc., hereby disclaims all copyright interest in the program - `Gnomovision' (which makes passes at compilers) written by James Hacker. - - , 1 April 1989 - Ty Coon, President of Vice - -This General Public License does not permit incorporating your program into -proprietary programs. If your program is a subroutine library, you may -consider it more useful to permit linking proprietary applications with the -library. If this is what you want to do, use the GNU Library General -Public License instead of this License. diff --git a/libs/cassowary/COPYING.LGPL b/libs/cassowary/COPYING.LGPL deleted file mode 100644 index 5f66256a83..0000000000 --- a/libs/cassowary/COPYING.LGPL +++ /dev/null @@ -1,444 +0,0 @@ -GNU LESSER GENERAL PUBLIC LICENSE - -Version 2.1, February 1999 - -Copyright (C) 1991, 1999 Free Software Foundation, Inc. -59 Temple Place, Suite 330, Boston, MA 02111-1307 USA -Everyone is permitted to copy and distribute verbatim copies -of this license document, but changing it is not allowed. - -[This is the first released version of the Lesser GPL. It also counts - as the successor of the GNU Library Public License, version 2, hence - the version number 2.1.] - -Preamble - -The licenses for most software are designed to take away your freedom to -share and change it. By contrast, the GNU General Public Licenses are -intended to guarantee your freedom to share and change free software--to -make sure the software is free for all its users. - -This license, the Lesser General Public License, applies to some -specially designated software packages--typically libraries--of the Free -Software Foundation and other authors who decide to use it. You can use -it too, but we suggest you first think carefully about whether this -license or the ordinary General Public License is the better strategy to -use in any particular case, based on the explanations below. - -When we speak of free software, we are referring to freedom of use, not -price. Our General Public Licenses are designed to make sure that you -have the freedom to distribute copies of free software (and charge for -this service if you wish); that you receive source code or can get it if -you want it; that you can change the software and use pieces of it in -new free programs; and that you are informed that you can do these -things. - -To protect your rights, we need to make restrictions that forbid -distributors to deny you these rights or to ask you to surrender these -rights. These restrictions translate to certain responsibilities for you -if you distribute copies of the library or if you modify it. - -For example, if you distribute copies of the library, whether gratis or -for a fee, you must give the recipients all the rights that we gave -you. You must make sure that they, too, receive or can get the source -code. If you link other code with the library, you must provide complete -object files to the recipients, so that they can relink them with the -library after making changes to the library and recompiling it. And you -must show them these terms so they know their rights. - -We protect your rights with a two-step method: (1) we copyright the -library, and (2) we offer you this license, which gives you legal -permission to copy, distribute and/or modify the library. - -To protect each distributor, we want to make it very clear that there is -no warranty for the free library. Also, if the library is modified by -someone else and passed on, the recipients should know that what they -have is not the original version, so that the original author's -reputation will not be affected by problems that might be introduced by -others. - -Finally, software patents pose a constant threat to the existence of any -free program. We wish to make sure that a company cannot effectively -restrict the users of a free program by obtaining a restrictive license -from a patent holder. Therefore, we insist that any patent license -obtained for a version of the library must be consistent with the full -freedom of use specified in this license. - -Most GNU software, including some libraries, is covered by the ordinary -GNU General Public License. This license, the GNU Lesser General Public -License, applies to certain designated libraries, and is quite different -from the ordinary General Public License. We use this license for -certain libraries in order to permit linking those libraries into -non-free programs. - -When a program is linked with a library, whether statically or using a -shared library, the combination of the two is legally speaking a -combined work, a derivative of the original library. The ordinary -General Public License therefore permits such linking only if the entire -combination fits its criteria of freedom. The Lesser General Public -License permits more lax criteria for linking other code with the -library. - -We call this license the "Lesser" General Public License because it does -Less to protect the user's freedom than the ordinary General Public -License. It also provides other free software developers Less of an -advantage over competing non-free programs. These disadvantages are the -reason we use the ordinary General Public License for many -libraries. However, the Lesser license provides advantages in certain -special circumstances. - -For example, on rare occasions, there may be a special need to encourage -the widest possible use of a certain library, so that it becomes a -de-facto standard. To achieve this, non-free programs must be allowed to -use the library. A more frequent case is that a free library does the -same job as widely used non-free libraries. In this case, there is -little to gain by limiting the free library to free software only, so we -use the Lesser General Public License. - -In other cases, permission to use a particular library in non-free -programs enables a greater number of people to use a large body of free -software. For example, permission to use the GNU C Library in non-free -programs enables many more people to use the whole GNU operating system, -as well as its variant, the GNU/Linux operating system. - -Although the Lesser General Public License is Less protective of the -users' freedom, it does ensure that the user of a program that is linked -with the Library has the freedom and the wherewithal to run that program -using a modified version of the Library. - -The precise terms and conditions for copying, distribution and -modification follow. Pay close attention to the difference between a -"work based on the library" and a "work that uses the library". The -former contains code derived from the library, whereas the latter must -be combined with the library in order to run. - -TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION - -0. This License Agreement applies to any software library or other -program which contains a notice placed by the copyright holder or other -authorized party saying it may be distributed under the terms of this -Lesser General Public License (also called "this License"). Each -licensee is addressed as "you". - -A "library" means a collection of software functions and/or data -prepared so as to be conveniently linked with application programs -(which use some of those functions and data) to form executables. - -The "Library", below, refers to any such software library or work which -has been distributed under these terms. A "work based on the Library" -means either the Library or any derivative work under copyright law: -that is to say, a work containing the Library or a portion of it, either -verbatim or with modifications and/or translated straightforwardly into -another language. (Hereinafter, translation is included without -limitation in the term "modification".) - -"Source code" for a work means the preferred form of the work for making -modifications to it. For a library, complete source code means all the -source code for all modules it contains, plus any associated interface -definition files, plus the scripts used to control compilation and -installation of the library. - -Activities other than copying, distribution and modification are not -covered by this License; they are outside its scope. The act of running -a program using the Library is not restricted, and output from such a -program is covered only if its contents constitute a work based on the -Library (independent of the use of the Library in a tool for writing -it). Whether that is true depends on what the Library does and what the -program that uses the Library does. - -1. You may copy and distribute verbatim copies of the Library's complete -source code as you receive it, in any medium, provided that you -conspicuously and appropriately publish on each copy an appropriate -copyright notice and disclaimer of warranty; keep intact all the notices -that refer to this License and to the absence of any warranty; and -distribute a copy of this License along with the Library. - -You may charge a fee for the physical act of transferring a copy, and -you may at your option offer warranty protection in exchange for a fee. - -2. You may modify your copy or copies of the Library or any portion of -it, thus forming a work based on the Library, and copy and distribute -such modifications or work under the terms of Section 1 above, provided -that you also meet all of these conditions: - - a) The modified work must itself be a software library. b) You - must cause the files modified to carry prominent notices stating - that you changed the files and the date of any change. c) You - must cause the whole of the work to be licensed at no charge to - all third parties under the terms of this License. d) If a - facility in the modified Library refers to a function or a table - of data to be supplied by an application program that uses the - facility, other than as an argument passed when the facility is - invoked, then you must make a good faith effort to ensure that, - in the event an application does not supply such function or - table, the facility still operates, and performs whatever part of - its purpose remains meaningful. - - (For example, a function in a library to compute square roots has - a purpose that is entirely well-defined independent of the - application. Therefore, Subsection 2d requires that any - application-supplied function or table used by this function must - be optional: if the application does not supply it, the square - root function must still compute square roots.) - - These requirements apply to the modified work as a whole. If - identifiable sections of that work are not derived from the - Library, and can be reasonably considered independent and - separate works in themselves, then this License, and its terms, - do not apply to those sections when you distribute them as - separate works. But when you distribute the same sections as part - of a whole which is a work based on the Library, the distribution - of the whole must be on the terms of this License, whose - permissions for other licensees extend to the entire whole, and - thus to each and every part regardless of who wrote it. - - Thus, it is not the intent of this section to claim rights or - contest your rights to work written entirely by you; rather, the - intent is to exercise the right to control the distribution of - derivative or collective works based on the Library. - - In addition, mere aggregation of another work not based on the - Library with the Library (or with a work based on the Library) on - a volume of a storage or distribution medium does not bring the - other work under the scope of this License. - -3. You may opt to apply the terms of the ordinary GNU General Public -License instead of this License to a given copy of the Library. To do -this, you must alter all the notices that refer to this License, so that -they refer to the ordinary GNU General Public License, version 2, -instead of to this License. (If a newer version than version 2 of the -ordinary GNU General Public License has appeared, then you can specify -that version instead if you wish.) Do not make any other change in these -notices. - -Once this change is made in a given copy, it is irreversible for that -copy, so the ordinary GNU General Public License applies to all -subsequent copies and derivative works made from that copy. - -This option is useful when you wish to copy part of the code of the -Library into a program that is not a library. - -4. You may copy and distribute the Library (or a portion or derivative -of it, under Section 2) in object code or executable form under the -terms of Sections 1 and 2 above provided that you accompany it with the -complete corresponding machine-readable source code, which must be -distributed under the terms of Sections 1 and 2 above on a medium -customarily used for software interchange. - -If distribution of object code is made by offering access to copy from a -designated place, then offering equivalent access to copy the source -code from the same place satisfies the requirement to distribute the -source code, even though third parties are not compelled to copy the -source along with the object code. - -5. A program that contains no derivative of any portion of the Library, -but is designed to work with the Library by being compiled or linked -with it, is called a "work that uses the Library". Such a work, in -isolation, is not a derivative work of the Library, and therefore falls -outside the scope of this License. - -However, linking a "work that uses the Library" with the Library creates -an executable that is a derivative of the Library (because it contains -portions of the Library), rather than a "work that uses the -library". The executable is therefore covered by this License. Section 6 -states terms for distribution of such executables. - -When a "work that uses the Library" uses material from a header file -that is part of the Library, the object code for the work may be a -derivative work of the Library even though the source code is -not. Whether this is true is especially significant if the work can be -linked without the Library, or if the work is itself a library. The -threshold for this to be true is not precisely defined by law. - -If such an object file uses only numerical parameters, data structure -layouts and accessors, and small macros and small inline functions (ten -lines or less in length), then the use of the object file is -unrestricted, regardless of whether it is legally a derivative -work. (Executables containing this object code plus portions of the -Library will still fall under Section 6.) - -Otherwise, if the work is a derivative of the Library, you may -distribute the object code for the work under the terms of Section -6. Any executables containing that work also fall under Section 6, -whether or not they are linked directly with the Library itself. - -6. As an exception to the Sections above, you may also combine or link a -"work that uses the Library" with the Library to produce a work -containing portions of the Library, and distribute that work under terms -of your choice, provided that the terms permit modification of the work -for the customer's own use and reverse engineering for debugging such -modifications. - -You must give prominent notice with each copy of the work that the -Library is used in it and that the Library and its use are covered by -this License. You must supply a copy of this License. If the work during -execution displays copyright notices, you must include the copyright -notice for the Library among them, as well as a reference directing the -user to the copy of this License. Also, you must do one of these things: - - a) Accompany the work with the complete corresponding - machine-readable source code for the Library including whatever - changes were used in the work (which must be distributed under - Sections 1 and 2 above); and, if the work is an executable linked - with the Library, with the complete machine-readable "work that - uses the Library", as object code and/or source code, so that the - user can modify the Library and then relink to produce a modified - executable containing the modified Library. (It is understood - that the user who changes the contents of definitions files in - the Library will not necessarily be able to recompile the - application to use the modified definitions.) b) Use a suitable - shared library mechanism for linking with the Library. A suitable - mechanism is one that (1) uses at run time a copy of the library - already present on the user's computer system, rather than - copying library functions into the executable, and (2) will - operate properly with a modified version of the library, if the - user installs one, as long as the modified version is - interface-compatible with the version that the work was made - with. c) Accompany the work with a written offer, valid for at - least three years, to give the same user the materials specified - in Subsection 6a, above, for a charge no more than the cost of - performing this distribution. d) If distribution of the work is - made by offering access to copy from a designated place, offer - equivalent access to copy the above specified materials from the - same place. e) Verify that the user has already received a copy - of these materials or that you have already sent this user a - copy. - -For an executable, the required form of the "work that uses the Library" -must include any data and utility programs needed for reproducing the -executable from it. However, as a special exception, the materials to be -distributed need not include anything that is normally distributed (in -either source or binary form) with the major components (compiler, -kernel, and so on) of the operating system on which the executable runs, -unless that component itself accompanies the executable. - -It may happen that this requirement contradicts the license restrictions -of other proprietary libraries that do not normally accompany the -operating system. Such a contradiction means you cannot use both them -and the Library together in an executable that you distribute. - -7. You may place library facilities that are a work based on the Library -side-by-side in a single library together with other library facilities -not covered by this License, and distribute such a combined library, -provided that the separate distribution of the work based on the Library -and of the other library facilities is otherwise permitted, and provided -that you do these two things: - - a) Accompany the combined library with a copy of the same work - based on the Library, uncombined with any other library - facilities. This must be distributed under the terms of the - Sections above. b) Give prominent notice with the combined - library of the fact that part of it is a work based on the - Library, and explaining where to find the accompanying uncombined - form of the same work. - -8. You may not copy, modify, sublicense, link with, or distribute the -Library except as expressly provided under this License. Any attempt -otherwise to copy, modify, sublicense, link with, or distribute the -Library is void, and will automatically terminate your rights under this -License. However, parties who have received copies, or rights, from you -under this License will not have their licenses terminated so long as -such parties remain in full compliance. - -9. You are not required to accept this License, since you have not -signed it. However, nothing else grants you permission to modify or -distribute the Library or its derivative works. These actions are -prohibited by law if you do not accept this License. Therefore, by -modifying or distributing the Library (or any work based on the -Library), you indicate your acceptance of this License to do so, and all -its terms and conditions for copying, distributing or modifying the -Library or works based on it. - -10. Each time you redistribute the Library (or any work based on the -Library), the recipient automatically receives a license from the -original licensor to copy, distribute, link with or modify the Library -subject to these terms and conditions. You may not impose any further -restrictions on the recipients' exercise of the rights granted -herein. You are not responsible for enforcing compliance by third -parties with this License. - -11. If, as a consequence of a court judgment or allegation of patent -infringement or for any other reason (not limited to patent issues), -conditions are imposed on you (whether by court order, agreement or -otherwise) that contradict the conditions of this License, they do not -excuse you from the conditions of this License. If you cannot distribute -so as to satisfy simultaneously your obligations under this License and -any other pertinent obligations, then as a consequence you may not -distribute the Library at all. For example, if a patent license would -not permit royalty-free redistribution of the Library by all those who -receive copies directly or indirectly through you, then the only way you -could satisfy both it and this License would be to refrain entirely from -distribution of the Library. - -If any portion of this section is held invalid or unenforceable under -any particular circumstance, the balance of the section is intended to -apply, and the section as a whole is intended to apply in other -circumstances. - -It is not the purpose of this section to induce you to infringe any -patents or other property right claims or to contest validity of any -such claims; this section has the sole purpose of protecting the -integrity of the free software distribution system which is implemented -by public license practices. Many people have made generous -contributions to the wide range of software distributed through that -system in reliance on consistent application of that system; it is up to -the author/donor to decide if he or she is willing to distribute -software through any other system and a licensee cannot impose that -choice. - -This section is intended to make thoroughly clear what is believed to be -a consequence of the rest of this License. - -12. If the distribution and/or use of the Library is restricted in -certain countries either by patents or by copyrighted interfaces, the -original copyright holder who places the Library under this License may -add an explicit geographical distribution limitation excluding those -countries, so that distribution is permitted only in or among countries -not thus excluded. In such case, this License incorporates the -limitation as if written in the body of this License. - -13. The Free Software Foundation may publish revised and/or new versions -of the Lesser General Public License from time to time. Such new -versions will be similar in spirit to the present version, but may -differ in detail to address new problems or concerns. - -Each version is given a distinguishing version number. If the Library -specifies a version number of this License which applies to it and "any -later version", you have the option of following the terms and -conditions either of that version or of any later version published by -the Free Software Foundation. If the Library does not specify a license -version number, you may choose any version ever published by the Free -Software Foundation. - -14. If you wish to incorporate parts of the Library into other free -programs whose distribution conditions are incompatible with these, -write to the author to ask for permission. For software which is -copyrighted by the Free Software Foundation, write to the Free Software -Foundation; we sometimes make exceptions for this. Our decision will be -guided by the two goals of preserving the free status of all derivatives -of our free software and of promoting the sharing and reuse of software -generally. - -NO WARRANTY - -15. BECAUSE THE LIBRARY IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY -FOR THE LIBRARY, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN -OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES -PROVIDE THE LIBRARY "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER -EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED -WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE -ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE LIBRARY IS WITH -YOU. SHOULD THE LIBRARY PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL -NECESSARY SERVICING, REPAIR OR CORRECTION. - -16. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN -WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY -AND/OR REDISTRIBUTE THE LIBRARY AS PERMITTED ABOVE, BE LIABLE TO YOU FOR -DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL -DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE LIBRARY -(INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING RENDERED -INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A FAILURE OF -THE LIBRARY TO OPERATE WITH ANY OTHER SOFTWARE), EVEN IF SUCH HOLDER OR -OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. - -END OF TERMS AND CONDITIONS diff --git a/libs/cassowary/ChangeLog b/libs/cassowary/ChangeLog deleted file mode 100644 index 11b4762616..0000000000 --- a/libs/cassowary/ChangeLog +++ /dev/null @@ -1,2005 +0,0 @@ -Tue May 17 16:24:00 2005 Taybin Rutkin - * Moved cassowary from autotools to scons. - -Fri Mar 18 15:41:00 2005 Taybin Rutkin - * Removed ClSet.h, ClMap.h. - * ClReader.l includes ClReader.cc.h instead of ClReader.hh. The - difference between yacc and bison. - * Various changes to fix compliation. - -Wed Jan 29 21:36:15 2003 Taybin Rutkin - * Updated to work with g++ 3.x compilers. - * More direct use of STL. - * Removed C wrappers - -Sun Mar 12 13:40:44 2000 Greg J. Badros - - * guile/cassowary_scm.cc: Give docstrings as arguments - - * guile/cl-snarf.h: Added docstring as an argument to CL_PROC to - be like the revised Scwm documentation extraction system. - -Sat Feb 12 20:34:55 2000 Greg J. Badros - - * Makefile.am: Added GTL.h.patch to EXTRA_DIST - -Sat Feb 12 20:31:47 2000 Greg J. Badros - - * c++/ClSimplexSolver.cc, c++/ClSimplexSolver.h: Drop - ExternalResetStayConstants, make ResetStayConstants() public. - Test _fResetStayConstantsAutomatically before doing so in - Resolve(). Use _fAutosolve instead of _fOptimizeAutomatically. - Drop DisplayObjective (wasn't defined anyway). Drop field - _fOptimizeAutomatically (use _fAutosolve from parent, instead). - - * guile/cassowary_scm.hpp, guile/cassowary_scm.cc: Drop extra - include of guile/gh.h - - * guile/cassowary_scm.cc: Added `cl-set-auto-solve!', - `cl-set-auto-reset-stay-constants!' - -Sat Jan 29 17:45:32 2000 Greg J. Badros - - * configure.in (CASSOWARY_VERSION): Bump to 0.55. - -Sat Jan 29 17:43:05 2000 Greg J. Badros - - * c++/ClSimplexSolver.cc (Resolve): Do not comment out - "ResetStayConstants()" as Beurivé had done. This was resulting in - quirky behaviour whereby the windows were "rubber-banding" back to - where they were at the start of an interaction (e.g., if I push a - window out of the way to the left with another window, as I move - the pushing window back to the right, the other window comes back - to the right with the pushing window). Maybe that's desirable - behaviour in some instances, but it's not the behaviour we - document and sure feels weird to me. - -Sat Jan 29 17:38:43 2000 Greg J. Badros - - * java/sym.java, java/parser.java, java/Yylex.java: Added -- these - are created by JavaCUP which I don't want to be necessary for - building. - -Mon Jan 24 09:34:20 2000 Greg J. Badros - - * c++/ClSymbolicWeight.h: Set SymbolicWeight multiplier to - 1000000, not 10000 (A.Beurivé) - - * c++/ClSimplexSolver.h, c++/ClSimplexSolver.cc: Added - ChangeStrength, ChangeStrengthAndWeight, ChangeWeight, - DisplayObjective, ExternalResetStayConstants fns. - (RemoveConstraintInternal) Avoid picking the objective row when - removing a constraint. (Optimize) Pick any negative row to avoid - unending pivots [I think this is a work-around to avoid having to - implement Bland's anti-cycling rule... maybe I should just do - that, though]. (A.Beurivé) - -Thu Dec 16 11:12:34 1999 Greg J. Badros - - * configure.in: Version bumped to 0.54a - -Thu Dec 16 11:10:42 1999 Greg J. Badros - - * java/Makefile.am: Force prefix ordering in SUBDIRS so that "." - dir gets built before the demos subdirectory. - - * smalltalk/Makefile.am: Fix .dat file -- thanks Alan! - -Wed Dec 15 19:31:48 1999 Greg J. Badros - - * java/README: More notes re: security problems w/ Java 2. - - * java/cda/Makefile.am: Added run target to ease running it. - - * Makefile.am (EXTRA_DIST): Added c++/{config.h.in,stamp-h.in} - - * java/cda/Makefile.am (EXTRA_DIST): Clean up install of .gif - files. - - * java/Makefile.am (EXTRA_DIST): Added ClReader.{cup,lex} - - * c++/Makefile.am: Do not make symlink to cassowary; let - configure.in do that. - -Wed Dec 15 18:13:14 1999 Greg J. Badros - - * java/Makefile.am: Put SUBDIRS demo cda back in since they - compile now. - - * scripts/recreate-symlinks: Update with links to ../../EDU from - demo directories for Java code. Use ln -sf, not just ln -s, to avoid - warnings. - - * Makefile.am (EXTRA_DIST): Include scripts/recreate-symlinks - - * configure.in: Run recreate-symlinks script. - -Wed Dec 15 18:07:27 1999 Greg J. Badros - - * java/cda/Makefile.am: Put Constraint/*, Main/* files into the - distribution and build with them. - - * java/demos/*.java: Move everything into the - EDU.Washington.grad.gjb.cassowary_demos package. - - * java/cda/classes/run.html, java/demos/quaddemo.htm: Fix nl - convention, name class explicitly w/ package in front, w/o - trailing .class. - - * java/cda/**: Move everything into the - EDU.Washington.grad.noth.cda package. - -Wed Dec 15 17:21:08 1999 Greg J. Badros - - * java/Makefile.am: Build java parser. - - * java/ClParseTest.java: Added. - - * GTL.h.patch: Added -- need by gcc-2.95 when compiling GTL-0.3.1 - - * java/README: Mention java parser. - - * java/ClReader.lex, java/ClReader.cup: Cleanup, guard debug messages. - -Tue Dec 14 11:15:01 1999 Greg J. Badros - - * configure.in: Fix -fpermissive test to not check "cc" as well as - $CC. Eliminate the --enable-permissive flag since it is no longer - necessary. - -Mon Dec 13 15:56:19 1999 Greg J. Badros - - * java/Yylex.java: Added, from Will Portnoy. - - * java/ClReader.cup, java/ClReader.lex: Latest version from Will, - cleaned up line breaks, set a tab-width for Emacs. - -Mon Dec 13 15:55:59 1999 Greg J. Badros - - * c++/Makefile.am: Remove ClReader.cc -- why did I add this - before? - -Fri Dec 10 13:29:00 1999 Greg J. Badros - - * java/ClSimplexSolver.java (addLowerBound, addUpperBound): Fix - these two functions to call addConstraint before returning. - Thanks Stephen Allain for catching this! Updated exception specs - for those methods and for addBounds. - -Tue Dec 7 08:42:34 1999 Greg J. Badros - - * smalltalk/A991206.dat: New image from Alan. Include correct - version of code for "ClSimplexSolver removeConstraint:" to fix bug - when deleting constraints with weights other than 1. Also - disallow invalid comparisons between symbolic weights and floats. - Replace expressions "x clApprox: 0.0" with "x clApproxZero", which - works correctly for both symbolic weights and floats. - - * smalltalk/*.st: Added from Alan. - -Mon Nov 29 16:23:06 1999 - - * configure.in: Bump to version 0.54, added -lGTL to GTL_LIB even - when no --with-gtl option is given. No longer create README from - README.in. Added --enable-static-library option, off by default. - - * c++/Makefile.am (sources): Added ClReader.cc - - * cassowary.spec.in, cassowary-both.spec.in: No longer need the - --enable-guile-build option; it's the default now. - -Mon Nov 29 10:52:49 1999 Greg J. Badros - - * c++/Makefile.am: Added use of AM_CONDITIONAL - CL_BUILD_STATIC_LIBRARY; only buile libcassowary.a if that option - was selected. - - * guile/Makefile.am (libconstraints_la_LIBADD): Added @GTL_LIB@ to - make the guile library work with the FD-enabled version of the library. - -Sat Nov 27 16:11:10 1999 Greg J. Badros - - * configure.in: Invert sense of --enable-guile-build and call it - --disable-guile-build; build guile wrapper automatically if - guile-config works. - -Sat Nov 27 15:20:03 1999 Greg J. Badros - - * configure.in: Use an AM_CONDITIONAL for CL_BUILD_FD_SOLVER, not - an AC_DEFINE. Also, remove duplicate AC_SUBST of GTL_LIB, and fix - AM_CONDITIONAL of CL_BUILD_TESTS. - -Sat Nov 27 15:19:20 1999 Greg J. Badros - - * c++/Makefile.am: Try separating out FD stuff better, and use - CL_BUILD_FD_SOLVER AM_CONDITIONAL to control dependence on that - code. - - * c++/config.h.in: Drop CL_BUILD_FD_SOLVER; it's now an - AM_CONDITIONAL instead of a define. - -Wed Nov 24 15:40:27 1999 Greg J. Badros - - * c++/ClSimplexSolver.cc: Fix typo in a throw message. - - * c++/ClLinearInequality.h: Throw an editmisuse when a - ClLinearInequality is created w/o an inequality operator. - -Tue Nov 23 16:54:05 1999 Greg J. Badros - - * configure.in: Use guile's pkglibdir, not pkgdatadir, for - choosing cassoguiledir. - -Tue Nov 16 17:35:54 1999 Greg J. Badros - - * java/ClReader.lex, java/ClReader.cup: Added -- code by Will - Portnoy for adding a parser to the Java implementation. Untested, - and an early version that he emailed me. - -Tue Nov 16 17:34:00 1999 Greg J. Badros - - * java/ClTestColumns.java, java/ClTests.java: Put in the cassowary - package, instead of importing cassowary.*; jikes needed this - (discovered during testing of java-ml work). - -Sat Nov 13 11:43:48 1999 Greg J. Badros - - * java/Timer.java (Timer): Remove return type from Timer() - constructor (jikes caught the bug when I used this as a test case - for my java-ml work). - -Sun Oct 24 13:17:14 1999 Greg J. Badros - - * configure.in: Updated version to 0.53, generate - smalltalk/Makefile from Makefile.am. - - * NEWS: Updated for 0.53 release. - - * Makefile.am: Added smalltalk directory to SUBDIRS. - -Sat Oct 23 14:34:27 1999 Greg J. Badros - - * COPYING.GPL: Added - - * LICENSE: Added Scwm exception - - -Sat Oct 23 14:33:48 1999 Greg J. Badros - - * c++/Makefile.am: Make cassowary/ directory symlink as needed. - -Sun Oct 3 16:50:43 1999 Greg J. Badros - - * c++/ClSimplexSolver.cc: Use clvNil some places instead of NULL. - This is important for newer, pickier gcc-2.95.x. Thanks Alexandre - Duret-Lutz for the patch! - -Thu Sep 30 08:17:16 1999 Greg J. Badros - - * c++/ClFDSolver.cc: Added missing #include -- Thanks - Harry Hochheiser for bug report. - -Sun Sep 26 13:43:12 1999 Greg J. Badros - - * c++/Makefile.am (libcassowary_la_LDFLAGS): Added -version-info - flag to make libcassowary.so.0.0.1, instead of .0.0.0 - -Sun Sep 26 13:15:32 1999 Greg J. Badros - - * README, ANNOUNCE: Removed - - * README.in, ANNOUNCE.in: Added - - * configure.in: Create README, ANNOUNCE, bump to 0.52post - -Sat Sep 25 16:02:22 1999 Greg J. Badros - - * cassowary.spec.in, configure.in: Update to version 0.52. - -Fri Sep 24 18:51:42 1999 Greg J. Badros - - * configure.in: Remove first of redundant checks for HAVE_SCM_MAKE_SMOB_TYPE_MFPE. - -Mon Sep 20 13:36:45 1999 Greg J. Badros - - * guile/cassowary_scm.cc: Fix `cl-int-value' to use gh_int2scm - instead of gh_double2scm - -Sun Sep 19 14:45:59 1999 Greg J. Badros - - * c++/ClSimplexSolver.h, c++/ClSimplexSolver.cc: Replace - _editVarMap with _editInfoList, a list. Make ClEditInfo class - contain the variable since its no longer stored as values in a - hash where the key is the variable. Drop the index from - ClEditInfo. Rename ClVarToEditInfoMap to ClEditInfoList. - -Sun Sep 19 14:44:00 1999 Greg J. Badros - - * c++/ClTests.cc (multiedit2): Added this new test to check nested - edits that share an existing variable better. This tests the fix - for the ScwmButtons auto-orientation seg-fault bug in Scwm. - - * c++/ClBug0.cc: Added comment re: new bug fix. - -Sat Sep 18 22:31:54 1999 Greg J. Badros - - * configure.in: Added GUILE_LIBS setting. - - * cassowary.spec.in: Use fake_root_for_install to get the - cassowary guile library in proper place. - - * autogen.sh: Only create symlink if not already created. - - * acconfig.h, c++/config.h.in: Added HAVE_SCM_MAKE_SMOB_TYPE_MFPE - - * README: Added note re: enable-permissive - - * guile/cassowary_scm.cc: Use new-style (guile-1.3.2 or better) - SMOBs conditioning on HAVE_SCM_MAKE_SMOB_TYPE_MFPE. - -Wed Sep 8 20:03:25 1999 Greg J. Badros - - * cassowary.spec.in: Bump to release 8 - - * cassowary-nofd.spec2.in: Bump to release 2. - -Wed Sep 8 19:43:53 1999 Greg J. Badros - - * c++/Makefile.am: Drop building of config-inline.h -- let - configure handle that-- this was causing a double-build - (!!!ugh!!!) of Cassowary when building from RPMs, e.g. - - * GTL.spec.in: Use install-strip target. - -Tue Sep 7 23:34:49 1999 Greg J. Badros - - * configure.in, Makefile.am: use cassowary-nofd.spec2.in - - * cassowary-nofd.spec2.in: Renamed from cassowary-nofd.spec.in, - since having two *.spec files in the top level upsets rpm (it cats - them together and then gets confused by the double .spec file). - - * cassowary-both.spec.in: Added-- rpm doesn't support two %build - tags (one for a subpackage), but if it did, this is what the - corresponding .spec file might look like. - -Tue Sep 7 23:02:26 1999 Greg J. Badros - - * Makefile.am: Added cassowary-nofd.spec to EXTRA_DIST, - bin_SCRIPTS = cassowary-config. Added dist-nofd target, and - supporting targets. - - * cassowary.spec.in: Bump to 7, provide virtual package, install - %{prefix}/bin/* (for cassowary-config script). - - * configure.in: Added CASSOWARY_VERSION variable, create - cassowary-config, cassowary-nofd.spec - - * cassowary-config.in, cassowary-nofd.spec.in: Added - -Mon Sep 6 21:40:58 1999 - - * cassowary.spec.in: Use install-strip target to remove debug - symbols and save disk space. Remove %{prefix}/doc/* from the - %files list as they are in the %doc listing already. - -Mon Sep 6 12:25:14 1999 Greg J. Badros - - * cassowary.spec.in: Use --host=alpha-linux on that platform - (using an %ifarch). Bump to release 6. - - * GTL.spec.in: Fix the ./configure line for alpha platform (was - missing "--" before the "prefix" option). Bump to release 2. - - * c++/ClSymbolicWeight.h, c++/ClSymbolicWeight.cc: Use int, not - unsigned, to remove ambiguity in ClSymbolicWeight constructor. - -Sat Sep 4 15:17:13 1999 Greg J. Badros - - * acconfig.h: Added NO_CC_PERMISSIVE flag. - - * autogen.sh: Added #!/bin/sh - to top. - - * configure.in: Test for g++/gcc -fpermissive flag. Hopefully - this will let it get used only where it is accepted. Some better - guile tests, too. - - * cassowary.spec.in: Use --enable-permissive flag, bump from - release 3 to 5. - -Sat Sep 4 14:44:14 1999 Greg J. Badros - - * c++/Makefile.am, guile/Makefile.am: Added CPPEXTRAFLAGS to - AM_CPPFLAGS. - - * guile/Makefile.am: Guard lib_LIBRARIES with HAVE_GUILE test so - that guile stuff is only built when GUILE is desired and we have - the libraries installed. - -Tue Aug 31 22:16:04 1999 Greg J. Badros - - * java/demos/Makefile.am, java/cda/Makefile.am, java/Makefile.am - (install-javaJAVA): Do not try to install .class files if no - HAVE_JAVA - -Tue Aug 31 21:30:24 1999 Greg J. Badros - - * cassowary.spec.in: Do not use --disable-java-build, since that - still invokes the rule which is not what I want. - - * java/demos/Makefile.am, java/cda/Makefile.am: Added bogus - classjava.stamp rule when no HAVE_JAVA to work around getting an - error when trying to run javac with no source files. - - * configure.in: Fix some HAVE_JAVA bugs. Still not perfect, but better. - -Tue Aug 31 17:07:31 1999 Greg J. Badros - - * java/demos/Makefile.am, java/cda/Makefile.am, java/Makefile.am: - Added EXTRA_DIST. - -Tue Aug 31 16:27:41 1999 Greg J. Badros - - * configure.in (HAVA_JAVA): AC_OUTPUT the java/*/Makefiles. - - * cassowary.spec.in: Use --disable-java-build ./configure option. - Bump to release 3. - - * Makefile.am: Do not conditionally do directories-- that is - really broken with automake/rpm building. - -Tue Aug 31 16:20:45 1999 Greg J. Badros - - * java/demos/Makefile.am, java/cda/Makefile.am, java/Makefile.am - (java_JAVA): Guard with if HAVE_JAVE. - -Mon Aug 30 12:03:26 1999 Greg J. Badros - - * cassowary.spec.in: Bump to release 2 - - * configure.in: Drop the java/* wrappers/* from AC_OUTPUT macro-- - this breaks java builds but make the Cassowary RPM build more - cleanly. I'm going to start making a separate cassowary-java - distribution unless I can figure out how to make automake and Java - co-exist more happily. - -Mon Aug 30 12:00:39 1999 Greg J. Badros - - * c++/ClAbstractVariable.h: #include "cl_auto_ptr.h" and use - cl_auto_ptr, not auto_ptr. - -Mon Aug 30 10:06:50 1999 Greg J. Badros - - * c++/cl_auto_ptr.h: Change the conditional inclusion sandwich to - CL_AUTO_PTR_H. Added "#define cl_auto_ptr auto_ptr" for MSVC. - -Thu Aug 26 22:42:50 1999 Greg J. Badros - - * cassowary.spec.in: Require guile 1.3.2, to be safe. Require GTL - >= 0.3.1, not gtl >= 0.3.1 (note capitalization) - -Thu Aug 26 14:12:42 1999 Greg J. Badros - - * c++/ClFDSolver.h, c++/ClCTest.c, c++/ClC.h, c++/ClC.cc, - c++/Cassowary.h, c++/ClConstraint.h: Use LONG_MIN, not MINLONG and - #include not since the latter is deprecated - (and does not work in VC++). - - * THANKS: Thank Pengling He for his VC++ bug report re: values.h - -Thu Aug 26 14:08:46 1999 Greg J. Badros - - * configure.in (GUILE_PKGDATA_DIR): Set cassoguiledir variable, - and use ${prefix} prefix of GUILE_PKGDATA_DIR to be sure that rpm - building succeeds (was failing because it was trying to write to - an absolute location that guile told it to use, instead of using - the prefix of $RPM_BUILD_ROOT). - - * c++/Makefile.am: Fix lex/yacc building dependencies. - - * guile/Makefile.am (cassoguile_LTLIBRARIES): Do not set - cassoguiledir here-- do it in configure.in instead. - -Thu Aug 26 11:02:36 1999 Greg J. Badros - - * guile/Makefile.am (EXTRA_DIST), docs/Makefile.am: Added docs to - EXTRA_DIST. - - * c++/Makefile.am: Added ClReader.l, ClReader.y to EXTRA_DIST, - remove ClReader.cc from sources. Added timer.h to - pkginclude_HEADERS. - - * Makefile.am: Update EXTRA_DIST - -Thu Aug 26 08:45:08 1999 Greg J. Badros - - * configure.in: Write cassowary.spec, GTL.spec. Bump version to - 0.51. - - * autogen.sh: Run configure, not config.status - - * VERSION, README, NEWS, ANNOUNCE: Bump to 0.51, add date, notes. - - * Makefile.am: Drop Java, Python to make easier to package. Added - EXTRA_DIST to include some doc files and the cassowary.spec file. - -Wed Aug 25 22:54:18 1999 Greg J. Badros - - * c++/Makefile.am (pkginclude_HEADERS): cl_auto_ptr.h now, not auto_ptr.h - -Mon Aug 23 21:26:31 1999 Greg J. Badros - - * ltmain.sh, ltconfig, libtool, configure: Removed -- these are - autogenerated by autogen.sh - -Mon Aug 23 21:23:53 1999 Greg J. Badros - - * c++/ClSimplexSolver.cc: Use cl_auto_ptr, not auto_ptr. - - * c++/ClAbstractVariable.h: #include , not "auto_ptr.h" - - * c++/cl_auto_ptr.h: Added -- renamed from auto_ptr.h since that - was causing some difficulties due to the standard C++ auto_ptr template. - -Mon Jul 26 10:19:35 1999 Greg Badros - - * c++/Makefile.am (libcassowary_la_SOURCES): Remove redundant - listing of ClFD* files from this target. - -Mon Jul 26 09:41:09 1999 Greg Badros - - * c++/Cl.h: Include ClConstraint.h, since cnLT, etc., need to be - defined for ClReader.y - -Mon Jul 26 09:22:11 1999 Greg Badros - - * acconfig.h, configure.in: Use CL_ prefix for BUILD_FD_SOLVER and - HAVE_GTL. - -Mon Jul 26 09:17:56 1999 Greg Badros - - * c++/config.h.in,c++/ClC.h,c++/ClC.cc,c++/Cl.h: Use CL_ prefix on - BUILD_FD_SOLVER and HAVE_GTL so that the config-inline.h gets the - right definitions. - - * c++/Makefile.am: Expanded out the sources_for_fd_solver since - the _OBJECTS make variable doesn't get expanded properly if this - step is deferred until later. This breaks builds w/o FD solver, - but I have to get Amaya working ASAP. - -Mon Jul 19 17:08:03 1999 Greg Badros - - * c++/ClSymbolicWeight.h: Increase multiplier to 10000 for - AsDouble-- works around the bug in resizing Scwm windows because - the medium stay constraints on width and height are too strong for - the strong edit constraint. - -Sun Jul 11 19:37:39 1999 Greg Badros - - * c++/ClLinearExpression.h: Remove "class" from a typedef - ClMap. Thanks Alexandre 'Pollux' Duret-Lutz - for testing against a more recent egcs (gcc-2.95) that caught this - problem. - - * configure.in: Improve checks for guile so that it uses --prefix - and --exec-prefix to --guile-prefix and --guile-exec-prefix - -Sat Jul 10 19:21:34 1999 Greg Badros - - * autogen.sh: rm libtool stuff just in case. - - * README: Updated version number, notes about building it and - needing GTL for fd solver. - - * configure.in: Added --enable-cxx-tests, --enable-fd-solver, - --with-gtl; switch --disable-java-build to --enable-java-build - - * acconfig.h, c++/config.h.in: Added HAVE_GTL, BUILD_FD_SOLVER options. - - * c++/Makefile.am: Make only the library and ClTests get built by - default (other binary test programs are each big when build -g, - and aren't useful to the end user). Use @SOURCES_FOR_FD_SOLVER@ - to permit a version of the toolkit to be build without the finite - domain subsolver. - - * c++/ClC.h, c++/ClC.cc, c++/Cl.h: Add #ifdefs for no fd subsolver. - -Fri May 7 17:02:09 1999 Greg J Badros - - * c++/ClC.cc (CL_ClvLookup): Return NULL if varmap is NULL instead - of asserting it is non-NULL - -Thu May 6 19:02:38 1999 Greg J Badros - - * c++/ClFDTests.cc: Added return type to connect1. - - * c++/ClFDSolver.cc: Return *this where missing. - - * c++/ClFDConnectorVariable.h: Reorder mem vars to match - initialization order in ctr. - - * c++/ClC.h, c++/ClC.cc: Added CL_ClvIsFD. - -Sun May 2 10:42:00 1999 Greg J Badros - - * c++/ClReader.l: Permit "_" in identifiers (needed for env - variable precondition variables). - - * c++/ClLinearInequality.h: Honour _fStrictInequality flag when - testing FIsSatisfied(). - - * c++/ClLinearConstraint.h: Added missing "void" return type for - ChangeConstant. - -Fri Apr 30 09:45:51 1999 Greg J Badros - - * c++/ClFDConnectorVariable.cc, c++/ClFDConnectorVariable.h: - Added -- support connecting the FD solver to the simplex solver - via a variable in the FD region that gets its value "copied" to a - analogous variable in the Simplex region. - - * Makefile.am: Added ClFDConnectorVariable.[ch] files. - - * c++/ClLinearConstraint.h: Added ChangeConstant() - - * c++/ClFloatVariable.h, c++/ClFDVariable.h, - c++/ClFloatVariable.cc, c++/ClFDVariable.cc, - c++/ClAbstractVariable.h: Move _pv, SetPv(), Pv() from - ClFloatVariable, ClFDVariable, into common parent - ClAbstractVariable. Drop ClFloatVariable::SetName(). - - * c++/ClFDTests.cc: Added connect1 test to test - ClFDConnectorVariable - - * c++/ClFDSolver.cc: Use 1 + value-rhs for errors to ensure that - strict inequalities behave reasonably. - -Thu Apr 29 19:29:34 1999 Greg J Badros - - * c++/ClVariable.h: Register variable in the dictionary when - initialized from a ClFDVariable*. Added const ClAbstractVariable - *operator() const. - - * c++/ClSolver.h, c++/ClSimplexSolver.h: Added _fAutosolve, - _pfnChangeClvCallback; added default ctr to initialize. Added - SolveNoException(); Moved SetAutosolve(), FIsAutosolving(), - SetChangeClvCallback() from ClSimplexSolver up to here. - - * c++/ClSolver.cc: Added PrintTo for list, operator<< - for same. - - * c++/ClSimplexSolver.cc: Test constraint with - FIsOkayForSimplexSolver() before trying to add it (avoids adding - FD constraints to the simplex solver). - s/_fOptimizeAutomatically/_fAutosolve/g - - * c++/ClParseTest.cc: Use FCanConvertCn() before trying to. - - * c++/ClFDVariable.h: Make PlfdnDomain() const and return const. - - * c++/ClFDVariable.cc: PrintOn now displays value (duh!) - - * c++/ClFDTests.cc: Use new ListPushOnto() instead of a bunch of - push_back. Added simple2, simple3. - - * c++/ClFDSolver.h, c++/ClFDSolver.cc: Added ChangeClv(), - AddConstraintInternal(), RemoveConstraintInternal(), - ListPushOnto(), fDebugFDSolve var, more debugging code. - - * c++/ClConstraint.h, c++/ClFDConstraint.h: Added - FIsOkayForSimplexSolver() returning false for FDCns, true in the - base class. - - * c++/ClFDBinaryOneWayConstraint.h, - c++/ClFDBinaryOneWayConstraint.cc: Make ctr take ClConstraint - instead of ClLinearConstraint. Added EnsurePreconditionsForCn(), - FCanConvertCn(). Throw better exceptions instead of - ExCLEditMisue-- use new ExCLTooDifficultSpecial. - - * c++/ClCTest.c: Use CL_ClvPrint instead of coding by hand. - Added CL_CldvNew() call. - - * c++/ClC.cc, c++/ClC.h: Added FDN_EOL defn, typedefs for Number, - FDNumber, CL_CldvNew(), CL_FDCanConvertCn(), CL_FDCnFromCn(), - CL_ClvPrint(). Use CL_Solver for PfnChangeClvCallback, not CL_SimplexSolver. - - * c++/ClAbstractVariable.h: Throw instead of assert(false) in base - class IsPivotable(), IsRestricted(). - -Wed Apr 28 19:38:46 1999 Greg J Badros - - * c++/ClC.cc: Added CL_FDSolverNew() - -Wed Apr 28 19:10:32 1999 Greg J Badros - - * c++/Makefile.am (INCLUDES): Include @GUILE_INCLUDES@ -- actually - done to get cassowary libraries (GJB:FIXME::) - -Wed Apr 28 18:49:51 1999 Greg J Badros - - * c++/Makefile.am: Added ClCTest to the _PROGRAMS, and use - -lstdc++ on them - - * c++/ClSolver.h: Expose Resolve() in base-class interface, along - with <<, and PrintOn. - - * c++/ClSolver.cc: Added << operator. - - * c++/ClC.h, c++/ClC.cc, c++/ClTest.c: Fixed bugs, use - CL_Solver... instead of CL_SimplexSolver... where appropriate. - -Wed Apr 28 17:15:47 1999 Greg J Badros - - * c++/ClSymbolicWeight.h: Make CLevels unsigned, not int, and - require all 3 args to the 3 double ctr to remove ambiguity. - - * c++/ClSimplexSolver.h: Check constraint before adding and throw - an error if the constraint is no good for the SimplexSolver. - - * c++/ClParseTest.cc: Don't assume a failed add is due to an - inconsistent system-- could be wrong kind of constraint was read - in. - - * c++/ClLinearInequality.h: Store the strictness of the - inequality, since other solvers may be able to use strict ones. - - * c++/ClFDSolver.cc: Fine-tune the exception objects thrown... use - the richer hierarchy. - - * c++/ClFDBinaryOneWayConstraint.c, - c++/ClFDBinaryOneWayConstraint.h: Added IsStrictInequality(), get - the direction of the inequality correct. - - * c++/ClErrors.h: Richer hierarchy of exceptions to cope with - solver limitations. - - * c++/ClConstraint.h: Added IsStrictInequality(); have - ReadOnlyVars return a const ClVarSet&, not value. - -Wed Apr 28 12:20:47 1999 Greg J Badros - - * c++/Makefile.am: Added ClFDBinaryOneWayConstraint.cc. - - * c++/ClReader.y, c++/ClReader.l: Added tokens GT, LT, and handle - them (for >, <, resp). - - * c++/ClParseTest.cc: try converting to a FD constraint, and show - what that object is. - - * c++/ClFDBinaryOneWayConstraint.h: Added ctr from a - ClLinearConstraint. Added IsInequality(). - -Wed Apr 28 12:08:16 1999 Greg J Badros - - * c++/ro-test.in: Added for testing below. - - * c++/ClFDBinaryOneWayConstraint.cc: Added -- so far just a ctr - from a ClLinearConstraint object (since the parser hands me a - constraint object that is a ClLinearConstraint object). - -Tue Apr 27 20:35:23 1999 Greg J Badros - - * c++/ClSymbolicWeight.h, c++/ClSymbolicWeight.cc: Drop default - ctr, and give default arg value to CLevels of 3. Added operator*. - - * c++/ClFDTests.cc: Better test. - - * c++/ClFDSolver.h, c++/ClFDSolver.cc: Use SymbolicWeights for - errors, so hierarchy is handled (i.e., strengths on constraints - are honoured). - - * c++/ClFDConstraint.h: Added ctr with strength, weight. - - * c++/ClFDBinaryOneWayConstraint.h: Added strength, weight - arguments to ctr. - - * c++/ClConstraint.h: Added symbolicWeight() accessor. - -Tue Apr 27 15:04:34 1999 Greg J Badros - - * c++/ClFDSolver.cc (RemoveConstraint): Fix some bugs-- handle nil - read-only variable properly, and clean up _mapVarToNode when - erasing nodes. - -Tue Apr 27 10:40:58 1999 Greg J Badros - - * c++/ClSolver.cc: Added -- wrote PrintTo, << basic impls, and - simple AddConstraint. - - * c++/QocaBench.cc, c++/ClTests.cc, c++/ClSubgraphTest.cc, - ClLeakTest.cc, ClC.cc: Use Solve(), not solve() - - * c++/ClVariable.h: Added DesiredValue, PlfdnDomain base-class - accessors, handle clvNil in PrintOn. - - * c++/Makefile.am: Added ClSolver.cc, link with -lGTL, added - missing and new .cc, .h files. - - * c++/ClTypedefs.h: added ClVarToConstraintSetMap. - - * c++/ClSolver.h: Added AddConstraint{,NoException}, - RemoveConstraint{,NoException}, Solver here to the abstract - interface, also the prototypes for the PrintTo and << on the - ClTypedefs.h types. - - * c++/ClSimplexSolver.h, c++/ClSimplexSolver.cc: Solve(), not - solve(), move some protos in abstract base class ClSolver. - - * c++/ClLinearInequality.h: Use ClCnRelation, not - ClInequalityOperator. - - * c++/ClFDVariable.h, c++/ClFDVariable.cc: More accessors, - settors, comment-out non-initial-domain ctr. - - * c++/ClFDTests.cc: Test more. - - * c++/ClFDSolver.h, c++/ClFDSolver.cc: Almost complete, but - largely untested implementation. - - * c++/ClFDBinaryOneWayConstraint.h: Added ctrs, setters, getters. - - * c++/ClErrors.h: Fixed throw message for ExCLConstraintNotFound - to not refer to the tableau. - - * c++/ClConstraint.h: Added ClCnRelation (was ClInequalityOperator - in c++/ClLinearInequality.h) and wrote StrCnRelation for printing - it. - - * c++/Cl.h: include ClFDSolver.h - - * c++/Cassowary.h : include values.h, def FDN_NOTSET (FIXME: drop this?) - -Sun Apr 25 18:55:26 1999 Greg J Badros - - * c++/Makefile.am: Added ClFDBinaryOneWayConstraint.h, - ClFDConstraint.h to pkginclude_HEADERS. - - * c++/ClSimplexSolver.h, c++/ClSimplexSolver.cc: Added optional - strength argument to AddPointStays, AddPointStay fns. - - * c++/ClFDVariable.h: Set _plfdnInitialDomain to avoid a warning - for now. - - * c++/ClFDBinaryOneWayConstraint.h: Added return xo to PrintOn. - - * c++/ClConstraint.h: Fix order of initializers. - - * c++/ClC.h, c++/ClC.cc: Document return value for - CL_VarMapDelete, and do proper return. - - * configure.in: Added --enable-cflags, --enable-cxxflags, - --enable-cppextraflags. Not tested yet. - -Sun Apr 25 11:46:28 1999 Greg J Badros - - * configure.in: Bump version to .50, for FD features. - -Sun Apr 25 11:37:52 1999 Greg J Badros - - * c++/Makefile.am: Comment out the Bug sources/builds, add the FD - sources. - - * c++/ClSimplexSolver.h: Inherit from ClSolver, too. Move SetPv, - Pv() out into ClSolver base class. - - * c++/ClSimplexSolver.cc, c++/Cl.h: Make szCassowaryVersion a const char *. - - * c++/ClReadery.y, c++/ClReader.l, c++/ClReader.h: Support "?" - read-only annotations, and use Constraint::AddROVars() to track - the ro vars of a constraint expression. - - * c++/ClParseTest.cc: Show whether the constraint is added - successfully or if it is inconsistent. - - * c++/ClLinearConstraint.h: Fix BUG-- super should be - ClConstraint, not ClLinearConstraint. - - * c++/ClFDVariable.cc: Use <, > to delimit FD vars, not [, ]. - - * c++/ClConstraint.h, c++/ClConstraint.cc: Added AddROVars, - FIsReadOnlyVar, ReadOnlyVars. - -Thu Apr 22 20:18:31 1999 Greg J Badros - - * c++/ClVariable.h: Added ClVariable ctr that takes a - ClFDVariable*, this ambiguates returning NULL as a ClVariable, so - may not be a good idea, but it does make it less confusing than - having another overloaded version of ClVariable's ctr. Added - IsFloatVariable, IsFDVariable fwding fns. - - * c++/ClSimplexSolver.cc: Disambiguate uses of NULL to be - (ClFloatVariable *)NULL. - - * c++/ClFloatVariable.h: Added IsFloatVariable() to return true - - * c++/ClC.h, c++/ClC.cc: Added CL_ClvLookupTrim for removing ws - around the var name. - - * c++/ClAbstractVariable.h: Make IsPivotable, IsRestricted both - assert false instead of being pure virtual -- they only need to be - overridden if we want to permit them to be called. Added - IsFloatVariable(), IsFDVariable() both returning false in this - base class. - - * c++/Cassowary.h: Added FDNumber typedef to be a long. - - * c++/Makefile.am: Added ClFDVariable.{cc,h} - - * c++/ClFDVariable.cc, c++/ClFDVariable.h: Added, copied from - ClFloatVariable and modified slightly. - -Tue Apr 20 10:18:32 1999 Greg J Badros - - * smalltalk/README: Note that smalltalk implementation is now in - the public domain. - - * README: Update to version 0.43, note about smalltalk - implementation being in public domain. - - * LICENSE: Note about not applying to smalltalk implementation - - * ANNOUNCE: Update date to today. - - * *: Changed copyright to be "Greg J. Badros and Alan Borning" - instead of "Alan Borning and Greg J. Badros". Okayed by Alan -- - to hopefully encourage more people to write me with their - questions/problems rather than Alan. - -Mon Apr 19 13:45:35 1999 Greg J Badros - - * cassowary.spec: Added --with-guile-prefix - -Mon Apr 19 13:02:46 1999 Greg J Badros - - * c++/ClReader.l: Be a bit more careful about end of string - handling in YY_INPUT-- only return result = 1 if we read a - non-null character. Call yy_flush_buffer() before throw-ing an - error, so that we start anew the next time we are asked to return - tokens for the parser. - - * c++/ClC.h, c++/ClC.cc: Added CL_SimplexSolverAddStay. (Fix typo - in .cc) - -Fri Apr 16 16:36:24 1999 Greg J Badros - - * c++/ClTests.cc, c++/ClSimplexSolver.h, c++/ClSimplexSolver.cc, : Use "RemoveConstraintNoException", not - "removeConstraintNoException" (fix initial caps.) - - * c++/ClReader.y: Start looking for a constraint, turn on verbose - warnings and DEBUG option (still need to set cldebug = 1 in - debugger) - - * c++/ClReader.h: In operator() for the lookup proc, Return - &clvNil() if _pmapVars is still NULL - - * c++/ClC.h, c++/ClC.cc: Added CL_VariableName(..), CL_VarMapDelete(..), - CL_RemoveConstraint(..) - - -Wed Apr 14 16:56:05 1999 Greg J Badros - - * configure.in: Bump to .43. - - * c++/ClC.cc (CL_VarMapDelete, CL_VariableName): Added new functions. - - * cassowary.spec: Added, for building rpms - - * c++/gdbinit-cassowary: Added a bunch of guile debugging macros. - - * c++/Makefile.am: Added ClC.cc to libcassowary_a_SOURCES - - * c++/ClReader.y: Turn off parser debugging messages by default - - * c++/ClC.h, c++/ClC.cc: Added CL_ConstraintPrint, CL_FIsSatisfied - protos - -Wed Mar 31 17:23:18 1999 Greg J Badros - - * wrappers/Makefile.in: Rename PYTHON_HEADERS to PYTHON_HEADER_DIR - so it does not get treated specially by automake (?). - - * configure.in: Bump to .42. Added --disable-cpp-build, - --disable-java-build, and disable Python/Guile builds - automatically if directories cannot be found. Drop the - cassowary from c++/cassowary/config.h -- just use c++/config.h - - * autogen.sh: do not fail if config.status is not -x. - - * Makefile.am: Honour the HAVE_foo flags so that not all subdirs - have to be built. - -Mon Mar 29 21:01:21 1999 Greg J Badros - - * ltconfig, ltmain.sh: Added -- so libtool isn't broken in - distributions. - -Mon Mar 29 20:59:17 1999 Greg J Badros - - * configure.in: Try to undo a bash-ism. Untested on a vendor sh, - but still works with bash. - -Sat Mar 20 19:19:37 1999 Greg J Badros - - * Release v0.41. - -Sat Mar 20 19:19:13 1999 Greg J Badros - - * Added config.sub and config.guess to the repo -- they were - symlinks before which broke the distribution. - -Thu Mar 18 15:20:51 1999 Greg J Badros - - * Release v0.4. - -Thu Mar 18 14:44:39 1999 Greg J Badros - - * configure.in: Do not let config-inline.h get overwritten if it - is unchanged. Add some extra messages to tell status of - config-inline.h - -Thu Mar 18 12:59:02 1999 Greg J Badros - - * README, configure.in, wrappers/Makefile.in: Added - --with-python-headers configure option. - -Thu Mar 18 12:48:55 1999 Greg J Badros - - * README: Added notes about what to do when a subdir build fails, - suggest -k by default. - - * guile/Makefile.am (test): Added this target for easier way to - run cltests.scm. - - * guile/README: Updated with notes about how to run cltests.scm. - - * java/Makefile.in: Fix tests build rule. - -Thu Mar 18 11:42:49 1999 Greg J Badros - - * configure.in: Create config-inline.h at end of script. - - * c++/Makefile.am: Do not have rule for building config-inline.h; - let configure script do that. - -Thu Mar 18 11:05:27 1999 Greg J Badros - - * c++/*.h: Use #include config-inline.h incantation so that header - files don't include config.h (since they may be included by - another package that has its own config.h) - - * c++/*.cc: Use #include config.h as these are build-time-only - used and can thus rely on the full configure details. - -Thu Mar 18 10:57:08 1999 Greg J Badros - - * guile/cassowary_scm.hpp: Use #include config-inline.h - incantation. - - * guile/cassowary_scm.h: Drop including config.h; it's not - needed. - - * guile/cassowary_scm.cc: Use cassowary/config.h, not config.h - -Thu Mar 18 10:29:40 1999 Greg J Badros - - * c++/Makefile.am: Install config-inline.h, not config.h, and - build config-inline.h by grepping for #define CL_ in config.h. - This works around the problem caused by Scwm including Cassowary - header files which then included cassowary's config.h and - conflicted with Scwm's config.h. - -Thu Mar 18 10:11:40 1999 Greg J Badros - - * c++/test-*.cc: Only #include "Cl.h" - -Thu Mar 18 09:50:45 1999 Greg J Badros - - * wrappers/Makefile.in (clean): use rm -f so we don't get a - warning if file is missing. - -Thu Mar 18 09:49:35 1999 Greg J Badros - - * java/Makefile.in: Use JAVA_CLASS_PATH configure variable. Fix - install target to echo a message about the install happening - during the build. - -Wed Mar 17 18:54:16 1999 Greg J Badros - - * c++/Makefile.am: Use libtool, and added lib_LTLIBRARIES. Put - benchmarks, bugs, and test programs all under $libdir/cassowary. - Drop cassoincludedir, as that's just pkginclude, and use - include_HEADERS for Cl.h and ClC.h, the main top-level includes. - Also install config.h. - - * c++/Cassowary.h: #undef PACKAGE, VERSION before #including - cassowary/config.h as a cheezy workaround. (Switched from "" to - <>, and ../ to cassowary/ also). - -Wed Mar 17 18:50:49 1999 Greg J Badros - - * configure.in: Put config.h in c++/cassowary so cassowary must do - #include so there is no filename conflict - with other packages including cassowary header files (e.g., - Scwm). Added AM_PROG_LIBTOOL call. Set GUILE variables outside - of the guile-prefix ACE_ARG_PATH macro, and set GUILE_PKGDATA_DIR - use guile-config to find out where we should install the .so file. - -Wed Mar 17 18:43:08 1999 Greg J Badros - - * guile/Makefile.am: Updated to build using libtool, and to - install header files. Changes name to libconstraints.* so that - the guile module name (cassowary constraints) works out, and set - it to install in the right place. - -Wed Mar 17 18:39:13 1999 Greg J Badros - - * guile/cltests.scm: Added #! lines, change name of module to - (cassowary constraints), remove redundant `use-modules' call. - - * guile/cassowary_scm.hpp: #include - cassowary/ClLinearExpression_fwd.h, not ClLinearExpression_fwd.h - - * guile/cassowary_scm.cc: Change name of module to (cassowary - constraints). Make the init_cassowary_scm fn static. - -Wed Mar 17 07:39:10 1999 Greg J Badros - - * c++/Cassowary.h, c++/ClSimplexSolver.cc: Switch back to - including config.h (now ../config.h) from Cassowary.h, instead of - from ClSimplexSolver.cc. - -Tue Mar 16 19:56:02 1999 Greg J Badros - - * acconfig.h: Fix missing comment closer */ - - * c++/Makefile.am: Added AM_CPPFLAGS = $(CPPEXTRAFLAGS) - - * configure.in: Use config.h, not c++/config.h, and permit - --enable-warnings option to turn on compile-time warnings (uses - AM_CPPFLAGS in Makefile.am) - -Tue Mar 16 19:26:23 1999 Greg J Badros - - * configure.in, acconfig.h: Better autoconf support, including - several --enable options. Added acconfig.h to support autoheader - doing the right thing in making config.h.in. - -Tue Mar 16 19:22:50 1999 Greg J Badros - - * c++/ClSimplexSolver.cc, c++/Cassowary.h: Include "config.h" from - here, not from Cassowary.h (still not right-- problem is scwm gets - the wrong config.h. Maybe config.h should be in ..? - -Tue Mar 16 19:21:06 1999 Greg J Badros - - * java/README: Added note about common error when CLASSPATH is wrong. - -Tue Mar 16 15:51:15 1999 Greg J Badros - - * c++/Cassowary.h: #include "config.h" - - * c++/ClSimplexSolver.cc: Use VERSION to init szCassowaryVersion. - -Tue Mar 16 12:44:33 1999 Greg J Badros - - * c++/**: Updated function names to always start with an uppercase - letter (follows C++ conventions, and brings API of Cassowary and - QOCA closer together). Used scripts/convert-ids to do the - conversion, along with scripts/ids-to-upper as the list of - conversions to do. - -Wed Mar 10 15:28:33 1999 Greg J Badros - - * Release v0.32. - -Wed Mar 10 11:36:37 1999 Greg J Badros - - * **/Makefile: Removed, since these are now generated by - autoconf from Makefile.in (which itself is generated by - automake from Makefile.am [only for some directories]) - - * configure.in: - - * c++/ClBug2.cc: Added to demonstrate a bug that Anthony Beurivé - reported. - - * c++/ClSimplexSolver.cc: Fix above-mentioned bug by changing the - coefficient of the added in removeConstraintInternal. - - * c++/ClReader.l: Reset the lexer on failed id lookup. - - * c++/ClC.cc, c++/ClC.h: Added VarMap access functionality, make - CL_ParseConstraint catch exceptions and return NULL on error - parsing. - - * c++/config.h.in, c++/stamp-h.in: Added, for automake/autoconf - support. - - * c++/Makefile.am: Improve installation support, updated for - ClBug2 - - * guile/Makefile.am: Build .x using guile-snarf - - * c++/Makefile.linux: Updated for ClBug2 - - * c++/demos/DraggableBox.h: Do not return references to - ClVariable-s -- just return by value since they are a handle - class. - - * guile/Makefile.am: changed name of library to - libcassowaryguile.a from libconstraints.a - - * java/CL.h: Added a String description argument to assert() to - permit easier tracking of failures. - - * java/ClSimplexSolver.java: Fix bug that Emmanuel Pietriga - reported -- use peek() to get at top element of _stkCedns stack - when removing edit variables in removeEditVarsTo(). Added - descriptions to assert()s and to throwing of ExCLInternalError. - Have the addBounds, addUpperBound, addLowerBound functions - propagate out ExCLInternalError-s instead of catching them and - printing an error message. Added messages to all assertions. - - * java/ClLinearExpression.java: Added description to throwing of - ExCLInternalError. - - * java/ClLinearInequality.java: Added description to throwing of - ExCLInternalError. - - * java/ExCLInternalError.java: Require description of the error in - constructor. - - * java/QuadDemo.java: Use System.err when printing errors, and - print the description of the exception. - - * smalltalk/ClKernel.app: Fix bug with not using the weight of a - constraint as the negating coefficient when removing a constraint. - -Mon Mar 8 16:40:17 1999 Greg J Badros - - * Added autoconf and partial automake support. Added numerous - Makefile.am's, renamed old Makefiles to Makefile.linux (and copied - to Makefile.in when I did not write a Makefile.am). Added - configure.in. - - * guile/cassowary_scm.cc: Use ClReader.h, not creader.h (I renamed - the file) - -Fri Mar 5 16:24:05 1999 Greg J Badros - - * c++/Makefile, c++/Cl.h: Fix for renaming of creader.* -> - ClReader.*; make C libraries as part of lib, shared_lib rules. - - * c++/ClReader.*: Added, renamed from creader.h, creader.y, - creader.l - - * c++/ClTableau.h, c++/ClTableau.cc: Added - printExternalVariablesTo() fn. - - * c++/ClSimplexSolver.cc: printExternalVariablesTo in - printInternalInfo. - - * c++/ClParseTest.cc: DO not include ClReader.h-- Cl.h includes it - - * c++/ClCTest.c: Make more like a browser-related test, use new - CL_TableauPrintExternalVariables() - - * c++/ClC.h, ClC.cc: Added CL_Tableau, - CL_TableauPrintExternalVariables. Use "ends" to terminate - strstreams. Make Strong Stays use medium strength stays. Make - CL_ParseConstraint call ClsFromSz instead of parsing the char * - itself. - -Thu Mar 4 19:08:23 1999 Greg J Badros - - * c++/ClVariable.h: Add assert(pclv) before dereferencing through - ClVariable's pclv member. - - * c++/Makefile: Added DYNLINK = yes/no variable for controlling - dynamic linking more easily. - - * c++/ClSimplexSolver.h: Changed PfnChangeClvCallback to take a - ClVariable * instead of a ClVariable. This make it easier for the - C interface since it has "CLV" as a "ClVariable *" and cannot - reason about ClVariable-s because it doesn't see the struct defn. - - * c++/ClC.cc, c++/ClC.h: Added CL_SimplexSolverSetEditedValue, - CL_SimplexSolverPrint, CL_SimplexSolverSetChangeClvCallback, - CL_VariableSetPv, CL_VariablePv. - - * c++/ClCTest.cc: Test CL_SimplexSolverSetEditedValue, CL_SimplexSolverPrint. - -Wed Mar 3 17:37:17 1999 Greg J Badros - - * c++/ClSimplexSolver.h (UpdateExternalVariables): Added this - function to provide a publicly available way to get at setExternalVariables() - - * c++/ClCTest.c, c++/ClC.h, c++/ClC.cc: Added for the beginnings - of a rudimentary C interface to the c++ library. - - * c++/Makefile: Updated to build ClCTest, libccassowary.so (the C - interface to Cassowary [for Amaya, initially]) - -Mon Mar 1 Greg J Badros - - * Release v0.31 - -Mon Mar 1 15:11:52 1999 Greg J Badros - - * c++/ClVariable.h: Added explict copy ctr. - - * c++/ClEditConstraint.h, c++/ClStayConstraint.h: Changed output - format so parentheses started by super:: call to ClConstraint.h - are closed properly. - - * c++/ClSimplexSolver.h, c++/ClSimplexSolver.cc: Undo removing a - pass by reference of ClVariable when used as an output argument. - Added printing for ClEditInfo class instancesm, - ClVarToEditInfoMap. - -Mon Mar 1 13:46:48 1999 Greg J Badros - - * README: Updated for version 0.31. - - * c++/Makefile: Added QocaBench.o to TEST_OBJS, comment out - CL_USE_HASH_MAP_AND_SET by default. - - * c++/ClTestColumns.cc: Allocate constraint objects on heap, not - as temporaries on local stack - - * c++/ClStayConstraint.h, c++/ClSimplexSolver.h, - c++/ClSimplexSolver.cc, c++/ClPoint.h, c++/ClLinearInequality.h, - c++/ClEditOrStayConstraint.h, c++/ClEditConstraint.h: Pass and - return ClVariable-s by value, not by reference. (Fixes bug in - QocaBench from re-use of a ClVariable object with the underlying - pointer different. - - * c++/Cl.h: include creader.h - - * c++/README: Fix spelling of deprecated, URL for WxWindows. - - * c++/test-ClConstraint.cc: Comment out unused variables - -Mon Mar 1 12:53:02 1999 Greg J Badros - - * c++/qdemos/QuadDemoWindow.cc: Allocate constraint objects on - heap, not as temporaries on local stack. - -Fri Feb 26 09:16:31 1999 Greg J Badros - - * wrappers/cassowary.i: Use .c_str() off of exception descriptions - to get the char * (description() now returns a string) - -Fri Feb 26 09:11:17 1999 Greg J Badros - - * c++/ClConstraint.h: Added FIsInSolver() - - * guile/cassowary_scm.cc: Wrap cl-constraint-is-in-solver? - -Thu Feb 25 18:58:55 1999 Greg J Badros - - * guile/cltests.scm: Added (use-modules..) invocation to get the - dynamically-loaded module so that it can be tested outside of - scwm. Updated to reflect changed behaviour in cl-add-stay. Added - some test code for make-cl-constraint-from-string. - - * guile/cassowary_scm.hpp: Added ScmMakeClConstraint(..) to - abstract out setting "answer" for the (now) two ClConstraint ctrs. - - * guile/cassowary_scm.cc: Added make-cl-constraint-from-string for - interfacing to the parser. Wrap - cl-constraint-change-{strength,weight}!. Make dynamically loadable - module! Fix BUG: was returning SCM_UNDEFINED instead of - SCM_UNSPECIFIED. - - * guile/Makefile: Build libconstraints.so, and necessary directory - structure if neeeded. - - -Thu Feb 25 18:41:34 1999 Greg J Badros - - * c++/ClSimplexSolver.h, c++/ClSimplexSolver.cc: Make constraints - get told when they're added/removed from a solver. This means - that constraints are no longer const params to add/remove - Constraint functions, and also that removeConstraint needs an - internal version that doesn't do the counting (since - removeConstraint can get called from addConstraint to clean up - after a failed addition). - - * c++/ClSimplexSolver.cc: Clean up uses of ClConstraint &cn -- - prefer ClConstraint *pcn even internally. - - * c++/ClConstraint.h: Added ChangeStrength(..), ChangeWeight(..) - and _times_added memvar along w/ private (for friend - ClSimplexSolver) addedTo(..) and removedFrom(..) functions. Only - permit strength/weight changing if constraint is in no solvers - presently. - - * c++/ClConstraint.cc: Output _times_added memvar in printOn(...) - -Thu Feb 25 15:58:27 1999 Greg J Badros - - * c++/ClErrors.h: Added parse error classes, and have description - return a "string" instead of a "char *" - - * c++/creader.y: Use exception ExCLParseErrorMisc in clerror, Use - ClVarLookupFunction instead of mapVars and fAutoCreate - - * c++/creader.l: Use ClVarLookupFunction instead of doing it - inline with mapVars and fAutoCreate; throw exceptions on errors. - - * c++/creader.h: Added ClVarLookupFunction and ClVarLookupInMap - and use them when parsing. - - * c++/Makefile: Added some dependencies for proper building of - .l,.y files - - * c++/ClSimplexSolver.cc: Descend VarInVarSet from - unary_function<..,..> - - * c++/ClParseTest.cc: Catch parse errors and display the message. - Use ClVarLookupInMap class - -Thu Feb 25 12:09:48 1999 Greg J Badros - - * c++/ClSimplexSolver.cc: Simplify removeConstraint to not use - references. - - * c++/ClSimplexSolver.h: Updated a comment - - * c++/ClTests.cc: Use addEditVar, beginEdit, and endEdit, instead - of building EditConstraints directly. - -Tue Feb 23 18:48:21 1999 Greg J Badros - - * c++/creader.y, c++/creader.h: Remove old crummy lexer. Added - fAutoCreate flag to PcnParseConstraint to allow parsing with - automatic introduction of newly-referenced variables. - - * c++/creader.l: Fixed bugs in missing tokens "|", "(", ")", and - permit "==" as a synonym for "=". Honour the _fAutoCreate flag by - introducing variables when needed. - - * c++/ClTests.cc: Display version id string at startup. - - * c++/ClSimplexSolver.cc, c++/Cl.h: Added szCassowaryVersion id - string. - - * c++/ClParseTest.cc: Test auto-addition of variable (fAutoCreate - = true) - -Tue Feb 23 18:12:23 1999 Greg J Badros - - * c++/Makefile: Build libcassowary.{a,so} by default, not - libcassowary-notrace.{a,so}. Remove special rule for building - ClParseTest; list creader-lex.o, creader.o in OBJS and have them - be a part of the library. - - * c++/ClVariable.h, c++/ClVariable.cc: Rename pmapSzPclv to - pmapStrPclv. Make it a map from "const string" not "string". - Make setName erase the old mapping, and add the new mapping. - - * c++/ClParseTest.cc: Accept "-" option to mean "rename x to foo" - for testing the setName change above. - - * c++/ClFloatVariable.cc: Do not output warning msg in setName -- - instead, do the right thing in ClVariable.h - -Tue Feb 23 08:55:28 1999 Greg J Badros - - * c++/Makefile: Fix build rules for bison/flex parser so - dependencies are correct. Added new targets, all-notests, - all-tests, make 'lib' the default target, and all really build - everything. - - * c++/creader.h, c++/creader.l, c++/creader.y: Take address of - ClVariable-s from the map's values (cannot use ClVariable in the - union directly because union members cannot have constructors). - #include ClVariable.h instead of fwd decl of ClVariable so that we - get the StringToVarMap typedef, too. - -Mon Feb 22 16:33:16 1999 Greg J Badros - - * c++/Makefile: Use CL_LIBRARY, not LIB_FILE, throughout. Use - flags for maximum performance. - - * c++/ClVariable.h, c++/ClConstraintHash.h, c++/Cassowary.h: - Divide pointer address by CL_PTR_HASH_DIVISOR in hash functions - - * c++/ClTests.cc: Added CL_SHOW_CNS_IN_BENCHMARK guard protecting - new displaying of constraints and listing of inconsistent constraints. - -Mon Feb 22 12:18:53 1999 Greg J Badros - - * c++/ClTests.cc (inconsistent3): Drop extra redundant - inconsistency for pedagogical reasons. Use simpler pointer-based - addConstraint in benchmark test - - * c++/ClSimplexSolver.h: Added addConstraintNoException, - removeConstraintNoException taking ClConstraint &'s -- deprecated. - Added CL_NO_DEPRECATED guard for turning off availability of - deprecated functions. - -Mon Feb 22 11:12:35 1999 Greg J Badros - - * c++/ClSimplexSolver.h: Added deprecated - FIsConstraintSatisfied(Constraint &) - - * guile/cassowary_scm.cc: Use ClConstraintToVarMap for return - value of ConstraintMap(). Pass Constraint *'s instead of &'s. - Use new name printOnVerbose instead of printDebugInfo. - -Fri Feb 19 Greg J Badros - - * Release v0.3. - -Fri Feb 19 18:00:49 1999 Greg J Badros - - * c++/ClTests.cc: Updated to fix below interface. - - * c++/ClSimplexSolver.cc, c++/ClSimplexSolver.h: make - addConstraint, addConstraintNoException, removeConstraint, - removeConstraintNoException take ClConstraint *'s instead of - ClConstraint &'s. Clarifies the mental model, and simplifies the - syntax. Old style is still accepted, but is deprecated. - -Fri Feb 19 17:41:45 1999 Greg J Badros - - * c++/ClFloatVariable.cc, c++/ClFloatVariable.h: Added -- moved - here from ClVariable.h, and renamed from class ClVariableRep since - they not what ClVariable wraps (ClVariable wraps - ClAbstractVariable) - - * c++/ClAbstractVariable.h: Fatten interface to include set_value, - change_value, setPv, and Pv. - - * c++/ClVariable.h, c++/ClVariable.cc: Move ClVariableRep into - ClFloatVariable.{h,cc}, and use pclv-> for - set_value, change_value, SetPv, and Pv since ClAbstractVariable - now has a fat interface and we do not need to do the dynamic - down-casting. - - * c++/Makefile: Added new files to build rules. - -Fri Feb 19 17:08:29 1999 Greg J Badros - - * c++/debug.h, c++/ClTableau.h: Move operator<< out into ClTableau.h - - * c++/ClVariable.h, c++/ClVariable.cc: Move some inline functions - into .cc so that the hash function can go in the .h file (some stl - dependency issue, it seems). - - * c++/ClErrors.h, c++/ClTypedefs.h: Move typedef for - ClConstraintSet from ClErrors.h into ClTypedefs.h, and have former - include the latter. - - * c++/Cassowary.h: #include ClConstraintHash.h - - * c++/ClConstraintHash.h: Added. The hash function needs to - appear before any typedef that uses a hash_map or hash_set, so - this file is included by Cassowary.h - -Fri Feb 19 08:45:24 1999 Greg J Badros - - * c++/ClSubgraphTest.cc: Fix some bugs just from not testing - completely. - - * c++/*: Fix bugs from not-updated-code hidden by #ifdefs. Builds - w/ all compile-options except -DCL_USE_HASH_MAP_AND_SET. Drop - some gratuitous appearances of ClAbstractVariable - -Thu Feb 18 18:53:56 1999 Greg J Badros - - * c++/ClLinearExpression.cc: Use clvNill when returning a - ClVariable instead of NULL - - * c++/ClVariable.h, c++/ClVariable.cc: operators ==, !=, < all should use the - contained pointers address, not value. Also define global clvNil, - isNil(). - - * c++/ClTests.cc: BUGFIX: #if 0 removed from adding stays in - simple1 test - - * c++/ClSimplexSolver.h: Use ClVariable-s internally for - ClObjectiveVariable-s. - - * c++/ClSimplexSolver.cc: Use ClVariable-s internally for - ClObjectiveVariable-s and replace ClAbstractVariable - *p{entryVar,exitVar} with ClVariable-s. (Use clvNil and isNil() - to test for not yet set). - -Thu Feb 18 Greg J Badros - - * c++/*: First compilable and almost working version with - ClVariable as a handle to ClVariableRep. Major simplifications - throughout. - -Thu Feb 18 14:22:14 1999 Greg J Badros - - * c++/Makefile: Split out the options into += lists so they can be - flipped independently more easily. - - * c++/ClSimplexSolver.cc, c++/ClSimplexSolver.h: Added output - operation for ClConstraintToVarSetMap; use fFoundErrorVar flag to - simplify some redundant tests in removeConstraint -- no longer use - errorVarsCopy. - - * c++/CLVariable.h: Fix a comment's example. - - * c++/ClTypedefs.h: Use set always for ClTableauVarSet (Steve - Wolfman notes that it's faster as a set than as a hash_set). - - * c++/debug.h: Add CtrTracer, DtrTracer fns that do nothing when - not CL_TRACE - - * c++/ClConstraint.h: Invoke CtrTracer, DtrTracer in ctr, dtr for - finding memory problem - - * c++/ClTests.cc: Fix some long-time bugs in the use of ctrs that - build temporary objects whose lifetime was expected to be longer - than it was. - - * c++/*: Invert sense of CL_NO_TRACE to CL_TRACE - -Wed Feb 17 12:10:28 1999 Greg J Badros - - * c++/ClTypedefs.h: Added -- factored out useful typedefs from - ClSimplexSolver.h, ClTableau.h and put them in this file. - - * c++/ClTableau.h, c++/ClSimplexSolver.h, c++/debug.h: Use - ClTypedefs.h. Drop gdb_print (it uses printOn and printTo, now). - Renamed printDebugInfo to printOnVerbose (for generalized gdb - interface) - - * c++/ClSimplexSolver.cc: Fix two bugs where I was modifying data - structures indirectly while iterating over them. Remove a delete - that was premature to fix another bug in optimized builds. - - * c++/ClLinearExpression.h, c++/ClConstraint.h, - c++/ClAbstractVariable.h: Drop gdb_print(). - - * c++/ClSymbolicWeight.h: Use Number instead of double more consistently. - -Tue Feb 16 15:04:06 1999 Greg J Badros - - * c++/Cassowary.h,ClAbstractVariable.h,ClMap.h,ClSet.h,Makefile: Use - CL_USE_HASH_MAP_AND_SET, not USE_HASH_MAP_AND_SET. - - * c++/Cl.h: #undef CL_TRACE_VERBOSE ifdef CL_NO_IO - -Tue Feb 16 14:55:12 1999 Greg J Badros - - * java/ClVariable.java: Add setVarMap(..), getVarMap() for - maintaining symbol table of ClVariables. Added - setAttachedObject(..), getAttachedObject() for hanging something - off of a variable. - - * java/ClConstraint.java: Added setAttachedObject(..), - getAttachedObject() for hanging something off of a constraint. - - * java/ClTests.java: Added inconsistent3() and multiedit() tests - - * java/ClSimplexSolver.java: Manage multiple (nested) edits - properly. Provide access to the _markerVars var through - getConstraintMap() accessor. Deprecate resolve(Vector) fn. - -Tue Feb 16 14:29:46 1999 Greg J Badros - - * README: Updated reference to swig web site. - -Tue Feb 16 12:45:04 1999 Greg J Badros - - * java/ClSimplexSolver.java, java/ClEditInfo.java, java/Makefile: - Fixed Michael Kaufmann's bug. (See Feb 15 note for C++ version - two entries below.) - - * java/*.java: Updated copyright to include 1999. - -Tue Feb 16 10:51:01 1999 Greg J Badros - - * c++/*: Added CL_FIND_LEAK guard and ctr/ctr counters for - tracking various variable kinds. - -Mon Feb 15 18:38:06 1999 Greg J Badros - - * c++/ClAbstractVariable.{cc,h}, ClSlackVariable.{cc,h}, - ClDummyVariable.{cc,h}: Add counters to ctr/dtr for leakage detection. - - * c++/ClSimplexSolver.{cc,h}: Replace ClConstraintAndIndex with - ClEditInfo, and remove ugliness of parallel vectors for edit - constraints. Drop _editPlusErrorVars, _editMinusErrorVars, - _prevEditConstants, and bundle them all up in the value end of the - map attached to _editVarMap. This fixes a bug reported in the - Java version by Michael Kaufmann long ago, and generally cleans - code up a bit. The resolve(vector) function is - deprecated, and now implemented in terms of the indices stored in - the new ClEditInfo class. - - * c++/*: Updated copyright to include 1999. - -1999-02-15 Greg J Badros - - * c++/ClVariable.{cc,h}, c++/ClAbstractVariable.h: Added - SetVarMap(..), VarMap(), and make variables given names get their - names mapped to the objects in the var map (for access when - parsing constraints as strings). Make setName() virtual so - ClVariable can override it. - -1999-02-12 Greg J Badros - - * c++/creader.{y,h}: New version from Steve Wolfman, slightly - updated for cleaner integration. Pass in a map instead of an array of ClVariable; improve error handling a - bit. - - * c++/debug.h: Use ClMap, ClSet - - * c++/{ClMap.h,ClSet.h}: Added, for optionally using hash_map, - hash_set instead of map, set. - - * c++/ClSimplexSolver.{cc,h}: Added Steve Wolfman's explanation - support (added back map for marker->constraint, _fExplainFailure - var + getter & settor). Use ClMap, ClSet. Cleaned up some cerr - output, and use DEBUG_FAILURES cpp symbol to guard some output. - - * c++/Cassowary.h: Added operator() for hash<..> to support - hashing things used as keys in hash_map/hash_set - - * c++/ClErrors.h: Added ExCLRequiredFailureWithExplanation class - for explanation support. - - * c++/{ClLinearExpression.h,ClTableau.h}: Use ClMap, not map. Use - ClSet, not set. - - * c++/ClSymbolicWeight.h: Return a symbolic weight even when - assert(false) to avoid compiler warning. - -1999-02-11 Greg J Badros - - * guile/cassowary_scm.cc: Use cl-snarf.h, not scwm-snarf.h. Use - CL_PROC to denote primitives, not SCWM_PROC. Use - CL_VAR_INIT_PERMANENT macro for variables, and document them (the - strength objects only, for now). Fix the default strength of - cl-add-editvar to Strong, not Weak, and update docs (was cut&paste - error from the cl-add-stay primitive). Thanks Anthony Beurivé for - noticing this bug, too! - -Sat Jan 30 Greg Badros - - * Release v0.23. - -Sat Jan 30 13:16:31 1999 Greg Badros - - * c++/ClSimplexSolver.cc: Fixed bug in removing a stay - constraint. Was editing a vector in place while iterating over - it. Now I use remove_if and erase. Thanks to Anthony Beurivé for - noticing the bug. - - * c++/ClBug1.cc: Added -- bug report from Anthony Beurivé. - -Sat Jan 23 Greg Badros - - * Release v0.22. - -Sat Jan 23 16:46:27 1999 Greg Badros - - * guile/cassowary_scm.cc: Replace iarg uses with literal argument - index numbers. Use const_cast to avoid warnings when calling - ScmMakeClStrength on clsWeak,clsMedium,clsStrong,clsRequired objects - -Sat Jan 23 15:30:16 1999 Greg Badros - - * c++/ClSimplexSolver.cc: Added some comments, some explanations - when exceptions are thrown, and some minor cleanups, bug-fixes - - * c++/ClTests.cc: Added inconsistent3() test, and run it. - - * c++/ClStrength.h: Added _pv memvar, and setPv(), Pv() -- needed - for tracking ClStrengths in guile - - * guile/cassowary_scm.cc: Replace all iarg uses with the literal - number. Point ClStrength objects at their scheme-level object - using their new _pv field. Protect ClStrength objects properly. - -Sat Sep 19 17:08:21 1998 Greg Badros - - * c++/Makefile (CPPFLAGS): Added USE_GC, commented out, and added - OTHER_LIBS variable for linking with the gc library - -Sat Sep 19 17:01:16 1998 Greg Badros - - * c++/ClTableau.h: Added AssertValid() for testing integrity of - Tableau - - * c++/ClSymbolicWeight.h, c++/ClStrength.h, c++/ClSlackVariable.h, - c++/ClLinearExpression.h, c++/ClErrors.h, c++/ClDummyVariable.h, - c++/ClConstraint.h, c++/ClAbstractVariable.h: Descend objects - from "gc" class conditioned on USE_GC* pp macros - - * c++/Cassowary.h: Conditionally include gc_cpp.h ifdef USE_GC; - added NEWVAR and DELVAR macros for outputting debug information at - new/delete sites - - * c++/ClSimplexSolver.h: Call AssertValid before solving - - * c++/ClSimplexSolver.cc: Remove memory leak of the artificial - objective variable - - * c++/ClLinearExpression.h: Fix gdb_print to have a newline - - * c++/ClLeakTest: Added leakTest2 which more obviously leaks, and - use GC_gcollect() to force a collect - -Tue Sep 15 16:36:20 1998 Greg Badros - - * c++/ClTableau.h, ClTableau.cc: Handle removing vars from _columns more - carefully, and add gdb_print(), virtual destructor - - * c++/ClLinearExpression.h, c++/ClConstraint.h, - c++/ClAbstractVariable.h: Added gdb_print() - -Tue Sep 14 Greg Badros - - * Release v0.21. - -Wed Sep 9 09:46:35 1998 Greg Badros - - * c++/ClLinearExpression.h, c++/ClLinearExpression.cc: added uses - of 'typename' keyword as needed by egcs-1.1b's -pedantic (and the - C++ FDIS) - -Sun Sep 6 13:19:01 1998 Greg Badros - - * c++/ClSimplexSolver.h: Added _pv field, and Pv() setPv() getter - and setter - - * guile/cassowary_scm.cc: Use solver's _pv field to point - ClSimplexSolver back at the scheme object that wraps it - -Fri Sep 4 18:52:50 1998 Greg Badros - - * guile/cassowary_scm.hpp, guile/cassowary_scm.cc: Added PvFromScm - and ScmFromPv to hide the reinterpret casts used to store a scheme - object as the void * Pv() attached to a cassowary object. Attach - the scheme-level cl-variable to a ClVariable object. Added - `clv-attach!' and `clv-attached-object' to manipulate the attached - object (often better to use scheme level properties, though) - -Fri Sep 4 18:51:30 1998 Greg Badros - - * guile/Makefile: Use "perl" from path to run extract docs instead - of relying on #! line, and generate the -procedures.txt file as - well as the .sgml file - -Wed Sep 2 17:08:14 1998 Greg Badros - - * guile/cassowary_scm.cc, guile/cassowary_scm.hpp: Added - ClStayConstraint wrapper. Make cl-add-stay, cl-add-editvar take a - list of variables instead of a varargs last argument and instead - add two optional arguments STRENGTH and FACTOR (thus those - primitives remain backward compatible as long as only one variable - was given). - -Wed Sep 2 13:55:37 1998 Greg Badros - - * ClSimplexSolver.h: Added weight option to addEditVar and use it - - * ClLinearExpression.h: Added PconstClAbstractVariable, use it; - use ClVarToCoeffMap in coefficientFor. - -Thu Aug 6 20:56:45 1998 Greg Badros - - * Release v0.2. - -Thu Aug 6 20:41:40 1998 Greg Badros - - * ClTests.cc: Added multiedit() test for testing nested - beginEdit-s - - * ClSimplexSolver.h, ClSimplexSolver.cc: Support nested - beginEdit-s -- use removeEditVarsTo(n), and rewrite - removeAllEditVars in terms of the former; Use FIsSatisfied on - constraint and compare with testing internally for - FIsConstraintSatisfied() -- untested. - - * ClLinearInequality.h, ClLinearEquation.h, ClConstraint.h: Added - virtual FIsSatisfied - - * ClLinearExpression.h, ClLinearExpression.cc: Added evaluate() - - * ClAbstractVariable.h: Return 0 for value(), and make it a - virtual function. - -Wed Aug 5 16:10:56 1998 Greg Badros - - * ClStrength.h: Have ClStrength::symbolicWeight return a const - ref, instead of by value, make clsXXX const refs. - - * ClSimplexSolver.cc, ClLinearInequality.cc, ClLinearEquation.cc, - ClLinearConstraint.cc: Take ClStrengths by const refs - -Tue Aug 4 15:22:08 1998 Greg Badros - - * guile/cassowary_scm.cc, cassowary_scm.hpp: Move all inline - functions into .hpp file. Added cl-is-constraint-satisfied? - - * ClTableau.h: Added a rowExpression() const memfn, for - FIsConstraintSatisfied() - - * ClSimplexSolver.h, ClSimplexSolver.cc: Added (probably broken) - FIsConstraintSatisfied(cn) memfn -- needs testing - -Sun Aug 2 16:49:34 1998 Greg Badros - - * ClSimplexSolver.h: Added ConstraintMap() accessor to - _markerVars, for cl-constraint-list guile primitive - - * ClConstraint.h: Added setPv(), Pv(), and _pv field to a - constraint, for attaching extra information. - -Thu Jul 30 19:15:40 1998 Greg Badros - - * ClTests.cc: Added simple2, to test new EditMisuse exception on - editing a variable that is nowhere in the solver. - - * ClTableau.h, ClTableau.cc: Be more careful about inserting into - _externalParametricVars; add FIsBasicVar to assist that care. - - * ClSimplexSolver.cc, ClSimplexSolver.h: Added pfnCnSatCallback -- - does nothing for now; throw an ExCLEditMisuse exception if an - edit constraint is added on a variable that is not in the tableau - (needs at least a stay constraint in the solver); replace some - calls to rowExpression with FIsBasicVar when the latter is the - intent. - -Thu Jul 21 Greg Badros - - * ClVariable.h, ClVariable.cc: Added _pv field, settor and gettor. - - -ABOVE CHANGES ONLY IN C++ IMPLEMENTATION AND ITS WRAPPERS - -Fri Jul 17 19:24:54 1998 Greg Badros - - * ClVariable.h, .java: Added change_value memfn, and make it virtual - instead of setValue -- thus subclasses can specialize behaviour - when the variable gets set by the solver. - - * ClSimplexSolver.h, .java: Use change_value for setEditedValue if - the variable is not in the tableau; call resolve() before - removeAllEditVars in endEdit - - * ClSimplexSolver.cc, .java (setExternalVariables): Use change_value - instead of set_value when so subclasses can override and notice a - changed variable - -Thu Jul 16 19:49:45 1998 Greg Badros - - * Added setEditedValue(), FContainsVariable(), and addVar() to c++ - and Java implementations - - * Fixed bug in C++ and Java in solvers lacking stay constraints - that was due to not-updating the external parametric variables - set. - -Fri Jul 10 09:00:15 1998 Greg Badros - - * Fixed bug whereby a dummy variable was being pivoted into the - basis because pexpr->anyVariable() didn't guarantee the variable - it returned was a pivotable variable -- now it's called - anyPivotableVariable(), and does the right thing. - - * Fixed bug whereby column mappings that had no rows remained in - the list of columns -- now erase the column key when its value is - the empty set - - * Fixed bug whereby constraints that threw required failure - exceptions remained in the tableau (a removeConstraint on a - constraint that failed to be added used to succeed, now it does - not) - -Monday Jun 29 16:50:00 1998 Greg Badros - - * Release Cassowary v0.1 --- see local/POST-ANNOUNCE-TO for - list of places where it was announced - diff --git a/libs/cassowary/ClAbstractVariable.cc b/libs/cassowary/ClAbstractVariable.cc deleted file mode 100644 index b5502d4fbb..0000000000 --- a/libs/cassowary/ClAbstractVariable.cc +++ /dev/null @@ -1,23 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClAbstractVariable.cc - -#include - -#ifdef HAVE_CONFIG_H -#include -#define CONFIG_H_INCLUDED -#endif - -long ClAbstractVariable::iVariableNumber = 0; -#ifdef CL_FIND_LEAK -long ClAbstractVariable::cAbstractVariables = 0; -#endif - diff --git a/libs/cassowary/ClBug0.cc b/libs/cassowary/ClBug0.cc deleted file mode 100644 index 09ca1826cb..0000000000 --- a/libs/cassowary/ClBug0.cc +++ /dev/null @@ -1,102 +0,0 @@ -// $Id$ - -#include - -/* This bug fixed --02/15/99 gjb - Replaced the parallel vectors for edit constraints - (the errorPlus..., errorMinus..., prevEditConstants vectors) - with a ClEditInfo class that is the Value of the _editVarMap map. - - Later I realized that I need to go to a _editVars list so that - multiple edits on the same variable that nest are handled properly. - --09/19/99 gjb -*/ - -int main() -{ - ClSimplexSolver solver; - - ClVariable x("x",7); - ClVariable y("y",8); - ClVariable z("z",9); - - solver - .AddStay(x) - .AddStay(y) - .AddStay(z); - - try { - solver.AddEditVar(x); - solver.AddEditVar(y); - solver.AddEditVar(z); - solver.BeginEdit(); - - solver.SuggestValue(x,1); - solver.SuggestValue(z,2); - - solver.RemoveEditVar(y); - - solver.SuggestValue(x,3); - solver.SuggestValue(z,4); - - solver.EndEdit(); - - } catch (ExCLError &e) { - cerr << e.description() << endl; - } - - cout << x << endl << y << endl << z < - To: - Subject: bugreport - Date: Thu, 1 Oct 1998 11:40:55 +0200 - Message-Id: <000001bded1f$973a2060$230e1fac@itc_mk.sbcs.swissbank.com> - Mime-Version: 1.0 - Content-Type: text/plain; - charset="iso-8859-1" - Content-Transfer-Encoding: 7bit - X-Priority: 3 (Normal) - X-Msmail-Priority: Normal - X-Mailer: Microsoft Outlook 8.5, Build 4.71.2173.0 - Importance: Normal - X-Mimeole: Produced By Microsoft MimeOLE V4.72.2106.4 - - Dear Mr Noth, - - I am currently working with the Java implementation of Cassowary and found - the following bug: - - If I Add several editConstraints, remove some of them again later and - perform a 'ClSimplexSolver.SuggestValue()', the indices of - 'ClConstraintAndIndex' in the variable 'cai' are sometimes wrong (see - ClSimplexSolver.SuggestValue(ClVariable v, double x), the 3rd line). This is - because if you remove an element from a 'java.util.Vector', and the element - is somewhere in the middle of the Vector, the indices of the Vector change. - (see java.util.Vector.removeElementAt(int index): - - public final synchronized void removeElementAt(int index) { - if (index >= elementCount) { - throw new ArrayIndexOutOfBoundsException(index + " >= " + - elementCount); - } - else if (index < 0) { - throw new ArrayIndexOutOfBoundsException(index); - } - int j = elementCount - index - 1; - if (j > 0) { - System.arraycopy(elementData, index + 1, elementData, index, j); - } - elementCount--; - elementData[elementCount] = null; /* to let gc do its work */ - } - - - My workaround now is, that everytime when I remove an EditVariable from the - Solver, I have to remove all the EditVariables and Add then the ones again, - that I do not want to remove. - -#endif diff --git a/libs/cassowary/ClBug1.cc b/libs/cassowary/ClBug1.cc deleted file mode 100644 index e7543757e3..0000000000 --- a/libs/cassowary/ClBug1.cc +++ /dev/null @@ -1,21 +0,0 @@ -#include - -int main() -{ - ClVariable *var = new ClVariable(); - ClSimplexSolver *solver = new ClSimplexSolver(); - ClStayConstraint *stcn = new ClStayConstraint(*var,ClsWeak(),1.0); - - cout << *solver; - solver->AddConstraint(*stcn); - cout << *solver; - solver->RemoveConstraint(*stcn); - cout << *solver; -} -/* -The result is a segmentation fault when the constraint is removed. I -don't understand why. - -Anthony Beurive'" -*/ - diff --git a/libs/cassowary/ClBug2.cc b/libs/cassowary/ClBug2.cc deleted file mode 100644 index 3a1e424259..0000000000 --- a/libs/cassowary/ClBug2.cc +++ /dev/null @@ -1,130 +0,0 @@ -/* $Id$ - -From: "Anthony Beurive'" -Subject: cassowary -To: gjb@cs.washington.edu -Date: Tue, 9 Mar 1999 12:42:24 +0100 (CET) - -I believe there's a bug in cassowary. It seems to be related to the -previous one I encountered a while ago, concerning the removal of -constraints. - -The three following examples may help you to track the bug, I hope. - --------------------------------------------------------------------------------- -#include "Cl.h" - -void main() -{ - ClSimplexSolver *solver = new ClSimplexSolver(); - ClVariable *var = new ClVariable(); - ClStayConstraint *stcn = new ClStayConstraint(*var,ClsWeak(),1.0); - - solver->AddConstraint(*stcn); - cout << *solver; - solver->RemoveConstraint(*stcn); - cout << *solver; -} --------------------------------------------------------------------------------- -This works fine. - - -Now, the factor of the stay constraint is changed. --------------------------------------------------------------------------------- -#include "Cl.h" - -void main() -{ - ClSimplexSolver *solver = new ClSimplexSolver(); - ClVariable *var = new ClVariable(); - ClStayConstraint *stcn = new ClStayConstraint(*var,ClsWeak(),2.0); - - solver->AddConstraint(*stcn); - cout << *solver; - solver->RemoveConstraint(*stcn); - cout << *solver; -} --------------------------------------------------------------------------------- -The result is: -test2: ClSimplexSolver.cc:1199: void ClSimplexSolver::Optimize(class ClVariable): Assertion \ -`pzRow != __null' failed. -Aborted - - -Now, the solver is created after the variable. --------------------------------------------------------------------------------- -#include "Cl.h" - -void main() -{ - ClVariable *var = new ClVariable(); - ClSimplexSolver *solver = new ClSimplexSolver(); - ClStayConstraint *stcn = new ClStayConstraint(*var,ClsWeak(),2.0); - - solver->AddConstraint(*stcn); - cout << *solver; - solver->RemoveConstraint(*stcn); - cout << *solver; -} --------------------------------------------------------------------------------- -This works again. - - -Can you reproduce the same results? Maybe the cause is my c++ -compiler (egcs-2.90.29 980515 (egcs-1.0.3 release)). I don't know. - -*/ - -#include - -void foo1() -{ - ClSimplexSolver *solver = new ClSimplexSolver(); - ClVariable *var = new ClVariable(); - ClStayConstraint *stcn = new ClStayConstraint(*var,ClsWeak(),1.0); - - solver->AddConstraint(*stcn); - cout << *solver; - solver->RemoveConstraint(*stcn); - cout << *solver; -} - - -void foo2() -{ - ClSimplexSolver *solver = new ClSimplexSolver(); - ClVariable *var = new ClVariable(); - ClStayConstraint *stcn = new ClStayConstraint(*var,ClsWeak(),2.0); - - solver->AddConstraint(*stcn); - cout << *solver; - solver->RemoveConstraint(*stcn); - cout << *solver; -} - - -void foo3() -{ - ClVariable *var = new ClVariable(); - ClSimplexSolver *solver = new ClSimplexSolver(); - ClStayConstraint *stcn = new ClStayConstraint(*var,ClsWeak(),2.0); - - solver->AddConstraint(*stcn); - cout << *solver; - solver->RemoveConstraint(*stcn); - cout << *solver; -} - - -int main() -{ - cerr << "Test1: " << endl; - foo1(); - - cerr << "\nTest2: " << endl; - foo2(); - - cerr << "\nTest3: " << endl; - foo3(); - -} diff --git a/libs/cassowary/ClConstraint.cc b/libs/cassowary/ClConstraint.cc deleted file mode 100644 index 1bc6be91b3..0000000000 --- a/libs/cassowary/ClConstraint.cc +++ /dev/null @@ -1,32 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClConstraint.cc - -#include - -#ifdef HAVE_CONFIG_H -#include -#define CONFIG_H_INCLUDED -#endif - -#ifndef CL_NO_IO -#include // for VarSet printing - -ostream & -ClConstraint::PrintOn(ostream &xo) const -{ - // Note that the trailing "= 0)" or ">= 0)" is missing, as derived classes will - // print the right thing after calling this function - xo << strength() << " w{" << weight() << "} ta{" - << _times_added << "} RO" << _readOnlyVars << " " << "(" << Expression(); - return xo; -} - -#endif diff --git a/libs/cassowary/ClDummyVariable.cc b/libs/cassowary/ClDummyVariable.cc deleted file mode 100644 index e1e9b39c0c..0000000000 --- a/libs/cassowary/ClDummyVariable.cc +++ /dev/null @@ -1,12 +0,0 @@ -// $Id$ - -#include - -#ifdef HAVE_CONFIG_H -#include -#define CONFIG_H_INCLUDED -#endif - -#ifdef CL_FIND_LEAK -long ClDummyVariable::cDummyVariables = 0; -#endif diff --git a/libs/cassowary/ClFDBinaryOneWayConstraint.cc b/libs/cassowary/ClFDBinaryOneWayConstraint.cc deleted file mode 100644 index e7bf7f1089..0000000000 --- a/libs/cassowary/ClFDBinaryOneWayConstraint.cc +++ /dev/null @@ -1,140 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClFDBinaryOneWayConstraint.cc - - -#ifdef HAVE_CONFIG_H -#include -#define CONFIG_H_INCLUDED -#endif - -#include -#include -#include -#include - - -void -ClFDBinaryOneWayConstraint::EnsurePreconditionsForCn(const ClConstraint &cn) -{ - ClVarSet setRO = cn.ReadOnlyVars(); - if (setRO.size() > 1) - throw ExCLTooDifficultSpecial("Only 0 or 1 read only variables are allowed"); - const ClLinearExpression &expr = cn.Expression(); - const ClVarToNumberMap &terms = expr.Terms(); - if (terms.size() > 2) - throw ExCLTooDifficultSpecial("Cannot have more than 2 variables"); - if (terms.size() == 0) - throw ExCLTooDifficultSpecial("Must have at least 1 variable"); - if (terms.size() == 2 && setRO.size() == 0) - throw ExCLTooDifficultSpecial("Both variables cannot be read-write, one must be read-only"); - if (terms.size() == 1 && setRO.size() == 1) - throw ExCLTooDifficultSpecial("Single read-only variable in LinearConstraint -- must not be read-only."); - ClVariable clv = (*terms.begin()).first; - /* GJB:FIXME:: iterate over all the variables */ - if (!clv->IsFDVariable()) { - throw ExCLTooDifficultSpecial("FD constraint contains non-FD variables"); - } -} - -bool -ClFDBinaryOneWayConstraint::FCanConvertCn(const ClConstraint &cn) -{ - try { - EnsurePreconditionsForCn(cn); - return true; - } catch (...) { - return false; - } -} - - -ClFDBinaryOneWayConstraint::ClFDBinaryOneWayConstraint(const ClConstraint &cn) - :ClFDConstraint(cn.strength(), cn.weight()) -{ - EnsurePreconditionsForCn(cn); - list l; - /* GJB:FIXME:: varargs inteface, with sentinel as first arg? */ - l.push_back(9); - l.push_back(10); - l.push_back(12); - l.push_back(14); - l.push_back(20); - - ClVarSet setRO = cn.ReadOnlyVars(); - - ClVariable clvRO = clvNil; - ClVariable clvROLinear = clvNil; - Number coeffRO = 0; - - ClVariable clvRW = clvNil; - Number coeffRW = 0; - - if (setRO.size() == 1) { - const ClVariable &clv = *(setRO.begin()); - if (clv->IsFDVariable()) - clvRO = clv; - else - clvRO = new ClFDVariable(clv.Name(),clv.IntValue(),l); - clvROLinear = clv; - } - const ClLinearExpression &expr = cn.Expression(); - const ClVarToNumberMap &terms = expr.Terms(); - - for (ClVarToNumberMap::const_iterator it = terms.begin(); - it != terms.end(); - ++it) { - ClVariable clv = (*it).first; - if (clv == clvROLinear) { - coeffRO = (*it).second; - } else { - if (clv->IsFDVariable()) - clvRW = clv; - else - clvRW = new ClFDVariable(clv.Name(),clv.Value(),l); - coeffRW = (*it).second; - } - } - assert(!clvRW.IsNil()); - if (coeffRW == 0) { - throw ExCLTooDifficultSpecial("RW variable's coefficient must be non-zero"); - } - - bool fInequality = cn.IsInequality(); - bool fStrictInequality = cn.IsStrictInequality(); - double rhs_constant = expr.Constant(); - - // now we have: - // coeffRW * clvRW + coeffRO * clvRO rhs_constant - // where is >= if fInequality, or = if !fInequality - // - // need: - // clvRW coefficient * clvRO + constant - // - // so: - // coefficient = -coeffRO/coeffRW - // constant = rhs_constant/coeffRW - - if (fStrictInequality) - _rel = cnGT; - else if (fInequality) - _rel = cnGEQ; - else - _rel = cnEQ; - - if (coeffRW < 0) - _rel = ReverseInequality(_rel); - - _coefficient = -coeffRO/coeffRW; - _constant = -rhs_constant/coeffRW; - _vRW = clvRW; - _vRO = clvRO; - return; -} diff --git a/libs/cassowary/ClFDConnectorVariable.cc b/libs/cassowary/ClFDConnectorVariable.cc deleted file mode 100644 index e6618eb9d4..0000000000 --- a/libs/cassowary/ClFDConnectorVariable.cc +++ /dev/null @@ -1,29 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClFDConnectorVariable.cc - -#include -#include // for list printing - -#ifdef HAVE_CONFIG_H -#include -#define CONFIG_H_INCLUDED -#endif - -// Use < > for ClFDConnector-s, instead of [ ] -#ifndef CL_NO_IO -ostream &ClFDConnectorVariable::PrintOn(ostream &xo) const -{ - xo << "<" << Name() << "=" << Value() - << "{" << _clvFloat << "}" - << ":" << *PlfdnDomain() << ">"; - return xo; -} -#endif diff --git a/libs/cassowary/ClFDSolver.cc b/libs/cassowary/ClFDSolver.cc deleted file mode 100644 index 7f2d199869..0000000000 --- a/libs/cassowary/ClFDSolver.cc +++ /dev/null @@ -1,364 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClFDSolver.cc - - -#ifdef HAVE_CONFIG_H -#include -#define CONFIG_H_INCLUDED -#endif - -#include -#include -#include -#include -#include -#include -#include -#include -#include - -static int fDebugFDSolve; - -ClFDSolver & -ClFDSolver::AddConstraint(ClConstraint *const pcn) -{ - AddConstraintInternal(pcn); - if (_fAutosolve) Solve(); - return *this; -} - -ClFDSolver & -ClFDSolver::RemoveConstraint(ClConstraint *const pcn) -{ - RemoveConstraintInternal(pcn); - if (_fAutosolve) Solve(); - return *this; -} - -ClFDSolver & -ClFDSolver::AddConstraintInternal(ClConstraint *const pcn) -{ -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); - cerr << "(" << *pcn << ")" << endl; -#endif - - ClFDBinaryOneWayConstraint *const pcnfd = - dynamic_cast(pcn); - if (!pcnfd) { - throw ExCLTooDifficultSpecial("Can only add ClFDBinaryOneWayConstraint-s to ClFDSolvers"); - } - ClVariable rw = pcnfd->ClvRW(); - ClVariable ro = pcnfd->ClvRO(); - if (!rw.IsFDVariable()) { - throw ExCLTooDifficultSpecial("RW variable must be an FDVariable"); - } - if (!(ro.IsNil() || ro.IsFDVariable())) { - throw ExCLTooDifficultSpecial("RO variable must be an FDVariable or clvNil"); - } - // add the constraint to our set of cns - _setCns.insert(pcn); - // and add the constraint to the cns that affect var rw - assert(!rw.IsNil()); - _mapClvToCns[rw].insert(pcn); - - - node nRw = GetVarNode(rw); - if (!ro.IsNil()) { - node nRo = GetVarNode(ro); - edge e = G.new_edge(nRo, nRw); - - _mapCnToEdge[pcn] = e; - - if (!G.is_acyclic()) { - /* there is a cycle... give up after cleaning up */ - RemoveConstraint(pcn); - throw ExCLCycleNotAllowed(); - } - } - return *this; -} - -ClFDSolver & -ClFDSolver::RemoveConstraintInternal(ClConstraint *const pcn) -{ -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); - cerr << "(" << *pcn << ")" << endl; -#endif - - ClFDBinaryOneWayConstraint *const pcnfd = - dynamic_cast(pcn); - - if (!pcnfd) { - throw ExCLInternalError("Could not downcast to a ClFDBinaryOneWayConstraint"); - } - - ClConstraintSet::iterator itCn = _setCns.find(pcnfd); - if (itCn == _setCns.end()) { - throw ExCLConstraintNotFound(); - } - _setCns.erase(itCn); - - ClVariable rw = pcnfd->ClvRW(); - ClVariable ro = pcnfd->ClvRO(); - ClConstraintSet &_cnsAffectingRW = _mapClvToCns[rw]; - ClConstraintSet::iterator it = _cnsAffectingRW.find(pcnfd); - if (it == _cnsAffectingRW.end()) { - throw ExCLInternalError("Cannot find pcnfd"); - } - _cnsAffectingRW.erase(it); - - if (!ro.IsNil()) { - edge e = _mapCnToEdge[pcn]; - G.del_edge(e); - _mapCnToEdge.erase(pcn); - - if (_mapVarToNode.find(ro) != _mapVarToNode.end() && - _mapVarToNode[ro].degree() == 0) { - G.del_node(_mapVarToNode[ro]); - _mapVarToNode.erase(ro); - } - } - if (_mapVarToNode.find(rw) != _mapVarToNode.end() && - _mapVarToNode[rw].degree() == 0) { - G.del_node(_mapVarToNode[rw]); - _mapVarToNode.erase(rw); - } - if (_mapClvToCns[rw].size() == 0) { - _mapClvToCns.erase(rw); - } - - return *this; -} - -ClFDSolver & -ClFDSolver::Solve() -{ - topsort t; - t.run(G); - topsort::topsort_iterator it = t.top_order_begin(); - topsort::topsort_iterator end = t.top_order_end(); - ClSymbolicWeight errorTotal; - ResetSetFlagsOnVariables(); - for (; it != end; ++it) { - ClVariable clv = nodeToVar[*it]; - ClFDVariable *pcldv = dynamic_cast(clv.get_pclv()); -#ifndef NO_FDSOLVE_DEBUG - if (fDebugFDSolve) { - if (!clv.IsNil()) cout << "node " << (*it) << " is " << clv << endl; - cerr << "Set from: " << endl; - for (ClConstraintSet::iterator itCns = _mapClvToCns[clv].begin(); - itCns != _mapClvToCns[clv].end(); - ++itCns) { - const ClConstraint *pcn = *itCns; - cerr << *pcn << endl; - } - cerr << endl; - } -#endif - pair p = ComputeBest(pcldv); - ClSymbolicWeight e = p.first; - FDNumber v = p.second; - if (v == FDN_NOTSET) - throw ExCLRequiredFailure(); - pcldv->ChangeValue(v); - pcldv->SetFIsSet(true); - errorTotal += e; - } - return *this; -} - -/* return the best (lowest) incremental error and the value - at which that error occurs */ -pair -ClFDSolver::ComputeBest(ClFDVariable *pcldv) -{ - assert(pcldv); - // assert(!pcldv->FIsSet()); //GJB:FIXME:: - ClSymbolicWeight minError = ClsRequired().symbolicWeight(); - FDNumber bestValue = FDN_NOTSET; - // ClVariable clv(pcldv); - // for each domain value - for (list::const_iterator itVal= pcldv->PlfdnDomain()->begin(); - itVal != pcldv->PlfdnDomain()->end(); - ++itVal) { - FDNumber value = *itVal; - ClSymbolicWeight error; - const ClConstraintSet &setCns = _mapClvToCns[pcldv]; - // for each constraint affecting *pcldv - for (ClConstraintSet::const_iterator itCn = setCns.begin(); - itCn != setCns.end(); - ++itCn) { - const ClConstraint *pcn = *itCn; - ClSymbolicWeight e = ErrorForClvAtValSubjectToCn(pcldv,value,*pcn); - error += e; - } - // now error is the total error for binding clv <- value - if (error < minError) { - minError = error; - bestValue = value; - } - } - // now minError is the lowest error we can get for clv - // and it occurs binding clv <- bestValue - if (bestValue == FDN_NOTSET) - throw ExCLRequiredFailure(); - return pair(minError,bestValue); -} - -ClSymbolicWeight -ClFDSolver::ErrorForClvAtValSubjectToCn(ClFDVariable *pcldv,FDNumber value,const ClConstraint &cn) -{ - const ClFDBinaryOneWayConstraint *pcnFd = dynamic_cast(&cn); - if (!pcnFd) throw ExCLInternalError("Not a binary FD constraint."); - ClCnRelation rel = pcnFd->Relation(); - double m = pcnFd->Coefficient(); - double b = pcnFd->Constant(); - ClVariable rw = pcnFd->ClvRW(); - ClVariable ro = pcnFd->ClvRO(); - assert(rw.get_pclv() == pcldv); - double e; - double x = ro.IsNil()? 0 : ro.Value(); - // return the error in satisfying: - // value REL m*x + b - double rhs = m*x + b; - switch (rel) { - case cnLEQ: - if (value <= rhs) e = 0; - else e = 1 + value-rhs; - break; - case cnLT: - if (value < rhs) e = 0; - else e = 1 + value-rhs; - break; - case cnGEQ: - if (value >= rhs) e = 0; - else e = 1+ rhs-value; - break; - case cnGT: - if (value > rhs) e = 0; - else e = 1 + rhs-value; - break; - case cnEQ: - if (value == rhs) e = 0; - else e = 1 + fabs(rhs-value); - break; - case cnNEQ: - if (value != rhs) e = 0; - else e = 1; /* GJB:FIXME:: what makes sense here? */ - break; - default: - e = 0; /* quiet warning */ - assert(false); - } - - ClSymbolicWeight err; - if (cn.IsRequired() && e > 0) - err = ClsRequired().symbolicWeight(); - else - err = cn.symbolicWeight() * (e*cn._weight); -#ifndef NO_FDSOLVE_DEBUG - if (fDebugFDSolve) { - cerr << "Error at " << value << " = " << err << endl; - } -#endif - return err; -} - - -ClFDSolver & -ClFDSolver::ShowSolve() -{ - topsort t; - t.run(G); - topsort::topsort_iterator it = t.top_order_begin(); - topsort::topsort_iterator end = t.top_order_end(); - for (; it != end; ++it) { - ClVariable clv = nodeToVar[*it]; - if (!clv.IsNil()) cout << "Node " << (*it) << " is " << clv << endl; - cout << "Set from: " << endl; - for (ClConstraintSet::iterator itCns = _mapClvToCns[clv].begin(); - itCns != _mapClvToCns[clv].end(); - ++itCns) { - const ClConstraint *pcn = *itCns; - cout << *pcn << endl; - } - cout << endl; - } - return *this; -} - - -/* Turn all FDVariable FIsSet() flags to false */ -void -ClFDSolver::ResetSetFlagsOnVariables() -{ - for (ClVarToConstraintSetMap::iterator it = _mapClvToCns.begin(); - it != _mapClvToCns.end(); - ++it) { - ClVariable clv = (*it).first; - ClFDVariable *pcldv = dynamic_cast(clv.get_pclv()); - assert(pcldv); - pcldv->SetFIsSet(false); - } -} - - -ostream & -ClFDSolver::PrintOn(ostream &xo) const -{ - xo << "FDSolver: " - << _setCns - << "Graph nodes, edges = " << G.number_of_nodes() << ", " << G.number_of_edges() - << endl; - return xo; -} - -ostream & -ClFDSolver::PrintInternalInfo(ostream &xo) const -{ return xo; } - - -ostream &operator<<(ostream &xo, const ClFDSolver &clfds) -{ return clfds.PrintOn(xo); } - - -//// protected member functions - -/* Create node for v in G, if necessary, - otherwise return the node we already created. */ -node -ClFDSolver::GetVarNode(ClVariable v) -{ - ClMap::iterator it = _mapVarToNode.find(v); - if (it == _mapVarToNode.end()) { - node n = G.new_node(); - _mapVarToNode[v] = n; - nodeToVar[n] = v; - return n; - } else { - return (*it).second; - } -} - - -void -ListPushOnto(list *pl, ...) -{ - va_list ap; - va_start(ap, pl); - FDNumber n; - while ( (n = va_arg(ap, FDNumber)) != FDN_EOL) { - pl->push_back(n); - } - va_end(ap); -} diff --git a/libs/cassowary/ClFDVariable.cc b/libs/cassowary/ClFDVariable.cc deleted file mode 100644 index 5ab9d518b1..0000000000 --- a/libs/cassowary/ClFDVariable.cc +++ /dev/null @@ -1,27 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClFDVariable.cc - -#include -#include // for list printing - -#ifdef HAVE_CONFIG_H -#include -#define CONFIG_H_INCLUDED -#endif - -// Use < > for ClFDVariable-s, instead of [ ] -#ifndef CL_NO_IO -ostream &ClFDVariable::PrintOn(ostream &xo) const -{ - xo << "<" << Name() << "=" << Value() << ":" << *PlfdnDomain() << ">"; - return xo; -} -#endif diff --git a/libs/cassowary/ClFloatVariable.cc b/libs/cassowary/ClFloatVariable.cc deleted file mode 100644 index a3096e4b08..0000000000 --- a/libs/cassowary/ClFloatVariable.cc +++ /dev/null @@ -1,25 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClFloatVariable.cc - -#include - -#ifdef HAVE_CONFIG_H -#include -#define CONFIG_H_INCLUDED -#endif - -#ifndef CL_NO_IO -ostream &ClFloatVariable::PrintOn(ostream &xo) const -{ - xo << "[" << Name() << ":" << _value << "]"; - return xo; -} -#endif diff --git a/libs/cassowary/ClLinearExpression.cc b/libs/cassowary/ClLinearExpression.cc deleted file mode 100644 index 72383ffec1..0000000000 --- a/libs/cassowary/ClLinearExpression.cc +++ /dev/null @@ -1,473 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClLinearExpression.cc - -using namespace std; - -#include -#include /// needed only to instantiate with T=ClSymbolicWeight -#include -#include -#include - -#ifdef HAVE_CONFIG_H -#include -#define CONFIG_H_INCLUDED -#endif - -template -ClGenericLinearExpression::ClGenericLinearExpression(T num) : - _constant(num) -{ } - -// Convert from ClVariable to a ClLinearExpression -// this replaces ClVariable::asLinearExpression -template -ClGenericLinearExpression::ClGenericLinearExpression(ClVariable clv, T value, - T Constant) : - _constant(Constant) -{ - _terms[clv] = value; -} - -template -ClGenericLinearExpression::~ClGenericLinearExpression() -{ } - -#ifndef CL_NO_IO -template -ostream & -ClGenericLinearExpression::PrintOn(ostream &xo) const -{ - typename ClVarToCoeffMap::const_iterator i = _terms.begin(); - - if (!ClApprox(_constant,0.0) || i == _terms.end()) - { - xo << _constant; - } - else - { - if (i == _terms.end()) - return xo; - xo << (*i).second << "*" << (*i).first; - ++i; - } - for ( ; i != _terms.end(); ++i) - { - xo << " + " << (*i).second << "*" << (*i).first; - } - return xo; -} -#endif - - - -// Destructively multiply self by x. -// (private memfn) -template -ClGenericLinearExpression & -ClGenericLinearExpression::MultiplyMe(T x) -{ - _constant *= x; - - typename ClVarToCoeffMap::const_iterator i = _terms.begin(); - for ( ; i != _terms.end(); ++i) - { - _terms[(*i).first] = (*i).second * x; - } - return *this; -} - -// Return a new linear expression formed by multiplying self by x. -// (Note that this result must be linear.) -template -ClGenericLinearExpression -ClGenericLinearExpression::Times(Number x) const -{ - ClGenericLinearExpression result = *this; - return result.MultiplyMe(x); -} - -// Return a new linear expression formed by multiplying self by x. -// (Note that this result must be linear.) -// The above function optimizes the specific case of multiplying -// by a Constant, here is the more general case -template -ClGenericLinearExpression -ClGenericLinearExpression::Times(const ClGenericLinearExpression &expr) const -{ - if (IsConstant()) - { - return expr.Times(_constant); - } - else if (!expr.IsConstant()) - { - // neither are constants, so we'd introduce non-linearity - throw ExCLNonlinearExpression(); - } - return Times(expr._constant); -} - - -// Return a new linear expression formed by adding x to self. -template -ClGenericLinearExpression -ClGenericLinearExpression::Plus(const ClGenericLinearExpression &expr) const -{ - ClGenericLinearExpression result = *this; - result.AddExpression(expr,1.0); - return result; -} - -// Return a new linear expression formed by subtracting x from self. -template -ClGenericLinearExpression -ClGenericLinearExpression::Minus(const ClGenericLinearExpression &expr) const -{ - ClGenericLinearExpression result = *this; - result.AddExpression(expr,-1.0); - return result; -} - -// Return a new linear expression formed by dividing self by x. -// (Note that this result must be linear.) -template -ClGenericLinearExpression -ClGenericLinearExpression::Divide(Number x) const -{ - if (ClApprox(x,0.0)) - { - throw ExCLNonlinearExpression(); - } - return Times(1.0/x); -} - -// Return a new linear expression formed by dividing self by x. -// (Note that this result must be linear.) -template -ClGenericLinearExpression -ClGenericLinearExpression::Divide(const ClGenericLinearExpression &expr) const -{ - if (!expr.IsConstant()) - { - throw ExCLNonlinearExpression(); - } - return Divide(expr._constant); -} - - -// Return a new linear expression (expr/this). Since the result -// must be linear, this is permissible only if 'this' is a Constant. -template -ClGenericLinearExpression -ClGenericLinearExpression::DivFrom(const ClGenericLinearExpression &expr) const -{ - if (!IsConstant() || ClApprox(_constant,0.0)) - { - throw ExCLNonlinearExpression(); - } - return expr.Divide(_constant); -} - -// Add n*expr to this expression for another expression expr. -template -ClGenericLinearExpression & -ClGenericLinearExpression::AddExpression(const ClGenericLinearExpression &expr, Number n) -{ - IncrementConstant(expr.Constant()*n); - - typename ClVarToCoeffMap::const_iterator i = expr._terms.begin(); - for ( ; i != expr._terms.end(); ++i) - { - AddVariable((*i).first, (*i).second * n); - } - return *this; -} - -// Add n*expr to this expression for another expression expr. -// Notify the solver if a variable is added or deleted from this -// expression. -template -ClGenericLinearExpression & -ClGenericLinearExpression::AddExpression(const ClGenericLinearExpression &expr, Number n, - ClVariable subject, - ClTableau &solver) -{ - IncrementConstant(expr.Constant() * n); - - typename ClVarToCoeffMap::const_iterator i = expr._terms.begin(); - for ( ; i != expr._terms.end(); ++i) - { - AddVariable((*i).first, (*i).second * n, subject, solver); - } - return *this; -} - -// Add a term c*v to this expression. If the expression already -// contains a term involving v, Add c to the existing coefficient. -// If the new coefficient is approximately 0, delete v. -template -ClGenericLinearExpression & -ClGenericLinearExpression::AddVariable(ClVariable v, T c) -{ // body largely duplicated below -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); - cerr << "(" << v << ", " << c << ")" << endl; -#endif - typename ClVarToCoeffMap::iterator i = _terms.find(v); - if (i != _terms.end()) - { - // expression already contains that variable, so Add to it - T new_coefficient = 0; - new_coefficient = (*i).second + c; - if (ClApprox(new_coefficient,0.0)) - { - // new coefficient is Zero, so erase it - _terms.erase(i); - } - else - { - (*i).second = new_coefficient; - } - } - else // expression did not contain that variable - { - if (!ClApprox(c,0.0)) - { - _terms[v] = c; - } - } - return *this; -} - -// Add a term c*v to this expression. If the expression already -// contains a term involving v, Add c to the existing coefficient. -// If the new coefficient is approximately 0, delete v. Notify the -// solver if v appears or disappears from this expression. -template -ClGenericLinearExpression & -ClGenericLinearExpression::AddVariable(ClVariable v, T c, - ClVariable subject, - ClTableau &solver) -{ // body largely duplicated above -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); - cerr << "(" << v << ", " << c << ", " << subject << ", ...)" << endl; -#endif - typename ClVarToCoeffMap::iterator i = _terms.find(v); - if (i != _terms.end()) - { - // expression already contains that variable, so Add to it - T new_coefficient = (*i).second + c; - if (ClApprox(new_coefficient,0.0)) - { - // new coefficient is Zero, so erase it - solver.NoteRemovedVariable((*i).first,subject); - _terms.erase(i); - } - else - { - (*i).second = new_coefficient; - } - } - else // expression did not contain that variable - { - if (!ClApprox(c,0.0)) - { - _terms[v] = c; - solver.NoteAddedVariable(v,subject); - } - } -#ifdef CL_TRACE - cerr << "Now *this == " << *this << endl; -#endif - return *this; -} - -// Return a variable in this expression. (It is an error if this -// expression is Constant -- signal ExCLInternalError in that case). -template -ClVariable -ClGenericLinearExpression::AnyPivotableVariable() const -{ - if (IsConstant()) - { - throw ExCLInternalError("(ExCLInternalError) No pivotable variables in Constant expression"); - } - typename ClVarToCoeffMap::const_iterator i = _terms.begin(); - for ( ; i != _terms.end(); ++i) - { - ClVariable v = (*i).first; - if (v.IsPivotable()) - return v; - } - return clvNil; -} - -// Replace var with a symbolic expression expr that is equal to it. -// If a variable has been added to this expression that wasn't there -// before, or if a variable has been dropped from this expression -// because it now has a coefficient of 0, inform the solver. -// PRECONDITIONS: -// var occurs with a non-Zero coefficient in this expression. -template -void -ClGenericLinearExpression::SubstituteOut(ClVariable var, - const ClGenericLinearExpression &expr, - ClVariable subject, - ClTableau &solver) -{ -#ifdef CL_TRACE - cerr << "* ClGenericLinearExpression::"; - Tracer TRACER(__FUNCTION__); - cerr << "(" << var << ", " << expr << ", " << subject << ", " - << solver << ")" << endl; - cerr << "*this == " << *this << endl; -#endif - - typename ClVarToCoeffMap::iterator pv = _terms.find(var); - -#ifndef NDEBUG - if (pv == _terms.end()) - { -#ifndef CL_NO_IO - cerr << "SubstituteOut: pv != _terms.end()" << endl; - cerr << "(" << var << ", " << expr << ", " << subject << ", " - << ")" << endl; - cerr << "*this == " << *this << endl; -#endif - throw "SubstituteOut: pv != _terms.end()"; - } -#endif - assert(pv != _terms.end()); - // FIXGJB: this got thrown! assert(!ClApprox((*pv).second,0.0)); - - T multiplier = (*pv).second; - _terms.erase(pv); - IncrementConstant(multiplier * expr._constant); - typename ClVarToCoeffMap::const_iterator i = expr._terms.begin(); - for ( ; i != expr._terms.end(); ++i) - { - ClVariable v = (*i).first; - T c = (*i).second; - typename ClVarToCoeffMap::iterator poc = _terms.find(v); - if (poc != _terms.end()) - { // if oldCoeff is not nil -#ifdef CL_TRACE - cerr << "Considering (*poc) == " << (*poc).second << "*" << (*poc).first << endl; -#endif - // found it, so new coefficient is old one Plus what is in *i - T newCoeff = (*poc).second + (multiplier*c); - if (ClApprox(newCoeff,0.0)) - { - solver.NoteRemovedVariable((*poc).first,subject); - _terms.erase(poc); - } - else - { - (*poc).second = newCoeff; - } - } - else - { // did not have that variable already (oldCoeff == nil) -#ifdef CL_TRACE - cerr << "Adding (*i) == " << (*i).second << "*" << (*i).first << endl; -#endif - _terms[v] = multiplier * c; - solver.NoteAddedVariable(v,subject); - } - } -#ifdef CL_TRACE - cerr << "Now (*this) is " << *this << endl; -#endif -} - -// This linear expression currently represents the equation -// oldSubject=self. Destructively modify it so that it represents -// the equation NewSubject=self. -// -// Precondition: NewSubject currently has a nonzero coefficient in -// this expression. -// -// NOTES -// Suppose this expression is c + a*NewSubject + a1*v1 + ... + an*vn. -// -// Then the current equation is -// oldSubject = c + a*NewSubject + a1*v1 + ... + an*vn. -// The new equation will be -// NewSubject = -c/a + oldSubject/a - (a1/a)*v1 - ... - (an/a)*vn. -// Note that the term involving NewSubject has been dropped. -// -// Basically, we consider the expression to be an equation with oldSubject -// equal to the expression, then Resolve the equation for NewSubject, -// and destructively make the expression what NewSubject is then equal to -template -void -ClGenericLinearExpression::ChangeSubject(ClVariable old_subject, - ClVariable new_subject) -{ - _terms[old_subject] = NewSubject(new_subject); -} - -inline double ReciprocalOf(double n) -{ return 1.0/n; } - -// This linear expression currently represents the equation self=0. Destructively modify it so -// that subject=self represents an equivalent equation. -// -// Precondition: subject must be one of the variables in this expression. -// NOTES -// Suppose this expression is -// c + a*subject + a1*v1 + ... + an*vn -// representing -// c + a*subject + a1*v1 + ... + an*vn = 0 -// The modified expression will be -// subject = -c/a - (a1/a)*v1 - ... - (an/a)*vn -// representing -// subject = -c/a - (a1/a)*v1 - ... - (an/a)*vn = 0 -// -// Note that the term involving subject has been dropped. -// -// Returns the reciprocal, so that NewSubject can be used by ChangeSubject -template -T -ClGenericLinearExpression::NewSubject(ClVariable subject) -{ -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); - cerr << "(" << subject << ")" << endl; -#endif - typename ClVarToCoeffMap::iterator pnewSubject = _terms.find(subject); - assert(pnewSubject != _terms.end()); - // assert(!ClApprox((*pnewSubject).second,0.0)); - T reciprocal = ReciprocalOf((*pnewSubject).second); - _terms.erase(pnewSubject); - MultiplyMe(-reciprocal); - return reciprocal; -} - -template -T -ClGenericLinearExpression::Evaluate() const -{ - T answer = _constant; - typename ClVarToCoeffMap::const_iterator i = _terms.begin(); - - for ( ; i != _terms.end(); ++i) - { - ClVariable v = (*i).first; - answer += (*i).second * v.Value(); - } - return answer; -} - - -template class ClGenericLinearExpression; -// template class ClGenericLinearExpression; diff --git a/libs/cassowary/ClReader.ll b/libs/cassowary/ClReader.ll deleted file mode 100644 index 77fa13a5a1..0000000000 --- a/libs/cassowary/ClReader.ll +++ /dev/null @@ -1,87 +0,0 @@ -/* $Id$ - Cassowary Incremental Constraint Solver - Original Smalltalk Implementation by Alan Borning - This C++ Implementation by Greg J. Badros, - http://www.cs.washington.edu/homes/gjb - (C) 1998, 1999 Greg J. Badros and Alan Borning - See ../LICENSE for legal details regarding this software - - ClReader.l - Scanner for constraint parsing. - By Greg J. Badros - */ - -%{ -/* Get the token numbers that bison created for us - (uses the -d option of bison) */ - -#include -#include "ClReader.cc.h" - -#ifdef HAVE_CONFIG_H -#include -#define CONFIG_H_INCLUDED -#endif - -/* global variable for the istream we are reading from; - gets set by PcnParseConstraint */ -istream *pxi_lexer; - -/* Pass in an extra variable (ClParseData *) to cllex so that - it can look up variable names */ -#define YY_DECL int cllex(YYSTYPE *lvalp, void *YYLEX_PARAM) - -/* Make lexer reader from the global variable */ -#define YY_INPUT(buf,result,max_size) \ - do { if (pxi_lexer->get(buf[0]) && buf[0] > 0) result = 1; \ - else result = YY_NULL; } while (0) - -%} - -%option noyywrap - -DIGIT [0-9] -ALPHA [A-Za-z] -ALPHANUM [A-Za-z0-9] -ID_OK_PUNC [-_\[\]] -RO_ANNOTATION "?" -ID {ALPHA}({ALPHANUM}|{ID_OK_PUNC})*({RO_ANNOTATION})? -NUMID "{"{DIGIT}+"}" -ws [ \t\n]+ - -%% -{ws} /* skip whitespace */ -\n|";" { return 0; } -">=" { return GEQ; } -">" { return GT; } -"<=" { return LEQ; } -"<" { return LT; } -"==" { return '='; } -"="|"-"|"+"|"*"|"/"|"("|")" { return yytext[0]; } - -{DIGIT}+("."{DIGIT}*)? | -"."{DIGIT}+ { lvalp->num = strtod(yytext,0); return NUM; } - -{ID} { /* Lookup the variable name */ - ClParseData *pclpd = ((ClParseData *) YYLEX_PARAM); - int cch = strlen(yytext); - ClVariable *pclv = NULL; - bool fReadOnly = false; - if (yytext[cch-1] == '?') { - yytext[cch-1] = '\0'; - fReadOnly = true; - } - const string str = string(yytext); - pclv = pclpd->_lookup_func(str); - if (!pclv->IsNil()) { - lvalp->pclv = pclv; - return fReadOnly?RO_VAR:VAR; - } else { - pxi_lexer = NULL; - yy_flush_buffer(YY_CURRENT_BUFFER); - throw ExCLParseErrorBadIdentifier(str); - return 0; - } - } - -. { pxi_lexer = NULL; throw ExCLParseErrorMisc("Unrecognized character"); } - diff --git a/libs/cassowary/ClReader.yy b/libs/cassowary/ClReader.yy deleted file mode 100644 index f9f0dca43e..0000000000 --- a/libs/cassowary/ClReader.yy +++ /dev/null @@ -1,154 +0,0 @@ -/* - $Id$ - - Cassowary Incremental Constraint Solver - Original Smalltalk Implementation by Alan Borning - This C++ Implementation by Greg J. Badros, - http://www.cs.washington.edu/homes/gjb - (C) 1998, 1999 Greg J. Badros and Alan Borning - See ../LICENSE for legal details regarding this software - - ClReader.y - Original implementation contributed by Steve Wolfman - Subsequently largely revised by Greg J. Badros - - Supports parsing of read-only variables in constraints via "?" suffix - annotations on variables. If a variable is followed by "?" in any of - its occurrences in the constraint, that variable is deemed read-only - and entered into the constraint object as such. E.g., - - x = 2*y? - - is a one-way constraint that sets x from y's value. - - x = y + y? - and - x = y? + y - - are identical one-way constraints with y read-only. One would prefer - to have it written like so: - - x = y? + y? - - but it need not be, and no warning or error is raised. -*/ - - -%{ - /* C Declarations */ - -#include -#include -#include - -#ifdef HAVE_CONFIG_H -#include -#define CONFIG_H_INCLUDED -#endif - -#ifdef USE_CRUMMY_LEXER -string current; /* Global to help in debugging/error messages */ -#endif - -/* Get yyparse, yylex to have an extra argument (type void *) */ -#define YYPARSE_PARAM cl_parse_data -#define YYLEX_PARAM cl_parse_data -#ifndef YYERROR_VERBOSE -#define YYERROR_VERBOSE -#endif -#define YYDEBUG 1 - -%} - - -/* Bison Declarations */ - -%pure_parser - -%union { - double num; - const ClVariable *pclv; - ClLinearExpression *pcle; - ClConstraint *pcn; -} - -%{ -int yylex(YYSTYPE *lvalp, void *YYLEX_PARAM); -void yyerror(const char *sz); -%} - -%start constraint - -%token NUM -%token VAR -%token RO_VAR - -%token GEQ -%token GT -%token LEQ -%token LT - -%type expr -%type constraint equation inequality - -%left '-' '+' -%left '*' '/' -%left NEG - -%% -/* Grammar Rules */ - -constraint: equation { $$ = $1; ((ClParseData*)YYPARSE_PARAM)->_pcn = $1; } - | inequality { $$ = $1; ((ClParseData*)YYPARSE_PARAM)->_pcn = $1; } -; - -equation: expr '=' expr { $$ = new ClLinearEquation(*$1, *$3); } -; - -inequality: expr GEQ expr { $$ = new ClLinearInequality(*$1, cnGEQ, *$3); } - | expr LEQ expr { $$ = new ClLinearInequality(*$1, cnLEQ, *$3); } - | expr LT expr { $$ = new ClLinearInequality(*$1, cnLT, *$3); } - | expr GT expr { $$ = new ClLinearInequality(*$1, cnGT, *$3); } -; - -expr: NUM { $$ = new ClLinearExpression($1); } - | VAR { $$ = new ClLinearExpression(*$1); } - | RO_VAR { $$ = new ClLinearExpression(*$1); - ((ClParseData*)YYPARSE_PARAM)->_readOnlyVarsSoFar.insert(*$1); } - | expr '+' expr { $$ = new ClLinearExpression(*$1 + *$3); } - | expr '-' expr { $$ = new ClLinearExpression(*$1 - *$3); } - | expr '*' expr { $$ = new ClLinearExpression(*$1 * *$3); } - | expr '/' expr { $$ = new ClLinearExpression(*$1 / *$3); } - | '-' expr %prec NEG { $$ = new ClLinearExpression(-1 * *$2); } - | '(' expr ')' { $$ = $2; } -; - -%% - -void clerror(const char *sz) -{ - throw ExCLParseErrorMisc(sz); -} - -extern istream *pxi_lexer; - -// xi is the stream from which to read the constraint. -// aVars is an array of variables large enough to account for -// each one that might be mentioned in a constraint -ClConstraint *PcnParseConstraint(istream &xi, const ClVarLookupFunction &lookup_func, - const ClStrength &strength) -{ - ClParseData cl_parse_data(xi, lookup_func); - pxi_lexer = ξ - if (yyparse(&cl_parse_data) == 0) { // success -#ifdef DEBUG_PARSER - cerr << *cl_parse_data.Pcn() << endl; -#endif - cl_parse_data.Pcn()->ChangeStrength(strength); - cl_parse_data.Pcn()->AddROVars(cl_parse_data._readOnlyVarsSoFar); - return cl_parse_data.Pcn(); - } - else { // failed - return 0; - } -} diff --git a/libs/cassowary/ClSimplexSolver.cc b/libs/cassowary/ClSimplexSolver.cc deleted file mode 100644 index 32ea59df74..0000000000 --- a/libs/cassowary/ClSimplexSolver.cc +++ /dev/null @@ -1,1631 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClSimplexSolver.cc - -using namespace std; - -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include -#include -#include -#include - -#ifdef HAVE_CONFIG_H -#include -#define CONFIG_H_INCLUDED -#endif - -// Need to delete all expressions -// and all slack and dummy variables -// See NewExpression -- all allocation is done in there -ClSimplexSolver::~ClSimplexSolver() -{ -#ifdef CL_SOLVER_STATS - cerr << "_slackCounter == " << _slackCounter - << "\n_artificialCounter == " << _artificialCounter - << "\n_dummyCounter == " << _dummyCounter << endl; - cerr << "stayMinusErrorVars " << _stayMinusErrorVars.size() << ", " - << "stayPlusErrorVars " << _stayPlusErrorVars.size() << ", " - << "errorVars " << _errorVars.size() << ", " - << "markerVars " << _markerVars.size() << endl; -#endif - // Cannot print *this here, since local ClVariable-s may have been - // destructed already -} - -// Add the constraint cn to the tableau -ClSimplexSolver & -ClSimplexSolver::AddConstraint(ClConstraint *const pcn) -{ -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); - cerr << "(" << *pcn << ")" << endl; -#endif - - if (!pcn->FIsOkayForSimplexSolver()) { - throw ExCLTooDifficultSpecial("SimplexSolver cannot handle this constraint object"); - } - - if (pcn->IsStrictInequality()) { - // cannot handle strict inequalities - throw ExCLStrictInequalityNotAllowed(); - } - - if (pcn->ReadOnlyVars().size() > 0) { - // cannot handle read-only vars - throw ExCLReadOnlyNotAllowed(); - } - - if (pcn->IsEditConstraint()) - { - ClEditConstraint *pcnEdit = dynamic_cast(pcn); - const ClVariable &v = pcnEdit->variable(); - if (!v.IsExternal() || - (!FIsBasicVar(v) && !ColumnsHasKey(v))) - { - // we could try to make this case work, - // but it'd be unnecessarily inefficient -- - // and probably easier for the client application - // to deal with - throw ExCLEditMisuse("(ExCLEditMisuse) Edit constraint on variable not in tableau."); - } - ClEditInfo *pcei = PEditInfoFromClv(v); - if (pcei) - { - // we need to only add a partial _editInfoList entry for this - // edit constraint since the variable is already being edited. - // otherwise a more complete entry is added later in this function - _editInfoList.push_back(new ClEditInfo(v, NULL, clvNil, clvNil, 0)); - return *this; - } - } - - ClVariable clvEplus, clvEminus; - Number prevEConstant; - ClLinearExpression *pexpr = NewExpression(pcn, /* output to: */ - clvEplus,clvEminus, - prevEConstant); - bool fAddedOkDirectly = false; - - try - { - // If possible Add expr directly to the appropriate tableau by - // choosing a subject for expr (a variable to become basic) from - // among the current variables in expr. If this doesn't work use an - // artificial variable. After adding expr re-Optimize. - fAddedOkDirectly = TryAddingDirectly(*pexpr); - } - catch (ExCLRequiredFailure &error) - { -#ifdef CL_TRACE - cerr << "could not Add directly -- caught ExCLRequiredFailure error" << endl; -#endif - RemoveConstraintInternal(pcn); - throw; - } - - if (!fAddedOkDirectly) - { // could not Add directly - ExCLRequiredFailureWithExplanation e; - if (!AddWithArtificialVariable(*pexpr, e)) - { -#ifdef CL_DEBUG_FAILURES - cerr << "Failed solve! Could not Add constraint.\n" - << *this << endl; -#endif - RemoveConstraintInternal(pcn); - if (FIsExplaining()) - throw e; - else - throw ExCLRequiredFailure(); - } - } - - _fNeedsSolving = true; - - if (pcn->IsEditConstraint()) - { - ClEditConstraint *pcnEdit = dynamic_cast(pcn); - ClVariable clv = pcnEdit->variable(); - _editInfoList.push_back(new ClEditInfo(clv, pcnEdit, clvEplus, clvEminus, - prevEConstant)); - } - - if (_fAutosolve) - { - Optimize(_objective); - SetExternalVariables(); - } - - pcn->addedTo(*this); - return *this; -} - -// Add weak stays to the x and y parts of each point. These have -// increasing weights so that the solver will try to satisfy the x -// and y stays on the same point, rather than the x stay on one and -// the y stay on another. -ClSimplexSolver & -ClSimplexSolver::AddPointStays(const vector &listOfPoints, - const ClStrength &strength) -{ -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); -#endif - - vector::const_iterator it = listOfPoints.begin(); - double weight = 1.0; - static const double multiplier = 2.0; - for ( ; it != listOfPoints.end(); ++it ) - { - AddPointStay((*it)->X(),(*it)->Y(),strength,weight); - weight *= multiplier; - } - return *this; -} - -ClSimplexSolver & -ClSimplexSolver::AddPointStay(const ClPoint &clp, const ClStrength &strength, double weight) -{ - AddPointStay(clp.X(),clp.Y(),strength,weight); - return *this; -} - - -ClSimplexSolver & -ClSimplexSolver::RemoveEditVarsTo(unsigned int n) -{ - queue qclv; - ClVarSet sclvStillEditing; // Set of edit variables that we need to *not* remove -#ifdef DEBUG_NESTED_EDITS - cerr << __FUNCTION__ << " " << n << endl; -#endif - unsigned int i = 0; - for ( ClEditInfoList::const_iterator it = _editInfoList.begin(); - (it != _editInfoList.end() && _editInfoList.size() != static_cast(n)); - ++it, ++i ) - { - const ClEditInfo *pcei = (*it); - assert(pcei); -#ifdef DEBUG_NESTED_EDITS - cerr << __FUNCTION__ << "Checking " << pcei->_clv - << ", index = " << i << endl; -#endif - if (i >= n) - qclv.push(pcei->_clv); - else - sclvStillEditing.insert(pcei->_clv); - } - while (!qclv.empty()) - { - ClVariable clv = qclv.front(); - // only remove the variable if it's not in the set of variable - // from a previous nested outer edit - // e.g., if I do: - // Edit x,y - // Edit w,h,x,y - // EndEdit - // The end edit needs to only get rid of the edits on w,h - // not the ones on x,y - if (sclvStillEditing.find(clv) == sclvStillEditing.end()) - { -#ifdef DEBUG_NESTED_EDITS - cerr << __FUNCTION__ << ": Removing " << clv << endl; -#endif - RemoveEditVar(clv); - } -#ifdef DEBUG_NESTED_EDITS - else - { - cerr << __FUNCTION__ << ": Not removing " << clv << endl; - } -#endif - qclv.pop(); - } - while (_editInfoList.size() > n) { - _editInfoList.pop_back(); - } - - return *this; -} - - -/* A predicate used for remove_if */ -class VarInVarSet : public unary_function { -public: - VarInVarSet(const ClVarSet &clvset) : - _set(clvset), - _setEnd(clvset.end()) - { } - - bool operator ()(ClVariable clv) const { - return (_set.find(clv) != _setEnd); - } - -private: - const ClVarSet &_set; - const ClVarSet::iterator _setEnd; -}; - - - -// Remove the constraint cn from the tableau -// Also remove any error variable associated with cn -ClSimplexSolver & -ClSimplexSolver::RemoveConstraintInternal(const ClConstraint *const pcn) -{ -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); - cerr << "(" << *pcn << ")" << endl; -#endif - - // We are about to remove a constraint. There may be some stay - // constraints that were unsatisfied previously -- if we just - // removed the constraint these could come into play. Instead, - // Reset all of the stays so that things should stay where they are - // at the moment. - _fNeedsSolving = true; - - ResetStayConstants(); - - // remove any error variables from the objective function - ClLinearExpression *pzRow = RowExpression(_objective); - -#ifdef CL_TRACE - cerr << _errorVars << endl << endl; -#endif - - ClConstraintToVarSetMap::iterator - it_eVars = _errorVars.find(pcn); - bool fFoundErrorVar = (it_eVars != _errorVars.end()); - - if (fFoundErrorVar) - { - ClVarSet &eVars = (*it_eVars).second; - ClVarSet::iterator it = eVars.begin(); - for ( ; it != eVars.end(); ++it ) - { - const ClLinearExpression *pexpr = RowExpression(*it); - if (pexpr == NULL ) - { - pzRow->AddVariable(*it,-pcn->weight() * pcn->strength().symbolicWeight().AsDouble(), - _objective,*this); - } - else - { // the error variable was in the basis - pzRow->AddExpression(*pexpr,-pcn->weight() * pcn->strength().symbolicWeight().AsDouble(), - _objective,*this); - } - } - } - - ClConstraintToVarMap::iterator - it_marker = _markerVars.find(pcn); - if (it_marker == _markerVars.end()) - { // could not find the constraint - throw ExCLConstraintNotFound(); - } - // try to make the marker variable basic if it isn't already - const ClVariable marker = (*it_marker).second; - _markerVars.erase(it_marker); - _constraintsMarked.erase(marker); -#ifdef CL_TRACE - cerr << "Looking to remove var " << marker << endl; -#endif - if (!FIsBasicVar(marker)) - { // not in the basis, so need to do some work - // first choose which variable to move out of the basis - // only consider restricted basic variables - ClVarSet &col = _columns[marker]; - ClVarSet::iterator it_col = col.begin(); -#ifdef CL_TRACE - cerr << "Must Pivot -- columns are " << col << endl; -#endif - - ClVariable exitVar = clvNil; - bool fExitVarSet = false; - double minRatio = 0.0; - for ( ; it_col != col.end(); ++it_col) - { - const ClVariable &v = *it_col; - if (v.IsRestricted() ) - { - const ClLinearExpression *pexpr = RowExpression(v); - assert(pexpr != NULL ); - Number coeff = pexpr->CoefficientFor(marker); -#ifdef CL_TRACE - cerr << "Marker " << marker << "'s coefficient in " << *pexpr << " is " - << coeff << endl; -#endif - // only consider negative coefficients - if (coeff < 0.0) - { - Number r = - pexpr->Constant() / coeff; - if (!fExitVarSet || r < minRatio) - { - minRatio = r; - exitVar = v; - fExitVarSet = true; - } - } - } - } - // if we didn't set exitvar above, then either the marker - // variable has a positive coefficient in all equations, or it - // only occurs in equations for unrestricted variables. If it - // does occur in an equation for a restricted variable, pick the - // equation that gives the smallest ratio. (The row with the - // marker variable will become infeasible, but all the other rows - // will still be feasible; and we will be dropping the row with - // the marker variable. In effect we are removing the - // non-negativity restriction on the marker variable.) - if (!fExitVarSet) - { -#ifdef CL_TRACE - cerr << "exitVar did not get set" << endl; -#endif - it_col = col.begin(); - for ( ; it_col != col.end(); ++it_col) - { - ClVariable v = *it_col; - if (v.IsRestricted() ) - { - const ClLinearExpression *pexpr = RowExpression(v); - assert(pexpr != NULL); - Number coeff = pexpr->CoefficientFor(marker); - Number r = pexpr->Constant() / coeff; - if (!fExitVarSet || r < minRatio) - { - minRatio = r; - exitVar = v; - fExitVarSet = true; - } - } - } - } - - if (!fExitVarSet) - { // exitVar is still nil - // If col is empty, then exitVar doesn't occur in any equations, - // so just remove it. Otherwise pick an exit var from among the - // unrestricted variables whose equation involves the marker var - if (col.size() == 0) - { - RemoveColumn(marker); - } - else - { - // A. Beurive' Tue Sep 14 18:26:05 CEST 1999 - // Don't pick the objective, or it will be removed! - it_col = col.begin(); - for ( ; it_col != col.end(); ++it_col) - { - ClVariable v = *it_col; - if (v != _objective) - { - exitVar = v; - fExitVarSet = true; - break; - } - } - assert(fExitVarSet == true); - } - } - - if (fExitVarSet) - { - Pivot(marker,exitVar); - } - } - - if (FIsBasicVar(marker)) - { - ClLinearExpression *pexpr = RemoveRow(marker); -#ifdef CL_TRACE - cerr << "delete@ " << pexpr << endl; -#endif - delete pexpr; - } - - // Delete any error variables. If cn is an inequality, it also - // contains a slack variable; but we use that as the marker variable - // and so it has been deleted when we removed its row. - if (fFoundErrorVar) - { - ClVarSet &eVars = (*it_eVars).second; - ClVarSet::iterator it = eVars.begin(); - for ( ; it != eVars.end(); ++it ) - { - ClVariable v = (*it); - if (v != marker) - { - RemoveColumn(v); - } - } - } - - if (pcn->isStayConstraint()) - { - // iterate over the stay{Plus,Minus}ErrorVars and remove those - // variables v in those vectors that are also in set eVars - if (fFoundErrorVar) - { - ClVarSet &eVars = (*it_eVars).second; - _stayPlusErrorVars - .erase(remove_if(_stayPlusErrorVars.begin(),_stayPlusErrorVars.end(), - VarInVarSet(eVars)), - _stayPlusErrorVars.end()); - _stayMinusErrorVars - .erase(remove_if(_stayMinusErrorVars.begin(),_stayMinusErrorVars.end(), - VarInVarSet(eVars)), - _stayMinusErrorVars.end()); - } - } - else if (pcn->IsEditConstraint()) - { - const ClEditConstraint *pcnEdit = dynamic_cast(pcn); - const ClVariable clv = pcnEdit->variable(); - ClEditInfo *pcei = PEditInfoFromClv(clv); - assert(pcei); - ClVariable clvEditMinus = pcei->_clvEditMinus; - RemoveColumn(clvEditMinus); // clvEditPlus is a marker var and gets removed later - delete pcei; - _editInfoList.remove(pcei); - } - - if (fFoundErrorVar) - { - // This code is not needed since the variables are deleted - // when they are removed from the row -- - // leaving it in results in double deletions - // delete the constraint's error variables - // ClVarSet &evars_set = (*it_eVars).second; - // ClVarSet::const_iterator it_set = evars_set.begin(); - // for ( ; it_set != evars_set.end(); ++it_set) - // { - // delete *it_set; - // } - _errorVars.erase((*it_eVars).first); - } - - if (_fAutosolve) - { - Optimize(_objective); - SetExternalVariables(); - } - - return *this; -} - - -// Re-initialize this solver from the original constraints, thus -// getting rid of any accumulated numerical problems. (Actually, -// Alan hasn't observed any such problems yet, but here's the method -// anyway.) -void -ClSimplexSolver::Reset() -{ -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); - cerr << "()" << endl; -#endif - // FIXGJB -- can postpone writing this for a while - // gotta be careful, though, as it's a likely place for - // a memory leak to sneak in - assert(false); -} - - -// Re-solve the cuurent collection of constraints, given the new -// values for the edit variables that have already been -// suggested (see SuggestValue() method) -void -ClSimplexSolver::Resolve() -{ // CODE DUPLICATED ABOVE -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); -#endif - DualOptimize(); - SetExternalVariables(); - _infeasibleRows.clear(); - if (_fResetStayConstantsAutomatically) - ResetStayConstants(); -} - -ClSimplexSolver & -ClSimplexSolver::SuggestValue(ClVariable v, Number x) -{ -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); -#endif - ClEditInfo *pcei = PEditInfoFromClv(v); - if (NULL == pcei) - { -#ifndef CL_NO_IO - std::stringstream ss; - ss << "SuggestValue for variable " << v << ", but var is not an edit variable" << ends; - throw ExCLEditMisuse(ss.str().c_str()); -#else - throw ExCLEditMisuse(v.Name().c_str()); -#endif - } - ClVariable clvEditPlus = pcei->_clvEditPlus; - ClVariable clvEditMinus = pcei->_clvEditMinus; - Number delta = x - pcei->_prevEditConstant; - pcei->_prevEditConstant = x; - DeltaEditConstant(delta,clvEditPlus,clvEditMinus); - return *this; -} - -// Re-solve the cuurent collection of constraints, given the new -// values for the edit variables that have already been -// suggested (see SuggestValue() method) -// This is not guaranteed to work if you remove an edit constraint -// from the middle of the edit constraints you added -// (e.g., edit A, edit B, edit C, remove B -> this will fail!) -// DEPRECATED -void -ClSimplexSolver::Resolve(const vector &newEditConstants) -{ - ClEditInfoList::iterator it = _editInfoList.begin(); - unsigned int i = 0; - for (; i < newEditConstants.size() && it != _editInfoList.end(); ++it, ++i) - { - ClEditInfo *pcei = (*it); - SuggestValue(pcei->_clv,newEditConstants[i]); - } - Resolve(); -} - - -//// protected - -// Add the constraint expr=0 to the inequality tableau using an -// artificial variable. To do this, create an artificial variable -// av and Add av=expr to the inequality tableau, then make av be 0. -// (Raise an exception if we can't attain av=0 -- and prepare explanation) -bool -ClSimplexSolver::AddWithArtificialVariable(ClLinearExpression &expr, - ExCLRequiredFailureWithExplanation &e) -{ -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); - cerr << "(" << expr << ")" << endl; -#endif - - // Allocate the objects on the heap because the objects - // will remain in the tableau if we throw an exception, - // and that will result in the destructor cleaning up - // after us - ClSlackVariable *pav = new ClSlackVariable(++_artificialCounter,"a"); - ClObjectiveVariable *paz = new ClObjectiveVariable("az"); - ClLinearExpression *pazRow = new ClLinearExpression(expr); - // the artificial objective is av, which we know is equal to expr - // (which contains only parametric variables) - -#ifdef CL_FIND_LEAK - cerr << "aC = " << _artificialCounter - << "\nDeletes = " << _cArtificialVarsDeleted << endl; -#endif -#ifdef CL_TRACE - cerr << __FUNCTION__ << " before addRow-s:\n" - << (*this) << endl; -#endif - - // the artificial objective is av, which we know is equal to expr - // (which contains only parametric variables) - - // objective is treated as a row in the tableau, - // so do the substitution for its value (we are minimizing - // the artificial variable) - // this row will be removed from the tableau after optimizing - addRow(*paz,*pazRow); - - // now Add the normal row to the tableau -- when artifical - // variable is minimized to 0 (if possible) - // this row remains in the tableau to maintain the constraint - // we are trying to Add - addRow(*pav,expr); - -#ifdef CL_TRACE - cerr << __FUNCTION__ << " after addRow-s:\n" - << (*this) << endl; -#endif - - // try to Optimize az to 0 - // note we are *not* optimizing the real objective, but optimizing - // the artificial objective to see if the error in the constraint - // we are adding can be set to 0 - Optimize(*paz); - - // Careful, we want to get the Expression that is in - // the tableau, not the one we initialized it with! - ClLinearExpression *pazTableauRow = RowExpression(*paz); -#ifdef CL_TRACE - cerr << "pazTableauRow->Constant() == " << pazTableauRow->Constant() << endl; -#endif - - // Check that we were able to make the objective value 0 - // If not, the original constraint was not satisfiable - if (!ClApprox(pazTableauRow->Constant(),0.0)) - { - BuildExplanation(e, paz, pazTableauRow); - // remove the artificial objective row that we just - // added temporarily - delete RemoveRow(*paz); - // and delete the artificial objective variable that we also added above - delete paz; - return false; - } - - // see if av is a basic variable - const ClLinearExpression *pe = RowExpression(*pav); - if (pe != NULL) - { - // FIXGJB: do we ever even get here? - // Find another variable in this row and Pivot, so that av becomes parametric - // If there isn't another variable in the row then - // the tableau contains the equation av = 0 -- just delete av's row - if (pe->IsConstant()) - { - // FIXGJB: do we ever get here? - assert(ClApprox(pe->Constant(),0.0)); - delete RemoveRow(*pav); - // remove the temporary objective function - // FIXGJB may need this too: delete RemoveRow(*paz); - delete pav; -#ifdef CL_FIND_LEAK - ++_cArtificialVarsDeleted; -#endif - return true; - } - ClVariable entryVar = pe->AnyPivotableVariable(); - if (entryVar.IsNil()) - { - BuildExplanation(e, *pav, pe); - return false; /* required failure */ - } - Pivot(entryVar, *pav); - } - // now av should be parametric - assert(RowExpression(*pav) == NULL); - RemoveColumn(*pav); - delete pav; -#ifdef CL_FIND_LEAK - ++_cArtificialVarsDeleted; -#endif - // remove the temporary objective function - delete RemoveRow(*paz); - delete paz; - return true; -} - - -// Using the given equation (av = cle) build an explanation which -// implicates all constraints used to construct the equation. That -// is, everything for which the variables in the equation are markers. -void ClSimplexSolver::BuildExplanation(ExCLRequiredFailureWithExplanation &e, - ClVariable av, - const ClLinearExpression *pcle) -{ - ClVarToConstraintMap::iterator it_cn; - it_cn = _constraintsMarked.find(av); - if (it_cn != _constraintsMarked.end()) - { - e.AddConstraint((*it_cn).second); - } - - assert(pcle != NULL); - - const ClVarToNumberMap & terms = pcle->Terms(); - ClVarToNumberMap::const_iterator it_term; - for (it_term = terms.begin(); it_term != terms.end(); it_term++) - { - it_cn = _constraintsMarked.find((*it_term).first); - if (it_cn != _constraintsMarked.end()) - { - e.AddConstraint((*it_cn).second); - } - } -} - - - -// We are trying to Add the constraint expr=0 to the appropriate -// tableau. Try to Add expr directly to the tableaus without -// creating an artificial variable. Return true if successful and -// false if not. -bool -ClSimplexSolver::TryAddingDirectly(ClLinearExpression &expr) -{ -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); - cerr << "(" << expr << ")" << endl; -#endif - ClVariable subject = ChooseSubject(expr); - if (subject.get_pclv() == NULL ) - { -#ifdef CL_TRACE - cerr << "- returning false" << endl; -#endif - return false; - } - expr.NewSubject(subject); - if (ColumnsHasKey(subject)) - { - SubstituteOut(subject,expr); - } - addRow(subject,expr); -#ifdef CL_TRACE - cerr << "- returning true" << endl; -#endif - return true; // successfully added directly -} - - -// We are trying to Add the constraint expr=0 to the tableaux. Try -// to choose a subject (a variable to become basic) from among the -// current variables in expr. If expr contains any unrestricted -// variables, then we must choose an unrestricted variable as the -// subject. Also, if the subject is new to the solver we won't have -// to do any substitutions, so we prefer new variables to ones that -// are currently noted as parametric. If expr contains only -// restricted variables, if there is a restricted variable with a -// negative coefficient that is new to the solver we can make that -// the subject. Otherwise we can't find a subject, so return nil. -// (In this last case we have to Add an artificial variable and use -// that variable as the subject -- this is done outside this method -// though.) -// -// Note: in checking for variables that are new to the solver, we -// ignore whether a variable occurs in the objective function, since -// new slack variables are added to the objective function by -// 'NewExpression:', which is called before this method. -ClVariable -ClSimplexSolver::ChooseSubject(ClLinearExpression &expr) -{ -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); - cerr << "(" << expr << ")" << endl; -#endif - ClVariable subject(clvNil); // the current best subject, if any - - // true iff we have found a subject that is an unrestricted variable - bool foundUnrestricted = false; - - // true iff we have found a restricted variable that is new to the - // solver (except for being in the obj. function) and that has a - // negative coefficient - bool foundNewRestricted = false; - - const ClVarToNumberMap &terms = expr.Terms(); - ClVarToNumberMap::const_iterator it = terms.begin(); - for ( ; it != terms.end(); ++it ) - { - ClVariable v = (*it).first; - Number c = (*it).second; - - if (foundUnrestricted) - { - // We have already found an unrestricted variable. The only - // time we will want to use v instead of the current choice - // 'subject' is if v is unrestricted and new to the solver and - // 'subject' isn't new. If this is the case just pick v - // immediately and return. - if (!v.IsRestricted()) - { - if (!ColumnsHasKey(v)) - return v; - } - } - else - { // we haven't found an restricted variable yet - if (v.IsRestricted()) - { - // v is restricted. If we have already found a suitable - // restricted variable just stick with that. Otherwise, if v - // is new to the solver and has a negative coefficient pick - // it. Regarding being new to the solver -- if the variable - // occurs only in the objective function we regard it as being - // new to the solver, since error variables are added to the - // objective function when we make the Expression. We also - // never pick a dummy variable here. - if (!foundNewRestricted && !v.IsDummy() && c < 0.0) - { - const ClTableauColumnsMap &col = Columns(); - ClTableauColumnsMap::const_iterator it_col = col.find(v); - if (it_col == col.end() || - ( col.size() == 1 && ColumnsHasKey(_objective) ) ) - { - subject = v; - foundNewRestricted = true; - } - } - } - else - { - // v is unrestricted. - // If v is also new to the solver just pick it now - subject = v; - foundUnrestricted = true; - } - } - } - if (!subject.IsNil()) - return subject; - - // subject is nil. - // Make one last check -- if all of the variables in expr are dummy - // variables, then we can pick a dummy variable as the subject - Number coeff = 0; - it = terms.begin(); - for ( ; it != terms.end(); ++it ) - { - ClVariable v = (*it).first; - Number c = (*it).second; - if (!v.IsDummy()) - return clvNil; // nope, no luck - // if v is new to the solver, tentatively make it the subject - if (!ColumnsHasKey(v)) - { - subject = v; - coeff = c; - } - } - - // If we get this far, all of the variables in the Expression should - // be dummy variables. If the Constant is nonzero we are trying to - // Add an unsatisfiable required constraint. (Remember that dummy - // variables must take on a value of 0.) Otherwise, if the Constant - // is Zero, multiply by -1 if necessary to make the coefficient for - // the subject negative." - if (!ClApprox(expr.Constant(),0.0)) - { -#ifdef CL_DEBUG_FAILURES - cerr << "required failure in choose subject:\n" - << *this << endl; -#endif - if (FIsExplaining()) - { - ExCLRequiredFailureWithExplanation e; - BuildExplanation(e, clvNil, &expr); - throw e; - } - else - throw ExCLRequiredFailure(); - } - if (coeff > 0.0) - { - expr.MultiplyMe(-1); - } - return subject; -} - -// Each of the non-required edits will be represented by an equation -// of the form -// v = c + eplus - eminus -// where v is the variable with the edit, c is the previous edit -// value, and eplus and eminus are slack variables that hold the -// error in satisfying the edit constraint. We are about to change -// something, and we want to fix the constants in the equations -// representing the edit constraints. If one of eplus and eminus is -// basic, the other must occur only in the Expression for that basic -// error variable. (They can't both be basic.) Fix the Constant in -// this Expression. Otherwise they are both nonbasic. Find all of -// the expressions in which they occur, and fix the constants in -// those. See the UIST paper for details. -// (This comment was for resetEditConstants(), but that is now -// gone since it was part of the screwey vector-based interface -// to resolveing. --02/15/99 gjb) -void -ClSimplexSolver::DeltaEditConstant(Number delta, - ClVariable plusErrorVar, - ClVariable minusErrorVar) -{ -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); - cerr << "(" << delta << ", " << plusErrorVar << ", " << minusErrorVar << ")" << endl; -#endif - // first check if the plusErrorVar is basic - ClLinearExpression *pexprPlus = RowExpression(plusErrorVar); - if (pexprPlus != NULL ) - { - pexprPlus->IncrementConstant(delta); - // error variables are always restricted - // so the row is infeasible if the Constant is negative - if (pexprPlus->Constant() < 0.0) - { - _infeasibleRows.insert(plusErrorVar); - } - return; - } - // check if minusErrorVar is basic - ClLinearExpression *pexprMinus = RowExpression(minusErrorVar); - if (pexprMinus != NULL) - { - pexprMinus->IncrementConstant(-delta); - if (pexprMinus->Constant() < 0.0) - { - _infeasibleRows.insert(minusErrorVar); - } - return; - } - // Neither is basic. So they must both be nonbasic, and will both - // occur in exactly the same expressions. Find all the expressions - // in which they occur by finding the column for the minusErrorVar - // (it doesn't matter whether we look for that one or for - // plusErrorVar). Fix the constants in these expressions. - ClVarSet &columnVars = _columns[minusErrorVar]; - ClVarSet::iterator it = columnVars.begin(); - for (; it != columnVars.end(); ++it) - { - ClVariable basicVar = *it; - ClLinearExpression *pexpr = RowExpression(basicVar); - assert(pexpr != NULL ); - double c = pexpr->CoefficientFor(minusErrorVar); - pexpr->IncrementConstant(c*delta); - if (basicVar.IsRestricted() && pexpr->Constant() < 0.0) - { - _infeasibleRows.insert(basicVar); - } - } -} - -// We have set new values for the constants in the edit constraints. -// Re-Optimize using the dual simplex algorithm. -void -ClSimplexSolver::DualOptimize() -{ -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); - cerr << "()" << endl; -#endif - const ClLinearExpression *pzRow = RowExpression(_objective); - // need to handle infeasible rows - while (!_infeasibleRows.empty()) - { - ClVarSet::iterator it_exitVar = _infeasibleRows.begin(); - ClVariable exitVar = *it_exitVar; - _infeasibleRows.erase(it_exitVar); - ClVariable entryVar; - // exitVar might have become basic after some other pivoting - // so allow for the case of its not being there any longer - ClLinearExpression *pexpr = RowExpression(exitVar); - if (pexpr != NULL ) - { - // make sure the row is still not feasible - if (pexpr->Constant() < 0.0) - { - double ratio = DBL_MAX; - double r; - ClVarToNumberMap &terms = pexpr->Terms(); - ClVarToNumberMap::iterator it = terms.begin(); - for ( ; it != terms.end(); ++it ) - { - ClVariable v = (*it).first; - Number c = (*it).second; - if (c > 0.0 && v.IsPivotable()) - { - Number zc = pzRow->CoefficientFor(v); - r = zc/c; // FIXGJB r:= zc/c or Zero, as ClSymbolicWeight-s - if (r < ratio) - { - entryVar = v; - ratio = r; - } - } - } - if (ratio == DBL_MAX) - { - stringstream ss; - ss << "ratio == nil (DBL_MAX)" << ends; - throw ExCLInternalError(ss.str().c_str()); - } - Pivot(entryVar,exitVar); - } - } - } -} - -// Make a new linear Expression representing the constraint cn, -// replacing any basic variables with their defining expressions. -// Normalize if necessary so that the Constant is non-negative. If -// the constraint is non-required give its error variables an -// appropriate weight in the objective function. -ClLinearExpression * -ClSimplexSolver::NewExpression(const ClConstraint *pcn, - /* output to */ - ClVariable &clvEplus, - ClVariable &clvEminus, - Number &prevEConstant) -{ -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); - cerr << "(" << *pcn << ")" << endl; - cerr << "cn.IsInequality() == " << pcn->IsInequality() << endl; - cerr << "cn.IsRequired() == " << pcn->IsRequired() << endl; -#endif - const ClLinearExpression &cnExpr = pcn->Expression(); - cl_auto_ptr pexpr ( new ClLinearExpression(cnExpr.Constant()) ); - cl_auto_ptr pslackVar; - cl_auto_ptr pdummyVar; - cl_auto_ptr peminus(0); - cl_auto_ptr peplus(0); - const ClVarToNumberMap &cnTerms = cnExpr.Terms(); - ClVarToNumberMap::const_iterator it = cnTerms.begin(); - for ( ; it != cnTerms.end(); ++it) - { - ClVariable v = (*it).first; - Number c = (*it).second; - const ClLinearExpression *pe = RowExpression(v); - if (pe == NULL) - { - pexpr->AddVariable(v,c); - } - else - { - pexpr->AddExpression(*pe,c); - } - } - - // Add slack and error variables as needed - if (pcn->IsInequality()) - { - // cn is an inequality, so Add a slack variable. The original - // constraint is expr>=0, so that the resulting equality is - // expr-slackVar=0. If cn is also non-required Add a negative - // error variable, giving - // expr-slackVar = -errorVar, in other words - // expr-slackVar+errorVar=0. - // Since both of these variables are newly created we can just Add - // them to the Expression (they can't be basic). - ++_slackCounter; - ReinitializeAutoPtr(pslackVar,new ClSlackVariable (_slackCounter, "s")); - pexpr->setVariable(*pslackVar,-1); - // index the constraint under its slack variable and vice-versa - _markerVars[pcn] = pslackVar.get(); - _constraintsMarked[pslackVar.get()] = pcn; - - if (!pcn->IsRequired()) - { - ++_slackCounter; - ReinitializeAutoPtr(peminus,new ClSlackVariable (_slackCounter, "em")); - pexpr->setVariable(*peminus,1.0); - // Add emnius to the objective function with the appropriate weight - ClLinearExpression *pzRow = RowExpression(_objective); - // FIXGJB: pzRow->AddVariable(eminus,pcn->strength().symbolicWeight() * pcn->weight()); - ClSymbolicWeight sw = pcn->strength().symbolicWeight().Times(pcn->weight()); - pzRow->setVariable(*peminus,sw.AsDouble()); - _errorVars[pcn].insert(peminus.get()); - NoteAddedVariable(*peminus,_objective); - } - } - else - { // cn is an equality - if (pcn->IsRequired()) - { - // Add a dummy variable to the Expression to serve as a marker - // for this constraint. The dummy variable is never allowed to - // enter the basis when pivoting. - ++_dummyCounter; - ReinitializeAutoPtr(pdummyVar,new ClDummyVariable (_dummyCounter, "d")); - pexpr->setVariable(*pdummyVar,1.0); - _markerVars[pcn] = pdummyVar.get(); - _constraintsMarked[pdummyVar.get()] = pcn; -#ifdef CL_TRACE - cerr << "Adding dummyVar == d" << _dummyCounter << endl; -#endif - } - else - { - // cn is a non-required equality. Add a positive and a negative - // error variable, making the resulting constraint - // expr = eplus - eminus, - // in other words: expr-eplus+eminus=0 - ++_slackCounter; - ReinitializeAutoPtr(peplus,new ClSlackVariable (_slackCounter, "ep")); - ReinitializeAutoPtr(peminus,new ClSlackVariable (_slackCounter, "em")); - - pexpr->setVariable(*peplus,-1.0); - pexpr->setVariable(*peminus,1.0); - // index the constraint under one of the error variables - _markerVars[pcn] = peplus.get(); - _constraintsMarked[peplus.get()] = pcn; - - ClLinearExpression *pzRow = RowExpression(_objective); - // FIXGJB: pzRow->AddVariable(eplus,pcn->strength().symbolicWeight() * pcn->weight()); - ClSymbolicWeight sw = pcn->strength().symbolicWeight().Times(pcn->weight()); - double swCoeff = sw.AsDouble(); -#ifdef CL_TRACE - if (swCoeff == 0) - { - cerr << "sw == " << sw << endl - << "cn == " << *pcn << endl; - cerr << "adding " << *peplus << " and " << *peminus - << " with swCoeff == " << swCoeff << endl; - } -#endif - pzRow->setVariable(*peplus,swCoeff); - NoteAddedVariable(*peplus,_objective); - // FIXGJB: pzRow->AddVariable(eminus,pcn->strength().symbolicWeight() * pcn->weight()); - pzRow->setVariable(*peminus,swCoeff); - NoteAddedVariable(*peminus,_objective); - _errorVars[pcn].insert(peminus.get()); - _errorVars[pcn].insert(peplus.get()); - if (pcn->isStayConstraint()) - { - _stayPlusErrorVars.push_back(peplus.get()); - _stayMinusErrorVars.push_back(peminus.get()); - } - else if (pcn->IsEditConstraint()) - { - clvEplus = peplus.get(); - clvEminus = peminus.get(); - prevEConstant = cnExpr.Constant(); - } - } - } - - // the Constant in the Expression should be non-negative. - // If necessary normalize the Expression by multiplying by -1 - if (pexpr->Constant() < 0) - { -#ifdef CL_TRACE - cerr << "NewExpression's Constant is " << pexpr->Constant() << ", < 0, so flipping" << endl; -#endif - pexpr->MultiplyMe(-1); - } -#ifdef CL_TRACE - cerr << "- returning " << *pexpr << endl; -#endif - // Terrible Name -- release() does *not* delete the object, - // only makes sure that the destructor won't delete the object - // (it releases the cl_auto_ptr from the responsibility of deleting the object) - pslackVar.release(); - pdummyVar.release(); - peminus.release(); - peplus.release(); - return pexpr.release(); -} - -// Minimize the value of the objective. (The tableau should already -// be feasible.) -void -ClSimplexSolver::Optimize(ClVariable zVar) -{ -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); - cerr << "(" << zVar << ")\n" - << *this << endl; -#endif - ClLinearExpression *pzRow = RowExpression(zVar); - assert(pzRow != NULL); - ClVariable entryVar = clvNil; - ClVariable exitVar = clvNil; - while (true) - { - Number objectiveCoeff = 0; - // Find the most negative coefficient in the objective function - // (ignoring the non-pivotable dummy variables). If all - // coefficients are positive we're done - ClVarToNumberMap &terms = pzRow->Terms(); - ClVarToNumberMap::iterator it = terms.begin(); - for (; it != terms.end(); ++it) - { - ClVariable v = (*it).first; - Number c = (*it).second; - if (v.IsPivotable() && c < objectiveCoeff) - { - objectiveCoeff = c; - entryVar = v; - // A. Beurive' Tue Jul 13 23:03:05 CEST 1999 Why the most - // negative? I encountered unending cycles of pivots! - break; - } - } - // if all coefficients were positive (or if the objective - // function has no pivotable variables) - // we are at an optimum - if (objectiveCoeff >= -_epsilon) - return; -#ifdef CL_TRACE - cerr << "entryVar == " << entryVar << ", " - << "objectiveCoeff == " << objectiveCoeff - << endl; -#endif - - // choose which variable to move out of the basis - // Only consider pivotable basic variables - // (i.e. restricted, non-dummy variables) - double minRatio = DBL_MAX; - ClVarSet &columnVars = _columns[entryVar]; - ClVarSet::iterator it_rowvars = columnVars.begin(); - Number r = 0.0; - for (; it_rowvars != columnVars.end(); ++it_rowvars) - { - ClVariable v = *it_rowvars; -#ifdef CL_TRACE - cerr << "Checking " << v << endl; -#endif - if (v.IsPivotable()) - { - const ClLinearExpression *pexpr = RowExpression(v); - Number coeff = pexpr->CoefficientFor(entryVar); - // only consider negative coefficients - if (coeff < 0.0) - { - r = - pexpr->Constant() / coeff; - if (r < minRatio) - { -#ifdef CL_TRACE - cerr << "New minRatio == " << r << endl; -#endif - minRatio = r; - exitVar = v; - } - } - } - } - // If minRatio is still nil at this point, it means that the - // objective function is unbounded, i.e. it can become - // arbitrarily negative. This should never happen in this - // application. - if (minRatio == DBL_MAX) - { - stringstream ss; - ss << "objective function is unbounded!" << ends; - throw ExCLInternalError(ss.str().c_str()); - } - Pivot(entryVar, exitVar); -#ifdef CL_TRACE - cerr << "After Optimize:\n" - << *this << endl; -#endif - } -} - -// Do a Pivot. Move entryVar into the basis (i.e. make it a basic variable), -// and move exitVar out of the basis (i.e., make it a parametric variable) -void -ClSimplexSolver::Pivot(ClVariable entryVar, ClVariable exitVar) -{ -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); - cerr << "(" << entryVar << ", " << exitVar << ")" << endl; -#endif - - // the entryVar might be non-pivotable if we're doing a RemoveConstraint -- - // otherwise it should be a pivotable variable -- enforced at call sites, - // hopefully - - // expr is the Expression for the exit variable (about to leave the basis) -- - // so that the old tableau includes the equation: - // exitVar = expr - ClLinearExpression *pexpr = RemoveRow(exitVar); - - // Compute an Expression for the entry variable. Since expr has - // been deleted from the tableau we can destructively modify it to - // build this Expression. - pexpr->ChangeSubject(exitVar,entryVar); - SubstituteOut(entryVar,*pexpr); - - if (entryVar.IsExternal()) - { - // entry var is no longer a parametric variable since we're moving - // it into the basis - _externalParametricVars.erase(entryVar); - } - addRow(entryVar,*pexpr); -} - - - -// Each of the non-required stays will be represented by an equation -// of the form -// v = c + eplus - eminus -// where v is the variable with the stay, c is the previous value of -// v, and eplus and eminus are slack variables that hold the error -// in satisfying the stay constraint. We are about to change -// something, and we want to fix the constants in the equations -// representing the stays. If both eplus and eminus are nonbasic -// they have value 0 in the current solution, meaning the previous -// stay was exactly satisfied. In this case nothing needs to be -// changed. Otherwise one of them is basic, and the other must -// occur only in the Expression for that basic error variable. -// Reset the Constant in this Expression to 0. -void -ClSimplexSolver::ResetStayConstants() -{ -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); - cerr << "()" << endl; -#endif - ClVarVector::const_iterator - itStayPlusErrorVars = _stayPlusErrorVars.begin(); - ClVarVector::const_iterator - itStayMinusErrorVars = _stayMinusErrorVars.begin(); - - for ( ; itStayPlusErrorVars != _stayPlusErrorVars.end(); - ++itStayPlusErrorVars, ++itStayMinusErrorVars ) - { - ClLinearExpression *pexpr = RowExpression(*itStayPlusErrorVars); - if (pexpr == NULL ) - { - pexpr = RowExpression(*itStayMinusErrorVars); - } - if (pexpr != NULL) - { - pexpr->Set_constant(0.0); - } - } -} - -// Set the external variables known to this solver to their appropriate values. -// Set each external basic variable to its value, and set each -// external parametric variable to 0. (It isn't clear that we will -// ever have external parametric variables -- every external -// variable should either have a stay on it, or have an equation -// that defines it in terms of other external variables that do have -// stays. For the moment I'll put this in though.) Variables that -// are internal to the solver don't actually store values -- their -// values are just implicit in the tableu -- so we don't need to set -// them." -void -ClSimplexSolver::SetExternalVariables() -{ -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); - cerr << "()\n" - << *this << endl; -#endif - - // FIXGJB -- oughta check some invariants here - - // Set external parametric variables first - // in case I've screwed up - ClVarSet::iterator itParVars = _externalParametricVars.begin(); - for ( ; itParVars != _externalParametricVars.end(); ++itParVars ) - { - ClVariable v = *itParVars; -#ifndef NDEBUG - // defensively skip it if it is basic -- ChangeValue is virtual - // so don't want to call it twice; this should never - // happen - if (FIsBasicVar(v)) - { -#ifndef CL_NO_IO - // WARNING - cerr << __FUNCTION__ << "Error: variable " << v - << " in _externalParametricVars is basic" << endl; - cerr << "Row is: " << *RowExpression(v) << endl; -#endif - continue; - } -#endif - ChangeClv(v,0.0); - } - - // Only iterate over the rows w/ external variables - ClVarSet::iterator itRowVars = _externalRows.begin(); - for ( ; itRowVars != _externalRows.end() ; ++itRowVars ) - { - ClVariable v = *itRowVars; - ClLinearExpression *pexpr = RowExpression(v); - ChangeClv(v,pexpr->Constant()); - } - - _fNeedsSolving = false; - if (_pfnResolveCallback) - _pfnResolveCallback(this); -} - -#ifndef CL_NO_IO -ostream & -PrintTo(ostream &xo, const ClVarVector &varlist) -{ - ClVarVector::const_iterator it = varlist.begin(); - xo << varlist.size() << ":" << "[ "; - if (it != varlist.end()) - { - xo << *it; - ++it; - } - for (; it != varlist.end(); ++it) - { - xo << ", " << *it; - } - xo << " ]"; - return xo; -} - -ostream &operator<<(ostream &xo, const ClVarVector &varlist) -{ return PrintTo(xo,varlist); } - - -ostream & -PrintTo(ostream &xo, const ClConstraintToVarSetMap &mapCnToVarSet) -{ - ClConstraintToVarSetMap::const_iterator it = mapCnToVarSet.begin(); - for ( ; it != mapCnToVarSet.end(); ++it) { - const ClConstraint *pcn = (*it).first; - const ClVarSet &set = (*it).second; - xo << "CN: " << pcn << *pcn << ":: " << set << endl; - } - return xo; -} - -ostream &operator <<(ostream &xo, const ClConstraintToVarSetMap &mapCnToVarSet) -{ return PrintTo(xo,mapCnToVarSet); } - - - -ostream & -ClSimplexSolver::PrintOn(ostream &xo) const -{ - ClTableau::PrintOn(xo); - - xo << "_stayPlusErrorVars: " - << _stayPlusErrorVars << endl; - xo << "_stayMinusErrorVars: " - << _stayMinusErrorVars << endl; - xo << "_editInfoList:\n" - << _editInfoList << endl; - return xo; -} - - -ostream & -ClSimplexSolver::PrintInternalInfo(ostream &xo) const -{ - ClTableau::PrintInternalInfo(xo); - xo << "; edvars: " << _editInfoList.size(); - xo << endl; - printExternalVariablesTo(xo); - return xo; -} - -ostream &operator<<(ostream &xo, const ClSimplexSolver &clss) -{ - return clss.PrintOn(xo); -} - -#endif - -bool -ClSimplexSolver::FIsConstraintSatisfied(const ClConstraint *const pcn) const -{ - ClConstraintToVarMap::const_iterator it_marker = _markerVars.find(pcn); - if (it_marker == _markerVars.end()) - { // could not find the constraint - throw ExCLConstraintNotFound(); - } - -#ifndef CL_NO_IO - bool fCnsays = pcn->FIsSatisfied(); -#endif - - ClConstraintToVarSetMap::const_iterator it_eVars = _errorVars.find(pcn); - - if (it_eVars != _errorVars.end()) - { - const ClVarSet &eVars = (*it_eVars).second; - ClVarSet::const_iterator it = eVars.begin(); - for ( ; it != eVars.end(); ++it ) - { - const ClLinearExpression *pexpr = RowExpression(*it); - if (pexpr != NULL && !ClApprox(pexpr->Constant(),0.0)) - { -#ifndef CL_NO_IO - if (fCnsays) - cerr << __FUNCTION__ << ": constraint says satisfiable, but solver does not" << endl; -#endif - return false; - } - } - } - -#ifndef CL_NO_IO - if (!fCnsays) - cerr << __FUNCTION__ << ": solver says satisfiable, but constraint does not" << endl; -#endif - return true; -} - - - -#ifndef CL_NO_ID - -ostream &PrintTo(ostream &xo, const ClSimplexSolver::ClEditInfoList &listPEditInfo) -{ - ClSimplexSolver::ClEditInfoList::const_iterator it = listPEditInfo.begin(); - for ( ; it != listPEditInfo.end(); ++it) { - const ClSimplexSolver::ClEditInfo *pcei = (*it); - xo << *pcei << endl; - } - return xo; -} - - -ostream &operator<<(ostream &xo, const ClSimplexSolver::ClEditInfoList &listPEditInfo) -{ return PrintTo(xo,listPEditInfo); } - -#endif - -// A. Beurive' Tue Jul 6 17:03:32 CEST 1999 -void -ClSimplexSolver::ChangeStrengthAndWeight(ClConstraint *pcn, const ClStrength &strength, double weight) -{ - ClConstraintToVarSetMap::iterator it_eVars = _errorVars.find(pcn); - // Only for constraints that already have error variables (i.e. non-required constraints) - assert(it_eVars != _errorVars.end()); - - ClLinearExpression *pzRow = RowExpression(_objective); - - Number old_coeff = pcn->weight() * pcn->strength().symbolicWeight().AsDouble(); - pcn->setStrength(strength); - pcn->setWeight(weight); - Number new_coeff = pcn->weight() * pcn->strength().symbolicWeight().AsDouble(); - - if (new_coeff != old_coeff) - { -#ifdef CL_TRACE - cerr << "Changing strength and/or weight for constraint: " << endl << *pcn << endl; - cerr << "Updating objective row from:" << endl << *pzRow << endl; -#endif - ClVarSet &eVars = (*it_eVars).second; - ClVarSet::iterator it = eVars.begin(); - for ( ; it != eVars.end(); ++it ) - { - const ClLinearExpression *pexpr = RowExpression(*it); - if (pexpr == NULL ) - { - pzRow->AddVariable(*it,-old_coeff,_objective,*this); - pzRow->AddVariable(*it,new_coeff,_objective,*this); - } - else - { - pzRow->AddExpression(*pexpr,-old_coeff,_objective,*this); - pzRow->AddExpression(*pexpr,new_coeff,_objective,*this); - } - } -#ifdef CL_TRACE - cerr << "to: " << endl << *pzRow << endl; -#endif - - if (_fAutosolve) - { - Optimize(_objective); - SetExternalVariables(); - } - } -} - -// A. Beurive' Tue Jul 6 17:03:42 CEST 1999 -void -ClSimplexSolver::ChangeStrength(ClConstraint *pcn, const ClStrength &strength) -{ - ChangeStrengthAndWeight(pcn,strength,pcn->weight()); -} - -// A. Beurive' Tue Jul 6 17:03:42 CEST 1999 -void -ClSimplexSolver::ChangeWeight(ClConstraint *pcn, double weight) -{ - ChangeStrengthAndWeight(pcn,pcn->strength(),weight); -} diff --git a/libs/cassowary/ClSlackVariable.cc b/libs/cassowary/ClSlackVariable.cc deleted file mode 100644 index eaf0432eb0..0000000000 --- a/libs/cassowary/ClSlackVariable.cc +++ /dev/null @@ -1,12 +0,0 @@ -// $Id$ - -#include - -#ifdef HAVE_CONFIG_H -#include -#define CONFIG_H_INCLUDED -#endif - -#ifdef CL_FIND_LEAK -long ClSlackVariable::cSlackVariables = 0; -#endif diff --git a/libs/cassowary/ClSolver.cc b/libs/cassowary/ClSolver.cc deleted file mode 100644 index 18b0b7f9cc..0000000000 --- a/libs/cassowary/ClSolver.cc +++ /dev/null @@ -1,59 +0,0 @@ -// $Id$ - -using namespace std; - -#ifdef HAVE_CONFIG_H -#include -#define CONFIG_H_INCLUDED -#endif - -#include -#include -#include -#include -#include - - -ClSolver & -ClSolver::AddConstraint(ClConstraint *const ) -{ - return *this; -} - - -ostream & -PrintTo(ostream &xo, const ClConstraintSet &setCn) -{ - ClConstraintSet::const_iterator it = setCn.begin(); - for (; it != setCn.end(); ++it) { - const ClConstraint *pcn = *it; - xo << *pcn << endl; - } - return xo; -} - -ostream & -PrintTo(ostream &xo, const list &listFDN) -{ - list::const_iterator it = listFDN.begin(); - for (; it != listFDN.end(); ) { - FDNumber n = *it; - xo << n; - ++it; - if (it != listFDN.end()) - xo << ","; - } - return xo; -} - - -ostream &operator<<(ostream &xo, const ClConstraintSet &setCn) -{ return PrintTo(xo,setCn); } - - -ostream &operator<<(ostream &xo, const ClSolver &solver) -{ return solver.PrintOn(xo); } - -ostream &operator<<(ostream &xo, const list &listFDN) -{ return PrintTo(xo,listFDN); } - diff --git a/libs/cassowary/ClStrength.cc b/libs/cassowary/ClStrength.cc deleted file mode 100644 index 0629d4afff..0000000000 --- a/libs/cassowary/ClStrength.cc +++ /dev/null @@ -1,52 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClStrength.cc - -#include - -#ifdef HAVE_CONFIG_H -#include -#define CONFIG_H_INCLUDED -#endif - -// Use the singleton pattern for the strength objects -const ClStrength &ClsRequired() -{ - // required is distinct by equality to this static object, - // but I still use an especially high symbolic weight, just in case - // FIXGJB: hack? - static ClStrength required_strength("", 1000, 1000, 1000); - return required_strength; -} - -const ClStrength &ClsStrong() -{ - static ClStrength strong_strength("strong", 1.0, 0.0, 0.0); - return strong_strength; -} - -const ClStrength &ClsMedium() -{ - static ClStrength medium_strength("medium", 0.0, 1.0, 0.0); - return medium_strength; -} - - -const ClStrength &ClsWeak() -{ - static ClStrength weak_strength("weak", 0.0, 0.0, 1.0); - return weak_strength; -} - -// special case for when nLevels = 3, should assert nLevels() == 3 -ClStrength::ClStrength(const string &Name, double w1, double w2, double w3) : - _name(Name), _symbolicWeight(w1, w2, w3) -{ -} diff --git a/libs/cassowary/ClSymbolicWeight.cc b/libs/cassowary/ClSymbolicWeight.cc deleted file mode 100644 index 9dddaa5949..0000000000 --- a/libs/cassowary/ClSymbolicWeight.cc +++ /dev/null @@ -1,149 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClSymbolicWeight.cc - -#include -#include - -#ifdef HAVE_CONFIG_H -#include -#define CONFIG_H_INCLUDED -#endif - -// Help g++ out, tell it to instantiate this -//template vector &vector::operator =(const vector &); - -ClSymbolicWeight::ClSymbolicWeight(unsigned int CLevels, double value) : - _values(CLevels, value) -{ - assert(_values.size() == CLevels); -} - -ClSymbolicWeight::ClSymbolicWeight(double w1, double w2, double w3) -{ - _values.push_back(w1); - _values.push_back(w2); - _values.push_back(w3); - assert(_values.size() == 3); -} - -ClSymbolicWeight::ClSymbolicWeight(const vector &weights) : - _values(weights) -{ } - -ClSymbolicWeight & -ClSymbolicWeight::Zero() -{ - static ClSymbolicWeight Zero(0.0, 0.0, 0.0); - return Zero; -} - - -ClSymbolicWeight & -ClSymbolicWeight::negated() -{ - vector::iterator it = _values.begin(); - for (; it != _values.end(); ++it) - { - *it = -*it; - } - return *this; -} - -ClSymbolicWeight & -ClSymbolicWeight::MultiplyMe(Number n) -{ - vector::iterator it = _values.begin(); - for (; it != _values.end(); ++it) - { - *it *= n; - } - return *this; -} - - -ClSymbolicWeight -ClSymbolicWeight::DivideBy(Number n) const -{ - assert(n!=0); - ClSymbolicWeight clsw(0); - vector::const_iterator i = _values.begin(); - for (; i != _values.end(); ++i) - { - clsw.push_back(*i / n); - } - return clsw; -} - -ClSymbolicWeight & -ClSymbolicWeight::addtoMe(const ClSymbolicWeight &cl) -{ - assert(cl.CLevels() == CLevels()); - - vector::iterator i1 = _values.begin(); - vector::const_iterator i2 = cl._values.begin(); - for (; i1 != _values.end(); ++i1, ++i2) - { - *i1 += *i2; - } - return *this; -} - -ClSymbolicWeight -ClSymbolicWeight::Subtract(const ClSymbolicWeight &cl) const -{ - assert(cl.CLevels() == CLevels()); - - ClSymbolicWeight clsw(0); - vector::const_iterator i1 = _values.begin(); - vector::const_iterator i2 = cl._values.begin(); - for (; i1 != _values.end(); ++i1, ++i2) - { - clsw.push_back(*i1 - *i2); - } - return clsw; -} - - -bool -ClSymbolicWeight::lessThan(const ClSymbolicWeight &cl) const -{ - return _values < cl._values; -} - -bool -ClSymbolicWeight::lessThanOrEqual(const ClSymbolicWeight &cl) const -{ - return _values <= cl._values; -} - -bool -ClSymbolicWeight::equal(const ClSymbolicWeight &cl) const -{ - return _values == cl._values; -} - -bool -ClSymbolicWeight::greaterThan(const ClSymbolicWeight &cl) const -{ - return _values > cl._values; -} - -bool -ClSymbolicWeight::greaterThanOrEqual(const ClSymbolicWeight &cl) const -{ - return _values >= cl._values; -} - -bool -ClSymbolicWeight::isNegative() const -{ - return _values < Zero()._values; -} diff --git a/libs/cassowary/ClTableau.cc b/libs/cassowary/ClTableau.cc deleted file mode 100644 index 85ac841725..0000000000 --- a/libs/cassowary/ClTableau.cc +++ /dev/null @@ -1,297 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClTableau.cc - -using namespace std; - -#include -#include - -#ifdef HAVE_CONFIG_H -#include -#define CONFIG_H_INCLUDED -#endif - - -// delete the linear expressions -// let ClSimplexSolver worry about deleting the variables -ClTableau::~ClTableau() -{ - ClTableauRowsMap::iterator it = _rows.begin(); - for (; it != _rows.end(); ++it) - { - // free the ClLinearExpression that we new-ed -#ifdef CL_TRACE - cerr << "Deleting row delete@ " << ((*it).second) << endl; -#endif - delete (*it).second; - } -} - -#ifndef CL_NO_IO -// Some extra debugging info -ostream & -ClTableau::PrintInternalInfo(ostream &xo) const -{ - xo << "ncns:" << _rows.size() -1 - << "; cols:" << _columns.size() - << "; infrows:" << _infeasibleRows.size() - << "; ebvars:" << _externalRows.size() - << "; epvars:" << _externalParametricVars.size(); - return xo; -} - - -ostream & -ClTableau::printExternalVariablesTo(ostream &xo) const -{ - xo << "Parametric: "; - ClVarSet::iterator itParVars = _externalParametricVars.begin(); - for ( ; itParVars != _externalParametricVars.end(); ++itParVars ) { - ClVariable v = *itParVars; - xo << v << " "; - } - xo << "\nBasic: "; - ClVarSet::iterator itRowVars = _externalRows.begin(); - for ( ; itRowVars != _externalRows.end() ; ++itRowVars ) { - ClVariable v = *itRowVars; - xo << v << " "; - } - return xo << endl; -} - -#endif - - -// Add v, update column cross indices -// v becomes a basic variable -// expr is now owned by ClTableau class, -// and ClTableauis responsible for deleting it -// (also, expr better be allocated on the heap!) -void -ClTableau::addRow(ClVariable var, const ClLinearExpression &expr) -{ -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); - cerr << "(" << var << ", " << expr << ")" << endl; -#endif - _rows[var] = const_cast(&expr); - ClVarToNumberMap::const_iterator it = expr.Terms().begin(); - // for each variable in expr, Add var to the set of rows which have that variable - // in their Expression - for (; it != expr.Terms().end(); ++it) - { - ClVariable v = (*it).first; - _columns[v].insert(var); - if (v.IsExternal() && !FIsBasicVar(v)) - { - _externalParametricVars.insert(v); - } - } - if (var.IsExternal()) - { - _externalRows.insert(var); - } -#ifdef CL_TRACE - cerr << *this << endl; -#endif -} - -// Remove var from the tableau -- remove the column cross indices for var -// and remove var from every Expression in rows in which v occurs -// Remove the parametric variable var, updating the appropriate column and row entries. -// (Renamed from Smalltalk implementation's `removeParametricVar') -ClVariable -ClTableau::RemoveColumn(ClVariable var) -{ -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); - cerr << "(" << var << ")" << endl; -#endif - ClTableauColumnsMap::iterator it_var = _columns.find(var); - if (it_var == _columns.end()) - return var; // nothing to do - - ClVarSet &varset = (*it_var).second; - // remove the rows with the variables in varset - ClVarSet::iterator it = varset.begin(); - for (; it != varset.end(); ++it) - { - ClVariable v = (*it); - ClVarToNumberMap &Terms = _rows[v]->Terms(); - Terms.erase(Terms.find(var)); - } - if (var.IsExternal()) - { - _externalRows.erase(var); - _externalParametricVars.erase(var); - } - _columns.erase(it_var); - return var; -} - -// Remove the basic variable v from the tableau row v=expr -// Then update column cross indices -ClLinearExpression * -ClTableau::RemoveRow(ClVariable var) -{ -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); - cerr << "(" << var << ")" << endl; -#endif - ClTableauRowsMap::iterator it = _rows.find(var); - assert(it != _rows.end()); - ClLinearExpression *pexpr = (*it).second; - ClVarToNumberMap &Terms = pexpr->Terms(); - ClVarToNumberMap::iterator it_term = Terms.begin(); - for (; it_term != Terms.end(); ++it_term) - { - ClVariable v = (*it_term).first; - _columns[v].erase(var); - if (_columns[v].size() == 0) - { - _columns.erase(v); - _externalParametricVars.erase(v); - } - } - - _infeasibleRows.erase(var); - - if (var.IsExternal()) - { - _externalRows.erase(var); - _externalParametricVars.erase(var); - } - - _rows.erase(it); -#ifdef CL_TRACE - cerr << "- returning " << *pexpr << endl; -#endif - return pexpr; -} - -// Replace all occurrences of oldVar with expr, and update column cross indices -// oldVar should now be a basic variable -// Uses the Columns data structure and calls SubstituteOut on each -// row that has oldVar in it -// oldVar is leaving the basis, and becoming parametric -void -ClTableau::SubstituteOut(ClVariable oldVar, const ClLinearExpression &expr) -{ -#ifdef CL_TRACE - cerr << "* ClTableau::"; - Tracer TRACER(__FUNCTION__); - cerr << "(" << oldVar << ", " << expr << ")" << endl; - cerr << (*this) << endl; -#endif - - ClTableauColumnsMap::iterator it_oldVar = _columns.find(oldVar); - if (it_oldVar == _columns.end()) - return; - - ClVarSet &varset = (*it_oldVar).second; - ClVarSet::iterator it = varset.begin(); - for (; it != varset.end(); ++it) - { - ClVariable v = (*it); - ClLinearExpression *prow = _rows[v]; - prow->SubstituteOut(oldVar,expr,v,*this); - if (v.IsRestricted() && prow->Constant() < 0.0) - { - _infeasibleRows.insert(v); - } - } - _columns.erase(it_oldVar); - if (oldVar.IsExternal()) - { - if (_columns[oldVar].size() > 0) - { - _externalRows.insert(oldVar); - } - _externalParametricVars.erase(oldVar); - } -} - - -#ifndef CL_NO_IO - -ostream & -PrintTo(ostream &xo, const ClVarSet & varset) -{ - ClVarSet::const_iterator it = varset.begin(); - xo << "{ "; - if (it != varset.end()) - { - xo << *it; - ++it; - } - for (; it != varset.end(); ++it) - { - xo << ", " << *it; - } - xo << " }"; - return xo; -} - -ostream &operator<<(ostream &xo, const ClVarSet & varset) -{ return PrintTo(xo,varset); } - -ostream & -PrintTo(ostream &xo, const ClTableauColumnsMap & varmap) -{ - ClTableauColumnsMap::const_iterator it = varmap.begin(); - for (; it != varmap.end(); ++it) - { - xo << (*it).first << " -> " << (*it).second << endl; - } - return xo; -} - -ostream &operator<<(ostream &xo, const ClTableauColumnsMap & varmap) -{ return PrintTo(xo,varmap); } - -ostream & -PrintTo(ostream &xo, const ClTableauRowsMap & rows) -{ - ClTableauRowsMap::const_iterator it = rows.begin(); - for (; it != rows.end(); ++it) - { - ClVariable v = it->first; - const ClLinearExpression *pe = it->second; - xo << v << " <-=-> "; - if (pe) xo << *pe; else xo << "NilExpr"; - xo << endl; - } - return xo; -} - -ostream &operator<<(ostream &xo, const ClTableauRowsMap & rows) -{ return PrintTo(xo,rows); } - -ostream & -ClTableau::PrintOn(ostream &xo) const -{ - xo << "Tableau:\n" - << _rows << endl; - xo << "Columns:\n" - << _columns << endl; - xo << "Infeasible rows: " - << _infeasibleRows << endl; - xo << "External basic variables: " - << _externalRows << endl; - xo << "External parametric variables: " - << _externalParametricVars << endl; - return xo; -} - -ostream &operator<<(ostream &xo, const ClTableau &clt) -{ return clt.PrintOn(xo); } - -#endif diff --git a/libs/cassowary/ClTests.cc b/libs/cassowary/ClTests.cc deleted file mode 100644 index 606d6f3e44..0000000000 --- a/libs/cassowary/ClTests.cc +++ /dev/null @@ -1,884 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClTests.cc - -#include -#include -#include -#include -#include - -inline -double UniformRandom() -{ return double(rand())/RAND_MAX; } - - -bool -simple1() -{ - try - { - bool fOkResult = true; - ClVariable x(167); - ClVariable y(2); - ClSimplexSolver solver; - - ClLinearEquation eq(x,y+0.0); - solver.AddStay(x); - solver.AddStay(y); - solver.AddConstraint(eq); - cout << "x = " << x.Value() << endl - << "y = " << y.Value() << endl; - fOkResult = (x.Value() == y.Value()); - return fOkResult; - } - catch (ExCLError &error) - { - cerr << "Exception! " << error.description() << endl; - return(false); - } - catch (...) - { - cerr << "Unknown exception" << endl; - return(false); - } -} - - -/* Add an edit variable to an empty solver */ -bool -simple2() -{ - try - { - ClVariable x(167); - ClSimplexSolver solver; - - solver.AddEditVar(x); - solver.BeginEdit(); - solver.SuggestValue(x,100); - solver.EndEdit(); - - cout << "x = " << x.Value() << endl; - } - catch (ExCLEditMisuse &error) - { - cout << "Success: got the exception" << endl; - return true; - } - catch (ExCLError &error) - { - cerr << "Exception! " << error.description() << endl; - return(false); - } - catch (...) - { - cerr << "Unknown exception" << endl; - return(false); - } - cerr << "Should have gotten an exception!" << endl; - return false; -} - - -bool -justStay1() -{ - try - { - bool fOkResult = true; - ClVariable x(5); - ClVariable y(10); - ClSimplexSolver solver; - -#if 0 - solver.AddPointStay(x,y,1); -#else - solver.AddStay(x); - solver.AddStay(y); -#endif - fOkResult = fOkResult && ClApprox(x,5); - fOkResult = fOkResult && ClApprox(y,10); - cout << "x == " << x.Value() << endl; - cout << "y == " << y.Value() << endl; - - return(fOkResult); - } - catch (ExCLError &error) - { - cerr << "Exception! " << error.description() << endl; - return(false); - } - catch (...) - { - cerr << "Unknown exception" << endl; - return(false); - } -} - - - -bool -addDelete1() -{ - try - { - bool fOkResult = true; - ClVariable x("x"); - ClSimplexSolver solver; - - solver.AddConstraint(new ClLinearEquation( x, 100, ClsWeak() )); - - ClLinearInequality c10(x,cnLEQ,10.0); - ClLinearInequality c20(x,cnLEQ,20.0); - solver - .AddConstraint(c10) - .AddConstraint(c20); - - fOkResult = fOkResult && ClApprox(x,10.0); - cout << "x == " << x.Value() << endl; - - cout << endl << solver << endl; - - solver.RemoveConstraint(c10); - - cout << endl << solver << endl; - - fOkResult = fOkResult && ClApprox(x,20.0); - cout << "x == " << x.Value() << endl; - - solver.RemoveConstraint(c20); - fOkResult = fOkResult && ClApprox(x,100.0); - cout << "x == " << x.Value() << endl; - - ClLinearInequality c10again(x,cnLEQ,10.0); - - solver - .AddConstraint(c10) - .AddConstraint(c10again); - - fOkResult = fOkResult && ClApprox(x,10.0); - cout << "x == " << x.Value() << endl; - - solver.RemoveConstraint(c10); - fOkResult = fOkResult && ClApprox(x,10.0); - cout << "x == " << x.Value() << endl; - - solver.RemoveConstraint(c10again); - fOkResult = fOkResult && ClApprox(x,100.0); - cout << "x == " << x.Value() << endl; - - return(fOkResult); - } - catch (ExCLError &error) - { - cerr << "Exception! " << error.description() << endl; - return(false); - } - catch (...) - { - cerr << "Unknown exception" << endl; - return(false); - } -} - -bool -addDelete2() -{ - try - { - bool fOkResult = true; - ClVariable x("x"); - ClVariable y("y"); - ClSimplexSolver solver; - - solver - .AddConstraint(new ClLinearEquation(x, 100.0, ClsWeak())) - .AddConstraint(new ClLinearEquation(y, 120.0, ClsStrong())); - - ClLinearInequality c10(x,cnLEQ,10.0); - ClLinearInequality c20(x,cnLEQ,20.0); - - solver - .AddConstraint(c10) - .AddConstraint(c20); - fOkResult = fOkResult && ClApprox(x,10.0) && ClApprox(y,120.0); - cout << "x == " << x.Value() << ", y == " << y.Value() << endl; - - solver.RemoveConstraint(c10); - fOkResult = fOkResult && ClApprox(x,20.0) && ClApprox(y,120.0); - cout << "x == " << x.Value() << ", y == " << y.Value() << endl; - - ClLinearEquation cxy( 2*x, y); - solver.AddConstraint(cxy); - fOkResult = fOkResult && ClApprox(x,20.0) && ClApprox(y,40.0); - cout << "x == " << x.Value() << ", y == " << y.Value() << endl; - - solver.RemoveConstraint(c20); - fOkResult = fOkResult && ClApprox(x,60.0) && ClApprox(y,120.0); - cout << "x == " << x.Value() << ", y == " << y.Value() << endl; - - solver.RemoveConstraint(cxy); - fOkResult = fOkResult && ClApprox(x,100.0) && ClApprox(y,120.0); - cout << "x == " << x.Value() << ", y == " << y.Value() << endl; - - - return(fOkResult); - } - catch (ExCLError &error) - { - cerr << "Exception! " << error.description() << endl; - return(false); - } - catch (...) - { - cerr << "Unknown exception" << endl; - return(false); - } -} - -bool -casso1() -{ - try - { - bool fOkResult = true; - ClVariable x("x"); - ClVariable y("y"); - ClSimplexSolver solver; - - solver - .AddConstraint(new ClLinearInequality(x,cnLEQ,y)) - .AddConstraint(new ClLinearEquation(y, x+3.0)) - .AddConstraint(new ClLinearEquation(x,10.0,ClsWeak())) - .AddConstraint(new ClLinearEquation(y,10.0,ClsWeak())) - ; - - fOkResult = fOkResult && - ( ClApprox(x,10.0) && ClApprox(y,13.0) || - ClApprox(x,7.0) && ClApprox(y,10.0) ); - - cout << "x == " << x.Value() << ", y == " << y.Value() << endl; - - return(fOkResult); - } - catch (ExCLError &error) - { - cerr << "Exception! " << error.description() << endl; - return(false); - } - catch (...) - { - cerr << "Unknown exception" << endl; - return(false); - } -} - -bool -inconsistent1() -{ - ClSimplexSolver solver; - ClVariable x("x"); - ClLinearEquation eq1(x,10.0); - ClLinearEquation eq2(x,5.0); - try - { - - solver.AddConstraint( eq1 ); - solver.AddConstraint( eq2 ); - - // no exception, we failed! - return(false); - } - catch (ExCLRequiredFailure) - { - // we want this exception to get thrown - cout << "Success -- got the exception" << endl; - // solver.RemoveConstraint(eq2); this would throw a constraint not found exception - // cout << solver << endl; - return(true); - } - catch (ExCLError &error) - { - cerr << "Exception! " << error.description() << endl; - return(false); - } - catch (...) - { - cerr << "Unknown exception" << endl; - return(false); - } -} - -bool -inconsistent2() -{ - try - { - ClVariable x("x"); - ClSimplexSolver solver; - - solver - .AddConstraint(new ClLinearInequality(x,cnGEQ,10.0)) - .AddConstraint(new ClLinearInequality(x,cnLEQ, 5.0)); - - // no exception, we failed! - return(false); - } - catch (ExCLRequiredFailure &) - { - // we want this exception to get thrown - cout << "Success -- got the exception" << endl; - // cout << solver << endl; - return(true); - } - catch (ExCLError &error) - { - cerr << "Exception! " << error.description() << endl; - return(false); - } - catch (...) - { - cerr << "Unknown exception" << endl; - return(false); - } -} - -bool -inconsistent3() -{ - try - { - ClVariable w("w"); - ClVariable x("x"); - ClVariable y("y"); - ClVariable z("z"); - ClSimplexSolver solver; - - solver - .AddConstraint(new ClLinearInequality(w,cnGEQ,10.0)) - .AddConstraint(new ClLinearInequality(x,cnGEQ,w)) - .AddConstraint(new ClLinearInequality(y,cnGEQ,x)) - .AddConstraint(new ClLinearInequality(z,cnGEQ,y)) - .AddConstraint(new ClLinearInequality(z,cnLEQ,4.0)); - - // no exception, we failed! - return(false); - } - catch (ExCLRequiredFailure &) - { - // we want this exception to get thrown - cout << "Success -- got the exception" << endl; - // cout << solver << endl; - return(true); - } - catch (ExCLError &error) - { - cerr << "Exception! " << error.description() << endl; - return(false); - } - catch (...) - { - cerr << "Unknown exception" << endl; - return(false); - } -} - - -bool -multiedit() -{ - try - { - bool fOkResult = true; - - ClVariable x("x",0); - ClVariable y("y",0); - ClVariable w("w",0); - ClVariable h("h",0); - ClSimplexSolver solver; - - solver - .AddStay(x) - .AddStay(y) - .AddStay(w) - .AddStay(h); - - solver - .AddEditVar(x) - .AddEditVar(y) - .BeginEdit(); - - solver - .SuggestValue(x,10) - .SuggestValue(y,20) - .Resolve(); - - cout << "x = " << x.Value() << "; y = " << y.Value() << endl - << "w = " << w.Value() << "; h = " << h.Value() << endl; - - fOkResult = fOkResult && - ClApprox(x,10) && ClApprox(y,20) && ClApprox(w,0) && ClApprox(h,0); - - solver - .AddEditVar(w) - .AddEditVar(h) - .BeginEdit(); - - solver - .SuggestValue(w,30) - .SuggestValue(h,40) - .EndEdit(); - - cout << "x = " << x.Value() << "; y = " << y.Value() << endl - << "w = " << w.Value() << "; h = " << h.Value() << endl; - - fOkResult = fOkResult && - ClApprox(x,10) && ClApprox(y,20) && ClApprox(w,30) && ClApprox(h,40); - - solver - .SuggestValue(x,50) - .SuggestValue(y,60) - .EndEdit(); - - cout << "x = " << x.Value() << "; y = " << y.Value() << endl - << "w = " << w.Value() << "; h = " << h.Value() << endl; - - fOkResult = fOkResult && - ClApprox(x,50) && ClApprox(y,60) && ClApprox(w,30) && ClApprox(h,40); - - return fOkResult; - } - catch (ExCLError &error) - { - cerr << "Exception! " << error.description() << endl; - return(false); - } - catch (...) - { - cerr << "Unknown exception" << endl; - return(false); - } - cerr << "Should have gotten an exception!" << endl; - return false; -} - - -bool -multiedit2() -{ - try - { - bool fOkResult = true; - - ClVariable x("x",0); - ClVariable y("y",0); - ClVariable w("w",0); - ClVariable h("h",0); - ClSimplexSolver solver; - - solver - .AddStay(x) - .AddStay(y) - .AddStay(w) - .AddStay(h); - - solver - .AddEditVar(x) - .AddEditVar(y) - .BeginEdit(); - - solver - .SuggestValue(x,10) - .SuggestValue(y,20) - .Resolve(); - - cout << "x = " << x.Value() << "; y = " << y.Value() << endl - << "w = " << w.Value() << "; h = " << h.Value() << endl; - - fOkResult = fOkResult && - ClApprox(x,10) && ClApprox(y,20) && ClApprox(w,0) && ClApprox(h,0); - - solver - .AddEditVar(x) - .AddEditVar(y) - .AddEditVar(w) - .AddEditVar(h) - .BeginEdit(); - - solver - .SuggestValue(w,30) - .SuggestValue(h,40) - .EndEdit(); - - cout << "x = " << x.Value() << "; y = " << y.Value() << endl - << "w = " << w.Value() << "; h = " << h.Value() << endl; - - fOkResult = fOkResult && - ClApprox(x,10) && ClApprox(y,20) && ClApprox(w,30) && ClApprox(h,40); - - solver - .SuggestValue(x,50) - .SuggestValue(y,60) - .EndEdit(); - - cout << "x = " << x.Value() << "; y = " << y.Value() << endl - << "w = " << w.Value() << "; h = " << h.Value() << endl; - - fOkResult = fOkResult && - ClApprox(x,50) && ClApprox(y,60) && ClApprox(w,30) && ClApprox(h,40); - - return fOkResult; - } - catch (ExCLError &error) - { - cerr << "Exception! " << error.description() << endl; - return(false); - } - catch (...) - { - cerr << "Unknown exception" << endl; - return(false); - } - cerr << "Should have gotten an exception!" << endl; - return false; -} - - -// From a bug report from Steve Wolfman on his -// SAT project using "blackbox" -bool -blackboxsat() -{ - try - { - ClSimplexSolver solver; - - ClVariable r1("r1"); - ClVariable r2("r2"); - ClVariable r3("r3"); - ClVariable r4("r4"); - ClVariable r5("r5"); - ClVariable r6("r6"); - ClVariable r7("r7"); - ClVariable r8("r8"); - - ClConstraint *rgpcn[30]; - for (int i=0; i> szCmd; - if (!cin) - break; - if (szCmd[0] == '#') - { - cin.getline(szCmd,900); - continue; - } - if (strcasecmp(szCmd,"Add") == 0) - { - cin >> i; - cout << "eq" << i << ": " << solver.AddConstraintNoException(rgpcn[i]) - << "\t" << *(rgpcn[i]) << endl; - cout << r1 << " = " << r1.Value() << endl; - } - else if (strcasecmp(szCmd,"del") == 0) - { - cin >> i; - cout << "REMeq" << i << ": " << solver.RemoveConstraintNoException(rgpcn[i]) - << "\t" << *(rgpcn[i]) << endl; - cout << r1 << " = " << r1.Value() << endl; - } - else if (strcasecmp(szCmd,"dump") == 0) - { - cout << solver << endl; - } - else if (strcasecmp(szCmd,"val") == 0) - { - cout << r1 << " = " << r1.Value() << endl; - } - else if (strcasecmp(szCmd,"solve") == 0) - { - cout << solver.Solve() << endl; - } - else if (strcasecmp(szCmd,"autosolve") == 0) - { - solver.SetAutosolve(true); - } - else if (strcasecmp(szCmd,"noautosolve") == 0) - { - solver.SetAutosolve(true); - } - } - - cout << r1 << " = " << r1.Value() << endl - << r2 << " = " << r2.Value() << endl - << r3 << " = " << r3.Value() << endl - << r4 << " = " << r4.Value() << endl - << r5 << " = " << r5.Value() << endl - << r6 << " = " << r6.Value() << endl - << r7 << " = " << r7.Value() << endl - << r8 << " = " << r8.Value() << endl; - - return false; - } - catch (ExCLError &error) - { - cerr << "Exception! " << error.description() << endl; - return(true); - } - catch (...) - { - cerr << "Unknown exception" << endl; - return(false); - } -} - -typedef ClVariable *PClVariable; - -bool -addDel(const int nCns = 900, const int nVars = 900, const int nResolves = 10000) -//addDel(int nCns = 300, int nVars = 300, int nResolves = 1000) -//addDel(int nCns = 30, int nVars = 30, int nResolves = 100) -{ - Timer timer; - // FIXGJB: from where did .12 come? - static const double ineqProb = 0.12; - static const int maxVars = 3; - - cout << "starting timing test. nCns = " << nCns - << ", nVars = " << nVars << ", nResolves = " << nResolves << endl; - - timer.Start(); - ClSimplexSolver solver; - solver.SetAutosolve(false); - - ClVariable **rgpclv = new PClVariable[nVars]; - for (int i = 0; i < nVars; i++) - { - rgpclv[i] = new ClVariable(i,"x"); - solver.AddStay(*rgpclv[i]); - } - - ClConstraint **rgpcns = new PClConstraint[nCns]; - int nvs = 0; - int k; - int j; - double coeff; - for (j = 0; j < nCns; j++) - { - // number of variables in this constraint - nvs = int(UniformRandom()*maxVars) + 1; - ClLinearExpression expr = UniformRandom()*20.0 - 10.0; - for (k = 0; k < nvs; k++) - { - coeff = UniformRandom()*10 - 5; - expr.AddExpression(*(rgpclv[int(UniformRandom()*nVars)]) * coeff); - } - if (UniformRandom() < ineqProb) - { - rgpcns[j] = new ClLinearInequality(expr); - } - else - { - rgpcns[j] = new ClLinearEquation(expr); - } -#ifdef CL_SHOW_CNS_IN_BENCHMARK - cout << "Cn[" << j << "]: " << *rgpcns[j] << endl; -#endif - } - - cout << "done building data structures" << endl; - cout << "time = " << timer.ElapsedTime() << "\n" << endl; - timer.Start(); - int cExceptions = 0; -#ifdef CL_SHOW_CNS_IN_BENCHMARK - cout << "Exceptions on: "; -#endif - for (j = 0; j < nCns; j++) - { - // Add the constraint -- if it's incompatible, just ignore it - try - { - solver.AddConstraint(rgpcns[j]); - } - catch (ExCLRequiredFailure &) - { - cExceptions++; - rgpcns[j] = NULL; -#ifdef CL_SHOW_CNS_IN_BENCHMARK - cout << j << " "; -#endif - } - } -#ifdef CL_SHOW_CNS_IN_BENCHMARK - cout << "\n" << endl; -#endif - solver.Solve(); - cout << "done adding constraints [" << cExceptions << " exceptions]" << endl; - cout << "time = " << timer.ElapsedTime() << "\n" << endl; - cout << "time per cn = " << timer.ElapsedTime()/nCns << "\n" << endl; - cout << "time per actual cn = " << timer.ElapsedTime()/(nCns - cExceptions) << "\n" <Value()*1.001) - .SuggestValue(e2,e2->Value()*1.001) - .Resolve(); - } - solver.EndEdit(); - // cout << "run time: " << - - cout << "done resolves -- now removing constraints" << endl; - cout << "time = " << timer.ElapsedTime() << "\n" < 1) - cns = atoi(argv[1]); - - if (argc > 2) - vars = atoi(argv[2]); - - if (argc > 3) - resolves = atoi(argv[3]); - - if (cns > 0) - { - cout << "addDel" << ":" << endl; - fResult = addDel(cns,vars,resolves); fAllOkResult &= fResult; - if (!fResult) cout << "Failed!" << endl; - } - -#undef RUN_TEST - -#ifdef CL_FIND_LEAK - cout << "ClAbstractVariables: " << ClAbstractVariable::cAbstractVariables - << "\nClDummyVariables: " << ClDummyVariable::cDummyVariables - << "\nClSlackVariables: " << ClSlackVariable::cSlackVariables - << endl; -#endif - - - return (fAllOkResult? 0 : 255); - - } - catch (...) - { - cerr << "exception!" << endl; - } -} diff --git a/libs/cassowary/ClVariable.cc b/libs/cassowary/ClVariable.cc deleted file mode 100644 index 2a136c1096..0000000000 --- a/libs/cassowary/ClVariable.cc +++ /dev/null @@ -1,21 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClVariable.cc - -#include - -#ifdef HAVE_CONFIG_H -#include -#define CONFIG_H_INCLUDED -#endif - -StringToVarMap *ClVariable::pmapStrPclv = NULL; -ClVariable clvNil(static_cast(0)); - diff --git a/libs/cassowary/IMPORTANT b/libs/cassowary/IMPORTANT deleted file mode 100644 index 1edaabfa01..0000000000 --- a/libs/cassowary/IMPORTANT +++ /dev/null @@ -1,26 +0,0 @@ -Cassowary/C++ needs to be compiled using a modern C++ compiler. -At one time or another, it has compiled using: - o egcs-1.0.1, egcs-1.0.3, egcs-1.1b, gcc-2.8.1, gcc-2.95.2 - o Visual C++ 5.0 - -Cassowary/Java was developed using Sun's JDK-1.1.3, ported to Linux -More recent versions should work fine, and it has been tested -with JDK-1.2pre2. - -The included Makefiles depend upon features of GNU Make. See: - -ftp://ftp.gnu.org/pub/gnu/ - -for a version that you can build. - - -To build the c++/qdemos/QuadDemo application, you'll need TrollTech's Qt -widget set for X11, available from: - -http://www.troll.no/dl/qtfree-dl.html - - -See also the Scwm (Scheme Constraints Window Manager) web page for a use -of Cassowary in a substantial application: - -http://scwm.mit.edu/scwm/ diff --git a/libs/cassowary/LICENSE b/libs/cassowary/LICENSE deleted file mode 100644 index 21ecedf70d..0000000000 --- a/libs/cassowary/LICENSE +++ /dev/null @@ -1,18 +0,0 @@ -Cassowary Constraint Solving Toolkit -Copyright (C) 1998-200 Greg J. Badros - -This library is free software; you can redistribute it and/or -modify it under the terms of the GNU Lesser General Public -License as published by the Free Software Foundation; either -version 2.1 of the License, or (at your option) any later version. - -This library is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU -Lesser General Public License for more details. - -You should have received a copy of the GNU Lesser General Public -License along with this library; if not, write to the Free Software -Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -See COPYING.LGPL diff --git a/libs/cassowary/NEWS b/libs/cassowary/NEWS deleted file mode 100644 index 0f950dacef..0000000000 --- a/libs/cassowary/NEWS +++ /dev/null @@ -1,229 +0,0 @@ -Cassowary NEWS -- history of user-visible changes. -*- text -*- - -Cassowary Constraint Solving Toolkit was -Implemented by: - -Greg J. Badros and -Alan Borning -University of Washington -Computer Science and Engineering -Seattle, WA 98195-2350 - -with Constraint Drawing Applet (CDA) by Michael Noth - -12-March-2000: Version 0.60 released. -* Changed license to LGPL!!! -* Added SetAutoResetStayConstants(), FIsAutoResetStayConstants(), make ResetStayConstants() public - -29-Jan-2000: Version 0.55 released. -* Some bug fixes -* Added ClSimplexSolver::{ChangeStrength,ChangeStrengthAndWeight,ChangeWeight, - DisplayObjective,ExternalResetStayConstants} fns - From A. Beurivé. - -16-Dec-1999: Version 0.54a released. -* Include correct version of OTI Smalltalk .dat file - (the source in the *.app files was right, the .dat file was old) -* Fix java build bug - -15-Dec-1999: Version 0.54 released. -* Bug fixes -* auto-configuration improvements -* Support Java 2 (jdk-1.2) -* Improved ease of building Java demos -* Build guile wrapper as long as guile-config works, use new --disable-guile-build to force off -* Alpha-version of Java constraint parser contributed by Will Portnoy - -24-October-1999: Version 0.53 released. -* Bug fixes -* License exception for linking with Scwm. - -25-September-1999: Version 0.52 released. -* Bug fix for nested edits where a later edit includes an already-being-edited variable - -14-September-1999: Version 0.51 released. -* Minor bug fixes -* Much better packaging, RPMs, etc. more forced reliance on GTL - -26-August-1999: Version 0.51 pre-releases begin - -12-July-1999: Version 0.50 released. -* Made only C++ version build by default, --enable-java-build is needed to turn java on -* Added restricted finite domain solver -** needs --with-gtl configure option, and libGTL.{a,so*} to be installed -* Added ClSolver base class, and use its type for pointers in callbacks - -14-Apr-1999: Version 0.43 released. -* DEBUG_PARSE turned off by default -* Added cassowary.spec for RPM building - -31-Mar-1999: Version 0.42 released. -* Fixed autoconf bugs (.41 was a buggy release) -* Added --disable-cpp-build,--disable-java-build, and disable Python/Guile builds -automatically if directories cannot be found - -20-Mar-1999: Version 0.41 released. -* Fixed bug in autoconf support -- config.sub, config.guess to the -distribution so configure should actually work (they were symlinks -before, in error). - -18-Mar-1999: Version 0.4 released. - -18-Mar-1999: Changes since Cassowary v0.32 (for release v0.4) -* MUCH improved autoconf/automake support including numerous configure -options, added libtool support. -* Renamed many identifiers in the public API; this will break old code -using Cassowary. See the scripts/convert-ids script for help converting -your code (beware false positives; i.e., improper or unnecessary -changes). - - -10-Mar-1999: Changes since Cassowary v0.31 (for release v0.32) -* Added automake/autoconf support. Old Makefiles are now -Makefile.linux. This is not yet fully tested or correct, but I need to -make a release now for the bug fixes. Consider compiling with "make -f -Makefile.linux all" if you have problems running autoconf and/or -automake. - -* Changes to C++ -** Bug fix for problem Anthony Beurivé noticed regarding removing non-1 -weight stay constraints. -** Minor bug fix for parser. Also renamed the creader files to ClReader. - -* Changes to Java -** Bug fix for problem Emmanuel Pietriga reported regarding edit -constraints. -** Improved debugging support a bit by adding descriptions to -ExCLInternalError-s and assert()s - -* Changes to guile wrapper -** changed name of library to libcassowaryguile.a from libconstraints.a - - -1-Mar-1999: Changes since Cassowary v0.3 (for release v0.31) -* Changes to C++ -** Some bug fixes -- pass ClVariable-s around by value instead of const -& since they are now a handle class. -** Changed output format for ClEditConstraint, ClStayConstraint instances -** Use a function-object for controlling lookup/creation of variables in PcnParseConstraint -** Fix bugs in creader.y parser (did not accept parens or division -before). Introduced "==" as a a synonym for "=" -** Added szCassowaryVersion id string as a public char *. -** Added ChangeStrength, ChangeWeight to ClConstraint's public -interface, and have it valid only when the constraint is not in a solver -** Added ClConstraint::FIsInSolver() - -* Changes to Guile wrapper -** Fix bugs -** Wrap parsing functionality, including a lambda for lookup/creation of -variables -** Build a dynamically-loadable guile module, update cltests.scm to use it - - -23-Feb-1999: Version 0.3 released. - -19-Feb-1999, Changes since Cassowary v0.23 (for release v0.3) - -* Changes to Java and C++ -** Bug fix for Michael Kaufmann's report (see ChangeLog for details) -** resolve(Vector..) procedure is now depracated; preferred interface is -suggestValue(...) calls followed by resolve() (the one taking no -arguments). -** Added ClVariable::SetVarMap(..), ClVariable::VarMap() to permit -ClVariable ctr to save the mapping between given name and actual object -in a symbol table (used for parsing ascii expressions in C++ version) - -* Changes to just C++ implementation -** Use ClVariable as a handle class to a ClAbstractVariable-- old -ClVariable is now a ClFloatVariable. SetChangeClvCallback now takes a -function that takes a ClVariable handle, not a pointer. -** Passing ClConstraints's by const & is now deprecated -- pass by -pointer to the ClConstraint object -** Added creader.y, creader.l and function PcnParseConstraint(..) for -creating a constraint from an ASCII string. -** Added CL_NO_IO compile-time option to C++ version for preventing need -to link with the stream library (is not complete) -** Added CL_FIND_LEAK compile-time option for counting ctrs/dtr -invocations -** Added CL_USE_HASH_MAP compile-time option to permit using the GNU -hash_map class instead of the standard STL map (which is a sorted -associative container whose performance for lookups is logarithmic -rather than constant time). Still does not work for me --02/16/99 gjb. - -* Changes to just Java implementation (updated to match changes to C++ -version for .2) -** Added {get,set}AttachedObject for ClVariable, ClConstant -** Permit access to ClSimplexSolver.ConstraintMap() -** Permit nested beginEdit()s and handle them correctly - -* Miscellaneous changes -** Updated copyright to include 1999 -** Fixed wrappers/Makefile for building Python wrapper -** Reference Anthony Beurivé's STk wrapper -** Fix Scwm URL - - -30-Jan-1999, Changes since Cassowary v0.22 (for release v0.23) -* Bug fix (see ChangeLog for details) - - -23-Jan-1999, Changes since Cassowary v0.21 (for release v0.22) -* Minor code cleanup, additions of comments. - - -14-Sep-98, Changes since Cassowary v0.2 (for release v0.21) - -* Make compile cleanly using egcs-1.1b -- use typename, and drop - unused templated instantiation - -* Improved guile interface: add a void pointer to the solver objects, - and let the guile wrapper use it to keep a pointer to the scheme-level - object; also added clv-attach! and clv-attached-object for attaching - an object to a cl-variable (somewhat redundant with guile's - object properties) - -* Wrap ClStayConstraints so they can be managed explicitly - -* cl-add-stay, cl-add-editvar now take strength and factor arguments, - instead of a list of cl-vars - -* Added weight option to addEditVar - - -6-Aug-98, Changes since Cassowary v0.1 (for release v0.2): - -* Changes to the distribution for release v0.2 - -** added guile/scheme wrapper of C++ version - -** mention SCWM in README - -** mention non-maintenance of Smalltalk implementation unless we have users - -* Changes to the C++ and Java implementations - -** Fixed several bugs -- dummy variables were wrongly being pivoted into - the basis, and constraints that threw required failure exceptions - were mistakenly remaining in the tableau (now trying to remove an - exception that was not added because of a required-failure exception - will correctly throw a ConstraintNotFound exception); more -- see ChangeLog - -** Added a virtual change_value function to permit applications to watch - for changes made to external variables. - -* Changes to only the C++ version (Java version will catch up in 0.3) - -** Added new test cases to ClTests, fixed bugs in ClTestColumns - -** Added _pv (void *) field hanging off of ClConstraint and ClVariable - for associating arbitrary structs with those (needed by SCWM) - -** Permit nested beginEdit()s, and do the right thing upon calling - endEdit() -- i.e., not all the edit variables are removed, only the - nested ones - -** Permit access to ClSimplexSolver::ConstraintMap() (used by - guile-wrapper to efficiently get at a list of constraints in the - solver) - -** Added ExCLEditMisuse exception diff --git a/libs/cassowary/README b/libs/cassowary/README deleted file mode 100644 index 16ed492b8e..0000000000 --- a/libs/cassowary/README +++ /dev/null @@ -1,241 +0,0 @@ -Cassowary Constraint Solving Toolkit for C++, Java, and Smalltalk -Version 0.60 - -Web Page: http://www.cs.washington.edu/research/constraints/cassowary -Contact: cassowary@cs.washington.edu - -Greg J. Badros and -Alan Borning -University of Washington -Computer Science and Engineering -Seattle, WA 98195-2350 -12-March-2000 - -with Constraint Drawing Applet (CDA) by Michael Noth - -See ANNOUNCE for a brief description and announcement of this distribution. -See NEWS for a history of user-visible changes. -See ChangeLog for a detailed listing of the changes to each source file. -See LICENSE for legalese regarding use of this distribution. - -The Smalltalk implementation is in the public domain -- see smalltalk/README. - -Please send bug reports to cassowary@cs.washington.edu - -Also, send mail to cassowary@cs.washington.edu if you would like to be -informed about bug fixes, feature enhancements, etc. Let us know what -implementation(s) you are using, too. - ------------------------------------------------------------------- - -HOW TO GET STARTED - -The Cassowary library uses GNU autoconf to permit easy building on -various platforms. You should be able to do: - -./configure -make - -and everything will work. A more complex, but realistic example is: - -./configure --with-prefix=/usr/contrib \ - --with-guile-prefix=/usr/contrib \ - --with-python-headers=/usr/include/python1.5 \ - --enable-java-build \ - --with-gtl=/usr/contrib \ - --with-java-class-path=/usr/contrib/share/java/site \ - --enable-warnings -make -k - -Be sure to give the extra --enable-permissive flag to configure if -you are building with gcc-2.95 or more recent. - -As yet another data point, I build Cassowary with: - -./configure --with-guile-exec-prefix=/uns/bin \ - --with-guile-prefix=/uns/share --prefix=/uns/share \ - --exec-prefix=/uns --enable-maintainer-mode - -See the file "INSTALL" for more details about -autoconf support and the options that the "configure" takes. You can -also do "./configure --help" for the list of the options that configure -accepts. - -If the make in any of the subdirectories fails, you can turn on the "-k" -option to make, or just do make in the subdirectories that you want -build. E.g., if you do not have the JDK installed, the Java version of -Cassowary might not compile; if you still want the guile version, just -"cd guile; make -k". - -Be sure that configure detects the validity of using the "-fpermissive" -flag of more recent g++/egcs compilers to work around some -const-discrepancies between the const-challenged guile header files and -Cassowary's more const-correct usage. You should get a message like: - - checking whether gcc understands -fpermissive option... yes - -when running configure if you're using, e.g., gcc-2.95 or later. - -You need to apply GTL.h.patch to the installed GTL.h header file for -Cassowary to compile with recent versions of egcs/gcc (e.g., gcc-2.95). - -Also, you may need to change libguile/gsubr.h from: - - extern SCM scm_make_gsubr SCM_P ((char *name, int req, int opt, - int rst, SCM (*fcn)())); - to - - extern SCM scm_make_gsubr SCM_P ((char *name, int req, int opt, - int rst, void*)); - -or patch guile's snarf.h to insert the appropriate case at each call to -SCM_PROC and SCM_PROC1. (Thanks to Alexandre Duret-Lutz for the above -information about more recent g++/egcs compilers). - -Note that the generated Makefiles depend upon features of GNU Make. See: - -ftp://ftp.gnu.org/pub/gnu/ - -for a version of make that you can build first to then build Cassowary. - -Example applications exist in subdirectories of the top-level -implementation subdirectories (e.g., c++/qdemos contains demos for C++ -that use the Qt Widget toolkit). - -Please send mail to cassowary@cs.washington.edu if you are using this -toolkit so we know how to reach you for bug fixes, updates, etc. - ------------------------------------------------------------------- - -WHAT THE DISTRIBUTION CONTAINS - -This distribution contains 3 implementations of the Cassowary constraint -solving toolkit: - -o C++ -o Java -o Smalltalk - -For each implementation language, there is at least one example program; -for some there are many. - -There is a wrapping of the C++ solver in Guile-Scheme -- see the guile/ -subdirectory. Also, Anthony Beurivé has wrapped Cassowary for -STk/Scheme. His code is available at: - - http://dept-info.labri.u-bordeaux.fr/~beurive/Code - -and the STk Scheme system is available at: - - http://kaolin.unice.fr/STk/ - -There is also a SWIG-generated wrapper of the C++ library making the -solver available from the Python language. - -A technical report describing the solver, its interface, and its -implementation is in cassowary-tr.ps (pdf version in cassowary-tr.pdf). -This paper is required reading if you intend to use the solver in your -own project(s). - -See also the Scwm (Scheme Constraints Window Manager) web page: - -http://scwm.mit.edu/scwm/ - -Scwm, also by Greg Badros (and Maciej Stachowiak), is the most -substantial application using this toolkit that we are aware of. - ------------------------------------------------------------------- - -VARIOUS IMPLEMENTATION NOTES - -Cassowary/C++ needs to be compiled using a modern C++ compiler. -At one time or another, it has compiled using: - o egcs-1.0.1 - o egcs-1.0.3a - o egcs-1.1b - o egcs-1.1.1 - o gcc-2.8.1 (needs libstdc++-2.8.x, too) - o Visual C++ 5.0 (not tried recently) - -In particular, Cassowary will *not* build with gcc-2.7.x.x! - -See c++/README for more details about building the C++ version. - -The C++ implementation of the toolkit also has an optional finite domain -subsolver. You need to build and install the GTL -- the Graph Template -Library -- and use the "--with-gtl=DIR" configure option for the finite -domain subsolver to be built. GTL is available from: - -http://www.fmi.uni-passau.de/Graphlet/GTL/ - -Cassowary was tested against GTL-0.3.1; it may work with later -versions, but I have not tried it. You need to apply GTL.h.patch to -the installed GTL.h header file for Cassowary to compile with recent -versions of egcs/gcc (e.g., gcc-2.95). - -Cassowary/Java was developed using Sun's JDK-1.1.x, ported to Linux -More recent versions should work fine. - -See java/README for more details about building the Java version. - - -Cassowary/Smalltalk was written under OTI Smalltalk-- other versions of -smalltalk will likely require (possibly significant) changes. - -See smalltalk/README for more details about the Smalltalk version. - -See guile/README for details about the Guile Scheme wrapper of the C++ -implementation, and for a pointer to SCWM, the Scheme Constraints Window -Manager which uses Cassowary. - -The Python bindings (by Tessa Lau) bindings for the Cassowary library -are in the wrappers/ subdirectory. SWIG was used in wrapping the -library. These bindings may no longer work, and are provided only for -your hacking pleasure (please send back useful patches if you do get the -code working). - -For more information about SWIG, see: - -http://www.swig.org/ - - -For more information about the Python language, see: - -http://www.python.org/ - - -For more information about the Guile-Scheme language, see: - -http://www.red-bean.com/guile/ -http://www.fsf.org/software/guile/guile.html - - ------------------------------------------------------------------- - -DEMONSTRATION APPLICATION - -A standard demonstration application is included for each implementation -of the Cassowary solver. The application builds a quadrilateral and -connects the neighboring midpoints of each of the outer edges to form an -interior quadrilateral which is provably a parallelogram. The -constraint solver manages the constraints to keep the outer -quadrilateral inside the window, keep the midpoints properly positioned, -and keep the outer quadrilateral from turning "inside out." - -The user is able to select points (draggable boxes) and move them around -within the window (both midpoints and endpoints can be selected, of -course). The solver updates the figure, and redraws. - - ------------------------------------------------------------------- - -FUNDING ACKNOWLEDGEMENTS - -This work has been funded in part by the National Science Foundation under -Grants IRI-9302249 and CCR-9402551, by Object Technology International, and -by a Fulbright Award from the Australian-American Educational -Foundation. - -Additionally, Greg Badros is supported by a National Science Foundation -Graduate Research Fellowship. Parts of this material are based upon -work supported under that fellowship. diff --git a/libs/cassowary/SConscript b/libs/cassowary/SConscript deleted file mode 100644 index 86222085f5..0000000000 --- a/libs/cassowary/SConscript +++ /dev/null @@ -1,32 +0,0 @@ -# -*- python -*- -Import('env libraries') - -cassowary = env.Copy(YACCFLAGS="-d") - -domain = 'libcassowary' -cassowary.Append(DOMAIN=domain,MAJOR=0,MINOR=60,MICRO=3) - -cassowary_files = Split(""" -ClAbstractVariable.cc -ClConstraint.cc -ClLinearExpression.cc -ClSolver.cc -ClSimplexSolver.cc -ClStrength.cc -ClSymbolicWeight.cc -ClTableau.cc -ClVariable.cc -ClFloatVariable.cc -ClSlackVariable.cc -ClDummyVariable.cc -ClReader.cc -ClReader-lex.cc -""") - -cassowary.Append(CCFLAGS="-D_REENTRANT") - -cassowary.CXXFile(target = ['ClReader.cc', 'ClReader.cc.h'], source = 'ClReader.yy') -cassowary.CXXFile(target = 'ClReader-lex.cc', source = 'ClReader.ll') - -libcassowary = cassowary.SharedLibrary('cassowary', cassowary_files) -Default(libcassowary) diff --git a/libs/cassowary/THANKS b/libs/cassowary/THANKS deleted file mode 100644 index 11918b3d52..0000000000 --- a/libs/cassowary/THANKS +++ /dev/null @@ -1,30 +0,0 @@ -Cassowary Constraint Solving Toolkit was -Implemented by: - -Greg J. Badros and -Alan Borning -University of Washington -Computer Science and Engineering -Seattle, WA 98195-2350 - -with Constraint Drawing Applet (CDA) by Michael Noth - -Please send bug reports to cassowary@cs.washington.edu - - -Bug reports, helpful testing, and/or code from: - -Spencer Allain -Anthony Beurivé -Robert Chassell -Alexandre 'Pollux' Duret-Lutz -Michael Kaufmann -Brian Grant -Pengling He -Tessa Lau -John MacPhail -Larry Melia -Michael Noth -Emmanuel Pietriga -Will Portnoy -Steve Wolfman diff --git a/libs/cassowary/cassowary-config.in b/libs/cassowary/cassowary-config.in deleted file mode 100755 index ac1b3ac8ce..0000000000 --- a/libs/cassowary/cassowary-config.in +++ /dev/null @@ -1,102 +0,0 @@ -#!/bin/sh -# Modified from gtk-config -# --09/07/99 gjb - -# gotten from LDADD in c++/Makefile.am -cassowary_gtllibs="@GTL_LIB@" -cassowary_libs="-L@prefix@/lib $cassowary_gtllibs" -cassowary_cflags="@GUILE_INCLUDES@ @GTL_INCLUDES@" - -prefix=@prefix@ -exec_prefix=@exec_prefix@ -exec_prefix_set=no - -usage() -{ - cat <&2 -fi - -while test $# -gt 0; do - case "$1" in - -*=*) optarg=`echo "$1" | sed 's/[-_a-zA-Z0-9]*=//'` ;; - *) optarg= ;; - esac - - case $1 in - --prefix=*) - prefix=$optarg - if test $exec_prefix_set = no ; then - exec_prefix=$optarg - fi - ;; - --prefix) - echo_prefix=yes - ;; - --exec-prefix=*) - exec_prefix=$optarg - exec_prefix_set=yes - ;; - --exec-prefix) - echo_exec_prefix=yes - ;; - --version) - echo @CASSOWARY_VERSION@ - ;; - --cflags) - echo_cflags=yes - ;; - --libs) - echo_libs=yes - ;; - --gtllibs) - echo_gtllibs=yes - ;; - *) - usage 1 1>&2 - ;; - esac - shift -done - -if test "$echo_prefix" = "yes"; then - echo $prefix -fi - -if test "$echo_exec_prefix" = "yes"; then - echo $exec_prefix -fi - - -if test "$echo_cflags" = "yes"; then - if test @includedir@ != /usr/include ; then - includes=-I@includedir@ - for i in $cassowary_cflags ; do - if test $i = -I@includedir@ ; then - includes="" - fi - done - fi - echo $includes $cassowary_cflags -fi - -if test "$echo_libs" = "yes"; then - echo -L@libdir@ -lcassowary -lstdc++ $cassowary_libs -fi - -if test "$echo_gtllibs" = "yes"; then - echo $cassowary_gtllibs -fi diff --git a/libs/cassowary/cassowary-nofd.spec2.in b/libs/cassowary/cassowary-nofd.spec2.in deleted file mode 100644 index ee951bb446..0000000000 --- a/libs/cassowary/cassowary-nofd.spec2.in +++ /dev/null @@ -1,84 +0,0 @@ -# Note that this is NOT a relocatable package -%define ver @VERSION@ -%define rel 2 -%define prefix /usr - -Name: cassowary-nofd -Summary: A Linear Arithmetic Constraint Solving Library. -Version: %ver -Release: %rel -# This source just has a different top-level directory name -Source: http://www.cs.washington.edu/research/constraints/cassowary/cassowary-nofd-%ver.tar.gz -Group: Development/Libraries -BuildRoot: /tmp/cassowary-%ver-build -Copyright: Copyright (C) 1998,1999 Greg J. Badros -Packager: Greg J. Badros -URL: http://www.cs.washington.edu/research/constraints/cassowary -Requires: guile >= 1.3.2 -Provides: cassowary-constraint-solver - -%description - -Cassowary is an advanced incremental constraint solving toolkit that -efficiently solves systems of linear equalities and inequalities. -Constraints may be either requirements or preferences. Client code -specifies the constraints to be maintained, and the solver updates the -constrained variables to have values that satisfy the constraints. - -This package lacks the finite domain subsolver. The cassowary RPM -contains that solver as well, but also requires the GTL (Graph -Template Library) package. - - -%changelog -* Tue Sep 7 1999 Greg J. Badros -- Rework spec file. - -* Wed Apr 14 1999 Greg J. Badros - -- Initial release of this package. - -%prep - -%setup - -%build -ln -sf . ./c++/cassowary - -%ifarch alpha -./configure --host=alpha-linux --prefix=%prefix --enable-guile-build --enable-fsstd --enable-permissive -%else -./configure --prefix=%prefix --enable-guile-build --enable-fsstd --enable-permissive -%endif - -make - -%install -make prefix=$RPM_BUILD_ROOT%{prefix} install-strip - -%clean -rm -rf $RPM_BUILD_ROOT - -%post - -%postun - -%files -%defattr(-, root, root) - -%{prefix}/bin/* -%{prefix}/lib/* -%{prefix}/include/* - -%doc ANNOUNCE AUTHORS COPYING IMPORTANT INSTALL LICENSE NEWS README THANKS -%doc ChangeLog docs/cassowary-tr.pdf docs/cassowary-tr.ps.gz -%doc guile/cassowary_scm-procedures.txt guile/cassowary_scm-variables.txt -%doc guile/cassowary_scm.sgml diff --git a/libs/cassowary/cassowary.spec.in b/libs/cassowary/cassowary.spec.in deleted file mode 100644 index 2b7c23a8e5..0000000000 --- a/libs/cassowary/cassowary.spec.in +++ /dev/null @@ -1,78 +0,0 @@ -# Note that this is NOT a relocatable package -%define ver @VERSION@ -%define rel 1 -%define prefix /usr - -Name: cassowary -Summary: A Linear Arithmetic Constraint Solving Library. -Version: %ver -Release: %rel -Source: http://www.cs.washington.edu/research/constraints/cassowary/cassowary-%ver.tar.gz -Group: Development/Libraries -BuildRoot: /tmp/cassowary-%ver-build -Copyright: Copyright (C) 1998,1999 Greg J. Badros -Packager: Greg J. Badros -URL: http://www.cs.washington.edu/research/constraints/cassowary -Requires: guile >= 1.3.4 -Requires: GTL >= 0.3.1 -Provides: cassowary-constraint-solver - -%description - -Cassowary is an advanced incremental constraint solving toolkit that -efficiently solves systems of linear equalities and inequalities. -Constraints may be either requirements or preferences. Client code -specifies the constraints to be maintained, and the solver updates the -constrained variables to have values that satisfy the constraints. - -%changelog -* Tue Sep 7 1999 Greg J. Badros -- Rework spec file. - -* Wed Apr 14 1999 Greg J. Badros - -- Initial release of this package. - -%prep - -%setup - -%build -ln -sf . ./c++/cassowary - -%ifarch alpha -fake_root_for_install=$RPM_BUILD_ROOT ./configure --host=alpha-linux --prefix=%prefix --with-gtl=%prefix --enable-fd-solver --enable-fsstd --enable-permissive -%else -fake_root_for_install=$RPM_BUILD_ROOT ./configure --prefix=%prefix --with-gtl=%prefix --enable-fd-solver --enable-fsstd --enable-permissive -%endif - -make - -%install -make prefix=$RPM_BUILD_ROOT%{prefix} fake_root_for_install=$RPM_BUILD_ROOT install-strip - -%clean -rm -rf $RPM_BUILD_ROOT - -%post - -%postun - -%files -%defattr(-, root, root) - -%{prefix}/bin/* -%{prefix}/lib/* -%{prefix}/include/* - -%doc ANNOUNCE AUTHORS COPYING IMPORTANT INSTALL LICENSE NEWS README THANKS -%doc ChangeLog docs/cassowary-tr.pdf docs/cassowary-tr.ps.gz -%doc guile/cassowary_scm-procedures.txt guile/cassowary_scm-variables.txt -%doc guile/cassowary_scm.sgml diff --git a/libs/cassowary/cassowary/.cvsignore b/libs/cassowary/cassowary/.cvsignore deleted file mode 100644 index e69de29bb2..0000000000 diff --git a/libs/cassowary/cassowary/Cassowary.h b/libs/cassowary/cassowary/Cassowary.h deleted file mode 100644 index 8413f321f9..0000000000 --- a/libs/cassowary/cassowary/Cassowary.h +++ /dev/null @@ -1,40 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// Cassowary.h - -#ifndef Cassowary_H -#define Cassowary_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) - #include - #define CONFIG_INLINE_H_INCLUDED -#endif - -#ifndef CL_PTR_HASH_DIVISOR - #define CL_PTR_HASH_DIVISOR 4 -#endif - -#include "ClConstraintHash.h" -#include - -#include -#include -#include - -typedef double Number; - -typedef long FDNumber; - -enum { FDN_NOTSET = LONG_MIN }; - -#define NEWVAR(x) do { cerr << "line " << __LINE__ << ": new " << x << endl; } while (0) -#define DELVAR(x) do { cerr << "line " << __LINE__ << ": del " << x << endl; } while (0) - -#endif // Cassowary_H diff --git a/libs/cassowary/cassowary/Cl.h b/libs/cassowary/cassowary/Cl.h deleted file mode 100644 index 6c2604da6f..0000000000 --- a/libs/cassowary/cassowary/Cl.h +++ /dev/null @@ -1,49 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// Cl.h -// This is the top level include file for external clients - -#ifndef CL_H -#define CL_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#ifdef CL_NO_IO -#undef CL_TRACE -#undef CL_SOLVER_STATS -#undef CL_DEBUG_FAILURES -#undef CL_TRACE_VERBOSE -#endif - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include "cassowary/ClVariable.h" -#include "cassowary/ClSimplexSolver.h" -#include "cassowary/ClLinearEquation.h" -#include "cassowary/ClLinearInequality.h" -#include "cassowary/ClErrors.h" -#include "cassowary/ClEditConstraint.h" -#include "cassowary/ClStayConstraint.h" -#include "cassowary/ClReader.h" -#include "cassowary/ClConstraint.h" -#if defined(CL_HAVE_GTL) && defined(CL_BUILD_FD_SOLVER) -#include "cassowary/ClFDBinaryOneWayConstraint.h" -#include "cassowary/ClFDSolver.h" -#endif - -extern const char *szCassowaryVersion; - -#endif diff --git a/libs/cassowary/cassowary/ClAbstractVariable.h b/libs/cassowary/cassowary/ClAbstractVariable.h deleted file mode 100644 index 08ade9ec98..0000000000 --- a/libs/cassowary/cassowary/ClAbstractVariable.h +++ /dev/null @@ -1,161 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClAbstractVariable.h - -#ifndef ClAbstractVariable_H -#define ClAbstractVariable_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include /* for sprintf */ -#include "Cassowary.h" -#include "ClErrors.h" -#include -#include -#include -#include "cl_auto_ptr.h" - -using std::string; -using std::ostream; - -class ClAbstractVariable { -public: - ClAbstractVariable(string Name = "") : - _name(Name), _pv(0) - { - ++iVariableNumber; -#ifdef CL_FIND_LEAK - ++cAbstractVariables; -#endif - if (Name.length() == 0) - { - char sz[16]; - sprintf(sz,"v%ld",iVariableNumber); - _name = string(sz); - } - } - - ClAbstractVariable(long varnumber, char *prefix) : - _pv(0) - { - cl_auto_ptr pch (new char[16+strlen(prefix)]); - iVariableNumber++; -#ifdef CL_FIND_LEAK - ++cAbstractVariables; -#endif - sprintf(pch.get(),"%s%ld",prefix,varnumber); - _name = string(pch.get()); - } - - virtual ~ClAbstractVariable() -#ifdef CL_FIND_LEAK - { --cAbstractVariables; } - - static long cAbstractVariables; -#else - { } -#endif - - // Return the Name of the variable - string Name() const - { return _name; } - - // Set the Name of the variable - virtual void SetName(string const &Name) - { _name = Name; } - - // Return true iff this variable is a ClFloatVariable - virtual bool IsFloatVariable() const - { return false; } - - // Return true iff this variable is a ClFDVariable - virtual bool IsFDVariable() const - { return false; } - - // Return true if this a dummy variable (used as a marker variable - // for required equality constraints). Such variables aren't - // allowed to enter the basis when pivoting. - virtual bool IsDummy() const - { return false; } - - // Return true if this a variable known outside the solver. - // (We need to give such variables a Value after solving is complete.) - virtual bool IsExternal() const - { return false; } - - // Return true if we can Pivot on this variable. - virtual bool IsPivotable() const - { throw ExCLTooDifficultSpecial("Variable not usable inside SimplexSolver"); return false; } - - // Return true if this is a restricted (or slack) variable. Such - // variables are constrained to be non-negative and occur only - // internally to the simplex solver. - virtual bool IsRestricted() const - { throw ExCLTooDifficultSpecial("Variable not usable inside SimplexSolver"); return false; } - -#ifndef CL_NO_IO - // Prints a semi-descriptive representation to the stream, using the - // Name if there is one, and otherwise the hash number of this - // object. - // EXAMPLES - // x[10.0] -- w/ Name - // x[0.0,100] -- w/ Name, bounds but no Value yet - // CV#345(10.0) -- w/o Name - virtual ostream &PrintOn(ostream &xo) const = 0; - - friend ostream& operator<<(ostream &xos, const ClAbstractVariable &clv) - { clv.PrintOn(xos); return xos; } - -#endif // CL_NO_IO - - friend bool operator<(const ClAbstractVariable &cl1, const ClAbstractVariable &cl2) - { return &cl1 < &cl2; } - - friend bool operator==(const ClAbstractVariable &cl1, const ClAbstractVariable &cl2) - { - return &cl1 == &cl2; - } - - friend bool operator!=(const ClAbstractVariable &cl1, const ClAbstractVariable &cl2) - { - return !(cl1 == cl2); - } - - virtual Number Value() const { return 0; } - virtual int IntValue() const { return 0; } - - virtual void SetValue(Number) - { assert(false); } - - virtual void ChangeValue(Number) - { assert(false); } - - void SetPv(void *pv) - { _pv = pv; } - - void *Pv() const - { return _pv; } - -private: - string _name; - - static long iVariableNumber; - - // C-style extension mechanism so I - // don't have to wrap ScwmClVariables separately - void *_pv; -}; - -typedef ClAbstractVariable *PClAbstractVariable; - -#endif diff --git a/libs/cassowary/cassowary/ClConstraint.h b/libs/cassowary/cassowary/ClConstraint.h deleted file mode 100644 index 0b670e6c07..0000000000 --- a/libs/cassowary/cassowary/ClConstraint.h +++ /dev/null @@ -1,198 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClConstraint.h - -#ifndef ClConstraint_H -#define ClConstraint_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include "debug.h" - -#include "Cassowary.h" -#include "ClLinearExpression.h" -#include "ClStrength.h" -#include - -using std::string; - -class ClSimplexSolver; -class ClFDSolver; -class ClBlueSolver; - -// enum setup so additive inverse flips the direction of the inequality -enum ClCnRelation {cnEQ = 0, cnNEQ = 100, cnLEQ = 2, cnGEQ = -2, cnLT = 3, cnGT = -3 }; - -inline enum ClCnRelation -ReverseInequality(enum ClCnRelation c) -{ - if (c != cnNEQ) - c = (enum ClCnRelation) (- int(c)); - return c; -} - -inline string -StrCnRelation(enum ClCnRelation rel) { - switch (rel) { - case cnEQ: return "="; - case cnNEQ: return "=/="; - case cnLEQ: return "<="; - case cnGEQ: return ">="; - case cnLT: return "<"; - case cnGT: return ">"; - default: assert(false); - } -} - - - -class ClConstraint { -public: - - ClConstraint(const ClStrength &strength = ClsRequired(), double weight = 1.0 ) : - _strength(strength), - _readOnlyVars(), - _weight(weight), - _pv(0), - _times_added(0) - { - CtrTracer(__FUNCTION__,this); - } - - virtual ~ClConstraint() - { - DtrTracer(__FUNCTION__,this); - } - - // Return my linear Expression. (For linear equations, this - // constraint represents Expression=0; for linear inequalities it - // represents Expression>=0.) - virtual ClLinearExpression Expression() const - { assert(false); } - - // Returns true if this is an edit constraint - virtual bool IsEditConstraint() const - { return false; } - - // Return true if this is an inequality constraint and - // false if it is an equality constraint. The default is - // that it is not. - virtual bool IsInequality() const - { return false; } - - virtual bool IsStrictInequality() const - { return false; } - - virtual bool IsRequired() const - { return _strength.IsRequired(); } - - virtual bool isStayConstraint() const - { return false; } - - virtual const ClStrength &strength() const - { return _strength; } - - virtual double weight() const - { return _weight; } - -#ifndef CL_NO_IO - virtual ostream &PrintOn(ostream &xo) const = 0; - - friend ostream& operator<<(ostream &xos, const ClConstraint &constraint) - { constraint.PrintOn(xos); return xos; } - -#endif - - - void SetPv(void *pv) - { _pv = pv; } - - void *Pv() const - { return _pv; } - - virtual bool FIsSatisfied() const { return false; } - - virtual bool FIsInSolver() const { return _times_added != 0; } - - virtual bool FIsOkayForSimplexSolver() const { return true; } - - void ChangeStrength( const ClStrength &strength) - { - if (_times_added == 0) { - setStrength(strength); - } else { - throw ExCLTooDifficult(); - } - } - - void ChangeWeight( double weight ) - { - if (_times_added == 0) { - setWeight(weight); - } else { - throw ExCLTooDifficult(); - } - } - - bool FIsReadOnlyVar(ClVariable v) const { - return !(_readOnlyVars.find(v) == _readOnlyVars.end()); - } - - const ClVarSet &ReadOnlyVars() const { - return _readOnlyVars; - } - - ClConstraint &AddROVars(const ClVarSet &setClv) { - for ( ClVarSet::const_iterator it = setClv.begin(); - it != setClv.end(); ++it) { - _readOnlyVars.insert(*it); - } - return *this; - } - - friend class ClSimplexSolver; - friend class ClFDSolver; - friend class ClBlueSolver; -private: - - ClSymbolicWeight symbolicWeight() const { - return _strength.symbolicWeight(); - } - - void addedTo(const ClSimplexSolver &) - { ++_times_added; } - - void removedFrom(const ClSimplexSolver &) - { --_times_added; } - - void setStrength( const ClStrength &strength ) - { _strength = strength; } - - void setWeight( double weight ) - { _weight = weight; } - - /// instance variables - ClStrength _strength; - - ClVarSet _readOnlyVars; - - double _weight; - - void *_pv; - - int _times_added; -}; - -typedef ClConstraint* PClConstraint; - -#endif diff --git a/libs/cassowary/cassowary/ClConstraintHash.h b/libs/cassowary/cassowary/ClConstraintHash.h deleted file mode 100644 index 9d51fad311..0000000000 --- a/libs/cassowary/cassowary/ClConstraintHash.h +++ /dev/null @@ -1,39 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClHash.h - -#ifndef CL_HASH_H__ -#define CL_HASH_H__ - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#ifdef CL_USE_HASH_MAP_AND_SET - -#include - -class ClConstraint; - -struct hash { - size_t operator()(const ClConstraint * const p) const - { return size_t((unsigned long)p/CL_PTR_HASH_DIVISOR); } -}; - -struct hash { - size_t operator()(ClConstraint * const p) const - { return size_t((unsigned long)p/CL_PTR_HASH_DIVISOR); } -}; - -#endif // CL_USE_HASH_MAP_AND_SET - - -#endif diff --git a/libs/cassowary/cassowary/ClDummyVariable.h b/libs/cassowary/cassowary/ClDummyVariable.h deleted file mode 100644 index ad959a6d20..0000000000 --- a/libs/cassowary/cassowary/ClDummyVariable.h +++ /dev/null @@ -1,88 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClDummyVariable.h - -#ifndef ClDummyVariable_H -#define ClDummyVariable_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include "Cassowary.h" -#include "ClAbstractVariable.h" - -class ClTableau; -class ClSimplexSolver; - -class ClDummyVariable : public ClAbstractVariable { - -public: - -#ifdef CL_FIND_LEAK - ~ClDummyVariable() { --cDummyVariables; }; - - static long cDummyVariables; - -#endif - -protected: - friend class ClTableau; - friend class ClSimplexSolver; - - ClDummyVariable(string Name = "") : - ClAbstractVariable(Name) - { -#ifdef CL_FIND_LEAK - ++cDummyVariables; -#endif - } - - ClDummyVariable(long number, char *prefix) : - ClAbstractVariable(number,prefix) - { -#ifdef CL_FIND_LEAK - ++cDummyVariables; -#endif - } - -#ifndef CL_NO_IO - virtual ostream &PrintOn(ostream &xo) const - { - xo << "[" << Name() << ":dummy]"; - return xo; - } -#endif - - // Return true if this a dummy variable (used as a marker variable - // for required equality constraints). Such variables aren't - // allowed to enter the basis when pivoting. - virtual bool IsDummy() const - { return true; } - - // Return true if this a variable known outside the solver. - // (We need to give such variables a Value after solving is complete.) - virtual bool IsExternal() const - { return false; } - - // Return true if we can Pivot on this variable. - virtual bool IsPivotable() const - { return false; } - - // Return true if this is a restricted (or slack) variable. Such - // variables are constrained to be non-negative and occur only - // internally to the simplex solver. - virtual bool IsRestricted() const - { return true; } - -}; - -#endif diff --git a/libs/cassowary/cassowary/ClEditConstraint.h b/libs/cassowary/cassowary/ClEditConstraint.h deleted file mode 100644 index 4bd91e2ca2..0000000000 --- a/libs/cassowary/cassowary/ClEditConstraint.h +++ /dev/null @@ -1,45 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClEditConstraint.h - -#ifndef ClEditConstraint_H -#define ClEditConstraint_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include "Cassowary.h" -#include "ClEditOrStayConstraint.h" - -class ClEditConstraint : public ClEditOrStayConstraint { - typedef ClEditOrStayConstraint super; - public: - - ClEditConstraint(const ClVariable var, - const ClStrength &strength = ClsStrong(), double weight = 1.0 ) : - ClEditOrStayConstraint(var,strength,weight) - { } - - // Returns true if this is an edit constraint - virtual bool IsEditConstraint() const - { return true; } - -#ifndef CL_NO_IO - virtual ostream &PrintOn(ostream &xo) const - { super::PrintOn(xo); return xo << "= edit)"; } -#endif - - private: - -}; - -#endif diff --git a/libs/cassowary/cassowary/ClEditOrStayConstraint.h b/libs/cassowary/cassowary/ClEditOrStayConstraint.h deleted file mode 100644 index 79b6761b69..0000000000 --- a/libs/cassowary/cassowary/ClEditOrStayConstraint.h +++ /dev/null @@ -1,51 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClEditOrStayConstraint.h - -#ifndef ClEditOrStayConstraint_H -#define ClEditOrStayConstraint_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include "ClConstraint.h" -#include "ClLinearExpression.h" - -class ClVariable; - -class ClEditOrStayConstraint : public ClConstraint { - public: - - ClEditOrStayConstraint(const ClVariable var, - const ClStrength &strength = ClsRequired(), double weight = 1.0 ) : - ClConstraint(strength,weight), - _variable(var) - { } - - const ClVariable variable() const - { return _variable; } - - ClLinearExpression Expression() const - { return ClLinearExpression(_variable,-1,_variable.Value()); } - - private: - - void setVariable( const ClVariable v) - { _variable = v; } - - /// instance variables - ClVariable _variable; - - -}; - -#endif diff --git a/libs/cassowary/cassowary/ClErrors.h b/libs/cassowary/cassowary/ClErrors.h deleted file mode 100644 index 867c578dbc..0000000000 --- a/libs/cassowary/cassowary/ClErrors.h +++ /dev/null @@ -1,179 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClErrors.h - -#ifndef ClErrors_H -#define ClErrors_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include "Cassowary.h" -#include "ClTypedefs.h" -#include -#include - -using std::string; -using std::exception; - -class ExCLError : public exception { - public: - ExCLError() : _msg(0) { } - virtual ~ExCLError() throw() {} - virtual string description() const - { return "(ExCLError) An error has occured in CL"; } - protected: - char *_msg; -}; - -class ExCLInternalError : public ExCLError { - public: - ExCLInternalError(const char *sz) - { _msg = strdup(sz); } - virtual string description() const - { - if (_msg) return _msg; - else return "(ExCLInternalError) An internal error has occurred"; - } -}; - -class ExCLBadResolve : public ExCLError { - public: - ExCLBadResolve(const char *sz) - { _msg = strdup(sz); } - virtual string description() const - { - if (_msg) return _msg; - else return "(ExCLBadResolve) Number of resolve values did not match number of edit vars"; - } -}; - -class ExCLEditMisuse : public ExCLError { - public: - ExCLEditMisuse(const char *sz) - { _msg = strdup(sz); } - virtual string description() const - { - if (_msg) return _msg; - return "(ExCLEditMisuse) Edit protocol usage violation"; - } -}; - -class ExCLTooDifficult : public ExCLError { - public: - virtual string description() const - { return "(ExCLTooDifficult) The constraints are too difficult to solve"; } -}; - -class ExCLTooDifficultSpecial : public ExCLTooDifficult { - public: - ExCLTooDifficultSpecial(const char *sz) - { _msg = strdup(sz); } - virtual string description() const - { - if (_msg) return _msg; - else return "(ExCLTooDifficultSpecial) Solver requirements are not satisfied"; - } -}; - -class ExCLReadOnlyNotAllowed : public ExCLTooDifficult { - public: - virtual string description() const - { return "(ExCLReadOnlyNotAllowed) The read-only annotation is not permitted by the solver"; } -}; - -class ExCLCycleNotAllowed : public ExCLTooDifficult { - public: - virtual string description() const - { return "(ExCLCycleNotAllowed) A cyclic constraint graph is not permitted by the solver"; } -}; - -class ExCLStrictInequalityNotAllowed : public ExCLTooDifficult { - public: - virtual string description() const - { return "(ExCLStrictInequalityNotAllowed) The strict inequality is not permitted by the solver"; } -}; - -class ExCLRequiredFailure : public ExCLError { - public: - virtual ~ExCLRequiredFailure() throw() {} - virtual string description() const - { return "(ExCLRequiredFailure) A required constraint cannot be satisfied"; } -}; - -class ExCLNotEnoughStays : public ExCLError { - public: - virtual string description() const - { return "(ExCLNotEnoughStays) There are not enough stays to give specific values to every variable"; } -}; - -class ExCLNonlinearExpression : public ExCLError { - public: - virtual string description() const - { return "(ExCLNonlinearExpression) The resulting expression would be nonlinear"; } -}; - -class ExCLConstraintNotFound : public ExCLError { - public: - virtual string description() const - { return "(ExCLConstraintNotFound) Tried to remove a constraint that was never added"; } -}; - -class ExCLParseError : public ExCLError { - public: - virtual ~ExCLParseError() throw() {} - virtual string description() const - { return "(ExCLParseError)"; } -}; - -class ExCLParseErrorMisc : public ExCLParseError { - public: - ExCLParseErrorMisc(const string &s) - : _msg("(ExCLParseError) ") - { _msg += s; } - virtual ~ExCLParseErrorMisc() throw() {} - virtual string description() const - { return _msg; } - private: - string _msg; -}; - -class ExCLParseErrorBadIdentifier : public ExCLParseError { - public: - ExCLParseErrorBadIdentifier(const string &id) - : _msg("(ExCLParseErrorBadIdentifier) Did not recognize identifier '") - { - _msg += id; - _msg += "'"; - } - virtual ~ExCLParseErrorBadIdentifier() throw() {} - virtual string description() const - { return _msg; } - private: - string _msg; -}; - -class ExCLRequiredFailureWithExplanation : public ExCLRequiredFailure -{ -public: - virtual ~ExCLRequiredFailureWithExplanation() throw() {} - virtual string description() const - { return "(ExCLRequiredFailureWithExplanation) A required constraint cannot be satisfied"; } - virtual void AddConstraint(const ClConstraint *cnExpl) - { _explanation.insert(cnExpl); } - virtual const ClConstraintSet & explanation() const - { return _explanation; } -protected: - ClConstraintSet _explanation; -}; - -#endif // ClErrors_H diff --git a/libs/cassowary/cassowary/ClFDBinaryOneWayConstraint.h b/libs/cassowary/cassowary/ClFDBinaryOneWayConstraint.h deleted file mode 100644 index a779ec1f91..0000000000 --- a/libs/cassowary/cassowary/ClFDBinaryOneWayConstraint.h +++ /dev/null @@ -1,94 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClFDBinaryOneWayConstraint.h - -#ifndef ClFDBinaryOneWayConstraint_H -#define ClFDBinaryOneWayConstraint_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include "Cassowary.h" -#include "ClFDConstraint.h" - -class ClLinearConstraint; - -// Just a node in the class hierarchy for now -class ClFDBinaryOneWayConstraint : public ClFDConstraint { - private: typedef ClFDConstraint super; - - public: - - ClFDBinaryOneWayConstraint(ClVariable vRW, enum ClCnRelation rel, ClVariable vRO, - double coefficient = 1.0, double constant = 0.0, - const ClStrength &strength = ClsRequired(), - double weight = 1.0) - : ClFDConstraint(strength,weight), _vRW(vRW), _rel(rel), _vRO(vRO), - _coefficient(coefficient), _constant(constant) - { } - - ClFDBinaryOneWayConstraint(ClVariable vRW, enum ClCnRelation rel, double constant, - const ClStrength &strength = ClsRequired(), - double weight = 1.0) - : ClFDConstraint(strength,weight), _vRW(vRW), _rel(rel), _vRO(clvNil), - _coefficient(0), _constant(constant) - { } - - ClFDBinaryOneWayConstraint(const ClConstraint &cn); - - static void EnsurePreconditionsForCn(const ClConstraint &cn); - - static bool FCanConvertCn(const ClConstraint &cn); - -#ifndef CL_NO_IO - virtual ostream &PrintOn(ostream &xo) const - { - xo << "FDCn: " << _vRW << " " << StrCnRelation(_rel) << " "; - if (_coefficient != 0) { - if (_coefficient != 1) xo << _coefficient << "*"; - if (_vRO != clvNil) xo << _vRO; - } - if (_constant != 0) xo << " + " << _constant; - return xo; - } - - friend ostream& operator<<(ostream &xos, const ClFDBinaryOneWayConstraint &constraint) - { return constraint.PrintOn(xos); } - -#endif - - ClVariable ClvRW() const - { return _vRW; } - ClVariable ClvRO() const - { return _vRO; } - enum ClCnRelation Relation() const - { return _rel; } - double Coefficient() const - { return _coefficient; } - double Constant() const - { return _constant; } - - bool IsInequality() const - { return (_rel != cnEQ && _rel != cnNEQ); } - - bool IsStrictInequality() const - { return (_rel == cnGT || _rel == cnLT); } - - protected: - ClVariable _vRW; - enum ClCnRelation _rel; - ClVariable _vRO; - double _coefficient; - double _constant; -}; - -#endif diff --git a/libs/cassowary/cassowary/ClFDConnectorVariable.h b/libs/cassowary/cassowary/ClFDConnectorVariable.h deleted file mode 100644 index 4ae38ae42e..0000000000 --- a/libs/cassowary/cassowary/ClFDConnectorVariable.h +++ /dev/null @@ -1,89 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClFDConnectorVariable.h - -#ifndef ClFDConnectorVariable_H -#define ClFDConnectorVariable_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include -#include -#include -#include -#include "Cassowary.h" -#include "ClVariable.h" -#include "ClFDVariable.h" -#include "ClLinearEquation.h" -#include "ClSimplexSolver.h" - -/* Creates a new variable in the FD region - that sets clvFloat in solver (simplex region) - when it changes */ -class ClFDConnectorVariable : public ClFDVariable { -public: - typedef ClFDVariable super; - - ClFDConnectorVariable(string name, FDNumber Value, const list &initial_domain, - ClSimplexSolver &solver, ClVariable clvFloat) : - ClFDVariable(name,Value,initial_domain), - _solver(solver), - _clvFloat(clvFloat), - _pcnRequiredLink(new ClLinearEquation(clvFloat,Value)) - { solver.AddConstraint(_pcnRequiredLink); } - -#ifndef CL_NO_IO - // Prints a semi-descriptive representation to the stream, using the - // name if there is one, and otherwise the hash number of this - // object. - // EXAMPLE - // [x:10.0] -- name = "x", Value = 10.0 - virtual ostream &PrintOn(ostream &xo) const; -#endif - - // permit overriding in subclasses in case something needs to be - // done when the Value is changed by the solver - // may be called when the Value hasn't actually changed -- just - // means the solver is setting the external variable - virtual void ChangeValue(FDNumber Value) - { - if (_value != Value) { - _value = Value; - cerr << "Updating " << _clvFloat << " now!" << endl; - _solver.RemoveConstraint(_pcnRequiredLink); - _pcnRequiredLink->ChangeConstant(_value); - _solver.AddConstraint(_pcnRequiredLink); - } - } - -private: - - // similar to SetValue -- see caveat above -- made private for now - // since it's probably the wrong thing and is too easy to invoke - FDNumber operator=(FDNumber Value) - { _value = Value; return Value; } - - // Copy constructor left undefined since we want to - // outlaw passing by Value! Will get a link error if you - // try to use within ClFDConnectorVariable.c, compile-time error everywhere else - ClFDConnectorVariable(const ClFDConnectorVariable &); - - ClSimplexSolver &_solver; - - ClVariable _clvFloat; - - ClLinearEquation *_pcnRequiredLink; - -}; - -#endif diff --git a/libs/cassowary/cassowary/ClFDConstraint.h b/libs/cassowary/cassowary/ClFDConstraint.h deleted file mode 100644 index 2cf9776449..0000000000 --- a/libs/cassowary/cassowary/ClFDConstraint.h +++ /dev/null @@ -1,40 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClFDConstraint.h - -#ifndef ClFDConstraint_H -#define ClFDConstraint_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include "Cassowary.h" -#include "ClConstraint.h" - - -// Just a node in the class hierarchy for now -class ClFDConstraint : public ClConstraint { - private: typedef ClConstraint super; - - public: - // Constructor - ClFDConstraint(const ClStrength &strength = ClsRequired(), - double weight = 1.0) - : ClConstraint(strength, weight) { } - - virtual bool FIsOkayForSimplexSolver() const { return false; } - - protected: - -}; - -#endif diff --git a/libs/cassowary/cassowary/ClFDSolver.h b/libs/cassowary/cassowary/ClFDSolver.h deleted file mode 100644 index 2fbb637764..0000000000 --- a/libs/cassowary/cassowary/ClFDSolver.h +++ /dev/null @@ -1,120 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClSolver.h - -#ifndef ClFDSolver_H -#define ClFDSolver_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include "Cassowary.h" -#include "ClSolver.h" -#include "ClVariable.h" -#include "ClErrors.h" -#include "ClTypedefs.h" -#include "ClSymbolicWeight.h" -#include -#include - -using std::map; - -class ClVariable; -class ClFDBinaryOneWayConstraint; - -// ClFDSolver is a concrete class -// implementing a very restricted (for now --04/23/99 gjb) -// finite-domain constraint solving algorithm -class ClFDSolver: public ClSolver { - public: - ClFDSolver() - : _setCns(), _mapClvToCns(), G(), nodeToVar(G) - { G.make_directed(); } - - virtual ~ClFDSolver() - { } - - virtual ClFDSolver &AddConstraint(ClConstraint *const pcn); - - virtual ClFDSolver &RemoveConstraint(ClConstraint *const pcn); - - virtual ClFDSolver &Solve(); - - virtual ClFDSolver &ShowSolve(); - - void ChangeClv(ClVariable clv, FDNumber n) { - clv.ChangeValue(n); - if (_pfnChangeClvCallback) { - _pfnChangeClvCallback(&clv,this); - } - } - - -#ifndef CL_NO_IO - ostream &PrintOn(ostream &xo) const; - - ostream &PrintInternalInfo(ostream &xo) const; - - ostream &PrintOnVerbose(ostream &xo) const - { PrintOn(xo); PrintInternalInfo(xo); xo << endl; return xo; } - - friend ostream &operator<<(ostream &xo, const ClFDSolver &solver); - -#endif - - protected: - - virtual ClFDSolver &AddConstraintInternal(ClConstraint *const pcn); - - virtual ClFDSolver &RemoveConstraintInternal(ClConstraint *const pcn); - - /* Create node for v in G, if necessary, - otherwise return the node we already created. */ - node GetVarNode(ClVariable v); - - /* return the best (lowest) incremental error and the value - at which that error occurs */ - pair ComputeBest(ClFDVariable *pcldv); - - ClSymbolicWeight ErrorForClvAtValSubjectToCn(ClFDVariable *pcldv, - FDNumber value,const ClConstraint &cn); - - /* Turn all FDVariable FIsSet() flags to false */ - void ResetSetFlagsOnVariables(); - - /* all the constraints in the solver */ - ClConstraintSet _setCns; - - /* _mapClvToCns maps variable to the constraints in which - it is rw (it omits where it is ro) */ - ClVarToConstraintSetMap _mapClvToCns; - - /* track what edges correspond to which constraints - so we can update the constraint graph when - removing a constraint */ - map _mapCnToEdge; - - /* track what nodes correspond to which variables */ - map _mapVarToNode; - - /* directed graph that mirrors the structure of - the relations of the added constraints */ - graph G; - - node_map nodeToVar; -}; - -#define FDN_EOL LONG_MIN - -void ListPushOnto(list *pl, ...); - -#endif diff --git a/libs/cassowary/cassowary/ClFDVariable.h b/libs/cassowary/cassowary/ClFDVariable.h deleted file mode 100644 index 326b339459..0000000000 --- a/libs/cassowary/cassowary/ClFDVariable.h +++ /dev/null @@ -1,126 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClFDVariable.h - -#ifndef ClFDVariable_H -#define ClFDVariable_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include -#include -#include -#include -#include "Cassowary.h" -#include "ClAbstractVariable.h" - -using std::map; -using std::list; -using std::string; - -class ClFDVariable : public ClAbstractVariable { -public: - typedef ClAbstractVariable super; - -#if 0 /* GJB:FIXME:: */ - ClFDVariable(string name, FDNumber Value) : - ClAbstractVariable(name), - _value(Value), - _fSet(true), - _desired_value(Value), - _plfdnInitialDomain(0) - { } -#endif - - ClFDVariable(string name, FDNumber Value, const list &initial_domain) : - ClAbstractVariable(name), - _value(Value), - _fSet(true), - _desired_value(Value), - _plfdnInitialDomain(new list()) - { - *_plfdnInitialDomain = initial_domain; - } - - virtual bool IsFDVariable() const - { return true; } - - // Return true if this a variable known outside the solver. - // (We need to give such variables a Value after solving is complete.) - virtual bool IsExternal() const - { return true; } - -#ifndef CL_NO_IO - // Prints a semi-descriptive representation to the stream, using the - // name if there is one, and otherwise the hash number of this - // object. - // EXAMPLE - // [x:10.0] -- name = "x", Value = 10.0 - virtual ostream &PrintOn(ostream &xo) const; -#endif - - // Return the current Value I hold. - Number Value() const - { return _value; } - - // Round the Value to an integer and return it - int IntValue() const - { return _value; } - - // change the Value held -- should *not* use this if the variable is - // in a solver -- instead use AddEditVar() and SuggestValue() interface - void SetValue(FDNumber Value) - { _value = Value; } - - // permit overriding in subclasses in case something needs to be - // done when the Value is changed by the solver - // may be called when the Value hasn't actually changed -- just - // means the solver is setting the external variable - virtual void ChangeValue(FDNumber Value) - { _value = Value; } - - virtual bool FIsSet() - { return _fSet; } - - virtual void SetFIsSet(bool f) - { _fSet = f; } - - virtual FDNumber DesiredValue() const - { return _desired_value; } - - virtual const list *PlfdnDomain() const - { return _plfdnInitialDomain; } - -protected: - - // similar to SetValue -- see caveat above -- made private for now - // since it's probably the wrong thing and is too easy to invoke - FDNumber operator=(FDNumber Value) - { _value = Value; return Value; } - - // Copy constructor left undefined since we want to - // outlaw passing by Value! Will get a link error if you - // try to use within ClFDVariable.c, compile-time error everywhere else - ClFDVariable(const ClFDVariable &); - - FDNumber _value; - - // has the _value been set? Used during solves. - bool _fSet; - - FDNumber _desired_value; - - list *_plfdnInitialDomain; -}; - -#endif diff --git a/libs/cassowary/cassowary/ClFloatVariable.h b/libs/cassowary/cassowary/ClFloatVariable.h deleted file mode 100644 index 4e58036ab7..0000000000 --- a/libs/cassowary/cassowary/ClFloatVariable.h +++ /dev/null @@ -1,119 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClFloatVariable.h - -#ifndef ClFloatVariable_H -#define ClFloatVariable_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include -#include -#include -#include "Cassowary.h" -#include "ClAbstractVariable.h" - -using std::map; -using std::string; - -class ClFloatVariable : public ClAbstractVariable { -public: - typedef ClAbstractVariable super; - - ClFloatVariable(string name, Number Value = 0.0) : - ClAbstractVariable(name), - _value(Value) - { } - - ClFloatVariable(Number Value = 0.0) : - ClAbstractVariable(""), - _value(Value) - { } - - ClFloatVariable(long number, char *prefix, Number Value = 0.0) : - ClAbstractVariable(number,prefix), - _value(Value) - { } - - virtual bool IsFloatVariable() const - { return true; } - - // Return true if this a dummy variable (used as a marker variable - // for required equality constraints). Such variables aren't - // allowed to enter the basis when pivoting. - virtual bool IsDummy() const - { return false; } - - // Return true if this a variable known outside the solver. - // (We need to give such variables a Value after solving is complete.) - virtual bool IsExternal() const - { return true; } - - // Return true if we can Pivot on this variable. - virtual bool IsPivotable() const - { return false; } - - // Return true if this is a restricted (or slack) variable. Such - // variables are constrained to be non-negative and occur only - // internally to the simplex solver. - virtual bool IsRestricted() const - { return false; } - -#ifndef CL_NO_IO - // Prints a semi-descriptive representation to the stream, using the - // name if there is one, and otherwise the hash number of this - // object. - // EXAMPLE - // [x:10.0] -- name = "x", Value = 10.0 - virtual ostream &PrintOn(ostream &xo) const; -#endif - - // Return the current Value I hold. - Number Value() const - { return _value; } - - // Round the Value to an integer and return it - int IntValue() const - { return int(_value + 0.5); } - - // change the Value held -- should *not* use this if the variable is - // in a solver -- instead use AddEditVar() and SuggestValue() interface - void SetValue(Number Value) - { _value = Value; } - - // permit overriding in subclasses in case something needs to be - // done when the Value is changed by the solver - // may be called when the Value hasn't actually changed -- just - // means the solver is setting the external variable - virtual void ChangeValue(Number Value) - { _value = Value; } - -private: - - // similar to SetValue -- see caveat above -- made private for now - // since it's probably the wrong thing and is too easy to invoke - Number operator=(Number Value) - { _value = Value; return Value; } - - // Copy constructor left undefined since we want to - // outlaw passing by Value! Will get a link error if you - // try to use within ClFloatVariable.c, compile-time error everywhere else - ClFloatVariable(const ClFloatVariable &); - - Number _value; - -}; - - - -#endif diff --git a/libs/cassowary/cassowary/ClLinearConstraint.h b/libs/cassowary/cassowary/ClLinearConstraint.h deleted file mode 100644 index d657d1d73e..0000000000 --- a/libs/cassowary/cassowary/ClLinearConstraint.h +++ /dev/null @@ -1,61 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClLinearConstraint.h - -#ifndef ClLinearConstraint_H -#define ClLinearConstraint_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include "Cassowary.h" -#include "ClConstraint.h" -#include "ClLinearExpression.h" - - -// Add the ClLinearExpression member variable needed for both -// ClLinearEquation and ClLinearInequality -class ClLinearConstraint : public ClConstraint { - private: typedef ClConstraint super; - - public: - - // Constructor - ClLinearConstraint(const ClLinearExpression &cle, - const ClStrength &strength = ClsRequired(), - double weight = 1.0) : - ClConstraint(strength, weight), - _expression(cle) - { } - - virtual ~ClLinearConstraint() {} - - // Return my linear Expression. (For linear equations, this - // constraint represents Expression=0; for linear inequalities it - // represents Expression>=0.) - ClLinearExpression Expression() const - { return _expression; } - - // do not do this if *this is inside a solver - void ChangeConstant(Number constant) - { _expression.Set_constant(constant); } - - protected: - - ClLinearExpression _expression; - - virtual void setExpression( const ClLinearExpression &expr) - { _expression = expr; } - -}; - -#endif diff --git a/libs/cassowary/cassowary/ClLinearEquation.h b/libs/cassowary/cassowary/ClLinearEquation.h deleted file mode 100644 index a02b51d70b..0000000000 --- a/libs/cassowary/cassowary/ClLinearEquation.h +++ /dev/null @@ -1,74 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClLinearEquation.h - -#ifndef ClLinearEquation_H -#define ClLinearEquation_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include "Cassowary.h" -#include "ClLinearConstraint.h" -#include "ClLinearExpression.h" - -class ClStrength; -class ClVariable; - -class ClLinearEquation : public ClLinearConstraint { - private: typedef ClLinearConstraint super; - - public: - //// Constructors - - // ClLinearEquation(expr,...) is expr == 0 - ClLinearEquation(const ClLinearExpression &cle, - const ClStrength &strength = ClsRequired(), - double weight = 1.0) : - ClLinearConstraint(cle,strength, weight) - { } - - // ClLinearEquation(var,expr,...) is var == expr - ClLinearEquation(ClVariable clv, - const ClLinearExpression &cle, - const ClStrength &strength = ClsRequired(), - double weight = 1.0) : - ClLinearConstraint(cle,strength,weight) - { _expression.AddVariable(clv,-1.0); } - - // ClLinearEquation(expr,var,...) is var == expr - ClLinearEquation(const ClLinearExpression &cle, - ClVariable clv, - const ClStrength &strength = ClsRequired(), - double weight = 1.0) : - ClLinearConstraint(cle,strength,weight) - { _expression.AddVariable(clv,-1.0); } - - // ClLinearEquation(expr,expr,...) is expr == expr - ClLinearEquation(const ClLinearExpression &cle1, - const ClLinearExpression &cle2, - const ClStrength &strength = ClsRequired(), - double weight = 1.0) : - ClLinearConstraint(cle1,strength,weight) - { _expression.AddExpression(cle2,-1.0); } - -#ifndef CL_NO_IO - virtual ostream &PrintOn(ostream &xo) const - { super::PrintOn(xo); xo << " = 0 )"; return xo; } -#endif - - virtual bool FIsSatisfied() const - { return (_expression.Evaluate() == 0); } - -}; - -#endif diff --git a/libs/cassowary/cassowary/ClLinearExpression.h b/libs/cassowary/cassowary/ClLinearExpression.h deleted file mode 100644 index 0a1df9c243..0000000000 --- a/libs/cassowary/cassowary/ClLinearExpression.h +++ /dev/null @@ -1,298 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClLinearExpression.h - -#ifndef ClLinearExpression_H -#define ClLinearExpression_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include "Cassowary.h" -#include "debug.h" -#include "ClVariable.h" -#include "ClLinearExpression_fwd.h" - -class ClSimplexSolver; -class ClTableau; -class ClSymbolicWeight; - -ClLinearExpression &cleNil(); - -template -class ClGenericLinearExpression { - public: - typedef std::map ClVarToCoeffMap; - - // convert Number-s into ClLinearExpression-s - ClGenericLinearExpression(T num = 0.0); - - // Convert from ClVariable to a ClLinearExpression - // this replaces ClVariable::asLinearExpression - ClGenericLinearExpression(ClVariable clv, T value = 1.0, T constant = 0.0); - - // copy ctr - ClGenericLinearExpression(const ClGenericLinearExpression &expr) : - _constant(expr._constant), - _terms(expr._terms) - { } - - virtual ~ClGenericLinearExpression(); - - // Return a new linear expression formed by multiplying self by x. - // (Note that this result must be linear.) - ClGenericLinearExpression Times(Number x) const; - - // Return a new linear expression formed by multiplying self by x. - // (Note that this result must be linear.) - ClGenericLinearExpression Times(const ClGenericLinearExpression &expr) const; - - // Return a new linear expression formed by adding x to self. - ClGenericLinearExpression Plus(const ClGenericLinearExpression &expr) const; - - // Return a new linear expression formed by subtracting x from self. - ClGenericLinearExpression Minus(const ClGenericLinearExpression &expr) const; - - // Return a new linear expression formed by dividing self by x. - // (Note that this result must be linear.) - ClGenericLinearExpression Divide(Number x) const; - - - - // Return a new linear expression formed by multiplying self by x. - // (Note that this result must be linear.) - ClGenericLinearExpression *P_times(Number x) const - { return new ClGenericLinearExpression(Times(x)); } - - // Return a new linear expression formed by adding x to self. - ClGenericLinearExpression *P_plus(const ClGenericLinearExpression &expr) const - { return new ClGenericLinearExpression(Plus(expr)); } - - // Return a new linear expression formed by subtracting x from self. - ClGenericLinearExpression *P_minus(const ClGenericLinearExpression &expr) const - { return new ClGenericLinearExpression(Minus(expr)); } - - // Return a new linear expression formed by dividing self by x. - // (Note that this result must be linear.) - ClGenericLinearExpression *P_divide(Number x) const - { return new ClGenericLinearExpression(Divide(x)); } - - // Return a new linear expression formed by dividing self by x. - // (Note that this result must be linear.) - ClGenericLinearExpression Divide(const ClGenericLinearExpression &expr) const; - - // Return a new linear expression (aNumber/this). Since the result - // must be linear, this is permissible only if 'this' is a constant. - ClGenericLinearExpression DivFrom(const ClGenericLinearExpression &expr) const; - - // Return a new linear expression (aNumber-this). - ClGenericLinearExpression SubtractFrom(const ClGenericLinearExpression &expr) const - { return expr.Minus(*this); } - - // Add n*expr to this expression from another expression expr. - ClGenericLinearExpression &AddExpression(const ClGenericLinearExpression &expr, - Number n = 1.0); - - // Add n*expr to this expression from another expression expr. - // Notify the solver if a variable is added or deleted from this - // expression. - ClGenericLinearExpression &AddExpression(const ClGenericLinearExpression &expr, Number n, - ClVariable subject, - ClTableau &solver); - - // Add a term c*v to this expression. If the expression already - // contains a term involving v, Add c to the existing coefficient. - // If the new coefficient is approximately 0, delete v. - ClGenericLinearExpression &AddVariable(ClVariable v, T c = 1.0); - - // Add a term c*v to this expression. If the expression already - // contains a term involving v, Add c to the existing coefficient. - // If the new coefficient is approximately 0, delete v. - ClGenericLinearExpression &setVariable(ClVariable v, T c) - {assert(c != 0.0); _terms[v] = c; return *this; } - - // Add a term c*v to this expression. If the expression already - // contains a term involving v, Add c to the existing coefficient. - // If the new coefficient is approximately 0, delete v. Notify the - // solver if v appears or disappears from this expression. - ClGenericLinearExpression &AddVariable(ClVariable v, T c, - ClVariable subject, - ClTableau &solver); - - // Return a pivotable variable in this expression. (It is an error - // if this expression is constant -- signal ExCLInternalError in - // that case). Return NULL if no pivotable variables - ClVariable AnyPivotableVariable() const; - - // Replace var with a symbolic expression expr that is equal to it. - // If a variable has been added to this expression that wasn't there - // before, or if a variable has been dropped from this expression - // because it now has a coefficient of 0, inform the solver. - // PRECONDITIONS: - // var occurs with a non-Zero coefficient in this expression. - void SubstituteOut(ClVariable v, - const ClGenericLinearExpression &expr, - ClVariable subject, - ClTableau &solver); - - // This linear expression currently represents the equation - // oldSubject=self. Destructively modify it so that it represents - // the equation NewSubject=self. - // - // Precondition: NewSubject currently has a nonzero coefficient in - // this expression. - // - // NOTES - // Suppose this expression is c + a*NewSubject + a1*v1 + ... + an*vn. - // - // Then the current equation is - // oldSubject = c + a*NewSubject + a1*v1 + ... + an*vn. - // The new equation will be - // NewSubject = -c/a + oldSubject/a - (a1/a)*v1 - ... - (an/a)*vn. - // Note that the term involving NewSubject has been dropped. - void ChangeSubject(ClVariable old_subject, - ClVariable new_subject); - - // This linear expression currently represents the equation self=0. Destructively modify it so - // that subject=self represents an equivalent equation. - // - // Precondition: subject must be one of the variables in this expression. - // NOTES - // Suppose this expression is - // c + a*subject + a1*v1 + ... + an*vn - // representing - // c + a*subject + a1*v1 + ... + an*vn = 0 - // The modified expression will be - // subject = -c/a - (a1/a)*v1 - ... - (an/a)*vn - // representing - // subject = -c/a - (a1/a)*v1 - ... - (an/a)*vn - // - // Note that the term involving subject has been dropped. - // Returns the reciprocal, so ChangeSubject can use it, too - T NewSubject(ClVariable subject); - - // Return the value of the linear expression - // given the current assignments of values to contained variables - T Evaluate() const; - - // Return the coefficient corresponding to variable var, i.e., - // the 'ci' corresponding to the 'vi' that var is: - // v1*c1 + v2*c2 + .. + vn*cn + c - T CoefficientFor(ClVariable var) const - { - typename ClVarToCoeffMap::const_iterator it = _terms.find(var); - if (it != _terms.end()) - return (*it).second; - return 0.0; - } - - T Constant() const - { return _constant; } - - void Set_constant(T c) - { _constant = c; } - - const ClVarToCoeffMap &Terms() const - { return _terms; } - - ClVarToCoeffMap &Terms() - { return _terms; } - - void IncrementConstant(T c) - { _constant += c; } - - bool IsConstant() const - { return _terms.size() == 0; } - -#ifndef CL_NO_IO - virtual ostream &PrintOn(ostream &xo) const; - - friend ostream &operator<<(ostream &xo,const ClGenericLinearExpression &cle) - { return cle.PrintOn(xo); } -#endif - - friend ClGenericLinearExpression operator+(const ClGenericLinearExpression &e1, - const ClGenericLinearExpression &e2) - { return e1.Plus(e2); } - - friend ClGenericLinearExpression operator-(const ClGenericLinearExpression &e1, - const ClGenericLinearExpression &e2) - { return e1.Minus(e2); } - - friend ClGenericLinearExpression operator*(const ClGenericLinearExpression &e1, - const ClGenericLinearExpression &e2) - { return e1.Times(e2); } - - - friend ClGenericLinearExpression operator/(const ClGenericLinearExpression &e1, - const ClGenericLinearExpression &e2) - { return e1.Divide(e2); } - - // FIXGJB -- this may be wrong -- should test underlying expression for equality - friend bool operator==(const ClGenericLinearExpression &e1, - const ClGenericLinearExpression &e2) - { return &e1 == &e2; } - - /// Named versions of the operator functions for ease of - /// wrapping, or expressing using prefix notation - - friend ClGenericLinearExpression Plus(const ClGenericLinearExpression &e1, - const ClGenericLinearExpression &e2) - { return e1.Plus(e2); } - - friend ClGenericLinearExpression Minus(const ClGenericLinearExpression &e1, - const ClGenericLinearExpression &e2) - { return e1.Minus(e2); } - - friend ClGenericLinearExpression Times(const ClGenericLinearExpression &e1, - const ClGenericLinearExpression &e2) - { return e1.Times(e2); } - - - friend ClGenericLinearExpression *Divide(const ClGenericLinearExpression &e1, - const ClGenericLinearExpression &e2) - { return new ClGenericLinearExpression(e1.Divide(e2)); } - - friend ClGenericLinearExpression *p_Plus(const ClGenericLinearExpression &e1, - const ClGenericLinearExpression &e2) - { return new ClGenericLinearExpression(e1.Plus(e2)); } - - friend ClGenericLinearExpression *p_Minus(const ClGenericLinearExpression &e1, - const ClGenericLinearExpression &e2) - { return new ClGenericLinearExpression(e1.Minus(e2)); } - - friend ClGenericLinearExpression *p_Times(const ClGenericLinearExpression &e1, - const ClGenericLinearExpression &e2) - { return new ClGenericLinearExpression(e1.Times(e2)); } - - friend ClGenericLinearExpression *p_Divide(const ClGenericLinearExpression &e1, - const ClGenericLinearExpression &e2) - { return new ClGenericLinearExpression(e1.Divide(e2)); } - - - // FIXGJB -- this may be wrong -- should test underlying expression for equality - friend bool FEquals(const ClGenericLinearExpression &e1, - const ClGenericLinearExpression &e2) - { return &e1 == &e2; } - - ClGenericLinearExpression &MultiplyMe(T x); - - private: - - T _constant; - ClVarToCoeffMap _terms; - -}; - -typedef ClGenericLinearExpression::ClVarToCoeffMap ClVarToNumberMap; - -#endif diff --git a/libs/cassowary/cassowary/ClLinearExpression_fwd.h b/libs/cassowary/cassowary/ClLinearExpression_fwd.h deleted file mode 100644 index 99b48557ec..0000000000 --- a/libs/cassowary/cassowary/ClLinearExpression_fwd.h +++ /dev/null @@ -1,26 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClLinearExpression.h - -#ifndef ClLinearExpression_fwd_H -#define ClLinearExpression_fwd_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include "Cassowary.h" - -template class ClGenericLinearExpression; -typedef ClGenericLinearExpression ClLinearExpression; -typedef ClLinearExpression* PClLinearExpression; - -#endif diff --git a/libs/cassowary/cassowary/ClLinearInequality.h b/libs/cassowary/cassowary/ClLinearInequality.h deleted file mode 100644 index 017c4b819e..0000000000 --- a/libs/cassowary/cassowary/ClLinearInequality.h +++ /dev/null @@ -1,167 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClLinearInequality.h - -#ifndef ClLinearInequality_H -#define ClLinearInequality_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include "ClConstraint.h" -#include "ClLinearConstraint.h" - -class ClVariable; - -class ClLinearInequality : public ClLinearConstraint { - private: typedef ClLinearConstraint super; - - public: - //// Constructors - // ClLinearInequality(expr,...) is expr >= 0 - ClLinearInequality(const ClLinearExpression &cle, - const ClStrength &strength = ClsRequired(), - double weight = 1.0) : - ClLinearConstraint(cle,strength, weight), - _fStrictInequality(false) - { } - - // ClLinearInequality(var,OP,expr) is var >= expr - ClLinearInequality(const ClVariable clv, - enum ClCnRelation op, - const ClLinearExpression &cle, - const ClStrength &strength = ClsRequired(), - double weight = 1.0) : - ClLinearConstraint( cle, strength, weight), - _fStrictInequality(false) - { - if (op == cnGEQ || op == cnGT) - { - _expression.MultiplyMe(-1.0); - _expression.AddVariable(clv,1.0); - } - else if (op == cnLEQ || op == cnGEQ) - { - _expression.AddVariable(clv,-1.0); - } - else - { - throw ExCLEditMisuse("Cannot use that operator for ClLinearInequality objects"); - } - if (op == cnLT || op == cnGT) { - _fStrictInequality = true; - } - } - -#ifdef FIXGJB_AMBIGUOUS - // ClLinearInequality(expr,OP,var) is var ?<>? expr - ClLinearInequality(const ClLinearExpression &cle, - enum ClCnRelation op, - const ClVariable clv, - const ClStrength &strength = ClsRequired(), - double weight = 1.0) : - ClLinearConstraint( cle, strength, weight), - _fStrictInequality(false) - { - if (op == cnLEQ || op == cnLT) - { - _expression.MultiplyMe(-1.0); - _expression.AddVariable(clv,1.0); - } - else if (op == cnGEQ || op == cnGT) - { - _expression.AddVariable(clv,-1.0); - } - if (op == cnLT || op == cnGT) { - _fStrictInequality = true; - } - } -#endif - - // ClLinearInequality(expr,OP,expr) is expr >= expr - ClLinearInequality(const ClLinearExpression &cle1, - enum ClCnRelation op, - const ClLinearExpression &cle2, - const ClStrength &strength = ClsRequired(), - double weight = 1.0) : - ClLinearConstraint( cle2, strength, weight), - _fStrictInequality(false) - { - if (op == cnGEQ || op == cnGT) - { - _expression.MultiplyMe(-1.0); - _expression.AddExpression(cle1); - } - else if (op == cnLEQ || op == cnLT) - { - _expression.AddExpression(cle1,-1.0); - } - if (op == cnLT || op == cnGT) { - _fStrictInequality = true; - } - } - -#ifdef FIXGJB_AMBIGUOUS - // ClLinearInequality(var,OP,var) is var ?<>? var - ClLinearInequality(const ClVariable clv1, - enum ClCnRelation op, - const ClVariable clv2, - const ClStrength &strength = ClsRequired(), - double weight = 1.0) : - ClLinearConstraint( clv2, strength, weight), - _fStrictInequality(false) - { - if (op == cnGEQ || op == cnGT) - { - _expression.MultiplyMe(-1.0); - _expression.AddVariable(clv1,1.0); - } - else if (op == cnLEQ || op == cnLT) - { - _expression.AddVariable(clv1,-1.0); - } - if (op == cnLT || op == cnGT) { - _fStrictInequality = true; - } - } -#endif - - - // Return true if this is an inequality constraint and - // false if it is an equality constraint. The default is - // that it is not. - virtual bool IsInequality() const - { return true; } - - virtual bool IsStrictInequality() const - { return _fStrictInequality; } - -#ifndef CL_NO_IO - virtual ostream &PrintOn(ostream &xo) const - { super::PrintOn(xo); xo << " >= 0 )"; return xo; } -#endif - - virtual bool FIsSatisfied() const - { - Number v = _expression.Evaluate(); - if (_fStrictInequality) - return (v > 0); - else - return (v >= 0); - } - - private: - - bool _fStrictInequality; -}; - -#endif diff --git a/libs/cassowary/cassowary/ClObjectiveVariable.h b/libs/cassowary/cassowary/ClObjectiveVariable.h deleted file mode 100644 index 664e2d65a4..0000000000 --- a/libs/cassowary/cassowary/ClObjectiveVariable.h +++ /dev/null @@ -1,63 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClObjectiveVariable.h - -#ifndef ClObjectiveVariable_H -#define ClObjectiveVariable_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include "Cassowary.h" -#include "ClAbstractVariable.h" - -class ClTableau; -class ClSimplexSolver; - -class ClObjectiveVariable : public ClAbstractVariable { -protected: - friend class ClTableau; - friend class ClSimplexSolver; - - ClObjectiveVariable(string name = "") : - ClAbstractVariable(name) - { } - - ClObjectiveVariable(long number, char *prefix) : - ClAbstractVariable(number,prefix) - { } - -#ifndef CL_NO_IO - virtual ostream &PrintOn(ostream &xo) const - { - xo << "[" << Name() << ":obj]"; - return xo; - } -#endif - - // We don't need to give such variables a Value after solving is complete. - virtual bool IsExternal() const - { return false; } - - // Return true if we can Pivot on this variable. - virtual bool IsPivotable() const - { return false; } - - // Return true if this is a restricted (or slack) variable. Such - // variables are constrained to be non-negative and occur only - // internally to the simplex solver. - virtual bool IsRestricted() const - { return false; } - -}; - -#endif diff --git a/libs/cassowary/cassowary/ClPoint.h b/libs/cassowary/cassowary/ClPoint.h deleted file mode 100644 index 15139aa73b..0000000000 --- a/libs/cassowary/cassowary/ClPoint.h +++ /dev/null @@ -1,74 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClPoint.h - -#ifndef ClPoint_H -#define ClPoint_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include "Cassowary.h" -#include "ClVariable.h" - -// ClPoint is just a convenience class for pairs of -// ClVariables -- often useful for coordinate pairs in 2-space -class ClPoint { - public: - ClPoint(Number x, Number y) - : _clv_x(x), _clv_y(y) - { } - - ClPoint() - { } - - ClVariable X() - { return _clv_x; } - - ClVariable Y() - { return _clv_y; } - - const ClVariable X() const - { return _clv_x; } - - const ClVariable Y() const - { return _clv_y; } - - void SetXY(Number x, Number y) - { _clv_x.SetValue(x); _clv_y.SetValue(y); } - - Number Xvalue() const - { return X().Value(); } - - Number Yvalue() const - { return Y().Value(); } - - private: - ClVariable _clv_x; - ClVariable _clv_y; - -#ifndef CL_NO_IO - friend ostream &operator<<(ostream &xo, const ClPoint &clp); -#endif - -}; - -#ifndef CL_NO_IO -inline ostream & -operator<<(ostream &xo, const ClPoint &clp) -{ - xo << "(" << clp._clv_x << ", " << clp._clv_y << ")"; - return xo; -} -#endif - -#endif diff --git a/libs/cassowary/cassowary/ClReader.h b/libs/cassowary/cassowary/ClReader.h deleted file mode 100644 index 4eef907759..0000000000 --- a/libs/cassowary/cassowary/ClReader.h +++ /dev/null @@ -1,120 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClReader.h -// Original implementation contributed by Steve Wolfman -// Subsequently largely revised by Greg J. Badros - -#ifndef CREADER_H -#define CREADER_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include -#include -#include -#include -#include "ClErrors.h" -#include "ClVariable.h" -#include "ClStrength.h" -#include "ClLinearExpression_fwd.h" - -using std::string; -using std::istream; - -class ClConstraint; - -class ClVarLookupFunction : public std::unary_function { -public: - virtual ~ClVarLookupFunction () {}; - virtual ClVariable *operator()(const string &) const { return &clvNil; } -}; - - -// Attempts to read a constraint of input stream in -// Returns constraint (freshly allocated, client responsibility to deallocate) -// if succesful. Otherwise, returns 0. -ClConstraint *PcnParseConstraint(istream &xi, const ClVarLookupFunction &lookup_func, - const ClStrength &strength = ClsRequired()); - -class ClVarLookupInMap : public ClVarLookupFunction { -public: - ClVarLookupInMap(StringToVarMap *pmapVars, bool fAutoCreate) - : _pmapVars(pmapVars), _fAutoCreate(fAutoCreate) { } - - virtual ~ClVarLookupInMap () {}; - - ClVariable *operator()(const string &str) const - { - if (!_pmapVars) - return &clvNil; - StringToVarMap &_mapVars = *_pmapVars; - StringToVarMap::iterator it = _mapVars.find(str); - if (it != _mapVars.end()) { - return &it->second; - } else if (_fAutoCreate) { - // save the old symbol table, if any - StringToVarMap *pmapOld = ClVariable::VarMap(); - // and set it to this one temporarily - ClVariable::SetVarMap(&_mapVars); - ClVariable *pclv = new ClVariable(str); - // now switch it back - ClVariable::SetVarMap(pmapOld); - return pclv; - } else { - return &clvNil; - } - } -private: - StringToVarMap *_pmapVars; - bool _fAutoCreate; -}; - - -/* the "yyerror" function */ -void clerror(const char *sz); - -struct ClParseData { - ClParseData(istream &xi, const ClVarLookupFunction &lookup_func) - : _xi(xi), _lookup_func(lookup_func) { } - - ClConstraint *Pcn() { return _pcn; } - - ClVarSet _readOnlyVarsSoFar; - - istream & _xi; - ClConstraint * _pcn; - const ClVarLookupFunction &_lookup_func; -}; - - -inline -const ClStrength -&ClsFromSz(const char *sz) -{ - const ClStrength *pcls = &ClsRequired(); - double n1, n2, n3; - if (strcmp("required",sz) == 0) - ; /* initialized to ClsRequired, above */ - else if (strcasecmp("strong",sz) == 0) { pcls = &ClsStrong(); } - else if (strcasecmp("medium",sz) == 0) { pcls = &ClsMedium(); } - else if (strcasecmp("weak",sz) == 0) { pcls = &ClsWeak(); } - else if (sscanf(sz,"(%lf,%lf,%lf)",&n1,&n2,&n3) == 3) { - pcls = new ClStrength("parsed",n1,n2,n3); - } else { - throw ExCLParseErrorMisc("Error parsing strength"); - } - return *pcls; -} - - -#endif diff --git a/libs/cassowary/cassowary/ClSimplexSolver.h b/libs/cassowary/cassowary/ClSimplexSolver.h deleted file mode 100644 index c187992728..0000000000 --- a/libs/cassowary/cassowary/ClSimplexSolver.h +++ /dev/null @@ -1,588 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClSimplexSolver.h - -#ifndef ClSimplexSolver_H -#define ClSimplexSolver_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include -#include -#include -#include "Cassowary.h" -#include "ClSolver.h" -#include "ClTableau.h" -#include "ClLinearInequality.h" -#include "ClStrength.h" -#include "ClStayConstraint.h" -#include "ClEditConstraint.h" -#include "ClSlackVariable.h" -#include "ClObjectiveVariable.h" -#include "ClErrors.h" -#include "ClTypedefs.h" - -using std::list; -using std::stack; -using std::ostream; - -class ClVariable; -class ClPoint; -class ExCLRequiredFailureWithExplanation; - - -// ClSimplexSolver encapsulates the solving behaviour -// of the cassowary algorithm -class ClSimplexSolver : public ClSolver, public ClTableau { - protected: - class ClEditInfo; - typedef list ClEditInfoList; - - ClEditInfo *PEditInfoFromClv(ClVariable clv) { - ClEditInfoList::iterator it = _editInfoList.begin(); - for (; it != _editInfoList.end(); ++it) { - ClEditInfo *pei = (*it); - if (pei->_clv == clv) - return pei; - } - return 0; - } - - public: - - // Constructor - ClSimplexSolver() : - ClSolver(), - _objective(ClVariable(new ClObjectiveVariable("Z"))), - _slackCounter(0), - _artificialCounter(0), -#ifdef CL_FIND_LEAK - _cArtificialVarsDeleted(0), -#endif - _dummyCounter(0), - _epsilon(1e-8), - _fResetStayConstantsAutomatically(true), - _fNeedsSolving(false), - _fExplainFailure(false), - _pfnResolveCallback(0), - _pfnCnSatCallback(0) - { - _rows[_objective] = new ClLinearExpression(); - // start out with no edit variables - _stkCedcns.push(0); -#ifdef CL_TRACE - std::cerr << "objective row new@ " << _rows[_objective] << std::endl; -#endif - } - - virtual ~ClSimplexSolver(); - - // Add constraints so that lower<=var<=upper. (nil means no bound.) - ClSimplexSolver &AddLowerBound(ClVariable v, Number lower) - { - ClLinearInequality *pcn = new ClLinearInequality(ClLinearExpression(v - lower)); - return AddConstraint(pcn); - } - ClSimplexSolver &AddUpperBound(ClVariable v, Number upper) - { - ClLinearInequality *pcn = new ClLinearInequality(ClLinearExpression(upper - v)); - return AddConstraint(pcn); - } - ClSimplexSolver &AddBounds(ClVariable v, Number lower, Number upper) - { AddLowerBound(v,lower); AddUpperBound(v,upper); return *this; } - - // Add the constraint cn to the tableau - ClSimplexSolver &AddConstraint(ClConstraint *const pcn); - -#ifndef CL_NO_DEPRECATED - // Deprecated! --02/19/99 gjb - ClSimplexSolver &AddConstraint(ClConstraint &cn) - { return AddConstraint(&cn); } -#endif - - // Add an edit constraint for "v" with given strength - ClSimplexSolver &AddEditVar(const ClVariable v, const ClStrength &strength = ClsStrong(), - double weight = 1.0 ) - { - ClEditConstraint *pedit = new ClEditConstraint(v, strength, weight); - return AddConstraint(pedit); - } - - ClSimplexSolver &RemoveEditVar(ClVariable v) - { - ClEditInfo *pcei = PEditInfoFromClv(v); - if (!pcei) { - throw ExCLEditMisuse("Removing edit variable that was not found"); - } - ClConstraint *pcnEdit = pcei->_pconstraint; - RemoveConstraint(pcnEdit); - delete pcnEdit; - return *this; - } - - // BeginEdit() should be called before sending - // Resolve() messages, after adding the appropriate edit variables - ClSimplexSolver &BeginEdit() - { - if (_editInfoList.size() == 0) { - throw ExCLEditMisuse("BeginEdit called, but no edit variable"); - } - // may later want to do more in here - _infeasibleRows.clear(); - ResetStayConstants(); - _stkCedcns.push(_editInfoList.size()); - return *this; - } - - // EndEdit should be called after editing has finished - // for now, it just removes edit variables added from before the last BeginEdit - ClSimplexSolver &EndEdit() - { - if (_editInfoList.size() == 0) - throw ExCLEditMisuse("EndEdit called but no edit variables"); - Resolve(); - _stkCedcns.pop(); - RemoveEditVarsTo(_stkCedcns.top()); - // may later want to do more in here - return *this; - } - - // RemoveAllEditVars() just eliminates all the edit constraints - // that were added - ClSimplexSolver &RemoveAllEditVars() { RemoveEditVarsTo(0); return *this; } - - // remove the last added edit vars to leave only n edit vars left - ClSimplexSolver &RemoveEditVarsTo(unsigned int n); - - int numEditVars() const - { return _editInfoList.size(); } - - // Add weak stays to the x and y parts of each point. These have - // increasing weights so that the solver will try to satisfy the x - // and y stays on the same point, rather than the x stay on one and - // the y stay on another. - ClSimplexSolver &AddPointStays(const vector &listOfPoints, - const ClStrength &strength = ClsWeak()); - - ClSimplexSolver &AddPointStay(const ClVariable vx, const ClVariable vy, - const ClStrength &strength = ClsWeak(), - double weight = 1.0) - { AddStay(vx,strength,weight); AddStay(vy,strength,weight); return *this; } - - ClSimplexSolver &AddPointStay(const ClPoint &clp, - const ClStrength &strength = ClsWeak(), - double weight = 1.0); - - - // Add a stay of the given strength (default to weak) of v to the tableau - ClSimplexSolver &AddStay(const ClVariable v, - const ClStrength &strength = ClsWeak(), double weight = 1.0 ) - { - ClStayConstraint *pcn = new ClStayConstraint(v,strength,weight); - return AddConstraint(pcn); - } - - // Remove the constraint cn from the tableau - // Also remove any error variable associated with cn - ClSimplexSolver &RemoveConstraint(ClConstraint *const pcn) - { RemoveConstraintInternal(pcn); pcn->removedFrom(*this); return *this; } - -#ifndef CL_NO_DEPRECATED - // Deprecated! --02/19/99 gjb - ClSimplexSolver &RemoveConstraint(ClConstraint &cn) - { return RemoveConstraint(&cn); } -#endif - - - // Re-initialize this solver from the original constraints, thus - // getting rid of any accumulated numerical problems. (Actually, we - // haven't definitely observed any such problems yet) - void Reset(); - - // Re-solve the current collection of constraints, given the new - // values for the edit variables that have already been - // suggested (see SuggestValue() method) - // This is not guaranteed to work if you remove an edit constraint - // from the middle of the edit constraints you added - // (e.g., edit A, edit B, edit C, remove B -> this will fail!) - // DEPRECATED - void Resolve(); - - // Re-solve the current collection of constraints for new values for - // the constants of the edit variables. - // This is implemented in terms of SuggestValue-s, and is - // less efficient than that more natural interface - void Resolve(const vector &newEditConstants); - - // Convenience function for Resolve-s of two variables - void Resolve(Number x, Number y) - { - vector vals; - vals.push_back(x); - vals.push_back(y); - Resolve(vals); - } - - // Suggest a new value for an edit variable - // the variable needs to be added as an edit variable - // and BeginEdit() needs to be called before this is called. - // The tableau will not be solved completely until - // after Resolve() has been called - ClSimplexSolver &SuggestValue(ClVariable v, Number x); - - // Set and check whether or not the solver will attempt to compile - // an explanation of failure when a required constraint conflicts - // with another required constraint - ClSimplexSolver &SetExplaining(bool f) - { _fExplainFailure = f; return *this; } - - bool FIsExplaining() const - { return _fExplainFailure; } - - // If autosolving has been turned off, client code needs - // to explicitly call solve() before accessing variables - // values - ClSimplexSolver &Solve() - { -#ifdef CL_SOLVER_CHECK_INTEGRITY - AssertValid(); -#endif - if (_fNeedsSolving) - { - Optimize(_objective); - SetExternalVariables(); -#ifdef CL_TRACE_VERBOSE - std::cerr << "Manual solve actually solving." << std::endl; -#endif - } - return *this; - } - - ClSimplexSolver &SetEditedValue(ClVariable v, double n) - { - if (!FContainsVariable(v)) - { - ChangeClv(v,n); - return *this; - } - - if (!ClApprox(n, v.Value())) - { - AddEditVar(v); - BeginEdit(); - SuggestValue(v,n); - EndEdit(); - } - return *this; - } - - // Solver contains the variable if it's in either the columns - // list or the rows list - bool FContainsVariable(const ClVariable v) - { return ColumnsHasKey(v) || RowExpression(v); } - - ClSimplexSolver &AddVar(const ClVariable v) - { if (!FContainsVariable(v)) - { - AddStay(v); -#ifdef CL_TRACE - std::cerr << "added initial stay on " << v << std::endl; -#endif - } - return *this; } - - typedef void (*PfnResolveCallback)(ClSimplexSolver *psolver); - - void SetResolveCallback(PfnResolveCallback pfn) - { _pfnResolveCallback = pfn; } - - typedef void (*PfnCnSatCallback)(ClSimplexSolver *psolver, - ClConstraint *pcn, bool fSatisfied); - - void SetCnSatCallback(PfnCnSatCallback pfn) - { _pfnCnSatCallback = pfn; } - -#ifndef CL_NO_IO - friend ostream &operator<<(ostream &xo, const ClSimplexSolver &tableau); - - ostream &PrintOn(ostream &xo) const; - - ostream &PrintInternalInfo(ostream &xo) const; - - ostream &PrintOnVerbose(ostream &xo) const - { PrintOn(xo); PrintInternalInfo(xo); xo << std::endl; return xo; } - -#endif - - const ClConstraintToVarMap &ConstraintMap() const - { return _markerVars; } - - const ClVarToConstraintMap &MarkerMap() const - { return _constraintsMarked; } - - bool FIsConstraintSatisfied(const ClConstraint *const pcn) const; - - // DEPRECATED - bool FIsConstraintSatisfied(const ClConstraint &pcn) const - { return FIsConstraintSatisfied(&pcn); } - - // re-set all the external variables to their current values - // most importantly, this re-calls all the ChangeClv callbacks - // (which might be used to copy the ClVariable's value to another - // variable) - void UpdateExternalVariables() - { SetExternalVariables(); } - - // A. Beurive' Tue Jul 6 17:05:39 CEST 1999 - void ChangeStrengthAndWeight(ClConstraint *pcn, const ClStrength &strength, double weight); - void ChangeStrength(ClConstraint *pcn, const ClStrength &strength); - void ChangeWeight(ClConstraint *pcn, double weight); - // void DisplayObjective(); - - // Each of the non-required stays will be represented by an equation - // of the form - // v = c + eplus - eminus - // where v is the variable with the stay, c is the previous value of - // v, and eplus and eminus are slack variables that hold the error - // in satisfying the stay constraint. We are about to change - // something, and we want to fix the constants in the equations - // representing the stays. If both eplus and eminus are nonbasic - // they have value 0 in the current solution, meaning the previous - // stay was exactly satisfied. In this case nothing needs to be - // changed. Otherwise one of them is basic, and the other must - // occur only in the Expression for that basic error variable. - // Reset the Constant in this Expression to 0. - void ResetStayConstants(); - - ClSimplexSolver &SetAutoResetStayConstants(bool f) - { _fResetStayConstantsAutomatically = f; if (f) ResetStayConstants(); return *this; } - - bool FIsAutoResetStayConstants() const - { return _fResetStayConstantsAutomatically; } - - protected: - - // ClEditInfo is a privately-used class - // that just wraps a constraint, its positive and negative - // error variables, and its prior edit Constant. - // It is used as values in _editInfoList, and replaces - // the parallel vectors of error variables and previous edit - // constants from the smalltalk version of the code. - class ClEditInfo { - friend class ClSimplexSolver; - public: - - // These instances own none of the pointers; - // the tableau row (the Expression) owns the peplus, peminus, - // and AddEditVar/RemoveEditVar pair or the client code owns - // the constraint object - ClEditInfo(ClVariable clv, - ClEditConstraint *pconstraint, - ClVariable eplus, ClVariable eminus, - Number prevEditConstant) - :_clv(clv), - _pconstraint(pconstraint), - _clvEditPlus(eplus), _clvEditMinus(eminus), - _prevEditConstant(prevEditConstant) - { } - - ~ClEditInfo() - { } - - ostream &PrintOn(ostream &xo) const - { xo << _clv << " -> [" << _clvEditPlus << ", " << _clvEditMinus << "](" - << _prevEditConstant << ")@" << " -- " - << *_pconstraint; - return xo; } - - friend ostream &operator<<(ostream &xo, const ClEditInfo &cei) - { return cei.PrintOn(xo); } - - private: - ClVariable _clv; - ClConstraint *_pconstraint; - ClVariable _clvEditPlus; - ClVariable _clvEditMinus; - Number _prevEditConstant; - }; - - // Add the constraint expr=0 to the inequality tableau using an - // artificial variable. To do this, create an artificial variable - // av and Add av=expr to the inequality tableau, then make av be 0. - // (Raise an exception if we can't attain av=0.) - // (Raise an exception if we can't attain av=0.) If the Add fails, - // prepare an explanation in e that describes why it failed (note - // that an empty explanation is considered to mean the explanation - // encompasses all active constraints. - bool AddWithArtificialVariable(ClLinearExpression &pexpr, - ExCLRequiredFailureWithExplanation &e); - - // Using the given equation (av = cle) build an explanation which - // implicates all constraints used to construct the equation. That - // is, everything for which the variables in the equation are markers. - // Thanks to Steve Wolfman for the implementation of the explanation feature - void BuildExplanation(ExCLRequiredFailureWithExplanation & e, - ClVariable av, - const ClLinearExpression * pcle); - - // We are trying to Add the constraint expr=0 to the appropriate - // tableau. Try to Add expr directly to the tableax without - // creating an artificial variable. Return true if successful and - // false if not. - bool TryAddingDirectly(ClLinearExpression &pexpr); - - // We are trying to Add the constraint expr=0 to the tableaux. Try - // to choose a subject (a variable to become basic) from among the - // current variables in expr. If expr contains any unrestricted - // variables, then we must choose an unrestricted variable as the - // subject. Also, if the subject is new to the solver we won't have - // to do any substitutions, so we prefer new variables to ones that - // are currently noted as parametric. If expr contains only - // restricted variables, if there is a restricted variable with a - // negative coefficient that is new to the solver we can make that - // the subject. Otherwise we can't find a subject, so return nil. - // (In this last case we have to Add an artificial variable and use - // that variable as the subject -- this is done outside this method - // though.) - // - // Note: in checking for variables that are new to the solver, we - // ignore whether a variable occurs in the objective function, since - // new slack variables are added to the objective function by - // 'NewExpression:', which is called before this method. - ClVariable ChooseSubject(ClLinearExpression &pexpr); - - // Each of the non-required edits will be represented by an equation - // of the form - // v = c + eplus - eminus - // where v is the variable with the edit, c is the previous edit - // value, and eplus and eminus are slack variables that hold the - // error in satisfying the edit constraint. We are about to change - // something, and we want to fix the constants in the equations - // representing the edit constraints. If one of eplus and eminus is - // basic, the other must occur only in the Expression for that basic - // error variable. (They can't both be basic.) Fix the Constant in - // this Expression. Otherwise they are both nonbasic. Find all of - // the expressions in which they occur, and fix the constants in - // those. See the UIST paper for details. - // (This comment was for resetEditConstants(), but that is now - // gone since it was part of the screwey vector-based interface - // to resolveing. --02/15/99 gjb) - void DeltaEditConstant(Number delta, ClVariable pv1, ClVariable pv2); - - // We have set new values for the constants in the edit constraints. - // Re-Optimize using the dual simplex algorithm. - void DualOptimize(); - - // Make a new linear Expression representing the constraint cn, - // replacing any basic variables with their defining expressions. - // Normalize if necessary so that the Constant is non-negative. If - // the constraint is non-required give its error variables an - // appropriate weight in the objective function. - ClLinearExpression *NewExpression(const ClConstraint *pcn, - /* output to */ - ClVariable &clvEplus, - ClVariable &clvEminus, - Number &prevEConstant); - - // Minimize the value of the objective. (The tableau should already - // be feasible.) - void Optimize(ClVariable zVar); - - // Do a Pivot. Move entryVar into the basis (i.e. make it a basic variable), - // and move exitVar out of the basis (i.e., make it a parametric variable) - void Pivot(ClVariable entryVar, ClVariable exitVar); - - // Set the external variables known to this solver to their appropriate values. - // Set each external basic variable to its value, and set each - // external parametric variable to 0. (It isn't clear that we will - // ever have external parametric variables -- every external - // variable should either have a stay on it, or have an equation - // that defines it in terms of other external variables that do have - // stays. For the moment I'll put this in though.) Variables that - // are internal to the solver don't actually store values -- their - // values are just implicit in the tableu -- so we don't need to set - // them. - void SetExternalVariables(); - - // this gets called by RemoveConstraint and by AddConstraint when the - // contraint we're trying to Add is inconsistent - ClSimplexSolver &RemoveConstraintInternal(const ClConstraint *const pcn); - - void ChangeClv(ClVariable clv, Number n) { - clv.ChangeValue(n); - if (_pfnChangeClvCallback) - _pfnChangeClvCallback(&clv,this); - } - - /// instance variables - - // the arrays of positive and negative error vars for the stay constraints - // (need both positive and negative since they have only non-negative values) - ClVarVector _stayMinusErrorVars; - ClVarVector _stayPlusErrorVars; - - // give error variables for a non required constraint, - // maps to ClSlackVariable-s - ClConstraintToVarSetMap _errorVars; - - // Return a lookup table giving the marker variable for each - // constraint (used when deleting a constraint). - ClConstraintToVarMap _markerVars; - - // Reverse of the above-- a lookup table giving the constraint - // for each marker variable (used when building failure explanations) - ClVarToConstraintMap _constraintsMarked; - - ClVariable _objective; - - // Map edit variables to their constraints, errors, and prior - // values - ClEditInfoList _editInfoList; - - int _slackCounter; - int _artificialCounter; -#ifdef CL_FIND_LEAK - int _cArtificialVarsDeleted; -#endif - int _dummyCounter; - const double _epsilon; - - bool _fResetStayConstantsAutomatically; - bool _fNeedsSolving; - bool _fExplainFailure; - - PfnResolveCallback _pfnResolveCallback; - PfnCnSatCallback _pfnCnSatCallback; - - // C-style extension mechanism so I - // don't have to wrap ScwmClSolver separately - void *_pv; - - // a stack of the number of edit constraints - // that existed at the prior BeginEdit. - // an EndEdit needs to pop off the top value, - // then remove constraints to get down - // to the # of constraints as in _stkCedcns.top() - stack _stkCedcns; - - -#ifndef CL_NO_IO - -friend ostream &PrintTo(ostream &xo, const ClSimplexSolver::ClEditInfoList &listPEditInfo); -friend ostream &operator<<(ostream &xo, const ClSimplexSolver::ClEditInfoList &listPEditInfo); - -#endif - -}; - -#endif // ClSimplexSolver_H diff --git a/libs/cassowary/cassowary/ClSlackVariable.h b/libs/cassowary/cassowary/ClSlackVariable.h deleted file mode 100644 index ca116702e9..0000000000 --- a/libs/cassowary/cassowary/ClSlackVariable.h +++ /dev/null @@ -1,75 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClSlackVariable.h - -#ifndef ClSlackVariable_H -#define ClSlackVariable_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include "Cassowary.h" -#include "ClAbstractVariable.h" - -class ClTableau; -class ClSimplexSolver; - - -class ClSlackVariable : public ClAbstractVariable { -public: -#ifdef CL_FIND_LEAK - ~ClSlackVariable() { --cSlackVariables; }; - - static long cSlackVariables; -#endif - -protected: - friend class ClTableau; - friend class ClSimplexSolver; - - ClSlackVariable(string Name = "") : - ClAbstractVariable(Name) - { -#ifdef CL_FIND_LEAK - ++cSlackVariables; -#endif - } - - ClSlackVariable(long number, char *prefix) : - ClAbstractVariable(number,prefix) - { -#ifdef CL_FIND_LEAK - ++cSlackVariables; -#endif - } - -#ifndef CL_NO_IO - virtual ostream &PrintOn(ostream &xo) const - { - xo << "[" << Name() << ":slack]"; - return xo; - } -#endif - - virtual bool IsExternal() const - { return false; } - - virtual bool IsPivotable() const - { return true; } - - virtual bool IsRestricted() const - { return true; } - -}; - - -#endif diff --git a/libs/cassowary/cassowary/ClSolver.h b/libs/cassowary/cassowary/ClSolver.h deleted file mode 100644 index 16e798d491..0000000000 --- a/libs/cassowary/cassowary/ClSolver.h +++ /dev/null @@ -1,167 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClSolver.h - -#ifndef ClSolver_H -#define ClSolver_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include "Cassowary.h" -#include "ClErrors.h" -#include "ClTypedefs.h" -#include -#include - -using std::list; -using std::ostream; - -class ClVariable; - -// ClSolver is an abstract base class -class ClSolver { - public: - - ClSolver() : _pv(0), _fAutosolve(true), _pfnChangeClvCallback(0) { } - - virtual ~ClSolver() - { } - - // Add the constraint cn to the solver - virtual ClSolver &AddConstraint(ClConstraint *const pcn) = 0; - - // Remove the constraint cn from the solver - virtual ClSolver &RemoveConstraint(ClConstraint *const pcn) = 0; - - // Same as above, but returns false if the constraint cannot be solved - // (i.e., the resulting system would be unsatisfiable) - // The above function "AddConstraint" throws an exception in that case - // which may be inconvenient - virtual bool AddConstraintNoException(ClConstraint *const pcn) - { - try { - AddConstraint(pcn); - return true; - } - catch (const ExCLRequiredFailure &e) - { return false; } - catch (const ExCLTooDifficult &e) - { return false; } - } - -#ifndef CL_NO_DEPRECATED - // Deprecated --02/22/99 gjb - bool AddConstraintNoException(ClConstraint &cn) - { return AddConstraintNoException(&cn); } -#endif - - virtual bool RemoveConstraintNoException(ClConstraint *const pcn) - { - try { - RemoveConstraint(pcn); - return true; - } - catch (const ExCLConstraintNotFound &e) - { return false; } - } - -#ifndef CL_NO_DEPRECATED - // Deprecated --02/22/99 gjb - bool RemoveConstraintNoException(ClConstraint &cn) - { return RemoveConstraintNoException(&cn); } -#endif - - - virtual ClSolver &Solve() - { assert(false); return *this; } - - virtual bool SolveNoException() - { - try { - Solve(); - return true; - } - catch (const ExCLTooDifficult &e) - { return false; } - catch (const ExCLRequiredFailure &e) - { return false; } - } - - - virtual void Resolve() - { assert(false); } - - void SetPv(void *pv) - { _pv = pv; } - - void *Pv() const - { return _pv; } - - typedef void (*PfnChangeClvCallback)(ClVariable *pclv, ClSolver *psolver); - - void SetChangeClvCallback(PfnChangeClvCallback pfn) - { _pfnChangeClvCallback = pfn; } - - // Control whether optimization and setting of external variables - // is done automatically or not. By default it is done - // automatically and solve() never needs to be explicitly - // called by client code; if SetAutosolve is put to false, - // then solve() needs to be invoked explicitly before using - // variables' values - // (Turning off autosolve while adding lots and lots of - // constraints [ala the addDel test in ClTests] saved - // about 20% in runtime, from 68sec to 54sec for 900 constraints, - // with 126 failed adds) - ClSolver &SetAutosolve(bool f) - { _fAutosolve = f; if (f) Solve(); return *this; } - - // Tell whether we are autosolving - bool FIsAutosolving() const - { return _fAutosolve; } - - -#ifndef CL_NO_IO - friend ostream &operator<<(ostream &xo, const ClSolver &solver); - - virtual ostream &PrintOn(ostream &xo) const = 0; - -#endif - - protected: - - // C-style extension mechanism so I - // don't have to wrap ScwmClSolver separately - void *_pv; - - bool _fAutosolve; - - PfnChangeClvCallback _pfnChangeClvCallback; -}; - - -#ifndef CL_NO_IO -ostream &PrintTo(ostream &xo, const ClVarVector &varlist); -ostream &operator<<(ostream &xo, const ClVarVector &varlist); - -ostream &PrintTo(ostream &xo, const ClConstraintToVarSetMap &mapCnToVarSet); -ostream &operator<<(ostream &xo, const ClConstraintToVarSetMap &mapCnToVarSet); - -ostream &PrintTo(ostream &xo, const ClConstraintSet &setCn); -ostream &operator<<(ostream &xo, const ClConstraintSet &setCn); - -ostream &PrintTo(ostream &xo, const list &listFDN); -ostream &operator<<(ostream &xo, const list &listFDN); - -#endif - -#endif diff --git a/libs/cassowary/cassowary/ClStayConstraint.h b/libs/cassowary/cassowary/ClStayConstraint.h deleted file mode 100644 index f009731b09..0000000000 --- a/libs/cassowary/cassowary/ClStayConstraint.h +++ /dev/null @@ -1,43 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClStayConstraint.h - -#ifndef ClStayConstraint_H -#define ClStayConstraint_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include "Cassowary.h" -#include "ClEditOrStayConstraint.h" - -class ClStayConstraint : public ClEditOrStayConstraint { - typedef ClEditOrStayConstraint super; - public: - - ClStayConstraint(const ClVariable var, - const ClStrength &strength = ClsWeak(), double weight = 1.0 ) : - ClEditOrStayConstraint(var,strength,weight) - { } - - virtual bool isStayConstraint() const - { return true; } - -#ifndef CL_NO_IO - virtual ostream &PrintOn(ostream &xo) const - { super::PrintOn(xo); return xo << " STAY)"; } -#endif - - private: -}; - -#endif diff --git a/libs/cassowary/cassowary/ClStrength.h b/libs/cassowary/cassowary/ClStrength.h deleted file mode 100644 index 644c04cb5f..0000000000 --- a/libs/cassowary/cassowary/ClStrength.h +++ /dev/null @@ -1,91 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClStrength.h - -#ifndef ClStrength_H -#define ClStrength_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include - -#include "Cassowary.h" -#include "ClSymbolicWeight.h" - -using std::string; - -class ClStrength; - -const ClStrength &ClsRequired(); -const ClStrength &ClsStrong(); -const ClStrength &ClsMedium(); -const ClStrength &ClsWeak(); - -class ClStrength { - public: - - ClStrength(const string &Name, const ClSymbolicWeight &symbolicWeight) : - _name(Name), _symbolicWeight(symbolicWeight) - { } - - // special case for when nLevels = 3, should assert nLevels() == 3 - ClStrength(const string &Name, double w1, double w2, double w3); - - virtual ~ClStrength() - { } - - virtual bool IsRequired() const - { return (_symbolicWeight == ClsRequired()._symbolicWeight); } - -#ifndef CL_NO_IO - virtual ostream &PrintOn(ostream &xo) const - { - xo << Name(); - if (!IsRequired()) - xo << ":" << symbolicWeight(); - return xo; - } - - friend ostream& operator<<(ostream &xos, const ClStrength &Cls) - { Cls.PrintOn(xos); return xos; } - -#endif - - virtual const ClSymbolicWeight &symbolicWeight() const - { return _symbolicWeight; } - - void SetPv(void *pv) - { _pv = pv; } - - void *Pv() const - { return _pv; } - - private: - string Name() const - { return _name; } - - void SetName(string Name) - { _name = Name; } - - void SetSymbolicWeight(const ClSymbolicWeight &symbolicWeight) - { _symbolicWeight = symbolicWeight; } - - // instance variables - string _name; - ClSymbolicWeight _symbolicWeight; - - void *_pv; - -}; - -#endif diff --git a/libs/cassowary/cassowary/ClSymbolicWeight.h b/libs/cassowary/cassowary/ClSymbolicWeight.h deleted file mode 100644 index 1c0339c887..0000000000 --- a/libs/cassowary/cassowary/ClSymbolicWeight.h +++ /dev/null @@ -1,197 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClSymbolicWeight.h - -#ifndef ClSymbolicWeight_H -#define ClSymbolicWeight_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include "Cassowary.h" -#include "ClErrors.h" -#include -#include - -using std::vector; -using std::ostream; - -class ClSymbolicWeight { - public: - ClSymbolicWeight(unsigned int CLevels = 3, Number value = 0.0); - - ClSymbolicWeight(Number w1, Number w2, Number w3); - - ClSymbolicWeight(const vector &weights); - - static ClSymbolicWeight &Zero(); - - ClSymbolicWeight &negated(); - - ClSymbolicWeight &MultiplyMe(Number n); - - ClSymbolicWeight Times(Number n) const - { ClSymbolicWeight cl = *this; cl.MultiplyMe(n); return cl; } - - ClSymbolicWeight DivideBy(Number n) const; - - ClSymbolicWeight &addtoMe(const ClSymbolicWeight &cl); - - ClSymbolicWeight Add(const ClSymbolicWeight &cl) const - { ClSymbolicWeight clRet = *this; clRet.addtoMe(cl); return clRet; } - - ClSymbolicWeight Subtract(const ClSymbolicWeight &cl) const; - - ClSymbolicWeight operator*(const Number &n) const - { return Times(n); } - - ClSymbolicWeight operator/(const Number &n) const - { return DivideBy(n); } - - // FIXGJB: can we express this statically? - ClSymbolicWeight operator*(ClSymbolicWeight &w) const - { throw ExCLInternalError("Multiplication of symbolic weights encountered"); - return w; } - ClSymbolicWeight &operator*=(ClSymbolicWeight &w) - { throw ExCLInternalError("Multiplicative assignment of symbolic weights encountered"); - return w; } - - // FIXGJB: can we express this statically? - ClSymbolicWeight operator-() const - { throw ExCLInternalError("Can not negate a symbolic weight"); - return ClSymbolicWeight::Zero(); } - - friend ClSymbolicWeight ReciprocalOf(const ClSymbolicWeight &); - - ClSymbolicWeight &operator*=(const Number &n) - { return MultiplyMe(n); } - - ClSymbolicWeight operator+(const ClSymbolicWeight &cl) const - { return Add(cl); } - - ClSymbolicWeight operator+=(const ClSymbolicWeight &cl) - { return addtoMe(cl); } - - ClSymbolicWeight operator*(const Number &n) - { ClSymbolicWeight answer(*this); - answer *= n; - return answer; } - - bool lessThan(const ClSymbolicWeight &cl) const; - bool lessThanOrEqual(const ClSymbolicWeight &cl) const; - bool equal(const ClSymbolicWeight &cl) const; - bool greaterThan(const ClSymbolicWeight &cl) const; - bool greaterThanOrEqual(const ClSymbolicWeight &cl) const; - bool isNegative() const; - - friend bool operator==(const ClSymbolicWeight &cl1, const ClSymbolicWeight &cl2) - { return cl1.equal(cl2); } - - friend bool operator!=(const ClSymbolicWeight &cl1, const ClSymbolicWeight &cl2) - { return !(cl1 == cl2); } - - friend bool operator<(const ClSymbolicWeight &cl1, const ClSymbolicWeight &cl2) - { return cl1.lessThan(cl2); } - - friend bool operator>(const ClSymbolicWeight &cl1, const ClSymbolicWeight &cl2) - { return (cl2 < cl1); } - - // function.h provides operator>, >=, <= from operator< - - double AsDouble() const - { - vector::const_reverse_iterator i = _values.rbegin(); - Number sum = 0; - Number factor = 1; - // A. Beurive' Wed Jul 7 11:07:47 CEST 1999 - Number multiplier = 1000000; - for ( ; i != _values.rend(); ++i) - { - sum += *i * factor; - factor *= multiplier; - } - return sum; - } - -#ifndef CL_NO_IO - ostream &PrintOn(ostream &xo) const - { - vector::const_iterator i = _values.begin(); - if (i == _values.end()) - return xo; - - xo << *i; - for (++i; i != _values.end(); ++i) - { - xo << "," << *i; - } - return xo; - } - - // FIXGJB: use a template function to generate these automatically - friend ostream& operator<<(ostream &xos, const ClSymbolicWeight &clsw) - { clsw.PrintOn(xos); return xos; } -#endif - - int CLevels() const - { return _values.size(); } - - friend bool ClApprox(const ClSymbolicWeight &cl, Number n); - friend bool ClApprox(const ClSymbolicWeight &cl1, const ClSymbolicWeight &cl2); - - private: - vector _values; - - void push_back(Number d) - { _values.push_back(d); } - -}; - -inline bool ClApprox(const ClSymbolicWeight &cl, Number n) -{ - vector::const_iterator it = cl._values.begin(); - if (!ClApprox(*it,n)) - return false; - - ++it; - for (; it != cl._values.end(); ++it) - { - if (!ClApprox(*it,0)) - return false; - } - - return true; -} - -inline bool ClApprox(const ClSymbolicWeight &cl1, const ClSymbolicWeight &cl2) -{ - vector::const_iterator it1 = cl1._values.begin(); - vector::const_iterator it2 = cl2._values.begin(); - - for (; it1 != cl1._values.end() && it2 != cl2._values.end(); - ++it1, ++it2) - { - if (!ClApprox(*it1,*it2)) - return false; - } - - if (it1 == cl1._values.end() && it2 == cl2._values.end()) - return true; - - return false; -} - -inline ClSymbolicWeight ReciprocalOf(const ClSymbolicWeight &) -{ throw(ExCLInternalError("Cannot take ReciprocalOf symbolic weight")); - return ClSymbolicWeight::Zero(); } - -#endif diff --git a/libs/cassowary/cassowary/ClTableau.h b/libs/cassowary/cassowary/ClTableau.h deleted file mode 100644 index 117ed0fb9d..0000000000 --- a/libs/cassowary/cassowary/ClTableau.h +++ /dev/null @@ -1,230 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClTableau.h - -#ifndef ClTableau_H -#define ClTableau_H - -#include - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include "Cassowary.h" -#include "ClLinearExpression.h" -#include "ClVariable.h" -#include "ClTypedefs.h" - - -#ifndef CL_NO_IO -class ClTableau; - -ostream &operator<<(ostream &xo, const ClTableau &clt); - -ostream &operator<<(ostream &xo, const ClVarSet &varset); - -ostream &operator<<(ostream &xo, const ClTableauColumnsMap &varmap); - -ostream &operator<<(ostream &xo, const ClTableauRowsMap &rows); - -ostream &operator<<(ostream &xo, const ClVarVector &varlist); -#endif // CL_NO_IO - -class ClTableau { - - public: - // No public constructor, since this does nothing but support - // an ADT for the ClSimplexSolver - - // Variable v has been removed from an Expression. If the - // Expression is in a tableau the corresponding basic variable is - // subject (or if subject is nil then it's in the objective function). - // Update the column cross-indices. - void NoteRemovedVariable(ClVariable v, ClVariable subject) - { -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); - std::cerr << "(" << v << ", " << subject << ")" << std::endl; -#endif - ClVarSet &column = _columns[v]; - ClVarSet::const_iterator it = column.find(subject); - assert(it != column.end()); - column.erase(it); -#ifdef CL_TRACE_VERBOSE - std::cerr << "v = " << v << " and Columns[v].size() = " - << column.size() << std::endl; -#endif - if (column.size() == 0) - { - _columns.erase(v); - _externalRows.erase(v); - _externalParametricVars.erase(v); - } - } - - // v has been added to the linear Expression for subject - // update column cross indices - void NoteAddedVariable(ClVariable v, ClVariable subject) - { -#ifdef CL_TRACE - Tracer TRACER(__FUNCTION__); - std::cerr << "(" << v << ", " << subject << ")" << std::endl; -#endif - _columns[v].insert(subject); - if (v.IsExternal() && !FIsBasicVar(v)) - { - _externalParametricVars.insert(v); - } - } - -#ifndef CL_NO_IO - std::ostream &PrintOn(ostream &xo) const; - - ostream &PrintInternalInfo(ostream &xo) const; - - ostream &printExternalVariablesTo(ostream &xo) const; - -#endif - - // Check integrity of the tableau - // not complete, yet, but a start, at least - // Guard calls to AssertValid with CL_SOLVER_CHECK_INTEGRITY, - // since this is expensive - virtual void AssertValid() const { -#ifndef NDEBUG - // all external basic variables are in _externalRows - // and all external parametric variables are in _externalParametricVars - ClTableauRowsMap::const_iterator itRow = _rows.begin(); - for (; itRow != _rows.end(); ++itRow) - { - const ClVariable clv = (*itRow).first; - if (clv.IsExternal()) - { - if (_externalRows.find(clv) == _externalRows.end()) - { -#ifndef CL_NO_IO - std::cerr << "External basic variable " << clv - << " is not in _externalRows" << std::endl; -#endif - } - } - const ClLinearExpression *pcle = RowExpression(clv); - assert(pcle); - ClVarToNumberMap::const_iterator it = pcle->Terms().begin(); - for (; it != pcle->Terms().end(); ++it) - { - ClVariable clv = (*it).first; - if (clv.IsExternal()) - { - if (_externalParametricVars.find(clv) == _externalParametricVars.end()) - { -#ifndef CL_NO_IO - std::cerr << "External parametric variable " << clv - << " is not in _externalParametricVars" << std::endl; -#endif - } - } - } - } -#endif /* !NDEBUG */ - } - - - protected: - // Constructor -- want to start with empty objects so not much to do - ClTableau() - { } - - virtual ~ClTableau(); - - // Add v=expr to the tableau, update column cross indices - // v becomes a basic variable - // expr is now owned by ClTableau class, - // and ClTableauis responsible for deleting it - // (also, expr better be allocated on the heap!) - void addRow(ClVariable v, const ClLinearExpression &expr); - - // Remove v from the tableau -- remove the column cross indices for v - // and remove v from every Expression in rows in which v occurs - // returns a pointer to the variable (since we often want to delete - // the variable) - ClVariable RemoveColumn(ClVariable v); - - // Remove the basic variable v from the tableau row v=expr - // Then update column cross indices - // Probably want to call delete on the ClLinearExpression * returned - // unless you're adding that same Expression back into the - // tableau - ClLinearExpression *RemoveRow(ClVariable v); - - // Replace all occurrences of oldVar with expr, and update column cross indices - // oldVar should now be a basic variable - void SubstituteOut(ClVariable oldVar, const ClLinearExpression &expr); - - ClTableauColumnsMap Columns() - { return _columns; } - - ClTableauRowsMap Rows() - { return _rows; } - - // return true iff the variable subject is in the Columns keys - bool ColumnsHasKey(ClVariable subject) const - { - ClTableauColumnsMap::const_iterator i = _columns.find(subject); - return (i != _columns.end()); - } - - const ClLinearExpression *RowExpression(ClVariable v) const - { - ClTableauRowsMap::const_iterator i = _rows.find(v); - if (i != _rows.end()) - return (*i).second; - else - return 0; - } - - ClLinearExpression *RowExpression(ClVariable v) - { - const ClTableau *pthis = const_cast(this); - return const_cast(pthis->RowExpression(v)); - } - - - bool FIsBasicVar(ClVariable v) - { return RowExpression(v) != 0; } - - // private: FIXGJB: can I improve the encapsulation? - - // _columns is a mapping from variables which occur in expressions to the - // set of basic variables whose expressions contain them - // i.e., it's a mapping from variables in expressions (a column) to the - // set of rows that contain them - ClTableauColumnsMap _columns; - - // _rows maps basic variables to the expressions for that row in the tableau - ClTableauRowsMap _rows; - - // the collection of basic variables that have infeasible rows - // (used when reoptimizing) - ClVarSet _infeasibleRows; - - // the set of rows where the basic variable is external - // this was added to the C++ version to reduce time in SetExternalVariables() - ClVarSet _externalRows; - - // the set of external variables which are parametric - // this was added to the C++ version to reduce time in SetExternalVariables() - ClVarSet _externalParametricVars; - -}; - -#endif diff --git a/libs/cassowary/cassowary/ClTypedefs.h b/libs/cassowary/cassowary/ClTypedefs.h deleted file mode 100644 index 74b625a72b..0000000000 --- a/libs/cassowary/cassowary/ClTypedefs.h +++ /dev/null @@ -1,48 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClTypedefs.h - -#ifndef CL_TYPEDEFS_H__ -#define CL_TYPEDEFS_H__ - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include "ClLinearExpression_fwd.h" -#include -#include -#include - -using std::set; -using std::map; -using std::vector; - -class ClVariable; -class ClConstraint; -class ClEditInfo; - -typedef set ClVarSet; -typedef map ClTableauColumnsMap; -typedef map ClTableauRowsMap; - -// For Solver -typedef map ClConstraintToVarSetMap; -typedef map ClConstraintToVarMap; -typedef map ClVarToConstraintMap; -typedef vector ClVarVector; - -typedef set ClConstraintSet; - -// For FDSolver -typedef map ClVarToConstraintSetMap; - -#endif diff --git a/libs/cassowary/cassowary/ClVariable.h b/libs/cassowary/cassowary/ClVariable.h deleted file mode 100644 index b046247c67..0000000000 --- a/libs/cassowary/cassowary/ClVariable.h +++ /dev/null @@ -1,169 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// ClVariable.h -// A handle on ClAbstractVariable-s - -#ifndef ClVariable_H -#define ClVariable_H - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include -#include -#include -#include "Cassowary.h" -#include "ClFloatVariable.h" -#include "ClFDVariable.h" - -using std::map; -using std::string; - -class ClVariable; -typedef map StringToVarMap; - - -class ClVariable { - ClAbstractVariable *pclv; -public: - // converters from raw ClAbstractVariable - ClVariable(ClAbstractVariable *pclv_) : pclv(pclv_) { } - ClVariable(ClAbstractVariable &clv_) : pclv(&clv_) { } - - // Copy ctr - ClVariable(const ClVariable &clv_) : pclv(clv_.pclv) { } - - /// These ctrs build ClFloatVariable-s - ClVariable(string name, Number Value = 0.0) - : pclv(new ClFloatVariable(name,Value)) - { if (pmapStrPclv) { (*pmapStrPclv)[name] = *this; } } - ClVariable(Number Value = 0.0) - : pclv(new ClFloatVariable(Value)) { } - ClVariable(long number, char *prefix, Number Value = 0.0) - : pclv(new ClFloatVariable(number,prefix,Value)) { } - - // This one builds a ClFDVariable - ClVariable(ClFDVariable *pcfv) - : pclv(pcfv) - { if (pmapStrPclv) { (*pmapStrPclv)[pcfv->Name()] = *this; } } - - // Destructor - virtual ~ClVariable() {}; - - /// permit ClVariables to be used as pointers to pclvs - ClAbstractVariable *operator->() { return pclv; } - const ClAbstractVariable *operator->() const { return pclv; } - - /// and also forward the function calls along - - - bool IsFloatVariable() const { assert(pclv); return pclv->IsFloatVariable(); } - bool IsFDVariable() const { assert(pclv); return pclv->IsFDVariable(); } - bool IsDummy() const { assert(pclv); return pclv->IsDummy(); } - bool IsExternal() const { assert(pclv); return pclv->IsExternal(); } - bool IsPivotable() const { assert(pclv); return pclv->IsPivotable(); } - bool IsRestricted() const { assert(pclv); return pclv->IsRestricted(); } - - string Name() const { assert(pclv); return pclv->Name(); } - - Number Value() const { assert(pclv); return pclv->Value(); } - int IntValue() const { assert(pclv); return pclv->IntValue(); } - void SetValue(Number Value) - { assert(pclv); pclv->SetValue(Value); } - void ChangeValue(Number Value) - { assert(pclv); pclv->ChangeValue(Value); } - void SetPv(void *pv) - { assert(pclv); pclv->SetPv(pv); } - void *Pv() const - { assert(pclv); return pclv->Pv(); } - - void SetName(string const &nm) { - assert(pclv); - if (pmapStrPclv) { - pmapStrPclv->erase(Name()); - (*pmapStrPclv)[nm] = *this; - } - pclv->SetName(nm); - } - - ClAbstractVariable *get_pclv() const { return pclv; } - bool IsNil() const { return pclv == 0; } - - virtual FDNumber DesiredValue() const - { assert(false); } - - virtual list *PlfdnDomain() - { assert(false); return 0; } - - static void SetVarMap(StringToVarMap *pmap) { pmapStrPclv = pmap; } - static StringToVarMap *VarMap() { return pmapStrPclv; } - static StringToVarMap *pmapStrPclv; -#ifndef CL_NO_IO - ostream &PrintOn(ostream &xo) const - { - if (pclv) return pclv->PrintOn(xo); /* return xo << "@" << pclv << endl; */ - return xo << "clvNil"; - } -#endif - - friend bool operator<(ClVariable cl1, ClVariable cl2) - { return cl1.pclv < cl2.pclv; } - - friend bool operator==(ClVariable cl1, ClVariable cl2) - { return cl1.pclv == cl2.pclv; } - - friend bool operator!=(ClVariable cl1, ClVariable cl2) - { return !(cl1 == cl2); } - -}; - -#ifndef CL_NO_IO -inline ostream &operator<<(ostream &xo, const ClVariable &clv) -{ return clv.PrintOn(xo); } -#endif - -#ifdef CL_USE_HASH_MAP_AND_SET -struct hash { - size_t operator()(const ClVariable & v) const - { return size_t((unsigned long)v.get_pclv()/CL_PTR_HASH_DIVISOR); } -}; -#endif - - -#include - -// Compare two double-s approximately, since equality is no good -inline bool ClApprox(double a, double b) -{ - const double epsilon = 1.0e-8; - if (a > b) { - return (a - b) < epsilon; - } else { - return (b - a) < epsilon; - } -} - -// Can remove these if I decide to -// autoconvert from ClVariable-s to double-s -inline bool ClApprox(ClVariable clv, double b) -{ - return ClApprox(clv->Value(),b); -} - -inline bool ClApprox(double a, ClVariable clv) -{ - return ClApprox(a,clv->Value()); -} - -extern ClVariable clvNil; - -#endif diff --git a/libs/cassowary/cassowary/cl_auto_ptr.h b/libs/cassowary/cassowary/cl_auto_ptr.h deleted file mode 100644 index 3c37429676..0000000000 --- a/libs/cassowary/cassowary/cl_auto_ptr.h +++ /dev/null @@ -1,69 +0,0 @@ -// $Id$ -// See http://cseng.aw.com/bookdetail.qry?ISBN=0-201-63371-X&ptype=634 -// auto_ptr from More Effective C++ an earlier appendix (works w/ egcs) - - -#ifndef CL_AUTO_PTR_H -#define CL_AUTO_PTR_H - -#ifdef _MSC_VER -#include -template -void ReinitializeAutoPtr(auto_ptr &apref, T *pt) -{ - auto_ptr ap(pt); - apref = ap; -} -#define cl_auto_ptr auto_ptr -#else -// FIXGJB: This implementation for egcs is buggy -- be careful -// and replace ASAP -template -class cl_auto_ptr { - public: - explicit cl_auto_ptr(T *p = 0): pointee(p) {} - - template - cl_auto_ptr(cl_auto_ptr& rhs): pointee(rhs.release()) {} - - ~cl_auto_ptr() { delete pointee; } - - template - cl_auto_ptr& operator=(cl_auto_ptr& rhs) - { - if (this != &rhs) reset(rhs.release()); - return *this; - } - - T& operator*() const { return *pointee; } - - T* operator->() const { return pointee; } - - T* get() const { return pointee; } - - T* release() - { - T *oldPointee = pointee; - pointee = 0; - return oldPointee; - } - - // protected: - // This is non-standard - void reset(T *p = 0) { delete pointee; pointee = p; } - - private: - T *pointee; -}; - -template -void ReinitializeAutoPtr(cl_auto_ptr &apref, T *pt) -{ - apref.reset(pt); -} - - -#endif - - -#endif diff --git a/libs/cassowary/cassowary/config-inline.h b/libs/cassowary/cassowary/config-inline.h deleted file mode 100644 index 8b13789179..0000000000 --- a/libs/cassowary/cassowary/config-inline.h +++ /dev/null @@ -1 +0,0 @@ - diff --git a/libs/cassowary/cassowary/debug.h b/libs/cassowary/cassowary/debug.h deleted file mode 100644 index aa0499c641..0000000000 --- a/libs/cassowary/cassowary/debug.h +++ /dev/null @@ -1,48 +0,0 @@ -// $Id$ -// -// Cassowary Incremental Constraint Solver -// Original Smalltalk Implementation by Alan Borning -// This C++ Implementation by Greg J. Badros, -// http://www.cs.washington.edu/homes/gjb -// (C) 1998, 1999 Greg J. Badros and Alan Borning -// See ../LICENSE for legal details regarding this software -// -// debug.h - -#ifndef CASSOWARY_DEBUG_H_ -#define CASSOWARY_DEBUG_H_ - -#if defined(HAVE_CONFIG_H) && !defined(CONFIG_H_INCLUDED) && !defined(CONFIG_INLINE_H_INCLUDED) -#include -#define CONFIG_INLINE_H_INCLUDED -#endif - -#include -#include "Cassowary.h" - -#ifdef CL_TRACE -class Tracer { - public: - Tracer(const char *const sz) : sz_(sz) { cerr << "* " << sz; } - ~Tracer() { cerr << "x " << sz_ << " exited." << endl; } - private: - const char *const sz_; -}; - -inline void CtrTracer(const char *const sz, const void *pv) -{ cerr << "@+ " << sz << " ctrnew@ " << pv << endl; } - -inline void DtrTracer(const char *const sz, const void *pv) -{ cerr << "@- " << sz << " dtrnew@ " << pv << endl; } - -#else -class Tracer { - public: - Tracer(const char *const) { } -}; - -inline void CtrTracer(const char *const, const void *) { } -inline void DtrTracer(const char *const, const void *) { } -#endif // CL_TRACE - -#endif diff --git a/libs/cassowary/cassowary/timer.h b/libs/cassowary/cassowary/timer.h deleted file mode 100644 index 6bad1a6fef..0000000000 --- a/libs/cassowary/cassowary/timer.h +++ /dev/null @@ -1,176 +0,0 @@ -/* $Id$ */ -#ifndef _TIMER_H_ -#define _TIMER_H_ - -// Programmer: John P. Russo -// -------------------------- -// John Russo has given permission to any of my students to use his -// "timer" class. -// -// Please give full credit to him any time you wish to use this class. -// Hossein Hakimzadeh 11/5/96 - -/************************** timer.cpp ********************************** - - A simple example that shows how C++ classes can be used to implement - a "Timer" object, which mimics the familiar actions of a stopwatch. - - The code relies heavily on the clock() function defined in the time - library. The clock() function returns the number of "ticks" that have - elapsed since a program starts. The size of a "tick" is compiler - dependent, but for PC compilers is about 1/18 second. - - The problem with the clock function is that it is not convenient to - use for typical timing operations. The timer class, defined below, by - contrast, shows that an object-oriented approach to modules can - provide tools that are natural and easy to use. - -= = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = */ -#include - -class Timer -{ - //==================== public section ================================ - - // The functions and/or data in the public section of a class are - // accessible to anyone who uses the Timer class. - -public: - Timer(); // Constructor, used to declare Timer objects - void Start(); // Starts a timer object - void Stop(); // Stop a timer object - void Reset(); // Reset timer object - int IsRunning(); // Is the timer object running? - double ElapsedTime(); // How much time has been recorded? - double Resolution(); // Shortest measurable amount of time - - //-------------------- private section ------------------------------- - - // The functions and/or data in the private section of a class are NOT - // accessible to those who use the Timer class. They are accessible by - // member functions of the class. This allows access to the data to be - // carefully controlled. - -private: - long StartReading; // Number of ticks when timer object last started. - long ElapsedTicks; // Number of ticks on timer object. - int TimerIsRunning; // 1 if and only if timer object is running. - double TicksPerSecond() // This inline function is used to convert -// {return 18.206481;} // "ticks" (returned by clock() ) to seconds. - {return CLOCKS_PER_SEC;} // "ticks" (returned by clock() ) to seconds. - // In most UNIX systems this is 1000000 -}; - -/**************************** Start ************************************ - - If the declaration "Timer StopWatch;" has been made, the the call, - "StopWatch.Start();" is like push the start button of a real stopwatch. - -- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -*/ -void Timer::Start() -{ - TimerIsRunning = 1; // Stopwatch is now running - StartReading = clock(); // Look at internal clock and remember reading -} - -/**************************** Stop ************************************ - - Looks at the PC's internal clock and computes the number of ticks that - have elapsed since the timer was started. - - Note that if a timer is not reset, it can be used to time several events - and return the elapsed time for the enter set of events. - -- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -*/ -void Timer::Stop() -{ - TimerIsRunning = 0; // Stop timer object. - ElapsedTicks += clock() - StartReading; // Add elapsed time to the -} // previous time. - -/**************************** Reset ************************************ - - Clears a Timer of previous elapsed times, so that a new event can be - timed. - -- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -*/ -void Timer::Reset() -{ - TimerIsRunning = 0; // Start not yet called. - ElapsedTicks = 0; // No time on timer object yet. -} - -/************************** IsRunning ************************************ - - The data member, "TimerIsRunning" is used to keep track of whether a - timer is active, i.e. whether an event is being timed. While we want - those using the timer class to know when a timer is active, we do NOT - want them to directly access the TimerIsRunning variable. We solve this - problem, by making TimerIsRunning private and providing the public - "access function" below. - -- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -*/ -int Timer::IsRunning() -{ - return TimerIsRunning; -} - -/************************* ElapsedTime *********************************** - - This function allows a client to determine the amount of time that has - elapsed on a timer object. Note that there are two possibilities: - - 1) A timer object has been started and stopped. We can detect this - case, because the variable "TimerIsRunning" is false. - - 2) A timer object is "running", i.e. is still in the process of timing - an event. It is not expected that this case will occur as frequently - as case 1). - - In either case, this function converts ticks to seconds. Note that - since the function TicksPerSecond() returns a value of type double, - an implicit type conversion takes place before doing the division - required in either case. - -- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -*/ -double Timer::ElapsedTime() -{ - if ( !TimerIsRunning ) // Normal case - return ElapsedTicks/TicksPerSecond(); - - else - return (ElapsedTicks + clock() - StartReading)/TicksPerSecond(); -} - -/************************** Resolution *********************************** - - Althould we have no way of knowing how accurate the internal clock is, - we can predict its resolution, which is the shortest event that can be - measured by the clock. - -- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -*/ -double Timer::Resolution() -{ - return 1/TicksPerSecond(); // Note 1 is coverted to 1.0 before division -} - -/******************** Timer (constructor) ******************************* - - A "constructor" is a special class member function, one which has the - same name as the class. The "default constructor" is a constructor that - has no parameters. A constructor is called automatically when an - instance of a class is declared. For example, the constructor defined - below is called when the declaration "Timer T;" is executed. - - If the programmer does not write a default constructor, then the - compiler will generate one automatically. However, by writing the - constructor below, we provide automatic initialization of timer objects. - -- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -*/ -Timer::Timer() -{ - TimerIsRunning = 0; // Start not yet called. - ElapsedTicks = 0; // No time on timer object yet. -} - -#endif /* _TIMER_H_ */ diff --git a/libs/libsndfile/src/sndfile.c b/libs/libsndfile/src/sndfile.c index b627c88ffe..47b74cfd7f 100644 --- a/libs/libsndfile/src/sndfile.c +++ b/libs/libsndfile/src/sndfile.c @@ -1087,7 +1087,7 @@ sf_command (SNDFILE *sndfile, int command, void *data, int datasize) broadcast_info_copy (psf->broadcast_info, data) ; broadcast_add_coding_history (psf->broadcast_info, psf->sf.channels, psf->sf.samplerate) ; - if (psf->write_header) + if (psf->auto_header && psf->write_header) psf->write_header (psf, SF_TRUE) ; return SF_TRUE ; @@ -1210,7 +1210,7 @@ sf_seek (SNDFILE *sndfile, sf_count_t offset, int whence) if (psf->error) return PSF_SEEK_ERROR ; -#ifdef ECDL_ORIGINAL# +#ifdef ECDL_ORIGINAL if (seek_from_start < 0 || seek_from_start > psf->sf.frames) { psf->error = SFE_BAD_SEEK ; return PSF_SEEK_ERROR ; diff --git a/tools/osx_packaging/Ardour2.icns b/tools/osx_packaging/Ardour2.icns new file mode 100644 index 0000000000000000000000000000000000000000..0e345fc1201ce4e83a1b899f97c2a4a6aa079140 GIT binary patch literal 53885 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

l`VXumSr+|))ix7IT0 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 U`}|%uGXMBTX6H|E8_t3M4 + + + + IBDocumentLocation + 99 362 356 240 0 0 1280 832 + IBEditorPositions + + 187 + 340 374 240 44 0 0 1280 832 + + IBFramework Version + 349.0 + IBOpenObjects + + 187 + + IBSystem Version + 7F44 + targetFramework + IBCarbonFramework + + diff --git a/tools/osx_packaging/MenuBar.nib/objects.xib b/tools/osx_packaging/MenuBar.nib/objects.xib new file mode 100644 index 0000000000..78f0a0a012 --- /dev/null +++ b/tools/osx_packaging/MenuBar.nib/objects.xib @@ -0,0 +1,73 @@ + + + IBCarbonFramework + + NSApplication + + + + MenuBar + + + ScriptExec + + ScriptExec + _NSAppleMenu + + + + _NSMainMenu + + + + + Window + + Window + + + TRUE + Minimize Window + m + mini + + + TRUE + Minimize All Windows + m + 1572864 + mini + + + TRUE + + + TRUE + Bring All to Front + frnt + + + TRUE + Bring in Front + 1572864 + frnt + + + _NSWindowsMenu + + + + + + + + + + + File's Owner + + MenuBar + + + 206 + diff --git a/tools/osx_packaging/ProgressWindow.nib/classes.nib b/tools/osx_packaging/ProgressWindow.nib/classes.nib new file mode 100644 index 0000000000..ea58db1189 --- /dev/null +++ b/tools/osx_packaging/ProgressWindow.nib/classes.nib @@ -0,0 +1,4 @@ +{ +IBClasses = (); +IBVersion = 1; +} diff --git a/tools/osx_packaging/ProgressWindow.nib/info.nib b/tools/osx_packaging/ProgressWindow.nib/info.nib new file mode 100644 index 0000000000..4e51560026 --- /dev/null +++ b/tools/osx_packaging/ProgressWindow.nib/info.nib @@ -0,0 +1,18 @@ + + + + + IBDocumentLocation + 124 298 356 240 0 0 1280 832 + IBFramework Version + 349.0 + IBOpenObjects + + 180 + + IBSystem Version + 7F44 + targetFramework + IBCarbonFramework + + diff --git a/tools/osx_packaging/ProgressWindow.nib/objects.xib b/tools/osx_packaging/ProgressWindow.nib/objects.xib new file mode 100644 index 0000000000..6eaacc43e9 --- /dev/null +++ b/tools/osx_packaging/ProgressWindow.nib/objects.xib @@ -0,0 +1,53 @@ + + + IBCarbonFramework + + NSApplication + + + + 404 523 457 899 + Caching Fonts... + + 0 0 53 376 + + + 19 17 32 270 + TRUE + 1 + 50 + + + 16 284 34 356 + TRUE + 1 + Cancel + quit + + + + FALSE + FALSE + FALSE + FALSE + 51 + 1 + + + + + + + + + + + + + File's Owner + + Window + + + 186 + diff --git a/tools/osx_packaging/README.rtf b/tools/osx_packaging/README.rtf new file mode 100644 index 0000000000..dd15e66151 --- /dev/null +++ b/tools/osx_packaging/README.rtf @@ -0,0 +1,68 @@ +{\rtf1\mac\ansicpg10000\cocoartf824\cocoasubrtf390 +{\fonttbl\f0\fswiss\fcharset77 Helvetica;} +{\colortbl;\red255\green255\blue255;} +\margl1440\margr1440\vieww9000\viewh8400\viewkind0 +\pard\tx720\tx1440\tx2160\tx2880\tx3600\tx4320\tx5040\tx5760\tx6480\tx7200\tx7920\tx8640\ql\qnatural\pardirnatural + +\f0\fs24 \cf0 This is the Mac OS X version of Ardour (http://ardour.org)\ +\ +You don't need a lot of stuff to get Ardour running on OS X. You will need:\ +\ + * At least OS X 10.4\ +\ + * Apple's X11 which is found on your OS X install CD (or a large download)\ +\ + * JACK (either JackOSX - http://jackosx.com or "regular" JACK.) In\ + general, we recommend JackOSX for new users, specifically version\ + 0.72 or above. It should run on OS X versions 10.3.x and above,\ + including Tiger. Version 0.73 or above must be used for Mac Intel\ + universal binary support.\ +\ +See http://ardour.org/requirements_osx for more information.\ +\ +The universal binary of Ardour should run on OSX versions >= 10.4. A version\ +that also runs on Panther should also be available.\ +Please report any problems to osx-support@ardour.org or on the #ardour \ +IRC channel at irc.freenode.net. And include any output from the \ +console.log as shown in the Applications->Utilities->Console application \ +in the report.\ +\ +IMPORTANT: before starting Ardour, you should configure and start the\ +JACK server. You can either use JackPilot, which comes with the\ +JackOSX package, or you can use the more advanced QJackCtl. A disk\ +image for QJackCtl is available at http://ardour.org/requirements_osx,\ +please read the included README carefully for initial setup\ +instructions.\ +\ +Because ardour does not come with any effect plugins, we are providing\ +installable packages for some of the top LADSPA plugins sets. Please\ +download and install them from http://ardour.org/requirements_osx\ +page.\ +\ +Also see the online documentation at http://ardour.org/manual/ for\ +basic usage of the software.\ +\ +\ +FAQ\ +------------------------\ +\ +Q: When I click on the Ardour icon, the program will not start\ +\ +First, check a few basic issues:\ + 1. Are you running at least OS X 10.4 ?\ + 2. Did you install Apple's X11 application?\ + 3. Did you install a suitable version of JACK ?\ + 4. Did you start JACK running before trying to run Ardour?\ + (Typically this is done using a JACK control app like JackPilot or qjackctl.)\ +\ +If the answer is yes to all of the above\ + 1. Launch "Console", which can be found in the "Applications->Utilities" folder\ + 2. Look at the console.log in the Console app.\ + Press the "clear" button to remove any previous messages.\ + 3. Try to launch Ardour again\ + 4. Cut and paste the entire contents of the Console window\ + (including any data stored in the scrollback) into a new posting\ + in the ardour OS X forum at http://ardour.org/forums .\ + Include details of your OS version and processor type. \ +\ +} \ No newline at end of file diff --git a/tools/osx_packaging/app_build.rb b/tools/osx_packaging/app_build.rb new file mode 100755 index 0000000000..965d87003d --- /dev/null +++ b/tools/osx_packaging/app_build.rb @@ -0,0 +1,22 @@ +#!/usr/bin/ruby + +# Ruby script for pulling together a MacOSX app bundle. + +if File.exist?("lib") then + Dir.foreach("lib") {|x| unless x[0] == 46 then File.delete("lib/"+x) end} +else + Dir.mkdir "lib" +end + +result = `otool -L ../../gtk2_ardour/ardour.bin` +results = result.split("\n") +results.delete_at(0) +results.each do |s| + s = s.split[0] + # exclude frameworks, system libraries, X11 libraries, and libjack. + unless s =~ /System|\/usr\/lib|\/usr\/X11R6|libjack/ then + `cp #{s} lib` + end +end + +`/usr/local/bin/platypus -a 'Ardour2' -t 'Shell' -o 'None' -u 'Paul Davis' -i '/bin/sh' -V '1.0' -s 'ArDr' -I 'org.ardour.Ardour2' -f 'bin' -f 'lib' -f 'Ardour2.icns' -f 'MenuBar.nib' -f 'ProgressWindow.nib' -f 'init' -f 'openDoc' 'script' 'Ardour2.app'` \ No newline at end of file diff --git a/tools/osx_packaging/bin/cache-fonts b/tools/osx_packaging/bin/cache-fonts new file mode 100755 index 0000000000000000000000000000000000000000..36d60e77e72f7d766ee26d7340efc42f01c43a71 GIT binary patch literal 9516 zcmeHNYiJzT6+Zj$W@XE@lB%sz%kpg6g21j67gN@WZB|BZ)+neZ71Sv-cSo}$Y0&P> zW_IN4rlV+NJ0)pMSx5|_II2>N;vXSVp)Uxi50X$Q6!N333H=e%Py$Xviqqm2Q}sKu zcUEI*Wi_Sr*IaaTzq#jq&fSsr&iv~y|NJcx-38(i2kju*mc#rcC(Cn1Ie zx_A!TNa4B%#JSWBy#8ChXd#a1)unk-`2YO+Z%a*xzy&)G5yu*^84CFAQ{;k0n zpQi^;jE)>1KGFJYpaisSKXEzznK=JIk8OPd#CyJTaHeVxmW=ViwUoF{IZ#jT(GRZq zTF~_6P8~S#(3gE_XiQk9qgm#JF*$Hx0NTblba=4-K~PUF|Bnmw08pUMen4NVR~@}P za4e+7H9~C_Omq)^@+jN8z_@o1_aQv^-ok_)Z8kDjz~TJXk56L(dYR{&v%fc&fw?yQ zM0`JpMpS{Q0#OD2_Z4vO+fmDAR&S1F=wKG+8@TH{ms$OV_c(6i-=pOH8pXc;t*-mr zOK*4M2G}w84yE06eCg-&s~2WnV2%u^%25M9-c{ zUG(Q4q!#`8SE)-pd&g2A&7Z+N{5;Xn3U$stomd+6k{QYSupKW?$!{`${!D7w!ySFl zyHywQ{Y~;;ZpS}7hn%!jGCNN>#HV{I~D!A#y(pl(^dZZjdUh~sRVgECT@7t8- zwd^8|X5qhZZtrroKylP3IgCGo!1n{k81sHO0vWGUDYzYpCC2LcE}9L0s6Qoabxs%Q^Wm{Bre1+ZYJ@zmM`wd-1mrTQ1v2IjjxC z=dcHV&3+K}3)TF!W4xCUAL5)l!@Z&hL+fd*yK?3oeHWIz?lSVw;n_S3WZV`PNqvX+j9>sGn_%-VFb;jd=M7^#`d$a(vlK_vLXmKqC_4q?)EAZUBE*;^%;0l=ykz*Cf6O{CkNPfv-z^2}h?pCB6(i zAo0t_=snQiK{r4*i4u5L zpV$w281x6w`#6T)hiAwiz|me%FX)q?&w%(@Y7a;O?FM}obT5g99z+@$1nHqwG#j5_OX;p9IvW>tx&ut_&1kgq%6o+n}Hf+4K zfEsAJaatEuwOlFbNbD=x2^=qSi>CE@dD0fe$5eabOAwqi@U-7X{2KQJqAiihk~OZD zu%J0pHkXf2D1~j!IEKj`=2sHd4Dbo3z}ciwi;yg + +CWD="`(cd \"\`dirname \\\"$0\\\"\`\"; echo $PWD)`" +TOP="`dirname \"$CWD\"`" +ETC=$HOME/Library/"Application Support"/Ardour + +export "DYLD_LIBRARY_PATH=$TOP/lib" +export "PATH=$CWD:$PATH" +export "PANGO_RC_FILE=$ETC/pangorc" +export "FONTCONFIG_PATH=$TOP/etc/fonts" +export "GTK_IM_MODULE_FILE=$ETC/gtk.immodules" +export "GDK_PIXBUF_MODULE_FILE=$ETC/gdk-pixbuf.loaders" +export "GTK_DATA_PREFIX=$TOP" +export "GTK_EXE_PREFIX=$TOP" +export "GS_LIB=$TOP/share/ghostscript/8.51/lib:$TOP/share/ghostscript/fonts" +export LANG=`grep '\b'\`defaults read .GlobalPreferences AppleCollationOrder\`_\ + /usr/share/locale/locale.alias | sed -n 's/.*\(.._..\)\..*/\1/p;1q'` + +export ARDOUR2_UI_RC=ardour2_ui.rc +export ARDOUR_CONFIG_PATH="$TOP/etc" +export ARDOUR_DATA_PATH="$TOP/share" +export ARDOUR_GLADE_PATH="$TOP/share/ardour2/glade" + +export LADSPA_RDF_PATH="$HOME/Library/Audio/Plug-Ins/LADSPA/rdf:/Library/Audio/Plug-Ins/LADSPA/rdf:$TOP/s +hare/ladspa/rdf:/usr/local/share/ladspa/rdf:/usr/share/ladspa/rdf" +export LADSPA_PATH="$HOME/Library/Audio/Plug-Ins/LADSPA:/Library/Audio/Plug-Ins/LADSPA:/usr/local/lib/lad +spa:/usr/lib/ladspa" + +mkdir -p "$ETC" +sed 's|${HOME}|'"$HOME|g" "$TOP/etc/pango/pangorc" > "$ETC/pangorc" +sed 's|${CWD}|'"$TOP|g" "$TOP/etc/pango/pango.modules" > "$ETC/pango.modules" +cp -f "$TOP/etc/pango/pangox.aliases" "$ETC" +sed 's|${CWD}|'"$TOP|g" "$TOP/etc/gtk-2.0/gtk.immodules" > "$ETC/gtk.immodules" +sed 's|${CWD}|'"$TOP|g" "$TOP/etc/gtk-2.0/gdk-pixbuf.loaders" \ + > "$ETC/gdk-pixbuf.loaders" + +exec "$CWD/ardour" "$@" diff --git a/tools/osx_packaging/bin/getdisplay.sh b/tools/osx_packaging/bin/getdisplay.sh new file mode 100755 index 0000000000..a88b930e72 --- /dev/null +++ b/tools/osx_packaging/bin/getdisplay.sh @@ -0,0 +1,9 @@ +#!/bin/sh +# +# Author: Aaron Voisine + +if [ "$DISPLAY"x == "x" ]; then + echo :0 > /tmp/$UID/TemporaryItems/display +else + echo $DISPLAY > /tmp/$UID/TemporaryItems/display +fi diff --git a/tools/osx_packaging/bin/gs b/tools/osx_packaging/bin/gs new file mode 100755 index 0000000000000000000000000000000000000000..9d531e32b6c20e96430e94851b9638bf1c1b8d0f GIT binary patch literal 6527252 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 z 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ɸ`GI}j&KsQhhNBcl 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%0A-q{BG&xW%dWEEa)*!+M&&P{eJx@729JYt2-+TGl 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

J(A8F@^ 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

+-DGJT*!0MPUkW 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

pw|A$W^kaVnZcVNs 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

hT#BuFaI{ccTX8~OTVt;$l&6CYXR5DA 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 z zPjTJ4$h%VZ=G+vFXV6s5%&I#%!2DRt25rcZukHcDV_vDt&^TYs9S=?(g zC2LAqzhAl)?LD$k(C8-0D$Sp)w#V3H*~Nqa#urFN(_~qyA_^5><1J$UAhGc>f37i` z+Ae>dF&pS}uJIv6f_dUP{o0aWKwkbK*f}1)p7rB9n9|LPlxA{gdtDn7#6c9a+lI0& zaE9vO&Y*^U8!1CgNYBl2ubR17cTwS50osns(8Z+W0aH+P^XQR{5rJk zIHBFBl2Y7$BIBhu(~k0it*|Stdn3jbgG0dUgYK#8EiMjs*xKg~fHEx(-i zF8GbQq74s_>Z)x+Uya}1|Mj0!>U7+Ld=Ji-#e9~ynZ(7YK#!z#HXRhyf8i&YtnmSz*;`FDG0?fcfS^ke$DpI!?aDe6; zXtdRta){mhi<*{i2(Vb&aJ*q_3!q17;&s`+MN2-P^LPZs&!VtANfqtT&%Mj8SHw5Rg_k4## zu)5M{IA2G87woeF2Du*fMop>$@d4M$Od$;Mi+>08kJ2O`+Y4RSl_lpIT_?xbh}gSP zXJ6RlOEYO}$k^)}*^QdgQ7qPt8Y>Nx&4TXoyI(bR7&k$+bWPeUeuizd!86<{=>m4t zvHNLRl|v7+x_C!^O4lk7{$gX~A2t0!YRKM*(2*xFjio$+g@Gg66G2B;M&wg4bv#4qR%K?` z=WUVw`Yrv7?BvaEk^MX)DNGz+$v|ho7k@^J?5WY)JvXt)#>lWQyPO`%Y*Y4*%#R96 z`FK>y9|x53b7HY6j7s@%zLcvd#T0`a*1Cnpnx7`B?Ypczay5hxBsMfxs|Yl>P7EY=8T~S9Tu8bn4J)W4Q_U-mrA?*!J*}i~hQ) zY|1@n>nheEW?{b}(8R5b>8T^59LMj>5Lvv-ziQ;F;`-O*vEo4HS`f-J z-M9+$Dq&&2Kdy)fFn{YR3?goz*Zj_%nXvrh{;w5P|EfO&=N@R1dl|jS=^DLq^G<`! z+a=zvr&e_1oh70mLm0C0sLWqAp<-#t72$WY3<)l~B}{yIC~gb|-dj!Qf z;EZkjUz6OHLYfDy^2U7S`PnJ1%KK)I;lv@7Q97?CB@n(gB3NQ|mQG4fnQPLHj)49; z{@Vc?{<_)VTBcB1UAHaqif(gee?E@+m$wFyliyxk-iktWN>;u1;tv30z5&OD>#Evlijx?q)E6=SzY zv2VNB7j@lZ#aQ`gR$3kUA?}E2SGye@D zb6mb~_FPx9b;O?dM9^{#aTXO{0lU99Ddv}7_wu+{>?R!9z3z_9;2F$l216CIlN@whSzD735+n&tZW0u z>Zcz+0b3C%oW_T!KCc`-CN$H#(P5odW>t9h<1vaNMxI6y6LuvYm(W<`E#6AJx#|_K z;k(Jb6n;#7;#pLqf#9jftWUFF0kYPsCwc2Hoz(c|5HIx-rEXDKkLo8kzIq(Qrl{2T zQZ3Q=GA5!zrveae??+8|5{_oE=_w_-G0rXN)xW~FZ-dxCW5W~Eyk^Z2glfI!17Muc zC%onnl#zMy(}w$B>Jj1ohHHg;k(ls?=VFa_5P#Fv#4i;~VX>H$@MYT(`EH0kF)cB> zYS6}7;N3J$2)m@SweE@R#~D<1)NuDp{;Sz{GHMbH`%m+dFN2LR;t5RWj#q%pFtIGx zXXvM?__?0~Kx`l9L*nm2JLat~x`2k%0>A|{Ev6^U`KX$6qHE4uH}*GY0rV0kRz}qG z&8u>|D6$Xgn8qpeF9AnK$+Q79v`NBtZXlL=&F`Ra(NrCO>iD|4XFiV8^Ql!~qUVRQ zr@5B@a(jLNUjF+V)&?#6z*De6gNI8~F2$B)JXbvSHk_V)fex7I-#MNCQ*E;MUxQ_Q z1woMw&cySeK4PKCSLrkkZqC`6o_0P#j_tRoJcL5d5Ki8tMFTniz>Y6EWyYrn<3S<= z6T>ux!A(gz71N&~q`Z=poO_)b*q9!>RZ)kicFy_5-h$QCz{e?xL+|mv)5d}KNx?!Z z^vU`U2MZ<386Oc(n0dN!i(sJyxF|xiK(MfiM(^&LdAhL?2?MziS~~!{*GtW5*fr-Z zUbEfk(Xv-4GuXKFW(In(ZMs3WvpsWKap%rMct)CiCUM=TGfk*fn(nsIhKZ(~+qP3C z=`mv1+uC3#Lj_k) zWxgHiKSd!w<7~1+06j6?-|4M+O6H60-kRaG2b0J%#3XyiQ>$Pl* z*G;E7h|)UfY_MdtK?HXR1F@FOt=I#ljc1TB+EQE#`7vd9;T3cZ(?<4Up2*IJGR02k zn|w%(act}g)gprA^NZ91-jkK8!hPN&G#)Wl9QGJ7ld8h|q7hT#M$FcqX~b+~fW$Xu z`^cM{5l3a(+q9-cHR{Ac&-{Ow=0MX7)h>{)#>h<+i{kbdOW4G;1j-Q*p2!Kf_^I8O zD{?Xz7+eG|c`b8`G;@9R6a2TiA-8e%@S^(Xqp>J;(=3pDM27P$L;Tl;g{MnRG?N1< z*06l3nJc)w`Ck<>VrA*Z+#Hw_KWW-kNW~SImzf--YgnM!6g6BjsfMI-vuv=$2zVD4 zSWX4#Nqt=S{Rn%%!4ks+zW60K?xr7HjHSBfZBi{HRoX;c3Pfaf?7AL%56Zbx<$TFf zC|-XYlZrw}?sDHB7!YE+b2+BRiJ$0m_C^|&6HeK0*0LOt%%S^U0nW-u7?;pgc5ag- zzoDI8^Ysvl;u^}%HC~UKsOJAvoHPxp8{x}uZ-4VNzcv%ZGu82~J1`UO#Tmp1R%_gg zooMJPy7N=jwfnwyRnU;BZs_t7jNqKJLh~x+CFDDST8i5SS@pr!P4carYc~efuff#^ zrmQo4oC-{qBS2hwNxq*d*TFw0pDyFjnpjKM+p&x9;pD`t7^m}i!)Mom+gy8ZL9tu5!bk;y1lDuNA*q%`vFt z*+wOMO?2I>gc!{OBeb-~;`UH2(RY-y_Qr`OS9v4j>P*KSq`DB$vwsx<&@S^v&97z_ z*_Mm*8e-60&g6hS7AEOQFuR#)j&bEb-iZ#Cd-V2sb7haJ{@7$x2V40Gl##ew(?XRH zTZ&=|yaShIx8S1}Er>6b+ExkaeYrk3EM6p8(iVqBkPO9gPl z{_2K(UP2CuvPDq~=H@sB$BX-dpK3UU7pz6m#A3s1-LA;1-@^IY(C!#pWz35oQyWT# zZjbji-VGOcMTFtHfe=f-3q>j{{S4nB`J+~%(wjj4CH}Xxdu8L@V#Uu2gcz8b4ny}A zXh$lCpZZA%kt{Xw6?JtK?XdC+#~xm)82fB^Il4suIjLGOFrd-Xq0Z@0Y8k!!E^5VH z!|xnlZ0cDJt~1~NISj-MKfDbb;H}$8y`-<*gkv4@#x~D9!vuRiZJBw-LMQOow)L-g zwt5>jIGI1bB&geX`fErRn#9Sw%-ay(bb5!kVWCz76#9*zmhx)9;dc)0oe8c^bPKx) zyPCEM7?Z+hR@W`@nm+~!1{;hU#Fu0L+58zIoPcpF3?VQb5QktSs?3G7ybWBrV$y~G z?C!VO-0(K6yR(v7y$!XS{Mtq*V+66r-G>-l-iGBJ5a>`;Qy z^trd8W9(M1_0v>Ix+Tf2@rgWl1$B*z9&6=eJGM3cZf`@oa|5LhHSWVVlJKa70(Yrn zw_bCL!5Z6gZmezQxiN6p7A$O|BJ4i!1cbdyWr>91zo_{w;`%i$Qb2eMXK4IH3+L{` zoFzth)Z|FC1WKDhBH_M6NRbsYpl%VN(-ll+Z8QC=AjG;CLCMycsA1@k{cMC%JhmJG zM`KXI*sDLWBw>{oYe91;GtTMTle=h2$5iBAkkz+IKL!03)GdeQQT9f^c2PK$)pt7% zfhBugjFZOLCO_5~UZ^#BqeXK9t`VHL|H$ zeXMWI36^m!%hkutfw%4?dW6C%FQdD#86syn0$%O2T>q!wEH6RO#X+^0_1Bt2E|&@(FFLo=?!Yv2Bl5l>9dGY zPC%3g;~>7As}T(W=JYF^TpT=757x=o{%1TTi@o;xJJma)?8W+~3g3iC$!1XYs-W0% zZ_RCGgKopaKefD#jCk<3*>CU#HL!<#B?^9vSAVC^7=emwCYQ!vW*2s5&FzEZ&l9zk zsIvGTMBewv767@}QL=7HD)zZK+fj05vDh(-XED_h>bh4;2JsD4Qw#5BobLY5ZNb7( z8iN119daAQ)Vpw{z3v#q)LXlJ(1oMOcb(;%Z{#;WB0n@atrpQ5MLY}kECL5X2VeEu zvyyOWnGQYk=u{cC+d!kYW(Kx)2;(>}#cXc7YSqnHSB)(0><&n}g`^JgN$a|+r@~7& zI>Ktrk=>=++uy8+lvC2UE!OD=YJNmdITd$i)qM?S5dfyDu31)P*tmenpYz~`vXcb7?6wZ$aSXId{9vS-TDvz z@L#Xr+A37#>%U6%yLwXEtN&ZAy{RBw&)-S+S%b=S&ILyaaxQ*dXNjUjqxr6+yII;u z0qAUwS>lLV%argWF(bY$QBV5Tvk|VH?W^knGk6WJo)}J@sEJuh%14l{KO9#?;VN%<`-C{mX7Qw z^X0RJqe0`kDsO|4@6wkaq7)ncxuM$M-P2cLnD}!myZ#d$DPtHpR#E@Kfu#8%(x$B( z4WOgTdW(7jgI2IlrQ;p!*#$7qF!6m2Qw`9>EB{w%y#dd(ejROohmucNG8@gYz1jDJ ziT*molvL_*^I#b{hC`S9#m})2!4%y0-h7AP9H=^F`n2ZvXfm{Lpe?I);3{BSF}2YG zSK<`J0yp`oUJHEIPaUwpEq>~d1#b0IZ&~0rKUJijpIncx5DU!0SBL_0TLHjNjkNH5 z3y-q!{T7zkfHxKkpJU-w7Cv9$1;&e>jDJ{Ec2b?Az%|!+McL1Q6AgpBTZDq4+DLz7 zGfF_NKV0c@-2_5{`_2Xp+}NC&uhJ)%atzi2_%*rT0-Tv$M!;XcoZsx*%vuAx`r_{w zc6Ih?lzU+!>KW@p8=P!Jx(=+$-VBP}(nwR$f*;fODEF~%?(o(RzMzV0m4?=rUN9_v z9P9b+o(n$WHETbqnenV$EfP#1!TT>5RzFskFYE&~b~7Bx1YCby@R9m6NivEg?;*)4 z&28})yDRevsiAwYt~?=SRs9>JdW{@^R^fN5@L^u_S9tmj`zJh^j&-SQ*4*4gh6nQt z8V?VvKM&cu@$mb-Dchw*O2oQ~ktpN8%O`r55}jZgCJz3tFJY!uTmCG$GpWnr!uu}$ zv*w`f>Z&mDu7^&F=({tb@7P|kE_vbz6Xz;vYzJt}uR*}0lod8-b-IO!?7_L&F}ms7 zwnpsOr3S&A?=aAq@Jg8BI#|4fi7%?m0R?sqD2>xL%#N3pN-)=8>EWGQwI;K?gk!Ekd-)$HYKEX`WhI4Jb$siv9_WJn4V~2oK%KNhw@Uk3h2i=PL zs|iWlttuvQ8SlzzLAk!Ypl|FYioVqx0~uRnv&`T!Q2SuB`oMfYAYX1Beh&nkdCzJP z(tvZM9qL@XcIlCM5F+-?d|h}9JieF>zdnXP`$P{YW8gfrlvG=p-Y14R3xBpjA}&g2 zUaEA_)Uo>km3R#-SS1dn#9--VdSlf&dKhoHZ%Na{Z;%$7Q}n8@ys`a-(m@N1F)TFo z_2pyy#S?|d3(xUerjRmmcUh^|{7IFwM0xzhIDzX6%{8Z=l-dM1%w#Di*`APHO!NNxX0 z;_R4HXhz~(Mr?r4Wn#n7K8;poqRTQRw*5i@a?A0e_Gi)J>f3qxmU#G{Q;RasP*3Jm zbxyKV6p;A98_|4V?@HbKJ@`*#mmJzy$y-(tZDbh!?8N_}XD~tx?>kMQ#q#bZk`Z9Q zMJrUiitC{`Tp#krw*hu@V6;3)d>jA*^|B4I9Q`b{w(BVMk-37zxLgi$pXb20p@fGv z)d@DAC3m#-9&2W_t?E~PL9SpRjX22Pbjt@!GHKJWyTtP+og+k@^gj%q4@9c$Bi1m^WL6_dV@ACV)ch*BDua7IW$|_=+ z!lC;oDF=V)`aVym2`R6XFJ4kEsl9o(@f*1DbRh@j&uZiR_kA1gwavh-ykErO?;ANs ze%;>Sat_y@MclO(&p~mEZ+qRlVXt@gH%}DEb58`kM5YRmI>X6bJor2!xq~j%@$|;pp-DSj%4FQlqXZzC`S`AW%THf6J%KIg|Tfs`Zvnk@*Cy)eDp@S zkyc(v%#Yn-K+>rFwsovAHQw$6AE9w6-^P9RMZ^tIVm%$Ss3+hU{e57Ix0=h#y@l`5 zD$|L>7gl%+Kg=t=`%pw7iQ%9d%z@$&4~-^2-`2REzcxeMnlZ$sle%|BBRQSi7=`@B zn}xGv8^7tKROb2~Y}f-?O4IqEQXgZCi!X$UapDtXiVVnhIynIE+O;xeLRC~)gTl~ zd<|P}64%rhM%%YOh19mtu>K_5O^dsrI87?2kP@HyYG$MGX`?fF4evqA4%Lyo$--jV zezH~JrCK56NozdF7&B}Pc{RI^=1qGE$b>opGO8c$k*=?ZtaN7x3E}))XeWddb9DtF zNYy5<$kH!QKC?y9HfsiXK1}ign!g_bBeWiK#T-q7*OJ0{kr#+*^XN{1T-P&A{;gaG zzeNuwjqAecYqhvrEKV;T{A&p{`B`8tDbsd#MWv?gNQ?`0fif4`M@TQ}mi@W7Xch%^ zHjd zo7w>1U8^FQ&9*DjNm(E(dziEl36rDtFZfB8 z>N6n8Z@E6|Dis_i&WqSWKhoMkn%^>OK&p=)mFk<8>Yf3qrX7_kZmAkcmEEdAv{YEl z4^Yz$^jCZ-;E4^(n_&>HR(dzPC2v*O*K_U~w76ot29_WN|%;dna+(Vk}nrfj&dz&viKk z{VE1#y=KrDnhWIE>^HGzfc`kn2p=&QI*dVD&T}i=WA;DiNxq{?dHD%SS2X--kB|>rf;_O|@loMwM$kkQCep1r+ zz;S%iayKV0Kk&D5N;ExI&fkF|joq97W=<9p$ISU%m$Ug6a%RuqC(*DCyRB>JfplyI znb`7O?jFnBLkfqYaH(+XZZen{+IjnP!q{@!gBY=b$C%J2ZbGA(!m2{M-e6Q1TSd&s zFt(aUWoX`*u=QTV8>^y7UC2y2Ct4K+NG7n|P4l6E*yhBcGCaN=D(8qL$PSjS;8z}x zatB7eRo+N{9%f zA`&brtn~;Lorsd(ae~E-Xowdj4qfLp-wJ#27D}_DF8L&H(8to708Iw+pXKSd+`=ys zop*KOxxbvC?=80y6V$E6FXCP&7+y=^BbMGqH1DyM5Go%=d`EN^)UF;^w<1S*EhcIPv^8M%(;Afj3~NXl zYj9do#~KVv*&j3bkaLcr?!EV+Px^z#m5Fg~9A@u;S9tSYhVVe;H{WG)+lcSDfjh!b zn>~&snfIJ$HjG2`K-d*kJaCST{;n3O@b>+)hZk+3n7-^GQzw0Gd4(^zq3FT8+E|E)!Z$*opRC6RkN{q_3P_+1i-*;A zpHqL?Bfg{3L^l0Jk%~hlN72+kQp;0Tb|w9m`N@Y2S>MnjLe}^X2-y!s&8>ca4%q>W zB21i0e0CFT&l|I~fToY8c~P(^T@6%w@(mmaW*#2E%#IL9?{OdvDFEpKa2_Vo5lG)3 z4@j6j(f@b~LVuI_3?o?@U)lUM|()f>ew0seWjwbS}=N8vMKd8f)^Yv>pjl=9$)Nd}l$blcH3!ZVpp&gXqdR zvmnLmmpI60O$yCnqD%3Sf)qP*Dc%#B14ozQ;(`=wEQKy(boa35G0F05&Q5vF)lf{}n(S~G(dxTuj8>CxflGhtc+u)9N@~QbQ&*M2 z?D5(feYawnUF}0KW4vr6r8~sjJ!zP*W0=T0g35?0NLmYxe1fF4#t0=y8stV2NCcyU zq+#0jaRWeL9+pB!z9K{iwmNVd(>0c|{!d5csNa?S1X+S5wk~3^Yv50ukjj5-C1^lY2rG~WQSLm6MQpgy#U(3U9BQQz$u^gv2}#JWVy;tD!0Jb5s(SHm_8PW#YYY+J@aGl&C`Jq@9dP=t=IBPUSO}5^L6i< zlmrIYZuGp)QpvxgU_f)#rfmJ=M5!*6gPr)8O;B7^CVeNTi$}95$>d`>dpi-07&C3-5xxs?RQDT<1*? zR)MRuZGICdGAm|V8%fuf(uQaudYphYA{7Z*Ng@A8v}L!E$@Ozhs9voWro)0tq+!Bhxq z_8e=7D?KZ##s2x@ONd%BxqU7;M_Q}7U?EJr=NULwY+rcaM-<>b*u+&9vp3*EH#Xc# z++EP-VsUl|KKt)n{fb^qbmm5#QW%u9N_|{bUZ=w}Wx?QrC=;~ZUQ(21fAB%&B9~+?{<=s6+wQ$O^@hhHimar_gshtPV-A#$BCkp}@9 zb}`rc&Av9;=bV638zKjlu)7h%;luvoc5nTNaB}AbL+_l<<;|t*y)C=K`pKQ%`pb(s zm}p<_$k2$hs^b;)U$(u_H2b_=lu|vpbk16Njy?h7n3IIeOB|n8_3*T!?oMd1apT(( z**HsV-rX?RuAr}=#67~fO`VVb-c8L~!O^NkbJRn7yVqb|oiEce56JcKz+Bf^uJS~i z3bmcoD#L)zlF9U^-*>|gAs)c@OR}=ncNlK!xd(_de-c~5fHyuW+S#Z-1Ac(fr`vdl zm)$+sJ9|c1{V6Wuc(3^(vWZVByS4uA{p1)NCSJPRG}_{}nk{J8C?Nd(w^mT6oYLwU z-uL$H+M2kAQy1g6`=Rv8s;~T5*?&L#A7yV-kx|7JRDA7JZB9hBf7`N4(?Jc#=jNl- z>%eVQ60?ha3omsXlRQ^nkr4cG1?(>g;qOqeB{G8(hu-bA$VXG+F;#b*w?HTR+{+o> z!dH1|eEhHK@%X8Yk120abYZR)shRO z-uk?GpWru#uxkr?>UPG}Ki5;p=tp<-x&JWx(LGhx-%|(fQSDJrO)YbMaUB?SM7MpT zR;b=I!zXt<(FXUS{f=QYuGDLpZq3|&$MNdeQca>Qa+~V9vdHEkSE#Le&koLlRKNDZ z-G6XIF}3`TXR^nUzMlxXf6G<_ed@dcXDTEVC-;y<{qZ&!4xPxCTt!?Mm%k4-hOJjL z+gQ>>o5npW_PMTaxDt!R!D3~>Ec!$%b4OI>dRmya%asYBz*kY#w$&4VSMZ3M%mnq0 z9DOw}BT?hy#%H|dF9Q#p4cW9=)>DbcI!TW6#56^PfhdF9u!w5!8k{d+g}&XlK#<9g zx(!4^BZJTyfloAGmj@4;Wnkx6*S*Rji6FFg;L3B?-LMctgr8J%xEYXNV?ud7{u?du z^5kmbg}}#XdT<$c5yyuIw=rQb4ge=o>BtjvKHqcXgP3JM#a1#Ml6_u{)og~mY_SF1 z^m$3M`EI(J&;L|64IDy8bknU?X0Dsw2b`{(=zyZ^m1?NEK8Lk@*Z&nzOU1V(|A}Hrly^xIvi{Ki0>= z{%pERh{t4~ogf9KmOC=wR+2jiQEy#45&gKxKtx}TA6|3HUEOQahH{cl~;t7U-us8-r2`X zI05$fWKK+!@fdt?FESMY99xv*FdYSL{mpYm1H`|xU9WRE^Z+-K+MZ5yE1|5Uap+)5 zy!xA*0*^a3A|WWc%hX$QsW$xCrXMj0$cj#A^W{UB$<@WY?0GoR_; zZ?dWP6&i4n?I07F5ei!vacMe{!#&X*Sk{ky5+r~cS*R2j>Yq^&w z(beT+laCwY*nAF4utywBx+M($YY#LY>Na34@HksRB{XHV6|7;0FWVJ@^*Xn=XuENN zZ6J_(txMe;G)Wt0tTXTPX$JEq2c3@GxwAynpLcvzjVQx~J-MAd`(8_l(*8++EaJPX zkadzOJlf{Eb~)g3YGBz>h5skBuSy1s3@{}_dMv2?djQG8E0|PDR@&`S#GCsUC!d*X zCCH?uD2%;KGMry+gDA9x9&57zr~I_{!bn*Ld<6^2kGssH=x2dpg*fEm>2582#5Sh* zXh7E zPpj9wm9L%u`EX5qZNrN}?K&Zh`Vs!`H|{#UDE4qJQ~a0S`r3y%3c`V*RxWneQOrf% z>;D-VMGc6XcI z(rx%{(RV{|Oa2D80tb~Vluy%ieky(cf6+-Ts!4xob9JmxU=AojPVzMkH5--Znp4@~ zc1)-KBQEY}55iHrIyF~wL4CJU-@oW2b_iKmUinKWs%=ZvF5T&3sE8=gtPepYfKs z@IWz4P;B>_SSQOA_C=I4SSlU5x~Nfk4nt`xmbckTzU0|T5TCCZp6t%lAhtrpCY4LwN-hD+@y;N}H5v9R zs6cCYe2xXR%LM%ZF7umN^!+io&yVj^{Qca((s%h3p99(6f;W*bv;xhyIEXj;6Vex! zf-MNx4)R@ChNq_?=?hIIo-krB&b|+ECR}O*Y4I(zI$H#K(nkLp3HjC>gPN0oXSbIe zJwUwVrzDdahpaLBWVJ<1xWQ_A#A>Ruj!?hhiSvxWx|<&Mdx#(OhJ-_Blmb zC#Q{o6xsdDjW|r`%SvU<)M}cYF^w88IzRlbF!7RDCG zOjPkfL_n-2>&NOc-BWd(y97#+fMlu6vuNLCqx^&Zq1@?ks0%~y`uAcRBaVfluM#^Z zLsh&I-Yktv=}(aWx@`BX`-jq~oFmOnp$jQBt$}$*GA2lnc^74wBhxF`2=zMv=#GB` zkYOQ@slQQN&Hul}jsE{o92a5S3bkj>)WnbYIgO^4bIQ@Xzm2O)eKS^*vcQ&H>X+H$ z*oj1wws<9DK+t>Q?M z$^D_ggxa38PIO$n4q#8O>+F7-tsLyDxv^*nxF`?nHu`1d4QxftA9#ubb47u24e&E-Yr3o_FD!VJxhPI~RH>p)I#W;MBtq2#Y)N%V}* ze2+<6zUqRx+Mm|WuN=@pdqb4g?QlA4O9cGYzi@``qD?Bj;_y)Bxmg^1wbxOnV+87g zKO60WA`c+&90X?pLHGA;d@=%-Lm`>bk{KGxbXL8+Uh&FK&&sWJN1m%w6b7gu=^?xBURShl2~TIcHA4$L@CzX^#30rnC>m z+e-IXt4Bv{0~7A5_BRI&!e2#0Bez$IWYC%iwT%aVgWV2d^Vs%8d)e;8-uhU}>0C~+ z(cfvVQ#J>6_n#}rc#F=BZ5+z(;{y~(kA}6s^}~7qpp7hvHsZ)Zh*OIpgT6(pXc0%{ z2YCy=rm8l?ek&)o`ws5n1Un8OYM(#2b0$v86LKx$Z=G4a{f-j*%PC$gXVD`_ zdfJrKjT7_ue**s(^YO3z*E176Wrv~nUqsKJM$hl?be0~?n)mCL%Y77=4Xkd}9)n-I zI*OumkBrj7azLuW_t-KrdaFAJ6qSn{P*^UqusC{){Ht3_Y_+nQ?kuidm58n6==REL zN8ia3SQ$%5iMcZYeWNk|^|fnvA0p>_ONPZZw3cKq;Y%XEw$y8u2nHoCYkQ%zwRS`I zY8U%^>-7j${Fvk$BnaBNN?T(ax|;%%fs5y7rR z`cha}TUl&F_F^OCjiiKTH@ioh9ZZkJ0P1sc&+c=_bb0XGO2HFv1 ztLqx)?9N^d`1o4rn8{_c({|d;2SJWHZN^x-5_-x0QpwiGHVhkpwd^m1p*(s)h@n(S zXuTMYitDG^LUi#E4p)I;%)EFpZUEUO7rjUuo~ufs6Lh7{cUze&5@5yNT&PB z$!@Asm6&9|NO+Ueh3*{KsSrD_7T{EbYEa3;;w zcAUx!k*F5b|nuH7JUVw%ztx0xC{I$@r|N-GbMO>dU$xix_zkW!eN&mMO-BS+po|I*1<# zlT}7!mHdXY`%9Fm9U}fGRN@`XJ!M>;EDg&ZvPFVf=1i-uEVzvC2Ymb05-B&GY*%yA zd@9HqELKHPlFXkzC3p|`x0NOPW+5#D9dyg&hPSq+Z30?DIcmeCApqP^=4he@ypZm5 z)`BjSDhv~T1!19OWwR=fd0u>)b|{Vobu`ToP@n_~IK zkgrNN@8L?=-6)tJX;}TRS@O4w-k2-;YLdl6guG|;IUq@J(Ow5-Y&0=>DD66lO4%j} z%7OeK((V|7`|9>5w%wHPX8iL@A>y`}9Ho=&aOU3~n3DzO+SP!G+`^_gBjhfO_o-MI z1~>n(x@QyHCKc3%GK|`+YYJ-neXk+q{Z`wm!rF#Yn^UHmhKfp!s#pb4unAcMh~R!# z5SPJ11dbUN^#1Z(7xh!kXIuuxf~c==(Xw0;^;5ydQP$e#Hs<_?A4q*FTJ(+0I9SqR5-xj^DRl2o<-CQR?-z z`~S%tll!wAI3i2O*n>J{Mg@m)irMSq=aXvW{PMz50A`JYxt(JlnMcub`CA)jO)9NF zK5S|rmp^w0NP?+0y|NCaM)YQ^##E7IQfoD9rq*g-j*r)gae>Gql#C)D@e8G20KW6- zn~#yc%8)&MQd<^eKk3)*<4)-cpcxAy>+qCEZ0&*FhaTXu&lXS<-T>r8- z;BVD4*mAt>A8hYCZD{Y%!;z^U2y(OoqK9^(lRX*Ff*0as@Iw4X78}|lhAk|*fdvQg zR;DZDqq5`V=gbf2g_A*<937Z~9~F^~A!N#D!mV8g78cl#a>l?!Z+-k^3PyLpofJ5& zWMs+LW$cYG_L}+u42y4PFGlHQL)!1f-^nO0y?WJK-#%d%%gmAOT_Xp@x=s}9nTR$_ zOHy2?xffb^6_*}+8wSs8&kTd&y$v%;X0~UCdmEl?e_?nr{v&6U=HCYwZ+{@CPXj7% zLm8ir!yhDiNflyQd4F|6pSSYhN$oG4RNOn_u=}J^@FnX$4R3#GxIPu|CWyr`re0lv z8e_ln<2X|uh)vB~9|!y+QQ7|42$g6D=;{M#9fl{mPCI7)(~gn9DVJYPW1|8Fx4$x2 zw^u~K{PTrP%omm$m{otLneXdksy!y4`fy}J_kQN6hMx4Vm9QjNLP1l9x4$wx-_-Z@ zvDQ2`Kzuk7plSKyj&3a5K4qB+qH>7T#wHeO+}Wd@4|eQotMITiTuX)e(}Tnp*20%` zZG4X|isY&tHe;q&B({}F3EKBUkU0KFBw#toR2v`ZQ-r1D7S^K^i>N=D+3=s#Oet}; z@GA3FjR+FGYgAQ5Ful^8_63RiSF335oUicX=wqqaeKGz>D@J9$NLeNuG&+dmR|F~3 zIFzLA2~BZhRgl`|+EW!S(Hs@pyNI@z@5VNfo}Ry4M(IkaKkW;RGDR9hotSPbQs`AIqd40?)$8f%#xX38@=I9=YY}$KUpOhFbNL13uSxeeE2dqI{Y-Z z-*&*jz{2Dz?iYg1nL!aQC2zZ>`&TMb(`CF&YV2>4Ge|90X>Ijd7M6vnM%-IO1!R8K zI~1t&U4MBy>wd1-AG#s?T?)&gb9`o$K#mt4$g2E5Dc8MLxqu2&*Sl&k8vFc%2Dr^P zpB%{nL(+WG(%h6!ll@75nh!*2K458X$*1{CL7IKhEqA+!9K25PhlGU{_O7k*J z3sbk{)4Zb~%@a|YCoD}fh%h82-d&L9!YIvmEKO@Z&HD?|yxY>uniHnx=f8in;QL?S zDR^gnI9)?Xi{7Uh%H6(rr|l1_|z${c=W=Ffn5V_lKYcXwtN)ZS2#?ntr~w{<29@r@e`!(s$QT+qDuqu6}d&>*7nZ%KUT2z8T_;S`J~${M&F69lqDGD^f}PMXZ#Ysvk*V-WmJ?-DaizhNI1$G_x%N(*GU$@$_m*`nVlmpE9-jpwlI zbtx^Xqd08g#_yznlosHek4kBQj*&SYZ^pObG3Rsteqzz>m0{_SvD>Q;c{2`)?_6Mf z=k8bhH@Ot8bl4H`jvI{DIL&c^6Vj<=B0>JtH=~gSLi;8pIJ6+k8x98Yic=gd>~Q&k zjQn%pR`NJ_va2gPOVZojV{FkacW9$5 zYTi=g3hLftY67qIDK*T@Hk&J`286*57yR5}4e9wY<`ANh!G&D8nIVsaldmX5$!OmC zQDURjYhED`Vw$!Rr@PU# za7{!NzbY)v2qzsA7K^ffi6F&Vc)CUOW+(Ba-x%aUqeeuY zIYOz38x_HZF=%F!Pu^8-Oerb=ZUR#NM?%S5jemw>ta8rprE+|m6()M-0%S28 zXS-iawDl!+nXbXwV{Tz{6H<_>#LAmFnHOWVc@D(r26^(4p`br`4QYjxaESy$fARUe zGr7}e&U=iQW1;Z)-DwQnq-x+M-(ax?UK}!ZE4%yN8o;hwnND89*LU>(Xm~m)rsYCc z5>h?RW0MQrM4SddqM=;Y^=&29=ETWcSPHt0xzwMMc+669R~miiUf4w$48s;=Yl#$& zR2~dpT>zfWxX3JQD-;_z2ftuh=@p~dKeS7#`j%V(I#@cI+yi=I*hRW5(bi>!fvl65?ew>NLWx73u_x^z;8)XJa3!-DULs;%49pR4q?Se@uE7K&Zp zHa`pk6AhhU>eqyrDj&0QAa~!)REcTW&*f;m&Qh+1bz$O9KR}92UchU2ZLnBRCN?=N zfG}mdRvH-#$|$icy2T-~%!^+ZSg}Bq{2raL^M9NAJZRoaE#}Qx4$!zC1XjFgT?&Z6 zt|W+zL9C>lkw^Vn7lJ2+_x(k1Ef&LzBHhwtizbE0FYT7)Lf3lRKTVx4yr;A)%V|*y zYoWwxR143y@DvN1ms|F~Q!5mSo4nLY3$*!mi632o8(>SXzT$>y3$G?D)L$X1S?3@( zwbs5@QEHHCv#|O1bn>)w0nOs-KL0@$S0^|-8H(_mSkNX8y&nH^O~bm|Kb^y2ysnt0 zs$W#i_ca!hYQ9)SVR!VSFX|3B6vp`b)m?_896G(EJV~X^JV$1c&Lmc+^NRo=OpN%U ztzXI_{Hm+_%f=mgZs8a4leV9}A(* zV~3G%ynv@ufZ0-^%V^q>3ryoiDHGFRy!9ud*&N#tgRaaK;2;`bmwT1@Mb|WoG>Ug=Z z@Nx_9vG58D@3rts3-7b=DhnU7u(n@<)LRzbZs8(O;-{pY4N|2R?zC{3h4)yv+`@Ym zPBcNoerlh^Uup4GjvOqkIUPP};fWS*weXb|o^Ro6EWF6V*IW303*ThnNfs`*@U0d; z-@@v;$m4cujD;mbu`;mmEtY1jh2>W)FidOwtk>IP*K7Q+$<+fn*rLOY2AP2ci}f*y zkBZxPdNJod(0*N%XkrkhXadnx7$h`~je4A~OLQvpCSmdXZ;Z0==Z}iA;hH2bt@`c| zcMW6}g(TOg5CaUzbJK7g{TwEqcEcghY756-Y(J?TJ5Np^wVOiCg6(leTA27jl-ZbS z{~)UJjWo0C-=dMxbhIK^ViOd$UD1@aELdXN1uVRxX>C!k#3s7B`MIgDHCSS!9ZU6S zR%{GR){xV1=}LmhI1N{lfP+~!U&@Hl=F4Dmg>MB1lPi6jFN4V=eXAUw>%PsG!Q?96 z01TXGdXpfWaN#=-9d0<9Jc0D;FOg80JitY=rMo z8Cr$+cL%J>xHx-QM|YIcXD4aM!_p?*lKq}e1)?M~H68||g`}&yPJ1(598U914#-Yo zmn=*~9F@w&I*+V8PrN4KxvvwI4%YYdM+Yhd3x;>xXmlOzk+NPlD2Z0etr?qOX%n3nA+57;1SYb3TzBa=?+ENVdFLk&jyt$jJC(mm;G#*p}J_ zQ#~zQ&hg(46DNKf#)NDjva-2?j)0UzkBG#Yx-Kivty+Q&CO~ojf4iok z+-v?nL#s4!6_R8}nj~vevO}gpYisF!lqbTPEA^T4|5xBjw-Qr-Ayt6Px-?8I{#GOi zC4Rpw;_!5j5HniqF|YX*RZP@WttQ<1!uFXXxlGG{>%h&|dPU(?6B#50#u)aIDsTJ< z$e`~(C>54df#H9H9+dR%t)Dzeh`4CV|6}ca;H<2w{r_{A0R|a8qfLr7>ZEvsh6-eKwSsX9PM_^i(Mlt>tf9q`gL@MGl!YS$49Uju%ewOj)m4pNTdSJ{G6yu*O3~(* z(X;b5=#K;C3EmL4Y%%_xp2M)!S4H{3)vaRqF}6@E&_vUBWEt5i(H{z5?zc*cPu*kY zN?cFv9U2{+uUVRKT8DY%{!Ff(?n7d5C1zmZk-BGBka_akP81a)#UjKUb%P2jlB54q z75&KMe3XY2)xYq4Hd<8&dJEVx+_WC-;j=Nv8;<{l+}C+HKvJ6KDrBC0Y;g`Y7gVAx zDXY6f-MZz;Nd1ATEV8z;V?VdfAD>t-6QfWe@&{BCCw^h3Kl41ru>)u^2|gtP6D37G z?-YrpC&Hk_eO7cW01#+QnRHPty^kWs9RnvB!R3R7oZCXG`@kj)+%bv%3JHs6F&bPI zFZbK5E{zTP$7(_K4xs|PGQ7#~I5lLl)A5O`W^(T31!|j6h%F4evLA%RoLqa>@bDj& z9h*p0AgElSauG~gbDaDpa?nhXQC|#7%G1s$yo+iK<5H-g@G&;31q7uGZ!skeuawP? z*B_%u+;v?qYLqlKvGdTY-!8^*I)%aC$}1>PnwW)L`s41DL^8UvSK@ zyF_J&sf^@-=i>I`%A@%(*Xl=^UrBthra^_ti}YK03O}L5$y*<9kb(k{6!XOdAoE~H#78sdRCPJbT zjD*UAu^wbF7CbpoM-CLSHB=^1q118`*PK{*oD&O=b7J9fPAojmiG{~GvG6!279QtB z!lM|9MqkREh!1}snJuzFqFEPd$;CYmpNa_x9hwx!xw5&&(fk=xoLFU}W`}AJ_Yylf z!`5$!9g(4#ywz3|qi&~6brOyLb;-k?DaJgL#KfgM6Q2W<|Lm5hR;>jyLAek zeBE&CgfzSDuj2RF8DY1nYJO&@wo8!S4&O7q6EQcJJF&jaZ!x`-^8lOfaH=}p(09UV zdU>RS;r6!^*N~Q*S9?usy!y3-Q}o@AreVF#(4d{*{&6eej?&g(R*L_U=|gz6((S-h z`zn}DVMiOV`?Ufmk1S9U7r6dpEyQ-eQT1t3bF;BaJL16kA`9-HJhE*6k*Kk^C@cK5 z>Rb}$(jkB4f%8}v+&?p}j9CZK-$-TT$ttX>V^I)eB8a!|Wx>4-9$iHg68oUQeXc-T zHT|T+ji-CIce7sjf#4Rkne1eJ2~1gMNVxa$&Jk68IjZV|D0BX2RW+)5;q%^SM^<&< zuyv!Y_kRqP$i`Lm=aE&diK?3WKdwr0rmO1ZkyQmzRgZ$)|4|1m8U^I_v5|w+MLkZ` zs*GwnS#B_rVA;hUVpWQ%ra#@o0GfC=N{rKnvwo)+NK!FIaR14x9Pt{lmAZ5chhmI+1rto=pg+t?KwzSk6 zd6*+^3!nGt=pxE9pb0ks$W!OAQnmKAP*jWYqW2=LGI$zbDO|PULmS|vWR_V;Wbac+ zCizUT(l{QBXc9M(Sl~Sl!^L;p-;C3Q4Q#-4fZO&IV_|%aQ9vl4{!&DE*&kZf5=cZ{ zZ^0kFNfE&^K$Ref$F_Skz{XMPi1XUnqo88{$!7s6$z7Jm87E%K@@t35{&b?G%x*Usg0QP+-BZifh+w>e^}BmS&I zgnC|-yR(3{TP?R(ULAp~UG57;=B|o!6Ias+xh}mt%K512#Keyc!T*t0k&!YSzC+3i zJ6-6_ogU66$-$*Jxqxl$mb%1FE56$k{-a5!f<)i-x7ChLqVETm!4{l~fVHsu52m8` zzRIvfYlE#2BM1@EPY3qUuAM|j%SG<+ubA=mW&N%CsDF<5nFAUa+eDr_MFPoo2E4DW zLh~gN9s6ToZ4s%J0XP?qkj%nx0m)qvd3dPG!EI zk)KSrZ}oOC^BO;*Usw9yI6g~D&DFY^O*=SAnE7`Pr%dUJeUNFebSD*f7||eyAS-*-~zu=Ctv_T$+51H(1N!weTGxb1IVG4hhsJJGz`dLrvR}#k^a(ymM6wa zRqnVCgB6L-mHsylv|0bfnTxj(msI+3C(B}cxqKs&{LFt*J2rt>@S(u64y?2eFj?nT zMg;)UFNx z^X3+w3A(J5;5JfFewD{sSH1h4`t7YM)3MXCb(T+Fu>JOpdd{xU^D3Q+p)n6se=7a3 z7c5tyWfc?(vORjvw&=HQG%FZSX(>ji<1`PPo!0Ow=?ow&Ka**%Ow=wB`ciFu^u~Fk z7LQ#^6++(R5th z-(Cp`irbi8hREzRW5)`9r;ugDW9UT;DfPRo78bjK_oouI*4p)3{Z1io_n*8@gT^p8 zxwrP=>&JM3QZS`zp8+N?p|Z#u&H>~>~dD z&VE1j6Q%v3dmX=@`iU~)c97q}{0YA6>Jw~F4|~1AjAWLWX_B{EUzS_yRQm^bzE8{F zf$_V;%*&%vOOK(i0oEa;)f&Lp@AsDN6-Dgm&5goA*s?XuS3fHv^V$da5NzI}VYQ~P zUaky-Hhtmz8+J4-Bi?*&k(WZk>*@$Z$5< zu;?(HT5_53ax2+hE^=-+;%|}8rNqXPHP&vrTApm1!M;fSu(7EzNP^N9{V)F|UB_GS zcZGp%sU6>O0zjV7NYrm5u-{5nJ*`AyKvEO{7 ztC}G5tAEDdVfH4vO!H+sNaN5#2)NV@&V6TLlx6vot$p@6kPG(OKv-(}Rn(HyY$ch2 zSG{)0cdDsMKt>%3+SdYw2KJ73al+8v6NA}hsNTGt_x|=B{1%3SRpOYc!}w?B$Dag3 zkqXnV259=*#oP6-zkMKj>TBPpC(xY#B+jXS-q5tih!GLJVOp2zDb2i6+H|15J)yOf zfBo&H`KPk{lU5G>!;|KjEVtf{-MMkSgnVU^wEcEuLeq2MLrTG4!KlgGLQUw_mlNoP zw+yG4M<3l0?%;D~nT!Eugzx2Z%gq>iw$<|l%bMj_Rydbem^h}->?v~ZVP$76oz!n@ zm>}t2S`kCHbVB~ADtgLnFO9E6pbNvF)N+w*TC z*pFXrJ#x2t*h%}#teJ;!bFxa^!2c3nYo2c$n{iirVq%fm(<)^(%cm2$0W=w+pyBcO za(&v=tOs^_g9mm{y^Ju-^DmOVi`pLBF+6KeDXK8XBIfPBoBGqNt{q#GVU z-KUA%c+AI!_{4{kpj%({4^e~a6o4Sk7c5owm@Ln-+{&YW5`N@y8~|I>Wd}+9bl5>3 z3?GPJ7v}DIKZ|ppzeR>5+2O`=r%-fmv7uGCuKxA6XgKsQw_jWa&HUmggUqcLv6p2& zXw@|HrQE1@!X`48G$VSDuCTiFwTr~QrD~l&hg2npg*(Iwoemqh&N|Hb1*LGmu4Z{c z+HrdUE32B;oDUJG@eALqsNft?RPCwgXXB#B)A&_UCsLlY!`k#c4LIHdT0;w@Ep4d7 z1o$%bm|=<7$%>`&>F|e?;melQ)RDJ#oNpOL?=la>&C0X~PR|~=m;gC{>3yY?wQ1;d zZpJkn^mZX@b2gx5z-tw~Xh4f;#oLjmmVIYPNXD^gY~`y%|JYK|PY-_cNb^D5r6QLH z=PwDCi4Ns+{pVT?Je;AyGMT)SF=lJ)lITSeH-AzU>LAFm1%2A3;asYY z=2?YI&W%d-{WiYm8yoTED}2$skfnCx4-fR%T;SHJL{zQDP_n;Sgn-I@oNOCSYwe@| zrTPFDTowR2x8Mspr8CI^&+yuTe0{s-p^PL!rD8zm9{xA-m@`v5`Mc+*`W}5-Ncnv2 zz#u;0^&M^zW3FyG#xXC=UC8yHz?^vB4JQZ&A)^NVY$?x9>%q8q-Zp}l2;`m{b`;Ss z>@S-AV&obi%LRfp1FIZYKZ(bKR0rJU0tnU}$~4cO#5rOPrQ`L+>-?3PoiLzN0yiz8 zS|Q$MaOK3@493h~Y24fL*!+84o+|Rt>MsF+KPyZhv-n0HA99cXCOCjR+@~>*8$2W5 zpczhzo#aQHhCg21@VdYl4d^;*-qRcar&x10EX|`ycWlkU9*e|ETO^LMG+0lkPaJ*> zBZ$G=@$Me_dwKk!L+F`@m%2gZ`aZKgGw^)0u8?IJjE6zm?}n=|R8fwI7Ga!a{st2e zh4jUrF%3%<4cFF}-&Es_qo4HHYd4fnenrO^Y@5+JE63zr=7mzDr{leJxy+`y!2RE3 zWREDaz|Q%<%V{tQKz3=(mBIYed;c^#DDPBh-M&61(=)a=S8_OAF@}g3DJId$!EA1l zj7{zkK$)R2Upvkli(~x5P0zb)C7IWf*Z=uQx+1}dHtq9LUhjclTO$}a&>=O#krjSq zxv;JQ+kJb0Ih_=RwP9_vVYUeZ;c83R(4MCE`gk;?Q++r(V>l z8RcHKl;=#h&ZnoPmL>t=aC+jHRNE2t&@$F`s)kg1R^VAZwOOTjeW}@9dZ5bWi(cm; zJ*KBHI%b;Eb{+YnUHs?`)F$8=T8Wdt_&%>X@HX$HePh*TDL(vM>!VWHpEK)<+e)>c z3$ybLlG;uIi|MT(Y%1sCLE8_NJzZ|i_=|K@BAdnU6sHC%RKk@*gLCr3I0)uH8>88x zzsbub=KBp(ykic0Vr0YLRx^g{l619ljDl$7aq218Cuu1P{c|VsPp^sl_Z*q%A7_c~ zvVJ94;C5pbh=~v19bT$~(v!qR|MX$*L}kk~TKx0Vlf3hMd&S}e^oXjCq$ehLOl7}J zm(0&*;hP@^M5cB$Us{>99f??ysucbw#Q4v)Xwa0ik(^AvZ%!Ky|BW!mII~+H_T_Z3F1>EnP+SVxhuu zSvN%jbWxo;0oNI&1x3Jn53hdy0K>P>Mz%O>zKLhKE#?eaN1rcU1 zgxjG-sWH%_Ij~TG6cMJI8J{jrt*=h*{%?sge2L2Yvz7FevPbJiLsdT90Ii}AB_+t( z(7Kpn(DK=L$3rWi!)hy3Hd_1Uuz`&k6VJU|X)hD-ETk?3rK5n8)y|zLMdzAMI*tOC zl}_}nEgO*V3&j<87QcMgUbK|Y$`8Z*QqJj-{y&&cF;-CHX3nfqH-#YS$xFl(oFm(t zi@-gwH3s~^c4OUkL-=EpBPAx+6d?@fX^Li!!vX}0%et|twv6zbS@{)06*g4X&ccxD zkEE!hGH>M&|0uI{I=Zj#FxL=>8t3;V@Kca3pR%B1R+5K`j#;AHGOZ;vn(5J{meOEW zi5SV^w_{^4Ox#s#-ubtzG98)ZLHC5YfKB@w?mqAwdB^x;X=T6w5~yzm&{L};fW8m` zRN7JihwVdTzsB9%RbXzs^gwSYrmj6lj8y6jFoPY^%Mcf8m~ai_Lry&{-skZ z0{WZYmD6Q8bfY_?I>}P>p|4@MiF@#^>bvr4fS zOx-i9ykx0#O(HhHv50_mOV>a~skV6l8$6)CNq9-`IRNn;(o!i=4S7)UoV0zAY9D7d zsAgs1_L+0-b~AWkjV$w+o;=hKEcE7b8RwbQ=J}N*ER??`oOf)#_(b={4Yxz7%`+z~ z^k$vN4|39>z8P;%_RXkF`WGXD;Gn4jML)1;`GEj!vqZW8XL{UH$#iX?!dWMhp_0FN zoMZKt=clm>s-ShcelI}EX2Mpm0siRlfI3U^^?dLH;}QWb4X{X=UqK(gVygh}0(pXO zKKyy9G1E0}(s`wK=v)7cQ=G!WHkJO$om2|d&FNpNC;bZ_16vU`(fmYcTiWA#WSE=u ze#W!@5C@SbN;%{j55Gk@V_FBkU#QKm-=h78D+XnCju7(Qj1+va1@<^}yDM6zUkLIlMPKqwW5o)>lkGS*neljXph=YLx=-Fi+K}WFcn}f|%g*T_dpIzzAsU&uuhlSA&wQ$hu-J+tcFH0;< z&BDounRA(s=j)Hz9k#wKA?a&}-PC-UpiA<-lcQn>^FC*WC?R1^>B7v-rx063-h1xZ z#SnOr`aLsL`n5BdIHTpB8T&=NN?e2)Zk25)>JRlkTVg(q?-Tuu{2C!{zTZ?4H0S)w zDx4cB9RX0^8U8#dS=Or_o?FUtKV}7CGqe{!mh4pBu(PL0m(_Gg4S@&S&p$Nzie=kG zBk1%?+$xA&ob~RpfsXVap~tqFRgGUj0QF}r!VymGV5)5wV0$lcfBS~ABmL4oq_UFK zwJxYb-mcdRrys%@uq`K}gE<>IFo4ccpGSRIKhCJ|W;MFqxIt)oo0`_GA{s)JZsv9Y zbLTt6jIqn12UDA89HSIpDfm9i>E&j<;8tHJmAUJ9fh>}*Bwq|J9EI$BaN6O8nHx{x z*s7^Kz|Qi5i4(;wE|^#i$W_`|L#PvI>NwIgFOT7Gg_>qiB|c+hSXOd}5#Bb*(ar*h zVWc?K`t;l4RO{G7 zMJcX#n@NEoUzgg{pwTJ27-h)8g_#+rB*V49pg{n2c@fasbz7j#D`-=T`YGOEZ?0_0 zjE+&>AZuQDE#;;?W?uER&Arc7XxtcHO1jJOarI6+VBvr&jk{?k(00V#zMql`4Got> z3W4O!KP5bYa?w_EjdIJmT+U0c3s%`N0kIGo)*P4;H0^{d>tGto>cQOarF)Uf`bzJ->Xe$Kc}SXkG-RWEl@Y27j%LNtBL za#eWk8wKAe&kiaa9ItDt(P=F@Tek~lo0RGDns%EqLnWW@(UkFsUZV@JtmOe$TDUS= zzrJ|lY;K!XmCDWmTO)uwz6iKf+gsfu3699@Gb19dy}o(q(Q8+{5Sv3Z#OMz`^YmFX5PZgFH|Uz@>T<2 zzw;DqzHNH^c1=7*|LKXQ)|sLjrdE%p)``5}9-4`D!6 zf2QUk{Tv)Q*O+5fbl>Kf6`QGLup)I2*E%?oEm>7GzmStfxLT_(;ZlYsn0B6A*p!%i z6*E?=Ps4WjTF)rr1Ex~9>uOuCA_Z=$uWWg!!sAl<_C5oW&G{PEZSlq24c{>OMJqrO z>o7?RmDKB}NnqXA9fcLO+Zs;<+){71oOqCDmgUJjQth&xC^g1Wvb`h9Hp5jv0gn!; z>~F+hUcjoOV=nAqE9zGK5!c+QO3@XSVCGFd}4 zj^<%zCC0x9CmQiD<4N!TI<-Y9^*yo>J(Cn_#gFrbGPt{AM+d%lG+rcd-kS&KFEsW# zW+X)u9>^-g^Nr`MjYsa=caRl2B*Bf_tt2Gz*+#;}l|(tK-PSaBT2C;2D&D#oN{tao z|KO6Wn8u^&N)j5Uj`EtehT{;NIP%jyp8QBpr`7|%&cB|e*B|G(2wQG4hg(zv`jEFi zsAD3TGLN)`CjxPl^k=$wV3ptQHajVAIiJEG!`Sjk9p4d~GyeNkKE}JcDY>t{Bihxm zQsa9BfmfGtf&AF$Mo1Jg0C9%4&m1dH8fDjyb@JDm2aP$Ay0o%te2l4LN7m zNRxK@L(xwWbDC^F&1Z{My5z9~1M-~f^4zLCEvf|3UPBnrtOP11X<%pUg5|Sg2(H_H zn|KP@+oV22`GGb=AOD#W9A(2N^sm4DPLqzwf~ePC0j+bl%g=21EIU=qZLE(Lp+Wl` z=R>jr0$wI7Gk3)9s?ia<{z;%%Wg0b*=8oin0cwZW`z=<#V<^L`R%`Z11mR}JEyuv- zB9A}p(IbZ!{s)4k>W1Jx>5OEewQq%3HK-lOTPA%lndwJYb+ERfg1~o$3gB8ehjf=W z51i_6l8uPhG?+>6OJc##cx*O@0}akH5tn2oKV@SD}-;GI5Cq z7`Q~HZ!B9@0wBPS2X66R_{~7FUk6%kk1gK!h7u6E_DN+Wb4xSfG(tSh-tEmV&mZqq zGsn>qS4`d&oNr1*qaS$8T}E*glZQaD+>FWcA1s-56>>c2`PQbFh~3D(_YkN#1{Em# z01-e*GyYAHE0zcoW1<7>NRpn)1k=QL)L&Fl!yThXzH&Mf8{MG|jF!9~l$uT4tqQk67yb_G0l6WN?l$uNssQpZ42vL~4>&~aQy0Y&N}=8G(*Wr@)p}4{@Z4P|(l6YUNJZ!c zb`xkm-cXN`<0JOhnLjOH!k2e=fpqx{(%<08#7$%ZK(0)HZXFh=`s`Y8cNzOPNW%tR ze1-J)GwOcUG>9=dxW+0cIvwZmB?Rx3!LpjXtgLmr;4-aL4Ct%X0QxG*s~~&zv$SS< zzJ7DtoTw0o!qxj!D(JT>76w-5)y$wEs1k6&@;~rIuLX6X82 zVe)c|MNrrcc3-GG*)0@SmHpX0(NmE5?E7V@a~tnL=b)B}&PF{4^9_mD=()?*psq!F z?p~wx?ge_z&N#$#wnNX~nE6@k2Rg6Nv%mXuJO?-NEVv{m`dw;49Nq6${laEf5-y#c zJM3Uu=-jywXSm-y#tRqKLVnyOE*`5O)8x;c$0Em6izf0P4LXtT(y`^#Dkxn~wNcTN zZZAa_XcYy>Z#S)t#bm;=Ts4cfsNmnnlwC!|AO3oEwC3z%X#GqY znz9Um&>#Wj_X(}3)vm9WNMGNz5c}_Jjw~!J9i~Ha8tm)}70b4ON!JEyk`toVBC0#G zTY8YHBTsq38ZzTs^2qPKuC+YUdmSX?FN*lxaeH6HAz2}aS2g?(LkDTmpa z>plhS*-~}^1bHQcLzrB{8^UZbVLJ}VB2I9Q9r?x8o>7uyypKX{ezz#l>n`WFpEW#X zw+c|sfjSot@PHeq;3hq|vG48??Ae|Cc1`ZeKkdsu?Z`h3L{DDVTw3T)KZDDk|HJtQ zFSXf8!^6YG7R;p|2g%;cEiZHC_x-oSQD1%;DH;o_ z+(qkOgdgY5(;w!LhVbFLjONQ+f*&oHsgoKFe+jgjz>&>O?-tyABC|| zL8Zgc0r3^E^5jTCAA0d;k$t~%p47(PPy{YJ~H)k4D>NcOBC z^D`9?TZC*y|D38{hLE$yhB%D|oKk5m7W|Q9#W0D~P@ra?(OdQ=wQX}voJJG<$bUik z#zzE`-(_fHik|fi7(kxZPx(9$X0LFi@lPNwXFx>cTJCp=C~KQ48z&1YcRT$u!rX^3 z$igXe`x2dkJ7&o-7}ao{_Uue^S+a48qqn-OSZ->`S(2`$30P1!>*~~!6M04Jvl!*n zczrSCv~Cx#H|8H??pkQbadzKX#a*zTVxP`%ZNBrEM5v?Y;Ql5X#}=9n?r-K<{B4O0 zW3o23jK`1u9ZoV>p=6HGjwOw~D```8$EX zrToSF<80Ff^H*wM?uXAdNhq~R*=^CgiE1-_$Hb%m1rQMaoenq}s_Qh2WWV<+Q%Ava zZuv+|9k8_F@OR`4GRY!Da~FV44_{vGrPpXiJTWaUU^m0p3pcp3-ewbVlp1Qwyq|fe ziTE({>Z)@Ri7I}+a5ie!_azcHyeE;EIfeL8{QSqHL}CgoNk2RI`6ln@^Yb2l9^{AE z;6hd~A9`@ao_RKvc{$biIhF^xI&j+Y$vYH(to=b|G>vyfjU(?ciizf`MB-|G{*j-v z`8k=N1V7KeBaxVh+M9Usw2|3X=5@ZlnWk@Y?}n!Plb~jpAes8(ciDp2rBdOBJo`#* z8ilcW$46<=xRu?NF%FjL9p!f!^V*+Ewfz+~gG@qU1j8mE)%+gL zV%2o$W6bnqT=3O=c`JNdTv!kN*+bMTcH5sF;)#yZmT}2k3DJ5}?Vl03w`CqLbK^7a z*hC`!xsvDj=OE8NKTfz2ucd1xS@kE=)56lngCDWxnS3w^^+6A=XPE&yx)MN3vJO5x zQrSaqiR0c!12nv3czF1*VWtcl3U#wnRVF*FMf-q%)8K-NS6y32t>joLaoFztOG##b z(q)1JM$2Am(^%p689J9AChui193lR$_=Al~G2(v;SrP6BwECBnVqc<%K(A;a=$}C4 z=@{2jo{mE&o$0Oe0*yqdkcT!+-t!o+WQLASwLkGPHMC`}qNkcG?|diDQ%~g^KV7Gz zusSV~_;-H3!B6lH%#E`WiFFfMT+ZbC8HvPV@?T0?<}MLa%I{tvWOeH$nkr!#*X=bZ z5~T(ZgZx#};CZeS(>r7)qYg+@R^{3KUq9=5gd5uK8N=$)++&;vL2n!S>Ek@RpPbtC zl}fJas^}0VPFy&+ki34kmEH8Ux0{g^sq?IcIh=@@=bY5$IpsWRoPE3ejKGGYy9p)P zYk*Sfv`&*c%wwTUW)!A*VWwLJ5~=K2EY5z{wdzp1Dv8}C`6aHzQkA7zylnPYQKj}u zh~thw04u^?$+HMjfh`qy3LQjA?3*~@89|2^>4Lb!XRrNXd5UI$!)dZNLTQ&|lT6gg?u&*?P_|uQ~xbZ~H!6 z3dx;fmd!-5)TXIu*M=~@9+PUn3*HMU{uvCL{Im^wb^ZJeHl&|1a5eqBmmdaX1&~l} z2p2)Tb9D}hvvj`7Z^FQPcvecccsPjaUQXWr?7j%Z0$&Q6S|B073|r`h->s2k!_LAj z8elP-#KkSp`wQG~@~eMoNeZQ6J%>?Wr?D%*Q%(`BQ2pF6epl~aS6C765xXzz0sC{3uV zjHA-jri(`*Xydb!2z#%R?ept<`uR2aT zyoOc*xPV6C5SYRcUf6ngSM=Em2s1(3m;?vHy#r(XE{7L$_P}^V>`&JKs^lVQ=^S$55L0;bo>>yPXuNgsRuNA=!`BI6;xK3si0dS!soTPMx!}KEB-#_KwhHq zUMQ^in&S3B^qv>B@Im3*TAF#@1a9XW-8puOr!?Rl0x;~vjO`%oU$MvWhkp=D3nXcK zkJK0xoQ=2tR9x1GMMjXO^T5%&mzB!Hw=KHT(>vVrXk8le(mON5Na-(7G&77T>i1tD zuPIt!YY}T%ZzX|XA+v{-oSxBXTvc6=b(>jXu88%Zk60P#3BGD?WuzC&cuW@tp zbCOU9kX65n*rIL!q&KIjfb&J*y3JywDfsQ5fY8wC5QYh|pdGJTiT<+b`War=AySIP z!SJxPsdZOdsYv*i^eUi8Dvd-|B^hLWqu-);-_wLMAXA%8@=a?YmAC=LHLxLS6JO8d z5D@L*xl~D~b^lK+>w0i9Zg?tSwY@e$7SEHWTBwWiD)C@Hu$Gq`URheIyD)R10SYJ%BVe5;@Nh8;n!TkDy-i`TP zYub=hn}UZ1_r6^_#Yn~R;SAgSNPcN#`4$iB9g4c{XC=1StNQKa7kGq~F6athS#lIz z;WdAt`_S~-RyAPK8#DTBQ01n$XVO@B$Dc{Cg^iH3DiWA{Q4K37>=nX8TpIAr>en$7 z#6pgEo$_f^E>BXXLWw587EC!us0FP0eUOB(h>C@Sd30%8BI@LB^n5)6 z@RvK$$87Tk-7)UVse5*W{~?NKkbGItPY1>%*)dGL z67ZQ>Nx+h^4kiUvOUv3$^ptO=L5SXe#e2g zEy=T_Sfo0e8$p&#yg2(nAUGT1WWLZKHL#gfZT5v-oeC*gh4kT#g>qKtpb9xDYLm63 zWEIkfHx?SOLi<#xxFsd4kUqSz&|WL_j0zREq+}J+hc_15Wrg;rP;pC2Rv~?OW1$^Z zXr~IrgMcL2rQ~saez!i1dy-inV-Q2i)Lk$BW}qmRnAoSRW2knCp;64Zi_TjhoL7j9T)J^*!f1j+D`48%f zeRvxjjnRTld!1L4=m(-se`b|G-);mQTMfm|DwRTFlpYtAN;EifI*&J&d)?P4^Nkf` z_IB3#7m4?-2@8p-gV3A(tl}Zsa8a%z-g=V z^GOF36PRIa%2km~txnZXx)Y;an|4r;-@K_>$1WnN1aE%Dw&7}S++Fp^aIuxk)hYAD)N$qw@GTBZpjrdq_V$d zK?*;}uXxrMmZ4LZzGNq)CxidIY-)#)zgne}X5;zr3dt&8ZDgI{Z_BMO4JZ5EyniY6 z?)nKV8QBet=}W0AdSAjvhkJf^eU(0JEc&45g0NoDVSS-`Tq67cvJR(!fNZodNurOP z&}DmET+VdoB0du7n&06#eU5fw)4U^@=RZQ{%)4m;iNGyic`&z~f3$;)5#Q~2L7O1H zujhMQ4t-}Ot9DS?EjYZ+4QiByl<`L3S)n%;(HmWj9Gc04$*0o0a8AN70H?9%BodtFz z#n?XZa#X3QO@sbOj(ns~i!M>YA|xH3-wDZ^13oPPb_VBEI*PnqXW6gI2R1b?%WqG-*8F1ri&2!_NxRH|zjR-1&%&U4HIY^+|GOG1R zDHGW4MMHGsvu~s*ookWBwl-wBoGgB%RUH>;RWD(OmuKhN#4nx*AjHYd?uD>kH-vt- z5=}eD$xgi9*rCifZOn&cCE?!RXGFgYKQ{&a6n?{sX`}(l7c=WgCXUi`7q~2eyr9 zAQd-Y$cvAroX|yBdm#^2-=-t6XiIBHC0iZN^Q5Q7FUCABb^9f{G;%ly3{`Xy_CAA%Rnna zH5V=0S86z&CZJnQC6Bm?)}MWb8t67(4TOjNnX&`CeE~=Cf@=zy51iaTb4Ymr28%=D zMAd!;oPCHaev&bG*1KWIH*!kdlT7v>*y~W{C_Ly|t7RvU9RpV9ZjV@NW39!)544Op z1WKg;J|ohfUaQvn)9dtyO)nK-5YA@U9yU0?sMR`Dy-7M?v1ca22sw1E7E7@^O)0CU z(_~UqHbr~LiA+kjRMNKh5~{VZ8UUhAt$}t__-}Zc7Hty^+62F$R`5RyEYbPcPvJzO z-1OSw!?8@9x()|8sZAB)7N54X#{vwPt+NW$wLa4Lyvx4r%JWi(1?AWfzNFPH;aodv$-~rIQ;{O#2x1)5~Fy2ksseJbRY+n#tZZZW-@>; zM#LfE*5r#tdSWsDB_U9JQ@qusH>Q?df0Bks=0$bst*P5SXRp%6)up$jmVMG**V}7P z>b8&ZT3B%l<}iMCBWUMbOQ#}c)jb>H+VUy`hwpzFBT6e9m#zGUuEduEalN2ZraVFR zRdyyCX<4L-Cu+z1v1j0hX4K@F)}UYk7JleIg*fXGE9;(T@tT!ai9Euh5!o^YU4{%g zeZh;zBqFmY6G(XVx+HO>9<-AjuUj1$scI6$UZ)@qIt5?g%#L0Mqg@q>ACjlP1QgN^Le`f$+8my+N@eGj(t+wWGXlJ5CR z>F(h->w!1Go-ustnYU`z8Z%{?H6}SHZ|S!5t7`1P9sPC`XnnYy8l4$KrkAt3R{_hk zld~h+1ur`T?qc=}Kh*(eTc!z#)sg%1x1+Py&s=_1@^j_6oXhdE?}OM*)Fl$L`0=}X z)YUH4d|>TS&>fBk1P77u8@~D+AUN-`hEK0+F-506k?ME?vj}Vghxy*EH0%cTY(CzT zPk3GPmDY82{(DKc^158!5L*hpJrUK=X*F0o{aHN=9nRsWp8UYZkBc8A@%ZV;M`Mz; zcF?i8kxdSXAG&X5H5-k%xsF3A<;qxV8jQTvQH2eL-z|8P-OA;Bu_mp(F#LNS4K7mE zlOsD4`E(Af;zvrltgF%Q0wUb?U+X2;Zk)?o^Z4p_Uuw8f@fc55%;4c(aHqqqRd3ZE z4NEvJ%ZmPmvG5^SQ8aMQ-?YINUSY{<&F@lPuj>l>Dm$%J2;9Ea?XZA-vO&e(O8H)? zaj{_>Eo4;+6Y72p-S~=m=O5xR69#R}EDvYuu7^cHBp;zwawUyM@MTL`cBP~^fRhn& z8A~hcERyU{jhJ&}cG;%wN_E@{5fYM26_`8qh@2ee(JdP2R*8261)7>L0v3U~F)EDC z2=v`r81N#<58MUsl_(CTjAy_x`xj{%2M#>ZRJVO$FM1k#Q7Dc^qoX-D@||J|;VN{G z(fq>?Pj>mM$|a^3dg@^$RDB@cI>qM%Y;?xpftoOeC$i`+Nn>%C8Di(Uo@FF6RFca6 z!SXU}L`)9Wil5n55{b3hOW~%hxyYWa(;R?DXy z4(}8!!6G3t5SI&Q{9dTA6~S=sCTY^RJJe4D$W3L;Jw3^}sx#e0BslOTjj6<(!IxFX z0>&^I)nSzTD072SewXnj)Bn8{t6%ZuxV|;2FA(obQisZ*4$<5Ht99yve0}p(pAq(C z>yZmrHaX&81|556u%JG&)pl!}6Lewm5=Z zhOVd%LswLXfrCbeWm@3qeuQ zb#77~u!zSwu4G(?O}fbCpO}&P4W!qvv)t}MKJ?@`qGubqT7wnugho!WUMAzh)TSXB zM_~$JvhH%1_SizNb1fy!9KepDH$UnHiD%U_)tI`cS698w9}IHgw@895tmF?>vJl%t zU-k$5P4;E~Lw|nZB%e!x%_dTjrpw#mJt03*+0}gHAVVz^T!NQx9_dyA9N6;P?{rOf zDjN=K$mJVMwSiJj?m0`l_`p1(RmhbZgEl@ZWVGxw6H?4YR8r%XRcXo5w{@xd3e{D- zuf6u|5&J1qJ`fad24>oa7XvOg2lma`pW)HVd7{W(peCkw;1a3iXJ(7mwVf1t^>b=k z=*>RG4>s7-JcNPus(m(>NCV++p-0RfLmv4~B+>Bd%{vYWUKz*ufiU3BD@|=O+;+@< zyB`Q!lstwsA-ZFBgPj~znQH*h!$nR+59n0=s>s|=< z%ExGLQ|B@@yD96d&aB3m?%t*sM`c}YJTLURgcc6FmfBml=n70Ou{WbSKUmI-XLyOK z>oC-yOtf5v9=@o(4nvUNZS8a!O1m@ywBv@POJjr@9B^ROph*-TUaVEs$Q2u8>1dt; zSvI+@foP%TG>Jc9CYRZ8~GbWut+V zY#y@eVYJ=+AXv7R6Dk><#>aDaw0(Rf-=@>85jtFUd8WFtz-_{WdNCR`MSR%e@I!yq z)IB>E;wqb`%>EgvwwqKsni?l`bZWq~DgFc+;zDT~#@AB!41!AGy`@`SOQbqp!q^ms zpwYAk4J2LIoK^jpm8fsUoJ2!gyuU9j@!?DQWa3{kS~Mi2#A2^;(>K{5J+?6B^iS%T z+ZLX<4&(H;@PtcjRkBL0f$;y38%54Te&%Dkr`4rxOiktBJ1!iA@xKa@Bu_g2B6vw7 zk6yNi-{F!cL_pPK6an>TCq_?sJwRSl;PticA0$uj{?cjaOjFYyOZFZAq~EEs<6dL} z>F>)2GX2@9`P!z(wZ*IoBU6$%>G6W~0)jdRtj-eEdAh4J6HZ9ob>uhur}Z4}txlz1 zOQi>Wt8^UJSLacl7&!bM_lnnfzTP60#Y{quM}|wPcgX4;rFzFkuv(j$@Ypxh-lJ92GO|+j&&qU zx%JVaA1+rY7s-qNq-N`P)ftqH$78fSHZ!w|+mE|EOTwLzkK;<+AghROxuBIWQHU$_ z=$}|ghcB5BYiSn0!+>b49?oJ`|LU8TbnRGb%cO*ni zYij1TTT<;!FjgnP6t)9))919J+ZF%C)JS(jds zTH3~&Yk+}-1dg^Oo<^(TKmJOcmzd?5zEYbF?bjsUM+a8#c&Kn7H73%-r}t{B!41=> z6%(u6(S)_-&ifLnW%r@aP2KjN55sD?Ih4xY&3pI+ulZFi->>L^2f--4Uuw4tK!Bu% zyE(FP>kap#OKd!DP?GK0GTXQPw}?3=zy!ho8ipKKJUl_)}9p>{}CVZJ5_=BkN8kHRf2edFPD>6 z;Gey%&kj;U@3S~D5dek89p|@-kGBf_E@g;X?0vq%bMM`1EWB8RWH>++i3cq*x$s6b zLi04jZvh@R!YhsN+c!o@4|vAXqM~;IWQqTImK63gChoLJBf}||j*5g`xZ1nNu$nsU zdhiTbhg+N)WP0Pht{qt@uk4K~?FL(PaV^#HnH_>^AB6-}_|B)`f_XEZuk_G{8G_}_ zT?#gB1*`h-SXc$6Fb$evCCoGk!=JUxqN4fyUGSCZmcXA(E&V=o1EE9mG+u*hccj{u zks@|zkapU>Kv$+EF-JW5%3k0>t-6{jYE2SMwcki76irI8s#8nuQ9Z`eirW4=8WF#H z5!pO5sCTM#awftJIb@2%;Vb_Mupmik(H;7Oqhq`>;k?n3mCx>%aM~@2s?S8_Wccrl z1pZPuTw%*`0(G9afGei6goVWoq$p5A%4^O|KIHI0u8I% z9S`ZrcE?-wBtQ2Xg(f4KqVaF|wILfhIo!xiJE#SL0N6(i!^IEsr7vt`1&&4#s9_~; zFW8+B(JE$-6b80UrlN^Toxm06V@xH~oxm?{E_Pu;Z7xrYsmp=G+h#0z+|(4h)Fa{?Xh)<+J2 zQ}=LIsw%YT?HesE-ZvvC+(Kq9HzF&MyB~T1ddNW<Fzsn5c`;uWwoWb3c zZz)AK^srRD(?*lZLu9sVXfvS?tPB1{S;eL&sH_JU)wHiJ1#O`22O4?AozadCTVcy>DsR zY+gS^bRSvt=Elu6_o=s4!~8a-Qn=~Q4nW8U{$ayn01kp1Rd#V6z)|6H0L*vB3BYD0 zm0;~s-m{dqztqju@Ur6EZZ?VVvO`hLN4g7Lms}m(dsfWSY)g<^dIDx;lb~^wgSnC| zw2_sP#&6ymwJ=xPvWC45?A)`PmBVyA>Am5poYZou=Gm#eAwpagV__N^yIgn)m%usJ z{8-u@Yu3(7BswonBtFE?Jbs?MD3SOV{?47R)j?iD*ag|5BhfXz_YF5&PNu-oZ?+U0 z;N@?&gde0A-V^e{afJrLPBxGH!5#L6r|Wpu*dEu(?QG>em|SG~Q50)*AWUwDg*Q?K zTf?a9`!}iUdtnxuKsJiu&A%;1&UWP>+Qi=I>vx{w>%DjFkJb>!qwhT)gl~SCK{hT4 zMI^#2Sws=vav4`a!=CV7Y@iBa;1{jwGVqJFeYn(p%QcY7{8_8yyczZ9LMwLLj@wm1e?Cvx z0M$6d53N$+tgSJI&GEvt$5~mq-1#HEhen!GKjJW&$huKQVNJF8WN9SVBO zRgt$rXLvyImo;x7OFBobG^%ZESadl4UJ#y zpV25B=>T%hV*lPRDc9F-68Bs!kfNSw`FlH{^GW-!%NO_0v0|M3{f*Ih7{iFdR7>0| zim*QB=hU~z;W}hP@B?0Lfq@Ocke^wNWsQ@7n|6iG?y5pWdq4lVYLo0)n4!1OsA&3r zEegg1=Ar=F4AXu z&4H|rs7-R*`7?&(K`)dJKPC1>DGKftvzyYV5UkS87R{2+LN3 zq#+vHMaT@2iUdaH!=p(83JHn%YeQeEk9&q2#kUcefDo4X$wBo@oCS1SDBnwA&C4r+ zD#$z@?+;WRL~2TcaMs9gMYySUkxRZWAkE=VO_wMI?#;#ty3`_?7Y9uK+wyw(FPQ!T zV-tCi=GxE2B2BUI_keMsgkaBi^Xf6$2U${r=MN{XxgDhF` z(MLFr=~NIcmfmB_nFK!hJa^3WAd{t#VLDhe#)*W}30N68Jd5Wctr z2nH)hqAaj8lyTmLg|+L$f@bAbYB*W@BHp~OollkAz7Ja zz-aTe|aAY@&(+yZP#mgR82HMC$fZzn=q5>=9f0DJMh<_Yk?Z{ucCggQPL#_ zYOXb1rO`Xl{~&jHkC(1!%O){Pl^y3`|q5B$xiNk zR32Q(Wb?yaN&SArpQTu1+CFv4e3^TfBuiXWO|a+ZpmbJvVeHZQTRW z=xe8a<&5%sddmtf)j9p|5O=2_7FP(mO6j|Jg%}&k1?Z%$tr660T66y(g z|BasXWpAb=w)$3adSkv$=74u^pAyB|?)AHj7v6>tDI zo{~qO1)Pr2SMiX#q0YkD- zfEH-TZj#Z2X|@A%J;NKz>2>4W$l-qm{Hw}bKUMa5{YRec{p;!B?MJDLVbEwtb!jw4 z*2SSfGzzO-UE7X4*88W^y-xKioI;I8ZLJ3vK!AP|0bcx|LaGHyxF}1Jbh3RVE9LDRQqE?Bnk-92g3uRj{36x)|kD7_qr6Z zs^z!FodlB|XVEAFo%@uUwJwtC{R`Q{WB6ngkvX`4vkHVo;=x*cQ-8U76$J$RcN*o< zzphL~zCv$k*tZp;#IUHeTUaHFey-SY16&;-bK5Ph7ChVg%Zy4MT3l9V5yBfk>2Ee# zOYfD@V0wG%9@y|coZ+t$YB`3v=tbO7ruWvR_oV9a8Nh#D_aR1e`^)oy;uqQ*V%4{O zfrcx!X~vB3v!vA3@4e**Y%A(4hlo+q}M*Z@RW&Z)(|>1q>IY_{lqhf)un8g1u)< z%CVSitZ<6v7*~oTbC+eGt))gytb|QOfLi=6Dlm@eVo4~pAW)SB#2*pGpe3jgL8EZm z=NW#z&02%79P!2gPWT5#c?%E2VKYzBo@r)q1$79P4Wy9oH(c<5VIKCUx`g~ARu6ZbSaK%;LHu5tNVQGo9Rk$&I2Y8a zWARr1ax_q7b$6)4xBL_(5G`a6FJ9{`OX_|mD!64O=jfK6y8Q*-+2sZyf8*-Q5{*rq zohV1o&0l0*KENZ6C;X3d8@%xtDA4OAJD%-&xZzh?YgwC~rJ0X1i@+h?WiFruPp}TP z#1qF1f~7G0xl6AEHRd`{tmzxnXzdUPEod6RhaI`a>Pd$um1)TqV+fRPTH+-wA|Gm2 zjMA8ze9GO%!(!YF2+ph*S22EHHcCSTbt=J zT=UBoz65Ok6k;m-(B^lUs zH23YbX2_Jf{ZVB$Ol1$>{64=+fN>L5z-y0H!QY^Kxjz#}3XP)~=b5FPQPp+|wM_%= z3S~{VRohufn#Mg(qb!mdX(DksJ^*F?5rw}fYw@RQ`&09{!J>waPDCz(rqy>8BBBah zPO0Ofwo!H6swkB;uMm#D8p?*hF8T`ZW{rv#ByOIT5gutRiV1^aRct08P`J2W{MEm%7(^Ryx^F zbP$)&U#Amo;B$U*6o!C|p>F>;I8(3k3AH2yOIxVe^{ZVhFSx8Mm_0T#bllg*Q(7>- z8(o7u9VUl{vIqP{%1)ro8P7MjlPhWBN2a0X>Rlfh=^4YoZlK;@PSc|5Ym<7(^Z*)mQ=Qb+CW&PMLw;s>iD?O zcA7zyBeaw`oLpdw2;}Hqbr*oxb2!4RA51*#JrT^F*pWU$n3u^7Rm_Fj`kdS3YD@+B z8^&~M9>DE}d_!$(8_?+XHlDV~VKcv?)i$^8 zUFvRlwvt%sHJ>}*n6%`LN&iMtek6$Hqq~%ILA&4vE5&d-#4bK7M(jKJ9?YI%H1+~Z z(+CKsQAhY&QW-L_xm0#NwHcoZ=ep5#$(rVjE_9s;PvwJplFAgy+3J^*N#T3`?!jR_NWd z8m=T!+5(_Bg?F)>^uF-RmYNUYo$5Hi;$y)qf1x1{7pWGcxhTYUs^eFDrw7`Y8($@S z@fEpSH?U+kbNpY)PL{6fL*YHk-L!%l8*;ctoJX6^OcwMUZ3)?SJIiR8SGsj76vH;*(w!>%c)B$(dU z{bkxz2h(@cH^MzWQ_C^VJW4kx&J3He^sez1R1}^6_?12M&a+p~p2Kz$_;L-%{wMi!Cu6rPq+Qc)1E zU8QVaJXLK*Wj=>sK}Wm}r9mL7r)9Cy7SCOnd0;KcST}z$B4gh2C4W2FP~cs}w|opT zZzgYXJ?B|HH*E1&RR~>=HJ;`#o1mwMkawfDYHxP!EA)0|`xU0WLCKdSC?mrG=9Ybj zFPc{IxAN>mi-~|LUn1UAzLhjp^rtHXS@=%9rU^%3(#V0Q-HN-tMKsYwRLg3=VWOAr zAbLsoE$`f+v1*&d9PraUXQsE?>y>(K*y7i3^%`|(8XKrZAv=%K4V9v?eQ!-;@whg9TJv6* zi>YBOt0P;=bUdCn)Wzd;?e!X`8@Bt)Y%CvYJcW5=qsopV8p|);WO{dS(Tm62Z4CdjEwG{1go?YzaQ?0ZH24b$r`yD61DgXgf$5_Sq! zm<+}8-Mhedpnkq+j#L_`H$0LVdLD;sqMC;36rDo#6rGfZrkccwd1&M!4el1r??Vnf zQisu`HZZV2ZHx@q13Qitjdjdoa!@2mP}Fp#=w;b|z;u~eZnR*glLh%@i+tzxzj8Sg z+BRFIOrKPDVMRqMdoJ&xg;t8^2~jm{UPP*sDBxZAxHxti&pL~*r#+3(eo{)BD*Mxw zpg9pfX&DUJXix~LixcNi0Y?0GBQYd7sm!;S&BQW5O>MephF8CnReh)O9`3D9t>{U0 zZu`x^Z=Tbcb;F)ade?BKVGoA@s-~eL*)Sny4X~nUp=dq0ljd_*qTTcBLGTp6VJbEY zUc+j?X}aHhp4YV8YhK}}?|i3SQEfZBR77#7->`awFWvO=Gt(=KO-#28%l(EGe%B(J z8Q14EtwCR}$0xn!wL};gpRUI9tn$H$Z2hTesH$z4n3~rxG3E-@XbLXcA+B%@EJQ2N z0{)h;gw?N$SDy6+uAuWK2AdGEUj2sT!(PKiR`TB0O1!2my6x1wo%o=zjP((}pk22t zoxeMnp=D`(ZF(InV;vk#EThNURRfSjCx(HRq_=o!_~M%J?OQb^8rF_q)x(2lubw?G z%sjZ3B)H~@K*HM(-P>>Z!}Y#~)#u=dJALOlV_Cqa!Lr|jq5#S>Jmy!hdk;k`n3*j| z5tqA&z!iAbZCG*6<*?-A4zgWN{u zhu66o_z}iN;>6F5(hjpQ-8y1n0**Cbb6F2VgRR>|GPXA5Ii?_XGE&W%;#yA0r%G>? zXc@jjxe=Ki1b3a`GXILt(zo1haww4gf`ssw{0gunYr0JypVA!xXJ~{&sISs`)3n`d z+T#SIL5KjF^;Wb9L}i6G(+!p%lFx0B=k#zvk>}b6>hG_xC!8i{kiuP-qM>3&1Ywi!gP4(5;Y2v-Q_8th007bo?i z>9O554?4UeZ&k;|#I+?#V7*1SZP2f}8>>$u4c^Z1CmUx&%iQVP3 zFQ*216pnVud)+QsYUFmejqXX-ZwHgLP3uz2o`y>(Ky7|-!2^`CQL^g4<3qwa4wBdb zd_%A4eFwf}S=fD(c1xUvsKMZ7kzOTD+Szq~R;&PMID-)<&=Zs!@r>+F6JOd)g?l*2gt^1~|N9mo zTDx>v)Qq|0DKr$R6w@0l9h0D~ZY-qm&zTGVrn1aWtxLkj3`Q<|pQcblRkC5?m@J-CJhKMnCC>Y?!d7>maW2xo=&XzyP~XP!@buVoG=f3yEL&wEW9yylIW z^ad7>jl+I()%a%E_3DUSn=D7<3T`+NgW3WL!YOOFrRHrDldg|MxHNzLW`a*QuPDK? z11Uo1d2Yk7)wVA2p5at-;!zf#kh@^eD{y>9e3<&4-r*8)?S>Vpdk_|PYVX3vCB26{ zTi=X{Z>`1U*gQ!rd&IjG4S>9q=$+OWpB5=TpW6k3#7qWHHg!Ur?W>x;P3x?I&kaV4TELqii;Q=p-0NKY|C zM0yh(kyXlo^+Ke)^iDExwz2~PaNNi-&edNvZsWL-W4wFWmcW448aFxxARRZ_1vh#Z zweN1;6{2p28?Euv>m4^D0=2l&`XX+0NMdHpjSd+%+GE^^K*a@aL?qk#J&L#8aLBk3 z8F!6O!)DQW?4c)o?h!{KU&AirNQdA^12IP;BC*rkFy=_Rk_>axp4ujy#~lmx z7Kh9ZHgBMAEhEuHEsfTk58*OHL-QWejkscU#_1&3EOl7x`huaTTY2KeZcTo%TdADl zUH2MaPkE0ZW)%W4x>XB}!TQ?tnm!bs0(vc%7|KzPI9f)#e-^`~t{00xoTtR>^?Vvp(hdFQsO04;N#A0(IFn|k1w4P}`n#$ITwh%4@SE3UZSaYdOu#|vaDEEukMVO$Fn zBj$W@RY&K14eNu_6RC(}xE)lBrLsb7hVxcUu8+Cofrp*Wr1ju>u#o%2_Yj4fCi=}IrC~NA4B|x}!2UJ8Ceu6} z)#BIDf7lFxKmM~l!{cnP+fX%m7u(v4I4eb7Df92piD6Acb?uX>c~9yP%9l`!aGT*T zk}C6M&2RPtvDdJ+h*KhtGMF)^T*)lf{SZW4oI_HedA*-*D@m`%6{Lx}8_}X`H*ccu zI-GAg1q__G!*nnRyR#+iuB#=2`@HnpqYJx8RB-D%V?Me1t@z{}fS;$%wr+JM=96tD zdXwOb;CiPCu0&oDCrxiK=m!w0vF!I6Rs@(a)i0Ot`1Ea&bjNM7^d7?9bMWui_jvV4 zcX>X_tY4AagP|&XG`$=uVNtt{c{h@ezD}ys3d+*GMMPR8)m_TbxMoB;W)x1cyKSK{ ziZ#YdUxF%>M|)~XcQ=O^}nlRV0f;C5SX zQr>PLY~8MzF`slOrZ;3la2yqM>LGmT2%P{`jFk(Nb30+iZ)Tk zWN=V4X!EW%>iI=@AKd9p7p)E)*I>5#5u4+V)!*=btHmu=WmZe7L-&%!^Xaf@rlK|P zV^+Mew=a=$EL`71pUx;V&(4_M)fFv}-h4OG@d8o2w0!jFC9iNxt2c3EN!Ab&ilF_} zzq*Mu0D}#Cg%8_3Y>>oybqZj#D!AQ4gI?JfTujGYF4Kp9IG<~~7S;FtU&hV_zN+fV z|9K%7xq5Zt2ATQ){YdWF@3q%n zd+oK?UVCi?Z3AJ)`jY#Xog2ygcOq?$5cg}j4nTMd z6BRFJfK-mw6V99$j|Vr#jQ?zqH}J)8iSctFc_tKyJ%~;#7#wf&g|+Y3u(-ESIxZtm z#=b`~7O?gA!r4qg2&3i6apHHAWXw`!wN0{jFDu;l___G8zEa;=#f+Cd<<$zNrl{~$ zDvU;imkujktgK|SCGLCtB3?gQtnUuRjOPgg^V*hqrvf_=2!NN|Okxk5yA@9q_MNN)_@}eVw&B1&#NIg1RZetYCRXa7l93yI5Y$ z8j_-MtLis&Q!M-BG1?`@`^BK{-f~pap>~bdn(ZMrNr7b(Cte&IwAwgdmv!xt56|?i zuGX%8u9*lKv-&(M{_&4~c50UD`lcaMkS zNSzSb8NWq*oz^j%zq6hh_u{zcdDf9{f1~R3w{%(_;c4939r{kK71eyqMgszJ*e(q) zM1C%~AUSK7j!(MW6`H_3HhMnSi&SOxg$*2Lv%}*oVqxwzKDLOP04_cWg(dO5V3W0u z(l_Ej8K+nF&mg}|Z?|?X`igOa_TR;Tq#v+g)OID$M<=z~BQd1Ry|b zp&&m#Z9H!I6^?nB8s^|NuJ)_)wf_))r}-hir%7h~FZxaD*A0cOcTSAF-l|>pgP^|F zrPbWNj_x*`3=n3d6N#HYcI>_VZAmQ#+mg(d_2ew^S{^CH^)xBY=rNL-*)+>GdAel6 z{B)}Y6yJ<&m~I#>2Fvk3IgdzYLRN`xGTbjIuYpG$^~9sayIkPF7JX@6k#&N)b@XUb zkX~=Q#?(~OS+ew)XQk6Fv z#1b#7x7&mCebsOJL*D$Z2(kdy2hac7?UJrr9L)tBg>J-Th*KVDMnWm(P3U3gRHB~^ z=2UUQ7|fZ-roJb&Rn)qqC&dF460Tp>*reB&r_Y{+#oETmPRb1I$XAm49)AKeJ}O5` z4XdBW3!7%i#MhZYYBoPJp{5zC*6q=!f^0Sy`k4%SCc~s4JX0fj6g^QSZP`hqyMW?m z#u`o+L2c#-`R&V{FkGyCIT9!}@NlqS-FP2X?dn1O`Y?Ht-Oo=qc@Lq{wnlqujXQ1ZiULHXS>-~ z{q<#D%SoEg>9fhtc0mJxsiScN6C+IV6^wU~jsb!q!1})^z?N^%X|o$#x>Tz~Yrhca z&TMoYKWM#|2s^WB=_bq`F}qmtMy){^PA3B{c5$N2lFY^fazw2>7fRa~%!ShW@vwo& z0{Wa09(aNnq1Y{JM6vtA^iCcf1;M#vskM2V78@~fujNyWxeGsF;g96Q(zALkC*;Fg znK<+!>{dS!U+&Mt09kjo!$r-7oT|M9$>hoed-}doTe+g;=(f*LRDx`NLZa&%U(foT z6>g<}b9>XN`MoJxt3=@2`kkIJ?ak`vy^G(``kh{f8Q){sk()Qds=!stIRXPYW@#c= zmJAkEz_Ln=U1d+R6l2X#-7~(#-!ltM9VN;H;4)iuDlgV%Ry$2BIx7$flxraGS<>-*5 zblK=US1M=6)dGBx<#GMLoBqEuYnSW)bZf-U2`&OLxsw$ZWXrCPp!zB!2~~Nv-)^W;8*?jq1R%q+ z-^S4{NL0wKgN*+~#^5ZVc!jJzb7`7BGJEsc<5?J{4lDn8bsU#sbE_KJezG6F0G z?Uw>AC?7knJGVf9cjvUyMjfB*ZIc#^NPso^+*27j+PSd#bc~{MgCj9N=umkKVZSL+>wVliViy}9-VOm~y zVA?x9t&gcS{_C;A`f@oro~`ap|2hZ1Dc}Br3jayv)G7Y?6#y1ieAaIjU_~{n zIsI4E9NQ!^moBRq{3$jEgO9|+t=?e?plgJ1_8}&o#@v8m99wRumhef9b@gz=-xT*( zemM&LJ!R!Jg$@<<7pojMwv1h?=qF$zv>G|34)`=lmyo zw!vMlPIYSV0SD0FHu}JH$h^Di#uH37?|OYK<4O3YKYaOVi!s|_&91tnvQ6;&FrSp) zQ)MOJ8|@Q#aVD}b#z1W4z*le4hL=MI6C6_;{Q3vs_tQ&HX3M~tcl}mv&d$~1F(1Qi zFME!yBgrvFlc{yy<`1;jcYB*JDs8XBGs=e3QV#->*K(o>FYKG=#?N!4WKgtgSTEtQ z(AM<^kNxz97ioLzPjBQW40bD^bDOQDLlfR*dxlbwGmq0Mc4`kZ8#&f z5qlT-Tz_@_dhgcPm4*$lGxWuMLeX-PlaygrzH)B?ckC`p?Za+0)z5v7zr-jjtT+~$ zd$T>^J@{Ut>kWH@X`r;azCZmsEzu;n^h>!1Ds!!s`Qvg;4X7|iqGmaRCZ2T@Es73h z(Ar%xCU+ksLc1GUI@2@a?(9={GO2x~QKSA4ton^0)yo}J#FX3#%rTdjI3jvdR>IET zSyAJjntT@T<3?CB5pLA9L&z{*x_gjixsO+!-kE;E?u0R+O!jmFb=>LIYTVHL06i0$E4=oy zoX-D8Nu#>ooYQN5Z>M^pF%EKA!h6Hy&jzf=eRy>Ae)Qf8Z$vJL4|}O$HW&{MALn;9 zy}~Cx;U4T8-}UrAeN(t1pp7o=B-h`1%t_FMs$VE}1LkkMSR7+}Q(%TSe%In6#hNJ!fWLW0l#zPeS6v ziUGn3Zf^kpb3I88HgpeGRzF@j(i|+AZa`E{aO+~DBA5pxmc%* z#p(XoxNC20+|_WVKQyMDI(>vX8BjnxRet@%Fw?IJ;Z>R>SX;oZ&KBwBBsKfJQRwMe z&kWw5Uo+H!%5lS}Wz&~zL1d6JK#bOrc!9p}K|VF>*}v^BDGMJi1rGL2Vjbns6Im*(tha<D6oo8{bhD6Hjklt;Ja$Q{lv6FoigPdJb3J_Z+rG#sQ4 zHNRH^G&g>Y-m=$Kq^&++n9QFjK(lOIb$7$6r@)$R-&Ju8Ly%Rm%z&BYH+>!6BL1@$ zV5cpunD&TCO2f@N)O$(m)>5J0u1&fz8OZ#id=i7V*onl5=TE2I!5<@-ZUUD*wbD0^ z_={HdG_?ST{_ANHBhhr|X%z^GtO2le>C3N5Njqrc5O_@8@4n ziISfAOWjX{`&s6GR(47q+}flN|Mj%0S!>MfR9)Py`r*Hx`HStRRdBdWx)!AWdRp&u zAAD_yzQluv2DGXH%g7ZKnH`gCnKq(X>DbFoC_z#}LkI=2YBtN=^NthQH7TFxtatqC9y$ z{r-TwV;&O;$uW+T1HV}X^}QG_8_BLnNIXv382E46b1q@#uALJ~2HHVG_T~gHO^%Aj zeo@is-GjZZzUBj0)762sRA~z=Jb+z(DpjeA-+eu)J;HzvnzMS6P!sL9GkDlfu81~j z_?SLrfqgO;nU$7HDhA_5BfJTX7<>uSi4~J22*Y-ssEI%u_=KChwA2Fgme-9j~ zecdf%6vJ(lUJYm1xK-#WVu{12AImFMCC=ACSijTnuy>2i*T=wRMpwOo#SNGRGRBVF zBny=Z!qdyz5~?%5dqz5yDm*y6X~Q-!VpA~$S6YjRz71by>oIM+##jR^(?3YZCt3H96G5dT zcN=|)cY3QJ!Ba`^m8|@H+T$p||DN&=+cOmi(|Js6q{YEs&)Pk>9(dbzw}a8g7sO&g zf>XwTm@RLD`CKz!{!nfOKSt`A1KP;WlJA&G`FoY(VaVHj$w($OgfxE0Pq0VsU**5~ zLjSm)O!wH9-OGOEb89oHg+Nn3n5oB=-#m5K;h&%SEbqR}jHfodW#Pa@D@D09u@j=T zNh5i62c{(hjez6)rJ0tR7%Tw{5oGV=rSeJu}EWWM36C*}-8P7ta3! z54GL+0hQ5*%w2@VYZ zHp_*~z0hV{#68&8#W8Ha1mWosgsHvx?d~4V3-*QVZ%}_U<-0OQ8M%bxUiy}LTDAXCwYyIV^GblkNv;0ta{Szo*YVbR02na z_L)ZYy}2obp~A?^5cnORN{mlc9_};ZWEmZwN*?YzEtMD*E(8)vOpXdif#ew}5{v6f zQcZD~R){GSSBdwhN7cE8-j^IV?SL#!R!>H^U+9%fJ1tci!)kfsUPORXWgKIG7lqFd zQbv`b7e!$qxYF-pPVYLcE-~xbS#eECfBP9+80tEsE^#WcaSM1INF`_Wol&1SHJ_7< zBB$b;=QMoMSpsvp6#a==hIeV94Mt7s>I#D#nM(u?XuFm2b-Fz5T%joRmjsO92 zwE-)x#9=vt!Umq9$s>;XiswNhqU*|Hx~A`{mEPwu;_8V}XQWqDO-kfDnxLU35O$hK zJYNY^Qs5?Rhhr+io^xa%88huDjAjGIInzZAJCaq0IQAyEcG_FugC00=$ zJ67uv9kcm-BqfZ-j+v>4f+C=SZ9v_QJ9Kz6h0khMiZgp)W;$Kjm(N0 zNjNG=7UzOW=z2V$HZU<3q!@S8xAMq=VaC{y#;_SWN0F%IDD(z?HLCwwLgGfD8As2B z?5^o?&$>PqQ-umb0eO%`<@vfIjx+9AvDxBM>SZ3hh~kuMG{xC00y)N{W9X>d$UNVo z7@Wnp90)ZCJ6%`{LHfmQim{BQIzz%J=D?^~o&s}lh#EC0ZqzDA(eJ1X*16H6rp_HP zYO02%rkI_Iyo}TfopZSoN91zsI?h#CG{(i0qhTn9DGEm@$}ckG`rtW|k8+&n zNQx)|=LkxQX)Dg*I_Kywt__~bY2NlcwMKa(ijH$dg3P!h#25{OH4>Ks>4aSaXNyC`H)62Wxndp@BLWzUnX@_@_rQ%D zJgm4WTN#RS!RgMZcYH426i9^pMLoqO-4uu`x5$0IK)C7vGV+9Uo9fMne>O2JG2k;~NQos#_6G<8_jz096 zSeiVw2s@Bcp$bOZVI&5OaG}D2G?ec%xMAqsiZZ&=d=@B{oyn+*=-g4psIZtg8ewEd z2{?dRs73uYW*33yh_jf(0vZ??-A>#YmA1t*?x#@6_A8%Woak~MK_gUL44jRH*3bgB zz>9&CM}($xkwhLhZ74TlaxspB>^ik;H2)B5FUlnpF&js%s_L*?(eiD&2{D=sY~e^~ zWi5=DV=Dy&jK&V+Sx90iN2Q8<3dm8YSd_4Ff%z6l8Nh8^Mxjrg86_fEt|J+eb#m^g|HD!v#|QH9E) zq&#gz#8wn8B$Cshi4#Ycw1J3|961zoK?y4u&x%cIwurB{ z$|)6#3+H=M7*fGcs37l&PKOkze^G*suBz{sQB{+zs&GLq_2f$ho9*D}?dA6k4(7jq zIr!^HX*t>N4xX6Fkq$u3WBT*q#8x6d*7itmi*Y!Iz1SIQ4WS0&fjJxOkS)DJno zAP1^b16-9HV1|)%TIx{v#6~MM^mdax5!E()Bc3NHw2f>w?$wcXI+Z`=zdk0Yv+$0? zVfJ&u8ndmJ*Py#2+j^aiTItWADJ9Q$GR_5Hcgf3~y>$!Dq2`Sb(xQ!J>QJfN8toT! zw^gG{)e*Y+3^Y@)!RHJwc7)k-tu*-wOm{P_W_KPSjSLOw#70{D<$o2J#U89-Qrv?z zpNP`-#A)f8$lX9sYcjI8Q=MxsLrWfJzPlM;rKZNV;}H)0MlMb2u)!UtW?E$&$Spp# z`+3^U{D(zg1n`5vU;DBLFq*p8jUdw8Vt7mgd@n5O?mR3<86=8vcSCZy;+`HEOFmG#T}~HtRc>e zDxP0j9$ucW_(!UEepz^VId13zPC0eu$4)-t(TO^E)#A8=J17EN=NKHVn?a6wRoLTq zM^R$OPb$^U4DHtI{|e)qKZ`p*j;fu-#$2GpVWnOGzl-YdelQpFq;hw(v&X0gtpBlY zLdmrB{!%%e!B!4m!W`>0=vYG&;Vz*lbHb*0BG|c-n+VyFWhVrPmaCf#e4NWCm=2mA zW?A+0IV0!6f)7<3zKg%S$1}t+{$<=0=KV<$c0lvcg z%(#kL4{Bxu@W0OFP`R@#_Zs1-4Vgzqh3Q1s0FFA#b0?CnKIAPv28qa>M5|G$4RI+5 z-<6t=XHX8y`f~DrWfOqq@;2Jb^$_7`-VQwDJ~lV**C5^0ke?rg{*P*VDaCUAM?&=&=&(iDcRb`9q0PrIrLQ;AXdwPu|e+@Dy0G*p9vge}f)JvP^_dN^m7Q{i_j(g%#eDy}BAzu~if-xz({ z2nq$lszxwq7DoB9^@`6D(ZaW*25wOUV$_GMo`Ht5s7K%VdW3IRk8mB=!%$g0U$AL6gW*%o3L83~bcAd2o0pqKq||E*K8Y^Scjv6HEga{brS<$T)uCK_eLjMiG_fZp0L8>a}l2_j`3Q4&HxiU zUn$;-k6`psp!2X#DJ-hz&aulPI59^^tpvkM!)S@ z9`<84{<9>_*ol2rV6_~jR74b)M5V5^Qd8BIuE*MCciOYI`U-7DrB04Yoo=OO$E8NK zRa7d1@V}pN5DtUdAZz_{t^=~VeeAoN*5(4=cNfjv0}9#8Naal!FaRg^%Yv-X=FjDU zAPtT`mxt@?0vR&<4rRno(GX{(`HDljurz$ORUD7W7RB2M7hWKRdGL z6S&LmaQi^-IEbOL?%pNd>2+If_$#5km+!6{PFD0fMR(rdDH>8cz01oSqszNljT(^^ zW7TYb)a-0)wuDZR)#&PmPm#%ph?w3RrVujc1xgp`+;D=@MI=i1GHXG5zVdmq8KkSD z+9zcD;#MXS8>$s`a<7$rV>jiuvzK11`W!`H9XhzKQGcGjp(@P$oz2Bc-pN)+hMB7| zbgD7R9jcw9mpIvGPG!{Q>CZ;(MU&ua>)Ao?nl8ao)Lw!xefuj{I_suHK6lpj;Akbz zp+u&qGBZ-^WlsRA+@G2K-Yw@LNQC(3)aJuYD5Qgs+d9mZoj-Mys3(Q#T4E zUH@gVVQ@xPztu)!-kN90=*Z1TP-Ql_G7GKD(x{AntBq8>P?ZNAMz(B67BT9TsdcW< zOe@qB71D3Dk+8RBf;D7}6k4Ba40@w0^y)l8w>B!I-)fr)UZ~A~(4kqOeF4wivos~9 zuQ?k==5xhYjJmq3aje{9YW^V3%&nN-TB~GckumS;zQ$v$FczF7C(2u`G;`~2@$>4w zn_V(YnB-)6RGRB=V)6N8wiL;l3lohKX`yCrva!;Zw&opLI?Ogp*KYFxVI=C@80*}< zu5%sw^{qo@|5Svzw?8K&w7Yy+{rZMElc$S@Ws~Jw7S*R;--aS5)r|5*L;i1;?>d(+ zt6$%SJa@cBU1d~!(7V!R5)>M4B;H#s14wEyDkZkdTfH}mSw}jEWXL*Z^EohU*m7DR z_o!w1pDNXb@zIrTiefgnN(c61M$b~VJ9nR}D4Ok8+Uy4o<0jr}xmBm4JV)_XKM=(T zdY~Klc3jcz|7%6}zptV@qnIsGMVC@h?q(vFcvE`?e1DWst%NJM3nM@Vh*aWGlsHL= zFLQ0gXFOZP#k2^`tsb z`VLu4zUd5|e-kbiN$P+>!In0NE&Z&&v#K0FHP*&9RWogv8}9rDSyin;;sIvD z>`Q`B8H85D^}xPEwhwA4MeoWJKBP@|h=*F&7~;FUg}ouy3{^|3l&;m5jRuvQm&~}g zd@!nQO;p>X3`(#~&<3|{6@!1glfQm1uAs-aEfe7!9DmPBeuGe%{AOkHZ&#+Ec?W;T zw>2r3eZSpoI#@4z7nB~f%~UZ{k~a6WDAP8vFXmDCmUT3n`xlCHOPX8dt2c;t38D#H znt9?nGM9dEck`=yIih*{y1$Q`51OTNJ=~Yw?q$EOQ3pG>=!}4OV}Z_lYVE&Soos{e z>O@L!xs6PwIC9XVo^buwJm`N`2wlF|VO`^=-QcMc-FDM1*HXQKhQyoI)pes|b<4`w zxTvOD!EX4otVhXX9&pt0;Wq_RiU{JRc|2`+^s%AP- z)7pTz<+XerMEHH-ao$U)s!z;?71 zKXw^PvaOODLL>CNSCa3<$gp^M7wi9kp>+#K0B#!HQi(=HUMq%S#hKNnYmOcBu zi5TfY+ixPRFrnVrKQhv^v(|>vrmqf}PQ^JlXvT#bsMmkNf~0Rs_S}`C5M4PKMMcZc zaIkFFNdG^`F{{VNxB~Nx*U?F{TxhX5#fG&2?KgW2+2$%VLSX&|t6qJ{)$zyM+@WD? zujDWy*kqcw2C8#|s&fyB@)xsN=WJY?+w%t%IIiuOO-T_@I7uJreL*8f7dTy*r=iSF zRV4kmw9@aG!FTm0tucWujNV1h`Qcl-4tU+a8Kc+opyx z{bRi+Tgn&SUs-Z^Z(wbo+J^@q<+u8?yKnxC|LpV*Yh{~S_Z}L?+c3H-&PDsYhvp>0 zim`snrt4H2cbHjSHwm!xtASNhp0(Dp)|=2(U|r)`LKW#6+x1SlAJ+2iKg&$>9=g2J z-fqdfTjI^%wdFZEwtETxJ%=F?xMw(zoVXw2@ARxX%S(j(C2@^gXbgX$dNA!-c7goz zQa68_yKVYx>Z9}FHi7GJ+bP^-t;P=3f@Wbpi_F<7WFU>(m3gJf53eR7*Di7k&sUle zM#QQ+@X!Na{6erzNtxG%9a-o;zxPm2*Kj%eSP~qYQ{zUUd5Ye+jToITWWT5SBQLg| zUoO_DrNSnVuA~0diPp{bxdM8dbu67Mzq!JFpaJ3-ec8^Nf5n9zt5Wlk z>*o(GNR*Go_l)v}8olz0+shq(g{!Pu)a+XMX=Yc4U@0{yP&AudYh|m4Yti7 z9WOpp*}lwrI}Al44iN7lZupfNb@LKmOyIw9iPMb!c+O9y-}Y{M(26bQZ>fnQI2`1= z+9Vh6wl7QQy%onZfl-$d^7#rPX&g zg(yEoF@}lUDoI8UPlP|);2OJe#l@A?_Uqt#7Ve?aj)(HfSMgC#qrq{P~|1SfT5Y*ui4?x$>vtb@51Vg2Fdpu6JF zJXN*#)a|(m;0XUSe}f>z)vlUWHRENQDBwry_lMbmA!YJD@?y7rEpQ*E9~SoQPVnCN;DQ zE1rEdsRJvixW6WK=;j?dNv@49iCuB|7n%>;s!hzf^C3T8E2)^W7&;$#X|FU5=@WTB zxppE~ni`g8hAX_5?J#4MRl%M2at;=ntY9Jn063?+JUC>B!$){h!)>uWa5D)`Qsv&z zmg_pU-FkM$%!jlFI{o}ZD~~H_-XW;m-lnw^i14ooo`L;I83>eUy~|D{hK-lF#otL* zx?2hbx5yNONSlc;^V-+ko7Zyg#`V2LQ{5G}A8W<0o8q_Yq&rAW^>GxZmZ-Gllce<+ z1**v&6MEg(Byvc)>@lvcuOO?r2p&*EDwS@@B8|3_VW!8moqrkUV@s2C$k_e@9Aw=^ ze)b>UZ7U)B9$PTgj9c8YoUPo$q+khsd$qitR(RPqg;(pKUVUFqC}R>g-aM{Xl0gNX zoG3?x6N1d6!HFd`m0tE@OBC8vZjObfMxiqZh0uC->z}M2+-kQ~f7eE*bFx#!4olRC zrIMM>#YT6`mD~Tr<#~g;=(O|BTIsdiOMlq+KZBaFFMaHa1iyPwt4-#2r2at zzJ7v42u;KIAp|eni{WmtO~Qmc4z@|)lheUAX^G_OtxdZ|dgZ%K1_XPLZ399Z*4t() z)nNJ7;Z>D>n?xI=XunNcVV!ZeEwm4w;#g!KJjEe}Jd@9FyV5>zj(@d2IwT1A_eg#( zklML~y4$YhZ%I$v_4=_d?OXI;U;yJ~LS30Z$$Q8E$aIcnv1Wy-G<^Ymy|^#4{ZqE5 zXd&lxd!d_MOWWm)X>hls3CO8si%`~9OWo{Q`I6#5UxDFgx`kss0Z;G3b8BEYEFYC~N0_=*%poX{74FO#pC4}?r_Gil=>!`*1~|N}g{J)QdXYfp`)l!? z$~0*pq+z@dsDlsq9ZM}WLnLFsCN)` z%t|jy!mRXC=*vXtfO7rw2hH(qMJ;56@bSzex zx(m&_bVn5&4RG27r~|({UCJNH=47xaw3K!0N!J2yi4s1fIZ`GtbbhzrCT#>!CYKm_ zo90DtlK5@XOZe~ly#p&=Dr~>pO2QsN+bt048@J@qukW+O_ZYfG3O%-l=qvXq3BeUr zeuspA|J?!`Hqkz?Jwf%{i7Y(c=FV}(q@g(xSt$OUemS>LBYC&1|C~H7x#Q2x2}n3e zhRpD>4Ocn&OGGzh2^yoqx)Q9BE(G^z6LrphyCJ);v%g|y--aPv2N>iU7K1k+=pGB} zL#hZ&oYk1@QpGfo$+zqpaLZM^a1Gvx{a?biPw6rWLtS{<>_w<39&u42Q(DF?5H#)>I9Mx&JaHKMv?cq$O?<>k0K#> z<=c{n8N z-*s>#_Y36{C9?mT43ID2@Cr7%j8AChqN)73dImEx+TTV@Uu<&jLWusn6gkyW&xDJ z2xZ$XRiKD15Au67qUg!CkRl`%FC$^cI%55fEjGFzw>+E`TAc@(P?+}GqQep-DxFvAJNE{}@D_*viZat%R{Kx^kP`|yxnHqt#wQ=*R0HEa zDs+U>V#`C&B`#814Fz8K394~K`Pro`G6*Bv#YNdI2 zB4wthw^SeWE;<v&g-bKS~o!4wb=Yd{g%_e@G*qcZ%i#JhsxZ~QEf2Gx+ zel}3g%s=xnlYwX3u6N3&u*;i_P|Kq=lfe}mw=E=A#a6DdvuV9X#wy%top2Q zNkidwO7)ZFfk*3eY73^4XyxT}MhxCt&Ke^7*ThAl^5uLsH=g+? zYV@+A3d1Mch#A^O+`P(dBW7BG+13zCE0g;hh>x0&Pa|ybZiC-=pD6&HLH0U^Bgj8; zvrvWUDCS@GjLkZ~=g4PlWS+eq7cV%jSXZ68FTi2;#lzDZ%@vqH!?j-#62A7Ro3S$) zNdtER>1f%>s2)GSh~f6nog_^5TI3yvu=mvM|3(frl#R1XBHjLD3?i<39iEGun1;M( zRo5WNoo8+qWeAPa;u-8Ff=d*T5i*Yy|DToJRU2KC`JmTos`q#&?j7+^|6B7@zh9W2h_}bEZl}+474S&$`TBN<1Z{`jhGUM(Db2vw@ZK&I zh|?AIbnwsCga6b+x!G6a?%KfzM6HMIo$$9C#vBo`I|3-Gy7?hj^;GiM9CUW+Ub~zO z@q&6^N8DI1_4Syk5k@hmyz%Yks zya>QVJ1eN$KyNga@>iYchWO1V{#`vw|C3WIM&l>X2=7u7RuNK5BwZ{X^}Q;iA%> zlvGWm--?*^F&wH+YCo2@j3&1)VyOal&;Lg?mwGIBD!;ZnAKdMrG6>EP1jeTggee3E zaWu8VPfa%ErTK2-+Q8(2fBO_mEN{7QPV*3W!?8i;jGIm@sV;4(#?|%=tj2+&VM_CR z;sOnmn%@%@HB>dfH>6)@R?BT6d6kpe&pslKh3jIjJ2`azwt75`9Kt6+3fJxp(<9Qn z>9fVr>5z5OJ+IQ;_4^7OZZEfWAerg+{O+#bDn@EJCn3nk)a$c=ooj?;(h2gK&GzX2 z0~0XQh3ld{jQklvQxmX)=^8VZZup4Mq*3a64jkDjTZb}azH%e_02vpdSE~$4LtL7= zoOVB?;dFUIO(kmGD8Umy>e86yxBW zaHFxMw>^I>CG4?nP4TV~DTwyxy2)h&%~U-OGkTQpEE*A&4YYky(<2#_)?}(0PAqBo zOiku8{hnKsxl+FuM}2?aBdD3~k<3fnh4kNbqSMzag5@07#6kClP51b(SNboFUtU#6 z$UL@OWSFR4y%VO`!0Vb9)((Cbzih{Ly;|;Vo-@9yzYMS1o984;JMH&4{yu)eH9;l; z{qi6}qH}JtaZ-!QGjFXT%yeF~cT zX{=^$mDlnGEi$Ne6J^1ID!*0nL7Vu9-)iqSwH>hUEeUP8zS#O8zcL|1pNqu-#n`%j z@fkKcYm^eS>IP*^+aAhzEuW67o*Y<=Z>j&E_bKhxq<6YqtE92Npt0se6ZHlb<;S-w z-QCI4+d4_g=hMm+Sd?$+D98jC4yHrZpsM80)V)$tA$A~`)$#Dt8iGeTKM#`J~6o;TC^I* z!=`8NJvi<<>f)qco8xYYazz&>|J`ElvY1}0u0z#n&ctl^`hmYe8-Z}r&QX0IyxQBm zwS4vpZQQVA$0;=q7x!kmPi}hm6|d#LL05Rih`m0|9jN80TsbjsZ$A$OE!F#dUBkzG zbmSB=tu5)Ki``|Jt_nnXB_!JCkF??BPC2ilwtYT_mgR#FDYaxWsU_?xrUHX%^&0~6C7 zDD>n8v8W6FIbvi?v%0<2mn0g_lVoa=%bbb=8!we4anE;PRd(_24*=d>@-r^p)glKa zblc7<@GnVBPj`klm&qn3;OWb`MRk}H;V-BTyJPn)>Y#9M`!V4H2@CPw5C42>Y~e}b ze0%-nmHyY0THLQUMi$;&%00c2a&_=V>7=`WZp}pe;3|Vma|hJMh7{i z;S{|dR=*Ehm@jvydS87COvkqrb1A5Zu_FFAqvD-+^u5fPrbwXlzbMXa;y~S~_&-ub z&h0Pv2DOOL{odxv_WDPg-re8u`KEXOyP>M--F~m-yR@oK@@Ama65@pQdu!$<n2m zz0(mM5D$sRCpyvVkv_!dqLlUiYPVQfo0T|AjG+3xljex_=T_+eY3@YY;C=L19U?{4 zz`IkKXwj>Chv+$@SJ|F@i?8m~YuvtC3n*Q`O$1M9E^*W=p(1pTAeoV`mc6H+PNJ?K zri>pwzoeSnvtm7V?SQf+Vd^#COv~NvgOF!IJNA>W$F4FQH}s=#_L#l8`>Fs#?kkc1 z(#eHt3bHC^B2pfPZvX?wy*GU%XvzGNJf+S@=W(#VfSvFcVVF1ZeH?u@r5{F?e7bei zjL1cwckWO})O580)vy9`yQXH7q=s~|X4_PLy_SbzT^ybAJ#9!EtgNE3VNCV$;!zl)2JS*h)f5~AzXD7HlaR*|ZZd(@7+8H+Cs7KNWVUzPr0C!Pn7_&=vHrivnNvj2u~&F=&r4Z1 z>E4Dy=G^xMbPUgUp5PELx_R04o(wQmc%u=-NW$MDg2?Z9EwR8_I*b?~joJTfJ!(mV zGqk;;t9G28<{GV~UeyTRD@8!{6J--MQE+k@kK@Vg9+I)14Ic&_oZPF3oFdEkzPdv} zZ%vDm?7IemF{~wM%ClsnV#!=#$9g#?))sOnPA~_Z7ynKgNUCzLz{< z-9CqZf0K=@yHZmz#m1Epn2RD3WVPR~312+AbOleW9qJ16*SA{)92El)*<1byQ|3~j z-_b`pRsaU4UAZx$;y!X=cR@Ly-05j$s$W;;OzUM z&~Db4X}G`bbx*Z%S-j$dXOH#TLQRdv2W6pj5uY{btsKiMZj(@3lYY$0eoes?TOKd_ z6+Zpm@)Vz!S?rclRM!{S=f?6BN8#t_dz;Ae$=^d7xnn^yeqpN_mo>VH%#jY=(|_)! zhB(JbUHO5pQi5fP$L^!5AU|q)oH`!0zZTk#Is*%%_P09klx@I1APPG)cl-_;yG`OK z9CG?yHhO{0)qy6CRWyRXksiKy1Pvw))(q>=4&NHqb4!@XY3lpJGA;EQ53mb+9qJ7o z3_`VD+{_1QCa@z}ze9}1%|2LBNp6uCc478u{)2acBUU+u%z8d0JDCqds)YF-!w)eL zeY=}%L5DK=9fFQiQGFZGj=|Cv<-`#5UrtX-xJ(f{Q`w`jvxxP?%?j^3=}sl=8+s=~HUzI@2Etj5KTNx1_yblZdz`z0qrVnt21e zJBt@nvLoqFs>fX0L{!kzI(`0&v%0~3uCj4*fl&(7NJwePoreO}9dMg?;!_%(7@r;^@xI@#J_n=a7xvNghRbVKN0l|mP@ z|6x5!#CL%H(WqH-SpVg|M{13`9<gnDVpoOmg%A3N{tcj*sr*wI?2|T~GAW*@5pJf(C4D@NJ!Ni!LcpLJ6I4UwNAN zPuN+s++}qQC9s9N#;y%|EzQInb!z3FS6*Wn_Hb3i4qj6;2!oRE3Tt=hj4EayhfLTZ zw$FUwMKNsiHA@GE-lD2alN7(Hg1^Bg@yKACxMR_zIT=W~_CN;Y!9~yw)3N|t(PEsd zH`w-SJg-%Kj#Wu_k^72@Guh_w8#eBI@^wYZ-*h}3Z8z#&V5su#ugyv0*P4?y(cGlB zH9vQirnv!=dszb=P3xo81NXOj+&xlTSlk6OH-B@-TUCh5)wc3+OCrBLZ+_Lz|Kw~R15L}%>NS3l6888q z-JPNOE;GZkh7+EoE)+FI#}u**We%`}NSJ8%L(!nLc|Z6Lc6HiWWeou7{p`tXEsvGo zC(YD}zZS2LHGC+)OvP;b_(JY){d=7IVRDD=-G?CG&@CHTYg7B!J!+q8Z&|Ys9iypF z+;odTO&r*V82ehWQ+o(HXtpy%OR;O;u-G-a2vOd#RNd%k;BR1f45HgmD;49O`Oe=U zk|Y_hL7_xl%V4?R*uqH(cZifX|HQScr9JQSsL4HXtvv2c(O{cev(vQ}9d4KkvB{L3 zZX^*XkG)qlsuTZ4_oM_pS}r|1>~b|J7cV#fUwzZKTXqmEZ`65CC0~YkI%_=a9ez3H z8}-_@Y+p5QsTMGc{g%M1vmd2k6k%gP%??Ea-()VR-DSyY*O%LLG!|yQy3{u`{C^KYtwRrGgP}=D^~haWZ?1al;L$f+vlypXg=nEJT|2RbB5S=tQP_ zm9`%BRpnT6r6z@!m96S}7v*7Pd1_)fZ|o`vw|dvji~Q$#+O4{qkAqyiO-~7qp)Z`? zF{tUOz%dbvcYdl6j5+X}-na+2+#F&7)|5_9k}}aH^CD!b=0?NqrcsMlLx|6 zRpmNM>xYoabwswmJcSZ!AgnscuRnmiU_sEzTaaM}79dq(i%D>vmTDbBFDsX2YkX^;s=VDmvTD6H=pc z3+?UQO|O=P6|3#=N~%DX%Z}|OeeK6!uYb5lYz?&_@rQf(!}o>ut?9#IuzgSFn`0W) zE_EP?xI;=n>?^{G?ZNHxP#0D$D!W}u*!B-ltv}qt1pYCQ9PW`$lm^^4pnKV??7NBX zdD+kLZTkJN;+W}nM_Gsm8HF9G!`Tl4A>C`)Ms?`A=%FFhZK;@V7l+(;vHg$X+ik0K zVnf<(6$mPp6P5QkcL%RWidZkJ#}R=Mz`bl4(D6;ry=<@hrsvo{18MVXCAECFTugpw z;O!>)y-TDog+wB+hD8v&Q*WnBqo+!PX@ct zQf~K&--lH6V< zCxbio@fVV4H#sZZR7z?XNnYBS=Dr}oK*k29$=mJupB4`+>b%fN2Q?dxB!CTm4C?pT z)pwWdR$fsr!!br`cEKHKE5B2Q_p_p8sk&YA7}3Kjk_-5!j)($U-V=O~Iq!9=vf@d` zdjH7xvCMTeN+nAlCsdzk-abQ>J8hO2l4(069(;W*M@sqZ$qks{c5^d`nvX``&$QD$ z)8_u1?QeI<3nF7#{Q^j#mZh6z9Bj&$QEiP;TX~8CpoorJW=B1`qtc+1BpFt8V9h0b zjE2Ke?Hs{j8sWb)I9_DDGC!V3>4=v!m6jsTtYV}5?;&4 z;3m;Tu;ElS>Upw+BX6U!na}w4>o!C)cRLk>+k8yxi$y(W(r)6uSF$pV1IcvZCY32{ziI1LF9OBs?~M;ei&YN$uGFuY(5FH&$ykxcLDel zE+n0;r%QoVr_gnjfVVE`X_nMhTGH%mDbu*+woA!y<09WQ2BUaX%hfETjBcm+)eY3J z1+=j+66-A6k*5t)$kXW`B+-aAd=xi=SR85;(gVCt&AZo_e=0m~DAAihQE*sri9tKm zXS2#{)o^O@#H};c%a;C`5VES$7#Jn^Q(f(D{&n1tKg!9 zZ%tI2{`ltq3NA`ko1dA+?L5K`_DXVFh8;130^wkc9J*?r>9SVv=Sm%*(~iiqKbrDt>y#+ZcI|&t2~1|2_K^IRccn~IQ-_2N zwIAXpI0Em$p9Ee-E<=$xS>Wk(H_p==<@tiDHGaVsk3`rQD}a~+m4)+<)y%q&ytz$K zlCcOgWa28y=i!E#X1kcJMl|GwNuW9Wxs0g0p&aUGPGlaitmYa}oF{*g`9(UPyMRB% zvF)>oFyoutiArLf%U?5J#BMt`@yOT@GBt8#M^xhnianq{=FN?wY3TVY)FY#i+_O;* zYa@3l%yHU5#|I`(w;AHNK^0OsOG#yysb8ROO%@Q9%>9hIw9datpXJ!`1uAr$|CglX zz5%Y>zGO#}u0|uD*3RQ-EB2m>EPRJ1xt(85l!y?U-0mncxm5$-`6U&ndf#r-lq^eE z##`=J*6AJ>Vk;u~Q7lm1R^IV2RrBgwoD&^rl8hAEeMLB%S=IdgcaxCP0Y?cc1wTt_ z6aL6A*n_3Eia~wJIPy@;G$lUbg`}<@Bu(S7vd$ni5T{K;SH1-yxm`yR!Q-}nPIp!h zc^3^aN!Lsjt4lpr-KG`QYgtb))A-nU?>2lPj>tK3C4}8(RPSuJwm9&vK9Sklko=6T7la^WSBh=-pBUQoQW({AKR9%@FjcYfrCT zoW69$B1O$4itx4RxhrZFKGTJ-OMhy`OoeB=@b&4BteC8@a|Kcq8l zAIHd%1@mnZc)~MxLCn}L_bKB=vKsAlXHKn}orn8=V6I-xpu&6VZY|F;;G7g&A#YU8 z*dH)|VG}0!w>dGO{Wb|)sfnV~IBCsZ2jK-Ki}jAXdxrtW**+^TjO7V}OFzK^V7?8*(j3t$q}E&E;Lxfye?ig1Rhg1^rLb zZqQ~M3{Fr_C1j6{17TJ+#iAa`pN>|~_pB)KQmNkb*M7h$8Ny>aLfLYZeV`adK#fZsXTK+zPw z^>1Z>b}08#YBNC;j(6EFsD3p_iq|a}o{^@8Q}Wn0^nm=MM=Tu;E{)#%ZD~CFQ4%3|$vV8io~Ng_ zYAfw#T&ehx7Fy%dsjYbx=TBMN%j>uL^_?M7qOrN!WF&9o`5ZkQxa#MOp1snYT}K(B zB0Z?gG+FXv=kD`GR&`s^F6Fi{xJMyPyW&$cl_LCAn@HicV@i*>Fp;sf*#y)QIL-mP zTA$3=Dz$T5t0ojjZsHgsB5@3fDHwPBR1;AO%v2}yyfYS0Q+q&Bb!w|um)hz?RAVRV z+kd_6D!+x9S>1?-2~7aMk#o5{#!23H72?cY?j8iZq%)v^?m^(RJz^yP_A%gSkpYY* ztwNf#U`cE3tlzn|{*tzif}HGch=1R_jgYXQ*-hQ2$Wts)`Ts#gZYL9fl97H-tGh$p zSuc^ekQ|J2PfCXZCAlH;x?_UOff)mP$8bi_?LUu@ae0vW=*5^a&rdddev7CE<6uWT z`>VYh=7Yk98Qo=N>X_{ALawA~db0n98ZSOr31RH_#|n%YW_f}n&`~z{x}6HCDjFYr z)c4FlrQnBs;Xu7W=;3^yQ~cN-xpoQw9Vae{8~4bdcfoAUacFKqZE(fe=tRATU=@43 z#}`apg7a>#t&Jw01Tstl7ku1B-AC(- z`3|+V&*7e`;vz7&D-M4rii&`|HI9lQys8l4!22tU2yZA2uBe@U=dUg}v83x=w2hbg zU0ttKl=kW;;eIMhd(m#1Hd9`K#Bvs#Zwo6sk&dBCmhL_XUXv$SurN+oNrF0Eb-e%L zbQX4OEJ}5VzTb6z;Bg2^Y*kA7^0fNxe<~iVC72<5ZF7Op9OUPF+WJpqc8Rk|G__{Y z(6s(-K6zT4To|NQwG??s|InypLrCkQLbCQP&L+CH5Lr*8*+pYdd$ze^FAZ-f%WW&< zm|T=&w#$*(UX~Mca6spvE?0$(R3Xdd`7Dwa@>xEyEDl;x&xDjC}0f;zQKby+xw z+lj-Q+-qRfEV3*3$UVRx-DF{g&E-B{xU@8PN+If#MCCqG2%n$0C z;lS6>a@q2+79`mXzeMmzJKx&cF9G>TW{8uwJw#MbYKP`BOJ#6^t^uZYuyU<#u_zWD z_fgqi2HWq{b2u+$da#n0=dCsFZs8uXQj65o{OnXHgiKRgr*o(c72ASczFN)eIB4K& zhzA(Hz^PKbr9GL{9#+sjaQTKrCbe^Ac6Y-LKx=O$JC-V1!OLdt#(p5iOU8Hl=*TOr2yE_VChr-0=5W zvH%3~yv=34IcLV?pX5GO9xfIDb|lHnMVCgTNaB#Sw1<$vlWi9~*#m?JFTo5;HREs6 zvcrba>66k_&06jOSxstPjdr@BK;He8mmdRC%uA;@WBT@Wfc=uq|kv3Rkh z`toh6(ly0Jsle5#hvtt`XZpdovgPN_!azZIvvn8XokVI1tJS|sm{0!hmDSq>O8S?s zSo02zqBH-rsbRz}i4yQC9H0=rS2mSCdKD>vH z^}~L}WR54ccUYiAkDE;L6JcnK$UBj}CIO^&W8jFYoQvr^ED6}YO?msF;<7IGX0)z)4ue;zeWT7Nz|=f{e2ey1>ZTIB((sKSys8*|HY z*?el(z}Lt*gu$6y&Ze72$$O8u2;*4Mk(rr9?%%p;5ILFV9jpojL)$|>{Uu7Soo-b7(NutYy>M3puifG_$R zW-k3aqd-jQE#peIK=31j8-OHp0DlLj*65@cc$)iQ=V5Ls9eU?&cDwdw4M`V`#fTIj`B9CUzn|u#Mh!Qg zIBdA_-^(;66E~e9wQb9tA7Xs%HpIDn?BSpI*JJ!!&%e9)*TTOB{$0yIXZwadj$K3* z*EJ#nyIc3u)d;7`1y**xRaw$LHoOV_ux^urMS~!Yhv$k}v0OBGSeNG|d<|25px}s6L6v`Xxp>5oEqm z8_h4*^szLB4CpcZ-~gdmCsHe35zRh&j?1Z-nXi(8@@`o%r1Y`PkN5YY%AXg70pZKJ zvqr(P;t#gSRe*cR{X*-|^{kPpeTVmE`pe5vXvywK)&$|5gXhznJ?;YV{Sk8>Sv1-4 zg21XMR+K%3P=Fkt?Oe9VG$PV(F~671WnnT+Suzj2lXOntQlBF=laMv`aYJ?_h!+vU=Uw@xpcdsDmGm;9=#%yR^&?I8u7$Eab;^yTzPfOh= z3~;J87i12UL8LfAplL1&L^ffgevOpLkzQi z#+x3|kfzEz{hF7_h7U))Zlwv|_P89r2=0C1w{{ng{!FDnP`@rPf{-E!*AsQUG{=31 z01?_xJr`{tQ9_~xUtLQRI7Pa1@6RXjdlhd3R0gwO)c2KLKX2TOD7yKvB*h*>Tb^3` za%%0*|KYJ;H*Wa(KWq+C8|(_rI;v@!XVs|qmG*YP`*ZH=N%aF9q_$r_4rSI^!JKE7 zbT(<7or>kM_J0;wMBIf%6jQDJzHzkaw^ znL@>A#GvE~9)21=MbJR|k{a*WK&^;a>9_b(_lK}TDr-g5A8x;EjB4RR8GqXsmX-Q% z^0%yeURk-eTQ%F%czT^sqB2ppPPz`prfFuyXd*CxAx$z2d=5dWd51b`hqGA&Gphy$ z9}hb$WaS2b@P3?h4YSW3B5P0f5PyXYzw3qj^^Kos{-P&X^MD}PrcmaMQh%FpHS6tJ z&xF}wzS!yNZ!hM^O2F!ezuZ{U&)d7B4O6g9nc6QKTgJaqkf4&?^TyKY?$YKiZJcX1 zse$xnc8L6n#~sPpgn-Z*OM(EG%Mc)s)5QoVfHn9qUA{a>C%wmy@iy=9HeXb3noB;$ zbiIP^a@Own?JzR&I4Sx7AHM+JgMF1Qxso+$a`v*e;CgI{(G}V zx_*C(xBhTh*Kf-xSN5$apSON{X(_M9PI##_Jv5;aHy($^*AGc^G?d8HAA&|yX=XGrlnzaJH{W}t zg^Gc_zk?M5Ok=WnL@zVnc=8h41o0Qac8Tn1CDm0JKMOP4YS7iEhMuTi^PAcJ@Zndx zUM~;QL*C;RmjnNnA3pHF1BYMpU+nsQnfv}Np2EVaOG|h2ltG^ikshy@%Rr%}zOl4( zS`Wb$8n;3V(Xh+}9&SpRKxuF6O1st%crkYhQwI?uxO}YDiBmBAQfThE#iTI5pVVA& zQXk9TK5z598*KAks!OfvA-S5Z-rjIVnE4|ncYICL>adZmNoM#%SVCB)`*G5S z>QJJEU?#)e2t{G$UbsVbs~TyzF3dEj0v9^oPfMQ0X-w{=Z@)Lv)4Fy%QZIG&wBE&+ z{ww6zL=M$i;~H%^F3kKV4LX-Mw}hFW#Q{?y9<8py)nR6n!I--Ork=;cgVIZ+^J2Oh zX$s`bXW2Eun(Kfk`^?QVg1ZG$cK5Pl0|S$tJMSIeN1QqvX8z?o)@|g#EiAYNpnG{< zx;R%yl55Z5Ht(kZ^aCTrL;T7}Tn-wDp5ls3-=)M<9Wi4VG$9#86QKM7ozy4TvNl zkpJ_Xxp#LHg7*FMBYWr0ojG&n%$YMYXU?2S9~epc7kHs|;GNSp%7y`=#dzM*&ms;^ zqMh5_MCQ0qD=ga^TPlQCfzXqYvb`WoL5dZ4&N8352DxadFbSl?d?_8nL>h%No~c8C ztYSwR3kh({JbwYE(QDO|AqMoCIG{JUKo4Wkbb)e}b8?_*Cjc$lw;4GidpP-_#n}*< z6yRbzB8q_#Jo{r+V=J(Pjk~WA%Y>@C_}MuwK{r(xOr=iGur6+9^g(5d`!fA!?2l@qi--$rU zrY@#C$2geE=7B4&0prrL>lI2u#y#N3S-5k>ioIKbH_4UAnJx%Ecgk^^w6 z*Rl*GV*%Si9@qm&gy4_{XwdCURCq|Ok?e?44FIzSr_@L^W~&pkEgCb2DQNq$>gSaV7vzBtvRm{yhAfIw~7ivW$tO5KaNi zSU4YmNVDQ{T(c0GuR3@N)5HPjlkj-g08BhQyCjL9XJVXncS;x^OaBs*X>`ox z^Td(t$rmx;^1$0bI77fW-Al1;2rb|Edg0j| z!1!G<2R62R0_6C9GUWbR?p7vrA0#x;Vrp9s|H?)0LZpk3ipwOL=ClMAnTqzkh?J4f z(XecExZT4{G+Wuug12!0nhk#PBa7jRs*RUGDOTS&&-%mV4f1^Pp*C@#uAYGfbH%w43-zLHH_(41MYNDEG4n3e&JTJQ+N zIgQw1mgRt6(3qsnA454`ur^WI0;5K0TJR|15K7j92QbJ{BQ=*zW$EWQ@T!@4pQJ^ufTh%YdrOE@rj`tlZ`}8I+ zsYsCrOj5MaCLnJd&j>7HvqJTkPbTW^2uv0QF8J!79IKrUdnj9(J~+##~q zOW>SpZY2)7f`m4&4PkljlAZ<4`qw^EPZuk`2}e=4|L{HZHa_eAMsLeHMX1}P?hbKU zoJKZxuo581%+sT6Bvb(ozvDOf9~Rvum~x3~U13yc)QILUPNj%wGIJNB9?r4dMf`9P zKh&wVnuB^Fl%NGK78Gh>i;|ezW;OoZ1pgv>ybO^>RoLB~nM5IMNHZq(jX z{-dNv?(W|NU3UuWXN!*wm}d!2f9Z_VDFndlRUN{b{z6jbEMld+*x7WctHk%4?}1>0KrqrK|AA<|d5WG$zP+6tNNORv3Y+S= zAK;=p36oAEqB7(S77A$h1DdVl9F2nY9AII{*Y^!lmJK*}oenG^q-EC)eVJx*pk*pW zkuw2o#75wzjj|^R^;qN`;ZCd;FI&uEXFXT4gbg$UkjT z0KPBHw8!ylcMa|BHN|bd&E-|3$vn(UH28SM*op`@Xup25OTyZ>eAI?kaa%@UmMUZXmg738>{;a#tp(L z9@ZVa?XmM16QA8}_a0LBj!vcTk1zdZX8)pV>2CHkse7+Zbw4VlJ9VdhoxS&Dr7xB2 zuXoD+JmcKD4`uce#>6A<*8MGvwc4CF@Efc9ON?{tE>jO)4Am*Si~P${I?Ibu-i$AO zB1@r*Vuu^JJxuB~j*##&4|j%i~Fhdy+l&ITGWrF{cam zFWZUFey!w~AO`k7%)p#)@Eaq;mv|HTVDqRfrXgyFZ@drY?iwu6wUv_+@@i}ZH+eT% zz9MbqsqSmN-kSWp<4jxj$@Bxs+#B<@HDZ@3Z_D23%h&|Gb=f0>Mt)4h`w{1eDWh?u zQkPqBH^9q`rOyNYI6-23V)im}cEH(iQ_ArAA9H7O`q?@z4$DoQ-WSgC;YX?|qW?P8UBXjkH;V0LL9dSv=tNJ2^pK86MUuPd*G1>7sz-dz#}pqUU*5? zRwToJgq7U^=fn9|z)ebH2E6renmJfoQLtn6EC4AwTu4wiZm9%h&mcIjG1`#@2iga3 z32mD7DYQJ9Sf1z~;VWjCwwy&|(w4uhW*2QKUrlapDOnBq?y;vs(vHeLt_9!6o4(f@ zU$^3c_^2P5HGPznT*>0GKc^ned<^l5sg%3i;%>s_>v+zjDY2kgw*HLdu%_BmV&!hEwa6Z^8o*vY~qcgJXNzU?gW)3Kf8%lzb#^MH=N*Jn_3)oAnf zO`|o#pXRF83Lo$A1a=fYe%zCPxph4pa&2wd!hO9lqN*5`eJsDXzBd6d)>b4T^M8yZ8M)Y=-hs_kdiSnr>Y*PwZ`LFac3StzX(IS<$~-=O2-H5r z+c+@z2nY^>!s-3UxHP(d2aMWwWcr%|yD|e2t(bcnMxfQ^&XDi?SjuLk(j({pn1^_0 zK|Od7))Lq+ZFd>?Qw?Z3_G!g?iEE%9W&?Hp-B5UD;EcV$ zG5=oLnfhDx_GE1yHR@r11WOzby*)w4P|yh^Z6*Hl0PU4 z7tsC^u{FP_?a|9$n_38q#+y)9^ZD=;jCeHQ?$SQiW4J%178zKV%)miSUrIdSdV+q{ zq^2cjpsmcnzLs94IlD9cTOYa2sMA)QO80durg}?rcaMB8@a3qf34z_CrX~hHw{TT0 zSRl8at@0(90H<_zkAzSYpA>+M(_}c4omrm`s~==e%ioXm_8O#Aaf%B%^r#^@Vb!~)=EKawI$Jo74= zJvUklxUbp`xL)0XGwP*D>?z0t)1g+h7y7w95U;6C%3_rGCMtYqFmY&9512&JmO~=#(%(k7{Y?VW-(aXkwkSy9_RFLvWP9f4u11h? zkNigBa&W^ZH42t^lcwx{;dZ&uHT4R#h~=-Ns>CdDZ339!#fb;iJ>LkQlY%Y=hjrq2 zk)E$us$;b>Ro|E1#RTElucgp)9PKCa5mF{UxLx}wz(ty% zM8O2XoIwjW4tSzK`Dr!}aIhtz6|75y9g9_V)c|T=`!gtP4mJj>`=t01;MW$fZM)QSaKn~}cSFtIB-3KFHLj0%t`aB%jL;Co!G|b*v4?aM zZaPFrbZjAkNs^T_4X{upripMzx2hv=i;kXZT7uB+=GUP$sx>R=XLSqObl+Is} zD&aQOFx&{R#QCzc4Te?f#w|$(8~bD94}zt{T*WMx$aE-AAwa1^BJp_Mm?u=CfD1uW ze(XuW`oyzfHbfm$G&9fXB2(dGSuoQ7DPEWu`UE7t@`S|n)Pcli5mitECtA+s5UFgz z2Z=-!`YJbrn1Qn3XojO$iZR1)I%O#BlA+tOuHjZhZc5?f#QAZcLY#XG&gZ%~N6YyP z-;vmyO%y`av#wVyiquj(SMD*S`rj?h;2X!-Xf2Wu8*PIQ@uF^j#m;RB$BlT)sNk7W z+>eT10#_@0W&0b_?RQ5X?YoFE8*#eNCvf9xoCYW+3r;`u~Qa(3dJR{&9$D&ZI&5d#%7 z=a7op{BwY=lauOvCFP1*iO%!dOYnW&;hzZGt6+?RDgE|oi zB%TW#Puc9S^xIAc|DrB^D`>h3aRO^0nG_CE{t~)3f2q9dfSMCZ0l!57giK*$=?R2L zny78}H&L-Tz>b(Rr`|t$>H~kcm}l(A-;cXX+MSpT6@x)F6-Qr{cq6v$fK73_`A%?- zWPaphCSpm9e+ThVVdxeT`#hV>pvpWgT0&a11VG}ifqH4ZQiEqD7?Q|Q)c$NB*5BWj5 zJelrVd~h1vDQ4Nu{#L4M_Ponr(Lt6S%PMw;Ux)eAThwLPzwl8(br@AZb zWSr(bC)!(UI`yK@z&LE58mE2oZ$JJOc_ENM^Kn@8rz+)2 zsMu@G|DP8QGwH8G5qH0xs{t){(VGiC(t5`Kr;Vp>H*&4qV_5! z<^rHrgR5M`lu2SV#uT)o@KzGh$$1#9T~h!{a4y{-$iZXcw^3}UBF&{;-8(tqT3gFBF;Yd0A06hl=G+55BHSht~DrmpGF zh?R=NdvHC?y?n6`I*Jyl`3lQroKkd;>_t>7$%(`he(ER!WjfCl4=yaW&SaY$aaxs{SgN(fWBc?&8}pl zec&ul1NnlDq>gTVHw6g*yL#4^cK3@KId|fVtJuM^`BY;I?9agnxXCZAC8S3RVGhEx zK}HP?{8M1D)RAWYT6F{rTLU3L+>+bL@fnieraVFR&6{G>j`Q!qC6qA#8d-W zreDC!N0=Eap&O976H$335EFdoB)E(TTq-cfSyB%f=HkwSW?`l@pKk`;pS3Cj= zk51*}#lfliz2MQQoau4jU&8lJ<>>o{VVVfvVru zQ1tyc%C~HHQF}157>y09K=etYL0k9Xm~1Ub7suMX%kewrCtC1yU^C_xElA_4G2^w+ zS$LYuKbw1&__(={>r8z+-hOqs; z#K^x4s#q(SxSt99TixrE%MK$Qj052#8di`k{dE63^nL>k>DB@C=;^Q2=2?<|D{t#- z^1=;T(;v3O&c-a*jBBAGZ-f`zzI(w+^zu4yVnLH3U)R?&xIVM4pr`0Od1#6EJ?KmTW*{Yo zZ(2Pb57>f5vLSbeSGO$XYLg69vnwgFj8GE=B2JJC1;7T@tBMU&(ca~32p5sCAVScF z#D}FczMJ}&Nar{oWDii0I}u6Vy8CqkwKLF#P05oekl39i5Cb$?DyCWV8iE{DNJguL zcN_2e;bGdmJE(OLMi_~r>;p)yuOT;Ja$8955(79;^(lv{H(||c<}M+rX;`#QU24fl zhbiD%sZx7WXUiwTi-y0s&Lht9^k!-3N~#Gu09klqvA3Eo*yuJ8rnvP`K({2}4l6GW zCL2%&rcsO3xV?iy;0h2GvimcrJYg4x1JB0smc+!sV%l$UmY%EZNil~>k(7bmnSti% z=XLoU_O@||{PGoXH2{2Z@7h{zb|LT+CsI4;V3%${YqgTKY?R#E%-m+JnEP#jrE#aD`n^N(wM5mWl65&h7Gt!F{J^bUL;>x* zY)O>JMmzjwlrp8O_hPXm6x<{v!l3Ody-q^*C6(<|&f*cwJ#M4LcvigvJZMgCrlSoYIk(kSYd zgZfGt%Y^Dqw~bUW%AvUkNs@LkAsk>)ZW9>}gaE!2y}^FU(aNqy8f$q79~~H+8sAKi z0_*bQq)SZp&f0G4QUS7s5vaE>2bPt?NTtIUtR8@;cH;&^dYVle2faGk=2{_cV6eUH zr6r`St&xzi(c0!wDH%43_O;@>%q7g>>`Up;Kw6V<+xjckqya|GVr$YcBWH;Y2u-%9T*6z`3V;)XrLU$}|@GI9!K?>Qs4uny-c>ii$$ZyWwTK@rVJfXQ#A~EEJp(Xf!IuAYi`-aM+CbB$!jG1x5WEXt2gjPpN75nN@U3=EV)e zDcSB$4o9kRYHYB_v*tbtSj;GVlvn*j`$k0nar6hQ=VYdTru+*0`TY zM!8eWn`HS6h%6VgK&3GrK!Dlg#Kfr(s4!CixO#%a-sa*A#06e4$EO%|ZJ*o zaknUN6d(lmG`53WM0CswFJ}FH}%nf3z3uhd>fqgjW?8Ry6fWs7 zCkBmPf2B7hw3A!wydgnVnpKC#JyVRPDYS!Owt4|-|0vGg_qr*e*G;g2z;)l1iS!Kt z76&cXf)v_MJ29bX5@GuW9dc|=aeNH#7A@rqkk^Z&_%{*I)4fJeZwzGZMg^>-l+rc7^j*A zwWfGwHo#T&ru1I}Wv(@=WXJ7l?s8E|aF+{**jK>WXk}ubc&4OZi@+lKZilvpD1TKDW=vwRv6~)Lwzj zS8JTt<@0P1fgo|}2MyARIjvOquzY3o^(h3&*4RcIuTOEAy7WKNKv1&nA4Z?g!23 zN+jE7V^u02k{Qpda~PjsXCOqR4mAwGOxFML0RJ|HBRB?1i^Um}Q`Mz^APV?QE4>B` zjeQaHC%1Ezixf$4BGJWSvV=uLf#P6|T?=G`G`7o+5}8Uktl~AF{#Hi|N8ih=wCKi2ohd%zI#l z1EvI-n&6>8UA1PVCWXfyoyAx=$P*q1eGuRLJJ{C{7<<$jm&F$LCNu0SR0m8F6ZC3n zciD-Bh#Pysw+>M7`4-Dn@LtrQ_0ScOWXdycI3LYG5)A={ZU;Nq*t+k9)YKHIaZOT3nmb)L@3j_ z8}pY4$4eV5>1%c+8X|txWFT<@9ExM!u$guxUfRg{AiUSJ9v1I|OJV6SZ^19^QhYj! zv@tJ0-7!4~;dKw|#YH5@|$6xCi{2tIQ zTcoyU?pTn8@}MIxy$w%j;a+&-DJmH6{s-a;?~%B>H$ry~%jMg*z(#%7_9_~zX)8l~ zQ1vb}fa>nm$$

^tP4Y!OHz)Ntnz@IO75SI%I81FVnij;PA`CQsG%!v*#vP?Q zhCxSU;~H`GY_7i$tBsGX5+dhH^s%15`DUocGUrFJ3XS~xd)9jOH^AF!jYcgvcYyD3 z(F{ggHdjrUw=7+)A$6eMgLhRWGDe`yHxvtOT2UyGgh!i+n$|@DpObk2+6vkbaSck4wUf z>Ay`l=6R$7FDL>Vczb2y2_x|-&s$kp`>3{HEpPX%$q=^Q!jx_pC?f-JQ+ZR~$Ui#n zp)jzKEzV`wr;Vt8tYttl?^CXu>S>ujdrL+A$!^(5zu$KgYb4`A2^#)!oJ%~O#9^ea z^jjymQo}K0tsh?}lPf(xOK7!Jjja;zr2uODM_nQV`xd=)H3B048wsTpDQNQbqPV$9c#(o?2^VXU zy6#B?i`kfJ-mg@_7SM)9syJdzWo8>44xp|J@m2a^{YbNlF?h%zH7CaXCh(q5QF)t`3Xb&U025g zy4WoTU#r<@lgp_B5IBrS(XzEui3=vgXlA+@6i+wB+<#Q=VhT4?_b8*wm~-Th`&icd zC_L^Pt29C98=v17oi+5UHeZ8(NNVuUPl_tSIo{w*_}LlrBneJWQaLH_M3OYD*5pv; zHQmd^vm;&2uGGO5;*&q@nYQy9QKFHRRKT#vy$5lU%FTWCyE?iCnYb8E>7PYVcfnT@ zjK-YuDVR;L+hpkEq>nL{Ls6E4*(I4Evw>W#H?Eab>a_WJu0%YVtjr{dyy4293QUpz zQ4;7%zJNeH=FE1-+UvhjyHwIk{nuhj=pNn)8O$2b2xfF1n@m%#@FRr3o;2Vp`1RLR z>nS}`zeykpNBm1en|Pap<}^f2)oo*@%Xund(?_C{)`?$XOtO&_f9c{WjSLs!$VDkN z&8n{@PDwpftR(Z@$Ui*+!a;TsKoov}r9$LC(KF_Y#KfJlerIW4mB*pKAk+!`4XY)9 zmwAC%Td?j#WQP``r6(dVX&trgqmHg<^%lr3X=Ui2vJ8DmAfS@c?Tk>`$^%$wWZEPDxfo(q5nfG0CX460zNqO5bK4k0Zrd0L6@5+% zMM7Zxy(S%^YO}S8A|n4FAvKUBRQM3IunESiqB>5B*?$7_>G*}Q*i_w8CGwhXLSiUo z?O{&gCMA?I!3(h{p0yVLGc2cnO2c5mmX0QJOGA;#B?EaSC)$c^tAwjObd@^jVPPhW zT^c0(B;ghti-jeuXeyZsXV6AkU+pz*MuumM9N$Cy9i=qUcJ>;Cv*=eVHLSH8=}6{y zqW$+%nXQq(w>aQUV|<`8o^M5drx;@c|LeMjnM*ZC!J$1H`6V9sOV!#-OpvnD12APfV^Xvz2YE zKz&i9%bh zS;jU>|8iC|tt+aT5!GN*o;TugnwWUZxieYsTqWrePpy}50&APRj)j@+bu%mP_$i}< zY4D;II{KAeAD;)po0+$)JgOPh`cAKbYeH=J(s>;69MBaFiwx@Zt?dU4+%|B1YE7>x zdB7=LMs^MbXTQLe8O2gAsHnT3a`t)AXiPj_#S3YSLu{QW@u=*u@-UOOAnaUByaMILl zC-+q}mxt$9grld{jlSX5GZZ`8Vn^DMSOn4n9#*pJkcG6VY41M@YXLGs8$bTPRv$Zz8y?#h|N!-xsFULuA(LxOPBijM4 zG<}968|D@vMsdVJGd2O)9&utP!oi=(W8D_35%CD&Tr+fw%IXVJK10f)OA^Dnzx%j5 zM|PwBhHli4n!2v6s))l|zut}ZNmHZo?KI2bJ)DsA%n{v5MolgDO9|$G&1@Ct5_8bN zR%bm)aIvE44^Vi55PIvL?mTfPRMQEs19CL(nLSXRI6M~$4>DM^+h*~-PcxyakL9?UV< z-(ko?Oura0i>RdIHwyW59MVWgVQMm}rL4@$-=q#lqAV?(z`N+gbk4Oe)*qa0CF07$ z@5zyR7A-}CSgml?$6{-5qm4b8YxE`QPn(Ds`FFmxm+~6sE6QFRZ5q--m$nG{e zcLPOrERV*g8s?-xWU_L~%A9~AL6Slw^m?Fllk2D7I+UL`5i@N?~Xond33tu&t(_fdj zdZ%r;y&_Y7<*y0+^_7LSRGai~Kk1%Xp#DKZUwTvU!kwe#j!GU?H?x6Twd5b(VH3Cf z!@FWV>b_Pahx|KG2kTEF@#efU^M(%orQ2gqaD|^Bp_F)qV=k!3uFE$f#KHLw&aQ#$ zp9O&0&8sL9Vq5-YK$3Yo(+(n1XZ~vvdqv4&xI4;H^)=yrQda~U-6DJf2YPWdzEMw7 z;OwHjzG_EVIYy=8)bc@I4W~Sg7ni|1 z4oKCX%!$z2^dr-cO!gtXpp|07*^dmG{dneUf_|FqN#NuW8csi%zaGK0I~bQF=}mN| zNi1Rd5qb}<|Cl;4%B+>dR(-PRFr1$Z0D&j>ztN`0UvaqY5fb+zTlyJk_R|mBj>m&N z_BtMrqS`$&E;+)hQ%sp;bsad85}qMy`!sVf{7$B zNKG!yGhMKB*qAvu&L3#Cb3XeN`TV6&L3n2cex4Js+R|I;bEfodA}OxUIv~7gcm>j+ z?Q!SxAClR}Gp*l70b6UwRm}VolNTFC&&N^#=GVJ>9T}d>$~+&+J;9dn@cdaoWb-ii!shU2bl+^u;@#@)TLxLO!jv4YijS+uC3{h+dZrvSe=k&}*& z(PVNG7tl1Dn_Y9i<1MrMXiOHGxV6J*w1;1wei%r%jgvaEtnC0EWo_dIyPp%?54$f4 zobWIRY8!W+_S?dh4Lto_co#mYeeXZIdbbZ{ts!Bgr?lVoMhPo052=Imd#9*zl0YZ6 z8_(Iy&H!xPYyLOsLe}>8f?@Vj?FF9H^5aH9VO+*F7F~N27gn=Pa7qiq_Hsy@*KuQc zKRbpkB`Z%L7wl1&62lHh524t58Te!hCrv;&{tWRegeW3r)6u%b zVe)xI2$w5_IwGbj0$P|fjfj&7V+BAHEVP}r;zt~YTRmm~cb)y8w+|}wngS95x~d#N z(yLqn+J70$=VW~<%jIJP&=`HX#KZVJqdW0%K2PjUJc7?7_*{9igX{hO41AeIn1ZP{iT9!c-)wuN$1#@|q?F2_Rf}3zur85SMGEK}O?q0<;%$7r# zQ3=2*CnsA$LUePO4t{p#H&E<~!zoLfVx9Tl0mTX}xZOPa9G^7MBS5)T3yIdaP${?- zY7lhhpCok0f#uxWXx4C?VJ@#f!CFoUpC#=ILwaZ4Ct>5-M+gz~U#ZZ2Qe535g_}ww z%fl)U&;KT7%6O9N%r7@aSH0pa3UTty!Q}m?D9Uc=-L8}dp+l2hNqMN`35TJ$HQyk_ z;oxVikR67S_CF5JTqDB?Lr^R94b5Lf?x-aB#U{~a%^%rq*fy4 zOpB?uJYrDfVMksu{S-3~H;$~h@2ue#sj@N{#JqX}h*bxN^JXQn5@8j4hl_novF4m9 zm_>CQYf0h$eBK?rOCdUl-*8?-{3X?EXzo#{{0s^*eCwjyl>_-=|2CX5>|iUtnWR+y zRf=DEN*uSe*2UfJ;?7ak_c!rDX@f}Ph`clZISLFHGyq_9e-lrlHBC|6>B_R;8HZyrmq#Yfx=)RfwT`h4oqb}72YpNl4P3MRzUG0`9H|k>;4fg|4<^V87l}~DYmU< ztd2o_$v}<(v(YM^#wA|jMT-eaD2vRW zSvI#^Nmy9?Xfvzq$TG03{*Md51zs=Ns%i^fC5f`MnfnFmC^G}(X9$j_tk33_@KX3O z!C|Bt%=UgW^3#j^QEQ<7@S$aCSR9(7?`{C$?Zc@wMxw zA72bU1@ws08mVc}QbnhhZr~aD8~V^>%Ebpe-x7CE=hn2)IeKtqUj9CO)>?wo0YPrs z<6?U!PXfz$4q{6G0$_#aF(M3vIS$iWyHV>`&xD4H-s;I8ZhG1F2WkP&N$WhN4YQ z@Osr%8Xu^oiy1b)-O-h@A`7FbD`5p!JbB0`q!GsDLsZZ99k$+}ojNmCxidJ4d8tiu0RFl+{x!+%VMTtF=zx9gz ziE0$C*=frkvM=V(p*(YP&01(nTe^k5q#bJ=QDJlWWVGnE1IaOENo=?!ZY+}rtm6e| za(Rh7czsx3%ULjdaLWh%^aBQ^SEX<*F5s8vzp+(|3ET){swB#AfFA?kKG%A5{E+f= zEeLxqYw6g1!9Fj46AB7BDo<`jAf3BaScS;y;_eJ)8%LqeVA$2iBp}^eV{kp5VX65czd-22}V5} z|IzJ+EzuyP&* zRzm_+CR5e4HE43xUt5DFUHwUz%Uwja1ocrgO$;J>RgH%^{o!?(Q(#|I7`?|=&c5u7 zx=va}SEwQWqdC@UcE}L}9YRz=yyJJmAGIH;Gmh*J%XDyY$UbEH!B7Sq4~N|0n0^E* z);{W^$Qj)6oAfdR*M@-Vu@ha^wE(i{OLXmywqOM4Q#%qe&{&Z~s$*KsghQqysdrBO z*}7%oi;QgyyN{+*;0NoC3SbMAcPAvkzRaf}(=bw@*`{b3Kk^K3-;AZky%I_?i$kjw zi*n`1q*AGK8-y=tZag%X4TdYMcqu`Rbo&@5Pks&wB={y?Z7&26+FsP z#oJ~~Mvky6s0gPwYW|!v(56o8CpRozGAzT)GKDTQo4b@sv%wWSBU>wEqdb{cYzGlx zPV|gdQl9xsnCW3-!88^c*Y)sSw$;)fSE=E9tYOa6D9AWW!1$ZbdzT&b==#bL}VuJSB|@}x?y`Egr;uyt(>J(K-J4Xgs)+7|4g?W(pdsHPmo z1#eoqySKsdTUZ?Z-+Q+>`h!bJg?kawELV@^FJyvbA0VfaT*xSewBeR7OgH7v;3Ks+ zy5j)IY!l{Qq{<&hSX6N!HmH1YxREEe*SWs>iqx{y%h{-(zS6W%tTB&nsjF9@FnsSQ z#^B8c1MK}$V9I|3j7zL*5ak+}BDSYsT%0*pvYZ+gQu_%nJ zJ(H)_O}@eNH)+K;Mmxa%YJrL}a>s@f8=A*(FuOF}1k^+>owv-|Y$??ED5vr<8sk0x zV|L~6K*Ou_O>IEavzR%h#VDDIF&xl|3mzbSTW}G0#d|5% z#68)DbdMI)b?b+G_*N7RQHiyYs;mEk`*O2_w`^FCW=;oRaq$jpi3C?d$@t03T`GoP zJL;bQC|HYyMWd0>`jj_+5^>#>c*HBElsHv@*zoq|{!Eh!tj(Awr%0+U(pc) z{^cHM+556AxeW9`?8=+_eTwyhN0iDWt~x`w7mQKJ#L8@>(y|6a)>?~~A2MRj&of+o z70<$3XpslL7>&I!WyhS06uoo9NevWlW5(!I+$DIGox!6tJEyC9w=3Evel_jBYT$R$ zK;a*-ouL~Gmoe!$L00bi3Z^b8BB3Q_LRF|XqbZw`Ngnaq5#zC1#MvZR*bSWV2r_VT z8a9%oc0eeFCm2a3Oz0r|H=EA`^8(@+Fw#=Z!noYm{zTq{;=A~Okz_xr&8(lfsc;)D zOL&sXzhC8FP9U{UQk^D5CAH5|?5!Hd_;iWI2(2;XO+d3~TwxUrDSQTrxm#W+pi{gK z=7ud<{Z;!D96meB1c%JqCagO7vwAf6m8Yea?3A^IjcAxuDM+WQb!$%;l?lXzZgb$g za5J4-yVq+HlW<~Vwq^+p?zjunU{Fr5a>tPVl$j)JBcZTY@Y7dg@bzws95&dUG#5*1 zx>DPgLM7{(c=@cQOqJ_*m0$QG09TNL)y1H0=qmIl#(nbARXB_%t2tTmur(Ar zMecdR4ROzTM9#Ldo;l1Z)L2h)T>s1mIw&(@;Nn~HtHTh3`1@;vmy|2o;)98^^ZSIHL z(zZs67fyxW!E(|~MIQl6g!0%&KobnjYrq zB-_orVU}*d1)E8(x9)~tD#f57H7@KP-AUmv0o$oiBZGFb#ohrN{=wh(>r7ImQvJ0B zTS%iJ@jQ}AneokicN_qJ%n7irE^ zSKN^nR8wDlAHR(|H1z7bYWG+8l~#EDqqVCAnK$oq;2~@8Z9$$8W+%Wzk`**@+wVh+ z$_AS(Kg77Ne>dAWdTb5t7Le;%ZmbSiUx7+BX;#QSG(YAfM#AcYqvJ7Lyx z7xT`b+~m~56fR!->FGGQ3Mwbo_c+;b#qWj4eA`fF-v)Lut8+*Ion zmjA@aZK0wb5kmX)sBXAbrzUuFUxg8cOReWt&muK*v_@1s zV)JkP7C4JseC8KOZ1G}+=L4y~+Qy&P^nYL#-OYPweQEPXS$)F2H+QP)lkB-kwMh0X z0s6ZzzwSaV>QTrDD@48F%{@+q1pRprD+fgyo^D{qsGf*C6578z5!5^W9rLm7wl9fA91!9vK8vLm71vsUnb%fAHg{$>Jhaom&8{2zf?Oq}qKZf` zWEb~VnfwTReuQb5YwDxgNC3@#!{)a5cx8g{A(FtXm4ANIN%0lCK&y#c!n@Y97CjQ} zE+?G9UEv>{U0n@lm3hrCAs@vq&Lz2+zSm6@0%+ffLh6ToCW-}bP#InagCPK@JRQdk zZOJyR7M`RfwD5|!dzzjgaW}dm~{6_bjV}S8n@a78qidT^U|HweI2@Zar0t z*>O{uhi&Ej@sjrrQ~LTR3Uw6C>DOew&TodG3X*6zm;&sEy})`ic!v5rjtuYqywMKE z9vU*fB`cxGd)LCq*Mv)zyY*evqvCkI;!(l!L8YX&)m3}*&(oxgOE-~3ZBFUErh6!| zn+IB8IAURu6|Q~5vBH@ESi%Y~coSNfPFT43^M>kpQK20iM>8$VB85q$u*D5qsX!6d z{CrT(NK?H-!rUGWXE=p#F=D* z3$sdAGiq(5VNs;R7oqdQrd_H^GD_UYb2g}V`x2nPwxAzxlvrlMo=Al?u}YDYUYrMh z$Cf%k1oKFUI^4y7GATx?qHf}r`qRRk>WHgf`v+bfnO@j~Od&#p$~TDE3H~?~;~f-D zw*z>OLT{na!Y#Xc(sK20P^LT%IXRcM*+?ie#7dq<2f=6IOcqo)aZ^l5KNZep#A1Q@ z6a*0O-^q0S_wgbwfB0aIAz_cIHI4JK%I4d~L2`>BYw!|>Ag!lq+i?pXLAXCRcwr7# zOAI#l#O|5D@#`2~qr%O!r}lcw4rs|&V2+G+E_a1iYivu9W-cGkm?GM5_dXssh&UKj z?d;8&VJ2h?`>zS{kxA2>m z&w26SLb;Nd$pXiJr6lBRLSU^`8VcdQ4nmqI=ve66CCRIMBzHS$*buvAPySNUhvU_U z;QWJndu@KQx%eIJeesutfD|)ug-y+G24x3uvfD?2~u<2-lt+sw!5$ zU;I^`(QqCqv@)*aOC$Atu?yWsixW@xT9;m*c>~^zae;FHCr=@FXegzh;a(qh=2;MH zQ!Cx94IAz)k|py(T+rFoC=Z(7C2W*mwLL|g)jX!IPd{GbiQIh9bsXrss~yz0E4k8( zj`=$(eriHdyI?ZE$Ts24Pec6C1im_$saBDwkKftL3+{J(PCJ-xddojH0J1_d{t`Q) zQ%PU9^eUd--9J`WS%~IM_+S2ZrL@Xx9V?Dx&*P-s=whxQa0?cJ!dB4vFJ>c^H1NZ$ z+xwET#yNF}YaTvOLu9$|c^L^y!F)-TBQn{&U#ffW$uX1_J)n#(Cu5r_Gspq+Ogie3 z6?EIgwOMBxW>Ll3@chdN}l1<;f#JZdoEChDJ>2{?0tT` zt7n@&M||NCWisu(kWzRfnX$OzMi-FfM{(>M4@6Yb^dieQ6b#&e&Mf;Av3?j8jSccq^Kjc|-H=^qFEAXA389MOo-}%L zBw4sdE_1xUcWS0>#Z+1y<;+V>x+=r?1lihVkFCuILp&yiTtHKk+9`6 z!dq(+=ymDd!thg+KP_&02#Bz2__r;^Gjhx^7I3clXbMPJKM4#yHVZJ{>l$ zO<-_E_Bqkf!Wd0E_k2&e_N{f(32_qXR-5Ig&I&%!m3ME?@+OI;s@?%E`bRyZzXPy^ zCyjTV+LKbJQww)AB!Lb?S6blgB+!98fxzsC(V`y_494<@YQvxJ)$#XUB<$?2Xwiq) z$URk6UMBa^1>Cur1pJAB;#B{;q;OZ`E;Tl7ZkLLE`C88;|D`tE$0{uHcO|WJnSXY? z+OYIHJ%->z1R|HdLZi9r%U@SnI8}L#{#jZAU>EQds)dxAhN$KN1-(F<3e%xX7E*k! z)aNz&+$$mUTdFpwfH*Mk(|fL3grfUSEfmzpc0c)nLKc?zSVsQFxpD2n&9r z0a-->tY!49_=QLUosVGcF6~%`h7=V$XTH(#6ap4z+%@@;pE;;(=Ue_ey=)#_bjMSO zTCv^Cu>yH*jdS^@6Hj)s)?2ntWlDbe?Q+($#UscPXb32k@^wNAyRw?r_o}5BD<0~5 zlJ}S2PmcKgJ70j4eYv$z+03Pcsd$Z`+{%dtmy70h_-*A$j^Dc+?iAKK&R}s$oY}2HCM~J3u&;N|%EIAw3zz#=6<0|vtBfwu*WwQ9adT;CH|7{PVWhy?3l^l#7 z;?5H)W<4vF+SXey#}$BXTwr0cW#C@KxxJ|w6JCDbN%OYh<2d+cIJk4!t!q8syt8-h zHgC)}+YoX$#cP^l-dJ($2VJS1wX?U({Fx5i4JlnAjmUprju<#z^lEnE1~pLASlqza z8A#hm;K%sRL@u)pOWa~4_wahnQb5VIm*gWvR6pO}@BFu!*Kxw$fB(~(g|T2Uqo=R2 zj?S*J66?R^W^X%cbr|P6#FAVATj+n7zGi85w>E@hDvZeN^4Ht?%h5oFqdLi&L>0C) z_?>fR9%mIETUz0Vrxz>C+#?DpE@gxax5|qAmmD9qF4kTYccWn2rb;9K;o*o=;Blu{ zNqA|>R#JAnnk*#lW|qrO>JK_Ogwo8&$woRQ!(jBcRdQvv-;NE)LWN{1LH&4oA#j!Yki=roZ%SLzb3?ro)6e(3UlHW}f$4XddPp|0*nq#ea(Abnl)=+OA zYi;@J69A>QWM0&u`eqd}iItIhAsanxWlh;^LRb1vsWqt=v4hV44#ws!o6_!r|AHHa zoKn(d`Co|VVNRG6F!{&q>)kLXpz>0dB^AepE&1X7;KPA(TYp+M?j%)d6_W**-6obyf#x=KUUyDBhEd(qo~CC zb0l>9{LEht-PogyPwiVq27i^bz))Q^##=U-E*-tMwY@U6#%sEyl>VS5!Ag|3ET^Mi zsSRFmJ1M#e)8U}waEeKJ%TlhC;2P5UM!YG%6@{Z{qBan*W?m0-`pp{73tv>iU2|p} z8s;_;$<(?_ZkUdTgmKQxdqioy)c7( zs#r>i$geG__&QZ=1fL|1CO(mkR8e7+YgE>7!1lENl#qb2a^=8n*kadNczq39{)KX! z&Hp!^=Jyyb>tA!UtF`A%$Oqk+FYKjbVKbbG^;-@vp409x&*M0b@mogak45s1E;(6IfdcE4!meveami;p0|rFY(N~Qos;3k_!042gmdm_JCb6QZo+@9M8=#x#phz(Ri+yF&cLlKe`ky!HVUF;lyUV zcKGdkYnKWb?;QKd+A|dhs_2qbZL62w9r=HLGnPUFD-JUI?%yz>-WR^tj&bmr^*sxG z%1}rA8z8m?=kW#Dyd^De3r59Z;Zos`S+;2*X$=9YNPWe3v9GWap_$oSp18ySdyCqK zUhkWnwSgiWRFY&9Xn`{@Rpy=*XJspTDQ)>`PR*MYEyu~f1s3q@^kwwD5wB08jDV1E5DX!TE}!Jgg-fwF6!2j}%|gE7A{A2hVPl z-%OFH_6So4^gmc=zmYF>Ko|%rh5ug0I!4U;YS!0kwM!?_zh;xkt8t!a%H!GGV|=s) zuTr;Ik2B5=>!TL++hHWP1M_}+IV9>R(R+IC4TP86-~PP@%6OjK4Q;`yxNJ649a%|; zbZ0u4SVXUwH7$mNBXr!=2vT`(_|X%_G~U zXwkXHI&~f9p~_RCW68lCyym}cCTI%fnslDk9Mj_mAwe)#_<<^^@>eU6tJ8nQq=9OU z4`F{JI2BJi(@<+g%i3-N(b1w4s57qQNLjPR<0A6U`H>S9xlM?KqVL-e*IXysa$)(& zY%Am6)KwGg29M7(I=Y_I9FyJk%DdVCQ|9~t?LTvJ(LRphW8hK|WSFz33$7rTWj6T{ z1Wo)_F|K%th8WY(ROzbT;RIQCwUaQ%2$vc|fLL^Fcjd~bm;5{oG<@^NQL5TB+}ds< zQVRQGn|^$l*72N9VvaGXZ8^DgS}FO)9VU=+(n;Kcn{@dg{pu0??!i)vsS9&(K0tJE zBp7)4DJ2OlLEy}X@O!G{+-j_tgdYXd7;gftnv&H$l#c>!lTzlk#!cN;eo)ztpo*{x zuZjCe7;9U|b^=LRjZbWHOt|CJp&OeQ2XCtQU^DU8Wmg4n@#WhWvQK=l$7}i*M+@E3 zWMJb!*T^)hfo+(6s&0Bt5&1u1g~_6_ew8aY`(g9lc22~7&Yq9_-Q2Jy)zN_I0j)2S z?be1@+UtxeW_%dk)>ZgBLeD_MN8ztVmnyh-yK3VCM>nrH2lwe$3qS9~fI!BSJ-Wcq zXEb2cTf@MJ7QJ^wk#eutCSp=Igy-efBM7SP>)6v)U&L$JXwf@lVAJb!Bz8Q{jivsD zQ$bm@bUROML6jq>YVbh<^M3y@E*EHF$+jnDqtf&$)wQd|8Z&<`{04nvJcYi>p<`T~ z1U9n@Sm&|u7*03a%=#l*+;bW=OlxJ4-gFX8KHFA6B@^i{xg06GjT5Zogee-Cy^uLT zi-ULfl9-H5HZ+Rl{Klalbk${=z4?7v_N8`~Os}q6naxJDGrjH$cA%g{;NTN;G)SUTWISi7V-wfr8UhL+?h>Igy33|c{(NTSg)P6 zeXz)$oe&{*919UogzSDs6#0WC^?w?cAC5tc_I0wwTQD>sKP;)%_sB=70QeJ8es zq$*y$q;e2&HCXv+(hp-%#Y!>_Sen2YusK!Tq_MsBiwzc#IMz)5_*?aqxp#mz`Kzo#G;My8o zfwrykJ^{)q_GOcBk#3KxVrnsFMI-K+gcQx$AB{&hH~b2dy242sYBmTs7Y~?mTo-ZL zc;D&G|DhIKA5Vc%vP&_er7(vi0ztegRyv``q%=(|4;_rAbDi`S!Fqy7g4Ci}r(@*c zQO)VQmC;Q~dkA!sQj+&d^7@vI?Q?EdQ~|ZoV4n5oC;3cUR~(4%@9u+GnZA3(*)x9- zjkg6+;~};>GA0zI@6KNhHP=_C0W&rs3U&c|Ic!z9)(Gk%LfKz#arync)Ohx5wf+RX}kSx?0B%s7fEW%SjB z9dsL~GnLw;0Lv#aD_XRpJKv!n%Qs4!4e1T}xtcomorli)YH=QV707zl*oj#S-R~y% z;wZWDJ1Db3`SCx)xh&F-+UQoMrf9My+^K|(Qe`q&gIrgXZPTcz7V!8^0?R7liGQag zlfMnFZox5Hbac05H{xS(T?ky<^+A%tUD`OwNo>%H;2nXo)QvqGy2Hk0?X&QLL@7gh zf6^3%kHXIh-_NMK9*a_q%hkqr=Qi(u^o}k~b?frN)k;<(vx^@|8MGgn-SO9Md3_;C zGv+8fU!E5>lujZ01 z7(h+3oYW6zzxb(jDu<@uaZ15AQDy+HvNSjX)sW!D@j7K-4XM?mk$yGb+Hfc;HJ*c( zP|?RX_pPoJQ<+5~3p2j<6NTCBeO9EY^AW-YnC>BN>TPRJ@c!0+YWL4JD>CG94Cq>K z{z3HC$Z5A;eZAK-m{)K9mlzQvr(J#1HD1%FX{a~<6^5AOP{9GD&;gb{{Q7$@_T~=| zfCdtWSp@x3u>j8S^VCF8c$?V?KO6RL-dU3MZEzxTl$$45Kq{ArF^sGfVo}l{UDIh35xo+Dw=fJ8PEMvem@d zKCI9}Or^$z{#_Xu&WEl?PP=ycG<>ts9&i31fqmq)H(he@n{eiCFs42%Jun8=iq5>9 z+F97`IC!Ng+UN$*P!<(A`2`THEqvg~j{$8I$l7G3d{pHZ+xN}-hD6KqO?-FvHW|)h zq7lASv@y7%B;xh@plhXqV??aP?z_-njQU0ZqxIapT%|WNl^V|5C(IXdAy>-y_BaYr zo&71i*!-eQ(m-c24nNdXv;ew#-sIp~UOUk(ln*>dO(V^a>gqJtTsDw7Unn zZsov8K?_~_BPSu*UxSTqnesVE&ZBvW3kS#g-Mpu@k<>LD6(q4({~@NTS;$vU*1t@r zXH2&JqzPgnsp#!^b~t@{LtzcQJ#v-}hZi-TrXu@z!85%2d(Y&SN*HELi$cqp>Y>Q! zasSNVQPLL^I{VBhI1j!glK=a*K4k@6^fU76Yi_yGYr0IYv-BFA!)xJ7`tDyp10MGU zz20>FwClWJfTB*;x5P59Db#p{<m#zM0@_XXhJc`-~RmZB-5WOOjI*-YEE3# z^GX*eAZ3?nhO146>GBpl31`H>%cG*Yr6#XL4-o{&OFss39)NL`yeI>xq!N_V1DkB!1Y%9Iz)_f$G;CvNa2l=lDdAdlmaw0$Lfr2e;PN z*iOcvjQF+pU1b(ERvO#jo0V)JL#XlE>Mok?jMFNIwg7vsB`znNh$lX*5GwOuhlMt- z738v=z*S{S$79wUf9ojhLe`~s3NovTUz6*j^iGN~Ly5RLZP1G;0FSX?0}Q8>c6}a} zL0qdzHSzTb-KAF#Z2?^%DxL0|RHF7I_ZcQlYFCp+s!4w+>ko>}+>RFcvunz_+oX#K ztV#DXX@9J)|7AzOX){*u+diPwI$7MRN;Ho(V& z8Xu41(6gZ@es|3b|NDP#=FA?T{~mG2HS-nTx|_d@ugIU!BkYHKQ4iP+C)8Zo^%rY$ z<5qP(q!A90Lhd{Im|fYHUd&5b#NFXj7IxHzn8U~1K*K1Z!SFyrQM~rm`s6<4fQ{Yg zrx%M~*JT#ZxPZaJsi$=H%+)9}BaGKXg~hV^{tso%dZt%~8%>hpX8v3hJVg5kf>|ic zZtIoaR-3NA^$|M;*YQ_tUsVVdSJqbVZ*x3$?tHvfoU<`(eO2fzS(v&(VwN!l@xduo z!Nxg<$Hzg~OHK}(;3_P=1t`kGif3_^kga%tGrqbV@w{g%pp4o~)txWXF@MRv=(kpc z<#l8BWM1od*HBKG{(Gt04i;f{WjClDVtGJZIkTg#YT?Xxap}2X;CklLJCBJf4tu#X zoDJPq){U4q{b>A-yQn#T#S)TCb;Fu7mDv|NmSxv;yr2OxyRxq0fy@s(ene&dR(u%P zd5pMSWYEM?Pt7|wwC0bCuhwAOe-&-XAM{@|Ia3*)e`B}HwO4*LmDJjFx82}q_Imam z1-bg34xzXovuH6BS&SGuieslSeVAytMf z?@GnFrD{xi#gI(xarXNioq5?Aq$#oe_d7c>+dc+aRSa2h9jS*vIclcuJjK+%gm0!2 zncHIPY%^oY zLkv7gI1f=qQWn29UnOHn%1X^7GVF{pvL3$FZ1_YQ5>Nl%N|}gbNCO7mIJ0 z-^P#(b_RvL7_w*}OF*Jbo57i!ieolr``9L_Y@psjg$&yh8rKRHB1ZM(yu0{_cZQPi zMmsl6Hf$0fC7RoD(Aoz-;CJpRAVPGu2EhcF z`gTYzJFZFtJE^P9j_Rnc!T_Enate$@W{F^>pKO(x6u!jC6KnPh^(w5O8@(|W9>OcKhx@lEmBcTe$x1q3?FJ&1(jF zO#m?dd0PzritN0+Ye;t9R(q++&f8`$)!BL5?WHC=uag(qjrNDW3OZjjb}`3kjm>+v{rYI4CoM zD-G&KSInNoiNtc91Q=5x?!z&vk4RXX**5*P>=#L+@F{t}Jf-b6b@ahjlC} zwv(ao2JW<-)abY{w3^=zE~4`xTc_uIa1jDa$Q-llo`k@@Q=19^Ilo*C^Gl z@V3bT3u&xm!Xe=#{Qj;DCsd_g3FRvUNi)%!gIcsE0=;aL4;Gg~-Z)?1vo7UhwDw?($YA)D+FTzb8??A4*W8+Yxt zyi)G?>CF|<=sp;_VX=qN&5iuvMu`s3v@^?o)_WFjh7|{z?f-pvEs1I-$#=;H?lOy- z$~9&LG4pgS@XtGj60@&+%Z`lBPi66Oufw2TQ?1y7>V9eH%Z$LN0t)0P!9OofExzYa za{0Rs^X3gvE6mj#`WEO?d{V7jlW&zqPYB7|&XV(D;F1JG~iKnXR4W*}3Wl zc_MOtin)S@c4uzW0!!Py6Wg(~pJmvC8jA4!6ArQ1IK*{X4!Ly-S0hq(#Pt1?zqc#% z%M!fb+E++z{aYnhKV)lT)XbO3z;c$&ke7po2yfXz9lyvX{josaTwQS|w@=4B2zOn&vgzyDsK<=g!K znExdHzvFl1<-A(VavOS3f2C&cWVY3H7pd0H%3gD)i5A?D?z(RhADXDUtOculD?uKQ z^QTGI1F7Imi~Hv2-7yvZO`9wHHT|TwgZ&PK;gxBE{Bl9Yc_ zOaH=8Ny;5{T7Wl!j{o=F>IRU%%d4L?bE3bis{Tm7wSQqQatNnVXz#Rd)2AIAy`Wu`d3xzpJ|bbZ9w)pI3Ot-N3AIA*%v}kE{h0 zmMcSgxu36qW0*5FyR`yb`kjY+^LHz{$zR08VZFL=VS(4ApZ=@lJqi0~zlWg2t>b?T z|6k&N68~;Gzgn$JuWD-$g!Fh>p~+gYs?9*856cSE2{Dm`zBLM$!qB-mehrsz>g1y- z2DyTvSojZQAiEi;W5aStsjTCLbu9-VUa5S!+p=xAK!VjAETURvZo5|&L7fh|Y;D%f8&|Prj zr$%E+FQ?mWm($%I%`Lf{?z>dQqP_vms6^%&x3um)2m}4^!$ww?fk@sL>3z6B>dYU* zJ2omH+K#NwQq(CH<(gI4&G4hv5|Br9gB;!0B%!S>od-VbPqyl( z<4oxxm+#sYTzE0%Ju6kOBwrMMjrndaffr6dH7n^8hsvy7Xv^!U5 z;F3iL2cFk3>UhG1#E{h!9;0apCu?*Y$Vy%GkpBu1ZW$3@>*dyFH2y#u-{YVY%gU3< z@yo4!SWr!1l&Jw&5EtLZ7T;De>$upK;+tk7g+;+5o4{i*m8a7V=1|2 zr2iife>G@Rnoa*h+D|G+aXJQj2xW0AdXG9){#6VhW{YNBs>P~^)~LaSBh}G`$|xrc ziU1WF2HQakqdvyL{iN=A(UJ+3-O0A~NTv&YIvyp~mI2t(3YVp`WnkE)60Ea8q{QFa z-tTr5v|w*MTZ&=hwOC%NL)i5dw#V&dUz(B&-_#JXFq&CbxPni=&^O9`5=d*6@epex zDL<)=-%-l{piG?afC|=A{f4%k1vI({bRu;9}?%0Y`H88f>5lgM`9kcp&7rxcD zbP{@D=U180yR<94kw|s}M0(Goe5V4X>t+)i`QkfkfEKwKNVu4H)db zHE6l(I$SOEY7gr|sMuevv1i7bA8_<4ij*vFE$j`%wsrPs=u#WjD880T7L2Scko2jZ zWo`9aj&ftZM_J#dtit)g6P@4b_>$XoMg`ZCQ>NKqPS`^IU=BM1B>K)1x_e8W^V_T! z#46e>h2sJONnvc+lPhceSU6D7p3POu(HKU(l5mQVXiK=C;@`GuFCm8R;*)-@AKu;e z?KUdZy?DtaU&>16q@aaprbx9p)}`7oOak;uFL(%|L@`Dp$Rzl(6(W#CG$-(-F1ibb z66O@Du6VlGW_76p>PUM_+FUq}?({k~>D|sy1VMR8m&> z5X`t7pYs;nNqsJkL}i87G-%aTqKaZy^_=^@gQ0O@lIDf~En_H>^p$)6N-kp}`z7h% zRE?7Ex%dlw?yx>jWd=By2hTZXzRtPfRUdbBlG3u&T~^3SQ_^a@QPT z`ylAr!ZW?Pr!Vo5^71DfK)m@js=|kfe;>OOUOgKc@l(Hat?y6 zky5640Y(W%aEz9!XiOqpyrFvFUWzImMnk&_tB6Xv<+Dk*e7a}1lyu4$AYRugI=o%@ z7AyWD{S7Y0F}s!(rbruL-7D-5BGRQiWzONQ&3?YO-+8n*Z*8%oq4cuCr^$y#XX#Xc zZCoc!9DB3$(aj*mPCCGFG-PT!=e%2xZ7>j>tT21 z!flH2BshH2X8vtbK}mEEFWH(sDn!m1zcqWwwjNyoftD3+P{t;I{UNRkrh&^{;9LK5 zO5T&O|1ZA_D5p1zk0kF3zTf6Q9KXER_?GPW<>B~My~eN2j$b9&Y%owoTrVAB{$+JeE%OOE=5fpgTD@7h$QPi=t|*4U?V@D-C^d0{#O?c<#tkBFB< z2{Gs0zX(vr*`58dI0ul3!6CW4ha~XdqRvb9wC+Y$6%UY3wLD%y{Y8U0mP(^>TV2cZ zqRYOB-EnCpqh_f|32No1)XL4pPvb(mSv4HL6<;0)yRq2xdw_B*LW9l~WJza`G-jb* zlUB$sl^A46s!64({$z1tH=5f@Qk`PeZll_R!UM%OA1Ib5Ix9(8M#^Z?p@nOh-CeLr z1V^XY?R#Xmb`jkEShE9eE!DsEDz7I07U>KkQnLR3>lc0y-% z)}BJMMjnWjvMd^B`>Mh(h<$$jK8Urka0L}Pd{op=G8}qAKZdKy&|X^4&iOWFxXzUR z)OytkidiR?uPNwy&7`~~j6pHRmw;8}sRMe#G)U#aGCTJzG!nYAkvcrPrttTeT3n+_ zspY-4eF}&P%pqBQPj=lhyMLVgRN1W=MbdORg&T6#lhZUt>_?5rKlc{u@YZn2-S8ML zS#G$S264~wqrc&JxBoM8cy~RnCjRPyIfr5Dd@y&+;fE(|oXQjng;z(7%E4Qeok-Az zEbKP-&Hti}$lTXP{()rFSWx&yUys8lCOhe4l8`#ITuHK1lfcg^(@{6anfmH03l~{Q zhv*!!HnuniW5!R;S4|B1%$fw?dsKUROW|B{M8DEk$`V%P}aPd zvff*BP}!{&+{QO7`wjzGC40Z3pq~TH=x{Nc!Ok&l+dM^xJNL|Y zH2FxrHuCTLciZ2o3>Tf!zpBi6zzpX#z-z=X+O9+KthdYD;euOl&+O zx?uqalDUdQ1Uzu!=8h}PSY~T#w|3=sSI)U5%;bZvJ3ot~UT@jNt*^ANEMqR^IQs7X z8)5~%&;e+(Zj@WcE!X+C&)Qpmho9b-f?84&QDV!2%WL|!P?Fgi?8rQmbgw+-Tr4HJELEl=9z6UdGoq)To>lxK!sjkdBN7T=kI(^s{|;SUkwq{#>OXQ6;)^%0hSAL_bpqKgSa^Fp-)O7j<@ee0{eQT78}O>C zYu`H|QG!Ny&{Szl+gP!JPzx20rlA&)jUOe7mMAKEY>%a$9&N2=D_VjHD?4PlSb$r5Y3!kJv_=>fVOhXgLtAmG}1_bFG~nw7s|Y-sgGW`|>o>e}^->QP1o~>8KZJaJko-rOk!BXaEqR z&1`kazsl2lls1uD)0RK>Eqp`&ZUb7*xetTM>W@ZkyisbRSyy8R4j8SCzPD6&mb|N7kwM3jvQSHk*E)nnf7@o{m8mvvj%c!7sO-*?xT?P2*@xHA<#Gv@hlx|=w1De|^PKt&U0eJhh7 z@*MopQ*RoP)_%rOrsK$>Plv3<%LgXR$816wS=_$7UZfgPhg~ghxZM`FMAX3+BiC}A z3u!Mqn?Aux5ZtC^4%$8pf$id{ z|1+@7f&!Tm{md3`>$HJ*lUxfOEbB&w2%3BN>vtW~iPTklZP3)E*JNL?X(tbr{k2nr zrX7~FCurKGB+RrYiVRsAMvOHN!?Lk;eMo(fqWleUrg9FFkX7{&@9*y&f(K`l+Ja%? z#HRN26fJkTb&u}jFh4O|)2tPp!Y@5)$aTEQxiZQNmhLpqmfxjr@|Lgsp=SK@wob&= zUA5_#$|ew$%W-E(!)s8a$YIy}VtHvn<-xUyNW~S0LS%v;w1I7oI-t>y?#;-o>)~`5 z->yXQdEmFZ+&4jVSwH+8>3Km(aDB1ghi}2E{xTwL5@z4WPpZxDBca6Ex!-PhRomUl zw%T(myAqA}>v?3lM|n#l0g!5J=6h6!Ydhi67+I9eR>SWpN*liwSt+ZEK62dNQabX{Ke zJ~nZ+pS0NTEIHj;6XQOf$9?Tk>>wfC?4$EM_e)Bbj%EcpEWa=W<*7o6eK zMpcZh>*hm8E`boaCnU)meP^njkR(U+%0znq_JN6XCJZ5Jf(H64pG%mV%EShPEO@?I-W9U}T2X=|(&juJJ|j!mQkr@To`Vt73y z*rX;oEPa0X=;u^3wf^A0X-O{7(DJG$-ej8Q0Bni@RKDw#??XH7pbj5>5SG}xDsFyU z<`gy0kq3OdZ4ukoAyGEbcrSm$<)?~);4sg#X|5p)g= zqmu>0<)x1yWYqLzFN9*b$|A4iLaO}RB}FIJ*yOw-zh;ivsfsVF03S#$Fc#yoLmpSFN* zh~hdYW$t!$vff$+e@+Z%`YoDi8@njVALRd=TQx*oT1uiyFPlGvO(2|iF3RZIPq9yB zGgd1Z#O1O;()(wQ^!w6#=Y4_dlRbY<%x?WNQN>VX{$Uo125Tj+GmG%dF}1=u!kX(( zSInEO21J49u&3WNr1n7`8`jz5N*+Jq9>33H);->~3Ek`dtPU~g{I%;*t~Tqxw_7^^ z?E}PUI26O#0~~my1PD?igSv`fp`sp|vTWhqP%OP2kRtE-wp|asKQ1+T zD+#n&B$1~dw9-Y zgsr1KOga&k%}X8UfxgVo2vR`K-8|Mw-X+P&F8AU4}w!2VG*2 zmxv`_GUR<^shOe{2UG9XV1-abs7~QuedpJS%S{F!HOwdOE|Ot8X~ zKu!+j7TOM@3mQYs6H)Y`)cG(2OZA9~-qteC4?4+>df|CucJD)y=$-mAlTbpFaST1* zZ%2_1IA66W?%==M;NCct`h=Q}MZ&%Qbu7}{&_7jtQZE(vXP%~eL9XnGhlgpx4|NOc zMsJaZx{z$Mt@Ttf2VsBCYmtNcZeH(n(=1X1O#PLRF)pYZA0#IRHK!7Wl&oC2Ci=w$ zc0C#p?TYNKf|^kf#1eZswfB@huA$H0v-izj1H(b zU9=MQll9a$jKIl5`RMl@)32SvslZSU3^2mcB2@=^K1YjKt{WJ(+&mI+Rd=M=}Hb31zk2!k~szrm8bL=tN}6j zPr7x6M#zwOQp1@%gQoP0^dNljA)w2CRnupkb#mkXd?#H$PC-=}KKP)jIm%5mJ3Bci z^M@^Nrqz`a(s{C?3f7dN6DsWYnah2dk6}|0vR|>jj}k%sR*%)AF+MJNR*%M&{$b(~ zLo><|fAZ=^LoQ3H?U4&=YHHw1``*xe552G5Vk<&%So5l1vrRjXEAGcc8;zhi)~LVQ z2%R2OcY*ei|L6eeEcZ4#+5l6Ik4cDc%yGJ@no-=2{#Q|r#m6r)Lag4QQ*c+T7R4me zXMsPxKI|bGYOO*zheE93)O-+Fx6449VcA z;63duz|<{&j@W%(Yc5K6i{Y zlse0C2h+%Z|1WHqybBIOmtHfXa!BokZc>O}#B2j-av~={o&K|f3SvB~(%u?_-gYe! z_MO;y4cAU`Jb9W{?S4hp`700N2ug~fHr)tzK<0Ll&Ace*$MheoTq0SUD7}WJV zcDYAGt%E6{_l2pB!gXDlmeR-AHs8lBRn3EvzfSVp#GhIdCnmS0M%;81zg?-an-1r9 zXR73;gZbT6J4r`9lC7Bncnwo$a1F;&11Dab#vZIami+|K+M<+A0m)5U(Dx*FI`2An~ITujw{Q-6a%o|AtiPI|B65TtSf> z8&B@Rc>^uKan8~e-4IiJJNMO@#p;4*;r zlc(y~4n-)atKG)w2C$mZcDvgs?HOt+B!%eSACx65D7!@Lm>_f}xJSfZ2eHq$O@7UP z9c03>y>Wt2WMw+mE)+1puv9JNEf}KGH(z(-FNM7ziAr?8=8|Rc2^QH>Yt_*^-Tbi5_VDAlWj}-?G{67_&G7)* zksL)L(+)h)_ifg9@Ic?egH@@%g9ocn8~z7+@PZ5 zYLaTmPu?EfVOBaqP9v+B2z%q94O^AlSS3fM8mZEvsv^K&!gfMXYNce=KA(YKrYSOn zrI%@_N6FMY2H3+=A0Z?>g6rWp`A;sXnm#ho`0sq}NUC~%w(2MJ?obQHi#0B}x=Tav z=G>Q6gTA;Zub^<5P$>G-W(7oy<{fN}A~$1D!5jF}G7iGr%(dIH+@XkQ=7R8ow-3U_ zPlG(Qv}$^VyHd~Fv=;EVvUr9O#VAEZST>7}cGS-{NrQeiwUR}>J``a(NZ#%z@9aqG z$O65)hhhxly&6Wgr{1|gM@xO8?OU&}h)br9@)lrvT52nQ^7hK)or&}==B?}6C=BRd zHG{_gLZ{B#=ZH5{b=50b*&8nxlr_tOg;&vmSW&(33VY!w_}U2L$$BsbcGu=(x57`Z zipDBFUmp!srsyo$RksE;t7I5|65(Db*}|{xZ?vjbxvI8`89s0cHj6vl_G5!4qZ#O2 z?2`V>gRdYDCD#Ns8+^+XB-c<|^K;Vu+v;jlq*zKOMsC>ewK%{Zm8tQEwy!wWgPv+y zL+>k&d;s$?vABKfu?Mj^av^*u&Czj9yqac!D~C@moyIE*i+A)-4k?(M7~RF8yzTHy zCau0swy!#-$EsrojPDpdgf2GIMa|>P$3MfX)#eN>GS6PF53e0-ADH5qFA(0*hCo=S zAeT(*_=vE?4WTi>?ik#vhhXlTTA?3#-@QchZn2m?+Fj(ExaBd@LhszaI1^XY&xHDU z0n_5K%r-cHmLQu}hJ?4*@$tb98j`pr+g4O+{y8#lu|~qs64SsK+M3Y22>DKPOIL zS)D#Ekq#}xBL3RR^*aUFOYhR2uCBZuis9-?{_5(=^jFChE?>^^0Kew$tYSJ01e0)# zKA+pvLpQ9sgLxCmfd0&zzcnHr%;~ZdpyAN_l*lvLnw?{BH?$5d$bLyvbh@~fh@dAL zO-BUhYQWrR;`1!bR@U5!FD4iZl6Siz&&G7)2>q6aB^2BqOr7CAA9<`XSW$$=;je2^ z-a>hFn!zXAEM*I(&g3V~GvS%PG7RIUk8?HresBYiQbVwQjfN3-{@3^oJ$1w_i>0p2 zU*a;Z)v*8-K3J4yuVN=*VT`TZyH8^Qc7*E;@k9;mWracZaNttMu@*(LJMtiDGa?_TR8F``oEIN(4qaWFOC;;zow zAZ*>Mu?#(rAXItZo_SC}A1|PF>64pk*^k(QAPFF@5T-e|ZZg z7xE5X85t9PlB6A!}_YGQ&%$S&#ru(4!fr2u;r5eE{MFxE6jyb2n6y1Q7R z@uy>wzxiW9(={YhqG*V3j}k#9o3?3sx!hUW604Vp%T+DW!c#kRvy`vBFG|%=(?>v! z=-4DX8Rt!78`d5+Gl|tRi>3Q#13MY0b|8WVW$KCBi}xw)0hV@7eIpC)$UMADn9KyX znLx9s-3I@muO`xr(;I0w&B|ooR1*e!`9BhhPO+pm)ukAV06AN250s}@^3bO z6dm1+MdTTo`UjDwP=s8A21^_JV2QT+KvxQMNPE(wm`i{*v}@neLWR_uSkfz+G|iU8 zW>aOLyINC!Vw1M?CH&3nwz-Hgx&az=oN<-5@~nW5 zBw2iQdKp6d!*^rK-ljqNCDT;qQ0BV0xgL zO+>f~y-&=yyaV+}&uCvN-4`g)s$N1ZJUY}LimV^oyE>Ac!ej657>RQ-RS!@pCwxQi z-WD^#(T!R5G+Vao(oy_Lc4o$Me(mK;+3=MSMIz1$*NL*SY7eKw2U)IG<+yHu7+qpv&lwK?~-J1}b^%yvw0hgr`M)V4xltdxY+FezeAj1Q=F+kI|h zs#-S8O`O=78h%qkFRgmv0u_p?!Fza3E=wJ8Q<*;A$y;@^^PHLRjAd7*4UjMv56;*r z$pGyniA@e`?Ul5uPH zfe+Q)f-KRfQ`rtd(SY@5#C(IW&=;$ZssYs>f}oBf1&{*^lyxtDZqeb~hxK zxaC|+Nao?E?>``rFO%$4_dggIxYhUN=C{pd>!LBBooeR$&ufkbW{t13`Ly6d6m$O^ zdh@T3(9ek7O7#vynu9nY^koi5s&pjHU`6J9J$)ES$Gxq6H1w8HZST)RuU5Z51kSHy zN(JKb@An^yfI2cbyX+DdB=9SlKd;hO9A+oDZTrnSa)bi<>$D7g8YymXOb|` zD_w|NY-?HZb2M3iSJ^8iW7@`Se`H<5IUn~s_r2Qo#=%4@Qp}^`G5jeS)7FvHf{1tZ z?dPsN6jVO6WiH;)pP5Va!P--+)^=QhX|(oiT#HBHls-6D>c4{29<1l%=(*>@i#>cH zGJWp@_|tOuIZ;);C-tj=k9eLFfsosJbJ^o=O6W6-X^hr!J)pJ8to&d$PF)6qgwN9> ze4ahI*BoNact%}v%@WDm+Stv=X;iP|LTJDJ#k#%3f7-jYlo(HYUQTwuc=ev&)n#71 zdasn%8Z{=)^o*mOo2XvRd|Azqeloy_4@5p&qUfmZQmdPoye6C~?^no6*^=)>b(|5^ z@z(EM9WshLNaH#>nHGL~ejSOZj%%Yj&W!4~?|?cmX;x(B|H76p*XO8sOZym zX)TMzXUDZ-xz?;toU_)J zHBo&>!bUJ^ISChv2(u@@>IUwbsQOz^a|1WYRD2C}W%4zE~c z+-MJAWAtZg;+R{q^u^*0FV?-rn7(FX+VkSoJ-@5l`Qp{DIfpLG?14x{psp)R{YI6Z z9W}rIm3~v-cd?{+*MJ-?cynl5(2KYR)%%%Jl=4<@~{iaZkhzY>yF!JAcfBNnF zI^^7t`WC-Tiqt87e`9Oy==_2Hj6+MwcWF}ajf>#h3Vdc{wjE5ev@J7C_Y+4b=;NyZ zofnn*Y*cCq>Al}W>W5+EWp9hJ&p#mhKa-xl+`%8YAsS`l!vGzBo-PQav?>?#p2W2% zO;<@>!@rKEYoaHC8Pl|x*mwWTWDogoM1C93HN}1#f?9iiRVnpJB$r{)fFq5JUlASd)Oq7CFtg~piOGZuuxd_O+C?*Au&h7GJQn`1$dB| zzRchbf4?kvNa{cVHjSDE*dMFlwXp#ojmmg!l5^Jg@7-nAcejC!Sp6W|m&^fX`#SFv z+;PpCpbOz63%pzg#PJqOgJmlsAjpwI9-V4G^D8;wQt0vDvP#H|CKi|d2%;&}7L8V> z?x*s>JplvDMfJ5zI{cUF8}0YvR;GQ!_qgMcT`OCT`q8YW;sC~cGSl)3)<*@K^9p`- zpy2rYf>B)DVH9Uce?gc((ZKrwS-HWr$qFWWs!T?xoy5TmcdAHJAS&<%1ytL&T&=~^ z)uO8_t-9ECT50d~A*rfhg@Sa&pwyl;0LJpcU@U$)9}E?W#lN^W0~aKOGHqrDQ3%{xAzp7FQ|0N9ql4G}M*b!z&GSBkW=4 z-sH%l+Uc@5_GJjlM|Wglguj&YWBy=tJvKB#CnrUmwdAr1ovO0EUU2NFhs@g67Zm>a&05?qw%&K&;EDh*ezoz5qD=EZr zO#Q9Df}Groq~{h(x$R1&w3x{&w3G%h82RfRaqViULmR&h2i-u4{k=c(_7Ayv3~K15 zdzj;{hK_|fhO}^iA!V;q6D~Y(av6u=c?B>Ik7_$+Psznv2kn|ualr6gt|Auy$HEe< zsRf3y>kQ6i^LXY2E}zCc>9@?ZEQ?Varf2bp2S%vk&9e&M=VESs<&mcKG^}r!wH!9p z(-b!vljglqKdft*fl=rh2$fuD4R`?MC6{rsSCCXD7bntJ^RUms&r>2T1^k33HhrHL zj*lC1GrJMr{5ZrLae(vWF9DR+kdef{1j3H z#Y--wp}>a3uf82a5|pYCWhI%7PZ5j98X-nMP23d*B=P($^@t zjk})tmA3b``G!=>O{~y*tD)X%u&mfe8m)Mv(u`mzUfry+59r$3vFnsCNZwP(NyBgk z&&@LqS{aQ%Zb&%vRa4J+aF2IQBfmwu7n9#&|84#r6d0I?+E^W$tUol_cxbYjK}+7v z6^B&GSOo^Mm#rW6q{8-Q>W2~jzA^f3wqG~8!?p~oxsw}~3qy6P(7^MO_Y@J9d_+~< zJ&C0+fY*KCkFT6xbfeh9OAd?KamwKc)G{@K7YsYg&*KH ztpPCRm>cWAIR03iqz;ZfQ&MJ!gI;ukn5>`!V?X3%b`fS%ow_G`$9r5H z`|ms}te9OpscJGe;k)C%MXb)j4Q`wW#T9QPr-LNd=1JZCMpS1~UDSuscc8+el zAj4e8h;(6qL%JJC_t4l2zPfu;TeI)7obF5BDU{Y8vS~R#*&2arI5XU0Q8qfycG2(v zbN(_XH1TqeM76U!w0@!AEy*bSjK9x&o&DatYa=K4YjJq5{TIGgZO|sQwhD=YI5fDH z+Dg=;S#|kNw-VhI#<74{!9d%aX2Z=1j=!E zMa;DC8~mB&o|P?9r>3#(@;0fe;})y}Ehiz&5zxG$x5xE#)IZSExCe!`=h1@;X!S!d z>3SeyjCydp^#HF#3>2;_2rHa}8i&qtD!!VY-JjuLJbuBGz_=6=0LC90jM~~)uyyrc zs9Yu`N$n)j*W#@VbNe8Tz%$P|YWyZmYtU`#LJ`-HE)B&7l^z&n6X_;p{z>wt!dzCH z{(Pe9av*+h(MLr4m@O--a7JA`(J&*R_9wSBjVjxWfT1#!u9RJ9Y>~ z-T1`-LRs!$vi0S6pR;{vS6(aIT#{?p_4r|uR4Ln%7%$781r~)KgwS9GI5Kr4Oa6uL z4-0#jX6GI7=|+8$hGGRV_(MV!sV}Vgf4Ri-c4-8;A}-+|W?Bruj%V;D?#06*=$VxKsk_ zeoD>Uqj-jGwUTRPvu?T#@Pb9s%du~n$-26>xrTlB+O|wdbMp1D=C#IFZnY5ti$@uh z1Ov|8yW5S|N(u`{zf>jF8zijkc*Ze6r%k6(dBO<3Rc*Elb)h$w4;cm9jP!iJ-wv4@ z2%2N&-WV+H10ozT3Om18@uQ&yHMAnYVILz5rfr2%90mmBN{+>xvPJF12heAO*&DaI=1Muv(L{T=hUi^JII>n9V7cnl=CM8Iq#(+lWd*0!85F% zf{Wc6TbIv^N~k%4?2)H|jKe?pqWqk@{d9nx$Gi2YlwB8atcA4)B_`Ye*GPw0IYQJI}Q`l#n&gwLC%YloK6WiKa}y?FJG z-_>=#c=hwxH~lRv7#&%=fNznUi2l*C0cC|lxBWXj5272NqVpJm@?ceJa{w((8}VhUBCu;}_wX?v*{R z@mHay?>DY^ys~MymA=9Xb0ABAsMsRe4yY?G9C7^N4MgjSge!dk zto9}H%iBlyK=rnp(8U!vBjL@Np`5nVeLIWHhcP_~$uU^e3OwX*+{CX7U(7fZgsCo3 zQi#!w7nEezb*Es^+>x4a)91_wcg#)4%Ln(mV+QJ9M6LJ~ z;&9;2f6=K{y5KU-L%rgFa~6Yr5A6s+{%vc~S%rot4k~Eas;-$rHsEMfi{dYHHK&AP zCip4OGsvqgC^H*860^sGmf#^nfasR*UjHG9#@T@4^$$xlYAfXRADU=X+!C+9G|_mm z9yY3QApz;_p}6)i_fV2ZSE<5OISxJP@p`Ntf&WbUI6Yd6iPdL}jGS65O!S6(FyKvi zX5Tu+jK(Z>Mg@2Doy&2)#FD=Ngum`e(!=HBE`?ZIDwGFrh|pVeo%u5|w@1;j{pS(s zVzM%Nla(<&QW-@%)&^ZxEh5a=?Vd;J z@-$x>qy*Fsq(MqO7d_Q)Sj@A3|1$n|G~CW#{R>(QcemcDe96&1;z?=nfSh9o$n7=W z9C4m8T6*#a>1G)G;gihXa3Y;`Zt(-+pgS1y$wy7Cdv(K8+sJRcl$ps4IQ$X&Fbg4u zK>}f_!(=+bD$A8H4s zn4cfIAQg$AO>w5d>rP-_Yj`aI=?-hp>-!N8yCIeGD6U7-;n{9KeJa0nc4?YUhhZac zemF`Mb9j6nV)0D7bU^wJS3m(J^xZ^Uq3%+4dZ6xPI>L=lVnL!@J!SWi7J3;CSz74M zo++AYQIm3Ba`h-@W`wJxk1t$H&0oxbe#=!nbfjnVmpp@@BSI~yVREsb9;b(vMlE$M zBX|zhsTi}d`92Dvr~ba-DO74W>uCbxT8W9xL8zKh!10$5;QUo9D1La7w2~gpL*UBI zczX1h?S5FUl(hchpI1Hvl^Ku6+Ca!hkHjH=PRx;Foaf7ajbeN|2ZxCPq)?p^Kbbj>@NGhG z%$(B=)|+NS`C_3beYx_sT)|)Fx_1+!`%Nw-)2k(F_d!?&qBxV(%o4B$U1uep6r44Q(eFN=fp}PGW?uO>F8eWI)phd*f%=JT2;H-w-yMZ(F zSsjTq{|3KBTv+q#GwWH&)022}+X%&bN>A3u4zHugd;Pt{>N+vBlB?BIXR8A>%1}Nk zGxgVQ+18%N>92`U6MsC8kKX>Fi6(KGpk<=kSXd8Z2$wIo!1%Umkr!KZu4^Xj_e|2n zaAm#kNVf7qnK$0v9fua|pNYOG(Reg4=ffYgR4Bhnwg_Gk3AohZ zQq~ed7Z^r`-%qtW3@ONlzJ6U_b0~V~R|va0rkl(E>Nbf-bm(RdN@&#FqTQk)+4o=G zt3+y@!DHwhJwh{nCeMltYKy96GK5OJ%~g5(R;sj8uCprRIvbDFwdBB-T9m?1usrop zUc;f&CL3Bh($gpjNCk?7nKsm-qiHeJ8ouO4nI3204L9&k11+N6ZVN8xp-;ZYlbHDIf?wIC#O*|N%m>K3)a*rcNsv?{qHk)CbS(3-$I z(^|=|@b8WHK!r!Dl4O@vIFx74dM(_r*wScavOHl_n!Qh}QmT9GI?(`u$TYl0SUJpp z8oZKP^5KL3$m7vYCzt;ZPsTd@n5+gy@u@8u#eqrmw~5fMkT;Q5Y9%5H?hzq=@qu__ zauwK(rd+0hDC&an--PkV$A#7RnbiWyDRpvEhR%gGVipc#Ipyg|w)U4cV z)NK3xG~40C;+!)~Rp&sfs%VBPVq3A2it^Qzkpe5F!({E|qq|deUaLCMU~Q79@A7a7vfaCJF&V+NUv%#pX|~|EjV5l#QIl< zrvBuHO|IZ8t{~qStS@DiTM{$2pa*4MFZmw*jsg+();JW|sw}VVGfIkv5`&U}baqx2 z>Ah!6O(wCrI#aa7y2GBP;5yJ?IFOhj9k{&6E$E=a4esIK;|k%%{J%3}x~iHaJ*Qge zoV+*zq1imSoyWP#TW-RAO83ZAkqi3}*Fsg3x{&z3v|`z#`5ceNjLai=*=q(tZk+07 z(2*fiyR=j$cj|zA^$wzahy!x?2zTw|C{CFL)#Lo?PEI-csjWfvM8CQ^HL=ce8wV-{(3g;!;0@?KaVy`Ym0uM$RJUrI6CZS{ z?$MTc6wF^Vq7@<9?S#RdWrq|*yPcj4j+#_vHlQu5oTjsc#>3^S$rVWqnRgy@O90Hz zx2qj{GN&`Y!B~z5ILz&&QQcYRF!vb(UIq z_<4>6868pu$0DFTg2uqtphFlOM-{dO>|LQc(cxA{hlf^gWrwP+)A0R9Z>i48zQj3w z!NW#xbz3XnO`P+t=M zBToA3UvjFtdMhVWNyywMzZ|Fcuj2ze9#|6Vr%b+U-;Jk=53fEfX0_c~8SV$41AO>% zhesbVEFr8ee$)wDELr|Lvc&DmpoWzEl|yz^dt$Y_e;4vsIEEgM*edtxJwp4g%$?6U z*6Rq?uN&>B$hFn4u8_7)$B4J-C@sMSs+ll!mg5>6EG9O^E-ojJ!-c)D)SV=b$UfDH zx8+!>K{4Xrq7miBO-5jKb=R2cosn`fqWtVPZNxhv>@n3lI+8Md6!f}~C8)8kVh}Qu z(Qt9%KhP|OtBeb($NMcSDd&d@{KpAuxQgF$kEPtJzwZotE7APAWZjyQ;5Lo-n0JW} zckUM7!gH`u3VeW6q`P|w`Yu`2z3?-@~l zUR;s`hb?^;UHHJTHK=lFkI$OVi0M4rUwdkCP8e`Sd|>YneF;v}%nR#+uLFEi5qQWAJz4uILeJ z*e;7hxY4{xFwjKya1|a*cV=?UBiF=3 z_Fcp->J_nzCL#9p=P8~28mn4i|CqWmE>Za{A6Q2s_fgsU%{#z621dzTkwIi?ebMmy zX-wXPY+fRF10Fejx8e#O75WW7((LbW0nT}pMzLh>(&4U}wPJp1Q*a zUmbc#K{)+#7K?B}2_N)z&UBvS0;v;OegCF&TN^^}?aS@33A)S^lN+ujVkt)>lvgLK zqr6)!Z|mT^tqD(bnX5Z5|LvBa<6!x9cV0U-u6yV})&FW)y9Q_N;(p!sipo?^B7GX@ zoUm6|nB#Wy$+gHBf5N6_Uc?2xEHGmu!k?qK<4JHthzpfMc}8D7Kjkl~khW|lL03Twx>DXHvIPT4$41Hsa@rBMD8 zwKaq+Ir#0w#gBvY>BT&tSR2k6&FOetlm+7%0e+{Jxf47W;s0^*Gi0~`Ka8@eBcfC) zzW60lFDs8tFi|}RQ#luMPsfYn;>QygdKFZs>Q%SZ>A405)qBDsEi%Nvym$oWvBxRe zsxtX?3xuQoR^9$|MWJ1!8>gw{gRsSzosszjN2?+~OD3k|hgUwbFS6bhfh0wXK?D## z;Sd0y*BotOU+4I#9TPZ0JNF=U=VEn7kz({nPj&uJf-}Xmr@iu{Dw8-%a=;F|tfj)+ zUz8#gcYe+Po}UYuA(nb3sxU~;iPrPvrw=wg;|VDog_78>A>k5!c^E)U&`-j&Pk znSGZb3o=)S>$LP#rs-uiSEE`62wW0Brq8^}Hd|%24HNeE-i8>&BpQ}DG5A-w1Mw6; z87{x8m{p6Y$lSYF`*FTD{*F|1|{f^%u+^o;u1TXE&}N8^15sP=shE`ZC`|)TeVpZC}d#(^;3=r`+4~4(XT! z$0A4d-(Zq+Fu4?C0D@nr1H&Z;X{KdPrWVf6#p06RGMfy3*FjQ}%{!y5e`rx!Df79 z6<;sf30kbe@()&ceg%8j536kqwH5ZEpwTT;lGsavTaDXbPx~{NA-?Uck}kzyvU7~V zoB=;kyxWVqnerIH$02iGY0#h05OITZ;RYAI=s3c-PCvYg&lnB_tzynub^s>q99SOL zAT0B$6?Jf6HqW|(k!?{8X>L#aC6GnTfFpiW$;pJDB`rdWp+wqVi#I%g zj@fh$Oqs;^;5{jYM%MR?dx};viq-H-$ub=e8sMqyzuZ5Ub_`H?R zt$0||M)n|vGi+I==2~X*Hw^EAX8f>T&*?SDX@0tq=Z^H{{H0&mi>`>CLcHi&W+)@x zVBusQ0;5szQW~^GT`0jnm@j!^=!miV5Ekuo%QaR=fWp_7%4CQ$tZNcuO=e=!3sh81j_;p(`h^Sa~r!k~pqg9v|puwy) z?^V8V?Kdl5sJ%Xzwr+>U()Q0V*L!~=0av~7r``V^I@pGeG7fus?-!?#aR~;M`U(t> zpBc8VPbED=3HB8AkE?+6Q)yI0zz_y1`;Mfisa#N&TI#(~OuKLQHldy-TgS8q-V-i+ z@5E@syCm5%Z4I2uT=?K|A{z8%()6(P{qL{Fs|zA%&Z`b=QNq-i2Y*c&vw%9P) zFys#(F39vv{cKO)sHaW!_WWHvx2JE?4;NtaL-4x9der~LJY#R;Zy{%(=CHp}-eG<9 zuNJez(KFZRG`olOR>82oy=j%Ae2Xfy@Ak0X+Kj(r2Wt@w_FWI#-%OoN{d#OJgs!6U z%|}CBQM-=Fnup|QEb2xCdb6=8zYPo*)CL|T>|uf3jVMi4^Oe)Di^%V2LF zYHe9}xFl1MAdF$i)MIw6$=;$4jVeJ6;^ART7~5BI=Np)mSse7BUSl9KI2wDV+yKu- zA?u>v{1H6}t5PI{2TjIKTWiM$E3^&;O%iteCO!Kr^c<`Zs|lLKMf@f``z!PuF*qsh z_m(2+wEeGF<#!Gi<*&*-bq&O)1-VD$qwDjegZ~11e77JUowp$SqqQJkWeXfDD*3W( z4wzDn_?iG_j~;)lN8M457`BTLap+0W`DvTfk=)5&Q&hOSD?)r8llO{cPg+UaZdQff zbzg`$J`q^J|4YXaDamE~35IKf$9*}CQu-q7Tg=eR>&HtJWYc&U%)6sr7zcqgX*G=` zzu%Xwgj(`?^&n*cyxD98H6IUGk+fdipEIK|OMJI*dJ!crw$|-T8n_7!Vq##TG z!f5Gd`kfxo1T zVn9Oy$ug8baBu|+HT|&a9>e&k-khlMw1$a{*>A#`XTzBz9bf2mY*hrGPAP+3s6WO; z>qtzYjmJWv$!8uFo<)F;!gp$} zTuBBmxvdaoCIniwOzpY%{tub!AC-P$ z!AHX4b0$19w_`FC4rAu>xXLF}eeSe0E=IXh=!fQFR7sX|aXUXF_$hY9&;DTXT!`lJ ziOoc!-JB{*Y_2X(Y*rA%lAvBtSQylibS~$T1qQUV#*--1f30rUz~Zz3t?eFk;9>E3 zgPW?V*^~NHbX5o)H6PQslO0p((AskbA*&>(MvLNo6}krLih$Py?4%YAcpkZR4$^(dF;`s;Mf#$4xz z;G7}m`Yq>>=1ls$=xAYZtBrVN=OgzbyDhjrP@- zwXrj5W&e`w;=7y{-1mX>ousR+1Jk=nSF;DEXX14sJ)5s!*G!wY$qgvI_vY~v_Og58 z0};V0pQ<}5EWTmFGh^PG+X0vwyw)L=+f#2fY!z;7-Lg0w%RhCl?O=lA-EZS_svCiQ zi<9lgwa)d6FQk0s^QrFMAI$Ynnd_f{Q*cuGIBfN0)~%Nfz& zn#)7#&AfJ@LT~qI#)KY}=Sc2O-YnES;N`fN=Ct0K5#lkQfW1UPFycY}=)W?^SZ}Kd zbdIqC+OVMrR^*M?iW$h%8Zld&*U#iFv6<0vqqXoW9~iBU12M0W8W`b$5$yiEBXZK< z5&0;j9Ts1E;GjJDA%pUTYBwlT-R}nng_+K{oae^n<=#6T9Py-!par8PiOn4%6#6R! zUUC)e!on}ZXp+wh<@{=)gaIX=aRr=WM-%qG_q3DG5ex&D`RO-Uyc&Ld!*F-;W2S|7 z<5vd-k;nt$W)l63O=ygpx)Q zt1eAERD2#^d!FsT%YSPaM>jLrjka@(pqJc5476RC)>DrXcf+o8N-d>%XpS{)H-Fg% zXRzB3@GA8HzH2N7kL!ij58XEC`jPC}pan_5n3_E}|5Q8+m?2*!vh`iKm;_v2m@E%V z&-AOYds;U*r+*Bf?m31?D%CxSpKf`!n;z5_`&;0e)w|~UQ#j5`=k9y|**`^{+m}f8 zd&x|pcl9oqWTrB?JN2;a(Ie%oU~3!mBUw(wR?y4<8Ao6-Gp?^CZ9*$c8T#!L=py+| zvpplT`Rgp~&-+hn4qias&|5p+E%i(Li5kF0F=SbBDXseo`CfZrq_2Z?&M14!#Lv`W z8?f{sD?2k`X8af5)`E`QH`KNUy?=-$72A56!FfM%admls#lia(-$fPT3Bd1o!`Iwz z#2aL!-am69Ww!Z4$yO0%8yWqYDTMTLy-PYH+;DzvQ8uehRV^!F*wB2)`+fi)tEFzq zZ4W*mw5pOkQToCHCrZCVa_AMieN+@P&UjgHknWF2G;1RenqmfluPoYcN%4Be$4n*K z{E%fZ5hwIc&CBrF5iY|DGBAw}n!`$j69zrVymBt%f~%nOFbJa^zPIgjBx~8A`d?b< zd2>{9#$hVis**pql3P2RO*TxmGAsbLGq2=#D5+Aj;G-&1t0I=GCok8R$rX>fAyHmc zE^LtrFcP~d9DKyIv)(2|=VVAmB<-d+L?YKf?Ui6I$Kg8s~rjy|4>DlhXD z^#Q@}58TL9HNDt{gtzEBVr#*{amRPh($R_3D{Bfpce8~X;)dOG81>8(QfgqWSY+!* zTBgsj`)1 zf&=r|c#$5fyM1>_q*d*k5fbNuB^WW#LdcR$r95ej+>^|wdJ?O*`#uWs$ChOQ%^yl!c@iQMFj* zLquBc%hL0WxE}EgKJ;_~2`#Ijt+YEBYrp=tp-anf>8!wo9I8;q{Klo7pcDm;Z|{G* z;?&Q34;es4bbsd^BIDqUanPh)1M^*CZ`q>cz8Br0@#4-k|BO?EJG6Xx{l$qTSAyZh z>aK9=(Bm|I&1XzLHLc-yb(}&SY@9Lpjf#|XqL*-y@gK001Ur0aZ#-2gWZmkrb_!)K zt1%q1e$29Vl2s{W-Qco5Hjp*uGJpEAYJH5XO5wQV999KP-;E~#ENkOZ6Y`!w>mu5@ z!wKoNDY!yk!&XggXN=e=Yc;MJKco)NUWnwOUAucJN;DqM%O=JF?U~Vhv(bM%HJr16 z4S4PX%2|LmsFnK724n5QaH-%3@6cl%#wh>P>o@a1q@WMNk6fTl{?$Gq@2$IhVlF$DgNS5TI#2{IUX)9cA zsOrnSi29KkkZ`zQd<(MgfueA^mE-cHLEqs>1=(Hp-Fn!UxogmOjY9S@z9UWs!{eoC zfZL)x-+%td?DxnKFMN`6H;6%|_t%~g3aYSmY}1{ma3>UFTQmSbt^$xR~uTr+f`vTMN+c2s(MKYXZi%lv(Q=cSKZ ziXNXbZwptp1l4kiRzBFR}Ky?C>`^p_bzWQa9B5%Ox?|F z;-#k50GFo1(K5dBEWtPLpu*`EfFO?Jr4rA#y*YyLf!UIVS9Di*;Zy#0_e4a&!l&9^ z9Z~o^VUsbG+A;Qw;&0^XdM!SqIb-()3re|QpwQhNZlVI#Sdqu}y1wlYGMD~k76}BUai27m(7Oh8Tm6mPkh8z2uGQaIK%z9zX)b!%|FGC=xV-H+ zj_ymJ2U8C0LuS6cJr=!vi#I%Q+^4VRzs$;iIYWi4skYaL`0p0gtR>KVRBCK~#!vE6 zRJRtDE^dQ`L^LWPA$)My>u|euy8ui((vl=tt=ZA`YBAiUrYkI8#_@en@)(C9E&r?` z6TEAc5m)RlVy{V1 zv?H9gj6PajuNlt;2{j<0MMH^Ej{D7vxUu4zQm<|Yj>U8Hk+9Ach>HK*-s1M|vbQc8 z32T>eJ4s^cJ2*h)K)p$yapFks)KrB|Br9t-@$sic*_dWWsC|4%!;w5_6f2Zqi?zQ_ zgb`d=8b105h|Ax&gU+#Ka_2MTzK@B&Tv_0jGozEhoo(GFUP*A)_sjLYt`pz4rMS*U zF4jv%p`h$Ym+?(7b(rg;o_arvN2{pdOW5>1%YYeI`6_F+C6@e=)F52Rs}tn|lheJn z$-X59smCgxN}ThQAC6Y58`r4ZJH%+&sCl8-;prZ_5Vo8u9?{aNXOmd{kQgPhhmrxg&0KJ#-B+V#zQ-tLxRf-^vySdYPnz>99YW@uYaka zpx)oOhw2l}XYx_b-RUb;1{+JuRXi|06~X|&AG!^88=2fTIJ#IWH>w7a7P4El7j{To z@&=D>uN~~KyIT#U@1=Qb!VWR%iNI!jY3n{XNNpI?{_tdyy!T=GZ~5zL1)MwW)M8^e zX<^V}9a#N5&JTQ542R;OetMpACLbG{Rx7rC5Fo$ZPtUg+Tuyr_+*0_0zpEY{SBGURcy3jA_B%s0vcQ#mLPs&FZIeqedi=ewn{`6W9m) zsY-Sx7N2CPB2}h~h`+K$FNySMn$E5i7Z8<>BW-|6k6?LY(F)cnYr|_sqw5sMJkk6S zJ_TB7CaQ#J^i+H3L|nN8dhyMhwj(`>R5yI%qo*LPCy`Y31_f%H%$p;uje49CtkaK? zm>yhqV#w)PBxdc4#ME+3V$<|hBz6xEc_enG(xaSdy*Lt^!IMbrKa8+u@+KIOzbq@Z zm#K_Ks7i}MeGOWKn4%W-2KvI(-ywpsp%56UH#k|&Z=vNb43#fP3nSE385mlNELEed z*2D6HbK|SrZhQryRjQ(lZ+l^-!-nl6J;NO1Cj?g2Fsf^m-x$yVqk2BVa`qYIRqs!Q z-qWps>zGUSUOpgyWN+p-Z*Lh2y?#je$o;*a@N5IlR#&eGk)4&6kO&t`L^fv2Ub3iV zEoGuL=gI%3czdvM1WAe2{r<*g)%Q+dRp8#|7Pgnj71%n0vFEOi^e8eJ;;B^yaQ>ym zqTz+_`fo)=R#L>XjD>~!IDtv7%JfM7rnXr)dTfYV(|#m!L@7EQ&Kxg7j%KtyMLO1X zSpEH;8I9Pw#UvG_w)*Rq@ennAkD%2JK{sD0FKx+yk^9@1K73O6y-Xv{ zk9tqFGIGAnl&Y;Um;aJ$~>I5L9gQDW)WVXV0tZse0^%`@PF zr8w9qU@GgjCYBV#JA-vf4K_(>(Qe0OwFDJU)kK`vexla!79PO z_LV{@0wOp|20`{NP8Pw1_*TZUn7l56bBlwcqwGKD-8Lpci|`Po-b!k&3+wY=exdS` z%wlQkPD_Yezs25Syv*m#ad?NrtL&?UQAxFL#KK*TOO^~ZaTzfR5=*`dN;ZQ=4sS#d zO(2igUdl|Xs@pL?lf8%>9qBvyt6>d7QCP4}m@RzE4|l68E&3W2_usY&)S?ek)Rf2l ze~}MCT4c$ZS=ixOm4(4Nm90v3&3`y{=kx89N=Lew4{9=8Zj{twloV_?>QP{wVBIP; zyI$kzuPfzQ!>MDW1H*Z9H}(J>4Q){gjp3T#kwO$u6Ht?a$z=8--PF_-PFpxeps8u7 zNcH2BsJF^cQhO@Mewk5+zoLi5$0Kc1R61PaJ3;aNA{Y}0OU3h2oi{(1{VWp)Zpr5A z{8GPVtsoDroQ&l$BO=i*{?_|oh# zZ3P89{NL(#QGcEcsnWLmPx@VOsRO!Yvlr#Tv*Mrh5_wikv*%i= zbaS2+^LWFOt$Jcx{b3Ua+v+>{t_BXY*URHVZ5@~{JHDDdFuglOsiFZfKMfm@Sh9~j zD+J;Hz_UWQ$@8rE)n}a%|2OWp@j3Z`{Es~=9IE75;qZiKMX1IRf)4PkP^vsDa_utW z|K~g_HlM*DBZ~Z8&x)(i91nO_T*F(QXT|8x4<0Q><^Ofhite#)P%`fK|Cnb*;g|n+ zJuALEU7i)q-;F&hs(5D}2K85>kjwY1SY}!BJS*l|LfFt4mmTn|Fw5ot4?HWZAOGL= ztk4ksPk2^n5vVB%7vAf*erae9wqiWddMnv!*W>SUJ~ei8@^;V2oQ$F|_QXiAuL!+2 z5~LtVAM`@(iScff@=wpp6XWbt20Sq~zS;Moo)|y-`2U@r7?U!`aWG4=p{;*rPtN{! zuav#bTP4XZ%Awcn)cNR@-^0(|wXAnp*7>Y4a?S>q_nin%jl}p;5F7fvsfUv+g^x4C z)Z*!aS>m#A(N!{2;VVVaYpo~;*>_se`25;AgNs&DG+a~*k5rk{RK~m}E*_li2(k?d zi^3BAA&wL0W2nF$^ncKCVij%#f6sB^!IR7a^+Cr8S@$!`rnu!|ljcI0?vae0?&5Da zeWJ6rvvF|V1;VC%5+05Q4P0vbNi?2J1K|>NEL@?aut}mRh`}m& z0ZJ~vBU?_E`b{=GiAF{L4wnc`;R+?iruDweXmZnv-$4#LnI3qb4F?kwJ8Ouk=J`Bg zBBdZpv=o*wxwtF1rtGCDsD#E009Hro$=!sP~5e`bsObgCWs&%P|3)!*nxbI&sz(TaU@xTw{i1wU^n%pvUQR+qRU<^=tNq zHG3asi7v?eDE_EJPyeXN`U(o?nXK7&as0U;Gj5XcMuOZjP?8PTi2eAcaQD|qDH|*^ z({hXSD889FI3rbWR_63feYfMNoCN0C?<(wr7?6Nbs5uAhkT6G6e}@yx{Qj|~cn`}9?0Um+*1;2_`d*|%VKAJ|`Jw8z-Ucmt zjB;E+jz`{<&f39r3-37y>Ufco%KE1e>7IcDFkfO^_d1&==K^{8V9oC_;~x3bK+WUx zYd)42rxqJ){SS+eK-Ed4GuPHJ`E7lIj(@QF@2mPh4phIL_Z;9`_0iTdSD!vYTpXaV z!_Q&R@EL6%FXF8J#jW9kNkVe7c_!AwIASAOZ-1y7Z05W7YY%w;8twrGOd&ID{QI<zPiBmL6!>I^F zS{9t;ELYJZa6#ppS{eo)H9C+oG_u1)};EPa|GvgI@CDs>@&$k6X zce!JJob}p;mDanug1n)Sg0;5sHyL}F?Kv_U*BY!7)|-n@i-NdH%uFkj;b;I>9oLb{ zc%ud_vABjtIKa$v(Bg*8X!~od%buZ_Q{KXKm6_zp&$DNPiCSM{T4g*kvDhfgs3-`H zGIS=_U}Csp>s9nUrmx&^M&D(*(n{mRH8aO1R(GJjqn)A_4Q1gLhXRmw$lk78pY7~` zw^8sEC6=C^>k}ydsMw%-)?PeB5wKimD?8_B2X**6{Rkk3sGw1^#_sD=Z@gW#Ns|0#tQx_Mu}Mf6RX=CEfjHi%KG9VG0=zi zb{NYVVA#%F>}?qx4AD$$G#Q^bBSpqVZJ8=l{qheeu6#PR^Ek$`KH+~vrc(}JbiPlX z>`>mqbu-8q8TI~&u_X8`3E~x-$MYv!LCJ8hNRcp*G3cro|G7Clv&={^yz24{}V2em`{iGpplWR_ASoOnGf zCoFy-Shf=U!J*O*Q1TJ6w`gU!QqAVQ&pzP&Ox|-aR`HTO8_LV23|9&_H!y0GqfrYs zYFc_7qXR;BmIQ0=$dc%9=eeVgP81OCC0~0Q(hbm?3j`aV( zIG$xjXUNCOyeDW*`6MYFYzy#Wj=UZlp3uFiz29$mq7W~v-WF_T@h2^b3soXch-7xw zL5@b4wTZ*7b`Fr%B@1XNK%`}E6d$6c&Ft~mMq0-9XvDHi^-ueZog^$}C=t+Ca+IfXUvqzU`S;`b?o z7B^?Hw$yaf+o6T;SEhE~K)}hqvB@59>r6SY%J0)2IJ6+%K=@&N0#cb?d{qdhm{A2< zos+w{cu?yksdS|rP=rDv6D2cNZmYk=`IGJ*(^o`X;Oaf$j1u(y^B(e_&wfiR5nJE$ zS#1hH;8!xoaq3FaKR689zk6uGC6{K4<8Qt66kq#45a~?)J$-~SRz>A1>sF>#(}SW^ zdF8%D<4%1~u2LUA3hnybic?o+?cKPH(3&_Z5llI`a!h|Xac1ujf4eh}tsIM&9pk7$ zJa@FPq#DwlTF;YR95m-nFu8KfdrFZ^-`Cj$o$ieR{W?XI|H8bq&$+ZlT@4I&iqKBs zn_JU^?niN9OG|1`v3~kBcPE;M(keU;Pp-Z(odhpVe^tm}phOPx>P&sy^gijcNRKd?)dFjb zs(J_hSjtEnlW9YJn@8V*qjfLC(SBED&5n7`WxuW@qo?!`>*X3o?<%iuO=0atj+)vN zi&n#1RjIKV>KpR0VFiV$p2E~xMIn_SlZ<;M>~H^!VIO*-MksBS)_^zkSl5-+3N34C zO;1EfoC>DN1dOIASzei3nP~hLLzbD~U~W{jQBWSmMJ8ZytKUB6{p=T24N+!0#}EqY z&O|d>*@DbQYq(RP2!QgtBg72BpBp*`4Of!FcPl#+$(psg35&_ni68bNUGnH?NLEH8 zpo)*uLq^X?FI%RqRy@1Fhjupk_;{O^z=!K;<55EC;8u%jRt;{pD!D4La5mLI=SCJ$ zqzkb3Qz{FpR~1qNWbt(Ncgj_LH&Tsm*uycL8E`vHEO|SjbaSMCdkp!kIh4- zVz*nQ1z?7ypXcE>^EB9JP!=`K@q_@TRN*Z}3a3xq|k zyMAgdLk!*vvbOoDE-6wF>Xq>V;PxFqA7u;+fh~K9Hd4uvRS1ZU-#5zW@w>(<0(6C6 zSXpyVqH#Jow9u*2(A)T_$V|duE%pSgxz-gfOl`>C#aGsX%x}kN z6)2ZrQMO>FZoK@I42t7*R9oxH!ihF3M&M%7@Xy~ml*8VZI{8CWwWXHvKbM!qZN23m zf8ZBehjhg_<{P4MA4MOFgGI`wwe|?#9^+)e5G5NpQEmYdB^x|ZvY?2PXYe?1CgTF_ zyQj<#Zk=#Mda7NC?p8&-KsvZxSbFze2fo%gWfyrSs6PPN|&yGan989c9I5I zJM6fIzIB+k&OKF7-aQ%d@)$PEA?=YTc~p!Cy4+d}>rK7g(J(v8?5b4!pF1rFIqUDv zJ=to@8_|JsX*+UHQt#_uM}1lDN%+=3KUs2VR*M_sDUI#q{-`A$-*b-$$v81ho#z(@ zQ|A+?k*iZwa0-4zjrIVMX%PG=9GqWl59RqK3;n6{0uE|UogYjo@vU$$rPQ~=!IU!J z3I|ileOI^!fW-MD0-LP;+i4a6bBE2siK8-eZ6zvINWUmH5Q%{$x;(6SayAir8OTH8 zH%RohPL2*O$+-Su)ent}_T^QtYd+#vYSLYsR(&oHi6w)o$0N$(2~5`+_|rMNb;Izg znHAT5C73*#X|>1B>IaiY@o`Vp%;IbLQ*qrJL@5o<98WmZL#k$$UVBj0%n{cUK zK?Vm0%^H2aZV7DkDVLbq*83BFulp4@JKkqVV=po;^Q0XAIF0^7_?;r}wfDlQdlUz; z{PRR-U?1$Y7J1$8`CG=k?Y%)1cGja^{@KNq?X}<7d&Zu^)OmsT6?g@AiV!k2Kmwm$ zT>qK(;VajlO91hz2UY?_!n>8f4Rt*g$Y9rBOfCZIH?-B8sJXLhp(ywInZEt@o{5x8 zN9SYwVmyiI8pmf~c&rTO8ESDvP18YyX_+U*E;?C>TQK5lWO6*X& zSg)gIac&>MyT@NB2qV}Mi=_VP-JpusD{IiCi3d0ns^%46JFaS8#dXIA*Ni9b<{?${ zg!FkMuH^z4NweuMYuIac)qnc^tfX(6J4jU+B{Je4A&rV&RyP)^*4~boZiW1s9p08A z@74GGnq5Gxz+qj)(sIb>#t2YWx3i(cp^WHaJFAunYl%fIKtDKM2Il~Qgzy!6_*Bq) za(L|?HmTth4P#|;SM4E{$?hADtW5S@e|Tke&vjS&Y&7cF2le?cR3-N$rn9Btrii1{ z&!m3EW(APX2~rvFO?=ogs7P=v91_{K2u-0h?)6w>tNjj9B-k9UG|rr82lXdZ*3r$nJx|f@%wa$4dy1ugVYXxL2>UYkRX#3+q-22qPPEtxA%dMs<`&Rv&lj>u=Q><#aPpl zKy0C)B`s~)2HTLbNwfrmvVeb3`l^=p+4m530j+_AyPM>Cy@*24T3<__w2xL=spU^< zL6eAVpj5*jC05!7n(8h~HCi4-Ysv5XJ#+776F}R~@BM!He6o9Y?#!7pXU?2CbLPyM zgQ3fYZNPhKEer4soMa{bCwL7wn@=B*n+<~g@JlDRat*>-t~SqqHuN2ZrGE|43$5^< zU4{U=bTU+tDn!BRzkWJAQo+@cr;y2iR;xIhMlBK-@Mi(OD(R)#0p>+*&kscVp z647D&S+v{rH0QK|MAUxqgf*mv(I-S|Sj1t3{_W-UIH!bEMD$!7P7#N>KH>n5O{*vt z@S;FQG6J%qyeZReX~4@HGJLL8L}32&SujD!3un4Ck!UkxA!#eoOzD;j2oJLiMiap>hmQzGoSg{>M|V5M3vJAYXEO~Wii66FJIJNM%$T)` zst-FQ)9wHpzr?+uFj^XaaWokoLYoYoXVo9zE(P`@>UloMD6hdZQm_9zcB;$0X8m{N z0ck>``jd+w%8lqoYRX3pYXiTVx8T#iPm`5xEXor@qNhYR24Z-2FFs1Q@onuD z5TxI!-^FL9YO5at%CX2cuAT53yPSMgx{Ux}%mKYPEh0C)#CpZwku9+FFNb_NQ zK`o5G{1MD-Qd(C)afDzi-sy;;-u=ESN`y`M^henQsD>&HVWuVH)ts@kMh3nzw@Jx8 zS#57-CZ;k$YV$V}MeRY79B~5h45X}e!({o_yc55TXe&O|I|Q`AGmfO=lMTcT5O}I@ zCl?sak4rw5F*(J2*0h+CWl8y5|9gw?E^Q{7OTGp7Yp7Tb#|Su_DhdBy7x-|nClI$T zHN&ZtWbrq%>J>j6zl$Ic)B~U6rPZeT6ja8q$_Fa-yVUcRO2WqAebq0z&P zxt@~Kb_cb?oUpXWEO(n`{Em?s{%bwqqtVmhW5z3K8J7JC#Sk9+Fm^<7zsxOMku6JU z4XAq#s`kZuXrBsGN>M|Pm5Yqvx((1_l`O~kn41OwHFa$;qoIVYb|@r`y%t?|3$;nC3*bSNhRa&yGw${nce{}q)DV`q*ZH~|%`dpHAvGvD+!++#Sa%GGYnsxf9w8CsV9KMtQyjW2^O z3(*mv#X(0}zL2v9MvbL+Ux%0)oSvZ&{sloxs2w!a0ToJMvq9u`1D9U71P!T6!gfi< z#ZmUTe%w^n4n9YLl_1u4F%pF^utx(huIuSev!Wv(`P8C3ry8X0ff8*^P;o)WuI_fN z7U4x3_f)kB$g~GYAi<)v;=Uy}nCpqA*$}~}ktud*8#hr-RAg4UmK0suW4DpfT7kL1 zLVz?B#biBDjiL&%a@ytu;uQ;cYUqxK-3*mMkFsWdr7bbs%G+z@&9d^E*>cNV{TB=v zZ?PN!i!Vo8L7QB&rT}MQYVr|FVYiQC3t=3bN2i}A#$TdYOnH@Z_2nJ4)oybK$IJkP zixq_Mv-P#zt)E|aL~G=GtaVB&7isz$KF__&(yQ1cw`vlivphkW#u!uoLD=tOn@K^m z8aJRsN=rl+v%7!oMx)L_u;Dh$S+tCG8*)pyvkEc=1GLvr4MzpvK?RA+kR9tpEU4u6 zG{!Ub;yjUEEODE|?+mRGOOgLw$bZ3f95KEALon5VDYfXdNE-UdTjGA0MUb~*L-0)j`bo| z_{qx#`l0~`vtTdxKSFS!Z<;&Um!=SBd@uTR*?*cl*dv%;E<k+uN2ga4{vP|+eEQGm-@f>7gjuzSRJ;gd<*?@{KsX{HCa zOgO=erPW*sVa0>cZ+d%yr9VS>ZrrvApi603ZG%D9AM99K#CgoV!3E&@;!QZ6M!o(| zsM=a|D!Bn%^_scJ%Zp5>dFw86@#49e?qrkspl~is@eexe&qI!~7hpCDU0Opwa<~T( zyh7_>V}rQE`~;f~HZ#yQ6e6jpc{2W!`D*I6#eoY`{8p`D6)DeYzWp{e&Ho-!0mh3J z_B_vv2l=}b;>2IwwHS*(7$UkX?Gm1Kq6ngfa+1#7ZNeescR zArr=T**J`HF4(UFhhxJg`VdHwIE)X-CZR^4i%aA~$;V_rp$oWWB$gmE1rp^DRyEaF znC8NoX@nuNJW!S}c_zMuVS2$l+_gZSQ7X?3@!5Gws09Iu0P`^6+n`MIz>TuQm%wNO zz#HP9I)7%uG|i1FGgUsPcBlzFO6UN@S?N)z`!SV+Q?D3fG4)QWKg(gWY@$^``+)U8 zwwO+GF||yhl1XFGBJiNssPc&X6s3?f{|d+{$`7Y-qx}73xA|b&0P3*j6!<$A7nd$u zv}CkZA^LWQ&Duq0F|D)IG>473Hp1aonzYj$)o3M z!l&4TG3RZ90zJ*6w|SEr)E+>p6{b|nn#Rh2B*)z&GBpuWyacs0FJ67I%?9Ktn+jwn z)7&?AWJdfA*zTb--7M=aQJF-AMc!Bg#~}aAio1-8MKPJH0eNMt;y!-CQTb++Hs=&l zip(iC=8QAvOf=?9GUrS-=1ei?OgH9KDJYPCaBHW=!9Q#eT-K_0zd^0YUhe_bsqz2L zh1b6R#XmySh%z&>QYkak12FA;^fBr)-R5teM7kaujeEE){cCn^SP!@~g*MoKz1!Gh zm0_yw!L$eZyCF2a%7H+sAC5|cZ!ht&++SveqQO9;f-6oHBwXJU#zi7J>ZG* zkbkj8?m(y~F4NT$*Yf=1)Hx+id4#!I6mT_1Bf01eEUjdUV#b(E73zsXT0Iq~p2nq~ zCgKT9fwGfQX_He=T=1x}Q&UgV?We>yAQ?rjfb(G8pTm{JEoQ|yqkJ4b(SemlO|kh9 z>&Kf>TvpUm4dSw*em5TcuY|I|NU{19iuEm09U4$ik-wxt}FPsjXa)+Qzv#I!IJ{Xs?X_lDoXoMHr_Xwhnx z_y?$uBk1=QJMTj@wuyc3I9}oMrDFsc{<&@BamY0_{x=vuh(xUy0qDMsFa0gAS?R{{ zB^a6zWen_0b8Dr?EaP6e*zYhrF~xebczf>tQn`^=i(CS_p(&@!PC)@{1>T4+m9?zU z)bE=E!HV*PC<0z??Qm8RLoDe34!EUN?#16Ittwn{t64J%t*@@H?d0^MH5>w1YrUAa zs}Gm1o`)*6#sf$!eRdN*7w6!{TVpjJ2dd5FwB#~II2D#wc^Chpv?_nePpt;W^3E;* zS3LT<(t2irJCgSsypC725fuUnl1Z*QS#0MjAP=n;6=$y|cf*V9QH!a&Fo7rXk;8bF zysPlj8iymrYS@4j;~h~o5~t8T`W+qbBRYz;PIe>`pJ6d+T%s6{DOLgNiQ`ec2yv5P zH#MIY_Bb8(B$uP}LdIEhMKSHEz40xWwh*QSXSTwBF)Q**D+vwc7@n400f)x= z&%T{QUqM8aU$uq3_iz=I7PEeM4Ol0WJI^fuhLhnJczf?J5m^30FM$k<2=U=W1J_&b zsACQGG4J|A|C@v7+`#*<2Hv-Q#Bij7T^4^8_6S}u>%%UCirvs>95~dCXj(wU=ri8t z^Ih_cxZC6Si&p7hgHtocOGeJ%MjwKO^5IbTL|0SvyLhs^pEax+Jm98T%UzE%8+?91 zKU)StWO0U|y`10!byOD)9Ez(7a6=k)d&c7;V*(`_>WKc=6Q`lREKr=L z=m)^G`tfYU(ZcI9UE?tZ!9{CKi>UeqhGud??`aB8Hg9Q7M~aSad%#19h%e1YzT2Fk;QV7#CsPf*&!tkpSS}AWa;`Tl1Ku z)`!Dht0h2L?E_|DjeXAoLsG!82WG7n`p5+~>V}YIcgbkI=^#|5z zkzey?bsb}*%>YZ594t8vSKdnobs||~9)X+0o~&TLKUf$3BNh4=1&-h(&~RH4 zU~1bLm3_mZ?u@`j#L*(gfel&{0^6o4-MQjHn%zN2RW7)7Jc82DVNF|o8+sqkMI@b# z_Udcc-s-Ir;0RZZcrgy*(MqO=cM_GUQgL@q8P|_Xp~7qE$Cl z!$CtIUS!!Xeux)!Q?vU+ZzkS_98oQB_0~eHG}K0LPKeGgxKSEzV(= z76y{xLx}03H9&`iYhEiZ$wSTl>c^K}4fdN5$VX##kIBn!YNjV$Xq*|WLtq$Y*{7{q zA{Fjug@}ol71-~`t?OTfOIM&(-$hcP1!Is0(Zu}KzNOz%J*B8frzOmYC9U>^U`J0! zK;CQ^@-ZjEdpz$_o)f6R!scoNqsY_7o8bDD7;~`{;WF22mT(MW1p9S?f*o|?rtW9t|>JJ~)Duq%B8Q*Dj zC%8ODS0q}%7b9Xa6*eLlbq5K==l@p>G}N_rttPA z5p^DaP@R7w+?goHFSB}szq&W1q3}jC_^7%NE%+$zcZYs5%7k>PF0}GId!T{f2ATHo zX@f88T#$v$Ihqw;5uA*h@`|X0BA_dbbCxDE#ttMS5?tNeJCjTFm@R~j$=2l!DC&E<2QtTsJkh! zF}ZP#qv_oh&!NE&iViRAgabzw+$LiB8>1O`6)|)5M3L6?aqz#j_TU<1ocfGWy9tZo z?$PFbtK3H48A$()Mn_xUFfH;UkPXW}EwUZ?+uqGGsyFL*YC8cc@^RBxn(udFjN+@68vqD%8`wA&+bV&Ml-;*w?C_C+oyKrDG^#!JRw^kL z?%IWdHsKwty8^or^UmlSTkal-&@AQdtgufH^nio~{$Njdmvi@;J(E2^Tm>6t;oHQ9 zbUE0-qk7}m>O8o*2D(`BQG<{x+&LYv3=wd(pof% zg<4&ufr9YgoEJ77w+P+f{Me0lffiee975nM%1Uy>|r zRXAg$0NaUgVvKNoXs!K)B{pe{j_Ir1WGU?V=kt3%Mov+zDA3z>79%AJ)b+C%DL+Cf zn{LNso1ngeQ#4ngtukicuwdQPbGW zksxNKecb59F!ZwBOzXf#VZdj3Ga*w-YYW3|xQE3SaH7{eLVRR2TupYBx_hK<+>O%< z<_-6b4a;!oVXbj2ochL2bLaHJO)smO!@(acEuC~Q?cs1Hm_L?Rlntp#CTk9i za9+_XGB8|#=ThKG0q(DfIp{8m7*u}-S&Cdmcc)c{!J(=8eA#V2&;vOY&yRkWso}A`pSHhhU zg!YioX*Io^m?~_Inu7atU@{N(=FF1!3iCG-JUtf+oJ6-~Fad%$4_E%Gb8vg6GsKkpBBh4Seb-IX%a;SoapnUfsTdE)`Qx?p^D7h}$Y zUjABNC=3_7tZ?^)Fy!=6m_1>pI7}NMPY>xRCg9+$w(P$VWfyMM;(p{TYX1!xT=1kq zjsDouV~OulCIq}^ApE^Wz`v)3A>yI3;l`&cC}RwGrR{Nrv+c7xj-w7&BM@tJ2>4GP zo2or&*7l6YXW%3njqrs~Phey?sUOQe1cOt&r~@jc89td6&i9AC%O+2Nq2?W|!Hl=t z5?NW*UD&RI{~K3zIHy<(Eg9i&54~l)=RqaAn=(;m>3)ENczy(9X*^GT6pRmoEQl*# zeac_msYU+-O|h{Q*+oNAz>8q#K5>Tf`h$7P&KxkmZ5_9tA9toaO)jg5A>wNDT2m3AvN$F`35A{_zn)Q>6sV_XW&4$M`U20 zvB+z5n0`h9`2;eL?~u3XU(D1rZu3+PK+;ee$H6FQ#a*~aYS2|)soT4{(J9E>4KKt{ zDT2WAQf@6e0$@SjktJERKC2R1M;!CM)_9zGtB;QK=z(q*PI7TiU5dg%G1%31eAu0O z?a2%+G8V<#?l|c?BNulefl5CT&`|Ve{-$0nQpA+Fn_6+mfHiwEx;Nf-Y}gszLkjgQ zI$DYx1q>u)Ac0M7yW=Qe90d#<+B&XjQEF2*nA-`)&2eOW7A9tAivi-w^znqs%M=^x zN9aU?F+j{k?{j6y>p%3k+uyeM&4kWm5B4oSPNQ`op17DC{Y7j%PPBK=5(#Dr_MimZ zy-R~}twB;)C<)KXL^s~I0Idx0LnmS}lm@!syvIT%h++>&3G_$e2_)$4DGEjZD8B~? z6y>&HiaMc8m_yUa6FJ8GZ7J$RXoAG@B%L@B`a1)}B|@3$F1Mh@lS{p1V^>?^2m}%M zA3ifcHzQUi`bn&e8n)xqo_?kgdk?q7Klv_|9(bC=#(}kg*IbN2u?H7VP)FTle#!MN zzk-Ma3h&X)5+DHMfAgW^JeL&Q0-Y1v{Mu7VUewRcQ$Mv9K*qQPG>kz zuifa@B0Lj?r$Q~F<0%#pb2UUdm~{2SAhK<%NdAXj+k((EUqljoWZA3x(S|*NBj8tP zVcLUqA24gT8nyc=7y_NLB^~-`3x$$eQku2<$7GKP9KjvUft?WGXrkK{P)%{WXfoO9 zug=#Zm!l5U<_bT6Sw35P@T07=c9R+23Q`(4fD?Ee8tZQ)xB?*i4jqpLTI*0v@)KB0 zw2m0wG+cjATl%TC6Yc}wY1O~;IO;-)6^6DwJK7$8jhRk&j#1f`y^5d@m|T;G9Z4EL z)CWt4wmrA7y(vgdn3pn*A(sX>w!N2$dBLpSMEM6#;@S?mE?_^#uMxz3WIezFxOe-s zhHZF~E4)&h(xOwW#@NH^53OcvFe(xFT2_AyD)LJB?GGePRE~@fY;!B3a6k2NGh0Xz zzakfZR^AIlq%A%?r@bwnV}H~iXJ44+Ytu)fN8Gs}6D~)Ixj`Y1Ui*0V%HJe@1ct_H z+l-hdxWU!c-@WEy*wy^_zZw6F@c&=-l!VFiG&Wz3zY*E(xBt*BuDi*v)Ipc^gIx<3J8Z8I*^PEZjle34C2J zD{-`eM=)Iuy(Cqx#r2m>yWCCn8SbiUo#ba%czcx>c-iOSI+V{_)i)RpB z9HIvM0Y4Yv^oVnjl_!PY1Iu+JW8&V>fqjR z=G6(+8zG1>N^w?gpNm>h7jBz8ny44%1uM8D?!koWjzfKVw}#jDWGtRM0_ZDPr#Ok% zvX}%;kCai;R0BdT=DxP$FgHzej>wTcY&_X!nEi<-Q5v!uD!Xl)+Mjq7Nnkbb@ezpfCJj;((modG7HNjz4z+^Vd zYk*!^Ms16k<9Z2SGMUB0Ij7r4W9CBraQ@*~>%mz+EwYvU$T@7q*X?x$lnts~+-ltu zcnL4LzI*Uz_=&qbpbCp5@4&Qju`^+TdBzMM5qJqwlFN-+ues9gs@+0Ol+#uVj)(Yz z`Qe|?>u9!Gp4NI!S5mgoMyA(p#q7GC1G#o!QccLvjxT{=qsFs9Q18#ie7sZ0_6K30G>dKp9(3&2`E<{Tea;| zz;7Hzn>maKR_|~X#h|$3n5`|j6gAP4m|n3T<6O0g*$yb^eLk)6dD1ST(*!Q_#AwL* zYw-UnntU_9_u;z{|G%-nH{0L51BU4v?C;0y?{)Z&1vcapY`};83R?+z93#%zFbTHE z0aWxI_XxM(kcTz-OBjnl6Pq1o?M5RT^O;f0Gpv|Q|B^nLDvpAl(W3N>@Gle70NS3S zRS)hNo`EUx+)wB-Tq14m%$GSc_0u=_r$>ImHrUxTic>3ecub~#+HfrGKGtq^)pqE$9gy~GK@(frV=jTfFX@*VB<2acl>D9^ z?r?{uv)0z*?xx^N$wo=}Y6?rYjaGGM>oIpz^-GCwfSJ^kya%&{ntHi=3dQK95rIz0 zp7^qGoZW7Z327aKb z8q-{WC)`I04T!f;Pp`@x4-4^`x8c~4# zszZhEA+zJPpr5=e{>c;QpTOgc2o2S@N!*)p7*oZ{VX(NeQvE+a54MY(+F26niGZUzEe6!WCzR-3m^Fn) za6b=`1Ut=|aWoUwOoZ+S{~hY+I8lj}U(FQg7}nYeJAh;GQ8^EQj(imjH}!rXh5C(E ztlttJE4gDw-B&F3z8_=v7$G&duDA0=`$}f~LV+|OAMBHdk-)sOKt8t%H z0-cnNcY>mn=OvS>x8xYyOfSr^!`0a~fPmxtY)JAsd31O785OwTK2H$=5=DjW5UCIO zjq`Tp9vILKH4h*~PA1lU1s}m0v5GQEEAtU?lhm*L6x}3E0bReFxXGeA9YWg+ zIT=evyrbPDFq6-KBKq6=5&e7%+Jz$%w$I~Vj-A^iiU^2|T=DJWj{^Rf2V{pfc2rtp z=N%eotk(2PV*4QtCe_nW?$9KBi_>I&gB0S91DnTGkf_4# z6dGpPp$ zk8qAnUo{rJg)`-q1*j$qNEtXi2#O(;!m^umwdt9#U-6KtzOX)Y&IH*E-}PFR4UJ zmlksU$B7Hm5t?_sC#En+ybd9G!7PGnV)F-Okya@K4rqg;7}(+XZxl$Jz=!I$EIq@8 zSO7vSKCyRH8VDF3A;;CLLR(a(CVN-na zfXsRFfRJ7J@{lJBdWbEa1vHG)B7ih_I*K4ylXfHl;i6wg{!Ea3Kg#qHdytyl;Plu>aP zoz*KAaYa~xyy8zZ|9OF-UA1rV4(+N}mp+Z3Pu_`X7%hI`Z#e5Q(Tsg$LBEHx6je}~*{M#X)|&5s*X*+RPh7dUhCxXgzz(g!Wj^ z9y767P|qGS%Y8;Yd(14)GwRu6h$x3o&==gmV_5vfKiix|8ONw?3m8)5c1CS0U&xSc z<#*vguvxx{!P?40#x!(FT7NXd#(g-6EY?y;ig(7q}=%RY!6Ce(HV#%Ej z@f&Uj4xq>Ch4^L{gz(KSXqYVzJx0Skd59Ygx5&duqhWzO^cqr_J<`C^s^eAb2D<0_ zW2DNirBef7%oX?@jj7l1h3wSDKH?vk3=W0$b(MX4TZSft9>->H5RgjCm& zJ7tchi8d^QZZ$a+3x#r++&*tgOEK`Ip&WS9P#&j}h8mS#Q>r&AeWt)Q(uM{6b8vhr zyCs2Il1a5T)myn-Q;R*w)oANIk0d*R!VU4n5%iVxa%>d^1OH;H(#Fd)4#~BPL6+2b zSt>uemX)HH$`>)_UOC5#iphsLZh^$ zsR2*BsjMI{1M?9^2WWrsN4_fKe?AnzibYUG#fBP) z3S;{cm^N&oi3bXjT#8^Nu2Z5ICBFZ^;2xCdTKXbB_bu+g=c`NG@#e|jwFvcJ;0d%e zsr-UUPKnz^QZ84@jRbG~4*5SwE-$y`a)7O_rl}=}dF!UK1!;U)wty+OBc%iAa~WQB zJ5v@S1-MDe$`&%^E~IoK#>$CuvGA9S<))OUGrt=q0niUFNig!uxNC!z;Ft5<74d|&na;(b7>E- zuEcoFy^fvJSO?j{6#{(14@*42E(ytS6oDLNiiPbJQ*0hQR_tIi0QmiH3BazUPvHk* zd7}@1#xDFZem?neutREMt#l;D6aUygNKzwu3Q7%`SSu+k_>mIOmA0^$tvb-@y#V&d z;8nZ85aXGwq^e;vc&A(}_8*e#r%-Z4(u2GO7$L|m10m4OC$6ut?!xW3SmtV1Roou_ z+`T3EUU=_>@OY!PfSt)&eSt3Klo5r3xxhy$=ZU`p3lvxo_S`!h-*<(sF-5(D7??-^ z4Wa~oFpP14fy1NiI5&@ZVXve2Yv#S2K%V;l68&oM<^NmsE50J=XI&Wm59y;0)swPr zoDqMuQ$!hUuO6%|aiVTItsv5Dm)vXwtGalcZlDtx zDj?8&L5$v8@Slr)5ebtN#bFsb77%XcRs|PjDG4A~0zG(y2$l0)7Mdf+w|r9s+u1ntGMoCov5E68v+>&rt|**_#RG#@;Yci;AbY#Sj#LH% zW^Mo^@zE-pTfHAoWp1XS-+YpEI94HB7D{4tX!lzHtVQV`f-LY7zY1vqN&AYOwqMfz zfezB53|h~89g@a_Tv~JsKJ|XMjc!8kK1V}>oB=-5H38vrt41S^f>ncvuiEMjcxBAV zv#Lgk8jF+46$JzalTe2ieFAT_`x#|D21my$ty8o zq>zgy<<(#0mDmxC75SXm)jl51Sq#PRK^g&L6>4Xvq5uVPARE}HP>jq+22L^1NWh1* zKT#w3)o(l*f0(}sV=l1C7*4{ngitatxHpQCs(`oL*z zSqwSA!y9N74p2q|J)xrL>E#vhWI9EMD<2|ba6QhsaT0@L%>M?qn1j7-@4*}H6?opj z!yKoxa81x>;fR)1ULXarFU-u(+fX2K&-_v8JiO~Aei>k#>9X@U6XDeOwtbi*uq=jZ z5YA`F{O^hrT@<8)LF!_d`G%YNXSIn%VDqVG7()6o@odl zh@~x~R&$dswKWMOe3${ev|n++Tkx5rNl*E7M3)X+32aWAGPF7@xiBBpsBt(L6T2Eq z|6?YMl~C5xD=K6~KrU5L|JpZ^&1r=>3(-;B@Qp#pApM|kpm`2uCdR+NR}@H6M)rtJ zZigU@fA&C135z@JcDn>ai6<(URpzne+AgF!zA@Ia zJlF$CO&l=Xy;H7-TES~?S;V^i)I{75JeQC416dcCPoBud?`Z^r$b2p^~KP!9segB*nt}tf+`@U z8ofonhKK>U`R8=#iqaLH@W(jg({w@dtCO$8wtKi2kZXPcagbgsIn8)@a=b@hF}Xkd zHo|b=ywHi{>*#=Zfx^P7PxSjT5Qn>5B%mzP)Xa&1N2y~KGKa*PZRxdq2pmmLp-K<# zH7mG7Z95JzKs;>a9Ae6oNba~m6<&Q|p38Uz2KGg`?E%A~VzS;hZ1G3+z7b2O>U|$s zHqyev0DZ?;Yi0$_-aoW-KkMRt1NvR6a@$qKk6!0e^DW|!Vod(d(l1kafsZga?Wj*8 zQ}Su2-v_w(l~*!q?Qn1p zFr1*+D^|gfLzw)8>WEEc%)!>v6eL0Kc527Qgr&d8s@M=AovLIy$_zcrl(yp^6)*;0Fv4 zU}YZB8TA94bp+cR*0!e+?xW}tc%X4vFR`I#?cRkBi+UJsF zgCqPZm_^&ZHOm8d+EdH&5#HbRwu-~yoM#3_=3*$~oLA^c*DLT+GhQ((^DTFo0X;mbY+x|@QT@g0EZD;<89;dw`xU*pKMp4oc*gWceO+>m0WW?(04J9-N*#sx`dFJ&Fo+b@;Ez zJy_JjcgoWH)~ZgFz@=mph?8y-_iB=v!O%fX0!JsK3qJ+m634^onSyw5H|oPOTyJ<- zK)D&330Y0}Oh^FDVkVFaVd^e`qX=bY1@@491}e?hF6`&%SA1z0b?y9|?U9PA{Qq z$t~uD#A7Hf3L-G{^7y9gi2>8g(SBudXn|@f12_Hk`yi%zJ*jnQQJ!E^@7NGV2M%Kh z<#Sj`XjilgOV~%?vjHB0Sj!XoNXto7kphWxs`q-c!zWA(@9U<(jD5X{=^dD1 z8WLE>VqlP9h(icW^In7j3S9xfn2(SIHC41Xyutni6*!rQ6L;S2Qa3Oq%2*II;qcnL zMh!2^%@qZ?NXY=i44;B-o(vhh%05?C(rV>VDa!y-7<5?sxqVPa-MMo32TruT;XfvL zx6WYOMlloL2ggX!3W!(=q&!Q&1}$c0-@wxzf-W1A+G3+_CYW7u8a$okWM7~i8WVRxMO(n!=idbb4ArO9ULuWM@ikaVVs&fj zSFW}@Ouwwpo;>M9T&(Wf0Bj(BIRMHesdOOmb|oW+rQ1SZ{%P!% z0Kz|s-RrxE-F1T9+zVm%;OPPE7(w7X*v@PZ$W6Ai?VRBC}E`YH5nU0O*z{yxW zH~RVK_>x2GxMOX~%^MRQM$6t6p95|d4?diNFvx|9aHl@CG9!EmLt3o3G;2@Y z>Ay7eS2YJ>X)87962#sblUj zSOc5NUNl!%p<*+)bnWdKBQrvuvW*R*)FH|yZbWHa-i#1VV-e6Z7#RyKH&AB;Bk)IJ zX*(DfgMC#;c;K-5sM@m-rD!}(Vkd$?6|>Gnd|7khjQ#+$J)?S!{%)4G`qM}RA9w*t zCOr0`rB{8w%REc9a0RZT~KVnxy3fH*j%UBOgwN%JVGNR-bAiOf;t_~U!TD*3x+ER zD+a-s2Rg{gB%L0pNmk8gM}r7}g~I{O;^UZCY*w#%hRJ4NUHn!V$6Dky&Q=n{5E|Wi z0kQ-K9s%0`6$0)wfRDyMVgtON09B2%2LrSLiCQrPphAE#y&Vi6k2CT$TkR*nK~1&+ zrTWroavFx`HhDw*-)(?#e8X(CuB5f(;OVwPs?p8uhq@0PSMdRjX6_>)!=vZP!1Inq zGkro$iT{<;uHt~177LA(;9-V51Hj|w0l>(0hQu{HKY+XV-T|=TJOF4bHJZ5~8Y$7| zFt$bt#u#B{@PXJW4rv*sfjW#nv-$y}oH_l`N7T|oPL7-m2+_1{8O2^Jx&gPJQ<0#AqLR+(VrX2zRbU+W%%~KGn6aXps5Cl- zp&nAgN#U1BrVpuk3$=cyFqGv~%@4D%MdUF%d`0;JmB3`|`~GO?_prg{U_0rz_{Np- zH{!_BJZ{Etzj;P+~O`+6Zi9F09|kV ztr=xQ%w{$uEmM&L#r}3W;ug4^U-b?`8AD8CZ4xCa*v}HqM3=SVZKu}wbBc9o6RvJz z1949kTc~<1RB1}0wtdk&ZF|*1iEaWJgvfp_!y@*kMGE;XmeHavj8(d|Pgdgak5hBEJ#aQ8!H=ws8n2Jus|`7`C~{Ny3V_Ac(5j z2XIm+gmH?KnpxgqCavi?3Tm67$oE>5C+l%H7oN@L7LJ5yA;@4f7vs}x7JjkRm0IJN zZcSu*^e{^`cd@4EB*{Nn(j7kf$q+uu=UbbP*5El7Ex;$6@94KkbAptMXM#!oSupNPu2{4^iqOP98RpV(0F6I*KY zQ;jK!AH+|jl;2{RbNPvN3P0Vc%{`p>B>Mo8KA?EZ5lUnx3MGtCXDoG!I-e;~kv`2LeWF#s*=U}DPqSIL%n~kZ zu3@@0o9WTrEY;k>nxgY0|1Fa4aMSuB+*HQ5Ha9(h=U8+)KFLl0lvKK1fU_dAnH61- zi-@}^xTi75ATEMbVnfVkHY6?6hjGzUHWv|Cn^z-j`GYCe@y(1Rv@l(A(t09>_OSWl?@Xf3d|c)f)^2`)xjOZOkp*s zpKgj5sK2?+ya`z*W;f9t%P4lJ{^24Vg^R5_UPDUITrsE^v`f)ft03uFjJhgTUI>*r zpmj>1Z>bhxBW@I2&IhA;9_MDrR^%Wh($qe!>9+-!+S3@x;sc#xPFTOm|;UGbLfd2NE~4q0#C1VK!Ic(}>17n3_+@z?y-EA{;iG z+uX}^>lD+Yw-AHo1^9&ODf!=*bOJ@EtzLyr)3(or64}kSyCx$&7VW{aGvLy3w$*?q ztD{gOcO!?kV=ffP3?e1q&1QlhI^>X~6i8xh3dU)p2}4e0uoXz6Z#EPCv`iRsDwF+9 zmqlvwjsp3FEvktMhFk!Q=V*`LM&os9667@7hcU+n`latf(@cwri1me$cg;}kk+@hS zjo)G!1YtxsXgeyQH?pe4F!l;OHUjygI)48Ts%ITt@k6I~>D(7D%zQOe-qM(F$lU%l zc6%ECsX$(X*~AAtq2%Kevt$~Z*wx^ft0guU7BgSR*$zvARU=YhC9!HFymj^T;V#d3oSL=>fnZCa-T1FY+p zg8jGywLH@}OD~Kv;jaE?*<;Bfgp}2`&$y`HfQtj7;jc8_J=Fa@SD-sL*i%<~IOCpc z^;kBJy&}5tlEcr^{*?kD{e!TgM}_!Zp<{w&jf-fmq;nFYw$Z0Da&Y-WQW@L;=)r-l zzThdi(=`1jpjj(ii3&A7;?p;x4}u=6{>R$D8)V-gdJ@ghV9wE1JwxqxQb;`AYdyus4 z?;r-@kIx)>z2x8~SVhiifp@SsobwK>?j?IAhU2p=!N86xTdP=4kgvD?MZP)n3gUnV zw-mjDFrh^Z=*t*@z1Yx2K={BZY+v=Z)4QJ_PH}nycv7yUuVQO z3739_JRQ`243n$Eyd5VDB%WWVisz@ola?G5D9mQZ0PEBOvAX^JXFAUu#Hc7j*rZcM zxI(=XLAY7#;hgu-5x{Ajb1}$CJ%KBfJ^&}6V&lZ8^WxN@aN6I3h)c}EmJPw_BYZU! zs}38h{SH=BGuHsXf3d;~ZMG+F0!t ztW;;|yQ|W~F1GQ(WO3-0m)oJhow(Z4v-X~x@PA2v$=;!P;@H=!%D~0lf!-W)0_u_R z0r`n|qb}EJfAz^Qyj}TjV1G|6zMFw?Jnu&kSL&9gSIn|0YOBM%82fDzMvO!ZYAr(V z0d6U)=aSRrfE8oacxfWjtm$ilE&f$2euQkcU7$i#J` zaxINfAAvGvJk*3wm16#qDdw-4f?H4S!>~Tb9j(RdcS{bG^kNc;6cehL_w{?R zKDmx2RW?kSRP{SBuGMS*s?Eq6`coR>e^!VaoeF87`@#diYDAq;{@QfJ#6<)w?vOui;)9ec*7O9Dw^1 zzvJ2gyJw+Z^Ex;7HWTJt4`!9)R=9&JL)7fv^l7J$xvuJjgO2Pk#rvQvsawI+9uM-L zcT0@r35UcOzyx=AJAj@Nt&5vQIhg5js}XmMa^TY*84A({HE2`pydZBO$m%-6+klNz z0^8^Svw@sP5Vam z9&9*R`tOfWr@^3y1_Z^{KGk;V4Z||@_B>pV`$

xDDg`FFB5lHgzTu6x5#T!c@Cv z()o6JaWT}r0@y&HQ0C)jzH%wYI+Z@@j#4%)vGua6bD2jDp4iqdmFy|Ez+X5vd9Ww;1NKoj@u6!uK$p z#vrOZhtXO~Z$G5g09N#NSu}G^XGIz9n1Xjs1AGXhE%+s4KDy9(vL{zD({JMqm?ZZ& z)g>jgAT6Zm2~a-#b%_2cDh51hv%PyW$?K zBUT&8gCOs)`e{$Sh#MngE>}3ucn6n+thk={mT+x&3ObrxRF3Axqrp?*;V6Ne+V)O^ z*V^?WW_Z|x6Cbi@nd#Q|c(Bc`2XKc6U*{u)aJa`Gj)yT&@;Fe8ULbRlVMtFx$tv0d zL>^p*W>VuxM(lx`k0#(a5Sq}bQ14Nmg>rL@zgJuRG~dPaw{SIuwwekX>;nkzjM0oR zr_%WGZHL}#3dVJ8{Y$Hg-ZOgrfxH#h8tu}a?xY9n;L>1s=nFXd6L)ZhBl<<2wx(*_ z_`-%5oke~AzVOQ!gH1T%i&Z4n)+`m?SM(le`N{D(h(P+`;1T3mhTOXemnm)gs6s?2 z55y5kz8#T#mBB#T-s6J5SZxn*FFMP{m!t7}0&!>}B?kv06hR`l)#hg@*uE?tB|N%ckTG$ZL%5w=hIYfpvlL=;%m2)&pg;Eiw>!m1;pJ1#21 zwHnwNj(F#gdel#f>alR_uAXu!=*pyXbeGk z$a-D8_#SI*Mk;3a^Weh46}Ok1E`is5To9iu_7X6bv#!IE6H#xmsJG*&<5D*$=c+9T zwc-z)3XN6wy!F6{g3BKvCriwG+|UGZ1FcP+9_)9`^qw77hTQ4k0a6VO`Pc{X1C`9AcAL)KMVG} zZV&AB=vGd8Ed_Wnp*G+Do;LG6(_%6&zxX-IVRf+j$1KlVl$r?@oASrH;ef&l1cLTd zlUR#8l{0Wa1rDa4@5oYycINb&wHh9Vb zw*|%m`Rv0)l0R`pO8~MDy!d;|EWRCL)Y?r%cw3XSt*twYSefC8)HCK38c}ZZbF1V% z&T>&wVSJR$hL;RJ_14k2WssM_MNcxZS-^2lCY0)lRIz6P%2B)|lt%ysMp)1$_ban< z?X`s2%-2SV7;>Xa#+3bcLj1R?y{0|(JeOAzEf&NkA6 zw2|&Gw)Np>Ec!k^S)En;sIjXRKg=jU0SyaGW`T#)EH`N){S6rg2&1cn)B_V6=QY^s!2Bf5^cnz!Op+c7)ytZA{$}H3Yq~O4_SQ3f#tFE{`pC7Q;jkmC%B?y1w>ib^q=#Ila6r)W5e7f zEXYH7!gVCN8Jx&1J46&_vL#)}&a9nCMwshOJisNa_jM~-(+LV=obk1C z_OweQ05<3FE>|C=%$qJ_+jLgaJcAjV^Y{!wv`wTFb+@CUbKqe>%1AC5+LBGAjB+(x zGazL)p?WYnsftm@b|GJ$DeVN8Lhi8jfZ{c`NwdI;$Zs1O1a0W9?>{gwqK1qmF_@=p z7MyKRoEjUdlj5nxXa5>!6tSsl6!A$$5pC>;ZPKT#2a07O(zsxOgH+6dz7=omwbjv8A{HOTj4dWB}tR zX~clWaw9hwR@+`t)*8>ku{a~jh@I%wk%6JSEHi$Jm*3WAzCD2sNwqsw99d_I$j$<1ia`I(rx6caPs`I&e(xk&~nxaNA( zA|f%FqRD5pk-HRck8zJuTsOi!3R)sADiM;=Xq}-=@6@FXFGE&}hhJcZTfwn1S$rUC zo7<$#=?pFeQ#ABY)<5hpILV+GoKM2w3><9fm#4@t#7v(i67PT+vw|tc{yTmuF6AN1 zHC)#@9?lhTr47r`MV_OQX`QaFv5JXosQ5KI5f6Rw&)pA}rhx(c6dK0No%o3V9Ec&b zG?p%-E&b??Hdj=rqxcB2RJM?d)~y#adVq7n2^SQg6cB+v3t%~L%7*y|A*XHIjT~`* z-rz)ly;F6#k|)}^jkk(c5Q5yrilHxMntIubBZ#d!^RD)GfzL(Q;X~wC(Xe8B zsKXc}=U9%h3R>XjWmP_l)4*i%#KHo7lTL3HJG{W1Oqa#|cYRiQ|jxlyCtIh-esZSwvES3i?Wu z-t)?$V3$i?%=<>O!oBp(3Y@}yv7xP~R}^53V&(ZBRKubbSVNf6eWUal3i0sIlZ}dv zaMr}$pfnpPdS!oq)jBB5ER;xIYEcf%z4?q5%4f|>CT7;Jb_ zhfY%*WFJEV`D7f?B-Q;XYK~$wmFY|vrek`hoaYxaED@K3i3Y4!P%`Ue^8{VUVfq8) zH0{vMXZNA)nFGTyb?8m(f^M@>3Zlh#Idx{kF8W{Wee7C0b=d~i0vgjG7GNckTRzb6 z;rj9dSLo(aIpq}^54LdYl?ATU`&@k?eytbNV>v=4gvt%c3R9y@iw%cC5N?amG^oy! z(*$H&YCnC8E5qLxI>;`ecL*4wIeEm=UkxhR!;xv07veP{VI+SHs-(5gEMw2ql$=&J zP%-v#u8TDmV7&5=v>x>{f?Ym_&o>}m7@kMP8t=1n#2P6jB(FmbLIXNWuY&PSJzjL* zFgD>5`)4;qudI$6ll#maY&k~9D0a+WzRQfTeQzgJ#N0Tc<}Lxa=GGLzAJ`ByV;b-k z!+s-j4k*RD)~4zaatLiLdOw;2vk%(lgF%w# zmAweG9H{`eLxPw!3oZSv8&sEZpcR6kvd(eSh6Cl{T4n?^9H3MCim-A_?=Y|DHMWtd zd`XuS9yxZ)kz*V@Mvzz>JO%L`;PFvlOoI`I2Y^_{c*)YUXQOi1 zYT0^@C@7#@W{qPvX_5Uv#}PyHf25INfX-Vm36tJOcr;)I9C%7=yS3(4dYGV&dndw+ z=S%PnsF-N3pUPf67@Cge1BluIVVVTLXgY{$Agqkf!jl0TD7ML%{wAU4s04uGDH!3M zrvCSr&la(sFO;(69>D5s{1EfGShd~@b z>op~nEOZlZ6Na7zh%|Czg3l&!#xWl$4?szi2cUF`JOHIj3(BB&t{xhaf zRQ*Nd(I?E4ygAz34rE?kg^Va5f%WnF8n2x`!%k;NaQiwo+*DIX&0g=jDU@^dMR=mN zYCc3A#H^<>Wz_T8c!}f^ROP!LI$<9rRAVu^q0nO=XgP zs}n`Ij_w%9hu`Y`^daxZ;rGq+#aqu|J5hOpK9oXm$WPZ1lXtXRJMp}azg5k*;=01T zjL=LR^xC%+VdQw-%1siE9yO(ECpJu1wGO27Hy2qV$uQw@sa4Xt_jy1&um-p zbM2$Z;eSPoJj79{uS2STj~3zHn)$2ceD`+fW9Hh8Og|7BRcbb|+(r6sk6QZ68;aO^ zRtV5Jr8={~v&v{>QYxn|)pHjQ%PL}83gvr*LPQH-n@^$dAQYvWphAeFyn(I4fkmT{ z4-O}$bS+$Qh5&07lQD_P7OpMc<4Ym~r{qx{7baWUkWBfk2%g^gLBlXhtk8dra)+|)-fhYIno zzq6aqJb-WNr{(z;c|I%83pisV9>;(hN{gB!xTNFd?n{ZU*&qU;k)LLRh=oRek`gp% zSq;T(83e1TkdBXd|oy27!(;MY8y?5SC8wbVd7U((qP{A0$H)(Vm5x*Qv(~^}cyp<9$qw=o?U# zi#MmQS@Q*S?M3!~`m>Xk{_VWyH(fdS?(%=~KON5hpU>a4@%(4&JYW9wG=~O+m!6&u zKRun#T*yrq@zioc#*O-cxNPPO3pXV1wA_YS-D%C3*2&mUGosjLKk7=9P#+5%#{B&( zHfDL5bGtU9Q-5z{3(W)C%ucI(m;)H@)3^uQ7y;KS*yX@Y=;#b{nK!W=9ErG42tlL| zdI!#9mc;rrjxC5+F9UOnzYv`f!Jpak>D+`P2I-i(5J!wtVMMs&s#q;kktDKbVA=kI z3E*EY+rNy{1Zc_R@*S{`9Xq#3iXvm~Vq2ne=#?Iq z{-0h~@&{@T#F;lBAJ13{VygA+}l6$ne|`wX7~C=5NM)Rnoty`~mx61>#fCVSP8`Wv}n z3@b7oD~XE)+QbTdv>85(eV+&;TszeITstOC%(>hS13$9XH~FZ4r&UcUR=Ash_Ael_ zVBcDccJqDkFeoHj)cB?-M`?P4d1=TZW1}&$#K{x4&uISkni27% zU#4CWPA0?Dc$O8aC+mmfq(pkj=g4@2QY`)R%*;lh@sFVKi5&7zz?=BCe1lRrhz~;> zu9YfVfW?QH0?9RKr0~nd-~2OrI+2C!@jHpqp7?cXm>tW;?M8MJ(ZdK;Bw@J*uzYQp zE8{tMGxaC99qcGvQ{(HGuqV7U*nCTEui3Y{%Cgcz$Vs$&6h;b0;%Jcup|4r`lFoDn z`zjiQ2Efpy;!2v~E{7q;w2~o0FywX((7wMWKb19b6!Z@;fI2)R87w27ar>X48ao-B zVexnthDBmAkcG|?KtROdq0oxY>wS}O0~%gwt3QL!t200@Epi8JuUBU1x7&(cbdY?OdC>DJbjivE67JVE~q<<{B0Z)*|8Ocwm_k33GQOjms~ol$;OpuG!3(uN^^C;6uyi&^~FLmVMS<5?uOYFXjHS z>+L1wFPmpC72G1k3(E{^gY%ia6dHSGZ3oq}%E{;%dKWg^GLWT(^I0!Bj>ayVV$W*~ zaW41d|BKv{quk;vQog`!okVPd_A?wDQYTQJoaE!>oyZHGxVqtYm8cXF&&=A#1XKLo z8>V-GBb#d?mNV-GErYI+)A%7Ks`61UFaImYQm0~Yx;jmBLjLQcvg8>D>h6y?&r(WtRlVhsOlbN^cZN*@I83xrjId@|sf4EQ-qva%+h35RYLK41C zN-|tYhV&;X0HnNG!-)a(CzR|b@{@j;ReAmwGFLZ_02^F+HD6(m z&MHH{{7fOcqVa=3-04=&`0j70sLtnWm9@rsC-$})3vHPi zbPIl_=&ng`aFnIAYZ4zd127yTxT}V9tcqt7f6^OW8CBNVlkC(CURK)j$*h4Qpz{Aj zP@$|sZc3wES4L^yeaU;f)vgHY%;n^%5-S5pXnh;vc9gqpeWGZyoLf%dCGe#`7i%FMa80g<-R!=M0LT4iDa{yh7~GNN6&1JtmT zm>>LPzupjDmys}7(W|dVTCRYl6OH3W6Q0z_ua9GxvL%TB*=&nBqa=d~WMAUSHmzTx zorj_R>g_lv;Wd@mSVs?w>x?>|CM3n$;e5IivynFS(i?|w@y$cW6#;9OHDQzo;B zF=-f3GN8OOhB3Q*+tRsl#?9@2#%ZeXI4mg0GDCj&edwcYSz_uv;Vy zI}Mi*wMwmdD!Mi{(jQ;x>07huHCA$3$I;R2bh*dP?x7w6(4ne}UU6!%^sX?y!=04O zrfpL-o9%W{VAZ92T(D#!KfNKF-stMO$ATSpG9$%KpfZ-HRmRb5dsm8i zXrxP~3}LsLiAkYSLI|OE-WsT@>^MqAv;J1ou>WB*J z1Jz-=%O$8Ss_82cD34l#11`ZAixMQG68>8WmMtvQ^8KP(`rhTh%_vRmEE6=|c42=P zz8019X{%_9tLRUU^tZY8J+6>yOR&KuxVNa54@L>jB|(s}?zi@?D5|A2O7l1147!b& zj6{A}RL*M=w7(`zm1g{n)SQjODn+ zCnMR^Rr!C48eeY3wS5&wc7-AO#iICw=crL_pTZckkpIzt?MMG^7e66P?{#^oob(yUCuPqa2PSz>WX+3QDny?s1w$ z<7i|_eg!g0=oOEoUS!t%kI4z2u>6(!m0$PMkzg2+J`VR3)VNM6(R44KsM2?3)9Wb? zB3Y-V1Q`QXGZ?JuOV*TR*OgStiDNPIEvo#<-uxX-F;X}NsT*LjTyyeB%SU`%#&b5h zPEe;0VSuG9A;;z^-;_g?d=4eE(JMPG&1Lq&#Oy4KK7tO;ZCGnf$%gy|th>uqisPo$ zKaS`a1AUJ96b$}sv*!BTArx;qF^7<3B>lASdM<4Lff`kM6`LUGUNL-IZJUoNX?jb- z`u#dIj1h)y;>fh8Oth`3M$6gcm_f-E(%>aC+BM^TzeIAybN2mPe%<9Q|I9XkrqC(% zYX06x|LZ(BGf1!cD8Uj-*+n2#l0JjdKF*@6mYZL_f5yM)g1N1q4X!{7v_D)u>i)qc zIpLZ_LnClGkbE4BsFJQXLIR*N4!Q-O(Ew=OL79UDW9u~wnpA!nALXs}3qE0&RPoWKfT)Kmmm-8*eu`%?DyeM>nPY)E##>-dse{?lB9BSU4=yTJgxyu;!A!(Vea zkD6I-%}n}F(~^8Wh0xbn6pYg{UKban59nvVK8NZpr=Q-!cFrM{9a-{)&gvr)JJrdc z@tD@yJH|QFOf!1uLq8`SA*X%I9Y}xwQA9OJs#k%tBFlzU?g1q?8;Mhs+%s|JQ<2=% zT)VQz^fq^SL~pHGDTcnrIKYJFRP@%~3!%9&5fNKkCF2t1UvNga`lYdnlH9i$u=M>q zqrN{bJ&kZepu=WG?o|xZk8kujG2F*DI@;FUsq~14i*%GJH}6*n(aUx*&fpcF43?Ro z-_tT7mhd&VE7tBxl?$OWaQzZ*Nyrw_cmsyZMZw8XITCJjrD)*+L7?tSL2}J!^Ykh&ldZ;V)Jmx-s1KX3;Ab{h*RAfH!Z;jo zd_-!^}QQtu%(o@?j79i`&@1a}U7kH0k!>K@1ZSNSnW@?Ub~tu5-|9D8IJ-v6bI z*GRGTTMRq2jBEKP+0eZUM;~bXbm)eJS`>4S7M;~FOlDNZ7rjf$ZW{a$Dz#&MPXuR1 z40!$7Ee8uJ43*qD=a5+6D^pT2+X##Qp&D5PwQxO0Y0HQDv6TDs+YP@}r$C>uW=F)q zBU9F3Yh2$`kf)9=KIcBO=IEr5^kg_3(~scr-xQ92b8vj}E#c5*@I`POnvhPkzN~g~ zD3b>)wO730`L+&E=x@^W!$ZhG~|cl8FRtXHobH6(NdEr zIXAu3WD^#OHTYf842zrQYQKB3Qr9PvnyDlJK)ikgI3%LVP)6`FI-UNSYp&3{nF@0VHvgoqWM*5$98?cx#(l^eP1aN4jLRJ3c z_f&M>e|haYP|i;wX*S)Xk&(3=A{@s(LX&1Ry-|%LvM6PkzQ+O4_CbcCfPia)%gD;|j-fwcYQ4+} zSoRxmNo8glEs2s|4=75y*Cp+G85l^D>ETd4sW2T`@2A&?={qCHD$4qc}@G?wJ=-=X5P3*=~};S3FM3c3k)q78(WNQ7~WWRu|2 z?6$-fWIb&&>}X@OPP;r_Vf?h?cpxvNRH4ulkh#*9_Zwk2^xlhGP~tN0$HPK4qXFaK zJ7CSd|K{W2+em8D!gR4GB{3^py^j>?-6s%ZPauS_eqXpc7sdbN6!DSNegEH&ujTT% zmd+A3n1$9i$3|Gc#}7@^rQ5>$n>NzhwyS1jKi*3E2lyc~wOyy9n0e#4 zwC~g2R_S%hlAYhNoT7%eW(o#df8lyNMd2;qmDDh&#c(1 zJief55ec=7d~5P?S~0^5!)lVrpfe`9+2nFN(V-3jCE@Cs5h3>;J&DjYBwgP3oI3Bu zDDPb-=Vi~>`aIM`6s}Hrj<3GLuJsASsgP20MYwu@)Iq!6BBiFVaP@ff2^yl`Iyt4N z!Av5e!o$^DB2d3{a^eC2nhe9$lcQqm{$a|7DCK+qVag3nuK9n#0PoG3uSpU_F;vy4 zM@~)|W~7aD{Cb#1w1%W3pT{r=&~Use+-ghn*Fiw;rzo{WbK_aa$JPghDOugZxmA8O zFkaIgcjdYLCs*qDwfOY#!1%OI2Xn`dsI_YY)EcCF5CblRRuDm#XiC) z1y8o%>aygDZ|f~{JHJ8WJy@??WPE=p-xClHq=-}BwQ+VJnfZ*qoXVUzLlTsofXdzV zB(Q6yEmSL7vueMrmlZegt7=DDu&Vu(-ZG8+290-8ZH10NB>W{(9jS^X(=2KgQ6Gw; zn&POL_Cn%0_EPRI`K(^F4odhYn*}D4`6ixWspXq&<~&U4n8pvJZgcfj#)XcJ3mq31 zI-Zy8l8OBCpW+W#@e=N|NUfPF%bA*nfXT%PdI%ABTr(gNqHL&}m{O#;L1C}{-++K( z!luk&OQ9O4J}|L@-n`7Z)wkb#2Wce$UXCZKWM%_^vvXfv#vVBu4qn;V<}LC*kb4Im zksrsJSy^tZq_B+t53*dVEN#j{H+OWHS_FI`(-pO0+^sXRt=6`4T*OC7}d5Z+BqWtp| zN@Imvc!VDAGRX4WPgzst&1}tzGf*H1jfv+4i%A^3AQ2rnrNnVbX(Vy@D}n7zg`&Lq zxOa8@5p+1{1WEq+!$KKXl}PVXlJtzi$3W}eRR)1(QA^mPgl3mNp$1$$tbrd7vCg%Q z0p$L;Lr~n44;33~#+I$se6u-7WIIHaR@lEP#HL@y7elT(kz9T`fbm7u+NobYfzSMB z_zBXTN(5~r$1I&f39V-@;3`N#&;vw021(5VdHJI_D|Fls+)d zl-5&cv0g-3(-th3FG(DRY}Qj6B`%h9cO{GIOy?X?^ViXfaFEOB*K{4ptPpzuu6w4Z zlZ)(m+OfsA!SP~64;)9}o1P#(e0Yjzo468!=xX+n3%S{{)cLHUkQiB&x%;QuycldW zh_|@2gUQb4g^%fF=w`TtkhyTFHH_=q0fBY5G^{jUF2bZMjgMfmm8fthoL#h&Ds`1G zcY>;2)8T%@ME$z>I6Bmf6%^Ae7ub@j8L=%k;5?y*1f9e^OkBUL)O9+)bVk2+C-iQ9 zA3ZGmNR+P|&djUZI1BsEMG1rW)&)6v`? z7T(1)Kd6pz9=lnmf97(L_8|b7$ysRjL{KJmEGR8$orq)a$Omn#C2$?kZN9;V; zKrPUIUvF54-TWbE)mTIvvi*=}u$B+gWgPmCqU<1a?qiat5AQ6ySPhl;9aE7_FYjC9 zE;(LZ42j&69F~(j1{)Nh9AHTc6uF(_^zPsYrNI@PM{gaxg=yhfU!Tv>RFq|;mPMxU zoFC?xh|bs{pI;^4sOS<^oX!&(d5J1YA)efooUF8icDeazoy=6bh3jmc4}k&hi29PF z;Ti6*R^cRVMIa#2g@^#p@}qOK@nB5k##mwIe2j`YI>XJ@trhsH%MWnJmE9p6ock?@ zi=~J8hd3(#vM<+FDNUzzby$IeSq4An=MzDYC7tJv?!;Hf=}hg;DFBWBH(kChHvrQW z;h@sC5-wnG=}IfS*IAoWRIl1D+EW!^_SovrsMwuloT;yBKhXMAoH=etW$s^9LAnA1 z)cK=14{Q~wHAlbe#)oAa zgYocy)3IYtcG`9zb`;#G^zxVgAnJ3_2Q@Pp16An*E%L9~w_SPX&yid6mv4O9%In*x zN^07m7=Li!J%95VC4Jj0XkKy9k1XiA;-EV$sHr%p%Yw!i1?6=IfQ1e%4xJf?;#a9q zulYlFg$ltiH=_;P*f@6eG!s2kbuC)w>?LlU&G5% zZH4?Ocz=fJ%BVhIt1O9L{=LU$8dR?;52P<_#_#Gy9jpkj*A)EAH#SnDr?gC z{+RK{$29fFG#wvvU4P7V$H&a;kC}ITOk00UTf`#@NMvkq2l8QDVu#al|92=BS0(t| z$K1%g1@k(4!cD_lhHwi4yPq??>k_4!&U%C*cn3`D@Pr%7S}uWV&!2D+>1<3!%w~rQ zfdLIZF7!u)Qtq!NjOFe^cz&wyQGY>M-&Xcq)=ijK*7}{k+v71-mMcwbj2W|NWt8Gc z6GRTjK70PT47u~@a}BxA^W4DS?fl7(YYBfo4rW)svI;>21GIMhjh*IL2s*lwuoi|I z^N-6@-i|Wyg=5dDsdXTQL9@sg*;)9*LG6gXzMyva$>HTE2C0P80w#s~(M@fR+c7Lx zHJNtkXm3TZdbEJTcTGIo8AROY4i#Np5u9x+^TF0{lTs zfPmp~z=$YCvAco7jyBtf6LWWAvX$m)_&GSUFRMx195FMwXI|ooUOY!KXe7ozLOo)s z(rOeOtf;7;v8SrRf;f+v<@9oeEv7*LTc&wNam?$NUdr+jj}$iz&(=m=5Ov5L5|yw` zRoliXC%<+f$C~ixqc9vaFYB}yjPtwf1><}frUi9F{bkw@5N}_0tGx{Om#wjv5&kmS z7X)=!sjst_N`Kj1_A=IAww@RDZ!AMXln9P$IS8oW!4NGLcp~^^r%P{5)#??ELWk5M zdPRy=@!;Fwsaw=pEn@?YV++5^<4 z$=n*9tsSoH{V1@#>#4ajs;wu3dGJ}BVQ|)KkI@5%;N<{gkJmF&J^5vX3aJe=2O{SL z4NcM*UBq}oo6`9>tz^ZV)&_9nUVd)iP(kWn_wzHWm!J9rearx0@+yDlgy~JKe}ToJ z<(V*Pcxw)uh>@+&FX&BVh~W2NP)9VaoacD$CIwG*?oBZOKT4_a|) zrK9!%Cpe5LOVvfgYx+W=QmgEseg{(YyQAfsV`N*@n7DZ+VI(F@D!*}3(AdK~cyWM_ z`KwqgBs(SNxxIVJ<(eE8bE=>Q*8)A+Nk%QfSDKjYrnpjUJ)?N_Dwhc4?m*XYTy3@> zh^vlwKOJ`SYZ(iu*~8V>MpzBLCNeiHiqp`}o>Pqh2V37#V2FUqf0CB>moD7pFQs(H zy(V+kCY{omJ)EDL8ZW^wBzVbx3C9|<#S=j^QqQL;94^J-g+>kNfD)EYg*>xM+r;$w z=b{kf>H1X-1p2EiK}VdR-|tq?p_oF34y7)XjQ*u&q&(SFn2?}ih;KYPM=OZ-g}s;djYRZs1IZRmgfZ2xPEz1n!k z|Ib7>dCg}TP!^m6MV*dmm|MOwKri-FS$BL^qQ&3|ZNqV2z{qd?tCRs66;FRoCTDJe zAkOd~B4g72cETkspPaC$tfe-0@l!c02M^@V;~85?kn+deWUUF}7O)w5%g+q+SnVq?Rc5Diwp+(yz(p5}o7}hGM9{L!pkG~fD(M4#A9=Q*4 zoIv7SDqOPj?GirlHH4H`zGS=jHIBw+2Z?P@*3 zh_2cWqPE*h>yfI*w}_&+zsNu2NUqM zTj|&8V);YpoVP`uW@PQ#$%zsj-aV2|l_WrL=UzTy%_Gd#Oya}FUcXyLlxCB{ zR#6l0PrkVAdwOyqj~-#?NSS#0W(gmJN-bWj_FLsvP&_YuLqY}E`@GW|e#WiQO%HXG zlK{3B_LP|doT0|ZSXC%>ih<$} z$n(|eku1b@Ut;WN-FDIVUR-oK01aXHWWvIF+=Q!5*~~P4h2t0v-&26Y!M5Hq=eRSx z$B+?NUZCzrLyQ>L0EdQT*QZs4Z4-2A|EIt0+!0KaN(e&30K5L01CPf*vTHc0mTc8F zApaJ-nMyJgo@X$f{NREQ#0LAV3qeyYV1AZ_abVKFT3_`Q-er}g$6<}c%Oz`RZk>d` zno4uk0n^p1gfcjTs448>aPFEl2&sKmHO172b^@ZMM%81e>i2>yR z-mQlE4HNx_@qR-he-2*^w=Fyt8<*DGG56LNzu92i4bZt+(&fqDL4~`@E~8F}gwymE zhF@A@YJ667MpIZL2Xo0~KKSrnKRwy0jjXISLP!X^uOq+jI<;a%?&Zw`ZONiIMv9Xl zLhEuYsaD@VFtR@R7^Q@1S@z>o*rFvz+c9^%CrOUN0NUsyCJf2w&T>Wk=+$(^z?R{` z;_LmbLdQcCC;HX5O$aBKmKl5|){9Z4_Y@eFAqY-YDNcn!U)!fl3W{s!Jw2N>CQ|L-vTBXFxN((9 zSKtBAt|CWxyA&uBDARF2T|JEqCEjBR?_VoYZ)?ZGa;Sf?To|kKB7I=rOAh~PbN;K6 zsT$2k9;aDoS4fc{SJKQ)wch9+g5S9{6c=*;RSe~^#*CK z&AQHN3mr9r6{tPEk79yF@3JGz=;?;4?3Be|G%U|be3s`s0V^)C(EXo^N=$ZrkP1&O zEUm(-F-0CN17s_!dZNC1<1Zw;(dh&6*HrJZvit}kAnrCbaaR#gQI`SGERq=lTx`t< zeF!l%mHAhR(-0~Qm;SfhD6GV_T4@}LAFWa*aLx9O_kn5L9}WnXe1CqVQtqF=E24!| z?!S~Q(sjB$|hHp)_5pb*@G- z-9`TEbPnRiMey&S0fozlPDAElcp_qzBc}0M;MiK|Ph~@35zxe{5A7cebR1p$4obT4 z{fUyk9|P+rbI)GjL=mJZWauFp@vKX+x#1s7nBiC+dXLRRsWYkEoZ)2)@2;&d6_}tg z7t2&&GEQCa4PduzfLMvarFqec4mJ5%1qYdTlg5ZXK#DuhrPrpWZ}6v!r0`^D7`%Y9uM6sM*;Nv-Dno(g<+D$=QJ zy4)2;F%^-Oc>mVJu-qr2V(M6!O&my9Ba?)yZ~b@rK+9V#%-oULi?c#}Nw(T)5x9vJ z%+{vRyWq(NH4d0VRf*^tdeU)1Cno<)`!f>+iWBECCkDSV_vA+mYf>9Du(fqST7VVg z3%$JqBxLtu!lswT{e9e@8sL%?@6yO^0*bz56lle&JCp#}hMcV-S*)U|O~kqmHO6~| z-WE6!J?{OJc&5v(@+icK!B&9!%B@Wbko5fsu(fcgPI+vc76v1q>`QO?J;hs?(L-hK zwK1+`9c$poQdMTXY?*EEx712zZy4G#oC|5@;W0Tm`PU(*h^wKNWT&Pq=`^McZGApq z_?1tn9h&TvTOe&g5BNC7042#=WFVmL8hYue(zw3{eDTEoN_O_Cw-~L`EyUwQslw($nVz}hm+Fl;N7`y7oKBwvT9 z+07>_8bgZu5|^%>CvYZ}%N=AtK7%W?+nl)+be&HrIh8V<@pYlPS=6E-8l1xl30<;- zkJqcp@+M81N?U*#)Hjy(c^L$=SK!_Luk9+uNcG_Q&itNRe{KQn&P z6lkgxW?DZK=+BVNAO4}46TFKPH=P>{@Q$9=at&w1Tk7Nh=LK)U$dY8|ZD4C`Pv1q@ zpmlnm;G@*}d^?NR_-{M!KjKg47PVZ_U!Xrz$#@@~cLt6&AC?ERUmd*R2_6-_R~qIARJbS@%v)*V+Tf*B(jkQv)= zjldfgRX;2*0a!c~%@=HRl??yXg{4Rxkn6}u;Bpw2Calc-IK!fGjtl7xM>a5Ou9+$% zqZlK>G*g>3S%R5S0_vEq@fQ2Vy#$v6lelUQhaB(sA9p?`gH>IiFf0rCE!pf3jUCH^*(d@+TQ078e=+1`aK8#k&#;Bb7;vOVhHyliq zWa~7kmdy3%kDTjYIXbM3?o^oT*HzB-XN)0mEYAz)a!_h|a`PkpmFWBNa`UUn&D+%{YRkiz zZTQ=CKj3Rzk-oWZbn@<9eLhFgU&p*(Qwr7T1*-;aRv-%5mTN<$UpEzA|IN^Q)}>dnoXa;aTBeMZz4vzcj08SF73|;#mrrHBQboaxiOIX=SC1A?Re3t=^}j<%#kMqC{WZgbx@l~$!og4T zN=%FyTc8bh#P6x(W+sjF;pFDaM<+L5JqETrSfUVWaYP~HVqA)`>5X|?T`EArs;dZU zhx&Cx12#14hG~<&Zg@mVKo9L0G4ZPFckGUiQ_<7MBYMJt2=r7t(XX2r;6j8J)lT-I zr`jo+fAIiNH#Mkj@ar0a+G&0r)2o4>+)Nj6ONS#JtuH`MhDiohb^3Vn`KIGZ+;vD- z0=g;kcTw6c* znxq~0cO@P8g4V!yP&ttDQliD}F=XF+-diKPk>Wt+T<02QZZ>lhCCGD9&b^yW>!Mv$KHI`njSUB3$f59<0g4hs-;hW(U8Yz&8Y^Raqxw?={ z6WS);_;i%sNWeQdk6_HBlbhQ{1}J&CEsKJuO!4b+5>$Pm&Z{==39cR|^-cYr;IfH6 zYo+vFRw_sQ?YiY_SG;W5&4M?ayz{6pXS#ch*;2g+!z8^{oHx^UoGOPczdY)<9>M`; zIBunniD~^oE~MS<TuA0PFU-+E7g%8fj= zf46fDEtOaZHr`YEXpqkNDM>@RyH)joJnz#0Q01uSW^BoAg(YRpyJ2{0*H1+z zU|XaM?>KiLTIpJwMlp|qp(p2hi$-#Lks?PmGRH>y@3rFg<=#kaqo)M}c%PQ7wP`n) zu657_p?CXVY(9mxyEy~-8q4nKlSA)kg_wBGAtqaEGkUgmDiFog8hT%e(yB|ephW_| zI>B|@wWbHSN(2vN%cwd(nGeSrB#wLwyK0Fen?^|3B5nO;##XA=Wxj`eRjDD z*T3v?CDcC^s%Km%T;>`Ijb#;AxT#ShUF5H%gAkb?kT?t_qmg7wrhY#qm8&GF5hL;7 z*s3PPTT`>YLp~onIhI*uYZV3;{uD6l_h|zE)aeOs3u=9zvdh{+M1azWMqUTY6m2|A z;a>ax0bIDzzJGA*<}kSFEH*Oh_bU4^WzQx%ScfMf~0(mRiJaMZA=7 zIsR@DD=cD{A|7`U8JQ{=G&mtsch~o-qTj$SB_{ndv5eASi<%hzw6>cX8Kbw7IlBE8 z6&`njp?g6Q=)V?eS&u#UV2TP&b^Rbk9Lw8Xq}J%YMUDP)RLxjb1Dp7nt7c48&4*8_ z25nV3(f17p@SY-oM@1za6Rq?E{4q+(%U7YxvAZb85%$W}#21gxafxyaB?nY3rs=M& zk`2?dY^X&nkV}18#A%~W662v@r6lukdbMviNnm?YwFeWR+eQ+~xEvCgi+yIM!Tznw zv?Cterfo+TCAHddQ8GGlQQE&Rjxr1Q%Opu|u_1M=WukwC0riN2PPJ?lzZm4ZEqR8{ z%Tn}lso6#wK#vwr5$uKwklg-vi}1^X4(T0yyBJoAj;n`9R|>O2p47&K!68BCur?!H zX?(Sifv0I-L)#$sL*02Ra{2<~sW@st%Eh;a(dd%Pq-KsdBx4n1 zh;!LJLKcz9&J@YB)h$-B*;Qky?$uw5%v7^5SfXmEpv=3jrPS|Mb>eBO6s%5NVXcQR z-=UVRFbsqv1uGYLFSk}z^Ti8Wm3@~Q`*)L4aE0~taeXci+416(~sbmt$PAPF4OCePMx!r`-z2q8uHN~lX7oo2BF?WTgU28 zhQ&<=xx<6#bl2`17X}O3g3DX{u#$YD*E-O?NpSMJ+oadQ90g+9qGt$%roum;OK zhWy-56z;CgB|9{1+}7tK%xpMvnw*jZe@s`-Z(mpyib7lekPqP={h9kIikso>Ml4~u z?_*Md%4~3I%NKFSHI|(LX;kfQ;biAxitsG)LRUEy(Diu&@l!!1WE}W4L+|A+-fPME zKaX@s{x7$^IC#{~fvtP}D_Q~@ui|@yH3mY%>?1A99YCTZ%mXq;uoV6t1G<931s)y* z3U8uqrRIcX;Z0mz>4L3#8`!=#unZIGT3V{(K5RX+072)SMu&2}#2kAxH~$bFYE^?p zcY$vZsw96}qJ>qj=zT3&=4R_gQnAx?R2fAiJ8{WZqCUF&GLd|;^KZc6*NyND0`5f> zl{;w~_gm377mBnYYT2-U57 z`-XaEe`BM--dx=+9}g=o@)oolYyF)_Pzcmu*Y({R);S$;B>Sl|x1tb-bq01}y-W~T z{kRRV@{?%MQJN0%^!+1$Y(@W)-69^gRGxA z@^dJzzx0zTHtmPqKO4*#=Pt`u<2aa2Wg4zO`vD!pkRG9L#dI5+r19TYOy+=rtJJq2 zd4om2U2uQHwp~6hL*dE0-F3a2gfzR2A$fN=oOhfNDMZYszjyL8)Qh1p{&?2Te2X*P`Tx~9?*a>5 zP%F$EIrK0#VtF3_ztTz}4X|Oas|FImPo!`Smg>|eDroJGFO{I6#V6wIgxW;1^Ab{o z-dF$NM01QDueOOCId>mzmE}D?t&*LRjab0i5I_({8|7U(gLw;u6!lmQpofphIA3Cd z$OS1Aj7{NG9xF`>>e95OEwh>eIeQdT)__P+?)0on9^a+7_3ye&)3FZZ_} zQb6R|2Wv6|;zBC$5@ATASo%0pOvey}4)hk`IXtsPv~(o@CmvLyp=^hFX64&p5^)zz z%$+Zlpj)X(43AFrAU}T0d%bK?UEu9+1Wvbm&(WQiPIDXhYI8wuw+(!=uHY_OC)RRo zXFVBXtBJrHK8s?eju=WORM4oD?gxns?Iihy)909M4btf3223SdAI{1U6aAJ7>f029 zJS^9SCQAY|_Cx0weq5Cx;4I%>18&}-p)B# zPMlyqkULYgfS4tJ_(O`#M5@pIO=_tndkf!vrlumvu0qg0OR}l(y(>=g--Vz}mgKhh zo2`iW6l+GK&-q))J;Zy_7Q`GtNj`+Ut6_vPcEDV}@rmR^kFul$70Jyv4Vvq>?oB>~ zbla;G4_%#*=?kmI`W)g|7tUZsWSsFlvd?Qjcr1A(zRWoAiD$s0guofDIBJWqL+o;O zJtw?3=FqmFx!}g*L*cjq!o@r&UVdbW?i;^zA4rtQlrhM0T^U)J#!G`_qkedt`TeQ!z2U>;ADv~qwA71c06fsE!z z8AbS0B`w#YLwkffN*fO^x&}o`=G8@?hpmo!y{hqW>q{thz|eu@-FrkKD5dHAuvO_ z=N&MEzFVOMc26qsY6m^QZEWl#VK-gjSe4^bUhMhNwgzZSFpoxa;0W#euakGb5lk6c z*jP#4y)CTR;&Z$7wyH-CyN*oF&4TrNx$=53hRL^(U(4mR-um!b>Ul9@C* zm^6&Xh5U`-6hrJ;PXocq5xDF+iZj+9E-viPITcpO;zk>~ap)#Dn0Ce!+jqZx(!|C+ z2%rrf%2w6@Ohvt;e@&DuIP1$P+m%D7O&Lxp+-m2b)>GB?7(L8kI6AFw3aV8BRS@VUCGWVFoSGHY5+>pS(;f~*pX`N;iq+Xa^!BDD*hrl zlFKKXcj_vZWxa!R0x9LKdpW^#h|#FvVJkJv`V0te zdNc>$F4J?Z@ILNwYGL=F+pA&>S{KzpN3S34U1qIS$Ss9e@tz5+RrPux^njJ*WA z`qEf23ZffGA>&v21P|<;dkuxLsL(Fxz?%r?t(8Y^IV{ski#h3DWD}50T9DVZ}=hgeB9!% zA61L@IN&pSQr~})>pL!2v&*$Q$~C|>d8Xys7v<8ETWZ zWV(Pg_b2oS+)HH5O@-0Zq8Np{_zT={B2VtYBSL6InlaJDofAFdI+}x3Mt(DmS5UXv zhf^MRw+=C*cZhU*=&d8%-xcp|31y}D5u{Aj-qI5GOek9m>EPhTDFP7(EUT@*O5e8lU z*`fO$V&_TvNiJn;hgXs_cR?iUAVXkEb&s_&XYLV3zz`g^nP=0k~F^6B=-|B;{{l zY($HU@9N8L;p_Y!uLUN3Jgd#`V7W)VLCUzpknlPh+&|`qGoF)U`sQD%Bqc^aZhp(Z zM=>jYa#ZU)&8Fg9`5*F0%7|`<*!+}#ISOouX3%-mkl#;W@u+3qEgH;)G0s4br^Uj=*4PMtNd7~>lJ6e_aw zQ6#JA=NgY=9-P-EcOe7KI7Np1t)%g`+C-Y{Jcp$u{={wUne;HEnu9mj7)Qsu_!MoO zO3e8vi}WDfBU-L$3h-ZEGn1`FzXr*Ew_o#FZ2{I?hvv$!xjxvm5!n43*(ud}$=3My zuxcw3rA*YBy))lV?a37%qF12obZ;{A9(7Q#6qjfD6tD5BsWMkX>mqYJmcn*QD6E?! zQA2AW>1rg`1L!{V#;Uk3A#a&P4Kn)<>^`vX!0rS44(vX#@4)V3cy_sIp-7fpZi{hc zkdhyDn=BgRRc&(fRU`2P5^dcsFBg$FV)Ifn#$TS|Bl*x7+5mp&#sSHP*fHeZn1?PO zt5sq69d)YZia!`uaEAX|05*)Et zvCe0y^+jlhjhqi)Kd(s4Mu{W8?C~*oVdq%JFZrYff)n}O5@kegDkjvi4g_yt?|<4> zC}fj1#C9Mf@@!^wd-2J8+r?a%ODeN0ILm|O9W;?H9W8Z(8n|{8P3CCOqBC8b!and} z!mx#3=%jrkjS1G*$?zR8+wdFe5x;Rqh%TqG2ZH0A#10-Q@XUVf@Rtgb4!{v+Bo(e6 z>B0vvT&d;0d8VT6`YmJw)55d0H}ZfoYCcqg=@9TUv(^z;uOFG(M+saBq^e(^8(T<~ zUgvHFtSEFO@HF+1%%Disujf-M1m>xaN0rZxDu*&u<=_7lS4m+JI3}^_B$Yd+L#n3= zsp{9oFg2YaaQ46%=#V0G81k4?5qVFI7UH;Y=mgw+^#+HVhrlxxuO4cMNlCJ9dQ=th zVk-rc8`8a+4%fesC`m58l^lFMdgD2q+uMfl>-D~&UeUB3XRPlfx2N=^+?HI<;$Clo zYI(DKjNW}536W0#ChuN5Nr6uQJci^SN4p3M66HMiOmtYapM3nC`Hdt z{nqx!epJs*&hU;tt-i19DF)efnS(q3FURK}|NoZ1H$Q>=F&iC```iD*9a|GZV|lQw z0}L=Kk~RiMi0t$JNC^omyNC%M+~6?e-TFKtNAk;Wj|^ok<-?Q_ls)H=IsXM87UnLJ zM}u>lcqwj>w5V%>XEl3wlJM#FR}ep5xd+22Gbl~(dnUc_=^GCHu6@tbH@qUV84x^; zJ=$f;4nll;soJ)9NY>tfro^*KF!;;2#0^_=aHF7=!UX=bH{3dtn6S1mImB$}!8{&Y z-2GlGI&J?TQuon?gI;3F(pf>wjF#+Bfl}FMLemTe6MN^gBq)jkr+&(xV#?75+2H#P z<)&wY?C8L;!qJiLH!1~>Afp=H6hW*`rLcYO>ZY1gBH@%JD z#w|%tWGUL+!uK`{O>aytzW{P^zJu?|ZKX>0zCI^YB*FA=#W2b8C4yF zbp1}sfR;MdDpUh#*P(DCNWBol!Qd53DMOgs#^!42d1hQV`J;p!dM_k=Nelj>lBjt|trm@ORU1#00M}jBpK{y}Mk=QvIdPq(p(yZl$eJY5a_4bcw~ytnWIxG}I1^JZ7^UDsB&k zfB6r9nX2|3TrvXak?Hez7GkAG1J`MQGWszPZEI=DM)Vq7+!{(UO-JrbgJV5V$C?j` zh!PLKWHG%Iq>7!wH(c#XNg?T}sZNr~h@<6p91wmsQj&esm^2@1>p!WawPRiXo3Vj# zN69K;Hv8I|qe;rK4y{+5#ND_fYFEmg|MyeQ5r=bvWQRr%U0RfZ!I=BdUk7V8`Pv7N zqrQx~of;%?Y@daEqPM0e^~K*W3hc+G&8fLVhuyS!05D)}kBP+beZ%hU3y%;(BepCT zk&ON|f3p&iBB*veFO=1M#S~WoQuc5@r;p`lcD1W;$g~kdMHHgH$yyj`KRj}Td_V$4 z=>0XS;~UG6Y5MP{GT5%qO%rTS`E)0jf?M_c)R$AWn$s{=-OEe0>Lb3nX*@qu1kuyf z>)r5ciDe_OxwrjZ9S3+eHdC|KkP?Kc=MFuus9vI!cxEGsnj5L3 z>1^Wpv&1u%pjlj~>0E-(jjvWS1`U5)nESenXm<*yiw&pCckzwdfEqqclY`nyp+piJ zoJ7Ym3@Z;Q6-kz4NOHwIYOCddL<>RT>fb630Y#Jf6>W-Y3ThWx)bCu>a7C@`a6`Lx zPGElKEWz(x0!^=h$+pUV9S6}!YYG0~63EC=QDbS8gx6H~Xe*9&_(i`G-rpxYAr1F>#{0`w_gA$ds!HWd9~M`&i=2~36sm$^__V5o z#i%Nw_Jpcb$yceQNV3RX{IZSpCBNH?R+Qb4%ILhp;^=&tF05jmo;#a#TJ@(B=<%w{ zC_K{xYWRq@Q2btTr(J}F-nEPsAm*<*qY$Om)8$rF=z?dfDfUi5n!7bxF13>OoK%uR zRFa-WCAnZ%l6y}DSN_HT=oW}@vd5E4wK|XbMjKMwzWgdste!zSzV_T?JWg-(2^SFe z{Z7r%2_gEL0(UV%e`SeY)bKem7=oOXW^s=yaBE zMTv8|0);5aE-LP?&%SwaH&}7w!s&@n!|;^FomYU7744bYC?0_L7NCto$!@UYYM-{+ zR6`j?68Y~k20_d!A!hM@5M$Oka)FhV!OK5F%pXx}GUAFvq2UsRzIprYw`(BYe*4cZ z&3*AX^-hkaJ20}0h||T<}aQ znDl37RCeySsF?lCeqQO?l{$IvY{Ha0HeEb)X*P416lz(>Rz#+Y53LHjJN3dQM5e<+ z*7)5EEo7gcY2(Fn*#di1SuM$%MW)_XD{s-Wz)~l|$W%M7cBL3cIK_R;P#_$S`W_`BtESkX~hw5#McgtLamsl=ZOyWw}DBBP4j!1CS=0+K5# z_!Wcv(QnXb7;URr`F9fB|9J|c9}Nqe9SYT;Dx71_(Ty7j?2ZDvuOqMsPbwD!`)>7e zkP(&S2FfC`ACpRfQ6@3i{~Gz^p2Ltb2t`SO5mw+3eK{FH!dlmPGuOKML7KtQEcqid z&)(UvwCBuF;27du8r!IB<2~pW=|&JO%DrB>U9qWd7ihT=wT6W5J7qh!;=slWm)=6(NBRKU z!%Z&#CLu9O)r{Oxkzg^7|Db@nc{;5Y)V09SMg(ARuJJuWYr@`<(hFftQCJ~vQ`8NIBx%x2ql?t{qEenyiBWE3hNfO< z=0(Dy&TRe-c!@g=5p*{EVDt^@hW)hJRZ%ID&B6QZr<5~_|Dmg4=Km1RDz5ne z>3?vg6K3he=AZM2EY|dU+9V-@eM8X4v%ASXe>h&~e0ZOD#VXh4D5@D#j+907jIuT7 zDUZ6EL{?ZN1(t6O`9kl%9Df~3YNHaCL2jOA_Dy9}cCH;mOEPBGQ|Iv+x>Uq*8B}O) zs%2=3GB~a!t$!-G*3Ip^Zn_qTyjx5s?6v@x7=slTS$wUi$SR~TwPKw;o5J<>91`{d z2y|zwx|=>linR(Mhb_eNY4{Q1p7(FokQ0kv^dBUQihAp!=YQ|G(U)Mf3mQj1Hu@Sh z`XUxD(uhV~gTXnI9&Cn2hOFIa-=otSZPDz|3`vZZ`mj0EqLQVY)z}@1-HG39W(O&p_;9oJ!01pRs@t`>d0Tk=tR>uwmUCbFm1s9* zsVg&j`kCD>Z%nnJFj2@4J!e4F$PLgix{aDxo<(z{Ey1>G*BalM7?D%~zV zE;u9gO~k+7k7b^^VGF}B;?792R`lrl2M8=oA^R*a?mUOhUKbX1|4i%Y9AV6{rs>^a zn%<43>AlBxMbQASF%9sYrU71O8er_0gfk#VrM<84feq;X!p9nAjFa8zr|*ns9SJXi zNiMm)IaN&=U1mUfvvil~Rnl~(Zw=CGkZ+jD1FlCkdnha({B#FeS3lhubhlYCDlB&% z{^vwlW36>gf*)$K!05&`M66X4Axoq7J4L?^4@T|i3x(ny^Vz z^ujaGw`Z08E_wx{;=o8Vo_*BfT(|Z@PK+@ue3cj=jOU6?Zsd&CzTD`>{lt8)!QgGS z`J&0aA2(k_@it$$cu|O(FTmsIdTfA0>InU*U1PT%wovVQo+b=npE9IK>!-Px!!?E^! zOOb@#hvrz=h{X{m_t_$(SX9wcB^G6XxQTjaKSNk7gh+?FX^Pb~lh)0KxSF*cg<)I~ zIWTcFJx{M5Cx)z@qTw@nj|l5J2fYPR!f#cBIJ^;7F^P(>#3YA}$em$1o5&dtZecIE zd?FnZHg@^ltE>Psi8YIzoXe^3A)o#g0;d_$H z|B8kp-@{tP$>~}+oXBcAxvWc1pmN>2>ph^sRnfOOWpH>)Pynq2!U}9ngYAlI2qRNCq)44iZDmiG%7( zSo4O|HK;xfIUv5WN%c8G7&2py>N^_McO6^yU(6|0yf@?I)coI|q2!7$(DTu<{0q+? zJJzvjIr%#B(=6DQ`O_@;77M;oL`$ds^KqSeJ4RwbW+W-piKdy5})iZ`^v3pT=yy^Qbz;gsmrf)iHAE(2;*X7Lmynr}G<$ zwVN#Rh(*4F7P4d0Ib`n$-KE_bu>P{*dEMW(y_jLir074uVK;tiXbx#yln zX^yqrV9tHEPGvzb3{uQ}fm3X3<2YSt+fcjA2bWy9B-Q;A$-DKIl9fG!{8FXW4W1R` zG)uafrfiiHL9?ZFpTYczWF2)#g8YnXc^9cm;ISZmfI4TY&LisK^u9AH#&v+Sp3r^+(I9kcoZ70M~Lxo1B`jcZTH-V@a*Qk9$Q=96pu{F`JMr>c5Y6%$T# z-LMlOz3_y5yP~Qlsw&Ge;>0Y+Kwoj=;w+PKNs@VFku?rQjO~4$qQ;&RvST-4=$xt= zk&>G0PO33{lPuF%r+GUZl{ms&a!?xYT>95;Lq|$|$TOM2cXvr}`Ou)IVnR*Id2qP> z$XCih4yuCD`y^vgGe^qYhUrz+bU(9p^JU}tX`aHDmSkm`+RRp|eogM^&xHn1l&W7t zFiYweErcedlm>G}ve8?q)mPjndYUOQfDI)}KU3xhvQ(HUUBwj%IolHGHUP}~e9^ZC z#NaKA$YXs^vpEz%;!`RnOi8soh~ zYaueI-x3)kz9^*5tH41!C5aHc7l?Yg9hZ#hSIzwJFzrb9K9lZ!`i8^5YtKD>!>e+L zRrX^tdes$J7xw)Z1gK)zye|)ML0dIoe%ZUU-zarSyx-^@oSOUZz0jsQF_F9*uiNuD zuep^ZCiZ-IyExen?X~@kpvk=; zasjq?JN$|zvK8H4R+Vi%)VC2#%H$-yi(89TExHqol7n$eiRhvE-uBJ581~M3P|w+- zVhL-fKRg(Wya+~KG>ja0`i29)YsVZDvM4&^8Be%!a!rgtfBUbJTv??wUarfN#x_Tm6mExD3yAj{63 z>FbpqeN7=cn4j=BeO51A9cQ*W*u&d2mFyf&ag3&9=Ok@q+GQ|?1S>{pzegysV)XT& z_BEBV^tDD`TLnSp*rIa-+nfQ#TUDuFu{^@E2`8=j(0huxwz%H{i;++g*l7$M%VE0!6KTfiJNP;ndl}xVv1)_NWrNdtAu&z;W4r z#FzC=aZXM+R9E`u@*{r-FmtV5fG5%J>s41aEZamKMxD1jBoxQkc#xzV89o~fnERq^ z*%BoL3spN?4>G>4Ea#^VS>FyriMB*aX4h<|MRHSVV8P}qGV^NohHVwyxkEV=5FZt! zEyFB*17H#El`%x2&y4#Ij(`aC(VK(-QlHmV|7nex0;mBWV4(9GXj6GNvJDr-9@Xa45N!rceYle#5ruMnfrei56xzjP<7^? z09Cxn zDslrZxaj;%5`YJ8n#`|%5h*1-G3xfIwg2vrJ`(D5OWN~$pHgP$&0Va?PWs8k=8$!w%_TT zHkCH6@zSfH;8j(&Yt@qW(zlidt+!Tf62!^OY<@f1_a1AR8qho2%h-G&B-o^1pPp*p z?YHl(GA5qP$TTb;NQ<&{BJowPFCKKhwJw`p9F$m6Y-yIAXHMS7< zirs_=fr!kU(xyhxrysyao^NW0zMgmmHZ^zcZa96k0!wB(VPLF?CIfKpg`dHxce+)W zExyV$7uF(iU^s`xykq%Vk`0CLR5ygHdw*=BWbLnt29?%cOpoOEyF%#;Qmeg zIx~OG^J|f9d1>)$aZtodn=a_o%R-+!I(g~n05iI&Q}1G6y0263W)xS;8k2X4;C^j2 zi}=zWEm7~>0wTBRUKCw_w)hO4*KyJn#tZ0p%2sX5oj%tuyNaP()!5tG*Y`|e_3F~m zC6yGKyILjDC1^xSPVSNe+1hd;_vMbMh)v+_HdBtvg7#4(H}GvJ)H|2#6mW75G(dVlOI;SFu1{2b zh15~m{bTV-lmxna7ujsfrLdZ8h;|N9PXW_AbZV;YtDHgvs}}|YY35~ia*>N~ zzcGSzG1Us3o0jRC?AC)0j=l~Wk*#(XY3?$hZ1qr;m#sFS`qwVQa(_fyAdVAzfVn9V zd4TD^uzRpSKKFeH@VHBYjH(jcKNWPY7za4XyC<)xzzZ{8oZUeuPE#}t4d#_=7`@^| zn8|xO7M?Mpq~)N0)zFwAv~IF~x)$Fp+x(sQS^Q|QM4JKwmrUk&!m|CCwS4)5w&?0w zx`9@x-!!dOcspg_Iian*{k)C^BT8Dc7xcVYiiOXT@-*evnJ)07`x7Jr>w$pboTg0Z%aN zPT0YrT%$_2yTFFACR{YUBzdcp=XSb!&0hvU5-ANdtrzXZXql5L$RzVBGOx<*b+wuw zR*z6N@hlkP`^br0aI2hu>xA@`47EkS^50-q&880v*uIaejkp5qT&k|thJ8J5yXkOV zU7yQ+^-}eemp+W+>{1qw^v&T3b>;0VIu_A4TalQuOZJk&O5Eqh*^+~jLvq)lg%BZB zbFBETOwXcfIavB72kP)8$OTztMm`;1fpp#()Zoahp<4vCgCAq5*!Nc2(wX&wS7fSBD zo@NB~cf$HmdTiu@H>54*4N2@xWX-J+thJSl1Iirn+8EUD;%=74dtiWxz|dy2b9CS` zD;-K$w~=nBzo*ok`HrgJ0EAM6r%E3Sa5i2=UiKxp-cCxvmI+nu8#;M{%*zy0L0kvKHy{fU8dy@k>PlQZ0Dtb!A@q0qeDN58&^us=q6l2@v2I z5^AHyT4a^^f?nZLb##8R^Pi}|F=HM1hj%4TQ>jMN=m)v`m&RQC=K)aa`fa&$MNE^1 zQ>aR~a#&c#wRUKc#dcMiZ)M+w1pDudH?CE0?c`dSVcDhXWBoJIg5^}O(kchYmO4>% zOD<^d3?5Q%;}!jY-+pUgIpD)P*w!gsD#9FP*Z<->yR__<6N_p6nfkX$OEWV)U1`1w zjs8Cf$V;}V0A%M&94K2QV1;0 z%TSc|2J=(+534$qym?G49@xBm4`!Xh`PVP+q-(Zvay?y-Em4_h`rbE~p- zZc?N!IvEgbQV4fv4rceOMUj?d$qoS_=66Alt1CNsTN#y`c4K?%%Y9zf60*&8QkIC1 z;`APuecX033=V`*=5V_DT5&W8r8iH+31&e z=-b!%zdviAbMKu2vA(}v|NDB~d(YVqYp=cb+H0@9_TFm?j8KQ`hQC?j#7n47Aho}` z+o5)tTvDK0aZLDJn3T)-P}ZxYh}NPKTy+|*U{)?#=vF)SNbg3hI>aY|yfiA~ztSepUo) z8W0&=igQx1=31U;ZQQRwcBHvETyTm4)=KMSuhYm+KQ;cj_el0rOBRWI4TG5!mM5IV zq<suGf3R9`Y0D4WKH3!S56-_yuG}g_D2E$brj{SIg-0wmk8gxc!Y(r`BuIIeh zhxpGvzuW6Bwoy7#fiQ1R&RmQ!Lly&RAM};xzT{C_5tzA+TXfH@q(L+}&~%NpV(zH9 zN*aK>50n$?-CRVN+FGo@o~+-+oN$D5N(FD-T~>t8s?gOGM{Kx*<>y2aP!L#(B1#== zTSSQE-ycv^&sx`X-u8K!$FW1`5Er5xt4E?t67&riEH`Sl`CK=#5`)S!kPm6lB`RYc zIjNqJPN%#FF{C73O;6w;ai=*5@ZaJTZ(?)iLAXTV9#aO9AaxG=^%%Y;)mG>z&(=Y; zT(|gT3Nv|i5{=I-RCu1i_CogiEc@~+n4V#DWgsIfS3v0VFavB zbY8W^3D9ueiZN5QtM43C|BM>+Eg|s|0ty~G5*dP5*5l+095OtE1DDbDU3S4QGM`~} zrf8q&%zhC>?i)0)j?WmB69l@V5zS7 zrmd}TzXCNJY*n@zHXp?^Rf{zr$^)x8qxti`SXm4l`bbgsE=U=q+8Bgn(#Ucbg^KIDKJD6?@Oc%_usM&drL?mu@4)M?T#D6h=16XE%NLfHs zMFer@U0hPD&L(G+b@B+qeP8r!c@97i#Q}adiUx{%+mKl6iR7Z^NuTdTlaIB^LysJ` zqNXyBV=L%pze^XVv;}t2O6%`MrPK@QQ*o->Nvo!(j^pW>o^tQa;z_t?YUKEG z=tyj*%xGV3lybI<%fiF`8SIkAwQ}1+gv9R@BOXV$B4VK6W^7w zW?e%s31U&{+Jmycg4$6pugtuRwMirP+O7kJaSs9T+jt{BeQ8zkfKushh>Tu~r< z%Q9K)CB{m<8h|vTW2mq2+uO4P?j1e(A2Ea<_l~06zJ(K`jzrwLS7Lj*VokwiqqU^- z_P%ViQRSdRB+A<}B`8|`uNeLL9s%!mmI1_Fx0D@`Ohqsx_O1OrDIh$v9o@n6QskK` zBK_n{6$PZd+pd#{enEqF+B;290Tev=fl``M*BzO^5_}YMm4rEvZaRa`5gf$5lov4H z;wp)?sWoxn{8DfXh~5Px*MMl$tlpe31;k`Ui?x0m90Sja;GUmY^ZNkVk?1BA%63O1 zRYyYNR373Ve57wEMf}82?Mkm5Dm3e#!T&$rZ|Textzw!QWjB zta1;7ocCtwB*^_cB!y@o0x`$ZqylTsS>+v`sH2a$@{P5YgAYYY2`;F*ZvE*w1i^{K zaHx-qdB2f3Wt=L#K{JwQ=7vmzrdK>~*S65O;nj~D**n;0wu^l}?bvTD8!=tp5LoyJ zD`Jad<~^gz-D6HS@OF>5np-~)zw(fc99AKhxBFAc5gQ$RnL>$tU+Qlm5*u@nC6}wL z1MT1%I{CIn-%a#p?x2r5qlfHQ7zNa`Z=fIhL+HN81}l3}b`Dm!nhv*ML=XCoTlTJ! zZQ5~hIcIiLkyOiq~A?OAfO2ulo&yA;TBW)-~qf2w4}*&d*MBQpry4PtJVvA$9ZeklA4c4V`!}r%Uj+O{^kq ziEfRObn!1gz+cyaa}O&@uY48F6)()^1=jJ*(m3xj`q(CQF%9-<$Af9_^94yR%Oxqc zBwb?DwD;A5B*|P74Rjg+Ey=QiB**5G=t5hENKg>}{G|~hx-7-%;FPkqAjy4UlI2&r z?B6bk`$iPEK!@e6^m_`T?~J0SxU3Hs#LbD~j!RqrrqrhjqHhkPosIFdE>wU}G1fpa zl&h!cT+Pp2;RcGvVF;c{@g;8ujTZ*-BFz1HYv`EFA0B{bR+bkp#S?BhiUT=mZ>*Mm z$HfxNjmv}J)pv##1;udg#bH}&04}%1#qOTrE?#0ocD>%^O_1`zp!rMBItwG`9!mPLxA&X1o&%hu+NP zDgiA+JxU7{+`8)hMgCfT##ci~58rqA4yUT>7pL%@!FN92 zMSMNJ>-hSKD)zd)?MCg?h;(f@YR@Kbnyb)}0+b&N`|p@d3UU7L);r$(`%pJa3>q~X z(V9m=(B{2^G|L%~sz~Mc�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≥=j4@uS*rZReq zJj#Dz#5(7l>r@RWg9lTZDPE&tVbjvD(Q97k+m&8aMd<9R^z?E3PsfAQ*k3GNM$A)u zanmX1NW+hPJ9dG*Da{guI??%5dM03&L|_O~=Zc@E@Lw$bssMzUFC_c|c^scLVtkwW z6mi}ADt4Jq3{Ah^BA2C=y?=4bZcs+PhziTRSCO!ZNgy3M+2Q}1?Xxmcs5aBUE)=}@ zwnFaqv45^@`4wqoE8>>nNOKN8Y_(J z{9mP4Zgl%^{XH4Y^}tRCer%815$N{ezILj}8TbP+UFEdP^n<6<+5J=*eK>oM>n)`D z3+AMPG^6rqUUU;=(md5aO>;iY=N+80Gq)=V78MlP63$xImikjzMdtJ&)8BG`3j5^Z z{uIvSRQOXEo#L|)esOO!`UuWJ7cYyAUHc)PmwaW#Lc(WMAPp8@s1ypNXDqGfC3r1q z2YR0U@7S14{uIb%cap7b|FW(8MB~sDK+l;$A-FG}g3vG*HMz)&jw!Y%#=(4M;!~>V z?if*dHl{$fPR_h2TZria^%@T6R|K^zy2qLtnJWuBNs_+W=78K^$$zBv~ztV4CzDVY2(P^)CGti6ltyS~m8X#clk)we(R^ z{PZ2PGQv?1$F%W}_C5wV8!w5C{aNgquYpvoIpt78s~P(<-7>ib1e`dSLkAnXIkxJ{ zG!#$0u@*I12(HuLHU8HzznR?W@`L1lhFV(DPfd#*`tIlz+URdi*IL!}3!isfLp>~EJUk$CbH@q{|3Z0`# z7ZMr&bRx2RHS+|K-@zV}BQmwVVnVvS%QT~cy z4xvlPg0bDUC&bO@!MEd=)0OS2q2gqoTe#=RSu>QY?ik^@8T zKZlM*KyVCQbV<*OtmxiLK-XgVq4pHa+oq*mdfW2_K1?G^|i$>@w?q>@!d{H zunjIrRjxSFXKrGu-sTn6sZ+$?hx^N5sh+ik&9}HgMa5cltPMzl*yaCv{L5E-EL}0Y z=kYM9SdW%Ii$pHD7IeepZT?&1+pjo82JS6AH<^$_8l7es{PUk?$^wcRW4-IBPAGup_)=cvropKNAQfYq$m z>m9`V>CJkd`D)w6cOj=XrH)u}IQLVh4qky-_I7VeiT6%v@-xB8+k2kEq*PW)FLx6G z8^;d09NuGoleis7S^?JjB-dFqe~WanYi{PZA#qo+igut;qm+Yd z$tfXXLxk3=T^HX47AQ%tDPz7!Ga<|4Fl=)h#x+kT^9=wCj~fzqwRM-YChkes-xD6Z z9bJFBQp*H)PHu(dwIi}HiCc}v-gD0R8nQZ5u@uoB^s9R`_s8MN<`Kd6#B@WODr zCH@^`b(^#hSI=Y|Ya#wYih$q7GT|I8{|b+3gp%sZBTrxN@t%a`O{v zk%pCRMa%1=RK?F;+$Pc_HkW$u3{Jhy5ms0QOC1LjF!XWuPdDhkpiQQnv0%c73AUDF zVr?pfV}+4x(~y!8CFG((q;!V>9<73uZN)3skWZ&>dbW_RlmS7#RgH90WtL-c&evv8 zzmcptPm&zV)cN=@;UWj=$_=vka-^ZHefMCmdyo$CRI=YAd6H<^Ece1j6aSp%&g@&! zTjSf5*kEC5i~$8%2AoCUJ_t^T3hX=DP>-eWAxCy{LBFcZc#ZU{6esA*J2;9@^PO9; zjCk!+`DMf-zJi_gs)eD|7Grc>Y7m=q7ujJRulp|r#$Kd!Mdm~SuIE(9f6sB2VUbJy zz%1^01Fg8IW?{hsfFYyRaE|<)yU?%i4F+SoPF8P8;vr%?WOXOY&CKiX=FA=^w^=es zjr0CelKen0Z4s%hK|TS3taz$c;rb^^GHVI3(75a>+|wB(w(HbTiX95QENJ1?$R+4| ztpI$_ci{Wbq)r*~6GofQzvlJ6VA?{nIalU`FCZ8Tbab3i?vOJ?8W83TS#Ep!$6Ps_G{Uj*I|}fYBM6-i<#` zF9iEev%}98$@V3fHj`k#&Cl(<5y|c+Z9kIrNAQXW)O#R!P9cKx-wVMHMo{gox>z8pt-{QkM(Q|*I|{8fz4o*_xx&KZ81@KCGPWG zry>veBgE#YzZcK{)7vZWynNnW#OCta_J*>|16M#F?fvLgfrZEB2c^u}KSma8TWRm7 zk1@FSKQ^y*CPu?_1x`VbxxK6x2f;5$=k0xLeum1S9dv9SmktAt&7W<+yL0T^t&vU| zfQn$%xNq&H0=q@d0S6wNKRfg0a$q})O|2Yz9EjP*`_ki_{$uk%-iG5H_@o6v^s_UM z?kmqJd*_+tg2>~>Q+LwwJkFw`Je)H6rOGGwopFbaqQ7%Rsn^rG}ULugs4VR$lPYVh#TP}be-40 zL}zW!p!%pbR(n(1+#(IRrk97u)hT>NoqIMIt|>vrT9a)E<-utvSq6nFVSy_Zf6%n* zN;<$_mt*S)2^f;KuN(l2&*C+s56yZ205&CPVwwYC2oBgx!`3ScMy8C+T(uN_18Eb! z$Y9B&^1%C_N7z`>LaYDP`%3`(h8TC>gXe6MMMi68Qzaba5U3CCL>y z9D_%zZ68sUUr+XJeqzK)sa_xWsct+nu;cCFDJ6q2jcBVmN-fP0_cr5)U(BkdB75YR zc94>E^L|JL3j*1oTcX7~=1ktq$NEKCdbh6U-A}Hb2SeV6ZCy<{cAt@Zff<$l%-&19 z>Z0U=$Wh@Dsz9viI+$3F2vM`C+@!>grJv-HCdF@Ix}r7qaBWGD+FraRs(Ia#4we(O zDeExl8*w?mFUY-YQ!umF5oNl+vchNCYi5Q{O5JBtfC%A8P!Xx~4w|G-U1@eP98wTa zmi?TuOf;f~?4r&L+~>^c>ksE=PJdWXICENh8Dh{D^f}uj z_7%&+vDfpgCdzG@v02nMw#C^j>X@1T>MY7ojtA2hcGTFW&z*_#(p1U(ryvlt!7~DV zFYKpOu4bXwWO}6wkw~=B|Eh&Fo+h_Fhj}Y^6yxV=S~A46@7zV&q19g_*G?uK|9Y-a z2>n06(!R+56s(c|L0F^yMOYu+n_l};>_oOPfc(Y3K(>Da>kQ4v&ASICt zXsNCcGWg`ZSiUA7QiqvA^Zx%pCzuKb|0%|uzBjCKQn?0p&X4WQZ2QsG#dD_vd2@aN zPjm`t5DwcC1plG3&Ux3eW=Hfk#eNS4Ce=>Xo_>nGGp``Lwn>+tl=fy#@2AUaFQyKc zFh+3BqJ!-1d96J28N6Sj(3kn2?D+wD`}g~8v(#o^&i(YPapQT!EERdy2-#;|4%No( zW3WJGJ_ELCWT2`4kxrI=e4ExEF^-Kq9~8Gpd9VS@SqN+1S5(yaPT!!SqN_e^g8+ci z-V3LiWH zdqNABu_s)hTf>~6J(ij{&sl!&t~c8MaRAF{yN@2dDP8*YbZG;Zv5np$ZC57D zw0EMap|PL5-z9HUm9)3`&I5{i?gRmM;N!I~Q9j}+h2Qk#D2g~K?Y(io6>c`jH?80l zp${Y+WnMLK=35}`y?sYM=~E8J7vB>{TSG{DKL`QJKVi?e!N_!yIw1td6|kFkT$u86 zR#c?@0jc+>k)No3Cz$9hMGAdUhAc5LSxfmB45gi(VE zqbLBFd5vsL=HV||Nt06LF;B{-Q?L(pstRDbraJmO#+l8uw^eV6?zH#JccBozFTHsy zamvF25?j@9+S(C2b+?MwL?8B8O{VI1k{|F_Zi{UgESF(mt@Q-rzC_%l)V9>0#ZSYm zWOM#=w(_hj=N!yCJ$I+BjcgTQ?&hBL;-}Lked{Z5zc#ZxJwcRro5O*7j8sxhkmE~_ zAO9SircdyD_fGXc>Ijx<*>BvW@+rSJbjoOw_1j-igQ2GDI0%OTn0mQ08<&C~>oRK} z`VJIeW>QbpN>6qbvr2y*aYj|S8sv{ro{x~nDqx_ez8mQB5cHQn4VCu=`jovvZzV`< zBZ9!~JFh~cTwZp|u6O({OzFF}>gic1Hq?K6^v^9!N0A~cyVhwscWw3d^u^BTBtLy{ ztM?8sz07_Oq2I)+-@58xUF0SxPpAHxE*;Or2wL5;Ymfg@&-Soc#u=%4ZSJ;RypzZ< zp&-MDar<1Kp?zp}^M}S+UoJpW7*hm;q5}xy0Gj`YU&E3Cvpz z4Tc9odsFPkFS9PeMT@wn+!p)smeK8gXX<5ULa`t3>bVZ2GQYjl+Rxh^yQ*sZbM3oJ zJuYn79lQGP%nz>`hLA13mMy}?oBS>uDL-eY$ilNO-&4*MK8WLtJAFqNT@|BptnVLP z^oe)+K2@~r!@A&xwdNDKPgxr(Ph5%28aA$C;`J~ z_7*JVUt1s6*%t8QOk`tYXKrP2_HgLqom8jF4j25XpPirGb1?_&!nqv(43+U3l^}q0 z-f{~3owjz4Nn}{wgG$$WAL0H7m8l!<42Z;}q4z%k>xW+Q?!D3b>pA;F@7go_p*Lm! z=zW>!f#}`*sePcQQK%;K*$6)opo@_Z5_&JJHypKh{;wh;p2q}T5Fq>4VVbQPcm^DuQ4n-e*i&@nBp4#XV^+TSS(u_0rQxBU!P*O1m< z5xAoYh(A>U=PNgvqukJ1m8r^HM=XhLBbB_0j$m>7X)t~^_30I?&W~+R9?oy)vM*`7 zo)FT+yvjD1{-q-k-(Y&%%b(Qv!P%QK?K5@p*}=w#Zl9j+ZM@_2swY^w;|kv4r`awI z?{BBF>*RYY?qCnCcgpGb(7lBu-qAeuD-Mhq`okk`8grS)hqZ`jI)QBpb9(Jr!bNJu z+Gp>=@PLS7Sn8`YSDTnMl~Ixm!wwF=*f()5J37Jr#r%VnCYA!2ixR~P1Ov73Sm{+Il@&Jc`DaqoEqTBsq|xUgR&tra z#I<|q@RJGt0!p6~EU!R6`e?9d1TFE|U{PH9rMg5^gihYRa|Vz)WNj-G%xG;rSR}Rj z7#YZb3huP%TTYY0Y?@yPr1g8&JMW?{HoJ{c6^xv3WRYSz*O?^a+_3{r9|)$8;q8M@ zKNZxC!gu+upvIW^T9%>+tBI>}SBEcF)5Z1@^@q#_(At|av4F^|K#BQ9LGpf@fA=0QjhjMLdtm!Q%FJgR^8#GzGYq?kNiLQ{!z$ zfS1Q$q(R?qKpqwJVCHr@0XF&V)ibxnn#K~(X+z2z-&V~k$2auMYK0w&Ehz62m1mew zYEe1Kd6QaHdh#6B4Cq`OukEd7zS8s;R|YpSH;Hw)@~?hJb$uq*q^qc_Uye1&Ln-qF z?&LunfXAy6JkAPa^XGqZ^(}J;kem>-R8d4wR|(|g((3x{$;-I~D!GvC`^@^ljuI*p z-rp3|R%(XzE@W@=;S}ubERJNG^{CX_vs-x#UCNK|%N_`SJ_><~dak#>>@)&wl+6B| zgpVjHTN%n@pY4_0DP1Fr<48Qt?+j{d(xvx>+eJ}Z?C6s&BJqD!J!9%JPNmJQo$mB} zcPeVSLh1@b>J&1sFl1g(EBm=lx71b@MpQ-fF2v5l%;e9)-8{Mrws^kV zPdw&t@wOb@{^kMPON=9c=l{$!ffM&dnM?o5Xepo4$GwUz=K!r+5RW(boqosje__Hq z_!4Ge&;KPzJS2zJZRxd#ehhT&)*KvCypKL)0*hs?(TAxeDP*n`4f-i(&Rim zWedx0BoIbwBhaL5_xXdU%wxX!=JTI0KYqlTtkRghZViYbIL14x!b2j!>#uNs2|g9- zyQz$t7aTK(F?Y6BkG5`dPn62Cd_a_;)6Ranjh&%TsA5$H`fm)yN#9MktGJz9&Q-s| zQ9P)Ti=HXo#Nw+a8~ot#gF8Ga<+vtx_ocLZ3sNv5@~DbdtJa6Yn4AWZozp1n=K6* zyKcR5U6;}Cx^0Rp9Z7Vv%s_T9e@@V%NNb%IOMqa}Oc7EQjDfCSs}_&ESb_$?M4P*P z4)Xu8>$&zfjt1f*^e#NnmuYY~GzLIa1DirVWo>L?!D!LaL>+^Mh<|^vP4~OGl%d?s zejyxWmK|o-|7~!T$ZD*CXlOc*lAv#X_R)NR8h(EEZWmxv_l21^&SN0Q>}P!?sL|?? z=`tk6C;819a&~Q1?~(b;S($TaJ+E47j5^1x&k+<6p!>IBluiA0%p*8(l4c!qFq)S! z`DkdR0489XXxoX>hBX8@_091c>y{_esH5388t)xKF8I@^dTLzfnZkL z>i<)&o4OqPfZx0vn%f@br^$&hJ9Pndg&v1vhW*`by4zZT3teD|1&kk>k zHqn`AQ0j|Z>K76Mp{a=iFLQxUTHs|N2t_j0v%8u@!JKFcxVN^i@7X=p6`w~upV+1y z;jL=g*YD>>>iO4de|alsh7vptPpr`^C0~$eQW&puJPxxIDURSd-es79I9${#2n%py z^UC~hVE2KB8;f8uEMfjzgRWPH8T7C^OJGz{pL!cQeV9(??)Ih+w_XV|Qk}#asuQ;K zXmC0kT_Vq{1^zD?Zh?ll)DR=-3m%LRfn9!X!sBfxJa%WU)C$wiSnFpbmZ1C#Sb+O6uL3`a zOczUXV*tr=(se(*;H%vwMcKbA8`)1h*fiE=b2n&xA^X3I((VY?k3jHCRvSA{q6MwY z9n24c{@1b8;y?cYoNFx|&XyGCI4Woyd9!(pZ)%(fQxtdhb>nOPLLT+48}QXKNOY%5 zm@gl~6D9`S(DU24`IhL$7qht>DP)+Ka5wC<5Q$|U4Vt{8RpwSJb0&}ao-*L;wq)gZ zfjCo)HoWwjqx~JhaH*+jv&!NbR_0k|N@lQeB3H&-j2CR-DD9{zGjS_BiYkNrtaE&Hf#+8uJVo6Td z8O5GFcQDiC;%EJtU9k=L+}QBgpd-e}`I@%==t?vJcd+jrhMAo&aTIt$#qcgkYT=UT1Hg5@YOB2QC-fV8)C zj16JABO2C|U=Zn6WBhj7UylL&58LvL*@l(dd#x z)_Hf(5zKRz+fIsNiFqp-?HIHU!4@{0A!)Os)7Y}dMxf}5lQY+2W`P)i?gVQ3Cg`Wp zd|=!zRmB+hnVt&mJ!4;Iml)}Aj^QxpIyLs>w84Xbn|LAOM0ic3uC0lfapN;ogh_0> z5>zL)C65BE_#_WTH*9uAN)yY*gXWILt&S7|14c8wpq_B|q#;E;tD>9g@;RUg9u&g` z6?Y6UXYHdele3e`T5omfU@j_^aU~ed)aOa3J2~a84xywap15D^cNOGgu-JFL%l4lS zO?uz?#_d0!1kOJ3+^unCUwE=dV=|OPsEH=*2aMPa}+U zlem8Y(2{=>kPdL|vouG9(ut2g3&>N7X%e-^ssZ zQ}fgAt-nUkrmrp^7qsXwsNd2m04@Jz&)3@X?e?t6X3!#y!EgD7evwk)K{{F4b5mI< zMys~bC-Rf=hf#m6X*9&zT-b0{eyXRXqI-}^n%n!1rAH;MpiG?|LTuLDbf$7K8Om+VrU4B z+FZ~{H&IBg9z)QTgS1_u`*f`JImXW5M$xFS$;Ct2G6K_{fwT&!fmGlYeB%ekPg&hV zfsQo^58u~bD~cpKCndJVu5HkB$WWNqU0Ydu_Z^d^Yv)Tab@NoQ^Q^*tI$Au7j}chH&mU{Ei!q1!!eb5 zi2^@YL-{gy9hZxW40LaaqKX1wN3_a-FLB>OtRxA?ldZpV$P-S$SBk@h7`!q#C>|9 zY3*gBUbL93m^Qsk3|~6a&ZHgG->J!iT4CG6;-BTLKE#7tj+coip19B1Ajh z9Yu<`s34*<`y2XE$ct4BH|bPHqCu^4mi4r}b0u9e9h&AX0|S*7A6SyKh7@rsK`As~ z#uFp;B9o_L#^_~w_%cB+HN2#kEpVc|fH0ysp%e5`;t+V4 zJ}g(()^o!wy`Y!21(aMCm6|IeL`Yda7-o5#EMYSbPu#30xL|nVcAhTo;%9y*KlR=G za96D}i8WsY%wY9;G40yRPPCmj!xkUL)}CPZ3Awv14vu;M1#D{4qy_-MJvAp;+F!<6 zE+nKQac|$@|Gb)PFUDFbscc7Ly#jJDk6b*G$XgBOkt^6tH1^oVc+HD@3gK;YZ1oKE zYn4#azl7h#S_T=whr$y66l;0Tio8z&z)0MlE2d=ei2yU8OR84bZl{|GD3L4sTv>^m zW2;vHQia_}#iQyNC{q6{*0P-fo`}E;0%4-=MujoNRgz5;@)0yWn|HMIgzfAhlZA=( zyrE3qt6m!zfz@}1AVKN7a2W{GEUTs7>4kK^O}Npa0sSD^O&a_ zieuLd;TNhGX9hLcVkwX!TH*w07VMw)y4YMm4`<6$n?22zb4zo{bK?ldO1G7{|L^T4 zL+1Vu$x81G@?*>p?NSx zRSX<%V{m4FZ+58*3-KNE9N1(vHwTG?+R`&17q9sIMg#F7Kr0IOEn(Dz6(>JoQK28G zTSMs2`}GfHS2*Z*gkdkRMw*qQCIbN~A=St9X4|4N3qsqnPq@$!W8;N6?KzUtUi4^w z(xaeb=4ecCznjl$!k834aSH_6%$o-^X=dk1O1MUw1=nOhOA)!&ACXIXBw#BA+qL#n z%5s}@JaV~Zj>JP0VzIf_J~oG16*)(a%v@_FHIS#ifx5eP&Zd~xJHhI0zcO1hkpKSZFtCFG^|Itlrwus3v5N2Sjef)q;`96-o9d1)N1IWvDu8&75R)m75a+cs> z=}BX`#k5E0xXP(wmQEbB;%MPLW_R{XYcl6QD++D1HC56EE}7c{3SWKEa?K{E<16lg z`T1z^3PZz~mHb4P!Q_&bk(7;KcUr18QsJ;iD@0NAo}O9!acf>-CJ~_Rrtz60c$(Rn zZ>5iX(8xSfWDc9^sj7W8m4aPU$?C19>V>qb%Yi1gqNW-*ps7w%v1+y85YolG-;pbJ z&CC3{rWz{*RlMio@3Q#s@N1-2thM>lhpkN|wOw1<&as*&tt}UzQN=dYezdigf#0aQ zk5&z=p?#aTv*C*pe4DoiEoyVW<#v7pH&?fLJC|b-LS;=GK0Pn+qlJgCs5#!P9|#*= z9_I{Wu|gQymJOAXzy;(QJ+NE_jlMDS;t6VW`qY?}{MdCysDA0SVNy3TWPWU^y4C32 z*&YNVjgAUFfzGT2(tNCkW6yO#XU{Y@A`#FYHkmOR#axvRwW zl2UFT|7^_>-Q>X(R6=R?+4UOfnXN9<^Zd)Q^J1&`-5TN;x&-Qu6dThg2YRKH_Svj=FZ zM;xmbYs`dusp&NuFSqU@4mS5&#VSWg&ryJUV?nci%Bl%XKBE&HUKaG4G z%(jTJ9hR5WZmz?lm7I$njEtOZ8Ttv{8)&3?Gb%@_t-q332Tc0IR1^%`5p!BrjaHUu)FsbtNDxh7> z8N$A+mmTFlyXzId)9e0J`#+BMUauLt$=ma(WtFXmxlI1E1LKx%^Se|A@oZ9P&kn{X z34Xuj2HMnc?4hv@c!4i&dhUvo#_z;x_xja-`}404eaUMZ65GIL1Y(xIVL@+006*^U zmd#a3_X-4}oz5s+!&^s5wos&#Bvn@2xO83dt}Qi?C-p&2eDpT8Eg#MPkD)q5%HFQi zSQ0Gr$N4NqnX%N{S!3rqmGBB#iA%#fj3xnE2RV1NcMopd*#NwuTY5I^3yGD6g!XBf zS~e!L2TOxWVSi5wSCs56>gHH*uyRB&v&#F&LCa1Hn%15OK)2CG_Je!*YOUrOzOVA# z&i9{u%V7_V@E_*O`bCkhUeh9r9CEMY8+d=>@}SB~)Bi1`#G@2t)X<~Di5 zm>v(0Gxfa|v}_|6C%U|)i{%x_?Ewmv*)X&x6WYO}_pL$8DA+H`)x+$`7J;Jpjc#{; zE`B{1Oc$oVIcS+$_}&^G^9b{2Q_wGHIlUlBR+lvdEp>%Knogq97Y0qXpl=igjkcg` z6~sjMn(t!tj*26dbNrDA-m%!qnmVhJy7Nr8crUAbN~~!zDJQ)?*YLuD2*yk5RDE+5ypH z6l^4S!Fr5>r}GSH1VoQfuuoE$p7I49OjDnl;K=c>|TT8gq_NXn5?pzUVG3z_D zg}p_|ttnh`Jw_)GX%H=^uvpP>C&4VX9!9HR!L$u_+Ex)RBx|>vUf2DX<<74ytA2HH zlM9(IoJga($ecQ;E=_>*z6r}W)G4!k24hK|jMnG?orv6v4O#9R`_ zXoL#9V+vx9Y<1ASPK=h*`O6*TbEW37Q0c#DQTpYVM3^b;q1CJ~=ku0^Fu>T==#y5) z@{^Tzu6yQs?YZ7@;DJULnqSr!j?2sQCmoHab;_Hz%Up824ac-Ahanooc?beO7;4(Q z4ux~)!if#)uk>lX*G6~Q7@Oz&XV_siNV^tRFUY-Fx8qFeOa9Cqb}%isOI`hF7M*>E zI5%+p(V@=8i@9KvH3*gsP8FQ4=B{*g8at`ot)U}A8ckV9IG z4c2LlC2VAHomz&lBZGAUMVPjHm;0ZT%m_6oT;czN(?@@2G7}vucT2on3+hhXxP)A< zSsaotB1br^XJ#KEa_G%fnEDo(PyhZTkG5(&cSnC}H-8=Zk@gCy9VLBdL~&78(I&}8 z(SdY&kls@s%$RDdI;%#SulVRV`ch7##*?;gN}ah?zEQSvv@`P)D(D#GRvIMSP{G(@ zCrIVt{W`18%+P-guRMX$M36X*K?NHI9-& zTxC&|E6ZurP+->Ng7{L4SLj6Xru^4DCC5hOgscw9S3_w8M%NieY#|Oi;dbAcUKknA ztJ7FPno+nD=NQglh~7-O4i>@}9Kh9HhOjy6LS7FG-VsUzobelfsLsY8+QFRbv&J7f zFMORSntdOQ4WHUnsxtEsdg{&SUKu1+!ze;& z-a%ebaj;5yrEBZ*V&4HUMMVI{w@up6M0{-OCV!P4G$*XIMUHU9m%-~dssTy^*@8T+8Q)AG2N%csU3!h$_dsO7SF+PwP0b>1y?f1BwAW2xLCuLxrp!^ z3=x~=^t?X6p+`8oycHXUND?05PF)^qQ{wP>U@5Btto7F0}ua_FAcr@r&d58N-lGxm3AmT>L4K*#4Upq)=|RukcCj7{f)MI7nQc zT~W}iV=^xvg%I3=XAV1K480EZE~7Wv0b9;ft2;jlVrg&NKjg@3o11}>?htPj$<)Td zFby$Uk7fCacL$`LSiN!1ML_PbXzN|pe?Y?Aw1zX%z50*ETmNx#=6xok2v~Q!fKr=$ zSF*8(Q|M0e{|~Z8E${_oOhnBb`pP9n3Tmq)wPua%FewCbMOk?U3jw<%awfqi6k|rqdII}Zb`H;BI-3`GRr^USmX&)%FksMCh02I3oWL;(oWnU{{UeUn5(-H z8={u%vHlsQ+=Im!cQ7N~LGZVUl-|rG?6rlxt0_lSutne{ekE1lGk4Cz^066<6y#uq$jGDJrI+ z=EP7`l`)yI%C@p>{L?JKD*f)vgMWt+m~F+HK2Ae-*ep;iD6SC7Y44^B@)L_64xyvF zsb;2cp(+w!>N^moBbAe>qZ54}te><*9|fdhJm8 z!tH?7s(? zo%$1Q({33jy0lE-S06W~7U;0fI3`tNFx@zF+uV2hI$ExbQq$nCOjgLX1tAA;lnnY7 zOpn}zZrA&m-FjcUD5M{Gzo@+XNO=hImsyW@*C5S$r25&fZ7Y58P3zMJT@1GXDhh@O zulF~v;N9$Vs!xZR<=j(4h$9;Xa!(r2T&(1`+2%K=*qh`#V+CAo0wlvRt zhGV!u7Wakw*=gk)>7>GCjZJSjtoKPJL0!?{IBAvGiP4H*DTvfbP=uK<%BiMQ5m0k6 zU>E{Z!}y$b%20&r`tc}!dKjNmP|>l7KT`2VvjIA#o0zJC{i70b7{5tx;V^!^x~s^gF}r%Tev>0fY5JMH@?xXPCPsR}q?Wyg^{yc#YUNCR=I$hN#DpZ0$H781L3 zlbYDnExr|FI;H{5>k>QP$ZKIB=!U=xD;$3H zxYU`KA| zKgGFw%lhUaWR=~>PT`)c>mNRi1~f7#SznwwXMIU(;ri0l73<4V7X>p%biiAH@V+$L zE<>>!V|UgT7pIOFV~oJ_Ule7bV+fr&!Y)*C8G_nzJue5G*tbv&#@La)uSRhbdY)BW zKRCI>5nyZ0=#+9rFc>V)1j~znW-KI38y5vk2m>ZW7G-zo z11|2+FSt0KA+P6gJJ-x{f7Zu#xQzXd`&*)$4G-+aV>0(1Y{b_j!03pNN0!krBY3-q zEIWxK>&HPet)wAgi#GH8Fy9~Wy^Zgm`M$z;Ctq)OS#nf*`mW&7Yk8~Q6TAK?{)48U zo7&4A8l%rESQ5LYfk<_9?Jo$XOkhp*^}*@VRrqv0Xh721({%%fa`&_awbOGi4+gbU zb1&b=v<`JLyH;bnjgsFG)Si=jX$orVqL*w^{j7Fj?%npk*G?9MpAF4h54BS!B@PrXhu#-KPZDMdomcrwgDF<=Sqdj(ZH*j9 zn41Tg)Tc}}p0Svz{bQ!*W2X0yIXxe9djFWZd`w;cm~-+m=k$+Rn2%W)JkUS|@wN1E zun$ay45sB9e+wE+-*Dl5gVF`FCiu^`zcx5saYJ#Js<6sJiEb2+F=b$O z5lwecKN4$QuyPdC?P3uh`I{=YMTf9E`d!Br;l7uCm&_nRaiVif*ZNPTUd5Pv$%l$c zE@|#cb?w~LmipYzP2*B^JGbE7Zr7%wqLQLiiB{wr{#+VMz-ttM4T!=LRg%5NappR? z!WU-S*$RM5H?2Hhqe00P-uIe!MH!c2G6(4ExpU{1;^a583mnVQ%`5!6h56&C9SyAz zK_4y5p{SaXUH|Ie9SseN;?vP!YbbiE(VmX0ZD2e5Ai< zWN`T?f6=Jm@-hCRF~Q~I{6)Z-;4hjGoHo&)KG9!3xud3ra;-~DpX%4av{n9e7<8mR z9cCQmPlxfw_|s==O>FwSj+!f#x}#>f{xaIs$BQx`JA@{ER{5Vx(@_Ez~fS(+9R%3rPDprzBE^&7N2W6$~x2jbNlIfIr43)gRG zB3Lcb2GbV#r!H!KZutk(r7xB#3F>It?G~nIr|moly(hDUnLZmGFdLi`w6rPVYW)T+ zTEy~K>o;i8LYTi=zd=j4J?oe0u088F^Z~XyW6#?yT)zy)IdZ@)r)O>|M?9IT5gNaC zo?2WQYhJBx@GoWaDpf;fOVnZfOF{M1oUDSMB zC@w{IADG19Fl#Ril76G{#i~*EY<#h5j6EA)tQu#};tN~l5(m~{1K3zq!fMi!N;Bxu zs?w68SYi{d{J;%Id>x6+x) zy54q9+B{aw(JBX3aJVFzGyGbsu;C;EipC|z%c6mrSvJbb49pOE@2o#6$m*@Ekki4U z-oCyAifQUxy&^D`4g(=F0E0{S0j5o08vZRXRS}qw+#|e|@f=E3g(!ujhW++Ul9%AZ zkksg`YmC}MGJgerA*sV+P!S$eyY_2E2UzqB?&6+jA_M0`C*4(xirZM{vZQ1yDgvemuQb)n#OAm?l>5yU_7L}*WfTjh zRrt-7_AtV4uCj+pzj>rRRQb)L>|vzeJjNbI`OV|(VT|9b1MUI(Yx6{VnBX^0wugzn zotX^In;sa7nfZ7{;|;69z0}~8{N?pzM8s3Mj$NYl6-ag2?eEV*w+VWwhHjdH4gFoVzY#&dt-FP!||$a(T{}=lcA{l zw(Z29!hQ^so>Mp}8+PKeRVsrB<6zymVETmWMP-Y}R{uOXL1Qd}`v8^&OCMm69by4b zyMX%%I29@5&VFbEgFP|lJvLqXcM9hm?A+2~W#eILacN=taP&U4Owl0>B%2U{KW3EW z$)wllDl=*}V_tAt+{K2jB4*4Jx2QaEsu}?0=`6R$r(Y5$h4z~S@v{#o5mw=iL6Kc} z+GIrPLAE+^?qsuR;F{W&D8s-S7bt(u>^E@O^*8pvdrZ$y`ssH&!uFXq&$mpITp)I$?cT@?(_KQ6xqUERGBO zg3?u%xaZl8BC?SqOagBTOwYsXlhdx2#&wNo*6 zL=YQOVie4X93EL9ECv3o0pJ@8z&93vuQKqc(s}T90!b$jF_xfPqvj{ZxI$D`B#~9f z_MQFf&|XkTdqE-NtdI%&Ekw1e%GHkDZMqvGG1(P7aX`UK1{7ReGN_;(2KCbn-lH8x z4Ftt0>Rgi^&|k@jKr#2(ZjOC=jX>OBDDu+^RRi$+1#1-%=Lgdl*ff3+Tz%GrP$+ua znX1^hRQ^DE^2cHu@N%>Rk^6DHlMmHXaeH^%9!jg*yGQU;{C4qMu?;7a=5VFi5+>ol zG^P|>bG0MZ^n{6+9qpNlk0f>+7mG>Z*)hJoy}M$3J6B0%D#rI(sQ>o(O$yxPceZDS zjqg0}BSjx6Qo3QJ>rzmc3nJApQguC>AyGXa;%DwCZX4g#o-Ok`+W%G-+raj{RJ`>t zW|^&}hZS==V0-aPeyX?iAb+=oojfSDoz$%dk=ozgT6%IoinkRqOd)%?uBEm7FmH3Y zhO=Ph4g#4O9!Cc+;tC}6~{Itc8o0ExwW7Own}J77k7vr* z;$&)i971z@4|DXD<;B1DS2APg{(xAMsoI~>lS-1@VDj`+ zOxcE5rl+53?=IQ3Rs9}YCV!ZlWVz0a-9DJf5Kig2Kh8ve6y7Q|{$Mf>RTXSs9C_gh zoA%{ANXmFGt2z9_;8{1uZX!I&_)_~&*-K+3X$j$%Z(t6-sRdxs06SBHHpZj72C96iz8~< zH)?LFiWPw}w!EM3+UMpEq^-|yo?jlgXPHaIMbHF;%o6a)Weije*fA9Xw z(Ou$2E6@#s?M~KA+9Y%i)<;$F8e7y_h$ne}by~~E`nZL)yMSf%Ij1SoBHYeX$!LUj zhayg}`UTTypt2ch%v|W2k?bCh=&;XLVB1{Q9(Wt`xtF0>LLH*O#} z$V1FQ#Ale!!*RNMSnFzZCM)J>e2F3DzYWjKfBKWaTI0KxjlEhl=(Yxxaf}vlUp1Kq zs#G7t+XdA&okhLjzJFG2G~chIr#f z5str6Lm=2FGVwQR6pXG`<=yrhvT|X^cB}e0OdbEBULCIw9&W(sK^wM=<;7LTp+V!} z)J{=9itACo|6wroY3U)? zIdBI)c#GMaIFP=vUeZVLA$vu#;dN{Nm0cfR#gptS3UFS*m#vgS;5P9hjLjSV+;IkbqNGS$BnMG< z6mjm3!M;XxTAe8MTBKAgb+)0%wU?i)X)pEGe^QW|8K^|X76v3b*EOQvYJ4Ow01^so zDXHG)t^W{_HMfg^+b8+GV{hM>K|ru&0JXmnc?r zqchm4m$+f0jD2teSyjPqcz7pM6C!@i@?tMNk2GOjj1sZCBN+++FY`VUtln#k zFzL2Shx~ z-&e5bG+2Gg3$;C6-3lC^5**s(vWk0Sz6%I~0l@MfTiq`h&}R6{k%R`3V8DidS()UR zR*CsqlB5o#Wl%8$^Q^y7!q)p3hBsFglJxPTOI6r?e~InJgp`WIs^Os&6Htzalo+WtO2n|r?)EHaLD1fN8HzR3cr z>~1$a5Blp(D0pNms1Y}uXVPv^r?ts#8>;uNnj!(5IjN43nMW>a9Yd~!fgh`6#Gu5X znuY2G*s6M$1|O2pi?GNqEgDjO!tq1;0?HAzM{cQ`g*c@S=`VNa*D!5+%cUzOyF)Y|?L!m3$b>Sczc zlEnpSeVLazq_DHy~tl)Tyra*j`AtDirTcI)$PG_RZV>< za=F6wwocseTM}v1uWz*$igIW7<}TBVO+`V6@ih=%Tyuv;QrjnVUe9PAI$Le*8L8bd z=6cTSsn3J@Qr|IS`q;7I`f`7@7;u=H88zB=Ff}vL%{b^)N&3rnsBry-sfIj$^5Ym} zMNE{7kMkeZFM@LPqfw}$^p`a;RH58^ktNhGX%qL%g1Zk<$aR`5eDv`j^|4=6coB$l z->UV^SW{b4tOy}xbYR{=(W3*C4bRJ9k)?Elm^ui669`0M4=uM1Pxpq((ajbMS?T3| zsBY1rgQ2l>$Or4YWC?VTOyz0dW>HvuoCU5f_^w%2f*(MU&8=v`bAfes@$eU9sBJCL z{+nybKk@AhW}1AP|6)XK3}$haQgIcS=<>4MrK$+5NXw_Pl0SCk{5jQBtDxj0*E3DD_I(S-z-cZ?dNy(GL@3pz~+FzsVO zUGemR>b*Cy7)##jOL0=v%=MLRf5jeh6U+d>KFiwwsUqD;QT_By7gj&h_U_b*ctP8* zsG`v4z!fUloiv7ROVe{yKl9o1!nim66n=$kt$M$j3S%pZQ?(_r7&kAp9*fa+uvOc7 zjFcl$Bdnw&Ie*`gFWYo1ORyw7m?P+M|5VYN{e4ATCD4xn5iYC~#nTrSPlwJYb7Au2 zFg`h7p>6eo!kYIapP3=7i)Ft~a!IkOhlMaZjOVAWFNwL*{qwVR)(&?T5L1Ap;r+6> zsSk9kSTNPy*n?*nZr*{OrnygXp8Z5ePbs47AVW;a__ zRt+pZ632K@n-)JzyLN9oh?9s#fm#8*TjUK5Uv?F$p>u;PumJGVazl_!4D#u=NFl|J zUbLcQ09Gdk+TMZnW6iR1Fa1*}I`!)Y$Z&r3rEQC8&2{W#nhJNEy7}ZbGAPzb|w$G!5wq?WzmPmZ1(BZ?S?Y1;ia6d!(fsZ zjBNV|;Q{KCL@8P%tpHtHqPdeBUSMlzr3@_Ug<=Y%b^D^Bfk^b#C;$E9F^FGs9xI4e0f_o6aMoU zC!tz#@`P&bUWkkVS7!5?t_Zyk(qKvZl^}5+kMn}H4HPFmj6C!NmY(J-J!rYl<#va# z=2YQg`1BQVKd~AADPH>T0U&ffO+)Vcvt@L-%dpw1i!$gaUY9m}qeVDGOjXi%Xn}_F z+CefwiMy80NNn?Vs3biNv`Tx9pS`L-9Dx-lH|KVjbNn-5cYP^jLvaQ#xE<>~}#v$SXrQXFV zS;+VR#U44Br>AR%j|?NvJsmEb@3;1PJDQ7^`Yn%mJ8*%z$J?=Ds<-0_nfEuxQ!jC& z-1UMVOYFzI9ku64>%+xM5B1|Lrf;}tI+1@JuE`@Cbo1izsts2MCvDo z!lqb9`<4zbak8j=AO+cA=3R}S`}BYEeQB!wk%G3Ya?L*eaEH;?VHFm}*;8oQlJ-1U z&vvfQY1x0^WLIKKx;HtQJqBeMcpi>_6rrZ85G}a)gexJHILrcnPj$=T zC1R9vfu_M`5)G@VumlNU$bXCz`+TeJPac0YXfs#XNIjI=bB!CuiJ_eAD9{Z`7<^bi zIV}fVmvQ6YWX#dt_e<$*8G{%u93zFF*@Ot_F2D7=?^Rf{&pcf7E6i+hMJ>|=CPA5P zifF`?Vy6O8zDlY&UjIJE?LTUDYl-~KASuF3skB)c$)B>C%5+%d3;g<-jr?Lp8(h&m zqjA=Z#s(aKOV69RPw|3Hq#U!?8H?x4Slpa?zN7C{vERKppFoyPY{^)Jw_`D%?&p)Y zqj9RA*`h?Qtk&Y{HN_LY!|)tn6-XkZ;+Z1rof)qD#_sYYkNvqn+i?sQJN(V#m`1=Zby{Cep? z+{{3NE~+<53FobMeWt!N``nr}V)@?soA?bft}Cl7<~oZR+m&j)w|>6jyF2m?F=7_- zdOlCnIB4s21t3K#3?kQ{7YAQ(S$mo+&%2qe814;VVS0lv00g+7*y!3J^mOYYtH4Hr z8yk5%jH9B=!`66>N0s%Xf42!VeZNLg)<4Nzn+#wZ>fhneCfjdgVuEfP#%mq~#CN_I zGD)4BF70*wZx-fp8{b-$VsWNfIj;6P1;>KZAr+;zUX-8y^>osD$3l?6(IZWYG* zUETh7)S^4s$AA+y&i6AzBta{|Z7T!-37Cq!27BY~5`9e7zZcDW_cp@SYfh?T(yK`r z*;u+Z2^DYq7aK)g_X=|Qq@ilo*aq`HlPgdth0wIXxEM{Sa$}gdN-p})*DEmrHS!>? z+!2);AD|+kd*L1D@f;Bg0&4*=5V}BAPu?jg?IgCxq_ci0{feTp09>SY3jmZz_lvaP zoAp-(3$N!4%45o!>E#z>rSBR2T6?{p86Y}L)qjr}F0)Pvtv1D~-67koe&!%=4wh;w z#!G({RtvOTzx=koljk5~`k6zPNJ&-8cfg`3l*;ss>lyBTLB+B=^!S?#3&NhGdgJPV z6JOAP!BvW31_KfDo%n)yfa2T}w}HcVU1sUsxV8b4>b+LOV>x2AW31Tt$*!(jf z+3Ic)8*+xmSswRc>RrOC1XaVEaH~E<>r`vwQF&a?K!q(HW}^NKx}&i| zue$y_fEv;beC~k#m>c-1{>go(iu~@wlsNmi2_s#?en!7w6e`jufPqvrlDvoZ7LCwM zU?WhJeq9BLvKUWP_o%1Z(8S#Ga734o@QODx`c8XY%@7KN+3DIssiP3QSNDmAB0 zSPH-RbEBj&ByPtcHPA9GYMR53jCV=BW2ddZwH_4f}uegpZ(MgPWa;#}O>W}BMzHE5a_#xn*R`SN*!rnyQt|1m0WDi4;F zq4;Z<{nYG7{pLAN^N8Aw0ec&l>8g}$?KJn8=^k_4W1b!|*y(NXpR8F@w!Akr>MF(j zlFS<}QUenePY!d)Cf1*N>}}!lSmwpHH^^vhO254%e;1}Uew()2+|0?c{Z;N{nbQif zf+87{=K zYdEN%i$XOU-zfCr6ep;it7T_dkKUy{oL7nxrYg6d*XqQvn;OaZj^xoX39u4Vnznxm znkvGwjOFW-8i_@5(8Ssz(jtZN^D#_Z{;*1kqcYx(?np}Yc^K?EFkZ;UnRuu+d29rd zSF0|0M~cn-yxLQCRcLx|o<--N?JVU{mdeIWOk{hq4YtW?DfAY$iwmOO7};LsNBn#S zAp>go8<%r7Qj^g^v3EOKf;@`-ZR;*|_?-h5y+?CD_iBN#-k^3FZy7BDO=kwO2Lg6g z*sHC_boNkCU&&4;8dTU2sG20YAlFVU)ZxGxNgP3IZ(vJ2=%}`4jXrtlx4ZJgt%JPk zo-D?clrow$QGRpL`fpK2pfnnO31TsMBy)dM*z&7%7JUJ(D|`$F7a2)%pX+p`&RdL_teiD!c^ zC`0{;g&KQ%X2a(;O{5nst4Wl~3J@FB+L>%|{2o;)k6-TueR)$aj4~Z#4_D0hc3^{d zw=Mj3)K2v~wXhQ~YN;UYWY1dfd6p^3w?YEpBV7y#G5WhVk|i~A1}%RyfX#+QRX!S~ zeKYFgeq&WoR}P9Nv!k23zA7dmK?EN*8mImU4v{oyMz(V*rM?hTz@m1=yLC8}rNG=^ z&Q7QT7N(Vk6QMZ;%$R6p36=D0syWtvAR0jaDGC|BONL7$d~x_A;P1$f@?)!F_*0n8 zxWhNWf|=0TTZ8j;^hNz;$KSGzj^#Jb1b+-FklFU>Ftta0ra`NOphQmC0y_<1djt=p zhE8W2ZC*gvLl);Tl+OHer@q+4VTC2jvy)VEw$V*AjW*Gw{;4#UpF_fwu0=d@M;_)I zgqmioS1a;5_Hd527wP+vhndvMC|h3T#WiqD%Bh<;%#5vz#kNgVca`5*^6;O$`#ZnJ zF*Os?l&C0CMtYJb#Ctntx+C79=a)6fCYnLMSmLwEdE(TYkm3upToK zbBg4DlU(X>R#%#Pj?UB0+a2?0E}IkghIqrUzSyt6aEyh`9cRpAUBWb428$W~#E`O9 z_zP+^y(YFwmCPMVy7zvkd}<_iiFfa@Ie;G1NEp7cW9YOmLQGy@UdD3og)*~s6>3^; zy}@E`Sr4G zcTr$A&nBY69t9d^5`Qxl=f2915wSTVXKM!E@*Wlxa~sfs-BembwpnH zJG3z}k|6oBXoydM{R>$g9N8AtQ)?SdhlAQmNe&1X_#nYILLVLyuwZdEZ#F_e`5~eF zKcBTlhkv`MBY8|yl{_T`tI7}~nuEp(#E85MA*21lV8z^^d7eLT;l7$VYoQeM*Dfr% zVQ_d7TjCV!_>nn8d`t_ii6E(RkaXQ7&Vo3CK-J8wbIc!@A#;{##HF0;6A5FrBk~4T zox9?wsP7z@gmwe7&P4fAKXWTwP{+I96I>Se!?fO@bGkcyJ&dg1-@Q_7@}&RU11C{2 zEBxevLC98?SA$YXqwLlRW`4Yer~U4YB+-I&_#BQ`{Ibx?oG@idsCxWxE5F#5(evpF zVA1&IfcT0^?ZkFJsE?feh69asU%#}Q(4e~D@~1d(iTuf_@>^KKD>)nkHKPJ|*i5zE zT5w>u)zfXiObHt`cWJ2ISQU`7j?<3Y$U`M%qW++@5~3buex;6#nKMVKo^()Em*lHf zZmZgmV^zyYslbcs9~Admlb6i^<>*qpQ=pxjWfq@o;`nJ>#ND62|Q%w%%B2w!U0%2))eOZ4&I~)3L$o5rnK(ZyG|F zc`EjSv8*~J&qO4DY~7`GQ>nkz#0_~7Dm{ItB#ziC>Zxy7G&A)bibKss16J?R0C2lG zqF~%PSiCAykI{zTqqjLbaV;lZ?-e$f|E{R?yYD0HmPHxiUlUPbcxwz}Yu={s!$_*> zWY~Bm&o%!}JHxv^_7H+mcN4bFN)W10Te`7|h1=a6rfybBTf6<~Tihbg^mtZ1 z!}9b(I5VeRgdQEF*U$hN&mC5W2`ntCCi(B7|6{i_LjrVlw)Tv!e+kZ#?|Ls2gZX9+ z4b~-RA_|jkO4X-qrh%jig*|&z(`ya;^c3jJ+hOd5y)KgH#|CUfSQ4$)F7z|k5=ISi zqS|7;&Y$w0leddt!8AYIq?C_zNVV6yA9v3g{DPoa= z#Yj^H6S3cfTgF}I{`67R&f@{#pHXx*)~u7u3d4lK!ihQXW{+Exx1e%}aLOEwlB zr2$*@t-By$Z^wtv^ILkE@lw6>b)Fw7{#KJIbU?jVBE zyMyE&Eui)T9e}!>a`3niT?OFBS_X=e`)!IpnEa7}sl9z_nO@h>_lx4`H#U=(8qf1~ z)J^pslANd?w1+Fw5A=w@UUeA zro)Vb7WhJ#I{j70xkd?*9u#S^^xvZbCViBl{d3ahX}@B4(mo+kr|X#r-ffFU9WWA0 zyZ8ro4^~FX8K>tOqcj@c&Cp|jpQXFORZ!jn2;Ggkd->epvUwNo3(GoFmtaT6dL;kC zYUL7?J+O!ORAblvKL8sGQ}1>$@i0~Nvv`5#G+KjiG;XqP$gN}Y<| zeBroza6SXbSThu8z{zP#n*Tv+>YF&{;qJFda=*QY}tnwKHnZ)0k1?zdTc zj9l`X^_g?!%*$!NgSA(xFV2cxIAN@|e9ul>FhT5S_fJ+!<=}#=V=CVW#3;QqfFW%0 zG1kwzI_3gnpbkWs>l=Lw=A*3!7p-7E+Q4zqwiz82Vz9et1@oz`p)Oj%e3t{MJC65J z6dR@)G1)LoeTB2h1|ez=j?u_2HmzG^v$fZfy}(~~U6A@#DGjQ>KD*{9F^bJfL_`E~ ztACofMp)0Tv5yuKr25OQ5pXUvmk@mDbasstT?$41A=WhT&VJ&Wc|5ag1h>nvj)&68 zNX^`1k2K>R6h>;sBw`?Y`F^;`Kn+lT0S6KrC|Y#m&rgS~ z!%%-&s&^XkT)mcu8b=@wYSQ&!l1IO6P}HyxVyHQ4sL9FAWa?xb|K4!foosTP&V7s@ z`d{K!$4UT;6oQ;(5t&fZlpx(N#L*Q-k3q-$e6q;@V?Qix@9~0ZIG{*<_B@EXa~7D% z(+V*C2XzD;T@*6zQ&er&GEzIQBsxr7%i?FJ2tVi$!lhp}?6M`@_NmWao$VCb^_R77 zP$=m91HbTTPJdpfJP=^esgY**Gk>3vr(2-;c#|fM6~)5%n;sBRTi3`sBK=*;0YS;H zAGs%3s};hG&XX1uYkRAlOqT3K{?F%70Z+MM@Lyr$3S^(i2$*&CBZ8>F>+S^t^kstr zDO`IcB|4CVLv?G{0h0*2ZWf9x8R`;Q5|e32nQ)9X(hg;cta*OKekNX&r&34eWjZss z+feY7moddTkj*v7yso#ZWOIWWXko#cj6%$ntcgN$BF#WwBm<`|`S*79+Nz=cM-a$Q z+=R>-u&UvkdndtBF0PM5UBSIyk_o16cDbrU1Y!dSs=SzcUtFwu++sPHD3c>9RAs|k zGs0ojh#NV^^4*6>>uo>9JrV@iI&Kcu?cGE$NbglKK}Q*Aplg;-O`SaFrZ>v{)}Q#N z`kpP0J?0Nchtc=!cYN5Z8m?-AO6O7AlPi4vEa(~#9pyj zFC(9ny0Fgc`YIu@QSLR>ZKwO9o9|X~PgQ?%>aE2*AG@`%twLEB$AOKj&%GFW^~ zm^%LpCXw0EpDW78CQcp*I|nHwkGsA$aKBevVE<-Npi2wjJ?5KSUtAiE`7_g;XKD1srO||bW}4?~~Vh&yZmS+xbR=wC1P>wMWgGa4==Pr5v}wJUbhdzEl@?+k6Zta_ZeznIk$G~d>rd34na ztgHxUdT;y1*s@L(8Wz46c8N!Ga$%#MVgYtBaV^av@)L3IUElN8UgX}cF81E_U2koP zd;4$+H{E$_Wd}{lFMa(hlMB3Q-{ri^9`9WPH^1GR_B|Kgck=}V4tnqU@0;I1V88dS zoY#qM7mSw^NH;{sNx-2w4}8(P#?*i#gVJ0LDpvf^aU8AXe`3?V*JYMOtw*_jw5Fio zgRk7oC8vwHFc`XPJvKJ-VzWtnBBKruUED`dl@VfIrW ze1+2p-rfC29*trijbi$ae9>DHTz&WCf}FhFdP_cU;bHQ6OTK2|$1Qx9g|`uoMhD7u zw(b3vqtO^$yADvtjEmD72Wh3&BZV;Y8NpgJT&TM zdrN*s3P^U#F!Q%j`|V;%o!<8_4L*I~xo=|{%A281>hEJk2GoW9tDm#Ia0W=J_*123 zDx8AgSES#&9L36+wLP;^wYA+jT9I27jAphiOs&y?UGjm>tKDEM2{QOL%U*L7LiF*v zSYdLqT{?awgHVy}5MuO~?GVQFmy;KU(V6icbQYsCV{fq5O~&5(FOWXmmen+m;M%$; zl!|4S)!%s1$)jvMD*!Wl_U#ZeM+$D0r0q_yC@J{vm11P$Po;L+BX6ra;*<;H?0SKM z-5z5;)z|*X%__RDEKKgVB_0wH#i#EFh{S%`tFJ94KWY~XYaB8kjrb^8TWS%9Mk6$2 z#uT(_OhM&i3aU7>pvp4~smCM>@G>%xq{{(s3Gkjv(cgJLJM_i>T=#RjYL_Izd@mAPc_CCJ zYaJ>InyK)!cinmi;eq9WKv0Z{Af2~B{C4;Vo#m`GwRwCiz zRBLMLml{bD2jycdT4#Pd#yZn`Of2DI_i|0 zW*Hr`JJo;%r)@-{)Y49MxjXq(M&FNYMq=zlqr=o!3*1UwVlPOlVvT8skGd{bnTern zhvWwRQM>bYAOoK@njDv&NDLO7^wK*BD_DvUX%{S++-Au%BUvfeQ=I<7)SWWKR}qr% zf;CFP(qcIxZIRb0krx5i>y#OaWz-N+US5W;V0b&|{+r%GiCrV09+v)_mv=cw3s$zW zoM;^sRERlVdY4L&x^Nnd=y>k)B7;Q9kptL4y&w5(AxM7&>FacEHD8pglH=F&c4|p$ z8^I%>kmhu589#;&)oh-_C_B4Gpz6ZXv=d)a+kLdvh<*)r=q{W)Nkj4YPy7 z*+)}@y~&TWe-k+-z#&vx|Szi&YpX;%65Skg?> z{%_q(zkX&=H%nGqb#wgsIYHfAzkaSiFg%SRrI{v=4=MCTVO&g5)wbNiQ zH@xeA?jVj$aP{oBnqDe477LzqgCu+BsW;!LJZ7a}Y9;q&FBHW@_c`>sH_Kav`28+ONu)kH(bH1C@Z!oeS&vMuHSkIC6`@E}t^Bm8` zJ`tctfMUsg$dSbm@upo|GJ)-(ydP2E@F%}PySSGWAuJ>JZ9KzT_w3eshxaec5>2j= zUIh{2FN4XWsv$2ewD$`yt0a;`hMgL$S>cL!gWN=^cGrM4 zd5wU1aSE@v*6-FxcBUa(&1E8hSoiBK0#noucD{PCrq~q^Ms_7iAb3rvJR^CKQMn@1 zHp}F7eb(yf1z!`?6E&ZDMl;q#885MnJM$UG*Emte!YHE?ZIPLFB0Fu^3Tv{9VRq^5 z9=)~f(_VOQb)UE4R{Of&@7AIeVMA&Dnz)*l0dL(r1zHb!>)uHqY{9%^tKVIv_Gv~i z8i>p8DPHCFXig5d;P6sQT-k}s{4X)U*~svi-n12WaQb6@cid{)>Rfh(cYQZtFQB_j zk(RKgWR17sQsrR7%-nDVp|V)~Ma1{*R(b51W%Nw-7P29F6$uUuVugXN1qqa13G{Rc zuE{4@K_FPGL8AHa_fQMwDkN3BZ$2iy9o;I$@1Dl*&JF}&wpDxN!@1gAI(waxH8?k0 zl-O3281mL%t=F|0RqWA}2Vs?RYip=mnZQ+P5UMQVq>V?npy~DMV9YWdPncqY~f zrg}K>!xDzELrDzG>J3`f`E?C5S`W^8%3stx{;IAQLS@@1l)plmO1eQ4XyDwI!Ppqg zFD--b*4_}buIqxqIrYjtT7O!}Qp+-)#XI11i{=DtJE&WLJSr%02E(R(-ON#-Rb&!Y zp6wiE{_D7R1Z7RovhBd2HL<<{RZh^d)m}|U)_xdiwq>i|vWZkdV$+m;`0@}C_Xrz7 zsBwd%mo?WyYvS5#uCo9>J+8L^TK*d>P>Micfiizhn*tb5HLVb}G_A}g5LMw8iOqWS zJs`AmRKl>I*wXiaI)no{)-SD$=gsN`HE8Gcj&QTutmgfPPcRGFt!Q*^L3Zs8z{tM> zTe#%@U8%~dhJQ6fixAJ>zo2N?}CHlcI> zqNqN0pE;JCyG1Xs{?=W&k6Lg5o7!B0ATr07AqcD2?`M0Hp~sftrcuOx55(rS+kjbT zMAdCX1$YBL)F|4Rdl5T@Ah9l6TPCdJW|J1V`f?6D3HU!yOYRAhkm=Ui#lD=wZ3z*51fUW3sSC^R(?W?vsr>qVcd5jZpeY#3pd? zI_XWuwl2BE(!+P}Gu={tr(iwx{M|HumQ?a{IeQtUO)NxraaO347LBdJ>BIfRW_<=9 zM?Y-?LA33}@Q*ar;y@$O`=a-e%bN+c>;YaWB@_2Y_M9v&QWtijp;*Ey<0FsKChQLs`gXma`G20bE_* zAg5Y1*UHt_Mbj(`BGYU2VVJ4Jg4DLky5vb{EOxx~4Mqq2Z^Q9J_A_>Rq8L4w&&<$e#1j?SiuEtXt!W6M^8 zqwW0M+tkh#&8$BihyzBlu75rPh}8L2$_nl_HfC(Z=lpf_DkkICH`{cRTP;SZ-L~A# zgdFv*eqkQNboj&;L=NYGKRP|GAs?N#4~(1IeP67 zH}Rd5eq-UmH?#^t#Zq!2W_t?h_aVc|wAB3nhe%W1732)VHh%rETwxaFJ(}M_ID=g! z;D;r=MqotSM_$(@qhO@>N`VmF7tpPlKjL8vZwNM;tn-xDwMo;CL6ur9Wpym*f&9#7 zI%|cAH-V&oRcuGgxv&Y%a+JEhEeO?Qro7^yr__OktZ)cQ3|kJ*e#+H1{8oIZxOLhd zt9Vdj^D;_ei^o;wcXsGYx0RtYuqHq=qpE{6qw4UCgi}qYJwlauO~rrlv^y14-~tus zIz3uNLgvl1O$hio(q;6q@c15B+j>%ewKs+eFD>(vAe={`0oO?xiTIsY2`P28zU{BU zb@ppC?v)+uXBZ1UJ}^asPVS5>GJi{*`IVITLtx|rw{xU%`i@xuqw^>c^b(#|w;!ZQx8YJ-nGH>&J_{i7}le^u+Ubl5mD#coStfl z#^GZW1+LLzmv^S~6WTdP#cx4>?NMU+l|N@LpPGT)9_ zyB5Q8*?RW4sc0KOK+xRaht~+pXl6548M^H?>bGk}b=`{h@4k+(`kcq;>e|7LVrzkC@tx6G!){E=$X_RJRP~Y>OSewCQD`YM_+h2bwM}{(@kDjR)oH zY@gys4nribCGR!SLg^|tz%Dl6*tmF7A1Uh^D~o-&0rIDI-eJ11L*AOxK!8^4^UWKW zR#U&_&Aa`GiyQFPJWELF_0{Rlo`_;99RyT0^8n_$2G`Y;J@YX?yjHEXHf!{M;cDI- z_wO=(jTzk(4Ra?IO9Xc^lE%vj-VQ&>>|-SL57g*-)orG!zrxf%moShzrHdNBu@=|> z@@?bFO>5}Rh9Fx`>l!~Y;#Yqd@nh(6=N1YSLoV>v9S1I~3RR;UUVk>2C%hjU$eNdi zuYWFz%$RAa5qRG4!1MPa_qcWhzNt2iT66u1HY0@GbW2eh!H}npyhi2sb0UpO*QE%u z2(XR`%&2b&H+BH(tfw3^306yN!k{pWbCSPSI8W|#&7ZNXIrZxfHfa^PdZtSj+v^I# zoU)i)MV7_SG?2#IaqHB+Ulxb+E{y=!M(c=Ka$r~QXc&I;|A`i;;Ho_)exq3 zb|GA7x^d+)SbhtX($1e2nr*-alX5%tvid>rH+nSx$0tvp-Wtn2%_H9l&4Ojr;J~h+ zw+XGyamq!dMwI?N9Bjz_>u3eG|IeoXsHEUG-oSLU1oj+FBDrrN)jL5JpDiZfbl7<4 z#ohwH^fUq*wRu`JY7GCJD}l$g&WM-Rz2Tb?@%c-EJNFjBkl0_87=Zn5*sZt5YYC>m zNiel)8B^#Mi@ZjW)73n414^L`42gXsCL4)CtI07)1oRW%qNe<`o%yh8`=r(`HU-=0 zA<+-niH`=)22yzIZ-+tW-lr;UTyQrjAbgN|v&Kj107Bwp3gsS9fvkp|vzLwkU@N%H z5BL-jdEJWO#+80goD7dhLFxZ?df#_=K{RFgW%`eYnL`TX_bHnhqH^(JTc8~njM<9b z=>RSa#iV9fNgVt5=$qhL{ z{fg;Fi=0z(S3~{E=_iY_!Nb^PahDB@?Dc#!VfD8_8`*C-a(pqW!3Hfl-lWa-+IXbO&R@ifLA<*zcXG|7w$ZyQ*dOEm zkK}Kx+?u9ql0SDP*Q{0fc>e2D4K-`^n|##U(NxUw?_{sD+bRy59ON_r_+9}%RKH*1 zqs-rFUD)K{Z>-SwpStg5ZtHJjMx68DO?eS(hxY9$9Rs-9GDnNSW6Q@sZDG=mx^j->Qu7FjHT4r4Q$bTy^k+7l8Pwzu4m<#ZPn z#n?PJ4xnCotzd0^uo^sMrl}n*TT*?K`(7$CMbs8RUccECW|%~88o7*NpIQ`M)DX08 z>bP}kLEAei|DgXw-*3)g2hx8fbv$<97kDa7?3;quxcyU3nc8Z<{A#8Wo1AaWEy@0% zeSr1!hF0nTAee9ytxUCVsq{K~g{s!AsZ+OkYljT9p)T&R9g-Kx_HF(v{)?$sX#6og zv9b0c8n{-@#QmdHx0Q6{vpKPdAD z)Jb$^SFG>($z6-M%%~9GfaJtrX8m8nK^Z_eI_FY~G5v7lot6UvAZ;pfXaw7b!S*4r z?WK#Ab$oX{jh@F4(KkG~t3H8R5o&WULd^!t9 zM*D@i(|-_l7z+*$xhzFy^S7n!7rNY_TK_c?&PHf!-8UvVeHtiYzxUu{#kzM5AJ!fA~04*-pv!D5zNUf+-P zUL5i+RZOxso7fEIU`_W654oEt$1k1##bLT02M zM9PBpih%2v!~4O9%|DqfgdqL&5@;s;)}=o?ub}!p&ZC;b-etjHACX+}AjL6v>FtughRn7{j=61H;#*@yhy4=S7}*D$xsV_@8E zSK+CP=<05REiD=ib}L+MSwHKrxq6RUWD2Y47H{VOtq>C+GQS{)dj8suNd>Xp1H2v2 zs5%ZMzoH_0Mx%<`Zd;l)g{dGb3DyegpkotlH43qvS`KJY+BIxf`iZW5l6yyz2th7M zwIx}X$6AmvJc-h&3#1b%Pb3uT0}aV19}^a@SLm>yca$Gdtr zo7onH@GnM46L3Gz*_;)#L{+gMRFk?I&Yz0J5%ef$uv@vj2VaRj`5WJ2e2a0tnB0@Q zjn9s(at}hlS<{)h`X;E^I)}!ia}9Tqv+vm=?}7dUgR_qx@2m6@172dUt9Qy?SM!u- z#@3oLI*6sLl31`?MO5!r>y!8A-YEv%V`xVG`4GUQjJ%lerDw$H8R9%t*ryvw<<1vFv9@txBgAy`ayJAZCkO6mTkO8NeD-R~?xj27Z}f=YRHDqE5*2Ed zW`oVmyqEqxuey6L_cOo{Daz;%YJ4Xja_WOIap$|liJ>E_Wug(K{2$hN6p`*=lkeC;ZXqi!t++<#BT3^6nGIHsPZUy7Tk@b6Tecma8l%|*;Ju}tNH7(D8v_LN7fkkNaX@U?){ zK77#z*ey$wWe5j2xn5Mu5eT|ki+*f!GWRQxYWgu-5v%t@RbG0KB|5}NeB9fx6wxpY zf+>(wXu1il59&TT`>E96QU94KT*YB2Qtzq6&s9b#y!4gIllo?rNbo@wzuuTw*sJg( z;#Tl}jc6r=@hbRX3znS=8$RiI8wRA+OH_6Yy^M2AW$V;FjX2UZQbLD=mX8nyY zPH2cY?;-m%>NYVmKNb0&^5?kpEi;Arw=)dSw; zY>r#38F6EgUY#iC)}wMxiDHu|Ir3Me7LI?eT-FQKEoHYASD*CO|BR@x=Ma_o$z5<6 z1vqfqEx574UFvgCx_#eLzx^rAyCkMs?7hqa?(c3_;{8jriKkh2*`f#+#md-FH5dPy z3SC(>2M+@Z&99oJD_`Zu)sYavDhi$E5T))SrZVW>>he`^INs%x*V?jRw}FH{lRU)>`RxUmxqZmnbmmf4|o zZ6-~LR`zZYAN9`#wmGg1vi776@~1nEL&JPT`6(4fB@k68S7+_^pTeEzchyY-4l+ov}_*2yRLc{DO?j@WlU|*W#_Ws(%5%9 zX)R^mLx#(+PCikz=FV&bvJZ;dZfXH|FxB-SFQP5y2c&;SYuOC^+;E_O0jG>LTvvV7 z?|Y4cytOj-&r@)ZD!?~3zaqzQqj26{=I=JuF2re{f~cR8?`PyGLtEzff*nwAhVxhbY8i8p8`DsKo@z0Mwj!U%giQKL~r8FRUurU zI+s)bALtTqc|k@kqCC{ZR%L5(kr5VAC|62~%wIDv=+do8(!3j#Oe1Gf>-QO8ev;vq zd@AB6ZxG%R6@gic;yYchbkLN5snX+b%z&Fjo2PCgT zuCGU^aLO_u76_u3e}OYj$GM9S5V0OLz4{ez{axapub5Bz&~3SOi`C{jSb;=lZ{h+p z-A?OaJ%znGw`jG$c{*osT1#RaGH)ppXP+z1OI+fxr6^Sj_;hKk1-7P}dDmZHDVPTb zaT^b3EP`J9SKi3fZ|~*0CAHrRd#Im$*w0zE4G##O|7MiPV!KoduP~dmXJ= zuR0FoJ+$wPfrHpcF4|p?yM&zd@^t(pz-n(xnTM*VFpI1`RQerG+A6lE(AM(!x5Ip-e}s#i3odfxuEFY2^BieEp$7302#4 zMtu4d%eff0-VqLusI~dgm-`8C9jD@6=FL)3-}U*oil=NLU+!(v_%`AZ#bheC35Z;8Y9dfdW{$6@)l}C~3MKecDamzwHem?Mom8?!Ni0#8P1szJtEaW$t)>2M zvD{oj>t-W}==+gvBMcwR&kXW|avB(~q-9d(S4GeA=vkp>;|^wg7kv*$pt*K{%P)o3fx_Y2Gm_29kr=uCAjWL_7!JBD`qb%Kd|a7csmqslP& zw}JC?Cc-}tv-BSE37hjMBa-<}y(^^;VGhIR(9aw4eoXN-A7+nJbCQ z`KrW_U166yPr-cb(CNXy;kkg5 zlh3@Vpx_DqXZimf{_o)bL;Syi|3}|gP_Uf;YtAnyc$DGsagXO43JUHdUzi-kwS~81 zGGJh-+f>N&Ii7KzLp)j5C**7eHdAgq`5I9~vIO@{i&<2x-XkJ)LPYC+sbwxu7r~-$ zjR*IbKu+ABQgLwWTqD5xJZXtTjPJ9C=0ZoK5+GyKPcTHJBsjfMYXec~q?~T73(KbX z`wWBlhkML#?~R@GPsN_{pOILc6U!e>0gf2}`Hv0&QEs|XtgwB*{O7C_S)Kv$ji4!b zc$@0gsHuN@L}>r`szBGH9YySoPXKmfJoif&YE;BWRh^?%E~<&|^meG-HVi5yT@?!3 zqs`VSK{H#OpixiL;^QuBG=kEP7$3KGm8l|pmaH1n6aP-v2jA2Nq{~(n0hKvx0F3}e z$rXsDGm-;m0aoV*XXaz76h5RKu+&LVx{9j39Y@JfYShL48M2PZi>IiK#|T9oGH6Qt z$=u&*Ic!rY%26NXsIRmvcytsaRTjUg*k2-pg)^#n`)gFuREp1>v+IbmOjJj?zocTc zjw;H2y=F93`W!hCSk{gx%WJh`n!jY`*>${TJ7)Py=A2!}YqVpozhvIH;riO-6tT_p zqnfPTz?OB&ndI~lxJdBL2S>>1qKKSUjM8{C{fv;)BqOJi8OejdKc3F(N^+l|zNid4 zT08ML;fg^>Qp9pb0rA`_=Fc!brSIAEagp8H8>Y{H1u+Z;V2<%~n?}c>t+ZYF?3%{6 zdNvM|jCS0wp>=M;C^&yvR>XoBi*?1hPrY^()yNr96SRL84fQjtxX7xA>?_Y`MM>@- zUb~7wqRgu|@)-$%ugcWn_(I$`e$EMfjXp=Qm2N7ikEVipn+hyTH2O3JxY0MRmbZ_c zIwq>ZM&I~4qCBrwheqGHI`Y#~m8Pc&>(J;MUq`+jqj|=)L!)n89r<>QrXM@?fvP5r zzVUVB+cBDFTpb#HxyL2S=6kIj(ySI~+SKKU^EORgua)3ajE>h#u=({$SONX#r~Ia< zqyNY`Ukw+>&Fz=5h$(2I0_vjH*IDb){aqxXAx~%R<&Dla@9Vf|@YUF{M5|F)&!n$~{*o)l*O_nU>(troFPT5C&U`zge6P{YT7OBy_&W3LjBr#xNxga| zA7C5G=N5`3^DM8bLyAOPGAXkDHM2(JNQ~+%Qj9XbiukEIZP;pt&DW_XlI!c$Y5ZYa zoe{7j{W99lGyBEZ(bzik?TpYnF^YWSd$}$NNfTwxBgyC?KWfI1uc3H^^k1#HqtrAe ztB>q^PSn+5h^^h%6w}_vyQ9MC~2Z9U%yjlg-nCLJa32k0w&QIA*nH{w{aYb&zv=`^%sq&<0$vYsI}Y^&Ke_} zOllG%;fnv&bDjdM0taJtB^AsD3r#uz6r?M@^XfY~rxtH;z$7aQ_ia{@)Ns z?x&LZ$97Z%aAVZm*Y2o={-P_#4aGkmYIRiZeR(#CqF{V?{ZZKdU$y+_vXUL!@(A`n zuI07D=I6kyhnC=xH z2U*4n)9RAK&gYLiuTy)`_fuF2r>-U_ES7snrHlpX11e?VTs3C$nK=wGqbMV5fkRW~ zN35YbR-IemW%d#o;nCKA)}pxIKICwa`Gch_A*DY)Wjt!TwJw7Pu7q4|Guwn<7!@H6NyDUQr7r13AvyOD@cw7O+bm^$(= z5&n5sH<$?oQR-i!^vL}=5YcuOn?KU9-?Umb@-RjVjmO2K#$wQbR{}kj3j5oD zC9{MaOXYsO_1>T*Ev0@L#uZ!n-?1{4NXJuq3(@alK3ScpY+H^QD3-xk^=|dPK5*dq z<9(HF_@R;k1RmbJ4EAu+2nZ6L5cRe%nHscoadtc?>2k-?0AVXn33OsbfNN~*cV%!mq6KbEv(Mwlr{;7Vl(jJK;h#Hy zdVf)Cmk@p;xjE|5+;qNs+nc72YTLWewr|dL8xiAoAudPu8^r~=@_-(a^7>ALrUUAk zi{>B46^<$zrL+F>?K|pmk?(1qS%La-SqwWJXlxKjS|h)WKAbvEqJe^D`eRIA>MJK~c?!Hx0hd;J^Z?Bq>NJvW(eDkF^lo<1lbf(?=;Os0z+ zD2w8N^02l(*+_Ls^Ze&96WH*_J}LfF86?r=%yL<}=ZS^2RN!jS4`&kQ;`xVKONx-i z9!ivl&6B07UeE_9?!=ujJnTSLy}^5A+k0ny7|$su`cA(MMH$<~9IUhNWzc2VP>A7z z?)T&v$skr~vj}RSUj%%(xPS0ujOeb+`-n~x{a5+uLW_QX6x~KNhKNO0NLS_qQS=vx z&SnGP8Udw*V~Z+sMFrOS z)Js!#g02FuW#4ocv0I%U_tu&TS&vab`dd{{h&IbMZrnJR;EQOd|B^bp`G1W6L9&W1 zq4jgL2ht-128ns^SXO+Z+rp(6+VfoZrCUhHC*_uym-#7q{e4HuI1NT*j7tNpZ@Q-T z{kk|cTzJbbx5V1sl>d0N$_qlJ>%uHmg&^`cPdwJw)tQ;ZdFjmpqTBlPsWy&@uOzl6 z)1hyjf62EQnKWVF;@#Jx%ncUP#cz;VX5n@G<|%+e)b}-+E&O_&Z?Zxjv}B5RUyCxE zEJh>{WbU=FC?ntb6tbV!n#=&dUgr=kpOHCe$rSIt7G-u>jCvotHVYr-w_~^Kb_!94 z*JMue>vewA3i*R2Q@s0Hlo_%Z^?Q&Rwy?;7xo&!o20+U270W$`MD6brpXvIVz8mg! zY%u)rX?Ds3Bi_`Y7bNF-+v9t?3j4l3pX~AK$54Q~K{V12@*tD@ETwQ*HnQBNDcz9B-zuF%_VrBJc`6Bes{R;-YclYze> z!MGa5UP)|G&kOweJtA`zdsJ_`l_GO`#p1D8c91HM6{!rlBdjXD?HBkjo%qp#=eT|s z#e7Bx%zbcz4?;oiGZTDJZMn@8d{FCh@8+u;RM=rxdH##N&&3M{A{JNJ_v?6AcRKff zKv~c;SHQ(*iziB+^Y{6Esa)ZTx`_7$#z0fgdC_1QOZOU@+_G30e|n^3H%uwumhW^t z%fY)J0AW;8>Vf%G1tZnN4eZDB`9{fin6*Bx{4k@i4PdN#Cp3|Et(UZLqL7%hzpsO@$x^O0=bF86=4#H-BO`JCI0x?%L7SHY-z5rFk*`h?c2N;6Z+TgNy z*ey^4Cx&P@Jzs*Y3WuM@SDfV^Cv&9N=sso z9&3U26G!T2b}blQO#a;aNS&9`W)eNT`&#KQ@Q2F63S-Jyes_To5XSY}r?Zq{DZy|t zVoouE*OJ%D_>S{Be$Ne6iu3c3&6E=c0%V~ILi)=~aMO5aJsLJlVgjA1mu@Ag?p79W zgKpypEIR@V8krfU^R?<<63)p9a$J)HS+CpANJ{W>-;iuYBRXPMZ+&C%5 zI@jC4Z5+s5<;3(oR~Uo}gz>52HtY1F)>_{Q-#ra{@Siwx$qWuob9rlbGw(rR5ep-h z?yQ3wt7P}JcUme_%a?e{M#Z%1-Kxu5_pD*0KzSUIyfhJ!><$~t-1;JDEURfOzxhsF zawyOFZjcS%g;MZH>UhRF1(}gjQ(qS{IQ%mfHHEp~7!y}(FoAILY}7VCYMcMWt9AO3 zTY|<)Z+iib@lJ(xNUc{<3_7VNQ_seVj059*5;-L5s@8eu#vk)DgBGLiKDXhqxStu) zd$+}g3i~EO`=L?@RVFB)su;nMV{5O6qdlQ++7m>m;ZiS6_SRocFNcklzKMrizZWhj z^TR7iP_wuUlR0kQ%g7mDu%OfrPbv`Vl}--27m~^^bc%YD*nQ~!9|&u5~DI;nS%`LrvR`zt=+ zPL;vqrj#DF{lwG3Zn2RQ&jhXW{BGenYwJum>?`>+o&oqr{ZshroW+NUXzCqNFI$hD zi{~f}@pBi^K`IKz8~moM0=h)CVXUsQsuR;ViuSLX=8d_fj>eeg(|1t$D637`AVTCG z?KMCtC%b_%`!pIcFVXKMp0Vu7CsNk7f}5wLb}LKlriG4Mt4S#vmuD7c<44N1v4x!~ zxcNyrUh8}dbM=wEqW~TG*U|EFFQaOAvyg7%xa1?6f^=;Y2E8TfG&qG!#==zU0aS@h zr8?evAGXrLWWUp#*+Uucqawx1i;yu1;87!WlF> z41yDC4u&WEXQn?vYid@McgxEKvo zO=F3d`Jyr{C=C{uRkyt0UEcCSHJY3Gt;N+(uKbcuQ=y zR{nYv+zpF}OMORJj;;Cu6@1LWKAIVYyEXY55(e!wj$Y;J~L7Ndzhs)lbk38TQH==F+SYv^e%;o7(zB7!5g2RlRqN7h98yM=gp zqg&)dVOYHj5YPaQ`MC1o+Ud*+D7NexQEM`|uBUU^PUeaWhK`npDW(C2Uj9)fgW0v8Baw;hugl!a*BayaKgGCEdM zU%K)DU%5K{w(s+fcF;6}!yI8$=b;8P7ehRb(vu~0ACz>=#*Dgf@JOMssv`5$XHHez z)u=WY!n-x1XjntP->GJXi|2$*b40`kX`U6u+2gEP18hM#l8y>@t zwmOExt`#>pXO=-7PT?HfZC%;DLi7@Kxt)2mEjp+76a28MqDPE3w3NkO^3f-ARY=s+ z<@9uBB?Zvg?Ms6<;((`A{eCXGA;r@Bt$}mD%yxrS9+M zxvWBL_^}BAD>0e$Tejv=V{C$=(A&Cw2XH+k+rb6GVTVv!&lqgO!%YcE+PZ>5-ncbK zZ|DBD8$`9m z)49O)MM^7LF5_X)e+=}W-nh-E>e`VJh1+-S*bRU7uOq6O8MMywT@PE|1+8;}mbren z(V00)4b~f-IX8Yb=7JXO-md?kh^uv)4obbp=&ZugnZH|ydpJZEJLR`_aOrkLZSB)y zPx$TWnr88p6(y^ZfqB;Q+cz2m+oqPXRRKS5-{pudA}6D@aXpfF&~M#3LVX{hI-|bU zw2@wW2P2Agy`ql}&td*%$xW-Bd}Q%83rkma1nnI)D<FHCBN9@~9%YKSis~7>5B^4_Qyb;B*v=6YZSm)^hFio$3?YiqXE-2wV}()WQ=u z^T`pl5wd}Nmd%_lIueysPJfb0bpEHD#*Q5E%G1QcX)~CinHy)UV4vbd(K1I4Fl$w< z#eFpAQJ?OqS~h(BB1nNc*f8UMbodkJSdyh25>z{q`@`gBl^uR7CHUJI0};%L3a z6+aDjQ+t-_Cab6g3n!-fS-=kQ|Nltqa<4Xa_Mmkuhi_kaX6v?D>vme}c10UL$@~5G zEkSY)j!nYkM%UhdoUpy^C)Hl(zGv((XU~|cYx5(W=ZcvO*I62_LG4^?JCU`*!Zanr zZ#yG?28iYepV<{mIMP>Yt~h(7pVCObRRlRQ(ob6J^CO*ce!s?faJib#ZR%|wr@mQ1 zLekeh)^`ggl#-8KW#-M?WDy`pDHX^y+^fi6{3yg zJtm6mQzj0WC1%RQEj8*2?l~Bqgo(|R$*gg;Fsxa_0H7sR@GKD_q?jlkek1Cik%C8t zhwbWXf}JFm+Sp71GlRwk9@B!x3f-GdTNnUUEPjKRKC5!Vm|Do>5axZK|=REh*84N|kZ^NKz(2E`xy*pw+hC zwx+(V^&(~jx%p&fAjgvvPzm5$uI2V(OIun|2}C83#N14vR0CQ?OK+o1ai&9UKnlSs zd7o$PbLJxuwfFz~^V7^Z`|OXk*Is+Awbx#I?Hq{s#3YgH7HcA|@-DdcUbpI-=9%?`Y#`Nt>wmO`#@!RLAL*A;hra6)O{Y7X@xHAA*&^d*UWZ%am*< z^xZ_2-Xd69Cnys9C_NUvPK*AUCLZ*}ca-5ipf-GTk$-2A-D_=haYbumYJ-KTmNk5M z(;4Mq5^L^)!%*YJePj4$v`2*DXm(##q<~4VwHirLVN=ZdWAb-mMzk2kD3*CV~H8)Tn1d??#TLhco^Kgj>f0C z=_KYmah2mV+{3P#f7$_10h2q`4g|(6TLTD|I)M8?+G#-24?K42G`t}Wfy1}6TRc!$ z@G7$W@DP@Iyk(>^yGnN~XK)$A7jgRr{Y_jmB*vKJUI5;u?L@c`_#)g_tk8Pw<>AMaDw6oP^VU*SqdnPW zHW6ssZNv4L)I#eBIIdI$kJ01!{{;R&X?l;xSq1}5ia~@Vn9~YkT}zqlyuAY2?gQ+{l2*2ItPPixOW7 zKUVV<@MW!lr;`Fh#3g{rz(m1WQ~c!MM}-Mpa8_&H9BB-53NjD}YWz;bF)c+~pd|J! zT#S8n{KeD~%%jU_EK}NFxPYoD!Ze&lQxIWQ?r`-ds^B<;R;%B1b3uDd{ERucdE^)f<|6*UzNTvqpHAv zvZ}y$5^j$tc?`ZvzfA(vD*K7h1;7G9fI3JQBo9DF@=%~gzUR$MGaIwlUZC#7jVzS+ z;YaQFa(O=-f4^SdJMH&GC@9)SFULm^i22ORZUp873CD^u)7-=UE1{~$1!X`AN9`Zi zNjTYw^m8MdW>~G4Sgrq1 zTCbjIKI64gZkNjamyW9M2U1`4bn_XXmGMgoilPsL;>!w(|BU?+ew|i7Mpb-~%JS^C zjM#GtKu^&)<#(CSS3D0i;VQnKFQU&w)n7NCUu2~`&6M8i`^@L>v{E)n3P8sS46Ts9 zh{|nWmROG8GoQcP%D7Y&{Z=aIsil^yQg0?2EK$|39##EZ$*6^B5v~66>Nc8l4yQjatUiI{iYwVsrZKd=vMSA+2m9j%p&gyCJG`pvD&#B5xRrEu9 zx<-{kPwfU5s_IAg^m~%=WAyZ9$r$gcpjk0z2rs$OKYEbu~%QefHi^t#L8#5^M~ ze7W{`XAmYXv+=<-oMC3;P4e5YtYoD6F!GeDJh3-`L&yqn4oW66JWi+e7zOMk$U@J$ zBb)+-nbwhC8xtXdvdP|Y0X^Qy4l$qzPdQV)iC8jL&fpuYLvssZGoKLHO&dfyLt9hK z$X(lbh`w~GXl~XNhiH~wCd4o8ofYKZunuPeypakQmw1_=&MXrb!Bp-SX-2&svCp8c zRpdiWK#R*I4|_CHkq2LOSrOUB6PD%zo#cgXBbGfOoi~|l$l88=_|zfTA+$Ne`Y<&2 zWuK9)c4vB*xweQA38$XKEoImZOb1|#HI(WIm&XR!jQ?*)TJMhxRm>)D2vlO0aGe8Gy!r#>RgL%y$9vfz?+D<^${Hx3F^q z)?yzHk1|lp45607uzPS+C+ci&B{yo0NC;-tD*8z&E7!kr(tS0u=w@IA>jJ+EgprQR z)A!<{;s+K??SzLtQc4`=f()kknUcX2r?~)Es`qKD))GJ01RkEu%Ts=e7mJ7j4}L~< zrBQwhS#WA6ZDv;P`4S`fOD7rb7_@`hH3zhn+>f*lr(mE; zF-rZ~%GV@O7Hdod)gzH^<5NdKUM(bdEJd-6Di7GQ?ZiWPWrBy`NJ<O| z9zZHEll@sD^sfq`;yg;tFo~N58=l6 zoPr2aY@5gYgs8JD&a267;&E{#q}!*h+=23(uQI9eeu(cU@lM{Xt$Giy81nfL9a?~U zyf$iY{InYK8S-1$sqKM8=K|6eUG|)%FqP>k!W2_jtcR5Y$pXu&e+wELt9~W4ET~t_ zQlm| znCJ(1vUol?5f<2eRb9hb8?ZBsLp*Tv;LmyHjTb@HgB|O7gpNGf^%gEIaHe;64Lho^ z@wn$;!2$n7ENs3XwzHmhyc<@G;ZH1~TI}!Ex9#X8gXDWgXUVj0#s`l8I z%!*v;wmwufWkxO351M4KWO4yPRRy>suS!QUeaO5$4tH&5_2+SsgwZ&I?7XtwU6JMQ z&~_rnsBHe%sbnJ)_!O9&%M9-0F;>nOV+GSWV*nzdwsd#vhSN6}#YUjCR^vjKJJePr zFRZBBh9&dVlcphn``TlZaXpE)XTHA=70I17-@*U^2!9{-+OWgz@6>|J&U6D!Y#I%2l-O0_> zH&`9?ZFJAf^6yaAkSRb62u|uO=r^;{&Qa3eYkId3dz{N)RBP_wg6DwVePtg`qgDSq zhef$D1&%++5Qo@FuyFa1iV-L|ik?w0b zM0EGrrR}N3{PNQfC+GS)dGeR$aG5d~s>#;MDQ|X%+=)JI7U*Pwm7wVR@7Xk{x3vag&|wK?W3E z%f>>uQq80#fu4J;nbcS1@$U0)!{7b>Ux=YP_JmQ}85*fu2je2=mvre|^J@g#D5K}s zH^-h|IFU$C9IPsccfuyK4G7J)=a&LX4PN8XW*|6{@g;lw){Y*(&B^1Z`#0#d8*!dh zue7FJVjz8+Qks)N$3Wt|{W7w{gEEkt>Gh>%BD)>9je*s@YsQ+18R-1SpNVV!_cKw2 z)emqsX6qTraUpqgPaWJs*qcYCHI4Nb2hy^Rxtr+8tlph9$09O6GFh!FPE;v_%d$5c*EWc4F^b zsI&fFNt>RowOj`V2cpCo>$sIk3*BL7)K>olc(!>WI!k6TY9zX4By#ML_$f}8lCD!n z0%zhkQ^r=|pg7Lb$F3Vo#%{&d{V49R8N6|m7QB^1f$Om>IV+>_tjO8e%NStCb=uDP ztO~;M8O*7-_NSA!5;c#tgQ#hh0V0G3v5nPO3$b2(69VXlPS#zA3&8x_wVl4_sE(?87##aFMZ998>Z^Id%l<^&<4+^aI z_W}6qgCFOOky=Vc^GLi@LXYEZLWd+Z#W=>}&p~ zWgie^tT_b8%)l*(mCQS*dGG;Cp+`W>lh|9+F_R&0t828K)P!94wiUlvX?cG^&VgS` zlNFJHIHY>F-YeZmbHba1{CQ&DtNDKK3ht!J@z3|`nTk57LRH^TS|jGMXwWcgS9Jx zjn?DZ*J-@I(EI-D-uGpb9f^_ElQUt_aW(FmB+GrTlcxNw@**aD$p4DmceO8czN>w+ z@%@X=!}>j`23UdTp#m65Ktt%34vWRBQ};4#^m+Qe1MeYx#lEih##a?U^)Jh1Jo?@Y zc<5lH{lB+7As29G1h)T*>2MoyP2GzP-^UnYq$_d-%)V3i!hAEyF^4`X`}}{$wHGO$ z(N!qCSeKl71AFiGX1~?vl$x_u&8PZL9sG#eQ?sxIY`bH7YAF5GA#MwEhghscmN`e3 z`!}18Te{vJUl7)IF32#mTFK_flrszZxcI`VzRY1}H<;NK=KKr4)P6-MHuuz9U4I!* zI|6pIv?u$`helvtZ%=PXYdH0$exNI=X*+S7PLdY@7DHeVxJX%lP1_uHbscdP^nMcS zSkzEb$~gcztNbdaiNj-L>s7Q7f)^nmO$lHw5i6q0suH!qDMZ`x3dYNtC=;IpWsN+G z|3`F;oYg_Ov6a5Ia`b8QaaY%Xt6=Dp@1Z#-+(dXVMl}mJcF3&Am*dUS1Y|eIT`-(M z;aKy2xf^q;=i)ZAPBRPt%`~(2V)Mhn&G0BLs=-fbDr(WMLBKWJYVT z08$oe0V=!GbX1s*&MF+`?}zJ8CwyIGPD$GXFiyY?E9^bWVa66y`d(P3;dNv?0^tnS zRo=+dgQJHEu3PYT1KNP6ENtt6O>gQmXBolL5-b+g>xPi7^-LPhFOK6eNoo zNPc%tJvgBs2kkzIeXn#TIFb@dGMJK)oPzO+^M^z$|8y;ZBk6%N(r8I$yhfR>==qK^ zTrN6iJX{ph`|vQX>rEFPc3zTu~P>c-z0YsrlAfbV<_NX zXC?3yGH3`H_VLP=6F3C#?D`vqSS7v)!{fdwl}DF-g={oIfR)*}5Y?zXf#?l4V_fkG zN3uwn{J1rgmE7n<)KYx9khp#U7-bNh%>Kp6ZH>9nO5JJ|xk- zjFEg`Us67BtPq|kd6sZafPNFx1_=pl$DQjyug7I`T--Uw_OHXfE4-A##js+-S4zjL zz6G>oyJo_zof~42?Rg@dp^o-YP||SRjt+q_(=faid<~xcuE6d!C=1KTYW(26vA3BI zbF!?cCx5~lO`AAM;wYVZaFnB=90A-;FM}_cvsdESzqbcBGh>Nzp%tx4X_S zRg2KzW`Nk(L#!%GT4g)z=|89QfUgs4{bvMV|JJeB`kil|wSMZvTEATj^27^PcD6Zm zD|I@1t&i)(ZwEmb+csbjzyW~fZ;QDfV^K17FI+6BR>9@-nEzenql^iN;Qw4m$Ia`q zPmG0fmY7IfN!?I3XKr4^9#hrIEy-%Mqu+!+AX5SKw4e0!-OFuyYO(2QO)5RD1+5)P zrm41b(bTd}fJ}PNCM6#7M1(o^a)w1rN7NliK(W79_Xpv(B3@STk8!CJMcPhmxdf~9 z>@thCe#HY#Ag?Cg-L)3hfFQT!4gVS}o$t2D>nSW|aiq>RSfgr+6IeJdJ2Fc1{;6$f zUsFBB*18)wLNr*zf}XH#`x9CHzcUeFkut@fP5+&BqpV185uk*1{n)p;T7Y%Ev4?0@ z1XjBSMp@YNWYa_7^)NUU3#(&45+n;kSiZkF29 z3+t{HN^GATdW`qlrZ(YTCqD&hv)ESWIr!4gY`)Y!CSTe`QkrH~uf!_BiCl^^U7&OK z0-VVU&IHW2!}od?splPwGwmX0vUbn*$XHo+e|z`rD_9a^|6puu$-zIJHQUd&mTdo6 z){>9Cd)7_@{;!*qwd7k#vs`Uk{K}#wf!(+LY=g<=gn85knxDMMT5Jlq34_T;ZlEPW zAiSkrt{}FDcq{N4x%jfg5N|$fh=ol+#TYGd$R;)^HgN;l1U&mpN15&of=hV&bniyW zp0!H$1V#32OqM-CFo#VTVW@)NV?;ZG6}Cj(KsF(q&fW#U!F5`M>5Z;L487;zP(MPAaZ53i+puZ(l~UD_OUDfpnG$`MkO$^^=E0q_ zAomN5z*Dy;bw6++DFQ|+*mnIn=G+eyDy33DaTYdha0?@$O8_q1*{}z*emm;7AsKXc zS69Lt6(g+hBQTJun}HYal4u@set^)^83f3B^evn zz%^bzOU<#(fQha*rFli2`if1gwltrQ)WUEqZ#-8He5XqZPV2?rNpsd>M4a89`2^hM z!}_bFQ8RF(f>k;(FJC_o>#->+q6`Kfw=!R91oFQQfJ>dmrDovsw1}6A^G>cztafN{ z*m71c39Q|QHb761^N}Mz!A&zb3AdZ{0~KX*;Fk2ds}Nel6pAv96Mr9{7WoFM!N=*w zd5}&5#Ux-Y&?7i`!3;1HMWv7*JOhEwh0yooInYAvMQLAbGoWO+E~^$12y=3}B5PwJ zHR~24Naz-wy)bZh1-=RumsTKQL0HNm4;=TH%zuHpoQ&!Vb({e8>DfGI0*2^3U?$Nq zt|W~GcOuxrq`>z9xPW|>4M2$n01Q)LK0Fa+H9zuZq6xeGvOC!`yJ+UvMbUb~liO$@ zRs)?`LQ;XFaK5DeVl=K{Wf?{z9a&)$G#WR^gVSiF;zBbh_OIyj9#~eG4rg|lkSvpH zyoycCh$=|YQUytwl-EcawyL1?9aY5w3kGktySx5;&%*?z)`NBXH(u}vTs7}{9ws>T zF>q?P*Hwo|FF76owdN2+tmi4hSpQowXh|vNt~-cRBG1cbcBqzEojNEk* zs2o$Wamg`EDFFTef7$ot@_;XO@&NR#kO!C1xKbXnjmC%MA;)NJk%wHP@ez5*GaA>) zL%z}Yf8}Aa(fGJL6ei|zVI+2;#Yhn?AF(d-K)atcAKiQ$6NTYW^dVlV4rfVv-$3nV zq>zQUywrb$?1)E)WNt;TRrDqHKj;uy7+QS&M)c7H-Q@|tKA{%>LP+F#&{TVnM;BtF zLCK;wy4NNceof>ngp&@z^g<^Xk-2LzPe3zIla!40{0plirvGAO3UpSud$I0DA|mEY z2xO+K93Xiu@CEBd0({Ii{cCA)tzdb|DNMoE55`MaqE4hGwOD5*OI898D87$0nqzB( zk(mJ(F-I07v(%o5s|X$c#U3`xAzT5`4cIk*9x28=TyZ;S8Y~#u2xkcNV4EQYFcuoQ zj`U4{{T_^=j0A?LM`gGZ!9_k%it7||^il-3&eajx0};eZ5y>rIFU0}$$$BXcr5Ea@ zIH6vomlhdi)AZ75M%i?|bUFr*OC!0-nQOTdSY`y$(xXT5`;q;K-j6{$SFXrO?At~w z)v)uxwky)4k&P#-F`q>f=;lRc;I1J-mtZ}B&WmL`DV76d?Fs!=qn-E*gtLh8KIlNk zB`}V-yX(&5HJ*sDZOm~n*ilzqrjAHgVBaCw zcMA3~T7_IctbpMKghulS=oW|S=^7UK04~td#4aRTM}@IRP@V*u#NS8gt|;U13lj%g z3nNo65D5%|*e2MyIlZpJsK_>jwVKA~{swxQjW&VkON~ql#7qzrmTQChaD?8{#I-FM znOn#fWX+C3xGZqOTMUl?*+fSHYcH0Ru{{YfLixz)a_EtC%4Chfb}YF@04Rz@N(gWkdk5sOIf3HFv7$vU63M?kSd z7^LI9yFOP7^3IXblYY}_O!~4M!iA{>RE@)IP!mz9t?{IGWKk+Bk{p3zNYGWJ5QJ1? zVL63?sA}>|IzeDHc@`12l7A6iOVat*ShY!>`PWz_QfsAXW2;1PtrSgcmB_A@{A;Wt zsi@Nd973fvSw;X77{1C$#$uDYMTO8COax`~&A{ClLA`7d6nxbsM5p0(<`6|YBX|Au z$cWw>nZqB8GY|aujF9Y0sL>33@*U6!$lwmRjgV8CfdVV#Wsp-l$1O@1belwTBQ28> z*ss1_FyD)+i1|(eX|dbS4UY$#1%%m_DwKqOTm6#3u+^=3#QD?_9Ko`WZ%Q_<11epS zg?~pU!yw2%!o~sewGAZ6xbZ&(eUf=D1`5`IgpzAh#Sm?Q^NRFO;6x2eXjHKkk!eo| z!amI(3t>+_t`NrYHUmF8st`5>XjBOMrIqrNjb}#o2*RePAnY3xDdlW{%|O}LtcZRT zyZL%A==in;EQZEDsvA&=|GnFs|LJ{6mPsY?jDsc2p%1=3)2Hi(5 zDS{XXJ&w|b2nEP+QIT4nV$w2%^bj+yjYiYIg$=(!Opsw=#nU8Lu@p_@3P=AX3Acrj^a;Q%^ep%%FDZfsQ;0w&z~@wiHDT}w zXu-4jTjB_pN_z|s0gkLVq^;+C@L%X&=`_S5;C;|b5K`oDV0kej%0ltQhhp44a4(9f zVEw;B+FbnKgOpYHjWQ1c(iCIa*5@gAX)TMHay{abKuN)<4|&R*TJU@{jBIZ2Auad~ zAkFaid6s5tp-cE&yT9RkIUne?`wjno;{gZaBQe*0tF~E zfgg~w%;hQ1uKi7{!Q(xuHSL2` zU|d@0%X}7K&JY;%3N`Mh9`OcxYb*u;M?FiO)qh5uI(M(XNr1>kr|Vvht+Gx;wUbpD zzC-$~X*#g!Kddjg(eMrEvx=iZkTb68!T4Nd_zz*TEQi6lJCJ`%h8DV0Fm#AbB8&eI zvVcL9MkI&5hmeV9u2?x3+mE?g7>Qns3bmFx{B_p?uU^)G*q5a<856T~HpUzsWikF3 z<=KiP%AJZNgchO<#3-ddEv2D)p)|yMQfYi(y;kY0QU5_`oBzw?$suqwoS5!x`>7Oo*)GSfg{8z?2ofSj`%2)ChnLT+I^ zfaqHNtkwJ!U%i8Ec(&V`y9)&uPn5rM)Os)Et69xW5pnSVdcnQSoJlAlH8q9c|jjB!%)ML~s z8AT+iP7ak-vdkJt3>60$?eZsD5%2R;sLAg0o_MW@*BDQIo6j5+FgH@>C_hww9I#fudvPmI;D8>id=YRJ}%3M17Smhz5JIcDI^KLMxG5^QNV z%^NNAwcukwZ5TQae)MI~;}+w#J?L?O6&w<~ErUh_RY|;*0=03{pnSd|paim|CwvM7 zLbZq3FT0byEW3jmMNwikp!zHdhArz^QE8);d|iaS*dikgA{~3mvfe2{X_GH?)JRJ@ z$QRC46~&0r7`g!9>tVC<6}@#4NoPK3K;r!l|CP&>>g&zQ9=-Jr>lSk}V^CLf&inUMy%SjO0;0u_#;ShH+ zQ2>cbLsaKr6j=&LU#9~AsrGt=w?}49KH0EBTcz2J-O`*m6c0*Au#!e3e4lIT!N?^b zF1^=Nn^lbk?&mqQ)=Y@302zSLi5oRh-~pF`ukishI~eGKJr4le04~rzgv{_EIn@sz z6_O%`B#V&ayj|d>7*(3=ceSsr7?7mGPS%z*ySjft$^-B^C2FjZEB*xDFCcAHIuqdu zqGf2_gr9*0arvWy|E5k9R?`VnVL!fNDsaC8b4>E05~6#@Q9)GjVPsc0CdEeAOX*iU z-X5)G7zuEU4u`lm&##zT9&caWM5rN%H_k-R9}dyfB4vL(Wx(U@XG(uOWk0H`0T}%# zt(mV&P5XJ{Js_&=ORC={4iHVYm}y~QTEpQpW>sLr;6cz}xPkBdM~*ZhNYwY}<$3I6 zc|LnwKAGJwFEoTaQ6zHz5E&@}CTU!NE(+QeBHCp1P%met;NY+1|B{`}L_uBPr57vW zu#82PNmT~Kh9~+>WDH1{Qim2I$C`RF+K##ag3;8Bs-R7pa;7;>MAl%e=2}mN{(R(* z-orv6nOxT3<~}SF`cvqu0Vfpnva&ycx9AJ#QVNl|W-SJ#^}VYVB6Ls>9!sn7+=+pU z?ZUKI{#e|;;;hEJ!kn_hI~@Tm!WkH$7`A5sZ!s)%3izQTk<)mH>#aan7CaS!(2L@SP*{-BwUFzr?9|{3h$ut@wm_!!dahNpK=G=H~KhyvtD=?2DcXEdLFB z@l@nl$A6Z%%#}cFePH;5rMN$lY^8~sCR~kn__AIepq*_AHX0Ind|B85Xxg2UC)-%! zOys$cm+J_)L%9D2RUqq_y`R2Br!lhU)xJ zVa(2o-8HHby*D}$WpKhd1@KTg5($@BUA5+)18@ZDLfnul_i)`3M14UdG+h1Z&w(2_ z4j{JI&B4|_5-M}xyN86nx-TfNyi}M$;H;E>^Qi6!*phg_OHT%CKd*dF^o&>^9XZ^U zgSA(RTT5(nmAiJZHdnm_up+chuVlm?XU>A|*b4nU{K%!P<~APvMwbSo3^ibJ0T(uj zK~OlB=HpRP%yI60r-YxY0mITkbvSMNnt)Q!@9wI<*v!7!c80-WZrK&%w2%j@a$a1^ z8H8i3#Fa-2HD?k-=A+lNRY~toTvpl29eXRC2V$NkQ1loKjYv&2t z0?Nr*QEyjO!GS7W1N{~tR3Ad1O;MrGtW5B&rBl9DUCmSaKFMd-So3RSkP;cOEmd+U zF8)F#QMZq#cvIggn!gjodzD0w=h5MdRZw|jeHM~!dkD-r>v@z9*WSW)hM|w3n8Z~# zd>LeS=vHu&TVJ(`=gurR znP9A!1j}wSCY&4$HVWaf9nOFM3phnqNMkCxeoDiD6A~xfz)T>)k#GZ{Qcpy$dLl;o zlx#l!?MYZBK}HZ+>zUJ7&0Kolgns|UW?;dqRKJ`&yRD3{@SGV+pU|fTe*zM-od2tr z7?M%XGy-2o0c=nhfp5wKd`!MA4_QW_N*-KB;QR8BZ3OO>ha4lYL>_XDzytD-rz5EF zoLqf@OP?d6wkXlOI+xQz1#&0l{V1TdAUTNzrN7?{T!I=?dZ18+m{_xN)%M$0BYUxF zPJxa6dh^j)ZfBZjVzmon4Av4D&O|&+A`Ow3Q8e5lXidC zP|zCQjPAW~u+)y^d8Tm!Xgzl016oO6Q2bv!J>7e#;t1(Y) zPUNCU4zptQlWmmni;I`nQWJ*%F*V_I{FSM5FmSYiLfX8~6@xct-e<1`2!Y`uEkpwn zggHtWxJ;ITc@S7%g)u^p)k;KyW|4Q<7Tfh(L2|KQQr26Vx#`WP7F5X*_T@)&P%DrR zSJG+78TsT1j8|ng<`FL0K-|arNeuJOPZ%T|Cdk9RJzw(XZ5gV*Ky3E$Z>PL@X@Jxp z4TrcF$liuSyc2{^W}tKi)}!)qgo0j$R_gXcgLrh5AXX5yknq$N`N$A zC6#s79He$_(OGnj1c>>FE2JOTSV;=3qxW+dbP9DS&R)`?d zL-8>W4ghS1AVBV1t8!f2W-*9R%1;Fs}Aw{1J#M$fM#S5|A2xELAFI`gD03U zu_m)sb+UQ%slim|H;Z&^{hsJcxl00uYNOsMtmip46?+t8y?}!RZk-A07%z?+YOIVo z&Z!5kEptrh@<)YWY{isbKHxTJMOX(2R@+fgY|e7>CO^cZu04V4tNcT!UWJ8z!Wk_n zx*+W4z8rVDw&DqntUpK3oP;RG5=kKN-YpN5;AR{8#uo9I5=$N(hnTB7d_zru4FQki z2QvIadhH3^){4xC*6l|yQA>-#5zCjl{x&}FcDjBha5DYnBQL)l=p6~XhBe>Nl|$Gp zzVbZx^`58p(q+RWU4kaYeheIuO6{nQbO3OX_>{9C z;zD94JK)-(`uzIFi=xCk-a@9*Iy?iNUaqsS=-3gxiM?QSm#L>{~)iv#+fTQA*OBa7Mr`8U;Y7HY6{)C_Rxf|j`-vL z!xK1K0q+R}#{+2}54O+w%5rME?rxStC&la#fQMJPv0yaV-Odi378RZf_&&xYGe6)I#F{ z#IVO!Pu=|8M9kEYse8lTej+;TeT6?&fg0bTG~S-xKLIrI$^_6zzh3zY15a;0m7adm z?c48v17GotXDcXkNpZy_kkqQi$Rr?tHS*kF(NAnq28=J!w;tLL`8<9SsxfunasD%cY0 z?&j_4m2%~JB@W~3yv#vZ;tN1Ue7|RqVoGF)*7AAzaF}=z0iy-wV=W4z_yB}v?1%0y zt>rCbNXH?m0TK%bfY!BKRg7Ecaf05zNNDL)f5ur~XXSnLch|ChM~1t%4r>#^ z*g!$AMB#$PD367)&x9G6j`8;%#p@h#1G^o=jV&9s$T zN}#ubDpXwW7@6m2>|u@e0cmkgiv2}uhk7`HsBrP4<&euA|6)(Tb)7TK|0jLO+BFyN z*EW_?w(Fbb_-h~ zFzjUmTU|L!u!`wFfw?^Dvt25za7?WU{sjs~6jopodzLE->VR^?am4=XW0=rz@U#(R z>k$fhpL=aQ?fasAiO-L4P=cPW^gBoyPl*F}c)*FE#OXgOkcrl%HoLjAa&?SiArMd`xDzG5XIUQPAu3Lqb|UntLkHK zmQ4Xwbi?HT9wH6*>-~FQ5G98X!XD!%$I)G{(IVa5TkWyx`>}LmSs`qUxv&rA7{T2% zCku2IM#Neo4jGotVRbNJMG-Q8@oj8g^y&xTF77VNtGT7V2vY<6v(D)r);4xy$paMv zs~~Pj4{95|f5g&q0EtJZSN^g3a`fqZt35>+qORFkoKib*T>HXnSW8VQao`E@Fu&Gs zcn1r-5xn`Zp`A6Q%>K}KT)X2ym3GaeU;IsG+VYGgZLrH&Z_oi^j{_^{yfM=`1wu3n z7f`|PKQLUk)QKBPFyohAi91jEere-rzCWO~r{kxf|G+SnKVDU!68cm^hEUkT1$1yX zigVziiM~AOsc_Vm8cjXGWoWPei@4MTPx{I}{@tchtC#3c$@|hAQM~%>?9~T6a~(B* zi|x~q#2nap7>}g-zv(SfV5L;H&H9w7KPB&~ny`FCA^4Ir1OMquvvsSHrP;ApEwaed zd+D-MeSy)$#WhyJp_BOCgU)h7EQVD&bQI4fJU~HbM}G-B`pQluScfq(LnAm9DS>BU zr%*3sx_X&YUSwwJ3$nnlroh$GWz;$Je%zJ9n~q$egAd;R99u$2y@x=9^|7zQ2j~gQ zjS5xsnY1cZ^Mzz7RpVtHcg4o8df5|G4>Ev4y}kfGu22e2y}^4lZi9|3Ug?r6x`ti8@ij>g#>*+);hC*Pc{`i$LD68Q}iUio(Eqs73SQj*`ym^Qr>N zoa3tJ^Gcdh7nre&K|?9}v7u1H1gzqj0N+SKWf%t(r1S76`!_J7a2Z$JkWNMXf#$B4 zO}5UyL+96m?=lt3l@*2f4jQxSmLos4Lv&4{Mgi{<4Aa_;>1k%&bfiGNJ0Ur3u&_-a zP>?6>cpUzID?3p!|1qVOrzW~5t?T5w`~`bE0_9RR<~PBA3X7DX2t5{PmS_}MmgSO4 z7$_8r6{9@IUGBnlj0^K{CdTAGDkA2UO#>V_7J%hKaW)jG)hEz^F)tTcT0V&^NHX6> z60;Vi^nG-frN1^x9YiVmyZJ`|o1Lv4!txOZYry^$%2j7Al=uEe0_Acua=Z)0*df+J z;^b1EgI=HuS_^%_73}ENLJZ`PQ36+gZS{I$=OyFTTz6mnc+YKFb-74wE(QW{;e~Z! z>JZYkX8KeJM?<%w;z=RfOXzm@nB^remj4N+K^ z6=FJEh~Np;#Wd{t+UW)odxG?mZp?MaD#!pF@&cD0FbBW}&-3GOGv4u@(lC{807w$< zU35SmiqyQ1T7EAn)O3-;Tc%@sZTY5$1Kqh?o1#N`*o2LZ<4sjPSR-Z3ddsdvL z>|FLIeJ2?sXU8hx#3!pW_1%18Qais{f==phJh}-f2q35Xn%NO3KLce5P8+%jcho?eMH#2RQs(mwFnj0@b^UOUp{p%bmTy&JS<39VVVA<$h1 zfzEn5zI(SJnw$N+9nh<1k9V8a9AV!ox4A2~YO6mh`ptGeH-AN@eq#?YN7*Kw$xlK7 z`Uw=Ep9%$eNhknzfC6C0LVQY2+YXs+gST;#W-`xII(<#(wU8q*ahAQMx!on22RPmD}$T@MtKou!NM6_ zvT>0#R(S@#1oPb(`_{R0d_?t0XcNwUHh@+G8x(in!kLOFg{U?G<40B^ks@7;CfUR|7Ru;~6 z@b7&*=cwbM!qVr>nML}{$vD5SBd~d4TbrC zvR;y{_kAOJAM#j=qwwi9hrw~fMg

Mxjqf88x?8)vGH8%tcqd4_LLaBFkoEPbg9 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

oIT(s8%s@Uy-Ekw(zc%_iH`Ube1( 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�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�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

9)O0M$5OX!dU9G&#@?Yp`^-WKrl{*G}gMUN) z*i5(XWM@|$u(&#nUmm{6hvY}GhI+u+YT*Xvwg$XEm-f2&>!h8oF=VcT>)onB{31?% zyR)AE#Q1mCpS*{7x|!yECv#oZlg3p4h&!VW&9ZQ1^H+TCLfh_IjgxlMw*8~{?H@JW zw40*c?t>d_yA@%(vA1croOZ1qjq{Ig@XsdM+v^02>~GHQZJ5ilz^_XVUldE4se2f? z%Y!+VH=9ut>YZ|uakTd>=r!5P1I2ri?t(WMfPX98%Lq)VA8VJ>9%6S8F4H}6lEpm7 ztq{yB_v@L)^ER@KX)MoodFH}li$^pEbXFD@BezLUpfSr{3SP`1$KK|11~um9e%}bL zd6y0G-~w!t27Kcn2RVb(W1lNBTdVn>e;QfSNx~O5M@NnJkF!z@O*E>5Ej1_21$ujz z`c zPJA{vDB-`j!}{ws&ikzO;bz^Ivd=RcjnxmFO+SIpr|%rcezz2ThvJxqH4gSXNBtCZ zZzp|k!5+SAFz)OeYIb%HrJWJ#?WWEMWxFVQkg^9T+rx7+zeg!w%I_6?-@)E0ehpdR zcRoC5GrX@Wo}TXxz}JsaXK7IW=1%zdL6zwpvBAUe`H0IB6_h;{maSla#%Rat zhiPX|4tOlUA~LgVxzfdi^168d9Np!WeDxu|+ts(Q&-_6>v%V>P&rLe3oE7mo zqC?~>+?E*|wb?Up}0P5)&5!@<2FZn3$RE&skRZ(~QivOg-=fL0gc zdsv@J%d?hj(EKfrNnfw|5zE_4AL4?;WAddJ4kw5E{t%BQ#M3E0egq#Di-S-1y|DQ4 zEqAGfcC>JeBiShN1m*b&cYwcL`D5-_{y6&|al7&-7+a9D4L*rF$9Ny(T|9l~B^G~c z4IT;kHLqmg1aQtm3`xD{mBfLAoJLZu;RIt6OTy&4}J^nu#`JHo@&(9Z4`JK1s z$Ild(08iE7M(}y}p-tHL$gyvIkC$yT3FdF_1{1Cq?UcWn?&T8CD4Ve6D_RK+8C1-f ze?_DyX7!E-L;FRY|0&`>fq&@xL@|8_j}Y4l-LFNjywc)t7d+l9*zjiW{2@67T>iLc zf^+&Db@oOQ-H{XIeZ>A#Yn~R)U>$U>%K7bNo6%ht?6qG-_BblOef3X(t!}%n)BG6Z zFLMUjhj@?x|KS%l?%wsOomp~~`m9UgJ`ww#z8gDZ6NB)CwBME`-}HBGLKd?*rt`nk zGk7JY=kMGAuHboO26-y9zePSHtpB+3%Vt;CZnpNoR$@7M_x_pO1-HY*vU7vHvBJ%& zJ3{{Q7TBq~IyEzhgV?auPb3x}wLCevoqejwE;i#9FBw_8$1LYoj*wt-jlIH}hFZUS56&d3jkE zt$)a;Vk7TY+u(*5i{DT2uR4bt;hUJZY_Wy&4SZO6KA^SOWaOiH%2!i#aq0{g+Dh-Z zWS#U7)|Y}aBi|XjhLcS?KYmk=u|-XccWtau9J<$>BTum4&hkW~@QAbiZfMiC+RfJv zSG${fYpa`9)~@#NAbv``Fg{`F;Y6F_F}%d04a8I1xOw5}bR3&7&z`yAA%Eqp2MYE= z=ujv0bh_*m5kHtj535)(Z`Pw9!N%hHeb`3OTPmK5J{r7|OqgrgR511kXO>tm`drGs zFdpUL&%G=7#1^-#r$DYZMM#|Sh@TA?aoi?_GIiv;Uj6`q4p(OBAk5FB9T zBFh8aRUQxSf_+1@c-XGP*4nsdK6Rz-19`l$rZ$7pZ(?6O6Mrw? zt!9i7_pba2;4<#l)OLn*s&b#Lji(>|6YvM;koPX<#J#>Yu5z`jc7!`cBhtz9?ft>l z2O;c_eWQ=r2L+oJEbbCqyswY%y)aB z`&rs9J15{RauLh#qDQ;P`k(HIq@~m1PUx&%zip8<(Ck2;l;hl$Uv*o^ht zjW`tYgOpdF%ywRU^0VdjC+G3Ez3bw`ygy9c!_+%WJ=V2K-xhz@H^;bRuRHVe8(pJZ zCBW9wgBLh;`L88UJzwX<^BdZ1P8rIRV;4A8`CClz3~tdG(>cbzdONb%T77?zZ&c6r zdFpq0;al`L<%ieN4*kHZlplVGKIy~0Z=^rQW8dHI%(r;~XXj_w`Oh*3p8WZHQpgi- z-iLqSER4-EPw6*sQEk_1*51#7f7gU?HD5Lk7ag&?y*BNccZKq+c}lP}xTO4T52Zvf}_kdFlGG_Tt{EIv1kCP!DK2n^!W{TGfd0N4|;9c{U zu0S+iG{f(|Rr)I6ckTjlM<|MV{x1!Hsu#~kCKL$|p(#~scU`#qrhV4kx)y>gg^a!Sv+oPkbq6NWhB ztgqQNa?UbjckGu=vX8Zu@8{L|SA)3BZR~M}v&P9fOTdH2;L%AIVXvu_)Q7_TK*%FS3F_Bi$wC`c{_CO3jFD&taN49&+%*F4`|z8S-Uj5 zxYo<|)-GcoQbVh3p8fO?v^%@9b_MmIk+tpA>7aaoGro~B?gTcQ8S}ZiBf$EYKb$|2 znemv7-9tv~YNV~k7VhKDiWfLP^u4h5Qcv_iG(!Cs<1@_*oHi<0KNH`u>1cjZ>t4Vy zto4Zad)6tTHFxj2wp+T|P`0cp$dxfaJBDVd20wm&RX|N7RPYURjKtGZ^=2Gg&gD1bx(Bf>ioaiT;BM% zCE=->-6S**-Y=w$4VDMV!W&@g4PXUlC*KIqMU;%rMFMH@vU;YAr+pa=Ge8QIQwp^Fy(?iX+R zs&dS%o(^Y?7nVF&fHQtSZTZA-PVOUCmty%%x287EUfaBKf)m*A%(mJVoBk+T*tWBAtV^b4=%Jff@BL z8VD^sRIrnakM+u;C;L_*CkpPAZ@Ki~D#;A8iL~sA26=S$MNasvkB^QG9{7*R*>xZca)kHYO+SO40SnO4%Fzq)-TO=J`?8;KpTdMci!;&6{b};cLnq|^CC~UC zc_k}`Lj1QNS0f*#;4Zr)ZP>Axig~Pcb!e*>O$}}JU)-zl!W*ylYfU0|y}if4B;|)- zI2-Gce~<-}TO-o*&K--3M~vsD_``S+f2eWJy8k1m@rU4pkUvCsUhzZv!Y9W$p|&^e zuiXsqC75#yZ6Dkb7ynn_57!>tWBJ2=_`|gNR{cqML-@jtvejvA#^%Ly!8v%$<^iJp zEy!mb{=>o9)>#!lcy<2eRbl@&=1j2bnUDQ&Y&JagBk;?9m-ymgp6Bx%x6gYG+%o49 zm}1|X^^MKNqS&(8@Ho)-Y?BkuehFT)rFIMB8-|a}!E5f!eiB}jwy9rFo%xjQqRwv0 zN8mFbAZJcE9&-%XE9kzDSRF-it_Hh5=729=IBRY5*b2=2F{gH|=5~;^L5A|+oy12a z19{|{lR8^XIo9AV&OYO{XBGM-+IDsRUvIN?i?)FUFQi+#uS9%*N1;A)$9DqwusUs1 zcn|IB4rtdel|zYj6dkDD4BQeAkl$$Kf^02&{)r9nE@}Cg!b>;k%!TLtG=3TwJ`Wyw zu)tRr@)|VTyx(8Op7_fxg)*yO6Nj`i&@&ksh-G5((C z`|JD_02=%?zD>_>qTG(-47yIytN_R4r}XH`hwYV_z;3h$`^0|E@Q1* z0$jUZ$(r9-oRTy12OQqvm%;ujt|5+1tyz1S+in)RqdNDG)QA>O^{sxei5BD+=|+VI ztv`qlPAvHPK5Jv724&y&E_nTgW|PTx8sbMsiT3~&flZ5}y$gO9;tu%m6^xPb!H?V6 zk?e)6+g8q~y`w0#Jvif>lRND9arE8gTANdO$o_n2@Jr~Pz8Uf?(&3;d4c6}+?-x8X zkJI#9#dFCnsjU`WYTr@0u%|rot?b3fLg<%O$3KfZLT-Q`;ch=(k$-=7%|Z1W_=(+YCdx&(oiiZ^3 z^~{n@{kcOui?5d7N+6$!<|JwN0`ARBAfs8|b7w%l(!hZ$S`EzOgHZN5{F6_v=XL03 zy3o6H!&jxq0a8v55JNtYO7ehI!w*<}fYqO&PxMUbNAwN!VS!*{Xij1m?N&*q!wz`N zoBdx}IE&)1ZGJj$_Q!u?`wYr1YT6!I)0hCp4LB8e(Ya&o1_b}$R3qC;27Ah&<1ogn zZ?=8q%oz0@dqx@mpi?v7Gs~{?oy0EAl6+Ddgfo--j5o&Eo1{Zx9=1N?0;da~!{0BH zey?2R)T`8(saLIfMRl&X^eIm4gT}V~EjnvQ`LQ);;d}a=&pOMtX#M%!Y+}GOZHI-k z^gX|S==xUn9C7E&X_(4UFpWpE`g+cccp~dNfsIRhti1-teC@TxFN}w^B}Qjo7G9%V z_(QNK`b7P9&&(|N$<wkv?4ORFQd(eZ7wJ^TZ?TSgZM}qc!RM)Ez0s-SqAz&mZ_p z{$_UEIpQC|cY{a34Xmf_KM_r7ZGnRk!NJ4q``hU&vUAC29-wdFHhNOIbL`q_{>8K!9Byd^JV!CDfKQl!x3{`7>Hk6* zB#sR$)R(oL9nz0O(y6gdb?FGQ`@EiR_vgUQ=sSGtzrxxyq8A)I$#>XQ@e7GzSBKQ~=J@fH-@S@5&SLgPB_$lEnFLw9Y_Dt_};<9NJ;(IwKldNql z2OaN@a7V#<^J+-z@aNjOH^c+S_@>$QjpHKIc_ph)+VeC_yhk!P6FPh3#i}0cC8orf zJwEfaZJG}yxTh|`*(=!G6yrTeoqo#gy>%+%%*MDA;T6W?Q^ zK6H0p8LoNPTh8q~0PDe=;iLIZem%jQ zS;x2IpQh$}I^TwEvhCohxh_pxdJ_AV&5c1n@)tp-u}I~ zCVFb1htR+D_n?E^*VnUvToubdp6ZKAclIE5bMOv)xbUX-^xz^>jeKqn?&S}g)4?87 z32yQZx4=+9Zw_ZoC-$Ito7KB{vlm@q`OHW~eLf4ok=r^yVc{~o`(@EZ`HAwu zK=0M;sP5#4%%6`%W*!&MXKiz`)onMO;L5I(t2!<|xe@!^x6A7%=a3_fI`nJp3FC8& z%`I87Le(WN>`e8)wj*_Wlh<5cqwT0Z4B(;z&?vvUyKrTXCCO7L#=LG&Zc zGsPTz`Wm3mLE(EhD?a7T7UZ^dN$LqFd!-M(WZ`OCg!ARRDtOFAPw8qngT(o-K8!AA zi_K+(z6_nu8b9#IQa+lcHdi#cZdr>u(P+`@M#kBhs{^Ol%CF9m!VoF&Xs17+P&E z%47Z?Ay*{vA^ITipgZ{QfbWn4E|DywbpVg?|JL;;mR*cL(v_C(jN>~KDK6hsRIc~P zUy&^T!4+=fXYi@%HRIU}O^kh0et~k)H|BXD+|w$-0`TE^vyb*@Pl}$e3vv3EaLt$5 z{FxopSs$)7c=Obn5D&c)I}mHYx|$Jk2HH7Sn+n#xoaf45-I-^nF}IR8gZ`Q|4#9!! zMSknL;SmSA!XI=oc|WoFqLImcC*@-#SSbZounU}g8XPrY`33OCbX%xofMTAZNLSHq zX&`tNI*{;UTdmHVIs8j$?%+56-_D*K@B0>UcTgdx#6D*i z??kWQRh{7`=G4@JZd<%AaSB$?hwOqbbP@7hlw64A^5so#%TEkA=(xD!lkXJs*~V}D z0-X-#qx>iEs?IXrt8cwe@_t45UO5-!N1<=)xx==zX+QRCXuIee_`ccg|IiVy>@(kH z|CjOIQt3=NtGesFQ}rmHDAc9i&D2|6RPSlxxYtO=wK`YEg5IdSX?0)&5g+H1kHNj` zL&uBt=F)MnhRWZ%#mcvm*|ZMWZoFA{5BWW`3BOI73C3`tm9_dC2HYI5n5Z5SJOB$T zR0jO~BHcTS9JN6?@W7o+)t|F6SlF(+Up(Xa*M#5I<!a~Hoft)bgu!9A22z)_fJ2u#yqT7)fksZC* z4x6Xajl%cTSiU03Ub))C7IXl1&$e+tJ-!*DDG;|92Ym%Z;W!ztQT9%YVc;!5{eEfWP`H4Kdl{ z(#61I)JflF<=^!t0ZqVG739{o=OyH0ICC~$p}-R|{%Xb((C$!|=9R3J&BMZ-+uwY` zi){;d!@Xv=Xk_8rn`8=?woHyW^du%L2 ziy!UqPvXOF$KPyyBRK=c9ksb}>Zlj`N<l>I$=9f$Vd-S4Rh=wWaV zv+9mr7~M?WdfWF&@s0O{_U_2@;Lf>Wot@ONemw3;#c|vd>Vb);?jbJp`;7mt=49av zGyZert0y_hi{0C!b;i$nDR;087PUD{o6Ev}ecD_U(&{x$i_FHb%@wD$`JN{WZO#kZ z9H7nSrW!LA)+finKLvJa;t(@skA?NW{d!pc0QD=1)+lY)=vmY6#dfU<`gdMFm5Zo( zppc8GIp+uZu^L03q`Q9-)*W4V(%Qo{|0x{C{LfN8hG72RF3g`iElvn~T1Au;`nHY2Tb1 ztbsG1Z)~odu%FTJn+p1IgE8+u7}i~YoO9%Vb9esnQB`NcKQkG^fKdmX;y6iQ2+Hz6>)SwZO9e#*Ga5uKtcUqMAk~qq$P5aIFVOI>H^wk5&7x(4~BgzTXdc2Ok^o% zVrN{3+sVz0h0Yme_vvb;&je@PYJaokR-Sa3t*7AUnciKaD${r33#hv_W}&yGr!tNb z@={HWgLVzT6*>Nax7#GQmVEf`QgY9KfEA~XJ@N3Tk#}*mi^CMz3^%!LzCTBZiyU7?uj&S~M zMttKB%V8_njOg^c{3T!IM?Da<%p^$=Jkii!LMkfUGy3)C%mL*Yp|8#O{&r zU#nUe*KatlGoi;L@6Pix>G6ntkIi|Kp9we#FG!7&$fK98kGyp078zIjF0nly$iYg- z5;%Sm$(?o~t2rkzd%mV4ng0mif#fj=ew?*-cyCYUPrqNX<&qQgEIhl3J+D6Wo5SJ* zAKLw){mMR@=rY8(%6M}9YkYaWdVV!y6W*=eiC))-e~va<7HpC=6uK4uk$I2U_shjL4bvw0moet* z%#j1pgpS!HdTVVj^>!@LkzAH>3^ggxQxyYe1mLO~LnF{H=GwbaI=@=T-N zuMnEJ>vi6l5a|LQ%QQP=#6{$I(Is={q9=;ucG6g;C_KO^;rrH*l4o!AokIELOV@gY6p$B2!( zM(RPW7h8;W=+x)PSv$0IY_?v`VH5rtb}$itS6FxBIh`G@YNpsHhoaz%R`JVHa-4ZzUfgx5G z0$?aM3cgy+E4%Pxhq8Z=eX)GqRqwH%EYqU8zIj@0KtA1%4Z|KJ^6mTZ2(YsrUA|0U zBXTBI=quGW4l#4GSFZ6tVlRE<`s&bt@6+&B^lVMWYgME#r|W;xpVQyqQ&n?V*VRD}&eYoDcSTR=dXz(4j;$7xhgN-J(o5Cl|fi@}wjfyOEMJ(()_Clb65bHoj zt_j@a8u+{1>0_JFuEc53M*;I&BkOH?GP$>FMXn(iSi>y*Lss2Q#~j{V);$T^X$*N2 zHtrkvt#c-5Ux`dy2Cft45_J{+!4U72Sne%yP3{?PiBVVE8JFlqdW^aaeb7%c_nxtK zfD86gWgWNiJLW3JEAa(Khw+mli;^Y``}jq!wx<#aqg`u_!2TeuN6WgQo8}YM)uX%7bX9Q zZ%uP~W0E<|45hM*r;uw$?0+PRou%N_+0>RQAm4j3F{YE%YHjcGU+#0Sg?onZcaAsk zH{10!Wu270w(mGPk{x4fwb$eC8O8glA0qQJXQ+7F3xv-#F~_yYMw#QHbG08<<|wfP z_+%BnXu%)84wr}Dc5cEhv0>dwa|(I+=+pQXTvf|7kBfZu6;IbrZJ}Fvi_kHui|;BRlQ8& z*k$~d8~Q3%#8)|ER@oPGaNvGD&#WfyUKta7ar(-^4c@YS+VU*(_2uGifU$Wrn3(?K_~m8ihQD=1ODnb(`?NSWOb^8ijvqWPV2J0;&H}BQ}N9A=36o zpK`}WU4IaIiWql5$MkKKk^@TLhH4TYoHFDr%VK-)^1g?e--F=uW60M7oLNad3+B`! z?f4zix)3;96V!9Kpte`)QJ_D0i{xbe`p?DPNNBYh9wAJ26QJf#mK z0PGky*98AMSEY8>@qYZK7QAkWZ&LW`xx6}@)9@p0x)6M}shX+;W5S=kc;!!S6+hVg zGU}i6E~5?_E}QG$Fk2~e%Jl>IP+e71n!Z1Oif0xvKeB(SzDXa#W71#diqrSkILGNP zO6^-UH)+&eKd^yyPx_10HGRLa?nHmv=p)CoIh!F8Wlr#H^`r3p3EibR? z55b@8*NWc}-<`}Y%KGyTXPZU4=$kp!h-}rmeDNA;25H%y$n8(&+cUE63%qjnmGn>F z3FMjhw}o#T^jPUP(s2>-pF=t>oO#F@I_#|gV`Mz@Ey2&`ftPBGFHYwC&;7%(6W}{v z-_Hn5JIJ+9gaPhAIoU_G=}UrwhVh`x%d1E-e8}`saw@3vZVS~ zvX6j_!7m`PVvWEBe&8&>A2=|29~l|8cvkw6c8zkz0CvuXN1V1H*X06};W6gfoN4k5 zEY75pym2{u5O}j!1HVOy1uT%gGUWJdIj`glCFdDR?zZq5`%S~=7ixV#Vw^-55S1@Q%6KYB*Y(`Bxqep}>u<%NE!Z;edl{nA$874xjwNzUb4z)1E^B!2lU zen$l!ygTv;>xOPipYq&wnbF_9Zs+J3@}6zN-<&9s;hS^vzH6wrl5#D>yMbkkeeGpE z7ENCxnZDhK{wd)$RN&}_~adOy>^#c zujP+t?XTn+vC#xpGRByv?GMhgo#3U0z7vcihnoh*L!2LUCjE*nEpcF@J~>H0gB>Y( zW!m4ki9Ij&d01N<-zT&0uqU4MVf+NLKg1p( zIF>k=7V(|g>&S(AEsJ^XTCCge)aMM;@O-W&ojcm=su#TB8&O>W){G|P!$No$-WEEK z@ZNM8wHU^zD6rP&^`;W)!e~Yvz^|gu=aG4EuL{`Q;oRH7INoO7GB(-gF5sO#jE`sV z-$J`F&)sXGnW*@2xF$8#qwpO2k}4qjnb5|G80X73YCjXt*)(ytu44;L?6XSLem%w- z^@@y_IcU8QWkz&7p+{%zgAeA$C-0LnOMBw<(|Om67%MQz>YOO{cW+E3T_K^Z_UGu& zz=p@3UPlZeb$Y~(#|Ng@jV^8b3VjJZ<@p80zoFMr$A*q%*q5iB*iXniA2QQp<7)CM zv72SQ@O4c5gLVw~+>MSe@0Bz@1@RqXGZAc|+~WU;^zoa%M5hq`ukKa*MR$pL{;d@F zN)9D{#|u`;`0U*4_b<_OMy!?ALx3~+=;NxRw%-nXdHJp6Icd+cmOM)vy?27YKJU5r z4r;oxpK(KX4bJ;EpaZO8ZbkXEEoE)kCSy;KFC$}j>i<0dQGSoPtlf3<-(|fzNsk-$ zec1O8$^BT+DjDe;F|5gV)X*kkLDzNjcSt+%iM?5XZ!fhi*Ish>^7vo&r^+>~>*jab zeW&IKUx_>yIWjU&PjD*h7k0X?H5xnr%i_bX$+bU;CS+X|o#sT0UH)@diM)ssKVF?- z%&m5RS_eJ<%PVsI2@FU2goVydhD&2#4sO!^Bt2NhFd`01=3J9fA*-(WP-N-klCFAS zI`P;zkp=j*yu3Rub&_QM`R~s4o%_zgbi`Oh=Kx2oYd++Dz_~yD^!Kkh=G>2d$o&KM zee(#id%Db(y&3WVO5O%18T&u6fTKzd@&B0f{{a8BKP?Y`0l|Ch{La09CH`{Hb&tTG zzHZ~MQ)0a}{hSVeBYgUtBbcM5&YAdKrJp$Cx&-*g&^L#Wm!gOJ`Jbr7Phl+K?C7QV zGqBM{;z(e2>KyO=O+HQMXf%h%+;=SaWTiYWI=IuvHmWq z?*0gV+ot_lbyrKQB{X8p%XRS84u_1@CvD&pTyYr+IH!-ZA368Ro(MQO>6h zOg_Y?Zb;1`XK#~r(j&AaG%d0p*b?KcYamB*@h6Ov_~h!FL|&ustRnuxqkWzkU@iJl zAN1-u?3};K8CIs+UtOzOKK*IdPv#(cbL81la`yhK(Rcs7D({&b9%cU1up=LC(pMK%f_$3|5>YU7W+!PlW#a3{94jk|x9968y;kTL2tKk{f|zt}zKhNg^L zp4Dr?qb0&Cr;MMm4(osU>!RjiC*LtAH+8Oo*158^V%LanY2ibaxyB0r?l%&v&l)Sa zn7MfU)7FF1YenzmJGA^cu@AhhwoQd&6OZ1Qc@_N-zl+eSw&99*Vc#fi{hxQ`EiGyFSYZj zxeMIW+8_|mgDKM7e$JYFux#jYij^W%+(9XNIV3uXSH)6f3~nLm4ql3%{- z#Y}<3Dyx-KEziF+Y*eACR>#Un!n3krr_$?oVyShiew~X=VGY;(!(O1Q-=gbqmK%EZ zoM_kO@X0bA>#<4fKzJX#ocD&rDFP$>Ik#*7PgG(XYgIJk&W~+$NsPDD2SdhZ7dy{~ zjhm5I@_fg6N42c$)A51fn5R8QL$5G~$Vo1)pU6^>35kd)#WCa6Cc2E&3}t1u^E) z0G&3nS67K$Ff)5TIZ@zV_kTY|b7Q{*-+jzQt#evD$<9XG$ere?7HL=CofHJZ6nAE^7a7aC`fG_&UB&?Bxu+ zMEkYH9_mJit0@<14dla( zXJj0}ZA>4!lMOfMPT&^lbKvIv3vdfVz#0$*D{rl{)T+G}`|7SDY6$pbo#5NsJ;~+Y+jiin{NKCD=~cs7kX;RhU!G z@k?w3x?2b`NBpTH_O}a5z{NG$W^}=guGM_jDCJJl#^SRdw|j>F9bA7(snJLfd4A-_ zHJvu0Q?KW@b63))(dtpEb@sX>vcwaiXJm4@(Q!pf>ymq2Y0f9M@HOxoz}ROB(2w*NQ;FkT^GiGF z+rE~z_ic8J+D;!0a!+U(ord~b*+V1y(+%{G7G_4g38;+7BJD#s_sg2)as)dDQD?fQQTnSTwK>7cuv^_1)4& z?#IM`FZcBIfzl@HPo)d({%#zlaq&Q@q2K@AQY)qw-LCD2o>4Cj!`K;@^b=EK#b2v& zQx$^$uPr{*eOd7Vqi$rn-iD-lOV)Z(M9h+BDLp#fV|YjW1noUNqNlHaErTH*SojCII)l zxZX`0>OlCAC(}e;%NU2(Le@pS9*&SHvQ`j3G)dO8+Krwq!uPWFN9x9ePvv_BUn{sz z^|SQA&$*9!7v3&8@jrK6R^Pk6a*Zxc24!?A2+XZEP4QD5o4C84NdhaQ` zuu;cq(-yucIQr3TANY*T%kE0rzL=w3{K5@#ZhcIRxk=w|D_Ae|E_xL8I74~#7&=}5 z)c4#7ot1+>o6fE+wWOW!zsM`&(R0unZ#Zt#U4iC*O^v}-Qf38n+)_^c;K0R_I@{wA(TctlkUC{zQ6%(3qfp#PamJd;JW57d}!v9kC)FhKFEL7z^4&jmbj=Ld`k_~XP{%Z z)k6%#_|i@dlZDxLfnzdVlRYN7Q`bUjFw|t8}3}ke_(Q!B~{zd8<4(9uJocDT+1^w}=%Zd-l zSrq1!ty*T9Qz}}>d3K4c(sC+69gNFLYr4?;k&pW$Unma9-f-h6&gY!?>ix(dH+a~N zJnD4f34PL^z=GP4#tGd~En{px>=}=YO<*u`Oi}Ay)>8H@p?!@@=v!bHQ+Gcrypg`l z;fq@M!UJE_aVEQq^_2g-OJceuA8?xEhb|ZS$k?M?Lyu97LbF1z{CE6sE{p5l=dk%k z`ZtNg+(kdJunxrUm@cIe#2}-y+G+f)0upUs?5%KdOuG=9xiV_sN?wewnP!=yliC zJuCQPq_y~st_jSmH@LlPS8zx7qF{gbgkT@v&#c>3e1OlPSa8*i62HD~S7`%dO3*$b zw8Z~Ten>rO0m>bv51S6^9d`vTZ6~uhrBhs^WClq!J}OF7J z*wYyG*3h2kf`h^b`FYA+?ZN&WT?kF|voz=JCr{qn)*m`yCu9#;uI!<%0(25&A#J_< zuFt!FnEP*Vt?{G#{NcX5XL5Zu<@FiMyPxY*@9PO}MxGH7X%Ftxe!q-51Nz<8-X7cz zT_j@X|M<1^%-|02G+BH_#MjrSSEyK32pEB$spsESS{emE@%=M{Z)-T_`8_S*Ao?A;sQA@fUG1guu1CSbdRe+r_ z0Pp%dPv|GwlijLgggfvZ+!Y`O`Hz0&q(AyBISN0zG>N~$#hTY)Tpo>gJyqHnS)$h# z@h|@AdE!#@;gJ`o*=2dy6WC2$&TQ!KH5J7-XUqCWN|zxwiH9s*1zZzdvrC(4tJ0H$ z&+xwmeCRWKx(bR9aBsD)NjJvTNN$8TC*Q<&JYgpiA2bQS6mVj_h^1L~uv6mb=Z)Y! ziZ8eXf4H23Q$$>=uNz-i_XPYAIp65W*xFod(#iX0l~#Lcf-!E_>wJ%^USw`{ANE3N zX|u>Z>qdKC>B+2P%sXwO|D)@qZ!E>fkKzJ2r9POU8}A7TYeudfoJJotmZN6nFm7FZ{**TOYnrg<_shKd$4=JfGfqVqff2 zzmk|29TQ2P#EiTcE50;W|DnUyd6fZ-qrlxI@IMLmtm`r-_?G>;;y1cy79W9U-|oJ# z_-J=&F*+YPOz@3GEo6re;cxVlG1PM%L*3TWV4vVK$D@7lu+Tv)_}=4k9o+5LJbjuN zDd7!~iPYNc=d)k)BQkL2Mfh53vj?=Uy>`zl@XJ2A2EX+0ef$M@g|kF!vxkvopF03O zA_p36T|N5>ZT8E3=bo2)`b<&bIpMdwdp_xeWUpnFDgp@zuJ+z|m6`1(xV~i|692h3*(nx$N&>{ch(wez#wo@VjXmc}Rs$$WvFu>VY2a z#P3FY=el2rpYiwx?Q{D_@wsI;#DYs#-2IE};YYa7y#wI5Uhr1iqmEfOXx*AU0rdK7 z;iF<;C_4UljhjQjaGKy*=v4bU1eWt`x-@gX4hNP3YwX!^LJzeYmG*JkzK(+Esc=$8 zHha85K6DMc*q>}RyJqCI+`SRsG1|rTc=4s9*NVLmU{2-OPVX{~LdFol=lTY)!G;_> z?ASJ9w;+?;T_Tf2KSdUva<0ZMx_`z}6i*oLLqI$PmbYzvfg}plVHSry- z5*;Pd$A|IY*K}2dc&E#SP5aK5G@LRnA9L`7M^{&Esov|C8mAG~-;>6V?^VXnc*49 zmhCE{ZDwz6h}y`Z7HP{fTaM3-v4(|=<11s~yk|OEGwYH(XYony-Mp*jI(O)@z3Gr; z)P2j}?+PW4&!zVBNoYxU~ggyH9Ko2_J^vKe{ zw5~>J`q0k^f4Wq5M46p=M&>v1J8Ew>>9pT@!i6= z!MDY|PCi|H*7Mnb9@@-j19~Xe)Uxhb0mbz=pGK~&U)LIZ3R>}|iLjTcP ze|k}1J@8n@yrjkxwx-Hpn{JcZcGNRfVkZh5bM~<4L3;~=t8=>0-lajq)`e8q(S^1O zjqIKBEcRG-AMxOm_omsSD4?bsbg*~xv+p{3%u~l3qSPYHZav=FR4(*!d~P#!82Kb_ z`SYNssOaD9@Gh9Q_khAv$M^oRez_eKXD+eG9xBf8?9-ebGhd2K`!gJN2wYb~Emb z&~y8epsvS}E(`i3htep%i2AxQ@>z%px=R(6UZ|#5Ee))X6a=P4X457!*Kh2(+Hc%@ zwI5q!o1DQCWnG4ri>PNa8M#Eg+&#p&4DA(p!dmoOWXdv;jn_Tln}IB@*S7T9g2#5Z z^-a5O1^!Ip&dgi>=z*ham=_1e2pIVm=76q|ESNPvfPYa z&aUJeI3xrH`S}TgKWla%41HqP1p@*TzQY2G?lNEq9MZEnTPOiukP9;vI(i~r*^Tb3 z<bQ+sD~4zcykuW)T`&3Y{O4MLb|rF6#>%z8h_Mz$dIRCeF4l!t zX$PM$*0Ja>o1Ar*ns&Mm4bSu}+A=P~J*NVgh+pHkf{z>?a(oWV>!r57=zQYy)UoMq z<&tN+#supH=g^+)|7rXaOVuUU#21aMl5+@(EPQbC4!%8RD122kqvV{WBJpkL>+qy; zS18W!z$w=|!f~lP_}O0_sWTGL@Y3v%?*A^4RY4E!@i7LKF`GR{YG5%&eU7!Py&@ay zl*kBsZ0V)J%3ah`r^fkKiA(3~pQmPUZ$?J^Fy~pu$6^)6{JDN~Ug`|HE&2;z+=dUU z*S$L39uynPEA1wh;a`=u|ADN!eu>|BaLL!V?osYg6uYC%~V*ttq1N>=ceguf9k8R6ZeBYYoZ6bwe2tYvOVtn_8Y}VsQvM4_8C8gi-TvAK)u9~xQtlU$viG6!0X)qz)(ZFv z*&?vZTnv2S&A3??uaNneDz0H>vIm`7W5aCS92MexXraFrnZs$?G~KtCHq^YJO+y-< z{fNHG>8pr#ZJnDt6gobR|mD-@kGeV~`KCfIezC&K}y&J&s z@nz3Jw>kN`b5r&i;~#8)e;OIddwu8_8NDYVa_=9|{X)nyS%X&=C#xo72N%F6=nk|E z==;PxYQ84^p6lfo-vjNwKs}Ndn&Pbmv3Toj>Qrp>G>Gi#UYy;+rzd@JAl%Nkal>4H z>+`XS^b%sfS%_2j?`Mo2RZ3io^lkj@w~&2-iu*QYH;B9k7d6K0&-smOb$nTvF-Y8| z)D;ao_e)r3HVCbx9*W7hHvpT%>}x+YGqHSmI-T9Hc;)h&8N=3+1{I$1wsKAUU)b`U z`!(N}euub_wyug)Gc{3&FE=+Vr4EEuVLrGtS)H)uKcZduB)TAELYn@-_W1JcEn|nVm^Yh^ccSYPP zTzV0_#~g+3q7P-!SpzcD%#*X@*xJqcu_Ji~8Uub9uORHxQI!>M&b z`}kSEsAWMwWCL^YwI&`;iVsenHE#eG#Gs`*`{iDFs$0XUBz2b~Kkm}c6t#x#O{S_} zPD)Udw2XbaHN3BfIeNo!V+^{tyIa;xd+gxUC~O+OE_-c^xhQqd0r~c)?twpc zWw#1W@U?A8t*Ml;Ju@?;MjNA=;!=Oeh*curH=Fnle z;l&RUZF;~+TtCow%OkVmb2HN8`0^1@+c~V3&FB?4%V8HnwfE z_ZVt>3uI6jCTd&9sB%1>Z@_=j%No_DjqkQw#Ur~dx6-JTAut{V7z(J zJnC4{Um^Xpze!&+{AS_#1IFPpzwt!n`1wW5_ig6;*76p!?I)GS*f;SxgX?S0YH5A( z+evfQ9G&VK+9uK>J5%znS;105;Hv&;z`rWoheS;vA4iM%(0MY6J5|uD0&^ zw(K!r8%-Q)t$V^Re%4gzr+(}Dpy-nDty>u#Px!@eD7kdR#jG{%XMMYkvyM+(yS?;M zbw!Q3>aFzof%OS>*TmA#tI5V3^}w|kah96Q@pr^3--JJtm^Ie zROZT|mPYnD4OP*SDx=-KD$dxJ86PY2r$m;J6K4Dx9MnX{SBnkt8a0VtLk5?O8!&GM z4+@#Suxh{zE%48u4Gt!QgEC+?`S}5J%CiH;m;ijf9obAh0GA!3BD6|hD%BkpezsB% zRth}8EAM+HmETcGMrJlGIaKZYp0ot3EV&4J&sBFFYVO=X3zhX>mH+++k$e!$5 z$X{Z)BV2T*Ut>@vjnodePvlW8v)X?AHfF-uU38_x?|8;*R6&M@G<-T{H20h3eF~ z-L=3>`6`L+nY?NYzOLBUV%?LJ)C|Vg1^(F!#_q=76%Y60IV_$n|6Tpwg zJMfcjQWj(GU>rrPgI@NUl4disrohcSzL%UsTodw~7*k!(P})S#O-jGH_P2&C#XQ#l z+fIQ^KWBmrPKuN7`26o>?{{j4Iv1MK{%Q7ZeoxI`$=mJ|oIMYIUIsscx0k_>)OpUW z2U@olKkQN!F!mznj#TS)L1Y!SeL#2_yVh&`7FsH1eGc-!060iZ*%w$77TUBaaG`yr zv5!7p9%^a5=fHS*AJ?W?uaYAg#xIgqC9VBO#*6Hg8fmF2;=!x3Z>7ct#;3yg^|mI) zx6b|Nf!6SA1FctY_8Viz4YXc@>{)X?w7v)bU)6xoago1uDROWN>qzw+WbH%fDCnZc zs|H%{o9j-0E+=cTvl=uk-r_e(zb-a!CX7bgFCprH_aY!nOXAFZ2Ia z*ZTR_A8Wm;>X4QjJhyN=w!GJ{{_eSdWD7u zd(YpWWS`|Bd(Sz)l<=kYRkFtf9<_gpIyg=3vxAkgAH-Q64Hftet9fU2g7>l)nrfTS za^2d|t>zuRufuniq5ihgT%xM@?V{$Hmv6m?Z%sJQ(zdJkiAu%R5nlp(+lzvp647x( z=lHkIVP8l47_=WKtaasGQtOJK_%X_joZgYf|BmmcM(DqGhpIW@pL)6_f*&8BPY*ty z8g$m8Dy1gO%f9)v_7!HnNVf((vfnztEOZ(F!y*UeJ!Tzic-ajV+c=wy z-28CYT=bX;!3h3e@jFFi&Bfmop`Xh1Oy)s;8S^MFoq}#OA?N`Q!}EypPOgPz?8H}! zzE_!g=&+*xZ@>6q;6afc`aJBB`-LaqFZ(6IsK872SHM{K9{~rLo6~dtoQubRduUyF zmh~`fG#5O^nRC-b-kJ-pNuEx3V{NT8SI8Nn$Sl@F!z!$ly>8n2j2QIf)_Po#34h{K z(7K$_dqS5pdTCEPW9!tU=IyT`uV^bg&a?XLRSP@cC@qkhMfi`oK1O+j&y6e4eJ)2n zjN#LUOz5l}Z;VBTw4;y2)c91hYamq=8lRdrX`nR*&rh2I-^1_TIq*IF-zoamPyOa( z_`hS1zx9@?fs|*i|GG-}+6P~sy{JX_J{5h)f8F16?QgmEnMEz;^6Lj$e>%f2yxrQp zz<=pB`1dRD`csz-T>Crt`$zEiUikYS_<4nE{k4y9t(|LaTq{7|`n79)F{zv$G?6KDP?~Y+NpViX1kKa%6`$>5H5qP~FUT=ffZ@AiTb_ON3DquDP(=${P z_4gXhPPgBjdk*I*VP~%Zeq+xaFy_#H3i?^YJIwQXbV~Hbx<3r0?xjv?UBa&SIfnL$ zCh--9g#S5@cE6!)y^h)wdVMfgBKP{7Yv^#S14YInpFAVE$S2y%Jy~1ou!kq9Fuqrb zrJBaMd8fz_*{2g)6W_Mfpq0HD*_RPo6ZyeABF3BS&%DI5k3#3K>3Z=svThJ7a6R%Y zLas=S?7K*eiTD**le&lbLHcEV$gM*L@@f}*>bkBw^2&LS)sBB(YKf8;SU%%0G6`8@ zZNzsO2vrzOWs-YNeK+^9bQ!!`8uSQ{rp-WDcocf{q-Wx*#-DDwn<}c;z@Pp2Z+Z`_ z3H|s9IOEk=0ln?rRw1z|mb&-6`CMSikoF=wy#VTg}{-{PZi z{25;HXNVmu@HNZkCB;TV4-2Py@mKU@cYuqc;eNeGRdlVYtcoi2iF@$X7HOU96?>kp zWvMBwh4@RWqAu~jh@E~|d{-imt9ho%0^a<_N2gL>)c%kncrIit<&4G^jFtF6El0+v zaP{KwiTkMq1)}?jZOK@pGS;WGEbT>4eVBJek@5JPWvmx>>UGE`>xB4) z^mWEjF;=e=zE21}e%ZB(@p|RAQHZT_B{W}rR!izm=zIa+3ta2hEmo0rwbbMMR@O&b zgR#r{A->G%;LOK=Y)zhX=-h}NuzfT);Ey5iQPcO_bJ5X&^AuHy-rDEXT?xy0;Wr8?!^6!lfc&Nj*Ui2$y*oEAVptsc+zeG3tvoFqC z=#BI-*Dv#ZnD4c0VfRbk7`6qn-?|asEOb17?*G;_W+wQ(GBsp)eHD@;WE9HY8a{Ps z(hNge$Vp=~*O;$7tMiE5@cCT!o9Z}U+Gz)V!n7?nS8|>G5^%J>eI`Cr{1n(Bm8l2u ze{39-JaCIKpB$UAG_CjDH80El7y7uIg__UH7VACmhh|*sOGc@1`%?Tt%(GenmtVU5 z?c^2PwNidts`pm#x$3-U;qA-Gap)6&$!}dY-4vAYoSd`9dEL%l)?S~^Qxtv_yDPFe zJ7jF0DzOsY$o1K*>{(g8_y($h(+%uvkmGJn31PqOkBdCX**}e|_RNYm^qpnQBW`Cc z?O9VqKb;@jGwZ5w-&y9zufS)tBx#n3AAmJSd;<6bpi{d>2L8jE=er>aQu~X~t;fbv(w08#drsb)-A@!iP8@-W(_{pwN;Zw$%amKoNNRQ2U zWU99H^T(V&PSfI@GR84WPV!x#i*1p3VQ|qCQ?C6sU%2{9E(b3!M;8aS8= z4zN`lo558KTwO_gbQ^8{NAN=I(n!4gzdF{Pw*NuaKdI{?eEPibW8NAldYz6dxb>uc zWQA^6j|~=q7TAwdtE~d1_a}|Hu}b55RT=F)D`K4)41YQ?yE6TWafieXZgjIh%XX5; zzg2CPO7+e4-x{@4^`fC8=~;aKk#l>#3SB)MsA9 zKDA3_%&Ui5i1pq;tapzw4!hZG8gKaEoeOUpFiNk&--8|a*(vBx3$PPkL#MjhZ!Et9 zU8>CA*o?gw!`{1cQOo@HCx)(Cy47zkLC1r!%#UNw5wm43LC0%H$6Jbyw*(z8#_uq{ zKaOq|4*HEN*5J3}eNpoD*-w+$0n^+d^QZ?lQKK+DAn?dq31!agW*o@*Z%$!c_>0yt zo+xYJ^0fozieLN9jSmjwk102flg5@CQ{Fi8$7g!cEjOyzKZGm=Oq&?TLXlsbAKGLl z>XIU}xE??Lbd!z^<9;LKj30lZ;Bzw0<4?!RvsN=}=-5E}m$3hOWKAElFWpK#&Iwt6 z`;V~~mcXx~r=zz|pO8IfE@fZhD^24y4zL}d-JaApuE+MCGhp5ZKE{n3NG(lk9Hc%w zZh$p&gPHgR_=t~BE%>$Hc!%#mncw&s_WDxr_7e6vwtecMUtq5Tvkh*)vGu9}#>zs>#>HlM&L z*Vb%v+BWF6KAoQ=zVlA(N&IN&Xrl8Z1+D_?PqpGFbKsr&iW=X&SglW=NqytR0%w=- z1UbkBkC{bvet2S)$PA+xn7tDaI$S3BFn$I+Cj(1hYo2?)hNW?DV0=D|z~2Vr$@9S* z{=?fGoQwk}x8!gKKEYe+mfHq2-U@0pj?8Xw1CH`xpO2$_{N&)Dv#l!sr|>`yA9yIi z|4<}na`4*+Y}bo@lv@5F__$I(6Od=jyO+u{=$YWCYu~%VFt~R|3{MeL+i61Fe`rHaTmv(dw z@+JcgGU$!{)@OLe!5eE@rxC*kQ8(0*x+glG|7)-d_N8ydjzdS$K1^Dzh|Af z6?$Nek@W=}u8}=!^K;1lTh@#hxtN*@&c~)TZ=`OMy%_vR_aNKhnS35#ES;$*Y6m`r zOfcG$qndj@ik05+E~51E!H|8jhG$yn~ac|z_r-ie>$2K*G*UjG^Y#eYWb2~O~R z|8;WD1&*54yOviS&GC}JDTgcLEBJu##V7QnYd~Zva;*ay*Z@xA!dFIdo!><6aXn!c zK?nH3#jhoD44!OGMS-WtGS-`%JQKNf8r-Z&oeg|NUV?|zE%=rM56DhgkMd=lA@~9h zIa!wP3(_)H)~#=xKah`y+hok=%9!?|op#KhykN=9?(|BZ`K#dxTqPnshcrn#82Plc6mAPd^?|JK2iJ-U3?$5 zK0}Ntv4dTFqZYq`u3^Wl_PU-yA3TI!ctB*I@M(@VL>JVu4gFALo9Ke@a*y$j8jrtu zya5lJ=c2cumuNabPt|WQ|0ij{co^H_ zsS|6Tk<;^Rolxr{lD8nbNKQ929zJ;uG&VbHU>+@qFC<3`#%7xq1jj-P;)fA>5PVx- zQVrJA$V23y;N5t*%x`SI$S?Shm3}({-VbQ}XQU2l&+QuTK^1Ut{Aa;2*R=0Y`pnT$ zj(+~uvhxZe(3Rd};GME}+qGC7VC`JRCx#ArAU%m1{aXWJD~2EI@go(;bX9sQe$(?= zI|D;4$bkl9p7!GurOQ}rM{~W9HPwr6bQ=4L6oxUUVq@SlH9SKt?fuXf{ygp%8FN^N zUDTlH>>n@db874F{OMBsWUSY%KMarm)T^B7=gkgjncs;HdnIee&8~sghTQ|LA7>vy z_6>_<|KMAGbM!dYXk^jkOW3FXDf_XZesuNw^IhLWevWXHMo^E_}ct^LT4XgSk~-k4gLme@Uz$+ z8~%FR<1f&emLCqC6&YvY-~TWg%hR)rOdgG8v>kGQeVYdBabloXIJA_x2)*hXyKTLy zP$4@GfQwb+1qAF^s!>P4eRI{*%xi5k@dKl_!1o7A&LqxP=wju#L*PCl@de;m$@-jL zNj(D2mK7b0?}T{^I@Jnr+zeeHtj#R+Q7Zq~Bp3jo5_tm!T1KDbde(*D}%3 zv~7xRruhNAU|2u}w6Pfc7I$2H+6J1X9Fww{I^|b#d^s;)rrr356^|nR! z=>0m;&z7Amdxq`OJlSKm<=H`P=-*?=;g|$2fq!}m^x;(ja2Pkk1&@g@(qRA1bffoz zTXcaM_%Mp!J}l43xf156+2VIpLQ}EQuRkiZ6wMT{Cs42rdTNfGsoXr*Bz{$XyV9Ge z2}T?WIBhE3s=_5v75>z$>@nUS>7Jw-hvmo;=*7|NE$}aPv#duc(IG5+5E*zH9Yp*Q zsRhWzJfFme=pTubbq`s8PUs#+p6-!C_ei1ZiSBV7zKLt_O{DNmg1=_ z1snexx?seJ-GZJC4FGS=kB*N5d@Rese^?)UOzVRZKeOyKx?ufZp$jJdKhy=|AE^uG z$!2qe4J^E*?clVkF&|q=Of0$}{DdADb!^~z(fw>Y_(@$4tJcC_gbxs0*z#F?d_8|& z2G1RcSn%T#;m0R0;D1bb5?_`Fc^u=pfXH~+1B91Xan?;JlHk4*J2X-^Aa`%Q#E|HH zr0=nhM17*z#I8HmPa4XI@4By?J;@{3ht%FNi)Saz8N@si=N+5))te;7t8XUx;S;}l zy~KX;TV)R)Lr?wc9El5)d)dqp`Clcz=t1hc?B2ZAm+d)Bq`qTa#?=ZsHg->I{&aBWGJ{Uqc{KC$V-->spo030}8I8S7>#tFKh4-8+?MH|=+G=E4Ew6LDOLgK5=F9p{#L z*@L6lv+_skvxDTk28ivdjPAr&*pYoha*O9>U%3E1N?#{$%V+OTx|R{oUuAbSuSZ%=wbD(5?ce|S63W{y7{4`&-BzmxAXo656^rt;&@7Jh5! zgTIdqhPHRbCf>hOa5ES>AiuvUI2#Q0%kM|Cmi*q|McH&>^zOf3a5fm~U{}_p&?HC$k%msoEW$p5xDN*R`R6b#hSk$AM+nach74`1b9LWqUdQ*%R1a z4xBAuOl`P-d6fA{-X6JE*>@zqPxdImSERPr)4)BS9m^|mM8kO%I!{~cz2Fs`$UU#X z+s?CAeHz~I7chEJ;0>G)2|NXs0&BSsocp9b@H!xH27ZV6^b5>rzmI3%0OtMKzNT{E zdYI>l{Z{*h*5vt@SETD{M?Dd>U*Ijc(D42}aGwUeca8qmU=-MI`iEoLjR#b82XT+o z#Ts;v{$n;h`nhb6bIm#&k4;?n`@!h3u546beH1*b`;|Py-f2VjA^lySP4msU0)wUd z^*PkXcY4bYObD(%xGQMP%f4{X!OPo&oaLUy-~ZV|@3i6fBnCJ;)HNa4DB~7b^v_8* zq(;Ax?7uKwU&X#pEZFxOc~;*mOV{^bk#1=H?ej_Q#kjXuuIs+J-p_rm>$>0Ed%C|? zMTt?2$o-d>q?a-73%C{+8sd74{~zPOrQ<;-5rZ^w-6&}*^!D=R^r697hs%H28|)aI z^soO2eU-;1-lys7 z4{q$KOO}jLV~s29*vbR5f~$}V{t~wuD|`4l#!_U$VfOE#mGmrZ5bTbwA$-a6hy%Tl zewL8y&^I?(GLL==?LA@L2l<9oA^N!2mMi>rne%8b?@nBuly}R1OuE*UDWR>5;bP(r zx@Qp&Nls_?BDKcG19_^PH?QNj7CEu^$RVBIL`-Ky;dJ);Dz$D$U26OPcsmY%krRi% zh}bQ?SM9VPGot;N@s-wY*9KGewTTHg%lNM2dpWwg%hh8>(QnzyAclLtxdI(N>Wi3V z!16}+y_ipG^ATX_PRbk@e?w}cPk2$z_VwymQ1bFq)TSX`uTkWd)ZB|$_#NcBmWTiJ zF^L6|YxA=IG)8zEct>;{2FYDyTp~khPwd6+3%EC(a{!}JYQpi`C%iBF_zrJNE%Qon z)iB+iJ;oYVWa2vpK8_!`u<}!7_z)+kM%u;Yz7dVt_a%NRS}5;nve!9Rf;Cfez1NE! z5u3PnQ2hF`mg(3h*1BBmq{KZ5jds1rdNPW$v_DP#|0QkpyVtfgyserpdV9Ebv#wQD z(_OASwDXL(7iA5uPq|}?Sa2QZ8+{PF7#+YEO@1)-v?TU7y1~9itgK7NhBL!BD%HN{ujwUo*4pn)Ug%&+MIb#GW9q)hZ}*Z;7?-r z9C+96{4o6ec>W3e{dmqtHeSxVpUFyzsMvfE;26;OxNto!Ja&Otw#WVWU1GQ zBTvYgsmAkmJQ1-HZ<7xwv6JNnad%=Ne8)nLu#wU zvq{X4)QA-tPF?Y{Bz4=VvwZvqsfQ0ktJ!_>oWuhPol!p`gnuorpQSzPU_|n<&N*(9 z^#^z@WbJ8^npBKGuqw(mbQi8K<9b4_@7)z#E%iRKlbGAi*_A>@Jd z+3fVWif5Zg^eOxItGV7H*GKdhhR!4KR(%(7YQ!yhy6IcTI-z%R%_no_EPGevx8#fw z$5z{uEtlH&z||vpv&7J%OX&EwfZ!y$lcJ_Q)CI}txLBzbnGxR2uTh}moSd_fwJe9o09qk{B9zTs)z45AFYEJ)D0m2KPq(x z1RlFD*YOf%^xN3YemnX=y#Lov3EvQ{}Or0n>bM0vma zf61Cy#xv2qo4>IA_bc7hW1((=w^^}2KOuWhLZJgikY^XppYq-iFsvb;Yl}4sdw6m% zhhH6gFsLHHT?bLKS zA=o4J4v35H(E8S^Y6G#*4amz*_+z29lNwh-zZ=ytXw)S%Nq)#2+h^pe;eI{$V(_3_ z>)IL4YL@mV+Lk(PebUzHD=zdNd6ardy1x(Jx7(<p5SnKCf*v z>o9(0gY&3_c7>J=;>V2AG9Ak=HC2f-VLuc3jy)!F-FTncr#acah_$rsNOV}X*Ewsm zTn9JvvOm1zglzxetsgDhpIys+)_UKE%Jvj-J*g=&zCB49n;H6%UVHM_8ySzRbHigg zMPGR7Hz&sQ(!q}&)As-POY03bT|(BJb=1BPI>*jyUN=E4nB;O&`jNg&m2FZW8ZYh4p+4vpn7PV0GD5>)v@WmPn&Q0d$L+IRx`)2qn ze~El~j+}?BnsJ(TeIe6=vVVFan#%kphJCRO&uqXNye*T6UAQzZ7-AlkOQmes|8unC9+_opU)tU zJr|FPzhgLm4E?E+{lFu{qb{`C>8k))^N4CTI*6HmR7w57XLY=B&-vTYU5=#P>^V|# z5!+Pi)Oh(l#J=_su~qSB9@#t%}laH?eXTeNyLh zr0&)6|33D?j~Mf)Rd;1DqvOi4r;$Mt19n8#m99BKsf`@2i|X^?`iMz7lD>tuV}n~R zUIT9syMrEmB$s2*bw+S&?arWuzI?2GlRDDAbKD`$El$cD7-!O|qlR29^_j^fVf?EN zcc`LqOfJTjJ(18wGQI%w655jbtS-S3V?UB!j*dw_Na`N)E;eSj$k?fy(xvIOHz+k! zoE$%0+eGy6BPC+rhRJiG4wTV0SMppWKf=#`jPsnFE2c`M55cRuT( zPunO<=lWw4TW`|%SQ4zPreFUGenxxGJA}Te-$UO%emni1 z_oB?lDh$T#@tohm+$xP9UYfM7fZy%~S1*ybwuA#vdtC=E{-Vxj^QA`zBWB@jy~i#1 zNskFez=80l)K*rEQ}U3Gq~`@a?N6eY-*vSg*sm5_*7(iUU$^UF9jTDqaGq&NpFy3g zE8*3;I)A!MmCT<)evcWeFlWNwl4C&rOI2BRNOA{isXthCWi~5zkcR&*d<9(RzgPIb z1R9ZkEVr(wgI_Is=$rM-qn7cwgAsvMrTFGht{Hv@MzS_U_ z400pw9KdpNSUlD!Cx3!`aOUZuW_b3SQp_rf&|4f23S!FWszv2Q;o$=-)*S|5Vy_ zq+A=S6*h86Dd83CM(Ff>as;kF$EhWSu1ijbo#%E!#5z6aWa^=-zi!UB z+W+JV${BF@H+QPR8Hbfi<|uZvRmeMEK-WEp{Y`$^ zyzGyurLB1+(A5f`)H1F*-dn5vVU_Im-o|e(s~rytNWxMn|C$v z)^ufD4sVaLYyX&IW+$swl0Vi1?+9Jh=-N1e)LJ{AO73gA0=D2GEU`M~mDuTXwOkO| zI*=l(1K(kQYbC&XwWe*GjyCE!wk*HEjcP_t~`8UH$viEN2d2doidp)olwZFo+{HG4S&fa$d zUuXAOF9J8^mW6#zoL5*vFF4l!NW}<3*Bjp zOZYc|zcl>#6zU{6xTT%wV;T=qqd?%+%`>$@9H)75x*D#*Jp<`9eM*{_M}$J z7=#wv=bUFjhlaHn8o1@B5*O7Zwae#aU%o)EIlX611Mf}DGdW?8#_4MMY%;cd%b&i$ zkrT^VYYVBZ2Y(4a=(-5KtV^TWi*_+)_Mhc>kx%9_VlNM4hyVNGLhD{#tIZHPVL#ks z6q3_)A$fy8AeKe^%x6^UoEY&POJ0n`E=W$%hvxr`#SgcZ&$J~;v#u^_u1&;^xxV~d zr7ggd+?u8bn18YznCthJ^4^&z-mCMYcy}%r=cGIw#vmZT)r)$!o7c>Gl#w2H5C|xI?HA2?&s*tki$IG|WgPsPirM9xK z1-VAdb)08vmtZAjEGN?`8m&rPdvX_)0W6f_G)Mxk%l zR>l^v7TWXx4XzP>;@c`|V*J3S--5&&b^H) zEPGQpmcIMq~!{)?cyfjl1{N-h<7vSRIMd>K zACJm=a(&A+r|&O~=)1hV8ku?E9g#QFoW6Zr^ElT6@?9O$@GO$|i5>^v9cgbPzfi`v z(On{PRn~FCbI$DU(9NzSUce1E+0oU@14;ismZPw>#T zJlI8Btv9sY9PE_&q+S9Zuc`mb-22BzSzU?$_n8bZXw(r$JA@<*Fk=K(^KWg&3a zK|VS?zU@<`PWtoMr=O3=9a6j#<{k2}Zy%%Ek+{~ls;o^ucBy3$o1Fu%5B1z@HW4F{ zmeVad`->6avGqV`uR+Njo4^-`7Tnyq!+(d)JkhCYH+7rsyz;EWH&qR7*O{|}^>Pm{ z?+NdBo)KR)n?9@gzR=~9{1$RXY<`CvKAaIpZ{Vz0&WP_4Tx!`7ihhn*#wvZ5w0yXa zo!ZtIHfN(Zr1}_sHr?riZ|UQ6^if0~zn&0@D*E_G`rvHF=_6NQi(aYw24&NRP zGk67G^}%&=uDbPXo)&;K``L4@{Ocj~zV*X9~<;-|D`q59wfmyEQEOeiZj;ZxYcxA-AI#ev@ zSJ7&lA9LPZFK18DMb7^w&g*5r+>1U&o?vpch2XW7cdz80pNDLHFg_K3(Hga56*s3^uosAe)#FT6|%lE>?f6xk8A|55%UYf`x(}Ea!!)6}^PBu1 z=g4~=*}vwuYF#)I{q`DPYx4sUeEd^-$4ksrW9%D;fYCK1eSkB&j|gvk$H*Cs?o@WYqwC0A9k;i(aUn9u{DPK0sXq5G{)otB$w+ zEjs90qfpZm=a{Um1<@N4=yG>!c^>^zW4-uNw|)-)T>Pp{;xeS&R%wHn48eu=hfT$I zb|*AG%-<%?6CB9c1qZ3|>+wqb#RTxccw-Z6Jm~mO@Q^I|IHP)to%YMEw)}eokJ*83dM8kWh={1Ay zZtt$I+ zJM9$ezV8ZX+LwB??G+fX85z)VBXcJE+DPtL=v~h2Z5tu$EjbwLD-l~juJj2E!?u7F zoWQgsK85kz8HNwOKVl|8!w%c@m?@dfPn zjmJeVM2<5bMiJ!!%5&RyahFe@*m{lC*dw`{206IH=oCGx0v^lz9=<*BVDT?@n*(}Z z;4ydMOGF*?5Xmd;;amGmN0%DG?Sl5a=A55ME>|rFo!_Hjt)re_ z%E}f2FLm^=}`EU^#y*)wh(w&!iKt^il~GPU0zzE<9= z+HY6hwjYt}{cROsUq;R&aJNwF8sfK)uJO=4Ru$u}{*)CB{zUe=9`Nlp+q8W5wWD{$ z-cY+mzh`V7{r}#rA^4pSo1b6ukDCuWd4Ha&uaEP-Ik->Hlesrkf62Ytwvc_veM;=@ z-bLuW!1V7<<&@TTc*SR?Il86*>bO{v>j{RS062Z+P7*c zx)gJz=c$_itd;l@?E27n?0#$zy~lzw7q!WL!~TAJo&CN337He(dC1L2KiEShKW%OD zIp_S-*sIIi$TQjxEl7T%R``Bx`g*j8QKOXT8SA{S>$F773A`Foh(CYe*=r_7~a^Vn@~chn}|ehGel zpo005vy%7?Qj`UvW?Pfd;7~`@E{{L(^E>hl9>t zigL~uPu*L#*v<_l`DO5x`bcO3J-vuAJNKW+bIo6b-+F_T%UMlr@;_e^y7_xc;Ui|} zBRtM;py#jQH?ZO55x;>AyH4#laPQlkbC$+V;Wt2eD$ex)zg2t(=lqj6=a>AZoby{d z(&Am@Y=0~I{Ppkv@hf}-8X8XwW}m*}#1Q{iIg2pwMW4KV&w1v*;y;WZf#gO_NIOsS zP2JXwufAg5g>JTym?g<^_^kK>a6gdSe_reUcV3AVlDjng;w!C%#uJyzceXg{sFyK`~j{Q1Y0<{Q**E z|0!R963&*)jl?f*fuE2!@h|2JK)yrh+>Vnaza785!@dCI!z=xBeF5+TfUXnFLtSuy zy;MJQ#921y@te(+=(YG!3B8B&BDp6&x4+hx`P}}VYs9u<`-Kt<&?m~%{*8UkjX#F3K_(Ao*1FXaT;pK~Lzo5HYQ+`3K#!!B0AG82IXtHPut1-)msPHr>zutzURQR{zQ0q z|I|Kl-+FNbrf>b|)G&3w2_Mrw`6u(i<}RtOOPIH+zA=@W2a0dVG4=}h4?DTJ8l#gq z8_$RDeNyg=w_-;uLsvNyK6!@bliAUhYa?yUOZ1-^+XSAU&2!$r^k#BK__2{?&5FdD zbxx!D=yH6TSd*OjHHi&H^54a#qT6?}Z$Ixj$t|%2St&6Cz2-Z*oh9ZsTF&GD654Fy zyV?BLuSi~jM)QDmUThZcWvw80z|VcLE$~S4>6`noHPCH$&#P*U)pSaH9oKv3oD|7E7=hUs_ocbDZ;9dA$EyMTf zMsiM_OT7=_yNAic@(g@(J$b~k`TjNh@(K9mYQAsf`)c^+L~^fuOzxE<RG~d)Yr_i@JJ0Z50bKlZ)9N#JG z4#)PU`A$Wx#lmB=u`%tATFeo9Yiy0=pT#cG%v~;DUh#^_x15=v6D)|`MLhj?u6jl0 zjybAhzU!h1a;P*D$K8sJfqj_yFXRD{cUFMQ5B!p=DyZ9S!fy(^^S?6MLOYU=#S4y! zu@+yO*qPwH>4ZEvjpk3VK}cSR;XEwN7qPeLIUmd{=8>EaDLIuckD?Q>%@CVwKKeJv z!yJNX}%9!hqS#! z=41r_HG+FR2ZDR%KMQGi1V$LbnMObjJbFZZ1KDCC@*9EaQ z!|Q^$p=c4dwK%Z~>r|!a--1*0>JWAta%89hor49PA{x*%KI|(O&im*6)-lH)ki8tT zMDEga`~m0HWY#Obsq>`bOFtyy;{TV;9b7&>UOs+&{QP|DJN5W3Ou@x|--ua3m7p*7$A1ERT?<9; z(Z2pCgO9bJ5k7RGzdn3-?X=-j+fItVuN@B`dl+LFhrTozvBjn1aWoFeAFuVX;ID0c zOmLXe$I3{|9<%CY&TB;f!e?|y?qp*BG)-(W*k_7FXX8I^Gs*p0XS-hOYz?AQ@=l$j zyVV3wPad_Hf33UCWWON(Uf9Sa4|oXOjkv~U+QipO<|X+8GBS(yOJxrt_bUmF!h475 zGPN)JZ~Ltizcs8Mo#3B;-xVXe$bDs2n!cv*B0MghZ{=LAi<~N+FJJo+xk`O)%aj8Se>kKirM0^QT6SkJ;l+M|{zw4Ob15!TuIsVC_?f zFYrp0#W}C+^Ywm^-+}gaRl|Q`CeUfFe=8Du`VjYW915|18Y&j2`LyRzhrH3X$$QJ> zUTgNp__W`9F|jix__ze6Y#0|j<9-3`Vx6-oE5$Av(t26msMtpS$I0znfnKlApx3H8 z@vn=bCqV;B&UM(Q3!aMj@5Ucr@FeH!9_P25uZ!=E;H+2fpMq8-NA|PiM<=Ed|FaYy zh>G8GU00BN>cQ>Yv;2BaDR$rz?7G~k(5d%7@BzQT6OVq%ni~jQHn*T;y4V{`eU}2U zJx`+t;IAzAD&Sl1Vf`0%&s5X+oz2J1$IJf!pIknEK0ZE$)^#~S;Hi}T$S~iu;jw~i zvEOXxj)&LN?|ArzzW)G6Yr09%VKfsRuKMl>9j@AVYC61q=U;#hg}>Q!*sDh9ko5{p zrsz<7!2Sd}oa4?+hqu4z$RoWjGSeYGOweJp06Gk*EKPUVYJ|=b&?EC})8q9g(&EYK zaQ2bRba;D}BY&*_AL;OT`h(t%qd(`~7r9G8$MLWyXK$tNZP2#85gKf28Q|Yqk##&>Fm{=iq`bhFp=@F6dP3*mB16C(~&686z~> zP0svN@yhnRzXgrz`@i~B&mZTNpXqwNISH>Eq0!Owxhlmk|1A3a95I-g z_+;C<|8evQJswA&e;R)bGxs&ICGf{4;g3IuKmPnr=Z|YM@yCDZ9?@C;<@Qt4p0(~z zqCM-Ba$0=fZ2oBLGq#*Qkw5lJoW`l;bj|+Ev}b+Sp*`QpX^%ZXnw-`=5?c=X)bTvB zRqI$M$m^5y$eKNwY0$FoiNJsHug4?z{V`d6N*=j`yJpg5wAd|$M~dx|7^g(^Q?nw% zE2Edy>T_pXW{(}zyz(zflXs=Xf8O=}scEwHj6X_~=rM9ul!|>5c^RFZ^=;;yeeJao zIWxD%0$s9?boA_8IiD3hTg&b7!@k>vDY|sdwQU{pPOYaCh9lE*tFG)AwNQ?jf#!aW@K`T~j9`v`No8A=v z8QH&Lb2)DRdNO{q;(kXidQV0-W$YD%f9X2`;W@|g8TJj`vTw-1XLx>!{p-ni%?gMA z{g04|az^8MQtn&hJSJr?`Y+1F-O$5dSWoMCXM~S+ynbqW{MyHw9#3UY$#Z04C-RNh zVl5M~osE)-wyySHm5H>C9pfZ2v7#=sO#Ir1j!f)~17jRJ&s>E}bRiR)I8(yLBDR*; z)0_)o2NpU7=HujHcWc@nHv_GnTqah8GRwrTIrd-o;lDa>!_LypxP^ZHdNQ$X?FcQk zb)TA+mOt`GdE4={WXnWoDNQE+sXG6L6L_0VLuoScWOTE9yG=J)^_p(PHkYCs=tbxT zy(vxSS1!?|(3=YXGWyiXXlJ>O!^DQV^>0o)e-*iCEgYd8YwoFO=c`}&8`4gO{bFd8 zTs#@=d^PUKMe?dUdiY6bN95zMZ8u#9|1ZnNlhMsr-m_u)pDP=GxHGx$wRN^#_ciX% z7Q3447bRD!+<7j(FYFup2grvp6j0>p4Bevh-Og0Y_`Oteehs=VY)XC$IYHb+GJZsC zX5M66|My5;sWZU&&(8JJrzPXfqFZ|hIRB9Qx_GCFcBbe&xieKWzt0`jra#%I+tj&l zqf{VQJee{t7g~N7kaFBkF_|YF` zeO2xfA3CF{=%{sL@euiVkM=MACmH9^#h#)eBkP}r^u6uP#iC=R^84v?De)ERJzwXv z();e$KCAIpwS)7sSvil3uV4Jr@Uo48ddp>4LGB@}=;e&y$n&-?*n%a(fW>kZS& z&ufxBE&D7VXE54Fk#h`19sFAIQn^ot{TKDSeR=iPj=ToS!%|nj--rMCj=VWw#a%Ks<# z)#H2ZHmi$UbgcNs^IFQLUa(R2c;A)Syqcdz5<4dC3ARomUvOS!!$xm;cyjp@z$X4( zc3ko{o%@oUn>@>K{v~&PSI|eS10Ny}F%)vgr{oO#x}7gfXcPUUzT!u;6T)viKY3Vi zY;6}GdG-{<;?*V(-VodMyNEO15V1oZc%BO8L+=l8*WH2%_-5n(JwxXw7%;EdQ*Y(u z)iDk?aB^pHKIbW%ug>RL3dT{kKhw@Dvq9F3tfTVtC+(H_7h6oi$uqNh%FzMymPwJe z#W{~l{8M~!UdWo2S6Ti=qwbQs@N=840u9wgrNMJt2cuKNN6f46u`^V7?qz2kD{o8g zgWjEd%Svn${Z@O;Hu=BiwqKfa#5#9UcKZ`KTiaLR(|^k(4|xZh+UHJ! z#;}Xrj9ufl!TMNecYXW0le}#oPV$8(?sz$YzeVf<;u1IfIug6%7m?V~*CMewKaI3L z_?<}bG0uC7o{y|DRPgRMB|dS(%QhZ;`>dC926P?H?OLx`1)l%+bxzr{))SNVRFF$S z?)-%Iizf6d8?OYb8-Lhvje92hu>-PxX(M5hBcb6}KRdQ+xl)gn z62}TYgr-~Xc#yFUoe@^&?3MrNe8o+`liId&I>#}Ga7ISZak9LmHMAhKM=f5jc=%~DK|KAM3veTve?- zdo{8_&FlA;2dlFNqXkOe?<;52e{Z=1N}UZQxHs9~V-O3Zwp3^DK_#u@x5e*g?J||% z|9(Jdw*MOk5m}v>{HU91V@yaX`M6%-c`m=DEoS{}Q>n2pDK(C=ahqv_;b&FSUMD{! zmRkW{pDxXSab6#1;>eV^Xf#Vh%6BqV$bs@dxpo;YwW8amQdqvJG^C0@`#MvZtuwL zR!(vV8PsCUhadd>cak4xd20TxHA!MJ9%cT|XdZ5F+aLUzE`>hyTs<16JS?;utWsud z4Zg{}XN1hz=S1k&a^@VqbVv~krI@QjBIn8i(1)dUooVs%;okwN2aO$)7`@OAWJ3-y z4$QTt|2L9{HBOEtkJKiAa<+}bGlOL_q5C)RamYu{f(BFc0Rk@rs$g^Nua!B%{nKi@?-{3kx4z8il+HCWZ)0HuIF}z}*hI9E`m$zK* zn~>aQl_7HTRv9`cuH>lQwf+L~7aNs>h7sI(hwBh|uG~YaxoAj9p4+VHM=i;7YlO%R zrpQ}fV=837TPb+fX7P11XXp50cLqgfxuyTAzSD<7KS&@i1Eq++V9C=0m5&cQyaC^G`^v0Nx^^$!+*7LCbB=|&s z0+-L4Rp1YL6CN*XU|4UOn@665k1JDfRc%Wy({fa31X{D#%SRLCU44eLmU}xwcHS|~ z@6mza_obcJ!ka|~Ekz$w%Wj959ol)xbOB3&^69z67s*-=EKdW=Tfjn|lG@~d zydPHMx7-{erjR&0p?_z+Neo^K|Cg5)pf9f69je+sK2h;BvAijsx+A$?)*n3e06g^| zZEYN(kJASATC-SF`N=~gJav5CaeejcH6wA&c3;{LQ1?}+`|=F)@BP9H()uck4W?wv zX~O@x6L552o_)~Ew3WBlaz7 zplbVvFNqE#dUdcmyX!<9MsYsr-N>gS^{!n$#*dz}9KD8monkwYQ}OjR5COn`c`4X@xhLAhP$@Lu8LQ$o}^ z&G6ap%lbL|tn|VAhoj9`e#M%fJYuRVTcmHfM_%rEEQ7z8)mIWbAo`y0es8(t&QA&SLX#KGvM>)_{QSyDnsW_hsW2!CBaPtWcZcM;BV+32 zj9SZ>m0HF$%)q`O?IV90|HoLcYn{<3`RtEALZ19PF9-r-;n48i4hFub#*(x? zx&+^X8~QpDy-4G3NN`tnso(`Xfj_~O#82q^>cJm)8W7wBnTMU7#d}THg5r_;Bgmg< z7|WRJ;vjo#@UcG(m;x&@c{jh8438K7J_THx<5P2)!pR4RZQOitQ1B)7`F}*iBQm=B zVPC?P*HfGP;029Ofzx?z@jO9alx<1%BlneXc9Jb)WbD#5`s)XY)IOnVn?cXga@rvg@U_EnKRD?gZde=fqBZ`V;B~=>yW(23C^i&lkXo)(NNX4 z_xDM^8a~755_$lJPJwf9`~_-oiqX02;R{NJrl_K!DOq0)PoDOohRFpDOi|O1_It>e zZxAzQthVv<{_yxiy>3g>68oeIy-$39x%_7x4GFCzm;+#GO2L8-E4XCM9_x{Bp%>=% zi0~tF8Wr=L_H0_$^EUp5h*1FwQ>)&_l{7u_fM+?|P zx@w90Aohd3WUMV*e`#(qIrr1FeZ%hhiY#PV|Dl)4pCM<@+t9@Tdz?3v(fZ6|k(m1# zos+5kN#xGti>`|G9#X5eqC@s2_thp3^~b-SJQRdxoYpCpf1KTjUE zo=hGDH~#MV*dKE6FDl0-@d?EHb7G3Vo;;j*GIZ(xauu@(1 z>n3&kWOF!HzF5b~3%=v!$vu}3%qjtfy%kTgSIJ54u2_@Y2aaE=$iYv3esZ6w=Jv$`$Y;)G{R?*>w=cjnP*toHElc&WP)OyxB<5}+b*~OeU#u=x6#+a>5 z5R~X(uk$&=eCP7{e`MYK=q4L>a*9+L+LmVBOP&ACXE&eUQ11*r1-fpPz2`NWEA;;I zJ=TBnpzJ-Mll{;Tb4+~2*Qq~WXhYM>VN>6$#C;iG$9|ThywGMgG_0UscXtjv?-OYE z6HTk=ghwN^BXqY1THG)6B<;}8Ug+zf&dK))X9C2%Q4cvv3?*|dIm4(w6s4}vi^LP@ z`>I^rS0(wqSgVrXOXv0i58&R5FVJq_af2(`htJR9KXA!2S%27N#2#?~fAo*2vz+~S zm*`r26Kk3k32i%!9Q`o2Y>MiTXQD^*%tE#fi0*3dGk?cDPkNte23gy+$=?-9efFKb zw%&bgYi;tkd)R|4=NWs`B6R3u8+cY4oZ%fiU2L(U*Ghi5u$u6`LnkfZ#w}x!{hsMMT-*@i&I@FzIcdzJ$kRjC*OlDw7GWJ& zdyw6)u7k!WZn_4azh&BfvqKGPJ1_0(Gr)eaDNX3s_95)(R<4pfg{QN(mOG&ecA3Vs zUA;zbunE0q9d~r2_zk+w4j=7mED|_gU8q`)KBA^$7l>d-HeZc%&mC)!Ia{)8n~|&6 zPOdRc-rGqmAZzEsU5m~RbFWNf=Q?-?ch9|ArL3b}t`B%GGNky9t7c%AnEHT>#cY~% z{CI4mn2S6wat7oDURNyon$G)K0nP*m6?+YA+yA;Sw&*qSchqC&>`3Q!mGc3y1M6IT zoPEfCqV=7pBCXFort|VKmSAl%D;jj-k4F2G$T^Spu{0;?IhXks-^%s}4Ig{QU@)3I z5FYbUcl$ze%5fefcn*(w>O=AmwrHIXn8AyxsCEr8#%$;JKCyp;C%NaS61`)ZUhjQI zfEd7_<whov!bW$e$fM1{3?8ENnOJyvSt+sNF zTx)?re2l86&Znxj>%8z;6$8k?Tq8)G7MXW}XRzR`lA(|%5zhJkc-~)8WvK@Epj+pc z{2cQ@pTX_O4aQs+5c|c@BTl_(tiMXZ7cc~*UV45O2Nn-~{+fAekuxhSa&&D|eB_d9}$|0ekqC_zYz={OYV@)&^G~tUl$~yU2I> z0Bax@S`4WGxD%Q$k-3ujV19gZ*GFu&Z5IYE@h27>>YNFq@h5a14Rh`W|Es)Hoo{ul z*oF?bDaHGKC^155>p*;Y$w{hZzO$lK7B-NBdK#~X(SWqu8->@TA~Q;BhlA50ML+JayXjJgmi(R2y1)jk6M&03 zNrPk5-ANiR209_IXqf|kw9MJ6WsW62-xcgvt;OU3Bgb&`?`k!_Gyj0xng2z2(Su7J zc~a`ostY=CXm!cw*^lO0QROB#(&XUA*@cpa9{Ayj$BsJi4(T-!S0SD`@{4ssz1ZJ9 zABp|rYY~0V47tsOcf`g#L!aNa?P+alpnVTI%0lpAfFITeXMBaktCkSUT8dqfeEw&u zEwl9(t+*M0CZ8zBOkEtn}I#y_+Q|5ymilpq)J4zq+*u-EuN*PcHL(uBUA3=Qa!7fWwO& zyk-+04}bXHJ+d~WpLW_z^`r01`nY0+J_kpykaO^;f0mwmXfS~t&lK8>-L7_5KyzBo zNgm&g=n~9d*nQoPoPHX?S5RmTo|i3j2X1Qm4OMPt?F+`*IY;5V(46>zFV?O^52`d< z{q<%(XW)MLF?%t=W$c+l^>VKr_QoEEUbX*aI&S2y$;$_Rm|Xk@HXHOM@)?HAHr5V2 z!;zc)?0Xl$FFY0NRHeWgFJSCTxd&wI;%<0Wq3A1uC-Tq*!dZQv*SZRO<+SyEI%`Jf zL9DDE;N1TZHcJ9~Lj#(}NKPj`XTXxerNH9!zXkZO1K&bpp321`m0m}$d2s5~O?0w` zg`dd%Jt5Aug%3~`g0EKw)#*y$+ycJBS!*{27wh{ue2l9`d@RE51y^u?Kv2VvPluKb z6CeI}!5#Q4k@3h}I6P|t?dSHdx9^!_|KNtURCwaUbC1Jy8gBrHg{E~r_d^oz!I?m? z4cq*fEOg9dkaKt(O3oLUJ)C(|a>q@flu2FA6auwL!>#LpmlRLecVXkdk{UbjTG9vb zg|N}edK12}9DB85o;)c&5q4jDogU*h^aAKm;7x4TV>BJQI}^GK=raV$g6owb^Om@F zxL$)r{ooj221eqG(cQI75!-Me)tAsp>`QV_f|A%{nHSL&{1)x#bAN0Rm9CHypB3iU zrp-|@M$a$zC5k@bjB`tP%$l1x7ck5vlOoX7G_l)=&4#rg?dJ-u$lPg~a`4aI$uG}^ z9@3wue2~SDMf(LIGfZ%5eo~?Pi%y)S{ey&;qx-x}8+zTFH^AFPM}>b1J<2#^qA%f# z@f2-w2Dn9NSo<7p8);M8amLY4d$$j_$5`~eoTJ(kdCxgO;yBv*SK1r=tk6%1IW|l7 zA)Fcip+ox9vPZ@&@Et%e80l{da+&j~JkH`;;e3|ifc+AG?1JRYX&LMab z90^@Kl}5kPK6|M_@u87^USqG7lKYivRta~p?=~ZoBG%{F1G8smoSo)x@Sc?ujA~oU&)=;onjY`SrdHld3?ZB(V#19Pc&zio|EK2 zGxsr{ckazX*KJ1O&29Kww5dwocUQd5Il&AymNxNc2o zrBf{xbn%&O$$Fk9@1YM_yf=pT$5J;Eo$87-RF9oGcPjoDuB64C1=i*L+~cjVZSnplyz#8ZBJ2hclu_hO}R6@f6!2yjy`gvXjfa-ks)+v@sWLdGk6mG)JT7nmx3ENV;&_@?UT^PH-l;5 zxQut#`m90uX1rUdr|t5)*1LNc<5y*Tj4i~c4xMKM;|bAMuk zH64CESKLQGs*kO^+N5nc*R^f`(mw6EXe$fY-A-Er(pL8rRU`289TxbVHlGF7fl+M; zd~V>gpi94oFJQx`+v5)R46wbRVQU*6|DZi?`##&$*i*1M?d;Cbj=t|*&JEIVR>OO4 z#-!H*@bAg+-d@JBXViOP-W$t%2qI(clYz|zESVi$@~Tv;;UAOj!7Q<1b5W( zsSoFbW~|!7c_DV*RrjIyP%i5|JbA+G;1r`ocny2_L9yQmFBKb(@a4)SmNGlAPqq7l z!+d(w-d=Pp`tZp8%%WpiS%z&#=~IpT?rhlLEw9*#-a?)X@wW-PZ~2P+*0Qi49=B8U zuC}GX5afJr9R66@TJGn(@uJ8a8BaLpjUUB!_|a$861z?AaTsZDijFIfqhIvHPwe(4 zI_+h#&)C*k1&=b+%#~Br48iHjh3ay>2DLqIzOUhWPh|t_I7VJUssA?2@f!qY>5rUxqF>6s^CM(|Eth4V?&#C;c4L7fD|8-C6W_`m3zIL1OkiCP z-`NL0a+`0cGUkQ5vY8{Xt*w|8iJm)4(}u_fkp~j{3Y>mzOPkpHX>4*U@S_RgL&eyP zM)pb}krN^xj~gTPuv0h4epA~iIx2e@+r>g_H}|V7+I&fT^9Dz-)Du5jl<)wDB?e>Jv;0dkeSdYf{;`hd!Qb*n1e z??~3&jBXE)X<~fdihlSy z{I`9pYOGX0OjblxgXlq(w}w>gK6vGJ^0Q1d8d~>16_GKf7un8O#162)(c`wp8FME-L7lUek&-FR$jM8rSTeLj^_0Jf@4#$z zT2QG#>o1-X8;$q@71BqrocVxOD#Me#Z_{Rwxdi^pN5G zBb$9QrVgm?8Mg0%*lJRDl8Aq7>jAm55RAFWQfY^;D!xw|13j{mLg5im4f8g+`qV~N!LoO$B*>hZHbZPtM+T?1% zyVQ~Az;5r+N9p?Lmb*o#6h5Ni#$KY~W-lr{#QfQ3Bi1aVv3w_cUieAtj~m zVnY;PN*iw15#YA(W+it|dYauvZohH0LXaS=`r`Qdl(KD-{#h{Eib?*)| z=?V@g1$}14zVVBQ)?2Yt$NJ~sQ+)VU`mStoxm2jl#kZ!x0c@Aec@bi=D~%S>jiCRo z*e>o~MNh8iPs$z49?^kiZ=`i1*T-6aiB4@Swsql;&34nMOYUnfB&U=+CTA+W$RzAy z^J?(Z7F#VcNaURG^w_f3@D;b`5?auFs%o7v2rh!GS=Y*?Dof;%;6=_YS32uhbe`D2 z7kr{CLo1u4{ka7r?Z*o2_JjB1ujlk(j^{p}98aa--|1@!eJ#K@+#|S)t!WH_Gr^bU z6|sRi;?wV`z_?T?&%(Q)J<+Fjiyk%17qB;QUoL*HM{4vw?#<+0^VUiBdDs2$u+&<^1}S=! z?77}n0xbe<< z#}2@J%K9BF_;5A3<$pxqdLJv#Qv29&&eUg9&r{D*x~1Mbi`@`@uKACXPdtsM2V%Fw z)5X5bJ@+yfm){UlTFwe@-+(TYjr<<(thw7JMSy8aMHP2X734Qq)qEt*mwD2>{feK; zeOgBFO?WAF-~-`s&MzI`LGBpqL-u0-(``JRUn%lg>{#KvX&*ay*i632pw?%__8|Hl zdN;m**!+&=IdwX*y{wjgbid4{$a?d~110oZmkzH}zi}RMdDuV;%qo{}*U}HCan@3Y zt-Nv&TfD%4Phe<>bHJn8Csu9RwH}`mLv23#i0cE>D)2$u_`|3zJbPSnV~6u5y$#Ma zU8dU}g$~7LDtMQ>#Wl`TG{77P9U?QAac)=V=o}&Jw4L+b!1v41wN3Ql*k^V9L7bFyY^-MxeJSnMUjAB9hjeivQGEA^!h-YE&iiL2muML?f(i%t@h z|L~w;UM9XD4HG?;*0siJa`qMLc@rHTn%DZ{#Cs(M=%Dq0t;6d(+NA&ckB8mXCDpT` zHf*PH=2g}{bH&_YSG?yaZESM%(SB@fTK^AjoL(pME_;CVxx@~$0)1+^Zo|#`6#Wi8 zf_9#W`LP@C%Pht zTA$n+Tf^C8GP$K9r1R6Yr1YoJ^DSrbGT*`{WWJe;>@*o)&$(ZnmH{sS@2<2t?f0y% zTIZ2FSS#UsQ-U2iM}!8#lgC^kwoGlW94R~Olugxk&OT3#$PU2;{btLUm_K)nK2{c> zYtWCD-=R6ac~=B38`dHEJpuak1d+J{FKsrqZ{u8J^4QN@vW7cP_+6p+-fPq$k2h5W zl$x2urd9=w1Ok`E`iZx}&KAzueS7e}l9zI6sXlY|*-jjIm!`#u!5~zTUpr2 zPaxLn9C&PDN{8nRk~mM-BaB02_H=OcS-WhGkFsUhI>eSZS<9P_lKnOuSx#&?xdr7+ z!-k_UGaO?FtKws~IPDkE{`qO`<5ytRr?r33Y2UV4V?PF8%fV}QIOqRdoG=a6wh5XRK>>}a^QCh4W+>^=U9of z_J?eETx&D5e-iwR*+lz^liBXzP*4oj?LxY zuX1#q`cdz?GQQiNe2I63KMTzs&zti+=pwexbkY6nqu08YRWz|b3@P{J>{my@S}8C( z^lQVprofllXQaW3ew%{zg^je|Ks%lDmSD%RY2PLCB_phsDmp2wSvIU)-r1~$HCx56)y>}=^mwh(>2VL(!F7H(l1C#uwex7anMq*<| zU&N+(1vbSiWe>N~P@fY!t?Y}iFNRlEsX5W9)!Lrl`KFrPxl`5Zy%Kx7IQ(5~*>i6U z70;a$!uQ>h{mT;BlS;qQ8_T(aZo2O#p6@Dnzia7@*ub&-ES;lm;d>e7DH{YF8Ein;QM> zlUk0>31iC+7rocjSUAL<=xC_k|K1~wh40O2EIg*>bZu(5^W8_R<^9aZ8gC4zww%wvbOAHkB znvJe@5BmcBOy`@P{TBO&w<6Jku-wTW(C4)s)K|6Kamzimz4-ZMWr^%;A(wNAeW1{3 zK<;6$Y~uWtvvk^RsBE%S6Zg?kFU*<OI_3GN#ntQSxJRmxLKA(7B4E1v&aI`G(Wo zGtJp|;Lm;s_g`M~vxaK^FD~F7OyaMna%V^NHLtL){rI`=j@@a`!HlWkc}}%&Zml(W z?wpR9y8Lv?+w5}ULWn`1?-QA4j{ky>`BI57;C&l1@j=;>9;=gmjNF;T9G@D4{UNfAbL@56-(sQmOF1`Y{d@&`7LU1D?FLsZLXS_4va4y>QZym3iM?_Z zY|u!*z$dT;*Rl85F7O0FU2@OhSnQCG@W1*O9Y^oVn!fArRAA@~?1f#f?+vL%Pa-ET+yiY>-%nl7(Hp6A zha!fIIybt$cl43@PZCdd;j0fSkBrBm`OWaz%i+Hs_O&7WitOM0Dil8-{?^W2*AHTY zn62FXF77`<|4;i}B)?goOR#Ip*?(@(tpdR-z_n7-iOZf&{aoZ#VXUJ_vF>t_gN6ET zVP&i~tGQzso<wB%X1NiY<()seWeC0Q7Zx(*QI-gvzD6o(H3VyHu(5(Ia)9rQmKhvL_8=Amjtil&7 zk&jOz_4(}TeD!8vqd_7jRDlaft!05T0eO$%% z$wLB5O6Rxw7z^jXvX>D!`LFkHDHw;#cwgR=_}J9D!)2-Q(T>=MQ}0TftG;gYI^i29 zjDvM0U-3%RQ`j$SVEH(ZL+Ld>;UQ&a-TEF+clN)!emVLF! zPd;Pwm9Zt_n+koi#~xcJXVxP3#0ORAhts}q2fzz@7jY-)3e>~g#8tX^H^6?Dk`%>roV(#x% zRXdD>8s?oUG!uLYUSwXtYmKbsblk{$0$1vN=lj!guHyWj7+jrSCuisKp7txrKXi}8 zyl6VyVJs1t^_gQweuEA3p<9C2DvwiMGg5x;GN*hlz2ubNLV4IJuNf)NU*MF_rM%uLFB~b)d)z6%RLVlw38~j8`zKlN ztE!b-?y1(ac<%xB9><1xwDo}Ur)Us6sCQ&ee?L*mSc6MsK80o}pOC6MQtzYprQVj? zIJ+OIH$6kWUDONHo~93{z2UW%*4{d&o{md%>K*6bW7F41D=uosIrKLC|B$2bi_)jZ>@luY%i?ADhlMu)aG$YX`b+gC?+P5!kJX5eB7H#v=f|X-j=IF?{&YLHsSeudwdJj92H*~Ky@^s-9H-(J<5+%0W}RV!x*(ueA`$Ak>L2l@Dv0xsp-1kK{F z@VXPPNs`oq}?gY**DUpG`%=ltojb)A%sJgQBPQ{Q`vHnW{NzD#W2kx+uX!2u;-wQqVpDZpKt5rVn2xg zol&=tasX8L6}HqQ=U>ED;vXS? zaL|Odb)?(gv>nFI^Z2;PdF&-_^KQrY>1FLxpxW7s2p-$Z(G#&Tw5?$+P9*0J{gp3w z)i=0`N_8#-_?pOl+6cA=IQLp-1kkl}tJa{~=OF*UC$yc*Z`(Hty|DdBVxK2z8(9&* zm$!c%JO3JdCPwOe)9M$-?miHTtxbqcWC6Hp79BOVHW0#QQHP&?QhxKP4{fK7eE6-< z#si!gp3f{RjBu^6~R2B(Ij-_k7|wS{TRr>}`~3f8g{sY#jgQ2aH4ObhXLfJYxPc zI-kbZ@~0N>Up=Y`$Od?_e59xQuqNPz;d}7FTod!-zNOd zig9o4s)fSSUCVgZ%(vW;yo~Q9e7Er3#P@Qm+O+^WjfB>a#Dnp6Un(*(+kMGOY_fgh zBwpX(`MAWn@W*Q;|A#HV#U@RT4s@aHX+rCFpNo!kE`D`0?vk}5aSoFEWmz2lYs>i4 zd!4Zu+FwJD7kNhAo6-5_HI4a=*mngNrW#k;Fy1{A_>V&9M zByHGr4t}ibn4CH3eh$7P^{HD=T`Pp0_;L$dJL8i2QkSw)r|$NKk@vpa@K3{SY;0&5 z{(Zl+CwOH)s}h{Y(r%#pb#Tm{vHPg~v0CL|@q1NDC5ysNP^Zv4z&=4$3bo|J8ZO=5v(i>Pz5B=dk_~U+~30tGv;?YG3?j&QS7PKI@ArH#%dE zFB;`OV(OazFu}KK75QH%Pf(WNy>8wSTnc|T#}gaLx7EX%gO}qs)lbg57wOL`p#{U){E|n2)@b9XPDzB6r1QE z=J<0YXO?T^9i6XlFZ30re>XhMW6t58b9}ZF{1={tzMm^Tv8;2sv%3zOX@DnXQ|<$Y zJ;?b&p(CMv$uA@{gU`ZCly%B^T2uK;#AbEtb+PZi>q|tPXY@tg z4(Wrki=FyIY4tC@1bxbRX9$|`N2fmLdtiJr$$a|FYbN*}a3zn)T8myru9(@Jt+;GE zZgi27Gw{-|8tX1+T(Xv1u`5B39;q+>!1`>=#Tmir(1WW=>(BJzja~*mXA^5(O<3%_x_g2i&M!SuHzalU&aI|i^;^D&3X;dl8Qa}L`&Yvod}CWA&ntLwalVM(sC$9U zgMWFG@LcmITUSWeHK1=#N{2|%w)xF>eW#@D9d37uhJ}8$9<^O)c+oqI*$*|5BQOAGR}CyLNSc8a|OepTa?T_b02=Av<>+OE>8rpXy=>>>8} z*XeN?W*+z3j?en`1FTnPUXMtQpV)n3b4m8={?D_|!}LC+k8z(hP;cgqD~;W^FVuds z@<1z{70^k!kNAPyt@UQ^;G?W}(GN;n#^WP|Y_{RqzsrouncO(&RFyc-o-h|5sCS;h zZ?J_6ooHG2_Lx+C@ri29g7*-Lu{rED5(1|KPd4!Mv<_{pkKKxL>oSV9T+>Tokl=-xU7lRjo)G2y#E8yC80H~&qDLrk{`-E8y?KF1plEkZ#sS1 zywKQm3BD-UA^I=*7m-s&&oG|_p3r)ua}{e*c%JYkhrf8PE)#v}t4~P(=8AWU_48H2 zr@s1xx#CUx|6>l1`oX)<-&a>kU34LLTHTcu-(@}A|CUc;e-b9L13ncSzw%MdC#vs+ zM{ySOn9U!B_Xv+PuL%{O$g7OHKZjS*zE}3F!gGWd#tX>ZJ5>edPF2&p`OO~oWB8B~ zJ{0PPe?4?+{)Mh=YMRE*F~X~wSBQ;*x%Q{}qTSEKo8V*Y#ch5y9{%PLeuaGKKsH$B zc-GNu_6d%Bq^^`JX*aB{f6r+jyUG8mqRda3*igKp8#{H!iH;_8FS0Rx&MB`Xcd`-M z{)fg*3*hbW+D*CeLCur?z&kDm{F@NoW1FA^KRC9%+Gma~oc`QVZ>4Qzz|2WNAxJsTO^aajwt zhrqn~p2`Xr>wf;Y(qOf#K0d{0j#sPP*mlbAN4HuNs5d*{72El+$81}v0&P#DoApw@ zf_At6#D|YjBGx;uv~3aNzwNS?wzotFYdJ&o+}H;Dz1W(4^Fc%b?|!% z%lzzWQ!Tp|sR%wz^^((*wbLVcC10g{56>(g<4HUF*fdd%)w+4#SU+b{oDHk4=id5p zguWYt=oe)H;=9q`!D&BwS7Or~)}7GFnegL(!8!O$c(Z?8DYoF!xdX`OIo$j33O?*IPbsJ9_PX2a3&{tcZE* zKJr%X8*kpre|)UXugU-a{8-y8@kN%iBAFxV+{8Hj=3|48ngiP zhu9imTANhV)&5aceeQbmoPkHpFFx%9_Yq`}#MS%fvE8n)fLU+@j)1$S^Bf$cPSfSS z_FKWRh2Q4a^ja^P$G*nmnZPaY0pr{h%um+L~xmbFYS0R_olHeahF4zA65Su{@1`Uy!_RC-N{_qW6bi#7aGm;EcU$rri!gv*NJ=H^h4dkJ0UiC2h ztvfl3sUlX!P?gAiH@y7pvjS*f-dxhA`m7HBt_d1C;7CVXf z(eeNDW()0|lMp>ezt`T1Ew<8muaEbLN2T7UE$}HcF1aiDf3BPX3(Z(AaQ^^nOz`dk z@4~bDj26bddfs)O%B#1blm5SqVGA(2!}pr&kG060NPNA_hq;kw9pp`U>Rq46Vsm{F zzFx1-0Eeq%x9hsS=2~@cY`a~bdA--fHfe6$C-u&yt$ywIPyCTRzpoqkfCljg4Z;7K zpMO);C!3mzp5Lj$$z)>@&svgikmq=v2$Byv({-G&jrzh8X^gIrgkNse%?5rTq<8sbDRL*;4XG*=V=z8Dsu#U0U z`jj_CXXwSfLTj@BPsM35H@RuF*nb=?iruYB+rV0&vE`Z;zYHy22rU{qZflqpV?CWh zQ{LFw1FE(1F6L*bgLZw=_i=5)gM~k*c=JOA@JjXs!lR+@1oYVzJdO2vI((fy26WyP z>ifit?5$@$MD8vF7M=4lN=$M%|KA71_ARm%-_L#8w*b4N_!a=8M`SH$2u;C$Rnq=C zzBu@Wa$Zw!?yrcX`~$-IySHmyCr_1<&u1E+5X;U$AI^hZt7&s7xb;gJ=S1T7pL%{3{HkL zEm|=8z8n<*?WKH}CbfW13!e@?J$yFv?)jD*y?fErWr=aNucq^?DZ{ho6Q3C^8J}Pe(GRZL^G!MORiKEZr6Qojplp=rFUl5nh$0V;Y z<)g})oU-N&WzBXOJoSY47^iO2h-4^>IAvCbGRrP=m7Z9}_;s7E%Jed5p*~@{DuoZE z``khU=l&OIppm&=#>e8bn$IRa+xYC}v!Blqwg=gK0(_tq16nbl6$4r^pcMmJF*frV z;PVon1AN4<(xIITnn%%2k+tZAXC)^-Gr}33)n$0rkm1>a49}p?(fu0BPkiQT%ai|PXwS^>jJ0w?y^ajeIx{@$I`LUnP5QI{=9(%>r&VXY z71?yGN-~s{IBO$(Vj1&quc^8WW!!%&YuISWP}bm-Eyz$t-V6O+hV_jOWtT0_@ZNH} z%++{e8T6vxb7kny<@ATW_XM5+{n+m<$xyb$Da!z-%YhU7@`-IObKc9qhg=RHa+w+4 zGoAM`@F-V`M|EU)ufut-GecRYQ`VKCtjjLTs!1=ic^mXNinm>I2m265ze&lqD(>B` z+Kykt9ir!|08GipZ^?I9$#)jtVUdO6&*AVQ)<{9uC|<-GIpG;=MwiJ~DO<*Qnftl1m~56FCF6V#k^*b)^ldpYl&h<$a*fur({IM*CGP@#?!` zQ{$6oskWp}Y=f7*UvkW;+k5`VaC;lh9%)bff5~6b@W61J{q5~p=(5M25S&+9DLbaxRU!O4ncGsz zen=g$>omm|V@JUL5yLr-`W?}!U+_tODB0iO?~koXEf`g&DOIO|bCa}srMjLg`2~q5 z;JrdA*Uzett#aCu_+>+$Nga!itaT^Bp__GJGoBHNq=dgBUg|!Wo_ZvE_eBPg$;eEHfFEpfSRA6-C zZ{h;SdgxGm?tTnDpT4FzUP!-V!gjx7WzS zBF@s)^gvT`pYW_Y=zmmy*id*cYq&4|+wYi7C+WwA@A3@rT`p&&Cxy>`&&zw44#Q`U zi~F@y=}F#W?HC>L^NmjP^gum1v)Jx%4m5^2k$YabzENTZSv$&Xn$KAxb8^1XVUaIU z*Tt8>bo0@5FT}Uc8)Vz`Vkqvsvs97)gIFSaeoo$(I)|7`<7c`r=-gan_a*)4{sgX6 zUrPGX^?AqXOWs-P)qORrA3NRQJvHzeuRec-55X6L{I=jp0lo)VhebRKm@Ch0A?9;+ z_xXm!e_z8&Po?wQlV~?A+WS8By}TDpYtPmr+BnN2Un=D#d=nF;+o+T8#4JO2o_-b$ zoY!I!)0D{4&!$OvG(hax$TNSgTV=^}Q;pPZS9_i5R2R7M9db*6YmaBN@ZI&%HBXVJnTC zD(zqkWiWCo*96On(q18fM?y&lLw1!`4mc51{752f(v`ckm7S614w4gWlk6yvE_MVN zFr+xaeyI)J_=k{%AzrA->x)~G#Wl|2m^7qzTfA{xoPg&0{+xS98VTXJ+x_nA`^UWI z-g|yO=lOM>^PK0v3(qwCgE6-)_A9fCBFp>dM3Rhc{oY0JnvFJZHGJzE%BwQuf30x4k(d1*Ggs}0{Vt@v7N(Vjc?a}PzTBjIXZYS4*0F0+n(9zmp^p7}&(Nm^ zlQ7=z{jx)TynJh;PqjB~vakr-zrb0!NE>ApoywTX!VpwGJibY5!2VB0lGj2)6R?B>rTpM?dB79_*_ha`ZfS4>+LjR?m3mpOl|( zF8fJUMfI$*b?me1arlnf9hzY*}o|LD}AS z`-5loNw5)&{&GHWlir8y_qFyZ(#L#wEceVtHMjbObDh$&()?xs25%6k+ONo$|rC0S339)hHaupZP`Wo6goY+ zLkVMyGDg#1Wyfh4r#;7N`*$#ZenS5uj1wIbJr7yJUJjg}ah5T^?9cq%o&}Q}ho=h$ z5$T4U?~IPMt@?`2C~G~T^+^2)zDUfA;4QmixW2J*I$0CkeN%5fPn|8q$BvP5Vt~es64hjb5qFUQ@3zfG|4-hTmB}=KZqu74X)}G5=w#JI$dVi7fT|_*S$J-MVIa z4}2`a`~~$@20YHfh3B!kn~b--zmxj$^GaJiM6i4Zb!)By{A8^aE$oe7eyoN3c2Dv$ z`3rMc$Q!~=JkQR1@w_OHaK*;157WoKx!A?SZv_}nfbVYldoTPip#5p!Uldv>_t#2h zDXzxQf^5&*z*Ka&oqe;Mjm2U27gUxx!%t|)(OlryWPI`OBAQkIQZv{yz0S2UO2+uK zzGGuA^jZ0|<`{c#rY}vz377vQ&z1%lyYh*TYfUocclNXk-^X}3{VwQ(_sub}OmAeV zbSB|j_YK#S%TDD#Vyfj+c)4+0t}fM~x>OH!#JHRFV{co>B%aM2%q8Bu_~i$fd!4Jf zkN;Bs=LUEm{WbAu%~hal{KB4DhDRQo3jZ@z!1WI93xn?jau1)N@Y%|}D+9R)FRQ-o zhWPKmlS=SGCAKvFUu%ImwD90Mcs=|rJHy%w6w`@0&NrijC#*a@Ae@hu3Wqc==E>-^2YV9^6;e!)y4ce=&1?(BvhB>nW_5|^ZajF z-?P*h9v9o%n#W{1@uV4>>cfX8Gsjf7HpPF(-UrED-J;VF*A>G+@XKb_&{o80mfvc? z^P+A@2OE&v$=mJ>;lWwB?mO|}1qPP>uF^Q@>k{yf_9wL!&C-9$Co*eHwe+Zdo|RAi z>AsHpP&Y202W|kve||)8p+E7d=I%1%jfOhRzjeF=Z!=zBbYx+)ojv`_jlD2t@-oH} z@t$`$cJ7gwJobNj^zFu;S;SiYPVAHsGdF#|ozpVGkg?}O9cwy$u=u9?Nn~TwU9ikw z?SoCmyY1Ha?_?sTM&s)K?WXc=GwfR3v2&<#fWypBiEz66jz;W)7dFslDc{Ocw-Wo= zMQ1JnFSc3STo0budqFkt=}l$Amu7I@;)`&8tnA`Xa)+1tf}M{##J@Oe9L1meG<67v z>7!%y)x;C|bM`*(xYdJ>*!h-?lYRP-Kjnb0bU5p``oL=XbnRvO^flWj(V?5=j6V3C z^k!gVgpLwVaPJecwLXXc)mZF-*PQg%&KmJ}^f3AOo+XBxy?2y2U-8tn^i%HzyH=6y zRXp><>+&CO^rwK$1GXQv#jsKTH4dHAuxBRRv z6kMl*$)<>j{cd}H@s#af3Wo&kmj%29SnQk%7XSG3$*{1vSz+liue@cBF7PLgJdeuf%irZ3 z_BT2sy&Gkt-+z6o`{j9K{AyC%rl%#(iuE}9I7OdJ(J@SRhcWcGy;#Rny~0UfdP9*O zr#Ub9f_aIA4%|HYy7BPpW&vRCNRI z-C1mOwB2gk5uQ%c8#3T`C`&azWufj6laE?T~op=q}3()R}*6}n}UA5 zLlftG?`|`FZ=dc|d+o2^*?j-w>9P8!n(ssIg!wM2|F$Xn9oDfV|Bsudsuz3eZt3{4 zWg=HBALQHK@Y^>F-{7g(KisXBPX^E1ik=4w&(edm?&6<2X6!y5x|ZANFLKe1+^)P za*2K5MzgQDCD}u6Y1qG0>WBD&bkYCs`{ZJ$;BGH)xqppYL7(FEsfs>T)2F#%pHBZ@ z?o$nYs-;gJeQKaj3HsDbpOW-xY1pST@1Rfk?wkKRbI05w^WQ*zpGVKWz}y?=KFZve zF!!Yz4?lE2x8`!=A`N@c+s?x&=@8U&`f@N3uhYIn!7oH|vf);X_xru3Gr%>nRB)Rj zpEI8CmE&)d&mGTq#($f9(V~3ux5*b7&-coax5+oHC?D{gIF5pCvMB!9pzisUt$a!T z%=bAzBAsD6Fok;w_hdL9k&K)cLWP#rSpQ7|=A^p_U>G+%% z)gRg_#b1N^7qbqywEpq*MBIFgeMQ>0^~EYi^?%TujOh?^%Hcwx=hdze0=TaW25;j`@{F^*}Qb#YqQ$JtO?Uwo>JSh|#`b*)QshXglSy)^BdCZoD&NhbI&`+ryTc3shRTlp2 z#kI#Q z-JV2C0d|7NJF%G-)?oPS+k2d+w39-&!gY(6i`;$CNoTkx(9S$Ur-k*N+hTEWXd(|` zPCHVpvpc{;){&1f&--M16Ye5E_BG-QM4er%2e7%h`wBJ*r6&$x3s{8jHhWjrUdOY= z&!*%&n?8`=jPAcx^CKP>u7#;{P(tj4Y}c0wPA5kbR^#*`3Vw-vp`El>%h7G8g#TB$n#<3d=E0d z(v45bqtIBa=kWw1tXEYMP= z{lImPrSChfGiS-}g-g1S0SUj+wA%GEIthLDY}<+lCfI>rf}M>QdRpiEE*{k0Z+hUI zX#VinI9ZEkiq3J3&HKc)yYIsn(G7^HI?nUxYv-k7yI|)Z+0;s(nt#{FR^gjuea=9y zQ}kIjutJ~1`Ia9rbFMzW%i2x{&R){z347#WU$r+@;Pdd(PUd4@$frB@_PTrJ&l{X| z%za<9XU}GJ19!eJ$>$CVZ$zh7_c~zlckSEakL-9;<8P;M*WRU$Jt)B63ytp(e{0{i z&7u52p-twIIEndf%w=HbnQT|kyLjt3{SHpFK_bfqf5u^DML>IJf!nEN-+;e>k9Hmx zxm%G-=S91jHEzuEoU3l02Orp~b(j4<$E`?7zE4L7Sp?smdEW?`fywTt?`2#+PEuD!OGLA3{B^BC=Gt<_|eXtS`KL-;4I$Q!m9@{EA4M z(!2rMMIS6q-*U>`#_#gukpIs3IC2_??1!O_itQ~Ji`DH4ym+#G+m6qX&fLE2MeOQD z{qrl_Q#yZaab(!E?oGLSb*`AZ$=LT7J#D{B@2SuKbe^TVHe_~#Yf{$&hiezlBmXza zOFW0|i*H1qQF9hD|kF67!7mr2b5Uf)#9k*@%3U~+lbdi6Qm6NmcXNu@7*Si)S z?P~#TK~H5m7d?^AoUG_)**&spGWLiYvwFoV&UtJX72W84z`fPtf5-7a$9NLjkd7f8 z_?v-#0Z$pR_mD8x-Er>Kz?U`DSt}%CXtT6;hkF=aP23gtaN0M=9~dTXKyLa%;AZ2- zw7S13eP(H@i97kkgLi?GeXmTwH za@rl#S#WTzf_~U{RG{Pbo8l?VjC3)M%kzX!qT|2|EKj%w{YreGm@gFZgw&xUEyX;+ z@?qksPvQqA1v^a4;Ce_Z}E1aoMxy)yxtOfXu*g0j--o`=EoGvVy(>U=} zE8Ww}J{9t8bT7eEbcgPBUh%1fThc|-yOQ(32Ye(Rd|rO_%9DPII634|8S-0xF8LVd zWv}qTJ;7NG&V;NCbm}oWU5Ty@?=E@|=27`71DOGjCy#TX`wr;$8Rl{mJm4=*&I9Ly z_1rhAC#>g!eo!YkEg50y0y$x2hLsW2Q*!bW86mu|a-x6_mG0w;QxM`~SvvkBduL3# zE~J4+rZ2oJZfT$m_?@EN(-zLd=)P@70$y_aX~Ey}5@@MJ@s~s^w_W#}^DX{Y0XNZ$ z=%I)|ieA9=3gt_arcyDFaoc7XUs3mGPR8*u zdB?nNS?LZS^QOje=?O(T0(_}>?R%VY)J&z52tVw77l9rW=n~*|kuGsubGhsh)=TWM zsK5RXLwVn0*Jshx72v}cknuB+^}AYFJK+l|+0PokAos1juVmbZ;2EL6?_~Z&JCoN2 z%-f}FgST62kBw(2pAcQw_XheAdR7g3mhQi~M9(Vd%fqwthl^n7WA7`?R0U@QBnvW8 z6ZOv!BNQJ7D|-Po(}$t;Ok^FYuxB23U98-J{4MRiN}>XCUppE=#q z?LI!Q9XoCJCz8l&e6rt4&g)sUr7Lyq?8g+Bs^?pYmY(1CT6(rGZ%N;;SQ}scs*N3j z>{b4rIf^s!)l7N?=ee5TU5USicM%`oH@74X7+-bRe8iw2-|fX^C6D>`5ygkHJO(@t zd`Z80b5GR+_B_3CJN!0_d5*(x63Y}*@;A!nrHS*LzVCMNCA)8@Z>cq`Yl%e;-gYYg zvd;pa9@li&kw$v=a$tauX!oD-ZiwqieJO*FPe${Y~XpzTYpW z-sY5P8ZUFj)!Lu;wRU_`xKJ!ZLOVynzR`;e04JiMe1!jlXUIyci;d|F=x4z*wp8}1 zpV5IF^@SW0dUF9=3Gq0^Oxl@&+a(!=;# zISbww+YTO15Sg^7EH+>SHm9*^Qm>B zPrRzYZ!g@}c07%18T;Ablc)M=x52i%@ob>$9SGM8^v~icGLgJC7Gi39IJXDrA9|t2 zE`7MMpZG5iofbZoNe1Z|yFom);&e;unj5#0Cp_h;>Gp zyLo?d1iJ6vo|;AZLoPZTYZKj5L!W!jJT*b~(Z5N&c=XH^ytv_QVKy{+$`4_d*gkr^ z=b8~Sf7FE!kB;3j_arzr*>+)VqtF-pl64C-6h2#-6xwfPOT*rBQS-<8wuI+=!A^!P zqU5d{%rC*s64}wZ`*9eBB3+>9o94ur1=9!!L7J8FX2&w-woj*++Ai&p&NkcwRf{ z9`SjgMHAzD8{eaRUt9QIZ}7QGpu69WZH*YJ>6OTo``+_dKpV{4?QTbU1?yGLr}q4m zV>|4Vbzk?l1UH ztHdkFf7R9V@C%Fr`!m$lpt}b7ua#b9=~{Lx`m4I=?+nHM8vDK-Wr#HVH(&Q>x~=uZ z%}Z~y@~brc_Zr`*bj?5(YW|Am^XbX!sVdgVtPSB$=V||}cmg__6Y@!&31IKcslvZ` zG}FU*of({8N3Tn9pK1C|)-oH%hgZC+eYRWD8oh`X}1My$c%G9^oHD zfA&lYWyAyJUmWipcC9X--lceIBR8kFb2e+(G%s6y#ll)Qf1dSS34M7B9(T+eF-~S- zq^;G|d@%KFS&igqYUD#d5Koj`)LKM3toU+0_wuG6JPuFJ$HfanTlG@y`DncC|CHM? zt_jB&nPQAX`5N+{1CQ-l_F$a(YIM_>WVF={e%1PQ9NzNNIC&X(YmAq`8=jx&T@BB8 zK)j4On+W3*7RDPbj5mZZ{*zw~y|{xAl|X@^b!y{9a_oDE0v%7Fq}WM7MJ|$Lb8JkBon= z{5N#xvDb8kjO5Mw5trf&VHjDcO)M; z+yC3-zctd~)7Fywp&!HJIySlPci5x20$y@T<#mS&G(FgTY0R-shE~h3k6#-v)R5lq|O5$ewZMME0H1tW|y6iXFmKsrAz;CEub*SupO~%H3^_n)uGu2M#ZQQTbz1lpMO1!5$^+2*k z_N(kBr>k)&zfHdOe$rX5Sp2e^WJ{b>VPc$iT77?4>k7z zWRmbWVw+?hz-PJ-TwH}7b6=ppsvo`!Pxmd(9J|SnivKnG$d*tG;gH9OkAH z6ANuNDf*l6OE_Di{qUiDEYrbx5}mIp!FIy^OFF0RCq+-}zZc_vvx%w?!he4^&y11t zR2lh2(sn0p4~G4ktA3#~$9&G^OAf;)*0YyhhTL5n!d_!#E=)?WryV_a3hw@utm|)e zY<%YItxhN7DCb+5e=9L~bskaA%ID%!oc#4Jzlrlkz!g4Q!MGA(+cnH*By1z5HvAcG zHh|Y?Ep3(Aw(hX);@=Ftg?5Wx=yifDX3b{L)3c_iKgF8vY|)*b53@!^pCBfXjakEe zTgk#ci{zPqt=VSpy;}o64%e4n-w=Lo+(l?(?*oT_f^BXAF1!fSWL$2auOG!6A5=xy7eg#(IzYpRx=LZ_y0 z(rbyKomi6p!mRX;5du}eD!+ude+@E%^vU&dhVDo)F46B}#d$*f4Rjk|bUFMjz)Wyp zUp~h@Sy92l>w99TcL?~cB*YEzi;<%qKO3i?ZxiMRI0Sc>aTg(TJ6GlTuc3}(q-~R4 zSKK$oy_xS8PnBP^;v?rL!90L1bK&iI;-oJZ|%=b<4gd&MD7?cIaO)-Y4ySP!q~lT3ej>Xbt_W4aa5e4H_3PAG>GE;!?X6h}cl@ zFQ6YP6OOHALYvnHc*B@#g=-pLal0CujsKM*zR3>ko{UfR(f8Wod{d0AwzwVP0I-Ia zIaB(^C{~izOP{u}Xiq#bx~H2VN& z)UEy)1-4}1vUh78UF(D(p)lRd`(@dX;`Gv3PSf5&( zVxID+nyxF)KI61xcRBD&>bqQC6XaEytV@13$S>Vdyh8d{0q=Ewn>*V}M91Eq@60X8 z(*o~T9mV|r>A)s=ccHGLdUA~$-MN{C$PM6a?bAEhr(Zd}tA2IiZs+M;3HfB9H{JqH z)(`x*)A(Mk&0I&!d)7d`k094(1$@1Dp4oF-Tlh}?cDr6Gq6O01i_+VsNN+1jUp__p z@}l&PDbhQN($`OszMej`2uJyERl4%i*G-egVef3VxV*#do1&h+qIUc#(*2_J)D-Ed zqIBy=GO2yrudw~iQ=7SnyJ_%youqglwuou)r7?Ns?b+`u$XRipEl=%sl8rke z$NX80@4p)9Yz_W)XG2iO1$=!b*71om*j0*fF|31iY=pU<-l_F&Vmtla?k-my%Ti_Y zv47lc>-ocgFV{Ei_pSYe{fbNLa*4?iX&A4|oTskv?wt!as~*++Hs#xhVSk~h{Nt3j zcKIdwU%vhh%C}Q~sHl7w<<|!A_~l>P^0NJ?4^#JlE#<+>0xWP>+m6l5&dD$DvgNf; zqw-p#Ujj?FgYt|Yyu{uU!qVnn)*x8^@&l@awS$#$zXFzB$jfu%by--Zg1-FX$L|0Z zDasEPl@~1iu>78PP~N9}XHj{e_AVn&mV@i}3{Z zXJlU7U*W9pdG)ETEZ@`rwG7)8v`f4q+i&{S-wkbPF7=(WkJ;^RXD(*0@mEaWVAo{& zETXx^bf(*1q|Eg7Y0eMZI>^g+D^n@c$=cn?@?IqS0~@jSmWpkP zVO$LDH+ea1EP-$4pdUqUMu0=JX=9DnNo<%Z_~2T;&BY$-q0_YE=U>gY4(yDI1H7L1 z+GOP)f7t8cj==4}A*Z{V|M>d!x3Kjp#!~{l_kQF0S26!foDH(kXJ@{SD(~J`kPgM>F1WC&QgAb zzMkAdJbr@fb@D%#F?)g`eY_dC)Q<}EKdYxxCzl`lc@ z-0;r0O~DV*^G&2MKTGm&E@lke)ruWb@WBSh9#^aOMKe8|=Ud5nzDjh0QS^o%a-MIP z^L*?H0he?9vyM-g{)L=b>*37WO3tiRx{2(l+noI&XV!+@rTq&z_t(R@zm=T(t8@)% zQPN6CE2UgH6=~I^&Bbrx6u;AhoUi@%F!9~_=Y1b-=J-Fu|6cz0Zy9zv z`6aO3#{$}Y?VmI!!Sm0*C)iopsyQrz%Vgb4I51KFGKbNL1O02GwS(-(77)E9jjr|i zN7tf{)Mlh>vA<9cYN`*|kJ3hi#=vtMzqS0P)YC2Q;x{M!ly6V{ZukS|XoL^a5wva- z9HbLye7%dg*)yVxjL+8?K`LkISV~ixHaSTxV1q&KRX)Kz?@U zBrE^ZU3^>Xr?5}*J^Z$Uwdrgx#XTK;U&z5X;Faqi5pE#^$^u`J3*Viv4xH?V37uIx z3iu^lQXK_;)B7;`h3fC?;|>twjIO}8@(g#0RIdMs)w`@N^VVN#UYUPqK|40g1b6%_ zbPn^|O+Ov}_ldsYD?{*UA6}5nRyqlOo&5Uv!RwuE{08`K=9lBQm*3<3Ml>(*`2>Eg z@U2J^-rwvWK=#0UxjXNBwBZK) zm)PN!Wr%mDwPIqsYy5|Ucnj!wZ=~<5*8ZqRxrzq*%f3S#`P#+tUK`>&_mr!@nfZqO zq>={gV-2a*w?5`SWfHwlxwT93oiE5wCbjyf^R(}+a`L@t9LOK9uXi?C`~YXXzTPtV zL?$cmxWV2jWO3tPzv@59SpFWlI5tn`W{%I(xjOcq3iMkIpD~ijnT5n9VUJ&NSh}0= zk0*~}I&yyHEV88&976{P?7PU7EYF>y|2h+tXRopAwyP*#qVmKuUg)N}7h9hvKYZ`A z@6?s{6RP((^jRx7g!ob$_R$US<)5F2|K6R>nfE8S2Uuy`J$kcva`5~wSI@0LCNX~e zfwqcv5M|LaDl*1gz&Rs&A?*g~lt;~_!o4g+hy;|IooD^=g z7va_-WE}c`{U^WC>Gu-fRx%DfSn@415XiTJU1LkPN$_h>J2s7c{&rJSlwMOPqdG|Q ziqdK+D}TOr{^yFnSUqbpFOgmuu34p5Ey?4P88>sy#)4}|0tnzr+kZt-|)Nrqq(|UKr|_ssh@>2=1X^& z!kq$h{ngKu7w!~LUV9&n+B*E9;xnp+yJ#lZhByZ~cXHoEcf!e=ban^b2AZuE{ifI_ z*Y{M@)#VdngiE(U_qIA7G3JYSMcm@w4xN29RbhQKnK|rdM5uF-_E6A~{OW{ahH~6k0`}U8mTp zaqfBZ3g45JpZOU1D|DAPWfkiruwxYIYUmXeveD6x!hc-vmQMyYv@RRN_C;Vle*Q>& zvWoFlYtA(8#IRZKyXZTMe!a^Z#tvI)n*Anc`2;&BV+IHAMt`bOe-b|MZs+{~hWoK~Yu@`F zu0n6BNygsnuw&$$u%%b#SM*wtr79oJXN4{Q^|A7$Vfh<0hr)l2gSuKjiJ%b+~x$LprnjvcaD6#cbUT7m>-4=s^EMbU5~Gl&*c$ zx*JA`_dL3f@1=Y%D}0w+C5>1O`L!Ag>E)!ygg5lN3jP;kPAa?});z!qy!mVXtGBSH z9q`N17beho5&j52_uhx*M`DyIuW`o9ds9?%L?~C1)PAX9}U$xt`;8*6)Nj9%jE{TEzO! z0$1*+`|Jw!MZ7CH^Z3o)Y&Y;{F6K-0*UpJ};X`xmoQt-@dFd2=rTue;c1lx~5qMz! zT<;F<>>WV%?=V|?hn=z;x0{=w$r9jtlkV~Gc9_$m!+M^Rm8)O4=^XDaYI649KsOJnfUmTc3fyi05d`@SkMm zs-LD)KYfgT6T?g6e6DW1-v@6G``v2Civ2Y?bNIoq@A9F#r0?KRDfkl)WtsSr-m50P zmlocIM|M8Nt0vNz_Q=-D-d4XlmlLfqR_On4tqw4G9Z28rZro+IijD$$%bz56+>tCg zw7x+*XZsgGFDtN_3|L!2>5}~V=VeEQ_qA~cp5Z&ToU307za`b4+7%7?eM2WMX)}cEGR`jLR&**c_eOtL|1t*!BEovC>i3_@Ja!Jo6e z$ZqPo*{);Iku%_}=)>Fd^}!H^v+;rJT$2Bs;;UNuz%9=97{G!8&XQ zd$agO9A(XW6#s%F?#DWryDIMI`yhAteehy?d*ubwQTYNi!o9o+&hR!Ps~VCOfAWDW ze5cTMaeTIS*lu%iyB_d5;x0Y^4%>eDf1~ZVZ7`0Sh^p{tje3`os z6UoXKcABn>@kAvs>wF<&Hoeej{1-$wz!th+KiFuR@Tu6qoG(Sc5Wh?D-p6|@@5_1L z%==c}n|V(rE4F-EV+OZ`>p_3%XI+9ms;~5YtiSHRslVI8{_YL?o1?#v)89e*J7W8r zF$2u|Zq9A*^Itam@h2I|%r=LU6&vmj=ixN{oe-n1fCEK5dawxR%2lt`e=0UyAJ!4@ z{31DA&}T#^N2238Cb55JAKiHC-~|);;KiH)*7=jZlRt%?P))v)qVM!8e}?aK3-Svb zsL0TErV0Ku2OX1jpW@Ebx9U{WC%ZU*fe$DDGj8qbUj3e~?zr2f*xjnTpK|?_(LQbN zO1meoSTqe8?mNxgfgW)s_Acu)LmjG%I#ieHP+j=ZlxIorCx3sCUp_X(^CbRpf}d;i zl#!=2b1VB#^b4EqHuc>vqRoHM)xG9ZT{_b#9Y?x= ze2{GVZry=Eo&If2hmzH1@(i`LIJ$C9y^9qb=fqDkG?o^y?S@n(OevGR!4ed~>Hp4*i? zk##DML92bbd$e%x=*3(|?C1*U&u@<%U0^ydwl9wzodq2xT4G0>$|D!!$=F4ch&^{S zdFFySTmAe_)Au~I`8;>XKHq4v`B78#Ja+;=@0e}LnP2I*x||=4=?>QVRc7Eqg1cDn z;U3iv$@0zXg7nCFe9z;`qjco#e)P=h^d`y7%^wN#oS2`9mfAB*I%_n#x!?aeaCFQW zoxy|7&q~Imzwkb}5iedc z`d=Om+lu*bnz{Cl;2*GV@M$Zj^uK*8NO#XO56PZ2U+b!GbgPpU>E~tB3-UQU6TjZ~Bf&Z}Mc{GMUx1A$@nYQ`Nu9(S0q; zw`80XTQaPRGp5b%$pE9zfeYZpad6>;@P#=(E?69WWN}pQnq%^JWE(3-n3v`CJDvC~ zX=C6Ie@vdW$hE2qtW}OX*!yDcpk#x;+}$rfsgw!ts&Oh0Hx6?bH{)Y3@VmjC_gCHR z$2h~mx$T}$f6dNY`Y&F!_iTtxlt=Uc=$DvMhqYJw8+Oj>`T$7&k3)r?p*POF9mbrtd-v| zV_uJsdKA4zcmH)_V=m)aaSUV7yUt7+j9 z{O|5kKPj6lPD|~Gx1^qeAB_Ip$HR1g>hzz9W>mhN`48%DL#lKPQH{cpZSImt<1^?(=ap$+*#mZ_ghM!!5m-@{k}?Y*l^ zXYWC?Ua*m!FJ4GY9aTYgzsg-SS8QF|8xhj?w)=Q-Y4EYfk*Dl4~YjBbbIkQ@l36y z#51L1i)SisEVi9QiuJqy5&TnUF6zpB8W}jBJxX-z)O*WnxiM5n!5+t-f*W56>@DIsz^3&-L5Jb}(4N|1UK)=s< zGjM=-tcE~7l?9q^KCEG^l3it?0%c}kV%VtYrHd?k&;L3_pd&?~FxOBwZ* zqg#(ihCP3eDLwk2`qEw)gv87{6a=|drP{Ku@~-=UzyfAb&YHx|M;n{^!uOFS)4?jV_NE1 zgJ`YOT5-it>u+2!su(%IGF+4W>}=f)Z|ENIL4EU@-Z<4i+wAB4arks-19@|;*YxJz zgVb}d(X6clw+^n7kGOFT!iVI?cTjw2r#U^sJ>d0?W-oONsXX5n4UP8+ArXm4ZP$BrP&j-acHZ(N9%#B_f6LZU1NOyDD#FWuN{X25gL zsBf+9^7(f*PvP_5MRkY6Up4&;Nvn$N7gxn?bb|*m(Z=r@Y6lE&yNG zdQtuM_H1bh(*NaAonuPuFiVw3I7faPuYqsgO@D6Ff|wZ66X6%>=%Fsfb?Nzsr?_|7 zbftd}|Cznwjc>k}vb6!9y!*q@>PgyFbD>tUiG}CQc=T~#W9P$u+mk&N>`(mjEa9~BV-rnT_(AWQt71FiMED_ZwZ1B{A*hq~ey~OE zeqvS*^4r9(kKa~)S$+fja%!g_gPtzfmO^_={UY*HulBb&SK7xuWT|u@_@IZL^gj0X zN>k0hF28OY7tVX?zYG=k(aKruZRuyUPm@2PK4syN^=)pJeZ*|<(7(SvcwoEgwD786 zY!$><7AzP`!JnhSr1K34-?XDMa*j!NewFGx6aOWbjGeesmhX-4pX4%C*usOeKrw%@ z>(`HnN3nOrGxM{_k6;gyJ*w%;$7L7t`bMe?zG&!7KN-{YK5zF}mRsAAY;Aob`-FSR z*aMG>K9aFbAGZ2K4w?bB!dHu<>;o0Ul{T@bqrXu$d#&qlNztE>zfK;zU1wt_6)hEX z3hfE8Pi156C!p!1`<=$X#`m4u#%+9${z+it`?B`OJipoX$6`YAoEX9;>V9WNSZ-EP zxdmalD*6mUcgXc2Nrm|+4{XY^J=m9@7?ek`C2gU6%Wt!Qs6$@M9xB(?{Xq_gk7R_ouV(aw~g&zWmml(>`Z>tPkF> zbAq%u<*<>HHtZbcy^44CTI~CN<CW+0z4GtWAkH+xytBtDwD7doRH-GyqQkx8H}& z6PxztBVOO;v);3tFW}3vELoYnFLS-|>J|~p=U)8jkTaGaFfYKeDt+&AeJf?Y_9`Fa zYv2r0gT~f>U9hi~ord}C{j7IMOMk)EQL4G6yy6+{4*RD%b}Jua2@$2nN?$(8-rtY;P3NrN_3QyQd0ytz zoM--s?#xSinQ10Q{#s&hmJoNdocNnD+Nxm;*j?Ps_FUv;;q;|)FK6yeR{q|q?8EM6 z`mb~1+vtbAvkJL<8TfvwhH_t`oZYu#?AvHldxDnsdMBNo8pa1vyr5uHFZeM@&x0>y zQ`~7O98A4c-_;#M$NSwSUBXALB^pJe+~s5Edk6jT)A{y3$+C+#WQe2IpK^Ee+b7+O z|Gn_|-J!e?o|MQJnL5e}>C9Vje*)hm1GQepH~FRBA$PNl&%<~4pn<1vChvNDPzG-D zBWD{AxLf@c_9%F*c!k&Z)Ozt?Z_oV`&fr+v|3+6jqRCPZ{n=#gyWrWDA@-io;kWFv z-v@Z#WO;gcPTxGE0BM7VAX;X2`5Rd9aO3F+6uZ)*Xr*_4|VTshY%c;|TE z8p1V)zgyWBbcoEtfRAbHSe*(^pR;#PWA_$ogYeJD{b9$#i;b!c_r|o%BGjI*aJkfTW62fNN!}{FYt$0 ztDhhJfFJNQ^pDxM{7*Ccxo2vZrk=R53tm;8x=`Qs-0+76x-bvkW&YC8% zZWexFt4u@QKbJ+%Tbge_o8`UvmXSp@*^Fs(-#`P%*z|ohhC0ic?-SkaWr}MSPZ6JK%R#eTc3%42cEmBuFXqly3wJ)(?i>BtKH`F4}-pABuZ76BHF8=1Y`IVGHG9B@u#0-JwD zdgF4Fxzd#4S2@xhPXzrhvE$wp_J1?&Z5kVQ+>TpwxRvi&JMJ3`@LH~MZwt!}kiKoK z|3SGN<#zKuH(}haEw?u;w~zF_lgbTJZa?1#Cyv`G%@Z#OAG)ZbWs#;UpQ$Hvw8WlKAAp&fiqMF0Q4 zpq;bfIA3EtXUE_g(9Su=`3B$5S-4K5o%3P23#6YPgO4o-(m77_h~r>`noK)RNl?xy zCB0-)xiZR?^Svy9>*;aY@z076$FM_+b`trVrJZJAy!3yMcAQw)j|$q0jg8yVfD@-5 zReX;J_*B3{;e}HjmYYj@^;rLday68z<$KM9aa-DPys%sY>E5Jr3CcC|Juz|Iq8*JJ z+F{%ps~xw49?@veE5Ae9agt%%OKBrHX{;@@-OBftV64To<17!$wUNGjQlHx?x0dhi z6UJ(3$LR>mttY)>Qn^mbZQy(7#IZs@%dJhsYeg^l)JxThKXpO2AgrB5FgL#-veg3H{(JKJoge`w)yvy zf3PUOHzEIa_Oxb1&XPZ2{Yo?V$t=a*wK&+n8Mnh|4elJ5T*r5G%+A`qDudru{rZB9 zU+33{Gx_C=GphK#$;$aJr2hIw>t}_0_pR;W1oz7Ch@6m2$9_5cZ+6X9Y>(N0bKl(k z^>Os7LvG(_``#>T-OZzkT=u!98~00Are3n;@CCyMJZ)yrn~A+YcBJOH8*dyMjqlCo zO)findRumMB%4LAPFUFOh*SZ$81FSVw{!M)iBqPtPw;7-g{>|Aru?i!-{5=6vKd#5 z$`AbmtVb8b7uBde$>#pq#^U|aZ{4^bn1TDqy^)UU#>cSTqaR;LoXb+Klza*05Aen` zKld^;p6{p*?Ei^JvCCKGzkWnKvpoOxO$HOk`&-SwjMA^N{MSdq_kXo_e&fg8whY@& zy4}1VU!S$qUuN5x#hy5AXz#(cgDj#?OKB^a&mS+e)%b5~OXv4Yh2l;H@NneIH#QNb2?wP-AYYX~!F*tCqn7G2nm8T%}GmlwgdjqxrYhwUvN55^0h zv9LWk3AU#v!Pa!9yPP<1ZI^Bvwo&#K^sJ&b*3t&pQ-JBhfBHAJQL4Qh>2O~eH3|Mb zKLwmBLpw_f{H%l*_%Z2}6+BlcUjTn}h*PpJj&8HCt(*i~d`l<5cGy^4P5<|wbsd2& zv=^=QLC+rS<==R2^`@%8*?>R3iT6;#cW~|LA z>*DiGKJ*xqzK`|6j{G_0!>;bs*BM8AjCF0h=vFi<+eJXD(OPgRpu^#4ndr&RIrPOG z5|eF=KGut7L_d7*)OX>W@Zjh!OK0#`)4?2c3LorTLuUakEm)?7{neR?mVEuAf_2-fUwt&d)BW5sQx%&=Rs;)>_z~AqE|EBI zZO3Re(BO_=p3puAuonI{!~eL~WV9LH$Nevk zFWuuwbc@0sZ=id8@Q8E|yO*Xtk;2|iE{Z;fUESETx9z=$oO0}Gm0sVU#k`&9U+gyx zI%YL_)_!}ZX-~Qbz9-ueI=TEio4rQUo{O??X`nyXsh?opUw4hW_qff*!64jzerYo_^2J<4kt<<8l)Ejhw4IG9yX3- zyH|1-^uoYtlXXQixXr zMfnEX#L3*^Xuqe>gb2; z`F{Ao^O{HMkPM$eSzlxKALPe5#KL}>{Lb`E`Y3)pN=p={!MEr5OMjoIB$gm>(|SBT z?NC>8+Cz(NABINv!xKEskIHUYZ4OgE@O^VddYcm$AArU;WEN8X)-T7z6GFXWE6*L> zH?qIv8~Cy5%UosJ$!FoM{ZRIr)~A~A?E~IDKXA(%hezAGXDsRxoz}(Kle&&ry7!GB zQ%9TSg9Pqzo8QIcgb~pOa#4@Lxz31~;{^?sMW!~anz8bId z-wrMX^RmOlCgT!qEYHk0g9}6>6ULK2JYhV;`Tduc&1>IUb_@ApohbMx6nLA?lZl=! ze`75#{?__zNrU$5Wy?>x|NZCk4`2*c@UGJO5ewTGylsxwnSS5>X4#$?XO-rCfOf2Z zkJ_4iPI|H~pmUp+m+lVt0P$%=o_SiMB;CLMzQvsbrcd(k?> zL-~oP>f7OMjaCkqsEl0$ixximchFSltej&SI!(g}dcz21me+rtb+U~moj;-cel(OH z&4Fyu**NOe{sl55+U_-dbh+^A+r##ZVHA0y^jNTGm_Llp<%?G*BY!djIM}_GVtzw}$4Hgk{-rM(9>rJy$tU-agB*59Is zWaZog#2+bDy5&=qb06hBX5aDUC4IZ-$-)6$LB1ihKO=>Ya?*Wvc1T}rCIes9A>LCt zcb#~K-Z{UAkLKLl`HyL>s&Bk677Pmb^i*+-!SV5xkBtx9(jKpHOJmpgv<4P#3Fjo= z#N)g@e-zVs*rfa2`@(*0Tkt-+&sv!&`QkR~lY*}-`KnZpH%edJ@2&{*>Ri_BkxG2? zHqM@#_uI{XJoPjAklOVs-=hb2&90GeDf8aIJAS5PdFJwt{j=RP4wyL4W#Mx<&*d7c z-mQ!d^o5qmxSfkY%vRn+#-^~~*Fj1MGxUdYgBYVillv%C18 zar3+;lOLpB`kjC4KltD+eGdKuf2-V8@Gs6z6xzdPu$6DF_SShmapQfQnZF_Ojk>GM zmEv`E3ECUT4~Un^p9mb!YHo*D<&Rk%1OH&lH`x2r+%m6zW-T#R9!8INfU!0k#neZK za~|IW4+bt*p}%hR>7@4)6VhmEh1E;lID<-Z#9zTi@dE02W0)f80HR&gInTyVnga zBS(6k{kHga5Kkv(W2v9W%`)-&?Zi?;)(SqoD|MEJJ37Ah{12Fmx#&*u`dt1k%`JOm zF=)WI{Eu-z2|UDC;WO>I3gG!Q;E6texjtUnKa-X2Cp{c^b;$pEehy#!Q{V1d)*ADq z@7Obs^j+sMkmp~reg?j&nE%)Cv4LIX>96fI^Z!-&kv{==t7zNug`UIT?()99e!`tm zq%W_h{;&Md#CTrHxTF&|^DkM{z`y)DYo#v+bCy4ioh3RpPY3cRyVr5I+85_^)y*RQ z%K}pZJd+kC=#-+70!)N|WBfqAg6Pf`XYe5x&UmK+Uq9)EmLK3(>Fv3r1|LeRS4wv3 zyZ0ix`<^@OJ*R?CxMn>e0z+?VdW5Neu-W3Sa!n&Px5bIidCLs08`am`@M|Nz?Vd{ksb?MA=V-~x>8f2mKkI(C@ zhhm%TaK#UF9X?lQWO3^DCG$*1(wt<_zBv&cU_gyRjA@jtw48?ro zf4|9pEpw-TE_17YDl-Q?*`=TBOw`}S_=%I+d%wl8Xa-#KUnPw-Dt-rsed%a6a?jlC zqSzZ-dcnOp_tf-9?y1c_e2z8nNc&huK29b0 zeVt?-6=mPyWOACf!dp|qWdP(2>Ep6IP�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

49dmX%yrNy&2{X?ZD^>u1 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 z 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

0E5`EByZwD>aflh?V!$0x({G?`tU5M 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 WMj&g2{Ek~h@1wvo+J&9~ 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[z99ocUZRjv0+d(syDUGxd+DvwT`wSWA& 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 z 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

kFf&K7#HBK7#JL7*A6cUEM7>$v64P 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%0A^VjNZoq}`g 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

?sX6K+y)O?ZFD{xoCOck*oRLu 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℘@T)R!P}T~wE;d(pA3L2=qik1?j5>R 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�ZOH#^k90J^ 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 miYUDNbo_*;MI0 + +CWD="`(cd \"\`dirname \\\"$0\\\"\`\"; echo $PWD)`" + +ps -wx -ocommand | grep -e '[X]11' > dev/null +if [ "$?" != "0" -a ! -f ~/.xinitrc ]; then + echo "rm -f ~/.xinitrc" > ~/.xinitrc + sed 's/xterm/# xterm/' /usr/X11R6/lib/X11/xinit/xinitrc >> ~/.xinitrc +fi + +open -a X11 || open -a XDarwin + +export "FONTCONFIG_PATH=$CWD/etc/fonts" +exec "$CWD/bin/cache-fonts" diff --git a/tools/osx_packaging/openDoc b/tools/osx_packaging/openDoc new file mode 100755 index 0000000000..888a42b176 --- /dev/null +++ b/tools/osx_packaging/openDoc @@ -0,0 +1,6 @@ +#!/bin/sh +# +# Author: Aaron Voisine + +export "DISPLAY=`cat /tmp/$UID/TemporaryItems/display`" +exec "`dirname \"$0\"`/bin/gimp-remote" "$@" diff --git a/tools/osx_packaging/script b/tools/osx_packaging/script new file mode 100755 index 0000000000..d689320d20 --- /dev/null +++ b/tools/osx_packaging/script @@ -0,0 +1,27 @@ +#!/bin/sh +# +# Author: Aaron Voisine + +CWD="`dirname \"$0\"`" +TMP=/tmp/$UID/TemporaryItems + +ps -wx -ocommand | grep -e '[X]11' > /dev/null +if [ "$?" != "0" -a ! -f ~/.xinitrc ]; then + echo "rm -f ~/.xinitrc" > ~/.xinitrc + sed 's/xterm/# xterm/' /usr/X11R6/lib/X11/xinit/xinitrc >> ~/.xinitrc +fi + +mkdir -p $TMP +cp -f "$CWD/bin/getdisplay.sh" $TMP +rm -f $TMP/display +open-x11 $TMP/getdisplay.sh || \ +open -a XDarwin $TMP/getdisplay.sh || \ +echo ":0" > $TMP/display + +while [ "$?" == "0" -a ! -f $TMP/display ]; do sleep 1; done +export "DISPLAY=`cat $TMP/display`" + +ps -wx -ocommand | grep -e '[X]11' > /dev/null || exit 11 + +cd ~/ +exec "$CWD/bin/exporter" "$@" From 5b289d30061a5b82b7c9dfb5a69b06c4da4b69ba Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Thu, 29 Jun 2006 18:45:41 +0000 Subject: [PATCH 09/27] r115@gandalf: fugalh | 2006-06-23 12:36:05 -0600 pass the object instead of an id git-svn-id: svn://localhost/ardour2/branches/undo@654 d708f5d6-7413-0410-9779-e7cbd77b26cf --- libs/pbd3/pbd/undo_command.h | 35 +++++++++++++++++------------------ 1 file changed, 17 insertions(+), 18 deletions(-) diff --git a/libs/pbd3/pbd/undo_command.h b/libs/pbd3/pbd/undo_command.h index 26550650be..1c9cac7684 100644 --- a/libs/pbd3/pbd/undo_command.h +++ b/libs/pbd3/pbd/undo_command.h @@ -38,7 +38,7 @@ using std::string; /* One of the joys of templates is that you have to do everything right here * in the header file; you can't split this to make undo_command.cc */ -template +template class UndoCommand { public: @@ -47,39 +47,39 @@ class UndoCommand * * UndoCommand cmd(id, key, foo_instance); */ - UndoCommand(id_t object_id, string key) - : _obj_id(object_id), _key(key) + UndoCommand(T_obj &object, string key) + : _obj(object), _key(key) { - _slot = mem_fun( get_object(object_id), get_method(key) ); + _slot = mem_fun( _obj, get_method(_key) ); } - UndoCommand(id_t object_id, string key, T1 &arg1) - : _obj_id(object_id), _key(key) + UndoCommand(T_obj &object, string key, T1 &arg1) + : _obj(object), _key(key) { - _slot = bind( mem_fun( get_object(object_id), get_method(key) ), + _slot = bind( mem_fun( _obj, get_method(_key) ), arg1); _args.push_back(&arg1); } - UndoCommand(id_t object_id, string key, T1 &arg1, T2 &arg2) - : _obj_id(object_id), _key(key) + UndoCommand(T_obj &object, string key, T1 &arg1, T2 &arg2) + : _obj(object), _key(key) { - _slot = bind( mem_fun( get_object(object_id), get_method(key) ), + _slot = bind( mem_fun( _obj, get_method(_key) ), arg1, arg2); _args.push_back(&arg1); _args.push_back(&arg2); } - UndoCommand(id_t object_id, string key, T1 &arg1, T2 &arg2, T3 &arg3) - : _obj_id(object_id), _key(key) + UndoCommand(T_obj &object, string key, T1 &arg1, T2 &arg2, T3 &arg3) + : _obj(object), _key(key) { - _slot = bind( mem_fun( get_object(object_id), get_method(key) ), + _slot = bind( mem_fun( _obj, get_method(_key) ), arg1, arg2, arg3); _args.push_back(&arg1); _args.push_back(&arg2); _args.push_back(&arg3); } - UndoCommand(id_t object_id, string key, T1 &arg1, T2 &arg2, T3 &arg3, T4 &arg4) - : _obj_id(object_id), _key(key) + UndoCommand(T_obj &object, string key, T1 &arg1, T2 &arg2, T3 &arg3, T4 &arg4) + : _obj(object), _key(key) { - _slot = bind( mem_fun( get_object(object_id), get_method(key) ), + _slot = bind( mem_fun( _obj, get_method(_key) ), arg1, arg2, arg4); _args.push_back(&arg1); _args.push_back(&arg2); @@ -91,9 +91,8 @@ class UndoCommand XMLNode &serialize(); protected: - template T_object &get_object(id_t); template T_method &get_method(string); - id_t _obj_id; + T_obj &_obj; string _key; slot _slot; From 6337a1894cb146fcfba9454c0cb41b6bdb3fced1 Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Thu, 29 Jun 2006 18:49:03 +0000 Subject: [PATCH 10/27] r132@gandalf: fugalh | 2006-06-29 12:45:16 -0600 Coding for undo/redo starts in earnest. Paul and I decided to go with a standard gang of four Command pattern, with serialization. This overcomes the terrible difficulties we were having with static type checking and the sigc++ approach. I'm adding the requirement that each command support undo, simplifying undo/redo. NOTE that an important fallout here is that Command::operator()() is the opposite of the old UndoAction::operator()(), i.e. Command::operator()() is execute/redo, and Command::undo() is undo. This commit is a reworking of the infrastructure, and won't compile until creating Command subclasses for the various commands being performed. That is primarily where you find get_memento and/or calls to add_(undo|redo.*). git-svn-id: svn://localhost/ardour2/branches/undo@655 d708f5d6-7413-0410-9779-e7cbd77b26cf --- libs/pbd3/pbd/command.h | 37 +++++++++++++ libs/pbd3/pbd/serializable.h | 2 +- libs/pbd3/pbd/undo.h | 15 ++--- libs/pbd3/pbd/undo_command.h | 104 ----------------------------------- libs/pbd3/undo.cc | 46 ++++++---------- 5 files changed, 62 insertions(+), 142 deletions(-) create mode 100644 libs/pbd3/pbd/command.h delete mode 100644 libs/pbd3/pbd/undo_command.h diff --git a/libs/pbd3/pbd/command.h b/libs/pbd3/pbd/command.h new file mode 100644 index 0000000000..b154c6b148 --- /dev/null +++ b/libs/pbd3/pbd/command.h @@ -0,0 +1,37 @@ +/* + Copyright (C) 2006 Hans Fugal & Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + + $Id: /local/undo/libs/pbd3/pbd/undo.h 80 2006-06-22T22:37:01.079855Z fugalh $ +*/ + +#ifndef __lib_pbd_undo_h__ +#define __lib_pbd_undo_h__ + +#include + +class Command : public Serializable +{ + public: + virtual ~Command(); + virtual void operator() () = 0; + virtual void undo() = 0; + virtual void redo() { (*this)(); } + protected: + Command(); +}; + +#endif diff --git a/libs/pbd3/pbd/serializable.h b/libs/pbd3/pbd/serializable.h index 8032f0038a..c0948b9933 100644 --- a/libs/pbd3/pbd/serializable.h +++ b/libs/pbd3/pbd/serializable.h @@ -26,7 +26,7 @@ class Serializable { public: - XMLNode &serialize(); + virtual XMLNode &serialize() = 0; }; #endif // __lib_pbd_serializable_h__ diff --git a/libs/pbd3/pbd/undo.h b/libs/pbd3/pbd/undo.h index d2ad6088cd..b97c8d9249 100644 --- a/libs/pbd3/pbd/undo.h +++ b/libs/pbd3/pbd/undo.h @@ -27,14 +27,14 @@ #include #include #include -#include +#include using std::string; using std::list; -typedef sigc::slot UndoAction; +typedef Command UndoAction; -class UndoTransaction +class UndoTransaction : public Command { public: UndoTransaction (); @@ -43,12 +43,10 @@ class UndoTransaction void clear (); - void add_undo (const UndoAction&); - void add_redo (const UndoAction&); - void add_redo_no_execute (const UndoAction&); + void add_command (const UndoAction&); + void operator() (); void undo(); - void redo(); void set_name (const string& str) { _name = str; @@ -64,8 +62,7 @@ class UndoTransaction } private: - list redo_actions; - list undo_actions; + list actions; struct timeval _timestamp; string _name; }; diff --git a/libs/pbd3/pbd/undo_command.h b/libs/pbd3/pbd/undo_command.h deleted file mode 100644 index 1c9cac7684..0000000000 --- a/libs/pbd3/pbd/undo_command.h +++ /dev/null @@ -1,104 +0,0 @@ -/* - Copyright (C) 2006 Paul Davis - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id: /local/undo/libs/pbd3/pbd/undo.h 59 2006-06-15T18:16:20.960977Z fugalh $ -*/ - -#ifndef __lib_pbd_undo_command_h__ -#define __lib_pbd_undo_command_h__ - -#include -#include -#include -#include -#include - -using sigc::nil; -using sigc::slot; -using sigc::bind; -using sigc::mem_fun; -using std::list; -using std::string; - - -/* One of the joys of templates is that you have to do everything right here - * in the header file; you can't split this to make undo_command.cc */ - -template -class UndoCommand -{ - public: - /* It only makes sense to use the constructor corresponding to the - * template given. e.g. - * - * UndoCommand cmd(id, key, foo_instance); - */ - UndoCommand(T_obj &object, string key) - : _obj(object), _key(key) - { - _slot = mem_fun( _obj, get_method(_key) ); - } - UndoCommand(T_obj &object, string key, T1 &arg1) - : _obj(object), _key(key) - { - _slot = bind( mem_fun( _obj, get_method(_key) ), - arg1); - _args.push_back(&arg1); - } - UndoCommand(T_obj &object, string key, T1 &arg1, T2 &arg2) - : _obj(object), _key(key) - { - _slot = bind( mem_fun( _obj, get_method(_key) ), - arg1, arg2); - _args.push_back(&arg1); - _args.push_back(&arg2); - } - UndoCommand(T_obj &object, string key, T1 &arg1, T2 &arg2, T3 &arg3) - : _obj(object), _key(key) - { - _slot = bind( mem_fun( _obj, get_method(_key) ), - arg1, arg2, arg3); - _args.push_back(&arg1); - _args.push_back(&arg2); - _args.push_back(&arg3); - } - UndoCommand(T_obj &object, string key, T1 &arg1, T2 &arg2, T3 &arg3, T4 &arg4) - : _obj(object), _key(key) - { - _slot = bind( mem_fun( _obj, get_method(_key) ), - arg1, arg2, arg4); - _args.push_back(&arg1); - _args.push_back(&arg2); - _args.push_back(&arg3); - _args.push_back(&arg4); - } - - void operator() () { return _slot(); } - - XMLNode &serialize(); - protected: - template T_method &get_method(string); - T_obj &_obj; - string _key; - slot _slot; - - // Note that arguments must be instances of Serializable or this will - // rightly cause a compiler error when compiling the constructor. - list _args; -}; - -#endif // __lib_pbd_undo_command_h__ diff --git a/libs/pbd3/undo.cc b/libs/pbd3/undo.cc index 0aac58effc..0a09ffd1e7 100644 --- a/libs/pbd3/undo.cc +++ b/libs/pbd3/undo.cc @@ -33,8 +33,7 @@ UndoTransaction::UndoTransaction (const UndoTransaction& rhs) { _name = rhs._name; clear (); - undo_actions.insert(undo_actions.end(),rhs.undo_actions.begin(),rhs.undo_actions.end()); - redo_actions.insert(redo_actions.end(),rhs.redo_actions.begin(),rhs.redo_actions.end()); + actions.insert(actions.end(),rhs.actions.begin(),rhs.actions.end()); } UndoTransaction& @@ -43,43 +42,36 @@ UndoTransaction::operator= (const UndoTransaction& rhs) if (this == &rhs) return *this; _name = rhs._name; clear (); - undo_actions.insert(undo_actions.end(),rhs.undo_actions.begin(),rhs.undo_actions.end()); - redo_actions.insert(redo_actions.end(),rhs.redo_actions.begin(),rhs.redo_actions.end()); + actions.insert(actions.end(),rhs.actions.begin(),rhs.actions.end()); return *this; } void -UndoTransaction::add_undo (const UndoAction& action) +UndoTransaction::add_command (const UndoAction& action) { - undo_actions.push_back (action); -} - -void -UndoTransaction::add_redo (const UndoAction& action) -{ - redo_actions.push_back (action); - redo_actions.back()(); // operator() -} - -void -UndoTransaction::add_redo_no_execute (const UndoAction& action) -{ - redo_actions.push_back (action); + actions.push_back (action); } void UndoTransaction::clear () { - undo_actions.clear (); - redo_actions.clear (); + actions.clear (); +} + +void +UndoTransaction::operator() () +{ + for (list::iterator i = actions.begin(); i != actions.end(); ++i) { + (*i)(); + } } void UndoTransaction::undo () { cerr << "Undo " << _name << endl; - for (list::reverse_iterator i = undo_actions.rbegin(); i != undo_actions.rend(); ++i) { - (*i)(); + for (list::reverse_iterator i = actions.rbegin(); i != actions.rend(); ++i) { + i->undo(); } } @@ -87,9 +79,7 @@ void UndoTransaction::redo () { cerr << "Redo " << _name << endl; - for (list::iterator i = redo_actions.begin(); i != redo_actions.end(); ++i) { - (*i)(); - } + (*this)(); } void @@ -119,9 +109,9 @@ UndoHistory::redo (unsigned int n) if (RedoList.size() == 0) { return; } - UndoTransaction trans = RedoList.back (); + UndoTransaction ut = RedoList.back (); RedoList.pop_back (); - trans.redo (); + ut.redo (); UndoList.push_back (trans); } } From 21af0d4ae2cf97bab7f462a0a1bf09ba8883c6e5 Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Fri, 30 Jun 2006 17:23:12 +0000 Subject: [PATCH 11/27] r154@gandalf: fugalh | 2006-06-30 11:16:27 -0600 fixed guard defines git-svn-id: svn://localhost/ardour2/branches/undo@660 d708f5d6-7413-0410-9779-e7cbd77b26cf --- libs/pbd3/pbd/command.h | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/libs/pbd3/pbd/command.h b/libs/pbd3/pbd/command.h index b154c6b148..89b358a770 100644 --- a/libs/pbd3/pbd/command.h +++ b/libs/pbd3/pbd/command.h @@ -18,8 +18,8 @@ $Id: /local/undo/libs/pbd3/pbd/undo.h 80 2006-06-22T22:37:01.079855Z fugalh $ */ -#ifndef __lib_pbd_undo_h__ -#define __lib_pbd_undo_h__ +#ifndef __lib_pbd_command_h__ +#define __lib_pbd_command_h__ #include @@ -34,4 +34,4 @@ class Command : public Serializable Command(); }; -#endif +#endif // __lib_pbd_command_h_ From a5386f8d59d595e930c1d179e0eb0fabc60a7c84 Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Fri, 30 Jun 2006 17:24:16 +0000 Subject: [PATCH 12/27] r155@gandalf: fugalh | 2006-06-30 11:21:45 -0600 MementoCommand - for the lazy at heart git-svn-id: svn://localhost/ardour2/branches/undo@661 d708f5d6-7413-0410-9779-e7cbd77b26cf --- libs/pbd3/pbd/memento_command.h | 54 +++++++++++++++++++++++++++++++++ 1 file changed, 54 insertions(+) create mode 100644 libs/pbd3/pbd/memento_command.h diff --git a/libs/pbd3/pbd/memento_command.h b/libs/pbd3/pbd/memento_command.h new file mode 100644 index 0000000000..6ecacf6d67 --- /dev/null +++ b/libs/pbd3/pbd/memento_command.h @@ -0,0 +1,54 @@ +/* + Copyright (C) 2006 Hans Fugal & Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + + $Id: /local/undo/libs/pbd3/pbd/undo.h 132 2006-06-29T18:45:16.609763Z fugalh $ +*/ + +#ifndef __lib_pbd_memento_command_h__ +#define __lib_pbd_memento_command_h__ + +#include +#include + +// TODO: make a macro to make constructing this even easier +template +class MementoCommand : public Command +{ + public: + MementoCommand(obj_T obj, + sigc::slot action, + std::string key + std::list args + ) + : obj(obj), action(action), key(key), args(args), memento(obj.get_memento()) {} + void operator() () { action(); } + void undo() { obj.set_memento(memento); } + virtual XMLNode &serialize() + { + // obj.id + // key + // args + } + protected: + obj_T &obj; + mem_T memento; + sigc::slot action; + std::string key; + std::list args; +}; + +#endif // __lib_pbd_memento_h__ From ab1b29bcb265404a3a31cd888c768b910c79fd77 Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Thu, 6 Jul 2006 18:25:58 +0000 Subject: [PATCH 13/27] r162@gandalf: fugalh | 2006-06-30 19:30:58 -0600 some macros for MementoCommand() git-svn-id: svn://localhost/ardour2/branches/undo@666 d708f5d6-7413-0410-9779-e7cbd77b26cf --- libs/pbd3/pbd/memento_command.h | 44 ++++++++++++++++++++++++++++++++- 1 file changed, 43 insertions(+), 1 deletion(-) diff --git a/libs/pbd3/pbd/memento_command.h b/libs/pbd3/pbd/memento_command.h index 6ecacf6d67..4b541a2327 100644 --- a/libs/pbd3/pbd/memento_command.h +++ b/libs/pbd3/pbd/memento_command.h @@ -24,7 +24,28 @@ #include #include -// TODO: make a macro to make constructing this even easier +#define MEMENTO_COMMAND(obj_T, mem_T, obj, meth) \ + (MementoCommand<(obj_T),(mem_T)>((obj),sigc::mem_fun((obj),&(meth)),#meth)) + +#define MEMENTO_COMMAND_1(obj_T, mem_T, obj, meth, arg1) \ + (MementoCommand<(obj_T),(mem_T)>((obj),\ + sigc::bind(sigc::mem_fun((obj),\ + &(meth)),\ + arg1),#meth)) + +#define MEMENTO_COMMAND_2(obj_T, mem_T, obj, meth, arg1, arg2) \ + (MementoCommand<(obj_T),(mem_T)>((obj),\ + sigc::bind(sigc::mem_fun((obj),\ + &(meth)),\ + arg1, arg2),#meth)) + +#define MEMENTO_COMMAND_3(obj_T, mem_T, obj, meth, arg1, arg2, arg3) \ + (MementoCommand<(obj_T),(mem_T)>((obj),\ + sigc::bind(sigc::mem_fun((obj),\ + &(meth)),\ + arg1, arg2, arg3),#meth)) + + template class MementoCommand : public Command { @@ -35,6 +56,27 @@ class MementoCommand : public Command std::list args ) : obj(obj), action(action), key(key), args(args), memento(obj.get_memento()) {} + MementoCommand(obj_T obj, + sigc::slot action, + std::string key + Serializable *arg1 = 0, + Serializable *arg2 = 0, + Serializable *arg3 = 0 + ) + : obj(obj), action(action), key(key), memento(obj.get_memento()) + { + if (arg1 == 0) + return; + args.push_back(arg1); + + if (arg2 == 0) + return; + args.push_back(arg2); + + if (arg3 == 0) + return; + args.push_back(arg3); + } void operator() () { action(); } void undo() { obj.set_memento(memento); } virtual XMLNode &serialize() From 0bd3b0b6700c6bc10c5f2a1322f396db9dac8526 Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Tue, 11 Jul 2006 22:29:39 +0000 Subject: [PATCH 14/27] r168@gandalf: fugalh | 2006-07-11 16:29:22 -0600 I just had an epiphany. I tried so many ways to make saving function name and args work, it never occured to me that you could just as easily save undo information as a pair of mementos, even in the Command-based structure we agreed on. Since many (read: almost all) existing undo commands take this form: begin_reversible_command (_("change fade in length")); session->add_undo (arv->region.get_memento()); arv->region.set_fade_in_length (fade_length); session->add_redo_no_execute (arv->region.get_memento()); commit_reversible_command (); We are already doing the save a memento before and after work. All we need to do is instantiate an appropriate instance of MementoCommand. So the above becomes: begin_reversible_command (_("change fade in length")); MementoCommand before, after; before = arv->region.get_memento(); arv->region.set_fade_in_length (fade_length); after = arv->region.get_memento(); session->add_command(arv->region, before, after); commit_reversible_command (); (With apologies for being too lazy to go look up what arv_region_t and arv_region_memento_t are) Note that the true command approach is still possible, and encouraged (both by dictate and design). git-svn-id: svn://localhost/ardour2/branches/undo@680 d708f5d6-7413-0410-9779-e7cbd77b26cf --- libs/pbd3/pbd/memento_command.h | 65 +++++---------------------------- 1 file changed, 9 insertions(+), 56 deletions(-) diff --git a/libs/pbd3/pbd/memento_command.h b/libs/pbd3/pbd/memento_command.h index 4b541a2327..adeb61659a 100644 --- a/libs/pbd3/pbd/memento_command.h +++ b/libs/pbd3/pbd/memento_command.h @@ -24,73 +24,26 @@ #include #include -#define MEMENTO_COMMAND(obj_T, mem_T, obj, meth) \ - (MementoCommand<(obj_T),(mem_T)>((obj),sigc::mem_fun((obj),&(meth)),#meth)) - -#define MEMENTO_COMMAND_1(obj_T, mem_T, obj, meth, arg1) \ - (MementoCommand<(obj_T),(mem_T)>((obj),\ - sigc::bind(sigc::mem_fun((obj),\ - &(meth)),\ - arg1),#meth)) - -#define MEMENTO_COMMAND_2(obj_T, mem_T, obj, meth, arg1, arg2) \ - (MementoCommand<(obj_T),(mem_T)>((obj),\ - sigc::bind(sigc::mem_fun((obj),\ - &(meth)),\ - arg1, arg2),#meth)) - -#define MEMENTO_COMMAND_3(obj_T, mem_T, obj, meth, arg1, arg2, arg3) \ - (MementoCommand<(obj_T),(mem_T)>((obj),\ - sigc::bind(sigc::mem_fun((obj),\ - &(meth)),\ - arg1, arg2, arg3),#meth)) - - template class MementoCommand : public Command { public: - MementoCommand(obj_T obj, - sigc::slot action, - std::string key - std::list args + MementoCommand(obj_T &obj, + mem_T before, + mem_T after ) - : obj(obj), action(action), key(key), args(args), memento(obj.get_memento()) {} - MementoCommand(obj_T obj, - sigc::slot action, - std::string key - Serializable *arg1 = 0, - Serializable *arg2 = 0, - Serializable *arg3 = 0 - ) - : obj(obj), action(action), key(key), memento(obj.get_memento()) - { - if (arg1 == 0) - return; - args.push_back(arg1); - - if (arg2 == 0) - return; - args.push_back(arg2); - - if (arg3 == 0) - return; - args.push_back(arg3); - } - void operator() () { action(); } - void undo() { obj.set_memento(memento); } + : obj(obj), before(before), after(after) {} + void operator() () { obj.set_memento(after); } + void undo() { obj.set_memento(before); } virtual XMLNode &serialize() { // obj.id - // key - // args + // key is "MementoCommand" or something + // before and after mementos } protected: obj_T &obj; - mem_T memento; - sigc::slot action; - std::string key; - std::list args; + mem_T before, after; }; #endif // __lib_pbd_memento_h__ From 72168803ee845adef9743fd24421b9719a0901b0 Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Tue, 18 Jul 2006 17:46:20 +0000 Subject: [PATCH 15/27] r183@gandalf: fugalh | 2006-07-17 19:01:39 -0600 Use XMLNode instead of templating memento types. git-svn-id: svn://localhost/ardour2/branches/undo@683 d708f5d6-7413-0410-9779-e7cbd77b26cf --- libs/pbd3/pbd/memento_command.h | 13 +++++++++---- 1 file changed, 9 insertions(+), 4 deletions(-) diff --git a/libs/pbd3/pbd/memento_command.h b/libs/pbd3/pbd/memento_command.h index adeb61659a..c9952c443c 100644 --- a/libs/pbd3/pbd/memento_command.h +++ b/libs/pbd3/pbd/memento_command.h @@ -24,13 +24,17 @@ #include #include -template +/** This command class is initialized with before and after mementos + * (from Stateful::get_state()), so undo becomes restoring the before + * memento, and redo is restoring the after memento. + */ +template class MementoCommand : public Command { public: MementoCommand(obj_T &obj, - mem_T before, - mem_T after + XMLNode &before, + XMLNode &after ) : obj(obj), before(before), after(after) {} void operator() () { obj.set_memento(after); } @@ -41,9 +45,10 @@ class MementoCommand : public Command // key is "MementoCommand" or something // before and after mementos } + // TODO does this need a copy constructor? protected: obj_T &obj; - mem_T before, after; + XMLNode &before, &after; }; #endif // __lib_pbd_memento_h__ From d819b922e1d858dc3addbe31962d12af64027e50 Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Tue, 18 Jul 2006 17:47:12 +0000 Subject: [PATCH 16/27] r184@gandalf: fugalh | 2006-07-17 19:02:10 -0600 (begin|commit)_reversible_command in Editor and Session git-svn-id: svn://localhost/ardour2/branches/undo@684 d708f5d6-7413-0410-9779-e7cbd77b26cf --- gtk2_ardour/editor.cc | 12 ++++++++---- gtk2_ardour/editor.h | 1 + libs/ardour/ardour/session.h | 4 ++-- libs/ardour/session_state.cc | 12 ++++-------- 4 files changed, 15 insertions(+), 14 deletions(-) diff --git a/gtk2_ardour/editor.cc b/gtk2_ardour/editor.cc index 08c716d442..0b9359bae7 100644 --- a/gtk2_ardour/editor.cc +++ b/gtk2_ardour/editor.cc @@ -2970,8 +2970,8 @@ void Editor::begin_reversible_command (string name) { if (session) { - UndoAction ua = get_memento(); - session->begin_reversible_command (name, &ua); + before = get_state(); + session->begin_reversible_command (name); } } @@ -2979,8 +2979,12 @@ void Editor::commit_reversible_command () { if (session) { - UndoAction ua = get_memento(); - session->commit_reversible_command (&ua); + // yes, cmd lasts long enough to be copied onto the action + // list in the history, but this has the potential to be a + // problem if memory management of actions changes in + // UndoTransaction + MementoCommand cmd(*this, before, get_state()); + session->commit_reversible_command (&cmd); } } diff --git a/gtk2_ardour/editor.h b/gtk2_ardour/editor.h index e517b1eaf1..2ef475a5e4 100644 --- a/gtk2_ardour/editor.h +++ b/gtk2_ardour/editor.h @@ -1608,6 +1608,7 @@ class Editor : public PublicEditor UndoAction get_memento() const; + XMLNode &before; /* used in *_reversible_command */ void begin_reversible_command (string cmd_name); void commit_reversible_command (); diff --git a/libs/ardour/ardour/session.h b/libs/ardour/ardour/session.h index 971e141363..ba12b79f48 100644 --- a/libs/ardour/ardour/session.h +++ b/libs/ardour/ardour/session.h @@ -841,8 +841,8 @@ class Session : public sigc::trackable, public Stateful string next_undo() const { return history.next_undo(); } string next_redo() const { return history.next_redo(); } - void begin_reversible_command (string cmd_name, UndoAction *private_undo = 0); - void commit_reversible_command (UndoAction* private_redo = 0); + void begin_reversible_command (string cmd_name); + void commit_reversible_command (Command* cmd = 0); void add_undo (const UndoAction& ua) { current_trans.add_undo (ua); diff --git a/libs/ardour/session_state.cc b/libs/ardour/session_state.cc index 92a21ea794..deda3363ab 100644 --- a/libs/ardour/session_state.cc +++ b/libs/ardour/session_state.cc @@ -2564,23 +2564,19 @@ Session::set_meter_falloff (float val) void -Session::begin_reversible_command (string name, UndoAction* private_undo) +Session::begin_reversible_command (string name) { current_trans.clear (); current_trans.set_name (name); - - if (private_undo) { - current_trans.add_undo (*private_undo); - } } void -Session::commit_reversible_command (UndoAction* private_redo) +Session::commit_reversible_command (Command *cmd) { struct timeval now; - if (private_redo) { - current_trans.add_redo_no_execute (*private_redo); + if (cmd) { + current_trans.add_command (*cmd); } gettimeofday (&now, 0); From 55159005b925396eeb41529f6e5b1d998fe63dc2 Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Tue, 18 Jul 2006 23:54:31 +0000 Subject: [PATCH 17/27] r189@gandalf: fugalh | 2006-07-18 17:54:25 -0600 This is the first swath of changes, replacing add_undo with MementoCommand pattern, through most of the editor_mouse.cc file. However there were a few places that weren't symmetrical that I need to think about. The question is whether to tweak things so that they are symmetrical (add_undo paired with add_redo*), or to allow Commands to not be undoable or not be redoable. Your thoughts are welcome. git-svn-id: svn://localhost/ardour2/branches/undo@685 d708f5d6-7413-0410-9779-e7cbd77b26cf --- gtk2_ardour/editor_mouse.cc | 93 +++++++++++++++++++++++---------- libs/ardour/ardour/session.h | 10 +--- libs/pbd3/pbd/memento_command.h | 4 +- 3 files changed, 69 insertions(+), 38 deletions(-) diff --git a/gtk2_ardour/editor_mouse.cc b/gtk2_ardour/editor_mouse.cc index 6c2919f5dd..e4d8ec6ce6 100644 --- a/gtk2_ardour/editor_mouse.cc +++ b/gtk2_ardour/editor_mouse.cc @@ -1812,9 +1812,15 @@ Editor::fade_in_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* even } begin_reversible_command (_("change fade in length")); - session->add_undo (arv->region.get_memento()); + XMLNode &before, &after; + before = arv->region.get_state(); + arv->region.set_fade_in_length (fade_length); - session->add_redo_no_execute (arv->region.get_memento()); + + after = arv->region.get_state(); + session->add_command(MementoCommand(arv->region, + before, + after)); commit_reversible_command (); fade_in_drag_motion_callback (item, event); } @@ -1904,9 +1910,13 @@ Editor::fade_out_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* eve } begin_reversible_command (_("change fade out length")); - session->add_undo (arv->region.get_memento()); + XMLNode &before, &after; + before = arv->region.get_state(); + arv->region.set_fade_out_length (fade_length); - session->add_redo_no_execute (arv->region.get_memento()); + + after = arv->region.get_state(); + session->add_command(MementoCommand(arv->region, before, after)); commit_reversible_command (); fade_out_drag_motion_callback (item, event); @@ -2140,7 +2150,8 @@ Editor::marker_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event begin_reversible_command ( _("move marker") ); - session->add_undo( session->locations()->get_memento() ); + XMLNode &before, &after; + before = session->locations()->get_state(); Location * location = find_location_from_marker (marker, is_start); @@ -2148,7 +2159,8 @@ Editor::marker_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event location->set (drag_info.copied_location->start(), drag_info.copied_location->end()); } - session->add_redo_no_execute( session->locations()->get_memento() ); + after = session->locations()->get_state(); + session->add_command(MementoCommand(session->locations(), before, after)); commit_reversible_command (); marker_drag_line->hide(); @@ -2260,11 +2272,14 @@ Editor::meter_marker_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* TempoMap& map (session->tempo_map()); map.bbt_time (drag_info.last_pointer_frame, when); + XMLNode &before, &after; + if (drag_info.copy == true) { begin_reversible_command (_("copy meter mark")); - session->add_undo (map.get_memento()); + before = map.get_state(); map.add_meter (marker->meter(), when); - session->add_redo_no_execute (map.get_memento()); + after = map.get_state(); + session->add_command(MementoCommand(map, before, after)); commit_reversible_command (); // delete the dummy marker we used for visual representation of copying. @@ -2272,9 +2287,10 @@ Editor::meter_marker_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* delete marker; } else { begin_reversible_command (_("move meter mark")); - session->add_undo (map.get_memento()); + before = map.get_state(); map.move_meter (marker->meter(), when); - session->add_redo_no_execute (map.get_memento()); + after = map.get_state(); + session->add_command(MementoCommand(map, before, after)); commit_reversible_command (); } } @@ -2389,12 +2405,15 @@ Editor::tempo_marker_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* TempoMap& map (session->tempo_map()); map.bbt_time (drag_info.last_pointer_frame, when); + + XMLNode &before, &after; if (drag_info.copy == true) { begin_reversible_command (_("copy tempo mark")); - session->add_undo (map.get_memento()); + before = map.get_state(); map.add_tempo (marker->tempo(), when); - session->add_redo_no_execute (map.get_memento()); + after = map.get_state(); + session->add_command (MementoCommand(map, before, after)); commit_reversible_command (); // delete the dummy marker we used for visual representation of copying. @@ -2402,9 +2421,10 @@ Editor::tempo_marker_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* delete marker; } else { begin_reversible_command (_("move tempo mark")); - session->add_undo (map.get_memento()); + before = map.get_state(); map.move_tempo (marker->tempo(), when); - session->add_redo_no_execute (map.get_memento()); + after = map.get_state(); + session->add_command (MementoCommand(map, before, after)); commit_reversible_command (); } } @@ -3610,9 +3630,10 @@ Editor::start_selection_grab (ArdourCanvas::Item* item, GdkEvent* event) Playlist* playlist = clicked_trackview->playlist(); - session->add_undo (playlist->get_memento ()); + before = playlist->get_state(); clicked_trackview->playlist()->add_region (*region, selection->time[clicked_selection].start); - session->add_redo_no_execute (playlist->get_memento ()); + after = playlist->get_state(); + session->add_command(MementoCommand(*playlist, before, after)); commit_reversible_command (); @@ -4200,18 +4221,24 @@ Editor::point_trim (GdkEvent* event) i != selection->audio_regions.by_layer().end(); ++i) { if (!(*i)->region.locked()) { - session->add_undo ((*i)->region.playlist()->get_memento()); + XMLNode &before, &after; + Playlist *pl = (*i)->region.playlist(); + before = pl->get_state(); (*i)->region.trim_front (new_bound, this); - session->add_redo_no_execute ((*i)->region.playlist()->get_memento()); + after = pl->get_state(); + session->add_command(MementoCommand(*pl, before, after)); } } } else { if (!rv->region.locked()) { - session->add_undo (rv->region.playlist()->get_memento()); + XMLNode &before, &after; + Playlist *pl = rv->region.playlist(); + before = pl->get_state(); rv->region.trim_front (new_bound, this); - session->add_redo_no_execute (rv->region.playlist()->get_memento()); + after = pl->get_state(); + session->add_command(MementoCommand(*pl, before, after)); } } @@ -4227,18 +4254,24 @@ Editor::point_trim (GdkEvent* event) for (list::const_iterator i = selection->audio_regions.by_layer().begin(); i != selection->audio_regions.by_layer().end(); ++i) { if (!(*i)->region.locked()) { - session->add_undo ((*i)->region.playlist()->get_memento()); + XMLNode &before, &after; + Playlist *pl = (*i)->region.playlist(); + before = pl->get_state(); (*i)->region.trim_end (new_bound, this); - session->add_redo_no_execute ((*i)->region.playlist()->get_memento()); + after = pl->get_state(); + session->add_command(MementoCommand(*pl, before, after)); } } } else { if (!rv->region.locked()) { - session->add_undo (rv->region.playlist()->get_memento()); + XMLNode &before, &after; + Playlist *pl = rv->region.playlist(); + before = pl->get_state(); rv->region.trim_end (new_bound, this); - session->add_redo_no_execute (rv->region.playlist()->get_memento()); + after = pl->get_state(); + session->add_command (MementoCommand(*pl, before, after)); } } @@ -4398,10 +4431,12 @@ Editor::end_range_markerbar_op (ArdourCanvas::Item* item, GdkEvent* event) switch (range_marker_op) { case CreateRangeMarker: begin_reversible_command (_("new range marker")); - session->add_undo (session->locations()->get_memento()); + XMLNode &before, &after; + before = session->locations()->get_state(); newloc = new Location(temp_location->start(), temp_location->end(), "unnamed", Location::IsRangeMarker); session->locations()->add (newloc, true); - session->add_redo_no_execute (session->locations()->get_memento()); + after = session->locations()->get_state(); + session->add_command(MementoCommand(session->locations(), before, after)); commit_reversible_command (); range_bar_drag_rect->hide(); @@ -4776,9 +4811,11 @@ Editor::mouse_brush_insert_region (AudioRegionView* rv, jack_nframes_t pos) Playlist* playlist = atv->playlist(); double speed = atv->get_diskstream()->speed(); - session->add_undo (playlist->get_memento()); + XMLNode &before, &after; + before = playlist->get_state(); playlist->add_region (*(new AudioRegion (rv->region)), (jack_nframes_t) (pos * speed)); - session->add_redo_no_execute (playlist->get_memento()); + after = playlist->get_state(); + session->add_command(MementoCommand(*playlist, before, after)); // playlist is frozen, so we have to update manually diff --git a/libs/ardour/ardour/session.h b/libs/ardour/ardour/session.h index ba12b79f48..a9e8780c38 100644 --- a/libs/ardour/ardour/session.h +++ b/libs/ardour/ardour/session.h @@ -844,14 +844,8 @@ class Session : public sigc::trackable, public Stateful void begin_reversible_command (string cmd_name); void commit_reversible_command (Command* cmd = 0); - void add_undo (const UndoAction& ua) { - current_trans.add_undo (ua); - } - void add_redo (const UndoAction& ua) { - current_trans.add_redo (ua); - } - void add_redo_no_execute (const UndoAction& ua) { - current_trans.add_redo_no_execute (ua); + void add_command (const Command& cmd) { + current_trans.add_command (cmd); } UndoAction global_solo_memento (void *src); diff --git a/libs/pbd3/pbd/memento_command.h b/libs/pbd3/pbd/memento_command.h index c9952c443c..8c2ddefcf7 100644 --- a/libs/pbd3/pbd/memento_command.h +++ b/libs/pbd3/pbd/memento_command.h @@ -37,8 +37,8 @@ class MementoCommand : public Command XMLNode &after ) : obj(obj), before(before), after(after) {} - void operator() () { obj.set_memento(after); } - void undo() { obj.set_memento(before); } + void operator() () { obj.set_state(after); } + void undo() { obj.set_state(before); } virtual XMLNode &serialize() { // obj.id From b7bffbe7a249356a93d25a41f7c472cc9dd8f27f Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Tue, 25 Jul 2006 01:50:20 +0000 Subject: [PATCH 18/27] r191@gandalf: fugalh | 2006-07-24 19:50:10 -0600 All the obvious MementoCommand grunt work. Now there's some add_undo/add_redo_no_execute sprinkled around where one is separated from the other (e.g. in different callbacks) or perhaps even where there's only an undo and no redo. Also some sigc-based undo/redo pairs that probably need their own Command class. git-svn-id: svn://localhost/ardour2/branches/undo@692 d708f5d6-7413-0410-9779-e7cbd77b26cf --- gtk2_ardour/audio_time_axis.cc | 5 +- gtk2_ardour/automation_line.cc | 7 +- gtk2_ardour/automation_time_axis.cc | 4 +- gtk2_ardour/editor_audio_import.cc | 4 +- gtk2_ardour/editor_keyboard.cc | 5 +- gtk2_ardour/editor_markers.cc | 27 ++- gtk2_ardour/editor_ops.cc | 182 +++++++++++-------- gtk2_ardour/editor_tempodisplay.cc | 29 +-- gtk2_ardour/editor_timefx.cc | 5 +- gtk2_ardour/gain_automation_time_axis.cc | 6 +- gtk2_ardour/location_ui.cc | 16 +- gtk2_ardour/pan_automation_time_axis.cc | 6 +- gtk2_ardour/redirect_automation_time_axis.cc | 6 +- gtk2_ardour/region_gain_line.cc | 4 +- gtk2_ardour/regionview.cc | 5 +- libs/ardour/audio_diskstream.cc | 5 +- 16 files changed, 191 insertions(+), 125 deletions(-) diff --git a/gtk2_ardour/audio_time_axis.cc b/gtk2_ardour/audio_time_axis.cc index 01205abfc8..7fbe7c9fd8 100644 --- a/gtk2_ardour/audio_time_axis.cc +++ b/gtk2_ardour/audio_time_axis.cc @@ -1786,9 +1786,10 @@ AudioTimeAxisView::paste (jack_nframes_t pos, float times, Selection& selection, if (get_diskstream()->speed() != 1.0f) pos = session_frame_to_track_frame(pos, get_diskstream()->speed() ); - _session.add_undo (playlist->get_memento()); + XMLNode &before = playlist->get_state(); playlist->paste (**p, pos, times); - _session.add_redo_no_execute (playlist->get_memento()); + _session.add_command(MementoCommand(*playlist, before, + playlist->get_state())); return true; } diff --git a/gtk2_ardour/automation_line.cc b/gtk2_ardour/automation_line.cc index b87a71ca87..f5b23f01ae 100644 --- a/gtk2_ardour/automation_line.cc +++ b/gtk2_ardour/automation_line.cc @@ -1013,11 +1013,11 @@ AutomationLine::remove_point (ControlPoint& cp) model_representation (cp, mr); trackview.editor.current_session()->begin_reversible_command (_("remove control point")); - trackview.editor.current_session()->add_undo (get_memento()); + XMLNode &before = get_state(); alist.erase (mr.start, mr.end); - trackview.editor.current_session()->add_redo_no_execute (get_memento()); + trackview.editor.current_session()->add_command(MementoCommand(*this, before, get_state())); trackview.editor.current_session()->commit_reversible_command (); trackview.editor.current_session()->set_dirty (); } @@ -1225,9 +1225,10 @@ void AutomationLine::clear () { /* parent must create command */ + XMLNode &before = get_state(); trackview.editor.current_session()->add_undo (get_memento()); alist.clear(); - trackview.editor.current_session()->add_redo_no_execute (get_memento()); + trackview.editor.current_session()->add_command (MementoCommand(*this, before, get_state())); trackview.editor.current_session()->commit_reversible_command (); trackview.editor.current_session()->set_dirty (); } diff --git a/gtk2_ardour/automation_time_axis.cc b/gtk2_ardour/automation_time_axis.cc index 165e124add..f4b9aaaf7b 100644 --- a/gtk2_ardour/automation_time_axis.cc +++ b/gtk2_ardour/automation_time_axis.cc @@ -662,9 +662,9 @@ AutomationTimeAxisView::paste_one (AutomationLine& line, jack_nframes_t pos, flo (*x)->value = foo; } - _session.add_undo (alist.get_memento()); + XMLNode &before = alist.get_state(); alist.paste (copy, pos, times); - _session.add_redo_no_execute (alist.get_memento()); + _session.add_command (MementoCommand(alist, before, alist.get_state())); return true; } diff --git a/gtk2_ardour/editor_audio_import.cc b/gtk2_ardour/editor_audio_import.cc index f3e2ee1cb2..4cdc38dcf3 100644 --- a/gtk2_ardour/editor_audio_import.cc +++ b/gtk2_ardour/editor_audio_import.cc @@ -318,9 +318,9 @@ int AudioRegion* copy = new AudioRegion (region); begin_reversible_command (_("insert sndfile")); - session->add_undo (playlist->get_memento()); + XMLNode &before = playlist->get_state(); playlist->add_region (*copy, pos); - session->add_redo_no_execute (playlist->get_memento()); + session->add_command (MementoCommand(*playlist, before, playlist->get_state())); commit_reversible_command (); pos += region.length(); diff --git a/gtk2_ardour/editor_keyboard.cc b/gtk2_ardour/editor_keyboard.cc index 1ffaf2146d..df9bbf00ba 100644 --- a/gtk2_ardour/editor_keyboard.cc +++ b/gtk2_ardour/editor_keyboard.cc @@ -102,11 +102,12 @@ Editor::kbd_mute_unmute_region () { if (entered_regionview) { begin_reversible_command (_("mute region")); - session->add_undo (entered_regionview->region.playlist()->get_memento()); + XMLNode &before = entered_regionview->region.playlist()->get_state(); entered_regionview->region.set_muted (!entered_regionview->region.muted()); - session->add_redo_no_execute (entered_regionview->region.playlist()->get_memento()); + XMLNode &after = entered_regionview->region.playlist()->get_state(); + session->add_command (MementoCommand(entered_regionview->region.playlist(), before, after)); commit_reversible_command(); } } diff --git a/gtk2_ardour/editor_markers.cc b/gtk2_ardour/editor_markers.cc index a584561e42..5be9cc2747 100644 --- a/gtk2_ardour/editor_markers.cc +++ b/gtk2_ardour/editor_markers.cc @@ -290,9 +290,11 @@ Editor::mouse_add_new_marker (jack_nframes_t where) if (session) { Location *location = new Location (where, where, "mark", Location::IsMark); session->begin_reversible_command (_("add marker")); - session->add_undo (session->locations()->get_memento()); + XMLNode &before, &after; + before = session->locations()->get_state(); session->locations()->add (location, true); - session->add_redo_no_execute (session->locations()->get_memento()); + after = session->locations()->get_state(); + session->add_command (MementoCommand(*(session->locations()), before, after)); session->commit_reversible_command (); } } @@ -329,9 +331,11 @@ gint Editor::really_remove_marker (Location* loc) { session->begin_reversible_command (_("remove marker")); - session->add_undo (session->locations()->get_memento()); + XMLNode &before, &after; + before = session->locations()->get_state(); session->locations()->remove (loc); - session->add_redo_no_execute (session->locations()->get_memento()); + after = session->locations()->get_state(); + session->add_command (MementoCommand(*(session->locations()), before, after)); session->commit_reversible_command (); return FALSE; } @@ -838,12 +842,13 @@ Editor::marker_menu_rename () } begin_reversible_command ( _("rename marker") ); - session->add_undo( session->locations()->get_memento() ); + XMLNode &before = session->locations()->get_state(); dialog.get_result(txt); loc->set_name (txt); - session->add_redo_no_execute( session->locations()->get_memento() ); + XMLNode &after = session->locations()->get_state(); + session->add_command (MementoCommand(*(session->locations()), before, after)); commit_reversible_command (); } @@ -868,10 +873,11 @@ Editor::new_transport_marker_menu_set_loop () if ((tll = transport_loop_location()) == 0) { Location* loc = new Location (temp_location->start(), temp_location->end(), _("Loop"), Location::IsAutoLoop); - session->add_undo (session->locations()->get_memento()); + XMLNode &before = session->locations()->get_state(); session->locations()->add (loc, true); session->set_auto_loop_location (loc); - session->add_redo_no_execute (session->locations()->get_memento()); + XMLNode &after = session->locations()->get_state(); + session->add_command (MementoCommand(*(session->locations()), before, after)); } else { session->add_undo (retype_return(bind (mem_fun (*tll, &Location::set), tll->start(), tll->end()))); @@ -894,10 +900,11 @@ Editor::new_transport_marker_menu_set_punch () if ((tpl = transport_punch_location()) == 0) { tpl = new Location (temp_location->start(), temp_location->end(), _("Punch"), Location::IsAutoPunch); - session->add_undo (session->locations()->get_memento()); + XMLNode &before = session->locations()->get_state(); session->locations()->add (tpl, true); session->set_auto_punch_location (tpl); - session->add_redo_no_execute (session->locations()->get_memento()); + XMLNode &after = session->locations()->get_state(); + session->add_command (MementoCommand(*(session->locations()), before, after)); } else { session->add_undo (retype_return(bind (mem_fun (*tpl, &Location::set), tpl->start(), tpl->end()))); session->add_redo (retype_return(bind (mem_fun (*tpl, &Location::set), temp_location->start(), temp_location->end()))); diff --git a/gtk2_ardour/editor_ops.cc b/gtk2_ardour/editor_ops.cc index d3845dd26b..579b2403c6 100644 --- a/gtk2_ardour/editor_ops.cc +++ b/gtk2_ardour/editor_ops.cc @@ -207,9 +207,11 @@ Editor::split_regions_at (jack_nframes_t where, AudioRegionSelection& regions) _new_regionviews_show_envelope = (*a)->envelope_visible(); if (pl) { - session->add_undo (pl->get_memento()); + XMLNode &before, &after; + before = pl->get_state(); pl->split_region ((*a)->region, where); - session->add_redo_no_execute (pl->get_memento()); + after = pl->get_state(); + session->add_command(MementoCommand(*pl, before, after)); } a = tmp; @@ -229,9 +231,10 @@ Editor::remove_clicked_region () Playlist* playlist = clicked_audio_trackview->playlist(); begin_reversible_command (_("remove region")); - session->add_undo (playlist->get_memento()); + XMLNode &before = playlist->get_state(); playlist->remove_region (&clicked_regionview->region); - session->add_redo_no_execute (playlist->get_memento()); + XMLNode &after = playlist->get_state(); + session->add_command(MementoCommand(*playlist, before, after)); commit_reversible_command (); } @@ -404,9 +407,10 @@ Editor::nudge_forward (bool next) distance = next_distance; } - session->add_undo (r.playlist()->get_memento()); + XMLNode &before = r.playlist()->get_state(); r.set_position (r.position() + distance, this); - session->add_redo_no_execute (r.playlist()->get_memento()); + XMLNode &after = r.playlist()->get_state(); + session->add_command (MementoCommand(*(r.playlist()), before, after)); } commit_reversible_command (); @@ -438,14 +442,15 @@ Editor::nudge_backward (bool next) distance = next_distance; } - session->add_undo (r.playlist()->get_memento()); + XMLNode &before = r.playlist()->get_state(); if (r.position() > distance) { r.set_position (r.position() - distance, this); } else { r.set_position (0, this); } - session->add_redo_no_execute (r.playlist()->get_memento()); + XMLNode &after = r.playlist()->get_state(); + session->add_command(MementoCommand(*(r.playlist()), before, after)); } commit_reversible_command (); @@ -478,9 +483,11 @@ Editor::nudge_forward_capture_offset () for (AudioRegionSelection::iterator i = selection->audio_regions.begin(); i != selection->audio_regions.end(); ++i) { AudioRegion& r ((*i)->region); - session->add_undo (r.playlist()->get_memento()); + XMLNode &before, &after; + before = r.playlist()->get_state(); r.set_position (r.position() + distance, this); - session->add_redo_no_execute (r.playlist()->get_memento()); + after = r.playlist()->get_state(); + session->add_command(MementoCommand(*(r.playlist()), before, after)); } commit_reversible_command (); @@ -504,14 +511,15 @@ Editor::nudge_backward_capture_offset () for (AudioRegionSelection::iterator i = selection->audio_regions.begin(); i != selection->audio_regions.end(); ++i) { AudioRegion& r ((*i)->region); - session->add_undo (r.playlist()->get_memento()); + XMLNode &before = r.playlist()->get_state(); if (r.position() > distance) { r.set_position (r.position() - distance, this); } else { r.set_position (0, this); } - session->add_redo_no_execute (r.playlist()->get_memento()); + XMLNode &after = r.playlist()->get_state(); + session->add_command(MementoCommand(*(r.playlist()), before, after)); } commit_reversible_command (); @@ -1288,9 +1296,10 @@ Editor::add_location_from_selection () Location *location = new Location (start, end, "selection"); session->begin_reversible_command (_("add marker")); - session->add_undo (session->locations()->get_memento()); + XMLNode &before = session->locations()->get_state(); session->locations()->add (location, true); - session->add_redo_no_execute (session->locations()->get_memento()); + XMLNode &after = session->locations()->get_state(); + session->add_command(MementoCommand(*(session->locations()), before, after)); session->commit_reversible_command (); } @@ -1301,9 +1310,10 @@ Editor::add_location_from_playhead_cursor () Location *location = new Location (where, where, "mark", Location::IsMark); session->begin_reversible_command (_("add marker")); - session->add_undo (session->locations()->get_memento()); + XMLNode &before = session->locations()->get_state(); session->locations()->add (location, true); - session->add_redo_no_execute (session->locations()->get_memento()); + XMLNode &after = session->locations()->get_state(); + session->add_command(MementoCommand(*(session->locations()), before, after)); session->commit_reversible_command (); } @@ -1319,9 +1329,10 @@ Editor::add_location_from_audio_region () Location *location = new Location (region.position(), region.last_frame(), region.name()); session->begin_reversible_command (_("add marker")); - session->add_undo (session->locations()->get_memento()); + XMLNode &before = session->locations()->get_state(); session->locations()->add (location, true); - session->add_redo_no_execute (session->locations()->get_memento()); + XMLNode &after = session->locations()->get_state(); + session->add_command(MementoCommand(*(session->locations()), before, after)); session->commit_reversible_command (); } @@ -1737,9 +1748,10 @@ Editor::clear_markers () { if (session) { session->begin_reversible_command (_("clear markers")); - session->add_undo (session->locations()->get_memento()); + XMLNode &before = session->locations()->get_state(); session->locations()->clear_markers (); - session->add_redo_no_execute (session->locations()->get_memento()); + XMLNode &after = session->locations()->get_state(); + session->add_command(MementoCommand(*(session->locations()), before, after)); session->commit_reversible_command (); } } @@ -1749,7 +1761,7 @@ Editor::clear_ranges () { if (session) { session->begin_reversible_command (_("clear ranges")); - session->add_undo (session->locations()->get_memento()); + XMLNode &before = session->locations()->get_state(); Location * looploc = session->locations()->auto_loop_location(); Location * punchloc = session->locations()->auto_punch_location(); @@ -1759,7 +1771,8 @@ Editor::clear_ranges () if (looploc) session->locations()->add (looploc); if (punchloc) session->locations()->add (punchloc); - session->add_redo_no_execute (session->locations()->get_memento()); + XMLNode &after = session->locations()->get_state(); + session->add_command(MementoCommand(*(session->locations()), before, after)); session->commit_reversible_command (); } } @@ -1768,9 +1781,10 @@ void Editor::clear_locations () { session->begin_reversible_command (_("clear locations")); - session->add_undo (session->locations()->get_memento()); + XMLNode &before = session->locations()->get_state(); session->locations()->clear (); - session->add_redo_no_execute (session->locations()->get_memento()); + XMLNode &after = session->locations()->get_state(); + session->add_command(MementoCommand(*(sessions->locations()), before, after)); session->commit_reversible_command (); session->locations()->clear (); } @@ -1818,9 +1832,9 @@ Editor::insert_region_list_drag (AudioRegion& region, int x, int y) snap_to (where); begin_reversible_command (_("insert dragged region")); - session->add_undo (playlist->get_memento()); + XMLNode &before = playlist->get_state(); playlist->add_region (*(new AudioRegion (region)), where, 1.0); - session->add_redo_no_execute (playlist->get_memento()); + session->add_command(MementoCommand(*playlist, before, playlist->get_state())); commit_reversible_command (); } @@ -1854,9 +1868,9 @@ Editor::insert_region_list_selection (float times) Region* region = (*i)[region_list_columns.region]; begin_reversible_command (_("insert region")); - session->add_undo (playlist->get_memento()); + XMLNode &before = playlist->get_state(); playlist->add_region (*(createRegion (*region)), edit_cursor->current_frame, times); - session->add_redo_no_execute (playlist->get_memento()); + session->add_command(MementoCommand(*playlist, before, playlist->get_state())); commit_reversible_command (); } @@ -2277,7 +2291,9 @@ Editor::separate_region_from_selection () begin_reversible_command (_("separate")); doing_undo = true; } - if (doing_undo) session->add_undo ((playlist)->get_memento()); + XMLNode &before, &after; + if (doing_undo) + before = playlist->get_state(); /* XXX need to consider musical time selections here at some point */ @@ -2287,7 +2303,8 @@ Editor::separate_region_from_selection () playlist->partition ((jack_nframes_t)((*t).start * speed), (jack_nframes_t)((*t).end * speed), true); } - if (doing_undo) session->add_redo_no_execute (playlist->get_memento()); + if (doing_undo) + session->add_command(MementoCommand(*playlist, before, playlist->get_state())); } } } @@ -2322,11 +2339,14 @@ Editor::separate_regions_using_location (Location& loc) if (atv->is_audio_track()) { if ((playlist = atv->playlist()) != 0) { + XMLNode &before, &after; if (!doing_undo) { begin_reversible_command (_("separate")); doing_undo = true; } - if (doing_undo) session->add_undo ((playlist)->get_memento()); + if (doing_undo) + before = playlist->get_state(); + /* XXX need to consider musical time selections here at some point */ @@ -2334,7 +2354,8 @@ Editor::separate_regions_using_location (Location& loc) playlist->partition ((jack_nframes_t)(loc.start() * speed), (jack_nframes_t)(loc.end() * speed), true); - if (doing_undo) session->add_redo_no_execute (playlist->get_memento()); + if (doing_undo) + session->add_command(MementoCommand(*playlist, before, playlist->get_state())); } } } @@ -2405,9 +2426,10 @@ Editor::crop_region_to_selection () end = min (selection->time.end_frame(), start + region->length() - 1); cnt = end - start + 1; - session->add_undo ((*i)->get_memento()); + XMLNode &before = (*i)->get_state(); region->trim_to (start, cnt, this); - session->add_redo_no_execute ((*i)->get_memento()); + XMLNode &after = (*i)->get_state(); + session->add_command (MementoCommand(*(*i), before, after)); } commit_reversible_command (); @@ -2442,9 +2464,9 @@ Editor::region_fill_track () return; } - session->add_undo (pl->get_memento()); + XMLNode &before = pl->get_state(); pl->add_region (*(new AudioRegion (region)), region.last_frame(), times); - session->add_redo_no_execute (pl->get_memento()); + session->add_command (MementoCommand(*pl, before, pl->get_state())); } commit_reversible_command (); @@ -2492,9 +2514,9 @@ Editor::region_fill_selection () continue; } - session->add_undo (playlist->get_memento()); + XMLNode &before = playlist->get_state(); playlist->add_region (*(createRegion (*region)), start, times); - session->add_redo_no_execute (playlist->get_memento()); + session->add_command (MementoCommand(*playlist, before, playlist->get_state())); } commit_reversible_command (); @@ -2509,9 +2531,10 @@ Editor::set_a_regions_sync_position (Region& region, jack_nframes_t position) return; } begin_reversible_command (_("set region sync position")); - session->add_undo (region.playlist()->get_memento()); + XMLNode &before = region.playlist()->get_state(); region.set_sync_position (position); - session->add_redo_no_execute (region.playlist()->get_memento()); + XMLNode &after = region.playlist()->get_state(); + session->add_command(MementoCommand(*(region.playlist()), before, after)); commit_reversible_command (); } @@ -2529,9 +2552,10 @@ Editor::set_region_sync_from_edit_cursor () Region& region (clicked_regionview->region); begin_reversible_command (_("set sync from edit cursor")); - session->add_undo (region.playlist()->get_memento()); + XMLNode &before = region.playlist()->get_state(); region.set_sync_position (edit_cursor->current_frame); - session->add_redo_no_execute (region.playlist()->get_memento()); + XMLNode &after = region.playlist()->get_state(); + session->add_command(MementoCommand(*(region.playlist()), before, after)); commit_reversible_command (); } @@ -2541,9 +2565,10 @@ Editor::remove_region_sync () if (clicked_regionview) { Region& region (clicked_regionview->region); begin_reversible_command (_("remove sync")); - session->add_undo (region.playlist()->get_memento()); + XMLNode &before = region.playlist()->get_state(); region.clear_sync_position (); - session->add_redo_no_execute (region.playlist()->get_memento()); + XMLNode &after = region.playlist()->get_state(); + session->add_command(MementoCommand(*(region.playlist()), before, after)); commit_reversible_command (); } } @@ -2556,9 +2581,10 @@ Editor::naturalize () } begin_reversible_command (_("naturalize")); for (AudioRegionSelection::iterator i = selection->audio_regions.begin(); i != selection->audio_regions.end(); ++i) { - session->add_undo ((*i)->region.get_memento()); + XMLNode &before = (*i)->region.get_state(); (*i)->region.move_to_natural_position (this); - session->add_redo_no_execute ((*i)->region.get_memento()); + XMLNode &after = (*i)->region.get_state(); + session->add_command (MementoCommand((*i)->region, before, after)); } commit_reversible_command (); } @@ -2624,7 +2650,7 @@ Editor::align_selection_relative (RegionPoint point, jack_nframes_t position) Region& region ((*i)->region); - session->add_undo (region.playlist()->get_memento()); + XMLNode &before = region.playlist()->get_state(); if (dir > 0) { region.set_position (region.position() + distance, this); @@ -2632,7 +2658,8 @@ Editor::align_selection_relative (RegionPoint point, jack_nframes_t position) region.set_position (region.position() - distance, this); } - session->add_redo_no_execute (region.playlist()->get_memento()); + XMLNode &after = region.playlist()->get_state(); + session->add_command(MementoCommand(*(region.playlist()), before, after)); } @@ -2666,7 +2693,8 @@ Editor::align_region (Region& region, RegionPoint point, jack_nframes_t position void Editor::align_region_internal (Region& region, RegionPoint point, jack_nframes_t position) { - session->add_undo (region.playlist()->get_memento()); + XMLNode &before, &after; + before = region.playlist()->get_state(); switch (point) { case SyncPoint: @@ -2684,7 +2712,8 @@ Editor::align_region_internal (Region& region, RegionPoint point, jack_nframes_t break; } - session->add_redo_no_execute (region.playlist()->get_memento()); + after = region.playlist()->get_state(); + session->add_command(MementoCommand(*(region.playlist()), before, after)); } void @@ -2706,9 +2735,10 @@ Editor::trim_region_to_edit_cursor () } begin_reversible_command (_("trim to edit")); - session->add_undo (region.playlist()->get_memento()); + XMLNode &before = region.playlist()->get_state(); region.trim_end( session_frame_to_track_frame(edit_cursor->current_frame, speed), this); - session->add_redo_no_execute (region.playlist()->get_memento()); + XMLNode &after = region.playlist()->get_state(); + session->add_command(MementoCommand(*(region.playlist()), before, after)); commit_reversible_command (); } @@ -2731,9 +2761,10 @@ Editor::trim_region_from_edit_cursor () } begin_reversible_command (_("trim to edit")); - session->add_undo (region.playlist()->get_memento()); + XMLNode &before = region.playlist()->get_state(); region.trim_front ( session_frame_to_track_frame(edit_cursor->current_frame, speed), this); - session->add_redo_no_execute (region.playlist()->get_memento()); + XMLNode &after = region.playlist()->get_state(); + session->add_command(MementoCommand(*(region.playlist()), before, after)); commit_reversible_command (); } @@ -2845,9 +2876,10 @@ Editor::bounce_range_selection () itt.cancel = false; itt.progress = false; - session->add_undo (playlist->get_memento()); + XMLNode &before = playlist->get_state(); atv->audio_track()->bounce_range (start, cnt, itt); - session->add_redo_no_execute (playlist->get_memento()); + XMLNode &after = playlist->get_state(); + session->add_command (MementoCommand (*playlist, before, after)); } commit_reversible_command (); @@ -3136,9 +3168,9 @@ Editor::paste_named_selection (float times) tmp = chunk; ++tmp; - session->add_undo (apl->get_memento()); + XMLNode &before = apl->get_state(); apl->paste (**chunk, edit_cursor->current_frame, times); - session->add_redo_no_execute (apl->get_memento()); + session->add_command(MementoCommand(*apl, before, apl->get_state())); if (tmp != ns->playlists.end()) { chunk = tmp; @@ -3167,9 +3199,9 @@ Editor::duplicate_some_regions (AudioRegionSelection& regions, float times) sigc::connection c = atv->view->AudioRegionViewAdded.connect (mem_fun(*this, &Editor::collect_new_region_view)); playlist = (*i)->region.playlist(); - session->add_undo (playlist->get_memento()); + XMLNode &before = playlist->get_state(); playlist->duplicate (r, r.last_frame(), times); - session->add_redo_no_execute (playlist->get_memento()); + session->add_command(MementoCommand(*playlist, before, playlist->get_state())); c.disconnect (); @@ -3207,9 +3239,10 @@ Editor::duplicate_selection (float times) if ((playlist = (*i)->playlist()) == 0) { continue; } - session->add_undo (playlist->get_memento()); + XMLNode &before = playlist->get_state(); playlist->duplicate (**ri, selection->time[clicked_selection].end, times); - session->add_redo_no_execute (playlist->get_memento()); + XMLNode &after = playlist->get_state(); + session->add_command (MementoCommand(*playlist, before, after)); ++ri; if (ri == new_regions.end()) { @@ -3257,9 +3290,10 @@ void Editor::clear_playlist (Playlist& playlist) { begin_reversible_command (_("clear playlist")); - session->add_undo (playlist.get_memento()); + XMLNode &before = playlist.get_state(); playlist.clear (); - session->add_redo_no_execute (playlist.get_memento()); + XMLNode &after = playlist.get_state(); + session->add_command (MementoCommand(playlist, before, after)); commit_reversible_command (); } @@ -3293,9 +3327,10 @@ Editor::nudge_track (bool use_edit_cursor, bool forwards) continue; } - session->add_undo (playlist->get_memento()); + XMLNode &before = playlist->get_state(); playlist->nudge_after (start, distance, forwards); - session->add_redo_no_execute (playlist->get_memento()); + XMLNode &after = playlist->get_state(); + session->add_command (MementoCommand(*playlist, before, after)); } commit_reversible_command (); @@ -3346,9 +3381,10 @@ Editor::normalize_region () gdk_flush (); for (AudioRegionSelection::iterator r = selection->audio_regions.begin(); r != selection->audio_regions.end(); ++r) { - session->add_undo ((*r)->region.get_memento()); + XMLNode &before = (*r)->region.get_state(); (*r)->region.normalize_to (0.0f); - session->add_redo_no_execute ((*r)->region.get_memento()); + XMLNode &after = (*r)->region.get_state(); + session->add_command (MementoCommand((*r)->region, before, after)); } commit_reversible_command (); @@ -3370,9 +3406,10 @@ Editor::denormalize_region () begin_reversible_command ("denormalize"); for (AudioRegionSelection::iterator r = selection->audio_regions.begin(); r != selection->audio_regions.end(); ++r) { - session->add_undo ((*r)->region.get_memento()); + XMLNode &before = (*r)->region.get_state(); (*r)->region.set_scale_amplitude (1.0f); - session->add_redo_no_execute ((*r)->region.get_memento()); + XMLNode &after = (*r)->region.get_state(); + session->add_command (MementoCommand((*r)->region, before, after)); } commit_reversible_command (); @@ -3414,9 +3451,10 @@ Editor::apply_filter (AudioFilter& filter, string command) if (region.apply (filter) == 0) { - session->add_undo (playlist->get_memento()); + XMLNode &before = playlist->get_state(); playlist->replace_region (region, *(filter.results.front()), region.position()); - session->add_redo_no_execute (playlist->get_memento()); + XMLNode &after = playlist->get_state(); + session->add_command(MementoCommand(*playlist, before, after)); } else { goto out; } diff --git a/gtk2_ardour/editor_tempodisplay.cc b/gtk2_ardour/editor_tempodisplay.cc index 5f998ada9f..0456087859 100644 --- a/gtk2_ardour/editor_tempodisplay.cc +++ b/gtk2_ardour/editor_tempodisplay.cc @@ -273,9 +273,10 @@ Editor::mouse_add_new_tempo_event (jack_nframes_t frame) tempo_dialog.get_bbt_time (requested); begin_reversible_command (_("add tempo mark")); - session->add_undo (map.get_memento()); + XMLNode &before = map.get_state(); map.add_tempo (Tempo (bpm), requested); - session->add_redo_no_execute (map.get_memento()); + XMLNode &after = map.get_state(); + session->add_command(MementoCommand(map, before, after)); commit_reversible_command (); map.dump (cerr); @@ -313,9 +314,9 @@ Editor::mouse_add_new_meter_event (jack_nframes_t frame) meter_dialog.get_bbt_time (requested); begin_reversible_command (_("add meter mark")); - session->add_undo (map.get_memento()); + XMLNode &before = map.get_state(); map.add_meter (Meter (bpb, note_type), requested); - session->add_redo_no_execute (map.get_memento()); + session->add_command(MementoCommand(map, before, map.get_state())); commit_reversible_command (); map.dump (cerr); @@ -364,9 +365,10 @@ Editor::edit_meter_section (MeterSection* section) double note_type = meter_dialog.get_note_type (); begin_reversible_command (_("replace tempo mark")); - session->add_undo (session->tempo_map().get_memento()); + XMLNode &before = session->tempo_map().get_state(); session->tempo_map().replace_meter (*section, Meter (bpb, note_type)); - session->add_redo_no_execute (session->tempo_map().get_memento()); + XMLNode &before = session->tempo_map().get_state(); + session->add_command(MementoCommand(session->tempo_map(), before, after)); commit_reversible_command (); } @@ -392,10 +394,11 @@ Editor::edit_tempo_section (TempoSection* section) bpm = max (0.01, bpm); begin_reversible_command (_("replace tempo mark")); - session->add_undo (session->tempo_map().get_memento()); + XMLNode &before = session->tempo_map().get_state(); session->tempo_map().replace_tempo (*section, Tempo (bpm)); session->tempo_map().move_tempo (*section, when); - session->add_redo_no_execute (session->tempo_map().get_memento()); + XMLNode &after = session->tempo_map().get_state(); + session->add_command (MementoCommand(session->tempo_map(), before, after)); commit_reversible_command (); } @@ -441,9 +444,10 @@ gint Editor::real_remove_tempo_marker (TempoSection *section) { begin_reversible_command (_("remove tempo mark")); - session->add_undo (session->tempo_map().get_memento()); + XMLNode &before = session->tempo_map().get_state(); session->tempo_map().remove_tempo (*section); - session->add_redo_no_execute (session->tempo_map().get_memento()); + XMLNode &after = session->tempo_map().get_state(); + session->add_command(MementoCommand(session->tempo_map(), before, after)); commit_reversible_command (); return FALSE; @@ -474,9 +478,10 @@ gint Editor::real_remove_meter_marker (MeterSection *section) { begin_reversible_command (_("remove tempo mark")); - session->add_undo (session->tempo_map().get_memento()); + XMLNode &before = session->tempo_map().get_state(); session->tempo_map().remove_meter (*section); - session->add_redo_no_execute (session->tempo_map().get_memento()); + XMLNode &after = session->tempo_map().get_state(); + session->add_command(MementoCommand(session->tempo_map(), before, after)); commit_reversible_command (); return FALSE; } diff --git a/gtk2_ardour/editor_timefx.cc b/gtk2_ardour/editor_timefx.cc index 6ff467454d..817a770fe5 100644 --- a/gtk2_ardour/editor_timefx.cc +++ b/gtk2_ardour/editor_timefx.cc @@ -203,9 +203,10 @@ Editor::do_timestretch (TimeStretchDialog& dialog) return; } - session->add_undo (playlist->get_memento()); + XMLNode &before = playlist->get_state(); playlist->replace_region (aregion, *new_region, aregion.position()); - session->add_redo_no_execute (playlist->get_memento()); + XMLNode &after = playlist->get_state(); + session->add_command (MementoCommand(*playlist, before, after)); i = tmp; } diff --git a/gtk2_ardour/gain_automation_time_axis.cc b/gtk2_ardour/gain_automation_time_axis.cc index 8f41f5def0..1697adbb9c 100644 --- a/gtk2_ardour/gain_automation_time_axis.cc +++ b/gtk2_ardour/gain_automation_time_axis.cc @@ -61,9 +61,11 @@ GainAutomationTimeAxisView::add_automation_event (ArdourCanvas::Item* item, GdkE _session.begin_reversible_command (_("add gain automation event")); - _session.add_undo (curve.get_memento()); + XMLNode &before, &after; + before = curve.get_state(); curve.add (when, y); - _session.add_redo_no_execute (curve.get_memento()); + after = curve.get_state(); + _session.add_command(MementoCommand(curve, before, after)); _session.commit_reversible_command (); _session.set_dirty (); } diff --git a/gtk2_ardour/location_ui.cc b/gtk2_ardour/location_ui.cc index f0fe230b57..08d5a0b3af 100644 --- a/gtk2_ardour/location_ui.cc +++ b/gtk2_ardour/location_ui.cc @@ -654,9 +654,11 @@ gint LocationUI::do_location_remove (ARDOUR::Location *loc) } session->begin_reversible_command (_("remove marker")); - session->add_undo (session->locations()->get_memento()); + XMLNode &before, &after; + before = session->locations()->get_state(); session->locations()->remove (loc); - session->add_redo_no_execute (session->locations()->get_memento()); + after = session->locations()->get_state(); + session->add_command(MementoCommand(*(session->locations()), before, after)); session->commit_reversible_command (); return FALSE; @@ -772,9 +774,10 @@ LocationUI::add_new_location() jack_nframes_t where = session->audible_frame(); Location *location = new Location (where, where, "mark", Location::IsMark); session->begin_reversible_command (_("add marker")); - session->add_undo (session->locations()->get_memento()); + XMLNode &before = session->locations()->get_state(); session->locations()->add (location, true); - session->add_redo_no_execute (session->locations()->get_memento()); + XMLNode &after = session->locations()->get_state(); + session->add_command (MementoCommand(*(session->locations()), before, after)); session->commit_reversible_command (); } @@ -788,9 +791,10 @@ LocationUI::add_new_range() Location *location = new Location (where, where, "unnamed", Location::IsRangeMarker); session->begin_reversible_command (_("add range marker")); - session->add_undo (session->locations()->get_memento()); + XMLNode &before = session->locations()->get_state(); session->locations()->add (location, true); - session->add_redo_no_execute (session->locations()->get_memento()); + XMLNode &after = session->locations()->get_state(); + session->add_command (MementoCommand(*(session->locations()), before, after)); session->commit_reversible_command (); } } diff --git a/gtk2_ardour/pan_automation_time_axis.cc b/gtk2_ardour/pan_automation_time_axis.cc index b72eda78bd..267bb6ef09 100644 --- a/gtk2_ardour/pan_automation_time_axis.cc +++ b/gtk2_ardour/pan_automation_time_axis.cc @@ -78,9 +78,11 @@ PanAutomationTimeAxisView::add_automation_event (ArdourCanvas::Item* item, GdkEv AutomationList& alist (lines.front()->the_list()); _session.begin_reversible_command (_("add pan automation event")); - _session.add_undo (alist.get_memento()); + XMLNode &before, &after; + before = alist.get_state(); alist.add (when, y); - _session.add_undo (alist.get_memento()); + after = alist.get_state(); + _seession.add_command(MementoCommand(alist, before, after)); _session.commit_reversible_command (); _session.set_dirty (); } diff --git a/gtk2_ardour/redirect_automation_time_axis.cc b/gtk2_ardour/redirect_automation_time_axis.cc index e1b71310ac..d6e2432338 100644 --- a/gtk2_ardour/redirect_automation_time_axis.cc +++ b/gtk2_ardour/redirect_automation_time_axis.cc @@ -97,9 +97,11 @@ RedirectAutomationTimeAxisView::add_automation_event (ArdourCanvas::Item* item, lines.front()->view_to_model_y (y); _session.begin_reversible_command (description); - _session.add_undo (alist.get_memento()); + XMLNode &before, &after; + before = alist.get_state(); alist.add (when, y); - _session.add_redo_no_execute (alist.get_memento()); + after = alist.get_state(); + _session.add_command(MementoCommand(alist, before, after)); _session.commit_reversible_command (); _session.set_dirty (); } diff --git a/gtk2_ardour/region_gain_line.cc b/gtk2_ardour/region_gain_line.cc index bba9410ffb..54b7fa5b56 100644 --- a/gtk2_ardour/region_gain_line.cc +++ b/gtk2_ardour/region_gain_line.cc @@ -60,7 +60,7 @@ AudioRegionGainLine::remove_point (ControlPoint& cp) model_representation (cp, mr); trackview.editor.current_session()->begin_reversible_command (_("remove control point")); - trackview.editor.current_session()->add_undo (get_memento()); + XMLNode &before = get_state(); if (!rv.region.envelope_active()) { trackview.session().add_undo( bind( mem_fun(rv.region, &AudioRegion::set_envelope_active), false) ); @@ -70,7 +70,7 @@ AudioRegionGainLine::remove_point (ControlPoint& cp) alist.erase (mr.start, mr.end); - trackview.editor.current_session()->add_redo_no_execute (get_memento()); + trackview.editor.current_session()->add_command (MementoCommand(*this, before, get_state())); trackview.editor.current_session()->commit_reversible_command (); trackview.editor.current_session()->set_dirty (); } diff --git a/gtk2_ardour/regionview.cc b/gtk2_ardour/regionview.cc index 114aaf5da3..fbd69105df 100644 --- a/gtk2_ardour/regionview.cc +++ b/gtk2_ardour/regionview.cc @@ -1144,7 +1144,7 @@ AudioRegionView::add_gain_point_event (ArdourCanvas::Item *item, GdkEvent *ev) gain_line->view_to_model_y (y); trackview.session().begin_reversible_command (_("add gain control point")); - trackview.session().add_undo (region.envelope().get_memento()); + XMLNode &before = region.envelope().get_state(); if (!region.envelope_active()) { @@ -1155,7 +1155,8 @@ AudioRegionView::add_gain_point_event (ArdourCanvas::Item *item, GdkEvent *ev) region.envelope().add (fx, y); - trackview.session().add_redo_no_execute (region.envelope().get_memento()); + XMLNode &after = region.envelope().get_state(); + trackview.session().add_command(MementoCommand(region.envelope(), before, after)); trackview.session().commit_reversible_command (); } diff --git a/libs/ardour/audio_diskstream.cc b/libs/ardour/audio_diskstream.cc index 96615fd077..b0561eb05d 100644 --- a/libs/ardour/audio_diskstream.cc +++ b/libs/ardour/audio_diskstream.cc @@ -1801,7 +1801,7 @@ AudioDiskstream::transport_stopped (struct tm& when, time_t twhen, bool abort_ca // cerr << _name << ": there are " << capture_info.size() << " capture_info records\n"; - _session.add_undo (_playlist->get_memento()); + XMLNode &before = _playlist->get_state(); _playlist->freeze (); for (buffer_position = channels[0].write_source->last_capture_start_frame(), ci = capture_info.begin(); ci != capture_info.end(); ++ci) { @@ -1832,7 +1832,8 @@ AudioDiskstream::transport_stopped (struct tm& when, time_t twhen, bool abort_ca } _playlist->thaw (); - _session.add_redo_no_execute (_playlist->get_memento()); + XMLNode &after = _playlist->get_state(); + _session.add_command (MementoCommand(*_playlist, before, after)); } mark_write_completed = true; From 8e301e875aacc4b7d37f6ed552e460511dafb7f2 Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Wed, 26 Jul 2006 23:28:54 +0000 Subject: [PATCH 19/27] r199@gandalf: fugalh | 2006-07-26 17:22:38 -0600 Memento(Redo|Undo)Command has a noop for the undo or redo respectively, and we don't need both before and after state. This is primarily useful for drag start/finish callbacks, and really only makes sense where wrapped by (begin|commit)_reversible_command (a composite command). Also a few more "normal" MementoCommands. git-svn-id: svn://localhost/ardour2/branches/undo@695 d708f5d6-7413-0410-9779-e7cbd77b26cf --- gtk2_ardour/audio_time_axis.cc | 10 +++++---- gtk2_ardour/automation_line.cc | 5 ++--- gtk2_ardour/automation_time_axis.cc | 14 +++++++----- gtk2_ardour/editor_mouse.cc | 17 ++++++++------- gtk2_ardour/editor_ops.cc | 4 ++-- libs/pbd3/pbd/memento_command.h | 34 +++++++++++++++++++++++++++++ 6 files changed, 61 insertions(+), 23 deletions(-) diff --git a/gtk2_ardour/audio_time_axis.cc b/gtk2_ardour/audio_time_axis.cc index 7fbe7c9fd8..ebc97be77b 100644 --- a/gtk2_ardour/audio_time_axis.cc +++ b/gtk2_ardour/audio_time_axis.cc @@ -1739,12 +1739,14 @@ AudioTimeAxisView::cut_copy_clear (Selection& selection, CutCopyOp op) } } + XMLNode &before, &after; switch (op) { case Cut: - _session.add_undo (playlist->get_memento()); + before = playlist->get_state(); if ((what_we_got = playlist->cut (time)) != 0) { editor.get_cut_buffer().add (what_we_got); - _session.add_redo_no_execute (playlist->get_memento()); + after = playlist->get_state(); + _session.add_command (MementoCommand(*playlist, before, after)); ret = true; } break; @@ -1755,9 +1757,9 @@ AudioTimeAxisView::cut_copy_clear (Selection& selection, CutCopyOp op) break; case Clear: - _session.add_undo (playlist->get_memento()); + before = playlist->get_state(); if ((what_we_got = playlist->cut (time)) != 0) { - _session.add_redo_no_execute (playlist->get_memento()); + _session.add_command(MementoCommand(*playlist, before, after)); what_we_got->unref (); ret = true; } diff --git a/gtk2_ardour/automation_line.cc b/gtk2_ardour/automation_line.cc index f5b23f01ae..bd7ed326d8 100644 --- a/gtk2_ardour/automation_line.cc +++ b/gtk2_ardour/automation_line.cc @@ -887,7 +887,7 @@ AutomationLine::start_drag (ControlPoint* cp, float fraction) } trackview.editor.current_session()->begin_reversible_command (str); - trackview.editor.current_session()->add_undo (get_memento()); + trackview.editor.current_session()->add_command (MementoUndoCommand(*this, get_state())); first_drag_fraction = fraction; last_drag_fraction = fraction; @@ -936,7 +936,7 @@ AutomationLine::end_drag (ControlPoint* cp) update_pending = false; - trackview.editor.current_session()->add_redo_no_execute (get_memento()); + trackview.editor.current_session()->add_command (MementoRedoCommand(*this, get_state())); trackview.editor.current_session()->commit_reversible_command (); trackview.editor.current_session()->set_dirty (); } @@ -1226,7 +1226,6 @@ AutomationLine::clear () { /* parent must create command */ XMLNode &before = get_state(); - trackview.editor.current_session()->add_undo (get_memento()); alist.clear(); trackview.editor.current_session()->add_command (MementoCommand(*this, before, get_state())); trackview.editor.current_session()->commit_reversible_command (); diff --git a/gtk2_ardour/automation_time_axis.cc b/gtk2_ardour/automation_time_axis.cc index f4b9aaaf7b..4680e3a35f 100644 --- a/gtk2_ardour/automation_time_axis.cc +++ b/gtk2_ardour/automation_time_axis.cc @@ -500,13 +500,14 @@ AutomationTimeAxisView::cut_copy_clear_one (AutomationLine& line, Selection& sel AutomationList& alist (line.the_list()); bool ret = false; - _session.add_undo (alist.get_memento()); + XMLNode &before, &after; + before = alist.get_state(); switch (op) { case Cut: if ((what_we_got = alist.cut (selection.time.front().start, selection.time.front().end)) != 0) { editor.get_cut_buffer().add (what_we_got); - _session.add_redo_no_execute (alist.get_memento()); + _session.add_command(MementoCommand(alist, before, alist.get_state())); ret = true; } break; @@ -518,7 +519,7 @@ AutomationTimeAxisView::cut_copy_clear_one (AutomationLine& line, Selection& sel case Clear: if ((what_we_got = alist.cut (selection.time.front().start, selection.time.front().end)) != 0) { - _session.add_redo_no_execute (alist.get_memento()); + _session.add_command(MementoCommand(alist, before, alist.get_state())); delete what_we_got; what_we_got = 0; ret = true; @@ -580,8 +581,9 @@ AutomationTimeAxisView::cut_copy_clear_objects_one (AutomationLine& line, PointS AutomationList* what_we_got = 0; AutomationList& alist (line.the_list()); bool ret = false; + XMLNode &before, &after; - _session.add_undo (alist.get_memento()); + before = alist.get_state(); for (PointSelection::iterator i = selection.begin(); i != selection.end(); ++i) { @@ -593,7 +595,7 @@ AutomationTimeAxisView::cut_copy_clear_objects_one (AutomationLine& line, PointS case Cut: if ((what_we_got = alist.cut ((*i).start, (*i).end)) != 0) { editor.get_cut_buffer().add (what_we_got); - _session.add_redo_no_execute (alist.get_memento()); + _session.add_command (MementoCommand(alist, before, alist.get_state())); ret = true; } break; @@ -605,7 +607,7 @@ AutomationTimeAxisView::cut_copy_clear_objects_one (AutomationLine& line, PointS case Clear: if ((what_we_got = alist.cut ((*i).start, (*i).end)) != 0) { - _session.add_redo_no_execute (alist.get_memento()); + _session.add_command (MementoCommand(alist, before, alist.get_state())); delete what_we_got; what_we_got = 0; ret = true; diff --git a/gtk2_ardour/editor_mouse.cc b/gtk2_ardour/editor_mouse.cc index e4d8ec6ce6..4b17c9e6b0 100644 --- a/gtk2_ardour/editor_mouse.cc +++ b/gtk2_ardour/editor_mouse.cc @@ -2787,7 +2787,7 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) insert_result = affected_playlists.insert (to_playlist); if (insert_result.second) { - session->add_undo (to_playlist->get_memento ()); + session->add_command (MementoUndoCommand(*to_playlist, to_playlist->get_state())); } latest_regionview = 0; @@ -3225,7 +3225,7 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) insert_result = motion_frozen_playlists.insert (pl); if (insert_result.second) { pl->freeze(); - session->add_undo(pl->get_memento()); + session->add_command(MementoUndoCommand(*pl, pl->get_state())); } } } @@ -3353,7 +3353,7 @@ Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event insert_result = motion_frozen_playlists.insert(to_playlist); if (insert_result.second) { to_playlist->freeze(); - session->add_undo(to_playlist->get_memento()); + session->add_command(MementoUndoCommand(*to_playlist, to_playlist->get_state())); } } @@ -3435,7 +3435,7 @@ Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event out: for (set::iterator p = motion_frozen_playlists.begin(); p != motion_frozen_playlists.end(); ++p) { (*p)->thaw (); - session->add_redo_no_execute ((*p)->get_memento()); + session->add_command (MementoRedoCommand(*(*p), (*p)->get_state())); } motion_frozen_playlists.clear (); @@ -3997,7 +3997,7 @@ Editor::trim_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) Playlist * pl = (*i)->region.playlist(); insert_result = motion_frozen_playlists.insert (pl); if (insert_result.second) { - session->add_undo (pl->get_memento()); + session->add_command(MementoUndoCommand(*pl, pl->get_state())); } } } @@ -4187,8 +4187,8 @@ Editor::trim_finished_callback (ArdourCanvas::Item* item, GdkEvent* event) for (set::iterator p = motion_frozen_playlists.begin(); p != motion_frozen_playlists.end(); ++p) { //(*p)->thaw (); - session->add_redo_no_execute ((*p)->get_memento()); - } + session->add_command (MementoRedoCommand(*(*p), (*p)->get_state())); + } motion_frozen_playlists.clear (); @@ -4293,7 +4293,8 @@ Editor::thaw_region_after_trim (AudioRegionView& rv) } region.thaw (_("trimmed region")); - session->add_redo_no_execute (region.playlist()->get_memento()); + XMLNode &after = region.playlist()->get_state(); + session->add_command (MementoRedoCommand(*(region.playlist()), after)); rv.unhide_envelope (); } diff --git a/gtk2_ardour/editor_ops.cc b/gtk2_ardour/editor_ops.cc index 579b2403c6..815d50ae3e 100644 --- a/gtk2_ardour/editor_ops.cc +++ b/gtk2_ardour/editor_ops.cc @@ -2997,7 +2997,7 @@ Editor::cut_copy_regions (CutCopyOp op) insert_result = freezelist.insert (pl); if (insert_result.second) { pl->freeze (); - session->add_undo (pl->get_memento()); + session->add_command (MementoUndoCommand(*pl, pl->get_state())); } } } @@ -3055,7 +3055,7 @@ Editor::cut_copy_regions (CutCopyOp op) for (set::iterator pl = freezelist.begin(); pl != freezelist.end(); ++pl) { (*pl)->thaw (); - session->add_redo_no_execute ((*pl)->get_memento()); + session->add_command (MementoRedoCommand(*(*pl), *(*pl)->get_state())); } } diff --git a/libs/pbd3/pbd/memento_command.h b/libs/pbd3/pbd/memento_command.h index 8c2ddefcf7..1419c904bb 100644 --- a/libs/pbd3/pbd/memento_command.h +++ b/libs/pbd3/pbd/memento_command.h @@ -51,4 +51,38 @@ class MementoCommand : public Command XMLNode &before, &after; }; +template +class MementoUndoCommand : public MementoCommand +{ +public: + MementoUndoCommand(obj_T &obj, + XMLNode &before) + : obj(obj), before(before) {} + void operator() () { /* noop */ } + void undo() { obj.set_state(before); } + virtual XMLNode &serialize() + { + // obj.id + // key is "MementoCommand" or something + // before and after mementos + } +} + +template +class MementoRedoCommand : public MementoCommand +{ +public: + MementoUndoCommand(obj_T &obj, + XMLNode &after) + : obj(obj), after(after) {} + void operator() () { obj.set_state(after); } + void undo() { /* noop */ } + virtual XMLNode &serialize() + { + // obj.id + // key is "MementoCommand" or something + // before and after mementos + } +} + #endif // __lib_pbd_memento_h__ From ed31a9a262bcda7ac2ae390793f2302247ddca94 Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Wed, 26 Jul 2006 23:29:20 +0000 Subject: [PATCH 20/27] r200@gandalf: fugalh | 2006-07-26 17:28:46 -0600 Oops, missed one. git-svn-id: svn://localhost/ardour2/branches/undo@696 d708f5d6-7413-0410-9779-e7cbd77b26cf --- gtk2_ardour/automation_time_axis.cc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gtk2_ardour/automation_time_axis.cc b/gtk2_ardour/automation_time_axis.cc index 4680e3a35f..92c35cf185 100644 --- a/gtk2_ardour/automation_time_axis.cc +++ b/gtk2_ardour/automation_time_axis.cc @@ -551,7 +551,7 @@ AutomationTimeAxisView::reset_objects_one (AutomationLine& line, PointSelection& { AutomationList& alist (line.the_list()); - _session.add_undo (alist.get_memento()); + _session.add_command (MementoUndoCommand(alist, alist.get_state())); for (PointSelection::iterator i = selection.begin(); i != selection.end(); ++i) { From 656d56b12d0b86f9140956badd9c9e11d791549b Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Thu, 27 Jul 2006 00:19:12 +0000 Subject: [PATCH 21/27] r205@gandalf: fugalh | 2006-07-26 18:11:47 -0600 More Command conversions git-svn-id: svn://localhost/ardour2/branches/undo@697 d708f5d6-7413-0410-9779-e7cbd77b26cf --- gtk2_ardour/editor_markers.cc | 5 +++-- gtk2_ardour/region_gain_line.cc | 8 +++++--- gtk2_ardour/regionview.cc | 6 ++++-- gtk2_ardour/route_ui.cc | 12 ++++++++---- libs/ardour/session_transport.cc | 6 ++++-- 5 files changed, 24 insertions(+), 13 deletions(-) diff --git a/gtk2_ardour/editor_markers.cc b/gtk2_ardour/editor_markers.cc index 5be9cc2747..0610b6aa9f 100644 --- a/gtk2_ardour/editor_markers.cc +++ b/gtk2_ardour/editor_markers.cc @@ -906,10 +906,11 @@ Editor::new_transport_marker_menu_set_punch () XMLNode &after = session->locations()->get_state(); session->add_command (MementoCommand(*(session->locations()), before, after)); } else { - session->add_undo (retype_return(bind (mem_fun (*tpl, &Location::set), tpl->start(), tpl->end()))); - session->add_redo (retype_return(bind (mem_fun (*tpl, &Location::set), temp_location->start(), temp_location->end()))); + XMLNode &before = tpl->get_state(); tpl->set_hidden(false, this); tpl->set(temp_location->start(), temp_location->end()); + XMLNode &after = tpl->get_state(); + session->add_command (MementoCommand(*tpl, before, after)); } commit_reversible_command (); diff --git a/gtk2_ardour/region_gain_line.cc b/gtk2_ardour/region_gain_line.cc index 54b7fa5b56..526e8844ef 100644 --- a/gtk2_ardour/region_gain_line.cc +++ b/gtk2_ardour/region_gain_line.cc @@ -47,7 +47,8 @@ AudioRegionGainLine::start_drag (ControlPoint* cp, float fraction) { AutomationLine::start_drag(cp,fraction); if (!rv.region.envelope_active()) { - trackview.session().add_undo( bind( mem_fun(rv.region, &AudioRegion::set_envelope_active), false) ); + trackview.session().add_command(MementoUndoCommand(rv.region, rv.region.get_state())); + rv.region.set_envelope_active(false); } } @@ -63,9 +64,10 @@ AudioRegionGainLine::remove_point (ControlPoint& cp) XMLNode &before = get_state(); if (!rv.region.envelope_active()) { - trackview.session().add_undo( bind( mem_fun(rv.region, &AudioRegion::set_envelope_active), false) ); - trackview.session().add_redo( bind( mem_fun(rv.region, &AudioRegion::set_envelope_active), true) ); + XMLNode &before = rv.region.get_state(); rv.region.set_envelope_active(true); + XMLNode &after = rv.region.get_state(); + trackview.session().add_command(MementoCommand(rv.region, before, after)); } alist.erase (mr.start, mr.end); diff --git a/gtk2_ardour/regionview.cc b/gtk2_ardour/regionview.cc index fbd69105df..b8658d2e00 100644 --- a/gtk2_ardour/regionview.cc +++ b/gtk2_ardour/regionview.cc @@ -1148,9 +1148,11 @@ AudioRegionView::add_gain_point_event (ArdourCanvas::Item *item, GdkEvent *ev) if (!region.envelope_active()) { - trackview.session().add_undo( bind( mem_fun(region, &AudioRegion::set_envelope_active), false) ); + XMLNode &before, &after; + before = region.get_state(); region.set_envelope_active(true); - trackview.session().add_redo( bind( mem_fun(region, &AudioRegion::set_envelope_active), true) ); + after = region.get_state(); + trackview.session().add_command(MementoCommand(region, before, after)); } region.envelope().add (fx, y); diff --git a/gtk2_ardour/route_ui.cc b/gtk2_ardour/route_ui.cc index 4559058b8d..84aeb9c73b 100644 --- a/gtk2_ardour/route_ui.cc +++ b/gtk2_ardour/route_ui.cc @@ -570,8 +570,10 @@ void RouteUI::reversibly_apply_route_boolean (string name, void (Route::*func)(bool, void *), bool yn, void *arg) { _session.begin_reversible_command (name); - _session.add_undo (bind (mem_fun (_route, func), !yn, (void *) arg)); - _session.add_redo (bind (mem_fun (_route, func), yn, (void *) arg)); + XMLNode &before = _route.get_state(); + bind(mem_fun(_route, func), yn, arg)(); + XMLNode &after = _route.get_state(); + _session.add_command (MementoCommand(_route, before, after)); _session.commit_reversible_command (); } @@ -579,8 +581,10 @@ void RouteUI::reversibly_apply_audio_track_boolean (string name, void (AudioTrack::*func)(bool, void *), bool yn, void *arg) { _session.begin_reversible_command (name); - _session.add_undo (bind (mem_fun (*audio_track(), func), !yn, (void *) arg)); - _session.add_redo (bind (mem_fun (*audio_track(), func), yn, (void *) arg)); + XMLNode &before = audio_track()->get_state(); + bind (mem_fun (*audio_track(), func), yn, arg)(); + XMLNode &after = audio_track()->get_state(); + _session.add_command (MementoCommand(*audio_track(), before, after)); _session.commit_reversible_command (); } diff --git a/libs/ardour/session_transport.cc b/libs/ardour/session_transport.cc index 376dee11a2..1d3da72ad8 100644 --- a/libs/ardour/session_transport.cc +++ b/libs/ardour/session_transport.cc @@ -320,8 +320,10 @@ Session::non_realtime_stop (bool abort) } if (change_end) { - add_undo (sigc::retype_return(sigc::bind (mem_fun (*loc, &Location::set_end), loc->end()))); - add_redo (sigc::retype_return(sigc::bind (mem_fun (*loc, &Location::set_end), _transport_frame))); + XMLNode &before = loc->get_state(); + loc->set_end(_transport_frame); + XMLNode &after = loc->get_state(); + add_command (MementoCommand(*loc, before, after)); } _end_location_is_free = false; From 6aeb09062f4b4ff8e684f6f5ba80d47cb69665d5 Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Thu, 27 Jul 2006 00:19:27 +0000 Subject: [PATCH 22/27] r206@gandalf: fugalh | 2006-07-26 18:19:07 -0600 A couple more Command conversions. Now all that's left are the half dozen or so global mementos. git-svn-id: svn://localhost/ardour2/branches/undo@698 d708f5d6-7413-0410-9779-e7cbd77b26cf --- gtk2_ardour/editor_markers.cc | 5 +++-- gtk2_ardour/region_gain_line.cc | 2 +- 2 files changed, 4 insertions(+), 3 deletions(-) diff --git a/gtk2_ardour/editor_markers.cc b/gtk2_ardour/editor_markers.cc index 0610b6aa9f..96504cd0f8 100644 --- a/gtk2_ardour/editor_markers.cc +++ b/gtk2_ardour/editor_markers.cc @@ -880,10 +880,11 @@ Editor::new_transport_marker_menu_set_loop () session->add_command (MementoCommand(*(session->locations()), before, after)); } else { - session->add_undo (retype_return(bind (mem_fun (*tll, &Location::set), tll->start(), tll->end()))); - session->add_redo (retype_return(bind (mem_fun (*tll, &Location::set), temp_location->start(), temp_location->end()))); + XMLNode &before = tll->get_state(); tll->set_hidden (false, this); tll->set (temp_location->start(), temp_location->end()); + XMLNode &after = tll->get_state(); + session->add_command (MementoCommand(*tll, before, after)); } commit_reversible_command (); diff --git a/gtk2_ardour/region_gain_line.cc b/gtk2_ardour/region_gain_line.cc index 526e8844ef..2faa63151b 100644 --- a/gtk2_ardour/region_gain_line.cc +++ b/gtk2_ardour/region_gain_line.cc @@ -81,8 +81,8 @@ void AudioRegionGainLine::end_drag (ControlPoint* cp) { if (!rv.region.envelope_active()) { - trackview.session().add_redo( bind( mem_fun(rv.region, &AudioRegion::set_envelope_active), true) ); rv.region.set_envelope_active(true); + trackview.session().add_command(MementoRedoCommand(rv.region, rv.region.get_state())); } AutomationLine::end_drag(cp); } From 277b771a978b10580a46e19f19ae0cf2d8819f46 Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Fri, 28 Jul 2006 23:38:30 +0000 Subject: [PATCH 23/27] r209@gandalf: fugalh | 2006-07-28 17:38:21 -0600 global {solo,mute,record enable,metering} state commands. Same philosophy as the MementoCommand but using only the appropriate state and not the entire state of the session. git-svn-id: svn://localhost/ardour2/branches/undo@718 d708f5d6-7413-0410-9779-e7cbd77b26cf --- gtk2_ardour/route_ui.cc | 35 ++++++++------ libs/ardour/ardour/session.h | 52 ++++++++++++++++++-- libs/ardour/session_command.cc | 86 ++++++++++++++++++++++++++++++++++ 3 files changed, 155 insertions(+), 18 deletions(-) create mode 100644 libs/ardour/session_command.cc diff --git a/gtk2_ardour/route_ui.cc b/gtk2_ardour/route_ui.cc index 84aeb9c73b..6ecb4d6255 100644 --- a/gtk2_ardour/route_ui.cc +++ b/gtk2_ardour/route_ui.cc @@ -132,9 +132,10 @@ RouteUI::mute_press(GdkEventButton* ev) /* ctrl-shift-click applies change to all routes */ _session.begin_reversible_command (_("mute change")); - _session.add_undo (_session.global_mute_memento(this)); + Session::GlobalMuteStateCommand cmd(this); _session.set_all_mute (!_route.muted()); - _session.add_redo_no_execute (_session.global_mute_memento(this)); + cmd.mark(); + _session.add_command(cmd); _session.commit_reversible_command (); } else if (Keyboard::modifier_state_equals (ev->state, Keyboard::Control)) { @@ -207,9 +208,10 @@ RouteUI::solo_press(GdkEventButton* ev) /* ctrl-shift-click applies change to all routes */ _session.begin_reversible_command (_("solo change")); - _session.add_undo (_session.global_solo_memento(this)); + Session::GlobalSoloStateCommand cmd(this); _session.set_all_solo (!_route.soloed()); - _session.add_redo_no_execute (_session.global_solo_memento(this)); + cmd.mark(); + _session.add_command (cmd); _session.commit_reversible_command (); } else if (Keyboard::modifier_state_contains (ev->state, Keyboard::ModifierMask (Keyboard::Control|Keyboard::Alt))) { @@ -217,10 +219,11 @@ RouteUI::solo_press(GdkEventButton* ev) // ctrl-alt-click: exclusively solo this track, not a toggle */ _session.begin_reversible_command (_("solo change")); - _session.add_undo (_session.global_solo_memento(this)); + Session::GlobalSoloStateCommand cmd(this); _session.set_all_solo (false); _route.set_solo (true, this); - _session.add_redo_no_execute (_session.global_solo_memento(this)); + cmd.mark(); + _session.add_command(cmd); _session.commit_reversible_command (); } else if (Keyboard::modifier_state_equals (ev->state, Keyboard::Shift)) { @@ -280,7 +283,7 @@ RouteUI::rec_enable_press(GdkEventButton* ev) else if (Keyboard::modifier_state_equals (ev->state, Keyboard::ModifierMask (Keyboard::Control|Keyboard::Shift))) { _session.begin_reversible_command (_("rec-enable change")); - _session.add_undo (_session.global_record_enable_memento(this)); + Session::GlobalRecordEnableStateCommand cmd(this); if (rec_enable_button->get_active()) { _session.record_disenable_all (); @@ -288,7 +291,8 @@ RouteUI::rec_enable_press(GdkEventButton* ev) _session.record_enable_all (); } - _session.add_redo_no_execute (_session.global_record_enable_memento(this)); + cmd.mark(); + _session.add_command(cmd); _session.commit_reversible_command (); } else if (Keyboard::modifier_state_equals (ev->state, Keyboard::Control)) { @@ -557,9 +561,10 @@ RouteUI::set_mix_group_solo(Route& route, bool yn) if((mix_group = route.mix_group()) != 0){ _session.begin_reversible_command (_("mix group solo change")); - _session.add_undo (_session.global_solo_memento (this)); + Session::GlobalSoloStateCommand cmd(this); mix_group->apply(&Route::set_solo, yn, this); - _session.add_redo_no_execute (_session.global_solo_memento(this)); + cmd.mark(); + _session.add_command (cmd); _session.commit_reversible_command (); } else { reversibly_apply_route_boolean ("solo change", &Route::set_solo, !route.soloed(), this); @@ -595,9 +600,10 @@ RouteUI::set_mix_group_mute(Route& route, bool yn) if((mix_group = route.mix_group()) != 0){ _session.begin_reversible_command (_("mix group mute change")); - _session.add_undo (_session.global_mute_memento (this)); + Session::GlobalMuteStateCommand cmd(this); mix_group->apply(&Route::set_mute, yn, this); - _session.add_redo_no_execute (_session.global_mute_memento(this)); + cmd.mark(); + _session.add_command(cmd); _session.commit_reversible_command (); } else { reversibly_apply_route_boolean ("mute change", &Route::set_mute, !route.muted(), this); @@ -611,9 +617,10 @@ RouteUI::set_mix_group_rec_enable(Route& route, bool yn) if((mix_group = route.mix_group()) != 0){ _session.begin_reversible_command (_("mix group rec-enable change")); - _session.add_undo (_session.global_record_enable_memento (this)); + Session::GlobalRecordEnableStateCommand cmd(this); mix_group->apply (&Route::set_record_enable, yn, this); - _session.add_redo_no_execute (_session.global_record_enable_memento(this)); + cmd.mark(); + _session.add_command(cmd); _session.commit_reversible_command (); } else { reversibly_apply_route_boolean ("rec-enable change", &Route::set_record_enable, !_route.record_enabled(), this); diff --git a/libs/ardour/ardour/session.h b/libs/ardour/ardour/session.h index a9e8780c38..35c1a08e25 100644 --- a/libs/ardour/ardour/session.h +++ b/libs/ardour/ardour/session.h @@ -848,10 +848,54 @@ class Session : public sigc::trackable, public Stateful current_trans.add_command (cmd); } - UndoAction global_solo_memento (void *src); - UndoAction global_mute_memento (void *src); - UndoAction global_record_enable_memento (void *src); - UndoAction global_metering_memento (void *src); + // these commands are implemented in libs/ardour/session_command.cc + class GlobalSoloStateCommand : public Command + { + GlobalRouteBooleanState before, after; + void *src; + public: + GlobalSoloStateCommand(void *src); + void operator()(); + void undo(); + XMLNode &serialize(); + void mark(); + } + + class GlobalMuteStateCommand : public Command + { + GlobalRouteBooleanState before, after; + void *src; + public: + GlobalMuteStateCommand(void *src); + void operator()(); + void undo(); + XMLNode &serialize(); + void mark(); + } + + class GlobalRecordEnableStateCommand : public Command + { + GlobalRouteBooleanState before, after; + void *src; + public: + GlobalRecordEnableStateCommand(void *src); + void operator()(); + void undo(); + XMLNode &serialize(); + void mark(); + } + + class GlobalMeteringStateCommand : public Command + { + GlobalRouteMeterState before, after; + void *src; + public: + GlobalMeteringStateCommand(void *src); + void operator()(); + void undo(); + XMLNode &serialize(); + void mark(); + } /* edit mode */ diff --git a/libs/ardour/session_command.cc b/libs/ardour/session_command.cc new file mode 100644 index 0000000000..8693a9adc4 --- /dev/null +++ b/libs/ardour/session_command.cc @@ -0,0 +1,86 @@ +#include + +// solo +Session::GlobalSoloStateCommand::GlobalSoloStateCommand(void *src) : src(src) +{ + after = before = get_global_route_boolean(&Route::soloed); +} +void Session::GlobalSoloStateCommand::mark() +{ + after = get_global_route_boolean(&Route::soloed); +} +void operator()() +{ + set_global_solo(after, src); +} +void undo() +{ + set_global_solo(before, src); +} +XMLNode &serialize() +{ +} + +// mute +Session::GlobalMuteStateCommand::GlobalMuteStateCommand(void *src) : src(src) +{ + after = before = get_global_route_boolean(&Route::muted); +} +void Session::GlobalMuteStateCommand::mark() +{ + after = get_global_route_boolean(&Route::muted); +} +void operator()() +{ + set_global_mute(after, src); +} +void undo() +{ + set_global_mute(before, src); +} +XMLNode &serialize() +{ +} + +// record enable +Session::GlobalRecordEnableStateCommand::GlobalRecordEnableStateCommand(void *src) : src(src) +{ + after = before = get_global_route_boolean(&Route::record_enabled); +} +void Session::GlobalRecordEnableStateCommand::mark() +{ + after = get_global_route_boolean(&Route::record_enabled); +} +void operator()() +{ + set_global_record_enable(after, src); +} +void undo() +{ + set_global_record_enable(before, src); +} +XMLNode &serialize() +{ +} + +// metering +Session::GlobalMeteringStateCommand::GlobalMeteringStateCommand(void *src) : src(src) +{ + after = before = get_global_route_metering(); +} +void Session::GlobalMeteringStateCommand::mark() +{ + after = get_global_route_metering(); +} +void operator()() +{ + set_global_route_metering(after, src); +} +void undo() +{ + set_global_route_metering(before, src); +} +XMLNode &serialize() +{ +} + From 1f1c4981de73b13d0b7617d8ebe89d9f22dddec3 Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Sat, 29 Jul 2006 03:17:11 +0000 Subject: [PATCH 24/27] Compiles, but doesn't link. The link errors are mostly expected and are tomorrow's task. git-svn-id: svn://localhost/ardour2/branches/undo@719 d708f5d6-7413-0410-9779-e7cbd77b26cf --- gtk2_ardour/audio_time_axis.cc | 14 +-- gtk2_ardour/automation_line.cc | 9 +- gtk2_ardour/automation_line.h | 5 +- gtk2_ardour/automation_time_axis.cc | 19 ++- gtk2_ardour/editor.cc | 10 +- gtk2_ardour/editor.h | 2 +- gtk2_ardour/editor_audio_import.cc | 3 +- gtk2_ardour/editor_keyboard.cc | 3 +- gtk2_ardour/editor_markers.cc | 25 ++-- gtk2_ardour/editor_mouse.cc | 118 +++++++++---------- gtk2_ardour/editor_ops.cc | 100 ++++++++-------- gtk2_ardour/editor_tempodisplay.cc | 15 +-- gtk2_ardour/editor_timefx.cc | 3 +- gtk2_ardour/gain_automation_time_axis.cc | 8 +- gtk2_ardour/location_ui.cc | 12 +- gtk2_ardour/pan_automation_time_axis.cc | 8 +- gtk2_ardour/redirect_automation_time_axis.cc | 8 +- gtk2_ardour/region_gain_line.cc | 9 +- gtk2_ardour/regionview.cc | 10 +- gtk2_ardour/route_ui.cc | 33 +++--- libs/ardour/ardour/automation_event.h | 8 +- libs/ardour/ardour/session.h | 10 +- libs/ardour/audio_diskstream.cc | 3 +- libs/ardour/session_command.cc | 2 + libs/ardour/session_state.cc | 4 +- libs/ardour/session_transport.cc | 3 +- libs/pbd3/pbd/memento_command.h | 34 +++--- libs/pbd3/pbd/serializable.h | 1 + libs/pbd3/pbd/undo.h | 9 +- libs/pbd3/undo.cc | 12 +- 30 files changed, 257 insertions(+), 243 deletions(-) diff --git a/gtk2_ardour/audio_time_axis.cc b/gtk2_ardour/audio_time_axis.cc index ebc97be77b..857adff6b9 100644 --- a/gtk2_ardour/audio_time_axis.cc +++ b/gtk2_ardour/audio_time_axis.cc @@ -30,6 +30,7 @@ #include #include #include +#include #include #include @@ -1739,14 +1740,13 @@ AudioTimeAxisView::cut_copy_clear (Selection& selection, CutCopyOp op) } } - XMLNode &before, &after; + XMLNode &before = playlist->get_state(); switch (op) { case Cut: - before = playlist->get_state(); if ((what_we_got = playlist->cut (time)) != 0) { editor.get_cut_buffer().add (what_we_got); - after = playlist->get_state(); - _session.add_command (MementoCommand(*playlist, before, after)); + XMLNode &after = playlist->get_state(); + _session.add_command (new MementoCommand(*playlist, before, after)); ret = true; } break; @@ -1757,9 +1757,9 @@ AudioTimeAxisView::cut_copy_clear (Selection& selection, CutCopyOp op) break; case Clear: - before = playlist->get_state(); if ((what_we_got = playlist->cut (time)) != 0) { - _session.add_command(MementoCommand(*playlist, before, after)); + XMLNode &after = playlist->get_state(); + _session.add_command(new MementoCommand(*playlist, before, after)); what_we_got->unref (); ret = true; } @@ -1790,7 +1790,7 @@ AudioTimeAxisView::paste (jack_nframes_t pos, float times, Selection& selection, XMLNode &before = playlist->get_state(); playlist->paste (**p, pos, times); - _session.add_command(MementoCommand(*playlist, before, + _session.add_command(new MementoCommand(*playlist, before, playlist->get_state())); return true; diff --git a/gtk2_ardour/automation_line.cc b/gtk2_ardour/automation_line.cc index bd7ed326d8..a8f2952ed9 100644 --- a/gtk2_ardour/automation_line.cc +++ b/gtk2_ardour/automation_line.cc @@ -23,6 +23,7 @@ #include #include +#include #include #include @@ -887,7 +888,7 @@ AutomationLine::start_drag (ControlPoint* cp, float fraction) } trackview.editor.current_session()->begin_reversible_command (str); - trackview.editor.current_session()->add_command (MementoUndoCommand(*this, get_state())); + trackview.editor.current_session()->add_command (new MementoUndoCommand(*this, get_state())); first_drag_fraction = fraction; last_drag_fraction = fraction; @@ -936,7 +937,7 @@ AutomationLine::end_drag (ControlPoint* cp) update_pending = false; - trackview.editor.current_session()->add_command (MementoRedoCommand(*this, get_state())); + trackview.editor.current_session()->add_command (new MementoRedoCommand(*this, get_state())); trackview.editor.current_session()->commit_reversible_command (); trackview.editor.current_session()->set_dirty (); } @@ -1017,7 +1018,7 @@ AutomationLine::remove_point (ControlPoint& cp) alist.erase (mr.start, mr.end); - trackview.editor.current_session()->add_command(MementoCommand(*this, before, get_state())); + trackview.editor.current_session()->add_command(new MementoCommand(*this, before, get_state())); trackview.editor.current_session()->commit_reversible_command (); trackview.editor.current_session()->set_dirty (); } @@ -1227,7 +1228,7 @@ AutomationLine::clear () /* parent must create command */ XMLNode &before = get_state(); alist.clear(); - trackview.editor.current_session()->add_command (MementoCommand(*this, before, get_state())); + trackview.editor.current_session()->add_command (new MementoCommand(*this, before, get_state())); trackview.editor.current_session()->commit_reversible_command (); trackview.editor.current_session()->set_dirty (); } diff --git a/gtk2_ardour/automation_line.h b/gtk2_ardour/automation_line.h index e922de6c80..9c6b932dfd 100644 --- a/gtk2_ardour/automation_line.h +++ b/gtk2_ardour/automation_line.h @@ -94,7 +94,7 @@ class ControlPoint ShapeType _shape; }; -class AutomationLine : public sigc::trackable +class AutomationLine : public sigc::trackable, public Stateful { public: AutomationLine (const string & name, TimeAxisView&, ArdourCanvas::Group&, ARDOUR::AutomationList&); @@ -158,6 +158,9 @@ class AutomationLine : public sigc::trackable bool is_last_point (ControlPoint &); bool is_first_point (ControlPoint &); + XMLNode& get_state (void); + int set_state (const XMLNode&); + protected: string _name; guint32 _height; diff --git a/gtk2_ardour/automation_time_axis.cc b/gtk2_ardour/automation_time_axis.cc index 92c35cf185..080a440bc9 100644 --- a/gtk2_ardour/automation_time_axis.cc +++ b/gtk2_ardour/automation_time_axis.cc @@ -1,4 +1,5 @@ #include +#include #include "ardour_ui.h" #include "automation_time_axis.h" @@ -500,14 +501,13 @@ AutomationTimeAxisView::cut_copy_clear_one (AutomationLine& line, Selection& sel AutomationList& alist (line.the_list()); bool ret = false; - XMLNode &before, &after; - before = alist.get_state(); + XMLNode &before = alist.get_state(); switch (op) { case Cut: if ((what_we_got = alist.cut (selection.time.front().start, selection.time.front().end)) != 0) { editor.get_cut_buffer().add (what_we_got); - _session.add_command(MementoCommand(alist, before, alist.get_state())); + _session.add_command(new MementoCommand(alist, before, alist.get_state())); ret = true; } break; @@ -519,7 +519,7 @@ AutomationTimeAxisView::cut_copy_clear_one (AutomationLine& line, Selection& sel case Clear: if ((what_we_got = alist.cut (selection.time.front().start, selection.time.front().end)) != 0) { - _session.add_command(MementoCommand(alist, before, alist.get_state())); + _session.add_command(new MementoCommand(alist, before, alist.get_state())); delete what_we_got; what_we_got = 0; ret = true; @@ -551,7 +551,7 @@ AutomationTimeAxisView::reset_objects_one (AutomationLine& line, PointSelection& { AutomationList& alist (line.the_list()); - _session.add_command (MementoUndoCommand(alist, alist.get_state())); + _session.add_command (new MementoUndoCommand(alist, alist.get_state())); for (PointSelection::iterator i = selection.begin(); i != selection.end(); ++i) { @@ -581,9 +581,8 @@ AutomationTimeAxisView::cut_copy_clear_objects_one (AutomationLine& line, PointS AutomationList* what_we_got = 0; AutomationList& alist (line.the_list()); bool ret = false; - XMLNode &before, &after; - before = alist.get_state(); + XMLNode &before = alist.get_state(); for (PointSelection::iterator i = selection.begin(); i != selection.end(); ++i) { @@ -595,7 +594,7 @@ AutomationTimeAxisView::cut_copy_clear_objects_one (AutomationLine& line, PointS case Cut: if ((what_we_got = alist.cut ((*i).start, (*i).end)) != 0) { editor.get_cut_buffer().add (what_we_got); - _session.add_command (MementoCommand(alist, before, alist.get_state())); + _session.add_command (new MementoCommand(alist, before, alist.get_state())); ret = true; } break; @@ -607,7 +606,7 @@ AutomationTimeAxisView::cut_copy_clear_objects_one (AutomationLine& line, PointS case Clear: if ((what_we_got = alist.cut ((*i).start, (*i).end)) != 0) { - _session.add_command (MementoCommand(alist, before, alist.get_state())); + _session.add_command (new MementoCommand(alist, before, alist.get_state())); delete what_we_got; what_we_got = 0; ret = true; @@ -666,7 +665,7 @@ AutomationTimeAxisView::paste_one (AutomationLine& line, jack_nframes_t pos, flo XMLNode &before = alist.get_state(); alist.paste (copy, pos, times); - _session.add_command (MementoCommand(alist, before, alist.get_state())); + _session.add_command (new MementoCommand(alist, before, alist.get_state())); return true; } diff --git a/gtk2_ardour/editor.cc b/gtk2_ardour/editor.cc index 0b9359bae7..6472974093 100644 --- a/gtk2_ardour/editor.cc +++ b/gtk2_ardour/editor.cc @@ -28,6 +28,7 @@ #include #include +#include #include #include @@ -2970,7 +2971,7 @@ void Editor::begin_reversible_command (string name) { if (session) { - before = get_state(); + before = &get_state(); session->begin_reversible_command (name); } } @@ -2979,12 +2980,7 @@ void Editor::commit_reversible_command () { if (session) { - // yes, cmd lasts long enough to be copied onto the action - // list in the history, but this has the potential to be a - // problem if memory management of actions changes in - // UndoTransaction - MementoCommand cmd(*this, before, get_state()); - session->commit_reversible_command (&cmd); + session->commit_reversible_command (new MementoCommand(*this, *before, get_state())); } } diff --git a/gtk2_ardour/editor.h b/gtk2_ardour/editor.h index 2ef475a5e4..478a8c96ab 100644 --- a/gtk2_ardour/editor.h +++ b/gtk2_ardour/editor.h @@ -1608,7 +1608,7 @@ class Editor : public PublicEditor UndoAction get_memento() const; - XMLNode &before; /* used in *_reversible_command */ + XMLNode *before; /* used in *_reversible_command */ void begin_reversible_command (string cmd_name); void commit_reversible_command (); diff --git a/gtk2_ardour/editor_audio_import.cc b/gtk2_ardour/editor_audio_import.cc index 4cdc38dcf3..2c64f2cf15 100644 --- a/gtk2_ardour/editor_audio_import.cc +++ b/gtk2_ardour/editor_audio_import.cc @@ -31,6 +31,7 @@ #include #include #include +#include #include "ardour_ui.h" #include "editor.h" @@ -320,7 +321,7 @@ int begin_reversible_command (_("insert sndfile")); XMLNode &before = playlist->get_state(); playlist->add_region (*copy, pos); - session->add_command (MementoCommand(*playlist, before, playlist->get_state())); + session->add_command (new MementoCommand(*playlist, before, playlist->get_state())); commit_reversible_command (); pos += region.length(); diff --git a/gtk2_ardour/editor_keyboard.cc b/gtk2_ardour/editor_keyboard.cc index df9bbf00ba..b665f8b0a6 100644 --- a/gtk2_ardour/editor_keyboard.cc +++ b/gtk2_ardour/editor_keyboard.cc @@ -20,6 +20,7 @@ #include #include +#include #include "editor.h" #include "regionview.h" @@ -107,7 +108,7 @@ Editor::kbd_mute_unmute_region () entered_regionview->region.set_muted (!entered_regionview->region.muted()); XMLNode &after = entered_regionview->region.playlist()->get_state(); - session->add_command (MementoCommand(entered_regionview->region.playlist(), before, after)); + session->add_command (new MementoCommand(*(entered_regionview->region.playlist()), before, after)); commit_reversible_command(); } } diff --git a/gtk2_ardour/editor_markers.cc b/gtk2_ardour/editor_markers.cc index 96504cd0f8..c4d8f3143f 100644 --- a/gtk2_ardour/editor_markers.cc +++ b/gtk2_ardour/editor_markers.cc @@ -26,6 +26,7 @@ #include #include +#include #include "editor.h" #include "marker.h" @@ -290,11 +291,10 @@ Editor::mouse_add_new_marker (jack_nframes_t where) if (session) { Location *location = new Location (where, where, "mark", Location::IsMark); session->begin_reversible_command (_("add marker")); - XMLNode &before, &after; - before = session->locations()->get_state(); + XMLNode &before = session->locations()->get_state(); session->locations()->add (location, true); - after = session->locations()->get_state(); - session->add_command (MementoCommand(*(session->locations()), before, after)); + XMLNode &after = session->locations()->get_state(); + session->add_command (new MementoCommand(*(session->locations()), before, after)); session->commit_reversible_command (); } } @@ -331,11 +331,10 @@ gint Editor::really_remove_marker (Location* loc) { session->begin_reversible_command (_("remove marker")); - XMLNode &before, &after; - before = session->locations()->get_state(); + XMLNode &before = session->locations()->get_state(); session->locations()->remove (loc); - after = session->locations()->get_state(); - session->add_command (MementoCommand(*(session->locations()), before, after)); + XMLNode &after = session->locations()->get_state(); + session->add_command (new MementoCommand(*(session->locations()), before, after)); session->commit_reversible_command (); return FALSE; } @@ -848,7 +847,7 @@ Editor::marker_menu_rename () loc->set_name (txt); XMLNode &after = session->locations()->get_state(); - session->add_command (MementoCommand(*(session->locations()), before, after)); + session->add_command (new MementoCommand(*(session->locations()), before, after)); commit_reversible_command (); } @@ -877,14 +876,14 @@ Editor::new_transport_marker_menu_set_loop () session->locations()->add (loc, true); session->set_auto_loop_location (loc); XMLNode &after = session->locations()->get_state(); - session->add_command (MementoCommand(*(session->locations()), before, after)); + session->add_command (new MementoCommand(*(session->locations()), before, after)); } else { XMLNode &before = tll->get_state(); tll->set_hidden (false, this); tll->set (temp_location->start(), temp_location->end()); XMLNode &after = tll->get_state(); - session->add_command (MementoCommand(*tll, before, after)); + session->add_command (new MementoCommand(*tll, before, after)); } commit_reversible_command (); @@ -905,13 +904,13 @@ Editor::new_transport_marker_menu_set_punch () session->locations()->add (tpl, true); session->set_auto_punch_location (tpl); XMLNode &after = session->locations()->get_state(); - session->add_command (MementoCommand(*(session->locations()), before, after)); + session->add_command (new MementoCommand(*(session->locations()), before, after)); } else { XMLNode &before = tpl->get_state(); tpl->set_hidden(false, this); tpl->set(temp_location->start(), temp_location->end()); XMLNode &after = tpl->get_state(); - session->add_command (MementoCommand(*tpl, before, after)); + session->add_command (new MementoCommand(*tpl, before, after)); } commit_reversible_command (); diff --git a/gtk2_ardour/editor_mouse.cc b/gtk2_ardour/editor_mouse.cc index 4b17c9e6b0..c7199984a8 100644 --- a/gtk2_ardour/editor_mouse.cc +++ b/gtk2_ardour/editor_mouse.cc @@ -27,6 +27,7 @@ #include #include +#include #include "ardour_ui.h" #include "editor.h" @@ -1812,15 +1813,14 @@ Editor::fade_in_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* even } begin_reversible_command (_("change fade in length")); - XMLNode &before, &after; - before = arv->region.get_state(); + XMLNode &before = arv->region.get_state(); arv->region.set_fade_in_length (fade_length); - after = arv->region.get_state(); - session->add_command(MementoCommand(arv->region, - before, - after)); + XMLNode &after = arv->region.get_state(); + session->add_command(new MementoCommand(arv->region, + before, + after)); commit_reversible_command (); fade_in_drag_motion_callback (item, event); } @@ -1910,13 +1910,12 @@ Editor::fade_out_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* eve } begin_reversible_command (_("change fade out length")); - XMLNode &before, &after; - before = arv->region.get_state(); + XMLNode &before = arv->region.get_state(); arv->region.set_fade_out_length (fade_length); - after = arv->region.get_state(); - session->add_command(MementoCommand(arv->region, before, after)); + XMLNode &after = arv->region.get_state(); + session->add_command(new MementoCommand(arv->region, before, after)); commit_reversible_command (); fade_out_drag_motion_callback (item, event); @@ -2150,8 +2149,7 @@ Editor::marker_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event begin_reversible_command ( _("move marker") ); - XMLNode &before, &after; - before = session->locations()->get_state(); + XMLNode &before = session->locations()->get_state(); Location * location = find_location_from_marker (marker, is_start); @@ -2159,8 +2157,8 @@ Editor::marker_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event location->set (drag_info.copied_location->start(), drag_info.copied_location->end()); } - after = session->locations()->get_state(); - session->add_command(MementoCommand(session->locations(), before, after)); + XMLNode &after = session->locations()->get_state(); + session->add_command(new MementoCommand(*(session->locations()), before, after)); commit_reversible_command (); marker_drag_line->hide(); @@ -2272,14 +2270,12 @@ Editor::meter_marker_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* TempoMap& map (session->tempo_map()); map.bbt_time (drag_info.last_pointer_frame, when); - XMLNode &before, &after; - if (drag_info.copy == true) { begin_reversible_command (_("copy meter mark")); - before = map.get_state(); + XMLNode &before = map.get_state(); map.add_meter (marker->meter(), when); - after = map.get_state(); - session->add_command(MementoCommand(map, before, after)); + XMLNode &after = map.get_state(); + session->add_command(new MementoCommand(map, before, after)); commit_reversible_command (); // delete the dummy marker we used for visual representation of copying. @@ -2287,10 +2283,10 @@ Editor::meter_marker_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* delete marker; } else { begin_reversible_command (_("move meter mark")); - before = map.get_state(); + XMLNode &before = map.get_state(); map.move_meter (marker->meter(), when); - after = map.get_state(); - session->add_command(MementoCommand(map, before, after)); + XMLNode &after = map.get_state(); + session->add_command(new MementoCommand(map, before, after)); commit_reversible_command (); } } @@ -2406,14 +2402,12 @@ Editor::tempo_marker_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* TempoMap& map (session->tempo_map()); map.bbt_time (drag_info.last_pointer_frame, when); - XMLNode &before, &after; - if (drag_info.copy == true) { begin_reversible_command (_("copy tempo mark")); - before = map.get_state(); + XMLNode &before = map.get_state(); map.add_tempo (marker->tempo(), when); - after = map.get_state(); - session->add_command (MementoCommand(map, before, after)); + XMLNode &after = map.get_state(); + session->add_command (new MementoCommand(map, before, after)); commit_reversible_command (); // delete the dummy marker we used for visual representation of copying. @@ -2421,10 +2415,10 @@ Editor::tempo_marker_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* delete marker; } else { begin_reversible_command (_("move tempo mark")); - before = map.get_state(); + XMLNode &before = map.get_state(); map.move_tempo (marker->tempo(), when); - after = map.get_state(); - session->add_command (MementoCommand(map, before, after)); + XMLNode &after = map.get_state(); + session->add_command (new MementoCommand(map, before, after)); commit_reversible_command (); } } @@ -2787,7 +2781,7 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) insert_result = affected_playlists.insert (to_playlist); if (insert_result.second) { - session->add_command (MementoUndoCommand(*to_playlist, to_playlist->get_state())); + session->add_command (new MementoUndoCommand(*to_playlist, to_playlist->get_state())); } latest_regionview = 0; @@ -3225,7 +3219,7 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) insert_result = motion_frozen_playlists.insert (pl); if (insert_result.second) { pl->freeze(); - session->add_command(MementoUndoCommand(*pl, pl->get_state())); + session->add_command(new MementoUndoCommand(*pl, pl->get_state())); } } } @@ -3353,7 +3347,7 @@ Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event insert_result = motion_frozen_playlists.insert(to_playlist); if (insert_result.second) { to_playlist->freeze(); - session->add_command(MementoUndoCommand(*to_playlist, to_playlist->get_state())); + session->add_command(new MementoUndoCommand(*to_playlist, to_playlist->get_state())); } } @@ -3435,7 +3429,7 @@ Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event out: for (set::iterator p = motion_frozen_playlists.begin(); p != motion_frozen_playlists.end(); ++p) { (*p)->thaw (); - session->add_command (MementoRedoCommand(*(*p), (*p)->get_state())); + session->add_command (new MementoRedoCommand(*(*p), (*p)->get_state())); } motion_frozen_playlists.clear (); @@ -3630,10 +3624,10 @@ Editor::start_selection_grab (ArdourCanvas::Item* item, GdkEvent* event) Playlist* playlist = clicked_trackview->playlist(); - before = playlist->get_state(); + before = &(playlist->get_state()); clicked_trackview->playlist()->add_region (*region, selection->time[clicked_selection].start); - after = playlist->get_state(); - session->add_command(MementoCommand(*playlist, before, after)); + XMLNode &after = playlist->get_state(); + session->add_command(new MementoCommand(*playlist, *before, after)); commit_reversible_command (); @@ -3997,7 +3991,7 @@ Editor::trim_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) Playlist * pl = (*i)->region.playlist(); insert_result = motion_frozen_playlists.insert (pl); if (insert_result.second) { - session->add_command(MementoUndoCommand(*pl, pl->get_state())); + session->add_command(new MementoUndoCommand(*pl, pl->get_state())); } } } @@ -4187,7 +4181,7 @@ Editor::trim_finished_callback (ArdourCanvas::Item* item, GdkEvent* event) for (set::iterator p = motion_frozen_playlists.begin(); p != motion_frozen_playlists.end(); ++p) { //(*p)->thaw (); - session->add_command (MementoRedoCommand(*(*p), (*p)->get_state())); + session->add_command (new MementoRedoCommand(*(*p), (*p)->get_state())); } motion_frozen_playlists.clear (); @@ -4221,24 +4215,22 @@ Editor::point_trim (GdkEvent* event) i != selection->audio_regions.by_layer().end(); ++i) { if (!(*i)->region.locked()) { - XMLNode &before, &after; Playlist *pl = (*i)->region.playlist(); - before = pl->get_state(); + XMLNode &before = pl->get_state(); (*i)->region.trim_front (new_bound, this); - after = pl->get_state(); - session->add_command(MementoCommand(*pl, before, after)); + XMLNode &after = pl->get_state(); + session->add_command(new MementoCommand(*pl, before, after)); } } } else { if (!rv->region.locked()) { - XMLNode &before, &after; Playlist *pl = rv->region.playlist(); - before = pl->get_state(); + XMLNode &before = pl->get_state(); rv->region.trim_front (new_bound, this); - after = pl->get_state(); - session->add_command(MementoCommand(*pl, before, after)); + XMLNode &after = pl->get_state(); + session->add_command(new MementoCommand(*pl, before, after)); } } @@ -4254,24 +4246,22 @@ Editor::point_trim (GdkEvent* event) for (list::const_iterator i = selection->audio_regions.by_layer().begin(); i != selection->audio_regions.by_layer().end(); ++i) { if (!(*i)->region.locked()) { - XMLNode &before, &after; Playlist *pl = (*i)->region.playlist(); - before = pl->get_state(); + XMLNode &before = pl->get_state(); (*i)->region.trim_end (new_bound, this); - after = pl->get_state(); - session->add_command(MementoCommand(*pl, before, after)); + XMLNode &after = pl->get_state(); + session->add_command(new MementoCommand(*pl, before, after)); } } } else { if (!rv->region.locked()) { - XMLNode &before, &after; Playlist *pl = rv->region.playlist(); - before = pl->get_state(); + XMLNode &before = pl->get_state(); rv->region.trim_end (new_bound, this); - after = pl->get_state(); - session->add_command (MementoCommand(*pl, before, after)); + XMLNode &after = pl->get_state(); + session->add_command (new MementoCommand(*pl, before, after)); } } @@ -4294,7 +4284,7 @@ Editor::thaw_region_after_trim (AudioRegionView& rv) region.thaw (_("trimmed region")); XMLNode &after = region.playlist()->get_state(); - session->add_command (MementoRedoCommand(*(region.playlist()), after)); + session->add_command (new MementoRedoCommand(*(region.playlist()), after)); rv.unhide_envelope (); } @@ -4431,18 +4421,19 @@ Editor::end_range_markerbar_op (ArdourCanvas::Item* item, GdkEvent* event) switch (range_marker_op) { case CreateRangeMarker: + { begin_reversible_command (_("new range marker")); - XMLNode &before, &after; - before = session->locations()->get_state(); + XMLNode &before = session->locations()->get_state(); newloc = new Location(temp_location->start(), temp_location->end(), "unnamed", Location::IsRangeMarker); session->locations()->add (newloc, true); - after = session->locations()->get_state(); - session->add_command(MementoCommand(session->locations(), before, after)); + XMLNode &after = session->locations()->get_state(); + session->add_command(new MementoCommand(*(session->locations()), before, after)); commit_reversible_command (); range_bar_drag_rect->hide(); range_marker_drag_rect->hide(); break; + } case CreateTransportMarker: // popup menu to pick loop or punch @@ -4812,11 +4803,10 @@ Editor::mouse_brush_insert_region (AudioRegionView* rv, jack_nframes_t pos) Playlist* playlist = atv->playlist(); double speed = atv->get_diskstream()->speed(); - XMLNode &before, &after; - before = playlist->get_state(); + XMLNode &before = playlist->get_state(); playlist->add_region (*(new AudioRegion (rv->region)), (jack_nframes_t) (pos * speed)); - after = playlist->get_state(); - session->add_command(MementoCommand(*playlist, before, after)); + XMLNode &after = playlist->get_state(); + session->add_command(new MementoCommand(*playlist, before, after)); // playlist is frozen, so we have to update manually diff --git a/gtk2_ardour/editor_ops.cc b/gtk2_ardour/editor_ops.cc index 815d50ae3e..e9fcc028e6 100644 --- a/gtk2_ardour/editor_ops.cc +++ b/gtk2_ardour/editor_ops.cc @@ -28,6 +28,7 @@ #include #include #include +#include #include #include @@ -207,11 +208,10 @@ Editor::split_regions_at (jack_nframes_t where, AudioRegionSelection& regions) _new_regionviews_show_envelope = (*a)->envelope_visible(); if (pl) { - XMLNode &before, &after; - before = pl->get_state(); + XMLNode &before = pl->get_state(); pl->split_region ((*a)->region, where); - after = pl->get_state(); - session->add_command(MementoCommand(*pl, before, after)); + XMLNode &after = pl->get_state(); + session->add_command(new MementoCommand(*pl, before, after)); } a = tmp; @@ -234,7 +234,7 @@ Editor::remove_clicked_region () XMLNode &before = playlist->get_state(); playlist->remove_region (&clicked_regionview->region); XMLNode &after = playlist->get_state(); - session->add_command(MementoCommand(*playlist, before, after)); + session->add_command(new MementoCommand(*playlist, before, after)); commit_reversible_command (); } @@ -410,7 +410,7 @@ Editor::nudge_forward (bool next) XMLNode &before = r.playlist()->get_state(); r.set_position (r.position() + distance, this); XMLNode &after = r.playlist()->get_state(); - session->add_command (MementoCommand(*(r.playlist()), before, after)); + session->add_command (new MementoCommand(*(r.playlist()), before, after)); } commit_reversible_command (); @@ -450,7 +450,7 @@ Editor::nudge_backward (bool next) r.set_position (0, this); } XMLNode &after = r.playlist()->get_state(); - session->add_command(MementoCommand(*(r.playlist()), before, after)); + session->add_command(new MementoCommand(*(r.playlist()), before, after)); } commit_reversible_command (); @@ -483,11 +483,10 @@ Editor::nudge_forward_capture_offset () for (AudioRegionSelection::iterator i = selection->audio_regions.begin(); i != selection->audio_regions.end(); ++i) { AudioRegion& r ((*i)->region); - XMLNode &before, &after; - before = r.playlist()->get_state(); + XMLNode &before = r.playlist()->get_state(); r.set_position (r.position() + distance, this); - after = r.playlist()->get_state(); - session->add_command(MementoCommand(*(r.playlist()), before, after)); + XMLNode &after = r.playlist()->get_state(); + session->add_command(new MementoCommand(*(r.playlist()), before, after)); } commit_reversible_command (); @@ -519,7 +518,7 @@ Editor::nudge_backward_capture_offset () r.set_position (0, this); } XMLNode &after = r.playlist()->get_state(); - session->add_command(MementoCommand(*(r.playlist()), before, after)); + session->add_command(new MementoCommand(*(r.playlist()), before, after)); } commit_reversible_command (); @@ -1299,7 +1298,7 @@ Editor::add_location_from_selection () XMLNode &before = session->locations()->get_state(); session->locations()->add (location, true); XMLNode &after = session->locations()->get_state(); - session->add_command(MementoCommand(*(session->locations()), before, after)); + session->add_command(new MementoCommand(*(session->locations()), before, after)); session->commit_reversible_command (); } @@ -1313,7 +1312,7 @@ Editor::add_location_from_playhead_cursor () XMLNode &before = session->locations()->get_state(); session->locations()->add (location, true); XMLNode &after = session->locations()->get_state(); - session->add_command(MementoCommand(*(session->locations()), before, after)); + session->add_command(new MementoCommand(*(session->locations()), before, after)); session->commit_reversible_command (); } @@ -1332,7 +1331,7 @@ Editor::add_location_from_audio_region () XMLNode &before = session->locations()->get_state(); session->locations()->add (location, true); XMLNode &after = session->locations()->get_state(); - session->add_command(MementoCommand(*(session->locations()), before, after)); + session->add_command(new MementoCommand(*(session->locations()), before, after)); session->commit_reversible_command (); } @@ -1751,7 +1750,7 @@ Editor::clear_markers () XMLNode &before = session->locations()->get_state(); session->locations()->clear_markers (); XMLNode &after = session->locations()->get_state(); - session->add_command(MementoCommand(*(session->locations()), before, after)); + session->add_command(new MementoCommand(*(session->locations()), before, after)); session->commit_reversible_command (); } } @@ -1772,7 +1771,7 @@ Editor::clear_ranges () if (punchloc) session->locations()->add (punchloc); XMLNode &after = session->locations()->get_state(); - session->add_command(MementoCommand(*(session->locations()), before, after)); + session->add_command(new MementoCommand(*(session->locations()), before, after)); session->commit_reversible_command (); } } @@ -1784,7 +1783,7 @@ Editor::clear_locations () XMLNode &before = session->locations()->get_state(); session->locations()->clear (); XMLNode &after = session->locations()->get_state(); - session->add_command(MementoCommand(*(sessions->locations()), before, after)); + session->add_command(new MementoCommand(*(session->locations()), before, after)); session->commit_reversible_command (); session->locations()->clear (); } @@ -1834,7 +1833,7 @@ Editor::insert_region_list_drag (AudioRegion& region, int x, int y) begin_reversible_command (_("insert dragged region")); XMLNode &before = playlist->get_state(); playlist->add_region (*(new AudioRegion (region)), where, 1.0); - session->add_command(MementoCommand(*playlist, before, playlist->get_state())); + session->add_command(new MementoCommand(*playlist, before, playlist->get_state())); commit_reversible_command (); } @@ -1870,7 +1869,7 @@ Editor::insert_region_list_selection (float times) begin_reversible_command (_("insert region")); XMLNode &before = playlist->get_state(); playlist->add_region (*(createRegion (*region)), edit_cursor->current_frame, times); - session->add_command(MementoCommand(*playlist, before, playlist->get_state())); + session->add_command(new MementoCommand(*playlist, before, playlist->get_state())); commit_reversible_command (); } @@ -2291,9 +2290,9 @@ Editor::separate_region_from_selection () begin_reversible_command (_("separate")); doing_undo = true; } - XMLNode &before, &after; + XMLNode *before; if (doing_undo) - before = playlist->get_state(); + before = &(playlist->get_state()); /* XXX need to consider musical time selections here at some point */ @@ -2304,7 +2303,7 @@ Editor::separate_region_from_selection () } if (doing_undo) - session->add_command(MementoCommand(*playlist, before, playlist->get_state())); + session->add_command(new MementoCommand(*playlist, *before, playlist->get_state())); } } } @@ -2339,13 +2338,13 @@ Editor::separate_regions_using_location (Location& loc) if (atv->is_audio_track()) { if ((playlist = atv->playlist()) != 0) { - XMLNode &before, &after; + XMLNode *before; if (!doing_undo) { begin_reversible_command (_("separate")); doing_undo = true; } if (doing_undo) - before = playlist->get_state(); + before = &(playlist->get_state()); /* XXX need to consider musical time selections here at some point */ @@ -2355,7 +2354,7 @@ Editor::separate_regions_using_location (Location& loc) playlist->partition ((jack_nframes_t)(loc.start() * speed), (jack_nframes_t)(loc.end() * speed), true); if (doing_undo) - session->add_command(MementoCommand(*playlist, before, playlist->get_state())); + session->add_command(new MementoCommand(*playlist, *before, playlist->get_state())); } } } @@ -2429,7 +2428,7 @@ Editor::crop_region_to_selection () XMLNode &before = (*i)->get_state(); region->trim_to (start, cnt, this); XMLNode &after = (*i)->get_state(); - session->add_command (MementoCommand(*(*i), before, after)); + session->add_command (new MementoCommand(*(*i), before, after)); } commit_reversible_command (); @@ -2466,7 +2465,7 @@ Editor::region_fill_track () XMLNode &before = pl->get_state(); pl->add_region (*(new AudioRegion (region)), region.last_frame(), times); - session->add_command (MementoCommand(*pl, before, pl->get_state())); + session->add_command (new MementoCommand(*pl, before, pl->get_state())); } commit_reversible_command (); @@ -2516,7 +2515,7 @@ Editor::region_fill_selection () XMLNode &before = playlist->get_state(); playlist->add_region (*(createRegion (*region)), start, times); - session->add_command (MementoCommand(*playlist, before, playlist->get_state())); + session->add_command (new MementoCommand(*playlist, before, playlist->get_state())); } commit_reversible_command (); @@ -2534,7 +2533,7 @@ Editor::set_a_regions_sync_position (Region& region, jack_nframes_t position) XMLNode &before = region.playlist()->get_state(); region.set_sync_position (position); XMLNode &after = region.playlist()->get_state(); - session->add_command(MementoCommand(*(region.playlist()), before, after)); + session->add_command(new MementoCommand(*(region.playlist()), before, after)); commit_reversible_command (); } @@ -2555,7 +2554,7 @@ Editor::set_region_sync_from_edit_cursor () XMLNode &before = region.playlist()->get_state(); region.set_sync_position (edit_cursor->current_frame); XMLNode &after = region.playlist()->get_state(); - session->add_command(MementoCommand(*(region.playlist()), before, after)); + session->add_command(new MementoCommand(*(region.playlist()), before, after)); commit_reversible_command (); } @@ -2568,7 +2567,7 @@ Editor::remove_region_sync () XMLNode &before = region.playlist()->get_state(); region.clear_sync_position (); XMLNode &after = region.playlist()->get_state(); - session->add_command(MementoCommand(*(region.playlist()), before, after)); + session->add_command(new MementoCommand(*(region.playlist()), before, after)); commit_reversible_command (); } } @@ -2584,7 +2583,7 @@ Editor::naturalize () XMLNode &before = (*i)->region.get_state(); (*i)->region.move_to_natural_position (this); XMLNode &after = (*i)->region.get_state(); - session->add_command (MementoCommand((*i)->region, before, after)); + session->add_command (new MementoCommand((*i)->region, before, after)); } commit_reversible_command (); } @@ -2659,7 +2658,7 @@ Editor::align_selection_relative (RegionPoint point, jack_nframes_t position) } XMLNode &after = region.playlist()->get_state(); - session->add_command(MementoCommand(*(region.playlist()), before, after)); + session->add_command(new MementoCommand(*(region.playlist()), before, after)); } @@ -2693,8 +2692,7 @@ Editor::align_region (Region& region, RegionPoint point, jack_nframes_t position void Editor::align_region_internal (Region& region, RegionPoint point, jack_nframes_t position) { - XMLNode &before, &after; - before = region.playlist()->get_state(); + XMLNode &before = region.playlist()->get_state(); switch (point) { case SyncPoint: @@ -2712,8 +2710,8 @@ Editor::align_region_internal (Region& region, RegionPoint point, jack_nframes_t break; } - after = region.playlist()->get_state(); - session->add_command(MementoCommand(*(region.playlist()), before, after)); + XMLNode &after = region.playlist()->get_state(); + session->add_command(new MementoCommand(*(region.playlist()), before, after)); } void @@ -2738,7 +2736,7 @@ Editor::trim_region_to_edit_cursor () XMLNode &before = region.playlist()->get_state(); region.trim_end( session_frame_to_track_frame(edit_cursor->current_frame, speed), this); XMLNode &after = region.playlist()->get_state(); - session->add_command(MementoCommand(*(region.playlist()), before, after)); + session->add_command(new MementoCommand(*(region.playlist()), before, after)); commit_reversible_command (); } @@ -2764,7 +2762,7 @@ Editor::trim_region_from_edit_cursor () XMLNode &before = region.playlist()->get_state(); region.trim_front ( session_frame_to_track_frame(edit_cursor->current_frame, speed), this); XMLNode &after = region.playlist()->get_state(); - session->add_command(MementoCommand(*(region.playlist()), before, after)); + session->add_command(new MementoCommand(*(region.playlist()), before, after)); commit_reversible_command (); } @@ -2879,7 +2877,7 @@ Editor::bounce_range_selection () XMLNode &before = playlist->get_state(); atv->audio_track()->bounce_range (start, cnt, itt); XMLNode &after = playlist->get_state(); - session->add_command (MementoCommand (*playlist, before, after)); + session->add_command (new MementoCommand (*playlist, before, after)); } commit_reversible_command (); @@ -2997,7 +2995,7 @@ Editor::cut_copy_regions (CutCopyOp op) insert_result = freezelist.insert (pl); if (insert_result.second) { pl->freeze (); - session->add_command (MementoUndoCommand(*pl, pl->get_state())); + session->add_command (new MementoUndoCommand(*pl, pl->get_state())); } } } @@ -3055,7 +3053,7 @@ Editor::cut_copy_regions (CutCopyOp op) for (set::iterator pl = freezelist.begin(); pl != freezelist.end(); ++pl) { (*pl)->thaw (); - session->add_command (MementoRedoCommand(*(*pl), *(*pl)->get_state())); + session->add_command (new MementoRedoCommand(*(*pl), (*pl)->get_state())); } } @@ -3170,7 +3168,7 @@ Editor::paste_named_selection (float times) XMLNode &before = apl->get_state(); apl->paste (**chunk, edit_cursor->current_frame, times); - session->add_command(MementoCommand(*apl, before, apl->get_state())); + session->add_command(new MementoCommand(*apl, before, apl->get_state())); if (tmp != ns->playlists.end()) { chunk = tmp; @@ -3201,7 +3199,7 @@ Editor::duplicate_some_regions (AudioRegionSelection& regions, float times) playlist = (*i)->region.playlist(); XMLNode &before = playlist->get_state(); playlist->duplicate (r, r.last_frame(), times); - session->add_command(MementoCommand(*playlist, before, playlist->get_state())); + session->add_command(new MementoCommand(*playlist, before, playlist->get_state())); c.disconnect (); @@ -3242,7 +3240,7 @@ Editor::duplicate_selection (float times) XMLNode &before = playlist->get_state(); playlist->duplicate (**ri, selection->time[clicked_selection].end, times); XMLNode &after = playlist->get_state(); - session->add_command (MementoCommand(*playlist, before, after)); + session->add_command (new MementoCommand(*playlist, before, after)); ++ri; if (ri == new_regions.end()) { @@ -3293,7 +3291,7 @@ Editor::clear_playlist (Playlist& playlist) XMLNode &before = playlist.get_state(); playlist.clear (); XMLNode &after = playlist.get_state(); - session->add_command (MementoCommand(playlist, before, after)); + session->add_command (new MementoCommand(playlist, before, after)); commit_reversible_command (); } @@ -3330,7 +3328,7 @@ Editor::nudge_track (bool use_edit_cursor, bool forwards) XMLNode &before = playlist->get_state(); playlist->nudge_after (start, distance, forwards); XMLNode &after = playlist->get_state(); - session->add_command (MementoCommand(*playlist, before, after)); + session->add_command (new MementoCommand(*playlist, before, after)); } commit_reversible_command (); @@ -3384,7 +3382,7 @@ Editor::normalize_region () XMLNode &before = (*r)->region.get_state(); (*r)->region.normalize_to (0.0f); XMLNode &after = (*r)->region.get_state(); - session->add_command (MementoCommand((*r)->region, before, after)); + session->add_command (new MementoCommand((*r)->region, before, after)); } commit_reversible_command (); @@ -3409,7 +3407,7 @@ Editor::denormalize_region () XMLNode &before = (*r)->region.get_state(); (*r)->region.set_scale_amplitude (1.0f); XMLNode &after = (*r)->region.get_state(); - session->add_command (MementoCommand((*r)->region, before, after)); + session->add_command (new MementoCommand((*r)->region, before, after)); } commit_reversible_command (); @@ -3454,7 +3452,7 @@ Editor::apply_filter (AudioFilter& filter, string command) XMLNode &before = playlist->get_state(); playlist->replace_region (region, *(filter.results.front()), region.position()); XMLNode &after = playlist->get_state(); - session->add_command(MementoCommand(*playlist, before, after)); + session->add_command(new MementoCommand(*playlist, before, after)); } else { goto out; } diff --git a/gtk2_ardour/editor_tempodisplay.cc b/gtk2_ardour/editor_tempodisplay.cc index 0456087859..9f7fe7cf09 100644 --- a/gtk2_ardour/editor_tempodisplay.cc +++ b/gtk2_ardour/editor_tempodisplay.cc @@ -27,6 +27,7 @@ #include #include +#include #include #include @@ -276,7 +277,7 @@ Editor::mouse_add_new_tempo_event (jack_nframes_t frame) XMLNode &before = map.get_state(); map.add_tempo (Tempo (bpm), requested); XMLNode &after = map.get_state(); - session->add_command(MementoCommand(map, before, after)); + session->add_command(new MementoCommand(map, before, after)); commit_reversible_command (); map.dump (cerr); @@ -316,7 +317,7 @@ Editor::mouse_add_new_meter_event (jack_nframes_t frame) begin_reversible_command (_("add meter mark")); XMLNode &before = map.get_state(); map.add_meter (Meter (bpb, note_type), requested); - session->add_command(MementoCommand(map, before, map.get_state())); + session->add_command(new MementoCommand(map, before, map.get_state())); commit_reversible_command (); map.dump (cerr); @@ -367,8 +368,8 @@ Editor::edit_meter_section (MeterSection* section) begin_reversible_command (_("replace tempo mark")); XMLNode &before = session->tempo_map().get_state(); session->tempo_map().replace_meter (*section, Meter (bpb, note_type)); - XMLNode &before = session->tempo_map().get_state(); - session->add_command(MementoCommand(session->tempo_map(), before, after)); + XMLNode &after = session->tempo_map().get_state(); + session->add_command(new MementoCommand(session->tempo_map(), before, after)); commit_reversible_command (); } @@ -398,7 +399,7 @@ Editor::edit_tempo_section (TempoSection* section) session->tempo_map().replace_tempo (*section, Tempo (bpm)); session->tempo_map().move_tempo (*section, when); XMLNode &after = session->tempo_map().get_state(); - session->add_command (MementoCommand(session->tempo_map(), before, after)); + session->add_command (new MementoCommand(session->tempo_map(), before, after)); commit_reversible_command (); } @@ -447,7 +448,7 @@ Editor::real_remove_tempo_marker (TempoSection *section) XMLNode &before = session->tempo_map().get_state(); session->tempo_map().remove_tempo (*section); XMLNode &after = session->tempo_map().get_state(); - session->add_command(MementoCommand(session->tempo_map(), before, after)); + session->add_command(new MementoCommand(session->tempo_map(), before, after)); commit_reversible_command (); return FALSE; @@ -481,7 +482,7 @@ Editor::real_remove_meter_marker (MeterSection *section) XMLNode &before = session->tempo_map().get_state(); session->tempo_map().remove_meter (*section); XMLNode &after = session->tempo_map().get_state(); - session->add_command(MementoCommand(session->tempo_map(), before, after)); + session->add_command(new MementoCommand(session->tempo_map(), before, after)); commit_reversible_command (); return FALSE; } diff --git a/gtk2_ardour/editor_timefx.cc b/gtk2_ardour/editor_timefx.cc index 817a770fe5..27fa6c9651 100644 --- a/gtk2_ardour/editor_timefx.cc +++ b/gtk2_ardour/editor_timefx.cc @@ -25,6 +25,7 @@ #include #include +#include #include "editor.h" #include "audio_time_axis.h" @@ -206,7 +207,7 @@ Editor::do_timestretch (TimeStretchDialog& dialog) XMLNode &before = playlist->get_state(); playlist->replace_region (aregion, *new_region, aregion.position()); XMLNode &after = playlist->get_state(); - session->add_command (MementoCommand(*playlist, before, after)); + session->add_command (new MementoCommand(*playlist, before, after)); i = tmp; } diff --git a/gtk2_ardour/gain_automation_time_axis.cc b/gtk2_ardour/gain_automation_time_axis.cc index 1697adbb9c..3e3d02bfc4 100644 --- a/gtk2_ardour/gain_automation_time_axis.cc +++ b/gtk2_ardour/gain_automation_time_axis.cc @@ -20,6 +20,7 @@ #include #include +#include #include "gain_automation_time_axis.h" #include "automation_line.h" @@ -61,11 +62,10 @@ GainAutomationTimeAxisView::add_automation_event (ArdourCanvas::Item* item, GdkE _session.begin_reversible_command (_("add gain automation event")); - XMLNode &before, &after; - before = curve.get_state(); + XMLNode &before = curve.get_state(); curve.add (when, y); - after = curve.get_state(); - _session.add_command(MementoCommand(curve, before, after)); + XMLNode &after = curve.get_state(); + _session.add_command(new MementoCommand(curve, before, after)); _session.commit_reversible_command (); _session.set_dirty (); } diff --git a/gtk2_ardour/location_ui.cc b/gtk2_ardour/location_ui.cc index 08d5a0b3af..deb4c1da36 100644 --- a/gtk2_ardour/location_ui.cc +++ b/gtk2_ardour/location_ui.cc @@ -27,6 +27,7 @@ #include #include #include +#include #include "ardour_ui.h" #include "prompter.h" @@ -654,11 +655,10 @@ gint LocationUI::do_location_remove (ARDOUR::Location *loc) } session->begin_reversible_command (_("remove marker")); - XMLNode &before, &after; - before = session->locations()->get_state(); + XMLNode &before = session->locations()->get_state(); session->locations()->remove (loc); - after = session->locations()->get_state(); - session->add_command(MementoCommand(*(session->locations()), before, after)); + XMLNode &after = session->locations()->get_state(); + session->add_command(new MementoCommand(*(session->locations()), before, after)); session->commit_reversible_command (); return FALSE; @@ -777,7 +777,7 @@ LocationUI::add_new_location() XMLNode &before = session->locations()->get_state(); session->locations()->add (location, true); XMLNode &after = session->locations()->get_state(); - session->add_command (MementoCommand(*(session->locations()), before, after)); + session->add_command (new MementoCommand(*(session->locations()), before, after)); session->commit_reversible_command (); } @@ -794,7 +794,7 @@ LocationUI::add_new_range() XMLNode &before = session->locations()->get_state(); session->locations()->add (location, true); XMLNode &after = session->locations()->get_state(); - session->add_command (MementoCommand(*(session->locations()), before, after)); + session->add_command (new MementoCommand(*(session->locations()), before, after)); session->commit_reversible_command (); } } diff --git a/gtk2_ardour/pan_automation_time_axis.cc b/gtk2_ardour/pan_automation_time_axis.cc index 267bb6ef09..73d0f7f1aa 100644 --- a/gtk2_ardour/pan_automation_time_axis.cc +++ b/gtk2_ardour/pan_automation_time_axis.cc @@ -23,6 +23,7 @@ #include #include +#include #include "pan_automation_time_axis.h" #include "automation_line.h" @@ -78,11 +79,10 @@ PanAutomationTimeAxisView::add_automation_event (ArdourCanvas::Item* item, GdkEv AutomationList& alist (lines.front()->the_list()); _session.begin_reversible_command (_("add pan automation event")); - XMLNode &before, &after; - before = alist.get_state(); + XMLNode &before = alist.get_state(); alist.add (when, y); - after = alist.get_state(); - _seession.add_command(MementoCommand(alist, before, after)); + XMLNode &after = alist.get_state(); + _session.add_command(new MementoCommand(alist, before, after)); _session.commit_reversible_command (); _session.set_dirty (); } diff --git a/gtk2_ardour/redirect_automation_time_axis.cc b/gtk2_ardour/redirect_automation_time_axis.cc index d6e2432338..e3ce4b08c6 100644 --- a/gtk2_ardour/redirect_automation_time_axis.cc +++ b/gtk2_ardour/redirect_automation_time_axis.cc @@ -21,6 +21,7 @@ #include #include #include +#include #include "redirect_automation_time_axis.h" #include "automation_line.h" @@ -97,11 +98,10 @@ RedirectAutomationTimeAxisView::add_automation_event (ArdourCanvas::Item* item, lines.front()->view_to_model_y (y); _session.begin_reversible_command (description); - XMLNode &before, &after; - before = alist.get_state(); + XMLNode &before = alist.get_state(); alist.add (when, y); - after = alist.get_state(); - _session.add_command(MementoCommand(alist, before, after)); + XMLNode &after = alist.get_state(); + _session.add_command(new MementoCommand(alist, before, after)); _session.commit_reversible_command (); _session.set_dirty (); } diff --git a/gtk2_ardour/region_gain_line.cc b/gtk2_ardour/region_gain_line.cc index 2faa63151b..ebcf65cedd 100644 --- a/gtk2_ardour/region_gain_line.cc +++ b/gtk2_ardour/region_gain_line.cc @@ -1,5 +1,6 @@ #include #include +#include #include "region_gain_line.h" #include "regionview.h" @@ -47,7 +48,7 @@ AudioRegionGainLine::start_drag (ControlPoint* cp, float fraction) { AutomationLine::start_drag(cp,fraction); if (!rv.region.envelope_active()) { - trackview.session().add_command(MementoUndoCommand(rv.region, rv.region.get_state())); + trackview.session().add_command(new MementoUndoCommand(rv.region, rv.region.get_state())); rv.region.set_envelope_active(false); } } @@ -67,12 +68,12 @@ AudioRegionGainLine::remove_point (ControlPoint& cp) XMLNode &before = rv.region.get_state(); rv.region.set_envelope_active(true); XMLNode &after = rv.region.get_state(); - trackview.session().add_command(MementoCommand(rv.region, before, after)); + trackview.session().add_command(new MementoCommand(rv.region, before, after)); } alist.erase (mr.start, mr.end); - trackview.editor.current_session()->add_command (MementoCommand(*this, before, get_state())); + trackview.editor.current_session()->add_command (new MementoCommand(*this, before, get_state())); trackview.editor.current_session()->commit_reversible_command (); trackview.editor.current_session()->set_dirty (); } @@ -82,7 +83,7 @@ AudioRegionGainLine::end_drag (ControlPoint* cp) { if (!rv.region.envelope_active()) { rv.region.set_envelope_active(true); - trackview.session().add_command(MementoRedoCommand(rv.region, rv.region.get_state())); + trackview.session().add_command(new MementoRedoCommand(rv.region, rv.region.get_state())); } AutomationLine::end_drag(cp); } diff --git a/gtk2_ardour/regionview.cc b/gtk2_ardour/regionview.cc index b8658d2e00..dcc71a03c4 100644 --- a/gtk2_ardour/regionview.cc +++ b/gtk2_ardour/regionview.cc @@ -29,6 +29,7 @@ #include #include #include +#include #include "streamview.h" #include "regionview.h" @@ -1148,17 +1149,16 @@ AudioRegionView::add_gain_point_event (ArdourCanvas::Item *item, GdkEvent *ev) if (!region.envelope_active()) { - XMLNode &before, &after; - before = region.get_state(); + XMLNode &before = region.get_state(); region.set_envelope_active(true); - after = region.get_state(); - trackview.session().add_command(MementoCommand(region, before, after)); + XMLNode &after = region.get_state(); + trackview.session().add_command(new MementoCommand(region, before, after)); } region.envelope().add (fx, y); XMLNode &after = region.envelope().get_state(); - trackview.session().add_command(MementoCommand(region.envelope(), before, after)); + trackview.session().add_command(new MementoCommand(region.envelope(), before, after)); trackview.session().commit_reversible_command (); } diff --git a/gtk2_ardour/route_ui.cc b/gtk2_ardour/route_ui.cc index 6ecb4d6255..0dc25f3f7b 100644 --- a/gtk2_ardour/route_ui.cc +++ b/gtk2_ardour/route_ui.cc @@ -25,6 +25,7 @@ #include #include +#include #include "route_ui.h" #include "keyboard.h" @@ -132,9 +133,9 @@ RouteUI::mute_press(GdkEventButton* ev) /* ctrl-shift-click applies change to all routes */ _session.begin_reversible_command (_("mute change")); - Session::GlobalMuteStateCommand cmd(this); + Session::GlobalMuteStateCommand *cmd = new Session::GlobalMuteStateCommand(this); _session.set_all_mute (!_route.muted()); - cmd.mark(); + cmd->mark(); _session.add_command(cmd); _session.commit_reversible_command (); @@ -208,9 +209,9 @@ RouteUI::solo_press(GdkEventButton* ev) /* ctrl-shift-click applies change to all routes */ _session.begin_reversible_command (_("solo change")); - Session::GlobalSoloStateCommand cmd(this); + Session::GlobalSoloStateCommand *cmd = new Session::GlobalSoloStateCommand(this); _session.set_all_solo (!_route.soloed()); - cmd.mark(); + cmd->mark(); _session.add_command (cmd); _session.commit_reversible_command (); @@ -219,10 +220,10 @@ RouteUI::solo_press(GdkEventButton* ev) // ctrl-alt-click: exclusively solo this track, not a toggle */ _session.begin_reversible_command (_("solo change")); - Session::GlobalSoloStateCommand cmd(this); + Session::GlobalSoloStateCommand *cmd = new Session::GlobalSoloStateCommand (this); _session.set_all_solo (false); _route.set_solo (true, this); - cmd.mark(); + cmd->mark(); _session.add_command(cmd); _session.commit_reversible_command (); @@ -283,7 +284,7 @@ RouteUI::rec_enable_press(GdkEventButton* ev) else if (Keyboard::modifier_state_equals (ev->state, Keyboard::ModifierMask (Keyboard::Control|Keyboard::Shift))) { _session.begin_reversible_command (_("rec-enable change")); - Session::GlobalRecordEnableStateCommand cmd(this); + Session::GlobalRecordEnableStateCommand *cmd = new Session::GlobalRecordEnableStateCommand(this); if (rec_enable_button->get_active()) { _session.record_disenable_all (); @@ -291,7 +292,7 @@ RouteUI::rec_enable_press(GdkEventButton* ev) _session.record_enable_all (); } - cmd.mark(); + cmd->mark(); _session.add_command(cmd); _session.commit_reversible_command (); @@ -561,9 +562,9 @@ RouteUI::set_mix_group_solo(Route& route, bool yn) if((mix_group = route.mix_group()) != 0){ _session.begin_reversible_command (_("mix group solo change")); - Session::GlobalSoloStateCommand cmd(this); + Session::GlobalSoloStateCommand *cmd = new Session::GlobalSoloStateCommand(this); mix_group->apply(&Route::set_solo, yn, this); - cmd.mark(); + cmd->mark(); _session.add_command (cmd); _session.commit_reversible_command (); } else { @@ -578,7 +579,7 @@ RouteUI::reversibly_apply_route_boolean (string name, void (Route::*func)(bool, XMLNode &before = _route.get_state(); bind(mem_fun(_route, func), yn, arg)(); XMLNode &after = _route.get_state(); - _session.add_command (MementoCommand(_route, before, after)); + _session.add_command (new MementoCommand(_route, before, after)); _session.commit_reversible_command (); } @@ -589,7 +590,7 @@ RouteUI::reversibly_apply_audio_track_boolean (string name, void (AudioTrack::*f XMLNode &before = audio_track()->get_state(); bind (mem_fun (*audio_track(), func), yn, arg)(); XMLNode &after = audio_track()->get_state(); - _session.add_command (MementoCommand(*audio_track(), before, after)); + _session.add_command (new MementoCommand(*audio_track(), before, after)); _session.commit_reversible_command (); } @@ -600,9 +601,9 @@ RouteUI::set_mix_group_mute(Route& route, bool yn) if((mix_group = route.mix_group()) != 0){ _session.begin_reversible_command (_("mix group mute change")); - Session::GlobalMuteStateCommand cmd(this); + Session::GlobalMuteStateCommand *cmd = new Session::GlobalMuteStateCommand (this); mix_group->apply(&Route::set_mute, yn, this); - cmd.mark(); + cmd->mark(); _session.add_command(cmd); _session.commit_reversible_command (); } else { @@ -617,9 +618,9 @@ RouteUI::set_mix_group_rec_enable(Route& route, bool yn) if((mix_group = route.mix_group()) != 0){ _session.begin_reversible_command (_("mix group rec-enable change")); - Session::GlobalRecordEnableStateCommand cmd(this); + Session::GlobalRecordEnableStateCommand *cmd = new Session::GlobalRecordEnableStateCommand(this); mix_group->apply (&Route::set_record_enable, yn, this); - cmd.mark(); + cmd->mark(); _session.add_command(cmd); _session.commit_reversible_command (); } else { diff --git a/libs/ardour/ardour/automation_event.h b/libs/ardour/ardour/automation_event.h index 78daa531dd..73aed389c1 100644 --- a/libs/ardour/ardour/automation_event.h +++ b/libs/ardour/ardour/automation_event.h @@ -51,7 +51,7 @@ struct ControlEvent { }; -class AutomationList : public StateManager +class AutomationList : public StateManager, public Stateful { public: typedef std::list AutomationEventList; @@ -153,6 +153,12 @@ class AutomationList : public StateManager virtual void store_state (XMLNode& node) const; virtual void load_state (const XMLNode&); + XMLNode &get_state(void); + int set_state (const XMLNode &s) { + load_state(s); + return 1; /*XXX*/ + } + void set_max_xval (double); double get_max_xval() const { return max_xval; } diff --git a/libs/ardour/ardour/session.h b/libs/ardour/ardour/session.h index 35c1a08e25..a809a2e479 100644 --- a/libs/ardour/ardour/session.h +++ b/libs/ardour/ardour/session.h @@ -844,7 +844,7 @@ class Session : public sigc::trackable, public Stateful void begin_reversible_command (string cmd_name); void commit_reversible_command (Command* cmd = 0); - void add_command (const Command& cmd) { + void add_command (Command *const cmd) { current_trans.add_command (cmd); } @@ -859,7 +859,7 @@ class Session : public sigc::trackable, public Stateful void undo(); XMLNode &serialize(); void mark(); - } + }; class GlobalMuteStateCommand : public Command { @@ -871,7 +871,7 @@ class Session : public sigc::trackable, public Stateful void undo(); XMLNode &serialize(); void mark(); - } + }; class GlobalRecordEnableStateCommand : public Command { @@ -883,7 +883,7 @@ class Session : public sigc::trackable, public Stateful void undo(); XMLNode &serialize(); void mark(); - } + }; class GlobalMeteringStateCommand : public Command { @@ -895,7 +895,7 @@ class Session : public sigc::trackable, public Stateful void undo(); XMLNode &serialize(); void mark(); - } + }; /* edit mode */ diff --git a/libs/ardour/audio_diskstream.cc b/libs/ardour/audio_diskstream.cc index b0561eb05d..977616dd8b 100644 --- a/libs/ardour/audio_diskstream.cc +++ b/libs/ardour/audio_diskstream.cc @@ -35,6 +35,7 @@ #include #include #include +#include #include #include @@ -1833,7 +1834,7 @@ AudioDiskstream::transport_stopped (struct tm& when, time_t twhen, bool abort_ca _playlist->thaw (); XMLNode &after = _playlist->get_state(); - _session.add_command (MementoCommand(*_playlist, before, after)); + _session.add_command (new MementoCommand(*_playlist, before, after)); } mark_write_completed = true; diff --git a/libs/ardour/session_command.cc b/libs/ardour/session_command.cc index 8693a9adc4..9e473fe233 100644 --- a/libs/ardour/session_command.cc +++ b/libs/ardour/session_command.cc @@ -1,5 +1,6 @@ #include +namespace ARDOUR { // solo Session::GlobalSoloStateCommand::GlobalSoloStateCommand(void *src) : src(src) { @@ -84,3 +85,4 @@ XMLNode &serialize() { } +} // namespace ARDOUR diff --git a/libs/ardour/session_state.cc b/libs/ardour/session_state.cc index deda3363ab..0ae73291e0 100644 --- a/libs/ardour/session_state.cc +++ b/libs/ardour/session_state.cc @@ -2576,7 +2576,7 @@ Session::commit_reversible_command (Command *cmd) struct timeval now; if (cmd) { - current_trans.add_command (*cmd); + current_trans.add_command (cmd); } gettimeofday (&now, 0); @@ -2659,6 +2659,7 @@ Session::set_global_record_enable (GlobalRouteBooleanState s, void* src) set_global_route_boolean (s, &Route::set_record_enable, src); } +#if 0 UndoAction Session::global_mute_memento (void* src) { @@ -2682,6 +2683,7 @@ Session::global_record_enable_memento (void* src) { return sigc::bind (mem_fun (*this, &Session::set_global_record_enable), get_global_route_boolean (&Route::record_enabled), src); } +#endif static bool template_filter (const string &str, void *arg) diff --git a/libs/ardour/session_transport.cc b/libs/ardour/session_transport.cc index 1d3da72ad8..55bdac064b 100644 --- a/libs/ardour/session_transport.cc +++ b/libs/ardour/session_transport.cc @@ -29,6 +29,7 @@ #include #include #include +#include #include #include @@ -323,7 +324,7 @@ Session::non_realtime_stop (bool abort) XMLNode &before = loc->get_state(); loc->set_end(_transport_frame); XMLNode &after = loc->get_state(); - add_command (MementoCommand(*loc, before, after)); + add_command (new MementoCommand(*loc, before, after)); } _end_location_is_free = false; diff --git a/libs/pbd3/pbd/memento_command.h b/libs/pbd3/pbd/memento_command.h index 1419c904bb..fe10893de6 100644 --- a/libs/pbd3/pbd/memento_command.h +++ b/libs/pbd3/pbd/memento_command.h @@ -39,12 +39,12 @@ class MementoCommand : public Command : obj(obj), before(before), after(after) {} void operator() () { obj.set_state(after); } void undo() { obj.set_state(before); } - virtual XMLNode &serialize() - { + virtual XMLNode &serialize() ; + //{ // obj.id // key is "MementoCommand" or something // before and after mementos - } + //} // TODO does this need a copy constructor? protected: obj_T &obj; @@ -52,7 +52,7 @@ class MementoCommand : public Command }; template -class MementoUndoCommand : public MementoCommand +class MementoUndoCommand : public Command { public: MementoUndoCommand(obj_T &obj, @@ -60,29 +60,35 @@ public: : obj(obj), before(before) {} void operator() () { /* noop */ } void undo() { obj.set_state(before); } - virtual XMLNode &serialize() - { + virtual XMLNode &serialize() ; + //{ // obj.id // key is "MementoCommand" or something // before and after mementos - } -} + //} +protected: + obj_T &obj; + XMLNode &before; +}; template -class MementoRedoCommand : public MementoCommand +class MementoRedoCommand : public Command { public: - MementoUndoCommand(obj_T &obj, + MementoRedoCommand(obj_T &obj, XMLNode &after) : obj(obj), after(after) {} void operator() () { obj.set_state(after); } void undo() { /* noop */ } - virtual XMLNode &serialize() - { + virtual XMLNode &serialize(); + //{ // obj.id // key is "MementoCommand" or something // before and after mementos - } -} + //} +protected: + obj_T &obj; + XMLNode &after; +}; #endif // __lib_pbd_memento_h__ diff --git a/libs/pbd3/pbd/serializable.h b/libs/pbd3/pbd/serializable.h index c0948b9933..4082b840f0 100644 --- a/libs/pbd3/pbd/serializable.h +++ b/libs/pbd3/pbd/serializable.h @@ -27,6 +27,7 @@ class Serializable { public: virtual XMLNode &serialize() = 0; + virtual ~Serializable(); }; #endif // __lib_pbd_serializable_h__ diff --git a/libs/pbd3/pbd/undo.h b/libs/pbd3/pbd/undo.h index b97c8d9249..33577ed4d7 100644 --- a/libs/pbd3/pbd/undo.h +++ b/libs/pbd3/pbd/undo.h @@ -32,7 +32,7 @@ using std::string; using std::list; -typedef Command UndoAction; +typedef sigc::slot UndoAction; class UndoTransaction : public Command { @@ -43,10 +43,13 @@ class UndoTransaction : public Command void clear (); - void add_command (const UndoAction&); + void add_command (Command *const); void operator() (); void undo(); + void redo(); + + XMLNode &serialize(); void set_name (const string& str) { _name = str; @@ -62,7 +65,7 @@ class UndoTransaction : public Command } private: - list actions; + list actions; struct timeval _timestamp; string _name; }; diff --git a/libs/pbd3/undo.cc b/libs/pbd3/undo.cc index 0a09ffd1e7..43e98313a2 100644 --- a/libs/pbd3/undo.cc +++ b/libs/pbd3/undo.cc @@ -47,7 +47,7 @@ UndoTransaction::operator= (const UndoTransaction& rhs) } void -UndoTransaction::add_command (const UndoAction& action) +UndoTransaction::add_command (Command *const action) { actions.push_back (action); } @@ -61,8 +61,8 @@ UndoTransaction::clear () void UndoTransaction::operator() () { - for (list::iterator i = actions.begin(); i != actions.end(); ++i) { - (*i)(); + for (list::iterator i = actions.begin(); i != actions.end(); ++i) { + (*(*i))(); } } @@ -70,8 +70,8 @@ void UndoTransaction::undo () { cerr << "Undo " << _name << endl; - for (list::reverse_iterator i = actions.rbegin(); i != actions.rend(); ++i) { - i->undo(); + for (list::reverse_iterator i = actions.rbegin(); i != actions.rend(); ++i) { + (*i)->undo(); } } @@ -112,7 +112,7 @@ UndoHistory::redo (unsigned int n) UndoTransaction ut = RedoList.back (); RedoList.pop_back (); ut.redo (); - UndoList.push_back (trans); + UndoList.push_back (ut); } } From b0b723445816bc968a6a183c6619fccc61e82859 Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Thu, 3 Aug 2006 21:54:14 +0000 Subject: [PATCH 25/27] r260@gandalf: fugalh | 2006-08-03 15:53:50 -0600 It compiles and runs and seems to still work. Still needed is the actual serialization. Time to merge back to trunk so things can be tested by all. git-svn-id: svn://localhost/ardour2/branches/undo@754 d708f5d6-7413-0410-9779-e7cbd77b26cf --- gtk2_ardour/automation_line.cc | 12 +++++ gtk2_ardour/route_ui.cc | 14 +++--- libs/ardour/SConscript | 1 + libs/ardour/ardour/automation_event.h | 5 +- libs/ardour/ardour/session.h | 12 +++-- libs/ardour/automation_event.cc | 14 ++++++ libs/ardour/session_command.cc | 69 ++++++++++++++------------- libs/pbd3/SConscript | 1 + libs/pbd3/command.cc | 10 ++++ libs/pbd3/pbd/command.h | 5 +- libs/pbd3/pbd/memento_command.h | 6 +-- libs/pbd3/pbd/serializable.h | 2 +- libs/pbd3/undo.cc | 7 +++ 13 files changed, 104 insertions(+), 54 deletions(-) create mode 100644 libs/pbd3/command.cc diff --git a/gtk2_ardour/automation_line.cc b/gtk2_ardour/automation_line.cc index a8f2952ed9..4cf6779c98 100644 --- a/gtk2_ardour/automation_line.cc +++ b/gtk2_ardour/automation_line.cc @@ -1267,3 +1267,15 @@ AutomationLine::hide_all_but_selected_control_points () } } } + +XMLNode &AutomationLine::get_state(void) +{ + // TODO + return alist.get_state(); +} + +int AutomationLine::set_state(const XMLNode &node) +{ + // TODO + alist.set_state(node); +} diff --git a/gtk2_ardour/route_ui.cc b/gtk2_ardour/route_ui.cc index 0dc25f3f7b..988d6c8b19 100644 --- a/gtk2_ardour/route_ui.cc +++ b/gtk2_ardour/route_ui.cc @@ -133,7 +133,7 @@ RouteUI::mute_press(GdkEventButton* ev) /* ctrl-shift-click applies change to all routes */ _session.begin_reversible_command (_("mute change")); - Session::GlobalMuteStateCommand *cmd = new Session::GlobalMuteStateCommand(this); + Session::GlobalMuteStateCommand *cmd = new Session::GlobalMuteStateCommand(_session, this); _session.set_all_mute (!_route.muted()); cmd->mark(); _session.add_command(cmd); @@ -209,7 +209,7 @@ RouteUI::solo_press(GdkEventButton* ev) /* ctrl-shift-click applies change to all routes */ _session.begin_reversible_command (_("solo change")); - Session::GlobalSoloStateCommand *cmd = new Session::GlobalSoloStateCommand(this); + Session::GlobalSoloStateCommand *cmd = new Session::GlobalSoloStateCommand(_session, this); _session.set_all_solo (!_route.soloed()); cmd->mark(); _session.add_command (cmd); @@ -220,7 +220,7 @@ RouteUI::solo_press(GdkEventButton* ev) // ctrl-alt-click: exclusively solo this track, not a toggle */ _session.begin_reversible_command (_("solo change")); - Session::GlobalSoloStateCommand *cmd = new Session::GlobalSoloStateCommand (this); + Session::GlobalSoloStateCommand *cmd = new Session::GlobalSoloStateCommand (_session, this); _session.set_all_solo (false); _route.set_solo (true, this); cmd->mark(); @@ -284,7 +284,7 @@ RouteUI::rec_enable_press(GdkEventButton* ev) else if (Keyboard::modifier_state_equals (ev->state, Keyboard::ModifierMask (Keyboard::Control|Keyboard::Shift))) { _session.begin_reversible_command (_("rec-enable change")); - Session::GlobalRecordEnableStateCommand *cmd = new Session::GlobalRecordEnableStateCommand(this); + Session::GlobalRecordEnableStateCommand *cmd = new Session::GlobalRecordEnableStateCommand(_session, this); if (rec_enable_button->get_active()) { _session.record_disenable_all (); @@ -562,7 +562,7 @@ RouteUI::set_mix_group_solo(Route& route, bool yn) if((mix_group = route.mix_group()) != 0){ _session.begin_reversible_command (_("mix group solo change")); - Session::GlobalSoloStateCommand *cmd = new Session::GlobalSoloStateCommand(this); + Session::GlobalSoloStateCommand *cmd = new Session::GlobalSoloStateCommand(_session, this); mix_group->apply(&Route::set_solo, yn, this); cmd->mark(); _session.add_command (cmd); @@ -601,7 +601,7 @@ RouteUI::set_mix_group_mute(Route& route, bool yn) if((mix_group = route.mix_group()) != 0){ _session.begin_reversible_command (_("mix group mute change")); - Session::GlobalMuteStateCommand *cmd = new Session::GlobalMuteStateCommand (this); + Session::GlobalMuteStateCommand *cmd = new Session::GlobalMuteStateCommand (_session, this); mix_group->apply(&Route::set_mute, yn, this); cmd->mark(); _session.add_command(cmd); @@ -618,7 +618,7 @@ RouteUI::set_mix_group_rec_enable(Route& route, bool yn) if((mix_group = route.mix_group()) != 0){ _session.begin_reversible_command (_("mix group rec-enable change")); - Session::GlobalRecordEnableStateCommand *cmd = new Session::GlobalRecordEnableStateCommand(this); + Session::GlobalRecordEnableStateCommand *cmd = new Session::GlobalRecordEnableStateCommand(_session, this); mix_group->apply (&Route::set_record_enable, yn, this); cmd->mark(); _session.add_command(cmd); diff --git a/libs/ardour/SConscript b/libs/ardour/SConscript index f5f1272fb8..a1bed7aeef 100644 --- a/libs/ardour/SConscript +++ b/libs/ardour/SConscript @@ -75,6 +75,7 @@ send.cc session.cc session_butler.cc session_click.cc +session_command.cc session_events.cc session_export.cc session_midi.cc diff --git a/libs/ardour/ardour/automation_event.h b/libs/ardour/ardour/automation_event.h index 73aed389c1..1fa29d4adf 100644 --- a/libs/ardour/ardour/automation_event.h +++ b/libs/ardour/ardour/automation_event.h @@ -154,10 +154,7 @@ class AutomationList : public StateManager, public Stateful virtual void load_state (const XMLNode&); XMLNode &get_state(void); - int set_state (const XMLNode &s) { - load_state(s); - return 1; /*XXX*/ - } + int set_state (const XMLNode &s); void set_max_xval (double); double get_max_xval() const { return max_xval; } diff --git a/libs/ardour/ardour/session.h b/libs/ardour/ardour/session.h index a809a2e479..7a9e50ae9b 100644 --- a/libs/ardour/ardour/session.h +++ b/libs/ardour/ardour/session.h @@ -853,8 +853,9 @@ class Session : public sigc::trackable, public Stateful { GlobalRouteBooleanState before, after; void *src; + Session &sess; public: - GlobalSoloStateCommand(void *src); + GlobalSoloStateCommand(Session &, void *src); void operator()(); void undo(); XMLNode &serialize(); @@ -865,8 +866,9 @@ class Session : public sigc::trackable, public Stateful { GlobalRouteBooleanState before, after; void *src; + Session &sess; public: - GlobalMuteStateCommand(void *src); + GlobalMuteStateCommand(Session &, void *src); void operator()(); void undo(); XMLNode &serialize(); @@ -877,8 +879,9 @@ class Session : public sigc::trackable, public Stateful { GlobalRouteBooleanState before, after; void *src; + Session &sess; public: - GlobalRecordEnableStateCommand(void *src); + GlobalRecordEnableStateCommand(Session &, void *src); void operator()(); void undo(); XMLNode &serialize(); @@ -889,8 +892,9 @@ class Session : public sigc::trackable, public Stateful { GlobalRouteMeterState before, after; void *src; + Session &sess; public: - GlobalMeteringStateCommand(void *src); + GlobalMeteringStateCommand(Session &, void *src); void operator()(); void undo(); XMLNode &serialize(); diff --git a/libs/ardour/automation_event.cc b/libs/ardour/automation_event.cc index 3df7dd94f7..a9e76ac55c 100644 --- a/libs/ardour/automation_event.cc +++ b/libs/ardour/automation_event.cc @@ -1246,3 +1246,17 @@ AutomationList::load_state (const XMLNode& node) add (x, y); } } + +XMLNode &AutomationList::get_state () +{ + XMLNode *node = new XMLNode("AutomationList"); + store_state(*node); + return *node; +} + +int AutomationList::set_state(const XMLNode &s) +{ + load_state(s); + return 0; +} + diff --git a/libs/ardour/session_command.cc b/libs/ardour/session_command.cc index 9e473fe233..6482de41fb 100644 --- a/libs/ardour/session_command.cc +++ b/libs/ardour/session_command.cc @@ -1,87 +1,92 @@ #include +#include namespace ARDOUR { // solo -Session::GlobalSoloStateCommand::GlobalSoloStateCommand(void *src) : src(src) +Session::GlobalSoloStateCommand::GlobalSoloStateCommand(Session &sess, void *src) + : sess(sess), src(src) { - after = before = get_global_route_boolean(&Route::soloed); + after = before = sess.get_global_route_boolean(&Route::soloed); } void Session::GlobalSoloStateCommand::mark() { - after = get_global_route_boolean(&Route::soloed); + after = sess.get_global_route_boolean(&Route::soloed); } -void operator()() +void Session::GlobalSoloStateCommand::operator()() { - set_global_solo(after, src); + sess.set_global_solo(after, src); } -void undo() +void Session::GlobalSoloStateCommand::undo() { - set_global_solo(before, src); + sess.set_global_solo(before, src); } -XMLNode &serialize() +XMLNode &Session::GlobalSoloStateCommand::serialize() { } // mute -Session::GlobalMuteStateCommand::GlobalMuteStateCommand(void *src) : src(src) +Session::GlobalMuteStateCommand::GlobalMuteStateCommand(Session &sess, void *src) + : sess(sess), src(src) { - after = before = get_global_route_boolean(&Route::muted); + after = before = sess.get_global_route_boolean(&Route::muted); } void Session::GlobalMuteStateCommand::mark() { - after = get_global_route_boolean(&Route::muted); + after = sess.get_global_route_boolean(&Route::muted); } -void operator()() +void Session::GlobalMuteStateCommand::operator()() { - set_global_mute(after, src); + sess.set_global_mute(after, src); } -void undo() +void Session::GlobalMuteStateCommand::undo() { - set_global_mute(before, src); + sess.set_global_mute(before, src); } -XMLNode &serialize() +XMLNode &Session::GlobalMuteStateCommand::serialize() { } // record enable -Session::GlobalRecordEnableStateCommand::GlobalRecordEnableStateCommand(void *src) : src(src) +Session::GlobalRecordEnableStateCommand::GlobalRecordEnableStateCommand(Session &sess, void *src) + : sess(sess), src(src) { - after = before = get_global_route_boolean(&Route::record_enabled); + after = before = sess.get_global_route_boolean(&Route::record_enabled); } void Session::GlobalRecordEnableStateCommand::mark() { - after = get_global_route_boolean(&Route::record_enabled); + after = sess.get_global_route_boolean(&Route::record_enabled); } -void operator()() +void Session::GlobalRecordEnableStateCommand::operator()() { - set_global_record_enable(after, src); + sess.set_global_record_enable(after, src); } -void undo() +void Session::GlobalRecordEnableStateCommand::undo() { - set_global_record_enable(before, src); + sess.set_global_record_enable(before, src); } -XMLNode &serialize() +XMLNode &Session::GlobalRecordEnableStateCommand::serialize() { } // metering -Session::GlobalMeteringStateCommand::GlobalMeteringStateCommand(void *src) : src(src) +Session::GlobalMeteringStateCommand::GlobalMeteringStateCommand(Session &sess, void *src) + : sess(sess), src(src) { - after = before = get_global_route_metering(); + after = before = sess.get_global_route_metering(); } void Session::GlobalMeteringStateCommand::mark() { - after = get_global_route_metering(); + after = sess.get_global_route_metering(); } -void operator()() +void Session::GlobalMeteringStateCommand::operator()() { - set_global_route_metering(after, src); + sess.set_global_route_metering(after, src); } -void undo() +void Session::GlobalMeteringStateCommand::undo() { - set_global_route_metering(before, src); + sess.set_global_route_metering(before, src); } -XMLNode &serialize() +XMLNode &Session::GlobalMeteringStateCommand::serialize() { } diff --git a/libs/pbd3/SConscript b/libs/pbd3/SConscript index 2766b3c5ed..fedb3cded4 100644 --- a/libs/pbd3/SConscript +++ b/libs/pbd3/SConscript @@ -21,6 +21,7 @@ pbd3_files = Split(""" basename.cc base_ui.cc convert.cc +command.cc dmalloc.cc error.cc mountpoint.cc diff --git a/libs/pbd3/command.cc b/libs/pbd3/command.cc new file mode 100644 index 0000000000..3f5aca8e51 --- /dev/null +++ b/libs/pbd3/command.cc @@ -0,0 +1,10 @@ +#include + +class XMLNode; + +XMLNode &Command::serialize() +{ + XMLNode *node = new XMLNode ("Command"); + // TODO + return *node; +} diff --git a/libs/pbd3/pbd/command.h b/libs/pbd3/pbd/command.h index 89b358a770..35ae011530 100644 --- a/libs/pbd3/pbd/command.h +++ b/libs/pbd3/pbd/command.h @@ -26,12 +26,11 @@ class Command : public Serializable { public: - virtual ~Command(); + virtual ~Command() {} virtual void operator() () = 0; virtual void undo() = 0; virtual void redo() { (*this)(); } - protected: - Command(); + virtual XMLNode &serialize(); }; #endif // __lib_pbd_command_h_ diff --git a/libs/pbd3/pbd/memento_command.h b/libs/pbd3/pbd/memento_command.h index fe10893de6..c8bfe5de4c 100644 --- a/libs/pbd3/pbd/memento_command.h +++ b/libs/pbd3/pbd/memento_command.h @@ -39,7 +39,7 @@ class MementoCommand : public Command : obj(obj), before(before), after(after) {} void operator() () { obj.set_state(after); } void undo() { obj.set_state(before); } - virtual XMLNode &serialize() ; + virtual XMLNode &serialize() {} //{ // obj.id // key is "MementoCommand" or something @@ -60,7 +60,7 @@ public: : obj(obj), before(before) {} void operator() () { /* noop */ } void undo() { obj.set_state(before); } - virtual XMLNode &serialize() ; + virtual XMLNode &serialize() {} //{ // obj.id // key is "MementoCommand" or something @@ -80,7 +80,7 @@ public: : obj(obj), after(after) {} void operator() () { obj.set_state(after); } void undo() { /* noop */ } - virtual XMLNode &serialize(); + virtual XMLNode &serialize() {} //{ // obj.id // key is "MementoCommand" or something diff --git a/libs/pbd3/pbd/serializable.h b/libs/pbd3/pbd/serializable.h index 4082b840f0..f6ac4e92fb 100644 --- a/libs/pbd3/pbd/serializable.h +++ b/libs/pbd3/pbd/serializable.h @@ -27,7 +27,7 @@ class Serializable { public: virtual XMLNode &serialize() = 0; - virtual ~Serializable(); + virtual ~Serializable() {} }; #endif // __lib_pbd_serializable_h__ diff --git a/libs/pbd3/undo.cc b/libs/pbd3/undo.cc index 43e98313a2..aa27f95789 100644 --- a/libs/pbd3/undo.cc +++ b/libs/pbd3/undo.cc @@ -82,6 +82,13 @@ UndoTransaction::redo () (*this)(); } +XMLNode &UndoTransaction::serialize() +{ + XMLNode *node = new XMLNode ("UndoTransaction"); + // TODO + return *node; +} + void UndoHistory::add (UndoTransaction ut) { From 79986643c0c904f6574bb5323e2233a43a9e622e Mon Sep 17 00:00:00 2001 From: Hans Fugal Date: Fri, 4 Aug 2006 02:18:45 +0000 Subject: [PATCH 26/27] r269@gandalf: fugalh | 2006-08-03 20:18:05 -0600 Trunk merge conflicts resolved git-svn-id: svn://localhost/ardour2/branches/undo@756 d708f5d6-7413-0410-9779-e7cbd77b26cf --- SConstruct | 341 ++-- ardour.dox | 2 +- gtk2_ardour/SConscript | 20 +- gtk2_ardour/actions.cc | 2 +- gtk2_ardour/analysis_window.cc | 47 +- gtk2_ardour/ardev_common.sh | 5 +- gtk2_ardour/ardour.menus | 4 +- gtk2_ardour/ardour2_ui.rc | 9 + gtk2_ardour/ardour_dialog.h | 3 +- gtk2_ardour/ardour_ui.cc | 140 +- gtk2_ardour/ardour_ui.h | 25 +- gtk2_ardour/ardour_ui2.cc | 66 +- gtk2_ardour/ardour_ui_dialogs.cc | 4 +- gtk2_ardour/ardour_ui_ed.cc | 17 +- gtk2_ardour/audio_clock.h | 6 +- ...egion_editor.cc => audio_region_editor.cc} | 9 +- gtk2_ardour/audio_region_editor.h | 186 ++ gtk2_ardour/audio_region_view.cc | 1127 ++++++++++++ .../{regionview.h => audio_region_view.h} | 116 +- .../{regionview.cc => audio_regionview.cc} | 17 +- gtk2_ardour/audio_streamview.cc | 700 +++++++ gtk2_ardour/audio_streamview.h | 110 ++ gtk2_ardour/audio_time_axis.cc | 1540 +--------------- gtk2_ardour/audio_time_axis.h | 245 +-- gtk2_ardour/automation_time_axis.cc | 160 +- gtk2_ardour/automation_time_axis.h | 17 +- gtk2_ardour/canvas-waveview.h | 6 +- gtk2_ardour/crossfade_edit.cc | 6 +- gtk2_ardour/crossfade_view.cc | 6 +- gtk2_ardour/crossfade_view.h | 4 +- gtk2_ardour/editing_syms.h | 1 + gtk2_ardour/editor.cc | 575 +++--- gtk2_ardour/editor.h | 89 +- gtk2_ardour/editor_actions.cc | 2 + gtk2_ardour/editor_audio_import.cc | 34 +- gtk2_ardour/editor_audiotrack.cc | 2 +- gtk2_ardour/editor_canvas.cc | 2 +- gtk2_ardour/editor_canvas_events.cc | 61 +- gtk2_ardour/editor_export_audio.cc | 36 +- gtk2_ardour/editor_items.h | 4 +- gtk2_ardour/editor_keyboard.cc | 16 +- gtk2_ardour/editor_keys.cc | 8 +- gtk2_ardour/editor_markers.cc | 6 +- gtk2_ardour/editor_mixer.cc | 6 +- gtk2_ardour/editor_mouse.cc | 413 +++-- gtk2_ardour/editor_ops.cc | 342 ++-- gtk2_ardour/editor_route_list.cc | 42 +- gtk2_ardour/editor_timefx.cc | 33 +- gtk2_ardour/export_dialog.cc | 8 +- gtk2_ardour/export_region_dialog.cc | 10 +- gtk2_ardour/export_region_dialog.h | 2 +- gtk2_ardour/fft_graph.cc | 6 +- gtk2_ardour/fft_graph.h | 2 +- gtk2_ardour/fft_result.cc | 6 +- gtk2_ardour/gain_automation_time_axis.cc | 6 +- gtk2_ardour/gain_automation_time_axis.h | 2 +- gtk2_ardour/gain_meter.cc | 59 +- gtk2_ardour/gain_meter.h | 6 +- gtk2_ardour/io_selector.cc | 84 +- gtk2_ardour/io_selector.h | 12 +- gtk2_ardour/keyboard.h | 2 +- gtk2_ardour/main.cc | 2 +- gtk2_ardour/mixer_strip.cc | 192 +- gtk2_ardour/mixer_strip.h | 17 +- gtk2_ardour/mixer_ui.cc | 41 +- gtk2_ardour/mixer_ui.h | 7 +- gtk2_ardour/option_editor.cc | 18 +- gtk2_ardour/option_editor.h | 18 +- gtk2_ardour/pan_automation_time_axis.cc | 75 +- gtk2_ardour/pan_automation_time_axis.h | 35 +- gtk2_ardour/panner_ui.cc | 106 +- gtk2_ardour/panner_ui.h | 6 +- gtk2_ardour/pixmaps/tool_audition.xpm | 19 + gtk2_ardour/pixmaps/tool_gain.xpm | 18 + gtk2_ardour/pixmaps/tool_object.xpm | 18 + gtk2_ardour/pixmaps/tool_range.xpm | 18 + gtk2_ardour/pixmaps/tool_stretch.xpm | 18 + gtk2_ardour/pixmaps/tool_zoom.xpm | 29 + gtk2_ardour/pixmaps/zoom_full.xpm | 30 + gtk2_ardour/pixmaps/zoom_in.xpm | 29 + gtk2_ardour/pixmaps/zoom_out.xpm | 29 + gtk2_ardour/playlist_selector.cc | 14 +- gtk2_ardour/playlist_selector.h | 2 +- gtk2_ardour/plugin_selector.cc | 208 ++- gtk2_ardour/plugin_selector.h | 53 +- gtk2_ardour/plugin_ui.cc | 98 +- gtk2_ardour/plugin_ui.h | 18 +- gtk2_ardour/po/SConscript | 2 +- gtk2_ardour/public_editor.h | 10 +- gtk2_ardour/redirect_automation_line.cc | 2 +- gtk2_ardour/redirect_automation_time_axis.cc | 3 +- gtk2_ardour/redirect_automation_time_axis.h | 2 +- gtk2_ardour/redirect_box.cc | 229 ++- gtk2_ardour/redirect_box.h | 57 +- gtk2_ardour/redirect_selection.h | 3 +- gtk2_ardour/region_editor.h | 165 +- gtk2_ardour/region_gain_line.cc | 22 +- gtk2_ardour/region_selection.cc | 74 +- gtk2_ardour/region_selection.h | 48 +- gtk2_ardour/region_view.cc | 494 +++++ gtk2_ardour/region_view.h | 140 ++ gtk2_ardour/route_params_ui.cc | 125 +- gtk2_ardour/route_params_ui.h | 20 +- gtk2_ardour/route_redirect_selection.cc | 55 +- gtk2_ardour/route_redirect_selection.h | 18 +- gtk2_ardour/route_selection.h | 4 +- gtk2_ardour/route_time_axis.cc | 1601 +++++++++++++++++ gtk2_ardour/route_time_axis.h | 256 +++ gtk2_ardour/route_ui.cc | 198 +- gtk2_ardour/route_ui.h | 39 +- gtk2_ardour/selectable.h | 2 +- gtk2_ardour/selection.cc | 97 +- gtk2_ardour/selection.h | 37 +- gtk2_ardour/selection_templates.h | 32 +- gtk2_ardour/send_ui.cc | 14 +- gtk2_ardour/send_ui.h | 6 +- gtk2_ardour/sfdb_ui.cc | 16 + gtk2_ardour/sfdb_ui.h | 1 + gtk2_ardour/streamview.cc | 755 +------- gtk2_ardour/streamview.h | 157 +- ...{taperegionview.cc => tape_region_view.cc} | 71 +- .../{taperegionview.h => tape_region_view.h} | 8 +- gtk2_ardour/time_axis_view.cc | 5 +- gtk2_ardour/time_axis_view.h | 4 +- gtk2_ardour/time_axis_view_item.cc | 8 +- gtk2_ardour/time_axis_view_item.h | 7 +- gtk2_ardour/utils.cc | 6 +- gtk2_ardour/visual_time_axis.cc | 2 +- gtk2_ardour/visual_time_axis.h | 4 +- libs/appleutility/AUOutputBL.cpp | 160 ++ libs/appleutility/AUOutputBL.h | 115 ++ libs/appleutility/CAAudioChannelLayout.cpp | 138 ++ libs/appleutility/CAAudioChannelLayout.h | 162 ++ .../CAAudioChannelLayoutObject.cpp | 199 ++ libs/appleutility/CAAudioUnit.cpp | 1202 +++++++++++++ libs/appleutility/CAAudioUnit.h | 383 ++++ libs/appleutility/CACFDictionary.cpp | 478 +++++ libs/appleutility/CACFDictionary.h | 141 ++ libs/appleutility/CACFNumber.cpp | 65 + libs/appleutility/CACFNumber.h | 102 ++ libs/appleutility/CACFString.cpp | 106 ++ libs/appleutility/CACFString.h | 156 ++ libs/appleutility/CAComponent.cpp | 257 +++ libs/appleutility/CAComponent.h | 120 ++ libs/appleutility/CAComponentDescription.cpp | 123 ++ libs/appleutility/CAComponentDescription.h | 148 ++ libs/appleutility/CAConditionalMacros.h | 74 + libs/appleutility/CADebugMacros.cpp | 84 + libs/appleutility/CADebugMacros.h | 414 +++++ libs/appleutility/CAMath.h | 64 + libs/appleutility/CAReferenceCounted.h | 83 + .../appleutility/CAStreamBasicDescription.cpp | 520 ++++++ libs/appleutility/CAStreamBasicDescription.h | 224 +++ libs/appleutility/SConscript | 23 + libs/ardour/SConscript | 10 +- libs/ardour/ardour/ardour.h | 6 +- libs/ardour/ardour/audio_diskstream.h | 279 +-- libs/ardour/ardour/audio_library.h | 9 +- libs/ardour/ardour/audio_track.h | 121 +- libs/ardour/ardour/audio_unit.h | 111 ++ libs/ardour/ardour/audioengine.h | 8 +- libs/ardour/ardour/audiofilesource.h | 10 +- libs/ardour/ardour/audioplaylist.h | 3 - libs/ardour/ardour/audioregion.h | 86 +- libs/ardour/ardour/audiosource.h | 9 +- libs/ardour/ardour/buffer.h | 106 ++ libs/ardour/ardour/configuration.h | 5 +- libs/ardour/ardour/connection.h | 2 +- libs/ardour/ardour/control_protocol_manager.h | 3 +- libs/ardour/ardour/curve.h | 2 +- libs/ardour/ardour/data_type.h | 79 + libs/ardour/ardour/destructive_filesource.h | 5 + libs/ardour/ardour/diskstream.h | 319 ++++ libs/ardour/ardour/export.h | 2 +- libs/ardour/ardour/insert.h | 17 +- libs/ardour/ardour/io.h | 80 +- libs/ardour/ardour/ladspa_plugin.h | 19 +- libs/ardour/ardour/location.h | 8 +- libs/ardour/ardour/logcurve.h | 2 +- libs/ardour/ardour/named_selection.h | 2 +- libs/ardour/ardour/panner.h | 46 +- libs/ardour/ardour/playlist.h | 31 +- libs/ardour/ardour/plugin.h | 63 +- libs/ardour/ardour/plugin_manager.h | 18 +- libs/ardour/ardour/port.h | 75 +- libs/ardour/ardour/redirect.h | 5 +- libs/ardour/ardour/region.h | 104 +- libs/ardour/ardour/route.h | 77 +- libs/ardour/ardour/route_group.h | 7 +- libs/ardour/ardour/route_group_specialized.h | 6 +- libs/ardour/ardour/send.h | 10 +- libs/ardour/ardour/session.h | 168 +- libs/ardour/ardour/session_region.h | 2 +- libs/ardour/ardour/session_route.h | 33 +- libs/ardour/ardour/sndfilesource.h | 4 +- libs/ardour/ardour/source.h | 7 +- libs/ardour/ardour/tempo.h | 2 +- libs/ardour/ardour/track.h | 158 ++ libs/ardour/ardour/types.h | 12 +- libs/ardour/ardour/utils.h | 10 +- libs/ardour/ardour/vst_plugin.h | 14 +- libs/ardour/audio_diskstream.cc | 591 ++---- libs/ardour/audio_library.cc | 51 +- libs/ardour/audio_playlist.cc | 40 +- libs/ardour/audio_track.cc | 429 +---- libs/ardour/audio_unit.cc | 362 ++++ libs/ardour/audioengine.cc | 37 +- libs/ardour/audiofilesource.cc | 46 +- libs/ardour/audioregion.cc | 61 +- libs/ardour/audiosource.cc | 2 +- libs/ardour/auditioner.cc | 41 +- libs/ardour/automation_event.cc | 2 +- libs/ardour/configuration.cc | 4 + libs/ardour/control_protocol_manager.cc | 5 + libs/ardour/coreaudiosource.cc | 33 +- libs/ardour/crossfade.cc | 17 +- libs/ardour/destructive_filesource.cc | 62 +- libs/ardour/diskstream.cc | 401 +++++ libs/ardour/globals.cc | 24 +- libs/ardour/insert.cc | 94 +- libs/ardour/io.cc | 284 +-- libs/ardour/ladspa_plugin.cc | 119 +- libs/ardour/location.cc | 8 + libs/ardour/mix.cc | 6 +- libs/ardour/panner.cc | 255 +-- libs/ardour/playlist.cc | 33 +- libs/ardour/plugin.cc | 240 +-- libs/ardour/plugin_manager.cc | 104 +- libs/ardour/po/el_GR.po | 82 +- libs/ardour/po/it_IT.po | 82 +- libs/ardour/po/ru_RU.po | 82 +- libs/ardour/port.cc | 18 +- libs/ardour/redirect.cc | 26 +- libs/ardour/region.cc | 47 +- libs/ardour/route.cc | 391 ++-- libs/ardour/session.cc | 514 +++--- libs/ardour/session_butler.cc | 51 +- libs/ardour/session_export.cc | 7 +- libs/ardour/session_midi.cc | 13 +- libs/ardour/session_process.cc | 57 +- libs/ardour/session_state.cc | 157 +- libs/ardour/session_time.cc | 5 - libs/ardour/session_transport.cc | 63 +- libs/ardour/sndfilesource.cc | 48 +- libs/ardour/source.cc | 5 +- libs/ardour/track.cc | 219 +++ libs/ardour/utils.cc | 27 +- libs/ardour/vst_plugin.cc | 41 +- libs/gtkmm2ext/SConscript | 10 +- libs/gtkmm2ext/barcontroller.cc | 103 +- libs/gtkmm2ext/binding_proxy.cc | 89 + libs/gtkmm2ext/controller.cc | 92 - libs/gtkmm2ext/gtkmm2ext/barcontroller.h | 23 +- libs/gtkmm2ext/gtkmm2ext/bindable_button.h | 50 +- .../gtkmm2ext/binding_proxy.h} | 46 +- .../gtkmm2ext/{controller.h => pathlist.h} | 60 +- libs/gtkmm2ext/gtkmm2ext/slider_controller.h | 42 +- libs/gtkmm2ext/pathlist.cc | 124 ++ libs/gtkmm2ext/popup.cc | 14 +- libs/gtkmm2ext/slider_controller.cc | 116 +- libs/libgnomecanvasmm/SConscript | 9 +- libs/libsndfile/src/sndfile.c | 15 +- libs/midi++2/SConscript | 3 +- libs/midi++2/midi++/channel.h | 2 +- libs/midi++2/midi++/controllable.h | 92 - libs/midi++2/midi++/coremidi_midiport.h | 2 +- libs/midi++2/midi++/factory.h | 2 +- libs/midi++2/midi++/fd_midiport.h | 2 +- libs/midi++2/midi++/fifomidi.h | 2 +- libs/midi++2/midi++/manager.h | 2 +- libs/midi++2/midi++/mmc.h | 4 +- libs/midi++2/midi++/nullmidi.h | 2 +- libs/midi++2/midi++/parser.h | 2 +- libs/midi++2/midi++/port.h | 5 +- libs/midi++2/midi++/port_request.h | 2 +- libs/midi++2/midi++/types.h | 4 +- libs/midi++2/midiparser.cc | 2 +- libs/{pbd3 => pbd}/.cvsignore | 0 libs/{pbd3 => pbd}/AUTHORS | 0 libs/{pbd3 => pbd}/COPYING | 0 libs/{pbd3 => pbd}/ChangeLog | 0 libs/{pbd3 => pbd}/NEWS | 0 libs/{pbd3 => pbd}/README | 0 libs/pbd/SConscript | 75 + libs/{pbd3 => pbd}/base_ui.cc | 0 libs/{pbd3 => pbd}/basename.cc | 0 libs/{pbd3 => pbd}/command.cc | 0 libs/pbd/controllable.cc | 26 + libs/{pbd3 => pbd}/convert.cc | 0 libs/{pbd3 => pbd}/dmalloc.cc | 0 libs/{pbd3 => pbd}/error.cc | 0 libs/{pbd3 => pbd}/gettext.h | 0 libs/{pbd3 => pbd}/i18n.h | 0 libs/pbd/id.cc | 63 + libs/{pbd3 => pbd}/libpbd.pc.in | 0 libs/{pbd3 => pbd}/libpbd.spec.in | 0 libs/{pbd3 => pbd}/mountpoint.cc | 55 +- libs/pbd/path.cc | 164 ++ libs/{pbd3 => pbd}/pathscanner.cc | 0 libs/{pbd3 => pbd}/pbd/.DS_Store | Bin libs/{pbd3 => pbd}/pbd/.cvsignore | 0 libs/{pbd3 => pbd}/pbd/abstract_ui.cc | 0 libs/{pbd3 => pbd}/pbd/abstract_ui.h | 0 libs/{pbd3 => pbd}/pbd/base_ui.h | 0 libs/{pbd3 => pbd}/pbd/basename.h | 2 +- libs/{pbd3 => pbd}/pbd/command.h | 0 libs/{pbd3 => pbd}/pbd/compose.h | 0 libs/pbd/pbd/controllable.h | 46 + libs/{pbd3 => pbd}/pbd/convert.h | 0 libs/{pbd3 => pbd}/pbd/error.h | 0 libs/{pbd3 => pbd}/pbd/failed_constructor.h | 0 libs/{pbd3 => pbd}/pbd/fastlog.h | 0 libs/{pbd3 => pbd}/pbd/forkexec.h | 0 libs/pbd/pbd/id.h | 47 + libs/{pbd3 => pbd}/pbd/mathfix.h | 0 libs/{pbd3 => pbd}/pbd/memento_command.h | 0 libs/{pbd3 => pbd}/pbd/mountpoint.h | 0 libs/pbd/pbd/path.h | 113 ++ libs/{pbd3 => pbd}/pbd/pathscanner.h | 0 libs/{pbd3 => pbd}/pbd/pool.h | 0 libs/{pbd3 => pbd}/pbd/pthread_utils.h | 0 libs/pbd/pbd/rcu.h | 120 ++ libs/{pbd3 => pbd}/pbd/receiver.h | 0 libs/{pbd3 => pbd}/pbd/restartable_rw.h | 0 libs/{pbd3 => pbd}/pbd/ringbuffer.h | 0 libs/{pbd3 => pbd}/pbd/ringbufferNPT.h | 0 libs/{pbd3 => pbd}/pbd/selectable.h | 0 libs/{pbd3 => pbd}/pbd/serializable.h | 0 libs/{pbd3 => pbd}/pbd/stacktrace.h | 0 libs/{ardour/ardour => pbd/pbd}/stateful.h | 8 +- libs/{pbd3 => pbd}/pbd/stl_delete.h | 0 libs/{pbd3 => pbd}/pbd/stl_functors.h | 0 libs/{pbd3 => pbd}/pbd/strsplit.h | 0 libs/{pbd3 => pbd}/pbd/textreceiver.h | 0 libs/{pbd3 => pbd}/pbd/thrown_error.h | 0 libs/pbd/pbd/tokenizer.h | 49 + libs/{pbd3 => pbd}/pbd/touchable.h | 0 libs/{pbd3 => pbd}/pbd/transmitter.h | 0 libs/{pbd3 => pbd}/pbd/undo.h | 0 libs/{pbd3 => pbd}/pbd/whitespace.h | 0 libs/{pbd3 => pbd}/pbd/xml++.h | 16 +- libs/{pbd3 => pbd}/pool.cc | 2 +- libs/{pbd3 => pbd}/pthread_utils.cc | 0 libs/{pbd3 => pbd}/receiver.cc | 0 libs/{pbd3 => pbd}/stacktrace.cc | 0 libs/{ardour => pbd}/stateful.cc | 13 +- libs/{pbd3 => pbd}/strsplit.cc | 0 libs/{pbd3 => pbd}/textreceiver.cc | 0 libs/{pbd3 => pbd}/transmitter.cc | 0 libs/{pbd3 => pbd}/undo.cc | 0 libs/pbd/whitespace.cc | 44 + libs/pbd/xml++.cc | 420 +++++ libs/pbd3/SConscript | 66 - libs/pbd3/whitespace.cc | 30 - libs/pbd3/xml++.cc | 422 ----- libs/soundtouch/STTypes.h | 2 +- libs/surfaces/control_protocol/SConscript | 2 +- .../control_protocol/control_protocol.cc | 51 +- .../control_protocol/control_protocol.h | 9 +- libs/surfaces/generic_midi/SConscript | 3 +- .../generic_midi_control_protocol.cc | 222 ++- .../generic_midi_control_protocol.h | 46 +- libs/surfaces/generic_midi/interface.cc | 10 +- .../generic_midi}/midicontrollable.cc | 198 +- libs/surfaces/generic_midi/midicontrollable.h | 97 + libs/surfaces/tranzport/SConscript | 2 +- .../tranzport/tranzport_control_protocol.cc | 16 +- .../tranzport/tranzport_control_protocol.h | 3 + tools/.cvsignore | 3 - tools/config.guess | 696 +++---- tools/osx_packaging/ardour2_mac_ui.rc | 1225 +++++++++++++ vst/SConscript | 6 +- 372 files changed, 20759 insertions(+), 10250 deletions(-) rename gtk2_ardour/{region_editor.cc => audio_region_editor.cc} (99%) create mode 100644 gtk2_ardour/audio_region_editor.h create mode 100644 gtk2_ardour/audio_region_view.cc rename gtk2_ardour/{regionview.h => audio_region_view.h} (56%) rename gtk2_ardour/{regionview.cc => audio_regionview.cc} (98%) create mode 100644 gtk2_ardour/audio_streamview.cc create mode 100644 gtk2_ardour/audio_streamview.h create mode 100644 gtk2_ardour/pixmaps/tool_audition.xpm create mode 100644 gtk2_ardour/pixmaps/tool_gain.xpm create mode 100644 gtk2_ardour/pixmaps/tool_object.xpm create mode 100644 gtk2_ardour/pixmaps/tool_range.xpm create mode 100644 gtk2_ardour/pixmaps/tool_stretch.xpm create mode 100644 gtk2_ardour/pixmaps/tool_zoom.xpm create mode 100644 gtk2_ardour/pixmaps/zoom_full.xpm create mode 100644 gtk2_ardour/pixmaps/zoom_in.xpm create mode 100644 gtk2_ardour/pixmaps/zoom_out.xpm create mode 100644 gtk2_ardour/region_view.cc create mode 100644 gtk2_ardour/region_view.h create mode 100644 gtk2_ardour/route_time_axis.cc create mode 100644 gtk2_ardour/route_time_axis.h rename gtk2_ardour/{taperegionview.cc => tape_region_view.cc} (58%) rename gtk2_ardour/{taperegionview.h => tape_region_view.h} (86%) create mode 100644 libs/appleutility/AUOutputBL.cpp create mode 100644 libs/appleutility/AUOutputBL.h create mode 100644 libs/appleutility/CAAudioChannelLayout.cpp create mode 100644 libs/appleutility/CAAudioChannelLayout.h create mode 100644 libs/appleutility/CAAudioChannelLayoutObject.cpp create mode 100644 libs/appleutility/CAAudioUnit.cpp create mode 100644 libs/appleutility/CAAudioUnit.h create mode 100644 libs/appleutility/CACFDictionary.cpp create mode 100644 libs/appleutility/CACFDictionary.h create mode 100644 libs/appleutility/CACFNumber.cpp create mode 100644 libs/appleutility/CACFNumber.h create mode 100644 libs/appleutility/CACFString.cpp create mode 100644 libs/appleutility/CACFString.h create mode 100644 libs/appleutility/CAComponent.cpp create mode 100644 libs/appleutility/CAComponent.h create mode 100644 libs/appleutility/CAComponentDescription.cpp create mode 100644 libs/appleutility/CAComponentDescription.h create mode 100644 libs/appleutility/CAConditionalMacros.h create mode 100644 libs/appleutility/CADebugMacros.cpp create mode 100644 libs/appleutility/CADebugMacros.h create mode 100644 libs/appleutility/CAMath.h create mode 100644 libs/appleutility/CAReferenceCounted.h create mode 100644 libs/appleutility/CAStreamBasicDescription.cpp create mode 100644 libs/appleutility/CAStreamBasicDescription.h create mode 100644 libs/appleutility/SConscript create mode 100644 libs/ardour/ardour/audio_unit.h create mode 100644 libs/ardour/ardour/buffer.h create mode 100644 libs/ardour/ardour/data_type.h create mode 100644 libs/ardour/ardour/diskstream.h create mode 100644 libs/ardour/ardour/track.h create mode 100644 libs/ardour/audio_unit.cc create mode 100644 libs/ardour/diskstream.cc create mode 100644 libs/ardour/track.cc create mode 100644 libs/gtkmm2ext/binding_proxy.cc delete mode 100644 libs/gtkmm2ext/controller.cc rename libs/{ardour/ardour/session_diskstream.h => gtkmm2ext/gtkmm2ext/binding_proxy.h} (50%) rename libs/gtkmm2ext/gtkmm2ext/{controller.h => pathlist.h} (51%) create mode 100644 libs/gtkmm2ext/pathlist.cc delete mode 100644 libs/midi++2/midi++/controllable.h rename libs/{pbd3 => pbd}/.cvsignore (100%) rename libs/{pbd3 => pbd}/AUTHORS (100%) rename libs/{pbd3 => pbd}/COPYING (100%) rename libs/{pbd3 => pbd}/ChangeLog (100%) rename libs/{pbd3 => pbd}/NEWS (100%) rename libs/{pbd3 => pbd}/README (100%) create mode 100644 libs/pbd/SConscript rename libs/{pbd3 => pbd}/base_ui.cc (100%) rename libs/{pbd3 => pbd}/basename.cc (100%) rename libs/{pbd3 => pbd}/command.cc (100%) create mode 100644 libs/pbd/controllable.cc rename libs/{pbd3 => pbd}/convert.cc (100%) rename libs/{pbd3 => pbd}/dmalloc.cc (100%) rename libs/{pbd3 => pbd}/error.cc (100%) rename libs/{pbd3 => pbd}/gettext.h (100%) rename libs/{pbd3 => pbd}/i18n.h (100%) create mode 100644 libs/pbd/id.cc rename libs/{pbd3 => pbd}/libpbd.pc.in (100%) rename libs/{pbd3 => pbd}/libpbd.spec.in (100%) rename libs/{pbd3 => pbd}/mountpoint.cc (68%) create mode 100644 libs/pbd/path.cc rename libs/{pbd3 => pbd}/pathscanner.cc (100%) rename libs/{pbd3 => pbd}/pbd/.DS_Store (100%) rename libs/{pbd3 => pbd}/pbd/.cvsignore (100%) rename libs/{pbd3 => pbd}/pbd/abstract_ui.cc (100%) rename libs/{pbd3 => pbd}/pbd/abstract_ui.h (100%) rename libs/{pbd3 => pbd}/pbd/base_ui.h (100%) rename libs/{pbd3 => pbd}/pbd/basename.h (90%) rename libs/{pbd3 => pbd}/pbd/command.h (100%) rename libs/{pbd3 => pbd}/pbd/compose.h (100%) create mode 100644 libs/pbd/pbd/controllable.h rename libs/{pbd3 => pbd}/pbd/convert.h (100%) rename libs/{pbd3 => pbd}/pbd/error.h (100%) rename libs/{pbd3 => pbd}/pbd/failed_constructor.h (100%) rename libs/{pbd3 => pbd}/pbd/fastlog.h (100%) rename libs/{pbd3 => pbd}/pbd/forkexec.h (100%) create mode 100644 libs/pbd/pbd/id.h rename libs/{pbd3 => pbd}/pbd/mathfix.h (100%) rename libs/{pbd3 => pbd}/pbd/memento_command.h (100%) rename libs/{pbd3 => pbd}/pbd/mountpoint.h (100%) create mode 100644 libs/pbd/pbd/path.h rename libs/{pbd3 => pbd}/pbd/pathscanner.h (100%) rename libs/{pbd3 => pbd}/pbd/pool.h (100%) rename libs/{pbd3 => pbd}/pbd/pthread_utils.h (100%) create mode 100644 libs/pbd/pbd/rcu.h rename libs/{pbd3 => pbd}/pbd/receiver.h (100%) rename libs/{pbd3 => pbd}/pbd/restartable_rw.h (100%) rename libs/{pbd3 => pbd}/pbd/ringbuffer.h (100%) rename libs/{pbd3 => pbd}/pbd/ringbufferNPT.h (100%) rename libs/{pbd3 => pbd}/pbd/selectable.h (100%) rename libs/{pbd3 => pbd}/pbd/serializable.h (100%) rename libs/{pbd3 => pbd}/pbd/stacktrace.h (100%) rename libs/{ardour/ardour => pbd/pbd}/stateful.h (89%) rename libs/{pbd3 => pbd}/pbd/stl_delete.h (100%) rename libs/{pbd3 => pbd}/pbd/stl_functors.h (100%) rename libs/{pbd3 => pbd}/pbd/strsplit.h (100%) rename libs/{pbd3 => pbd}/pbd/textreceiver.h (100%) rename libs/{pbd3 => pbd}/pbd/thrown_error.h (100%) create mode 100644 libs/pbd/pbd/tokenizer.h rename libs/{pbd3 => pbd}/pbd/touchable.h (100%) rename libs/{pbd3 => pbd}/pbd/transmitter.h (100%) rename libs/{pbd3 => pbd}/pbd/undo.h (100%) rename libs/{pbd3 => pbd}/pbd/whitespace.h (100%) rename libs/{pbd3 => pbd}/pbd/xml++.h (86%) rename libs/{pbd3 => pbd}/pool.cc (99%) rename libs/{pbd3 => pbd}/pthread_utils.cc (100%) rename libs/{pbd3 => pbd}/receiver.cc (100%) rename libs/{pbd3 => pbd}/stacktrace.cc (100%) rename libs/{ardour => pbd}/stateful.cc (95%) rename libs/{pbd3 => pbd}/strsplit.cc (100%) rename libs/{pbd3 => pbd}/textreceiver.cc (100%) rename libs/{pbd3 => pbd}/transmitter.cc (100%) rename libs/{pbd3 => pbd}/undo.cc (100%) create mode 100644 libs/pbd/whitespace.cc create mode 100644 libs/pbd/xml++.cc delete mode 100644 libs/pbd3/SConscript delete mode 100644 libs/pbd3/whitespace.cc delete mode 100644 libs/pbd3/xml++.cc rename libs/{midi++2 => surfaces/generic_midi}/midicontrollable.cc (53%) create mode 100644 libs/surfaces/generic_midi/midicontrollable.h delete mode 100644 tools/.cvsignore create mode 100644 tools/osx_packaging/ardour2_mac_ui.rc diff --git a/SConstruct b/SConstruct index 1dd250edfb..e93aad96a8 100644 --- a/SConstruct +++ b/SConstruct @@ -31,6 +31,7 @@ opts.AddOptions( PathOption('DESTDIR', 'Set the intermediate install "prefix"', '/'), EnumOption('DIST_TARGET', 'Build target for cross compiling packagers', 'auto', allowed_values=('auto', 'i386', 'i686', 'x86_64', 'powerpc', 'tiger', 'panther', 'none' ), ignorecase=2), BoolOption('DMALLOC', 'Compile and link using the dmalloc library', 0), + BoolOption('EXTRA_WARN', 'Compile with -Wextra, -ansi, and -pedantic. Might break compilation. For pedants', 0), BoolOption('FFT_ANALYSIS', 'Include FFT analysis window', 0), BoolOption('FPU_OPTIMIZATION', 'Build runtime checked assembler code', 1), BoolOption('LIBLO', 'Compile with support for liblo library', 1), @@ -50,18 +51,25 @@ opts.AddOptions( class LibraryInfo(Environment): def __init__(self,*args,**kw): Environment.__init__ (self,*args,**kw) - + def Merge (self,others): for other in others: self.Append (LIBS = other.get ('LIBS',[])) - self.Append (LIBPATH = other.get ('LIBPATH', [])) + self.Append (LIBPATH = other.get ('LIBPATH', [])) self.Append (CPPPATH = other.get('CPPPATH', [])) self.Append (LINKFLAGS = other.get('LINKFLAGS', [])) self.Replace(LIBPATH = list(Set(self.get('LIBPATH', [])))) self.Replace(CPPPATH = list(Set(self.get('CPPPATH',[])))) #doing LINKFLAGS breaks -framework #doing LIBS break link order dependency - + + def ENV_update(self, src_ENV): + for k in src_ENV.keys(): + if k in self['ENV'].keys() and k in [ 'PATH', 'LD_LIBRARY_PATH', + 'LIB', 'INCLUDE' ]: + self['ENV'][k]=SCons.Util.AppendPath(self['ENV'][k], src_ENV[k]) + else: + self['ENV'][k]=src_ENV[k] env = LibraryInfo (options = opts, CPPPATH = [ '.' ], @@ -72,68 +80,69 @@ env = LibraryInfo (options = opts, DISTCHECKDIR = '#ardour-' + version + '/check' ) +env.ENV_update(os.environ) #---------------------------------------------------------------------- # Builders #---------------------------------------------------------------------- # Handy subst-in-file builder -# +# def do_subst_in_file(targetfile, sourcefile, dict): - """Replace all instances of the keys of dict with their values. - For example, if dict is {'%VERSION%': '1.2345', '%BASE%': 'MyProg'}, - then all instances of %VERSION% in the file will be replaced with 1.2345 etc. - """ - try: - f = open(sourcefile, 'rb') - contents = f.read() - f.close() - except: - raise SCons.Errors.UserError, "Can't read source file %s"%sourcefile - for (k,v) in dict.items(): - contents = re.sub(k, v, contents) - try: - f = open(targetfile, 'wb') - f.write(contents) - f.close() - except: - raise SCons.Errors.UserError, "Can't write target file %s"%targetfile - return 0 # success - + """Replace all instances of the keys of dict with their values. + For example, if dict is {'%VERSION%': '1.2345', '%BASE%': 'MyProg'}, + then all instances of %VERSION% in the file will be replaced with 1.2345 etc. + """ + try: + f = open(sourcefile, 'rb') + contents = f.read() + f.close() + except: + raise SCons.Errors.UserError, "Can't read source file %s"%sourcefile + for (k,v) in dict.items(): + contents = re.sub(k, v, contents) + try: + f = open(targetfile, 'wb') + f.write(contents) + f.close() + except: + raise SCons.Errors.UserError, "Can't write target file %s"%targetfile + return 0 # success + def subst_in_file(target, source, env): - if not env.has_key('SUBST_DICT'): - raise SCons.Errors.UserError, "SubstInFile requires SUBST_DICT to be set." - d = dict(env['SUBST_DICT']) # copy it - for (k,v) in d.items(): - if callable(v): - d[k] = env.subst(v()) - elif SCons.Util.is_String(v): - d[k]=env.subst(v) - else: - raise SCons.Errors.UserError, "SubstInFile: key %s: %s must be a string or callable"%(k, repr(v)) - for (t,s) in zip(target, source): - return do_subst_in_file(str(t), str(s), d) - + if not env.has_key('SUBST_DICT'): + raise SCons.Errors.UserError, "SubstInFile requires SUBST_DICT to be set." + d = dict(env['SUBST_DICT']) # copy it + for (k,v) in d.items(): + if callable(v): + d[k] = env.subst(v()) + elif SCons.Util.is_String(v): + d[k]=env.subst(v) + else: + raise SCons.Errors.UserError, "SubstInFile: key %s: %s must be a string or callable"%(k, repr(v)) + for (t,s) in zip(target, source): + return do_subst_in_file(str(t), str(s), d) + def subst_in_file_string(target, source, env): - """This is what gets printed on the console.""" - return '\n'.join(['Substituting vars from %s into %s'%(str(s), str(t)) - for (t,s) in zip(target, source)]) - + """This is what gets printed on the console.""" + return '\n'.join(['Substituting vars from %s into %s'%(str(s), str(t)) + for (t,s) in zip(target, source)]) + def subst_emitter(target, source, env): - """Add dependency from substituted SUBST_DICT to target. - Returns original target, source tuple unchanged. - """ - d = env['SUBST_DICT'].copy() # copy it - for (k,v) in d.items(): - if callable(v): - d[k] = env.subst(v()) - elif SCons.Util.is_String(v): - d[k]=env.subst(v) - Depends(target, SCons.Node.Python.Value(d)) - # Depends(target, source) # this doesn't help the install-sapphire-linux.sh problem - return target, source - + """Add dependency from substituted SUBST_DICT to target. + Returns original target, source tuple unchanged. + """ + d = env['SUBST_DICT'].copy() # copy it + for (k,v) in d.items(): + if callable(v): + d[k] = env.subst(v()) + elif SCons.Util.is_String(v): + d[k]=env.subst(v) + Depends(target, SCons.Node.Python.Value(d)) + # Depends(target, source) # this doesn't help the install-sapphire-linux.sh problem + return target, source + subst_action = Action (subst_in_file, subst_in_file_string) env['BUILDERS']['SubstInFile'] = Builder(action=subst_action, emitter=subst_emitter) @@ -141,31 +150,31 @@ env['BUILDERS']['SubstInFile'] = Builder(action=subst_action, emitter=subst_emit # internationalization # -# po_helper -# -# this is not a builder. we can't list the .po files as a target, -# because then scons -c will remove them (even Precious doesn't alter -# this). this function is called whenever a .mo file is being -# built, and will conditionally update the .po file if necessary. -# - -def po_helper(po,pot): - args = [ 'msgmerge', - '--update', - po, - pot, - ] - print 'Updating ' + po - return os.spawnvp (os.P_WAIT, 'msgmerge', args) - -# mo_builder: builder function for (binary) message catalogs (.mo) +# po_builder: builder function to copy po files to the parent directory while updating them # # first source: .po file # second source: .pot file # +def po_builder(target,source,env): + os.spawnvp (os.P_WAIT, 'cp', ['cp', str(source[0]), str(target[0])]) + args = [ 'msgmerge', + '--update', + str(target[0]), + str(source[1]) + ] + print 'Updating ' + str(target[0]) + return os.spawnvp (os.P_WAIT, 'msgmerge', args) + +po_bld = Builder (action = po_builder) +env.Append(BUILDERS = {'PoBuild' : po_bld}) + +# mo_builder: builder function for (binary) message catalogs (.mo) +# +# first source: .po file +# + def mo_builder(target,source,env): - po_helper (source[0].get_path(), source[1].get_path()) args = [ 'msgfmt', '-c', '-o', @@ -183,15 +192,15 @@ env.Append(BUILDERS = {'MoBuild' : mo_bld}) # def pot_builder(target,source,env): - args = [ 'xgettext', + args = [ 'xgettext', '--keyword=_', '--keyword=N_', '--from-code=UTF-8', - '-o', target[0].get_path(), + '-o', target[0].get_path(), "--default-domain=" + env['PACKAGE'], '--copyright-holder="Paul Davis"' ] args += [ src.get_path() for src in source ] - + return os.spawnvp (os.P_WAIT, 'xgettext', args) pot_bld = Builder (action = pot_builder) @@ -204,33 +213,33 @@ env.Append(BUILDERS = {'PotBuild' : pot_bld}) def i18n (buildenv, sources, installenv): domain = buildenv['PACKAGE'] potfile = buildenv['POTFILE'] - + installenv.Alias ('potupdate', buildenv.PotBuild (potfile, sources)) - + p_oze = [ os.path.basename (po) for po in glob.glob ('po/*.po') ] languages = [ po.replace ('.po', '') for po in p_oze ] - m_oze = [ po.replace (".po", ".mo") for po in p_oze ] - for mo in m_oze[:]: - po = 'po/' + mo.replace (".mo", ".po") - installenv.Alias ('install', buildenv.MoBuild (mo, [ po, potfile ])) - - for lang in languages[:]: + for po_file in p_oze: + buildenv.PoBuild(po_file, ['po/'+po_file, potfile]) + mo_file = po_file.replace (".po", ".mo") + installenv.Alias ('install', buildenv.MoBuild (mo_file, po_file)) + + for lang in languages: modir = (os.path.join (install_prefix, 'share/locale/' + lang + '/LC_MESSAGES/')) moname = domain + '.mo' installenv.Alias('install', installenv.InstallAs (os.path.join (modir, moname), lang + '.mo')) # # A generic builder for version.cc files -# +# # note: requires that DOMAIN, MAJOR, MINOR, MICRO are set in the construction environment # note: assumes one source files, the header that declares the version variables -# +# def version_builder (target, source, env): text = "int " + env['DOMAIN'] + "_major_version = " + str (env['MAJOR']) + ";\n" text += "int " + env['DOMAIN'] + "_minor_version = " + str (env['MINOR']) + ";\n" text += "int " + env['DOMAIN'] + "_micro_version = " + str (env['MICRO']) + ";\n" - + try: o = file (target[0].get_path(), 'w') o.write (text) @@ -238,14 +247,14 @@ def version_builder (target, source, env): except IOError: print "Could not open", target[0].get_path(), " for writing\n" sys.exit (-1) - + text = "#ifndef __" + env['DOMAIN'] + "_version_h__\n" text += "#define __" + env['DOMAIN'] + "_version_h__\n" text += "extern int " + env['DOMAIN'] + "_major_version;\n" text += "extern int " + env['DOMAIN'] + "_minor_version;\n" text += "extern int " + env['DOMAIN'] + "_micro_version;\n" text += "#endif /* __" + env['DOMAIN'] + "_version_h__ */\n" - + try: o = file (target[1].get_path(), 'w') o.write (text) @@ -253,7 +262,7 @@ def version_builder (target, source, env): except IOError: print "Could not open", target[1].get_path(), " for writing\n" sys.exit (-1) - + return None version_bld = Builder (action = version_builder) @@ -276,8 +285,8 @@ def versioned_builder(target,source,env): except IOError: print "Could not CVS/Entries for reading" return -1 - - last_date = "" + + last_date = "" lines = o.readlines() for line in lines: if line[0:12] == '/SConscript/': @@ -285,20 +294,20 @@ def versioned_builder(target,source,env): last_date = parts[3] break o.close () - + if last_date == "": print "No SConscript CVS update info found - versioned executable cannot be built" return -1 - + tag = time.strftime ('%Y%M%d%H%m', time.strptime (last_date)) print "The current build ID is " + tag - + tagged_executable = source[0].get_path() + '-' + tag - + if os.path.exists (tagged_executable): print "Replacing existing executable with the same build tag." os.unlink (tagged_executable) - + return os.link (source[0].get_path(), tagged_executable) verbuild = Builder (action = versioned_builder) @@ -310,13 +319,13 @@ env.Append (BUILDERS = {'VersionedExecutable' : verbuild}) def distcopy (target, source, env): treedir = str (target[0]) - + try: os.mkdir (treedir) except OSError, (errnum, strerror): if errnum != errno.EEXIST: print 'mkdir ', treedir, ':', strerror - + cmd = 'tar cf - ' # # we don't know what characters might be in the file names @@ -328,7 +337,7 @@ def distcopy (target, source, env): p = os.popen (cmd) return p.close () -def tarballer (target, source, env): +def tarballer (target, source, env): cmd = 'tar -jcf ' + str (target[0]) + ' ' + str(source[0]) + " --exclude '*~'" print 'running ', cmd, ' ... ' p = os.popen (cmd) @@ -359,7 +368,7 @@ if env['VST']: env['VST'] = 0; else: print "OK, VST support will be enabled" - + # ---------------------------------------------------------------------- # Construction environment setup @@ -381,7 +390,7 @@ libraries['raptor'].ParseConfig('pkg-config --cflags --libs raptor') libraries['samplerate'] = LibraryInfo() libraries['samplerate'].ParseConfig('pkg-config --cflags --libs samplerate') -if env['FFT_ANALYSIS']: +if env['FFT_ANALYSIS']: libraries['fftw3f'] = LibraryInfo() libraries['fftw3f'].ParseConfig('pkg-config --cflags --libs fftw3f') @@ -420,9 +429,8 @@ libraries['ardour_cp'] = LibraryInfo (LIBS='ardour_cp', LIBPATH='#libs/surfaces/ libraries['ardour'] = LibraryInfo (LIBS='ardour', LIBPATH='#libs/ardour', CPPPATH='#libs/ardour') libraries['midi++2'] = LibraryInfo (LIBS='midi++', LIBPATH='#libs/midi++2', CPPPATH='#libs/midi++2') -libraries['pbd3'] = LibraryInfo (LIBS='pbd', LIBPATH='#libs/pbd3', CPPPATH='#libs/pbd3') +libraries['pbd'] = LibraryInfo (LIBS='pbd', LIBPATH='#libs/pbd', CPPPATH='#libs/pbd') libraries['gtkmm2ext'] = LibraryInfo (LIBS='gtkmm2ext', LIBPATH='#libs/gtkmm2ext', CPPPATH='#libs/gtkmm2ext') -#libraries['cassowary'] = LibraryInfo(LIBS='cassowary', LIBPATH='#libs/cassowary', CPPPATH='#libs/cassowary') # # Check for libusb @@ -434,7 +442,7 @@ if conf.CheckLib ('usb', 'usb_interrupt_write'): have_libusb = True else: have_libusb = False - + libraries['usb'] = conf.Finish () # @@ -443,7 +451,7 @@ libraries['usb'] = conf.Finish () libraries['flac'] = LibraryInfo () conf = Configure (libraries['flac']) -conf.CheckLib ('FLAC', 'FLAC__stream_decoder_new') +conf.CheckLib ('FLAC', 'FLAC__stream_decoder_new', language='CXX') libraries['flac'] = conf.Finish () # @@ -451,7 +459,7 @@ libraries['flac'] = conf.Finish () if env['LIBLO']: libraries['lo'] = LibraryInfo () - + conf = Configure (libraries['lo']) if conf.CheckLib ('lo', 'lo_server_new') == False: print "liblo does not appear to be installed." @@ -473,14 +481,14 @@ if conf.CheckLib ('dmallocth', 'dmalloc_shutdown'): have_libdmalloc = True else: have_libdmalloc = False - + libraries['dmalloc'] = conf.Finish () # # # Audio/MIDI library (needed for MIDI, since audio is all handled via JACK) -# +# conf = Configure(env) @@ -498,11 +506,11 @@ elif conf.CheckCHeader('/System/Library/Frameworks/CoreMIDI.framework/Headers/Co else: print "It appears you don't have the required MIDI libraries installed." sys.exit (1) - + env = conf.Finish() if env['SYSLIBS']: - + libraries['sigc2'] = LibraryInfo() libraries['sigc2'].ParseConfig('pkg-config --cflags --libs sigc++-2.0') libraries['glibmm2'] = LibraryInfo() @@ -521,7 +529,7 @@ if env['SYSLIBS']: # # cannot use system one for the time being # - + libraries['sndfile'] = LibraryInfo(LIBS='libsndfile', LIBPATH='#libs/libsndfile', CPPPATH=['#libs/libsndfile', '#libs/libsndfile/src']) @@ -531,22 +539,29 @@ if env['SYSLIBS']: # libraries['flowcanvas'] = LibraryInfo(LIBS='flowcanvas', LIBPATH='#/libs/flowcanvas', CPPPATH='#libs/flowcanvas') libraries['soundtouch'] = LibraryInfo() - libraries['soundtouch'].ParseConfig ('pkg-config --cflags --libs soundtouch-1.0') + libraries['soundtouch'].ParseConfig ('pkg-config --cflags --libs libSoundTouch') + libraries['appleutility'] = LibraryInfo(LIBS='libappleutility', + LIBPATH='#libs/appleutility', + CPPPATH='#libs/appleutility') + coredirs = [ 'templates' ] - + subdirs = [ 'libs/libsndfile', - 'libs/pbd3', + 'libs/pbd', 'libs/midi++2', 'libs/ardour' ] - + if env['VST']: subdirs = ['libs/fst'] + subdirs + ['vst'] + if env['COREAUDIO']: + subdirs = subdirs + ['libs/appleutility'] + gtk_subdirs = [ # 'libs/flowcanvas', 'libs/gtkmm2ext', @@ -575,7 +590,7 @@ else: libraries['libgnomecanvasmm'] = LibraryInfo(LIBS='libgnomecanvasmm', LIBPATH='#libs/libgnomecanvasmm', CPPPATH='#libs/libgnomecanvasmm') - + libraries['soundtouch'] = LibraryInfo(LIBS='soundtouch', LIBPATH='#libs/soundtouch', CPPPATH=['#libs', '#libs/soundtouch']) @@ -585,24 +600,29 @@ else: # libraries['libglademm'] = LibraryInfo(LIBS='libglademm', # LIBPATH='#libs/libglademm', # CPPPATH='#libs/libglademm') + libraries['appleutility'] = LibraryInfo(LIBS='libappleutility', + LIBPATH='#libs/appleutility', + CPPPATH='#libs/appleutility') coredirs = [ 'libs/soundtouch', 'templates' ] - + subdirs = [ -# 'libs/cassowary', 'libs/sigc++2', 'libs/libsndfile', - 'libs/pbd3', + 'libs/pbd', 'libs/midi++2', 'libs/ardour' ] - + if env['VST']: subdirs = ['libs/fst'] + subdirs + ['vst'] + if env['COREAUDIO']: + subdirs = subdirs + ['libs/appleutility'] + gtk_subdirs = [ 'libs/glibmm2', 'libs/gtkmm2/pango', @@ -627,7 +647,7 @@ if env['SURFACES']: surface_subdirs += [ 'libs/surfaces/tranzport' ] if os.access ('libs/surfaces/sony9pin', os.F_OK): surface_subdirs += [ 'libs/surfaces/sony9pin' ] - + opts.Save('scache.conf', env) Help(opts.GenerateHelpText(env)) @@ -646,7 +666,7 @@ if os.environ.has_key('CXX'): if os.environ.has_key('DISTCC_HOSTS'): env['ENV']['DISTCC_HOSTS'] = os.environ['DISTCC_HOSTS'] env['ENV']['HOME'] = os.environ['HOME'] - + final_prefix = '$PREFIX' install_prefix = '$DESTDIR/$PREFIX' @@ -670,7 +690,7 @@ if have_cxx[0] != 1: exit (1) else: print "Congratulations, you have a functioning C++ compiler." - + env = conf.Finish() # @@ -724,37 +744,37 @@ if config[config_cpu] == 'powerpc' and env['DIST_TARGET'] != 'none': if config[config_arch] == 'apple': opt_flags.extend ([ "-mcpu=7450", "-faltivec"]) else: - opt_flags.extend ([ "-mcpu=7400", "-maltivec", "-mabi=altivec"]) + opt_flags.extend ([ "-mcpu=7400", "-maltivec", "-mabi=altivec"]) else: opt_flags.extend([ "-mcpu=750", "-mmultiple" ]) opt_flags.extend (["-mhard-float", "-mpowerpc-gfxopt"]) elif ((re.search ("i[0-9]86", config[config_cpu]) != None) or (re.search ("x86_64", config[config_cpu]) != None)) and env['DIST_TARGET'] != 'none': - + build_host_supports_sse = 0 debug_flags.append ("-DARCH_X86") opt_flags.append ("-DARCH_X86") - + if config[config_kernel] == 'linux' : - - if env['DIST_TARGET'] != 'i386': - + + if env['DIST_TARGET'] != 'i386': + flag_line = os.popen ("cat /proc/cpuinfo | grep '^flags'").read()[:-1] x86_flags = flag_line.split (": ")[1:][0].split (' ') - + if "mmx" in x86_flags: opt_flags.append ("-mmmx") if "sse" in x86_flags: build_host_supports_sse = 1 if "3dnow" in x86_flags: opt_flags.append ("-m3dnow") - + if config[config_cpu] == "i586": opt_flags.append ("-march=i586") elif config[config_cpu] == "i686": opt_flags.append ("-march=i686") - + if ((env['DIST_TARGET'] == 'i686') or (env['DIST_TARGET'] == 'x86_64')) and build_host_supports_sse: opt_flags.extend (["-msse", "-mfpmath=sse"]) debug_flags.extend (["-msse", "-mfpmath=sse"]) @@ -783,7 +803,7 @@ env.Append(CONFIG_ARCH=config[config_arch]) # -# ARCH="..." overrides all +# ARCH="..." overrides all # if env['ARCH'] != '': @@ -812,6 +832,10 @@ else: env.Append(CCFLAGS="-Wall") env.Append(CXXFLAGS="-Woverloaded-virtual") +if env['EXTRA_WARN']: + env.Append(CCFLAGS="-Wextra -pedantic") + env.Append(CXXFLAGS="-ansi") + if env['LIBLO']: env.Append(CCFLAGS="-DHAVE_LIBLO") @@ -822,34 +846,47 @@ if env['LIBLO']: env.Merge ([ libraries['core'] ]) # -# i18n support +# fix scons nitpickiness on APPLE +# + +if env['DIST_TARGET'] == 'panther' or env['DIST_TARGET'] == 'tiger': + env.Append(CCFLAGS="-I/opt/local/include", LINKFLAGS="-L/opt/local/lib") + +# +# i18n support # conf = Configure (env) - if env['NLS']: + nls_error = 'This system is not configured for internationalized applications. An english-only version will be built:' print 'Checking for internationalization support ...' have_gettext = conf.TryAction(Action('xgettext --version')) if have_gettext[0] != 1: - print 'This system is not configured for internationalized applications (no xgettext command). An english-only version will be built\n' + nls_error += ' No xgettext command.' + env['NLS'] = 0 + else: + print "Found xgettext" + + have_msgmerge = conf.TryAction(Action('msgmerge --version')) + if have_msgmerge[0] != 1: + nls_error += ' No msgmerge command.' + env['NLS'] = 0 + else: + print "Found msgmerge" + + if not conf.CheckCHeader('libintl.h'): + nls_error += ' No libintl.h.' env['NLS'] = 0 - if conf.CheckCHeader('libintl.h') == None: - print 'This system is not configured for internationalized applications (no libintl.h). An english-only version will be built\n' - env['NLS'] = 0 - - have_intltool = conf.TryAction(Action('intltool-update --version')) - if have_intltool[0] != 1: - print 'This system is not configured for internationalized applications (no intltool-update command). An english-only version will be built\n' - env['NLS'] = 0 - - + if env['NLS'] == 0: + print nls_error + else: + print "International version will be built." env = conf.Finish() if env['NLS'] == 1: env.Append(CCFLAGS="-DENABLE_NLS") - Export('env install_prefix final_prefix config_prefix final_config_prefix libraries i18n version subst_dict') # @@ -903,18 +940,18 @@ env.Distribute (env['DISTTREE'], glob.glob ('DOCUMENTATION/FAQ*') + glob.glob ('DOCUMENTATION/README*') ) - + srcdist = env.Tarball(env['TARBALL'], env['DISTTREE']) env.Alias ('srctar', srcdist) # -# don't leave the distree around +# don't leave the distree around # env.AddPreAction (env['DISTTREE'], Action ('rm -rf ' + str (File (env['DISTTREE'])))) env.AddPostAction (srcdist, Action ('rm -rf ' + str (File (env['DISTTREE'])))) # # the subdirs -# +# for subdir in coredirs: SConscript (subdir + '/SConscript') @@ -922,7 +959,7 @@ for subdir in coredirs: for sublistdir in [ subdirs, gtk_subdirs, surface_subdirs ]: for subdir in sublistdir: SConscript (subdir + '/SConscript') - + # cleanup env.Clean ('scrub', [ 'scache.conf', '.sconf_temp', '.sconsign.dblite', 'config.log']) diff --git a/ardour.dox b/ardour.dox index 8bd87d6fa3..a72ecbc588 100644 --- a/ardour.dox +++ b/ardour.dox @@ -459,7 +459,7 @@ WARN_LOGFILE = # directories like "/usr/src/myproject". Separate the files or directories # with spaces. -INPUT = libs/pbd3 libs/midi++2 libs/ardour libs/gtkmm2ext gtk2_ardour +INPUT = libs/pbd libs/midi++2 libs/ardour libs/gtkmm2ext gtk2_ardour # If the value of the INPUT tag contains directories, you can use the # FILE_PATTERNS tag to specify one or more wildcard pattern (like *.cpp diff --git a/gtk2_ardour/SConscript b/gtk2_ardour/SConscript index 65f8dfca73..d004c9c4c6 100644 --- a/gtk2_ardour/SConscript +++ b/gtk2_ardour/SConscript @@ -27,7 +27,7 @@ gtkardour.Merge ([ libraries['ardour_cp'], libraries['gtkmm2ext'], libraries['midi++2'], - libraries['pbd3'], + libraries['pbd'], libraries['gtkmm2'], libraries['glib2'], libraries['libgnomecanvas2'], @@ -57,6 +57,10 @@ if gtkardour['FFT_ANALYSIS']: gtkardour.Merge ([libraries['fftw3f']]) gtkardour.Append(CCFLAGS='-DFFT_ANALYSIS') +if gtkardour['COREAUDIO']: + gtkardour.Append(CCFLAGS='-DHAVE_COREAUDIO') + gtkardour.Merge([libraries['appleutility']]) + skipped_files=Split(""" connection_editor.cc """) @@ -75,6 +79,7 @@ ardour_ui_ed.cc ardour_ui_mixer.cc ardour_ui_options.cc audio_clock.cc +route_time_axis.cc audio_time_axis.cc automation_gain_line.cc automation_line.cc @@ -141,8 +146,6 @@ marker.cc marker_time_axis.cc marker_time_axis_view.cc marker_view.cc -meter_bridge.cc -meter_bridge_strip.cc mixer_strip.cc mixer_ui.cc new_session_dialog.cc @@ -159,10 +162,11 @@ public_editor.cc redirect_automation_line.cc redirect_automation_time_axis.cc redirect_box.cc -region_editor.cc +audio_region_editor.cc region_gain_line.cc region_selection.cc -regionview.cc +region_view.cc +audio_region_view.cc route_params_ui.cc route_redirect_selection.cc route_ui.cc @@ -170,7 +174,8 @@ selection.cc sfdb_ui.cc send_ui.cc streamview.cc -taperegionview.cc +audio_streamview.cc +tape_region_view.cc tempo_dialog.cc time_axis_view.cc time_axis_view_item.cc @@ -255,8 +260,7 @@ else: env.Alias('install', env.InstallAs(os.path.join(install_prefix, 'bin')+'/ardour2', ardoursh)) if env['NLS']: - Export('gtkardour', 'intl_files') - SConscript ('po/SConscript') + i18n (gtkardour, gtkardour_files+skipped_files+fft_analysis_files, env) # configuration files env.Alias('install', env.Install(os.path.join(config_prefix, 'ardour2'), 'ardour2_ui.rc')) diff --git a/gtk2_ardour/actions.cc b/gtk2_ardour/actions.cc index ee688c3660..2197d4dc00 100644 --- a/gtk2_ardour/actions.cc +++ b/gtk2_ardour/actions.cc @@ -19,7 +19,7 @@ */ #include -#include +#include #include #include diff --git a/gtk2_ardour/analysis_window.cc b/gtk2_ardour/analysis_window.cc index b8318f45fe..f742afd727 100644 --- a/gtk2_ardour/analysis_window.cc +++ b/gtk2_ardour/analysis_window.cc @@ -26,7 +26,7 @@ #include #include -#include +#include #include #include "analysis_window.h" @@ -35,7 +35,7 @@ #include "time_axis_view.h" #include "public_editor.h" #include "selection.h" -#include "regionview.h" +#include "audio_region_view.h" #include "i18n.h" @@ -45,16 +45,15 @@ using namespace PBD; AnalysisWindow::AnalysisWindow() : ArdourDialog(_("analysis window")), - fft_graph (2048), - source_selection_label (_("Signal source")), source_selection_ranges_rb (_("Selected ranges")), source_selection_regions_rb (_("Selected regions")), - + display_model_label (_("Display model")), display_model_composite_separate_rb (_("Composite graphs for each track")), - display_model_composite_all_tracks_rb (_("Composite graph of all tracks")) + display_model_composite_all_tracks_rb (_("Composite graph of all tracks")), + fft_graph (2048) { track_list_ready = false; @@ -226,18 +225,23 @@ AnalysisWindow::analyze_data (Gtk::Button *button) Selection s = PublicEditor::instance().get_selection(); TimeSelection ts = s.time; - AudioRegionSelection ars = s.audio_regions; + RegionSelection ars = s.regions; for (TrackSelection::iterator i = s.tracks.begin(); i != s.tracks.end(); ++i) { - ARDOUR::Playlist *pl = (*i)->playlist(); + ARDOUR::AudioPlaylist *pl + = dynamic_cast((*i)->playlist()); + + if (!pl) + continue; + RouteUI *rui = dynamic_cast(*i); // Busses don't have playlists, so we need to check that we actually are working with a playlist if (!pl || !rui) continue; - FFTResult *res = fft_graph.prepareResult(*&rui->color(), *&rui->route().name()); + FFTResult *res = fft_graph.prepareResult(rui->color(), rui->route()->name()); // if timeSelection if (source_selection_ranges_rb.get_active()) { @@ -275,24 +279,29 @@ AnalysisWindow::analyze_data (Gtk::Button *button) TimeAxisView *current_axis = (*i); - for (std::set::iterator j = ars.begin(); j != ars.end(); ++j) { + for (std::set::iterator j = ars.begin(); j != ars.end(); ++j) { + // Check that the region is actually audio (so we can analyze it) + AudioRegionView* arv = dynamic_cast(*j); + if (!arv) + continue; + // Check that the region really is selected on _this_ track/solo - if ( &(*j)->get_time_axis_view() != current_axis) + if ( &arv->get_time_axis_view() != current_axis) continue; -// cerr << " - " << (*j)->region.name() << ": " << (*j)->region.length() << " samples starting at " << (*j)->region.position() << endl; +// cerr << " - " << (*j)->region().name() << ": " << (*j)->region().length() << " samples starting at " << (*j)->region().position() << endl; jack_nframes_t i = 0; int n; - while ( i < (*j)->region.length() ) { + while ( i < arv->region().length() ) { // TODO: What about stereo+ channels? composite all to one, I guess n = fft_graph.windowSize(); - if (i + n >= (*j)->region.length() ) { - n = (*j)->region.length() - i; + if (i + n >= arv->region().length() ) { + n = arv->region().length() - i; } - - n = (*j)->region.read_at(buf, mixbuf, gain, work, (*j)->region.position() + i, n); + + n = arv->audio_region().read_at(buf, mixbuf, gain, work, arv->region().position() + i, n); if ( n < fft_graph.windowSize()) { for (int j = n; j < fft_graph.windowSize(); j++) { @@ -313,9 +322,9 @@ AnalysisWindow::analyze_data (Gtk::Button *button) Gtk::TreeModel::Row newrow = *(tlmodel)->append(); - newrow[tlcols.trackname] = rui->route().name(); + newrow[tlcols.trackname] = rui->route()->name(); newrow[tlcols.visible] = true; - newrow[tlcols.color] = *&rui->color(); + newrow[tlcols.color] = rui->color(); newrow[tlcols.graph] = res; } diff --git a/gtk2_ardour/ardev_common.sh b/gtk2_ardour/ardev_common.sh index 5c68933a96..bf644f3e84 100755 --- a/gtk2_ardour/ardev_common.sh +++ b/gtk2_ardour/ardev_common.sh @@ -2,7 +2,10 @@ export ARDOUR_PATH=./glade:./pixmaps:. -export LD_LIBRARY_PATH=../libs/surfaces/control_protocol:../libs/ardour:../libs/midi++2:../libs/pbd3:../libs/soundtouch:../libs/gtkmm2ext:../libs/sigc++2:../libs/glibmm2:../libs/gtkmm2/atk:../libs/gtkmm2/pango:../libs/gtkmm2/gdk:../libs/gtkmm2/gtk:../libs/libgnomecanvasmm:../libs/libsndfile:$LD_LIBRARY_PATH +export LD_LIBRARY_PATH=../libs/surfaces/control_protocol:../libs/ardour:../libs/midi++2:../libs/pbd:../libs/soundtouch:../libs/gtkmm2ext:../libs/sigc++2:../libs/glibmm2:../libs/gtkmm2/atk:../libs/gtkmm2/pango:../libs/gtkmm2/gdk:../libs/gtkmm2/gtk:../libs/libgnomecanvasmm:../libs/libsndfile:../libs/appleutility:$LD_LIBRARY_PATH # DYLD_LIBRARY_PATH is for darwin. export DYLD_LIBRARY_PATH=$LD_LIBRARY_PATH + +# LADSPA_PATH for OSX +export LADSPA_PATH=$LADSPA_PATH:/Library/Audio/Plug-Ins/LADSPA diff --git a/gtk2_ardour/ardour.menus b/gtk2_ardour/ardour.menus index 9293883067..b1064b8e87 100644 --- a/gtk2_ardour/ardour.menus +++ b/gtk2_ardour/ardour.menus @@ -15,8 +15,10 @@

- + + + diff --git a/gtk2_ardour/ardour2_ui.rc b/gtk2_ardour/ardour2_ui.rc index ac4f055df6..5422a63b8b 100644 --- a/gtk2_ardour/ardour2_ui.rc +++ b/gtk2_ardour/ardour2_ui.rc @@ -219,6 +219,14 @@ style "mute_button" = "small_button" fg[PRELIGHT] = { 0, 0, 0 } } + +style "multiline_combo" = "small_button" +{ + font_name = "sans 8" + xthickness = 0 + ythickness = 0 +} + style "mixer_mute_button" = "mute_button" { font_name = "sans 7" @@ -936,6 +944,7 @@ widget "*TrackRecordEnableButton" style "track_rec_enable_button" widget "*TrackRecordEnableButton*" style "track_rec_enable_button" widget "*TrackMuteButton*" style "mute_button" widget "*TrackLoopButton*" style "track_loop_button" +widget "*PanAutomationLineSelector*" style "multiline_combo" widget "*EditorTimeButton*" style "time_button" widget "*EditorMixerButton*" style "default_buttons_menus" widget "*SoloButton*" style "solo_button" diff --git a/gtk2_ardour/ardour_dialog.h b/gtk2_ardour/ardour_dialog.h index a23dcda9e0..069768c143 100644 --- a/gtk2_ardour/ardour_dialog.h +++ b/gtk2_ardour/ardour_dialog.h @@ -26,7 +26,7 @@ namespace ARDOUR { class Session; -}; +} /* * This virtual parent class is so that each dialog box uses the @@ -55,3 +55,4 @@ class ArdourDialog : public Gtk::Dialog }; #endif // __ardour_dialog_h__ + diff --git a/gtk2_ardour/ardour_ui.cc b/gtk2_ardour/ardour_ui.cc index f452ec9c7e..e5367d6280 100644 --- a/gtk2_ardour/ardour_ui.cc +++ b/gtk2_ardour/ardour_ui.cc @@ -46,6 +46,7 @@ #include #include +#include #include #include #include @@ -53,7 +54,6 @@ #include #include #include -#include #include #include @@ -116,16 +116,15 @@ ARDOUR_UI::ARDOUR_UI (int *argcp, char **argvp[], string rcfile) shuttle_units_button (_("% ")), - punch_in_button (_("punch\nin")), - punch_out_button (_("punch\nout")), - auto_return_button (_("auto\nreturn")), - auto_play_button (_("auto\nplay")), - auto_input_button (_("auto\ninput")), - click_button (_("click")), - auditioning_alert_button (_("AUDITIONING")), + punch_in_button (_("Punch In")), + punch_out_button (_("Punch Out")), + auto_return_button (_("Auto Return")), + auto_play_button (_("Autuo Play")), + auto_input_button (_("Auto Input")), + click_button (_("Click")), + auditioning_alert_button (_("AUDITION")), solo_alert_button (_("SOLO")), shown_flag (false) - { using namespace Gtk::Menu_Helpers; @@ -186,8 +185,8 @@ ARDOUR_UI::ARDOUR_UI (int *argcp, char **argvp[], string rcfile) gettimeofday (&last_shuttle_request, 0); ARDOUR::AudioDiskstream::DeleteSources.connect (mem_fun(*this, &ARDOUR_UI::delete_sources_in_the_right_thread)); - ARDOUR::AudioDiskstream::DiskOverrun.connect (mem_fun(*this, &ARDOUR_UI::disk_overrun_handler)); - ARDOUR::AudioDiskstream::DiskUnderrun.connect (mem_fun(*this, &ARDOUR_UI::disk_underrun_handler)); + ARDOUR::Diskstream::DiskOverrun.connect (mem_fun(*this, &ARDOUR_UI::disk_overrun_handler)); + ARDOUR::Diskstream::DiskUnderrun.connect (mem_fun(*this, &ARDOUR_UI::disk_underrun_handler)); /* handle pending state with a dialog */ @@ -339,15 +338,15 @@ ARDOUR_UI::save_ardour_state () Config->add_extra_xml (*node); Config->save_state(); - XMLNode& enode (static_cast(editor)->get_state()); - XMLNode& mnode (mixer->get_state()); + XMLNode enode(static_cast(editor)->get_state()); + XMLNode mnode(mixer->get_state()); if (session) { - session->add_instant_xml(enode, session->path()); - session->add_instant_xml(mnode, session->path()); + session->add_instant_xml (enode, session->path()); + session->add_instant_xml (mnode, session->path()); } else { - Config->add_instant_xml(enode, get_user_ardour_path()); - Config->add_instant_xml(mnode, get_user_ardour_path()); + Config->add_instant_xml (enode, get_user_ardour_path()); + Config->add_instant_xml (mnode, get_user_ardour_path()); } /* keybindings */ @@ -507,11 +506,11 @@ ARDOUR_UI::update_sample_rate (jack_nframes_t ignored) jack_nframes_t rate = engine->frame_rate(); if (fmod (rate, 1000.0) != 0.0) { - snprintf (buf, sizeof (buf), _("SR: %.1f kHz / %4.1f msecs"), + snprintf (buf, sizeof (buf), _("%.1f kHz / %4.1f msecs"), (float) rate/1000.0f, (engine->frames_per_cycle() / (float) rate) * 1000.0f); } else { - snprintf (buf, sizeof (buf), _("SR: %u kHz / %4.1f msecs"), + snprintf (buf, sizeof (buf), _("%u kHz / %4.1f msecs"), rate/1000, (engine->frames_per_cycle() / (float) rate) * 1000.0f); } @@ -524,7 +523,7 @@ void ARDOUR_UI::update_cpu_load () { char buf[32]; - snprintf (buf, sizeof (buf), _("DSP Load: %.1f%%"), engine->get_cpu_load()); + snprintf (buf, sizeof (buf), _("DSP: %.1f%%"), engine->get_cpu_load()); cpu_load_label.set_text (buf); } @@ -543,9 +542,10 @@ ARDOUR_UI::update_buffer_load () } void -ARDOUR_UI::count_recenabled_diskstreams (AudioDiskstream& ds) +ARDOUR_UI::count_recenabled_diskstreams (Route& route) { - if (ds.record_enabled()) { + Track* track = dynamic_cast(&route); + if (track && track->diskstream().record_enabled()) { rec_enabled_diskstreams++; } } @@ -561,7 +561,7 @@ ARDOUR_UI::update_disk_space() char buf[64]; if (frames == max_frames) { - strcpy (buf, _("space: 24hrs+")); + strcpy (buf, _("Disk: 24hrs+")); } else { int hrs; int mins; @@ -571,7 +571,7 @@ ARDOUR_UI::update_disk_space() if (session->actively_recording()){ rec_enabled_diskstreams = 0; - session->foreach_audio_diskstream (this, &ARDOUR_UI::count_recenabled_diskstreams); + session->foreach_route (this, &ARDOUR_UI::count_recenabled_diskstreams); if (rec_enabled_diskstreams) { frames /= rec_enabled_diskstreams; @@ -591,7 +591,7 @@ ARDOUR_UI::update_disk_space() frames -= mins * fr * 60; secs = frames / fr; - snprintf (buf, sizeof(buf), _("space: %02dh:%02dm:%02ds"), hrs, mins, secs); + snprintf (buf, sizeof(buf), _("Disk: %02dh:%02dm:%02ds"), hrs, mins, secs); } disk_space_label.set_text (buf); @@ -876,7 +876,7 @@ ARDOUR_UI::session_add_midi_track () void ARDOUR_UI::session_add_audio_route (bool disk, int32_t input_channels, int32_t output_channels, ARDOUR::TrackMode mode) { - Route* route; + boost::shared_ptr route; if (session == 0) { warning << _("You cannot add a track without a session already loaded.") << endmsg; @@ -918,7 +918,7 @@ restart JACK with more ports.")); } void -ARDOUR_UI::diskstream_added (AudioDiskstream* ds) +ARDOUR_UI::diskstream_added (Diskstream* ds) { } @@ -1159,32 +1159,25 @@ ARDOUR_UI::transport_forward (int option) } void -ARDOUR_UI::toggle_monitor_enable (guint32 dstream) +ARDOUR_UI::toggle_record_enable (uint32_t dstream) { if (session == 0) { return; } - AudioDiskstream *ds; + boost::shared_ptr r; + + if ((r = session->route_by_remote_id (dstream)) != 0) { - if ((ds = session->diskstream_by_id (dstream)) != 0) { - Port *port = ds->io()->input (0); - port->request_monitor_input (!port->monitoring_input()); + Track* t; + + if ((t = dynamic_cast(r.get())) != 0) { + t->diskstream().set_record_enabled (!t->diskstream().record_enabled()); + } } -} - -void -ARDOUR_UI::toggle_record_enable (guint32 dstream) -{ if (session == 0) { return; } - - AudioDiskstream *ds; - - if ((ds = session->diskstream_by_id (dstream)) != 0) { - ds->set_record_enabled (!ds->record_enabled(), this); - } } void @@ -1385,63 +1378,6 @@ ARDOUR_UI::stop_blinking () } } - -void -ARDOUR_UI::add_diskstream_to_menu (AudioDiskstream& dstream) -{ - using namespace Gtk; - using namespace Menu_Helpers; - - if (dstream.hidden()) { - return; - } - - MenuList& items = diskstream_menu->items(); - items.push_back (MenuElem (dstream.name(), bind (mem_fun(*this, &ARDOUR_UI::diskstream_selected), (gint32) dstream.id()))); -} - -void -ARDOUR_UI::diskstream_selected (gint32 id) -{ - selected_dstream = id; - Main::quit (); -} - -gint32 -ARDOUR_UI::select_diskstream (GdkEventButton *ev) -{ - using namespace Gtk; - using namespace Menu_Helpers; - - if (session == 0) { - return -1; - } - - diskstream_menu = new Menu(); - diskstream_menu->set_name ("ArdourContextMenu"); - using namespace Gtk; - using namespace Menu_Helpers; - - MenuList& items = diskstream_menu->items(); - items.push_back (MenuElem (_("No Stream"), (bind (mem_fun(*this, &ARDOUR_UI::diskstream_selected), -1)))); - - session->foreach_audio_diskstream (this, &ARDOUR_UI::add_diskstream_to_menu); - - if (ev) { - diskstream_menu->popup (ev->button, ev->time); - } else { - diskstream_menu->popup (0, 0); - } - - selected_dstream = -1; - - Main::run (); - - delete diskstream_menu; - - return selected_dstream; -} - void ARDOUR_UI::name_io_setup (AudioEngine& engine, string& buf, @@ -2217,11 +2153,11 @@ ARDOUR_UI::halt_on_xrun_message () } void -ARDOUR_UI::delete_sources_in_the_right_thread (list* deletion_list) +ARDOUR_UI::delete_sources_in_the_right_thread (list* deletion_list) { ENSURE_GUI_THREAD (bind (mem_fun(*this, &ARDOUR_UI::delete_sources_in_the_right_thread), deletion_list)); - for (list::iterator i = deletion_list->begin(); i != deletion_list->end(); ++i) { + for (list::iterator i = deletion_list->begin(); i != deletion_list->end(); ++i) { delete *i; } diff --git a/gtk2_ardour/ardour_ui.h b/gtk2_ardour/ardour_ui.h index 678342f32b..297c9c3c65 100644 --- a/gtk2_ardour/ardour_ui.h +++ b/gtk2_ardour/ardour_ui.h @@ -79,7 +79,7 @@ class ColorManager; namespace Gtkmm2ext { class TearOff; -}; +} namespace ARDOUR { class AudioEngine; @@ -87,11 +87,11 @@ namespace ARDOUR { class Port; class IO; class ControlProtocolInfo; -}; +} namespace ALSA { class MultiChannelDevice; -}; +} #define FRAME_NAME "BaseFrame" @@ -154,8 +154,6 @@ class ARDOUR_UI : public Gtkmm2ext::UI void toggle_tempo_window (); void toggle_editing_space(); - gint32 select_diskstream (GdkEventButton *ev); - Gtk::Tooltips& tooltips() { return _tooltips; } static sigc::signal Blink; @@ -522,7 +520,7 @@ class ARDOUR_UI : public Gtkmm2ext::UI sigc::connection point_one_second_connection; sigc::connection point_zero_one_second_connection; - void diskstream_added (ARDOUR::AudioDiskstream*); + void diskstream_added (ARDOUR::Diskstream*); gint session_menu (GdkEventButton *); @@ -536,14 +534,8 @@ class ARDOUR_UI : public Gtkmm2ext::UI void save_template (); - void session_add_audio_route (bool disk, int32_t input_channels, int32_t output_channels, ARDOUR::TrackMode mode); - void add_diskstream_to_menu (ARDOUR::AudioDiskstream&); - void diskstream_selected (gint32); - Gtk::Menu *diskstream_menu; - gint32 selected_dstream; - void set_transport_sensitivity (bool); void remove_last_capture (); @@ -626,11 +618,10 @@ class ARDOUR_UI : public Gtkmm2ext::UI void test_binding_action (const char *); void start_keyboard_prefix(); - void toggle_record_enable (guint32); - void toggle_monitor_enable (guint32); + void toggle_record_enable (uint32_t); uint32_t rec_enabled_diskstreams; - void count_recenabled_diskstreams (ARDOUR::AudioDiskstream&); + void count_recenabled_diskstreams (ARDOUR::Route&); About* about; bool shown_flag; @@ -649,7 +640,7 @@ class ARDOUR_UI : public Gtkmm2ext::UI struct timeval last_peak_grab; struct timeval last_shuttle_request; - void delete_sources_in_the_right_thread (list*); + void delete_sources_in_the_right_thread (list*); void editor_display_control_changed (Editing::DisplayControl c); @@ -716,5 +707,5 @@ class ARDOUR_UI : public Gtkmm2ext::UI void toggle_control_protocol (ARDOUR::ControlProtocolInfo*); }; - #endif /* __ardour_gui_h__ */ + diff --git a/gtk2_ardour/ardour_ui2.cc b/gtk2_ardour/ardour_ui2.cc index f92201e36c..44287fe61e 100644 --- a/gtk2_ardour/ardour_ui2.cc +++ b/gtk2_ardour/ardour_ui2.cc @@ -359,10 +359,10 @@ ARDOUR_UI::setup_transport () auditioning_alert_button.set_name ("TransportAuditioningAlert"); auditioning_alert_button.signal_pressed().connect (mem_fun(*this,&ARDOUR_UI::audition_alert_toggle)); - alert_box.pack_start (solo_alert_button); - alert_box.pack_start (auditioning_alert_button); + alert_box.pack_start (solo_alert_button, false, false); + alert_box.pack_start (auditioning_alert_button, false, false); - transport_tearoff_hbox.set_border_width (5); + transport_tearoff_hbox.set_border_width (3); transport_tearoff_hbox.pack_start (goto_start_button, false, false); transport_tearoff_hbox.pack_start (goto_end_button, false, false); @@ -398,6 +398,7 @@ ARDOUR_UI::setup_transport () mtc_port_changed (); sync_option_combo.set_active_text (positional_sync_strings.front()); sync_option_combo.signal_changed().connect (mem_fun (*this, &ARDOUR_UI::sync_option_changed)); + Gtkmm2ext::set_size_request_to_display_given_text (sync_option_combo, "Internal", 22, 10); shbox->pack_start (*sdframe, false, false); shbox->pack_start (shuttle_units_button, true, true); @@ -406,37 +407,52 @@ ARDOUR_UI::setup_transport () svbox->pack_start (*sframe, false, false); svbox->pack_start (*shbox, false, false); - transport_tearoff_hbox.pack_start (*svbox, false, false, 5); + transport_tearoff_hbox.pack_start (*svbox, false, false, 3); transport_tearoff_hbox.pack_start (auto_loop_button, false, false); transport_tearoff_hbox.pack_start (play_selection_button, false, false); transport_tearoff_hbox.pack_start (roll_button, false, false); transport_tearoff_hbox.pack_start (stop_button, false, false); - transport_tearoff_hbox.pack_start (rec_button, false, false, 10); + transport_tearoff_hbox.pack_start (rec_button, false, false, 6); - transport_tearoff_hbox.pack_start (primary_clock, false, false, 5); - transport_tearoff_hbox.pack_start (secondary_clock, false, false, 5); + HBox* clock_box = manage (new HBox); + clock_box->pack_start (primary_clock, false, false); + clock_box->pack_start (secondary_clock, false, false); + VBox* time_controls_box = manage (new VBox); + time_controls_box->pack_start (sync_option_combo, false, false); + time_controls_box->pack_start (time_master_button, false, false); + clock_box->pack_start (*time_controls_box, false, false, 1); + transport_tearoff_hbox.pack_start (*clock_box, false, false, 0); + + HBox* toggle_box = manage(new HBox); + + VBox* punch_box = manage (new VBox); + punch_box->pack_start (punch_in_button, false, false); + punch_box->pack_start (punch_out_button, false, false); + toggle_box->pack_start (*punch_box, false, false); - transport_tearoff_hbox.pack_start (sync_option_combo, false, false); - transport_tearoff_hbox.pack_start (time_master_button, false, false); - transport_tearoff_hbox.pack_start (punch_in_button, false, false); - transport_tearoff_hbox.pack_start (punch_out_button, false, false); - transport_tearoff_hbox.pack_start (auto_input_button, false, false); - transport_tearoff_hbox.pack_start (auto_return_button, false, false); - transport_tearoff_hbox.pack_start (auto_play_button, false, false); - transport_tearoff_hbox.pack_start (click_button, false, false); + VBox* auto_box = manage (new VBox); + auto_box->pack_start (auto_play_button, false, false); + auto_box->pack_start (auto_return_button, false, false); + toggle_box->pack_start (*auto_box, false, false); + + VBox* io_box = manage (new VBox); + io_box->pack_start (auto_input_button, false, false); + io_box->pack_start (click_button, false, false); + toggle_box->pack_start (*io_box, false, false); /* desensitize */ set_transport_sensitivity (false); -// transport_tearoff_hbox.pack_start (preroll_button, false, false); -// transport_tearoff_hbox.pack_start (preroll_clock, false, false); +// toggle_box->pack_start (preroll_button, false, false); +// toggle_box->pack_start (preroll_clock, false, false); -// transport_tearoff_hbox.pack_start (postroll_button, false, false); -// transport_tearoff_hbox.pack_start (postroll_clock, false, false); +// toggle_box->pack_start (postroll_button, false, false); +// toggle_box->pack_start (postroll_clock, false, false); - transport_tearoff_hbox.pack_start (alert_box, false, false, 5); + transport_tearoff_hbox.pack_start (*toggle_box, false, false, 4); + transport_tearoff_hbox.pack_start (alert_box, false, false); } void @@ -820,7 +836,7 @@ ARDOUR_UI::set_shuttle_units (ShuttleUnits u) shuttle_units_button.set_label("% "); break; case Semitones: - shuttle_units_button.set_label(_("st")); + shuttle_units_button.set_label(_("ST")); break; } } @@ -864,7 +880,7 @@ ARDOUR_UI::update_speed_display () { if (!session) { if (last_speed_displayed != 0) { - speed_display_label.set_text (_("stopped")); + speed_display_label.set_text (_("stop")); last_speed_displayed = 0; } return; @@ -877,7 +893,7 @@ ARDOUR_UI::update_speed_display () if (x != 0) { if (shuttle_units == Percentage) { - snprintf (buf, sizeof (buf), "%.4f", x); + snprintf (buf, sizeof (buf), "%.2f", x); } else { if (x < 0) { snprintf (buf, sizeof (buf), "< %.1f", 12.0 * fast_log2 (-x)); @@ -887,7 +903,7 @@ ARDOUR_UI::update_speed_display () } speed_display_label.set_text (buf); } else { - speed_display_label.set_text (_("stopped")); + speed_display_label.set_text (_("stop")); } last_speed_displayed = x; @@ -904,7 +920,7 @@ ARDOUR_UI::set_transport_sensitivity (bool yn) void ARDOUR_UI::editor_realized () { - set_size_request_to_display_given_text (speed_display_box, _("stopped"), 2, 2); + set_size_request_to_display_given_text (speed_display_box, _("-0.55"), 2, 2); /* XXX: this should really be saved in instant.xml or something similar and restored from there */ shuttle_style_button.set_active_text (_("sprung")); const guint32 FUDGE = 20; // Combo's are stupid - they steal space from the entry for the button diff --git a/gtk2_ardour/ardour_ui_dialogs.cc b/gtk2_ardour/ardour_ui_dialogs.cc index 202fa88b59..25f3068a81 100644 --- a/gtk2_ardour/ardour_ui_dialogs.cc +++ b/gtk2_ardour/ardour_ui_dialogs.cc @@ -76,8 +76,8 @@ ARDOUR_UI::connect_to_session (Session *s) rec_button.set_sensitive (true); shuttle_box.set_sensitive (true); - if (session->n_audio_diskstreams() == 0) { - session->AudioDiskstreamAdded.connect (mem_fun(*this, &ARDOUR_UI::diskstream_added)); + if (session->n_diskstreams() == 0) { + session->DiskstreamAdded.connect (mem_fun(*this, &ARDOUR_UI::diskstream_added)); } if (connection_editor) { diff --git a/gtk2_ardour/ardour_ui_ed.cc b/gtk2_ardour/ardour_ui_ed.cc index 1bc2de26d1..238f81dd4f 100644 --- a/gtk2_ardour/ardour_ui_ed.cc +++ b/gtk2_ardour/ardour_ui_ed.cc @@ -264,31 +264,26 @@ ARDOUR_UI::install_actions () ActionManager::session_sensitive_actions.push_back (act); ActionManager::transport_sensitive_actions.push_back (act); - /* XXX the newline in the displayed names of these action is really wrong, but its because we want the button - that proxies for these action to be more compact. It would be nice to find a way to override the action - name appearance on the buttons. - */ - - act = ActionManager::register_toggle_action (transport_actions, X_("TogglePunchIn"), _("Punch\nin"), mem_fun(*this, &ARDOUR_UI::toggle_punch_in)); + act = ActionManager::register_toggle_action (transport_actions, X_("TogglePunchIn"), _("Punch In"), mem_fun(*this, &ARDOUR_UI::toggle_punch_in)); ActionManager::session_sensitive_actions.push_back (act); ActionManager::transport_sensitive_actions.push_back (act); - act = ActionManager::register_toggle_action (transport_actions, X_("TogglePunchOut"), _("Punch\nout"), mem_fun(*this, &ARDOUR_UI::toggle_punch_out)); + act = ActionManager::register_toggle_action (transport_actions, X_("TogglePunchOut"), _("Punch Out"), mem_fun(*this, &ARDOUR_UI::toggle_punch_out)); ActionManager::session_sensitive_actions.push_back (act); ActionManager::transport_sensitive_actions.push_back (act); act = ActionManager::register_toggle_action (transport_actions, X_("ToggleClick"), _("Click"), mem_fun(*this, &ARDOUR_UI::toggle_click)); ActionManager::session_sensitive_actions.push_back (act); ActionManager::transport_sensitive_actions.push_back (act); - act = ActionManager::register_toggle_action (transport_actions, X_("ToggleAutoInput"), _("Auto\ninput"), mem_fun(*this, &ARDOUR_UI::toggle_auto_input)); + act = ActionManager::register_toggle_action (transport_actions, X_("ToggleAutoInput"), _("Auto Input"), mem_fun(*this, &ARDOUR_UI::toggle_auto_input)); ActionManager::session_sensitive_actions.push_back (act); ActionManager::transport_sensitive_actions.push_back (act); - act = ActionManager::register_toggle_action (transport_actions, X_("ToggleAutoPlay"), _("Auto\nplay"), mem_fun(*this, &ARDOUR_UI::toggle_auto_play)); + act = ActionManager::register_toggle_action (transport_actions, X_("ToggleAutoPlay"), _("Auto Play"), mem_fun(*this, &ARDOUR_UI::toggle_auto_play)); ActionManager::session_sensitive_actions.push_back (act); ActionManager::transport_sensitive_actions.push_back (act); - act = ActionManager::register_toggle_action (transport_actions, X_("ToggleAutoReturn"), _("Auto\nreturn"), mem_fun(*this, &ARDOUR_UI::toggle_auto_return)); + act = ActionManager::register_toggle_action (transport_actions, X_("ToggleAutoReturn"), _("Auto Return"), mem_fun(*this, &ARDOUR_UI::toggle_auto_return)); ActionManager::session_sensitive_actions.push_back (act); ActionManager::transport_sensitive_actions.push_back (act); - act = ActionManager::register_toggle_action (transport_actions, X_("ToggleTimeMaster"), _("Time\nmaster"), mem_fun(*this, &ARDOUR_UI::toggle_time_master)); + act = ActionManager::register_toggle_action (transport_actions, X_("ToggleTimeMaster"), _("Master"), mem_fun(*this, &ARDOUR_UI::toggle_time_master)); ActionManager::session_sensitive_actions.push_back (act); act = ActionManager::register_action (common_actions, X_("ToggleRecordEnableTrack1"), _("Toggle Record Enable Track1"), bind (mem_fun(*this, &ARDOUR_UI::toggle_record_enable), 0U)); diff --git a/gtk2_ardour/audio_clock.h b/gtk2_ardour/audio_clock.h index 14dc6ba673..9ff5f45ddf 100644 --- a/gtk2_ardour/audio_clock.h +++ b/gtk2_ardour/audio_clock.h @@ -30,7 +30,7 @@ namespace ARDOUR { class Session; -}; +} class AudioClock : public Gtk::HBox { @@ -40,7 +40,7 @@ class AudioClock : public Gtk::HBox BBT, MinSec, Frames, - Off, + Off }; AudioClock (const string& name, bool editable, bool is_duration = false, bool with_tempo_meter = false); @@ -87,7 +87,7 @@ class AudioClock : public Gtk::HBox Bars, Beats, Ticks, - AudioFrames, + AudioFrames }; Gtk::EventBox audio_frames_ebox; diff --git a/gtk2_ardour/region_editor.cc b/gtk2_ardour/audio_region_editor.cc similarity index 99% rename from gtk2_ardour/region_editor.cc rename to gtk2_ardour/audio_region_editor.cc index 413ff01753..194f358b42 100644 --- a/gtk2_ardour/region_editor.cc +++ b/gtk2_ardour/audio_region_editor.cc @@ -24,8 +24,8 @@ #include #include -#include "region_editor.h" -#include "regionview.h" +#include "audio_region_editor.h" +#include "audio_region_view.h" #include "ardour_ui.h" #include "utils.h" #include "gui_thread.h" @@ -37,9 +37,8 @@ using namespace PBD; using namespace sigc; using namespace std; -AudioRegionEditor::AudioRegionEditor (Session&s, AudioRegion& r, AudioRegionView& rv) - : ArdourDialog ("audio region editor"), - _session (s), +AudioRegionEditor::AudioRegionEditor (Session& s, AudioRegion& r, AudioRegionView& rv) + : RegionEditor (s), _region (r), _region_view (rv), name_label (_("NAME:")), diff --git a/gtk2_ardour/audio_region_editor.h b/gtk2_ardour/audio_region_editor.h new file mode 100644 index 0000000000..38cd920e5e --- /dev/null +++ b/gtk2_ardour/audio_region_editor.h @@ -0,0 +1,186 @@ +/* + Copyright (C) 2001 Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + + $Id$ +*/ + +#ifndef __gtk_ardour_audio_region_edit_h__ +#define __gtk_ardour_audio_region_edit_h__ + +#include + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include + +#include "audio_clock.h" +#include "ardour_dialog.h" +#include "region_editor.h" + +namespace ARDOUR { + class AudioRegion; + class Session; +} + +class AudioRegionView; + +class AudioRegionEditor : public RegionEditor +{ + public: + AudioRegionEditor (ARDOUR::Session&, ARDOUR::AudioRegion&, AudioRegionView& rv); + ~AudioRegionEditor (); + + private: + ARDOUR::AudioRegion& _region; + AudioRegionView& _region_view; + + void connect_editor_events (); + + Gtk::Label name_label; + Gtk::Entry name_entry; + Gtk::HBox name_hbox; + + Gtk::HBox top_row_hbox; + Gtk::HBox top_row_button_hbox; + + Gtk::ToggleButton lock_button; + Gtk::ToggleButton mute_button; + Gtk::ToggleButton opaque_button; + Gtk::ToggleButton envelope_active_button; + Gtk::ToggleButton envelope_view_button; + + Gtk::Button raise_button; + Gtk::Arrow raise_arrow; + Gtk::Button lower_button; + Gtk::Arrow lower_arrow; + Gtk::Frame layer_frame; + Gtk::Label layer_value_label; + Gtk::Label layer_label; + Gtk::HBox layer_hbox; + + Gtk::ToggleButton audition_button; + + Gtk::HBox lower_hbox; + + Gtk::Table time_table; + + Gtk::Label start_label; + Gtk::Label end_label; + Gtk::Label length_label; + Gtk::Alignment start_alignment; + Gtk::Alignment end_alignment; + Gtk::Alignment length_alignment; + + AudioClock start_clock; + AudioClock end_clock; + AudioClock length_clock; + AudioClock sync_offset_clock; + + Gtk::Table envelope_loop_table; + Gtk::Button loop_button; + Gtk::Label loop_label; + Gtk::Label envelope_label; + + Gtk::Table fade_in_table; + Gtk::Label fade_in_label; + Gtk::Alignment fade_in_label_align; + Gtk::Label fade_in_active_button_label; + Gtk::ToggleButton fade_in_active_button; + Gtk::Label fade_in_length_label; + + Gtk::Adjustment fade_in_length_adjustment; + Gtk::SpinButton fade_in_length_spinner; + + Gtk::Table fade_out_table; + Gtk::Label fade_out_label; + Gtk::Alignment fade_out_label_align; + Gtk::Label fade_out_active_button_label; + Gtk::ToggleButton fade_out_active_button; + Gtk::Label fade_out_length_label; + + Gtk::Adjustment fade_out_length_adjustment; + Gtk::SpinButton fade_out_length_spinner; + + Gtk::HSeparator sep3; + Gtk::VSeparator sep1; + Gtk::VSeparator sep2; + + void region_changed (ARDOUR::Change); + void bounds_changed (ARDOUR::Change); + void name_changed (); + void opacity_changed (); + void mute_changed (); + void envelope_active_changed (); + void lock_changed (); + void layer_changed (); + + void fade_in_length_adjustment_changed (); + void fade_out_length_adjustment_changed (); + void fade_in_changed (); + void fade_out_changed (); + void audition_state_changed (bool); + + void activation (); + + void name_entry_changed (); + void start_clock_changed (); + void end_clock_changed (); + void length_clock_changed (); + + gint envelope_active_button_press (GdkEventButton *); + gint envelope_active_button_release (GdkEventButton *); + + void audition_button_toggled (); + void envelope_view_button_toggled (); + void lock_button_clicked (); + void mute_button_clicked (); + void opaque_button_clicked (); + void raise_button_clicked (); + void lower_button_clicked (); + + void fade_in_active_toggled (); + void fade_out_active_toggled (); + void fade_in_active_changed (); + void fade_out_active_changed (); + + void fade_in_realized (); + void fade_out_realized (); + + void start_editing_fade_in (); + void start_editing_fade_out (); + void stop_editing_fade_in (); + void stop_editing_fade_out (); + + gint bpressed (GdkEventButton* ev, Gtk::SpinButton* but, void (AudioRegionEditor::*pmf)()); + gint breleased (GdkEventButton* ev, Gtk::SpinButton* but, void (AudioRegionEditor::*pmf)()); + + bool spin_arrow_grab; +}; + +#endif /* __gtk_ardour_audio_region_edit_h__ */ diff --git a/gtk2_ardour/audio_region_view.cc b/gtk2_ardour/audio_region_view.cc new file mode 100644 index 0000000000..feb8f4fd0b --- /dev/null +++ b/gtk2_ardour/audio_region_view.cc @@ -0,0 +1,1127 @@ +/* + Copyright (C) 2001-2006 Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + + $Id$ +*/ + +#include +#include +#include + +#include + +#include + +#include +#include +#include +#include + +#include "streamview.h" +#include "audio_region_view.h" +#include "audio_time_axis.h" +#include "simplerect.h" +#include "simpleline.h" +#include "waveview.h" +#include "public_editor.h" +#include "audio_region_editor.h" +#include "region_gain_line.h" +#include "ghostregion.h" +#include "audio_time_axis.h" +#include "utils.h" +#include "rgb_macros.h" +#include "gui_thread.h" + +#include "i18n.h" + +using namespace sigc; +using namespace ARDOUR; +using namespace PBD; +using namespace Editing; +using namespace ArdourCanvas; + +static const int32_t sync_mark_width = 9; + +AudioRegionView::AudioRegionView (ArdourCanvas::Group *parent, RouteTimeAxisView &tv, AudioRegion& r, double spu, + Gdk::Color& basic_color) + : RegionView (parent, tv, r, spu, basic_color) + , sync_mark(0) + , zero_line(0) + , fade_in_shape(0) + , fade_out_shape(0) + , fade_in_handle(0) + , fade_out_handle(0) + , gain_line(0) + , _amplitude_above_axis(1.0) + , _flags(0) + , fade_color(0) +{ +} + +AudioRegionView::AudioRegionView (ArdourCanvas::Group *parent, RouteTimeAxisView &tv, AudioRegion& r, double spu, + Gdk::Color& basic_color, TimeAxisViewItem::Visibility visibility) + : RegionView (parent, tv, r, spu, basic_color, visibility) + , sync_mark(0) + , zero_line(0) + , fade_in_shape(0) + , fade_out_shape(0) + , fade_in_handle(0) + , fade_out_handle(0) + , gain_line(0) + , _amplitude_above_axis(1.0) + , _flags(0) + , fade_color(0) +{ +} + +void +AudioRegionView::init (Gdk::Color& basic_color, bool wfd) +{ + // FIXME: Some redundancy here with RegionView::init. Need to figure out + // where order is important and where it isn't... + + RegionView::init(basic_color, wfd); + + XMLNode *node; + + _amplitude_above_axis = 1.0; + zero_line = 0; + _flags = 0; + + if ((node = _region.extra_xml ("GUI")) != 0) { + set_flags (node); + } else { + _flags = WaveformVisible; + store_flags (); + } + + if (trackview.editor.new_regionviews_display_gain()) { + _flags |= EnvelopeVisible; + } + + compute_colors (basic_color); + + create_waves (); + + fade_in_shape = new ArdourCanvas::Polygon (*group); + fade_in_shape->property_fill_color_rgba() = fade_color; + fade_in_shape->set_data ("regionview", this); + + fade_out_shape = new ArdourCanvas::Polygon (*group); + fade_out_shape->property_fill_color_rgba() = fade_color; + fade_out_shape->set_data ("regionview", this); + + + { + uint32_t r,g,b,a; + UINT_TO_RGBA(fill_color,&r,&g,&b,&a); + + + fade_in_handle = new ArdourCanvas::SimpleRect (*group); + fade_in_handle->property_fill_color_rgba() = RGBA_TO_UINT(r,g,b,0); + fade_in_handle->property_outline_pixels() = 0; + fade_in_handle->property_y1() = 2.0; + fade_in_handle->property_y2() = 7.0; + + fade_in_handle->set_data ("regionview", this); + + fade_out_handle = new ArdourCanvas::SimpleRect (*group); + fade_out_handle->property_fill_color_rgba() = RGBA_TO_UINT(r,g,b,0); + fade_out_handle->property_outline_pixels() = 0; + fade_out_handle->property_y1() = 2.0; + fade_out_handle->property_y2() = 7.0; + + fade_out_handle->set_data ("regionview", this); + } + + string foo = _region.name(); + foo += ':'; + foo += "gain"; + + gain_line = new AudioRegionGainLine (foo, trackview.session(), *this, *group, audio_region().envelope()); + + if (!(_flags & EnvelopeVisible)) { + gain_line->hide (); + } else { + gain_line->show (); + } + + reset_width_dependent_items ((double) _region.length() / samples_per_unit); + + gain_line->reset (); + + set_height (trackview.height); + + region_muted (); + region_sync_changed (); + region_resized (BoundsChanged); + set_waveview_data_src(); + region_locked (); + envelope_active_changed (); + fade_in_active_changed (); + fade_out_active_changed (); + + _region.StateChanged.connect (mem_fun(*this, &AudioRegionView::region_changed)); + + fade_in_shape->signal_event().connect (bind (mem_fun (PublicEditor::instance(), &PublicEditor::canvas_fade_in_event), fade_in_shape, this)); + fade_in_handle->signal_event().connect (bind (mem_fun (PublicEditor::instance(), &PublicEditor::canvas_fade_in_handle_event), fade_in_handle, this)); + fade_out_shape->signal_event().connect (bind (mem_fun (PublicEditor::instance(), &PublicEditor::canvas_fade_out_event), fade_out_shape, this)); + fade_out_handle->signal_event().connect (bind (mem_fun (PublicEditor::instance(), &PublicEditor::canvas_fade_out_handle_event), fade_out_handle, this)); + + set_colors (); + + /* XXX sync mark drag? */ +} + +AudioRegionView::~AudioRegionView () +{ + in_destructor = true; + + RegionViewGoingAway (this); /* EMIT_SIGNAL */ + + for (vector::iterator cache = wave_caches.begin(); cache != wave_caches.end() ; ++cache) { + gnome_canvas_waveview_cache_destroy (*cache); + } + + /* all waveviews etc will be destroyed when the group is destroyed */ + + if (gain_line) { + delete gain_line; + } +} + +ARDOUR::AudioRegion& +AudioRegionView::audio_region() const +{ + // "Guaranteed" to succeed... + return dynamic_cast(_region); +} + +void +AudioRegionView::region_changed (Change what_changed) +{ + ENSURE_GUI_THREAD (bind (mem_fun(*this, &AudioRegionView::region_changed), what_changed)); + + RegionView::region_changed(what_changed); + + if (what_changed & AudioRegion::ScaleAmplitudeChanged) { + region_scale_amplitude_changed (); + } + if (what_changed & AudioRegion::FadeInChanged) { + fade_in_changed (); + } + if (what_changed & AudioRegion::FadeOutChanged) { + fade_out_changed (); + } + if (what_changed & AudioRegion::FadeInActiveChanged) { + fade_in_active_changed (); + } + if (what_changed & AudioRegion::FadeOutActiveChanged) { + fade_out_active_changed (); + } + if (what_changed & AudioRegion::EnvelopeActiveChanged) { + envelope_active_changed (); + } +} + +void +AudioRegionView::fade_in_changed () +{ + reset_fade_in_shape (); +} + +void +AudioRegionView::fade_out_changed () +{ + reset_fade_out_shape (); +} + +void +AudioRegionView::set_fade_in_active (bool yn) +{ + audio_region().set_fade_in_active (yn); +} + +void +AudioRegionView::set_fade_out_active (bool yn) +{ + audio_region().set_fade_out_active (yn); +} + +void +AudioRegionView::fade_in_active_changed () +{ + uint32_t r,g,b,a; + uint32_t col; + UINT_TO_RGBA(fade_color,&r,&g,&b,&a); + + if (audio_region().fade_in_active()) { + col = RGBA_TO_UINT(r,g,b,120); + fade_in_shape->property_fill_color_rgba() = col; + fade_in_shape->property_width_pixels() = 0; + fade_in_shape->property_outline_color_rgba() = RGBA_TO_UINT(r,g,b,0); + } else { + col = RGBA_TO_UINT(r,g,b,0); + fade_in_shape->property_fill_color_rgba() = col; + fade_in_shape->property_width_pixels() = 1; + fade_in_shape->property_outline_color_rgba() = RGBA_TO_UINT(r,g,b,255); + } +} + +void +AudioRegionView::fade_out_active_changed () +{ + uint32_t r,g,b,a; + uint32_t col; + UINT_TO_RGBA(fade_color,&r,&g,&b,&a); + + if (audio_region().fade_out_active()) { + col = RGBA_TO_UINT(r,g,b,120); + fade_out_shape->property_fill_color_rgba() = col; + fade_out_shape->property_width_pixels() = 0; + fade_out_shape->property_outline_color_rgba() = RGBA_TO_UINT(r,g,b,0); + } else { + col = RGBA_TO_UINT(r,g,b,0); + fade_out_shape->property_fill_color_rgba() = col; + fade_out_shape->property_width_pixels() = 1; + fade_out_shape->property_outline_color_rgba() = RGBA_TO_UINT(r,g,b,255); + } +} + + +void +AudioRegionView::region_scale_amplitude_changed () +{ + ENSURE_GUI_THREAD (mem_fun(*this, &AudioRegionView::region_scale_amplitude_changed)); + + for (uint32_t n = 0; n < waves.size(); ++n) { + // force a reload of the cache + waves[n]->property_data_src() = &_region; + } +} + +void +AudioRegionView::region_resized (Change what_changed) +{ + RegionView::region_resized(what_changed); + + if (what_changed & Change (StartChanged|LengthChanged)) { + + for (uint32_t n = 0; n < waves.size(); ++n) { + waves[n]->property_region_start() = _region.start(); + } + + for (vector::iterator i = ghosts.begin(); i != ghosts.end(); ++i) { + + for (vector::iterator w = (*i)->waves.begin(); w != (*i)->waves.end(); ++w) { + (*w)->property_region_start() = _region.start(); + } + } + } +} + +void +AudioRegionView::reset_width_dependent_items (double pixel_width) +{ + RegionView::reset_width_dependent_items(pixel_width); + assert(_pixel_width == pixel_width); + + if (zero_line) { + zero_line->property_x2() = pixel_width - 1.0; + } + + if (fade_in_handle) { + if (pixel_width <= 6.0) { + fade_in_handle->hide(); + fade_out_handle->hide(); + } else { + if (_height < 5.0) { + fade_in_handle->hide(); + fade_out_handle->hide(); + } else { + fade_in_handle->show(); + fade_out_handle->show(); + } + } + } + + reset_fade_shapes (); +} + +void +AudioRegionView::region_muted () +{ + RegionView::region_muted(); + + for (uint32_t n=0; n < waves.size(); ++n) { + if (_region.muted()) { + waves[n]->property_wave_color() = color_map[cMutedWaveForm]; + } else { + waves[n]->property_wave_color() = color_map[cWaveForm]; + } + } +} + + +void +AudioRegionView::set_height (gdouble height) +{ + uint32_t wcnt = waves.size(); + + // FIXME: ick + TimeAxisViewItem::set_height (height - 2); + + _height = height; + + for (uint32_t n=0; n < wcnt; ++n) { + gdouble ht; + + if ((height) <= NAME_HIGHLIGHT_THRESH) { + ht = ((height-2*wcnt) / (double) wcnt); + } else { + ht = (((height-2*wcnt) - NAME_HIGHLIGHT_SIZE) / (double) wcnt); + } + + gdouble yoff = n * (ht+1); + + waves[n]->property_height() = ht; + waves[n]->property_y() = yoff + 2; + } + + if (gain_line) { + if ((height/wcnt) < NAME_HIGHLIGHT_SIZE) { + gain_line->hide (); + } else { + if (_flags & EnvelopeVisible) { + gain_line->show (); + } + } + gain_line->set_height ((uint32_t) rint (height - NAME_HIGHLIGHT_SIZE)); + } + + manage_zero_line (); + reset_fade_shapes (); + + if (name_text) { + name_text->raise_to_top(); + } +} + +void +AudioRegionView::manage_zero_line () +{ + if (!zero_line) { + return; + } + + if (_height >= 100) { + gdouble wave_midpoint = (_height - NAME_HIGHLIGHT_SIZE) / 2.0; + zero_line->property_y1() = wave_midpoint; + zero_line->property_y2() = wave_midpoint; + zero_line->show(); + } else { + zero_line->hide(); + } +} + +void +AudioRegionView::reset_fade_shapes () +{ + reset_fade_in_shape (); + reset_fade_out_shape (); +} + +void +AudioRegionView::reset_fade_in_shape () +{ + reset_fade_in_shape_width ((jack_nframes_t) audio_region().fade_in().back()->when); +} + +void +AudioRegionView::reset_fade_in_shape_width (jack_nframes_t width) +{ + if (fade_in_handle == 0) { + return; + } + + /* smallest size for a fade is 64 frames */ + + width = std::max ((jack_nframes_t) 64, width); + + Points* points; + double pwidth = width / samples_per_unit; + uint32_t npoints = std::min (gdk_screen_width(), (int) pwidth); + double h; + + if (_height < 5) { + fade_in_shape->hide(); + fade_in_handle->hide(); + return; + } + + double handle_center; + handle_center = pwidth; + + if (handle_center > 7.0) { + handle_center -= 3.0; + } else { + handle_center = 3.0; + } + + fade_in_handle->property_x1() = handle_center - 3.0; + fade_in_handle->property_x2() = handle_center + 3.0; + + if (pwidth < 5) { + fade_in_shape->hide(); + return; + } + + fade_in_shape->show(); + + float curve[npoints]; + audio_region().fade_in().get_vector (0, audio_region().fade_in().back()->when, curve, npoints); + + points = get_canvas_points ("fade in shape", npoints+3); + + if (_height > NAME_HIGHLIGHT_THRESH) { + h = _height - NAME_HIGHLIGHT_SIZE; + } else { + h = _height; + } + + /* points *MUST* be in anti-clockwise order */ + + uint32_t pi, pc; + double xdelta = pwidth/npoints; + + for (pi = 0, pc = 0; pc < npoints; ++pc) { + (*points)[pi].set_x(1 + (pc * xdelta)); + (*points)[pi++].set_y(2 + (h - (curve[pc] * h))); + } + + /* fold back */ + + (*points)[pi].set_x(pwidth); + (*points)[pi++].set_y(2); + + (*points)[pi].set_x(1); + (*points)[pi++].set_y(2); + + /* connect the dots ... */ + + (*points)[pi] = (*points)[0]; + + fade_in_shape->property_points() = *points; + delete points; +} + +void +AudioRegionView::reset_fade_out_shape () +{ + reset_fade_out_shape_width ((jack_nframes_t) audio_region().fade_out().back()->when); +} + +void +AudioRegionView::reset_fade_out_shape_width (jack_nframes_t width) +{ + if (fade_out_handle == 0) { + return; + } + + /* smallest size for a fade is 64 frames */ + + width = std::max ((jack_nframes_t) 64, width); + + Points* points; + double pwidth = width / samples_per_unit; + uint32_t npoints = std::min (gdk_screen_width(), (int) pwidth); + double h; + + if (_height < 5) { + fade_out_shape->hide(); + fade_out_handle->hide(); + return; + } + + double handle_center; + handle_center = (_region.length() - width) / samples_per_unit; + + if (handle_center > 7.0) { + handle_center -= 3.0; + } else { + handle_center = 3.0; + } + + fade_out_handle->property_x1() = handle_center - 3.0; + fade_out_handle->property_x2() = handle_center + 3.0; + + /* don't show shape if its too small */ + + if (pwidth < 5) { + fade_out_shape->hide(); + return; + } + + fade_out_shape->show(); + + float curve[npoints]; + audio_region().fade_out().get_vector (0, audio_region().fade_out().back()->when, curve, npoints); + + if (_height > NAME_HIGHLIGHT_THRESH) { + h = _height - NAME_HIGHLIGHT_SIZE; + } else { + h = _height; + } + + /* points *MUST* be in anti-clockwise order */ + + points = get_canvas_points ("fade out shape", npoints+3); + + uint32_t pi, pc; + double xdelta = pwidth/npoints; + + for (pi = 0, pc = 0; pc < npoints; ++pc) { + (*points)[pi].set_x(_pixel_width - 1 - pwidth + (pc*xdelta)); + (*points)[pi++].set_y(2 + (h - (curve[pc] * h))); + } + + /* fold back */ + + (*points)[pi].set_x(_pixel_width); + (*points)[pi++].set_y(h); + + (*points)[pi].set_x(_pixel_width); + (*points)[pi++].set_y(2); + + /* connect the dots ... */ + + (*points)[pi] = (*points)[0]; + + fade_out_shape->property_points() = *points; + delete points; +} + +void +AudioRegionView::set_samples_per_unit (gdouble spu) +{ + RegionView::set_samples_per_unit (spu); + + for (uint32_t n=0; n < waves.size(); ++n) { + waves[n]->property_samples_per_unit() = spu; + } + + if (gain_line) { + gain_line->reset (); + } + reset_fade_shapes (); +} + +void +AudioRegionView::set_amplitude_above_axis (gdouble spp) +{ + for (uint32_t n=0; n < waves.size(); ++n) { + waves[n]->property_amplitude_above_axis() = spp; + } +} + +void +AudioRegionView::compute_colors (Gdk::Color& basic_color) +{ + RegionView::compute_colors(basic_color); + + uint32_t r, g, b, a; + + /* gain color computed in envelope_active_changed() */ + + UINT_TO_RGBA (fill_color, &r, &g, &b, &a); + fade_color = RGBA_TO_UINT(r,g,b,120); +} + +void +AudioRegionView::set_colors () +{ + RegionView::set_colors(); + + if (gain_line) { + gain_line->set_line_color (audio_region().envelope_active() ? color_map[cGainLine] : color_map[cGainLineInactive]); + } + + for (uint32_t n=0; n < waves.size(); ++n) { + if (_region.muted()) { + waves[n]->property_wave_color() = color_map[cMutedWaveForm]; + } else { + waves[n]->property_wave_color() = color_map[cWaveForm]; + } + } +} + +void +AudioRegionView::show_region_editor () +{ + if (editor == 0) { + editor = new AudioRegionEditor (trackview.session(), audio_region(), *this); + // GTK2FIX : how to ensure float without realizing + // editor->realize (); + // trackview.editor.ensure_float (*editor); + } + + editor->show_all (); + editor->get_window()->raise(); +} + +void +AudioRegionView::set_waveform_visible (bool yn) +{ + if (((_flags & WaveformVisible) != yn)) { + if (yn) { + for (uint32_t n=0; n < waves.size(); ++n) { + waves[n]->show(); + } + _flags |= WaveformVisible; + } else { + for (uint32_t n=0; n < waves.size(); ++n) { + waves[n]->hide(); + } + _flags &= ~WaveformVisible; + } + store_flags (); + } +} + +void +AudioRegionView::temporarily_hide_envelope () +{ + if (gain_line) { + gain_line->hide (); + } +} + +void +AudioRegionView::unhide_envelope () +{ + if (gain_line && (_flags & EnvelopeVisible)) { + gain_line->show (); + } +} + +void +AudioRegionView::set_envelope_visible (bool yn) +{ + if (gain_line && ((_flags & EnvelopeVisible) != yn)) { + if (yn) { + gain_line->show (); + _flags |= EnvelopeVisible; + } else { + gain_line->hide (); + _flags &= ~EnvelopeVisible; + } + store_flags (); + } +} + +void +AudioRegionView::create_waves () +{ + bool create_zero_line = true; + + RouteTimeAxisView& atv (*(dynamic_cast(&trackview))); // ick + + if (!atv.get_diskstream()) { + return; + } + + uint32_t nchans = atv.get_diskstream()->n_channels(); + + /* in tmp_waves, set up null pointers for each channel so the vector is allocated */ + for (uint32_t n = 0; n < nchans; ++n) { + tmp_waves.push_back (0); + } + + for (uint32_t n = 0; n < nchans; ++n) { + + if (n >= audio_region().n_channels()) { + break; + } + + wave_caches.push_back (WaveView::create_cache ()); + + if (wait_for_data) { + if (audio_region().source(n).peaks_ready (bind (mem_fun(*this, &AudioRegionView::peaks_ready_handler), n), data_ready_connection)) { + create_one_wave (n, true); + } else { + create_zero_line = false; + } + } else { + create_one_wave (n, true); + } + } + + if (create_zero_line) { + zero_line = new ArdourCanvas::SimpleLine (*group); + zero_line->property_x1() = (gdouble) 1.0; + zero_line->property_x2() = (gdouble) (_region.length() / samples_per_unit) - 1.0; + zero_line->property_color_rgba() = (guint) color_map[cZeroLine]; + manage_zero_line (); + } +} + +void +AudioRegionView::create_one_wave (uint32_t which, bool direct) +{ + RouteTimeAxisView& atv (*(dynamic_cast(&trackview))); // ick + uint32_t nchans = atv.get_diskstream()->n_channels(); + uint32_t n; + uint32_t nwaves = std::min (nchans, audio_region().n_channels()); + gdouble ht; + + if (trackview.height < NAME_HIGHLIGHT_SIZE) { + ht = ((trackview.height) / (double) nchans); + } else { + ht = ((trackview.height - NAME_HIGHLIGHT_SIZE) / (double) nchans); + } + + gdouble yoff = which * ht; + + WaveView *wave = new WaveView(*group); + + wave->property_data_src() = (gpointer) &_region; + wave->property_cache() = wave_caches[which]; + wave->property_cache_updater() = true; + wave->property_channel() = which; + wave->property_length_function() = (gpointer) region_length_from_c; + wave->property_sourcefile_length_function() = (gpointer) sourcefile_length_from_c; + wave->property_peak_function() = (gpointer) region_read_peaks_from_c; + wave->property_x() = 0.0; + wave->property_y() = yoff; + wave->property_height() = (double) ht; + wave->property_samples_per_unit() = samples_per_unit; + wave->property_amplitude_above_axis() = _amplitude_above_axis; + wave->property_wave_color() = _region.muted() ? color_map[cMutedWaveForm] : color_map[cWaveForm]; + wave->property_region_start() = _region.start(); + + if (!(_flags & WaveformVisible)) { + wave->hide(); + } + + /* note: calling this function is serialized by the lock + held in the peak building thread that signals that + peaks are ready for use *or* by the fact that it is + called one by one from the GUI thread. + */ + + if (which < nchans) { + tmp_waves[which] = wave; + } else { + /* n-channel track, >n-channel source */ + } + + /* see if we're all ready */ + + for (n = 0; n < nchans; ++n) { + if (tmp_waves[n] == 0) { + break; + } + } + + if (n == nwaves && waves.empty()) { + /* all waves are ready */ + tmp_waves.resize(nwaves); + + waves = tmp_waves; + tmp_waves.clear (); + + if (!zero_line) { + zero_line = new ArdourCanvas::SimpleLine (*group); + zero_line->property_x1() = (gdouble) 1.0; + zero_line->property_x2() = (gdouble) (_region.length() / samples_per_unit) - 1.0; + zero_line->property_color_rgba() = (guint) color_map[cZeroLine]; + manage_zero_line (); + } + } +} + +void +AudioRegionView::peaks_ready_handler (uint32_t which) +{ + Gtkmm2ext::UI::instance()->call_slot (bind (mem_fun(*this, &AudioRegionView::create_one_wave), which, false)); + + if (!waves.empty()) { + /* all waves created, don't hook into peaks ready anymore */ + data_ready_connection.disconnect (); + } +} + +void +AudioRegionView::add_gain_point_event (ArdourCanvas::Item *item, GdkEvent *ev) +{ + if (gain_line == 0) { + return; + } + + double x, y; + + /* don't create points that can't be seen */ + + set_envelope_visible (true); + + x = ev->button.x; + y = ev->button.y; + + item->w2i (x, y); + + jack_nframes_t fx = trackview.editor.pixel_to_frame (x); + + if (fx > _region.length()) { + return; + } + + /* compute vertical fractional position */ + + y = 1.0 - (y / (trackview.height - NAME_HIGHLIGHT_SIZE)); + + /* map using gain line */ + + gain_line->view_to_model_y (y); + + trackview.session().begin_reversible_command (_("add gain control point")); + trackview.session().add_undo (audio_region().envelope().get_memento()); + + + if (!audio_region().envelope_active()) { + trackview.session().add_undo( bind( mem_fun(audio_region(), &AudioRegion::set_envelope_active), false) ); + audio_region().set_envelope_active(true); + trackview.session().add_redo( bind( mem_fun(audio_region(), &AudioRegion::set_envelope_active), true) ); + } + + audio_region().envelope().add (fx, y); + + trackview.session().add_redo_no_execute (audio_region().envelope().get_memento()); + trackview.session().commit_reversible_command (); +} + +void +AudioRegionView::remove_gain_point_event (ArdourCanvas::Item *item, GdkEvent *ev) +{ + ControlPoint *cp = reinterpret_cast (item->get_data ("control_point")); + audio_region().envelope().erase (cp->model); +} + +void +AudioRegionView::store_flags() +{ + XMLNode *node = new XMLNode ("GUI"); + + node->add_property ("waveform-visible", (_flags & WaveformVisible) ? "yes" : "no"); + node->add_property ("envelope-visible", (_flags & EnvelopeVisible) ? "yes" : "no"); + + _region.add_extra_xml (*node); +} + +void +AudioRegionView::set_flags (XMLNode* node) +{ + XMLProperty *prop; + + if ((prop = node->property ("waveform-visible")) != 0) { + if (prop->value() == "yes") { + _flags |= WaveformVisible; + } + } + + if ((prop = node->property ("envelope-visible")) != 0) { + if (prop->value() == "yes") { + _flags |= EnvelopeVisible; + } + } +} + +void +AudioRegionView::set_waveform_shape (WaveformShape shape) +{ + bool yn; + + /* this slightly odd approach is to leave the door open to + other "shapes" such as spectral displays, etc. + */ + + switch (shape) { + case Rectified: + yn = true; + break; + + default: + yn = false; + break; + } + + if (yn != (bool) (_flags & WaveformRectified)) { + for (vector::iterator wave = waves.begin(); wave != waves.end() ; ++wave) { + (*wave)->property_rectified() = yn; + } + + if (zero_line) { + if (yn) { + zero_line->hide(); + } else { + zero_line->show(); + } + } + + if (yn) { + _flags |= WaveformRectified; + } else { + _flags &= ~WaveformRectified; + } + } +} + +GhostRegion* +AudioRegionView::add_ghost (AutomationTimeAxisView& atv) +{ + RouteTimeAxisView* rtv = dynamic_cast(&trackview); + assert(rtv); + + double unit_position = _region.position () / samples_per_unit; + GhostRegion* ghost = new GhostRegion (atv, unit_position); + uint32_t nchans; + + nchans = rtv->get_diskstream()->n_channels(); + + for (uint32_t n = 0; n < nchans; ++n) { + + if (n >= audio_region().n_channels()) { + break; + } + + WaveView *wave = new WaveView(*ghost->group); + + wave->property_data_src() = &_region; + wave->property_cache() = wave_caches[n]; + wave->property_cache_updater() = false; + wave->property_channel() = n; + wave->property_length_function() = (gpointer)region_length_from_c; + wave->property_sourcefile_length_function() = (gpointer) sourcefile_length_from_c; + wave->property_peak_function() = (gpointer) region_read_peaks_from_c; + wave->property_x() = 0.0; + wave->property_samples_per_unit() = samples_per_unit; + wave->property_amplitude_above_axis() = _amplitude_above_axis; + wave->property_wave_color() = color_map[cGhostTrackWave]; + wave->property_region_start() = _region.start(); + + ghost->waves.push_back(wave); + } + + ghost->set_height (); + ghost->set_duration (_region.length() / samples_per_unit); + ghosts.push_back (ghost); + + ghost->GoingAway.connect (mem_fun(*this, &AudioRegionView::remove_ghost)); + + return ghost; +} + +void +AudioRegionView::entered () +{ + if (gain_line && _flags & EnvelopeVisible) { + gain_line->show_all_control_points (); + } + + uint32_t r,g,b,a; + UINT_TO_RGBA(fade_color,&r,&g,&b,&a); + a=255; + + if (fade_in_handle) { + fade_in_handle->property_fill_color_rgba() = RGBA_TO_UINT(r,g,b,a); + fade_out_handle->property_fill_color_rgba() = RGBA_TO_UINT(r,g,b,a); + } +} + +void +AudioRegionView::exited () +{ + if (gain_line) { + gain_line->hide_all_but_selected_control_points (); + } + + uint32_t r,g,b,a; + UINT_TO_RGBA(fade_color,&r,&g,&b,&a); + a=0; + + if (fade_in_handle) { + fade_in_handle->property_fill_color_rgba() = RGBA_TO_UINT(r,g,b,a); + fade_out_handle->property_fill_color_rgba() = RGBA_TO_UINT(r,g,b,a); + } +} + +void +AudioRegionView::envelope_active_changed () +{ + if (gain_line) { + gain_line->set_line_color (audio_region().envelope_active() ? color_map[cGainLine] : color_map[cGainLineInactive]); + } +} + +void +AudioRegionView::set_waveview_data_src() +{ + + double unit_length= _region.length() / samples_per_unit; + + for (uint32_t n = 0; n < waves.size(); ++n) { + // TODO: something else to let it know the channel + waves[n]->property_data_src() = &_region; + } + + for (vector::iterator i = ghosts.begin(); i != ghosts.end(); ++i) { + + (*i)->set_duration (unit_length); + + for (vector::iterator w = (*i)->waves.begin(); w != (*i)->waves.end(); ++w) { + (*w)->property_data_src() = &_region; + } + } + +} + +void +AudioRegionView::color_handler (ColorID id, uint32_t val) +{ + switch (id) { + case cMutedWaveForm: + case cWaveForm: + set_colors (); + break; + + case cGainLineInactive: + case cGainLine: + envelope_active_changed(); + break; + + case cZeroLine: + if (zero_line) { + zero_line->property_color_rgba() = (guint) color_map[cZeroLine]; + } + break; + + case cGhostTrackWave: + break; + + default: + break; + } +} diff --git a/gtk2_ardour/regionview.h b/gtk2_ardour/audio_region_view.h similarity index 56% rename from gtk2_ardour/regionview.h rename to gtk2_ardour/audio_region_view.h index f49b46aea4..ec3ea6c4c5 100644 --- a/gtk2_ardour/regionview.h +++ b/gtk2_ardour/audio_region_view.h @@ -1,5 +1,5 @@ /* - Copyright (C) 2001-2004 Paul Davis + Copyright (C) 2001-2006 Paul Davis This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -14,12 +14,10 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ */ -#ifndef __gtk_ardour_region_view_h__ -#define __gtk_ardour_region_view_h__ +#ifndef __gtk_ardour_audio_region_view_h__ +#define __gtk_ardour_audio_region_view_h__ #include @@ -28,6 +26,8 @@ #include #include +#include "region_view.h" +#include "route_time_axis.h" #include "time_axis_view_item.h" #include "automation_line.h" #include "enums.h" @@ -46,51 +46,38 @@ class AudioRegionEditor; class GhostRegion; class AutomationTimeAxisView; -class AudioRegionView : public TimeAxisViewItem +class AudioRegionView : public RegionView { public: AudioRegionView (ArdourCanvas::Group *, - AudioTimeAxisView&, + RouteTimeAxisView&, ARDOUR::AudioRegion&, double initial_samples_per_unit, Gdk::Color& basic_color); ~AudioRegionView (); - virtual void init (double amplitude_above_axis, Gdk::Color& base_color, bool wait_for_waves); + virtual void init (Gdk::Color& base_color, bool wait_for_data = false); + + ARDOUR::AudioRegion& audio_region() const; - ARDOUR::AudioRegion& region; // ok, let 'em have it - bool is_valid() const { return valid; } - void set_valid (bool yn) { valid = yn; } - void set_height (double); void set_samples_per_unit (double); - bool set_duration (jack_nframes_t, void*); void set_amplitude_above_axis (gdouble spp); - void move (double xdelta, double ydelta); - - void raise (); - void raise_to_top (); - void lower (); - void lower_to_bottom (); - - bool set_position(jack_nframes_t pos, void* src, double* delta = 0); - - void temporarily_hide_envelope (); // dangerous - void unhide_envelope (); // dangerous + void temporarily_hide_envelope (); ///< Dangerous! + void unhide_envelope (); ///< Dangerous! void set_envelope_visible (bool); void set_waveform_visible (bool yn); void set_waveform_shape (WaveformShape); bool waveform_rectified() const { return _flags & WaveformRectified; } - bool waveform_visible() const { return _flags & WaveformVisible; } - bool envelope_visible() const { return _flags & EnvelopeVisible; } + bool waveform_visible() const { return _flags & WaveformVisible; } + bool envelope_visible() const { return _flags & EnvelopeVisible; } void show_region_editor (); - void hide_region_editor(); void add_gain_point_event (ArdourCanvas::Item *item, GdkEvent *event); void remove_gain_point_event (ArdourCanvas::Item *item, GdkEvent *event); @@ -100,19 +87,13 @@ class AudioRegionView : public TimeAxisViewItem void region_changed (ARDOUR::Change); void envelope_active_changed (); - static sigc::signal AudioRegionViewGoingAway; - sigc::signal GoingAway; - GhostRegion* add_ghost (AutomationTimeAxisView&); - void remove_ghost (GhostRegion*); void reset_fade_in_shape_width (jack_nframes_t); void reset_fade_out_shape_width (jack_nframes_t); void set_fade_in_active (bool); void set_fade_out_active (bool); - uint32_t get_fill_color (); - virtual void entered (); virtual void exited (); @@ -124,44 +105,18 @@ class AudioRegionView : public TimeAxisViewItem */ AudioRegionView (ArdourCanvas::Group *, - AudioTimeAxisView&, - ARDOUR::AudioRegion&, - double initial_samples_per_unit, - Gdk::Color& basic_color, - TimeAxisViewItem::Visibility); + RouteTimeAxisView&, + ARDOUR::AudioRegion&, + double samples_per_unit, + Gdk::Color& basic_color, + TimeAxisViewItem::Visibility); enum Flags { EnvelopeVisible = 0x1, WaveformVisible = 0x4, WaveformRectified = 0x8 }; - - vector waves; /* waveviews */ - vector tmp_waves; /* see ::create_waves()*/ - ArdourCanvas::Polygon* sync_mark; /* polgyon for sync position */ - ArdourCanvas::Text* no_wave_msg; /* text */ - ArdourCanvas::SimpleLine* zero_line; /* simpleline */ - ArdourCanvas::Polygon* fade_in_shape; /* polygon */ - ArdourCanvas::Polygon* fade_out_shape; /* polygon */ - ArdourCanvas::SimpleRect* fade_in_handle; /* simplerect */ - ArdourCanvas::SimpleRect* fade_out_handle; /* simplerect */ - - AudioRegionGainLine* gain_line; - AudioRegionEditor *editor; - - vector control_points; - double _amplitude_above_axis; - double current_visible_sync_position; - - uint32_t _flags; - uint32_t fade_color; - bool valid; /* see StreamView::redisplay_diskstream() */ - double _pixel_width; - double _height; - bool in_destructor; - bool wait_for_waves; - sigc::connection peaks_ready_connection; - + void reset_fade_shapes (); void reset_fade_in_shape (); void reset_fade_out_shape (); @@ -173,34 +128,37 @@ class AudioRegionView : public TimeAxisViewItem void region_resized (ARDOUR::Change); void region_moved (void *); void region_muted (); - void region_locked (); - void region_opacity (); - void region_layered (); - void region_renamed (); - void region_sync_changed (); void region_scale_amplitude_changed (); - static gint _lock_toggle (ArdourCanvas::Item*, GdkEvent*, void*); - void lock_toggle (); - void create_waves (); void create_one_wave (uint32_t, bool); void manage_zero_line (); void peaks_ready_handler (uint32_t); - void reset_name (gdouble width); void set_flags (XMLNode *); void store_flags (); void set_colors (); void compute_colors (Gdk::Color&); - virtual void set_frame_color (); void reset_width_dependent_items (double pixel_width); void set_waveview_data_src(); + + void color_handler (ColorID, uint32_t); vector wave_caches; - vector ghosts; - - void color_handler (ColorID, uint32_t); + vector waves; + vector tmp_waves; ///< see ::create_waves() + ArdourCanvas::Polygon* sync_mark; ///< polgyon for sync position + ArdourCanvas::SimpleLine* zero_line; + ArdourCanvas::Polygon* fade_in_shape; + ArdourCanvas::Polygon* fade_out_shape; + ArdourCanvas::SimpleRect* fade_in_handle; + ArdourCanvas::SimpleRect* fade_out_handle; + AudioRegionGainLine* gain_line; + + double _amplitude_above_axis; + + uint32_t _flags; + uint32_t fade_color; }; -#endif /* __gtk_ardour_region_view_h__ */ +#endif /* __gtk_ardour_audio_region_view_h__ */ diff --git a/gtk2_ardour/regionview.cc b/gtk2_ardour/audio_regionview.cc similarity index 98% rename from gtk2_ardour/regionview.cc rename to gtk2_ardour/audio_regionview.cc index dcc71a03c4..e2d20c0cc0 100644 --- a/gtk2_ardour/regionview.cc +++ b/gtk2_ardour/audio_regionview.cc @@ -15,7 +15,7 @@ along with this program; if not, write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - $Id$ + $Id: regionview.cc 678 2006-07-11 15:45:19Z paul $ */ #include @@ -29,10 +29,9 @@ #include #include #include -#include #include "streamview.h" -#include "regionview.h" +#include "region_view.h" #include "audio_time_axis.h" #include "simplerect.h" #include "simpleline.h" @@ -519,7 +518,7 @@ AudioRegionView::set_height (gdouble height) for (uint32_t n=0; n < wcnt; ++n) { gdouble ht; - if ((height) < NAME_HIGHLIGHT_THRESH) { + if ((height) <= NAME_HIGHLIGHT_THRESH) { ht = ((height-2*wcnt) / (double) wcnt); } else { ht = (((height-2*wcnt) - NAME_HIGHLIGHT_SIZE) / (double) wcnt); @@ -1145,20 +1144,18 @@ AudioRegionView::add_gain_point_event (ArdourCanvas::Item *item, GdkEvent *ev) gain_line->view_to_model_y (y); trackview.session().begin_reversible_command (_("add gain control point")); - XMLNode &before = region.envelope().get_state(); + trackview.session().add_undo (region.envelope().get_memento()); if (!region.envelope_active()) { - XMLNode &before = region.get_state(); + trackview.session().add_undo( bind( mem_fun(region, &AudioRegion::set_envelope_active), false) ); region.set_envelope_active(true); - XMLNode &after = region.get_state(); - trackview.session().add_command(new MementoCommand(region, before, after)); + trackview.session().add_redo( bind( mem_fun(region, &AudioRegion::set_envelope_active), true) ); } region.envelope().add (fx, y); - XMLNode &after = region.envelope().get_state(); - trackview.session().add_command(new MementoCommand(region.envelope(), before, after)); + trackview.session().add_redo_no_execute (region.envelope().get_memento()); trackview.session().commit_reversible_command (); } diff --git a/gtk2_ardour/audio_streamview.cc b/gtk2_ardour/audio_streamview.cc new file mode 100644 index 0000000000..82349947c6 --- /dev/null +++ b/gtk2_ardour/audio_streamview.cc @@ -0,0 +1,700 @@ +/* + Copyright (C) 2001, 2006 Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. +*/ + +#include +#include + +#include + +#include + +#include +#include +#include +#include +#include +#include +#include + +#include "audio_streamview.h" +#include "audio_region_view.h" +#include "tape_region_view.h" +#include "audio_time_axis.h" +#include "canvas-waveview.h" +#include "canvas-simplerect.h" +#include "region_selection.h" +#include "selection.h" +#include "public_editor.h" +#include "ardour_ui.h" +#include "crossfade_view.h" +#include "rgb_macros.h" +#include "gui_thread.h" +#include "utils.h" +#include "color.h" + +using namespace ARDOUR; +using namespace PBD; +using namespace Editing; + +AudioStreamView::AudioStreamView (AudioTimeAxisView& tv) + : StreamView (tv) +{ + crossfades_visible = true; + + if (tv.is_audio_track()) + stream_base_color = color_map[cAudioTrackBase]; + else + stream_base_color = color_map[cAudioBusBase]; + + canvas_rect->property_fill_color_rgba() = stream_base_color; + canvas_rect->property_outline_color_rgba() = color_map[cAudioTrackOutline]; + + _amplitude_above_axis = 1.0; + + use_rec_regions = tv.editor.show_waveforms_recording (); + last_rec_peak_frame = 0; +} + +AudioStreamView::~AudioStreamView () +{ +} + +int +AudioStreamView::set_height (gdouble h) +{ + /* limit the values to something sane-ish */ + if (h < 10.0 || h > 1000.0) { + return -1; + } + + StreamView::set_height(h); + + for (CrossfadeViewList::iterator i = crossfade_views.begin(); i != crossfade_views.end(); ++i) { + (*i)->set_height (h); + } + + return 0; +} + +int +AudioStreamView::set_samples_per_unit (gdouble spp) +{ + StreamView::set_samples_per_unit(spp); + + for (CrossfadeViewList::iterator xi = crossfade_views.begin(); xi != crossfade_views.end(); ++xi) { + (*xi)->set_samples_per_unit (spp); + } + + return 0; +} + +int +AudioStreamView::set_amplitude_above_axis (gdouble app) +{ + RegionViewList::iterator i; + + if (app < 1.0) { + return -1; + } + + _amplitude_above_axis = app; + + for (i = region_views.begin(); i != region_views.end(); ++i) { + AudioRegionView* const arv = dynamic_cast(*i); + if (arv) + arv->set_amplitude_above_axis (app); + } + + return 0; +} + +void +AudioStreamView::add_region_view_internal (Region *r, bool wait_for_waves) +{ + ENSURE_GUI_THREAD (bind (mem_fun (*this, &AudioStreamView::add_region_view), r)); + + AudioRegion* region = dynamic_cast (r); + + if (region == 0) { + return; + } + + AudioRegionView *region_view; + list::iterator i; + + for (i = region_views.begin(); i != region_views.end(); ++i) { + if (&(*i)->region() == r) { + + /* great. we already have a AudioRegionView for this Region. use it again. */ + + (*i)->set_valid (true); + return; + } + } + + switch (_trackview.audio_track()->mode()) { + case Normal: + region_view = new AudioRegionView (canvas_group, _trackview, *region, + _samples_per_unit, region_color); + break; + case Destructive: + region_view = new TapeAudioRegionView (canvas_group, _trackview, *region, + _samples_per_unit, region_color); + break; + } + + region_view->init (region_color, wait_for_waves); + region_view->set_amplitude_above_axis(_amplitude_above_axis); + region_views.push_front (region_view); + + /* follow global waveform setting */ + + region_view->set_waveform_visible(_trackview.editor.show_waveforms()); + + /* catch regionview going away */ + + region->GoingAway.connect (mem_fun (*this, &AudioStreamView::remove_region_view)); + + RegionViewAdded (region_view); +} + +void +AudioStreamView::remove_region_view (Region *r) +{ + ENSURE_GUI_THREAD (bind (mem_fun (*this, &AudioStreamView::remove_region_view), r)); + + for (list::iterator i = crossfade_views.begin(); i != crossfade_views.end();) { + list::iterator tmp; + + tmp = i; + ++tmp; + + AudioRegion* ar = dynamic_cast(r); + if (ar && (*i)->crossfade.involves (*ar)) { + delete *i; + crossfade_views.erase (i); + } + + i = tmp; + } + + StreamView::remove_region_view(r); +} + +void +AudioStreamView::undisplay_diskstream () +{ + StreamView::undisplay_diskstream(); + + for (CrossfadeViewList::iterator i = crossfade_views.begin(); i != crossfade_views.end(); ++i) { + delete *i; + } + + crossfade_views.clear (); +} + +void +AudioStreamView::playlist_modified () +{ + ENSURE_GUI_THREAD (mem_fun (*this, &AudioStreamView::playlist_modified)); + + StreamView::playlist_modified(); + + /* if the playlist is modified, make sure xfades are on top and all the regionviews are stacked + correctly. + */ + + for (list::iterator i = crossfade_views.begin(); i != crossfade_views.end(); ++i) { + (*i)->get_canvas_group()->raise_to_top(); + } +} + +void +AudioStreamView::playlist_changed (Diskstream *ds) +{ + ENSURE_GUI_THREAD (bind (mem_fun (*this, &AudioStreamView::playlist_changed), ds)); + + StreamView::playlist_changed(ds); + + AudioPlaylist* apl = dynamic_cast(ds->playlist()); + if (apl) + playlist_connections.push_back (apl->NewCrossfade.connect (mem_fun (*this, &AudioStreamView::add_crossfade))); +} + +void +AudioStreamView::add_crossfade (Crossfade *crossfade) +{ + AudioRegionView* lview = 0; + AudioRegionView* rview = 0; + + ENSURE_GUI_THREAD (bind (mem_fun (*this, &AudioStreamView::add_crossfade), crossfade)); + + /* first see if we already have a CrossfadeView for this Crossfade */ + + for (list::iterator i = crossfade_views.begin(); i != crossfade_views.end(); ++i) { + if (&(*i)->crossfade == crossfade) { + if (!crossfades_visible) { + (*i)->hide(); + } else { + (*i)->show (); + } + (*i)->set_valid (true); + return; + } + } + + /* create a new one */ + + for (list::iterator i = region_views.begin(); i != region_views.end(); ++i) { + AudioRegionView* arv = dynamic_cast(*i); + + if (!lview && arv && &(arv->region()) == &crossfade->out()) { + lview = arv; + } + if (!rview && arv && &(arv->region()) == &crossfade->in()) { + rview = arv; + } + } + + CrossfadeView *cv = new CrossfadeView (_trackview.canvas_display, + _trackview, + *crossfade, + _samples_per_unit, + region_color, + *lview, *rview); + + crossfade->Invalidated.connect (mem_fun (*this, &AudioStreamView::remove_crossfade)); + crossfade_views.push_back (cv); + + if (!crossfades_visible) { + cv->hide (); + } +} + +void +AudioStreamView::remove_crossfade (Crossfade *xfade) +{ + ENSURE_GUI_THREAD (bind (mem_fun (*this, &AudioStreamView::remove_crossfade), xfade)); + + for (list::iterator i = crossfade_views.begin(); i != crossfade_views.end(); ++i) { + if (&(*i)->crossfade == xfade) { + delete *i; + crossfade_views.erase (i); + break; + } + } +} + +void +AudioStreamView::redisplay_diskstream () +{ + list::iterator i, tmp; + list::iterator xi, tmpx; + + + for (i = region_views.begin(); i != region_views.end(); ++i) { + (*i)->set_valid (false); + } + + for (xi = crossfade_views.begin(); xi != crossfade_views.end(); ++xi) { + (*xi)->set_valid (false); + if ((*xi)->visible()) { + (*xi)->show (); + } + } + + if (_trackview.is_audio_track()) { + _trackview.get_diskstream()->playlist()->foreach_region (static_cast(this), &StreamView::add_region_view); + AudioPlaylist* apl = dynamic_cast(_trackview.get_diskstream()->playlist()); + if (apl) + apl->foreach_crossfade (this, &AudioStreamView::add_crossfade); + } + + for (i = region_views.begin(); i != region_views.end(); ) { + tmp = i; + tmp++; + + if (!(*i)->is_valid()) { + delete *i; + region_views.erase (i); + } + + i = tmp; + } + + for (xi = crossfade_views.begin(); xi != crossfade_views.end();) { + tmpx = xi; + tmpx++; + + if (!(*xi)->valid()) { + delete *xi; + crossfade_views.erase (xi); + } + + xi = tmpx; + } + + /* now fix layering */ + + playlist_modified (); +} + +void +AudioStreamView::set_show_waveforms (bool yn) +{ + for (list::iterator i = region_views.begin(); i != region_views.end(); ++i) { + AudioRegionView* const arv = dynamic_cast(*i); + if (arv) + arv->set_waveform_visible (yn); + } +} + +void +AudioStreamView::set_waveform_shape (WaveformShape shape) +{ + for (RegionViewList::iterator i = region_views.begin(); i != region_views.end(); ++i) { + AudioRegionView* const arv = dynamic_cast(*i); + if (arv) + arv->set_waveform_shape (shape); + } +} + +void +AudioStreamView::setup_rec_box () +{ + // cerr << _trackview.name() << " streamview SRB\n"; + + if (_trackview.session().transport_rolling()) { + + // cerr << "\trolling\n"; + + if (!rec_active && + _trackview.session().record_status() == Session::Recording && + _trackview.get_diskstream()->record_enabled()) { + + if (_trackview.audio_track()->mode() == Normal && use_rec_regions && rec_regions.size() == rec_rects.size()) { + + /* add a new region, but don't bother if they set use_rec_regions mid-record */ + + AudioRegion::SourceList sources; + + for (list::iterator prc = peak_ready_connections.begin(); prc != peak_ready_connections.end(); ++prc) { + (*prc).disconnect(); + } + peak_ready_connections.clear(); + + // FIXME + AudioDiskstream* ads = dynamic_cast(_trackview.get_diskstream()); + assert(ads); + + for (uint32_t n=0; n < ads->n_channels(); ++n) { + AudioSource *src = (AudioSource *) ads->write_source (n); + if (src) { + sources.push_back (src); + peak_ready_connections.push_back (src->PeakRangeReady.connect (bind (mem_fun (*this, &AudioStreamView::rec_peak_range_ready), src))); + } + } + + // handle multi + + jack_nframes_t start = 0; + if (rec_regions.size() > 0) { + start = rec_regions.back()->start() + _trackview.get_diskstream()->get_captured_frames(rec_regions.size()-1); + } + + AudioRegion * region = new AudioRegion(sources, start, 1 , "", 0, (Region::Flag)(Region::DefaultFlags | Region::DoNotSaveState), false); + region->set_position (_trackview.session().transport_frame(), this); + rec_regions.push_back (region); + /* catch it if it goes away */ + region->GoingAway.connect (mem_fun (*this, &AudioStreamView::remove_rec_region)); + + /* we add the region later */ + } + + /* start a new rec box */ + + AudioTrack* at; + + at = _trackview.audio_track(); /* we know what it is already */ + AudioDiskstream& ds = at->audio_diskstream(); + jack_nframes_t frame_pos = ds.current_capture_start (); + gdouble xstart = _trackview.editor.frame_to_pixel (frame_pos); + gdouble xend; + uint32_t fill_color; + + switch (_trackview.audio_track()->mode()) { + case Normal: + xend = xstart; + fill_color = color_map[cRecordingRectFill]; + break; + + case Destructive: + xend = xstart + 2; + fill_color = color_map[cRecordingRectFill]; + /* make the recording rect translucent to allow + the user to see the peak data coming in, etc. + */ + fill_color = UINT_RGBA_CHANGE_A (fill_color, 120); + break; + } + + ArdourCanvas::SimpleRect * rec_rect = new Gnome::Canvas::SimpleRect (*canvas_group); + rec_rect->property_x1() = xstart; + rec_rect->property_y1() = 1.0; + rec_rect->property_x2() = xend; + rec_rect->property_y2() = (double) _trackview.height - 1; + rec_rect->property_outline_color_rgba() = color_map[cRecordingRectOutline]; + rec_rect->property_fill_color_rgba() = fill_color; + + RecBoxInfo recbox; + recbox.rectangle = rec_rect; + recbox.start = _trackview.session().transport_frame(); + recbox.length = 0; + + rec_rects.push_back (recbox); + + screen_update_connection.disconnect(); + screen_update_connection = ARDOUR_UI::instance()->SuperRapidScreenUpdate.connect (mem_fun (*this, &AudioStreamView::update_rec_box)); + rec_updating = true; + rec_active = true; + + } else if (rec_active && + (_trackview.session().record_status() != Session::Recording || + !_trackview.get_diskstream()->record_enabled())) { + + screen_update_connection.disconnect(); + rec_active = false; + rec_updating = false; + + } + + } else { + + // cerr << "\tNOT rolling, rec_rects = " << rec_rects.size() << " rec_regions = " << rec_regions.size() << endl; + + if (!rec_rects.empty() || !rec_regions.empty()) { + + /* disconnect rapid update */ + screen_update_connection.disconnect(); + + for (list::iterator prc = peak_ready_connections.begin(); prc != peak_ready_connections.end(); ++prc) { + (*prc).disconnect(); + } + peak_ready_connections.clear(); + + rec_updating = false; + rec_active = false; + last_rec_peak_frame = 0; + + /* remove temp regions */ + for (list::iterator iter=rec_regions.begin(); iter != rec_regions.end(); ) + { + list::iterator tmp; + + tmp = iter; + ++tmp; + + /* this will trigger the remove_region_view */ + delete *iter; + + iter = tmp; + } + + rec_regions.clear(); + + // cerr << "\tclear " << rec_rects.size() << " rec rects\n"; + + + /* transport stopped, clear boxes */ + for (vector::iterator iter=rec_rects.begin(); iter != rec_rects.end(); ++iter) { + RecBoxInfo &rect = (*iter); + delete rect.rectangle; + } + + rec_rects.clear(); + + } + } +} + +void +AudioStreamView::foreach_crossfadeview (void (CrossfadeView::*pmf)(void)) +{ + for (list::iterator i = crossfade_views.begin(); i != crossfade_views.end(); ++i) { + ((*i)->*pmf) (); + } +} + +void +AudioStreamView::rec_peak_range_ready (jack_nframes_t start, jack_nframes_t cnt, Source * src) +{ + // this is called from the peak building thread + + ENSURE_GUI_THREAD(bind (mem_fun (*this, &AudioStreamView::rec_peak_range_ready), start, cnt, src)); + + if (rec_peak_ready_map.size() == 0 || start+cnt > last_rec_peak_frame) { + last_rec_peak_frame = start + cnt; + } + + rec_peak_ready_map[src] = true; + + if (rec_peak_ready_map.size() == _trackview.get_diskstream()->n_channels()) { + this->update_rec_regions (); + rec_peak_ready_map.clear(); + } +} + +void +AudioStreamView::update_rec_regions () +{ + if (use_rec_regions) { + + uint32_t n = 0; + + for (list::iterator iter = rec_regions.begin(); iter != rec_regions.end(); n++) { + + list::iterator tmp; + + tmp = iter; + ++tmp; + + if (!canvas_item_visible (rec_rects[n].rectangle)) { + /* rect already hidden, this region is done */ + iter = tmp; + continue; + } + + // FIXME + AudioRegion * region = dynamic_cast(*iter); + assert(region); + + jack_nframes_t origlen = region->length(); + + if (region == rec_regions.back() && rec_active) { + + if (last_rec_peak_frame > region->start()) { + + jack_nframes_t nlen = last_rec_peak_frame - region->start(); + + if (nlen != region->length()) { + + region->freeze (); + region->set_position (_trackview.get_diskstream()->get_capture_start_frame(n), this); + region->set_length (nlen, this); + region->thaw ("updated"); + + if (origlen == 1) { + /* our special initial length */ + add_region_view_internal (region, false); + } + + /* also update rect */ + ArdourCanvas::SimpleRect * rect = rec_rects[n].rectangle; + gdouble xend = _trackview.editor.frame_to_pixel (region->position() + region->length()); + rect->property_x2() = xend; + } + } + + } else { + + jack_nframes_t nlen = _trackview.get_diskstream()->get_captured_frames(n); + + if (nlen != region->length()) { + + if (region->source(0).length() >= region->start() + nlen) { + + region->freeze (); + region->set_position (_trackview.get_diskstream()->get_capture_start_frame(n), this); + region->set_length (nlen, this); + region->thaw ("updated"); + + if (origlen == 1) { + /* our special initial length */ + add_region_view_internal (region, false); + } + + /* also hide rect */ + ArdourCanvas::Item * rect = rec_rects[n].rectangle; + rect->hide(); + + } + } + } + + iter = tmp; + } + } +} + +void +AudioStreamView::show_all_xfades () +{ + foreach_crossfadeview (&CrossfadeView::show); + crossfades_visible = true; +} + +void +AudioStreamView::hide_all_xfades () +{ + foreach_crossfadeview (&CrossfadeView::hide); + crossfades_visible = false; +} + +void +AudioStreamView::hide_xfades_involving (AudioRegionView& rv) +{ + for (list::iterator i = crossfade_views.begin(); i != crossfade_views.end(); ++i) { + if ((*i)->crossfade.involves (rv.audio_region())) { + (*i)->fake_hide (); + } + } +} + +void +AudioStreamView::reveal_xfades_involving (AudioRegionView& rv) +{ + for (list::iterator i = crossfade_views.begin(); i != crossfade_views.end(); ++i) { + if ((*i)->crossfade.involves (rv.audio_region()) && (*i)->visible()) { + (*i)->show (); + } + } +} + +void +AudioStreamView::color_handler (ColorID id, uint32_t val) +{ + switch (id) { + case cAudioTrackBase: + if (_trackview.is_track()) { + canvas_rect->property_fill_color_rgba() = val; + } + break; + case cAudioBusBase: + if (!_trackview.is_track()) { + canvas_rect->property_fill_color_rgba() = val; + } + break; + case cAudioTrackOutline: + canvas_rect->property_outline_color_rgba() = val; + break; + + default: + break; + } +} + diff --git a/gtk2_ardour/audio_streamview.h b/gtk2_ardour/audio_streamview.h new file mode 100644 index 0000000000..05ce8125f6 --- /dev/null +++ b/gtk2_ardour/audio_streamview.h @@ -0,0 +1,110 @@ +/* + Copyright (C) 2001, 2006 Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. +*/ + +#ifndef __ardour_audio_streamview_h__ +#define __ardour_audio_streamview_h__ + +#include +#include +#include + +#include +#include "enums.h" +#include "simplerect.h" +#include "color.h" +#include "streamview.h" + +namespace Gdk { + class Color; +} + +namespace ARDOUR { + class Route; + class Diskstream; + class Crossfade; + class PeakData; + class AudioRegion; + class Source; +} + +class PublicEditor; +class Selectable; +class AudioTimeAxisView; +class AudioRegionView; +class RegionSelection; +class CrossfadeView; +class Selection; + +class AudioStreamView : public StreamView +{ + public: + AudioStreamView (AudioTimeAxisView&); + ~AudioStreamView (); + + void set_waveform_shape (WaveformShape); + + int set_height (gdouble h); + int set_samples_per_unit (gdouble spp); + + int set_amplitude_above_axis (gdouble app); + gdouble get_amplitude_above_axis () { return _amplitude_above_axis; } + + void set_show_waveforms (bool yn); + void set_show_waveforms_recording (bool yn) { use_rec_regions = yn; } + + void foreach_crossfadeview (void (CrossfadeView::*pmf)(void)); + + void show_all_xfades (); + void hide_all_xfades (); + void hide_xfades_involving (AudioRegionView&); + void reveal_xfades_involving (AudioRegionView&); + + private: + void setup_rec_box (); + void rec_peak_range_ready (jack_nframes_t start, jack_nframes_t cnt, ARDOUR::Source* src); + void update_rec_regions (); + + void add_region_view_internal (ARDOUR::Region*, bool wait_for_waves); + void remove_region_view (ARDOUR::Region* ); + void remove_audio_region_view (ARDOUR::AudioRegion* ); + void remove_audio_rec_region (ARDOUR::AudioRegion*); + + void undisplay_diskstream (); + void redisplay_diskstream (); + void playlist_modified (); + void playlist_changed (ARDOUR::Diskstream *ds); + + void add_crossfade (ARDOUR::Crossfade*); + void remove_crossfade (ARDOUR::Crossfade*); + + void color_handler (ColorID id, uint32_t val); + + + double _amplitude_above_axis; + + typedef list CrossfadeViewList; + CrossfadeViewList crossfade_views; + bool crossfades_visible; + + list peak_ready_connections; + jack_nframes_t last_rec_peak_frame; + map rec_peak_ready_map; + +}; + +#endif /* __ardour_audio_streamview_h__ */ diff --git a/gtk2_ardour/audio_time_axis.cc b/gtk2_ardour/audio_time_axis.cc index 857adff6b9..9ae94d1fe0 100644 --- a/gtk2_ardour/audio_time_axis.cc +++ b/gtk2_ardour/audio_time_axis.cc @@ -1,5 +1,5 @@ /* - Copyright (C) 2000 Paul Davis + Copyright (C) 2000-2006 Paul Davis This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -20,6 +20,7 @@ #include #include +#include #include #include @@ -32,16 +33,15 @@ #include #include -#include #include #include #include +#include #include #include #include #include -#include #include #include #include @@ -53,27 +53,20 @@ #include "audio_time_axis.h" #include "automation_gain_line.h" #include "automation_pan_line.h" -#include "automation_time_axis.h" #include "canvas_impl.h" #include "crossfade_view.h" #include "enums.h" #include "gain_automation_time_axis.h" -#include "gui_thread.h" #include "keyboard.h" #include "pan_automation_time_axis.h" #include "playlist_selector.h" #include "plugin_selector.h" #include "plugin_ui.h" -#include "point_selection.h" #include "prompter.h" #include "public_editor.h" -#include "redirect_automation_line.h" -#include "redirect_automation_time_axis.h" -#include "regionview.h" -#include "rgb_macros.h" -#include "selection.h" +#include "audio_region_view.h" #include "simplerect.h" -#include "streamview.h" +#include "audio_streamview.h" #include "utils.h" #include @@ -82,202 +75,76 @@ using namespace ARDOUR; using namespace PBD; -using namespace LADSPA; using namespace Gtk; using namespace Editing; -AudioTimeAxisView::AudioTimeAxisView (PublicEditor& ed, Session& sess, Route& rt, Canvas& canvas) - : AxisView(sess), - RouteUI(rt, sess, _("m"), _("s"), _("r")), // mute, solo, and record - TimeAxisView(sess,ed,(TimeAxisView*) 0, canvas), - parent_canvas (canvas), - button_table (3, 3), - edit_group_button (_("g")), // group - playlist_button (_("p")), - size_button (_("h")), // height - automation_button (_("a")), - visual_button (_("v")) - +AudioTimeAxisView::AudioTimeAxisView (PublicEditor& ed, Session& sess, boost::shared_ptr rt, Canvas& canvas) + : AxisView(sess) + , RouteTimeAxisView(ed, sess, rt, canvas) { - _has_state = true; + // Make sure things are sane... + assert(!is_track() || is_audio_track()); + subplugin_menu.set_name ("ArdourContextMenu"); - playlist_menu = 0; - playlist_action_menu = 0; - automation_action_menu = 0; gain_track = 0; pan_track = 0; - view = 0; - timestretch_rect = 0; waveform_item = 0; pan_automation_item = 0; gain_automation_item = 0; - no_redraw = false; - view = new StreamView (*this); + _view = new AudioStreamView (*this); add_gain_automation_child (); add_pan_automation_child (); ignore_toggle = false; - rec_enable_button->set_active (false); mute_button->set_active (false); solo_button->set_active (false); - rec_enable_button->set_name ("TrackRecordEnableButton"); - mute_button->set_name ("TrackMuteButton"); - solo_button->set_name ("SoloButton"); - edit_group_button.set_name ("TrackGroupButton"); - playlist_button.set_name ("TrackPlaylistButton"); - automation_button.set_name ("TrackAutomationButton"); - size_button.set_name ("TrackSizeButton"); - visual_button.set_name ("TrackVisualButton"); - hide_button.set_name ("TrackRemoveButton"); - - hide_button.add (*(manage (new Image (get_xpm("small_x.xpm"))))); - - solo_button->signal_button_press_event().connect (mem_fun (*this, &AudioTimeAxisView::select_me), false); - mute_button->signal_button_press_event().connect (mem_fun (*this, &AudioTimeAxisView::select_me), false); - rec_enable_button->signal_button_press_event().connect (mem_fun (*this, &AudioTimeAxisView::select_me), false); - playlist_button.signal_button_press_event().connect (mem_fun (*this, &AudioTimeAxisView::select_me), false); - automation_button.signal_button_press_event().connect (mem_fun (*this, &AudioTimeAxisView::select_me), false); - size_button.signal_button_press_event().connect (mem_fun (*this, &AudioTimeAxisView::select_me), false); - visual_button.signal_button_press_event().connect (mem_fun (*this, &AudioTimeAxisView::select_me), false); - hide_button.signal_button_press_event().connect (mem_fun (*this, &AudioTimeAxisView::select_me), false); - - solo_button->signal_button_press_event().connect (mem_fun(*this, &RouteUI::solo_press), false); - solo_button->signal_button_release_event().connect (mem_fun(*this, &RouteUI::solo_release), false); - mute_button->signal_button_press_event().connect (mem_fun(*this, &RouteUI::mute_press), false); - mute_button->signal_button_release_event().connect (mem_fun(*this, &RouteUI::mute_release), false); - rec_enable_button->signal_button_press_event().connect (mem_fun(*this, &RouteUI::rec_enable_press)); - edit_group_button.signal_button_release_event().connect (mem_fun(*this, &AudioTimeAxisView::edit_click), false); - playlist_button.signal_clicked().connect (mem_fun(*this, &AudioTimeAxisView::playlist_click)); - automation_button.signal_clicked().connect (mem_fun(*this, &AudioTimeAxisView::automation_click)); - size_button.signal_button_release_event().connect (mem_fun(*this, &AudioTimeAxisView::size_click), false); - visual_button.signal_clicked().connect (mem_fun(*this, &AudioTimeAxisView::visual_click)); - hide_button.signal_clicked().connect (mem_fun(*this, &AudioTimeAxisView::hide_click)); - - if (is_audio_track()) { - controls_table.attach (*rec_enable_button, 5, 6, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND, 0, 0); - } - controls_table.attach (*mute_button, 6, 7, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND, 0, 0); - controls_table.attach (*solo_button, 7, 8, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::FILL|Gtk::EXPAND, 0, 0); - - controls_table.attach (edit_group_button, 6, 7, 1, 2, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND, 0, 0); - - ARDOUR_UI::instance()->tooltips().set_tip(*rec_enable_button, _("Record")); - ARDOUR_UI::instance()->tooltips().set_tip(*solo_button,_("Solo")); - ARDOUR_UI::instance()->tooltips().set_tip(*mute_button,_("Mute")); - ARDOUR_UI::instance()->tooltips().set_tip(edit_group_button,_("Edit Group")); - ARDOUR_UI::instance()->tooltips().set_tip(size_button,_("Display Height")); - ARDOUR_UI::instance()->tooltips().set_tip(playlist_button,_("Playlist")); - ARDOUR_UI::instance()->tooltips().set_tip(automation_button, _("Automation")); - ARDOUR_UI::instance()->tooltips().set_tip(visual_button, _("Visual options")); - ARDOUR_UI::instance()->tooltips().set_tip(hide_button, _("Hide this track")); - - label_view (); - - controls_table.attach (hide_button, 0, 1, 1, 2, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - controls_table.attach (visual_button, 1, 2, 1, 2, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - controls_table.attach (size_button, 2, 3, 1, 2, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - controls_table.attach (automation_button, 3, 4, 1, 2, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - - if (is_audio_track() && audio_track()->mode() == ARDOUR::Normal) { - controls_table.attach (playlist_button, 5, 6, 1, 2, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - } - - /* remove focus from the buttons */ - - automation_button.unset_flags (Gtk::CAN_FOCUS); - solo_button->unset_flags (Gtk::CAN_FOCUS); - mute_button->unset_flags (Gtk::CAN_FOCUS); - edit_group_button.unset_flags (Gtk::CAN_FOCUS); - size_button.unset_flags (Gtk::CAN_FOCUS); - playlist_button.unset_flags (Gtk::CAN_FOCUS); - hide_button.unset_flags (Gtk::CAN_FOCUS); - visual_button.unset_flags (Gtk::CAN_FOCUS); + if (is_audio_track()) + controls_ebox.set_name ("AudioTimeAxisViewControlsBaseUnselected"); + else // bus + controls_ebox.set_name ("AudioBusControlsBaseUnselected"); /* map current state of the route */ - update_diskstream_display (); - solo_changed(0); - mute_changed(0); redirects_changed (0); reset_redirect_automation_curves (); - y_position = -1; ensure_xml_node (); set_state (*xml_node); - _route.mute_changed.connect (mem_fun(*this, &RouteUI::mute_changed)); - _route.solo_changed.connect (mem_fun(*this, &RouteUI::solo_changed)); - _route.redirects_changed.connect (mem_fun(*this, &AudioTimeAxisView::redirects_changed)); - _route.name_changed.connect (mem_fun(*this, &AudioTimeAxisView::route_name_changed)); - _route.solo_safe_changed.connect (mem_fun(*this, &RouteUI::solo_changed)); - _route.panner().Changed.connect (mem_fun(*this, &AudioTimeAxisView::update_pans)); + _route->panner().Changed.connect (mem_fun(*this, &AudioTimeAxisView::update_pans)); if (is_audio_track()) { - /* track */ - - audio_track()->FreezeChange.connect (mem_fun(*this, &AudioTimeAxisView::map_frozen)); - - audio_track()->diskstream_changed.connect (mem_fun(*this, &AudioTimeAxisView::diskstream_changed)); - get_diskstream()->speed_changed.connect (mem_fun(*this, &AudioTimeAxisView::speed_changed)); - controls_ebox.set_name ("AudioTrackControlsBaseUnselected"); controls_base_selected_name = "AudioTrackControlsBaseSelected"; controls_base_unselected_name = "AudioTrackControlsBaseUnselected"; /* ask for notifications of any new RegionViews */ + _view->RegionViewAdded.connect (mem_fun(*this, &AudioTimeAxisView::region_view_added)); + _view->attach (); - view->AudioRegionViewAdded.connect (mem_fun(*this, &AudioTimeAxisView::region_view_added)); + } else { /* bus */ - view->attach (); - - /* pick up the correct freeze state */ - - map_frozen (); - - } else { - - /* bus */ - - controls_ebox.set_name ("BusControlsBaseUnselected"); - controls_base_selected_name = "BusControlsBaseSelected"; - controls_base_unselected_name = "BusControlsBaseUnselected"; + controls_ebox.set_name ("AudioBusControlsBaseUnselected"); + controls_base_selected_name = "AudioBusControlsBaseSelected"; + controls_base_unselected_name = "AudioBusControlsBaseUnselected"; } - - editor.ZoomChanged.connect (mem_fun(*this, &AudioTimeAxisView::reset_samples_per_unit)); - ColorChanged.connect (mem_fun (*this, &AudioTimeAxisView::color_handler)); } AudioTimeAxisView::~AudioTimeAxisView () { - GoingAway (); /* EMIT_SIGNAL */ +} - if (playlist_menu) { - delete playlist_menu; - playlist_menu = 0; - } - - if (playlist_action_menu) { - delete playlist_action_menu; - playlist_action_menu = 0; - } - - vector_delete (&redirect_automation_curves); - - for (list::iterator i = redirect_automation.begin(); i != redirect_automation.end(); ++i) { - delete *i; - } - - if (view) { - delete view; - view = 0; - } +AudioStreamView* +AudioTimeAxisView::audio_view() +{ + return dynamic_cast(_view); } guint32 @@ -298,233 +165,6 @@ AudioTimeAxisView::hide () TimeAxisView::hide (); } -void -AudioTimeAxisView::set_playlist (AudioPlaylist *newplaylist) -{ - AudioPlaylist *pl; - - modified_connection.disconnect (); - state_changed_connection.disconnect (); - - if ((pl = dynamic_cast (playlist())) != 0) { - state_changed_connection = pl->StateChanged.connect (mem_fun(*this, &AudioTimeAxisView::playlist_state_changed)); - modified_connection = pl->Modified.connect (mem_fun(*this, &AudioTimeAxisView::playlist_modified)); - } -} - -void -AudioTimeAxisView::playlist_modified () -{ -} - -gint -AudioTimeAxisView::edit_click (GdkEventButton *ev) -{ - if (Keyboard::modifier_state_equals (ev->state, Keyboard::Control)) { - _route.set_edit_group (0, this); - return FALSE; - } - - using namespace Menu_Helpers; - - MenuList& items = edit_group_menu.items (); - RadioMenuItem::Group group; - - items.clear (); - items.push_back (RadioMenuElem (group, _("No group"), - bind (mem_fun(*this, &AudioTimeAxisView::set_edit_group_from_menu), (RouteGroup *) 0))); - - if (_route.edit_group() == 0) { - static_cast(&items.back())->set_active (); - } - - _session.foreach_edit_group (bind (mem_fun (*this, &AudioTimeAxisView::add_edit_group_menu_item), &group)); - edit_group_menu.popup (ev->button, ev->time); - - return FALSE; -} - -void -AudioTimeAxisView::add_edit_group_menu_item (RouteGroup *eg, RadioMenuItem::Group* group) -{ - using namespace Menu_Helpers; - - MenuList &items = edit_group_menu.items(); - - cerr << "adding edit group called " << eg->name() << endl; - - items.push_back (RadioMenuElem (*group, eg->name(), bind (mem_fun(*this, &AudioTimeAxisView::set_edit_group_from_menu), eg))); - if (_route.edit_group() == eg) { - static_cast(&items.back())->set_active (); - } -} - -void -AudioTimeAxisView::set_edit_group_from_menu (RouteGroup *eg) - -{ - _route.set_edit_group (eg, this); -} - -void -AudioTimeAxisView::playlist_state_changed (Change ignored) -{ - // ENSURE_GUI_THREAD (bind (mem_fun(*this, &AudioTimeAxisView::playlist_state_changed), ignored)); - // why are we here ? -} - -void -AudioTimeAxisView::playlist_changed () - -{ - label_view (); - - if (is_audio_track()) { - set_playlist (get_diskstream()->playlist()); - } -} - -void -AudioTimeAxisView::label_view () -{ - string x = _route.name(); - - if (x != name_entry.get_text()) { - name_entry.set_text (x); - } - - ARDOUR_UI::instance()->tooltips().set_tip (name_entry, x); -} - -void -AudioTimeAxisView::route_name_changed (void *src) -{ - editor.route_name_changed (this); - label_view (); -} - -void -AudioTimeAxisView::take_name_changed (void *src) - -{ - if (src != this) { - label_view (); - } -} - -void -AudioTimeAxisView::playlist_click () -{ - // always build a new action menu - - if (playlist_action_menu == 0) { - playlist_action_menu = new Menu; - playlist_action_menu->set_name ("ArdourContextMenu"); - } - - build_playlist_menu(playlist_action_menu); - - playlist_action_menu->popup (1, 0); -} - -void -AudioTimeAxisView::automation_click () -{ - if (automation_action_menu == 0) { - /* this seems odd, but the automation action - menu is built as part of the display menu. - */ - build_display_menu (); - } - automation_action_menu->popup (1, 0); -} - -void -AudioTimeAxisView::show_timestretch (jack_nframes_t start, jack_nframes_t end) -{ - double x1; - double x2; - double y2; - - TimeAxisView::show_timestretch (start, end); - - hide_timestretch (); - -#if 0 - if (ts.empty()) { - return; - } - - - /* check that the time selection was made in our route, or our edit group. - remember that edit_group() == 0 implies the route is *not* in a edit group. - */ - - if (!(ts.track == this || (ts.group != 0 && ts.group == _route.edit_group()))) { - /* this doesn't apply to us */ - return; - } - - /* ignore it if our edit group is not active */ - - if ((ts.track != this) && _route.edit_group() && !_route.edit_group()->is_active()) { - return; - } -#endif - - if (timestretch_rect == 0) { - timestretch_rect = new SimpleRect (*canvas_display); - timestretch_rect->property_x1() = 0.0; - timestretch_rect->property_y1() = 0.0; - timestretch_rect->property_x2() = 0.0; - timestretch_rect->property_y2() = 0.0; - timestretch_rect->property_fill_color_rgba() = color_map[cTimeStretchFill]; - timestretch_rect->property_outline_color_rgba() = color_map[cTimeStretchOutline]; - } - - timestretch_rect->show (); - timestretch_rect->raise_to_top (); - - x1 = start / editor.get_current_zoom(); - x2 = (end - 1) / editor.get_current_zoom(); - y2 = height - 2; - - timestretch_rect->property_x1() = x1; - timestretch_rect->property_y1() = 1.0; - timestretch_rect->property_x2() = x2; - timestretch_rect->property_y2() = y2; -} - -void -AudioTimeAxisView::hide_timestretch () -{ - TimeAxisView::hide_timestretch (); - - if (timestretch_rect) { - timestretch_rect->hide (); - } -} - -void -AudioTimeAxisView::show_selection (TimeSelection& ts) -{ - -#if 0 - /* ignore it if our edit group is not active or if the selection was started - in some other track or edit group (remember that edit_group() == 0 means - that the track is not in an edit group). - */ - - if (((ts.track != this && !is_child (ts.track)) && _route.edit_group() && !_route.edit_group()->is_active()) || - (!(ts.track == this || is_child (ts.track) || (ts.group != 0 && ts.group == _route.edit_group())))) { - hide_selection (); - return; - } -#endif - - TimeAxisView::show_selection (ts); -} - void AudioTimeAxisView::set_state (const XMLNode& node) { @@ -578,153 +218,14 @@ AudioTimeAxisView::set_state (const XMLNode& node) } void -AudioTimeAxisView::set_height (TrackHeight h) -{ - bool height_changed = (height == 0) || (h != height_style); - - TimeAxisView::set_height (h); - - ensure_xml_node (); - - view->set_height ((double) height); - - switch (height_style) { - case Largest: - xml_node->add_property ("track_height", "largest"); - show_name_entry (); - hide_name_label (); - controls_table.show_all(); - break; - case Large: - xml_node->add_property ("track_height", "large"); - show_name_entry (); - hide_name_label (); - controls_table.show_all(); - break; - case Larger: - xml_node->add_property ("track_height", "larger"); - show_name_entry (); - hide_name_label (); - controls_table.show_all(); - break; - case Normal: - xml_node->add_property ("track_height", "normal"); - show_name_entry (); - hide_name_label (); - controls_table.show_all(); - break; - case Smaller: - xml_node->add_property ("track_height", "smaller"); - controls_table.show_all (); - show_name_entry (); - hide_name_label (); - edit_group_button.hide (); - hide_button.hide (); - visual_button.hide (); - size_button.hide (); - automation_button.hide (); - playlist_button.hide (); - break; - case Small: - xml_node->add_property ("track_height", "small"); - controls_table.hide_all (); - controls_table.show (); - hide_name_entry (); - show_name_label (); - name_label.set_text (_route.name()); - break; - } - - if (height_changed) { - /* only emit the signal if the height really changed */ - _route.gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ - } -} - -void -AudioTimeAxisView::select_track_color () -{ - if (RouteUI::choose_color ()) { - - if (view) { - view->apply_color (_color, StreamView::RegionColor); - } - } -} - -void -AudioTimeAxisView::reset_redirect_automation_curves () -{ - for (vector::iterator i = redirect_automation_curves.begin(); i != redirect_automation_curves.end(); ++i) { - (*i)->reset(); - } -} - -void -AudioTimeAxisView::reset_samples_per_unit () -{ - set_samples_per_unit (editor.get_current_zoom()); -} - -void -AudioTimeAxisView::set_samples_per_unit (double spu) -{ - double speed = 1.0; - - if (get_diskstream() != 0) { - speed = get_diskstream()->speed(); - } - - if (view) { - view->set_samples_per_unit (spu * speed); - } - - TimeAxisView::set_samples_per_unit (spu * speed); -} - -void -AudioTimeAxisView::build_display_menu () +AudioTimeAxisView::build_automation_action_menu () { using namespace Menu_Helpers; - /* get the size menu ready */ + RouteTimeAxisView::build_automation_action_menu (); - build_size_menu (); - - /* prepare it */ - - TimeAxisView::build_display_menu (); - - /* now fill it with our stuff */ - - MenuList& items = display_menu->items(); - display_menu->set_name ("ArdourContextMenu"); - - items.push_back (MenuElem (_("Height"), *size_menu)); - items.push_back (MenuElem (_("Color"), mem_fun(*this, &AudioTimeAxisView::select_track_color))); - - - items.push_back (SeparatorElem()); - items.push_back (MenuElem (_("Hide all crossfades"), mem_fun(*this, &AudioTimeAxisView::hide_all_xfades))); - items.push_back (MenuElem (_("Show all crossfades"), mem_fun(*this, &AudioTimeAxisView::show_all_xfades))); - items.push_back (SeparatorElem()); - - build_remote_control_menu (); - items.push_back (MenuElem (_("Remote Control ID"), *remote_control_menu)); - - automation_action_menu = manage (new Menu); MenuList& automation_items = automation_action_menu->items(); - automation_action_menu->set_name ("ArdourContextMenu"); - automation_items.push_back (MenuElem (_("Show all automation"), - mem_fun(*this, &AudioTimeAxisView::show_all_automation))); - - automation_items.push_back (MenuElem (_("Show existing automation"), - mem_fun(*this, &AudioTimeAxisView::show_existing_automation))); - - automation_items.push_back (MenuElem (_("Hide all automation"), - mem_fun(*this, &AudioTimeAxisView::hide_all_automation))); - automation_items.push_back (SeparatorElem()); automation_items.push_back (CheckMenuElem (_("Fader"), @@ -736,11 +237,21 @@ AudioTimeAxisView::build_display_menu () mem_fun(*this, &AudioTimeAxisView::toggle_pan_track))); pan_automation_item = static_cast (&automation_items.back()); pan_automation_item->set_active(show_pan_automation); + +} - automation_items.push_back (MenuElem (_("Plugins"), subplugin_menu)); +void +AudioTimeAxisView::append_extra_display_menu_items () +{ + using namespace Menu_Helpers; - items.push_back (MenuElem (_("Automation"), *automation_action_menu)); + MenuList& items = display_menu->items(); + // crossfade stuff + items.push_back (MenuElem (_("Hide all crossfades"), mem_fun(*this, &AudioTimeAxisView::hide_all_xfades))); + items.push_back (MenuElem (_("Show all crossfades"), mem_fun(*this, &AudioTimeAxisView::show_all_xfades))); + + // waveform menu Menu *waveform_menu = manage(new Menu); MenuList& waveform_items = waveform_menu->items(); waveform_menu->set_name ("ArdourContextMenu"); @@ -760,400 +271,54 @@ AudioTimeAxisView::build_display_menu () rectified_item = static_cast (&waveform_items.back()); items.push_back (MenuElem (_("Waveform"), *waveform_menu)); - - if (is_audio_track()) { - - Menu* alignment_menu = manage (new Menu); - MenuList& alignment_items = alignment_menu->items(); - alignment_menu->set_name ("ArdourContextMenu"); - - RadioMenuItem::Group align_group; - - alignment_items.push_back (RadioMenuElem (align_group, _("Align with existing material"), bind (mem_fun(*this, &AudioTimeAxisView::set_align_style), ExistingMaterial))); - align_existing_item = dynamic_cast(&alignment_items.back()); - if (get_diskstream()->alignment_style() == ExistingMaterial) { - align_existing_item->set_active(); - } - alignment_items.push_back (RadioMenuElem (align_group, _("Align with capture time"), bind (mem_fun(*this, &AudioTimeAxisView::set_align_style), CaptureTime))); - align_capture_item = dynamic_cast(&alignment_items.back()); - if (get_diskstream()->alignment_style() == CaptureTime) { - align_capture_item->set_active(); - } - - items.push_back (MenuElem (_("Alignment"), *alignment_menu)); - - get_diskstream()->AlignmentStyleChanged.connect (mem_fun(*this, &AudioTimeAxisView::align_style_changed)); - } - - items.push_back (SeparatorElem()); - items.push_back (CheckMenuElem (_("Active"), mem_fun(*this, &RouteUI::toggle_route_active))); - route_active_menu_item = dynamic_cast (&items.back()); - route_active_menu_item->set_active (_route.active()); - - items.push_back (SeparatorElem()); - items.push_back (MenuElem (_("Remove"), mem_fun(*this, &RouteUI::remove_this_route))); - -} - -void -AudioTimeAxisView::align_style_changed () -{ - switch (get_diskstream()->alignment_style()) { - case ExistingMaterial: - if (!align_existing_item->get_active()) { - align_existing_item->set_active(); - } - break; - case CaptureTime: - if (!align_capture_item->get_active()) { - align_capture_item->set_active(); - } - break; - } -} - -void -AudioTimeAxisView::set_align_style (AlignStyle style) -{ - get_diskstream()->set_align_style (style); -} - -void -AudioTimeAxisView::rename_current_playlist () -{ - ArdourPrompter prompter (true); - string name; - - AudioPlaylist *pl; - AudioDiskstream *ds; - - if (((ds = get_diskstream()) == 0) || ds->destructive() || ((pl = ds->playlist()) == 0)) { - return; - } - - prompter.set_prompt (_("Name for playlist")); - prompter.set_initial_text (pl->name()); - prompter.add_button (_("Rename"), Gtk::RESPONSE_ACCEPT); - prompter.set_response_sensitive (Gtk::RESPONSE_ACCEPT, false); - - switch (prompter.run ()) { - case Gtk::RESPONSE_ACCEPT: - prompter.get_result (name); - if (name.length()) { - pl->set_name (name); - } - break; - - default: - break; - } -} - -void -AudioTimeAxisView::use_copy_playlist (bool prompt) -{ - AudioPlaylist *pl; - AudioDiskstream *ds; - string name; - - if (((ds = get_diskstream()) == 0) || ds->destructive() || ((pl = ds->playlist()) == 0)) { - return; - } - - name = Playlist::bump_name (pl->name(), _session); - - if (prompt) { - - ArdourPrompter prompter (true); - - prompter.set_prompt (_("Name for Playlist")); - prompter.set_initial_text (name); - prompter.add_button (Gtk::Stock::NEW, Gtk::RESPONSE_ACCEPT); - prompter.set_response_sensitive (Gtk::RESPONSE_ACCEPT, false); - prompter.show_all (); - - switch (prompter.run ()) { - case Gtk::RESPONSE_ACCEPT: - prompter.get_result (name); - break; - - default: - return; - } - } - - if (name.length()) { - ds->use_copy_playlist (); - pl = ds->playlist(); - pl->set_name (name); - } -} - -void -AudioTimeAxisView::use_new_playlist (bool prompt) -{ - AudioPlaylist *pl; - AudioDiskstream *ds; - string name; - - if (((ds = get_diskstream()) == 0) || ds->destructive() || ((pl = ds->playlist()) == 0)) { - return; - } - - name = Playlist::bump_name (pl->name(), _session); - - if (prompt) { - - ArdourPrompter prompter (true); - - prompter.set_prompt (_("Name for Playlist")); - prompter.set_initial_text (name); - prompter.add_button (Gtk::Stock::NEW, Gtk::RESPONSE_ACCEPT); - prompter.set_response_sensitive (Gtk::RESPONSE_ACCEPT, false); - - switch (prompter.run ()) { - case Gtk::RESPONSE_ACCEPT: - prompter.get_result (name); - break; - - default: - return; - } - } - - if (name.length()) { - ds->use_new_playlist (); - pl = ds->playlist(); - pl->set_name (name); - } -} - -void -AudioTimeAxisView::clear_playlist () -{ - AudioPlaylist *pl; - AudioDiskstream *ds; - - if ((ds = get_diskstream()) != 0) { - if ((pl = ds->playlist()) != 0) { - editor.clear_playlist (*pl); - } - } } void AudioTimeAxisView::toggle_waveforms () { - if (view && waveform_item && !ignore_toggle) { - view->set_show_waveforms (waveform_item->get_active()); + AudioStreamView* asv = audio_view(); + assert(asv); + + if (asv && waveform_item && !ignore_toggle) { + asv->set_show_waveforms (waveform_item->get_active()); } } void AudioTimeAxisView::set_show_waveforms (bool yn) { + AudioStreamView* asv = audio_view(); + assert(asv); + if (waveform_item) { waveform_item->set_active (yn); } else { - view->set_show_waveforms (yn); + asv->set_show_waveforms (yn); } } void AudioTimeAxisView::set_show_waveforms_recording (bool yn) { - if (view) { - view->set_show_waveforms_recording (yn); + AudioStreamView* asv = audio_view(); + + if (asv) { + asv->set_show_waveforms_recording (yn); } } void AudioTimeAxisView::set_waveform_shape (WaveformShape shape) { - if (view) { - view->set_waveform_shape (shape); - } -} + AudioStreamView* asv = audio_view(); -void -AudioTimeAxisView::speed_changed () -{ - Gtkmm2ext::UI::instance()->call_slot (mem_fun(*this, &AudioTimeAxisView::reset_samples_per_unit)); -} - -void -AudioTimeAxisView::diskstream_changed (void *src) -{ - Gtkmm2ext::UI::instance()->call_slot (mem_fun(*this, &AudioTimeAxisView::update_diskstream_display)); -} - -void -AudioTimeAxisView::update_diskstream_display () -{ - AudioDiskstream *ds; - - if ((ds = get_diskstream()) != 0) { - set_playlist (ds->playlist ()); + if (asv) { + asv->set_waveform_shape (shape); } map_frozen (); } -void -AudioTimeAxisView::selection_click (GdkEventButton* ev) -{ - PublicEditor::TrackViewList* tracks = editor.get_valid_views (this, _route.edit_group()); - - switch (Keyboard::selection_type (ev->state)) { - case Selection::Toggle: - /* XXX this is not right */ - editor.get_selection().add (*tracks); - break; - - case Selection::Set: - editor.get_selection().set (*tracks); - break; - - case Selection::Extend: - /* not defined yet */ - break; - } - - delete tracks; -} - -void -AudioTimeAxisView::set_selected_regionviews (AudioRegionSelection& regions) -{ - if (view) { - view->set_selected_regionviews (regions); - } -} - -void -AudioTimeAxisView::set_selected_points (PointSelection& points) -{ - for (vector::iterator i = children.begin(); i != children.end(); ++i) { - (*i)->set_selected_points (points); - } -} - -void -AudioTimeAxisView::get_selectables (jack_nframes_t start, jack_nframes_t end, double top, double bot, list& results) -{ - double speed = 1.0; - - if (get_diskstream() != 0) { - speed = get_diskstream()->speed(); - } - - jack_nframes_t start_adjusted = session_frame_to_track_frame(start, speed); - jack_nframes_t end_adjusted = session_frame_to_track_frame(end, speed); - - if (view && ((top < 0.0 && bot < 0.0)) || touched (top, bot)) { - view->get_selectables (start_adjusted, end_adjusted, results); - } - - /* pick up visible automation tracks */ - - for (vector::iterator i = children.begin(); i != children.end(); ++i) { - if (!(*i)->hidden()) { - (*i)->get_selectables (start_adjusted, end_adjusted, top, bot, results); - } - } -} - -void -AudioTimeAxisView::get_inverted_selectables (Selection& sel, list& results) -{ - if (view) { - view->get_inverted_selectables (sel, results); - } - - for (vector::iterator i = children.begin(); i != children.end(); ++i) { - if (!(*i)->hidden()) { - (*i)->get_inverted_selectables (sel, results); - } - } - - return; -} - -RouteGroup* -AudioTimeAxisView::edit_group() const -{ - return _route.edit_group(); -} - -string -AudioTimeAxisView::name() const -{ - return _route.name(); -} - -Playlist * -AudioTimeAxisView::playlist () const -{ - AudioDiskstream *ds; - - if ((ds = get_diskstream()) != 0) { - return ds->playlist(); - } else { - return 0; - } -} - -void -AudioTimeAxisView::name_entry_changed () -{ - string x; - - x = name_entry.get_text (); - - if (x == _route.name()) { - return; - } - - if (x.length() == 0) { - name_entry.set_text (_route.name()); - return; - } - - strip_whitespace_edges(x); - - if (_session.route_name_unique (x)) { - _route.set_name (x, this); - } else { - ARDOUR_UI::instance()->popup_error (_("a track already exists with that name")); - name_entry.set_text (_route.name()); - } -} - -void -AudioTimeAxisView::visual_click () -{ - popup_display_menu (0); -} - -void -AudioTimeAxisView::hide_click () -{ - editor.hide_track_in_display (*this); -} - -Region* -AudioTimeAxisView::find_next_region (jack_nframes_t pos, RegionPoint point, int32_t dir) -{ - AudioDiskstream *stream; - AudioPlaylist *playlist; - - if ((stream = get_diskstream()) != 0 && (playlist = stream->playlist()) != 0) { - return playlist->find_next_region (pos, point, dir); - } - - return 0; -} - void AudioTimeAxisView::add_gain_automation_child () { @@ -1166,13 +331,13 @@ AudioTimeAxisView::add_gain_automation_child () *this, parent_canvas, _("gain"), - _route.gain_automation_curve()); + _route->gain_automation_curve()); line = new AutomationGainLine ("automation gain", _session, *gain_track, *gain_track->canvas_display, - _route.gain_automation_curve()); + _route->gain_automation_curve()); line->set_line_color (color_map[cAutomationLine]); @@ -1241,11 +406,11 @@ AudioTimeAxisView::update_pans () /* we don't draw lines for "greater than stereo" panning. */ - if (_route.n_outputs() > 2) { + if (_route->n_outputs() > 2) { return; } - for (p = _route.panner().begin(); p != _route.panner().end(); ++p) { + for (p = _route->panner().begin(); p != _route->panner().end(); ++p) { AutomationLine* line; @@ -1253,7 +418,7 @@ AudioTimeAxisView::update_pans () *pan_track->canvas_display, (*p)->automation()); - if (p == _route.panner().begin()) { + if (p == _route->panner().begin()) { /* first line is a nice orange */ line->set_line_color (color_map[cLeftPanAutomationLine]); } else { @@ -1285,7 +450,7 @@ AudioTimeAxisView::toggle_gain_track () /* now trigger a redisplay */ if (!no_redraw) { - _route.gui_changed (X_("track_height"), (void *) 0); /* EMIT_SIGNAL */ + _route->gui_changed (X_("track_height"), (void *) 0); /* EMIT_SIGNAL */ } } } @@ -1299,7 +464,7 @@ AudioTimeAxisView::gain_hidden () gain_automation_item->set_active (false); } - _route.gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ + _route->gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ } void @@ -1321,7 +486,7 @@ AudioTimeAxisView::toggle_pan_track () /* now trigger a redisplay */ if (!no_redraw) { - _route.gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ + _route->gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ } } } @@ -1335,322 +500,7 @@ AudioTimeAxisView::pan_hidden () pan_automation_item->set_active (false); } - _route.gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ -} - -AudioTimeAxisView::RedirectAutomationInfo::~RedirectAutomationInfo () -{ - for (vector::iterator i = lines.begin(); i != lines.end(); ++i) { - delete *i; - } -} - - -AudioTimeAxisView::RedirectAutomationNode::~RedirectAutomationNode () -{ - parent.remove_ran (this); - - if (view) { - delete view; - } -} - -void -AudioTimeAxisView::remove_ran (RedirectAutomationNode* ran) -{ - if (ran->view) { - remove_child (ran->view); - } -} - -AudioTimeAxisView::RedirectAutomationNode* -AudioTimeAxisView::find_redirect_automation_node (Redirect *redirect, uint32_t what) -{ - for (list::iterator i = redirect_automation.begin(); i != redirect_automation.end(); ++i) { - - if ((*i)->redirect == redirect) { - - for (vector::iterator ii = (*i)->lines.begin(); ii != (*i)->lines.end(); ++ii) { - if ((*ii)->what == what) { - return *ii; - } - } - } - } - - return 0; -} - -static string -legalize_for_xml_node (string str) -{ - string::size_type pos; - string legal_chars = "abcdefghijklmnopqrtsuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789_+=:"; - string legal; - - legal = str; - pos = 0; - - while ((pos = legal.find_first_not_of (legal_chars, pos)) != string::npos) { - legal.replace (pos, 1, "_"); - pos += 1; - } - - return legal; -} - - -void -AudioTimeAxisView::add_redirect_automation_curve (Redirect *redirect, uint32_t what) -{ - RedirectAutomationLine* ral; - string name; - RedirectAutomationNode* ran; - - if ((ran = find_redirect_automation_node (redirect, what)) == 0) { - fatal << _("programming error: ") - << string_compose (X_("redirect automation curve for %1:%2 not registered with audio track!"), - redirect->name(), what) - << endmsg; - /*NOTREACHED*/ - return; - } - - if (ran->view) { - return; - } - - name = redirect->describe_parameter (what); - - /* create a string that is a legal XML node name that can be used to refer to this redirect+port combination */ - - char state_name[256]; - snprintf (state_name, sizeof (state_name), "Redirect-%s-%" PRIu32, legalize_for_xml_node (redirect->name()).c_str(), what); - - ran->view = new RedirectAutomationTimeAxisView (_session, _route, editor, *this, parent_canvas, name, what, *redirect, state_name); - - ral = new RedirectAutomationLine (name, - *redirect, what, _session, *ran->view, - *ran->view->canvas_display, redirect->automation_list (what)); - - ral->set_line_color (color_map[cRedirectAutomationLine]); - ral->queue_reset (); - - ran->view->add_line (*ral); - - ran->view->Hiding.connect (bind (mem_fun(*this, &AudioTimeAxisView::redirect_automation_track_hidden), ran, redirect)); - - if (!ran->view->marked_for_display()) { - ran->view->hide (); - } else { - ran->menu_item->set_active (true); - } - - add_child (ran->view); - - view->foreach_regionview (bind (mem_fun(*this, &AudioTimeAxisView::add_ghost_to_redirect), ran->view)); - - redirect->mark_automation_visible (what, true); -} - -void -AudioTimeAxisView::redirect_automation_track_hidden (AudioTimeAxisView::RedirectAutomationNode* ran, Redirect* r) -{ - if (!_hidden) { - ran->menu_item->set_active (false); - } - - r->mark_automation_visible (ran->what, false); - - _route.gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ -} - -void -AudioTimeAxisView::add_existing_redirect_automation_curves (Redirect *redirect) -{ - set s; - RedirectAutomationLine *ral; - - redirect->what_has_visible_automation (s); - - for (set::iterator i = s.begin(); i != s.end(); ++i) { - - if ((ral = find_redirect_automation_curve (redirect, *i)) != 0) { - ral->queue_reset (); - } else { - add_redirect_automation_curve (redirect, (*i)); - } - } -} - -void -AudioTimeAxisView::add_redirect_to_subplugin_menu (Redirect* r) -{ - using namespace Menu_Helpers; - RedirectAutomationInfo *rai; - list::iterator x; - - const std::set& automatable = r->what_can_be_automated (); - std::set has_visible_automation; - - r->what_has_visible_automation(has_visible_automation); - - if (automatable.empty()) { - return; - } - - for (x = redirect_automation.begin(); x != redirect_automation.end(); ++x) { - if ((*x)->redirect == r) { - break; - } - } - - if (x == redirect_automation.end()) { - - rai = new RedirectAutomationInfo (r); - redirect_automation.push_back (rai); - - } else { - - rai = *x; - - } - - /* any older menu was deleted at the top of redirects_changed() - when we cleared the subplugin menu. - */ - - rai->menu = manage (new Menu); - MenuList& items = rai->menu->items(); - rai->menu->set_name ("ArdourContextMenu"); - - items.clear (); - - for (std::set::const_iterator i = automatable.begin(); i != automatable.end(); ++i) { - - RedirectAutomationNode* ran; - CheckMenuItem* mitem; - - string name = r->describe_parameter (*i); - - items.push_back (CheckMenuElem (name)); - mitem = dynamic_cast (&items.back()); - - if (has_visible_automation.find((*i)) != has_visible_automation.end()) { - mitem->set_active(true); - } - - if ((ran = find_redirect_automation_node (r, *i)) == 0) { - - /* new item */ - - ran = new RedirectAutomationNode (*i, mitem, *this); - - rai->lines.push_back (ran); - - } else { - - ran->menu_item = mitem; - - } - - mitem->signal_toggled().connect (bind (mem_fun(*this, &AudioTimeAxisView::redirect_menu_item_toggled), rai, ran)); - } - - /* add the menu for this redirect, because the subplugin - menu is always cleared at the top of redirects_changed(). - this is the result of some poor design in gtkmm and/or - GTK+. - */ - - subplugin_menu.items().push_back (MenuElem (r->name(), *rai->menu)); - rai->valid = true; -} - -void -AudioTimeAxisView::redirect_menu_item_toggled (AudioTimeAxisView::RedirectAutomationInfo* rai, - AudioTimeAxisView::RedirectAutomationNode* ran) -{ - bool showit = ran->menu_item->get_active(); - bool redraw = false; - - if (ran->view == 0 && showit) { - add_redirect_automation_curve (rai->redirect, ran->what); - redraw = true; - } - - if (showit != ran->view->marked_for_display()) { - - if (showit) { - ran->view->set_marked_for_display (true); - ran->view->canvas_display->show(); - } else { - rai->redirect->mark_automation_visible (ran->what, true); - ran->view->set_marked_for_display (false); - ran->view->hide (); - } - - redraw = true; - - } - - if (redraw && !no_redraw) { - - /* now trigger a redisplay */ - - _route.gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ - - } -} - -void -AudioTimeAxisView::redirects_changed (void *src) -{ - using namespace Menu_Helpers; - - for (list::iterator i = redirect_automation.begin(); i != redirect_automation.end(); ++i) { - (*i)->valid = false; - } - - subplugin_menu.items().clear (); - - _route.foreach_redirect (this, &AudioTimeAxisView::add_redirect_to_subplugin_menu); - _route.foreach_redirect (this, &AudioTimeAxisView::add_existing_redirect_automation_curves); - - for (list::iterator i = redirect_automation.begin(); i != redirect_automation.end(); ) { - - list::iterator tmp; - - tmp = i; - ++tmp; - - if (!(*i)->valid) { - - delete *i; - redirect_automation.erase (i); - - } - - i = tmp; - } - - /* change in visibility was possible */ - - _route.gui_changed ("track_height", this); -} - -RedirectAutomationLine * -AudioTimeAxisView::find_redirect_automation_curve (Redirect *redirect, uint32_t what) -{ - RedirectAutomationNode* ran; - - if ((ran = find_redirect_automation_node (redirect, what)) != 0) { - if (ran->view) { - return dynamic_cast (ran->view->lines.front()); - } - } - - return 0; + _route->gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ } void @@ -1661,19 +511,11 @@ AudioTimeAxisView::show_all_automation () pan_automation_item->set_active (true); gain_automation_item->set_active (true); - for (list::iterator i = redirect_automation.begin(); i != redirect_automation.end(); ++i) { - for (vector::iterator ii = (*i)->lines.begin(); ii != (*i)->lines.end(); ++ii) { - if ((*ii)->view == 0) { - add_redirect_automation_curve ((*i)->redirect, (*ii)->what); - } - - (*ii)->menu_item->set_active (true); - } - } + RouteTimeAxisView::show_all_automation (); no_redraw = false; - _route.gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ + _route->gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ } void @@ -1684,17 +526,11 @@ AudioTimeAxisView::show_existing_automation () pan_automation_item->set_active (true); gain_automation_item->set_active (true); - for (list::iterator i = redirect_automation.begin(); i != redirect_automation.end(); ++i) { - for (vector::iterator ii = (*i)->lines.begin(); ii != (*i)->lines.end(); ++ii) { - if ((*ii)->view != 0) { - (*ii)->menu_item->set_active (true); - } - } - } + RouteTimeAxisView::show_existing_automation (); no_redraw = false; - _route.gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ + _route->gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ } void @@ -1705,236 +541,61 @@ AudioTimeAxisView::hide_all_automation () pan_automation_item->set_active (false); gain_automation_item->set_active (false); - for (list::iterator i = redirect_automation.begin(); i != redirect_automation.end(); ++i) { - for (vector::iterator ii = (*i)->lines.begin(); ii != (*i)->lines.end(); ++ii) { - (*ii)->menu_item->set_active (false); - } - } + RouteTimeAxisView::hide_all_automation(); no_redraw = false; - _route.gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ -} - -bool -AudioTimeAxisView::cut_copy_clear (Selection& selection, CutCopyOp op) -{ - Playlist* what_we_got; - AudioDiskstream* ds = get_diskstream(); - Playlist* playlist; - bool ret = false; - - if (ds == 0) { - /* route is a bus, not a track */ - return false; - } - - playlist = ds->playlist(); - - - TimeSelection time (selection.time); - float speed = ds->speed(); - if (speed != 1.0f) { - for (TimeSelection::iterator i = time.begin(); i != time.end(); ++i) { - (*i).start = session_frame_to_track_frame((*i).start, speed); - (*i).end = session_frame_to_track_frame((*i).end, speed); - } - } - - XMLNode &before = playlist->get_state(); - switch (op) { - case Cut: - if ((what_we_got = playlist->cut (time)) != 0) { - editor.get_cut_buffer().add (what_we_got); - XMLNode &after = playlist->get_state(); - _session.add_command (new MementoCommand(*playlist, before, after)); - ret = true; - } - break; - case Copy: - if ((what_we_got = playlist->copy (time)) != 0) { - editor.get_cut_buffer().add (what_we_got); - } - break; - - case Clear: - if ((what_we_got = playlist->cut (time)) != 0) { - XMLNode &after = playlist->get_state(); - _session.add_command(new MementoCommand(*playlist, before, after)); - what_we_got->unref (); - ret = true; - } - break; - } - - return ret; -} - -bool -AudioTimeAxisView::paste (jack_nframes_t pos, float times, Selection& selection, size_t nth) -{ - if (!is_audio_track()) { - return false; - } - - Playlist* playlist = get_diskstream()->playlist(); - PlaylistSelection::iterator p; - - for (p = selection.playlists.begin(); p != selection.playlists.end() && nth; ++p, --nth); - - if (p == selection.playlists.end()) { - return false; - } - - if (get_diskstream()->speed() != 1.0f) - pos = session_frame_to_track_frame(pos, get_diskstream()->speed() ); - - XMLNode &before = playlist->get_state(); - playlist->paste (**p, pos, times); - _session.add_command(new MementoCommand(*playlist, before, - playlist->get_state())); - - return true; -} - -void -AudioTimeAxisView::region_view_added (AudioRegionView* arv) -{ - for (vector::iterator i = children.begin(); i != children.end(); ++i) { - AutomationTimeAxisView* atv; - - if ((atv = dynamic_cast (*i)) != 0) { - arv->add_ghost (*atv); - } - } -} - -void -AudioTimeAxisView::add_ghost_to_redirect (AudioRegionView* arv, AutomationTimeAxisView* atv) -{ - arv->add_ghost (*atv); -} - -list -AudioTimeAxisView::get_child_list() -{ - - listredirect_children; - - for (vector::iterator i = children.begin(); i != children.end(); ++i) { - if (!(*i)->hidden()) { - redirect_children.push_back(*i); - } - } - return redirect_children; -} - - -void -AudioTimeAxisView::build_playlist_menu (Gtk::Menu * menu) -{ - using namespace Menu_Helpers; - - if (!menu || !is_audio_track()) { - return; - } - - MenuList& playlist_items = menu->items(); - menu->set_name ("ArdourContextMenu"); - playlist_items.clear(); - - if (playlist_menu) { - delete playlist_menu; - } - playlist_menu = new Menu; - playlist_menu->set_name ("ArdourContextMenu"); - - playlist_items.push_back (MenuElem (string_compose (_("Current: %1"), get_diskstream()->playlist()->name()))); - playlist_items.push_back (SeparatorElem()); - - playlist_items.push_back (MenuElem (_("Rename"), mem_fun(*this, &AudioTimeAxisView::rename_current_playlist))); - playlist_items.push_back (SeparatorElem()); - - playlist_items.push_back (MenuElem (_("New"), mem_fun(editor, &PublicEditor::new_playlists))); - playlist_items.push_back (MenuElem (_("New Copy"), mem_fun(editor, &PublicEditor::copy_playlists))); - playlist_items.push_back (SeparatorElem()); - playlist_items.push_back (MenuElem (_("Clear Current"), mem_fun(editor, &PublicEditor::clear_playlists))); - playlist_items.push_back (SeparatorElem()); - playlist_items.push_back (MenuElem(_("Select"), mem_fun(*this, &AudioTimeAxisView::show_playlist_selector))); - -} - -void -AudioTimeAxisView::show_playlist_selector () -{ - editor.playlist_selector().show_for (this); -} - - -void -AudioTimeAxisView::map_frozen () -{ - if (!is_audio_track()) { - return; - } - - ENSURE_GUI_THREAD (mem_fun(*this, &AudioTimeAxisView::map_frozen)); - - - switch (audio_track()->freeze_state()) { - case AudioTrack::Frozen: - playlist_button.set_sensitive (false); - rec_enable_button->set_sensitive (false); - break; - default: - playlist_button.set_sensitive (true); - rec_enable_button->set_sensitive (true); - break; - } + _route->gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ } void AudioTimeAxisView::show_all_xfades () { - if (view) { - view->show_all_xfades (); + AudioStreamView* asv = audio_view(); + + if (asv) { + asv->show_all_xfades (); } } void AudioTimeAxisView::hide_all_xfades () { - if (view) { - view->hide_all_xfades (); + AudioStreamView* asv = audio_view(); + + if (asv) { + asv->hide_all_xfades (); } } void AudioTimeAxisView::hide_dependent_views (TimeAxisViewItem& tavi) { + AudioStreamView* asv = audio_view(); AudioRegionView* rv; - if (view && (rv = dynamic_cast(&tavi)) != 0) { - view->hide_xfades_involving (*rv); + if (asv && (rv = dynamic_cast(&tavi)) != 0) { + asv->hide_xfades_involving (*rv); } } void AudioTimeAxisView::reveal_dependent_views (TimeAxisViewItem& tavi) { + AudioStreamView* asv = audio_view(); AudioRegionView* rv; - if (view && (rv = dynamic_cast(&tavi)) != 0) { - view->reveal_xfades_involving (*rv); + if (asv && (rv = dynamic_cast(&tavi)) != 0) { + asv->reveal_xfades_involving (*rv); } } void AudioTimeAxisView::route_active_changed () { - RouteUI::route_active_changed (); + RouteTimeAxisView::route_active_changed (); if (is_audio_track()) { - if (_route.active()) { + if (_route->active()) { controls_ebox.set_name ("AudioTrackControlsBaseUnselected"); controls_base_selected_name = "AudioTrackControlsBaseSelected"; controls_base_unselected_name = "AudioTrackControlsBaseUnselected"; @@ -1944,7 +605,7 @@ AudioTimeAxisView::route_active_changed () controls_base_unselected_name = "AudioTrackControlsBaseInactiveUnselected"; } } else { - if (_route.active()) { + if (_route->active()) { controls_ebox.set_name ("BusControlsBaseUnselected"); controls_base_selected_name = "BusControlsBaseSelected"; controls_base_unselected_name = "BusControlsBaseUnselected"; @@ -1962,24 +623,3 @@ AudioTimeAxisView::get_child_xml_node (const string & childname) return RouteUI::get_child_xml_node (childname); } -void -AudioTimeAxisView::color_handler (ColorID id, uint32_t val) -{ - switch (id) { - case cTimeStretchOutline: - timestretch_rect->property_outline_color_rgba() = val; - break; - case cTimeStretchFill: - timestretch_rect->property_fill_color_rgba() = val; - break; - default: - break; - } -} - -bool -AudioTimeAxisView::select_me (GdkEventButton* ev) -{ - editor.get_selection().add (this); - return false; -} diff --git a/gtk2_ardour/audio_time_axis.h b/gtk2_ardour/audio_time_axis.h index b319d0ea99..2162771285 100644 --- a/gtk2_ardour/audio_time_axis.h +++ b/gtk2_ardour/audio_time_axis.h @@ -1,5 +1,5 @@ /* - Copyright (C) 2000 Paul Davis + Copyright (C) 2000-2006 Paul Davis This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -18,8 +18,8 @@ $Id$ */ -#ifndef __ardour_trackview_h__ -#define __ardour_trackview_h__ +#ifndef __ardour_audio_time_axis_h__ +#define __ardour_audio_time_axis_h__ #include #include @@ -33,19 +33,14 @@ #include #include -#include #include "ardour_dialog.h" #include "route_ui.h" #include "enums.h" -#include "time_axis_view.h" +#include "route_time_axis.h" #include "canvas.h" #include "color.h" -namespace ALSA { - class MultiChannelDevice; -} - namespace ARDOUR { class Session; class AudioDiskstream; @@ -56,247 +51,58 @@ namespace ARDOUR { class AudioPlaylist; } -namespace LADSPA { - class Manager; - class Plugin; -} - class PublicEditor; class AudioThing; -class StreamView; +class AudioStreamView; class Selection; class Selectable; +class RegionView; class AudioRegionView; class AutomationLine; class AutomationGainLine; class AutomationPanLine; -class RedirectAutomationLine; class TimeSelection; class AutomationTimeAxisView; -class AudioTimeAxisView : public RouteUI, public TimeAxisView +class AudioTimeAxisView : public RouteTimeAxisView { public: - AudioTimeAxisView (PublicEditor&, ARDOUR::Session&, ARDOUR::Route&, ArdourCanvas::Canvas& canvas); + AudioTimeAxisView (PublicEditor&, ARDOUR::Session&, boost::shared_ptr, ArdourCanvas::Canvas& canvas); virtual ~AudioTimeAxisView (); + + AudioStreamView* audio_view(); - void show_selection (TimeSelection&); - void automation_control_point_changed (ARDOUR::AutomationType); - - void set_samples_per_unit (double); - void set_height (TimeAxisView::TrackHeight); void set_show_waveforms (bool yn); void set_show_waveforms_recording (bool yn); - void show_timestretch (jack_nframes_t start, jack_nframes_t end); - void hide_timestretch (); - void selection_click (GdkEventButton*); - void set_selected_regionviews (AudioRegionSelection&); - void set_selected_points (PointSelection&); - void get_selectables (jack_nframes_t start, jack_nframes_t end, double top, double bot, list&); - void get_inverted_selectables (Selection&, list&); void show_all_xfades (); void hide_all_xfades (); void hide_dependent_views (TimeAxisViewItem&); void reveal_dependent_views (TimeAxisViewItem&); - ARDOUR::Region* find_next_region (jack_nframes_t pos, ARDOUR::RegionPoint, int32_t dir); - - string name() const; - - ARDOUR::RouteGroup* edit_group() const; - - void build_playlist_menu (Gtk::Menu *); - ARDOUR::Playlist* playlist() const; - - /* overridden from parent to store display state */ + /* Overridden from parent to store display state */ guint32 show_at (double y, int& nth, Gtk::VBox *parent); void hide (); - /* need accessors/mutators */ - - StreamView *view; - - /* editing operations */ - - bool cut_copy_clear (Selection&, Editing::CutCopyOp); - bool paste (jack_nframes_t, float times, Selection&, size_t nth); - - listget_child_list(); - void set_state (const XMLNode&); XMLNode* get_child_xml_node (const string & childname); - /* the editor calls these when mapping an operation across multiple tracks */ - - void use_new_playlist (bool prompt); - void use_copy_playlist (bool prompt); - void clear_playlist (); - private: - friend class StreamView; + friend class AudioStreamView; friend class AudioRegionView; - - ArdourCanvas::Canvas& parent_canvas; - - bool no_redraw; - - AutomationTimeAxisView *gain_track; - AutomationTimeAxisView *pan_track; - - void update_automation_view (ARDOUR::AutomationType); - void reset_redirect_automation_curves (); - - Gtk::HBox other_button_hbox; - - Gtk::Table button_table; - - Gtk::Button redirect_button; - Gtk::Button edit_group_button; - Gtk::Button playlist_button; - Gtk::Button size_button; - Gtk::Button automation_button; - Gtk::Button hide_button; - Gtk::Button visual_button; - + void route_active_changed (); - void diskstream_changed (void *src); - void update_diskstream_display (); + void build_automation_action_menu (); + void append_extra_display_menu_items (); - gint edit_click (GdkEventButton *); - - // variables to get the context menu - // automation buttons correctly initialized - bool show_gain_automation; - bool show_pan_automation; - - void build_redirect_window (); - void redirect_click (); - void redirect_add (); - void redirect_remove (); - void redirect_edit (); - void redirect_relist (); - void redirect_row_selected (gint row, gint col, GdkEvent *ev); - void add_to_redirect_display (ARDOUR::Redirect *); - void redirects_changed (void *); - - sigc::connection modified_connection; - sigc::connection state_changed_connection; - - void take_name_changed (void *); - void route_name_changed (void *); - void name_entry_changed (); - - void on_area_realize (); - - virtual void label_view (); - - Gtk::Menu edit_group_menu; - - void add_edit_group_menu_item (ARDOUR::RouteGroup *, Gtk::RadioMenuItem::Group*); - void set_edit_group_from_menu (ARDOUR::RouteGroup *); - - void reset_samples_per_unit (); - - void select_track_color(); - - virtual void build_display_menu (); - - Gtk::CheckMenuItem* waveform_item; - Gtk::RadioMenuItem* traditional_item; - Gtk::RadioMenuItem* rectified_item; - - Gtk::RadioMenuItem* align_existing_item; - Gtk::RadioMenuItem* align_capture_item; - - void align_style_changed (); - void set_align_style (ARDOUR::AlignStyle); - void toggle_show_waveforms (); - void set_waveform_shape (WaveformShape); void toggle_waveforms (); - Gtk::Menu *playlist_menu; - Gtk::Menu *playlist_action_menu; - Gtk::MenuItem *playlist_item; - - /* playlist */ - - void set_playlist (ARDOUR::AudioPlaylist *); - void playlist_click (); - void show_playlist_selector (); - - void playlist_changed (); - void playlist_state_changed (ARDOUR::Change); - void playlist_modified (); - - void add_playlist_to_playlist_menu (ARDOUR::Playlist*); - void rename_current_playlist (); - - /* automation stuff */ - - Gtk::Menu* automation_action_menu; - Gtk::CheckMenuItem* gain_automation_item; - Gtk::CheckMenuItem* pan_automation_item; - - void automation_click (); - void clear_automation (); - void hide_all_automation (); void show_all_automation (); void show_existing_automation (); + void hide_all_automation (); - struct RedirectAutomationNode { - uint32_t what; - Gtk::CheckMenuItem* menu_item; - AutomationTimeAxisView* view; - AudioTimeAxisView& parent; - - RedirectAutomationNode (uint32_t w, Gtk::CheckMenuItem* mitem, AudioTimeAxisView& p) - : what (w), menu_item (mitem), view (0), parent (p) {} - - ~RedirectAutomationNode (); - }; - - struct RedirectAutomationInfo { - ARDOUR::Redirect* redirect; - bool valid; - Gtk::Menu* menu; - vector lines; - - RedirectAutomationInfo (ARDOUR::Redirect* r) - : redirect (r), valid (true) {} - - ~RedirectAutomationInfo (); - }; - - list redirect_automation; - RedirectAutomationNode* find_redirect_automation_node (ARDOUR::Redirect *redirect, uint32_t what); - - Gtk::Menu subplugin_menu; - void add_redirect_to_subplugin_menu (ARDOUR::Redirect *); - - void remove_ran (RedirectAutomationNode* ran); - - void redirect_menu_item_toggled (AudioTimeAxisView::RedirectAutomationInfo*, - AudioTimeAxisView::RedirectAutomationNode*); - void redirect_automation_track_hidden (RedirectAutomationNode*, ARDOUR::Redirect*); - - vector redirect_automation_curves; - RedirectAutomationLine *find_redirect_automation_curve (ARDOUR::Redirect*,uint32_t); - void add_redirect_automation_curve (ARDOUR::Redirect*, uint32_t); - void add_existing_redirect_automation_curves (ARDOUR::Redirect*); - - ArdourCanvas::SimpleRect *timestretch_rect; - - void timestretch (jack_nframes_t start, jack_nframes_t end); - - void visual_click (); - void hide_click (); - gint when_displayed (GdkEventAny*); - - void speed_changed (); - void add_gain_automation_child (); void add_pan_automation_child (); void add_parameter_automation_child (); @@ -309,14 +115,19 @@ class AudioTimeAxisView : public RouteUI, public TimeAxisView void update_pans (); - void region_view_added (AudioRegionView*); - void add_ghost_to_redirect (AudioRegionView*, AutomationTimeAxisView*); + AutomationTimeAxisView* gain_track; + AutomationTimeAxisView* pan_track; - void map_frozen (); - - void color_handler (ColorID, uint32_t); - bool select_me (GdkEventButton*); + // Set from XML so context menu automation buttons can be correctly initialized + bool show_gain_automation; + bool show_pan_automation; + + Gtk::CheckMenuItem* waveform_item; + Gtk::RadioMenuItem* traditional_item; + Gtk::RadioMenuItem* rectified_item; + Gtk::CheckMenuItem* gain_automation_item; + Gtk::CheckMenuItem* pan_automation_item; }; -#endif /* __ardour_trackview_h__ */ +#endif /* __ardour_audio_time_axis_h__ */ diff --git a/gtk2_ardour/automation_time_axis.cc b/gtk2_ardour/automation_time_axis.cc index 080a440bc9..6e2a93889f 100644 --- a/gtk2_ardour/automation_time_axis.cc +++ b/gtk2_ardour/automation_time_axis.cc @@ -21,7 +21,7 @@ using namespace PBD; using namespace Gtk; using namespace Editing; -AutomationTimeAxisView::AutomationTimeAxisView (Session& s, Route& r, PublicEditor& e, TimeAxisView& rent, +AutomationTimeAxisView::AutomationTimeAxisView (Session& s, boost::shared_ptr r, PublicEditor& e, TimeAxisView& rent, ArdourCanvas::Canvas& canvas, const string & nom, const string & state_name, const string & nomparent) @@ -41,6 +41,7 @@ AutomationTimeAxisView::AutomationTimeAxisView (Session& s, Route& r, PublicEdit auto_write_item = 0; auto_play_item = 0; ignore_state_request = false; + first_call_to_set_height = true; // base_rect = gnome_canvas_item_new (GNOME_CANVAS_GROUP(canvas_display), // gnome_canvas_simplerect_get_type(), @@ -73,6 +74,8 @@ AutomationTimeAxisView::AutomationTimeAxisView (Session& s, Route& r, PublicEdit clear_button.set_name ("TrackVisualButton"); hide_button.set_name ("TrackRemoveButton"); + controls_table.set_no_show_all(); + ARDOUR_UI::instance()->tooltips().set_tip(height_button, _("track height")); ARDOUR_UI::instance()->tooltips().set_tip(auto_button, _("automation state")); ARDOUR_UI::instance()->tooltips().set_tip(clear_button, _("clear track")); @@ -116,6 +119,7 @@ AutomationTimeAxisView::AutomationTimeAxisView (Session& s, Route& r, PublicEdit plugname = new Label (pname); plugname->set_name (X_("TrackPlugName")); plugname->set_alignment (1.0, 0.5); + plugname->show(); name_label.set_name (X_("TrackParameterName")); controls_table.remove (name_hbox); controls_table.attach (*plugname, 1, 5, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); @@ -139,9 +143,9 @@ AutomationTimeAxisView::AutomationTimeAxisView (Session& s, Route& r, PublicEdit controls_table.attach (hide_button, 0, 1, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); controls_table.attach (height_button, 0, 1, 1, 2, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - controls_table.attach (auto_button, 6, 8, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - controls_table.attach (clear_button, 6, 8, 1, 2, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - + controls_table.attach (auto_button, 5, 8, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); + controls_table.attach (clear_button, 5, 8, 1, 2, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); + controls_table.show_all (); height_button.signal_clicked().connect (mem_fun(*this, &AutomationTimeAxisView::height_clicked)); @@ -282,11 +286,11 @@ AutomationTimeAxisView::set_height (TrackHeight ht) uint32_t h = height_to_pixels (ht); bool changed = (height != (uint32_t) h); + bool changed_between_small_and_normal = ( (ht == Small || ht == Smaller) ^ (height_style == Small || height_style == Smaller) ); + TimeAxisView* state_parent = get_parent_with_state (); XMLNode* xml_node = state_parent->get_child_xml_node (_state_name); - controls_table.show_all (); - TimeAxisView::set_height (ht); base_rect->property_y2() = h; @@ -298,119 +302,91 @@ AutomationTimeAxisView::set_height (TrackHeight ht) (*i)->set_height (); } - switch (height) { + + switch (ht) { case Largest: xml_node->add_property ("track_height", "largest"); - controls_table.remove (name_hbox); - if (plugname) { - if (plugname_packed) { - controls_table.remove (*plugname); - plugname_packed = false; - } - controls_table.attach (*plugname, 1, 5, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - plugname_packed = true; - controls_table.attach (name_hbox, 1, 5, 1, 2, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - } else { - controls_table.attach (name_hbox, 1, 5, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - } - controls_table.show_all (); - hide_name_entry (); - show_name_label (); break; case Large: xml_node->add_property ("track_height", "large"); - controls_table.remove (name_hbox); - if (plugname) { - if (plugname_packed) { - controls_table.remove (*plugname); - plugname_packed = false; - } - controls_table.attach (*plugname, 1, 5, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - plugname_packed = true; - } else { - controls_table.attach (name_hbox, 1, 5, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - } - controls_table.show_all (); - hide_name_entry (); - show_name_label (); break; case Larger: xml_node->add_property ("track_height", "larger"); - controls_table.remove (name_hbox); - if (plugname) { - if (plugname_packed) { - controls_table.remove (*plugname); - plugname_packed = false; - } - controls_table.attach (*plugname, 1, 5, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - plugname_packed = true; - } else { - controls_table.attach (name_hbox, 1, 5, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - } - controls_table.show_all (); - hide_name_entry (); - show_name_label (); break; case Normal: xml_node->add_property ("track_height", "normal"); - controls_table.remove (name_hbox); - if (plugname) { - if (plugname_packed) { - controls_table.remove (*plugname); - plugname_packed = false; - } - controls_table.attach (*plugname, 1, 5, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - plugname_packed = true; - controls_table.attach (name_hbox, 1, 5, 1, 2, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - } else { - controls_table.attach (name_hbox, 1, 5, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - } - controls_table.show_all (); - hide_name_entry (); - show_name_label (); break; case Smaller: xml_node->add_property ("track_height", "smaller"); - controls_table.remove (name_hbox); - if (plugname) { - if (plugname_packed) { - controls_table.remove (*plugname); - plugname_packed = false; - } - } - controls_table.attach (name_hbox, 1, 5, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - controls_table.hide_all (); - hide_name_entry (); - show_name_label (); - name_hbox.show_all (); - controls_table.show (); break; case Small: xml_node->add_property ("track_height", "small"); - controls_table.remove (name_hbox); - if (plugname) { - if (plugname_packed) { - controls_table.remove (*plugname); - plugname_packed = false; - } - } - controls_table.attach (name_hbox, 1, 5, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - controls_table.hide_all (); - hide_name_entry (); - show_name_label (); - name_hbox.show_all (); - controls_table.show (); break; } + if (changed_between_small_and_normal || first_call_to_set_height) { + first_call_to_set_height = false; + switch (ht) { + case Largest: + case Large: + case Larger: + case Normal: + + controls_table.remove (name_hbox); + + if (plugname) { + if (plugname_packed) { + controls_table.remove (*plugname); + plugname_packed = false; + } + controls_table.attach (*plugname, 1, 5, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); + plugname_packed = true; + controls_table.attach (name_hbox, 1, 5, 1, 2, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); + } else { + controls_table.attach (name_hbox, 1, 5, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); + } + hide_name_entry (); + show_name_label (); + name_hbox.show_all (); + + auto_button.show(); + height_button.show(); + clear_button.show(); + hide_button.show_all(); + break; + + case Smaller: + case Small: + + controls_table.remove (name_hbox); + if (plugname) { + if (plugname_packed) { + controls_table.remove (*plugname); + plugname_packed = false; + } + } + controls_table.attach (name_hbox, 1, 5, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); + controls_table.hide_all (); + hide_name_entry (); + show_name_label (); + name_hbox.show_all (); + + auto_button.hide(); + height_button.hide(); + clear_button.hide(); + hide_button.hide(); + break; + } + } + if (changed) { /* only emit the signal if the height really changed */ - route.gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ + route->gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ } } diff --git a/gtk2_ardour/automation_time_axis.h b/gtk2_ardour/automation_time_axis.h index deb08b41f0..0cd9acc034 100644 --- a/gtk2_ardour/automation_time_axis.h +++ b/gtk2_ardour/automation_time_axis.h @@ -4,6 +4,9 @@ #include #include #include + +#include + #include #include "canvas.h" @@ -21,7 +24,7 @@ namespace ARDOUR { class PublicEditor; class TimeSelection; -class AudioRegionSelection; +class RegionSelection; class PointSelection; class AutomationLine; class GhostRegion; @@ -31,7 +34,7 @@ class Selectable; class AutomationTimeAxisView : public TimeAxisView { public: AutomationTimeAxisView (ARDOUR::Session&, - ARDOUR::Route&, + boost::shared_ptr, PublicEditor&, TimeAxisView& parent, ArdourCanvas::Canvas& canvas, @@ -41,14 +44,14 @@ class AutomationTimeAxisView : public TimeAxisView { ~AutomationTimeAxisView(); - void set_height (TimeAxisView::TrackHeight); + virtual void set_height (TimeAxisView::TrackHeight); void set_samples_per_unit (double); std::string name() const { return _name; } virtual void add_automation_event (ArdourCanvas::Item *item, GdkEvent *event, jack_nframes_t, double) = 0; - void clear_lines (); - void add_line (AutomationLine&); + virtual void clear_lines (); + virtual void add_line (AutomationLine&); vector lines; @@ -75,12 +78,14 @@ class AutomationTimeAxisView : public TimeAxisView { XMLNode* get_state_node (); protected: - ARDOUR::Route& route; + boost::shared_ptr route; ArdourCanvas::SimpleRect* base_rect; string _name; string _state_name; bool in_destructor; + bool first_call_to_set_height; + Gtk::Button hide_button; Gtk::Button height_button; Gtk::Button clear_button; diff --git a/gtk2_ardour/canvas-waveview.h b/gtk2_ardour/canvas-waveview.h index 97ac91f622..75281f69eb 100644 --- a/gtk2_ardour/canvas-waveview.h +++ b/gtk2_ardour/canvas-waveview.h @@ -80,10 +80,10 @@ struct _GnomeCanvasWaveView void (*gain_curve_function)(void *arg, double start, double end, float* vector, guint32 veclen); void *gain_src; - /* x-axis: samples per canvas unit. */ + /** x-axis: samples per canvas unit. */ double samples_per_unit; - /* y-axis: amplitude_above_axis. + /** y-axis: amplitude_above_axis. * * the default is that an (scaled, normalized -1.0 ... +1.0) amplitude of 1.0 * corresponds to the top of the area assigned to the waveview. @@ -92,8 +92,8 @@ struct _GnomeCanvasWaveView * smaller values will decrease the vertical scale, moving peaks/troughs toward * the middle of the area assigned to the waveview. */ - double amplitude_above_axis; + double x; double y; double height; diff --git a/gtk2_ardour/crossfade_edit.cc b/gtk2_ardour/crossfade_edit.cc index 5b587594de..b2967dc4a9 100644 --- a/gtk2_ardour/crossfade_edit.cc +++ b/gtk2_ardour/crossfade_edit.cc @@ -1077,7 +1077,7 @@ CrossfadeEditor::peaks_ready (AudioRegion* r, WhichFade which) void CrossfadeEditor::audition_both () { - AudioPlaylist& pl (session.the_auditioner().prepare_playlist()); + AudioPlaylist& pl (session.the_auditioner()->prepare_playlist()); jack_nframes_t preroll; jack_nframes_t postroll; jack_nframes_t length; @@ -1140,7 +1140,7 @@ CrossfadeEditor::audition_left_dry () void CrossfadeEditor::audition_left () { - AudioPlaylist& pl (session.the_auditioner().prepare_playlist()); + AudioPlaylist& pl (session.the_auditioner()->prepare_playlist()); AudioRegion* left = new AudioRegion (xfade.out(), xfade.out().length() - xfade.length(), xfade.length(), "xfade left", 0, Region::DefaultFlags, false); @@ -1172,7 +1172,7 @@ CrossfadeEditor::audition_right_dry () void CrossfadeEditor::audition_right () { - AudioPlaylist& pl (session.the_auditioner().prepare_playlist()); + AudioPlaylist& pl (session.the_auditioner()->prepare_playlist()); AudioRegion* left = new AudioRegion (xfade.out(), xfade.out().length() - xfade.length(), xfade.length(), "xfade out", 0, Region::DefaultFlags, false); diff --git a/gtk2_ardour/crossfade_view.cc b/gtk2_ardour/crossfade_view.cc index 350698ec48..087af25e73 100644 --- a/gtk2_ardour/crossfade_view.cc +++ b/gtk2_ardour/crossfade_view.cc @@ -29,7 +29,7 @@ #include "rgb_macros.h" #include "audio_time_axis.h" #include "public_editor.h" -#include "regionview.h" +#include "audio_region_view.h" #include "utils.h" #include "canvas_impl.h" @@ -43,7 +43,7 @@ using namespace Canvas; sigc::signal CrossfadeView::GoingAway; CrossfadeView::CrossfadeView (ArdourCanvas::Group *parent, - AudioTimeAxisView &tv, + RouteTimeAxisView &tv, Crossfade& xf, double spu, Gdk::Color& basic_color, @@ -227,7 +227,7 @@ CrossfadeView::set_valid (bool yn) AudioRegionView& CrossfadeView::upper_regionview () const { - if (left_view.region.layer() > right_view.region.layer()) { + if (left_view.region().layer() > right_view.region().layer()) { return left_view; } else { return right_view; diff --git a/gtk2_ardour/crossfade_view.h b/gtk2_ardour/crossfade_view.h index 403edfe297..adbd74b420 100644 --- a/gtk2_ardour/crossfade_view.h +++ b/gtk2_ardour/crossfade_view.h @@ -28,13 +28,13 @@ #include "time_axis_view_item.h" -class AudioTimeAxisView; +class RouteTimeAxisView; class AudioRegionView; struct CrossfadeView : public TimeAxisViewItem { CrossfadeView (ArdourCanvas::Group*, - AudioTimeAxisView&, + RouteTimeAxisView&, ARDOUR::Crossfade&, double initial_samples_per_unit, Gdk::Color& basic_color, diff --git a/gtk2_ardour/editing_syms.h b/gtk2_ardour/editing_syms.h index cf36550fb4..654ddc8852 100644 --- a/gtk2_ardour/editing_syms.h +++ b/gtk2_ardour/editing_syms.h @@ -56,4 +56,5 @@ DISPLAYCONTROL(ShowWaveformsRecording) IMPORTMODE(ImportAsRegion) IMPORTMODE(ImportAsTrack) +IMPORTMODE(ImportAsTapeTrack) IMPORTMODE(ImportToTrack) diff --git a/gtk2_ardour/editor.cc b/gtk2_ardour/editor.cc index 6472974093..513251085c 100644 --- a/gtk2_ardour/editor.cc +++ b/gtk2_ardour/editor.cc @@ -57,10 +57,10 @@ #include "keyboard.h" #include "marker.h" #include "playlist_selector.h" -#include "regionview.h" +#include "audio_region_view.h" #include "rgb_macros.h" #include "selection.h" -#include "streamview.h" +#include "audio_streamview.h" #include "time_axis_view.h" #include "utils.h" #include "crossfade_view.h" @@ -102,8 +102,8 @@ static const int32_t slide_index = 0; static const int32_t splice_index = 1; static const gchar *edit_mode_strings[] = { - N_("Slide"), - N_("Splice"), + N_("Slide Edit"), + N_("Splice Edit"), 0 }; @@ -132,17 +132,17 @@ static const gchar *snap_type_strings[] = { }; static const gchar *snap_mode_strings[] = { - N_("Normal"), - N_("Magnetic"), + N_("Normal Snap"), + N_("Magnetic Snap"), 0 }; static const gchar *zoom_focus_strings[] = { - N_("Left"), - N_("Right"), - N_("Center"), - N_("Playhead"), - N_("Edit Cursor"), + N_("Focus Left"), + N_("Focus Right"), + N_("Focus Center"), + N_("Focus Play"), + N_("Focus Edit"), 0 }; @@ -205,37 +205,20 @@ Editor::Editor (AudioEngine& eng) /* tool bar related */ - selection_start_clock (X_("SelectionStartClock"), true), - selection_end_clock (X_("SelectionEndClock"), true), edit_cursor_clock (X_("EditCursorClock"), true), zoom_range_clock (X_("ZoomRangeClock"), true, true), toolbar_selection_clock_table (2,3), - mouse_mode_button_table (2, 3), - - mouse_select_button (_("range")), - mouse_move_button (_("object")), - mouse_gain_button (_("gain")), - mouse_zoom_button (_("zoom")), - mouse_timefx_button (_("timefx")), - mouse_audition_button (_("listen")), - automation_mode_button (_("mode")), global_automation_button (_("automation")), - edit_mode_label (_("Edit Mode")), - snap_type_label (_("Snap To")), - snap_mode_label(_("Snap Mode")), - zoom_focus_label (_("Zoom Focus")), - /* */ image_socket_listener(0), /* */ /* nudge */ - nudge_label (_("Nudge")), nudge_clock (X_("NudgeClock"), true, true) { @@ -346,6 +329,7 @@ Editor::Editor (AudioEngine& eng) reset_hscrollbar_stepping (); zoom_focus = ZoomFocusLeft; + set_zoom_focus (ZoomFocusLeft); zoom_range_clock.ValueChanged.connect (mem_fun(*this, &Editor::zoom_adjustment_changed)); initialize_rulers (); @@ -466,36 +450,7 @@ Editor::Editor (AudioEngine& eng) edit_packer.attach (edit_hscrollbar, 2, 3, 2, 3, FILL|EXPAND, FILL, 0, 0); - zoom_in_button.set_name ("EditorTimeButton"); - zoom_out_button.set_name ("EditorTimeButton"); - ARDOUR_UI::instance()->tooltips().set_tip (zoom_in_button, _("Zoom in")); - ARDOUR_UI::instance()->tooltips().set_tip (zoom_out_button, _("Zoom out")); - - zoom_out_full_button.set_name ("EditorTimeButton"); - ARDOUR_UI::instance()->tooltips().set_tip (zoom_out_full_button, _("Zoom to session")); - - zoom_in_button.add (*(manage (new Image (Stock::ZOOM_IN, ICON_SIZE_BUTTON)))); - zoom_out_button.add (*(manage (new Image (Stock::ZOOM_OUT, ICON_SIZE_BUTTON)))); - zoom_out_full_button.add (*(manage (new Image (Stock::ZOOM_FIT, ICON_SIZE_BUTTON)))); - - zoom_in_button.signal_clicked().connect (bind (mem_fun(*this, &Editor::temporal_zoom_step), false)); - zoom_out_button.signal_clicked().connect (bind (mem_fun(*this, &Editor::temporal_zoom_step), true)); - zoom_out_full_button.signal_clicked().connect (mem_fun(*this, &Editor::temporal_zoom_session)); - - zoom_indicator_box.pack_start (zoom_out_button, false, false); - zoom_indicator_box.pack_start (zoom_in_button, false, false); - zoom_indicator_box.pack_start (zoom_range_clock, false, false); - zoom_indicator_box.pack_start (zoom_out_full_button, false, false); - - zoom_indicator_label.set_text (_("Zoom Span")); - zoom_indicator_label.set_name ("ToolBarLabel"); - - zoom_indicator_vbox.set_spacing (3); - zoom_indicator_vbox.set_border_width (3); - zoom_indicator_vbox.pack_start (zoom_indicator_label, false, false); - zoom_indicator_vbox.pack_start (zoom_indicator_box, false, false); - - bottom_hbox.set_border_width (3); + bottom_hbox.set_border_width (2); bottom_hbox.set_spacing (3); route_display_model = ListStore::create(route_display_columns); @@ -718,15 +673,15 @@ Editor::Editor (AudioEngine& eng) _playlist_selector = new PlaylistSelector(); _playlist_selector->signal_delete_event().connect (bind (sigc::ptr_fun (just_hide_it), static_cast (_playlist_selector))); - AudioRegionView::AudioRegionViewGoingAway.connect (mem_fun(*this, &Editor::catch_vanishing_audio_regionview)); + RegionView::RegionViewGoingAway.connect (mem_fun(*this, &Editor::catch_vanishing_regionview)); /* nudge stuff */ nudge_forward_button.add (*(manage (new Image (get_xpm("right_arrow.xpm"))))); nudge_backward_button.add (*(manage (new Image (get_xpm("left_arrow.xpm"))))); - ARDOUR_UI::instance()->tooltips().set_tip (nudge_forward_button, _("Nudge region/selection forwards")); - ARDOUR_UI::instance()->tooltips().set_tip (nudge_backward_button, _("Nudge region/selection backwards")); + ARDOUR_UI::instance()->tooltips().set_tip (nudge_forward_button, _("Nudge Region/Selection Forwards")); + ARDOUR_UI::instance()->tooltips().set_tip (nudge_backward_button, _("Nudge Region/Selection Backwards")); nudge_forward_button.set_name ("TransportButton"); nudge_backward_button.set_name ("TransportButton"); @@ -776,7 +731,7 @@ Editor::add_toplevel_controls (Container& cont) } void -Editor::catch_vanishing_audio_regionview (AudioRegionView *rv) +Editor::catch_vanishing_regionview (RegionView *rv) { /* note: the selection will take care of the vanishing audioregionview by itself. @@ -792,7 +747,7 @@ Editor::catch_vanishing_audio_regionview (AudioRegionView *rv) } void -Editor::set_entered_regionview (AudioRegionView* rv) +Editor::set_entered_regionview (RegionView* rv) { if (rv == entered_regionview) { return; @@ -914,7 +869,7 @@ Editor::set_frames_per_unit (double fpu) void Editor::instant_save () { - if (!constructed || !ARDOUR_UI::instance()->session_loaded) { + if (!constructed || !ARDOUR_UI::instance()->session_loaded) { return; } @@ -1222,7 +1177,7 @@ Editor::connect_to_session (Session *t) session_connections.push_back (session->TransportStateChange.connect (mem_fun(*this, &Editor::map_transport_state))); session_connections.push_back (session->PositionChanged.connect (mem_fun(*this, &Editor::map_position_change))); - session_connections.push_back (session->RouteAdded.connect (mem_fun(*this, &Editor::handle_new_route_p))); + session_connections.push_back (session->RouteAdded.connect (mem_fun(*this, &Editor::handle_new_route))); session_connections.push_back (session->AudioRegionAdded.connect (mem_fun(*this, &Editor::handle_new_audio_region))); session_connections.push_back (session->AudioRegionRemoved.connect (mem_fun(*this, &Editor::handle_audio_region_removed))); session_connections.push_back (session->DurationChanged.connect (mem_fun(*this, &Editor::handle_new_duration))); @@ -1243,8 +1198,6 @@ Editor::connect_to_session (Session *t) edit_groups_changed (); edit_cursor_clock.set_session (session); - selection_start_clock.set_session (session); - selection_end_clock.set_session (session); zoom_range_clock.set_session (session); _playlist_selector->set_session (session); nudge_clock.set_session (session); @@ -1377,7 +1330,7 @@ Editor::connect_to_session (Session *t) AudioTimeAxisView *atv; if ((atv = dynamic_cast(tv)) != 0) { - if (atv->route().master()) { + if (atv->route()->master()) { route_list_display.get_selection()->unselect (i); } } @@ -1448,7 +1401,7 @@ Editor::popup_fade_context_menu (int button, int32_t time, ArdourCanvas::Item* i switch (item_type) { case FadeInItem: case FadeInHandleItem: - if (arv->region.fade_in_active()) { + if (arv->audio_region().fade_in_active()) { items.push_back (MenuElem (_("Deactivate"), bind (mem_fun (*arv, &AudioRegionView::set_fade_in_active), false))); } else { items.push_back (MenuElem (_("Activate"), bind (mem_fun (*arv, &AudioRegionView::set_fade_in_active), true))); @@ -1456,16 +1409,16 @@ Editor::popup_fade_context_menu (int button, int32_t time, ArdourCanvas::Item* i items.push_back (SeparatorElem()); - items.push_back (MenuElem (_("Linear"), bind (mem_fun (arv->region, &AudioRegion::set_fade_in_shape), AudioRegion::Linear))); - items.push_back (MenuElem (_("Slowest"), bind (mem_fun (arv->region, &AudioRegion::set_fade_in_shape), AudioRegion::LogB))); - items.push_back (MenuElem (_("Slow"), bind (mem_fun (arv->region, &AudioRegion::set_fade_in_shape), AudioRegion::Fast))); - items.push_back (MenuElem (_("Fast"), bind (mem_fun (arv->region, &AudioRegion::set_fade_in_shape), AudioRegion::LogA))); - items.push_back (MenuElem (_("Fastest"), bind (mem_fun (arv->region, &AudioRegion::set_fade_in_shape), AudioRegion::Slow))); + items.push_back (MenuElem (_("Linear"), bind (mem_fun (arv->audio_region(), &AudioRegion::set_fade_in_shape), AudioRegion::Linear))); + items.push_back (MenuElem (_("Slowest"), bind (mem_fun (arv->audio_region(), &AudioRegion::set_fade_in_shape), AudioRegion::LogB))); + items.push_back (MenuElem (_("Slow"), bind (mem_fun (arv->audio_region(), &AudioRegion::set_fade_in_shape), AudioRegion::Fast))); + items.push_back (MenuElem (_("Fast"), bind (mem_fun (arv->audio_region(), &AudioRegion::set_fade_in_shape), AudioRegion::LogA))); + items.push_back (MenuElem (_("Fastest"), bind (mem_fun (arv->audio_region(), &AudioRegion::set_fade_in_shape), AudioRegion::Slow))); break; case FadeOutItem: case FadeOutHandleItem: - if (arv->region.fade_out_active()) { + if (arv->audio_region().fade_out_active()) { items.push_back (MenuElem (_("Deactivate"), bind (mem_fun (*arv, &AudioRegionView::set_fade_out_active), false))); } else { items.push_back (MenuElem (_("Activate"), bind (mem_fun (*arv, &AudioRegionView::set_fade_out_active), true))); @@ -1473,11 +1426,11 @@ Editor::popup_fade_context_menu (int button, int32_t time, ArdourCanvas::Item* i items.push_back (SeparatorElem()); - items.push_back (MenuElem (_("Linear"), bind (mem_fun (arv->region, &AudioRegion::set_fade_out_shape), AudioRegion::Linear))); - items.push_back (MenuElem (_("Slowest"), bind (mem_fun (arv->region, &AudioRegion::set_fade_out_shape), AudioRegion::Fast))); - items.push_back (MenuElem (_("Slow"), bind (mem_fun (arv->region, &AudioRegion::set_fade_out_shape), AudioRegion::LogB))); - items.push_back (MenuElem (_("Fast"), bind (mem_fun (arv->region, &AudioRegion::set_fade_out_shape), AudioRegion::LogA))); - items.push_back (MenuElem (_("Fastest"), bind (mem_fun (arv->region, &AudioRegion::set_fade_out_shape), AudioRegion::Slow))); + items.push_back (MenuElem (_("Linear"), bind (mem_fun (arv->audio_region(), &AudioRegion::set_fade_out_shape), AudioRegion::Linear))); + items.push_back (MenuElem (_("Slowest"), bind (mem_fun (arv->audio_region(), &AudioRegion::set_fade_out_shape), AudioRegion::Fast))); + items.push_back (MenuElem (_("Slow"), bind (mem_fun (arv->audio_region(), &AudioRegion::set_fade_out_shape), AudioRegion::LogB))); + items.push_back (MenuElem (_("Fast"), bind (mem_fun (arv->audio_region(), &AudioRegion::set_fade_out_shape), AudioRegion::LogA))); + items.push_back (MenuElem (_("Fastest"), bind (mem_fun (arv->audio_region(), &AudioRegion::set_fade_out_shape), AudioRegion::Slow))); break; default: @@ -1499,8 +1452,8 @@ Editor::popup_track_context_menu (int button, int32_t time, ItemType item_type, switch (item_type) { case RegionItem: - case AudioRegionViewName: - case AudioRegionViewNameHighlight: + case RegionViewName: + case RegionViewNameHighlight: if (with_selection) { build_menu_function = &Editor::build_track_selection_context_menu; } else { @@ -1540,25 +1493,26 @@ Editor::popup_track_context_menu (int button, int32_t time, ItemType item_type, switch (item_type) { case RegionItem: - case AudioRegionViewName: - case AudioRegionViewNameHighlight: + case RegionViewName: + case RegionViewNameHighlight: if (!with_selection) { if (region_edit_menu_split_item) { - if (clicked_regionview && clicked_regionview->region.covers (edit_cursor->current_frame)) { + if (clicked_regionview && clicked_regionview->region().covers (edit_cursor->current_frame)) { ActionManager::set_sensitive (ActionManager::edit_cursor_in_region_sensitive_actions, true); } else { ActionManager::set_sensitive (ActionManager::edit_cursor_in_region_sensitive_actions, false); } } + /* if (region_edit_menu_split_multichannel_item) { - if (clicked_regionview && clicked_regionview->region.n_channels() > 1) { + if (clicked_regionview && clicked_regionview->region().n_channels() > 1) { // GTK2FIX find the action, change its sensitivity // region_edit_menu_split_multichannel_item->set_sensitive (true); } else { // GTK2FIX see above // region_edit_menu_split_multichannel_item->set_sensitive (false); } - } + }*/ } break; @@ -1638,13 +1592,13 @@ Editor::build_track_region_context_menu (jack_nframes_t frame) AudioTimeAxisView* atv = dynamic_cast (clicked_trackview); if (atv) { - AudioDiskstream* ds; + Diskstream* ds; Playlist* pl; if ((ds = atv->get_diskstream()) && ((pl = ds->playlist()))) { Playlist::RegionList* regions = pl->regions_at ((jack_nframes_t) floor ( (double)frame * ds->speed())); for (Playlist::RegionList::iterator i = regions->begin(); i != regions->end(); ++i) { - add_region_context_items (atv->view, (*i), edit_items); + add_region_context_items (atv->audio_view(), (*i), edit_items); } delete regions; } @@ -1665,7 +1619,7 @@ Editor::build_track_crossfade_context_menu (jack_nframes_t frame) AudioTimeAxisView* atv = dynamic_cast (clicked_trackview); if (atv) { - AudioDiskstream* ds; + Diskstream* ds; Playlist* pl; AudioPlaylist* apl; @@ -1679,11 +1633,11 @@ Editor::build_track_crossfade_context_menu (jack_nframes_t frame) bool many = xfades.size() > 1; for (AudioPlaylist::Crossfades::iterator i = xfades.begin(); i != xfades.end(); ++i) { - add_crossfade_context_items (atv->view, (*i), edit_items, many); + add_crossfade_context_items (atv->audio_view(), (*i), edit_items, many); } for (Playlist::RegionList::iterator i = regions->begin(); i != regions->end(); ++i) { - add_region_context_items (atv->view, (*i), edit_items); + add_region_context_items (atv->audio_view(), (*i), edit_items); } delete regions; @@ -1749,7 +1703,7 @@ Editor::build_track_selection_context_menu (jack_nframes_t ignored) } void -Editor::add_crossfade_context_items (StreamView* view, Crossfade* xfade, Menu_Helpers::MenuList& edit_items, bool many) +Editor::add_crossfade_context_items (AudioStreamView* view, Crossfade* xfade, Menu_Helpers::MenuList& edit_items, bool many) { using namespace Menu_Helpers; Menu *xfade_menu = manage (new Menu); @@ -1806,7 +1760,7 @@ Editor::xfade_edit_right_region () } void -Editor::add_region_context_items (StreamView* sv, Region* region, Menu_Helpers::MenuList& edit_items) +Editor::add_region_context_items (AudioStreamView* sv, Region* region, Menu_Helpers::MenuList& edit_items) { using namespace Menu_Helpers; Menu *region_menu = manage (new Menu); @@ -2185,7 +2139,6 @@ Editor::set_state (const XMLNode& node) yoff = atoi(geometry->property("y_off")->value()); } - set_geometry_hints (vpacker, g, Gdk::HINT_BASE_SIZE); set_default_size (g.base_width, g.base_height); move (x, y); @@ -2297,7 +2250,7 @@ Editor::get_state () char buf[32]; if (is_realized()) { - Glib::RefPtr win = get_window(); + Glib::RefPtr win = get_window(); int x, y, xoff, yoff, width, height; win->get_root_origin(x, y); @@ -2586,30 +2539,56 @@ void Editor::setup_toolbar () { string pixmap_path; + + const guint32 FUDGE = 18; // Combo's are stupid - they steal space from the entry for the button + + + /* Mode Buttons (tool selection) */ + vector mouse_mode_buttons; + mouse_move_button.add (*(manage (new Image (get_xpm("tool_object.xpm"))))); + mouse_move_button.set_relief(Gtk::RELIEF_NONE); mouse_mode_buttons.push_back (&mouse_move_button); + mouse_select_button.add (*(manage (new Image (get_xpm("tool_range.xpm"))))); + mouse_select_button.set_relief(Gtk::RELIEF_NONE); mouse_mode_buttons.push_back (&mouse_select_button); + mouse_gain_button.add (*(manage (new Image (get_xpm("tool_gain.xpm"))))); + mouse_gain_button.set_relief(Gtk::RELIEF_NONE); mouse_mode_buttons.push_back (&mouse_gain_button); + mouse_zoom_button.add (*(manage (new Image (get_xpm("tool_zoom.xpm"))))); + mouse_zoom_button.set_relief(Gtk::RELIEF_NONE); mouse_mode_buttons.push_back (&mouse_zoom_button); + mouse_timefx_button.add (*(manage (new Image (get_xpm("tool_stretch.xpm"))))); + mouse_timefx_button.set_relief(Gtk::RELIEF_NONE); mouse_mode_buttons.push_back (&mouse_timefx_button); + mouse_audition_button.add (*(manage (new Image (get_xpm("tool_audition.xpm"))))); + mouse_audition_button.set_relief(Gtk::RELIEF_NONE); mouse_mode_buttons.push_back (&mouse_audition_button); + mouse_mode_button_set = new GroupedButtons (mouse_mode_buttons); - mouse_mode_button_table.set_homogeneous (true); - mouse_mode_button_table.set_col_spacings (2); - mouse_mode_button_table.set_row_spacings (2); - mouse_mode_button_table.set_border_width (5); + HBox* mode_box = manage(new HBox); + mode_box->set_border_width (2); + mode_box->set_spacing(4); + mouse_mode_button_box.set_spacing(1); + mouse_mode_button_box.pack_start(mouse_move_button, true, true); + mouse_mode_button_box.pack_start(mouse_select_button, true, true); + mouse_mode_button_box.pack_start(mouse_zoom_button, true, true); + mouse_mode_button_box.pack_start(mouse_gain_button, true, true); + mouse_mode_button_box.pack_start(mouse_timefx_button, true, true); + mouse_mode_button_box.pack_start(mouse_audition_button, true, true); + mouse_mode_button_box.set_homogeneous(true); - mouse_mode_button_table.attach (mouse_move_button, 0, 1, 0, 1); - mouse_mode_button_table.attach (mouse_select_button, 1, 2, 0, 1); - mouse_mode_button_table.attach (mouse_zoom_button, 2, 3, 0, 1); - - mouse_mode_button_table.attach (mouse_gain_button, 0, 1, 1, 2); - mouse_mode_button_table.attach (mouse_timefx_button, 1, 2, 1, 2); - mouse_mode_button_table.attach (mouse_audition_button, 2, 3, 1, 2); + edit_mode_selector.set_name ("EditModeSelector"); + Gtkmm2ext::set_size_request_to_display_given_text (edit_mode_selector, "Splice Edit", 2+FUDGE, 10); + set_popdown_strings (edit_mode_selector, internationalize (edit_mode_strings)); + edit_mode_selector.signal_changed().connect (mem_fun(*this, &Editor::edit_mode_selection_done)); - mouse_mode_tearoff = manage (new TearOff (mouse_mode_button_table)); + mode_box->pack_start(edit_mode_selector); + mode_box->pack_start(mouse_mode_button_box); + + mouse_mode_tearoff = manage (new TearOff (*mode_box)); mouse_mode_tearoff->set_name ("MouseModeBase"); mouse_mode_tearoff->Detach.connect (bind (mem_fun(*this, &Editor::detach_tearoff), static_cast(&toolbar_hbox), @@ -2628,12 +2607,12 @@ Editor::setup_toolbar () mouse_timefx_button.set_name ("MouseModeButton"); mouse_audition_button.set_name ("MouseModeButton"); - ARDOUR_UI::instance()->tooltips().set_tip (mouse_move_button, _("select/move objects")); - ARDOUR_UI::instance()->tooltips().set_tip (mouse_select_button, _("select/move ranges")); - ARDOUR_UI::instance()->tooltips().set_tip (mouse_gain_button, _("draw gain automation")); - ARDOUR_UI::instance()->tooltips().set_tip (mouse_zoom_button, _("select zoom range")); - ARDOUR_UI::instance()->tooltips().set_tip (mouse_timefx_button, _("stretch/shrink regions")); - ARDOUR_UI::instance()->tooltips().set_tip (mouse_audition_button, _("listen to specific regions")); + ARDOUR_UI::instance()->tooltips().set_tip (mouse_move_button, _("Select/Move Objects")); + ARDOUR_UI::instance()->tooltips().set_tip (mouse_select_button, _("Select/Move Ranges")); + ARDOUR_UI::instance()->tooltips().set_tip (mouse_gain_button, _("Draw Gain Automation")); + ARDOUR_UI::instance()->tooltips().set_tip (mouse_zoom_button, _("Select Zoom Range")); + ARDOUR_UI::instance()->tooltips().set_tip (mouse_timefx_button, _("Stretch/Shrink Regions")); + ARDOUR_UI::instance()->tooltips().set_tip (mouse_audition_button, _("Listen to Specific Regions")); mouse_move_button.unset_flags (CAN_FOCUS); mouse_select_button.unset_flags (CAN_FOCUS); @@ -2652,160 +2631,82 @@ Editor::setup_toolbar () mouse_audition_button.signal_toggled().connect (bind (mem_fun(*this, &Editor::mouse_mode_toggled), Editing::MouseAudition)); // mouse_move_button.set_active (true); - - /* automation control */ - - global_automation_button.set_name ("MouseModeButton"); - automation_mode_button.set_name ("MouseModeButton"); - - automation_box.set_spacing (2); - automation_box.set_border_width (2); - automation_box.pack_start (global_automation_button, false, false); - automation_box.pack_start (automation_mode_button, false, false); - - /* Edit mode */ - - edit_mode_label.set_name ("ToolBarLabel"); - - edit_mode_selector.set_name ("EditModeSelector"); - - edit_mode_box.set_spacing (3); - edit_mode_box.set_border_width (3); - - /* XXX another disgusting hack because of the way combo boxes size themselves */ - - const guint32 FUDGE = 20; // Combo's are stupid - they steal space from the entry for the button - Gtkmm2ext::set_size_request_to_display_given_text (edit_mode_selector, "EdgtMode", 2+FUDGE, 10); - set_popdown_strings (edit_mode_selector, internationalize (edit_mode_strings)); - edit_mode_box.pack_start (edit_mode_label, false, false); - edit_mode_box.pack_start (edit_mode_selector, false, false); - - edit_mode_selector.signal_changed().connect (mem_fun(*this, &Editor::edit_mode_selection_done)); - - /* Snap Type */ - - snap_type_label.set_name ("ToolBarLabel"); - - snap_type_selector.set_name ("SnapTypeSelector"); - - snap_type_box.set_spacing (3); - snap_type_box.set_border_width (3); - - /* XXX another disgusting hack because of the way combo boxes size themselves */ - - Gtkmm2ext::set_size_request_to_display_given_text (snap_type_selector, "SMPTE Seconds", 2+FUDGE, 10); - set_popdown_strings (snap_type_selector, internationalize (snap_type_strings)); - - snap_type_box.pack_start (snap_type_label, false, false); - snap_type_box.pack_start (snap_type_selector, false, false); - - snap_type_selector.signal_changed().connect (mem_fun(*this, &Editor::snap_type_selection_done)); - - /* Snap mode, not snap type */ - - snap_mode_label.set_name ("ToolBarLabel"); - - snap_mode_selector.set_name ("SnapModeSelector"); - snap_mode_box.set_spacing (3); - snap_mode_box.set_border_width (3); - Gtkmm2ext::set_size_request_to_display_given_text (snap_mode_selector, "SngpMode", 2+FUDGE, 10); - set_popdown_strings (snap_mode_selector, internationalize (snap_mode_strings)); + /* Zoom */ + + zoom_box.set_spacing (1); + zoom_box.set_border_width (2); - snap_mode_box.pack_start (snap_mode_label, false, false); - snap_mode_box.pack_start (snap_mode_selector, false, false); - - snap_mode_selector.signal_changed().connect (mem_fun(*this, &Editor::snap_mode_selection_done)); - - /* Zoom focus mode */ - - zoom_focus_label.set_name ("ToolBarLabel"); + zoom_in_button.set_name ("EditorTimeButton"); + zoom_in_button.add (*(manage (new Image (get_xpm("zoom_in.xpm"))))); + zoom_in_button.signal_clicked().connect (bind (mem_fun(*this, &Editor::temporal_zoom_step), false)); + ARDOUR_UI::instance()->tooltips().set_tip (zoom_in_button, _("Zoom In")); + + zoom_out_button.set_name ("EditorTimeButton"); + zoom_out_button.add (*(manage (new Image (get_xpm("zoom_out.xpm"))))); + zoom_out_button.signal_clicked().connect (bind (mem_fun(*this, &Editor::temporal_zoom_step), true)); + ARDOUR_UI::instance()->tooltips().set_tip (zoom_out_button, _("Zoom Out")); + zoom_out_full_button.set_name ("EditorTimeButton"); + zoom_out_full_button.add (*(manage (new Image (get_xpm("zoom_full.xpm"))))); + zoom_out_full_button.signal_clicked().connect (mem_fun(*this, &Editor::temporal_zoom_session)); + ARDOUR_UI::instance()->tooltips().set_tip (zoom_out_full_button, _("Zoom to Session")); + + zoom_box.pack_start (zoom_out_button, false, false); + zoom_box.pack_start (zoom_in_button, false, false); + zoom_box.pack_start (zoom_range_clock, false, false); + zoom_box.pack_start (zoom_out_full_button, false, false); + + ARDOUR_UI::instance()->tooltips().set_tip (zoom_range_clock, _("Current Zoom Range\n(Width of visible area)")); + zoom_focus_selector.set_name ("ZoomFocusSelector"); - - zoom_focus_box.set_spacing (3); - zoom_focus_box.set_border_width (3); - - /* XXX another disgusting hack because of the way combo boxes size themselves */ - - Gtkmm2ext::set_size_request_to_display_given_text (zoom_focus_selector, "Edgt Cursor", 2+FUDGE, 10); + Gtkmm2ext::set_size_request_to_display_given_text (zoom_focus_selector, "Focus Center", 2+FUDGE, 0); set_popdown_strings (zoom_focus_selector, internationalize (zoom_focus_strings)); - - zoom_focus_box.pack_start (zoom_focus_label, false, false); - zoom_focus_box.pack_start (zoom_focus_selector, false, false); - zoom_focus_selector.signal_changed().connect (mem_fun(*this, &Editor::zoom_focus_selection_done)); - /* selection/cursor clocks */ + zoom_box.pack_start (zoom_focus_selector, false, false); - toolbar_selection_cursor_label.set_name ("ToolBarLabel"); - selection_start_clock_label.set_name ("ToolBarLabel"); - selection_end_clock_label.set_name ("ToolBarLabel"); - edit_cursor_clock_label.set_name ("ToolBarLabel"); - selection_start_clock_label.set_text (_("Start:")); - selection_end_clock_label.set_text (_("End:")); - edit_cursor_clock_label.set_text (_("Edit")); + /* Edit Cursor / Snap */ - /* the zoom in/out buttons are generally taller than the clocks, so - put all the toolbar clocks into a size group with one of the - buttons to make them all equal height. + snap_box.set_spacing (1); + snap_box.set_border_width (2); - this also applies to the various toolbar combos - */ + snap_type_selector.set_name ("SnapTypeSelector"); + Gtkmm2ext::set_size_request_to_display_given_text (snap_type_selector, "SMPTE Seconds", 2+FUDGE, 10); + set_popdown_strings (snap_type_selector, internationalize (snap_type_strings)); + snap_type_selector.signal_changed().connect (mem_fun(*this, &Editor::snap_type_selection_done)); + ARDOUR_UI::instance()->tooltips().set_tip (snap_type_selector, _("Unit to snap cursors and ranges to")); - RefPtr toolbar_clock_size_group = SizeGroup::create (SIZE_GROUP_VERTICAL); - toolbar_clock_size_group->add_widget (zoom_out_button); - toolbar_clock_size_group->add_widget (edit_cursor_clock); - toolbar_clock_size_group->add_widget (zoom_range_clock); - toolbar_clock_size_group->add_widget (nudge_clock); - toolbar_clock_size_group->add_widget (edit_mode_selector); - toolbar_clock_size_group->add_widget (snap_type_selector); - toolbar_clock_size_group->add_widget (snap_mode_selector); - toolbar_clock_size_group->add_widget (zoom_focus_selector); + snap_mode_selector.set_name ("SnapModeSelector"); + Gtkmm2ext::set_size_request_to_display_given_text (snap_mode_selector, "Magnetic Snap", 2+FUDGE, 10); + set_popdown_strings (snap_mode_selector, internationalize (snap_mode_strings)); + snap_mode_selector.signal_changed().connect (mem_fun(*this, &Editor::snap_mode_selection_done)); - HBox* edit_clock_hbox = manage (new HBox()); - VBox* edit_clock_vbox = manage (new VBox()); + snap_box.pack_start (edit_cursor_clock, false, false); + snap_box.pack_start (snap_mode_selector, false, false); + snap_box.pack_start (snap_type_selector, false, false); - edit_clock_hbox->pack_start (edit_cursor_clock, false, false); - edit_clock_vbox->set_spacing (3); - edit_clock_vbox->set_border_width (3); - edit_clock_vbox->pack_start (edit_cursor_clock_label, false, false); - edit_clock_vbox->pack_start (*edit_clock_hbox, false, false); + /* Nudge */ - HBox* hbox = new HBox; + HBox *nudge_box = manage (new HBox); + nudge_box->set_spacing(1); + nudge_box->set_border_width (2); - hbox->pack_start (*edit_clock_vbox, false, false); - hbox->pack_start (zoom_indicator_vbox, false, false); - hbox->pack_start (zoom_focus_box, false, false); - hbox->pack_start (snap_type_box, false, false); - hbox->pack_start (snap_mode_box, false, false); - hbox->pack_start (edit_mode_box, false, false); - - VBox *vbox = manage (new VBox); - - vbox->set_spacing (3); - vbox->set_border_width (3); - - HBox *nbox = manage (new HBox); - nudge_forward_button.signal_clicked().connect (bind (mem_fun(*this, &Editor::nudge_forward), false)); nudge_backward_button.signal_clicked().connect (bind (mem_fun(*this, &Editor::nudge_backward), false)); - nbox->pack_start (nudge_backward_button, false, false); - nbox->pack_start (nudge_forward_button, false, false); - nbox->pack_start (nudge_clock, false, false, 5); + nudge_box->pack_start (nudge_backward_button, false, false); + nudge_box->pack_start (nudge_forward_button, false, false); + nudge_box->pack_start (nudge_clock, false, false); - nudge_label.set_name ("ToolBarLabel"); - vbox->pack_start (nudge_label, false, false); - vbox->pack_start (*nbox, false, false); + /* Pack everything in... */ - hbox->pack_start (*vbox, false, false); - - hbox->show_all (); + HBox* hbox = new HBox; + hbox->set_spacing(10); tools_tearoff = new TearOff (*hbox); tools_tearoff->set_name ("MouseModeBase"); @@ -2819,11 +2720,18 @@ Editor::setup_toolbar () tools_tearoff->Visible.connect (bind (mem_fun(*this, &Editor::reattach_tearoff), static_cast (&toolbar_hbox), &tools_tearoff->tearoff_window(), 0)); - toolbar_hbox.set_spacing (8); - toolbar_hbox.set_border_width (2); + toolbar_hbox.set_spacing (10); + toolbar_hbox.set_border_width (1); - toolbar_hbox.pack_start (*tools_tearoff, false, false); toolbar_hbox.pack_start (*mouse_mode_tearoff, false, false); + toolbar_hbox.pack_start (*tools_tearoff, false, false); + + + hbox->pack_start (snap_box, false, false); + hbox->pack_start (zoom_box, false, false); + hbox->pack_start (*nudge_box, false, false); + + hbox->show_all (); toolbar_base.set_name ("ToolBarBase"); toolbar_base.add (toolbar_hbox); @@ -3055,7 +2963,7 @@ Editor::get_relevant_audio_tracks (AudioTimeAxisView& base, setroute().edit_group(); + RouteGroup* group = atv->route()->edit_group(); if (group && group->is_active()) { @@ -3067,7 +2975,7 @@ Editor::get_relevant_audio_tracks (AudioTimeAxisView& base, set (*i)) != 0) { - if (tatv->route().edit_group() == group) { + if (tatv->route()->edit_group() == group) { relevant_tracks.insert (tatv); } } @@ -3102,31 +3010,31 @@ Editor::mapover_audio_tracks (slot sl) } void -Editor::mapped_set_selected_regionview_from_click (AudioTimeAxisView& atv, uint32_t ignored, - AudioRegionView* basis, vector* all_equivs) +Editor::mapped_set_selected_regionview_from_click (RouteTimeAxisView& tv, uint32_t ignored, + RegionView* basis, vector* all_equivs) { - AudioPlaylist* pl; - vector results; - AudioRegionView* marv; - AudioDiskstream* ds; + Playlist* pl; + vector results; + RegionView* marv; + Diskstream* ds; - if ((ds = atv.get_diskstream()) == 0) { + if ((ds = tv.get_diskstream()) == 0) { /* bus */ return; } - if (&atv == &basis->get_time_axis_view()) { + if (&tv == &basis->get_time_axis_view()) { /* looking in same track as the original */ return; } - if ((pl = ds->playlist()) != 0) { - pl->get_equivalent_regions (basis->region, results); + if ((pl = dynamic_cast(ds->playlist())) != 0) { + pl->get_equivalent_regions (basis->region(), results); } - for (vector::iterator ir = results.begin(); ir != results.end(); ++ir) { - if ((marv = atv.view->find_view (**ir)) != 0) { + for (vector::iterator ir = results.begin(); ir != results.end(); ++ir) { + if ((marv = tv.view()->find_view (**ir)) != 0) { all_equivs->push_back (marv); } } @@ -3135,7 +3043,7 @@ Editor::mapped_set_selected_regionview_from_click (AudioTimeAxisView& atv, uint3 bool Editor::set_selected_regionview_from_click (bool press, Selection::Operation op, bool no_track_remove) { - vector all_equivalent_regions; + vector all_equivalent_regions; bool commit = false; if (!clicked_regionview || !clicked_audio_trackview) { @@ -3190,7 +3098,7 @@ Editor::set_selected_regionview_from_click (bool press, Selection::Operation op, commit = true; } - for (vector::iterator i = all_equivalent_regions.begin(); i != all_equivalent_regions.end(); ++i) { + for (vector::iterator i = all_equivalent_regions.begin(); i != all_equivalent_regions.end(); ++i) { selection->add (*i); } } @@ -3223,58 +3131,58 @@ Editor::set_selected_regionview_from_click (bool press, Selection::Operation op, last_frame = 0; first_frame = max_frames; - for (AudioRegionSelection::iterator x = selection->audio_regions.begin(); x != selection->audio_regions.end(); ++x) { + for (RegionSelection::iterator x = selection->regions.begin(); x != selection->regions.end(); ++x) { if (&(*x)->get_time_axis_view() == &clicked_regionview->get_time_axis_view()) { - if ((*x)->region.last_frame() > last_frame) { - last_frame = (*x)->region.last_frame(); + if ((*x)->region().last_frame() > last_frame) { + last_frame = (*x)->region().last_frame(); } - if ((*x)->region.first_frame() < first_frame) { - first_frame = (*x)->region.first_frame(); + if ((*x)->region().first_frame() < first_frame) { + first_frame = (*x)->region().first_frame(); } } } /* 2. figure out the boundaries for our search for new objects */ - switch (clicked_regionview->region.coverage (first_frame, last_frame)) { + switch (clicked_regionview->region().coverage (first_frame, last_frame)) { case OverlapNone: cerr << "no overlap, first = " << first_frame << " last = " << last_frame << " region = " - << clicked_regionview->region.first_frame() << " .. " << clicked_regionview->region.last_frame() << endl; + << clicked_regionview->region().first_frame() << " .. " << clicked_regionview->region().last_frame() << endl; - if (last_frame < clicked_regionview->region.first_frame()) { + if (last_frame < clicked_regionview->region().first_frame()) { first_frame = last_frame; - last_frame = clicked_regionview->region.last_frame(); + last_frame = clicked_regionview->region().last_frame(); } else { last_frame = first_frame; - first_frame = clicked_regionview->region.first_frame(); + first_frame = clicked_regionview->region().first_frame(); } break; case OverlapExternal: cerr << "external overlap, first = " << first_frame << " last = " << last_frame << " region = " - << clicked_regionview->region.first_frame() << " .. " << clicked_regionview->region.last_frame() << endl; + << clicked_regionview->region().first_frame() << " .. " << clicked_regionview->region().last_frame() << endl; - if (last_frame < clicked_regionview->region.first_frame()) { + if (last_frame < clicked_regionview->region().first_frame()) { first_frame = last_frame; - last_frame = clicked_regionview->region.last_frame(); + last_frame = clicked_regionview->region().last_frame(); } else { last_frame = first_frame; - first_frame = clicked_regionview->region.first_frame(); + first_frame = clicked_regionview->region().first_frame(); } break; case OverlapInternal: cerr << "internal overlap, first = " << first_frame << " last = " << last_frame << " region = " - << clicked_regionview->region.first_frame() << " .. " << clicked_regionview->region.last_frame() << endl; + << clicked_regionview->region().first_frame() << " .. " << clicked_regionview->region().last_frame() << endl; - if (last_frame < clicked_regionview->region.first_frame()) { + if (last_frame < clicked_regionview->region().first_frame()) { first_frame = last_frame; - last_frame = clicked_regionview->region.last_frame(); + last_frame = clicked_regionview->region().last_frame(); } else { last_frame = first_frame; - first_frame = clicked_regionview->region.first_frame(); + first_frame = clicked_regionview->region().first_frame(); } break; @@ -3300,18 +3208,18 @@ Editor::set_selected_regionview_from_click (bool press, Selection::Operation op, /* 3. convert to a vector of audio regions */ - vector audio_regions; + vector regions; for (list::iterator x = results.begin(); x != results.end(); ++x) { - AudioRegionView* arv; + RegionView* arv; - if ((arv = dynamic_cast(*x)) != 0) { - audio_regions.push_back (arv); + if ((arv = dynamic_cast(*x)) != 0) { + regions.push_back (arv); } } - if (!audio_regions.empty()) { - selection->add (audio_regions); + if (!regions.empty()) { + selection->add (regions); commit = true; } } @@ -3321,37 +3229,32 @@ Editor::set_selected_regionview_from_click (bool press, Selection::Operation op, } void -Editor::set_selected_regionview_from_region_list (Region& r, Selection::Operation op) +Editor::set_selected_regionview_from_region_list (Region& region, Selection::Operation op) { - vector all_equivalent_regions; - AudioRegion* region; - - if ((region = dynamic_cast(&r)) == 0) { - return; - } + vector all_equivalent_regions; for (TrackViewList::iterator i = track_views.begin(); i != track_views.end(); ++i) { - AudioTimeAxisView* tatv; + RouteTimeAxisView* tatv; - if ((tatv = dynamic_cast (*i)) != 0) { + if ((tatv = dynamic_cast (*i)) != 0) { - AudioPlaylist* pl; - vector results; - AudioRegionView* marv; - AudioDiskstream* ds; + Playlist* pl; + vector results; + RegionView* marv; + Diskstream* ds; if ((ds = tatv->get_diskstream()) == 0) { /* bus */ continue; } - if ((pl = ds->playlist()) != 0) { - pl->get_region_list_equivalent_regions (*region, results); + if ((pl = dynamic_cast(ds->playlist())) != 0) { + pl->get_region_list_equivalent_regions (region, results); } - for (vector::iterator ir = results.begin(); ir != results.end(); ++ir) { - if ((marv = tatv->view->find_view (**ir)) != 0) { + for (vector::iterator ir = results.begin(); ir != results.end(); ++ir) { + if ((marv = tatv->view()->find_view (**ir)) != 0) { all_equivalent_regions.push_back (marv); } } @@ -3380,10 +3283,10 @@ Editor::set_selected_regionview_from_region_list (Region& r, Selection::Operatio bool Editor::set_selected_regionview_from_map_event (GdkEventAny* ev, StreamView* sv, Region* r) { - AudioRegionView* rv; - AudioRegion* ar; + RegionView* rv; + Region* ar; - if ((ar = dynamic_cast (r)) == 0) { + if ((ar = dynamic_cast (r)) == 0) { return TRUE; } @@ -3395,7 +3298,7 @@ Editor::set_selected_regionview_from_map_event (GdkEventAny* ev, StreamView* sv, a single other region. */ - if (selection->audio_regions.size() > 1) { + if (selection->regions.size() > 1) { return TRUE; } @@ -3560,7 +3463,7 @@ Editor::duplicate_dialog (bool dup_region) if (sscanf (text.c_str(), "%f", ×) == 1) { if (dup_region) { - AudioRegionSelection regions; + RegionSelection regions; regions.add (clicked_regionview); duplicate_some_regions (regions, times); } else { @@ -3611,9 +3514,9 @@ Editor::edit_mode_selection_done () string choice = edit_mode_selector.get_active_text(); EditMode mode = Slide; - if (choice == _("Splice")) { + if (choice == _("Splice Edit")) { mode = Splice; - } else if (choice == _("Slide")) { + } else if (choice == _("Slide Edit")) { mode = Slide; } @@ -3629,18 +3532,18 @@ Editor::snap_type_selection_done () string choice = snap_type_selector.get_active_text(); SnapType snaptype = SnapToFrame; - + if (choice == _("Beats/3")) { - snaptype = SnapToAThirdBeat; - } else if (choice == _("Beats/4")) { - snaptype = SnapToAQuarterBeat; - } else if (choice == _("Beats/8")) { - snaptype = SnapToAEighthBeat; - } else if (choice == _("Beats/16")) { - snaptype = SnapToASixteenthBeat; - } else if (choice == _("Beats/32")) { - snaptype = SnapToAThirtysecondBeat; - } else if (choice == _("Beats")) { + snaptype = SnapToAThirdBeat; + } else if (choice == _("Beats/4")) { + snaptype = SnapToAQuarterBeat; + } else if (choice == _("Beats/8")) { + snaptype = SnapToAEighthBeat; + } else if (choice == _("Beats/16")) { + snaptype = SnapToASixteenthBeat; + } else if (choice == _("Beats/32")) { + snaptype = SnapToAThirtysecondBeat; + } else if (choice == _("Beats")) { snaptype = SnapToBeat; } else if (choice == _("Bars")) { snaptype = SnapToBar; @@ -3668,10 +3571,10 @@ Editor::snap_type_selection_done () snaptype = SnapToSeconds; } else if (choice == _("Minutes")) { snaptype = SnapToMinutes; - } else if (choice == _("None")) { + } else if (choice == _("None")) { snaptype = SnapToFrame; } - + set_snap_to (snaptype); } @@ -3685,9 +3588,9 @@ Editor::snap_mode_selection_done () string choice = snap_mode_selector.get_active_text(); SnapMode mode = SnapNormal; - if (choice == _("Normal")) { + if (choice == _("Normal Snap")) { mode = SnapNormal; - } else if (choice == _("Magnetic")) { + } else if (choice == _("Magnetic Snap")) { mode = SnapMagnetic; } @@ -3704,15 +3607,15 @@ Editor::zoom_focus_selection_done () string choice = zoom_focus_selector.get_active_text(); ZoomFocus focus_type = ZoomFocusLeft; - if (choice == _("Left")) { + if (choice == _("Focus Left")) { focus_type = ZoomFocusLeft; - } else if (choice == _("Right")) { + } else if (choice == _("Focus Right")) { focus_type = ZoomFocusRight; - } else if (choice == _("Center")) { + } else if (choice == _("Focus Center")) { focus_type = ZoomFocusCenter; - } else if (choice == _("Playhead")) { + } else if (choice == _("Focus Playhead")) { focus_type = ZoomFocusPlayhead; - } else if (choice == _("Edit Cursor")) { + } else if (choice == _("Focus Edit Cursor")) { focus_type = ZoomFocusEdit; } @@ -3782,7 +3685,7 @@ void Editor::region_selection_changed () { for (TrackViewList::iterator i = track_views.begin(); i != track_views.end(); ++i) { - (*i)->set_selected_regionviews (selection->audio_regions); + (*i)->set_selected_regionviews (selection->regions); } } @@ -4052,8 +3955,8 @@ Editor::playlist_deletion_dialog (Playlist* pl) bool Editor::audio_region_selection_covers (jack_nframes_t where) { - for (AudioRegionSelection::iterator a = selection->audio_regions.begin(); a != selection->audio_regions.end(); ++a) { - if ((*a)->region.covers (where)) { + for (RegionSelection::iterator a = selection->regions.begin(); a != selection->regions.end(); ++a) { + if ((*a)->region().covers (where)) { return true; } } @@ -4064,10 +3967,10 @@ Editor::audio_region_selection_covers (jack_nframes_t where) void Editor::prepare_for_cleanup () { - cut_buffer->clear_audio_regions (); + cut_buffer->clear_regions (); cut_buffer->clear_playlists (); - selection->clear_audio_regions (); + selection->clear_regions (); selection->clear_playlists (); } diff --git a/gtk2_ardour/editor.h b/gtk2_ardour/editor.h index 478a8c96ab..c31dfd5ede 100644 --- a/gtk2_ardour/editor.h +++ b/gtk2_ardour/editor.h @@ -40,7 +40,7 @@ #include #include -#include +#include #include #include #include @@ -69,6 +69,7 @@ namespace ARDOUR { class AudioDiskstream; class RouteGroup; class Playlist; + class AudioPlaylist; class Region; class Location; class TempoSection; @@ -83,6 +84,7 @@ namespace LADSPA { } class TimeAxisView; +class RouteTimeAxisView; class AudioTimeAxisView; class AutomationTimeAxisView; class AudioRegionView; @@ -100,6 +102,7 @@ class TrackSelection; class AutomationSelection; class MixerStrip; class StreamView; +class AudioStreamView; class ControlPoint; #ifdef FFT_ANALYSIS class AnalysisWindow; @@ -405,8 +408,8 @@ class Editor : public PublicEditor TimeAxisView* clicked_trackview; AudioTimeAxisView* clicked_audio_trackview; - AudioRegionView* clicked_regionview; - AudioRegionView* latest_regionview; + RegionView* clicked_regionview; + RegionView* latest_regionview; uint32_t clicked_selection; CrossfadeView* clicked_crossfadeview; ControlPoint* clicked_control_point; @@ -416,7 +419,7 @@ class Editor : public PublicEditor /* functions to be passed to mapover_audio_tracks(), possibly with sigc::bind()-supplied arguments */ - void mapped_set_selected_regionview_from_click (AudioTimeAxisView&, uint32_t, AudioRegionView*, vector*); + void mapped_set_selected_regionview_from_click (RouteTimeAxisView&, uint32_t, RegionView*, vector*); void mapped_use_new_playlist (AudioTimeAxisView&, uint32_t); void mapped_use_copy_playlist (AudioTimeAxisView&, uint32_t); void mapped_clear_playlist (AudioTimeAxisView&, uint32_t); @@ -426,7 +429,7 @@ class Editor : public PublicEditor void button_selection (ArdourCanvas::Item* item, GdkEvent* event, ItemType item_type); bool button_release_can_deselect; - void catch_vanishing_audio_regionview (AudioRegionView *); + void catch_vanishing_regionview (RegionView *); bool set_selected_control_point_from_click (bool press, Selection::Operation op = Selection::Set, bool with_undo = true, bool no_remove=false); bool set_selected_track_from_click (bool press, Selection::Operation op = Selection::Set, bool with_undo = true, bool no_remove=false); @@ -434,7 +437,7 @@ class Editor : public PublicEditor void set_selected_regionview_from_region_list (ARDOUR::Region& region, Selection::Operation op = Selection::Set); bool set_selected_regionview_from_map_event (GdkEventAny*, StreamView*, ARDOUR::Region*); - void collect_new_region_view (AudioRegionView *); + void collect_new_region_view (RegionView *); Gtk::Menu track_context_menu; Gtk::Menu track_region_context_menu; @@ -455,12 +458,11 @@ class Editor : public PublicEditor Gtk::Menu* build_track_selection_context_menu (jack_nframes_t); void add_dstream_context_items (Gtk::Menu_Helpers::MenuList&); void add_bus_context_items (Gtk::Menu_Helpers::MenuList&); - void add_region_context_items (StreamView*, ARDOUR::Region*, Gtk::Menu_Helpers::MenuList&); - void add_crossfade_context_items (StreamView*, ARDOUR::Crossfade*, Gtk::Menu_Helpers::MenuList&, bool many); + void add_region_context_items (AudioStreamView*, ARDOUR::Region*, Gtk::Menu_Helpers::MenuList&); + void add_crossfade_context_items (AudioStreamView*, ARDOUR::Crossfade*, Gtk::Menu_Helpers::MenuList&, bool many); void add_selection_context_items (Gtk::Menu_Helpers::MenuList&); - void handle_new_route (ARDOUR::Route&); - void handle_new_route_p (ARDOUR::Route*); + void handle_new_route (boost::shared_ptr); void remove_route (TimeAxisView *); bool route_removal; @@ -854,7 +856,7 @@ class Editor : public PublicEditor void lower_region_to_bottom (); void split_region (); void split_region_at (jack_nframes_t); - void split_regions_at (jack_nframes_t, AudioRegionSelection&); + void split_regions_at (jack_nframes_t, RegionSelection&); void crop_region_to_selection (); void set_a_regions_sync_position (ARDOUR::Region&, jack_nframes_t); void set_region_sync_from_edit_cursor (); @@ -867,13 +869,13 @@ class Editor : public PublicEditor void remove_clicked_region (); void destroy_clicked_region (); void edit_region (); - void duplicate_some_regions (AudioRegionSelection&, float times); + void duplicate_some_regions (RegionSelection&, float times); void duplicate_selection (float times); void region_fill_selection (); void region_fill_track (); - void audition_playlist_region_standalone (ARDOUR::AudioRegion&); - void audition_playlist_region_via_route (ARDOUR::AudioRegion&, ARDOUR::Route&); + void audition_playlist_region_standalone (ARDOUR::Region&); + void audition_playlist_region_via_route (ARDOUR::Region&, ARDOUR::Route&); void split_multichannel_region(); void reverse_region (); void normalize_region (); @@ -1020,7 +1022,7 @@ class Editor : public PublicEditor bool have_pending_keyboard_selection; jack_nframes_t pending_keyboard_selection_start; - ARDOUR::AudioRegion* select_region_for_operation (int dir, TimeAxisView **tv); + ARDOUR::Region* select_region_for_operation (int dir, TimeAxisView **tv); void extend_selection_to_end_of_region (bool next); void extend_selection_to_start_of_region (bool previous); @@ -1094,7 +1096,7 @@ class Editor : public PublicEditor void remove_gain_control_point (ArdourCanvas::Item*, GdkEvent*); void remove_control_point (ArdourCanvas::Item*, GdkEvent*); - void mouse_brush_insert_region (AudioRegionView*, jack_nframes_t pos); + void mouse_brush_insert_region (RegionView*, jack_nframes_t pos); void brush (jack_nframes_t); void show_verbose_time_cursor (jack_nframes_t frame, double offset = 0, double xpos=-1, double ypos=-1); @@ -1112,10 +1114,10 @@ class Editor : public PublicEditor bool canvas_fade_in_handle_event (GdkEvent* event,ArdourCanvas::Item*, AudioRegionView*); bool canvas_fade_out_event (GdkEvent* event,ArdourCanvas::Item*, AudioRegionView*); bool canvas_fade_out_handle_event (GdkEvent* event,ArdourCanvas::Item*, AudioRegionView*); - bool canvas_region_view_event (GdkEvent* event,ArdourCanvas::Item*, AudioRegionView*); - bool canvas_region_view_name_highlight_event (GdkEvent* event,ArdourCanvas::Item*, AudioRegionView*); - bool canvas_region_view_name_event (GdkEvent* event,ArdourCanvas::Item*, AudioRegionView*); - bool canvas_stream_view_event (GdkEvent* event,ArdourCanvas::Item*, AudioTimeAxisView*); + bool canvas_region_view_event (GdkEvent* event,ArdourCanvas::Item*, RegionView*); + bool canvas_region_view_name_highlight_event (GdkEvent* event,ArdourCanvas::Item*, RegionView*); + bool canvas_region_view_name_event (GdkEvent* event,ArdourCanvas::Item*, RegionView*); + bool canvas_stream_view_event (GdkEvent* event,ArdourCanvas::Item*, RouteTimeAxisView*); bool canvas_marker_event (GdkEvent* event,ArdourCanvas::Item*, Marker*); bool canvas_zoom_rect_event (GdkEvent* event,ArdourCanvas::Item*); bool canvas_tempo_marker_event (GdkEvent* event,ArdourCanvas::Item*, TempoMarker*); @@ -1263,12 +1265,7 @@ class Editor : public PublicEditor void editor_mixer_button_toggled (); - AudioClock selection_start_clock; - Gtk::Label selection_start_clock_label; - AudioClock selection_end_clock; - Gtk::Label selection_end_clock_label; AudioClock edit_cursor_clock; - Gtk::Label edit_cursor_clock_label; AudioClock zoom_range_clock; Gtk::Button zoom_in_button; Gtk::Button zoom_out_button; @@ -1280,8 +1277,8 @@ class Editor : public PublicEditor Gtk::Table toolbar_selection_clock_table; Gtk::Label toolbar_selection_cursor_label; - Gtk::Table mouse_mode_button_table; - Gtkmm2ext::TearOff* mouse_mode_tearoff; + Gtk::HBox mouse_mode_button_box; + Gtkmm2ext::TearOff* mouse_mode_tearoff; Gtk::ToggleButton mouse_select_button; Gtk::ToggleButton mouse_move_button; Gtk::ToggleButton mouse_gain_button; @@ -1299,32 +1296,23 @@ class Editor : public PublicEditor Gtk::ToggleButton global_automation_button; Gtk::ComboBoxText edit_mode_selector; - Gtk::Label edit_mode_label; - Gtk::VBox edit_mode_box; + Gtk::VBox edit_mode_box; void edit_mode_selection_done (); Gtk::ComboBoxText snap_type_selector; - Gtk::Label snap_type_label; - Gtk::VBox snap_type_box; + Gtk::ComboBoxText snap_mode_selector; + Gtk::HBox snap_box; void snap_type_selection_done (); - - Gtk::ComboBoxText snap_mode_selector; - Gtk::Label snap_mode_label; - Gtk::VBox snap_mode_box; - void snap_mode_selection_done (); Gtk::ComboBoxText zoom_focus_selector; - Gtk::Label zoom_focus_label; Gtk::VBox zoom_focus_box; void zoom_focus_selection_done (); - Gtk::Label zoom_indicator_label; - Gtk::HBox zoom_indicator_box; - Gtk::VBox zoom_indicator_vbox; + Gtk::HBox zoom_box; void update_zoom_indicator (); void zoom_adjustment_changed(); @@ -1533,12 +1521,12 @@ class Editor : public PublicEditor void start_trim (ArdourCanvas::Item*, GdkEvent*); void point_trim (GdkEvent*); void trim_motion_callback (ArdourCanvas::Item*, GdkEvent*); - void single_contents_trim (AudioRegionView&, jack_nframes_t, bool, bool, bool); - void single_start_trim (AudioRegionView&, jack_nframes_t, bool, bool); - void single_end_trim (AudioRegionView&, jack_nframes_t, bool, bool); + void single_contents_trim (RegionView&, jack_nframes_t, bool, bool, bool); + void single_start_trim (RegionView&, jack_nframes_t, bool, bool); + void single_end_trim (RegionView&, jack_nframes_t, bool, bool); void trim_finished_callback (ArdourCanvas::Item*, GdkEvent*); - void thaw_region_after_trim (AudioRegionView& rv); + void thaw_region_after_trim (RegionView& rv); void trim_region_to_edit_cursor (); void trim_region_from_edit_cursor (); @@ -1592,7 +1580,7 @@ class Editor : public PublicEditor void export_range (jack_nframes_t start, jack_nframes_t end); void export_range_markers (); - int write_region_selection(AudioRegionSelection&); + int write_region_selection(RegionSelection&); bool write_region (string path, ARDOUR::AudioRegion&); void export_region (); void bounce_region_selection (); @@ -1600,7 +1588,7 @@ class Editor : public PublicEditor void external_edit_region (); int write_audio_selection (TimeSelection&); - bool write_audio_range (ARDOUR::Playlist&, uint32_t channels, list&); + bool write_audio_range (ARDOUR::AudioPlaylist&, uint32_t channels, list&); void write_selection (); @@ -1671,7 +1659,7 @@ class Editor : public PublicEditor struct TimeStretchDialog : public ArdourDialog { ARDOUR::Session::TimeStretchRequest request; Editor& editor; - AudioRegionSelection regions; + RegionSelection regions; Gtk::ProgressBar progress_bar; Gtk::ToggleButton quick_button; Gtk::ToggleButton antialias_button; @@ -1697,7 +1685,7 @@ class Editor : public PublicEditor TimeStretchDialog* current_timestretch; static void* timestretch_thread (void *arg); - int run_timestretch (AudioRegionSelection&, float fraction); + int run_timestretch (RegionSelection&, float fraction); void do_timestretch (TimeStretchDialog&); /* editor-mixer strip */ @@ -1776,7 +1764,6 @@ class Editor : public PublicEditor Gtk::Button nudge_backward_button; Gtk::HBox nudge_hbox; Gtk::VBox nudge_vbox; - Gtk::Label nudge_label; AudioClock nudge_clock; jack_nframes_t get_nudge_distance (jack_nframes_t pos, jack_nframes_t& next); @@ -1799,11 +1786,11 @@ class Editor : public PublicEditor sigc::connection step_timeout; TimeAxisView* entered_track; - AudioRegionView* entered_regionview; + RegionView* entered_regionview; bool clear_entered_track; gint left_track_canvas (GdkEventCrossing*); void set_entered_track (TimeAxisView*); - void set_entered_regionview (AudioRegionView*); + void set_entered_regionview (RegionView*); gint left_automation_track (); bool _new_regionviews_show_envelope; diff --git a/gtk2_ardour/editor_actions.cc b/gtk2_ardour/editor_actions.cc index e20e6ee8eb..65195ca822 100644 --- a/gtk2_ardour/editor_actions.cc +++ b/gtk2_ardour/editor_actions.cc @@ -357,6 +357,8 @@ Editor::register_actions () ActionManager::session_sensitive_actions.push_back (act); act = ActionManager::register_action (editor_actions, X_("addExternalAudioAsTrack"), _("as Tracks"), bind (mem_fun(*this, &Editor::add_external_audio_action), ImportAsTrack)); ActionManager::session_sensitive_actions.push_back (act); + act = ActionManager::register_action (editor_actions, X_("addExternalAudioAsTapeTrack"), _("as Tape Tracks"), bind (mem_fun(*this, &Editor::add_external_audio_action), ImportAsTapeTrack)); + ActionManager::session_sensitive_actions.push_back (act); act = ActionManager::register_action (editor_actions, X_("addExternalAudioToTrack"), _("to Tracks"), bind (mem_fun(*this, &Editor::add_external_audio_action), ImportToTrack)); ActionManager::session_sensitive_actions.push_back (act); diff --git a/gtk2_ardour/editor_audio_import.cc b/gtk2_ardour/editor_audio_import.cc index 2c64f2cf15..7524f9605c 100644 --- a/gtk2_ardour/editor_audio_import.cc +++ b/gtk2_ardour/editor_audio_import.cc @@ -268,7 +268,7 @@ Editor::embed_sndfile (Glib::ustring path, bool split, bool multiple_files, bool idspec += string_compose(":%1", n); try { - source = AudioFileSource::create (idspec.c_str()); + source = AudioFileSource::create (idspec.c_str(), (mode == ImportAsTrack ? AudioFileSource::Destructive : AudioFileSource::Flag (0))); sources.push_back(source); } @@ -306,16 +306,18 @@ Editor::embed_sndfile (Glib::ustring path, bool split, bool multiple_files, bool } int - Editor::finish_bringing_in_audio (AudioRegion& region, uint32_t in_chans, uint32_t out_chans, AudioTrack* track, jack_nframes_t& pos, ImportMode mode) - { - switch (mode) { - case ImportAsRegion: - /* relax, its been done */ - break; +Editor::finish_bringing_in_audio (AudioRegion& region, uint32_t in_chans, uint32_t out_chans, AudioTrack* track, jack_nframes_t& pos, ImportMode mode) +{ + AudioRegion* copy; + + switch (mode) { + case ImportAsRegion: + /* relax, its been done */ + break; case ImportToTrack: if (track) { - Playlist* playlist = track->disk_stream().playlist(); + Playlist* playlist = track->diskstream().playlist(); AudioRegion* copy = new AudioRegion (region); begin_reversible_command (_("insert sndfile")); @@ -329,12 +331,22 @@ int break; case ImportAsTrack: - AudioTrack* at = session->new_audio_track (in_chans, out_chans); - AudioRegion* copy = new AudioRegion (region); - at->disk_stream().playlist()->add_region (*copy, pos); + { + boost::shared_ptr at (session->new_audio_track (in_chans, out_chans, Normal)); + copy = new AudioRegion (region); + at->diskstream().playlist()->add_region (*copy, pos); break; } + case ImportAsTapeTrack: + { + boost::shared_ptr at (session->new_audio_track (in_chans, out_chans, Destructive)); + copy = new AudioRegion (region); + at->diskstream().playlist()->add_region (*copy, pos); + break; + } + } + return 0; } diff --git a/gtk2_ardour/editor_audiotrack.cc b/gtk2_ardour/editor_audiotrack.cc index acad3371a0..5b575b4814 100644 --- a/gtk2_ardour/editor_audiotrack.cc +++ b/gtk2_ardour/editor_audiotrack.cc @@ -4,7 +4,7 @@ #include "editor.h" #include "editing.h" #include "audio_time_axis.h" -#include "regionview.h" +#include "region_view.h" #include "selection.h" using namespace ARDOUR; diff --git a/gtk2_ardour/editor_canvas.cc b/gtk2_ardour/editor_canvas.cc index 41350a1da4..e8ba2b8a60 100644 --- a/gtk2_ardour/editor_canvas.cc +++ b/gtk2_ardour/editor_canvas.cc @@ -128,7 +128,7 @@ Editor::initialize_canvas () time_line_group = new ArdourCanvas::Group (*track_canvas.root(), 0.0, 0.0); cursor_group = new ArdourCanvas::Group (*track_canvas.root(), 0.0, 0.0); - + time_canvas.set_name ("EditorTimeCanvas"); time_canvas.add_events (Gdk::POINTER_MOTION_HINT_MASK); time_canvas.set_flags (CAN_FOCUS); diff --git a/gtk2_ardour/editor_canvas_events.cc b/gtk2_ardour/editor_canvas_events.cc index 43114534c5..8e635bbe13 100644 --- a/gtk2_ardour/editor_canvas_events.cc +++ b/gtk2_ardour/editor_canvas_events.cc @@ -26,8 +26,8 @@ #include "editor.h" #include "public_editor.h" -#include "regionview.h" -#include "streamview.h" +#include "audio_region_view.h" +#include "audio_streamview.h" #include "crossfade_view.h" #include "audio_time_axis.h" #include "region_gain_line.h" @@ -212,7 +212,7 @@ Editor::typed_event (ArdourCanvas::Item* item, GdkEvent *event, ItemType type) } bool -Editor::canvas_region_view_event (GdkEvent *event, ArdourCanvas::Item* item, AudioRegionView *rv) +Editor::canvas_region_view_event (GdkEvent *event, ArdourCanvas::Item* item, RegionView *rv) { gint ret = FALSE; @@ -251,7 +251,7 @@ Editor::canvas_region_view_event (GdkEvent *event, ArdourCanvas::Item* item, Aud } bool -Editor::canvas_stream_view_event (GdkEvent *event, ArdourCanvas::Item* item, AudioTimeAxisView *tv) +Editor::canvas_stream_view_event (GdkEvent *event, ArdourCanvas::Item* item, RouteTimeAxisView *tv) { bool ret = FALSE; @@ -262,7 +262,7 @@ Editor::canvas_stream_view_event (GdkEvent *event, ArdourCanvas::Item* item, Aud clicked_regionview = 0; clicked_control_point = 0; clicked_trackview = tv; - clicked_audio_trackview = tv; + clicked_audio_trackview = dynamic_cast(tv); ret = button_press_handler (item, event, StreamItem); break; @@ -512,22 +512,25 @@ Editor::canvas_crossfade_view_event (GdkEvent* event, ArdourCanvas::Item* item, if ((atv = dynamic_cast(&tv)) != 0) { if (atv->is_audio_track()) { - - AudioPlaylist* pl = atv->get_diskstream()->playlist(); - Playlist::RegionList* rl = pl->regions_at (event_frame (event)); - if (!rl->empty()) { - DescendingRegionLayerSorter cmp; - rl->sort (cmp); + AudioPlaylist* pl; + if ((pl = dynamic_cast (atv->get_diskstream()->playlist())) != 0) { - AudioRegionView* arv = atv->view->find_view (*(dynamic_cast (rl->front()))); + Playlist::RegionList* rl = pl->regions_at (event_frame (event)); - /* proxy */ - - delete rl; + if (!rl->empty()) { + DescendingRegionLayerSorter cmp; + rl->sort (cmp); - return canvas_region_view_event (event, arv->get_canvas_group(), arv); - } + RegionView* rv = atv->view()->find_view (*rl->front()); + + /* proxy */ + + delete rl; + + return canvas_region_view_event (event, rv->get_canvas_group(), rv); + } + } } } @@ -696,7 +699,7 @@ Editor::canvas_selection_end_trim_event (GdkEvent *event, ArdourCanvas::Item* it bool -Editor::canvas_region_view_name_highlight_event (GdkEvent* event, ArdourCanvas::Item* item, AudioRegionView* rv) +Editor::canvas_region_view_name_highlight_event (GdkEvent* event, ArdourCanvas::Item* item, RegionView* rv) { bool ret = false; @@ -708,20 +711,20 @@ Editor::canvas_region_view_name_highlight_event (GdkEvent* event, ArdourCanvas:: clicked_control_point = 0; clicked_trackview = &clicked_regionview->get_time_axis_view(); clicked_audio_trackview = dynamic_cast(clicked_trackview); - ret = button_press_handler (item, event, AudioRegionViewNameHighlight); + ret = button_press_handler (item, event, RegionViewNameHighlight); break; case GDK_BUTTON_RELEASE: - ret = button_release_handler (item, event, AudioRegionViewNameHighlight); + ret = button_release_handler (item, event, RegionViewNameHighlight); break; case GDK_MOTION_NOTIFY: - ret = motion_handler (item, event, AudioRegionViewNameHighlight); + ret = motion_handler (item, event, RegionViewNameHighlight); break; case GDK_ENTER_NOTIFY: - ret = enter_handler (item, event, AudioRegionViewNameHighlight); + ret = enter_handler (item, event, RegionViewNameHighlight); break; case GDK_LEAVE_NOTIFY: - ret = leave_handler (item, event, AudioRegionViewNameHighlight); + ret = leave_handler (item, event, RegionViewNameHighlight); break; default: @@ -732,7 +735,7 @@ Editor::canvas_region_view_name_highlight_event (GdkEvent* event, ArdourCanvas:: } bool -Editor::canvas_region_view_name_event (GdkEvent *event, ArdourCanvas::Item* item, AudioRegionView* rv) +Editor::canvas_region_view_name_event (GdkEvent *event, ArdourCanvas::Item* item, RegionView* rv) { bool ret = false; @@ -744,20 +747,20 @@ Editor::canvas_region_view_name_event (GdkEvent *event, ArdourCanvas::Item* item clicked_control_point = 0; clicked_trackview = &clicked_regionview->get_time_axis_view(); clicked_audio_trackview = dynamic_cast(clicked_trackview); - ret = button_press_handler (item, event, AudioRegionViewName); + ret = button_press_handler (item, event, RegionViewName); break; case GDK_BUTTON_RELEASE: - ret = button_release_handler (item, event, AudioRegionViewName); + ret = button_release_handler (item, event, RegionViewName); break; case GDK_MOTION_NOTIFY: - ret = motion_handler (item, event, AudioRegionViewName); + ret = motion_handler (item, event, RegionViewName); break; case GDK_ENTER_NOTIFY: - ret = enter_handler (item, event, AudioRegionViewName); + ret = enter_handler (item, event, RegionViewName); break; case GDK_LEAVE_NOTIFY: - ret = leave_handler (item, event, AudioRegionViewName); + ret = leave_handler (item, event, RegionViewName); break; default: diff --git a/gtk2_ardour/editor_export_audio.cc b/gtk2_ardour/editor_export_audio.cc index 7339536e42..46a704b435 100644 --- a/gtk2_ardour/editor_export_audio.cc +++ b/gtk2_ardour/editor_export_audio.cc @@ -31,7 +31,7 @@ #include "selection.h" #include "time_axis_view.h" #include "audio_time_axis.h" -#include "regionview.h" +#include "audio_region_view.h" #include #include @@ -92,12 +92,12 @@ Editor::export_region () return; } - ExportDialog* dialog = new ExportRegionDialog (*this, &clicked_regionview->region); + ExportDialog* dialog = new ExportRegionDialog (*this, &clicked_regionview->region()); dialog->connect_to_session (session); dialog->set_range ( - clicked_regionview->region.first_frame(), - clicked_regionview->region.last_frame()); + clicked_regionview->region().first_frame(), + clicked_regionview->region().last_frame()); dialog->start_export(); } @@ -123,24 +123,26 @@ Editor::export_range_markers () } int -Editor::write_region_selection (AudioRegionSelection& regions) +Editor::write_region_selection (RegionSelection& regions) { - for (AudioRegionSelection::iterator i = regions.begin(); i != regions.end(); ++i) { - if (write_region ("", (*i)->region) == false) { - return -1; - } + for (RegionSelection::iterator i = regions.begin(); i != regions.end(); ++i) { + AudioRegionView* arv = dynamic_cast(*i); + if (arv) + if (write_region ("", arv->audio_region()) == false) + return -1; } + return 0; } void Editor::bounce_region_selection () { - for (AudioRegionSelection::iterator i = selection->audio_regions.begin(); i != selection->audio_regions.end(); ++i) { + for (RegionSelection::iterator i = selection->regions.begin(); i != selection->regions.end(); ++i) { - AudioRegion& region ((*i)->region); - AudioTimeAxisView* atv = dynamic_cast(&(*i)->get_time_axis_view()); - AudioTrack* track = dynamic_cast(&(atv->route())); + Region& region ((*i)->region()); + RouteTimeAxisView* rtv = dynamic_cast(&(*i)->get_time_axis_view()); + Track* track = dynamic_cast(rtv->route().get()); InterThreadInfo itt; @@ -287,7 +289,7 @@ Editor::write_audio_selection (TimeSelection& ts) if (atv->is_audio_track()) { - Playlist* playlist = atv->get_diskstream()->playlist(); + AudioPlaylist* playlist = dynamic_cast(atv->get_diskstream()->playlist()); if (playlist && write_audio_range (*playlist, atv->get_diskstream()->n_channels(), ts) == 0) { ret = -1; @@ -300,7 +302,7 @@ Editor::write_audio_selection (TimeSelection& ts) } bool -Editor::write_audio_range (Playlist& playlist, uint32_t channels, list& range) +Editor::write_audio_range (AudioPlaylist& playlist, uint32_t channels, list& range) { AudioFileSource* fs; const jack_nframes_t chunk_size = 4096; @@ -435,7 +437,7 @@ Editor::write_selection () { if (!selection->time.empty()) { write_audio_selection (selection->time); - } else if (!selection->audio_regions.empty()) { - write_region_selection (selection->audio_regions); + } else if (!selection->regions.empty()) { + write_region_selection (selection->regions); } } diff --git a/gtk2_ardour/editor_items.h b/gtk2_ardour/editor_items.h index 4f6010ec2c..7f3a0d3fcc 100644 --- a/gtk2_ardour/editor_items.h +++ b/gtk2_ardour/editor_items.h @@ -23,8 +23,8 @@ enum ItemType { TempoMarkerItem, MeterBarItem, TempoBarItem, - AudioRegionViewNameHighlight, - AudioRegionViewName, + RegionViewNameHighlight, + RegionViewName, StartSelectionTrimItem, EndSelectionTrimItem, AutomationTrackItem, diff --git a/gtk2_ardour/editor_keyboard.cc b/gtk2_ardour/editor_keyboard.cc index b665f8b0a6..a0368b23b0 100644 --- a/gtk2_ardour/editor_keyboard.cc +++ b/gtk2_ardour/editor_keyboard.cc @@ -23,7 +23,7 @@ #include #include "editor.h" -#include "regionview.h" +#include "region_view.h" #include "selection.h" #include "i18n.h" @@ -82,10 +82,10 @@ Editor::kbd_do_split (GdkEvent* ev) jack_nframes_t where = event_frame (ev); if (entered_regionview) { - if (selection->audio_regions.find (entered_regionview) != selection->audio_regions.end()) { - split_regions_at (where, selection->audio_regions); + if (selection->regions.find (entered_regionview) != selection->regions.end()) { + split_regions_at (where, selection->regions); } else { - AudioRegionSelection s; + RegionSelection s; s.add (entered_regionview); split_regions_at (where, s); } @@ -103,11 +103,11 @@ Editor::kbd_mute_unmute_region () { if (entered_regionview) { begin_reversible_command (_("mute region")); - XMLNode &before = entered_regionview->region.playlist()->get_state(); + XMLNode &before = entered_regionview->region().playlist()->get_state(); - entered_regionview->region.set_muted (!entered_regionview->region.muted()); + entered_regionview->region().set_muted (!entered_regionview->region().muted()); - XMLNode &after = entered_regionview->region.playlist()->get_state(); + XMLNode &after = entered_regionview->region().playlist()->get_state(); session->add_command (new MementoCommand(*(entered_regionview->region.playlist()), before, after)); commit_reversible_command(); } @@ -126,7 +126,7 @@ Editor::kbd_do_set_sync_position (GdkEvent* ev) snap_to (where); if (entered_regionview) { - set_a_regions_sync_position (entered_regionview->region, where); + set_a_regions_sync_position (entered_regionview->region(), where); } } diff --git a/gtk2_ardour/editor_keys.cc b/gtk2_ardour/editor_keys.cc index baa158cbf8..1bcaafd279 100644 --- a/gtk2_ardour/editor_keys.cc +++ b/gtk2_ardour/editor_keys.cc @@ -30,7 +30,7 @@ #include "ardour_ui.h" #include "editor.h" #include "time_axis_view.h" -#include "regionview.h" +#include "region_view.h" #include "selection.h" #include "i18n.h" @@ -66,7 +66,7 @@ Editor::keyboard_selection_begin () void Editor::keyboard_duplicate_region () { - if (selection->audio_regions.empty()) { + if (selection->regions.empty()) { return; } @@ -74,9 +74,9 @@ Editor::keyboard_duplicate_region () bool was_floating; if (get_prefix (prefix, was_floating) == 0) { - duplicate_some_regions (selection->audio_regions, prefix); + duplicate_some_regions (selection->regions, prefix); } else { - duplicate_some_regions (selection->audio_regions, 1); + duplicate_some_regions (selection->regions, 1); } } diff --git a/gtk2_ardour/editor_markers.cc b/gtk2_ardour/editor_markers.cc index c4d8f3143f..ccc1415888 100644 --- a/gtk2_ardour/editor_markers.cc +++ b/gtk2_ardour/editor_markers.cc @@ -717,9 +717,9 @@ Editor::marker_menu_set_from_selection () } } else { - if (!selection->audio_regions.empty()) { - l->set_start (selection->audio_regions.start()); - l->set_end (selection->audio_regions.end_frame()); + if (!selection->regions.empty()) { + l->set_start (selection->regions.start()); + l->set_end (selection->regions.end_frame()); } } } diff --git a/gtk2_ardour/editor_mixer.cc b/gtk2_ardour/editor_mixer.cc index a55b6f2066..246dbdc647 100644 --- a/gtk2_ardour/editor_mixer.cc +++ b/gtk2_ardour/editor_mixer.cc @@ -131,7 +131,7 @@ Editor::set_selected_mixer_strip (TimeAxisView& view) /* might be nothing to do */ - if (¤t_mixer_strip->route() == &at->route()) { + if (current_mixer_strip->route() == at->route()) { return; } @@ -221,7 +221,7 @@ Editor::current_mixer_strip_hidden () AudioTimeAxisView* tmp; if ((tmp = dynamic_cast(*i)) != 0) { - if (&(tmp->route()) == &(current_mixer_strip->route())) { + if (tmp->route() == current_mixer_strip->route()) { (*i)->set_selected (false); break; } @@ -270,8 +270,6 @@ Editor::session_going_away () group_model->clear (); edit_cursor_clock.set_session (0); - selection_start_clock.set_session (0); - selection_end_clock.set_session (0); zoom_range_clock.set_session (0); nudge_clock.set_session (0); diff --git a/gtk2_ardour/editor_mouse.cc b/gtk2_ardour/editor_mouse.cc index c7199984a8..f7abe7fdea 100644 --- a/gtk2_ardour/editor_mouse.cc +++ b/gtk2_ardour/editor_mouse.cc @@ -18,6 +18,7 @@ $Id$ */ +#include #include #include #include @@ -33,7 +34,7 @@ #include "editor.h" #include "time_axis_view.h" #include "audio_time_axis.h" -#include "regionview.h" +#include "audio_region_view.h" #include "marker.h" #include "streamview.h" #include "region_gain_line.h" @@ -183,7 +184,7 @@ Editor::set_mouse_mode (MouseMode m, bool force) show the object (region) selection. */ - for (AudioRegionSelection::iterator i = selection->audio_regions.begin(); i != selection->audio_regions.end(); ++i) { + for (RegionSelection::iterator i = selection->regions.begin(); i != selection->regions.end(); ++i) { (*i)->set_should_show_selection (true); } for (TrackViewList::iterator i = track_views.begin(); i != track_views.end(); ++i) { @@ -320,8 +321,8 @@ Editor::button_selection (ArdourCanvas::Item* item, GdkEvent* event, ItemType it commit = (c1 || c2); break; - case AudioRegionViewNameHighlight: - case AudioRegionViewName: + case RegionViewNameHighlight: + case RegionViewName: c1 = set_selected_track_from_click (press, op, true, true); c2 = set_selected_regionview_from_click (press, op, true); commit = (c1 || c2); @@ -522,12 +523,12 @@ Editor::button_press_handler (ArdourCanvas::Item* item, GdkEvent* event, ItemTyp } break; - case AudioRegionViewNameHighlight: + case RegionViewNameHighlight: start_trim (item, event); return true; break; - case AudioRegionViewName: + case RegionViewName: /* rename happens on edit clicks */ start_trim (clicked_regionview->get_name_highlight(), event); return true; @@ -693,12 +694,12 @@ Editor::button_press_handler (ArdourCanvas::Item* item, GdkEvent* event, ItemTyp switch (item_type) { - case AudioRegionViewNameHighlight: + case RegionViewNameHighlight: start_trim (item, event); return true; break; - case AudioRegionViewName: + case RegionViewName: start_trim (clicked_regionview->get_name_highlight(), event); return true; break; @@ -854,7 +855,7 @@ Editor::button_release_handler (ArdourCanvas::Item* item, GdkEvent* event, ItemT edit_meter_marker (item); break; - case AudioRegionViewName: + case RegionViewName: if (clicked_regionview->name_active()) { return mouse_rename_region (item, event); } @@ -889,8 +890,8 @@ Editor::button_release_handler (ArdourCanvas::Item* item, GdkEvent* event, ItemT break; case RegionItem: - case AudioRegionViewNameHighlight: - case AudioRegionViewName: + case RegionViewNameHighlight: + case RegionViewName: popup_track_context_menu (1, event->button.time, item_type, false, where); break; @@ -1048,9 +1049,13 @@ Editor::button_release_handler (ArdourCanvas::Item* item, GdkEvent* event, ItemT break; case MouseGain: + // Gain only makes sense for audio regions + if ( ! dynamic_cast(clicked_regionview)) + break; + switch (item_type) { case RegionItem: - clicked_regionview->add_gain_point_event (item, event); + dynamic_cast(clicked_regionview)->add_gain_point_event (item, event); return true; break; @@ -1204,7 +1209,7 @@ Editor::enter_handler (ArdourCanvas::Item* item, GdkEvent* event, ItemType item_ } break; - case AudioRegionViewNameHighlight: + case RegionViewNameHighlight: if (is_drawable() && mouse_mode == MouseObject) { track_canvas.get_window()->set_cursor (*trimmer_cursor); } @@ -1231,11 +1236,11 @@ Editor::enter_handler (ArdourCanvas::Item* item, GdkEvent* event, ItemType item_ } break; - case AudioRegionViewName: + case RegionViewName: /* when the name is not an active item, the entire name highlight is for trimming */ - if (!reinterpret_cast (item->get_data ("regionview"))->name_active()) { + if (!reinterpret_cast (item->get_data ("regionview"))->name_active()) { if (mouse_mode == MouseObject && is_drawable()) { track_canvas.get_window()->set_cursor (*trimmer_cursor); } @@ -1340,7 +1345,7 @@ Editor::leave_handler (ArdourCanvas::Item* item, GdkEvent* event, ItemType item_ ControlPoint* cp; Marker *marker; Location *loc; - AudioRegionView* rv; + RegionView* rv; bool is_start; switch (item_type) { @@ -1362,7 +1367,7 @@ Editor::leave_handler (ArdourCanvas::Item* item, GdkEvent* event, ItemType item_ hide_verbose_canvas_cursor (); break; - case AudioRegionViewNameHighlight: + case RegionViewNameHighlight: case StartSelectionTrimItem: case EndSelectionTrimItem: case EditCursorItem: @@ -1393,9 +1398,9 @@ Editor::leave_handler (ArdourCanvas::Item* item, GdkEvent* event, ItemType item_ } break; - case AudioRegionViewName: + case RegionViewName: /* see enter_handler() for notes */ - if (!reinterpret_cast (item->get_data ("regionview"))->name_active()) { + if (!reinterpret_cast (item->get_data ("regionview"))->name_active()) { if (is_drawable() && mouse_mode == MouseObject) { track_canvas.get_window()->set_cursor (*current_canvas_cursor); } @@ -1430,7 +1435,7 @@ Editor::leave_handler (ArdourCanvas::Item* item, GdkEvent* event, ItemType item_ case FadeInHandleItem: case FadeOutHandleItem: - rv = static_cast(item->get_data ("regionview")); + rv = static_cast(item->get_data ("regionview")); { ArdourCanvas::SimpleRect *rect = dynamic_cast (item); if (rect) { @@ -1525,7 +1530,7 @@ Editor::motion_handler (ArdourCanvas::Item* item, GdkEvent* event, ItemType item case PanAutomationControlPointItem: case TempoMarkerItem: case MeterMarkerItem: - case AudioRegionViewNameHighlight: + case RegionViewNameHighlight: case StartSelectionTrimItem: case EndSelectionTrimItem: case SelectionItem: @@ -1746,7 +1751,7 @@ Editor::start_fade_in_grab (ArdourCanvas::Item* item, GdkEvent* event) AudioRegionView* arv = static_cast(drag_info.data); - drag_info.pointer_frame_offset = drag_info.grab_frame - ((jack_nframes_t) arv->region.fade_in().back()->when + arv->region.position()); + drag_info.pointer_frame_offset = drag_info.grab_frame - ((jack_nframes_t) arv->audio_region().fade_in().back()->when + arv->region().position()); } void @@ -1767,17 +1772,17 @@ Editor::fade_in_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) snap_to (pos); } - if (pos < (arv->region.position() + 64)) { + if (pos < (arv->region().position() + 64)) { fade_length = 64; // this should be a minimum defined somewhere - } else if (pos > arv->region.last_frame()) { - fade_length = arv->region.length(); + } else if (pos > arv->region().last_frame()) { + fade_length = arv->region().length(); } else { - fade_length = pos - arv->region.position(); + fade_length = pos - arv->region().position(); } arv->reset_fade_in_shape_width (fade_length); - show_verbose_duration_cursor (arv->region.position(), arv->region.position() + fade_length, 10); + show_verbose_duration_cursor (arv->region().position(), arv->region().position() + fade_length, 10); drag_info.first_move = false; } @@ -1802,23 +1807,23 @@ Editor::fade_in_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* even snap_to (pos); } - if (pos < (arv->region.position() + 64)) { + if (pos < (arv->region().position() + 64)) { fade_length = 64; // this should be a minimum defined somewhere } - else if (pos > arv->region.last_frame()) { - fade_length = arv->region.length(); + else if (pos > arv->region().last_frame()) { + fade_length = arv->region().length(); } else { - fade_length = pos - arv->region.position(); + fade_length = pos - arv->region().position(); } begin_reversible_command (_("change fade in length")); - XMLNode &before = arv->region.get_state(); + XMLNode &before = arv->audio_region().get_state(); - arv->region.set_fade_in_length (fade_length); + arv->audio_region().set_fade_in_length (fade_length); - XMLNode &after = arv->region.get_state(); - session->add_command(new MementoCommand(arv->region, + XMLNode &after = arv->audio_region().get_state(); + session->add_command(new MementoCommand(arv->audio_regio(), before, after)); commit_reversible_command (); @@ -1841,7 +1846,7 @@ Editor::start_fade_out_grab (ArdourCanvas::Item* item, GdkEvent* event) AudioRegionView* arv = static_cast(drag_info.data); - drag_info.pointer_frame_offset = drag_info.grab_frame - (arv->region.length() - (jack_nframes_t) arv->region.fade_out().back()->when + arv->region.position()); + drag_info.pointer_frame_offset = drag_info.grab_frame - (arv->region().length() - (jack_nframes_t) arv->audio_region().fade_out().back()->when + arv->region().position()); } void @@ -1862,19 +1867,19 @@ Editor::fade_out_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event snap_to (pos); } - if (pos > (arv->region.last_frame() - 64)) { + if (pos > (arv->region().last_frame() - 64)) { fade_length = 64; // this should really be a minimum fade defined somewhere } - else if (pos < arv->region.position()) { - fade_length = arv->region.length(); + else if (pos < arv->region().position()) { + fade_length = arv->region().length(); } else { - fade_length = arv->region.last_frame() - pos; + fade_length = arv->region().last_frame() - pos; } arv->reset_fade_out_shape_width (fade_length); - show_verbose_duration_cursor (arv->region.last_frame() - fade_length, arv->region.last_frame(), 10); + show_verbose_duration_cursor (arv->region().last_frame() - fade_length, arv->region().last_frame(), 10); drag_info.first_move = false; } @@ -1899,23 +1904,23 @@ Editor::fade_out_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* eve snap_to (pos); } - if (pos > (arv->region.last_frame() - 64)) { + if (pos > (arv->region().last_frame() - 64)) { fade_length = 64; // this should really be a minimum fade defined somewhere } - else if (pos < arv->region.position()) { - fade_length = arv->region.length(); + else if (pos < arv->region().position()) { + fade_length = arv->region().length(); } else { - fade_length = arv->region.last_frame() - pos; + fade_length = arv->region().last_frame() - pos; } begin_reversible_command (_("change fade out length")); - XMLNode &before = arv->region.get_state(); + XMLNode &before = arv->region().get_state(); - arv->region.set_fade_out_length (fade_length); + arv->audio_region().set_fade_out_length (fade_length); - XMLNode &after = arv->region.get_state(); - session->add_command(new MementoCommand(arv->region, before, after)); + XMLNode &after = arv->region().get_state(); + session->add_command(new MementoCommand(arv->region(), before, after)); commit_reversible_command (); fade_out_drag_motion_callback (item, event); @@ -2038,7 +2043,7 @@ Editor::start_marker_grab (ArdourCanvas::Item* item, GdkEvent* event) drag_info.copied_location = new Location (*location); drag_info.pointer_frame_offset = drag_info.grab_frame - (is_start ? location->start() : location->end()); - + update_marker_drag_item (location); if (location->is_mark()) { @@ -2097,31 +2102,39 @@ Editor::marker_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) move_both = true; } - if (is_start) { // start marker + if (copy_location->is_mark()) { + /* just move it */ - if (move_both) { - copy_location->set_start (newframe); - copy_location->set_end (newframe + f_delta); - } else if (newframe < copy_location->end()) { - copy_location->set_start (newframe); - } else { - snap_to (next, 1, true); - copy_location->set_end (next); - copy_location->set_start (newframe); - } + copy_location->set_start (newframe); - } else { // end marker + } else { - if (move_both) { - copy_location->set_end (newframe); - copy_location->set_start (newframe - f_delta); - } else if (newframe > copy_location->start()) { - copy_location->set_end (newframe); + if (is_start) { // start-of-range marker - } else if (newframe > 0) { - snap_to (next, -1, true); - copy_location->set_start (next); - copy_location->set_end (newframe); + if (move_both) { + copy_location->set_start (newframe); + copy_location->set_end (newframe + f_delta); + } else if (newframe < copy_location->end()) { + copy_location->set_start (newframe); + } else { + snap_to (next, 1, true); + copy_location->set_end (next); + copy_location->set_start (newframe); + } + + } else { // end marker + + if (move_both) { + copy_location->set_end (newframe); + copy_location->set_start (newframe - f_delta); + } else if (newframe > copy_location->start()) { + copy_location->set_end (newframe); + + } else if (newframe > 0) { + snap_to (next, -1, true); + copy_location->set_start (next); + copy_location->set_end (newframe); + } } } @@ -2154,7 +2167,11 @@ Editor::marker_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event Location * location = find_location_from_marker (marker, is_start); if (location) { - location->set (drag_info.copied_location->start(), drag_info.copied_location->end()); + if (location->is_mark()) { + location->set_start (drag_info.copied_location->start()); + } else { + location->set (drag_info.copied_location->start(), drag_info.copied_location->end()); + } } XMLNode &after = session->locations()->get_state(); @@ -2553,7 +2570,8 @@ Editor::start_line_grab_from_regionview (ArdourCanvas::Item* item, GdkEvent* eve { switch (mouse_mode) { case MouseGain: - start_line_grab (clicked_regionview->get_gain_line(), event); + assert(dynamic_cast(clicked_regionview)); + start_line_grab (dynamic_cast(clicked_regionview)->get_gain_line(), event); break; default: break; @@ -2647,7 +2665,7 @@ Editor::line_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event) void Editor::start_region_grab (ArdourCanvas::Item* item, GdkEvent* event) { - if (selection->audio_regions.empty() || clicked_regionview == 0) { + if (selection->regions.empty() || clicked_regionview == 0) { return; } @@ -2661,13 +2679,13 @@ Editor::start_region_grab (ArdourCanvas::Item* item, GdkEvent* event) double speed = 1.0; TimeAxisView* tvp = clicked_trackview; - AudioTimeAxisView* tv = dynamic_cast(tvp); + RouteTimeAxisView* tv = dynamic_cast(tvp); if (tv && tv->is_audio_track()) { speed = tv->get_diskstream()->speed(); } - drag_info.last_frame_position = (jack_nframes_t) (clicked_regionview->region.position() / speed); + drag_info.last_frame_position = (jack_nframes_t) (clicked_regionview->region().position() / speed); drag_info.pointer_frame_offset = drag_info.grab_frame - drag_info.last_frame_position; drag_info.last_trackview = &clicked_regionview->get_time_axis_view(); // we want a move threshold @@ -2681,7 +2699,7 @@ Editor::start_region_grab (ArdourCanvas::Item* item, GdkEvent* event) void Editor::start_region_copy_grab (ArdourCanvas::Item* item, GdkEvent* event) { - if (selection->audio_regions.empty() || clicked_regionview == 0) { + if (selection->regions.empty() || clicked_regionview == 0) { return; } @@ -2692,7 +2710,7 @@ Editor::start_region_copy_grab (ArdourCanvas::Item* item, GdkEvent* event) start_grab(event); TimeAxisView* tv = &clicked_regionview->get_time_axis_view(); - AudioTimeAxisView* atv = dynamic_cast(tv); + RouteTimeAxisView* atv = dynamic_cast(tv); double speed = 1.0; if (atv && atv->is_audio_track()) { @@ -2700,7 +2718,7 @@ Editor::start_region_copy_grab (ArdourCanvas::Item* item, GdkEvent* event) } drag_info.last_trackview = &clicked_regionview->get_time_axis_view(); - drag_info.last_frame_position = (jack_nframes_t) (clicked_regionview->region.position() / speed); + drag_info.last_frame_position = (jack_nframes_t) (clicked_regionview->region().position() / speed); drag_info.pointer_frame_offset = drag_info.grab_frame - drag_info.last_frame_position; // we want a move threshold drag_info.want_move_threshold = true; @@ -2711,7 +2729,7 @@ Editor::start_region_copy_grab (ArdourCanvas::Item* item, GdkEvent* event) void Editor::start_region_brush_grab (ArdourCanvas::Item* item, GdkEvent* event) { - if (selection->audio_regions.empty() || clicked_regionview == 0) { + if (selection->regions.empty() || clicked_regionview == 0) { return; } @@ -2725,13 +2743,13 @@ Editor::start_region_brush_grab (ArdourCanvas::Item* item, GdkEvent* event) double speed = 1.0; TimeAxisView* tvp = clicked_trackview; - AudioTimeAxisView* tv = dynamic_cast(tvp); + RouteTimeAxisView* tv = dynamic_cast(tvp); if (tv && tv->is_audio_track()) { speed = tv->get_diskstream()->speed(); } - drag_info.last_frame_position = (jack_nframes_t) (clicked_regionview->region.position() / speed); + drag_info.last_frame_position = (jack_nframes_t) (clicked_regionview->region().position() / speed); drag_info.pointer_frame_offset = drag_info.grab_frame - drag_info.last_frame_position; drag_info.last_trackview = &clicked_regionview->get_time_axis_view(); // we want a move threshold @@ -2746,7 +2764,7 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) { double x_delta; double y_delta = 0; - AudioRegionView *rv = reinterpret_cast (drag_info.data); + RegionView* rv = reinterpret_cast (drag_info.data); jack_nframes_t pending_region_position = 0; int32_t pointer_y_span = 0, canvas_pointer_y_span = 0, original_pointer_order; int32_t visible_y_high = 0, visible_y_low = 512; //high meaning higher numbered.. not the height on the screen @@ -2766,18 +2784,18 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) /* duplicate the region(s) */ - vector new_regionviews; + vector new_regionviews; set affected_playlists; pair::iterator,bool> insert_result; - for (list::const_iterator i = selection->audio_regions.by_layer().begin(); i != selection->audio_regions.by_layer().end(); ++i) { - AudioRegionView* rv; + for (list::const_iterator i = selection->regions.by_layer().begin(); i != selection->regions.by_layer().end(); ++i) { + RegionView* rv; rv = (*i); - Playlist* to_playlist = rv->region.playlist(); - AudioTimeAxisView* atv = dynamic_cast(&rv->get_time_axis_view()); + Playlist* to_playlist = rv->region().playlist(); + RouteTimeAxisView* atv = dynamic_cast(&rv->get_time_axis_view()); insert_result = affected_playlists.insert (to_playlist); if (insert_result.second) { @@ -2786,18 +2804,21 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) latest_regionview = 0; - sigc::connection c = atv->view->AudioRegionViewAdded.connect (mem_fun(*this, &Editor::collect_new_region_view)); + sigc::connection c = atv->view()->RegionViewAdded.connect (mem_fun(*this, &Editor::collect_new_region_view)); - /* create a new region with the same name. - */ - - AudioRegion* newregion = new AudioRegion (rv->region); + /* create a new region with the same name. */ + // FIXME: ew. need a (virtual) Region::duplicate() or something? + Region* newregion = NULL; + if (dynamic_cast(&rv->region())) + newregion = new AudioRegion (dynamic_cast(rv->region())); + assert(newregion); + /* if the original region was locked, we don't care */ newregion->set_locked (false); - to_playlist->add_region (*newregion, (jack_nframes_t) (rv->region.position() * atv->get_diskstream()->speed())); + to_playlist->add_region (*newregion, (jack_nframes_t) (rv->region().position() * atv->get_diskstream()->speed())); c.disconnect (); @@ -2909,16 +2930,15 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) } } - for (list::const_iterator i = selection->audio_regions.by_layer().begin(); i != selection->audio_regions.by_layer().end(); ++i) { - AudioRegionView* rv2; - rv2 = (*i); + for (list::const_iterator i = selection->regions.by_layer().begin(); i != selection->regions.by_layer().end(); ++i) { + RegionView* rv2 = (*i); double ix1, ix2, iy1, iy2; int32_t n = 0; rv2->get_canvas_frame()->get_bounds (ix1, iy1, ix2, iy2); rv2->get_canvas_group()->i2w (ix1, iy1); TimeAxisView* tvp2 = trackview_by_y_position (iy1); - AudioTimeAxisView* atv2 = dynamic_cast(tvp2); + RouteTimeAxisView* atv2 = dynamic_cast(tvp2); if (atv2->order != original_pointer_order) { /* this isn't the pointer track */ @@ -3013,8 +3033,8 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) pending_region_position = drag_info.current_pointer_frame - drag_info.pointer_frame_offset; - sync_offset = rv->region.sync_offset (sync_dir); - sync_frame = rv->region.adjust_to_sync (pending_region_position); + sync_offset = rv->region().sync_offset (sync_dir); + sync_frame = rv->region().adjust_to_sync (pending_region_position); /* we snap if the snap modifier is not enabled. */ @@ -3033,7 +3053,7 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) pending_region_position = 0; } - if (pending_region_position > max_frames - rv->region.length()) { + if (pending_region_position > max_frames - rv->region().length()) { pending_region_position = drag_info.last_frame_position; } @@ -3075,14 +3095,11 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) } if (x_delta < 0) { - for (list::const_iterator i = selection->audio_regions.by_layer().begin(); i != selection->audio_regions.by_layer().end(); ++i) { + for (list::const_iterator i = selection->regions.by_layer().begin(); i != selection->regions.by_layer().end(); ++i) { - AudioRegionView* rv2; - rv2 = (*i); + RegionView* rv2 = (*i); - /* if any regionview is at zero, we need to know so we can - stop further leftward motion. - */ + // If any regionview is at zero, we need to know so we can stop further leftward motion. double ix1, ix2, iy1, iy2; rv2->get_canvas_frame()->get_bounds (ix1, iy1, ix2, iy2); @@ -3100,12 +3117,11 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) ************************************************************/ pair::iterator,bool> insert_result; - const list& layered_regions = selection->audio_regions.by_layer(); + const list& layered_regions = selection->regions.by_layer(); - for (list::const_iterator i = layered_regions.begin(); i != layered_regions.end(); ++i) { + for (list::const_iterator i = layered_regions.begin(); i != layered_regions.end(); ++i) { - AudioRegionView* rv; - rv = (*i); + RegionView* rv = (*i); double ix1, ix2, iy1, iy2; int32_t temp_pointer_y_span = pointer_y_span; @@ -3186,8 +3202,8 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) if (-x_delta > ix1) { x_delta = -ix1; } - } else if ((x_delta > 0) &&(rv->region.last_frame() > max_frames - x_delta)) { - x_delta = max_frames - rv->region.last_frame(); + } else if ((x_delta > 0) &&(rv->region().last_frame() > max_frames - x_delta)) { + x_delta = max_frames - rv->region().last_frame(); } if (drag_info.first_move) { @@ -3212,7 +3228,7 @@ Editor::region_drag_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) AudioTimeAxisView* atv = dynamic_cast (&rv->get_time_axis_view()); if (atv && atv->is_audio_track()) { - AudioPlaylist* pl = atv->get_diskstream()->playlist(); + AudioPlaylist* pl = dynamic_cast(atv->get_diskstream()->playlist()); if (pl) { /* only freeze and capture state once */ @@ -3248,11 +3264,11 @@ void Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event) { jack_nframes_t where; - AudioRegionView* rv = reinterpret_cast (drag_info.data); + RegionView* rv = reinterpret_cast (drag_info.data); pair::iterator,bool> insert_result; bool nocommit = true; double speed; - AudioTimeAxisView* atv; + RouteTimeAxisView* atv; bool regionview_y_movement; bool regionview_x_movement; @@ -3286,7 +3302,7 @@ Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event speed = atv->get_diskstream()->speed(); } - regionview_x_movement = (drag_info.last_frame_position != (jack_nframes_t) (rv->region.position()/speed)); + regionview_x_movement = (drag_info.last_frame_position != (jack_nframes_t) (rv->region().position()/speed)); regionview_y_movement = (drag_info.last_trackview != &rv->get_time_axis_view()); //printf ("last_frame: %s position is %lu %g\n", rv->get_time_axis_view().name().c_str(), drag_info.last_frame_position, speed); @@ -3296,13 +3312,13 @@ Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event /* motion between tracks */ - list new_selection; + list new_selection; /* moved to a different audio track. */ - for (list::const_iterator i = selection->audio_regions.by_layer().begin(); i != selection->audio_regions.by_layer().end(); ) { + for (list::const_iterator i = selection->regions.by_layer().begin(); i != selection->regions.by_layer().end(); ) { - AudioRegionView* rv2 = (*i); + RegionView* rv2 = (*i); /* the region that used to be in the old playlist is not moved to the new one - we make a copy of it. as a result, @@ -3319,7 +3335,7 @@ Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event /* first, freeze the target tracks */ - for (list::const_iterator i = new_selection.begin(); i != new_selection.end();i++ ) { + for (list::const_iterator i = new_selection.begin(); i != new_selection.end();i++ ) { Playlist* from_playlist; Playlist* to_playlist; @@ -3331,7 +3347,7 @@ Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event TimeAxisView* tvp2 = trackview_by_y_position (iy1); AudioTimeAxisView* atv2 = dynamic_cast(tvp2); - from_playlist = (*i)->region.playlist(); + from_playlist = (*i)->region().playlist(); to_playlist = atv2->playlist(); /* the from_playlist was frozen in the "first_move" case @@ -3354,7 +3370,7 @@ Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event /* now do it again with the actual operations */ - for (list::const_iterator i = new_selection.begin(); i != new_selection.end();i++ ) { + for (list::const_iterator i = new_selection.begin(); i != new_selection.end();i++ ) { Playlist* from_playlist; Playlist* to_playlist; @@ -3366,17 +3382,17 @@ Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event TimeAxisView* tvp2 = trackview_by_y_position (iy1); AudioTimeAxisView* atv2 = dynamic_cast(tvp2); - from_playlist = (*i)->region.playlist(); + from_playlist = (*i)->region().playlist(); to_playlist = atv2->playlist(); latest_regionview = 0; where = (jack_nframes_t) (unit_to_frame (ix1) * speed); - Region* new_region = createRegion ((*i)->region); + Region* new_region = createRegion ((*i)->region()); - from_playlist->remove_region (&((*i)->region)); + from_playlist->remove_region (&((*i)->region())); - sigc::connection c = atv2->view->AudioRegionViewAdded.connect (mem_fun(*this, &Editor::collect_new_region_view)); + sigc::connection c = atv2->view()->RegionViewAdded.connect (mem_fun(*this, &Editor::collect_new_region_view)); to_playlist->add_region (*new_region, where); c.disconnect (); @@ -3389,11 +3405,11 @@ Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event /* motion within a single track */ - for (list::const_iterator i = selection->audio_regions.by_layer().begin(); i != selection->audio_regions.by_layer().end(); ++i) { + for (list::const_iterator i = selection->regions.by_layer().begin(); i != selection->regions.by_layer().end(); ++i) { rv = (*i); - if (rv->region.locked()) { + if (rv->region().locked()) { continue; } @@ -3415,14 +3431,14 @@ Editor::region_drag_finished_callback (ArdourCanvas::Item* item, GdkEvent* event } else { - where = rv->region.position(); + where = rv->region().position(); } rv->get_time_axis_view().reveal_dependent_views (*rv); /* no need to add an undo here, we did that when we added this playlist to motion_frozen playlists */ - rv->region.set_position (where, (void *) this); + rv->region().set_position (where, (void *) this); } } @@ -3456,15 +3472,15 @@ Editor::region_view_item_click (AudioRegionView& rv, GdkEventButton* event) if (Keyboard::modifier_state_equals (event->state, Keyboard::ModifierMask (Keyboard::Control|Keyboard::Alt))) { - align_region (rv.region, SyncPoint, (jack_nframes_t) (edit_cursor->current_frame * speed)); + align_region (rv.region(), SyncPoint, (jack_nframes_t) (edit_cursor->current_frame * speed)); } else if (Keyboard::modifier_state_equals (event->state, Keyboard::ModifierMask (Keyboard::Control|Keyboard::Shift))) { - align_region (rv.region, End, (jack_nframes_t) (edit_cursor->current_frame * speed)); + align_region (rv.region(), End, (jack_nframes_t) (edit_cursor->current_frame * speed)); } else { - align_region (rv.region, Start, (jack_nframes_t) (edit_cursor->current_frame * speed)); + align_region (rv.region(), Start, (jack_nframes_t) (edit_cursor->current_frame * speed)); } } } @@ -3581,7 +3597,7 @@ Editor::show_verbose_duration_cursor (jack_nframes_t start, jack_nframes_t end, } void -Editor::collect_new_region_view (AudioRegionView* rv) +Editor::collect_new_region_view (RegionView* rv) { latest_regionview = rv; } @@ -3614,7 +3630,7 @@ Editor::start_selection_grab (ArdourCanvas::Item* item, GdkEvent* event) */ latest_regionview = 0; - sigc::connection c = clicked_audio_trackview->view->AudioRegionViewAdded.connect (mem_fun(*this, &Editor::collect_new_region_view)); + sigc::connection c = clicked_audio_trackview->view()->RegionViewAdded.connect (mem_fun(*this, &Editor::collect_new_region_view)); /* A selection grab currently creates two undo/redo operations, one for creating the new region and another for moving it. @@ -3650,7 +3666,7 @@ Editor::start_selection_grab (ArdourCanvas::Item* item, GdkEvent* event) start_grab (event); drag_info.last_trackview = clicked_trackview; - drag_info.last_frame_position = latest_regionview->region.position(); + drag_info.last_frame_position = latest_regionview->region().position(); drag_info.pointer_frame_offset = drag_info.grab_frame - drag_info.last_frame_position; show_verbose_time_cursor (drag_info.last_frame_position, 10); @@ -3891,9 +3907,9 @@ Editor::start_trim (ArdourCanvas::Item* item, GdkEvent* event) speed = tv->get_diskstream()->speed(); } - jack_nframes_t region_start = (jack_nframes_t) (clicked_regionview->region.position() / speed); - jack_nframes_t region_end = (jack_nframes_t) (clicked_regionview->region.last_frame() / speed); - jack_nframes_t region_length = (jack_nframes_t) (clicked_regionview->region.length() / speed); + jack_nframes_t region_start = (jack_nframes_t) (clicked_regionview->region().position() / speed); + jack_nframes_t region_end = (jack_nframes_t) (clicked_regionview->region().last_frame() / speed); + jack_nframes_t region_length = (jack_nframes_t) (clicked_regionview->region().length() / speed); motion_frozen_playlists.clear(); @@ -3933,7 +3949,7 @@ Editor::start_trim (ArdourCanvas::Item* item, GdkEvent* event) void Editor::trim_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) { - AudioRegionView* rv = clicked_regionview; + RegionView* rv = clicked_regionview; jack_nframes_t frame_delta = 0; bool left_direction; bool obey_snap = !Keyboard::modifier_state_contains (event->button.state, Keyboard::snap_modifier()); @@ -3945,7 +3961,7 @@ Editor::trim_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) double speed = 1.0; TimeAxisView* tvp = clicked_trackview; - AudioTimeAxisView* tv = dynamic_cast(tvp); + RouteTimeAxisView* tv = dynamic_cast(tvp); pair::iterator,bool> insert_result; if (tv && tv->is_audio_track()) { @@ -3984,11 +4000,14 @@ Editor::trim_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) begin_reversible_command (trim_type); - for (list::const_iterator i = selection->audio_regions.by_layer().begin(); i != selection->audio_regions.by_layer().end(); ++i) { - (*i)->region.freeze (); - (*i)->temporarily_hide_envelope (); + for (list::const_iterator i = selection->regions.by_layer().begin(); i != selection->regions.by_layer().end(); ++i) { + (*i)->region().freeze (); + + AudioRegionView* const arv = dynamic_cast(*i); + if (arv) + arv->temporarily_hide_envelope (); - Playlist * pl = (*i)->region.playlist(); + Playlist * pl = (*i)->region().playlist(); insert_result = motion_frozen_playlists.insert (pl); if (insert_result.second) { session->add_command(new MementoUndoCommand(*pl, pl->get_state())); @@ -4004,20 +4023,20 @@ Editor::trim_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) switch (trim_op) { case StartTrim: - if ((left_direction == false) && (drag_info.current_pointer_frame <= rv->region.first_frame()/speed)) { + if ((left_direction == false) && (drag_info.current_pointer_frame <= rv->region().first_frame()/speed)) { break; } else { - for (list::const_iterator i = selection->audio_regions.by_layer().begin(); i != selection->audio_regions.by_layer().end(); ++i) { + for (list::const_iterator i = selection->regions.by_layer().begin(); i != selection->regions.by_layer().end(); ++i) { single_start_trim (**i, frame_delta, left_direction, obey_snap); } break; } case EndTrim: - if ((left_direction == true) && (drag_info.current_pointer_frame > (jack_nframes_t) (rv->region.last_frame()/speed))) { + if ((left_direction == true) && (drag_info.current_pointer_frame > (jack_nframes_t) (rv->region().last_frame()/speed))) { break; } else { - for (list::const_iterator i = selection->audio_regions.by_layer().begin(); i != selection->audio_regions.by_layer().end(); ++i) { + for (list::const_iterator i = selection->regions.by_layer().begin(); i != selection->regions.by_layer().end(); ++i) { single_end_trim (**i, frame_delta, left_direction, obey_snap); } break; @@ -4031,8 +4050,8 @@ Editor::trim_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) swap_direction = true; } - for (list::const_iterator i = selection->audio_regions.by_layer().begin(); - i != selection->audio_regions.by_layer().end(); ++i) + for (list::const_iterator i = selection->regions.by_layer().begin(); + i != selection->regions.by_layer().end(); ++i) { single_contents_trim (**i, frame_delta, left_direction, swap_direction, obey_snap); } @@ -4042,10 +4061,10 @@ Editor::trim_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) switch (trim_op) { case StartTrim: - show_verbose_time_cursor((jack_nframes_t) (rv->region.position()/speed), 10); + show_verbose_time_cursor((jack_nframes_t) (rv->region().position()/speed), 10); break; case EndTrim: - show_verbose_time_cursor((jack_nframes_t) (rv->region.last_frame()/speed), 10); + show_verbose_time_cursor((jack_nframes_t) (rv->region().last_frame()/speed), 10); break; case ContentsTrim: show_verbose_time_cursor(drag_info.current_pointer_frame, 10); @@ -4057,9 +4076,9 @@ Editor::trim_motion_callback (ArdourCanvas::Item* item, GdkEvent* event) } void -Editor::single_contents_trim (AudioRegionView& rv, jack_nframes_t frame_delta, bool left_direction, bool swap_direction, bool obey_snap) +Editor::single_contents_trim (RegionView& rv, jack_nframes_t frame_delta, bool left_direction, bool swap_direction, bool obey_snap) { - Region& region (rv.region); + Region& region (rv.region()); if (region.locked()) { return; @@ -4069,7 +4088,7 @@ Editor::single_contents_trim (AudioRegionView& rv, jack_nframes_t frame_delta, b double speed = 1.0; TimeAxisView* tvp = clicked_trackview; - AudioTimeAxisView* tv = dynamic_cast(tvp); + RouteTimeAxisView* tv = dynamic_cast(tvp); if (tv && tv->is_audio_track()) { speed = tv->get_diskstream()->speed(); @@ -4097,9 +4116,9 @@ Editor::single_contents_trim (AudioRegionView& rv, jack_nframes_t frame_delta, b } void -Editor::single_start_trim (AudioRegionView& rv, jack_nframes_t frame_delta, bool left_direction, bool obey_snap) +Editor::single_start_trim (RegionView& rv, jack_nframes_t frame_delta, bool left_direction, bool obey_snap) { - Region& region (rv.region); + Region& region (rv.region()); if (region.locked()) { return; @@ -4131,9 +4150,9 @@ Editor::single_start_trim (AudioRegionView& rv, jack_nframes_t frame_delta, bool } void -Editor::single_end_trim (AudioRegionView& rv, jack_nframes_t frame_delta, bool left_direction, bool obey_snap) +Editor::single_end_trim (RegionView& rv, jack_nframes_t frame_delta, bool left_direction, bool obey_snap) { - Region& region (rv.region); + Region& region (rv.region()); if (region.locked()) { return; @@ -4172,8 +4191,8 @@ Editor::trim_finished_callback (ArdourCanvas::Item* item, GdkEvent* event) thaw_region_after_trim (*clicked_regionview); } else { - for (list::const_iterator i = selection->audio_regions.by_layer().begin(); - i != selection->audio_regions.by_layer().end(); ++i) + for (list::const_iterator i = selection->regions.by_layer().begin(); + i != selection->regions.by_layer().end(); ++i) { thaw_region_after_trim (**i); } @@ -4196,7 +4215,7 @@ Editor::trim_finished_callback (ArdourCanvas::Item* item, GdkEvent* event) void Editor::point_trim (GdkEvent* event) { - AudioRegionView* rv = clicked_regionview; + RegionView* rv = clicked_regionview; jack_nframes_t new_bound = drag_info.current_pointer_frame; if (!Keyboard::modifier_state_contains (event->button.state, Keyboard::snap_modifier())) { @@ -4211,13 +4230,13 @@ Editor::point_trim (GdkEvent* event) if (rv->get_selected()) { - for (list::const_iterator i = selection->audio_regions.by_layer().begin(); - i != selection->audio_regions.by_layer().end(); ++i) + for (list::const_iterator i = selection->regions.by_layer().begin(); + i != selection->regions.by_layer().end(); ++i) { - if (!(*i)->region.locked()) { + if (!(*i)->region().locked()) { Playlist *pl = (*i)->region.playlist(); XMLNode &before = pl->get_state(); - (*i)->region.trim_front (new_bound, this); + (*i)->region().trim_front (new_bound, this); XMLNode &after = pl->get_state(); session->add_command(new MementoCommand(*pl, before, after)); } @@ -4225,10 +4244,10 @@ Editor::point_trim (GdkEvent* event) } else { - if (!rv->region.locked()) { - Playlist *pl = rv->region.playlist(); + if (!rv->region().locked()) { + Playlist *pl = rv->region().playlist(); XMLNode &before = pl->get_state(); - rv->region.trim_front (new_bound, this); + rv->region().trim_front (new_bound, this); XMLNode &after = pl->get_state(); session->add_command(new MementoCommand(*pl, before, after)); } @@ -4243,12 +4262,12 @@ Editor::point_trim (GdkEvent* event) if (rv->get_selected()) { - for (list::const_iterator i = selection->audio_regions.by_layer().begin(); i != selection->audio_regions.by_layer().end(); ++i) + for (list::const_iterator i = selection->regions.by_layer().begin(); i != selection->regions.by_layer().end(); ++i) { - if (!(*i)->region.locked()) { - Playlist *pl = (*i)->region.playlist(); + if (!(*i)->region().locked()) { + Playlist *pl = (*i)->region().playlist(); XMLNode &before = pl->get_state(); - (*i)->region.trim_end (new_bound, this); + (*i)->region().trim_end (new_bound, this); XMLNode &after = pl->get_state(); session->add_command(new MementoCommand(*pl, before, after)); } @@ -4256,10 +4275,10 @@ Editor::point_trim (GdkEvent* event) } else { - if (!rv->region.locked()) { - Playlist *pl = rv->region.playlist(); + if (!rv->region().locked()) { + Playlist *pl = rv->region().playlist(); XMLNode &before = pl->get_state(); - rv->region.trim_end (new_bound, this); + rv->region().trim_end (new_bound, this); XMLNode &after = pl->get_state(); session->add_command (new MementoCommand(*pl, before, after)); } @@ -4274,9 +4293,9 @@ Editor::point_trim (GdkEvent* event) } void -Editor::thaw_region_after_trim (AudioRegionView& rv) +Editor::thaw_region_after_trim (RegionView& rv) { - Region& region (rv.region); + Region& region (rv.region()); if (region.locked()) { return; @@ -4286,7 +4305,9 @@ Editor::thaw_region_after_trim (AudioRegionView& rv) XMLNode &after = region.playlist()->get_state(); session->add_command (new MementoRedoCommand(*(region.playlist()), after)); - rv.unhide_envelope (); + AudioRegionView* arv = dynamic_cast(&rv); + if (arv) + arv->unhide_envelope (); } void @@ -4679,7 +4700,7 @@ Editor::end_rubberband_select (ArdourCanvas::Item* item, GdkEvent* event) } } else { - selection->clear_audio_regions(); + selection->clear_regions(); selection->clear_points (); selection->clear_lines (); } @@ -4696,7 +4717,7 @@ Editor::mouse_rename_region (ArdourCanvas::Item* item, GdkEvent* event) ArdourPrompter prompter (false); prompter.set_prompt (_("Name for region:")); - prompter.set_initial_text (clicked_regionview->region.name()); + prompter.set_initial_text (clicked_regionview->region().name()); prompter.add_button (_("Rename"), Gtk::RESPONSE_ACCEPT); prompter.set_response_sensitive (Gtk::RESPONSE_ACCEPT, false); prompter.show_all (); @@ -4705,7 +4726,7 @@ Editor::mouse_rename_region (ArdourCanvas::Item* item, GdkEvent* event) string str; prompter.get_result(str); if (str.length()) { - clicked_regionview->region.set_name (str); + clicked_regionview->region().set_name (str); } break; } @@ -4727,7 +4748,7 @@ Editor::start_time_fx (ArdourCanvas::Item* item, GdkEvent* event) void Editor::time_fx_motion (ArdourCanvas::Item *item, GdkEvent* event) { - AudioRegionView* rv = clicked_regionview; + RegionView* rv = clicked_regionview; if (!Keyboard::modifier_state_contains (event->button.state, Keyboard::snap_modifier())) { snap_to (drag_info.current_pointer_frame); @@ -4737,8 +4758,8 @@ Editor::time_fx_motion (ArdourCanvas::Item *item, GdkEvent* event) return; } - if (drag_info.current_pointer_frame > rv->region.position()) { - rv->get_time_axis_view().show_timestretch (rv->region.position(), drag_info.current_pointer_frame); + if (drag_info.current_pointer_frame > rv->region().position()) { + rv->get_time_axis_view().show_timestretch (rv->region().position(), drag_info.current_pointer_frame); } drag_info.last_pointer_frame = drag_info.current_pointer_frame; @@ -4756,21 +4777,25 @@ Editor::end_time_fx (ArdourCanvas::Item* item, GdkEvent* event) return; } - jack_nframes_t newlen = drag_info.last_pointer_frame - clicked_regionview->region.position(); - float percentage = (float) ((double) newlen - (double) clicked_regionview->region.length()) / ((double) newlen) * 100.0f; + jack_nframes_t newlen = drag_info.last_pointer_frame - clicked_regionview->region().position(); + float percentage = (float) ((double) newlen - (double) clicked_regionview->region().length()) / ((double) newlen) * 100.0f; begin_reversible_command (_("timestretch")); - if (run_timestretch (selection->audio_regions, percentage) == 0) { + if (run_timestretch (selection->regions, percentage) == 0) { session->commit_reversible_command (); } } void -Editor::mouse_brush_insert_region (AudioRegionView* rv, jack_nframes_t pos) +Editor::mouse_brush_insert_region (RegionView* rv, jack_nframes_t pos) { /* no brushing without a useful snap setting */ + // FIXME + AudioRegionView* arv = dynamic_cast(rv); + assert(arv); + switch (snap_mode) { case SnapMagnetic: return; /* can't work because it allows region to be placed anywhere */ @@ -4790,11 +4815,11 @@ Editor::mouse_brush_insert_region (AudioRegionView* rv, jack_nframes_t pos) /* don't brush a copy over the original */ - if (pos == rv->region.position()) { + if (pos == rv->region().position()) { return; } - AudioTimeAxisView* atv = dynamic_cast(&rv->get_time_axis_view()); + RouteTimeAxisView* atv = dynamic_cast(&arv->get_time_axis_view()); if (atv == 0 || !atv->is_audio_track()) { return; @@ -4804,7 +4829,7 @@ Editor::mouse_brush_insert_region (AudioRegionView* rv, jack_nframes_t pos) double speed = atv->get_diskstream()->speed(); XMLNode &before = playlist->get_state(); - playlist->add_region (*(new AudioRegion (rv->region)), (jack_nframes_t) (pos * speed)); + playlist->add_region (*(new AudioRegion (arv->audio_region)), (jack_nframes_t) (pos * speed)); XMLNode &after = playlist->get_state(); session->add_command(new MementoCommand(*playlist, before, after)); diff --git a/gtk2_ardour/editor_ops.cc b/gtk2_ardour/editor_ops.cc index e9fcc028e6..d98be4f088 100644 --- a/gtk2_ardour/editor_ops.cc +++ b/gtk2_ardour/editor_ops.cc @@ -52,7 +52,7 @@ #include "audio_time_axis.h" #include "automation_time_axis.h" #include "streamview.h" -#include "regionview.h" +#include "audio_region_view.h" #include "rgb_macros.h" #include "selection_templates.h" #include "selection.h" @@ -187,29 +187,31 @@ Editor::split_region () void Editor::split_region_at (jack_nframes_t where) { - split_regions_at (where, selection->audio_regions); + split_regions_at (where, selection->regions); } void -Editor::split_regions_at (jack_nframes_t where, AudioRegionSelection& regions) +Editor::split_regions_at (jack_nframes_t where, RegionSelection& regions) { begin_reversible_command (_("split")); snap_to (where); - for (AudioRegionSelection::iterator a = regions.begin(); a != regions.end(); ) { + for (RegionSelection::iterator a = regions.begin(); a != regions.end(); ) { - AudioRegionSelection::iterator tmp; + RegionSelection::iterator tmp; tmp = a; ++tmp; - Playlist* pl = (*a)->region.playlist(); + Playlist* pl = (*a)->region().playlist(); - _new_regionviews_show_envelope = (*a)->envelope_visible(); + AudioRegionView* const arv = dynamic_cast(*a); + if (arv) + _new_regionviews_show_envelope = arv->envelope_visible(); if (pl) { XMLNode &before = pl->get_state(); - pl->split_region ((*a)->region, where); + pl->split_region ((*a)->region(), where); XMLNode &after = pl->get_state(); session->add_command(new MementoCommand(*pl, before, after)); } @@ -232,7 +234,7 @@ Editor::remove_clicked_region () begin_reversible_command (_("remove region")); XMLNode &before = playlist->get_state(); - playlist->remove_region (&clicked_regionview->region); + playlist->remove_region (&clicked_regionview->region()); XMLNode &after = playlist->get_state(); session->add_command(new MementoCommand(*playlist, before, after)); commit_reversible_command (); @@ -241,7 +243,7 @@ Editor::remove_clicked_region () void Editor::destroy_clicked_region () { - int32_t selected = selection->audio_regions.size(); + int32_t selected = selection->regions.size(); if (!session || clicked_regionview == 0 && selected == 0) { return; @@ -273,29 +275,29 @@ Do you really want to destroy %1 ?"), if (selected > 0) { list r; - for (AudioRegionSelection::iterator i = selection->audio_regions.begin(); i != selection->audio_regions.end(); ++i) { - r.push_back (&(*i)->region); + for (RegionSelection::iterator i = selection->regions.begin(); i != selection->regions.end(); ++i) { + r.push_back (&(*i)->region()); } session->destroy_regions (r); } else if (clicked_regionview) { - session->destroy_region (&clicked_regionview->region); + session->destroy_region (&clicked_regionview->region()); } } -AudioRegion * +Region * Editor::select_region_for_operation (int dir, TimeAxisView **tv) { - AudioRegionView* rv; - AudioRegion *region; + RegionView* rv; + Region *region; jack_nframes_t start = 0; if (selection->time.start () == selection->time.end_frame ()) { /* no current selection-> is there a selected regionview? */ - if (selection->audio_regions.empty()) { + if (selection->regions.empty()) { return 0; } @@ -303,26 +305,26 @@ Editor::select_region_for_operation (int dir, TimeAxisView **tv) region = 0; - if (!selection->audio_regions.empty()) { + if (!selection->regions.empty()) { - rv = *(selection->audio_regions.begin()); + rv = *(selection->regions.begin()); (*tv) = &rv->get_time_axis_view(); - region = &rv->region; + region = &rv->region(); } else if (!selection->tracks.empty()) { (*tv) = selection->tracks.front(); - AudioTimeAxisView* atv; + RouteTimeAxisView* rtv; - if ((atv = dynamic_cast (*tv)) != 0) { + if ((rtv = dynamic_cast (*tv)) != 0) { Playlist *pl; - if ((pl = atv->playlist()) == 0) { + if ((pl = rtv->playlist()) == 0) { return 0; } - region = dynamic_cast (pl->top_region_at (start)); + region = pl->top_region_at (start); } } @@ -394,12 +396,12 @@ Editor::nudge_forward (bool next) if (!session) return; - if (!selection->audio_regions.empty()) { + if (!selection->regions.empty()) { begin_reversible_command (_("nudge forward")); - for (AudioRegionSelection::iterator i = selection->audio_regions.begin(); i != selection->audio_regions.end(); ++i) { - AudioRegion& r ((*i)->region); + for (RegionSelection::iterator i = selection->regions.begin(); i != selection->regions.end(); ++i) { + Region& r ((*i)->region()); distance = get_nudge_distance (r.position(), next_distance); @@ -429,12 +431,12 @@ Editor::nudge_backward (bool next) if (!session) return; - if (!selection->audio_regions.empty()) { + if (!selection->regions.empty()) { begin_reversible_command (_("nudge forward")); - for (AudioRegionSelection::iterator i = selection->audio_regions.begin(); i != selection->audio_regions.end(); ++i) { - AudioRegion& r ((*i)->region); + for (RegionSelection::iterator i = selection->regions.begin(); i != selection->regions.end(); ++i) { + Region& r ((*i)->region()); distance = get_nudge_distance (r.position(), next_distance); @@ -474,14 +476,14 @@ Editor::nudge_forward_capture_offset () if (!session) return; - if (!selection->audio_regions.empty()) { + if (!selection->regions.empty()) { begin_reversible_command (_("nudge forward")); distance = session->worst_output_latency(); - for (AudioRegionSelection::iterator i = selection->audio_regions.begin(); i != selection->audio_regions.end(); ++i) { - AudioRegion& r ((*i)->region); + for (RegionSelection::iterator i = selection->regions.begin(); i != selection->regions.end(); ++i) { + Region& r ((*i)->region()); XMLNode &before = r.playlist()->get_state(); r.set_position (r.position() + distance, this); @@ -501,14 +503,14 @@ Editor::nudge_backward_capture_offset () if (!session) return; - if (!selection->audio_regions.empty()) { + if (!selection->regions.empty()) { begin_reversible_command (_("nudge forward")); distance = session->worst_output_latency(); - for (AudioRegionSelection::iterator i = selection->audio_regions.begin(); i != selection->audio_regions.end(); ++i) { - AudioRegion& r ((*i)->region); + for (RegionSelection::iterator i = selection->regions.begin(); i != selection->regions.end(); ++i) { + Region& r ((*i)->region()); XMLNode &before = r.playlist()->get_state(); @@ -789,8 +791,8 @@ Editor::cursor_to_selection_start (Cursor *cursor) jack_nframes_t pos = 0; switch (mouse_mode) { case MouseObject: - if (!selection->audio_regions.empty()) { - pos = selection->audio_regions.start(); + if (!selection->regions.empty()) { + pos = selection->regions.start(); } break; @@ -818,8 +820,8 @@ Editor::cursor_to_selection_end (Cursor *cursor) switch (mouse_mode) { case MouseObject: - if (!selection->audio_regions.empty()) { - pos = selection->audio_regions.end_frame(); + if (!selection->regions.empty()) { + pos = selection->regions.end_frame(); } break; @@ -1319,12 +1321,12 @@ Editor::add_location_from_playhead_cursor () void Editor::add_location_from_audio_region () { - if (selection->audio_regions.empty()) { + if (selection->regions.empty()) { return; } - AudioRegionView* rv = *(selection->audio_regions.begin()); - Region& region = rv->region; + RegionView* rv = *(selection->regions.begin()); + Region& region = rv->region(); Location *location = new Location (region.position(), region.last_frame(), region.name()); session->begin_reversible_command (_("add marker")); @@ -1452,12 +1454,12 @@ Editor::select_all_within (jack_nframes_t start, jack_nframes_t end, double top, void Editor::set_selection_from_audio_region () { - if (selection->audio_regions.empty()) { + if (selection->regions.empty()) { return; } - AudioRegionView* rv = *(selection->audio_regions.begin()); - Region& region = rv->region; + RegionView* rv = *(selection->regions.begin()); + Region& region = rv->region(); begin_reversible_command (_("set selection from region")); selection->set (0, region.position(), region.last_frame()); @@ -1840,13 +1842,13 @@ Editor::insert_region_list_drag (AudioRegion& region, int x, int y) void Editor::insert_region_list_selection (float times) { - AudioTimeAxisView *tv = 0; + RouteTimeAxisView *tv = 0; Playlist *playlist; if (clicked_audio_trackview != 0) { tv = clicked_audio_trackview; } else if (!selection->tracks.empty()) { - if ((tv = dynamic_cast(selection->tracks.front())) == 0) { + if ((tv = dynamic_cast(selection->tracks.front())) == 0) { return; } } else { @@ -1941,23 +1943,23 @@ Editor::play_selection () void Editor::play_selected_region () { - if (!selection->audio_regions.empty()) { - AudioRegionView *rv = *(selection->audio_regions.begin()); + if (!selection->regions.empty()) { + RegionView *rv = *(selection->regions.begin()); - session->request_bounded_roll (rv->region.position(), rv->region.last_frame()); + session->request_bounded_roll (rv->region().position(), rv->region().last_frame()); } } void Editor::loop_selected_region () { - if (!selection->audio_regions.empty()) { - AudioRegionView *rv = *(selection->audio_regions.begin()); + if (!selection->regions.empty()) { + RegionView *rv = *(selection->regions.begin()); Location* tll; if ((tll = transport_loop_location()) != 0) { - tll->set (rv->region.position(), rv->region.last_frame()); + tll->set (rv->region().position(), rv->region().last_frame()); // enable looping, reposition and start rolling @@ -2000,10 +2002,10 @@ void Editor::toggle_region_mute () { if (clicked_regionview) { - clicked_regionview->region.set_muted (!clicked_regionview->region.muted()); - } else if (!selection->audio_regions.empty()) { - bool yn = ! (*selection->audio_regions.begin())->region.muted(); - selection->foreach_audio_region (&AudioRegion::set_muted, yn); + clicked_regionview->region().set_muted (!clicked_regionview->region().muted()); + } else if (!selection->regions.empty()) { + bool yn = ! (*selection->regions.begin())->region().muted(); + selection->foreach_region (&Region::set_muted, yn); } } @@ -2011,35 +2013,35 @@ void Editor::toggle_region_opaque () { if (clicked_regionview) { - clicked_regionview->region.set_opaque (!clicked_regionview->region.opaque()); - } else if (!selection->audio_regions.empty()) { - bool yn = ! (*selection->audio_regions.begin())->region.opaque(); - selection->foreach_audio_region (&Region::set_opaque, yn); + clicked_regionview->region().set_opaque (!clicked_regionview->region().opaque()); + } else if (!selection->regions.empty()) { + bool yn = ! (*selection->regions.begin())->region().opaque(); + selection->foreach_region (&Region::set_opaque, yn); } } void Editor::raise_region () { - selection->foreach_audio_region (&Region::raise); + selection->foreach_region (&Region::raise); } void Editor::raise_region_to_top () { - selection->foreach_audio_region (&Region::raise_to_top); + selection->foreach_region (&Region::raise_to_top); } void Editor::lower_region () { - selection->foreach_audio_region (&Region::lower); + selection->foreach_region (&Region::lower); } void Editor::lower_region_to_bottom () { - selection->foreach_audio_region (&Region::lower_to_bottom); + selection->foreach_region (&Region::lower_to_bottom); } void @@ -2060,7 +2062,7 @@ Editor::rename_region () Button ok_button (_("OK")); Button cancel_button (_("Cancel")); - if (selection->audio_regions.empty()) { + if (selection->regions.empty()) { return; } @@ -2091,7 +2093,7 @@ Editor::rename_region () Main::run (); if (region_renamed) { - (*selection->audio_regions.begin())->region.set_name (entry.get_text()); + (*selection->regions.begin())->region().set_name (entry.get_text()); redisplay_regions (); } } @@ -2105,7 +2107,7 @@ Editor::rename_region_finished (bool status) } void -Editor::audition_playlist_region_via_route (AudioRegion& region, Route& route) +Editor::audition_playlist_region_via_route (Region& region, Route& route) { if (session->is_auditioning()) { session->cancel_audition (); @@ -2126,14 +2128,14 @@ Editor::audition_playlist_region_via_route (AudioRegion& region, Route& route) void Editor::audition_selected_region () { - if (!selection->audio_regions.empty()) { - AudioRegionView* rv = *(selection->audio_regions.begin()); - session->audition_region (rv->region); + if (!selection->regions.empty()) { + RegionView* rv = *(selection->regions.begin()); + session->audition_region (rv->region()); } } void -Editor::audition_playlist_region_standalone (AudioRegion& region) +Editor::audition_playlist_region_standalone (Region& region) { session->audition_region (region); } @@ -2183,7 +2185,6 @@ Editor::region_from_selection () jack_nframes_t selection_cnt = end - start + 1; for (TrackSelection::iterator i = selection->tracks.begin(); i != selection->tracks.end(); ++i) { - AudioRegion *region; AudioRegion *current; Region* current_r; @@ -2200,7 +2201,9 @@ Editor::region_from_selection () continue; } - if ((current = dynamic_cast (current_r)) != 0) { + current = dynamic_cast (current_r); + // FIXME: audio only + if (current != 0) { internal_start = start - current->position(); session->region_name (new_name, current->name(), true); region = new AudioRegion (*current, internal_start, selection_cnt, new_name); @@ -2250,11 +2253,13 @@ Editor::split_multichannel_region () { vector v; - if (!clicked_regionview || clicked_regionview->region.n_channels() < 2) { + AudioRegionView* clicked_arv = dynamic_cast(clicked_regionview); + + if (!clicked_arv || clicked_arv->audio_region().n_channels() < 2) { return; } - clicked_regionview->region.separate_by_channel (*session, v); + clicked_arv->audio_region().separate_by_channel (*session, v); /* nothing else to do, really */ } @@ -2440,7 +2445,7 @@ Editor::region_fill_track () { jack_nframes_t end; - if (!session || selection->audio_regions.empty()) { + if (!session || selection->regions.empty()) { return; } @@ -2448,9 +2453,15 @@ Editor::region_fill_track () begin_reversible_command (_("region fill")); - for (AudioRegionSelection::iterator i = selection->audio_regions.begin(); i != selection->audio_regions.end(); ++i) { + for (RegionSelection::iterator i = selection->regions.begin(); i != selection->regions.end(); ++i) { + + Region& region ((*i)->region()); + + // FIXME + AudioRegion* const ar = dynamic_cast(®ion); + if (!ar) + continue; - AudioRegion& region ((*i)->region); Playlist* pl = region.playlist(); if (end <= region.last_frame()) { @@ -2464,7 +2475,7 @@ Editor::region_fill_track () } XMLNode &before = pl->get_state(); - pl->add_region (*(new AudioRegion (region)), region.last_frame(), times); + pl->add_region (*(new AudioRegion (*ar)), ar->last_frame(), times); session->add_command (new MementoCommand(*pl, before, pl->get_state())); } @@ -2544,12 +2555,12 @@ Editor::set_region_sync_from_edit_cursor () return; } - if (!clicked_regionview->region.covers (edit_cursor->current_frame)) { + if (!clicked_regionview->region().covers (edit_cursor->current_frame)) { error << _("Place the edit cursor at the desired sync point") << endmsg; return; } - Region& region (clicked_regionview->region); + Region& region (clicked_regionview->region()); begin_reversible_command (_("set sync from edit cursor")); XMLNode &before = region.playlist()->get_state(); region.set_sync_position (edit_cursor->current_frame); @@ -2562,7 +2573,7 @@ void Editor::remove_region_sync () { if (clicked_regionview) { - Region& region (clicked_regionview->region); + Region& region (clicked_regionview->region()); begin_reversible_command (_("remove sync")); XMLNode &before = region.playlist()->get_state(); region.clear_sync_position (); @@ -2575,15 +2586,15 @@ Editor::remove_region_sync () void Editor::naturalize () { - if (selection->audio_regions.empty()) { + if (selection->regions.empty()) { return; } begin_reversible_command (_("naturalize")); - for (AudioRegionSelection::iterator i = selection->audio_regions.begin(); i != selection->audio_regions.end(); ++i) { - XMLNode &before = (*i)->region.get_state(); - (*i)->region.move_to_natural_position (this); - XMLNode &after = (*i)->region.get_state(); - session->add_command (new MementoCommand((*i)->region, before, after)); + for (RegionSelection::iterator i = selection->regions.begin(); i != selection->regions.end(); ++i) { + XMLNode &before = (*i)->region().get_state(); + (*i)->region().move_to_natural_position (this); + XMLNode &after = (*i)->region().get_state(); + session->add_command (new MementoCommand((*i)->region(), before, after)); } commit_reversible_command (); } @@ -2602,14 +2613,14 @@ Editor::align_relative (RegionPoint what) struct RegionSortByTime { bool operator() (const AudioRegionView* a, const AudioRegionView* b) { - return a->region.position() < b->region.position(); + return a->region().position() < b->region().position(); } }; void Editor::align_selection_relative (RegionPoint point, jack_nframes_t position) { - if (selection->audio_regions.empty()) { + if (selection->regions.empty()) { return; } @@ -2617,9 +2628,9 @@ Editor::align_selection_relative (RegionPoint point, jack_nframes_t position) jack_nframes_t pos = 0; int dir; - list sorted; - selection->audio_regions.by_position (sorted); - Region& r ((*sorted.begin())->region); + list sorted; + selection->regions.by_position (sorted); + Region& r ((*sorted.begin())->region()); switch (point) { case Start: @@ -2645,9 +2656,9 @@ Editor::align_selection_relative (RegionPoint point, jack_nframes_t position) begin_reversible_command (_("align selection (relative)")); - for (AudioRegionSelection::iterator i = selection->audio_regions.begin(); i != selection->audio_regions.end(); ++i) { + for (RegionSelection::iterator i = selection->regions.begin(); i != selection->regions.end(); ++i) { - Region& region ((*i)->region); + Region& region ((*i)->region()); XMLNode &before = region.playlist()->get_state(); @@ -2668,14 +2679,14 @@ Editor::align_selection_relative (RegionPoint point, jack_nframes_t position) void Editor::align_selection (RegionPoint point, jack_nframes_t position) { - if (selection->audio_regions.empty()) { + if (selection->regions.empty()) { return; } begin_reversible_command (_("align selection")); - for (AudioRegionSelection::iterator i = selection->audio_regions.begin(); i != selection->audio_regions.end(); ++i) { - align_region_internal ((*i)->region, point, position); + for (RegionSelection::iterator i = selection->regions.begin(); i != selection->regions.end(); ++i) { + align_region_internal ((*i)->region(), point, position); } commit_reversible_command (); @@ -2721,7 +2732,7 @@ Editor::trim_region_to_edit_cursor () return; } - Region& region (clicked_regionview->region); + Region& region (clicked_regionview->region()); float speed = 1.0f; AudioTimeAxisView *atav; @@ -2747,7 +2758,7 @@ Editor::trim_region_from_edit_cursor () return; } - Region& region (clicked_regionview->region); + Region& region (clicked_regionview->region()); float speed = 1.0f; AudioTimeAxisView *atav; @@ -2920,16 +2931,16 @@ Editor::cut_copy (CutCopyOp op) switch (current_mouse_mode()) { case MouseObject: - if (!selection->audio_regions.empty() || !selection->points.empty()) { + if (!selection->regions.empty() || !selection->points.empty()) { begin_reversible_command (opname + _(" objects")); - if (!selection->audio_regions.empty()) { + if (!selection->regions.empty()) { cut_copy_regions (op); if (op == Cut) { - selection->clear_audio_regions (); + selection->clear_regions (); } } @@ -2986,11 +2997,11 @@ Editor::cut_copy_regions (CutCopyOp op) set freezelist; pair::iterator,bool> insert_result; - for (AudioRegionSelection::iterator x = selection->audio_regions.begin(); x != selection->audio_regions.end(); ++x) { - first_position = min ((*x)->region.position(), first_position); + for (RegionSelection::iterator x = selection->regions.begin(); x != selection->regions.end(); ++x) { + first_position = min ((*x)->region().position(), first_position); if (op == Cut || op == Clear) { - AudioPlaylist *pl = dynamic_cast((*x)->region.playlist()); + AudioPlaylist *pl = dynamic_cast((*x)->region().playlist()); if (pl) { insert_result = freezelist.insert (pl); if (insert_result.second) { @@ -3001,11 +3012,11 @@ Editor::cut_copy_regions (CutCopyOp op) } } - for (AudioRegionSelection::iterator x = selection->audio_regions.begin(); x != selection->audio_regions.end(); ) { + for (RegionSelection::iterator x = selection->regions.begin(); x != selection->regions.end(); ) { - AudioPlaylist *pl = dynamic_cast((*x)->region.playlist()); + AudioPlaylist *pl = dynamic_cast((*x)->region().playlist()); AudioPlaylist* npl; - AudioRegionSelection::iterator tmp; + RegionSelection::iterator tmp; tmp = x; ++tmp; @@ -3022,18 +3033,24 @@ Editor::cut_copy_regions (CutCopyOp op) npl = pi->second; } + // FIXME + AudioRegion* const ar = dynamic_cast(&(*x)->region()); switch (op) { case Cut: - npl->add_region (*(new AudioRegion ((*x)->region)), (*x)->region.position() - first_position); - pl->remove_region (&((*x)->region)); + if (!ar) break; + + npl->add_region (*(new AudioRegion (*ar)), (*x)->region().position() - first_position); + pl->remove_region (&((*x)->region())); break; case Copy: - npl->add_region (*(new AudioRegion ((*x)->region)), (*x)->region.position() - first_position); + if (!ar) break; + + npl->add_region (*(new AudioRegion (*ar)), (*x)->region().position() - first_position); break; case Clear: - pl->remove_region (&((*x)->region)); + pl->remove_region (&((*x)->region())); break; } } @@ -3179,24 +3196,24 @@ Editor::paste_named_selection (float times) } void -Editor::duplicate_some_regions (AudioRegionSelection& regions, float times) +Editor::duplicate_some_regions (RegionSelection& regions, float times) { Playlist *playlist; - AudioRegionSelection sel = regions; // clear (below) will clear the argument list + RegionSelection sel = regions; // clear (below) will clear the argument list begin_reversible_command (_("duplicate region")); - selection->clear_audio_regions (); + selection->clear_regions (); - for (AudioRegionSelection::iterator i = sel.begin(); i != sel.end(); ++i) { + for (RegionSelection::iterator i = sel.begin(); i != sel.end(); ++i) { - Region& r ((*i)->region); + Region& r ((*i)->region()); TimeAxisView& tv = (*i)->get_time_axis_view(); AudioTimeAxisView* atv = dynamic_cast (&tv); - sigc::connection c = atv->view->AudioRegionViewAdded.connect (mem_fun(*this, &Editor::collect_new_region_view)); + sigc::connection c = atv->view()->RegionViewAdded.connect (mem_fun(*this, &Editor::collect_new_region_view)); - playlist = (*i)->region.playlist(); + playlist = (*i)->region().playlist(); XMLNode &before = playlist->get_state(); playlist->duplicate (r, r.last_frame(), times); session->add_command(new MementoCommand(*playlist, before, playlist->get_state())); @@ -3369,7 +3386,7 @@ Editor::normalize_region () return; } - if (selection->audio_regions.empty()) { + if (selection->regions.empty()) { return; } @@ -3378,11 +3395,13 @@ Editor::normalize_region () track_canvas.get_window()->set_cursor (*wait_cursor); gdk_flush (); - for (AudioRegionSelection::iterator r = selection->audio_regions.begin(); r != selection->audio_regions.end(); ++r) { - XMLNode &before = (*r)->region.get_state(); - (*r)->region.normalize_to (0.0f); - XMLNode &after = (*r)->region.get_state(); - session->add_command (new MementoCommand((*r)->region, before, after)); + for (RegionSelection::iterator r = selection->regions.begin(); r != selection->regions.end(); ++r) { + AudioRegionView* const arv = dynamic_cast(*r); + if (!arv) + continue; + XMLNode &before = arv->region().get_state(); + arv->audio_region().normalize_to (0.0f); + session->add_command (new MementoCommand(arv->region, arv->region().get_state()); } commit_reversible_command (); @@ -3397,17 +3416,19 @@ Editor::denormalize_region () return; } - if (selection->audio_regions.empty()) { + if (selection->regions.empty()) { return; } begin_reversible_command ("denormalize"); - for (AudioRegionSelection::iterator r = selection->audio_regions.begin(); r != selection->audio_regions.end(); ++r) { - XMLNode &before = (*r)->region.get_state(); - (*r)->region.set_scale_amplitude (1.0f); - XMLNode &after = (*r)->region.get_state(); - session->add_command (new MementoCommand((*r)->region, before, after)); + for (RegionSelection::iterator r = selection->regions.begin(); r != selection->regions.end(); ++r) { + AudioRegionView* const arv = dynamic_cast(*r); + if (!arv) + continue; + XMLNode &before = arv->region().get_state(); + arv->audio_region().set_scale_amplitude (1.0f); + session->add_command (new MementoCommand(arv->region, before, arv->region().get_state()); } commit_reversible_command (); @@ -3428,7 +3449,7 @@ Editor::reverse_region () void Editor::apply_filter (AudioFilter& filter, string command) { - if (selection->audio_regions.empty()) { + if (selection->regions.empty()) { return; } @@ -3437,20 +3458,22 @@ Editor::apply_filter (AudioFilter& filter, string command) track_canvas.get_window()->set_cursor (*wait_cursor); gdk_flush (); - for (AudioRegionSelection::iterator r = selection->audio_regions.begin(); r != selection->audio_regions.end(); ) { + for (RegionSelection::iterator r = selection->regions.begin(); r != selection->regions.end(); ) { + AudioRegionView* const arv = dynamic_cast(*r); + if (!arv) + continue; - AudioRegion& region ((*r)->region); - Playlist* playlist = region.playlist(); + Playlist* playlist = arv->region().playlist(); - AudioRegionSelection::iterator tmp; + RegionSelection::iterator tmp; tmp = r; ++tmp; - if (region.apply (filter) == 0) { + if (arv->audio_region().apply (filter) == 0) { XMLNode &before = playlist->get_state(); - playlist->replace_region (region, *(filter.results.front()), region.position()); + playlist->replace_region (arv->region(), *(filter.results.front()), arv->region()position()); XMLNode &after = playlist->get_state(); session->add_command(new MementoCommand(*playlist, before, after)); } else { @@ -3461,7 +3484,7 @@ Editor::apply_filter (AudioFilter& filter, string command) } commit_reversible_command (); - selection->audio_regions.clear (); + selection->regions.clear (); out: track_canvas.get_window()->set_cursor (*current_canvas_cursor); @@ -3470,8 +3493,8 @@ Editor::apply_filter (AudioFilter& filter, string command) void Editor::region_selection_op (void (Region::*pmf)(void)) { - for (AudioRegionSelection::iterator i = selection->audio_regions.begin(); i != selection->audio_regions.end(); ++i) { - ((*i)->region.*pmf)(); + for (RegionSelection::iterator i = selection->regions.begin(); i != selection->regions.end(); ++i) { + ((*i)->region().*pmf)(); } } @@ -3479,16 +3502,16 @@ Editor::region_selection_op (void (Region::*pmf)(void)) void Editor::region_selection_op (void (Region::*pmf)(void*), void *arg) { - for (AudioRegionSelection::iterator i = selection->audio_regions.begin(); i != selection->audio_regions.end(); ++i) { - ((*i)->region.*pmf)(arg); + for (RegionSelection::iterator i = selection->regions.begin(); i != selection->regions.end(); ++i) { + ((*i)->region().*pmf)(arg); } } void Editor::region_selection_op (void (Region::*pmf)(bool), bool yn) { - for (AudioRegionSelection::iterator i = selection->audio_regions.begin(); i != selection->audio_regions.end(); ++i) { - ((*i)->region.*pmf)(yn); + for (RegionSelection::iterator i = selection->regions.begin(); i != selection->regions.end(); ++i) { + ((*i)->region().*pmf)(yn); } } @@ -3505,20 +3528,20 @@ Editor::external_edit_region () void Editor::brush (jack_nframes_t pos) { - AudioRegionSelection sel; + RegionSelection sel; snap_to (pos); - if (selection->audio_regions.empty()) { + if (selection->regions.empty()) { /* XXX get selection from region list */ } else { - sel = selection->audio_regions; + sel = selection->regions; } if (sel.empty()) { return; } - for (AudioRegionSelection::iterator i = selection->audio_regions.begin(); i != selection->audio_regions.end(); ++i) { + for (RegionSelection::iterator i = selection->regions.begin(); i != selection->regions.end(); ++i) { mouse_brush_insert_region ((*i), pos); } } @@ -3526,18 +3549,19 @@ Editor::brush (jack_nframes_t pos) void Editor::toggle_gain_envelope_visibility () { - for (AudioRegionSelection::iterator i = selection->audio_regions.begin(); i != selection->audio_regions.end(); ++i) { - (*i)->set_envelope_visible (!(*i)->envelope_visible()); + for (RegionSelection::iterator i = selection->regions.begin(); i != selection->regions.end(); ++i) { + AudioRegionView* const arv = dynamic_cast(*i); + if (arv) + arv->set_envelope_visible (!arv->envelope_visible()); } } void Editor::toggle_gain_envelope_active () { - for (AudioRegionSelection::iterator i = selection->audio_regions.begin(); i != selection->audio_regions.end(); ++i) { - AudioRegion* ar = dynamic_cast(&(*i)->region); - if (ar) { - ar->set_envelope_active (true); - } + for (RegionSelection::iterator i = selection->regions.begin(); i != selection->regions.end(); ++i) { + AudioRegionView* const arv = dynamic_cast(*i); + if (arv) + arv->audio_region().set_envelope_active (true); } } diff --git a/gtk2_ardour/editor_route_list.cc b/gtk2_ardour/editor_route_list.cc index 2e036f5001..c93cf9aba2 100644 --- a/gtk2_ardour/editor_route_list.cc +++ b/gtk2_ardour/editor_route_list.cc @@ -39,21 +39,16 @@ using namespace PBD; using namespace Gtk; void -Editor::handle_new_route_p (Route* route) -{ - ENSURE_GUI_THREAD(bind (mem_fun(*this, &Editor::handle_new_route_p), route)); - handle_new_route (*route); -} - -void -Editor::handle_new_route (Route& route) +Editor::handle_new_route (boost::shared_ptr route) { + ENSURE_GUI_THREAD(bind (mem_fun(*this, &Editor::handle_new_route), route)); + TimeAxisView *tv; AudioTimeAxisView *atv; TreeModel::Row parent; TreeModel::Row row; - if (route.hidden()) { + if (route->hidden()) { return; } @@ -75,7 +70,7 @@ Editor::handle_new_route (Route& route) } - if (dynamic_cast(&route) != 0) { + if (dynamic_cast(route.get()) != 0) { TreeModel::iterator iter = route_display_model->get_iter ("1"); // audio tracks parent = *iter; } else { @@ -89,7 +84,7 @@ Editor::handle_new_route (Route& route) row = *(route_display_model->append ()); #endif - row[route_display_columns.text] = route.name(); + row[route_display_columns.text] = route->name(); row[route_display_columns.visible] = tv->marked_for_display(); row[route_display_columns.tv] = tv; @@ -99,14 +94,14 @@ Editor::handle_new_route (Route& route) if ((atv = dynamic_cast (tv)) != 0) { /* added a new fresh one at the end */ - if (atv->route().order_key(N_("editor")) == -1) { - atv->route().set_order_key (N_("editor"), route_display_model->children().size()-1); + if (atv->route()->order_key(N_("editor")) == -1) { + atv->route()->set_order_key (N_("editor"), route_display_model->children().size()-1); } } ignore_route_list_reorder = false; - route.gui_changed.connect (mem_fun(*this, &Editor::handle_gui_changes)); + route->gui_changed.connect (mem_fun(*this, &Editor::handle_gui_changes)); tv->GoingAway.connect (bind (mem_fun(*this, &Editor::remove_route), tv)); @@ -188,7 +183,7 @@ Editor::hide_track_in_display (TimeAxisView& tv) AudioTimeAxisView* atv = dynamic_cast (&tv); - if (atv && current_mixer_strip && &(atv->route()) == &(current_mixer_strip->route())) { + if (atv && current_mixer_strip && (atv->route() == current_mixer_strip->route())) { // this will hide the mixer strip set_selected_mixer_strip (tv); } @@ -244,7 +239,7 @@ Editor::redisplay_route_list () */ if ((at = dynamic_cast (tv)) != 0) { - at->route().set_order_key (N_("editor"), order); + at->route()->set_order_key (N_("editor"), order); ++order; } } @@ -263,6 +258,10 @@ Editor::redisplay_route_list () } + /* make sure the cursors stay on top of every newly added track */ + + cursor_group->raise_to_top (); + reset_scrolling_region (); } @@ -473,7 +472,7 @@ Editor::route_list_selection_filter (const Glib::RefPtr& model, const } struct EditorOrderRouteSorter { - bool operator() (Route* a, Route* b) { + bool operator() (boost::shared_ptr a, boost::shared_ptr b) { /* use of ">" forces the correct sort order */ return a->order_key ("editor") < b->order_key ("editor"); } @@ -482,17 +481,18 @@ struct EditorOrderRouteSorter { void Editor::initial_route_list_display () { - Session::RouteList routes = session->get_routes(); + boost::shared_ptr routes = session->get_routes(); + Session::RouteList r (*routes); EditorOrderRouteSorter sorter; - routes.sort (sorter); + r.sort (sorter); no_route_list_redisplay = true; route_display_model->clear (); - for (Session::RouteList::iterator i = routes.begin(); i != routes.end(); ++i) { - handle_new_route (**i); + for (Session::RouteList::iterator i = r.begin(); i != r.end(); ++i) { + handle_new_route (*i); } no_route_list_redisplay = false; diff --git a/gtk2_ardour/editor_timefx.cc b/gtk2_ardour/editor_timefx.cc index 27fa6c9651..3fe0023d07 100644 --- a/gtk2_ardour/editor_timefx.cc +++ b/gtk2_ardour/editor_timefx.cc @@ -29,7 +29,7 @@ #include "editor.h" #include "audio_time_axis.h" -#include "regionview.h" +#include "audio_region_view.h" #include "region_selection.h" #include @@ -101,7 +101,7 @@ Editor::TimeStretchDialog::delete_timestretch_in_progress (GdkEventAny* ev) } int -Editor::run_timestretch (AudioRegionSelection& regions, float fraction) +Editor::run_timestretch (RegionSelection& regions, float fraction) { pthread_t thread; @@ -158,39 +158,42 @@ Editor::run_timestretch (AudioRegionSelection& regions, float fraction) void Editor::do_timestretch (TimeStretchDialog& dialog) { - AudioTrack* at; + Track* t; Playlist* playlist; - AudioRegion* new_region; + Region* new_region; - for (AudioRegionSelection::iterator i = dialog.regions.begin(); i != dialog.regions.end(); ) { + for (RegionSelection::iterator i = dialog.regions.begin(); i != dialog.regions.end(); ) { + AudioRegionView* arv = dynamic_cast(*i); + if (!arv) + continue; - AudioRegion& aregion ((*i)->region); - TimeAxisView* tv = &(*i)->get_time_axis_view(); - AudioTimeAxisView* atv; - AudioRegionSelection::iterator tmp; + AudioRegion& region (arv->audio_region()); + TimeAxisView* tv = &(arv->get_time_axis_view()); + RouteTimeAxisView* rtv; + RegionSelection::iterator tmp; - cerr << "stretch " << aregion.name() << endl; + cerr << "stretch " << region.name() << endl; tmp = i; ++tmp; - if ((atv = dynamic_cast (tv)) == 0) { + if ((rtv = dynamic_cast (tv)) == 0) { i = tmp; continue; } - if ((at = dynamic_cast (&atv->route())) == 0) { + if ((t = dynamic_cast (rtv->route().get())) == 0) { i = tmp; continue; } - if ((playlist = at->disk_stream().playlist()) == 0) { + if ((playlist = t->diskstream().playlist()) == 0) { i = tmp; continue; } - dialog.request.region = &aregion; + dialog.request.region = ®ion; if (!dialog.request.running) { /* we were cancelled */ @@ -205,7 +208,7 @@ Editor::do_timestretch (TimeStretchDialog& dialog) } XMLNode &before = playlist->get_state(); - playlist->replace_region (aregion, *new_region, aregion.position()); + playlist->replace_region (region, *new_region, region.position()); XMLNode &after = playlist->get_state(); session->add_command (new MementoCommand(*playlist, before, after)); diff --git a/gtk2_ardour/export_dialog.cc b/gtk2_ardour/export_dialog.cc index bcf8cd85ad..b5a4757090 100644 --- a/gtk2_ardour/export_dialog.cc +++ b/gtk2_ardour/export_dialog.cc @@ -1082,11 +1082,11 @@ ExportDialog::fill_lists () track_list->clear(); master_list->clear(); - Session::RouteList routes = session->get_routes (); + boost::shared_ptr routes = session->get_routes (); - for (Session::RouteList::iterator ri = routes.begin(); ri != routes.end(); ++ri) { - - Route* route = (*ri); + for (Session::RouteList::iterator ri = routes->begin(); ri != routes->end(); ++ri) { + + boost::shared_ptr route = (*ri); if (route->hidden()) { continue; diff --git a/gtk2_ardour/export_region_dialog.cc b/gtk2_ardour/export_region_dialog.cc index 97bf7c22b1..1964fabbfe 100644 --- a/gtk2_ardour/export_region_dialog.cc +++ b/gtk2_ardour/export_region_dialog.cc @@ -18,6 +18,8 @@ */ +#include + #include #include @@ -26,11 +28,13 @@ #include "i18n.h" -ExportRegionDialog::ExportRegionDialog (PublicEditor& editor, ARDOUR::AudioRegion* region) +ExportRegionDialog::ExportRegionDialog (PublicEditor& editor, ARDOUR::Region* region) : ExportDialog(editor) { - audio_region = region; - + // FIXME + ARDOUR::AudioRegion* audio_region = dynamic_cast(region); + assert(audio_region); + do_not_allow_track_and_master_selection(); do_not_allow_channel_count_selection(); } diff --git a/gtk2_ardour/export_region_dialog.h b/gtk2_ardour/export_region_dialog.h index 00464eb5b3..e8afe97d6b 100644 --- a/gtk2_ardour/export_region_dialog.h +++ b/gtk2_ardour/export_region_dialog.h @@ -27,7 +27,7 @@ class ExportRegionDialog : public ExportDialog { public: - ExportRegionDialog (PublicEditor&, ARDOUR::AudioRegion*); + ExportRegionDialog (PublicEditor&, ARDOUR::Region*); static void* _export_region_thread (void *); void export_region (); diff --git a/gtk2_ardour/fft_graph.cc b/gtk2_ardour/fft_graph.cc index c2d81abf3c..367dc54b7c 100644 --- a/gtk2_ardour/fft_graph.cc +++ b/gtk2_ardour/fft_graph.cc @@ -234,11 +234,11 @@ FFTGraph::draw_scales(Glib::RefPtr window) while (_logScale[logscale_pos] < position_on_scale) logscale_pos++; - int coord = v_margin + 1.0 + position_on_scale; + int coord = (int)(v_margin + 1.0 + position_on_scale); int SR = 44100; - int rate_at_pos = (double)(SR/2) * (double)logscale_pos / (double)_dataSize; + int rate_at_pos = (int)((double)(SR/2) * (double)logscale_pos / (double)_dataSize); char buf[32]; snprintf(buf,32,"%dhz",rate_at_pos); @@ -384,7 +384,7 @@ FFTGraph::on_size_request(Gtk::Requisition* requisition) } void -FFTGraph::on_size_allocate(Gtk::Allocation alloc) +FFTGraph::on_size_allocate(Gtk::Allocation & alloc) { width = alloc.get_width(); height = alloc.get_height(); diff --git a/gtk2_ardour/fft_graph.h b/gtk2_ardour/fft_graph.h index 80c78180a6..73636b989d 100644 --- a/gtk2_ardour/fft_graph.h +++ b/gtk2_ardour/fft_graph.h @@ -51,7 +51,7 @@ class FFTGraph : public Gtk::DrawingArea bool on_expose_event (GdkEventExpose* event); void on_size_request(Gtk::Requisition* requisition); - void on_size_allocate(Gtk::Allocation alloc); + void on_size_allocate(Gtk::Allocation & alloc); FFTResult *prepareResult(Gdk::Color color, std::string trackname); private: diff --git a/gtk2_ardour/fft_result.cc b/gtk2_ardour/fft_result.cc index 9a55b59cb5..f5acef92ed 100644 --- a/gtk2_ardour/fft_result.cc +++ b/gtk2_ardour/fft_result.cc @@ -20,9 +20,9 @@ #include #include -#include -#include -#include +#include +#include +#include #include diff --git a/gtk2_ardour/gain_automation_time_axis.cc b/gtk2_ardour/gain_automation_time_axis.cc index 3e3d02bfc4..c86c1390f3 100644 --- a/gtk2_ardour/gain_automation_time_axis.cc +++ b/gtk2_ardour/gain_automation_time_axis.cc @@ -32,7 +32,9 @@ using namespace ARDOUR; using namespace PBD; using namespace Gtk; -GainAutomationTimeAxisView::GainAutomationTimeAxisView (Session& s, Route& r, PublicEditor& e, TimeAxisView& parent, ArdourCanvas::Canvas& canvas, const string & n, ARDOUR::Curve& c) +GainAutomationTimeAxisView::GainAutomationTimeAxisView (Session& s, boost::shared_ptr r, + PublicEditor& e, TimeAxisView& parent, + ArdourCanvas::Canvas& canvas, const string & n, ARDOUR::Curve& c) : AxisView (s), AutomationTimeAxisView (s, r, e, parent, canvas, n, X_("gain"), ""), @@ -74,6 +76,6 @@ void GainAutomationTimeAxisView::set_automation_state (AutoState state) { if (!ignore_state_request) { - route.set_gain_automation_state (state); + route->set_gain_automation_state (state); } } diff --git a/gtk2_ardour/gain_automation_time_axis.h b/gtk2_ardour/gain_automation_time_axis.h index 50f1cba3f9..dc6d5bd28e 100644 --- a/gtk2_ardour/gain_automation_time_axis.h +++ b/gtk2_ardour/gain_automation_time_axis.h @@ -13,7 +13,7 @@ class GainAutomationTimeAxisView : public AutomationTimeAxisView { public: GainAutomationTimeAxisView (ARDOUR::Session&, - ARDOUR::Route&, + boost::shared_ptr, PublicEditor&, TimeAxisView& parent_axis, ArdourCanvas::Canvas& canvas, diff --git a/gtk2_ardour/gain_meter.cc b/gtk2_ardour/gain_meter.cc index b7746c4b19..5fa8c462bc 100644 --- a/gtk2_ardour/gain_meter.cc +++ b/gtk2_ardour/gain_meter.cc @@ -79,7 +79,7 @@ GainMeter::setup_slider_pix () return 0; } -GainMeter::GainMeter (IO& io, Session& s) +GainMeter::GainMeter (boost::shared_ptr io, Session& s) : _io (io), _session (s), gain_slider (0), @@ -99,18 +99,13 @@ GainMeter::GainMeter (IO& io, Session& s) gain_slider = manage (new VSliderController (slider, rail, &gain_adjustment, - & _io.midi_gain_control(), + _io->gain_control(), false)); gain_slider->signal_button_press_event().connect (mem_fun(*this, &GainMeter::start_gain_touch)); gain_slider->signal_button_release_event().connect (mem_fun(*this, &GainMeter::end_gain_touch)); gain_slider->set_name ("MixerGainMeter"); - if (_session.midi_port()) { - _io.set_midi_to_gain_function (slider_position_to_gain); - _io.set_gain_to_midi_function (gain_to_slider_position); - } - gain_display.set_print_func (_gain_printer, this); gain_display_box.set_spacing (2); @@ -157,7 +152,7 @@ GainMeter::GainMeter (IO& io, Session& s) Route* r; - if ((r = dynamic_cast (&_io)) != 0) { + if ((r = dynamic_cast (_io.get())) != 0) { /* if we don't have a route (if we're the click), pack some route-dependent stuff. @@ -170,13 +165,13 @@ GainMeter::GainMeter (IO& io, Session& s) using namespace Menu_Helpers; gain_astate_menu.items().push_back (MenuElem (_("Off"), - bind (mem_fun (&_io, &IO::set_gain_automation_state), (AutoState) Off))); + bind (mem_fun (*_io, &IO::set_gain_automation_state), (AutoState) Off))); gain_astate_menu.items().push_back (MenuElem (_("Play"), - bind (mem_fun (&_io, &IO::set_gain_automation_state), (AutoState) Play))); + bind (mem_fun (*_io, &IO::set_gain_automation_state), (AutoState) Play))); gain_astate_menu.items().push_back (MenuElem (_("Write"), - bind (mem_fun (&_io, &IO::set_gain_automation_state), (AutoState) Write))); + bind (mem_fun (*_io, &IO::set_gain_automation_state), (AutoState) Write))); gain_astate_menu.items().push_back (MenuElem (_("Touch"), - bind (mem_fun (&_io, &IO::set_gain_automation_state), (AutoState) Touch))); + bind (mem_fun (*_io, &IO::set_gain_automation_state), (AutoState) Touch))); gain_astyle_menu.items().push_back (MenuElem (_("Trim"))); gain_astyle_menu.items().push_back (MenuElem (_("Abs"))); @@ -200,7 +195,7 @@ GainMeter::GainMeter (IO& io, Session& s) pack_start (gain_display_box, Gtk::PACK_SHRINK); pack_start (hbox, Gtk::PACK_SHRINK); - _io.gain_changed.connect (mem_fun(*this, &GainMeter::gain_changed)); + _io->gain_changed.connect (mem_fun(*this, &GainMeter::gain_changed)); meter_metric_area.signal_expose_event().connect (mem_fun(*this, &GainMeter::meter_metrics_expose)); gain_adjustment.signal_value_changed().connect (mem_fun(*this, &GainMeter::gain_adjusted)); @@ -328,7 +323,7 @@ GainMeter::update_meters () for (n = 0, i = meters.begin(); i != meters.end(); ++i, ++n) { if ((*i).packed) { - peak = _io.peak_input_power (n); + peak = _io->peak_input_power (n); (*i).meter->set (log_meter (peak), peak); @@ -387,14 +382,14 @@ GainMeter::hide_all_meters () void GainMeter::setup_meters () { - uint32_t nmeters = _io.n_outputs(); + uint32_t nmeters = _io->n_outputs(); guint16 width; hide_all_meters (); Route* r; - if ((r = dynamic_cast (&_io)) != 0) { + if ((r = dynamic_cast (_io.get())) != 0) { switch (r->meter_point()) { case MeterPreFader: @@ -408,7 +403,7 @@ GainMeter::setup_meters () } else { - nmeters = _io.n_outputs(); + nmeters = _io->n_outputs(); } @@ -456,7 +451,7 @@ GainMeter::peak_button_release (GdkEventButton* ev) ResetAllPeakDisplays (); } else if (ev->button == 1 && Keyboard::modifier_state_equals (ev->state, Keyboard::Control)) { Route* r; - if ((r = dynamic_cast (&_io)) != 0) { + if ((r = dynamic_cast (_io.get())) != 0) { ResetGroupPeakDisplays (r->mix_group()); } } else { @@ -477,7 +472,7 @@ void GainMeter::reset_group_peak_display (RouteGroup* group) { Route* r; - if ((r = dynamic_cast (&_io)) != 0) { + if ((r = dynamic_cast (_io.get())) != 0) { if (group == r->mix_group()) { reset_peak_display (); } @@ -546,14 +541,14 @@ void GainMeter::gain_adjusted () { if (!ignore_toggle) { - _io.set_gain (slider_position_to_gain (gain_adjustment.get_value()), this); + _io->set_gain (slider_position_to_gain (gain_adjustment.get_value()), this); } } void GainMeter::effective_gain_display () { - gfloat value = gain_to_slider_position (_io.effective_gain()); + gfloat value = gain_to_slider_position (_io->effective_gain()); if (gain_adjustment.get_value() != value) { ignore_toggle = true; @@ -583,7 +578,7 @@ GainMeter::set_fader_name (const char * name) void GainMeter::update_gain_sensitive () { - static_cast(gain_slider)->set_sensitive (!(_io.gain_automation_state() & Play)); + static_cast(gain_slider)->set_sensitive (!(_io->gain_automation_state() & Play)); } @@ -614,7 +609,7 @@ GainMeter::meter_press(GdkEventButton* ev) wait_for_release = false; - if ((_route = dynamic_cast(&_io)) == 0) { + if ((_route = dynamic_cast(_io.get())) == 0) { return FALSE; } @@ -676,7 +671,7 @@ GainMeter::meter_release(GdkEventButton* ev) if(!ignore_toggle){ if (wait_for_release){ wait_for_release = false; - set_meter_point (*(dynamic_cast(&_io)), old_meter_point); + set_meter_point (*(dynamic_cast(_io.get())), old_meter_point); } } return true; @@ -705,7 +700,7 @@ GainMeter::meter_point_clicked () { Route* r; - if ((r = dynamic_cast (&_io)) != 0) { + if ((r = dynamic_cast (_io.get())) != 0) { } } @@ -713,14 +708,14 @@ GainMeter::meter_point_clicked () gint GainMeter::start_gain_touch (GdkEventButton* ev) { - _io.start_gain_touch (); + _io->start_gain_touch (); return FALSE; } gint GainMeter::end_gain_touch (GdkEventButton* ev) { - _io.end_gain_touch (); + _io->end_gain_touch (); return FALSE; } @@ -824,10 +819,10 @@ GainMeter::gain_automation_style_changed () // Route* _route = dynamic_cast(&_io); switch (_width) { case Wide: - gain_automation_style_button.set_label (astyle_string(_io.gain_automation_curve().automation_style())); + gain_automation_style_button.set_label (astyle_string(_io->gain_automation_curve().automation_style())); break; case Narrow: - gain_automation_style_button.set_label (short_astyle_string(_io.gain_automation_curve().automation_style())); + gain_automation_style_button.set_label (short_astyle_string(_io->gain_automation_curve().automation_style())); break; } } @@ -842,14 +837,14 @@ GainMeter::gain_automation_state_changed () switch (_width) { case Wide: - gain_automation_state_button.set_label (astate_string(_io.gain_automation_curve().automation_state())); + gain_automation_state_button.set_label (astate_string(_io->gain_automation_curve().automation_state())); break; case Narrow: - gain_automation_state_button.set_label (short_astate_string(_io.gain_automation_curve().automation_state())); + gain_automation_state_button.set_label (short_astate_string(_io->gain_automation_curve().automation_state())); break; } - x = (_io.gain_automation_state() != Off); + x = (_io->gain_automation_state() != Off); if (gain_automation_state_button.get_active() != x) { ignore_toggle = true; diff --git a/gtk2_ardour/gain_meter.h b/gtk2_ardour/gain_meter.h index ddf93b579f..1dfc088248 100644 --- a/gtk2_ardour/gain_meter.h +++ b/gtk2_ardour/gain_meter.h @@ -34,8 +34,8 @@ #include -#include #include +#include #include "enums.h" @@ -56,7 +56,7 @@ namespace Gtk { class GainMeter : public Gtk::VBox { public: - GainMeter (ARDOUR::IO&, ARDOUR::Session&); + GainMeter (boost::shared_ptr, ARDOUR::Session&); ~GainMeter (); void update_gain_sensitive (); @@ -75,7 +75,7 @@ class GainMeter : public Gtk::VBox private: friend class MixerStrip; - ARDOUR::IO& _io; + boost::shared_ptr _io; ARDOUR::Session& _session; bool ignore_toggle; diff --git a/gtk2_ardour/io_selector.cc b/gtk2_ardour/io_selector.cc index b0ecd05077..f754435112 100644 --- a/gtk2_ardour/io_selector.cc +++ b/gtk2_ardour/io_selector.cc @@ -52,7 +52,7 @@ using namespace ARDOUR; using namespace PBD; using namespace Gtkmm2ext; -IOSelectorWindow::IOSelectorWindow (Session& sess, IO& ior, bool input, bool can_cancel) +IOSelectorWindow::IOSelectorWindow (Session& sess, boost::shared_ptr ior, bool input, bool can_cancel) : ArdourDialog ("i/o selector"), _selector (sess, ior, input), ok_button (can_cancel ? _("OK"): _("Close")), @@ -65,9 +65,9 @@ IOSelectorWindow::IOSelectorWindow (Session& sess, IO& ior, bool input, bool can string title; if (input) { - title = string_compose(_("%1 input"), ior.name()); + title = string_compose(_("%1 input"), ior->name()); } else { - title = string_compose(_("%1 output"), ior.name()); + title = string_compose(_("%1 output"), ior->name()); } ok_button.set_name ("IOSelectorButton"); @@ -135,7 +135,7 @@ IOSelectorWindow::on_map () The IO Selector "widget" *************************/ -IOSelector::IOSelector (Session& sess, IO& ior, bool input) +IOSelector::IOSelector (Session& sess, boost::shared_ptr ior, bool input) : session (sess), io (ior), for_input (input), @@ -184,14 +184,14 @@ IOSelector::IOSelector (Session& sess, IO& ior, bool input) port_button_box.pack_start (add_port_button, false, false); if (for_input) { - if (io.input_maximum() < 0 || io.input_maximum() > (int) io.n_inputs()) { + if (io->input_maximum() < 0 || io->input_maximum() > (int) io->n_inputs()) { add_port_button.set_sensitive (true); } else { add_port_button.set_sensitive (false); } } else { - if (io.output_maximum() < 0 || io.output_maximum() > (int) io.n_outputs()) { + if (io->output_maximum() < 0 || io->output_maximum() > (int) io->n_outputs()) { add_port_button.set_sensitive (true); } else { add_port_button.set_sensitive (false); @@ -202,14 +202,14 @@ IOSelector::IOSelector (Session& sess, IO& ior, bool input) port_button_box.pack_start (remove_port_button, false, false); if (for_input) { - if (io.input_minimum() < 0 || io.input_minimum() < (int) io.n_inputs()) { + if (io->input_minimum() < 0 || io->input_minimum() < (int) io->n_inputs()) { remove_port_button.set_sensitive (true); } else { remove_port_button.set_sensitive (false); } } else { - if (io.output_minimum() < 0 || io.output_minimum() < (int) io.n_outputs()) { + if (io->output_minimum() < 0 || io->output_minimum() < (int) io->n_outputs()) { remove_port_button.set_sensitive (true); } else { remove_port_button.set_sensitive (false); @@ -241,12 +241,12 @@ IOSelector::IOSelector (Session& sess, IO& ior, bool input) remove_port_button.signal_clicked().connect (mem_fun(*this, &IOSelector::remove_port)); if (for_input) { - io.input_changed.connect (mem_fun(*this, &IOSelector::ports_changed)); + io->input_changed.connect (mem_fun(*this, &IOSelector::ports_changed)); } else { - io.output_changed.connect (mem_fun(*this, &IOSelector::ports_changed)); + io->output_changed.connect (mem_fun(*this, &IOSelector::ports_changed)); } - io.name_changed.connect (mem_fun(*this, &IOSelector::name_changed)); + io->name_changed.connect (mem_fun(*this, &IOSelector::name_changed)); } IOSelector::~IOSelector () @@ -265,9 +265,9 @@ void IOSelector::clear_connections () { if (for_input) { - io.disconnect_inputs (this); + io->disconnect_inputs (this); } else { - io.disconnect_outputs (this); + io->disconnect_outputs (this); } } @@ -374,9 +374,9 @@ IOSelector::display_ports () uint32_t limit; if (for_input) { - limit = io.n_inputs(); + limit = io->n_inputs(); } else { - limit = io.n_outputs(); + limit = io->n_outputs(); } for (slist::iterator i = port_displays.begin(); i != port_displays.end(); ) { @@ -401,9 +401,9 @@ IOSelector::display_ports () string really_short_name; if (for_input) { - port = io.input (n); + port = io->input (n); } else { - port = io.output (n); + port = io->output (n); } /* we know there is '/' because we put it there */ @@ -443,7 +443,7 @@ IOSelector::display_ports () if (for_input) { - if (io.input_maximum() == 1) { + if (io->input_maximum() == 1) { selected_port = port; selected_port_tview = tview; } else { @@ -454,7 +454,7 @@ IOSelector::display_ports () } else { - if (io.output_maximum() == 1) { + if (io->output_maximum() == 1) { selected_port = port; selected_port_tview = tview; } else { @@ -516,12 +516,12 @@ IOSelector::port_selection_changed (GdkEventButton *ev, TreeView* treeview) ustring other_port_name = (*i)[port_display_columns.full_name]; if (for_input) { - if ((status = io.connect_input (selected_port, other_port_name, this)) == 0) { + if ((status = io->connect_input (selected_port, other_port_name, this)) == 0) { Port *p = session.engine().get_port_by_name (other_port_name); p->enable_metering(); } } else { - status = io.connect_output (selected_port, other_port_name, this); + status = io->connect_output (selected_port, other_port_name, this); } if (status == 0) { @@ -548,7 +548,7 @@ IOSelector::add_port () if (for_input) { try { - io.add_input_port ("", this); + io->add_input_port ("", this); } catch (AudioEngine::PortRegistrationFailure& err) { @@ -556,18 +556,18 @@ IOSelector::add_port () msg.run (); } - if (io.input_maximum() >= 0 && io.input_maximum() <= (int) io.n_inputs()) { + if (io->input_maximum() >= 0 && io->input_maximum() <= (int) io->n_inputs()) { add_port_button.set_sensitive (false); } - if (io.input_minimum() < (int) io.n_inputs()) { + if (io->input_minimum() < (int) io->n_inputs()) { remove_port_button.set_sensitive (true); } } else { try { - io.add_output_port ("", this); + io->add_output_port ("", this); } catch (AudioEngine::PortRegistrationFailure& err) { @@ -575,7 +575,7 @@ IOSelector::add_port () msg.run (); } - if (io.output_maximum() >= 0 && io.output_maximum() <= (int) io.n_outputs()) { + if (io->output_maximum() >= 0 && io->output_maximum() <= (int) io->n_outputs()) { add_port_button.set_sensitive (false); } } @@ -589,15 +589,15 @@ IOSelector::remove_port () // always remove last port if (for_input) { - if ((nports = io.n_inputs()) > 0) { - io.remove_input_port (io.input(nports-1), this); + if ((nports = io->n_inputs()) > 0) { + io->remove_input_port (io->input(nports-1), this); } - if (io.input_minimum() == (int) io.n_inputs()) { + if (io->input_minimum() == (int) io->n_inputs()) { remove_port_button.set_sensitive (false); } } else { - if ((nports = io.n_outputs()) > 0) { - io.remove_output_port (io.output(nports-1), this); + if ((nports = io->n_outputs()) > 0) { + io->remove_output_port (io->output(nports-1), this); } } } @@ -606,9 +606,9 @@ gint IOSelector::remove_port_when_idle (Port *port) { if (for_input) { - io.remove_input_port (port, this); + io->remove_input_port (port, this); } else { - io.remove_output_port (port, this); + io->remove_output_port (port, this); } return FALSE; @@ -651,9 +651,9 @@ IOSelector::connection_button_release (GdkEventButton *ev, TreeView *treeview) if (for_input) { Port *p = session.engine().get_port_by_name (connected_port_name); p->disable_metering(); - io.disconnect_input (port, connected_port_name, this); + io->disconnect_input (port, connected_port_name, this); } else { - io.disconnect_output (port, connected_port_name, this); + io->disconnect_output (port, connected_port_name, this); } } @@ -749,17 +749,17 @@ IOSelector::redisplay () display_ports (); if (for_input) { - if (io.input_maximum() != 0) { + if (io->input_maximum() != 0) { rescan (); } } else { - if (io.output_maximum() != 0) { + if (io->output_maximum() != 0) { rescan(); } } } -PortInsertUI::PortInsertUI (Session& sess, PortInsert& pi) +PortInsertUI::PortInsertUI (Session& sess, boost::shared_ptr pi) : input_selector (sess, pi, true), output_selector (sess, pi, false) { @@ -786,9 +786,9 @@ PortInsertUI::finished(IOSelector::Result r) } -PortInsertWindow::PortInsertWindow (Session& sess, PortInsert& pi, bool can_cancel) +PortInsertWindow::PortInsertWindow (Session& sess, boost::shared_ptr pi, bool can_cancel) : ArdourDialog ("port insert dialog"), - _portinsertui(sess, pi), + _portinsertui (sess, pi), ok_button (can_cancel ? _("OK"): _("Close")), cancel_button (_("Cancel")), rescan_button (_("Rescan")) @@ -796,7 +796,7 @@ PortInsertWindow::PortInsertWindow (Session& sess, PortInsert& pi, bool can_canc set_name ("IOSelectorWindow"); string title = _("ardour: "); - title += pi.name(); + title += pi->name(); set_title (title); ok_button.set_name ("IOSelectorButton"); @@ -823,7 +823,7 @@ PortInsertWindow::PortInsertWindow (Session& sess, PortInsert& pi, bool can_canc rescan_button.signal_clicked().connect (mem_fun(*this, &PortInsertWindow::rescan)); signal_delete_event().connect (bind (sigc::ptr_fun (just_hide_it), reinterpret_cast (this))); - pi.GoingAway.connect (mem_fun(*this, &PortInsertWindow::plugin_going_away)); + pi->GoingAway.connect (mem_fun(*this, &PortInsertWindow::plugin_going_away)); } void diff --git a/gtk2_ardour/io_selector.h b/gtk2_ardour/io_selector.h index 44518e6759..993d4aa1ad 100644 --- a/gtk2_ardour/io_selector.h +++ b/gtk2_ardour/io_selector.h @@ -53,7 +53,7 @@ namespace ARDOUR { class IOSelector : public Gtk::VBox { public: - IOSelector (ARDOUR::Session&, ARDOUR::IO&, bool for_input); + IOSelector (ARDOUR::Session&, boost::shared_ptr, bool for_input); ~IOSelector (); void redisplay (); @@ -67,9 +67,9 @@ class IOSelector : public Gtk::VBox { protected: ARDOUR::Session& session; - + private: - ARDOUR::IO& io; + boost::shared_ptr io; bool for_input; ARDOUR::Port *selected_port; @@ -135,7 +135,7 @@ class IOSelector : public Gtk::VBox { class IOSelectorWindow : public ArdourDialog { public: - IOSelectorWindow (ARDOUR::Session&, ARDOUR::IO&, bool for_input, bool can_cancel=false); + IOSelectorWindow (ARDOUR::Session&, boost::shared_ptr, bool for_input, bool can_cancel=false); ~IOSelectorWindow (); IOSelector& selector() { return _selector; } @@ -162,7 +162,7 @@ class IOSelectorWindow : public ArdourDialog class PortInsertUI : public Gtk::VBox { public: - PortInsertUI (ARDOUR::Session&, ARDOUR::PortInsert&); + PortInsertUI (ARDOUR::Session&, boost::shared_ptr); void redisplay (); void finished (IOSelector::Result); @@ -178,7 +178,7 @@ class PortInsertUI : public Gtk::VBox class PortInsertWindow : public ArdourDialog { public: - PortInsertWindow (ARDOUR::Session&, ARDOUR::PortInsert&, bool can_cancel=false); + PortInsertWindow (ARDOUR::Session&, boost::shared_ptr, bool can_cancel=false); protected: void on_map (); diff --git a/gtk2_ardour/keyboard.h b/gtk2_ardour/keyboard.h index 06ed4c800d..c13b06afe5 100644 --- a/gtk2_ardour/keyboard.h +++ b/gtk2_ardour/keyboard.h @@ -28,7 +28,7 @@ #include #include -#include +#include #include "selection.h" diff --git a/gtk2_ardour/main.cc b/gtk2_ardour/main.cc index 778355c858..047bb130a4 100644 --- a/gtk2_ardour/main.cc +++ b/gtk2_ardour/main.cc @@ -446,7 +446,7 @@ int main (int argc, char *argv[]) try { engine = new ARDOUR::AudioEngine (jack_client_name); - ARDOUR::init (*engine, use_vst, try_hw_optimization); + ARDOUR::init (use_vst, try_hw_optimization); ui->set_engine (*engine); } catch (AudioEngine::NoBackendAvailable& err) { gui_jack_error (); diff --git a/gtk2_ardour/mixer_strip.cc b/gtk2_ardour/mixer_strip.cc index 47d884be5e..4f3dc720d9 100644 --- a/gtk2_ardour/mixer_strip.cc +++ b/gtk2_ardour/mixer_strip.cc @@ -27,10 +27,10 @@ #include #include #include -#include #include -#include #include +#include +#include #include #include @@ -52,7 +52,6 @@ #include "keyboard.h" #include "plugin_selector.h" #include "public_editor.h" - #include "plugin_ui.h" #include "send_ui.h" #include "io_selector.h" @@ -81,7 +80,7 @@ speed_printer (char buf[32], Gtk::Adjustment& adj, void* arg) } #endif -MixerStrip::MixerStrip (Mixer_UI& mx, Session& sess, Route& rt, bool in_mixer) +MixerStrip::MixerStrip (Mixer_UI& mx, Session& sess, boost::shared_ptr rt, bool in_mixer) : AxisView(sess), RouteUI (rt, sess, _("Mute"), _("Solo"), _("Record")), _mixer(mx), @@ -126,12 +125,12 @@ MixerStrip::MixerStrip (Mixer_UI& mx, Session& sess, Route& rt, bool in_mixer) output_button.set_name ("MixerIOButton"); output_label.set_name ("MixerIOButtonLabel"); - _route.meter_change.connect (mem_fun(*this, &MixerStrip::meter_changed)); + _route->meter_change.connect (mem_fun(*this, &MixerStrip::meter_changed)); meter_point_button.add (meter_point_label); meter_point_button.set_name ("MixerStripMeterPreButton"); meter_point_label.set_name ("MixerStripMeterPreButton"); - switch (_route.meter_point()) { + switch (_route->meter_point()) { case MeterInput: meter_point_label.set_text (_("input")); break; @@ -159,9 +158,6 @@ MixerStrip::MixerStrip (Mixer_UI& mx, Session& sess, Route& rt, bool in_mixer) /* XXX what is this meant to do? */ //meter_point_button.signal_button_release_event().connect (mem_fun (gpm, &GainMeter::meter_release), false); - rec_enable_button->set_name ("MixerRecordEnableButton"); - rec_enable_button->unset_flags (Gtk::CAN_FOCUS); - solo_button->set_name ("MixerSoloButton"); mute_button->set_name ("MixerMuteButton"); @@ -191,7 +187,11 @@ MixerStrip::MixerStrip (Mixer_UI& mx, Session& sess, Route& rt, bool in_mixer) if (is_audio_track()) { - AudioTrack* at = dynamic_cast(&_route); + rec_enable_button->set_name ("MixerRecordEnableButton"); + rec_enable_button->unset_flags (Gtk::CAN_FOCUS); + rec_enable_button->signal_button_press_event().connect (mem_fun(*this, &RouteUI::rec_enable_press)); + + AudioTrack* at = audio_track(); at->FreezeChange.connect (mem_fun(*this, &MixerStrip::map_frozen)); @@ -217,10 +217,10 @@ MixerStrip::MixerStrip (Mixer_UI& mx, Session& sess, Route& rt, bool in_mixer) Gtkmm2ext::set_size_request_to_display_given_text (name_button, "longest label", 2, 2); name_label.set_name ("MixerNameButtonLabel"); - if (_route.phase_invert()) { + if (_route->phase_invert()) { name_label.set_text (X_("Ø ") + name_label.get_text()); } else { - name_label.set_text (_route.name()); + name_label.set_text (_route->name()); } group_button.add (group_label); @@ -229,9 +229,9 @@ MixerStrip::MixerStrip (Mixer_UI& mx, Session& sess, Route& rt, bool in_mixer) comment_button.set_name ("MixerCommentButton"); - ARDOUR_UI::instance()->tooltips().set_tip (comment_button, _route.comment()=="" ? + ARDOUR_UI::instance()->tooltips().set_tip (comment_button, _route->comment()=="" ? _("Click to Add/Edit Comments"): - _route.comment()); + _route->comment()); comment_button.signal_clicked().connect (mem_fun(*this, &MixerStrip::comment_button_clicked)); @@ -281,27 +281,26 @@ MixerStrip::MixerStrip (Mixer_UI& mx, Session& sess, Route& rt, bool in_mixer) _session.engine().Stopped.connect (mem_fun(*this, &MixerStrip::engine_stopped)); _session.engine().Running.connect (mem_fun(*this, &MixerStrip::engine_running)); - _route.input_changed.connect (mem_fun(*this, &MixerStrip::input_changed)); - _route.output_changed.connect (mem_fun(*this, &MixerStrip::output_changed)); - _route.mute_changed.connect (mem_fun(*this, &RouteUI::mute_changed)); - _route.solo_changed.connect (mem_fun(*this, &RouteUI::solo_changed)); - _route.solo_safe_changed.connect (mem_fun(*this, &RouteUI::solo_changed)); - _route.mix_group_changed.connect (mem_fun(*this, &MixerStrip::mix_group_changed)); - _route.panner().Changed.connect (mem_fun(*this, &MixerStrip::connect_to_pan)); + _route->input_changed.connect (mem_fun(*this, &MixerStrip::input_changed)); + _route->output_changed.connect (mem_fun(*this, &MixerStrip::output_changed)); + _route->mute_changed.connect (mem_fun(*this, &RouteUI::mute_changed)); + _route->solo_changed.connect (mem_fun(*this, &RouteUI::solo_changed)); + _route->solo_safe_changed.connect (mem_fun(*this, &RouteUI::solo_changed)); + _route->mix_group_changed.connect (mem_fun(*this, &MixerStrip::mix_group_changed)); + _route->panner().Changed.connect (mem_fun(*this, &MixerStrip::connect_to_pan)); if (is_audio_track()) { - audio_track()->diskstream_changed.connect (mem_fun(*this, &MixerStrip::diskstream_changed)); - get_diskstream()->speed_changed.connect (mem_fun(*this, &MixerStrip::speed_changed)); + audio_track()->DiskstreamChanged.connect (mem_fun(*this, &MixerStrip::diskstream_changed)); + get_diskstream()->SpeedChanged.connect (mem_fun(*this, &MixerStrip::speed_changed)); } - _route.name_changed.connect (mem_fun(*this, &RouteUI::name_changed)); - _route.comment_changed.connect (mem_fun(*this, &MixerStrip::comment_changed)); - _route.gui_changed.connect (mem_fun(*this, &MixerStrip::route_gui_changed)); + _route->name_changed.connect (mem_fun(*this, &RouteUI::name_changed)); + _route->comment_changed.connect (mem_fun(*this, &MixerStrip::comment_changed)); + _route->gui_changed.connect (mem_fun(*this, &MixerStrip::route_gui_changed)); input_button.signal_button_press_event().connect (mem_fun(*this, &MixerStrip::input_press), false); output_button.signal_button_press_event().connect (mem_fun(*this, &MixerStrip::output_press), false); - rec_enable_button->signal_button_press_event().connect (mem_fun(*this, &RouteUI::rec_enable_press)); solo_button->signal_button_press_event().connect (mem_fun(*this, &RouteUI::solo_press), false); solo_button->signal_button_release_event().connect (mem_fun(*this, &RouteUI::solo_release), false); mute_button->signal_button_press_event().connect (mem_fun(*this, &RouteUI::mute_press), false); @@ -414,20 +413,22 @@ MixerStrip::set_width (Width w) set_size_request (-1, -1); xml_node->add_property ("strip_width", "wide"); - rec_enable_button->set_label (_("record")); + if (rec_enable_button) { + rec_enable_button->set_label (_("record")); + } mute_button->set_label (_("mute")); solo_button->set_label (_("solo")); - if (_route.comment() == "") { + if (_route->comment() == "") { comment_button.set_label (_("comments")); } else { comment_button.set_label (_("*comments*")); } - gpm.gain_automation_style_button.set_label (gpm.astyle_string(_route.gain_automation_curve().automation_style())); - gpm.gain_automation_state_button.set_label (gpm.astate_string(_route.gain_automation_curve().automation_state())); - panners.pan_automation_style_button.set_label (panners.astyle_string(_route.panner().automation_style())); - panners.pan_automation_state_button.set_label (panners.astate_string(_route.panner().automation_state())); + gpm.gain_automation_style_button.set_label (gpm.astyle_string(_route->gain_automation_curve().automation_style())); + gpm.gain_automation_state_button.set_label (gpm.astate_string(_route->gain_automation_curve().automation_state())); + panners.pan_automation_style_button.set_label (panners.astyle_string(_route->panner().automation_style())); + panners.pan_automation_state_button.set_label (panners.astate_string(_route->panner().automation_state())); Gtkmm2ext::set_size_request_to_display_given_text (name_button, "long", 2, 2); break; @@ -435,20 +436,22 @@ MixerStrip::set_width (Width w) set_size_request (50, -1); xml_node->add_property ("strip_width", "narrow"); - rec_enable_button->set_label (_("Rec")); + if (rec_enable_button) { + rec_enable_button->set_label (_("Rec")); + } mute_button->set_label (_("M")); solo_button->set_label (_("S")); - if (_route.comment() == "") { + if (_route->comment() == "") { comment_button.set_label (_("Cmt")); } else { comment_button.set_label (_("*Cmt*")); } - gpm.gain_automation_style_button.set_label (gpm.short_astyle_string(_route.gain_automation_curve().automation_style())); - gpm.gain_automation_state_button.set_label (gpm.short_astate_string(_route.gain_automation_curve().automation_state())); - panners.pan_automation_style_button.set_label (panners.short_astyle_string(_route.panner().automation_style())); - panners.pan_automation_state_button.set_label (panners.short_astate_string(_route.panner().automation_state())); + gpm.gain_automation_style_button.set_label (gpm.short_astyle_string(_route->gain_automation_curve().automation_style())); + gpm.gain_automation_state_button.set_label (gpm.short_astate_string(_route->gain_automation_curve().automation_state())); + panners.pan_automation_style_button.set_label (panners.short_astyle_string(_route->panner().automation_style())); + panners.pan_automation_state_button.set_label (panners.short_astate_string(_route->panner().automation_state())); Gtkmm2ext::set_size_request_to_display_given_text (name_button, "longest label", 2, 2); break; } @@ -555,11 +558,6 @@ MixerStrip::input_press (GdkEventButton *ev) case 1: -#if ADVANCED_ROUTE_DISKSTREAM_CONNECTIVITY - if (is_audio_track()) { - citems.push_back (MenuElem (_("Track"), mem_fun(*this, &MixerStrip::select_stream_input))); - } -#endif citems.push_back (MenuElem (_("Edit"), mem_fun(*this, &MixerStrip::edit_input_configuration))); citems.push_back (SeparatorElem()); citems.push_back (MenuElem (_("Disconnect"), mem_fun (*(static_cast(this)), &RouteUI::disconnect_input))); @@ -581,7 +579,7 @@ MixerStrip::connection_input_chosen (ARDOUR::Connection *c) if (!ignore_toggle) { try { - _route.use_input_connection (*c, this); + _route->use_input_connection (*c, this); } catch (AudioEngine::PortRegistrationFailure& err) { @@ -597,7 +595,7 @@ MixerStrip::connection_output_chosen (ARDOUR::Connection *c) if (!ignore_toggle) { try { - _route.use_output_connection (*c, this); + _route->use_output_connection (*c, this); } catch (AudioEngine::PortRegistrationFailure& err) { @@ -618,11 +616,11 @@ MixerStrip::add_connection_to_input_menu (ARDOUR::Connection* c) MenuList& citems = input_menu.items(); - if (c->nports() == _route.n_inputs()) { + if (c->nports() == _route->n_inputs()) { citems.push_back (CheckMenuElem (c->name(), bind (mem_fun(*this, &MixerStrip::connection_input_chosen), c))); - ARDOUR::Connection *current = _route.input_connection(); + ARDOUR::Connection *current = _route->input_connection(); if (current == c) { ignore_toggle = true; @@ -641,12 +639,12 @@ MixerStrip::add_connection_to_output_menu (ARDOUR::Connection* c) return; } - if (c->nports() == _route.n_outputs()) { + if (c->nports() == _route->n_outputs()) { MenuList& citems = output_menu.items(); citems.push_back (CheckMenuElem (c->name(), bind (mem_fun(*this, &MixerStrip::connection_output_chosen), c))); - ARDOUR::Connection *current = _route.output_connection(); + ARDOUR::Connection *current = _route->output_connection(); if (current == c) { ignore_toggle = true; @@ -656,42 +654,6 @@ MixerStrip::add_connection_to_output_menu (ARDOUR::Connection* c) } } -void -MixerStrip::select_stream_input () -{ - using namespace Menu_Helpers; - - Menu *stream_menu = manage (new Menu); - MenuList& items = stream_menu->items(); - stream_menu->set_name ("ArdourContextMenu"); - - Session::AudioDiskstreamList streams = _session.audio_disk_streams(); - - for (Session::AudioDiskstreamList::iterator i = streams.begin(); i != streams.end(); ++i) { - - if (!(*i)->hidden()) { - - items.push_back (CheckMenuElem ((*i)->name(), bind (mem_fun(*this, &MixerStrip::stream_input_chosen), *i))); - - if (get_diskstream() == *i) { - ignore_toggle = true; - static_cast (&items.back())->set_active (true); - ignore_toggle = false; - } - } - } - - stream_menu->popup (1, 0); -} - -void -MixerStrip::stream_input_chosen (AudioDiskstream *stream) -{ - if (is_audio_track()) { - audio_track()->set_diskstream (*stream, this); - } -} - void MixerStrip::update_diskstream_display () { @@ -724,8 +686,8 @@ MixerStrip::connect_to_pan () panstate_connection.disconnect (); panstyle_connection.disconnect (); - if (!_route.panner().empty()) { - StreamPanner* sp = _route.panner().front(); + if (!_route->panner().empty()) { + StreamPanner* sp = _route->panner().front(); panstate_connection = sp->automation().automation_state_changed.connect (mem_fun(panners, &PannerUI::pan_automation_state_changed)); panstyle_connection = sp->automation().automation_style_changed.connect (mem_fun(panners, &PannerUI::pan_automation_style_changed)); @@ -739,7 +701,7 @@ MixerStrip::update_input_display () { ARDOUR::Connection *c; - if ((c = _route.input_connection()) != 0) { + if ((c = _route->input_connection()) != 0) { input_label.set_text (c->name()); } else { switch (_width) { @@ -759,7 +721,7 @@ MixerStrip::update_output_display () { ARDOUR::Connection *c; - if ((c = _route.output_connection()) != 0) { + if ((c = _route->output_connection()) != 0) { output_label.set_text (c->name()); } else { switch (_width) { @@ -782,7 +744,7 @@ MixerStrip::fast_update () } void -MixerStrip::diskstream_changed (void *src) +MixerStrip::diskstream_changed () { Gtkmm2ext::UI::instance()->call_slot (mem_fun(*this, &MixerStrip::update_diskstream_display)); } @@ -810,8 +772,8 @@ MixerStrip::comment_button_clicked () if (comment_window->is_visible()) { string str = comment_area->get_buffer()->get_text(); - if (_route.comment() != str) { - _route.set_comment (str, this); + if (_route->comment() != str) { + _route->set_comment (str, this); switch (_width) { @@ -855,7 +817,7 @@ void MixerStrip::setup_comment_editor () { string title; - title = _route.name(); + title = _route->name(); title += _(": comment editor"); comment_window = new ArdourDialog (title, false); @@ -867,7 +829,7 @@ MixerStrip::setup_comment_editor () comment_area->set_size_request (110, 178); comment_area->set_wrap_mode (WRAP_WORD); comment_area->set_editable (true); - comment_area->get_buffer()->set_text (_route.comment()); + comment_area->get_buffer()->set_text (_route->comment()); comment_area->show (); comment_window->get_vbox()->pack_start (*comment_area); @@ -882,7 +844,7 @@ MixerStrip::comment_changed (void *src) if (src != this) { ignore_comment_edit = true; if (comment_area) { - comment_area->get_buffer()->set_text (_route.comment()); + comment_area->get_buffer()->set_text (_route->comment()); } ignore_comment_edit = false; } @@ -891,7 +853,7 @@ MixerStrip::comment_changed (void *src) void MixerStrip::set_mix_group (RouteGroup *rg) { - _route.set_mix_group (rg, this); + _route->set_mix_group (rg, this); } void @@ -903,7 +865,7 @@ MixerStrip::add_mix_group_to_menu (RouteGroup *rg, RadioMenuItem::Group* group) items.push_back (RadioMenuElem (*group, rg->name(), bind (mem_fun(*this, &MixerStrip::set_mix_group), rg))); - if (_route.mix_group() == rg) { + if (_route->mix_group() == rg) { static_cast(&items.back())->set_active (); } } @@ -943,7 +905,7 @@ MixerStrip::mix_group_changed (void *ignored) { ENSURE_GUI_THREAD(bind (mem_fun(*this, &MixerStrip::mix_group_changed), ignored)); - RouteGroup *rg = _route.mix_group(); + RouteGroup *rg = _route->mix_group(); if (rg) { group_label.set_text (rg->name()); @@ -999,11 +961,11 @@ MixerStrip::build_route_ops_menu () items.push_back (SeparatorElem()); items.push_back (CheckMenuElem (_("Active"), mem_fun (*this, &RouteUI::toggle_route_active))); route_active_menu_item = dynamic_cast (&items.back()); - route_active_menu_item->set_active (_route.active()); + route_active_menu_item->set_active (_route->active()); items.push_back (SeparatorElem()); items.push_back (CheckMenuElem (_("Invert Polarity"), mem_fun (*this, &RouteUI::toggle_polarity))); polarity_menu_item = dynamic_cast (&items.back()); - polarity_menu_item->set_active (_route.phase_invert()); + polarity_menu_item->set_active (_route->phase_invert()); build_remote_control_menu (); @@ -1093,10 +1055,10 @@ MixerStrip::name_changed (void *src) RouteUI::name_changed (src); break; case Narrow: - name_label.set_text (PBD::short_version (_route.name(), 5)); + name_label.set_text (PBD::short_version (_route->name(), 5)); break; } - if (_route.phase_invert()) { + if (_route->phase_invert()) { name_label.set_text (X_("Ø ") + name_label.get_text()); } } @@ -1135,7 +1097,7 @@ MixerStrip::map_frozen () { ENSURE_GUI_THREAD (mem_fun(*this, &MixerStrip::map_frozen)); - AudioTrack* at = dynamic_cast(&_route); + AudioTrack* at = audio_track(); if (at) { switch (at->freeze_state()) { @@ -1151,11 +1113,11 @@ MixerStrip::map_frozen () break; } } - _route.foreach_redirect (this, &MixerStrip::hide_redirect_editor); + _route->foreach_redirect (this, &MixerStrip::hide_redirect_editor); } void -MixerStrip::hide_redirect_editor (Redirect* redirect) +MixerStrip::hide_redirect_editor (boost::shared_ptr redirect) { void* gui = redirect->get_gui (); @@ -1170,7 +1132,7 @@ MixerStrip::route_active_changed () RouteUI::route_active_changed (); if (is_audio_track()) { - if (_route.active()) { + if (_route->active()) { set_name ("AudioTrackStripBase"); gpm.set_meter_strip_name ("AudioTrackStripBase"); } else { @@ -1178,8 +1140,8 @@ MixerStrip::route_active_changed () gpm.set_meter_strip_name ("AudioTrackStripBaseInactive"); } gpm.set_fader_name ("AudioTrackFader"); - } else { - if (_route.active()) { + } else { // FIXME: assumed audio bus + if (_route->active()) { set_name ("AudioBusStripBase"); gpm.set_meter_strip_name ("AudioBusStripBase"); } else { @@ -1193,14 +1155,16 @@ MixerStrip::route_active_changed () RouteGroup* MixerStrip::mix_group() const { - return _route.mix_group(); + return _route->mix_group(); } void MixerStrip::engine_stopped () { input_button.set_sensitive (false); - rec_enable_button->set_sensitive (false); + if (rec_enable_button) { + rec_enable_button->set_sensitive (false); + } output_button.set_sensitive (false); } @@ -1208,7 +1172,9 @@ void MixerStrip::engine_running () { input_button.set_sensitive (true); - rec_enable_button->set_sensitive (true); + if (rec_enable_button) { + rec_enable_button->set_sensitive (true); + } output_button.set_sensitive (true); } @@ -1218,7 +1184,7 @@ MixerStrip::meter_changed (void *src) ENSURE_GUI_THREAD (bind (mem_fun(*this, &MixerStrip::meter_changed), src)); - switch (_route.meter_point()) { + switch (_route->meter_point()) { case MeterInput: meter_point_label.set_text (_("input")); break; diff --git a/gtk2_ardour/mixer_strip.h b/gtk2_ardour/mixer_strip.h index 0cc8fed8e3..21db0d14ca 100644 --- a/gtk2_ardour/mixer_strip.h +++ b/gtk2_ardour/mixer_strip.h @@ -1,5 +1,5 @@ /* - Copyright (C) 2000 Paul Davis + Copyright (C) 2000-2006 Paul Davis This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -14,8 +14,6 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ */ #ifndef __ardour_mixer_strip__ @@ -37,14 +35,15 @@ #include #include -#include #include +#include + +#include #include #include #include #include -#include #include #include @@ -83,7 +82,7 @@ class Mixer_UI; class MixerStrip : public RouteUI, public Gtk::EventBox { public: - MixerStrip (Mixer_UI&, ARDOUR::Session&, ARDOUR::Route &, bool in_mixer = true); + MixerStrip (Mixer_UI&, ARDOUR::Session&, boost::shared_ptr, bool in_mixer = true); ~MixerStrip (); void set_width (Width); @@ -170,15 +169,13 @@ class MixerStrip : public RouteUI, public Gtk::EventBox Gtk::Menu output_menu; void add_connection_to_output_menu (ARDOUR::Connection *); - void stream_input_chosen (ARDOUR::AudioDiskstream*); - void select_stream_input (); void connection_input_chosen (ARDOUR::Connection *); void connection_output_chosen (ARDOUR::Connection *); void edit_input_configuration (); void edit_output_configuration (); - void diskstream_changed (void *src); + void diskstream_changed (); Gtk::Menu *send_action_menu; void build_send_action_menu (); @@ -238,7 +235,7 @@ class MixerStrip : public RouteUI, public Gtk::EventBox void name_changed (void *src); void update_speed_display (); void map_frozen (); - void hide_redirect_editor (ARDOUR::Redirect* redirect); + void hide_redirect_editor (boost::shared_ptr redirect); bool ignore_speed_adjustment; diff --git a/gtk2_ardour/mixer_ui.cc b/gtk2_ardour/mixer_ui.cc index 983903d6dd..c2eb588b2f 100644 --- a/gtk2_ardour/mixer_ui.cc +++ b/gtk2_ardour/mixer_ui.cc @@ -251,7 +251,7 @@ Mixer_UI::show_window () } void -Mixer_UI::add_strip (Route* route) +Mixer_UI::add_strip (boost::shared_ptr route) { ENSURE_GUI_THREAD(bind (mem_fun(*this, &Mixer_UI::add_strip), route)); @@ -261,7 +261,7 @@ Mixer_UI::add_strip (Route* route) return; } - strip = new MixerStrip (*this, *session, *route); + strip = new MixerStrip (*this, *session, route); strips.push_back (strip); strip->set_width (_strip_width); @@ -310,7 +310,7 @@ void Mixer_UI::follow_strip_selection () { for (list::iterator i = strips.begin(); i != strips.end(); ++i) { - (*i)->set_selected (_selection.selected (&(*i)->route())); + (*i)->set_selected (_selection.selected ((*i)->route())); } } @@ -324,13 +324,13 @@ Mixer_UI::strip_button_release_event (GdkEventButton *ev, MixerStrip *strip) at the same time. */ - if (_selection.selected (&strip->route())) { - _selection.remove (&strip->route()); + if (_selection.selected (strip->route())) { + _selection.remove (strip->route()); } else { if (Keyboard::modifier_state_equals (ev->state, Keyboard::Shift)) { - _selection.add (&strip->route()); + _selection.add (strip->route()); } else { - _selection.set (&strip->route()); + _selection.set (strip->route()); } } } @@ -444,7 +444,7 @@ Mixer_UI::set_all_strips_visibility (bool yn) continue; } - if (strip->route().master() || strip->route().control()) { + if (strip->route()->master() || strip->route()->control()) { continue; } @@ -472,11 +472,11 @@ Mixer_UI::set_all_audio_visibility (int tracks, bool yn) continue; } - if (strip->route().master() || strip->route().control()) { + if (strip->route()->master() || strip->route()->control()) { continue; } - AudioTrack* at = dynamic_cast (&strip->route()); + AudioTrack* at = strip->audio_track(); switch (tracks) { case 0: @@ -570,11 +570,11 @@ Mixer_UI::redisplay_track_list () if (visible) { strip->set_marked_for_display (true); - strip->route().set_order_key (N_("signal"), order); + strip->route()->set_order_key (N_("signal"), order); if (strip->packed()) { - if (strip->route().master() || strip->route().control()) { + if (strip->route()->master() || strip->route()->control()) { out_packer.reorder_child (*strip, -1); } else { strip_packer.reorder_child (*strip, -1); /* put at end */ @@ -582,7 +582,7 @@ Mixer_UI::redisplay_track_list () } else { - if (strip->route().master() || strip->route().control()) { + if (strip->route()->master() || strip->route()->control()) { out_packer.pack_start (*strip, false, false); } else { strip_packer.pack_start (*strip, false, false); @@ -593,7 +593,7 @@ Mixer_UI::redisplay_track_list () } else { - if (strip->route().master() || strip->route().control()) { + if (strip->route()->master() || strip->route()->control()) { /* do nothing, these cannot be hidden */ } else { strip_packer.remove (*strip); @@ -604,7 +604,7 @@ Mixer_UI::redisplay_track_list () } struct SignalOrderRouteSorter { - bool operator() (Route* a, Route* b) { + bool operator() (boost::shared_ptr a, boost::shared_ptr b) { /* use of ">" forces the correct sort order */ return a->order_key ("signal") < b->order_key ("signal"); } @@ -613,16 +613,17 @@ struct SignalOrderRouteSorter { void Mixer_UI::initial_track_display () { - Session::RouteList routes = session->get_routes(); + boost::shared_ptr routes = session->get_routes(); + Session::RouteList copy (*routes); SignalOrderRouteSorter sorter; - routes.sort (sorter); + copy.sort (sorter); no_track_list_redisplay = true; track_model->clear (); - for (Session::RouteList::iterator i = routes.begin(); i != routes.end(); ++i) { + for (Session::RouteList::iterator i = copy.begin(); i != copy.end(); ++i) { add_strip (*i); } @@ -670,7 +671,7 @@ Mixer_UI::track_display_button_press (GdkEventButton* ev) MixerStrip* strip = (*iter)[track_columns.strip]; if (strip) { - if (!strip->route().master() && !strip->route().control()) { + if (!strip->route()->master() && !strip->route()->control()) { bool visible = (*iter)[track_columns.visible]; (*iter)[track_columns.visible] = !visible; } @@ -715,7 +716,7 @@ Mixer_UI::strip_name_changed (void* src, MixerStrip* mx) for (i = rows.begin(); i != rows.end(); ++i) { if ((*i)[track_columns.strip] == mx) { - (*i)[track_columns.text] = mx->route().name(); + (*i)[track_columns.text] = mx->route()->name(); return; } } diff --git a/gtk2_ardour/mixer_ui.h b/gtk2_ardour/mixer_ui.h index 5108df6014..6fe4120427 100644 --- a/gtk2_ardour/mixer_ui.h +++ b/gtk2_ardour/mixer_ui.h @@ -33,8 +33,9 @@ #include #include +#include + #include -#include #include #include "keyboard_target.h" @@ -110,7 +111,7 @@ class Mixer_UI : public Gtk::Window bool strip_scroller_button_release (GdkEventButton*); - void add_strip (ARDOUR::Route*); + void add_strip (boost::shared_ptr); void remove_strip (MixerStrip *); void hide_all_strips (bool with_select); @@ -193,7 +194,7 @@ class Mixer_UI : public Gtk::Window } Gtk::TreeModelColumn visible; Gtk::TreeModelColumn text; - Gtk::TreeModelColumn route; + Gtk::TreeModelColumn > route; Gtk::TreeModelColumn strip; }; diff --git a/gtk2_ardour/option_editor.cc b/gtk2_ardour/option_editor.cc index d4c2715742..b7fc7e746e 100644 --- a/gtk2_ardour/option_editor.cc +++ b/gtk2_ardour/option_editor.cc @@ -1,5 +1,5 @@ /* - Copyright (C) 2001 Paul Davis + Copyright (C) 2001-2006 Paul Davis This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -20,6 +20,7 @@ #include +#include #include #include #include @@ -59,9 +60,7 @@ OptionEditor::OptionEditor (ARDOUR_UI& uip, PublicEditor& ed, Mixer_UI& mixui) /* Paths */ path_table (11, 2), - sfdb_path_columns(), - sfdb_paths(ListStore::create(sfdb_path_columns)), - sfdb_path_view(sfdb_paths), + sfdb_path_view(), /* Fades */ @@ -163,7 +162,6 @@ OptionEditor::set_session (Session *s) return; } - click_path_entry.set_sensitive (true); click_emphasis_path_entry.set_sensitive (true); session_raid_entry.set_sensitive (true); @@ -251,12 +249,18 @@ OptionEditor::setup_path_options() path_table.attach(*label, 0, 1, 2, 3, FILL|EXPAND, FILL); path_table.attach(sfdb_path_view, 1, 3, 2, 3, Gtk::FILL|Gtk::EXPAND, FILL); - sfdb_path_view.append_column(_("Paths"), sfdb_path_columns.paths); - sfdb_path_view.set_size_request(-1, 100); + sfdb_path_view.set_paths(Library->get_paths()); + sfdb_path_view.PathsUpdated.connect (mem_fun(*this, &OptionEditor::sfdb_paths_changed)); path_table.show_all(); } +void +OptionEditor::sfdb_paths_changed () +{ + Library->set_paths (sfdb_path_view.get_paths()); +} + void OptionEditor::add_session_paths () { diff --git a/gtk2_ardour/option_editor.h b/gtk2_ardour/option_editor.h index b9690b02e2..1331d3126e 100644 --- a/gtk2_ardour/option_editor.h +++ b/gtk2_ardour/option_editor.h @@ -33,6 +33,8 @@ #include #include +#include + #include #include "ardour_dialog.h" @@ -70,24 +72,16 @@ class OptionEditor : public Gtk::Dialog /* paths */ - Gtk::Table path_table; - Gtk::Entry session_raid_entry; + Gtk::Table path_table; + Gtk::Entry session_raid_entry; - struct SoundFilePathColumns : public Gtk::TreeModel::ColumnRecord { - public: - SoundFilePathColumns() { add (paths); } - Gtk::TreeModelColumn paths; - - }; - - SoundFilePathColumns sfdb_path_columns; - Glib::RefPtr sfdb_paths; - Gtk::TreeView sfdb_path_view; + Gtkmm2ext::PathList sfdb_path_view; void setup_path_options(); void add_session_paths (); void remove_session_paths (); void raid_path_changed (); + void sfdb_paths_changed (); /* fades */ diff --git a/gtk2_ardour/pan_automation_time_axis.cc b/gtk2_ardour/pan_automation_time_axis.cc index 73d0f7f1aa..3169f65059 100644 --- a/gtk2_ardour/pan_automation_time_axis.cc +++ b/gtk2_ardour/pan_automation_time_axis.cc @@ -28,6 +28,7 @@ #include "pan_automation_time_axis.h" #include "automation_line.h" #include "canvas_impl.h" +#include "route_ui.h" #include "i18n.h" @@ -35,11 +36,15 @@ using namespace ARDOUR; using namespace PBD; using namespace Gtk; -PanAutomationTimeAxisView::PanAutomationTimeAxisView (Session& s, Route& r, PublicEditor& e, TimeAxisView& parent, Canvas& canvas, std::string n) +PanAutomationTimeAxisView::PanAutomationTimeAxisView (Session& s, boost::shared_ptr r, PublicEditor& e, + TimeAxisView& parent, Canvas& canvas, std::string n) : AxisView (s), AutomationTimeAxisView (s, r, e, parent, canvas, n, X_("pan"), "") { + multiline_selector.set_name ("PanAutomationLineSelector"); + + controls_table.attach (multiline_selector, 1, 5, 1, 2, Gtk::EXPAND, Gtk::EXPAND); } PanAutomationTimeAxisView::~PanAutomationTimeAxisView () @@ -54,14 +59,19 @@ PanAutomationTimeAxisView::add_automation_event (ArdourCanvas::Item* item, GdkEv return; } - if (lines.size() > 1) { + int line_index = 0; - Gtkmm2ext::PopUp* msg = new Gtkmm2ext::PopUp (Gtk::WIN_POS_MOUSE, 5000, true); + if (lines.size() > 1) { + line_index = multiline_selector.get_active_row_number(); + + if (line_index < 0 || line_index >= (int)lines.size()) { + Gtkmm2ext::PopUp* msg = new Gtkmm2ext::PopUp (Gtk::WIN_POS_MOUSE, 5000, true); - msg->set_text (_("You can't graphically edit panning of more than stream")); - msg->touch (); - - return; + msg->set_text (_("You need to select which line to edit")); + msg->touch (); + + return; + } } double x = 0; @@ -76,7 +86,7 @@ PanAutomationTimeAxisView::add_automation_event (ArdourCanvas::Item* item, GdkEv lines.front()->view_to_model_y (y); - AutomationList& alist (lines.front()->the_list()); + AutomationList& alist (lines[line_index]->the_list()); _session.begin_reversible_command (_("add pan automation event")); XMLNode &before = alist.get_state(); @@ -87,10 +97,57 @@ PanAutomationTimeAxisView::add_automation_event (ArdourCanvas::Item* item, GdkEv _session.set_dirty (); } +void +PanAutomationTimeAxisView::clear_lines () +{ + AutomationTimeAxisView::clear_lines(); + multiline_selector.clear(); +} + +void +PanAutomationTimeAxisView::add_line (AutomationLine& line) +{ + char buf[32]; + snprintf(buf,32,"Line %u",lines.size()+1); + multiline_selector.append_text(buf); + + if (lines.empty()) { + multiline_selector.set_active(0); + } + + if (lines.size() + 1 > 1 && (height_style != Small && height_style != Smaller)) { + multiline_selector.show(); + } else { + multiline_selector.hide(); + + } + + AutomationTimeAxisView::add_line(line); +} + +void +PanAutomationTimeAxisView::set_height (TimeAxisView::TrackHeight th) +{ + AutomationTimeAxisView::set_height(th); + + switch (th) { + case Largest: + case Large: + case Larger: + case Normal: + if (lines.size() > 1) { + multiline_selector.show(); + break; + } + default: + multiline_selector.hide(); + } +} + void PanAutomationTimeAxisView::set_automation_state (AutoState state) { if (!ignore_state_request) { - route.panner().set_automation_state (state); + route->panner().set_automation_state (state); } } diff --git a/gtk2_ardour/pan_automation_time_axis.h b/gtk2_ardour/pan_automation_time_axis.h index b35ee67735..ca4a4db8e7 100644 --- a/gtk2_ardour/pan_automation_time_axis.h +++ b/gtk2_ardour/pan_automation_time_axis.h @@ -4,27 +4,36 @@ #include "canvas.h" #include "automation_time_axis.h" +#include + namespace ARDOUR { class Redirect; } class PanAutomationTimeAxisView : public AutomationTimeAxisView { - public: - PanAutomationTimeAxisView (ARDOUR::Session&, - ARDOUR::Route&, - PublicEditor&, - TimeAxisView& parent_axis, - ArdourCanvas::Canvas& canvas, - std::string name); + public: + PanAutomationTimeAxisView (ARDOUR::Session&, + boost::shared_ptr, + PublicEditor&, + TimeAxisView& parent_axis, + ArdourCanvas::Canvas& canvas, + std::string name); - ~PanAutomationTimeAxisView(); + ~PanAutomationTimeAxisView(); - void add_automation_event (ArdourCanvas::Item *item, GdkEvent *event, jack_nframes_t, double); - - private: - void automation_changed (); - void set_automation_state (ARDOUR::AutoState); + void add_automation_event (ArdourCanvas::Item *item, GdkEvent *event, jack_nframes_t, double); + + void clear_lines (); + void add_line (AutomationLine&); + void set_height (TimeAxisView::TrackHeight); + + protected: + Gtk::ComboBoxText multiline_selector; + + private: + void automation_changed (); + void set_automation_state (ARDOUR::AutoState); }; #endif /* __ardour_gtk_pan_automation_time_axis_h__ */ diff --git a/gtk2_ardour/panner_ui.cc b/gtk2_ardour/panner_ui.cc index 63a19867a8..ccce2ec9f1 100644 --- a/gtk2_ardour/panner_ui.cc +++ b/gtk2_ardour/panner_ui.cc @@ -14,8 +14,6 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ */ #include @@ -47,7 +45,7 @@ using namespace Gtk; using namespace sigc; -PannerUI::PannerUI (IO& io, Session& s) +PannerUI::PannerUI (boost::shared_ptr io, Session& s) : _io (io), _session (s), hAdjustment(0.0, 0.0, 0.0), @@ -87,13 +85,13 @@ PannerUI::PannerUI (IO& io, Session& s) using namespace Menu_Helpers; pan_astate_menu.items().push_back (MenuElem (_("Off"), - bind (mem_fun (_io.panner(), &Panner::set_automation_state), (AutoState) Off))); + bind (mem_fun (_io->panner(), &Panner::set_automation_state), (AutoState) Off))); pan_astate_menu.items().push_back (MenuElem (_("Play"), - bind (mem_fun (_io.panner(), &Panner::set_automation_state), (AutoState) Play))); + bind (mem_fun (_io->panner(), &Panner::set_automation_state), (AutoState) Play))); pan_astate_menu.items().push_back (MenuElem (_("Write"), - bind (mem_fun (_io.panner(), &Panner::set_automation_state), (AutoState) Write))); + bind (mem_fun (_io->panner(), &Panner::set_automation_state), (AutoState) Write))); pan_astate_menu.items().push_back (MenuElem (_("Touch"), - bind (mem_fun (_io.panner(), &Panner::set_automation_state), (AutoState) Touch))); + bind (mem_fun (_io->panner(), &Panner::set_automation_state), (AutoState) Touch))); pan_astyle_menu.items().push_back (MenuElem (_("Trim"))); pan_astyle_menu.items().push_back (MenuElem (_("Abs"))); @@ -143,9 +141,9 @@ PannerUI::PannerUI (IO& io, Session& s) set_width(Narrow); - _io.panner().Changed.connect (mem_fun(*this, &PannerUI::panner_changed)); - _io.panner().LinkStateChanged.connect (mem_fun(*this, &PannerUI::update_pan_linkage)); - _io.panner().StateChanged.connect (mem_fun(*this, &PannerUI::update_pan_state)); + _io->panner().Changed.connect (mem_fun(*this, &PannerUI::panner_changed)); + _io->panner().LinkStateChanged.connect (mem_fun(*this, &PannerUI::update_pan_linkage)); + _io->panner().StateChanged.connect (mem_fun(*this, &PannerUI::update_pan_state)); pan_changed (0); update_pan_sensitive (); @@ -165,7 +163,7 @@ PannerUI::panning_link_button_release (GdkEventButton* ev) { cerr << "link release\n"; if (!ignore_toggle) { - _io.panner().set_linked (!_io.panner().linked()); + _io->panner().set_linked (!_io->panner().linked()); } return true; } @@ -173,12 +171,12 @@ PannerUI::panning_link_button_release (GdkEventButton* ev) void PannerUI::panning_link_direction_clicked() { - switch (_io.panner().link_direction()) { + switch (_io->panner().link_direction()) { case Panner::SameDirection: - _io.panner().set_link_direction (Panner::OppositeDirection); + _io->panner().set_link_direction (Panner::OppositeDirection); break; default: - _io.panner().set_link_direction (Panner::SameDirection); + _io->panner().set_link_direction (Panner::SameDirection); break; } } @@ -188,7 +186,7 @@ PannerUI::update_pan_linkage () { ENSURE_GUI_THREAD(mem_fun(*this, &PannerUI::update_pan_linkage)); - bool x = _io.panner().linked(); + bool x = _io->panner().linked(); bool bx = panning_link_button.get_active(); if (x != bx) { @@ -200,7 +198,7 @@ PannerUI::update_pan_linkage () panning_link_direction_button.set_sensitive (x); - switch (_io.panner().link_direction()) { + switch (_io->panner().link_direction()) { case Panner::SameDirection: panning_link_direction_button.set_image (*(manage (new Image (get_xpm ("forwardblarrow.xpm"))))); break; @@ -278,7 +276,7 @@ PannerUI::update_pan_state () void PannerUI::setup_pan () { - uint32_t nouts = _io.n_outputs (); + uint32_t nouts = _io->n_outputs (); if (nouts == 0 || nouts == 1) { @@ -292,7 +290,7 @@ PannerUI::setup_pan () } else if (nouts == 2) { vector::size_type asz; - uint32_t npans = _io.panner().size(); + uint32_t npans = _io->panner().size(); while (!pan_adjustments.empty()) { delete pan_bars.back(); @@ -308,34 +306,26 @@ PannerUI::setup_pan () /* initialize adjustment with current value of panner */ - _io.panner()[asz]->get_position (x); + _io->panner()[asz]->get_position (x); pan_adjustments.push_back (new Adjustment (x, 0, 1.0, 0.05, 0.1)); pan_adjustments.back()->signal_value_changed().connect (bind (mem_fun(*this, &PannerUI::pan_adjustment_changed), (uint32_t) asz)); - _io.panner()[asz]->Changed.connect (bind (mem_fun(*this, &PannerUI::pan_value_changed), (uint32_t) asz)); + _io->panner()[asz]->Changed.connect (bind (mem_fun(*this, &PannerUI::pan_value_changed), (uint32_t) asz)); bc = new BarController (*pan_adjustments[asz], - &_io.panner()[asz]->midi_control(), + _io->panner()[asz]->control(), bind (mem_fun(*this, &PannerUI::pan_printer), pan_adjustments[asz])); - if (_session.midi_port()) { - _io.panner()[asz]->reset_midi_control (_session.midi_port(), true); - } - bc->set_name ("PanSlider"); bc->set_shadow_type (Gtk::SHADOW_NONE); bc->set_style (BarController::Line); - bc->StartGesture.connect (bind (mem_fun (_io, &IO::start_pan_touch), (uint32_t) asz)); - bc->StopGesture.connect (bind (mem_fun (_io, &IO::end_pan_touch), (uint32_t) asz)); + bc->StartGesture.connect (bind (mem_fun (*_io, &IO::start_pan_touch), (uint32_t) asz)); + bc->StopGesture.connect (bind (mem_fun (*_io, &IO::end_pan_touch), (uint32_t) asz)); char buf[64]; -#ifdef __APPLE__ - snprintf (buf, sizeof (buf), _("panner for channel %lu"), asz + 1); -#else - snprintf (buf, sizeof (buf), _("panner for channel %u"), asz + 1); -#endif + snprintf (buf, sizeof (buf), _("panner for channel %zu"), asz + 1); ARDOUR_UI::instance()->tooltips().set_tip (bc->event_widget(), buf); bc->event_widget().signal_button_release_event().connect @@ -379,13 +369,13 @@ PannerUI::setup_pan () } if (panner == 0) { - panner = new Panner2d (_io.panner(), w, 61); + panner = new Panner2d (_io->panner(), w, 61); panner->set_name ("MixerPanZone"); panner->show (); } update_pan_sensitive (); - panner->reset (_io.n_inputs()); + panner->reset (_io->n_inputs()); panner->set_size_request (w, 61); /* and finally, add it to the panner frame */ @@ -428,7 +418,7 @@ PannerUI::build_pan_menu (uint32_t which) /* set state first, connect second */ - (dynamic_cast (&items.back()))->set_active (_io.panner()[which]->muted()); + (dynamic_cast (&items.back()))->set_active (_io->panner()[which]->muted()); (dynamic_cast (&items.back()))->signal_toggled().connect (bind (mem_fun(*this, &PannerUI::pan_mute), which)); @@ -437,7 +427,7 @@ PannerUI::build_pan_menu (uint32_t which) /* set state first, connect second */ - bypass_menu_item->set_active (_io.panner().bypassed()); + bypass_menu_item->set_active (_io->panner().bypassed()); bypass_menu_item->signal_toggled().connect (mem_fun(*this, &PannerUI::pan_bypass_toggle)); items.push_back (MenuElem (_("Reset"), mem_fun(*this, &PannerUI::pan_reset))); @@ -448,15 +438,15 @@ PannerUI::build_pan_menu (uint32_t which) void PannerUI::pan_mute (uint32_t which) { - StreamPanner* sp = _io.panner()[which]; + StreamPanner* sp = _io->panner()[which]; sp->set_muted (!sp->muted()); } void PannerUI::pan_bypass_toggle () { - if (bypass_menu_item && (_io.panner().bypassed() != bypass_menu_item->get_active())) { - _io.panner().set_bypassed (!_io.panner().bypassed()); + if (bypass_menu_item && (_io->panner().bypassed() != bypass_menu_item->get_active())) { + _io->panner().set_bypassed (!_io->panner().bypassed()); } } @@ -468,11 +458,11 @@ PannerUI::pan_reset () void PannerUI::effective_pan_display () { - if (_io.panner().empty()) { + if (_io->panner().empty()) { return; } - switch (_io.n_outputs()) { + switch (_io->n_outputs()) { case 0: case 1: /* relax */ @@ -495,7 +485,7 @@ PannerUI::pan_changed (void *src) return; } - switch (_io.panner().size()) { + switch (_io->panner().size()) { case 0: panning_link_direction_button.set_sensitive (false); panning_link_button.set_sensitive (false); @@ -509,7 +499,7 @@ PannerUI::pan_changed (void *src) panning_link_button.set_sensitive (true); } - uint32_t nouts = _io.n_outputs(); + uint32_t nouts = _io->n_outputs(); switch (nouts) { case 0: @@ -530,11 +520,11 @@ PannerUI::pan_changed (void *src) void PannerUI::pan_adjustment_changed (uint32_t which) { - if (!in_pan_update && which < _io.panner().size()) { + if (!in_pan_update && which < _io->panner().size()) { float xpos; float val = pan_adjustments[which]->get_value (); - _io.panner()[which]->get_position (xpos); + _io->panner()[which]->get_position (xpos); /* add a kinda-sorta detent for the middle */ @@ -551,7 +541,7 @@ PannerUI::pan_adjustment_changed (uint32_t which) if (!Panner::equivalent (val, xpos)) { - _io.panner()[which]->set_position (val); + _io->panner()[which]->set_position (val); /* XXX the panner objects have no access to the session, so do this here. ick. @@ -566,11 +556,11 @@ PannerUI::pan_value_changed (uint32_t which) { ENSURE_GUI_THREAD (bind (mem_fun(*this, &PannerUI::pan_value_changed), which)); - if (_io.n_outputs() > 1 && which < _io.panner().size()) { + if (_io->n_outputs() > 1 && which < _io->panner().size()) { float xpos; float val = pan_adjustments[which]->get_value (); - _io.panner()[which]->get_position (xpos); + _io->panner()[which]->get_position (xpos); if (!Panner::equivalent (val, xpos)) { in_pan_update = true; @@ -596,14 +586,14 @@ PannerUI::update_pan_bars (bool only_if_aplay) float xpos, val; if (only_if_aplay) { - AutomationList& alist (_io.panner()[n]->automation()); + AutomationList& alist (_io->panner()[n]->automation()); if (!alist.automation_playback()) { continue; } } - _io.panner()[n]->get_effective_position (xpos); + _io->panner()[n]->get_effective_position (xpos); val = (*i)->get_value (); if (!Panner::equivalent (val, xpos)) { @@ -634,9 +624,9 @@ PannerUI::pan_printer (char *buf, uint32_t len, Adjustment* adj) void PannerUI::update_pan_sensitive () { - bool sensitive = !(_io.panner().automation_state() & Play); + bool sensitive = !(_io->panner().automation_state() & Play); - switch (_io.n_outputs()) { + switch (_io->n_outputs()) { case 0: case 1: break; @@ -697,10 +687,10 @@ PannerUI::pan_automation_style_changed () switch (_width) { case Wide: - pan_automation_style_button.set_label (astyle_string(_io.panner().automation_style())); + pan_automation_style_button.set_label (astyle_string(_io->panner().automation_style())); break; case Narrow: - pan_automation_style_button.set_label (short_astyle_string(_io.panner().automation_style())); + pan_automation_style_button.set_label (short_astyle_string(_io->panner().automation_style())); break; } } @@ -714,10 +704,10 @@ PannerUI::pan_automation_state_changed () switch (_width) { case Wide: - pan_automation_state_button.set_label (astate_string(_io.panner().automation_state())); + pan_automation_state_button.set_label (astate_string(_io->panner().automation_state())); break; case Narrow: - pan_automation_state_button.set_label (short_astate_string(_io.panner().automation_state())); + pan_automation_state_button.set_label (short_astate_string(_io->panner().automation_state())); break; } @@ -726,11 +716,11 @@ PannerUI::pan_automation_state_changed () here. */ - if (_io.panner().empty()) { + if (_io->panner().empty()) { return; } - x = (_io.panner().front()->automation().automation_state() != Off); + x = (_io->panner().front()->automation().automation_state() != Off); if (pan_automation_state_button.get_active() != x) { ignore_toggle = true; diff --git a/gtk2_ardour/panner_ui.h b/gtk2_ardour/panner_ui.h index 80b14465cf..7658978233 100644 --- a/gtk2_ardour/panner_ui.h +++ b/gtk2_ardour/panner_ui.h @@ -31,8 +31,8 @@ #include #include -#include #include +#include #include "enums.h" @@ -55,7 +55,7 @@ namespace Gtk { class PannerUI : public Gtk::HBox { public: - PannerUI (ARDOUR::IO&, ARDOUR::Session&); + PannerUI (boost::shared_ptr, ARDOUR::Session&); ~PannerUI (); void pan_changed (void *); @@ -72,7 +72,7 @@ class PannerUI : public Gtk::HBox private: friend class MixerStrip; - ARDOUR::IO& _io; + boost::shared_ptr _io; ARDOUR::Session& _session; bool ignore_toggle; diff --git a/gtk2_ardour/pixmaps/tool_audition.xpm b/gtk2_ardour/pixmaps/tool_audition.xpm new file mode 100644 index 0000000000..d6f2ccd127 --- /dev/null +++ b/gtk2_ardour/pixmaps/tool_audition.xpm @@ -0,0 +1,19 @@ +/* XPM */ +static char * tool_audition_xpm[] = { +"16 12 4 1", +" c None", +". c #000000", +"+ c #ECECEC", +"@ c #FFFFFF", +" .. ", +" .+. . ", +" .++. .@. ", +"....+@+... .@. ", +".+++@@+..@. .@.", +".+@@@@+. .@. .@.", +".+@@@@+. .@. .@.", +".+++@@+..@. .@.", +"....+@+... .@. ", +" .++. .@. ", +" .+. . ", +" .. "}; diff --git a/gtk2_ardour/pixmaps/tool_gain.xpm b/gtk2_ardour/pixmaps/tool_gain.xpm new file mode 100644 index 0000000000..480426fab8 --- /dev/null +++ b/gtk2_ardour/pixmaps/tool_gain.xpm @@ -0,0 +1,18 @@ +/* XPM */ +static char * tool_gain_xpm[] = { +"16 12 3 1", +" c None", +". c #000000", +"+ c #FFFFFF", +"... ", +".++.. ", +"...++. ", +" ..+. ", +" .+. ", +" .+. ", +" .+. ", +" .+. ", +" .+.. ", +" .++.....", +" ..++++.", +" ....."}; diff --git a/gtk2_ardour/pixmaps/tool_object.xpm b/gtk2_ardour/pixmaps/tool_object.xpm new file mode 100644 index 0000000000..3d18ab8af7 --- /dev/null +++ b/gtk2_ardour/pixmaps/tool_object.xpm @@ -0,0 +1,18 @@ +/* XPM */ +static char * tool_object_xpm[] = { +"16 12 3 1", +" c None", +". c #000000", +"+ c #FFFFFF", +" ... ", +" .+. ", +" .+. ", +" .+. ", +" .+..... ", +" .+.+.+... ", +" ...+.+.+.+. ", +" .+.+++++++. ", +" .+++++++++. ", +" ..+++++++.. ", +" ...+++++. ", +" .+++++. "}; diff --git a/gtk2_ardour/pixmaps/tool_range.xpm b/gtk2_ardour/pixmaps/tool_range.xpm new file mode 100644 index 0000000000..75ee865ca2 --- /dev/null +++ b/gtk2_ardour/pixmaps/tool_range.xpm @@ -0,0 +1,18 @@ +/* XPM */ +static char * tool_range_xpm[] = { +"16 12 3 1", +" c None", +". c #000000", +"+ c #FFFFFF", +"... ...", +".+. .. .. .+.", +".+. .+. .+. .+.", +".+..+. .+..+.", +".+.++......++.+.", +".++++++++++++++.", +".+.++......++.+.", +".+..+. .+..+.", +".+. .+. .+. .+.", +".+. .. .. .+.", +".+. .+.", +"... ..."}; diff --git a/gtk2_ardour/pixmaps/tool_stretch.xpm b/gtk2_ardour/pixmaps/tool_stretch.xpm new file mode 100644 index 0000000000..77943cd7d4 --- /dev/null +++ b/gtk2_ardour/pixmaps/tool_stretch.xpm @@ -0,0 +1,18 @@ +/* XPM */ +static char * tool_stretch_xpm[] = { +"16 12 3 1", +" c None", +". c #000000", +"+ c #FFFFFF", +" .. .. ", +" .+. .+. ", +".++..........++.", +"++++++++++++++++", +".++..........++.", +" .+. .+. ", +" .. .. ", +" + + + + ", +" ++ +++ + + +++ ", +"++++++++++++++++", +" ++ + ++ + + ", +" + + + + "}; diff --git a/gtk2_ardour/pixmaps/tool_zoom.xpm b/gtk2_ardour/pixmaps/tool_zoom.xpm new file mode 100644 index 0000000000..581363f3f4 --- /dev/null +++ b/gtk2_ardour/pixmaps/tool_zoom.xpm @@ -0,0 +1,29 @@ +/* XPM */ +static char * tool_zoom_xpm[] = { +"16 12 14 1", +" c None", +". c #000000", +"+ c #474747", +"@ c #E7E7E7", +"# c #F6F6F6", +"$ c #DCDCDC", +"% c #FFFFFF", +"& c #DFDFDF", +"* c #D7D7D7", +"= c #D6D6D6", +"- c #040404", +"; c #070707", +"> c #060606", +", c #050505", +" ... ", +" +.@#$.+ ", +" .%%%%%. ", +" .&%%%%%*. ", +" .#%%%%%#. ", +" .$%%%%%&. ", +" .%%%%%.+ ", +" +.*#=... ", +" ...+... ", +" -.; ", +" >.- ", +" ,. "}; diff --git a/gtk2_ardour/pixmaps/zoom_full.xpm b/gtk2_ardour/pixmaps/zoom_full.xpm new file mode 100644 index 0000000000..5564074875 --- /dev/null +++ b/gtk2_ardour/pixmaps/zoom_full.xpm @@ -0,0 +1,30 @@ +/* XPM */ +static char * zoom_full_xpm[] = { +"12 12 15 1", +" c None", +". c #000000", +"+ c #474747", +"@ c #E7E7E7", +"# c #F6F6F6", +"$ c #DCDCDC", +"% c #ACACAC", +"& c #FFFFFF", +"* c #DFDFDF", +"= c #D7D7D7", +"- c #D6D6D6", +"; c #040404", +"> c #070707", +", c #060606", +"' c #050505", +" ... ", +" +.@#$.+ ", +" .%&&&%. ", +".*..&..=. ", +".#.&&&.#. ", +".$..&..*. ", +" .%&&&%.+ ", +" +.=#-... ", +" ...+... ", +" ;.> ", +" ,.;", +" '."}; diff --git a/gtk2_ardour/pixmaps/zoom_in.xpm b/gtk2_ardour/pixmaps/zoom_in.xpm new file mode 100644 index 0000000000..1f8d4e8273 --- /dev/null +++ b/gtk2_ardour/pixmaps/zoom_in.xpm @@ -0,0 +1,29 @@ +/* XPM */ +static char * zoom_in_xpm[] = { +"12 12 14 1", +" c None", +". c #000000", +"+ c #474747", +"@ c #E7E7E7", +"# c #F6F6F6", +"$ c #DCDCDC", +"% c #FFFFFF", +"& c #DFDFDF", +"* c #D7D7D7", +"= c #D6D6D6", +"- c #040404", +"; c #070707", +"> c #060606", +", c #050505", +" ... ", +" +.@#$.+ ", +" .%%.%%. ", +".&%%.%%*. ", +".#.....#. ", +".$%%.%%&. ", +" .%%.%%.+ ", +" +.*#=... ", +" ...+... ", +" -.; ", +" >.-", +" ,."}; diff --git a/gtk2_ardour/pixmaps/zoom_out.xpm b/gtk2_ardour/pixmaps/zoom_out.xpm new file mode 100644 index 0000000000..ea50d145ad --- /dev/null +++ b/gtk2_ardour/pixmaps/zoom_out.xpm @@ -0,0 +1,29 @@ +/* XPM */ +static char * zoom_out_xpm[] = { +"12 12 14 1", +" c None", +". c #000000", +"+ c #474747", +"@ c #E7E7E7", +"# c #F6F6F6", +"$ c #DCDCDC", +"% c #FFFFFF", +"& c #DFDFDF", +"* c #D7D7D7", +"= c #D6D6D6", +"- c #040404", +"; c #070707", +"> c #060606", +", c #050505", +" ... ", +" +.@#$.+ ", +" .%%%%%. ", +".&%%%%%*. ", +".#.....#. ", +".$%%%%%&. ", +" .%%%%%.+ ", +" +.*#=... ", +" ...+... ", +" -.; ", +" >.-", +" ,."}; diff --git a/gtk2_ardour/playlist_selector.cc b/gtk2_ardour/playlist_selector.cc index f1a975d5dc..8eaac7cb9d 100644 --- a/gtk2_ardour/playlist_selector.cc +++ b/gtk2_ardour/playlist_selector.cc @@ -90,13 +90,13 @@ void PlaylistSelector::show_for (RouteUI* ruix) { vector item; - AudioDiskstream* this_ds; + Diskstream* this_ds; string str; rui = ruix; str = _("ardour: playlist for "); - str += rui->route().name(); + str += rui->route()->name(); set_title (str); @@ -116,7 +116,7 @@ PlaylistSelector::show_for (RouteUI* ruix) for (DSPL_Map::iterator x = dspl_map.begin(); x != dspl_map.end(); ++x) { - AudioDiskstream* ds = session->diskstream_by_id (x->first); + Diskstream* ds = session->diskstream_by_id (x->first); if (ds == 0) { continue; @@ -189,7 +189,7 @@ PlaylistSelector::add_playlist_to_map (Playlist *pl) if ((x = dspl_map.find (apl->get_orig_diskstream_id())) == dspl_map.end()) { - pair*> newp (apl->get_orig_diskstream_id(), new list); + pair*> newp (apl->get_orig_diskstream_id(), new list); x = dspl_map.insert (dspl_map.end(), newp); } @@ -223,7 +223,7 @@ PlaylistSelector::selection_changed () TreeModel::iterator iter = tree.get_selection()->get_selected(); - if (!iter) { + if (!iter || rui == 0) { /* nothing selected */ return; } @@ -233,7 +233,7 @@ PlaylistSelector::selection_changed () AudioTrack* at; AudioPlaylist* apl; - if ((at = dynamic_cast (&rui->route())) == 0) { + if ((at = rui->audio_track()) == 0) { /* eh? */ return; } @@ -243,7 +243,7 @@ PlaylistSelector::selection_changed () return; } - at->disk_stream().use_playlist (apl); + at->diskstream().use_playlist (apl); hide (); } diff --git a/gtk2_ardour/playlist_selector.h b/gtk2_ardour/playlist_selector.h index 863d6cc7f3..2829ba54bb 100644 --- a/gtk2_ardour/playlist_selector.h +++ b/gtk2_ardour/playlist_selector.h @@ -46,7 +46,7 @@ class PlaylistSelector : public ArdourDialog void show_for (RouteUI*); private: - typedef std::map*> DSPL_Map; + typedef std::map*> DSPL_Map; ARDOUR::Session* session; Gtk::ScrolledWindow scroller; diff --git a/gtk2_ardour/plugin_selector.cc b/gtk2_ardour/plugin_selector.cc index 16796df160..e0a62b177f 100644 --- a/gtk2_ardour/plugin_selector.cc +++ b/gtk2_ardour/plugin_selector.cc @@ -1,5 +1,5 @@ /* - Copyright (C) 2000 Paul Davis + Copyright (C) 2000-2006 Paul Davis This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -48,8 +48,8 @@ PluginSelector::PluginSelector (PluginManager *mgr) manager = mgr; session = 0; - o_selected_plug = -1; - i_selected_plug = 0; + + current_selection = PluginInfo::LADSPA; lmodel = Gtk::ListStore::create(lcols); ladspa_display.set_model (lmodel); @@ -91,6 +91,25 @@ PluginSelector::PluginSelector (PluginManager *mgr) column->set_sort_column(i); } #endif + +#ifdef HAVE_COREAUDIO + aumodel = ListStore::create(aucols); + au_display.set_model (aumodel); + au_display.append_column (_("Available plugins"), aucols.name); + au_display.append_column (_("# Inputs"), aucols.ins); + au_display.append_column (_("# Outputs"), aucols.outs); + au_display.set_headers_visible (true); + au_display.set_reorderable (false); + auscroller.set_border_width(10); + auscroller.set_policy(Gtk::POLICY_AUTOMATIC, Gtk::POLICY_AUTOMATIC); + auscroller.add(au_display); + + for (int i = 0; i <=2; i++) { + Gtk::TreeView::Column* column = au_display.get_column(i); + column->set_sort_column(i); + } +#endif + ascroller.set_border_width(10); ascroller.set_policy(Gtk::POLICY_AUTOMATIC, Gtk::POLICY_AUTOMATIC); ascroller.add(added_list); @@ -124,35 +143,51 @@ PluginSelector::PluginSelector (PluginManager *mgr) using namespace Gtk::Notebook_Helpers; notebook.pages().push_back (TabElem (lscroller, _("LADSPA"))); + #ifdef VST_SUPPORT if (Config->get_use_vst()) { notebook.pages().push_back (TabElem (vscroller, _("VST"))); } #endif +#ifdef HAVE_COREAUDIO + notebook.pages().push_back (TabElem (auscroller, _("AudioUnit"))); +#endif + table->set_name("PluginSelectorTable"); ladspa_display.set_name("PluginSelectorDisplay"); //ladspa_display.set_name("PluginSelectorList"); added_list.set_name("PluginSelectorList"); ladspa_display.signal_button_press_event().connect_notify (mem_fun(*this, &PluginSelector::row_clicked)); + ladspa_display.get_selection()->signal_changed().connect (mem_fun(*this, &PluginSelector::ladspa_display_selection_changed)); + #ifdef VST_SUPPORT if (Config->get_use_vst()) { vst_display.signal_button_press_event().connect_notify (mem_fun(*this, &PluginSelector::row_clicked)); vst_display.get_selection()->signal_changed().connect (mem_fun(*this, &PluginSelector::vst_display_selection_changed)); } #endif - + +#ifdef HAVE_COREAUDIO + au_display.signal_button_press_event().connect_notify (mem_fun(*this, &PluginSelector::row_clicked)); + au_display.get_selection()->signal_changed().connect (mem_fun(*this, &PluginSelector::au_display_selection_changed)); +#endif + btn_update->signal_clicked().connect (mem_fun(*this, &PluginSelector::btn_update_clicked)); btn_add->signal_clicked().connect(mem_fun(*this, &PluginSelector::btn_add_clicked)); btn_remove->signal_clicked().connect(mem_fun(*this, &PluginSelector::btn_remove_clicked)); - ladspa_display.get_selection()->signal_changed().connect (mem_fun(*this, &PluginSelector::ladspa_display_selection_changed)); added_list.get_selection()->signal_changed().connect (mem_fun(*this, &PluginSelector::added_list_selection_changed)); input_refiller (); + #ifdef VST_SUPPORT vst_refiller (); #endif + +#ifdef HAVE_COREAUDIO + au_refiller (); +#endif } void @@ -189,13 +224,11 @@ void PluginSelector::input_refiller () { guint row; - list &plugs = manager->ladspa_plugin_info (); - list::iterator i; + PluginInfoList &plugs = manager->ladspa_plugin_info (); + PluginInfoList::iterator i; char ibuf[16], obuf[16]; lmodel->clear(); -#ifdef VST_SUPPORT - vmodel->clear(); -#endif + // Insert into GTK list for (row = 0, i=plugs.begin(); i != plugs.end(); ++i, ++row) { snprintf (ibuf, sizeof(ibuf)-1, "%d", (*i)->n_inputs); @@ -224,9 +257,10 @@ void PluginSelector::vst_refiller () { guint row; - list &plugs = manager->vst_plugin_info (); - list::iterator i; + PluginInfoList &plugs = manager->vst_plugin_info (); + PluginInfoList::iterator i; char ibuf[16], obuf[16]; + vmodel->clear(); // Insert into GTK list for (row = 0, i=plugs.begin(); i != plugs.end(); ++i, ++row) { @@ -242,18 +276,75 @@ PluginSelector::vst_refiller () } vmodel->set_sort_column (0, Gtk::SORT_ASCENDING); } -#endif void -PluginSelector::use_plugin (PluginInfo* pi) +PluginSelector::vst_display_selection_changed() { - list::iterator i; + if (vst_display.get_selection()->count_selected_rows() != 0) { + btn_add->set_sensitive (true); + } else { + btn_add->set_sensitive (false); + } - if (pi == 0 || session == 0) { + current_selection = PluginInfo::VST; +} + +#endif //VST_SUPPORT + +#ifdef HAVE_COREAUDIO + +void +PluginSelector::_au_refiller (void *arg) +{ + ((PluginSelector *) arg)->au_refiller (); +} + +void +PluginSelector::au_refiller () +{ + guint row; + PluginInfoList plugs (AUPluginInfo::discover ()); + PluginInfoList::iterator i; + char ibuf[16], obuf[16]; + aumodel->clear(); + + // Insert into GTK list + for (row = 0, i=plugs.begin(); i != plugs.end(); ++i, ++row) { + + snprintf (ibuf, sizeof(ibuf)-1, "%d", (*i)->n_inputs); + snprintf (obuf, sizeof(obuf)-1, "%d", (*i)->n_outputs); + + Gtk::TreeModel::Row newrow = *(aumodel->append()); + newrow[aucols.name] = (*i)->name.c_str(); + newrow[aucols.ins] = ibuf; + newrow[aucols.outs] = obuf; + newrow[aucols.plugin] = *i; + } + aumodel->set_sort_column (0, Gtk::SORT_ASCENDING); +} + +void +PluginSelector::au_display_selection_changed() +{ + if (au_display.get_selection()->count_selected_rows() != 0) { + btn_add->set_sensitive (true); + } else { + btn_add->set_sensitive (false); + } + + current_selection = PluginInfo::AudioUnit; +} + +#endif //HAVE_COREAUDIO + +void +PluginSelector::use_plugin (PluginInfoPtr pi) +{ + if (session == 0) { return; } - Plugin *plugin = manager->load (*session, pi); + PluginPtr plugin = pi->load (*session); if (plugin) { PluginCreated (plugin); @@ -263,46 +354,54 @@ PluginSelector::use_plugin (PluginInfo* pi) void PluginSelector::btn_add_clicked() { - bool vst = notebook.get_current_page(); // 0 = LADSPA, 1 = VST std::string name; - ARDOUR::PluginInfo *pi; + PluginInfoPtr pi; Gtk::TreeModel::Row newrow = *(amodel->append()); - if (vst) { + Gtk::TreeModel::Row row; + + switch (current_selection) { + case PluginInfo::LADSPA: + row = *(ladspa_display.get_selection()->get_selected()); + name = row[lcols.name]; + pi = row[lcols.plugin]; + break; + case PluginInfo::VST: #ifdef VST_SUPPORT - Gtk::TreeModel::Row row = *(vst_display.get_selection()->get_selected()); - name = row[vcols.name]; - pi = row[vcols.plugin]; - added_plugins.push_back (row[vcols.plugin]); + row = *(vst_display.get_selection()->get_selected()); + name = row[vcols.name]; + pi = row[vcols.plugin]; #endif - } else { - Gtk::TreeModel::Row row = *(ladspa_display.get_selection()->get_selected()); - name = row[lcols.name]; - pi = row[lcols.plugin]; - added_plugins.push_back (row[lcols.plugin]); + break; + case PluginInfo::AudioUnit: +#ifdef HAVE_COREAUDIO + row = *(au_display.get_selection()->get_selected()); + name = row[aucols.name]; + pi = row[aucols.plugin]; +#endif + break; + default: + error << "Programming error. Unknown plugin selected." << endmsg; + return; } + newrow[acols.text] = name; newrow[acols.plugin] = pi; if (!amodel->children().empty()) { - set_response_sensitive (RESPONSE_APPLY, true); + set_response_sensitive (RESPONSE_APPLY, true); } } void PluginSelector::btn_remove_clicked() { - list::iterator i; Gtk::TreeModel::iterator iter = added_list.get_selection()->get_selected(); - for (i = added_plugins.begin(); (*i) != (*iter)[acols.plugin]; ++i); - - added_plugins.erase(i); + amodel->erase(iter); if (amodel->children().empty()) { - set_response_sensitive (RESPONSE_APPLY, false); + set_response_sensitive (RESPONSE_APPLY, false); } - - } void @@ -313,28 +412,21 @@ PluginSelector::btn_update_clicked() #ifdef VST_SUPPORT vst_refiller (); #endif -} - -#ifdef VST_SUPPORT -void -PluginSelector::vst_display_selection_changed() -{ - if (vst_display.get_selection()->count_selected_rows() != 0) { - btn_add->set_sensitive (true); - } else { - btn_add->set_sensitive (false); - } -} +#ifdef HAVE_COREAUDIO + au_refiller (); #endif +} void PluginSelector::ladspa_display_selection_changed() { - if (ladspa_display.get_selection()->count_selected_rows() != 0) { - btn_add->set_sensitive (true); - } else { - btn_add->set_sensitive (false); - } + if (ladspa_display.get_selection()->count_selected_rows() != 0) { + btn_add->set_sensitive (true); + } else { + btn_add->set_sensitive (false); + } + + current_selection = PluginInfo::LADSPA; } void @@ -351,14 +443,14 @@ int PluginSelector::run () { ResponseType r; - list::iterator i; + TreeModel::Children::iterator i; r = (ResponseType) Dialog::run (); switch (r) { case RESPONSE_APPLY: - for (i = added_plugins.begin(); i != added_plugins.end(); ++i){ - use_plugin (*i); + for (i = amodel->children().begin(); i != amodel->children().end(); ++i) { + use_plugin ((*i)[acols.plugin]); } break; @@ -375,7 +467,5 @@ void PluginSelector::cleanup () { hide(); - added_plugins.clear(); amodel->clear(); } - diff --git a/gtk2_ardour/plugin_selector.h b/gtk2_ardour/plugin_selector.h index 125ce1b80a..583506972a 100644 --- a/gtk2_ardour/plugin_selector.h +++ b/gtk2_ardour/plugin_selector.h @@ -25,17 +25,18 @@ #include #include +#include + namespace ARDOUR { class Session; class PluginManager; - class Plugin; } class PluginSelector : public ArdourDialog { public: PluginSelector (ARDOUR::PluginManager *); - sigc::signal PluginCreated; + sigc::signal > PluginCreated; int run (); // XXX should we try not to overload the non-virtual Gtk::Dialog::run() ? @@ -44,9 +45,12 @@ class PluginSelector : public ArdourDialog private: ARDOUR::Session* session; Gtk::Notebook notebook; - Gtk::ScrolledWindow lscroller; - Gtk::ScrolledWindow vscroller; - Gtk::ScrolledWindow ascroller; + Gtk::ScrolledWindow lscroller; // ladspa + Gtk::ScrolledWindow vscroller; // vst + Gtk::ScrolledWindow auscroller; // AudioUnit + Gtk::ScrolledWindow ascroller; // Added plugins + + ARDOUR::PluginInfo::Type current_selection; // page 1 struct LadspaColumns : public Gtk::TreeModel::ColumnRecord { @@ -61,7 +65,7 @@ class PluginSelector : public ArdourDialog Gtk::TreeModelColumn type; Gtk::TreeModelColumn ins; Gtk::TreeModelColumn outs; - Gtk::TreeModelColumn plugin; + Gtk::TreeModelColumn plugin; }; LadspaColumns lcols; Glib::RefPtr lmodel; @@ -76,7 +80,7 @@ class PluginSelector : public ArdourDialog add (plugin); } Gtk::TreeModelColumn text; - Gtk::TreeModelColumn plugin; + Gtk::TreeModelColumn plugin; }; AddedColumns acols; Glib::RefPtr amodel; @@ -95,7 +99,7 @@ class PluginSelector : public ArdourDialog Gtk::TreeModelColumn name; Gtk::TreeModelColumn ins; Gtk::TreeModelColumn outs; - Gtk::TreeModelColumn plugin; + Gtk::TreeModelColumn plugin; }; VstColumns vcols; Glib::RefPtr vmodel; @@ -104,16 +108,32 @@ class PluginSelector : public ArdourDialog static void _vst_refiller (void *); void vst_refiller (); void vst_display_selection_changed(); -#endif +#endif // VST_SUPPORT - ARDOUR::PluginInfo* i_selected_plug; - - // We need an integer for the output side because - // the name isn't promised to be unique. - gint o_selected_plug; +#ifdef HAVE_COREAUDIO + // page 3 + struct AUColumns : public Gtk::TreeModel::ColumnRecord { + AUColumns () { + add (name); + add (ins); + add (outs); + add (plugin); + } + Gtk::TreeModelColumn name; + Gtk::TreeModelColumn ins; + Gtk::TreeModelColumn outs; + Gtk::TreeModelColumn plugin; + }; + AUColumns aucols; + Glib::RefPtr aumodel; + Glib::RefPtr auselection; + Gtk::TreeView au_display; + static void _au_refiller (void *); + void au_refiller (); + void au_display_selection_changed(); +#endif //HAVE_COREAUDIO ARDOUR::PluginManager *manager; - list added_plugins; static void _input_refiller (void *); @@ -125,8 +145,9 @@ class PluginSelector : public ArdourDialog void added_list_selection_changed(); void ladspa_display_selection_changed(); void btn_apply_clicked(); - void use_plugin (ARDOUR::PluginInfo*); + void use_plugin (ARDOUR::PluginInfoPtr); void cleanup (); }; #endif // __ardour_plugin_selector_h__ + diff --git a/gtk2_ardour/plugin_ui.cc b/gtk2_ardour/plugin_ui.cc index 749ab9d4ac..5e5263b9ad 100644 --- a/gtk2_ardour/plugin_ui.cc +++ b/gtk2_ardour/plugin_ui.cc @@ -29,10 +29,10 @@ #include #include -#include #include #include #include +#include #include @@ -61,19 +61,19 @@ using namespace Gtkmm2ext; using namespace Gtk; using namespace sigc; -PluginUIWindow::PluginUIWindow (AudioEngine &engine, PluginInsert& insert, bool scrollable) +PluginUIWindow::PluginUIWindow (AudioEngine &engine, boost::shared_ptr insert, bool scrollable) : ArdourDialog ("plugin ui") { - if (insert.plugin().has_editor()) { + if (insert->plugin()->has_editor()) { #ifdef VST_SUPPORT - VSTPlugin* vp; + boost::shared_ptr vp; - if ((vp = dynamic_cast (&insert.plugin())) != 0) { + if ((vp = boost::dynamic_pointer_cast (insert->plugin())) != 0) { - VSTPluginUI* vpu = new VSTPluginUI (insert, *vp); + VSTPluginUI* vpu = new VSTPluginUI (insert, vp); _pluginui = vpu; get_vbox()->add (*vpu); @@ -104,7 +104,7 @@ PluginUIWindow::PluginUIWindow (AudioEngine &engine, PluginInsert& insert, bool add_events (Gdk::KEY_PRESS_MASK|Gdk::KEY_RELEASE_MASK|Gdk::BUTTON_PRESS_MASK|Gdk::BUTTON_RELEASE_MASK); signal_delete_event().connect (bind (sigc::ptr_fun (just_hide_it), reinterpret_cast (this))); - insert.GoingAway.connect (mem_fun(*this, &PluginUIWindow::plugin_going_away)); + insert->GoingAway.connect (mem_fun(*this, &PluginUIWindow::plugin_going_away)); if (scrollable) { gint h = _pluginui->get_preferred_height (); @@ -117,7 +117,7 @@ PluginUIWindow::~PluginUIWindow () { } -PluginUI::PluginUI (AudioEngine &engine, PluginInsert& pi, bool scrollable) +PluginUI::PluginUI (AudioEngine &engine, boost::shared_ptr pi, bool scrollable) : PlugUIBase (pi), engine(engine), button_table (initial_button_rows, initial_button_cols), @@ -165,8 +165,8 @@ PluginUI::PluginUI (AudioEngine &engine, PluginInsert& pi, bool scrollable) pack_start (hpacker, false, false); } - insert.active_changed.connect (mem_fun(*this, &PluginUI::redirect_active_changed)); - bypass_button.set_active (!insert.active()); + insert->active_changed.connect (mem_fun(*this, &PluginUI::redirect_active_changed)); + bypass_button.set_active (!insert->active()); build (engine); } @@ -233,13 +233,13 @@ PluginUI::build (AudioEngine &engine) /* find all ports. build control elements for all appropriate control ports */ - for (i = 0; i < plugin.parameter_count(); ++i) { + for (i = 0; i < plugin->parameter_count(); ++i) { - if (plugin.parameter_is_control (i)) { + if (plugin->parameter_is_control (i)) { /* Don't show latency control ports */ - if (plugin.describe_parameter (i) == X_("latency")) { + if (plugin->describe_parameter (i) == X_("latency")) { continue; } @@ -263,7 +263,7 @@ PluginUI::build (AudioEngine &engine) } } - if ((cui = build_control_ui (engine, i, plugin.get_nth_midi_control (i))) == 0) { + if ((cui = build_control_ui (engine, i, plugin->get_nth_control (i))) == 0) { error << string_compose(_("Plugin Editor: could not build control element for port %1"), i) << endmsg; continue; } @@ -326,8 +326,8 @@ PluginUI::build (AudioEngine &engine) } } - n_ins = plugin.get_info().n_inputs; - n_outs = plugin.get_info().n_outputs; + n_ins = plugin->get_info()->n_inputs; + n_outs = plugin->get_info()->n_outputs; if (box->children().empty()) { hpacker.remove (*frame); @@ -387,7 +387,7 @@ PluginUI::automation_state_changed (ControlUI* cui) { /* update button label */ - switch (insert.get_port_automation_state (cui->port_index) & (Off|Play|Touch|Write)) { + switch (insert->get_port_automation_state (cui->port_index) & (Off|Play|Touch|Write)) { case Off: cui->automate_button.set_label (_("Off")); break; @@ -415,17 +415,17 @@ static void integer_printer (char buf[32], Adjustment &adj, void *arg) void PluginUI::print_parameter (char *buf, uint32_t len, uint32_t param) { - plugin.print_parameter (param, buf, len); + plugin->print_parameter (param, buf, len); } PluginUI::ControlUI* -PluginUI::build_control_ui (AudioEngine &engine, guint32 port_index, MIDI::Controllable* mcontrol) +PluginUI::build_control_ui (AudioEngine &engine, guint32 port_index, PBD::Controllable* mcontrol) { ControlUI* control_ui; Plugin::ParameterDescriptor desc; - plugin.get_parameter_descriptor (port_index, desc); + plugin->get_parameter_descriptor (port_index, desc); control_ui = manage (new ControlUI ()); control_ui->adjustment = 0; @@ -439,11 +439,11 @@ PluginUI::build_control_ui (AudioEngine &engine, guint32 port_index, MIDI::Contr control_ui->set_spacing (5); - if (plugin.parameter_is_input (port_index)) { + if (plugin->parameter_is_input (port_index)) { - LadspaPlugin* lp; + boost::shared_ptr lp; - if ((lp = dynamic_cast(&plugin)) != 0) { + if ((lp = boost::dynamic_pointer_cast(plugin)) != 0) { lrdf_defaults* defaults = lrdf_get_scale_values(lp->unique_id(), port_index); @@ -453,7 +453,7 @@ PluginUI::build_control_ui (AudioEngine &engine, guint32 port_index, MIDI::Contr //control_ui->combo->set_value_in_list(true, false); set_popdown_strings (*control_ui->combo, setup_scale_values(port_index, control_ui)); control_ui->combo->signal_changed().connect (bind (mem_fun(*this, &PluginUI::control_combo_changed), control_ui)); - plugin.ParameterChanged.connect (bind (mem_fun (*this, &PluginUI::parameter_changed), control_ui)); + plugin->ParameterChanged.connect (bind (mem_fun (*this, &PluginUI::parameter_changed), control_ui)); control_ui->pack_start(control_ui->label, true, true); control_ui->pack_start(*control_ui->combo, false, true); @@ -478,7 +478,7 @@ PluginUI::build_control_ui (AudioEngine &engine, guint32 port_index, MIDI::Contr control_ui->button->signal_clicked().connect (bind (mem_fun(*this, &PluginUI::control_port_toggled), control_ui)); - if(plugin.get_parameter (port_index) == 1){ + if(plugin->get_parameter (port_index) == 1){ control_ui->button->set_active(true); } @@ -516,7 +516,7 @@ PluginUI::build_control_ui (AudioEngine &engine, guint32 port_index, MIDI::Contr } else { sigc::slot pslot = sigc::bind (mem_fun(*this, &PluginUI::print_parameter), (uint32_t) port_index); - control_ui->control = new BarController (*control_ui->adjustment, mcontrol, pslot); + control_ui->control = new BarController (*control_ui->adjustment, *mcontrol, pslot); // should really match the height of the text in the automation button+label control_ui->control->set_size_request (200, 22); control_ui->control->set_name (X_("PluginSlider")); @@ -529,9 +529,9 @@ PluginUI::build_control_ui (AudioEngine &engine, guint32 port_index, MIDI::Contr } if (control_ui->logarithmic) { - control_ui->adjustment->set_value(log(plugin.get_parameter(port_index))); + control_ui->adjustment->set_value(log(plugin->get_parameter(port_index))); } else{ - control_ui->adjustment->set_value(plugin.get_parameter(port_index)); + control_ui->adjustment->set_value(plugin->get_parameter(port_index)); } /* XXX memory leak: SliderController not destroyed by ControlUI @@ -552,11 +552,11 @@ PluginUI::build_control_ui (AudioEngine &engine, guint32 port_index, MIDI::Contr automation_state_changed (control_ui); - plugin.ParameterChanged.connect (bind (mem_fun(*this, &PluginUI::parameter_changed), control_ui)); - insert.automation_list (port_index).automation_state_changed.connect + plugin->ParameterChanged.connect (bind (mem_fun(*this, &PluginUI::parameter_changed), control_ui)); + insert->automation_list (port_index).automation_state_changed.connect (bind (mem_fun(*this, &PluginUI::automation_state_changed), control_ui)); - } else if (plugin.parameter_is_output (port_index)) { + } else if (plugin->parameter_is_output (port_index)) { control_ui->display = manage (new EventBox); control_ui->display->set_name ("ParameterValueDisplay"); @@ -603,20 +603,20 @@ PluginUI::build_control_ui (AudioEngine &engine, guint32 port_index, MIDI::Contr output_controls.push_back (control_ui); } - plugin.ParameterChanged.connect (bind (mem_fun(*this, &PluginUI::parameter_changed), control_ui)); + plugin->ParameterChanged.connect (bind (mem_fun(*this, &PluginUI::parameter_changed), control_ui)); return control_ui; } void PluginUI::start_touch (PluginUI::ControlUI* cui) { - insert.automation_list (cui->port_index).start_touch (); + insert->automation_list (cui->port_index).start_touch (); } void PluginUI::stop_touch (PluginUI::ControlUI* cui) { - insert.automation_list (cui->port_index).stop_touch (); + insert->automation_list (cui->port_index).stop_touch (); } void @@ -647,7 +647,7 @@ PluginUI::astate_clicked (ControlUI* cui, uint32_t port) void PluginUI::set_automation_state (AutoState state, ControlUI* cui) { - insert.set_port_automation_state (cui->port_index, state); + insert->set_port_automation_state (cui->port_index, state); } void @@ -663,7 +663,7 @@ PluginUI::control_adjustment_changed (ControlUI* cui) value = exp(value); } - insert.set_parameter (cui->port_index, (float) value); + insert->set_parameter (cui->port_index, (float) value); } void @@ -684,7 +684,7 @@ PluginUI::update_control_display (ControlUI* cui) cui->update_pending = false; - float val = plugin.get_parameter (cui->port_index); + float val = plugin->get_parameter (cui->port_index); cui->ignore_change++; if (cui->combo) { @@ -718,7 +718,7 @@ void PluginUI::control_port_toggled (ControlUI* cui) { if (!cui->ignore_change) { - insert.set_parameter (cui->port_index, cui->button->get_active()); + insert->set_parameter (cui->port_index, cui->button->get_active()); } } @@ -728,7 +728,7 @@ PluginUI::control_combo_changed (ControlUI* cui) if (!cui->ignore_change) { string value = cui->combo->get_active_text(); std::map mapping = *cui->combo_map; - insert.set_parameter (cui->port_index, mapping[value]); + insert->set_parameter (cui->port_index, mapping[value]); } } @@ -774,7 +774,7 @@ void PluginUI::output_update () { for (vector::iterator i = output_controls.begin(); i != output_controls.end(); ++i) { - float val = plugin.get_parameter ((*i)->port_index); + float val = plugin->get_parameter ((*i)->port_index); char buf[32]; snprintf (buf, sizeof(buf), "%.2f", val); (*i)->display_label->set_text (buf); @@ -808,7 +808,7 @@ vector PluginUI::setup_scale_values(guint32 port_index, ControlUI* cui) { vector enums; - LadspaPlugin* lp = dynamic_cast (&plugin); + boost::shared_ptr lp = boost::dynamic_pointer_cast (plugin); cui->combo_map = new std::map; lrdf_defaults* defaults = lrdf_get_scale_values(lp->unique_id(), port_index); @@ -827,14 +827,14 @@ PluginUI::setup_scale_values(guint32 port_index, ControlUI* cui) return enums; } -PlugUIBase::PlugUIBase (PluginInsert& pi) +PlugUIBase::PlugUIBase (boost::shared_ptr pi) : insert (pi), - plugin (insert.plugin()), + plugin (insert->plugin()), save_button(_("Add")), bypass_button (_("Bypass")) { //combo.set_use_arrows_always(true); - set_popdown_strings (combo, plugin.get_presets()); + set_popdown_strings (combo, plugin->get_presets()); combo.set_size_request (100, -1); combo.set_active_text (""); combo.signal_changed().connect(mem_fun(*this, &PlugUIBase::setting_selected)); @@ -850,7 +850,7 @@ void PlugUIBase::setting_selected() { if (combo.get_active_text().length() > 0) { - if (!plugin.load_preset(combo.get_active_text())) { + if (!plugin->load_preset(combo.get_active_text())) { warning << string_compose(_("Plugin preset %1 not found"), combo.get_active_text()) << endmsg; } } @@ -875,8 +875,8 @@ PlugUIBase::save_plugin_setting () prompter.get_result(name); if (name.length()) { - if(plugin.save_preset(name)){ - set_popdown_strings (combo, plugin.get_presets()); + if(plugin->save_preset(name)){ + set_popdown_strings (combo, plugin->get_presets()); combo.set_active_text (name); } } @@ -889,8 +889,8 @@ PlugUIBase::bypass_toggled () { bool x; - if ((x = bypass_button.get_active()) == insert.active()) { - insert.set_active (!x, this); + if ((x = bypass_button.get_active()) == insert->active()) { + insert->set_active (!x, this); } } diff --git a/gtk2_ardour/plugin_ui.h b/gtk2_ardour/plugin_ui.h index e5800e8ece..570a224b66 100644 --- a/gtk2_ardour/plugin_ui.h +++ b/gtk2_ardour/plugin_ui.h @@ -52,7 +52,7 @@ namespace ARDOUR { class Redirect; } -namespace MIDI { +namespace PBD { class Controllable; } @@ -67,7 +67,7 @@ namespace Gtkmm2ext { class PlugUIBase : public virtual sigc::trackable { public: - PlugUIBase (ARDOUR::PluginInsert&); + PlugUIBase (boost::shared_ptr); virtual ~PlugUIBase() {} virtual gint get_preferred_height () = 0; @@ -75,8 +75,8 @@ class PlugUIBase : public virtual sigc::trackable virtual bool stop_updating(GdkEventAny*) = 0; protected: - ARDOUR::PluginInsert& insert; - ARDOUR::Plugin& plugin; + boost::shared_ptr insert; + boost::shared_ptr plugin; Gtk::ComboBoxText combo; Gtk::Button save_button; Gtk::ToggleButton bypass_button; @@ -89,7 +89,7 @@ class PlugUIBase : public virtual sigc::trackable class PluginUI : public PlugUIBase, public Gtk::VBox { public: - PluginUI (ARDOUR::AudioEngine &, ARDOUR::PluginInsert& plug, bool scrollable=false); + PluginUI (ARDOUR::AudioEngine &, boost::shared_ptr plug, bool scrollable=false); ~PluginUI (); gint get_preferred_height () { return prefheight; } @@ -174,7 +174,7 @@ class PluginUI : public PlugUIBase, public Gtk::VBox void output_update(); void build (ARDOUR::AudioEngine &); - ControlUI* build_control_ui (ARDOUR::AudioEngine &, guint32 port_index, MIDI::Controllable *); + ControlUI* build_control_ui (ARDOUR::AudioEngine &, guint32 port_index, PBD::Controllable *); std::vector setup_scale_values(guint32 port_index, ControlUI* cui); void control_adjustment_changed (ControlUI* cui); void parameter_changed (uint32_t, float, ControlUI* cui); @@ -196,7 +196,7 @@ class PluginUI : public PlugUIBase, public Gtk::VBox class PluginUIWindow : public ArdourDialog { public: - PluginUIWindow (ARDOUR::AudioEngine &, ARDOUR::PluginInsert& insert, bool scrollable=false); + PluginUIWindow (ARDOUR::AudioEngine &, boost::shared_ptr insert, bool scrollable=false); ~PluginUIWindow (); PlugUIBase& pluginui() { return *_pluginui; } @@ -213,7 +213,7 @@ class PluginUIWindow : public ArdourDialog class VSTPluginUI : public PlugUIBase, public Gtk::VBox { public: - VSTPluginUI (ARDOUR::PluginInsert&, ARDOUR::VSTPlugin&); + VSTPluginUI (boost::shared_ptr, boost::shared_ptr); ~VSTPluginUI (); gint get_preferred_height (); @@ -223,7 +223,7 @@ class VSTPluginUI : public PlugUIBase, public Gtk::VBox int package (Gtk::Window&); private: - ARDOUR::VSTPlugin& vst; + boost::shared_ptr vst; Gtk::Socket socket; Gtk::HBox preset_box; Gtk::VBox vpacker; diff --git a/gtk2_ardour/po/SConscript b/gtk2_ardour/po/SConscript index 868f123988..d7e957b3eb 100644 --- a/gtk2_ardour/po/SConscript +++ b/gtk2_ardour/po/SConscript @@ -27,7 +27,7 @@ print "Updating pot file: " domain = gtkardour['DOMAIN'] potfile = gtkardour['POTFILE'] -poaction = Action('intltool-update -p -g=' + domain) +poaction = env.Action('intltool-update -p -g=' + domain) Execute(poaction) diff --git a/gtk2_ardour/public_editor.h b/gtk2_ardour/public_editor.h index 4c12b99d7c..f70e4c20bd 100644 --- a/gtk2_ardour/public_editor.h +++ b/gtk2_ardour/public_editor.h @@ -39,7 +39,7 @@ class AutomationLine; class ControlPoint; class SelectionRect; class CrossfadeView; -class AudioTimeAxisView; +class RouteTimeAxisView; class AudioRegionView; class TempoMarker; class MeterMarker; @@ -145,10 +145,10 @@ class PublicEditor : public Gtk::Window, public Stateful { virtual bool canvas_fade_in_handle_event (GdkEvent* event,ArdourCanvas::Item*, AudioRegionView*) = 0; virtual bool canvas_fade_out_event (GdkEvent* event,ArdourCanvas::Item*, AudioRegionView*) = 0; virtual bool canvas_fade_out_handle_event (GdkEvent* event,ArdourCanvas::Item*, AudioRegionView*) = 0; - virtual bool canvas_region_view_event (GdkEvent* event,ArdourCanvas::Item*, AudioRegionView*) = 0; - virtual bool canvas_region_view_name_highlight_event (GdkEvent* event,ArdourCanvas::Item*, AudioRegionView*) = 0; - virtual bool canvas_region_view_name_event (GdkEvent* event,ArdourCanvas::Item*, AudioRegionView*) = 0; - virtual bool canvas_stream_view_event (GdkEvent* event,ArdourCanvas::Item*, AudioTimeAxisView*) = 0; + virtual bool canvas_region_view_event (GdkEvent* event,ArdourCanvas::Item*, RegionView*) = 0; + virtual bool canvas_region_view_name_highlight_event (GdkEvent* event,ArdourCanvas::Item*, RegionView*) = 0; + virtual bool canvas_region_view_name_event (GdkEvent* event,ArdourCanvas::Item*, RegionView*) = 0; + virtual bool canvas_stream_view_event (GdkEvent* event,ArdourCanvas::Item*, RouteTimeAxisView*) = 0; virtual bool canvas_marker_event (GdkEvent* event,ArdourCanvas::Item*, Marker*) = 0; virtual bool canvas_zoom_rect_event (GdkEvent* event,ArdourCanvas::Item*) = 0; virtual bool canvas_tempo_marker_event (GdkEvent* event,ArdourCanvas::Item*, TempoMarker*) = 0; diff --git a/gtk2_ardour/redirect_automation_line.cc b/gtk2_ardour/redirect_automation_line.cc index 8971e8ff10..1ea5013295 100644 --- a/gtk2_ardour/redirect_automation_line.cc +++ b/gtk2_ardour/redirect_automation_line.cc @@ -55,7 +55,7 @@ RedirectAutomationLine::RedirectAutomationLine (const string & name, Redirect& r /*NOTREACHED*/ } - pi->plugin().get_parameter_descriptor (_port, desc); + pi->plugin()->get_parameter_descriptor (_port, desc); upper = desc.upper; lower = desc.lower; diff --git a/gtk2_ardour/redirect_automation_time_axis.cc b/gtk2_ardour/redirect_automation_time_axis.cc index e3ce4b08c6..e527fd1d5e 100644 --- a/gtk2_ardour/redirect_automation_time_axis.cc +++ b/gtk2_ardour/redirect_automation_time_axis.cc @@ -33,7 +33,8 @@ using namespace ARDOUR; using namespace PBD; using namespace Gtk; -RedirectAutomationTimeAxisView::RedirectAutomationTimeAxisView (Session& s, Route& r, PublicEditor& e, TimeAxisView& parent, Canvas& canvas, std::string n, +RedirectAutomationTimeAxisView::RedirectAutomationTimeAxisView (Session& s, boost::shared_ptr r, + PublicEditor& e, TimeAxisView& parent, Canvas& canvas, std::string n, uint32_t prt, Redirect& rd, string state_name) : AxisView (s), diff --git a/gtk2_ardour/redirect_automation_time_axis.h b/gtk2_ardour/redirect_automation_time_axis.h index b8d94b2a3e..6976dc2358 100644 --- a/gtk2_ardour/redirect_automation_time_axis.h +++ b/gtk2_ardour/redirect_automation_time_axis.h @@ -14,7 +14,7 @@ class RedirectAutomationTimeAxisView : public AutomationTimeAxisView { public: RedirectAutomationTimeAxisView (ARDOUR::Session&, - ARDOUR::Route&, + boost::shared_ptr, PublicEditor&, TimeAxisView& parent, ArdourCanvas::Canvas& canvas, diff --git a/gtk2_ardour/redirect_box.cc b/gtk2_ardour/redirect_box.cc index f5cb9522e0..74198265d9 100644 --- a/gtk2_ardour/redirect_box.cc +++ b/gtk2_ardour/redirect_box.cc @@ -76,7 +76,7 @@ bool RedirectBox::get_colors = true; Gdk::Color* RedirectBox::active_redirect_color; Gdk::Color* RedirectBox::inactive_redirect_color; -RedirectBox::RedirectBox (Placement pcmnt, Session& sess, Route& rt, PluginSelector &plugsel, +RedirectBox::RedirectBox (Placement pcmnt, Session& sess, boost::shared_ptr rt, PluginSelector &plugsel, RouteRedirectSelection & rsel, bool owner_is_mixer) : _route(rt), _session(sess), @@ -132,7 +132,7 @@ RedirectBox::RedirectBox (Placement pcmnt, Session& sess, Route& rt, PluginSelec pack_start (redirect_eventbox, true, true); - _route.redirects_changed.connect (mem_fun(*this, &RedirectBox::redisplay_redirects)); + _route->redirects_changed.connect (mem_fun(*this, &RedirectBox::redisplay_redirects)); redirect_eventbox.signal_enter_notify_event().connect (bind (sigc::ptr_fun (RedirectBox::enter_box), this)); @@ -161,10 +161,10 @@ RedirectBox::object_drop (string type, uint32_t cnt, void** ptr) /* do something with the dropped redirects */ - list redirects; - + list > redirects; + for (uint32_t n = 0; n < cnt; ++n) { - redirects.push_back ((Redirect*) ptr[n]); + redirects.push_back (boost::shared_ptr ((Redirect*) ptr[n])); } paste_redirect_list (redirects); @@ -189,21 +189,21 @@ RedirectBox::set_width (Width w) } void -RedirectBox::remove_redirect_gui (Redirect *redirect) +RedirectBox::remove_redirect_gui (boost::shared_ptr redirect) { - Insert *insert = 0; - Send *send = 0; - PortInsert *port_insert = 0; + boost::shared_ptr insert; + boost::shared_ptr send; + boost::shared_ptr port_insert; - if ((insert = dynamic_cast (redirect)) != 0) { + if ((insert = boost::dynamic_pointer_cast (redirect)) != 0) { - if ((port_insert = dynamic_cast (insert)) != 0) { + if ((port_insert = boost::dynamic_pointer_cast (insert)) != 0) { PortInsertUI *io_selector = reinterpret_cast (port_insert->get_gui()); port_insert->set_gui (0); delete io_selector; } - } else if ((send = dynamic_cast (insert)) != 0) { + } else if ((send = boost::dynamic_pointer_cast (insert)) != 0) { SendUIWindow *sui = reinterpret_cast (send->get_gui()); send->set_gui (0); delete sui; @@ -268,7 +268,7 @@ RedirectBox::redirect_button_press_event (GdkEventButton *ev) TreeViewColumn* column; int cellx; int celly; - Redirect* redirect = 0; + boost::shared_ptr redirect; int ret = false; bool selected = false; @@ -353,32 +353,32 @@ RedirectBox::choose_plugin () } void -RedirectBox::insert_plugin_chosen (Plugin *plugin) +RedirectBox::insert_plugin_chosen (boost::shared_ptr plugin) { if (plugin) { - Redirect *redirect = new PluginInsert (_session, *plugin, _placement); + boost::shared_ptr redirect (new PluginInsert (_session, plugin, _placement)); redirect->active_changed.connect (mem_fun(*this, &RedirectBox::show_redirect_active)); uint32_t err_streams; - if (_route.add_redirect (redirect, this, &err_streams)) { + if (_route->add_redirect (redirect, this, &err_streams)) { wierd_plugin_dialog (*plugin, err_streams, _route); - delete redirect; + // XXX SHAREDPTR delete plugin here .. do we even need to care? } } } void -RedirectBox::wierd_plugin_dialog (Plugin& p, uint32_t streams, IO& io) +RedirectBox::wierd_plugin_dialog (Plugin& p, uint32_t streams, boost::shared_ptr io) { ArdourDialog dialog ("wierd plugin dialog"); Label label; /* i hate this kind of code */ - if (streams > p.get_info().n_inputs) { + if (streams > p.get_info()->n_inputs) { label.set_text (string_compose (_( "You attempted to add a plugin (%1).\n" "The plugin has %2 inputs\n" @@ -388,9 +388,9 @@ RedirectBox::wierd_plugin_dialog (Plugin& p, uint32_t streams, IO& io) "This makes no sense - you are throwing away\n" "part of the signal."), p.name(), - p.get_info().n_inputs, + p.get_info()->n_inputs, streams)); - } else if (streams < p.get_info().n_inputs) { + } else if (streams < p.get_info()->n_inputs) { label.set_text (string_compose (_( "You attempted to add a plugin (%1).\n" "The plugin has %2 inputs\n" @@ -401,7 +401,7 @@ RedirectBox::wierd_plugin_dialog (Plugin& p, uint32_t streams, IO& io) "side-chain inputs. A future version of Ardour will\n" "support this type of configuration."), p.name(), - p.get_info().n_inputs, + p.get_info()->n_inputs, streams)); } else { label.set_text (string_compose (_( @@ -415,10 +415,10 @@ RedirectBox::wierd_plugin_dialog (Plugin& p, uint32_t streams, IO& io) "\n" "Ardour does not understand what to do in such situations.\n"), p.name(), - p.get_info().n_inputs, - p.get_info().n_outputs, - io.n_inputs(), - io.n_outputs(), + p.get_info()->n_inputs, + p.get_info()->n_outputs, + io->n_inputs(), + io->n_outputs(), streams)); } @@ -436,36 +436,36 @@ RedirectBox::wierd_plugin_dialog (Plugin& p, uint32_t streams, IO& io) void RedirectBox::choose_insert () { - Redirect *redirect = new PortInsert (_session, _placement); + boost::shared_ptr redirect (new PortInsert (_session, _placement)); redirect->active_changed.connect (mem_fun(*this, &RedirectBox::show_redirect_active)); - _route.add_redirect (redirect, this); + _route->add_redirect (redirect, this); } void RedirectBox::choose_send () { - Send *send = new Send (_session, _placement); + boost::shared_ptr send (new Send (_session, _placement)); /* XXX need redirect lock on route */ - send->ensure_io (0, _route.max_redirect_outs(), false, this); + send->ensure_io (0, _route->max_redirect_outs(), false, this); - IOSelectorWindow *ios = new IOSelectorWindow (_session, *send, false, true); + IOSelectorWindow *ios = new IOSelectorWindow (_session, send, false, true); ios->show_all (); - ios->selector().Finished.connect (bind (mem_fun(*this, &RedirectBox::send_io_finished), static_cast(send), ios)); + ios->selector().Finished.connect (bind (mem_fun(*this, &RedirectBox::send_io_finished), boost::static_pointer_cast(send), ios)); } void -RedirectBox::send_io_finished (IOSelector::Result r, Redirect* redirect, IOSelectorWindow* ios) +RedirectBox::send_io_finished (IOSelector::Result r, boost::shared_ptr redirect, IOSelectorWindow* ios) { switch (r) { case IOSelector::Cancelled: - delete redirect; + // delete redirect; XXX SHAREDPTR HOW TO DESTROY THE REDIRECT ? do we even need to think about it? break; case IOSelector::Accepted: - _route.add_redirect (redirect, this); + _route->add_redirect (redirect, this); break; } @@ -488,7 +488,8 @@ RedirectBox::redisplay_redirects (void *src) redirect_active_connections.clear (); redirect_name_connections.clear (); - _route.foreach_redirect (this, &RedirectBox::add_redirect_to_display); + void (RedirectBox::*pmf)(boost::shared_ptr) = &RedirectBox::add_redirect_to_display; + _route->foreach_redirect (this, pmf); switch (_placement) { case PreFader: @@ -501,33 +502,33 @@ RedirectBox::redisplay_redirects (void *src) } void -RedirectBox::add_redirect_to_display (Redirect *redirect) +RedirectBox::add_redirect_to_display (boost::shared_ptr redirect) { if (redirect->placement() != _placement) { return; } Gtk::TreeModel::Row row = *(model->append()); - row[columns.text] = redirect_name (*redirect); + row[columns.text] = redirect_name (redirect); row[columns.redirect] = redirect; - show_redirect_active (redirect, this); + show_redirect_active (redirect.get(), this); redirect_active_connections.push_back (redirect->active_changed.connect (mem_fun(*this, &RedirectBox::show_redirect_active))); redirect_name_connections.push_back (redirect->name_changed.connect (bind (mem_fun(*this, &RedirectBox::show_redirect_name), redirect))); } string -RedirectBox::redirect_name (Redirect& redirect) +RedirectBox::redirect_name (boost::shared_ptr redirect) { - Send *send; + boost::shared_ptr send; string name_display; - if (!redirect.active()) { + if (!redirect->active()) { name_display = " ("; } - if ((send = dynamic_cast (&redirect)) != 0) { + if ((send = boost::dynamic_pointer_cast (redirect)) != 0) { name_display += '>'; @@ -550,16 +551,16 @@ RedirectBox::redirect_name (Redirect& redirect) switch (_width) { case Wide: - name_display += redirect.name(); + name_display += redirect->name(); break; case Narrow: - name_display += PBD::short_version (redirect.name(), 5); + name_display += PBD::short_version (redirect->name(), 5); break; } } - if (!redirect.active()) { + if (!redirect->active()) { name_display += ')'; } @@ -581,35 +582,37 @@ RedirectBox::build_redirect_tooltip (EventBox& box, string start) } void -RedirectBox::show_redirect_name (void* src, Redirect *redirect) +RedirectBox::show_redirect_name (void* src, boost::shared_ptr redirect) { ENSURE_GUI_THREAD(bind (mem_fun(*this, &RedirectBox::show_redirect_name), src, redirect)); - - show_redirect_active (redirect, src); + show_redirect_active (redirect.get(), src); } void -RedirectBox::show_redirect_active (Redirect *redirect, void *src) +RedirectBox::show_redirect_active (Redirect* redirect, void *src) { ENSURE_GUI_THREAD(bind (mem_fun(*this, &RedirectBox::show_redirect_active), redirect, src)); Gtk::TreeModel::Children children = model->children(); Gtk::TreeModel::Children::iterator iter = children.begin(); - while( iter != children.end()) - { - if ((*iter)[columns.redirect] == redirect) + while (iter != children.end()) { + + boost::shared_ptr r = (*iter)[columns.redirect]; + + if (r.get() == redirect) { + (*iter)[columns.text] = redirect_name (r); + + if (redirect->active()) { + (*iter)[columns.color] = *active_redirect_color; + } else { + (*iter)[columns.color] = *inactive_redirect_color; + } break; + } + iter++; } - - (*iter)[columns.text] = redirect_name (*redirect); - - if (redirect->active()) { - (*iter)[columns.color] = *active_redirect_color; - } else { - (*iter)[columns.color] = *inactive_redirect_color; - } } void @@ -627,12 +630,12 @@ RedirectBox::compute_redirect_sort_keys () Gtk::TreeModel::Children children = model->children(); for (Gtk::TreeModel::Children::iterator iter = children.begin(); iter != children.end(); ++iter) { - Redirect *redirect = (*iter)[columns.redirect]; - redirect->set_sort_key (sort_key); + boost::shared_ptr r = (*iter)[columns.redirect]; + r->set_sort_key (sort_key); sort_key++; } - if (_route.sort_redirects ()) { + if (_route->sort_redirects ()) { redisplay_redirects (0); @@ -661,7 +664,7 @@ outputs do not work correctly.")); void RedirectBox::rename_redirects () { - vector to_be_renamed; + vector > to_be_renamed; get_selected_redirects (to_be_renamed); @@ -669,7 +672,7 @@ RedirectBox::rename_redirects () return; } - for (vector::iterator i = to_be_renamed.begin(); i != to_be_renamed.end(); ++i) { + for (vector >::iterator i = to_be_renamed.begin(); i != to_be_renamed.end(); ++i) { rename_redirect (*i); } } @@ -677,7 +680,7 @@ RedirectBox::rename_redirects () void RedirectBox::cut_redirects () { - vector to_be_removed; + vector > to_be_removed; get_selected_redirects (to_be_removed); @@ -692,7 +695,7 @@ RedirectBox::cut_redirects () _rr_selection.set (to_be_removed); - for (vector::iterator i = to_be_removed.begin(); i != to_be_removed.end(); ++i) { + for (vector >::iterator i = to_be_removed.begin(); i != to_be_removed.end(); ++i) { void* gui = (*i)->get_gui (); @@ -700,7 +703,7 @@ RedirectBox::cut_redirects () static_cast(gui)->hide (); } - if (_route.remove_redirect (*i, this)) { + if (_route->remove_redirect (*i, this)) { /* removal failed */ _rr_selection.remove (*i); } @@ -711,8 +714,8 @@ RedirectBox::cut_redirects () void RedirectBox::copy_redirects () { - vector to_be_copied; - vector copies; + vector > to_be_copied; + vector > copies; get_selected_redirects (to_be_copied); @@ -720,29 +723,24 @@ RedirectBox::copy_redirects () return; } - for (vector::iterator i = to_be_copied.begin(); i != to_be_copied.end(); ++i) { - copies.push_back (Redirect::clone (**i)); + for (vector >::iterator i = to_be_copied.begin(); i != to_be_copied.end(); ++i) { + copies.push_back (Redirect::clone (*i)); } _rr_selection.set (copies); } gint -RedirectBox::idle_delete_redirect (Redirect *redirect) +RedirectBox::idle_delete_redirect (boost::shared_ptr redirect) { /* NOT copied to _mixer.selection() */ - if (_route.remove_redirect (redirect, this)) { - /* removal failed */ - return FALSE; - } - - delete redirect; + _route->remove_redirect (redirect, this); return FALSE; } void -RedirectBox::rename_redirect (Redirect* redirect) +RedirectBox::rename_redirect (boost::shared_ptr redirect) { ArdourPrompter name_prompter (true); string result; @@ -767,7 +765,7 @@ RedirectBox::rename_redirect (Redirect* redirect) } void -RedirectBox::cut_redirect (Redirect *redirect) +RedirectBox::cut_redirect (boost::shared_ptr redirect) { /* this essentially transfers ownership of the redirect of the redirect from the route to the mixer @@ -782,15 +780,15 @@ RedirectBox::cut_redirect (Redirect *redirect) static_cast(gui)->hide (); } - if (_route.remove_redirect (redirect, this)) { + if (_route->remove_redirect (redirect, this)) { _rr_selection.remove (redirect); } } void -RedirectBox::copy_redirect (Redirect *redirect) +RedirectBox::copy_redirect (boost::shared_ptr redirect) { - Redirect* copy = Redirect::clone (*redirect); + boost::shared_ptr copy = Redirect::clone (redirect); _rr_selection.add (copy); } @@ -805,22 +803,19 @@ RedirectBox::paste_redirects () } void -RedirectBox::paste_redirect_list (list& redirects) +RedirectBox::paste_redirect_list (list >& redirects) { - list copies; + list > copies; - for (list::iterator i = redirects.begin(); i != redirects.end(); ++i) { + for (list >::iterator i = redirects.begin(); i != redirects.end(); ++i) { - Redirect* copy = Redirect::clone (**i); + boost::shared_ptr copy = Redirect::clone (*i); copy->set_placement (_placement, this); copies.push_back (copy); } - if (_route.add_redirects (copies, this)) { - for (list::iterator i = copies.begin(); i != copies.end(); ++i) { - delete *i; - } + if (_route->add_redirects (copies, this)) { string msg = _( "Copying the set of redirects on the clipboard failed,\n\ @@ -832,19 +827,19 @@ could not match the configuration of this track."); } void -RedirectBox::activate_redirect (Redirect *r) +RedirectBox::activate_redirect (boost::shared_ptr r) { r->set_active (true, 0); } void -RedirectBox::deactivate_redirect (Redirect *r) +RedirectBox::deactivate_redirect (boost::shared_ptr r) { r->set_active (false, 0); } void -RedirectBox::get_selected_redirects (vector& redirects) +RedirectBox::get_selected_redirects (vector >& redirects) { vector pathlist = redirect_display.get_selection()->get_selected_rows(); @@ -853,12 +848,12 @@ RedirectBox::get_selected_redirects (vector& redirects) } void -RedirectBox::for_selected_redirects (void (RedirectBox::*pmf)(Redirect*)) +RedirectBox::for_selected_redirects (void (RedirectBox::*pmf)(boost::shared_ptr)) { vector pathlist = redirect_display.get_selection()->get_selected_rows(); for (vector::iterator iter = pathlist.begin(); iter != pathlist.end(); ++iter) { - Redirect* redirect = (*(model->get_iter(*iter)))[columns.redirect]; + boost::shared_ptr redirect = (*(model->get_iter(*iter)))[columns.redirect]; (this->*pmf)(redirect); } } @@ -869,7 +864,7 @@ RedirectBox::clone_redirects () RouteSelection& routes (_rr_selection.routes); if (!routes.empty()) { - if (_route.copy_redirects (*routes.front(), _placement)) { + if (_route->copy_redirects (*routes.front(), _placement)) { string msg = _( "Copying the set of redirects on the clipboard failed,\n\ probably because the I/O configuration of the plugins\n\ @@ -883,7 +878,7 @@ could not match the configuration of this track."); void RedirectBox::all_redirects_active (bool state) { - _route.all_redirects_active (state); + _route->all_redirects_active (state); } void @@ -892,7 +887,7 @@ RedirectBox::clear_redirects() string prompt; vector choices; - if (dynamic_cast(&_route) != 0) { + if (boost::dynamic_pointer_cast(_route) != 0) { prompt = _("Do you really want to remove all redirects from this track?\n" "(this cannot be undone)"); } else { @@ -906,23 +901,23 @@ RedirectBox::clear_redirects() Gtkmm2ext::Choice prompter (prompt, choices); if (prompter.run () == 1) { - _route.clear_redirects (this); + _route->clear_redirects (this); } } void -RedirectBox::edit_redirect (Redirect* redirect) +RedirectBox::edit_redirect (boost::shared_ptr redirect) { - Insert *insert; + boost::shared_ptr insert; - if (dynamic_cast(&_route) != 0) { + if (boost::dynamic_pointer_cast(_route) != 0) { - if (dynamic_cast (&_route)->freeze_state() == AudioTrack::Frozen) { + if (boost::dynamic_pointer_cast (_route)->freeze_state() == AudioTrack::Frozen) { return; } } - if ((insert = dynamic_cast (redirect)) == 0) { + if ((insert = boost::dynamic_pointer_cast (redirect)) == 0) { /* its a send */ @@ -930,7 +925,7 @@ RedirectBox::edit_redirect (Redirect* redirect) return; } - Send *send = dynamic_cast (redirect); + boost::shared_ptr send = boost::dynamic_pointer_cast (redirect); SendUIWindow *send_ui; @@ -939,7 +934,7 @@ RedirectBox::edit_redirect (Redirect* redirect) string title; title = string_compose(_("ardour: %1"), send->name()); - send_ui = new SendUIWindow (*send, _session); + send_ui = new SendUIWindow (send, _session); send_ui->set_title (title); send->set_gui (send_ui); @@ -957,17 +952,17 @@ RedirectBox::edit_redirect (Redirect* redirect) /* its an insert */ - PluginInsert *plugin_insert; - PortInsert *port_insert; + boost::shared_ptr plugin_insert; + boost::shared_ptr port_insert; - if ((plugin_insert = dynamic_cast (insert)) != 0) { + if ((plugin_insert = boost::dynamic_pointer_cast (insert)) != 0) { PluginUIWindow *plugin_ui; if (plugin_insert->get_gui() == 0) { string title; - string maker = plugin_insert->plugin().maker(); + string maker = plugin_insert->plugin()->maker(); string::size_type email_pos; if ((email_pos = maker.find_first_of ('<')) != string::npos) { @@ -979,9 +974,9 @@ RedirectBox::edit_redirect (Redirect* redirect) maker += " ..."; } - title = string_compose(_("ardour: %1: %2 (by %3)"), _route.name(), plugin_insert->name(), maker); + title = string_compose(_("ardour: %1: %2 (by %3)"), _route->name(), plugin_insert->name(), maker); - plugin_ui = new PluginUIWindow (_session.engine(), *plugin_insert); + plugin_ui = new PluginUIWindow (_session.engine(), plugin_insert); if (_owner_is_mixer) { ARDOUR_UI::instance()->the_mixer()->ensure_float (*plugin_ui); } else { @@ -1000,7 +995,7 @@ RedirectBox::edit_redirect (Redirect* redirect) plugin_ui->show_all (); } - } else if ((port_insert = dynamic_cast (insert)) != 0) { + } else if ((port_insert = boost::dynamic_pointer_cast (insert)) != 0) { if (!_session.engine().connected()) { MessageDialog msg ( _("Not connected to JACK - no I/O changes are possible")); @@ -1011,7 +1006,7 @@ RedirectBox::edit_redirect (Redirect* redirect) PortInsertWindow *io_selector; if (port_insert->get_gui() == 0) { - io_selector = new PortInsertWindow (_session, *port_insert); + io_selector = new PortInsertWindow (_session, port_insert); port_insert->set_gui (io_selector); } else { diff --git a/gtk2_ardour/redirect_box.h b/gtk2_ardour/redirect_box.h index bc162fac17..51c17cad51 100644 --- a/gtk2_ardour/redirect_box.h +++ b/gtk2_ardour/redirect_box.h @@ -33,11 +33,12 @@ #include #include +#include + #include #include #include #include -#include #include #include @@ -64,7 +65,8 @@ namespace ARDOUR { class RedirectBox : public Gtk::HBox { public: - RedirectBox (ARDOUR::Placement, ARDOUR::Session&, ARDOUR::Route &, PluginSelector &, RouteRedirectSelection &, bool owner_is_mixer = false); + RedirectBox (ARDOUR::Placement, ARDOUR::Session&, + boost::shared_ptr, PluginSelector &, RouteRedirectSelection &, bool owner_is_mixer = false); ~RedirectBox (); void set_width (Width); @@ -77,8 +79,8 @@ class RedirectBox : public Gtk::HBox void select_all_inserts (); void select_all_sends (); - sigc::signal RedirectSelected; - sigc::signal RedirectUnselected; + sigc::signal > RedirectSelected; + sigc::signal > RedirectUnselected; static void register_actions(); @@ -86,7 +88,7 @@ class RedirectBox : public Gtk::HBox void set_stuff_from_route (); private: - ARDOUR::Route & _route; + boost::shared_ptr _route; ARDOUR::Session & _session; bool _owner_is_mixer; @@ -102,7 +104,7 @@ class RedirectBox : public Gtk::HBox add (color); } Gtk::TreeModelColumn text; - Gtk::TreeModelColumn redirect; + Gtk::TreeModelColumn > redirect; Gtk::TreeModelColumn color; }; @@ -137,24 +139,29 @@ class RedirectBox : public Gtk::HBox void show_redirect_menu (gint arg); void choose_send (); - void send_io_finished (IOSelector::Result, ARDOUR::Redirect*, IOSelectorWindow*); + void send_io_finished (IOSelector::Result, boost::shared_ptr, IOSelectorWindow*); void choose_insert (); void choose_plugin (); - void insert_plugin_chosen (ARDOUR::Plugin *); + void insert_plugin_chosen (boost::shared_ptr); bool no_redirect_redisplay; bool ignore_delete; bool redirect_button_press_event (GdkEventButton *); void redisplay_redirects (void* src); - void show_redirect_active (ARDOUR::Redirect *, void *); - void show_redirect_name (void*, ARDOUR::Redirect *); - void add_redirect_to_display (ARDOUR::Redirect *); + void add_redirect_to_display (boost::shared_ptr); void row_deleted (const Gtk::TreeModel::Path& path); + void show_redirect_name (void*, boost::shared_ptr); - string redirect_name (ARDOUR::Redirect&); + /* these are handlers for Redirect signals, so they take Redirect* + directly, rather than shared_ptr + */ - void remove_redirect_gui (ARDOUR::Redirect *); + void show_redirect_active (ARDOUR::Redirect*, void *); + + string redirect_name (boost::shared_ptr); + + void remove_redirect_gui (boost::shared_ptr); void redirects_reordered (const Gtk::TreeModel::Path&, const Gtk::TreeModel::iterator&, int*); void compute_redirect_sort_keys (); @@ -173,23 +180,23 @@ class RedirectBox : public Gtk::HBox void clone_redirects (); void rename_redirects (); - void for_selected_redirects (void (RedirectBox::*pmf)(ARDOUR::Redirect*)); - void get_selected_redirects (vector&); + void for_selected_redirects (void (RedirectBox::*pmf)(boost::shared_ptr)); + void get_selected_redirects (vector >&); static Glib::RefPtr paste_action; - void paste_redirect_list (std::list& redirects); + void paste_redirect_list (std::list >& redirects); - void activate_redirect (ARDOUR::Redirect*); - void deactivate_redirect (ARDOUR::Redirect*); - void cut_redirect (ARDOUR::Redirect*); - void copy_redirect (ARDOUR::Redirect*); - void edit_redirect (ARDOUR::Redirect*); - void hide_redirect_editor (ARDOUR::Redirect*); - void rename_redirect (ARDOUR::Redirect*); + void activate_redirect (boost::shared_ptr); + void deactivate_redirect (boost::shared_ptr); + void cut_redirect (boost::shared_ptr); + void copy_redirect (boost::shared_ptr); + void edit_redirect (boost::shared_ptr); + void hide_redirect_editor (boost::shared_ptr); + void rename_redirect (boost::shared_ptr); - gint idle_delete_redirect (ARDOUR::Redirect *); + gint idle_delete_redirect (boost::shared_ptr); - void wierd_plugin_dialog (ARDOUR::Plugin& p, uint32_t streams, ARDOUR::IO& io); + void wierd_plugin_dialog (ARDOUR::Plugin& p, uint32_t streams, boost::shared_ptr io); static RedirectBox* _current_redirect_box; static bool enter_box (GdkEventCrossing*, RedirectBox*); diff --git a/gtk2_ardour/redirect_selection.h b/gtk2_ardour/redirect_selection.h index 3695f85c60..5bcd77cfe4 100644 --- a/gtk2_ardour/redirect_selection.h +++ b/gtk2_ardour/redirect_selection.h @@ -2,11 +2,12 @@ #define __ardour_gtk_redirect_selection_h__ #include +#include namespace ARDOUR { class Redirect; } -struct RedirectSelection : list {}; +struct RedirectSelection : list > {}; #endif /* __ardour_gtk_redirect_selection_h__ */ diff --git a/gtk2_ardour/region_editor.h b/gtk2_ardour/region_editor.h index 65b0bbaa94..70590b0db5 100644 --- a/gtk2_ardour/region_editor.h +++ b/gtk2_ardour/region_editor.h @@ -15,172 +15,29 @@ along with this program; if not, write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - $Id$ + $Id: /local/undo/gtk2_ardour/region_editor.h 5 2006-05-31T02:48:48.738745Z paul $ */ #ifndef __gtk_ardour_region_edit_h__ #define __gtk_ardour_region_edit_h__ -#include - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include -#include - -#include "audio_clock.h" #include "ardour_dialog.h" -namespace ARDOUR { - class AudioRegion; - class Session; -} +namespace ARDOUR { class Session; } -class AudioRegionView; - -class AudioRegionEditor : public ArdourDialog +/** Just a useless stub for now... */ +class RegionEditor : public ArdourDialog { public: - AudioRegionEditor (ARDOUR::Session&, ARDOUR::AudioRegion&, AudioRegionView& rv); - ~AudioRegionEditor (); + RegionEditor(ARDOUR::Session& s) + : ArdourDialog ("region editor") + , _session(s) + {} - private: - ARDOUR::Session& _session; - ARDOUR::AudioRegion& _region; - AudioRegionView& _region_view; + virtual ~RegionEditor () {} - void connect_editor_events (); - - Gtk::Label name_label; - Gtk::Entry name_entry; - Gtk::HBox name_hbox; - - Gtk::HBox top_row_hbox; - Gtk::HBox top_row_button_hbox; - - Gtk::ToggleButton lock_button; - Gtk::ToggleButton mute_button; - Gtk::ToggleButton opaque_button; - Gtk::ToggleButton envelope_active_button; - Gtk::ToggleButton envelope_view_button; - - Gtk::Button raise_button; - Gtk::Arrow raise_arrow; - Gtk::Button lower_button; - Gtk::Arrow lower_arrow; - Gtk::Frame layer_frame; - Gtk::Label layer_value_label; - Gtk::Label layer_label; - Gtk::HBox layer_hbox; - - Gtk::ToggleButton audition_button; - - Gtk::HBox lower_hbox; - - Gtk::Table time_table; - - Gtk::Label start_label; - Gtk::Label end_label; - Gtk::Label length_label; - Gtk::Alignment start_alignment; - Gtk::Alignment end_alignment; - Gtk::Alignment length_alignment; - - AudioClock start_clock; - AudioClock end_clock; - AudioClock length_clock; - AudioClock sync_offset_clock; - - Gtk::Table envelope_loop_table; - Gtk::Button loop_button; - Gtk::Label loop_label; - Gtk::Label envelope_label; - - Gtk::Table fade_in_table; - Gtk::Label fade_in_label; - Gtk::Alignment fade_in_label_align; - Gtk::Label fade_in_active_button_label; - Gtk::ToggleButton fade_in_active_button; - Gtk::Label fade_in_length_label; - - Gtk::Adjustment fade_in_length_adjustment; - Gtk::SpinButton fade_in_length_spinner; - - Gtk::Table fade_out_table; - Gtk::Label fade_out_label; - Gtk::Alignment fade_out_label_align; - Gtk::Label fade_out_active_button_label; - Gtk::ToggleButton fade_out_active_button; - Gtk::Label fade_out_length_label; - - Gtk::Adjustment fade_out_length_adjustment; - Gtk::SpinButton fade_out_length_spinner; - - Gtk::HSeparator sep3; - Gtk::VSeparator sep1; - Gtk::VSeparator sep2; - - void region_changed (ARDOUR::Change); - void bounds_changed (ARDOUR::Change); - void name_changed (); - void opacity_changed (); - void mute_changed (); - void envelope_active_changed (); - void lock_changed (); - void layer_changed (); - - void fade_in_length_adjustment_changed (); - void fade_out_length_adjustment_changed (); - void fade_in_changed (); - void fade_out_changed (); - void audition_state_changed (bool); - - void activation (); - - void name_entry_changed (); - void start_clock_changed (); - void end_clock_changed (); - void length_clock_changed (); - - gint envelope_active_button_press (GdkEventButton *); - gint envelope_active_button_release (GdkEventButton *); - - void audition_button_toggled (); - void envelope_view_button_toggled (); - void lock_button_clicked (); - void mute_button_clicked (); - void opaque_button_clicked (); - void raise_button_clicked (); - void lower_button_clicked (); - - void fade_in_active_toggled (); - void fade_out_active_toggled (); - void fade_in_active_changed (); - void fade_out_active_changed (); - - void fade_in_realized (); - void fade_out_realized (); - - void start_editing_fade_in (); - void start_editing_fade_out (); - void stop_editing_fade_in (); - void stop_editing_fade_out (); - - gint bpressed (GdkEventButton* ev, Gtk::SpinButton* but, void (AudioRegionEditor::*pmf)()); - gint breleased (GdkEventButton* ev, Gtk::SpinButton* but, void (AudioRegionEditor::*pmf)()); - - bool spin_arrow_grab; + protected: + ARDOUR::Session& _session; }; #endif /* __gtk_ardour_region_edit_h__ */ diff --git a/gtk2_ardour/region_gain_line.cc b/gtk2_ardour/region_gain_line.cc index ebcf65cedd..920d2cdca9 100644 --- a/gtk2_ardour/region_gain_line.cc +++ b/gtk2_ardour/region_gain_line.cc @@ -3,7 +3,7 @@ #include #include "region_gain_line.h" -#include "regionview.h" +#include "audio_region_view.h" #include "utils.h" #include "time_axis_view.h" @@ -47,8 +47,8 @@ void AudioRegionGainLine::start_drag (ControlPoint* cp, float fraction) { AutomationLine::start_drag(cp,fraction); - if (!rv.region.envelope_active()) { - trackview.session().add_command(new MementoUndoCommand(rv.region, rv.region.get_state())); + if (!rv.audio_region().envelope_active()) { + trackview.session().add_command(new MementoUndoCommand(rv.audio_region(), rv.audio_region().get_state())); rv.region.set_envelope_active(false); } } @@ -64,11 +64,11 @@ AudioRegionGainLine::remove_point (ControlPoint& cp) trackview.editor.current_session()->begin_reversible_command (_("remove control point")); XMLNode &before = get_state(); - if (!rv.region.envelope_active()) { - XMLNode &before = rv.region.get_state(); - rv.region.set_envelope_active(true); - XMLNode &after = rv.region.get_state(); - trackview.session().add_command(new MementoCommand(rv.region, before, after)); + if (!rv.audio_region().envelope_active()) { + XMLNode &before = rv.audio_region().get_state(); + rv.audio_region().set_envelope_active(true); + XMLNode &after = rv.audio_region().get_state(); + trackview.session().add_command(new MementoCommand(rv.audio_region(), before, after)); } alist.erase (mr.start, mr.end); @@ -81,9 +81,9 @@ AudioRegionGainLine::remove_point (ControlPoint& cp) void AudioRegionGainLine::end_drag (ControlPoint* cp) { - if (!rv.region.envelope_active()) { - rv.region.set_envelope_active(true); - trackview.session().add_command(new MementoRedoCommand(rv.region, rv.region.get_state())); + if (!rv.audio_region().envelope_active()) { + rv.audio_region().set_envelope_active(true); + trackview.session().add_command(new MementoRedoCommand(rv.audio_region(), rv.audio_region().get_state())); } AutomationLine::end_drag(cp); } diff --git a/gtk2_ardour/region_selection.cc b/gtk2_ardour/region_selection.cc index 751584cab7..f8c9f384a9 100644 --- a/gtk2_ardour/region_selection.cc +++ b/gtk2_ardour/region_selection.cc @@ -1,8 +1,26 @@ +/* + Copyright (C) 2006 Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. +*/ + #include -#include +#include -#include "regionview.h" +#include "region_view.h" #include "region_selection.h" using namespace ARDOUR; @@ -11,7 +29,7 @@ using namespace sigc; bool -AudioRegionComparator::operator() (const AudioRegionView* a, const AudioRegionView* b) const +RegionComparator::operator() (const RegionView* a, const RegionView* b) const { if (a == b) { return false; @@ -20,16 +38,16 @@ AudioRegionComparator::operator() (const AudioRegionView* a, const AudioRegionVi } } -AudioRegionSelection::AudioRegionSelection () +RegionSelection::RegionSelection () { _current_start = 0; _current_end = 0; } -AudioRegionSelection::AudioRegionSelection (const AudioRegionSelection& other) +RegionSelection::RegionSelection (const RegionSelection& other) { - for (AudioRegionSelection::const_iterator i = other.begin(); i != other.end(); ++i) { + for (RegionSelection::const_iterator i = other.begin(); i != other.end(); ++i) { add (*i, false); } _current_start = other._current_start; @@ -38,14 +56,14 @@ AudioRegionSelection::AudioRegionSelection (const AudioRegionSelection& other) -AudioRegionSelection& -AudioRegionSelection::operator= (const AudioRegionSelection& other) +RegionSelection& +RegionSelection::operator= (const RegionSelection& other) { if (this != &other) { clear_all(); - for (AudioRegionSelection::const_iterator i = other.begin(); i != other.end(); ++i) { + for (RegionSelection::const_iterator i = other.begin(); i != other.end(); ++i) { add (*i, false); } @@ -57,13 +75,13 @@ AudioRegionSelection::operator= (const AudioRegionSelection& other) } void -AudioRegionSelection::clear_all() +RegionSelection::clear_all() { clear(); _bylayer.clear(); } -bool AudioRegionSelection::contains (AudioRegionView* rv) +bool RegionSelection::contains (RegionView* rv) { if (this->find (rv) != end()) { return true; @@ -75,21 +93,21 @@ bool AudioRegionSelection::contains (AudioRegionView* rv) } void -AudioRegionSelection::add (AudioRegionView* rv, bool dosort) +RegionSelection::add (RegionView* rv, bool dosort) { if (this->find (rv) != end()) { /* we already have it */ return; } - rv->AudioRegionViewGoingAway.connect (mem_fun(*this, &AudioRegionSelection::remove_it)); + rv->RegionViewGoingAway.connect (mem_fun(*this, &RegionSelection::remove_it)); - if (rv->region.first_frame() < _current_start || empty()) { - _current_start = rv->region.first_frame(); + if (rv->region().first_frame() < _current_start || empty()) { + _current_start = rv->region().first_frame(); } - if (rv->region.last_frame() > _current_end || empty()) { - _current_end = rv->region.last_frame(); + if (rv->region().last_frame() > _current_end || empty()) { + _current_end = rv->region().last_frame(); } insert (rv); @@ -100,15 +118,15 @@ AudioRegionSelection::add (AudioRegionView* rv, bool dosort) } void -AudioRegionSelection::remove_it (AudioRegionView *rv) +RegionSelection::remove_it (RegionView *rv) { remove (rv); } bool -AudioRegionSelection::remove (AudioRegionView* rv) +RegionSelection::remove (RegionView* rv) { - AudioRegionSelection::iterator i; + RegionSelection::iterator i; if ((i = this->find (rv)) != end()) { @@ -124,7 +142,7 @@ AudioRegionSelection::remove (AudioRegionView* rv) } else { - AudioRegion& region ((*i)->region); + Region& region ((*i)->region()); if (region.first_frame() == _current_start) { @@ -165,15 +183,15 @@ AudioRegionSelection::remove (AudioRegionView* rv) } void -AudioRegionSelection::add_to_layer (AudioRegionView * rv) +RegionSelection::add_to_layer (RegionView * rv) { // insert it into layer sorted position - list::iterator i; + list::iterator i; for (i = _bylayer.begin(); i != _bylayer.end(); ++i) { - if (rv->region.layer() < (*i)->region.layer()) { + if (rv->region().layer() < (*i)->region().layer()) { _bylayer.insert(i, rv); return; } @@ -184,16 +202,16 @@ AudioRegionSelection::add_to_layer (AudioRegionView * rv) } struct RegionSortByTime { - bool operator() (const AudioRegionView* a, const AudioRegionView* b) { - return a->region.position() < b->region.position(); + bool operator() (const RegionView* a, const RegionView* b) { + return a->region().position() < b->region().position(); } }; void -AudioRegionSelection::by_position (list& foo) const +RegionSelection::by_position (list& foo) const { - list::const_iterator i; + list::const_iterator i; RegionSortByTime sorter; for (i = _bylayer.begin(); i != _bylayer.end(); ++i) { diff --git a/gtk2_ardour/region_selection.h b/gtk2_ardour/region_selection.h index 0c2b7be025..2192442cb0 100644 --- a/gtk2_ardour/region_selection.h +++ b/gtk2_ardour/region_selection.h @@ -1,3 +1,21 @@ +/* + Copyright (C) 2006 Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. +*/ + #ifndef __ardour_gtk_region_selection_h__ #define __ardour_gtk_region_selection_h__ @@ -9,23 +27,23 @@ using std::list; using std::set; -class AudioRegionView; +class RegionView; -struct AudioRegionComparator { - bool operator() (const AudioRegionView* a, const AudioRegionView* b) const; +struct RegionComparator { + bool operator() (const RegionView* a, const RegionView* b) const; }; -class AudioRegionSelection : public set, public sigc::trackable +class RegionSelection : public set, public sigc::trackable { public: - AudioRegionSelection(); - AudioRegionSelection (const AudioRegionSelection&); + RegionSelection(); + RegionSelection (const RegionSelection&); - AudioRegionSelection& operator= (const AudioRegionSelection&); + RegionSelection& operator= (const RegionSelection&); - void add (AudioRegionView*, bool dosort = true); - bool remove (AudioRegionView*); - bool contains (AudioRegionView*); + void add (RegionView*, bool dosort = true); + bool remove (RegionView*); + bool contains (RegionView*); void clear_all(); @@ -39,18 +57,18 @@ class AudioRegionSelection : public set return _current_end; } - const list & by_layer() const { return _bylayer; } - void by_position (list&) const; + const list & by_layer() const { return _bylayer; } + void by_position (list&) const; private: - void remove_it (AudioRegionView*); + void remove_it (RegionView*); - void add_to_layer (AudioRegionView *); + void add_to_layer (RegionView *); jack_nframes_t _current_start; jack_nframes_t _current_end; - list _bylayer; + list _bylayer; }; #endif /* __ardour_gtk_region_selection_h__ */ diff --git a/gtk2_ardour/region_view.cc b/gtk2_ardour/region_view.cc new file mode 100644 index 0000000000..ebec4261ac --- /dev/null +++ b/gtk2_ardour/region_view.cc @@ -0,0 +1,494 @@ +/* + Copyright (C) 2001-2006 Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + + $Id: regionview.cc 691 2006-07-23 12:03:19Z drobilla $ +*/ + +#include +#include +#include + +#include + +#include + +#include +#include +#include +#include + +#include "streamview.h" +#include "region_view.h" +#include "route_time_axis.h" +#include "simplerect.h" +#include "simpleline.h" +#include "waveview.h" +#include "public_editor.h" +#include "region_editor.h" +#include "ghostregion.h" +#include "route_time_axis.h" +#include "utils.h" +#include "rgb_macros.h" +#include "gui_thread.h" + +#include "i18n.h" + +using namespace sigc; +using namespace ARDOUR; +using namespace PBD; +using namespace Editing; +using namespace ArdourCanvas; + +static const int32_t sync_mark_width = 9; + +sigc::signal RegionView::RegionViewGoingAway; + +RegionView::RegionView (ArdourCanvas::Group* parent, + TimeAxisView& tv, + ARDOUR::Region& r, + double spu, + Gdk::Color& basic_color) + : TimeAxisViewItem (r.name(), *parent, tv, spu, basic_color, r.position(), r.length(), + TimeAxisViewItem::Visibility (TimeAxisViewItem::ShowNameText| + TimeAxisViewItem::ShowNameHighlight| + TimeAxisViewItem::ShowFrame)) + , _region (r) + , sync_mark(0) + , no_wave_msg(0) + , editor(0) + , current_visible_sync_position(0.0) + , valid(false) + , _pixel_width(1.0) + , _height(1.0) + , in_destructor(false) + , wait_for_data(false) +{ +} + +RegionView::RegionView (ArdourCanvas::Group* parent, + TimeAxisView& tv, + ARDOUR::Region& r, + double spu, + Gdk::Color& basic_color, + TimeAxisViewItem::Visibility visibility) + : TimeAxisViewItem (r.name(), *parent, tv, spu, basic_color, r.position(), r.length(), visibility) + , _region (r) + , sync_mark(0) + , no_wave_msg(0) + , editor(0) + , current_visible_sync_position(0.0) + , valid(false) + , _pixel_width(1.0) + , _height(1.0) + , in_destructor(false) + , wait_for_data(false) +{ +} + +void +RegionView::init (Gdk::Color& basic_color, bool wfd) +{ + editor = 0; + valid = true; + in_destructor = false; + _height = 0; + wait_for_data = wfd; + + compute_colors (basic_color); + + name_highlight->set_data ("regionview", this); + name_text->set_data ("regionview", this); + + /* an equilateral triangle */ + ArdourCanvas::Points shape; + shape.push_back (Gnome::Art::Point (-((sync_mark_width-1)/2), 1)); + shape.push_back (Gnome::Art::Point ((sync_mark_width - 1)/2, 1)); + shape.push_back (Gnome::Art::Point (0, sync_mark_width - 1)); + shape.push_back (Gnome::Art::Point (-((sync_mark_width-1)/2), 1)); + + sync_mark = new ArdourCanvas::Polygon (*group); + sync_mark->property_points() = shape; + sync_mark->property_fill_color_rgba() = fill_color; + sync_mark->hide(); + + reset_width_dependent_items ((double) _region.length() / samples_per_unit); + + set_height (trackview.height); + + region_muted (); + region_sync_changed (); + region_resized (BoundsChanged); + region_locked (); + + _region.StateChanged.connect (mem_fun(*this, &RegionView::region_changed)); + + group->signal_event().connect (bind (mem_fun (PublicEditor::instance(), &PublicEditor::canvas_region_view_event), group, this)); + name_highlight->signal_event().connect (bind (mem_fun (PublicEditor::instance(), &PublicEditor::canvas_region_view_name_highlight_event), name_highlight, this)); + + set_colors (); + + ColorChanged.connect (mem_fun (*this, &RegionView::color_handler)); + + /* XXX sync mark drag? */ +} + +RegionView::~RegionView () +{ + in_destructor = true; + + RegionViewGoingAway (this); /* EMIT_SIGNAL */ + + for (vector::iterator g = ghosts.begin(); g != ghosts.end(); ++g) { + delete *g; + } + + if (editor) { + delete editor; + } +} + +gint +RegionView::_lock_toggle (ArdourCanvas::Item* item, GdkEvent* ev, void* arg) +{ + switch (ev->type) { + case GDK_BUTTON_RELEASE: + static_cast(arg)->lock_toggle (); + return TRUE; + break; + default: + break; + } + return FALSE; +} + +void +RegionView::lock_toggle () +{ + _region.set_locked (!_region.locked()); +} + +void +RegionView::region_changed (Change what_changed) +{ + ENSURE_GUI_THREAD (bind (mem_fun(*this, &RegionView::region_changed), what_changed)); + + if (what_changed & BoundsChanged) { + region_resized (what_changed); + region_sync_changed (); + } + if (what_changed & Region::MuteChanged) { + region_muted (); + } + if (what_changed & Region::OpacityChanged) { + region_opacity (); + } + if (what_changed & ARDOUR::NameChanged) { + region_renamed (); + } + if (what_changed & Region::SyncOffsetChanged) { + region_sync_changed (); + } + if (what_changed & Region::LayerChanged) { + region_layered (); + } + if (what_changed & Region::LockChanged) { + region_locked (); + } +} + +void +RegionView::region_locked () +{ + /* name will show locked status */ + region_renamed (); +} + +void +RegionView::region_resized (Change what_changed) +{ + double unit_length; + + if (what_changed & ARDOUR::PositionChanged) { + set_position (_region.position(), 0); + } + + if (what_changed & Change (StartChanged|LengthChanged)) { + + set_duration (_region.length(), 0); + + unit_length = _region.length() / samples_per_unit; + + reset_width_dependent_items (unit_length); + + for (vector::iterator i = ghosts.begin(); i != ghosts.end(); ++i) { + + (*i)->set_duration (unit_length); + + } + } +} + +void +RegionView::reset_width_dependent_items (double pixel_width) +{ + TimeAxisViewItem::reset_width_dependent_items (pixel_width); + _pixel_width = pixel_width; +} + +void +RegionView::region_layered () +{ + RouteTimeAxisView *rtv = dynamic_cast(&get_time_axis_view()); + assert(rtv); + rtv->view()->region_layered (this); +} + +void +RegionView::region_muted () +{ + set_frame_color (); + region_renamed (); +} + +void +RegionView::region_opacity () +{ + set_frame_color (); +} + +void +RegionView::raise () +{ + _region.raise (); +} + +void +RegionView::raise_to_top () +{ + _region.raise_to_top (); +} + +void +RegionView::lower () +{ + _region.lower (); +} + +void +RegionView::lower_to_bottom () +{ + _region.lower_to_bottom (); +} + +bool +RegionView::set_position (jack_nframes_t pos, void* src, double* ignored) +{ + double delta; + bool ret; + + if (!(ret = TimeAxisViewItem::set_position (pos, this, &delta))) { + return false; + } + + if (ignored) { + *ignored = delta; + } + + if (delta) { + for (vector::iterator i = ghosts.begin(); i != ghosts.end(); ++i) { + (*i)->group->move (delta, 0.0); + } + } + + return ret; +} + +void +RegionView::set_samples_per_unit (gdouble spu) +{ + TimeAxisViewItem::set_samples_per_unit (spu); + + for (vector::iterator i = ghosts.begin(); i != ghosts.end(); ++i) { + (*i)->set_samples_per_unit (spu); + (*i)->set_duration (_region.length() / samples_per_unit); + } + + region_sync_changed (); +} + +bool +RegionView::set_duration (jack_nframes_t frames, void *src) +{ + if (!TimeAxisViewItem::set_duration (frames, src)) { + return false; + } + + for (vector::iterator i = ghosts.begin(); i != ghosts.end(); ++i) { + (*i)->set_duration (_region.length() / samples_per_unit); + } + + return true; +} + +void +RegionView::compute_colors (Gdk::Color& basic_color) +{ + TimeAxisViewItem::compute_colors (basic_color); +} + +void +RegionView::set_colors () +{ + TimeAxisViewItem::set_colors (); + + if (sync_mark) { + sync_mark->property_fill_color_rgba() = fill_color; + } +} + +void +RegionView::set_frame_color () +{ + if (_region.opaque()) { + fill_opacity = 180; + } else { + fill_opacity = 100; + } + + TimeAxisViewItem::set_frame_color (); +} + +void +RegionView::hide_region_editor() +{ + if (editor) { + editor->hide_all (); + } +} + +void +RegionView::region_renamed () +{ + string str; + + if (_region.locked()) { + str += '>'; + str += _region.name(); + str += '<'; + } else { + str = _region.name(); + } + + if (_region.speed_mismatch (trackview.session().frame_rate())) { + str = string ("*") + str; + } + + if (_region.muted()) { + str = string ("!") + str; + } + + set_item_name (str, this); + set_name_text (str); +} + +void +RegionView::region_sync_changed () +{ + if (sync_mark == 0) { + return; + } + + int sync_dir; + jack_nframes_t sync_offset; + + sync_offset = _region.sync_offset (sync_dir); + + /* this has to handle both a genuine change of position, a change of samples_per_unit, + and a change in the bounds of the _region. + */ + + if (sync_offset == 0) { + + /* no sync mark - its the start of the region */ + + sync_mark->hide(); + + } else { + + if ((sync_dir < 0) || ((sync_dir > 0) && (sync_offset > _region.length()))) { + + /* no sync mark - its out of the bounds of the region */ + + sync_mark->hide(); + + } else { + + /* lets do it */ + + Points points; + + //points = sync_mark->property_points().get_value(); + + double offset = sync_offset / samples_per_unit; + points.push_back (Gnome::Art::Point (offset - ((sync_mark_width-1)/2), 1)); + points.push_back (Gnome::Art::Point (offset + ((sync_mark_width-1)/2), 1)); + points.push_back (Gnome::Art::Point (offset, sync_mark_width - 1)); + points.push_back (Gnome::Art::Point (offset - ((sync_mark_width-1)/2), 1)); + sync_mark->property_points().set_value (points); + sync_mark->show(); + + } + } +} + +void +RegionView::move (double x_delta, double y_delta) +{ + if (_region.locked() || (x_delta == 0 && y_delta == 0)) { + return; + } + + get_canvas_group()->move (x_delta, y_delta); + + /* note: ghosts never leave their tracks so y_delta for them is always zero */ + + for (vector::iterator i = ghosts.begin(); i != ghosts.end(); ++i) { + (*i)->group->move (x_delta, 0.0); + } +} + +void +RegionView::remove_ghost (GhostRegion* ghost) +{ + if (in_destructor) { + return; + } + + for (vector::iterator i = ghosts.begin(); i != ghosts.end(); ++i) { + if (*i == ghost) { + ghosts.erase (i); + break; + } + } +} + +uint32_t +RegionView::get_fill_color () +{ + return fill_color; +} + diff --git a/gtk2_ardour/region_view.h b/gtk2_ardour/region_view.h new file mode 100644 index 0000000000..fdc69ea70e --- /dev/null +++ b/gtk2_ardour/region_view.h @@ -0,0 +1,140 @@ +/* + Copyright (C) 2001-2006 Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. +*/ + +#ifndef __gtk_ardour_region_view_h__ +#define __gtk_ardour_region_view_h__ + +#include + +#include +#include +#include +#include + +#include "time_axis_view_item.h" +#include "automation_line.h" +#include "enums.h" +#include "waveview.h" +#include "canvas.h" +#include "color.h" + +class TimeAxisView; +class RegionEditor; +class GhostRegion; +class AutomationTimeAxisView; + +class RegionView : public TimeAxisViewItem +{ + public: + RegionView (ArdourCanvas::Group* parent, + TimeAxisView& time_view, + ARDOUR::Region& region, + double samples_per_unit, + Gdk::Color& basic_color); + + ~RegionView (); + + virtual void init (Gdk::Color& base_color, bool wait_for_data); + + ARDOUR::Region& region() const { return _region; } + + bool is_valid() const { return valid; } + void set_valid (bool yn) { valid = yn; } + + virtual void set_height (double) = 0; + virtual void set_samples_per_unit (double); + virtual bool set_duration (jack_nframes_t, void*); + + void move (double xdelta, double ydelta); + + void raise (); + void raise_to_top (); + void lower (); + void lower_to_bottom (); + + bool set_position(jack_nframes_t pos, void* src, double* delta = 0); + + virtual void show_region_editor () = 0; + virtual void hide_region_editor(); + + virtual void region_changed (ARDOUR::Change); + + virtual GhostRegion* add_ghost (AutomationTimeAxisView&) = 0; + void remove_ghost (GhostRegion*); + + uint32_t get_fill_color (); + + virtual void entered () {} + virtual void exited () {} + + static sigc::signal RegionViewGoingAway; + sigc::signal GoingAway; + + protected: + + /** Allows derived types to specify their visibility requirements + * to the TimeAxisViewItem parent class + */ + RegionView (ArdourCanvas::Group *, + TimeAxisView&, + ARDOUR::Region&, + double samples_per_unit, + Gdk::Color& basic_color, + TimeAxisViewItem::Visibility); + + virtual void region_resized (ARDOUR::Change); + void region_moved (void *); + virtual void region_muted (); + void region_locked (); + void region_opacity (); + void region_layered (); + void region_renamed (); + void region_sync_changed (); + + static gint _lock_toggle (ArdourCanvas::Item*, GdkEvent*, void*); + void lock_toggle (); + + virtual void set_colors (); + virtual void compute_colors (Gdk::Color&); + virtual void set_frame_color (); + virtual void reset_width_dependent_items (double pixel_width); + + virtual void color_handler (ColorID, uint32_t) {} + + ARDOUR::Region& _region; + + ArdourCanvas::Polygon* sync_mark; ///< polgyon for sync position + ArdourCanvas::Text* no_wave_msg; + + RegionEditor* editor; + + vector control_points; + double current_visible_sync_position; + + bool valid; ///< see StreamView::redisplay_diskstream() + double _pixel_width; + double _height; + bool in_destructor; + + bool wait_for_data; + sigc::connection data_ready_connection; + + vector ghosts; +}; + +#endif /* __gtk_ardour_region_view_h__ */ diff --git a/gtk2_ardour/route_params_ui.cc b/gtk2_ardour/route_params_ui.cc index d6ec7eab6c..8b47a17511 100644 --- a/gtk2_ardour/route_params_ui.cc +++ b/gtk2_ardour/route_params_ui.cc @@ -59,14 +59,10 @@ using namespace sigc; RouteParams_UI::RouteParams_UI (AudioEngine& eng) : ArdourDialog ("track/bus inspector"), engine (eng), - _route(0), track_menu(0) { pre_redirect_box = 0; post_redirect_box = 0; - _route = 0; - _pre_redirect = 0; - _post_redirect = 0; _input_iosel = 0; _output_iosel = 0; _active_pre_view = 0; @@ -163,7 +159,7 @@ RouteParams_UI::~RouteParams_UI () } void -RouteParams_UI::add_route (Route* route) +RouteParams_UI::add_route (boost::shared_ptr route) { ENSURE_GUI_THREAD(bind (mem_fun(*this, &RouteParams_UI::add_route), route)); @@ -183,22 +179,22 @@ RouteParams_UI::add_route (Route* route) void -RouteParams_UI::route_name_changed (void *src, Route *route) +RouteParams_UI::route_name_changed (void *src, boost::shared_ptr route) { ENSURE_GUI_THREAD(bind (mem_fun(*this, &RouteParams_UI::route_name_changed), src, route)); bool found = false ; TreeModel::Children rows = route_display_model->children(); for(TreeModel::Children::iterator iter = rows.begin(); iter != rows.end(); ++iter) { - if((*iter)[route_display_columns.route] == route) { + boost::shared_ptr r =(*iter)[route_display_columns.route]; + if (r == route) { (*iter)[route_display_columns.text] = route->name() ; found = true ; break; } } - if(!found) - { + if(!found) { error << _("route display list item for renamed route not found!") << endmsg; } @@ -217,8 +213,8 @@ RouteParams_UI::setup_redirect_boxes() cleanup_redirect_boxes(); // construct new redirect boxes - pre_redirect_box = new RedirectBox(PreFader, *session, *_route, *_plugin_selector, _rr_selection); - post_redirect_box = new RedirectBox(PostFader, *session, *_route, *_plugin_selector, _rr_selection); + pre_redirect_box = new RedirectBox(PreFader, *session, _route, *_plugin_selector, _rr_selection); + post_redirect_box = new RedirectBox(PostFader, *session, _route, *_plugin_selector, _rr_selection); pre_redir_hpane.pack1 (*pre_redirect_box); post_redir_hpane.pack1 (*post_redirect_box); @@ -256,13 +252,13 @@ RouteParams_UI::setup_io_frames() cleanup_io_frames(); // input - _input_iosel = new IOSelector (*session, *_route, true); + _input_iosel = new IOSelector (*session, _route, true); _input_iosel->redisplay (); input_frame.add (*_input_iosel); input_frame.show_all(); // output - _output_iosel = new IOSelector (*session, *_route, false); + _output_iosel = new IOSelector (*session, _route, false); _output_iosel->redisplay (); output_frame.add (*_output_iosel); output_frame.show_all(); @@ -322,36 +318,31 @@ RouteParams_UI::cleanup_post_view (bool stopupdate) void -RouteParams_UI::route_removed (Route *route) +RouteParams_UI::route_removed (boost::shared_ptr route) { ENSURE_GUI_THREAD(bind (mem_fun(*this, &RouteParams_UI::route_removed), route)); - /* - route_select_list.freeze (); - route_select_list.clear (); - session->foreach_route (this, &RouteParams_UI::add_route); - route_select_list.thaw (); - */ TreeModel::Children rows = route_display_model->children(); TreeModel::Children::iterator ri; for(TreeModel::Children::iterator iter = rows.begin(); iter != rows.end(); ++iter) { - if((*iter)[route_display_columns.route] == route) { + boost::shared_ptr r =(*iter)[route_display_columns.route]; + + if (r == route) { route_display_model->erase(iter); break; } } - if (route == _route) - { + if (route == _route) { cleanup_io_frames(); cleanup_pre_view(); cleanup_post_view(); cleanup_redirect_boxes(); - _route = 0; - _pre_redirect = 0; - _post_redirect = 0; + _route.reset ((Route*) 0); + _pre_redirect.reset ((Redirect*) 0); + _post_redirect.reset ((Redirect*) 0); update_title(); } } @@ -390,9 +381,9 @@ RouteParams_UI::session_gone () cleanup_post_view(); cleanup_redirect_boxes(); - _route = 0; - _pre_redirect = 0; - _post_redirect = 0; + _route.reset ((Route*) 0); + _pre_redirect.reset ((Redirect*) 0); + _post_redirect.reset ((Redirect*) 0); update_title(); ArdourDialog::session_gone(); @@ -406,7 +397,7 @@ RouteParams_UI::route_selected() TreeModel::iterator iter = selection->get_selected(); // only used with Gtk::SELECTION_SINGLE if(iter) { //If anything is selected - Route* route = (*iter)[route_display_columns.route] ; + boost::shared_ptr route = (*iter)[route_display_columns.route] ; if (_route == route) { // do nothing @@ -447,9 +438,9 @@ RouteParams_UI::route_selected() cleanup_post_view(); cleanup_redirect_boxes(); - _route = 0; - _pre_redirect = 0; - _post_redirect = 0; + _route.reset ((Route*) 0); + _pre_redirect.reset ((Redirect*) 0); + _post_redirect.reset ((Redirect *) 0); track_input_label.set_text(_("NO TRACK")); update_title(); } @@ -468,7 +459,7 @@ RouteParams_UI::route_selected() // cleanup_post_view(); // cleanup_redirect_boxes(); -// _route = 0; +// _route.reset ((Route*)0); // _pre_redirect = 0; // _post_redirect = 0; // track_input_label.set_text(_("NO TRACK")); @@ -495,8 +486,8 @@ RouteParams_UI::redirects_changed (void *src) cleanup_pre_view(); cleanup_post_view(); - _pre_redirect = 0; - _post_redirect = 0; + _pre_redirect.reset ((Redirect*) 0); + _post_redirect.reset ((Redirect*) 0); //update_title(); } @@ -520,24 +511,24 @@ RouteParams_UI::show_track_menu() void -RouteParams_UI::redirect_selected (ARDOUR::Redirect *redirect, ARDOUR::Placement place) +RouteParams_UI::redirect_selected (boost::shared_ptr redirect, ARDOUR::Placement place) { - Insert *insert; + boost::shared_ptr insert; if ((place == PreFader && _pre_redirect == redirect) || (place == PostFader && _post_redirect == redirect)){ return; } - if ((insert = dynamic_cast (redirect)) == 0) { + if ((insert = boost::dynamic_pointer_cast (redirect)) == 0) { - Send *send; - - if ((send = dynamic_cast (redirect)) != 0) { + boost::shared_ptr send; + + if ((send = boost::dynamic_pointer_cast (redirect)) != 0) { /* its a send */ - SendUI *send_ui = new SendUI (*send, *session); + SendUI *send_ui = new SendUI (send, *session); if (place == PreFader) { cleanup_pre_view(); @@ -560,16 +551,16 @@ RouteParams_UI::redirect_selected (ARDOUR::Redirect *redirect, ARDOUR::Placement } else { /* its an insert, though we don't know what kind yet. */ - PluginInsert *plugin_insert; - PortInsert *port_insert; + boost::shared_ptr plugin_insert; + boost::shared_ptr port_insert; - if ((plugin_insert = dynamic_cast (insert)) != 0) { + if ((plugin_insert = boost::dynamic_pointer_cast (insert)) != 0) { - PluginUI *plugin_ui = new PluginUI (session->engine(), *plugin_insert, true); + PluginUI *plugin_ui = new PluginUI (session->engine(), plugin_insert, true); if (place == PreFader) { cleanup_pre_view(); - _pre_plugin_conn = plugin_insert->plugin().GoingAway.connect (bind (mem_fun(*this, &RouteParams_UI::plugin_going_away), PreFader)); + _pre_plugin_conn = plugin_insert->plugin()->GoingAway.connect (bind (mem_fun(*this, &RouteParams_UI::plugin_going_away), PreFader)); plugin_ui->start_updating (0); _active_pre_view = plugin_ui; pre_redir_hpane.pack2 (*_active_pre_view); @@ -577,16 +568,16 @@ RouteParams_UI::redirect_selected (ARDOUR::Redirect *redirect, ARDOUR::Placement } else { cleanup_post_view(); - _post_plugin_conn = plugin_insert->plugin().GoingAway.connect (bind (mem_fun(*this, &RouteParams_UI::plugin_going_away), PostFader)); + _post_plugin_conn = plugin_insert->plugin()->GoingAway.connect (bind (mem_fun(*this, &RouteParams_UI::plugin_going_away), PostFader)); plugin_ui->start_updating (0); _active_post_view = plugin_ui; post_redir_hpane.pack2 (*_active_post_view); post_redir_hpane.show_all(); } - } else if ((port_insert = dynamic_cast (insert)) != 0) { + } else if ((port_insert = boost::dynamic_pointer_cast (insert)) != 0) { - PortInsertUI *portinsert_ui = new PortInsertUI (*session, *port_insert); + PortInsertUI *portinsert_ui = new PortInsertUI (*session, port_insert); if (place == PreFader) { cleanup_pre_view(); @@ -610,8 +601,7 @@ RouteParams_UI::redirect_selected (ARDOUR::Redirect *redirect, ARDOUR::Placement if (place == PreFader) { _pre_redirect = redirect; - } - else { + } else { _post_redirect = redirect; } @@ -619,23 +609,6 @@ RouteParams_UI::redirect_selected (ARDOUR::Redirect *redirect, ARDOUR::Placement } -void -RouteParams_UI::redirect_unselected (ARDOUR::Redirect *redirect) -{ - // not called anymore - - if (redirect == _pre_redirect) { - cleanup_pre_view(); - _pre_redirect = 0; - } - else if (redirect == _post_redirect) { - cleanup_post_view(); - _post_redirect = 0; - } -} - - - void RouteParams_UI::plugin_going_away (Plugin *plugin, Placement place) { @@ -645,11 +618,11 @@ RouteParams_UI::plugin_going_away (Plugin *plugin, Placement place) if (place == PreFader) { cleanup_pre_view (false); - _pre_redirect = 0; + _pre_redirect.reset ((Redirect*) 0); } else { cleanup_post_view (false); - _post_redirect = 0; + _post_redirect.reset ((Redirect*) 0); } } @@ -661,13 +634,13 @@ RouteParams_UI::redirect_going_away (ARDOUR::Redirect *plugin) printf ("redirect going away\n"); // delete the current view without calling finish - if (plugin == _pre_redirect) { + if (plugin == _pre_redirect.get()) { cleanup_pre_view (false); - _pre_redirect = 0; + _pre_redirect.reset ((Redirect*) 0); } - else if (plugin == _post_redirect) { + else if (plugin == _post_redirect.get()) { cleanup_post_view (false); - _post_redirect = 0; + _post_redirect.reset ((Redirect*) 0); } } diff --git a/gtk2_ardour/route_params_ui.h b/gtk2_ardour/route_params_ui.h index 96b2041db4..5f487d6e5c 100644 --- a/gtk2_ardour/route_params_ui.h +++ b/gtk2_ardour/route_params_ui.h @@ -33,8 +33,9 @@ #include #include +#include + #include -#include #include #include @@ -120,14 +121,14 @@ class RouteParams_UI : public ArdourDialog PluginSelector *_plugin_selector; RouteRedirectSelection _rr_selection; - ARDOUR::Route *_route; + boost::shared_ptr _route; sigc::connection _route_conn; sigc::connection _route_ds_conn; - ARDOUR::Redirect * _pre_redirect; + boost::shared_ptr _pre_redirect; sigc::connection _pre_plugin_conn; - ARDOUR::Redirect * _post_redirect; + boost::shared_ptr _post_redirect; sigc::connection _post_plugin_conn; @@ -150,7 +151,7 @@ class RouteParams_UI : public ArdourDialog add(route); } Gtk::TreeModelColumn text; - Gtk::TreeModelColumn route; + Gtk::TreeModelColumn > route; }; RouteDisplayModelColumns route_display_columns ; @@ -158,10 +159,10 @@ class RouteParams_UI : public ArdourDialog Glib::RefPtr route_display_model; - void add_route (ARDOUR::Route*); + void add_route (boost::shared_ptr); - void route_name_changed (void *src, ARDOUR::Route *route); - void route_removed (ARDOUR::Route *route); + void route_name_changed (void *src, boost::shared_ptr route); + void route_removed (boost::shared_ptr route); void route_selected(); @@ -179,8 +180,7 @@ class RouteParams_UI : public ArdourDialog void setup_redirect_boxes(); void cleanup_redirect_boxes(); - void redirect_selected (ARDOUR::Redirect *, ARDOUR::Placement); - void redirect_unselected (ARDOUR::Redirect *); + void redirect_selected (boost::shared_ptr, ARDOUR::Placement); void plugin_going_away (ARDOUR::Plugin *foo, ARDOUR::Placement); void redirect_going_away (ARDOUR::Redirect *foo); diff --git a/gtk2_ardour/route_redirect_selection.cc b/gtk2_ardour/route_redirect_selection.cc index 6d315e0aae..76f202dd92 100644 --- a/gtk2_ardour/route_redirect_selection.cc +++ b/gtk2_ardour/route_redirect_selection.cc @@ -61,17 +61,6 @@ RouteRedirectSelection::clear () void RouteRedirectSelection::clear_redirects () { - for (RedirectSelection::iterator i = redirects.begin(); i != redirects.end(); ) { - RedirectSelection::iterator tmp; - - tmp = i; - ++tmp; - - delete *i; - - i = tmp; - } - redirects.clear (); RedirectsChanged (); } @@ -84,29 +73,32 @@ RouteRedirectSelection::clear_routes () } void -RouteRedirectSelection::add (Redirect* r) +RouteRedirectSelection::add (boost::shared_ptr r) { if (find (redirects.begin(), redirects.end(), r) == redirects.end()) { redirects.push_back (r); - - void (RouteRedirectSelection::*pmf)(Redirect*) = &RouteRedirectSelection::remove; - r->GoingAway.connect (mem_fun(*this, pmf)); + + // XXX SHAREDPTR FIXME + // void (RouteRedirectSelection::*pmf)(Redirect*) = &RouteRedirectSelection::remove; + // r->GoingAway.connect (mem_fun(*this, pmf)); RedirectsChanged(); } } void -RouteRedirectSelection::add (const vector& rlist) +RouteRedirectSelection::add (const vector >& rlist) { bool changed = false; - for (vector::const_iterator i = rlist.begin(); i != rlist.end(); ++i) { + for (vector >::const_iterator i = rlist.begin(); i != rlist.end(); ++i) { if (find (redirects.begin(), redirects.end(), *i) == redirects.end()) { redirects.push_back (*i); - void (RouteRedirectSelection::*pmf)(Redirect*) = &RouteRedirectSelection::remove; - (*i)->GoingAway.connect (mem_fun(*this, pmf)); + // XXX SHAREDPTR FIXME + + //void (RouteRedirectSelection::*pmf)(Redirect*) = &RouteRedirectSelection::remove; + // (*i)->GoingAway.connect (mem_fun(*this, pmf)); changed = true; } } @@ -117,9 +109,9 @@ RouteRedirectSelection::add (const vector& rlist) } void -RouteRedirectSelection::remove (Redirect* r) +RouteRedirectSelection::remove (boost::shared_ptr r) { - list::iterator i; + list >::iterator i; if ((i = find (redirects.begin(), redirects.end(), r)) != redirects.end()) { redirects.erase (i); RedirectsChanged (); @@ -127,36 +119,37 @@ RouteRedirectSelection::remove (Redirect* r) } void -RouteRedirectSelection::set (Redirect *r) +RouteRedirectSelection::set (boost::shared_ptr r) { clear_redirects (); add (r); } void -RouteRedirectSelection::set (const vector& rlist) +RouteRedirectSelection::set (const vector >& rlist) { clear_redirects (); add (rlist); } void -RouteRedirectSelection::add (Route* r) +RouteRedirectSelection::add (boost::shared_ptr r) { if (find (routes.begin(), routes.end(), r) == routes.end()) { routes.push_back (r); - void (RouteRedirectSelection::*pmf)(Route*) = &RouteRedirectSelection::remove; - r->GoingAway.connect (bind (mem_fun(*this, pmf), r)); + // XXX SHAREDPTR FIXME + // void (RouteRedirectSelection::*pmf)(Route*) = &RouteRedirectSelection::remove; + // r->GoingAway.connect (bind (mem_fun(*this, pmf), r)); RoutesChanged(); } } void -RouteRedirectSelection::remove (Route* r) +RouteRedirectSelection::remove (boost::shared_ptr r) { - list::iterator i; + list >::iterator i; if ((i = find (routes.begin(), routes.end(), r)) != routes.end()) { routes.erase (i); RoutesChanged (); @@ -164,16 +157,16 @@ RouteRedirectSelection::remove (Route* r) } void -RouteRedirectSelection::set (Route *r) +RouteRedirectSelection::set (boost::shared_ptr r) { clear_routes (); add (r); } bool -RouteRedirectSelection::selected (Route* ms) +RouteRedirectSelection::selected (boost::shared_ptr r) { - return find (routes.begin(), routes.end(), ms) != routes.end(); + return find (routes.begin(), routes.end(), r) != routes.end(); } bool diff --git a/gtk2_ardour/route_redirect_selection.h b/gtk2_ardour/route_redirect_selection.h index 9e2b866171..60d301e762 100644 --- a/gtk2_ardour/route_redirect_selection.h +++ b/gtk2_ardour/route_redirect_selection.h @@ -43,20 +43,20 @@ class RouteRedirectSelection : public sigc::trackable void clear (); bool empty(); - void set (ARDOUR::Redirect*); - void set (const std::vector&); - void add (ARDOUR::Redirect*); - void add (const std::vector&); - void remove (ARDOUR::Redirect*); + void set (boost::shared_ptr); + void set (const std::vector >&); + void add (boost::shared_ptr); + void add (const std::vector >&); + void remove (boost::shared_ptr); - void set (ARDOUR::Route*); - void add (ARDOUR::Route*); - void remove (ARDOUR::Route*); + void set (boost::shared_ptr); + void add (boost::shared_ptr); + void remove (boost::shared_ptr); void clear_redirects (); void clear_routes (); - bool selected (ARDOUR::Route*); + bool selected (boost::shared_ptr); }; bool operator==(const RouteRedirectSelection& a, const RouteRedirectSelection& b); diff --git a/gtk2_ardour/route_selection.h b/gtk2_ardour/route_selection.h index 50797deed3..8d5673a2ef 100644 --- a/gtk2_ardour/route_selection.h +++ b/gtk2_ardour/route_selection.h @@ -1,12 +1,14 @@ #ifndef __ardour_gtk_route_selection_h__ #define __ardour_gtk_route_selection_h__ + +#include #include namespace ARDOUR { class Route; } -struct RouteSelection : list {}; +struct RouteSelection : std::list > {}; #endif /* __ardour_gtk_route_selection_h__ */ diff --git a/gtk2_ardour/route_time_axis.cc b/gtk2_ardour/route_time_axis.cc new file mode 100644 index 0000000000..8dca7be480 --- /dev/null +++ b/gtk2_ardour/route_time_axis.cc @@ -0,0 +1,1601 @@ +/* + Copyright (C) 2006 Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. +*/ + +#include +#include +#include + +#include +#include +#include + +#include + +#include +#include +#include + +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include "ardour_ui.h" +#include "route_time_axis.h" +#include "automation_time_axis.h" +#include "redirect_automation_time_axis.h" +#include "redirect_automation_line.h" +#include "canvas_impl.h" +#include "crossfade_view.h" +#include "enums.h" +#include "gui_thread.h" +#include "keyboard.h" +#include "playlist_selector.h" +#include "plugin_selector.h" +#include "plugin_ui.h" +#include "point_selection.h" +#include "prompter.h" +#include "public_editor.h" +#include "region_view.h" +#include "rgb_macros.h" +#include "selection.h" +#include "simplerect.h" +#include "streamview.h" +#include "utils.h" + +#include + +#include "i18n.h" + +using namespace ARDOUR; +using namespace PBD; +using namespace Gtk; +using namespace Editing; + + +RouteTimeAxisView::RouteTimeAxisView (PublicEditor& ed, Session& sess, boost::shared_ptr rt, Canvas& canvas) + : AxisView(sess), + RouteUI(rt, sess, _("m"), _("s"), _("r")), // mute, solo, and record + TimeAxisView(sess,ed,(TimeAxisView*) 0, canvas), + parent_canvas (canvas), + button_table (3, 3), + edit_group_button (_("g")), // group + playlist_button (_("p")), + size_button (_("h")), // height + automation_button (_("a")), + visual_button (_("v")) + +{ + _has_state = true; + playlist_menu = 0; + playlist_action_menu = 0; + automation_action_menu = 0; + _view = 0; + timestretch_rect = 0; + no_redraw = false; + + ignore_toggle = false; + + mute_button->set_active (false); + solo_button->set_active (false); + + mute_button->set_name ("TrackMuteButton"); + solo_button->set_name ("SoloButton"); + edit_group_button.set_name ("TrackGroupButton"); + playlist_button.set_name ("TrackPlaylistButton"); + automation_button.set_name ("TrackAutomationButton"); + size_button.set_name ("TrackSizeButton"); + visual_button.set_name ("TrackVisualButton"); + hide_button.set_name ("TrackRemoveButton"); + + hide_button.add (*(manage (new Image (get_xpm("small_x.xpm"))))); + + solo_button->signal_button_press_event().connect (mem_fun (*this, &RouteTimeAxisView::select_me), false); + mute_button->signal_button_press_event().connect (mem_fun (*this, &RouteTimeAxisView::select_me), false); + playlist_button.signal_button_press_event().connect (mem_fun (*this, &RouteTimeAxisView::select_me), false); + automation_button.signal_button_press_event().connect (mem_fun (*this, &RouteTimeAxisView::select_me), false); + size_button.signal_button_press_event().connect (mem_fun (*this, &RouteTimeAxisView::select_me), false); + visual_button.signal_button_press_event().connect (mem_fun (*this, &RouteTimeAxisView::select_me), false); + hide_button.signal_button_press_event().connect (mem_fun (*this, &RouteTimeAxisView::select_me), false); + + solo_button->signal_button_press_event().connect (mem_fun(*this, &RouteUI::solo_press), false); + solo_button->signal_button_release_event().connect (mem_fun(*this, &RouteUI::solo_release), false); + mute_button->signal_button_press_event().connect (mem_fun(*this, &RouteUI::mute_press), false); + mute_button->signal_button_release_event().connect (mem_fun(*this, &RouteUI::mute_release), false); + edit_group_button.signal_button_release_event().connect (mem_fun(*this, &RouteTimeAxisView::edit_click), false); + playlist_button.signal_clicked().connect (mem_fun(*this, &RouteTimeAxisView::playlist_click)); + automation_button.signal_clicked().connect (mem_fun(*this, &RouteTimeAxisView::automation_click)); + size_button.signal_button_release_event().connect (mem_fun(*this, &RouteTimeAxisView::size_click), false); + visual_button.signal_clicked().connect (mem_fun(*this, &RouteTimeAxisView::visual_click)); + hide_button.signal_clicked().connect (mem_fun(*this, &RouteTimeAxisView::hide_click)); + + if (is_track()) { + rec_enable_button->set_active (false); + rec_enable_button->set_name ("TrackRecordEnableButton"); + rec_enable_button->signal_button_press_event().connect (mem_fun (*this, &RouteTimeAxisView::select_me), false); + rec_enable_button->signal_button_press_event().connect (mem_fun(*this, &RouteUI::rec_enable_press)); + controls_table.attach (*rec_enable_button, 5, 6, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND, 0, 0); + ARDOUR_UI::instance()->tooltips().set_tip(*rec_enable_button, _("Record")); + } + + controls_table.attach (*mute_button, 6, 7, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND, 0, 0); + controls_table.attach (*solo_button, 7, 8, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::FILL|Gtk::EXPAND, 0, 0); + + controls_table.attach (edit_group_button, 6, 7, 1, 2, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND, 0, 0); + + ARDOUR_UI::instance()->tooltips().set_tip(*solo_button,_("Solo")); + ARDOUR_UI::instance()->tooltips().set_tip(*mute_button,_("Mute")); + ARDOUR_UI::instance()->tooltips().set_tip(edit_group_button,_("Edit Group")); + ARDOUR_UI::instance()->tooltips().set_tip(size_button,_("Display Height")); + ARDOUR_UI::instance()->tooltips().set_tip(playlist_button,_("Playlist")); + ARDOUR_UI::instance()->tooltips().set_tip(automation_button, _("Automation")); + ARDOUR_UI::instance()->tooltips().set_tip(visual_button, _("Visual options")); + ARDOUR_UI::instance()->tooltips().set_tip(hide_button, _("Hide this track")); + + label_view (); + + controls_table.attach (hide_button, 0, 1, 1, 2, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); + controls_table.attach (visual_button, 1, 2, 1, 2, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); + controls_table.attach (size_button, 2, 3, 1, 2, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); + controls_table.attach (automation_button, 3, 4, 1, 2, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); + + if (is_track() && track()->mode() == ARDOUR::Normal) { + controls_table.attach (playlist_button, 5, 6, 1, 2, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); + } + + /* remove focus from the buttons */ + + automation_button.unset_flags (Gtk::CAN_FOCUS); + solo_button->unset_flags (Gtk::CAN_FOCUS); + mute_button->unset_flags (Gtk::CAN_FOCUS); + edit_group_button.unset_flags (Gtk::CAN_FOCUS); + size_button.unset_flags (Gtk::CAN_FOCUS); + playlist_button.unset_flags (Gtk::CAN_FOCUS); + hide_button.unset_flags (Gtk::CAN_FOCUS); + visual_button.unset_flags (Gtk::CAN_FOCUS); + + /* map current state of the route */ + + update_diskstream_display (); + solo_changed(0); + mute_changed(0); + //redirects_changed (0); + //reset_redirect_automation_curves (); + y_position = -1; + + _route->mute_changed.connect (mem_fun(*this, &RouteUI::mute_changed)); + _route->solo_changed.connect (mem_fun(*this, &RouteUI::solo_changed)); + _route->redirects_changed.connect (mem_fun(*this, &RouteTimeAxisView::redirects_changed)); + _route->name_changed.connect (mem_fun(*this, &RouteTimeAxisView::route_name_changed)); + _route->solo_safe_changed.connect (mem_fun(*this, &RouteUI::solo_changed)); + + if (is_track()) { + + track()->FreezeChange.connect (mem_fun(*this, &RouteTimeAxisView::map_frozen)); + track()->DiskstreamChanged.connect (mem_fun(*this, &RouteTimeAxisView::diskstream_changed)); + get_diskstream()->SpeedChanged.connect (mem_fun(*this, &RouteTimeAxisView::speed_changed)); + + /* ask for notifications of any new RegionViews */ + // FIXME: _view is NULL, but it would be nice to attach this here :/ + //_view->RegionViewAdded.connect (mem_fun(*this, &RouteTimeAxisView::region_view_added)); + //_view->attach (); + + /* pick up the correct freeze state */ + map_frozen (); + + } + + editor.ZoomChanged.connect (mem_fun(*this, &RouteTimeAxisView::reset_samples_per_unit)); + ColorChanged.connect (mem_fun (*this, &RouteTimeAxisView::color_handler)); +} + +RouteTimeAxisView::~RouteTimeAxisView () +{ + GoingAway (); /* EMIT_SIGNAL */ + + vector_delete (&redirect_automation_curves); + + for (list::iterator i = redirect_automation.begin(); i != redirect_automation.end(); ++i) { + delete *i; + } + + if (playlist_menu) { + delete playlist_menu; + playlist_menu = 0; + } + + if (playlist_action_menu) { + delete playlist_action_menu; + playlist_action_menu = 0; + } + + if (_view) { + delete _view; + _view = 0; + } +} + +void +RouteTimeAxisView::set_playlist (Playlist *newplaylist) +{ + Playlist *pl = playlist(); + assert(pl); + + modified_connection.disconnect (); + state_changed_connection.disconnect (); + + state_changed_connection = pl->StateChanged.connect (mem_fun(*this, &RouteTimeAxisView::playlist_state_changed)); + modified_connection = pl->Modified.connect (mem_fun(*this, &RouteTimeAxisView::playlist_modified)); +} + +void +RouteTimeAxisView::playlist_modified () +{ +} + +gint +RouteTimeAxisView::edit_click (GdkEventButton *ev) +{ + if (Keyboard::modifier_state_equals (ev->state, Keyboard::Control)) { + _route->set_edit_group (0, this); + return FALSE; + } + + using namespace Menu_Helpers; + + MenuList& items = edit_group_menu.items (); + RadioMenuItem::Group group; + + items.clear (); + items.push_back (RadioMenuElem (group, _("No group"), + bind (mem_fun(*this, &RouteTimeAxisView::set_edit_group_from_menu), (RouteGroup *) 0))); + + if (_route->edit_group() == 0) { + static_cast(&items.back())->set_active (); + } + + _session.foreach_edit_group (bind (mem_fun (*this, &RouteTimeAxisView::add_edit_group_menu_item), &group)); + edit_group_menu.popup (ev->button, ev->time); + + return FALSE; +} + +void +RouteTimeAxisView::add_edit_group_menu_item (RouteGroup *eg, RadioMenuItem::Group* group) +{ + using namespace Menu_Helpers; + + MenuList &items = edit_group_menu.items(); + + cerr << "adding edit group " << eg->name() << endl; + + items.push_back (RadioMenuElem (*group, eg->name(), bind (mem_fun(*this, &RouteTimeAxisView::set_edit_group_from_menu), eg))); + if (_route->edit_group() == eg) { + static_cast(&items.back())->set_active (); + } +} + +void +RouteTimeAxisView::set_edit_group_from_menu (RouteGroup *eg) + +{ + _route->set_edit_group (eg, this); +} + +void +RouteTimeAxisView::playlist_state_changed (Change ignored) +{ + // ENSURE_GUI_THREAD (bind (mem_fun(*this, &RouteTimeAxisView::playlist_state_changed), ignored)); + // why are we here ? +} + +void +RouteTimeAxisView::playlist_changed () + +{ + label_view (); + + if (is_track()) { + set_playlist (dynamic_cast(get_diskstream()->playlist())); + } +} + +void +RouteTimeAxisView::label_view () +{ + string x = _route->name(); + + if (x != name_entry.get_text()) { + name_entry.set_text (x); + } + + ARDOUR_UI::instance()->tooltips().set_tip (name_entry, x); +} + +void +RouteTimeAxisView::route_name_changed (void *src) +{ + editor.route_name_changed (this); + label_view (); +} + +void +RouteTimeAxisView::take_name_changed (void *src) + +{ + if (src != this) { + label_view (); + } +} + +void +RouteTimeAxisView::playlist_click () +{ + // always build a new action menu + + if (playlist_action_menu == 0) { + playlist_action_menu = new Menu; + playlist_action_menu->set_name ("ArdourContextMenu"); + } + + build_playlist_menu(playlist_action_menu); + + playlist_action_menu->popup (1, 0); +} + +void +RouteTimeAxisView::automation_click () +{ + if (automation_action_menu == 0) { + /* this seems odd, but the automation action + menu is built as part of the display menu. + */ + build_display_menu (); + } + automation_action_menu->popup (1, 0); +} + +void +RouteTimeAxisView::build_automation_action_menu () +{ + using namespace Menu_Helpers; + + automation_action_menu = manage (new Menu); + MenuList& automation_items = automation_action_menu->items(); + automation_action_menu->set_name ("ArdourContextMenu"); + + automation_items.push_back (MenuElem (_("Show all automation"), + mem_fun(*this, &RouteTimeAxisView::show_all_automation))); + + automation_items.push_back (MenuElem (_("Show existing automation"), + mem_fun(*this, &RouteTimeAxisView::show_existing_automation))); + + automation_items.push_back (MenuElem (_("Hide all automation"), + mem_fun(*this, &RouteTimeAxisView::hide_all_automation))); + + automation_items.push_back (MenuElem (_("Plugins"), subplugin_menu)); +} + +void +RouteTimeAxisView::build_display_menu () +{ + using namespace Menu_Helpers; + + /* get the size menu ready */ + + build_size_menu (); + + /* prepare it */ + + TimeAxisView::build_display_menu (); + + /* now fill it with our stuff */ + + MenuList& items = display_menu->items(); + display_menu->set_name ("ArdourContextMenu"); + + items.push_back (MenuElem (_("Height"), *size_menu)); + items.push_back (MenuElem (_("Color"), mem_fun(*this, &RouteTimeAxisView::select_track_color))); + + items.push_back (SeparatorElem()); + + build_remote_control_menu (); + items.push_back (MenuElem (_("Remote Control ID"), *remote_control_menu)); + + build_automation_action_menu (); + items.push_back (MenuElem (_("Automation"), *automation_action_menu)); + + // Hook for derived classes to add type specific stuff + items.push_back (SeparatorElem()); + append_extra_display_menu_items (); + items.push_back (SeparatorElem()); + + if (is_track()) { + + Menu* alignment_menu = manage (new Menu); + MenuList& alignment_items = alignment_menu->items(); + alignment_menu->set_name ("ArdourContextMenu"); + + RadioMenuItem::Group align_group; + + alignment_items.push_back (RadioMenuElem (align_group, _("Align with existing material"), + bind (mem_fun(*this, &RouteTimeAxisView::set_align_style), ExistingMaterial))); + align_existing_item = dynamic_cast(&alignment_items.back()); + if (get_diskstream()->alignment_style() == ExistingMaterial) + align_existing_item->set_active(); + + alignment_items.push_back (RadioMenuElem (align_group, _("Align with capture time"), + bind (mem_fun(*this, &RouteTimeAxisView::set_align_style), CaptureTime))); + align_capture_item = dynamic_cast(&alignment_items.back()); + if (get_diskstream()->alignment_style() == CaptureTime) + align_capture_item->set_active(); + + items.push_back (MenuElem (_("Alignment"), *alignment_menu)); + + get_diskstream()->AlignmentStyleChanged.connect ( + mem_fun(*this, &RouteTimeAxisView::align_style_changed)); + } + + items.push_back (SeparatorElem()); + items.push_back (CheckMenuElem (_("Active"), mem_fun(*this, &RouteUI::toggle_route_active))); + route_active_menu_item = dynamic_cast (&items.back()); + route_active_menu_item->set_active (_route->active()); + + items.push_back (SeparatorElem()); + items.push_back (MenuElem (_("Remove"), mem_fun(*this, &RouteUI::remove_this_route))); +} + + +void +RouteTimeAxisView::show_timestretch (jack_nframes_t start, jack_nframes_t end) +{ + double x1; + double x2; + double y2; + + TimeAxisView::show_timestretch (start, end); + + hide_timestretch (); + +#if 0 + if (ts.empty()) { + return; + } + + + /* check that the time selection was made in our route, or our edit group. + remember that edit_group() == 0 implies the route is *not* in a edit group. + */ + + if (!(ts.track == this || (ts.group != 0 && ts.group == _route->edit_group()))) { + /* this doesn't apply to us */ + return; + } + + /* ignore it if our edit group is not active */ + + if ((ts.track != this) && _route->edit_group() && !_route->edit_group()->is_active()) { + return; + } +#endif + + if (timestretch_rect == 0) { + timestretch_rect = new SimpleRect (*canvas_display); + timestretch_rect->property_x1() = 0.0; + timestretch_rect->property_y1() = 0.0; + timestretch_rect->property_x2() = 0.0; + timestretch_rect->property_y2() = 0.0; + timestretch_rect->property_fill_color_rgba() = color_map[cTimeStretchFill]; + timestretch_rect->property_outline_color_rgba() = color_map[cTimeStretchOutline]; + } + + timestretch_rect->show (); + timestretch_rect->raise_to_top (); + + x1 = start / editor.get_current_zoom(); + x2 = (end - 1) / editor.get_current_zoom(); + y2 = height - 2; + + timestretch_rect->property_x1() = x1; + timestretch_rect->property_y1() = 1.0; + timestretch_rect->property_x2() = x2; + timestretch_rect->property_y2() = y2; +} + +void +RouteTimeAxisView::hide_timestretch () +{ + TimeAxisView::hide_timestretch (); + + if (timestretch_rect) { + timestretch_rect->hide (); + } +} + +void +RouteTimeAxisView::show_selection (TimeSelection& ts) +{ + +#if 0 + /* ignore it if our edit group is not active or if the selection was started + in some other track or edit group (remember that edit_group() == 0 means + that the track is not in an edit group). + */ + + if (((ts.track != this && !is_child (ts.track)) && _route->edit_group() && !_route->edit_group()->is_active()) || + (!(ts.track == this || is_child (ts.track) || (ts.group != 0 && ts.group == _route->edit_group())))) { + hide_selection (); + return; + } +#endif + + TimeAxisView::show_selection (ts); +} + +void +RouteTimeAxisView::set_height (TrackHeight h) +{ + bool height_changed = (height == 0) || (h != height_style); + + TimeAxisView::set_height (h); + + ensure_xml_node (); + + _view->set_height ((double) height); + + switch (height_style) { + case Largest: + xml_node->add_property ("track_height", "largest"); + break; + + case Large: + xml_node->add_property ("track_height", "large"); + break; + + case Larger: + xml_node->add_property ("track_height", "larger"); + break; + + case Normal: + xml_node->add_property ("track_height", "normal"); + break; + + case Smaller: + xml_node->add_property ("track_height", "smaller"); + break; + + case Small: + xml_node->add_property ("track_height", "small"); + break; + } + + switch (height_style) { + case Largest: + case Large: + case Larger: + case Normal: + show_name_entry (); + hide_name_label (); + + mute_button->show_all(); + solo_button->show_all(); + if (rec_enable_button) + rec_enable_button->show_all(); + + edit_group_button.show_all(); + hide_button.show_all(); + visual_button.show_all(); + size_button.show_all(); + automation_button.show_all(); + + if (is_track() && track()->mode() == ARDOUR::Normal) { + playlist_button.show_all(); + } + break; + + case Smaller: + show_name_entry (); + hide_name_label (); + + mute_button->show_all(); + solo_button->show_all(); + if (rec_enable_button) + rec_enable_button->show_all(); + + edit_group_button.hide (); + hide_button.hide (); + visual_button.hide (); + size_button.hide (); + automation_button.hide (); + + if (is_track() && track()->mode() == ARDOUR::Normal) { + playlist_button.hide (); + } + break; + + case Small: + hide_name_entry (); + show_name_label (); + + mute_button->hide(); + solo_button->hide(); + if (rec_enable_button) + rec_enable_button->hide(); + + edit_group_button.hide (); + hide_button.hide (); + visual_button.hide (); + size_button.hide (); + automation_button.hide (); + playlist_button.hide (); + name_label.set_text (_route->name()); + break; + } + + if (height_changed) { + /* only emit the signal if the height really changed */ + _route->gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ + } +} + +void +RouteTimeAxisView::select_track_color () +{ + if (RouteUI::choose_color ()) { + + if (_view) { + _view->apply_color (_color, StreamView::RegionColor); + } + } +} + +void +RouteTimeAxisView::reset_samples_per_unit () +{ + set_samples_per_unit (editor.get_current_zoom()); +} + +void +RouteTimeAxisView::set_samples_per_unit (double spu) +{ + double speed = 1.0; + + if (get_diskstream() != 0) { + speed = get_diskstream()->speed(); + } + + if (_view) { + _view->set_samples_per_unit (spu * speed); + } + + TimeAxisView::set_samples_per_unit (spu * speed); +} + +void +RouteTimeAxisView::align_style_changed () +{ + switch (get_diskstream()->alignment_style()) { + case ExistingMaterial: + if (!align_existing_item->get_active()) { + align_existing_item->set_active(); + } + break; + case CaptureTime: + if (!align_capture_item->get_active()) { + align_capture_item->set_active(); + } + break; + } +} + +void +RouteTimeAxisView::set_align_style (AlignStyle style) +{ + get_diskstream()->set_align_style (style); +} + +void +RouteTimeAxisView::rename_current_playlist () +{ + ArdourPrompter prompter (true); + string name; + + Diskstream *const ds = get_diskstream(); + if (!ds || ds->destructive()) + return; + + Playlist *const pl = ds->playlist(); + if (!pl) + return; + + prompter.set_prompt (_("Name for playlist")); + prompter.set_initial_text (pl->name()); + prompter.add_button (_("Rename"), Gtk::RESPONSE_ACCEPT); + prompter.set_response_sensitive (Gtk::RESPONSE_ACCEPT, false); + + switch (prompter.run ()) { + case Gtk::RESPONSE_ACCEPT: + prompter.get_result (name); + if (name.length()) { + pl->set_name (name); + } + break; + + default: + break; + } +} + +void +RouteTimeAxisView::use_copy_playlist (bool prompt) +{ + string name; + + Diskstream *const ds = get_diskstream(); + if (!ds || ds->destructive()) + return; + + Playlist *const pl = ds->playlist(); + if (!pl) + return; + + name = Playlist::bump_name (pl->name(), _session); + + if (prompt) { + + ArdourPrompter prompter (true); + + prompter.set_prompt (_("Name for Playlist")); + prompter.set_initial_text (name); + prompter.add_button (Gtk::Stock::NEW, Gtk::RESPONSE_ACCEPT); + prompter.set_response_sensitive (Gtk::RESPONSE_ACCEPT, false); + prompter.show_all (); + + switch (prompter.run ()) { + case Gtk::RESPONSE_ACCEPT: + prompter.get_result (name); + break; + + default: + return; + } + } + + if (name.length()) { + ds->use_copy_playlist (); + pl->set_name (name); + } +} + +void +RouteTimeAxisView::use_new_playlist (bool prompt) +{ + string name; + + Diskstream *const ds = get_diskstream(); + if (!ds || ds->destructive()) + return; + + Playlist *const pl = ds->playlist(); + if (!pl) + return; + + name = Playlist::bump_name (pl->name(), _session); + + if (prompt) { + + ArdourPrompter prompter (true); + + prompter.set_prompt (_("Name for Playlist")); + prompter.set_initial_text (name); + prompter.add_button (Gtk::Stock::NEW, Gtk::RESPONSE_ACCEPT); + prompter.set_response_sensitive (Gtk::RESPONSE_ACCEPT, false); + + switch (prompter.run ()) { + case Gtk::RESPONSE_ACCEPT: + prompter.get_result (name); + break; + + default: + return; + } + } + + if (name.length()) { + ds->use_new_playlist (); + pl->set_name (name); + } +} + +void +RouteTimeAxisView::clear_playlist () +{ + Diskstream *const ds = get_diskstream(); + if (!ds || ds->destructive()) + return; + + Playlist *const pl = ds->playlist(); + if (!pl) + return; + + editor.clear_playlist (*pl); +} + +void +RouteTimeAxisView::speed_changed () +{ + Gtkmm2ext::UI::instance()->call_slot (mem_fun(*this, &RouteTimeAxisView::reset_samples_per_unit)); +} + +void +RouteTimeAxisView::diskstream_changed () +{ + Gtkmm2ext::UI::instance()->call_slot (mem_fun(*this, &RouteTimeAxisView::update_diskstream_display)); +} + +void +RouteTimeAxisView::update_diskstream_display () +{ + if (!get_diskstream()) // bus + return; + + set_playlist (get_diskstream()->playlist()); + map_frozen (); +} + +void +RouteTimeAxisView::selection_click (GdkEventButton* ev) +{ + PublicEditor::TrackViewList* tracks = editor.get_valid_views (this, _route->edit_group()); + + switch (Keyboard::selection_type (ev->state)) { + case Selection::Toggle: + /* XXX this is not right */ + editor.get_selection().add (*tracks); + break; + + case Selection::Set: + editor.get_selection().set (*tracks); + break; + + case Selection::Extend: + /* not defined yet */ + break; + } + + delete tracks; +} + +void +RouteTimeAxisView::set_selected_points (PointSelection& points) +{ + for (vector::iterator i = children.begin(); i != children.end(); ++i) { + (*i)->set_selected_points (points); + } +} + +void +RouteTimeAxisView::set_selected_regionviews (RegionSelection& regions) +{ + _view->set_selected_regionviews (regions); +} + +void +RouteTimeAxisView::get_selectables (jack_nframes_t start, jack_nframes_t end, double top, double bot, list& results) +{ + double speed = 1.0; + + if (get_diskstream() != 0) { + speed = get_diskstream()->speed(); + } + + jack_nframes_t start_adjusted = session_frame_to_track_frame(start, speed); + jack_nframes_t end_adjusted = session_frame_to_track_frame(end, speed); + + if (_view && ((top < 0.0 && bot < 0.0)) || touched (top, bot)) { + _view->get_selectables (start_adjusted, end_adjusted, results); + } + + /* pick up visible automation tracks */ + + for (vector::iterator i = children.begin(); i != children.end(); ++i) { + if (!(*i)->hidden()) { + (*i)->get_selectables (start_adjusted, end_adjusted, top, bot, results); + } + } +} + +void +RouteTimeAxisView::get_inverted_selectables (Selection& sel, list& results) +{ + if (_view) { + _view->get_inverted_selectables (sel, results); + } + + for (vector::iterator i = children.begin(); i != children.end(); ++i) { + if (!(*i)->hidden()) { + (*i)->get_inverted_selectables (sel, results); + } + } + + return; +} + +RouteGroup* +RouteTimeAxisView::edit_group() const +{ + return _route->edit_group(); +} + +string +RouteTimeAxisView::name() const +{ + return _route->name(); +} + +Playlist * +RouteTimeAxisView::playlist () const +{ + Diskstream *ds; + + if ((ds = get_diskstream()) != 0) { + return ds->playlist(); + } else { + return 0; + } +} + +void +RouteTimeAxisView::name_entry_changed () +{ + string x; + + x = name_entry.get_text (); + + if (x == _route->name()) { + return; + } + + if (x.length() == 0) { + name_entry.set_text (_route->name()); + return; + } + + strip_whitespace_edges(x); + + if (_session.route_name_unique (x)) { + _route->set_name (x, this); + } else { + ARDOUR_UI::instance()->popup_error (_("a track already exists with that name")); + name_entry.set_text (_route->name()); + } +} + +void +RouteTimeAxisView::visual_click () +{ + popup_display_menu (0); +} + +void +RouteTimeAxisView::hide_click () +{ + editor.hide_track_in_display (*this); +} + +Region* +RouteTimeAxisView::find_next_region (jack_nframes_t pos, RegionPoint point, int32_t dir) +{ + Diskstream *stream; + Playlist *playlist; + + if ((stream = get_diskstream()) != 0 && (playlist = stream->playlist()) != 0) { + return playlist->find_next_region (pos, point, dir); + } + + return 0; +} + +bool +RouteTimeAxisView::cut_copy_clear (Selection& selection, CutCopyOp op) +{ + Playlist* what_we_got; + Diskstream* ds = get_diskstream(); + Playlist* playlist; + bool ret = false; + + if (ds == 0) { + /* route is a bus, not a track */ + return false; + } + + playlist = ds->playlist(); + + + TimeSelection time (selection.time); + float speed = ds->speed(); + if (speed != 1.0f) { + for (TimeSelection::iterator i = time.begin(); i != time.end(); ++i) { + (*i).start = session_frame_to_track_frame((*i).start, speed); + (*i).end = session_frame_to_track_frame((*i).end, speed); + } + } + + switch (op) { + case Cut: + _session.add_undo (playlist->get_memento()); + if ((what_we_got = playlist->cut (time)) != 0) { + editor.get_cut_buffer().add (what_we_got); + _session.add_redo_no_execute (playlist->get_memento()); + ret = true; + } + break; + case Copy: + if ((what_we_got = playlist->copy (time)) != 0) { + editor.get_cut_buffer().add (what_we_got); + } + break; + + case Clear: + _session.add_undo (playlist->get_memento()); + if ((what_we_got = playlist->cut (time)) != 0) { + _session.add_redo_no_execute (playlist->get_memento()); + what_we_got->unref (); + ret = true; + } + break; + } + + return ret; +} + +bool +RouteTimeAxisView::paste (jack_nframes_t pos, float times, Selection& selection, size_t nth) +{ + if (!is_track()) { + return false; + } + + Playlist* playlist = get_diskstream()->playlist(); + PlaylistSelection::iterator p; + + for (p = selection.playlists.begin(); p != selection.playlists.end() && nth; ++p, --nth); + + if (p == selection.playlists.end()) { + return false; + } + + if (get_diskstream()->speed() != 1.0f) + pos = session_frame_to_track_frame(pos, get_diskstream()->speed() ); + + _session.add_undo (playlist->get_memento()); + playlist->paste (**p, pos, times); + _session.add_redo_no_execute (playlist->get_memento()); + + return true; +} + + +list +RouteTimeAxisView::get_child_list() +{ + + listredirect_children; + + for (vector::iterator i = children.begin(); i != children.end(); ++i) { + if (!(*i)->hidden()) { + redirect_children.push_back(*i); + } + } + return redirect_children; +} + + +void +RouteTimeAxisView::build_playlist_menu (Gtk::Menu * menu) +{ + using namespace Menu_Helpers; + + if (!menu || !is_track()) { + return; + } + + MenuList& playlist_items = menu->items(); + menu->set_name ("ArdourContextMenu"); + playlist_items.clear(); + + if (playlist_menu) { + delete playlist_menu; + } + playlist_menu = new Menu; + playlist_menu->set_name ("ArdourContextMenu"); + + playlist_items.push_back (MenuElem (string_compose (_("Current: %1"), get_diskstream()->playlist()->name()))); + playlist_items.push_back (SeparatorElem()); + + playlist_items.push_back (MenuElem (_("Rename"), mem_fun(*this, &RouteTimeAxisView::rename_current_playlist))); + playlist_items.push_back (SeparatorElem()); + + playlist_items.push_back (MenuElem (_("New"), mem_fun(editor, &PublicEditor::new_playlists))); + playlist_items.push_back (MenuElem (_("New Copy"), mem_fun(editor, &PublicEditor::copy_playlists))); + playlist_items.push_back (SeparatorElem()); + playlist_items.push_back (MenuElem (_("Clear Current"), mem_fun(editor, &PublicEditor::clear_playlists))); + playlist_items.push_back (SeparatorElem()); + playlist_items.push_back (MenuElem(_("Select"), mem_fun(*this, &RouteTimeAxisView::show_playlist_selector))); + +} + +void +RouteTimeAxisView::show_playlist_selector () +{ + editor.playlist_selector().show_for (this); +} + +void +RouteTimeAxisView::map_frozen () +{ + if (!is_track()) { + return; + } + + ENSURE_GUI_THREAD (mem_fun(*this, &RouteTimeAxisView::map_frozen)); + + switch (track()->freeze_state()) { + case Track::Frozen: + playlist_button.set_sensitive (false); + rec_enable_button->set_sensitive (false); + break; + default: + playlist_button.set_sensitive (true); + rec_enable_button->set_sensitive (true); + break; + } +} + +void +RouteTimeAxisView::color_handler (ColorID id, uint32_t val) +{ + switch (id) { + case cTimeStretchOutline: + timestretch_rect->property_outline_color_rgba() = val; + break; + case cTimeStretchFill: + timestretch_rect->property_fill_color_rgba() = val; + break; + default: + break; + } +} + +bool +RouteTimeAxisView::select_me (GdkEventButton* ev) +{ + editor.get_selection().add (this); + return false; +} + +void +RouteTimeAxisView::show_all_automation () +{ + no_redraw = true; + + for (list::iterator i = redirect_automation.begin(); i != redirect_automation.end(); ++i) { + for (vector::iterator ii = (*i)->lines.begin(); ii != (*i)->lines.end(); ++ii) { + if ((*ii)->view == 0) { + add_redirect_automation_curve ((*i)->redirect, (*ii)->what); + } + + (*ii)->menu_item->set_active (true); + } + } + + no_redraw = false; + + _route->gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ +} + +void +RouteTimeAxisView::show_existing_automation () +{ + no_redraw = true; + + for (list::iterator i = redirect_automation.begin(); i != redirect_automation.end(); ++i) { + for (vector::iterator ii = (*i)->lines.begin(); ii != (*i)->lines.end(); ++ii) { + if ((*ii)->view != 0) { + (*ii)->menu_item->set_active (true); + } + } + } + + no_redraw = false; + + _route->gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ +} + +void +RouteTimeAxisView::hide_all_automation () +{ + no_redraw = true; + + for (list::iterator i = redirect_automation.begin(); i != redirect_automation.end(); ++i) { + for (vector::iterator ii = (*i)->lines.begin(); ii != (*i)->lines.end(); ++ii) { + (*ii)->menu_item->set_active (false); + } + } + + no_redraw = false; + _route->gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ +} + + +void +RouteTimeAxisView::region_view_added (RegionView* rv) +{ + for (vector::iterator i = children.begin(); i != children.end(); ++i) { + AutomationTimeAxisView* atv; + + if ((atv = dynamic_cast (*i)) != 0) { + rv->add_ghost (*atv); + } + } +} + +void +RouteTimeAxisView::add_ghost_to_redirect (RegionView* rv, AutomationTimeAxisView* atv) +{ + rv->add_ghost (*atv); +} + +RouteTimeAxisView::RedirectAutomationInfo::~RedirectAutomationInfo () +{ + for (vector::iterator i = lines.begin(); i != lines.end(); ++i) { + delete *i; + } +} + + +RouteTimeAxisView::RedirectAutomationNode::~RedirectAutomationNode () +{ + parent.remove_ran (this); + + if (view) { + delete view; + } +} + +void +RouteTimeAxisView::remove_ran (RedirectAutomationNode* ran) +{ + if (ran->view) { + remove_child (ran->view); + } +} + +RouteTimeAxisView::RedirectAutomationNode* +RouteTimeAxisView::find_redirect_automation_node (boost::shared_ptr redirect, uint32_t what) +{ + for (list::iterator i = redirect_automation.begin(); i != redirect_automation.end(); ++i) { + + if ((*i)->redirect == redirect) { + + for (vector::iterator ii = (*i)->lines.begin(); ii != (*i)->lines.end(); ++ii) { + if ((*ii)->what == what) { + return *ii; + } + } + } + } + + return 0; +} + +// FIXME: duplicated in midi_time_axis.cc +static string +legalize_for_xml_node (string str) +{ + string::size_type pos; + string legal_chars = "abcdefghijklmnopqrtsuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789_+=:"; + string legal; + + legal = str; + pos = 0; + + while ((pos = legal.find_first_not_of (legal_chars, pos)) != string::npos) { + legal.replace (pos, 1, "_"); + pos += 1; + } + + return legal; +} + + +void +RouteTimeAxisView::add_redirect_automation_curve (boost::shared_ptr redirect, uint32_t what) +{ + RedirectAutomationLine* ral; + string name; + RedirectAutomationNode* ran; + + if ((ran = find_redirect_automation_node (redirect, what)) == 0) { + fatal << _("programming error: ") + << string_compose (X_("redirect automation curve for %1:%2 not registered with audio track!"), + redirect->name(), what) + << endmsg; + /*NOTREACHED*/ + return; + } + + if (ran->view) { + return; + } + + name = redirect->describe_parameter (what); + + /* create a string that is a legal XML node name that can be used to refer to this redirect+port combination */ + + char state_name[256]; + snprintf (state_name, sizeof (state_name), "Redirect-%s-%" PRIu32, legalize_for_xml_node (redirect->name()).c_str(), what); + + ran->view = new RedirectAutomationTimeAxisView (_session, _route, editor, *this, parent_canvas, name, what, *redirect, state_name); + + ral = new RedirectAutomationLine (name, + *redirect, what, _session, *ran->view, + *ran->view->canvas_display, redirect->automation_list (what)); + + ral->set_line_color (color_map[cRedirectAutomationLine]); + ral->queue_reset (); + + ran->view->add_line (*ral); + + ran->view->Hiding.connect (bind (mem_fun(*this, &RouteTimeAxisView::redirect_automation_track_hidden), ran, redirect)); + + if (!ran->view->marked_for_display()) { + ran->view->hide (); + } else { + ran->menu_item->set_active (true); + } + + add_child (ran->view); + + _view->foreach_regionview (bind (mem_fun(*this, &RouteTimeAxisView::add_ghost_to_redirect), ran->view)); + + redirect->mark_automation_visible (what, true); +} + +void +RouteTimeAxisView::redirect_automation_track_hidden (RouteTimeAxisView::RedirectAutomationNode* ran, boost::shared_ptr r) +{ + if (!_hidden) { + ran->menu_item->set_active (false); + } + + r->mark_automation_visible (ran->what, false); + + _route->gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ +} + +void +RouteTimeAxisView::add_existing_redirect_automation_curves (boost::shared_ptr redirect) +{ + set s; + RedirectAutomationLine *ral; + + redirect->what_has_visible_automation (s); + + for (set::iterator i = s.begin(); i != s.end(); ++i) { + + if ((ral = find_redirect_automation_curve (redirect, *i)) != 0) { + ral->queue_reset (); + } else { + add_redirect_automation_curve (redirect, (*i)); + } + } +} + +void +RouteTimeAxisView::add_redirect_to_subplugin_menu (boost::shared_ptr r) +{ + using namespace Menu_Helpers; + RedirectAutomationInfo *rai; + list::iterator x; + + const std::set& automatable = r->what_can_be_automated (); + std::set has_visible_automation; + + r->what_has_visible_automation(has_visible_automation); + + if (automatable.empty()) { + return; + } + + for (x = redirect_automation.begin(); x != redirect_automation.end(); ++x) { + if ((*x)->redirect == r) { + break; + } + } + + if (x == redirect_automation.end()) { + + rai = new RedirectAutomationInfo (r); + redirect_automation.push_back (rai); + + } else { + + rai = *x; + + } + + /* any older menu was deleted at the top of redirects_changed() + when we cleared the subplugin menu. + */ + + rai->menu = manage (new Menu); + MenuList& items = rai->menu->items(); + rai->menu->set_name ("ArdourContextMenu"); + + items.clear (); + + for (std::set::const_iterator i = automatable.begin(); i != automatable.end(); ++i) { + + RedirectAutomationNode* ran; + CheckMenuItem* mitem; + + string name = r->describe_parameter (*i); + + items.push_back (CheckMenuElem (name)); + mitem = dynamic_cast (&items.back()); + + if (has_visible_automation.find((*i)) != has_visible_automation.end()) { + mitem->set_active(true); + } + + if ((ran = find_redirect_automation_node (r, *i)) == 0) { + + /* new item */ + + ran = new RedirectAutomationNode (*i, mitem, *this); + + rai->lines.push_back (ran); + + } else { + + ran->menu_item = mitem; + + } + + mitem->signal_toggled().connect (bind (mem_fun(*this, &RouteTimeAxisView::redirect_menu_item_toggled), rai, ran)); + } + + /* add the menu for this redirect, because the subplugin + menu is always cleared at the top of redirects_changed(). + this is the result of some poor design in gtkmm and/or + GTK+. + */ + + subplugin_menu.items().push_back (MenuElem (r->name(), *rai->menu)); + rai->valid = true; +} + +void +RouteTimeAxisView::redirect_menu_item_toggled (RouteTimeAxisView::RedirectAutomationInfo* rai, + RouteTimeAxisView::RedirectAutomationNode* ran) +{ + bool showit = ran->menu_item->get_active(); + bool redraw = false; + + if (ran->view == 0 && showit) { + add_redirect_automation_curve (rai->redirect, ran->what); + redraw = true; + } + + if (showit != ran->view->marked_for_display()) { + + if (showit) { + ran->view->set_marked_for_display (true); + ran->view->canvas_display->show(); + } else { + rai->redirect->mark_automation_visible (ran->what, true); + ran->view->set_marked_for_display (false); + ran->view->hide (); + } + + redraw = true; + + } + + if (redraw && !no_redraw) { + + /* now trigger a redisplay */ + + _route->gui_changed ("track_height", (void *) 0); /* EMIT_SIGNAL */ + + } +} + +void +RouteTimeAxisView::redirects_changed (void *src) +{ + using namespace Menu_Helpers; + + for (list::iterator i = redirect_automation.begin(); i != redirect_automation.end(); ++i) { + (*i)->valid = false; + } + + subplugin_menu.items().clear (); + + _route->foreach_redirect (this, &RouteTimeAxisView::add_redirect_to_subplugin_menu); + _route->foreach_redirect (this, &RouteTimeAxisView::add_existing_redirect_automation_curves); + + for (list::iterator i = redirect_automation.begin(); i != redirect_automation.end(); ) { + + list::iterator tmp; + + tmp = i; + ++tmp; + + if (!(*i)->valid) { + + delete *i; + redirect_automation.erase (i); + + } + + i = tmp; + } + + /* change in visibility was possible */ + + _route->gui_changed ("track_height", this); +} + +RedirectAutomationLine * +RouteTimeAxisView::find_redirect_automation_curve (boost::shared_ptr redirect, uint32_t what) +{ + RedirectAutomationNode* ran; + + if ((ran = find_redirect_automation_node (redirect, what)) != 0) { + if (ran->view) { + return dynamic_cast (ran->view->lines.front()); + } + } + + return 0; +} + +void +RouteTimeAxisView::reset_redirect_automation_curves () +{ + for (vector::iterator i = redirect_automation_curves.begin(); i != redirect_automation_curves.end(); ++i) { + (*i)->reset(); + } +} + diff --git a/gtk2_ardour/route_time_axis.h b/gtk2_ardour/route_time_axis.h new file mode 100644 index 0000000000..d305fd390c --- /dev/null +++ b/gtk2_ardour/route_time_axis.h @@ -0,0 +1,256 @@ +/* + Copyright (C) 2006 Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + + $Id: audio_time_axis.h 664 2006-07-05 19:47:25Z drobilla $ +*/ + +#ifndef __ardour_route_time_axis_h__ +#define __ardour_route_time_axis_h__ + +#include +#include +#include +#include +#include +#include +#include + +#include +#include + +#include + +#include "ardour_dialog.h" +#include "route_ui.h" +#include "enums.h" +#include "time_axis_view.h" +#include "canvas.h" +#include "color.h" + +namespace ARDOUR { + class Session; + class Region; + class Diskstream; + class RouteGroup; + class Redirect; + class Insert; + class Location; + class Playlist; +} + +class PublicEditor; +class RegionView; +class StreamView; +class Selection; +class RegionSelection; +class Selectable; +class AutomationTimeAxisView; +class AutomationLine; +class RedirectAutomationLine; +class TimeSelection; + +class RouteTimeAxisView : public RouteUI, public TimeAxisView +{ +public: + RouteTimeAxisView (PublicEditor&, ARDOUR::Session&, boost::shared_ptr, ArdourCanvas::Canvas& canvas); + virtual ~RouteTimeAxisView (); + + void show_selection (TimeSelection&); + + void set_samples_per_unit (double); + void set_height (TimeAxisView::TrackHeight); + void show_timestretch (jack_nframes_t start, jack_nframes_t end); + void hide_timestretch (); + void selection_click (GdkEventButton*); + void set_selected_points (PointSelection&); + void set_selected_regionviews (RegionSelection&); + void get_selectables (jack_nframes_t start, jack_nframes_t end, double top, double bot, list&); + void get_inverted_selectables (Selection&, list&); + + ARDOUR::Region* find_next_region (jack_nframes_t pos, ARDOUR::RegionPoint, int32_t dir); + + /* Editing operations */ + bool cut_copy_clear (Selection&, Editing::CutCopyOp); + bool paste (jack_nframes_t, float times, Selection&, size_t nth); + + list get_child_list(); + + /* The editor calls these when mapping an operation across multiple tracks */ + void use_new_playlist (bool prompt); + void use_copy_playlist (bool prompt); + void clear_playlist (); + + void build_playlist_menu (Gtk::Menu *); + + string name() const; + StreamView* view() const { return _view; } + ARDOUR::RouteGroup* edit_group() const; + ARDOUR::Playlist* playlist() const; + +protected: + friend class StreamView; + + struct RedirectAutomationNode { + uint32_t what; + Gtk::CheckMenuItem* menu_item; + AutomationTimeAxisView* view; + RouteTimeAxisView& parent; + + RedirectAutomationNode (uint32_t w, Gtk::CheckMenuItem* mitem, RouteTimeAxisView& p) + : what (w), menu_item (mitem), view (0), parent (p) {} + + ~RedirectAutomationNode (); + }; + + struct RedirectAutomationInfo { + boost::shared_ptr redirect; + bool valid; + Gtk::Menu* menu; + vector lines; + + RedirectAutomationInfo (boost::shared_ptr r) + : redirect (r), valid (true), menu (0) {} + + ~RedirectAutomationInfo (); + }; + + + void diskstream_changed (); + void update_diskstream_display (); + + gint edit_click (GdkEventButton *); + + void build_redirect_window (); + void redirect_click (); + void redirect_add (); + void redirect_remove (); + void redirect_edit (); + void redirect_relist (); + void redirect_row_selected (gint row, gint col, GdkEvent *ev); + void add_to_redirect_display (ARDOUR::Redirect *); + void redirects_changed (void *); + + void add_redirect_to_subplugin_menu (boost::shared_ptr); + void remove_ran (RedirectAutomationNode* ran); + + void redirect_menu_item_toggled (RouteTimeAxisView::RedirectAutomationInfo*, + RouteTimeAxisView::RedirectAutomationNode*); + + void redirect_automation_track_hidden (RedirectAutomationNode*, + boost::shared_ptr); + + RedirectAutomationNode* + find_redirect_automation_node (boost::shared_ptr r, uint32_t); + + RedirectAutomationLine* + find_redirect_automation_curve (boost::shared_ptr r, uint32_t); + + void add_redirect_automation_curve (boost::shared_ptr r, uint32_t); + void add_existing_redirect_automation_curves (boost::shared_ptr); + + void reset_redirect_automation_curves (); + + void update_automation_view (ARDOUR::AutomationType); + + void take_name_changed (void *); + void route_name_changed (void *); + void name_entry_changed (); + + void on_area_realize (); + + virtual void label_view (); + + void add_edit_group_menu_item (ARDOUR::RouteGroup *, Gtk::RadioMenuItem::Group*); + void set_edit_group_from_menu (ARDOUR::RouteGroup *); + + void reset_samples_per_unit (); + + void select_track_color(); + + virtual void build_automation_action_menu (); + virtual void append_extra_display_menu_items () {} + void build_display_menu (); + + void align_style_changed (); + void set_align_style (ARDOUR::AlignStyle); + + virtual void set_playlist (ARDOUR::Playlist *); + void playlist_click (); + void show_playlist_selector (); + void playlist_changed (); + void playlist_state_changed (ARDOUR::Change); + void playlist_modified (); + + void add_playlist_to_playlist_menu (ARDOUR::Playlist*); + void rename_current_playlist (); + + void automation_click (); + virtual void show_all_automation (); + virtual void show_existing_automation (); + virtual void hide_all_automation (); + + void timestretch (jack_nframes_t start, jack_nframes_t end); + + void visual_click (); + void hide_click (); + gint when_displayed (GdkEventAny*); + + void speed_changed (); + + void map_frozen (); + + void color_handler (ColorID, uint32_t); + bool select_me (GdkEventButton*); + + void region_view_added (RegionView*); + void add_ghost_to_redirect (RegionView*, AutomationTimeAxisView*); + + + StreamView* _view; + ArdourCanvas::Canvas& parent_canvas; + bool no_redraw; + + Gtk::HBox other_button_hbox; + Gtk::Table button_table; + Gtk::Button redirect_button; + Gtk::Button edit_group_button; + Gtk::Button playlist_button; + Gtk::Button size_button; + Gtk::Button automation_button; + Gtk::Button hide_button; + Gtk::Button visual_button; + + Gtk::Menu subplugin_menu; + Gtk::Menu* automation_action_menu; + Gtk::Menu edit_group_menu; + Gtk::RadioMenuItem* align_existing_item; + Gtk::RadioMenuItem* align_capture_item; + Gtk::Menu* playlist_menu; + Gtk::Menu* playlist_action_menu; + Gtk::MenuItem* playlist_item; + + ArdourCanvas::SimpleRect* timestretch_rect; + + list redirect_automation; + vector redirect_automation_curves; + + sigc::connection modified_connection; + sigc::connection state_changed_connection; +}; + +#endif /* __ardour_route_time_axis_h__ */ + diff --git a/gtk2_ardour/route_ui.cc b/gtk2_ardour/route_ui.cc index 988d6c8b19..8a1fb1c21a 100644 --- a/gtk2_ardour/route_ui.cc +++ b/gtk2_ardour/route_ui.cc @@ -1,5 +1,5 @@ /* - Copyright (C) 2002 Paul Davis + Copyright (C) 2002-2006 Paul Davis This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -21,8 +21,8 @@ #include #include #include -#include #include +#include #include #include @@ -45,9 +45,9 @@ using namespace ARDOUR; using namespace PBD; -RouteUI::RouteUI (ARDOUR::Route& rt, ARDOUR::Session& sess, const char* m_name, +RouteUI::RouteUI (boost::shared_ptr rt, ARDOUR::Session& sess, const char* m_name, const char* s_name, const char* r_name) - : AxisView(sess), + : AxisView(sess), _route(rt), mute_button(0), solo_button(0), @@ -65,35 +65,31 @@ RouteUI::RouteUI (ARDOUR::Route& rt, ARDOUR::Session& sess, const char* m_name, set_color (unique_random_color()); } - _route.GoingAway.connect (mem_fun (*this, &RouteUI::route_removed)); - _route.active_changed.connect (mem_fun (*this, &RouteUI::route_active_changed)); + _route->GoingAway.connect (mem_fun (*this, &RouteUI::route_removed)); + _route->active_changed.connect (mem_fun (*this, &RouteUI::route_active_changed)); - mute_button = manage (new BindableToggleButton (& _route.midi_mute_control(), m_name )); - mute_button->set_bind_button_state (2, GDK_CONTROL_MASK); - solo_button = manage (new BindableToggleButton (& _route.midi_solo_control(), s_name )); - solo_button->set_bind_button_state (2, GDK_CONTROL_MASK); + mute_button = manage (new BindableToggleButton (_route->mute_control(), m_name )); + solo_button = manage (new BindableToggleButton (_route->solo_control(), s_name )); + + if (is_track()) { + boost::shared_ptr t = boost::dynamic_pointer_cast(_route); - if (is_audio_track()) { - AudioTrack* at = dynamic_cast(&_route); - - get_diskstream()->record_enable_changed.connect (mem_fun (*this, &RouteUI::route_rec_enable_changed)); + t->diskstream().RecordEnableChanged.connect (mem_fun (*this, &RouteUI::route_rec_enable_changed)); _session.RecordStateChanged.connect (mem_fun (*this, &RouteUI::session_rec_enable_changed)); - rec_enable_button = manage (new BindableToggleButton (& at->midi_rec_enable_control(), r_name )); - rec_enable_button->set_bind_button_state (2, GDK_CONTROL_MASK); + rec_enable_button = manage (new BindableToggleButton (t->rec_enable_control(), r_name )); - } else { - rec_enable_button = manage (new BindableToggleButton (0, r_name )); - } + rec_enable_button->unset_flags (Gtk::CAN_FOCUS); + + update_rec_display (); + } mute_button->unset_flags (Gtk::CAN_FOCUS); solo_button->unset_flags (Gtk::CAN_FOCUS); - rec_enable_button->unset_flags (Gtk::CAN_FOCUS); /* map the current state */ - update_rec_display (); map_frozen (); } @@ -146,14 +142,14 @@ RouteUI::mute_press(GdkEventButton* ev) */ if (ev->button == 1) { - set_mix_group_mute (_route, !_route.muted()); + set_mix_group_mute (_route, !_route->muted()); } } else { /* plain click applies change to this route */ - reversibly_apply_route_boolean ("mute change", &Route::set_mute, !_route.muted(), this); + reversibly_apply_route_boolean ("mute change", &Route::set_mute, !_route->muted(), this); } } } @@ -231,7 +227,7 @@ RouteUI::solo_press(GdkEventButton* ev) // shift-click: set this route to solo safe - _route.set_solo_safe (!_route.solo_safe(), this); + _route->set_solo_safe (!_route->solo_safe(), this); wait_for_release = false; } else if (Keyboard::modifier_state_equals (ev->state, Keyboard::Control)) { @@ -241,14 +237,14 @@ RouteUI::solo_press(GdkEventButton* ev) */ if (ev->button == 1) { - set_mix_group_solo (_route, !_route.soloed()); + set_mix_group_solo (_route, !_route->soloed()); } } else { /* click: solo this route */ - reversibly_apply_route_boolean ("solo change", &Route::set_solo, !_route.soloed(), this); + reversibly_apply_route_boolean ("solo change", &Route::set_solo, !_route->soloed(), this); } } } @@ -276,7 +272,7 @@ RouteUI::solo_release(GdkEventButton* ev) gint RouteUI::rec_enable_press(GdkEventButton* ev) { - if (!ignore_toggle && is_audio_track()) { + if (!ignore_toggle && is_track() && rec_enable_button) { if (ev->button == 2 && Keyboard::modifier_state_equals (ev->state, Keyboard::Control)) { // do nothing on midi bind event @@ -298,7 +294,7 @@ RouteUI::rec_enable_press(GdkEventButton* ev) } else if (Keyboard::modifier_state_equals (ev->state, Keyboard::Control)) { - set_mix_group_rec_enable (_route, !_route.record_enabled()); + set_mix_group_rec_enable (_route, !_route->record_enabled()); } else { @@ -326,7 +322,7 @@ RouteUI::update_solo_display () { bool x; - if (solo_button->get_active() != (x = _route.soloed())){ + if (solo_button->get_active() != (x = _route->soloed())){ ignore_toggle = true; solo_button->set_active(x); ignore_toggle = false; @@ -334,7 +330,7 @@ RouteUI::update_solo_display () /* show solo safe */ - if (_route.solo_safe()){ + if (_route->solo_safe()){ solo_button->set_name(safe_solo_button_name()); } else { solo_button->set_name(solo_button_name()); @@ -352,7 +348,7 @@ RouteUI::update_mute_display () { bool x; - if (mute_button->get_active() != (x = _route.muted())){ + if (mute_button->get_active() != (x = _route->muted())){ ignore_toggle = true; mute_button->set_active(x); ignore_toggle = false; @@ -360,7 +356,7 @@ RouteUI::update_mute_display () } void -RouteUI::route_rec_enable_changed (void *src) +RouteUI::route_rec_enable_changed () { Gtkmm2ext::UI::instance()->call_slot (mem_fun (*this, &RouteUI::update_rec_display)); } @@ -374,7 +370,7 @@ RouteUI::session_rec_enable_changed () void RouteUI::update_rec_display () { - bool model = _route.record_enabled(); + bool model = _route->record_enabled(); bool view = rec_enable_button->get_active(); /* first make sure the button's "depressed" visual @@ -440,7 +436,7 @@ RouteUI::refresh_remote_control_menu () limit += 4; /* leave some breathing room */ rc_items.push_back (RadioMenuElem (rc_group, _("None"))); - if (_route.remote_control_id() == 0) { + if (_route->remote_control_id() == 0) { rc_active = dynamic_cast (&rc_items.back()); rc_active->set_active (); } @@ -449,7 +445,7 @@ RouteUI::refresh_remote_control_menu () snprintf (buf, sizeof (buf), "%u", i); rc_items.push_back (RadioMenuElem (rc_group, buf)); rc_active = dynamic_cast(&rc_items.back()); - if (_route.remote_control_id() == i) { + if (_route->remote_control_id() == i) { rc_active = dynamic_cast (&rc_items.back()); rc_active->set_active (); } @@ -467,7 +463,7 @@ RouteUI::set_remote_control_id (uint32_t id, CheckMenuItem* item) */ if (item->get_active()) { - _route.set_remote_control_id (id); + _route->set_remote_control_id (id); } } @@ -482,14 +478,14 @@ RouteUI::build_solo_menu (void) CheckMenuItem* check; check = new CheckMenuItem(_("Solo-safe")); - check->set_active (_route.solo_safe()); + check->set_active (_route->solo_safe()); check->signal_toggled().connect (bind (mem_fun (*this, &RouteUI::toggle_solo_safe), check)); - _route.solo_safe_changed.connect(bind (mem_fun (*this, &RouteUI::solo_safe_toggle), check)); + _route->solo_safe_changed.connect(bind (mem_fun (*this, &RouteUI::solo_safe_toggle), check)); items.push_back (CheckMenuElem(*check)); check->show_all(); items.push_back (SeparatorElem()); - items.push_back (MenuElem (_("MIDI Bind"), mem_fun (*mute_button, &BindableToggleButton::midi_learn))); + // items.push_back (MenuElem (_("MIDI Bind"), mem_fun (*mute_button, &BindableToggleButton::midi_learn))); } @@ -506,39 +502,39 @@ RouteUI::build_mute_menu(void) check = new CheckMenuItem(_("Pre Fader")); init_mute_menu(PRE_FADER, check); check->signal_toggled().connect(bind (mem_fun (*this, &RouteUI::toggle_mute_menu), PRE_FADER, check)); - _route.pre_fader_changed.connect(bind (mem_fun (*this, &RouteUI::pre_fader_toggle), check)); + _route->pre_fader_changed.connect(bind (mem_fun (*this, &RouteUI::pre_fader_toggle), check)); items.push_back (CheckMenuElem(*check)); check->show_all(); check = new CheckMenuItem(_("Post Fader")); init_mute_menu(POST_FADER, check); check->signal_toggled().connect(bind (mem_fun (*this, &RouteUI::toggle_mute_menu), POST_FADER, check)); - _route.post_fader_changed.connect(bind (mem_fun (*this, &RouteUI::post_fader_toggle), check)); + _route->post_fader_changed.connect(bind (mem_fun (*this, &RouteUI::post_fader_toggle), check)); items.push_back (CheckMenuElem(*check)); check->show_all(); check = new CheckMenuItem(_("Control Outs")); init_mute_menu(CONTROL_OUTS, check); check->signal_toggled().connect(bind (mem_fun (*this, &RouteUI::toggle_mute_menu), CONTROL_OUTS, check)); - _route.control_outs_changed.connect(bind (mem_fun (*this, &RouteUI::control_outs_toggle), check)); + _route->control_outs_changed.connect(bind (mem_fun (*this, &RouteUI::control_outs_toggle), check)); items.push_back (CheckMenuElem(*check)); check->show_all(); check = new CheckMenuItem(_("Main Outs")); init_mute_menu(MAIN_OUTS, check); check->signal_toggled().connect(bind (mem_fun (*this, &RouteUI::toggle_mute_menu), MAIN_OUTS, check)); - _route.main_outs_changed.connect(bind (mem_fun (*this, &RouteUI::main_outs_toggle), check)); + _route->main_outs_changed.connect(bind (mem_fun (*this, &RouteUI::main_outs_toggle), check)); items.push_back (CheckMenuElem(*check)); check->show_all(); items.push_back (SeparatorElem()); - items.push_back (MenuElem (_("MIDI Bind"), mem_fun (*mute_button, &BindableToggleButton::midi_learn))); + // items.push_back (MenuElem (_("MIDI Bind"), mem_fun (*mute_button, &BindableToggleButton::midi_learn))); } void RouteUI::init_mute_menu(mute_type type, CheckMenuItem* check) { - if (_route.get_mute_config (type)) { + if (_route->get_mute_config (type)) { check->set_active (true); } } @@ -546,21 +542,21 @@ RouteUI::init_mute_menu(mute_type type, CheckMenuItem* check) void RouteUI::toggle_mute_menu(mute_type type, Gtk::CheckMenuItem* check) { - _route.set_mute_config(type, check->get_active(), this); + _route->set_mute_config(type, check->get_active(), this); } void RouteUI::toggle_solo_safe (Gtk::CheckMenuItem* check) { - _route.set_solo_safe (check->get_active(), this); + _route->set_solo_safe (check->get_active(), this); } void -RouteUI::set_mix_group_solo(Route& route, bool yn) +RouteUI::set_mix_group_solo(boost::shared_ptr route, bool yn) { RouteGroup* mix_group; - if((mix_group = route.mix_group()) != 0){ + if((mix_group = route->mix_group()) != 0){ _session.begin_reversible_command (_("mix group solo change")); Session::GlobalSoloStateCommand *cmd = new Session::GlobalSoloStateCommand(_session, this); mix_group->apply(&Route::set_solo, yn, this); @@ -568,7 +564,7 @@ RouteUI::set_mix_group_solo(Route& route, bool yn) _session.add_command (cmd); _session.commit_reversible_command (); } else { - reversibly_apply_route_boolean ("solo change", &Route::set_solo, !route.soloed(), this); + reversibly_apply_route_boolean ("solo change", &Route::set_solo, !route->soloed(), this); } } @@ -595,11 +591,11 @@ RouteUI::reversibly_apply_audio_track_boolean (string name, void (AudioTrack::*f } void -RouteUI::set_mix_group_mute(Route& route, bool yn) +RouteUI::set_mix_group_mute(boost::shared_ptr route, bool yn) { RouteGroup* mix_group; - if((mix_group = route.mix_group()) != 0){ + if((mix_group = route->mix_group()) != 0){ _session.begin_reversible_command (_("mix group mute change")); Session::GlobalMuteStateCommand *cmd = new Session::GlobalMuteStateCommand (_session, this); mix_group->apply(&Route::set_mute, yn, this); @@ -607,16 +603,16 @@ RouteUI::set_mix_group_mute(Route& route, bool yn) _session.add_command(cmd); _session.commit_reversible_command (); } else { - reversibly_apply_route_boolean ("mute change", &Route::set_mute, !route.muted(), this); + reversibly_apply_route_boolean ("mute change", &Route::set_mute, !route->muted(), this); } } void -RouteUI::set_mix_group_rec_enable(Route& route, bool yn) +RouteUI::set_mix_group_rec_enable(boost::shared_ptr route, bool yn) { RouteGroup* mix_group; - if((mix_group = route.mix_group()) != 0){ + if((mix_group = route->mix_group()) != 0){ _session.begin_reversible_command (_("mix group rec-enable change")); Session::GlobalRecordEnableStateCommand *cmd = new Session::GlobalRecordEnableStateCommand(_session, this); mix_group->apply (&Route::set_record_enable, yn, this); @@ -624,7 +620,7 @@ RouteUI::set_mix_group_rec_enable(Route& route, bool yn) _session.add_command(cmd); _session.commit_reversible_command (); } else { - reversibly_apply_route_boolean ("rec-enable change", &Route::set_record_enable, !_route.record_enabled(), this); + reversibly_apply_route_boolean ("rec-enable change", &Route::set_record_enable, !_route->record_enabled(), this); } } @@ -655,7 +651,7 @@ RouteUI::set_color (const Gdk::Color & c) snprintf (buf, sizeof (buf), "%d:%d:%d", c.get_red(), c.get_green(), c.get_blue()); xml_node->add_property ("color", buf); - _route.gui_changed ("color", (void *) 0); /* EMIT_SIGNAL */ + _route->gui_changed ("color", (void *) 0); /* EMIT_SIGNAL */ } @@ -663,9 +659,9 @@ void RouteUI::ensure_xml_node () { if (xml_node == 0) { - if ((xml_node = _route.extra_xml ("GUI")) == 0) { + if ((xml_node = _route->extra_xml ("GUI")) == 0) { xml_node = new XMLNode ("GUI"); - _route.add_extra_xml (*xml_node); + _route->add_extra_xml (*xml_node); } } } @@ -710,10 +706,10 @@ RouteUI::remove_this_route () vector choices; string prompt; - if (is_audio_track()) { - prompt = string_compose (_("Do you really want to remove track \"%1\" ?\n\nYou may also lose the playlist used by this track.\n(cannot be undone)"), _route.name()); + if (is_track()) { + prompt = string_compose (_("Do you really want to remove track \"%1\" ?\n\nYou may also lose the playlist used by this track.\n(cannot be undone)"), _route->name()); } else { - prompt = string_compose (_("Do you really want to remove bus \"%1\" ?\n(cannot be undone)"), _route.name()); + prompt = string_compose (_("Do you really want to remove bus \"%1\" ?\n(cannot be undone)"), _route->name()); } choices.push_back (_("No, do nothing.")); @@ -747,7 +743,7 @@ RouteUI::route_rename () ArdourPrompter name_prompter (true); string result; name_prompter.set_prompt (_("New Name: ")); - name_prompter.set_initial_text (_route.name()); + name_prompter.set_initial_text (_route->name()); name_prompter.add_button (_("Rename"), Gtk::RESPONSE_ACCEPT); name_prompter.set_response_sensitive (Gtk::RESPONSE_ACCEPT, false); name_prompter.show_all (); @@ -757,7 +753,7 @@ RouteUI::route_rename () case Gtk::RESPONSE_ACCEPT: name_prompter.get_result (result); if (result.length()) { - _route.set_name (result, this); + _route->set_name (result, this); } break; } @@ -771,7 +767,7 @@ RouteUI::name_changed (void *src) { ENSURE_GUI_THREAD(bind (mem_fun (*this, &RouteUI::name_changed), src)); - name_label.set_text (_route.name()); + name_label.set_text (_route->name()); } void @@ -780,8 +776,8 @@ RouteUI::toggle_route_active () bool yn; if (route_active_menu_item) { - if (route_active_menu_item->get_active() != (yn = _route.active())) { - _route.set_active (!yn); + if (route_active_menu_item->get_active() != (yn = _route->active())) { + _route->set_active (!yn); } } } @@ -790,7 +786,7 @@ void RouteUI::route_active_changed () { if (route_active_menu_item) { - Gtkmm2ext::UI::instance()->call_slot (bind (mem_fun (*route_active_menu_item, &CheckMenuItem::set_active), _route.active())); + Gtkmm2ext::UI::instance()->call_slot (bind (mem_fun (*route_active_menu_item, &CheckMenuItem::set_active), _route->active())); } } @@ -803,12 +799,12 @@ RouteUI::toggle_polarity () ENSURE_GUI_THREAD(mem_fun (*this, &RouteUI::toggle_polarity)); - if ((x = polarity_menu_item->get_active()) != _route.phase_invert()) { - _route.set_phase_invert (x, this); + if ((x = polarity_menu_item->get_active()) != _route->phase_invert()) { + _route->set_phase_invert (x, this); if (x) { name_label.set_text (X_("Ø ") + name_label.get_text()); } else { - name_label.set_text (_route.name()); + name_label.set_text (_route->name()); } } } @@ -823,7 +819,7 @@ RouteUI::polarity_changed () void RouteUI::solo_safe_toggle(void* src, Gtk::CheckMenuItem* check) { - bool yn = _route.solo_safe (); + bool yn = _route->solo_safe (); if (check->get_active() != yn) { check->set_active (yn); @@ -834,7 +830,7 @@ RouteUI::pre_fader_toggle(void* src, Gtk::CheckMenuItem* check) { ENSURE_GUI_THREAD(bind (mem_fun (*this, &RouteUI::pre_fader_toggle), src, check)); - bool yn = _route.get_mute_config(PRE_FADER); + bool yn = _route->get_mute_config(PRE_FADER); if (check->get_active() != yn) { check->set_active (yn); } @@ -845,7 +841,7 @@ RouteUI::post_fader_toggle(void* src, Gtk::CheckMenuItem* check) { ENSURE_GUI_THREAD(bind (mem_fun (*this, &RouteUI::post_fader_toggle), src, check)); - bool yn = _route.get_mute_config(POST_FADER); + bool yn = _route->get_mute_config(POST_FADER); if (check->get_active() != yn) { check->set_active (yn); } @@ -856,7 +852,7 @@ RouteUI::control_outs_toggle(void* src, Gtk::CheckMenuItem* check) { ENSURE_GUI_THREAD(bind (mem_fun (*this, &RouteUI::control_outs_toggle), src, check)); - bool yn = _route.get_mute_config(CONTROL_OUTS); + bool yn = _route->get_mute_config(CONTROL_OUTS); if (check->get_active() != yn) { check->set_active (yn); } @@ -867,7 +863,7 @@ RouteUI::main_outs_toggle(void* src, Gtk::CheckMenuItem* check) { ENSURE_GUI_THREAD(bind (mem_fun (*this, &RouteUI::main_outs_toggle), src, check)); - bool yn = _route.get_mute_config(MAIN_OUTS); + bool yn = _route->get_mute_config(MAIN_OUTS); if (check->get_active() != yn) { check->set_active (yn); } @@ -876,42 +872,55 @@ RouteUI::main_outs_toggle(void* src, Gtk::CheckMenuItem* check) void RouteUI::disconnect_input () { - _route.disconnect_inputs (this); + _route->disconnect_inputs (this); } void RouteUI::disconnect_output () { - _route.disconnect_outputs (this); + _route->disconnect_outputs (this); +} + +bool +RouteUI::is_track () const +{ + return dynamic_cast(_route.get()) != 0; +} + +Track* +RouteUI::track() const +{ + return dynamic_cast(_route.get()); } bool RouteUI::is_audio_track () const { - return dynamic_cast(&_route) != 0; -} - -AudioDiskstream* -RouteUI::get_diskstream () const -{ - AudioTrack *at; - - if ((at = dynamic_cast(&_route)) != 0) { - return &at->disk_stream(); - } else { - return 0; - } + return dynamic_cast(_route.get()) != 0; } AudioTrack* RouteUI::audio_track() const { - return dynamic_cast(&_route); + return dynamic_cast(_route.get()); } + +Diskstream* +RouteUI::get_diskstream () const +{ + boost::shared_ptr t; + + if ((t = boost::dynamic_pointer_cast(_route)) != 0) { + return &t->diskstream(); + } else { + return 0; + } +} + string RouteUI::name() const { - return _route.name(); + return _route->name(); } void @@ -919,7 +928,7 @@ RouteUI::map_frozen () { ENSURE_GUI_THREAD (mem_fun (*this, &RouteUI::map_frozen)); - AudioTrack* at = dynamic_cast(&_route); + AudioTrack* at = dynamic_cast(_route.get()); if (at) { switch (at->freeze_state()) { @@ -932,3 +941,4 @@ RouteUI::map_frozen () } } } + diff --git a/gtk2_ardour/route_ui.h b/gtk2_ardour/route_ui.h index 69c9b7f5a9..7415eddad6 100644 --- a/gtk2_ardour/route_ui.h +++ b/gtk2_ardour/route_ui.h @@ -26,13 +26,10 @@ #include #include #include +#include #include "axis_view.h" -namespace Gtkmm2ext { - class BindableToggleButton; -} - namespace ARDOUR { class AudioTrack; } @@ -43,21 +40,30 @@ namespace Gtk { class Widget; } +class BindableToggleButton; + class RouteUI : public virtual AxisView { public: - RouteUI(ARDOUR::Route&, ARDOUR::Session&, const char*, const char*, const char*); + RouteUI(boost::shared_ptr, ARDOUR::Session&, const char*, const char*, const char*); virtual ~RouteUI(); + bool is_track() const; bool is_audio_track() const; - ARDOUR::AudioDiskstream* get_diskstream() const; - ARDOUR::Route& route() const { return _route; } + boost::shared_ptr route() const { return _route; } + + // FIXME: make these return shared_ptr + ARDOUR::Track* track() const; ARDOUR::AudioTrack* audio_track() const; + + ARDOUR::Diskstream* get_diskstream() const; string name() const; - - ARDOUR::Route& _route; + + // protected: XXX sigh this should be here + + boost::shared_ptr _route; void set_color (const Gdk::Color & c); bool choose_color (); @@ -65,9 +71,9 @@ class RouteUI : public virtual AxisView bool ignore_toggle; bool wait_for_release; - Gtkmm2ext::BindableToggleButton * mute_button; - Gtkmm2ext::BindableToggleButton * solo_button; - Gtkmm2ext::BindableToggleButton * rec_enable_button; + BindableToggleButton* mute_button; + BindableToggleButton* solo_button; + BindableToggleButton* rec_enable_button; virtual string solo_button_name () const { return "SoloButton"; } virtual string safe_solo_button_name () const { return "SafeSoloButton"; } @@ -89,7 +95,8 @@ class RouteUI : public virtual AxisView void solo_changed(void*); void mute_changed(void*); - void route_rec_enable_changed(void*); + virtual void redirects_changed (void *) {} + void route_rec_enable_changed(); void session_rec_enable_changed(); void build_solo_menu (void); @@ -108,9 +115,9 @@ class RouteUI : public virtual AxisView void build_mute_menu(void); void init_mute_menu(ARDOUR::mute_type, Gtk::CheckMenuItem*); - void set_mix_group_solo(ARDOUR::Route&, bool); - void set_mix_group_mute(ARDOUR::Route&, bool); - void set_mix_group_rec_enable(ARDOUR::Route&, bool); + void set_mix_group_solo(boost::shared_ptr, bool); + void set_mix_group_mute(boost::shared_ptr, bool); + void set_mix_group_rec_enable(boost::shared_ptr, bool); int set_color_from_route (); diff --git a/gtk2_ardour/selectable.h b/gtk2_ardour/selectable.h index b4be7090e2..b52214c9c9 100644 --- a/gtk2_ardour/selectable.h +++ b/gtk2_ardour/selectable.h @@ -34,7 +34,7 @@ class Selectable : public virtual sigc::trackable virtual void set_selected (bool yn) { if (yn != _selected) { - _selected = true; + _selected = yn; Selected (_selected); /* EMIT_SIGNAL */ } } diff --git a/gtk2_ardour/selection.cc b/gtk2_ardour/selection.cc index 2e4ed8a117..086d878994 100644 --- a/gtk2_ardour/selection.cc +++ b/gtk2_ardour/selection.cc @@ -24,7 +24,7 @@ #include -#include "regionview.h" +#include "region_view.h" #include "selection.h" #include "selection_templates.h" #include "time_axis_view.h" @@ -46,7 +46,7 @@ Selection& Selection::operator= (const Selection& other) { if (&other != this) { - audio_regions = other.audio_regions; + regions = other.regions; tracks = other.tracks; time = other.time; lines = other.lines; @@ -57,7 +57,7 @@ Selection::operator= (const Selection& other) bool operator== (const Selection& a, const Selection& b) { - return a.audio_regions == b.audio_regions && + return a.regions == b.regions && a.tracks == b.tracks && a.time.track == b.time.track && a.time.group == b.time.group && @@ -71,7 +71,7 @@ void Selection::clear () { clear_tracks (); - clear_audio_regions (); + clear_regions (); clear_points (); clear_lines(); clear_time (); @@ -83,8 +83,8 @@ void Selection::dump_region_layers() { cerr << "region selection layer dump" << endl; - for (AudioRegionSelection::iterator i = audio_regions.begin(); i != audio_regions.end(); ++i) { - cerr << "layer: " << (int)(*i)->region.layer() << endl; + for (RegionSelection::iterator i = regions.begin(); i != regions.end(); ++i) { + cerr << "layer: " << (int)(*i)->region().layer() << endl; } } @@ -99,10 +99,10 @@ Selection::clear_redirects () } void -Selection::clear_audio_regions () +Selection::clear_regions () { - if (!audio_regions.empty()) { - audio_regions.clear_all (); + if (!regions.empty()) { + regions.clear_all (); RegionsChanged(); } } @@ -151,7 +151,7 @@ Selection::clear_lines () } void -Selection::toggle (Redirect* r) +Selection::toggle (boost::shared_ptr r) { RedirectSelection::iterator i; @@ -196,29 +196,29 @@ Selection::toggle (TimeAxisView* track) } void -Selection::toggle (AudioRegionView* r) +Selection::toggle (RegionView* r) { - AudioRegionSelection::iterator i; + RegionSelection::iterator i; - if ((i = find (audio_regions.begin(), audio_regions.end(), r)) == audio_regions.end()) { - audio_regions.add (r); + if ((i = find (regions.begin(), regions.end(), r)) == regions.end()) { + regions.add (r); } else { - audio_regions.erase (i); + regions.erase (i); } RegionsChanged (); } void -Selection::toggle (vector& r) +Selection::toggle (vector& r) { - AudioRegionSelection::iterator i; + RegionSelection::iterator i; - for (vector::iterator x = r.begin(); x != r.end(); ++x) { - if ((i = find (audio_regions.begin(), audio_regions.end(), (*x))) == audio_regions.end()) { - audio_regions.add ((*x)); + for (vector::iterator x = r.begin(); x != r.end(); ++x) { + if ((i = find (regions.begin(), regions.end(), (*x))) == regions.end()) { + regions.add ((*x)); } else { - audio_regions.erase (i); + regions.erase (i); } } @@ -243,7 +243,7 @@ Selection::toggle (jack_nframes_t start, jack_nframes_t end) void -Selection::add (Redirect* r) +Selection::add (boost::shared_ptr r) { if (find (redirects.begin(), redirects.end(), r) == redirects.end()) { redirects.push_back (r); @@ -310,22 +310,22 @@ Selection::add (TimeAxisView* track) } void -Selection::add (AudioRegionView* r) +Selection::add (RegionView* r) { - if (find (audio_regions.begin(), audio_regions.end(), r) == audio_regions.end()) { - audio_regions.add (r); + if (find (regions.begin(), regions.end(), r) == regions.end()) { + regions.add (r); RegionsChanged (); } } void -Selection::add (vector& v) +Selection::add (vector& v) { bool changed = false; - for (vector::iterator i = v.begin(); i != v.end(); ++i) { - if (find (audio_regions.begin(), audio_regions.end(), (*i)) == audio_regions.end()) { - audio_regions.add ((*i)); + for (vector::iterator i = v.begin(); i != v.end(); ++i) { + if (find (regions.begin(), regions.end(), (*i)) == regions.end()) { + regions.add ((*i)); changed = true; } } @@ -381,9 +381,9 @@ Selection::add (AutomationList* ac) } void -Selection::remove (Redirect* r) +Selection::remove (boost::shared_ptr r) { - list::iterator i; + RedirectSelection::iterator i; if ((i = find (redirects.begin(), redirects.end(), r)) != redirects.end()) { redirects.erase (i); RedirectsChanged (); @@ -451,9 +451,9 @@ Selection::remove (const list& pllist) } void -Selection::remove (AudioRegionView* r) +Selection::remove (RegionView* r) { - audio_regions.remove (r); + regions.remove (r); RegionsChanged (); } @@ -491,7 +491,7 @@ Selection::remove (AutomationList *ac) } void -Selection::set (Redirect *r) +Selection::set (boost::shared_ptr r) { clear_redirects (); add (r); @@ -526,17 +526,16 @@ Selection::set (const list& pllist) } void -Selection::set (AudioRegionView* r) +Selection::set (RegionView* r) { - clear_audio_regions (); + clear_regions (); add (r); } void -Selection::set (vector& v) +Selection::set (vector& v) { - - clear_audio_regions (); + clear_regions (); // make sure to deselect any automation selections clear_points(); add (v); @@ -590,15 +589,15 @@ Selection::selected (TimeAxisView* tv) } bool -Selection::selected (AudioRegionView* arv) +Selection::selected (RegionView* rv) { - return find (audio_regions.begin(), audio_regions.end(), arv) != audio_regions.end(); + return find (regions.begin(), regions.end(), rv) != regions.end(); } bool Selection::empty () { - return audio_regions.empty () && + return regions.empty () && tracks.empty () && points.empty () && playlists.empty () && @@ -612,7 +611,7 @@ Selection::empty () void Selection::set (list& selectables) { - clear_audio_regions(); + clear_regions(); clear_points (); add (selectables); } @@ -620,14 +619,14 @@ Selection::set (list& selectables) void Selection::add (list& selectables) { - AudioRegionView* arv; + RegionView* rv; AutomationSelectable* as; - vector arvs; + vector rvs; vector autos; for (std::list::iterator i = selectables.begin(); i != selectables.end(); ++i) { - if ((arv = dynamic_cast (*i)) != 0) { - arvs.push_back (arv); + if ((rv = dynamic_cast (*i)) != 0) { + rvs.push_back (rv); } else if ((as = dynamic_cast (*i)) != 0) { autos.push_back (as); } else { @@ -638,8 +637,8 @@ Selection::add (list& selectables) } } - if (!arvs.empty()) { - add (arvs); + if (!rvs.empty()) { + add (rvs); } if (!autos.empty()) { diff --git a/gtk2_ardour/selection.h b/gtk2_ardour/selection.h index ebeda1aea7..7b503a5e63 100644 --- a/gtk2_ardour/selection.h +++ b/gtk2_ardour/selection.h @@ -22,6 +22,7 @@ #define __ardour_gtk_selection_h__ #include +#include #include @@ -34,7 +35,7 @@ #include "point_selection.h" class TimeAxisView; -class AudioRegionView; +class RegionView; class Selectable; namespace ARDOUR { @@ -60,7 +61,7 @@ class Selection : public sigc::trackable }; TrackSelection tracks; - AudioRegionSelection audio_regions; + RegionSelection regions; TimeSelection time; AutomationSelection lines; PlaylistSelection playlists; @@ -88,55 +89,55 @@ class Selection : public sigc::trackable void dump_region_layers(); bool selected (TimeAxisView*); - bool selected (AudioRegionView*); + bool selected (RegionView*); void set (list&); void add (list&); void set (TimeAxisView*); void set (const list&); - void set (AudioRegionView*); - void set (std::vector&); + void set (RegionView*); + void set (std::vector&); long set (TimeAxisView*, jack_nframes_t, jack_nframes_t); void set (ARDOUR::AutomationList*); void set (ARDOUR::Playlist*); void set (const list&); - void set (ARDOUR::Redirect*); + void set (boost::shared_ptr); void set (AutomationSelectable*); void toggle (TimeAxisView*); void toggle (const list&); - void toggle (AudioRegionView*); - void toggle (std::vector&); + void toggle (RegionView*); + void toggle (std::vector&); long toggle (jack_nframes_t, jack_nframes_t); void toggle (ARDOUR::AutomationList*); void toggle (ARDOUR::Playlist*); void toggle (const list&); - void toggle (ARDOUR::Redirect*); + void toggle (boost::shared_ptr); void add (TimeAxisView*); void add (const list&); - void add (AudioRegionView*); - void add (std::vector&); + void add (RegionView*); + void add (std::vector&); long add (jack_nframes_t, jack_nframes_t); void add (ARDOUR::AutomationList*); void add (ARDOUR::Playlist*); void add (const list&); - void add (ARDOUR::Redirect*); + void add (boost::shared_ptr); void remove (TimeAxisView*); void remove (const list&); - void remove (AudioRegionView*); + void remove (RegionView*); void remove (uint32_t selection_id); void remove (jack_nframes_t, jack_nframes_t); void remove (ARDOUR::AutomationList*); void remove (ARDOUR::Playlist*); void remove (const list&); - void remove (ARDOUR::Redirect*); + void remove (boost::shared_ptr); void replace (uint32_t time_index, jack_nframes_t start, jack_nframes_t end); - void clear_audio_regions(); + void clear_regions(); void clear_tracks (); void clear_time(); void clear_lines (); @@ -144,10 +145,8 @@ class Selection : public sigc::trackable void clear_redirects (); void clear_points (); - void foreach_audio_region (void (ARDOUR::AudioRegion::*method)(void)); - void foreach_audio_region (void (ARDOUR::Region::*method)(void)); - template void foreach_audio_region (void (ARDOUR::AudioRegion::*method)(A), A arg); - template void foreach_audio_region (void (ARDOUR::Region::*method)(A), A arg); + void foreach_region (void (ARDOUR::Region::*method)(void)); + template void foreach_region (void (ARDOUR::Region::*method)(A), A arg); private: uint32_t next_time_id; diff --git a/gtk2_ardour/selection_templates.h b/gtk2_ardour/selection_templates.h index c2ca70b526..9511db7d61 100644 --- a/gtk2_ardour/selection_templates.h +++ b/gtk2_ardour/selection_templates.h @@ -27,35 +27,21 @@ */ #include -#include #include "selection.h" +#include "region_view.h" inline void -Selection::foreach_audio_region (void (ARDOUR::AudioRegion::*method)(void)) { - for (AudioRegionSelection::iterator i = audio_regions.begin(); i != audio_regions.end(); ++i) { - ((*i)->region.*(method))(); - } -} - -inline void -Selection::foreach_audio_region (void (ARDOUR::Region::*method)(void)) { - for (AudioRegionSelection::iterator i = audio_regions.begin(); i != audio_regions.end(); ++i) { - ((*i)->region.*(method))(); +Selection::foreach_region (void (ARDOUR::Region::*method)(void)) { + for (RegionSelection::iterator i = regions.begin(); i != regions.end(); ++i) { + ((*i)->region().*(method))(); } } template inline void -Selection::foreach_audio_region (void (ARDOUR::AudioRegion::*method)(A), A arg) { - for (AudioRegionSelection::iterator i = audio_regions.begin(); i != audio_regions.end(); ++i) { - ((*i)->region.*(method))(arg); - } -} - -template inline void -Selection::foreach_audio_region (void (ARDOUR::Region::*method)(A), A arg) { - for (AudioRegionSelection::iterator i = audio_regions.begin(); i != audio_regions.end(); ++i) { - ((*i)->region.*(method))(arg); +Selection::foreach_region (void (ARDOUR::Region::*method)(A), A arg) { + for (RegionSelection::iterator i = regions.begin(); i != regions.end(); ++i) { + ((*i)->region().*(method))(arg); } } @@ -64,14 +50,14 @@ Selection::foreach_audio_region (void (ARDOUR::Region::*method)(A), A arg) { template inline void Selection::foreach_route (void (ARDOUR::Route::*method)(A), A arg) { for (list::iterator i = routes.begin(); i != routes.end(); ++i) { - ((*i)->region.*(method))(arg); + ((*i)->region().*(method))(arg); } } template inline void Selection::foreach_route (void (ARDOUR::Route::*method)(A1,A2), A1 arg1, A2 arg2) { for (list::iterator i = routes.begin(); i != routes.end(); ++i) { - ((*i)->region.*(method))(arg1, arg2); + ((*i)->region().*(method))(arg1, arg2); } } diff --git a/gtk2_ardour/send_ui.cc b/gtk2_ardour/send_ui.cc index be95f753e7..9925ff51d4 100644 --- a/gtk2_ardour/send_ui.cc +++ b/gtk2_ardour/send_ui.cc @@ -30,7 +30,7 @@ using namespace ARDOUR; using namespace PBD; -SendUI::SendUI (Send& s, Session& se) +SendUI::SendUI (boost::shared_ptr s, Session& se) : _send (s), _session (se), gpm (s, se), @@ -53,10 +53,10 @@ SendUI::SendUI (Send& s, Session& se) show_all (); - _send.set_metering (true); + _send->set_metering (true); - _send.output_changed.connect (mem_fun (*this, &SendUI::ins_changed)); - _send.output_changed.connect (mem_fun (*this, &SendUI::outs_changed)); + _send->output_changed.connect (mem_fun (*this, &SendUI::ins_changed)); + _send->output_changed.connect (mem_fun (*this, &SendUI::outs_changed)); panners.set_width (Wide); panners.setup_pan (); @@ -70,7 +70,7 @@ SendUI::SendUI (Send& s, Session& se) SendUI::~SendUI () { - _send.set_metering (false); + _send->set_metering (false); /* XXX not clear that we need to do this */ @@ -118,7 +118,7 @@ SendUI::fast_update () } } -SendUIWindow::SendUIWindow (Send& s, Session& ss) +SendUIWindow::SendUIWindow (boost::shared_ptr s, Session& ss) { ui = new SendUI (s, ss); @@ -131,7 +131,7 @@ SendUIWindow::SendUIWindow (Send& s, Session& ss) add (vpacker); set_name ("SendUIWindow"); - s.GoingAway.connect (mem_fun (*this, &SendUIWindow::send_going_away)); + s->GoingAway.connect (mem_fun (*this, &SendUIWindow::send_going_away)); signal_delete_event().connect (bind (ptr_fun (just_hide_it), reinterpret_cast (this))); diff --git a/gtk2_ardour/send_ui.h b/gtk2_ardour/send_ui.h index d1a49930ea..1d5a74e102 100644 --- a/gtk2_ardour/send_ui.h +++ b/gtk2_ardour/send_ui.h @@ -35,7 +35,7 @@ class IOSelector; class SendUI : public Gtk::HBox { public: - SendUI (ARDOUR::Send&, ARDOUR::Session&); + SendUI (boost::shared_ptr, ARDOUR::Session&); ~SendUI(); void update (); @@ -44,7 +44,7 @@ class SendUI : public Gtk::HBox IOSelector* io; private: - ARDOUR::Send& _send; + boost::shared_ptr _send; ARDOUR::Session& _session; GainMeter gpm; PannerUI panners; @@ -62,7 +62,7 @@ class SendUI : public Gtk::HBox class SendUIWindow : public Gtk::Window { public: - SendUIWindow(ARDOUR::Send&, ARDOUR::Session&); + SendUIWindow(boost::shared_ptr, ARDOUR::Session&); ~SendUIWindow(); SendUI* ui; diff --git a/gtk2_ardour/sfdb_ui.cc b/gtk2_ardour/sfdb_ui.cc index 79546880de..d9ded04d2b 100644 --- a/gtk2_ardour/sfdb_ui.cc +++ b/gtk2_ardour/sfdb_ui.cc @@ -97,6 +97,9 @@ SoundFileBox::SoundFileBox () (mem_fun (*this, &SoundFileBox::add_field_clicked)); remove_field_btn.signal_clicked().connect (mem_fun (*this, &SoundFileBox::remove_field_clicked)); + + Gtk::CellRendererText* cell(dynamic_cast(field_view.get_column_cell_renderer(1))); + cell->signal_edited().connect (mem_fun (*this, &SoundFileBox::field_edited)); field_view.get_selection()->signal_changed().connect (mem_fun (*this, &SoundFileBox::field_selected)); Library->fields_changed.connect (mem_fun (*this, &SoundFileBox::setup_fields)); @@ -259,6 +262,13 @@ SoundFileBox::remove_field_clicked () Library->save_changes (); } +void +SoundFileBox::field_edited (const Glib::ustring& str1, const Glib::ustring& str2) +{ + cout << "field_edited" << endl; + Library->save_changes (); +} + void SoundFileBox::delete_row (const Gtk::TreeModel::iterator& iter) { @@ -394,6 +404,9 @@ SoundFileOmega::set_mode (Editing::ImportMode mode) case Editing::ImportToTrack: split_check.set_sensitive (false); break; + case Editing::ImportAsTapeTrack: + split_check.set_sensitive (true); + break; } } @@ -433,5 +446,8 @@ SoundFileOmega::mode_changed () case Editing::ImportToTrack: split_check.set_sensitive (false); break; + case Editing::ImportAsTapeTrack: + split_check.set_sensitive (true); + break; } } diff --git a/gtk2_ardour/sfdb_ui.h b/gtk2_ardour/sfdb_ui.h index 79c73b97ac..8ef57d7b9f 100644 --- a/gtk2_ardour/sfdb_ui.h +++ b/gtk2_ardour/sfdb_ui.h @@ -100,6 +100,7 @@ class SoundFileBox : public Gtk::VBox void stop_btn_clicked (); void add_field_clicked (); void remove_field_clicked (); + void field_edited (const Glib::ustring&, const Glib::ustring&); void delete_row (const Gtk::TreeModel::iterator& iter); void field_selected (); diff --git a/gtk2_ardour/streamview.cc b/gtk2_ardour/streamview.cc index a60e0d59e7..d1d163d7a2 100644 --- a/gtk2_ardour/streamview.cc +++ b/gtk2_ardour/streamview.cc @@ -1,28 +1,42 @@ +/* + Copyright (C) 2001, 2006 Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. +*/ + #include #include #include -#include -#include -#include -#include -#include -#include +#include +#include #include +#include +#include #include "streamview.h" -#include "regionview.h" -#include "taperegionview.h" -#include "audio_time_axis.h" +#include "region_view.h" +#include "route_time_axis.h" #include "canvas-waveview.h" #include "canvas-simplerect.h" #include "region_selection.h" #include "selection.h" #include "public_editor.h" #include "ardour_ui.h" -#include "crossfade_view.h" #include "rgb_macros.h" #include "gui_thread.h" #include "utils.h" @@ -32,52 +46,36 @@ using namespace ARDOUR; using namespace PBD; using namespace Editing; -StreamView::StreamView (AudioTimeAxisView& tv) +StreamView::StreamView (RouteTimeAxisView& tv) : _trackview (tv) + , canvas_group(new ArdourCanvas::Group(*_trackview.canvas_display)) + , canvas_rect(new ArdourCanvas::SimpleRect (*canvas_group)) + , _samples_per_unit(_trackview.editor.get_current_zoom()) + , rec_updating(false) + , rec_active(false) + , use_rec_regions(tv.editor.show_waveforms_recording()) + , region_color(_trackview.color()) + , stream_base_color(0xFFFFFFFF) { - region_color = _trackview.color(); - crossfades_visible = true; - - if (tv.is_audio_track()) { - /* TRACK */ - //stream_base_color = RGBA_TO_UINT (222,223,218,255); - stream_base_color = color_map[cAudioTrackBase]; - } else { - /* BUS */ - //stream_base_color = RGBA_TO_UINT (230,226,238,255); - stream_base_color = color_map[cAudioBusBase]; - } - /* set_position() will position the group */ - canvas_group = new ArdourCanvas::Group(*_trackview.canvas_display); - canvas_rect = new ArdourCanvas::SimpleRect (*canvas_group); canvas_rect->property_x1() = 0.0; canvas_rect->property_y1() = 0.0; canvas_rect->property_x2() = 1000000.0; canvas_rect->property_y2() = (double) tv.height; - canvas_rect->property_outline_color_rgba() = color_map[cAudioTrackOutline]; canvas_rect->property_outline_what() = (guint32) (0x1|0x2|0x8); // outline ends and bottom - canvas_rect->property_fill_color_rgba() = stream_base_color; + // (Fill/Outline colours set in derived classes) canvas_rect->signal_event().connect (bind (mem_fun (_trackview.editor, &PublicEditor::canvas_stream_view_event), canvas_rect, &_trackview)); - _samples_per_unit = _trackview.editor.get_current_zoom(); - _amplitude_above_axis = 1.0; - - if (_trackview.is_audio_track()) { - _trackview.audio_track()->diskstream_changed.connect (mem_fun (*this, &StreamView::diskstream_changed)); + if (_trackview.is_track()) { + _trackview.track()->DiskstreamChanged.connect (mem_fun (*this, &StreamView::diskstream_changed)); _trackview.session().TransportStateChange.connect (mem_fun (*this, &StreamView::transport_changed)); - _trackview.get_diskstream()->record_enable_changed.connect (mem_fun (*this, &StreamView::rec_enable_changed)); + _trackview.get_diskstream()->RecordEnableChanged.connect (mem_fun (*this, &StreamView::rec_enable_changed)); _trackview.session().RecordStateChanged.connect (mem_fun (*this, &StreamView::sess_rec_enable_changed)); } - rec_updating = false; - rec_active = false; - use_rec_regions = tv.editor.show_waveforms_recording (); - last_rec_peak_frame = 0; - ColorChanged.connect (mem_fun (*this, &StreamView::color_handler)); } @@ -90,7 +88,7 @@ StreamView::~StreamView () void StreamView::attach () { - if (_trackview.is_audio_track()) { + if (_trackview.is_track()) { display_diskstream (_trackview.get_diskstream()); } } @@ -115,13 +113,13 @@ StreamView::set_height (gdouble h) canvas_rect->property_y2() = h; - for (AudioRegionViewList::iterator i = region_views.begin(); i != region_views.end(); ++i) { + for (RegionViewList::iterator i = region_views.begin(); i != region_views.end(); ++i) { (*i)->set_height (h); } - for (CrossfadeViewList::iterator i = crossfade_views.begin(); i != crossfade_views.end(); ++i) { + /*for (CrossfadeViewList::iterator i = crossfade_views.begin(); i != crossfade_views.end(); ++i) { (*i)->set_height (h); - } + }*/ for (vector::iterator i = rec_rects.begin(); i != rec_rects.end(); ++i) { RecBoxInfo &recbox = (*i); @@ -134,7 +132,7 @@ StreamView::set_height (gdouble h) int StreamView::set_samples_per_unit (gdouble spp) { - AudioRegionViewList::iterator i; + RegionViewList::iterator i; if (spp < 1.0) { return -1; @@ -146,10 +144,6 @@ StreamView::set_samples_per_unit (gdouble spp) (*i)->set_samples_per_unit (spp); } - for (CrossfadeViewList::iterator xi = crossfade_views.begin(); xi != crossfade_views.end(); ++xi) { - (*xi)->set_samples_per_unit (spp); - } - for (vector::iterator xi = rec_rects.begin(); xi != rec_rects.end(); ++xi) { RecBoxInfo &recbox = (*xi); @@ -163,113 +157,24 @@ StreamView::set_samples_per_unit (gdouble spp) return 0; } -int -StreamView::set_amplitude_above_axis (gdouble app) - -{ - AudioRegionViewList::iterator i; - - if (app < 1.0) { - return -1; - } - - _amplitude_above_axis = app; - - for (i = region_views.begin(); i != region_views.end(); ++i) { - (*i)->set_amplitude_above_axis (app); - } - - return 0; -} - void StreamView::add_region_view (Region *r) { add_region_view_internal (r, true); } -void -StreamView::add_region_view_internal (Region *r, bool wait_for_waves) -{ - ENSURE_GUI_THREAD (bind (mem_fun (*this, &StreamView::add_region_view), r)); - - AudioRegion* region = dynamic_cast (r); - - if (region == 0) { - return; - } - - AudioRegionView *region_view; - list::iterator i; - - for (i = region_views.begin(); i != region_views.end(); ++i) { - if (&(*i)->region == region) { - - /* great. we already have a AudioRegionView for this Region. use it again. - */ - - (*i)->set_valid (true); - return; - } - } - - switch (_trackview.audio_track()->mode()) { - case Normal: - region_view = new AudioRegionView (canvas_group, _trackview, *region, - _samples_per_unit, region_color); - break; - case Destructive: - region_view = new TapeAudioRegionView (canvas_group, _trackview, *region, - _samples_per_unit, region_color); - break; - } - - region_view->init (_amplitude_above_axis, region_color, wait_for_waves); - region_views.push_front (region_view); - - /* follow global waveform setting */ - - region_view->set_waveform_visible(_trackview.editor.show_waveforms()); - - /* catch regionview going away */ - - region->GoingAway.connect (mem_fun (*this, &StreamView::remove_region_view)); - - AudioRegionViewAdded (region_view); -} - void StreamView::remove_region_view (Region *r) { ENSURE_GUI_THREAD (bind (mem_fun (*this, &StreamView::remove_region_view), r)); - AudioRegion* ar = dynamic_cast (r); - - if (ar == 0) { - return; - } - - for (list::iterator i = region_views.begin(); i != region_views.end(); ++i) { - if (&((*i)->region) == ar) { + for (list::iterator i = region_views.begin(); i != region_views.end(); ++i) { + if (&((*i)->region()) == r) { delete *i; region_views.erase (i); break; } } - - for (list::iterator i = crossfade_views.begin(); i != crossfade_views.end();) { - list::iterator tmp; - - tmp = i; - ++tmp; - - if ((*i)->crossfade.involves (*ar)) { - delete *i; - crossfade_views.erase (i); - } - - i = tmp; - } } void @@ -282,14 +187,8 @@ StreamView::remove_rec_region (Region *r) /*NOTREACHED*/ } - AudioRegion* ar = dynamic_cast (r); - - if (ar == 0) { - return; - } - - for (list::iterator i = rec_regions.begin(); i != rec_regions.end(); ++i) { - if (*i == ar) { + for (list::iterator i = rec_regions.begin(); i != rec_regions.end(); ++i) { + if (*i == r) { rec_regions.erase (i); break; } @@ -299,21 +198,15 @@ StreamView::remove_rec_region (Region *r) void StreamView::undisplay_diskstream () { - - for (AudioRegionViewList::iterator i = region_views.begin(); i != region_views.end(); ++i) { - delete *i; - } - - for (CrossfadeViewList::iterator i = crossfade_views.begin(); i != crossfade_views.end(); ++i) { + for (RegionViewList::iterator i = region_views.begin(); i != region_views.end(); ++i) { delete *i; } region_views.clear(); - crossfade_views.clear (); } void -StreamView::display_diskstream (AudioDiskstream *ds) +StreamView::display_diskstream (Diskstream *ds) { playlist_change_connection.disconnect(); playlist_changed (ds); @@ -325,21 +218,13 @@ StreamView::playlist_modified () { ENSURE_GUI_THREAD (mem_fun (*this, &StreamView::playlist_modified)); - /* if the playlist is modified, make sure xfades are on top and all the regionviews are stacked - correctly. - */ - - for (AudioRegionViewList::iterator i = region_views.begin(); i != region_views.end(); ++i) { + for (RegionViewList::iterator i = region_views.begin(); i != region_views.end(); ++i) { region_layered (*i); } - - for (list::iterator i = crossfade_views.begin(); i != crossfade_views.end(); ++i) { - (*i)->get_canvas_group()->raise_to_top(); - } } void -StreamView::playlist_changed (AudioDiskstream *ds) +StreamView::playlist_changed (Diskstream *ds) { ENSURE_GUI_THREAD (bind (mem_fun (*this, &StreamView::playlist_changed), ds)); @@ -362,69 +247,6 @@ StreamView::playlist_changed (AudioDiskstream *ds) playlist_connections.push_back (ds->playlist()->RegionRemoved.connect (mem_fun (*this, &StreamView::remove_region_view))); playlist_connections.push_back (ds->playlist()->StateChanged.connect (mem_fun (*this, &StreamView::playlist_state_changed))); playlist_connections.push_back (ds->playlist()->Modified.connect (mem_fun (*this, &StreamView::playlist_modified))); - playlist_connections.push_back (ds->playlist()->NewCrossfade.connect (mem_fun (*this, &StreamView::add_crossfade))); -} - -void -StreamView::add_crossfade (Crossfade *crossfade) -{ - AudioRegionView* lview = 0; - AudioRegionView* rview = 0; - - ENSURE_GUI_THREAD (bind (mem_fun (*this, &StreamView::add_crossfade), crossfade)); - - /* first see if we already have a CrossfadeView for this Crossfade */ - - for (list::iterator i = crossfade_views.begin(); i != crossfade_views.end(); ++i) { - if (&(*i)->crossfade == crossfade) { - if (!crossfades_visible) { - (*i)->hide(); - } else { - (*i)->show (); - } - (*i)->set_valid (true); - return; - } - } - - /* create a new one */ - - for (list::iterator i = region_views.begin(); i != region_views.end(); ++i) { - if (!lview && &((*i)->region) == &crossfade->out()) { - lview = *i; - } - if (!rview && &((*i)->region) == &crossfade->in()) { - rview = *i; - } - } - - CrossfadeView *cv = new CrossfadeView (_trackview.canvas_display, - _trackview, - *crossfade, - _samples_per_unit, - region_color, - *lview, *rview); - - crossfade->Invalidated.connect (mem_fun (*this, &StreamView::remove_crossfade)); - crossfade_views.push_back (cv); - - if (!crossfades_visible) { - cv->hide (); - } -} - -void -StreamView::remove_crossfade (Crossfade *xfade) -{ - ENSURE_GUI_THREAD (bind (mem_fun (*this, &StreamView::remove_crossfade), xfade)); - - for (list::iterator i = crossfade_views.begin(); i != crossfade_views.end(); ++i) { - if (&(*i)->crossfade == xfade) { - delete *i; - crossfade_views.erase (i); - break; - } - } } void @@ -436,64 +258,12 @@ StreamView::playlist_state_changed (Change ignored) } void -StreamView::redisplay_diskstream () +StreamView::diskstream_changed () { - list::iterator i, tmp; - list::iterator xi, tmpx; + Track *t; - - for (i = region_views.begin(); i != region_views.end(); ++i) { - (*i)->set_valid (false); - } - - for (xi = crossfade_views.begin(); xi != crossfade_views.end(); ++xi) { - (*xi)->set_valid (false); - if ((*xi)->visible()) { - (*xi)->show (); - } - } - - if (_trackview.is_audio_track()) { - _trackview.get_diskstream()->playlist()->foreach_region (this, &StreamView::add_region_view); - _trackview.get_diskstream()->playlist()->foreach_crossfade (this, &StreamView::add_crossfade); - } - - for (i = region_views.begin(); i != region_views.end(); ) { - tmp = i; - tmp++; - - if (!(*i)->is_valid()) { - delete *i; - region_views.erase (i); - } - - i = tmp; - } - - for (xi = crossfade_views.begin(); xi != crossfade_views.end();) { - tmpx = xi; - tmpx++; - - if (!(*xi)->valid()) { - delete *xi; - crossfade_views.erase (xi); - } - - xi = tmpx; - } - - /* now fix layering */ - - playlist_modified (); -} - -void -StreamView::diskstream_changed (void *src_ignored) -{ - AudioTrack *at; - - if ((at = _trackview.audio_track()) != 0) { - AudioDiskstream& ds = at->disk_stream(); + if ((t = _trackview.track()) != 0) { + Diskstream& ds = t->diskstream(); /* XXX grrr: when will SigC++ allow me to bind references? */ Gtkmm2ext::UI::instance()->call_slot (bind (mem_fun (*this, &StreamView::display_diskstream), &ds)); } else { @@ -505,7 +275,7 @@ void StreamView::apply_color (Gdk::Color& color, ColorTarget target) { - list::iterator i; + list::iterator i; switch (target) { case RegionColor: @@ -513,76 +283,18 @@ StreamView::apply_color (Gdk::Color& color, ColorTarget target) for (i = region_views.begin(); i != region_views.end(); ++i) { (*i)->set_color (region_color); } - // stream_base_color = RGBA_TO_UINT (color.red/256, color.green/256, color.blue/256, 255); - // gnome_canvas_item_set (canvas_rect, "fill_color_rgba", stream_base_color, NULL); break; case StreamBaseColor: - // stream_base_color = RGBA_TO_UINT (color.red/256, color.green/256, color.blue/256, 255); - // gnome_canvas_item_set (canvas_rect, "fill_color_rgba", stream_base_color, NULL); + stream_base_color = RGBA_TO_UINT ( + color.get_red_p(), color.get_green_p(), color.get_blue_p(), 255); + canvas_rect->property_fill_color_rgba() = stream_base_color; break; } } void -StreamView::set_show_waveforms (bool yn) -{ - for (list::iterator i = region_views.begin(); i != region_views.end(); ++i) { - (*i)->set_waveform_visible (yn); - } -} - -void -StreamView::set_selected_regionviews (AudioRegionSelection& regions) -{ - bool selected; - - // cerr << _trackview.name() << " (selected = " << regions.size() << ")" << endl; - for (list::iterator i = region_views.begin(); i != region_views.end(); ++i) { - - selected = false; - - for (AudioRegionSelection::iterator ii = regions.begin(); ii != regions.end(); ++ii) { - if (*i == *ii) { - selected = true; - } - } - - // cerr << "\tregion " << (*i)->region.name() << " selected = " << selected << endl; - (*i)->set_selected (selected); - } -} - -void -StreamView::get_selectables (jack_nframes_t start, jack_nframes_t end, list& results) -{ - for (list::iterator i = region_views.begin(); i != region_views.end(); ++i) { - if ((*i)->region.coverage(start, end) != OverlapNone) { - results.push_back (*i); - } - } -} - -void -StreamView::get_inverted_selectables (Selection& sel, list& results) -{ - for (list::iterator i = region_views.begin(); i != region_views.end(); ++i) { - if (!sel.audio_regions.contains (*i)) { - results.push_back (*i); - } - } -} - -void -StreamView::set_waveform_shape (WaveformShape shape) -{ - for (AudioRegionViewList::iterator i = region_views.begin(); i != region_views.end(); ++i) { - (*i)->set_waveform_shape (shape); - } -} - -void -StreamView::region_layered (AudioRegionView* rv) +StreamView::region_layered (RegionView* rv) { rv->get_canvas_group()->lower_to_bottom(); @@ -590,11 +302,14 @@ StreamView::region_layered (AudioRegionView* rv) get events - the parent group does instead ... */ - rv->get_canvas_group()->raise (rv->region.layer() + 1); + /* this used to be + 1, but regions to the left ended up below + ..something.. and couldn't receive events. why? good question. + */ + rv->get_canvas_group()->raise (rv->region().layer() + 2); } void -StreamView::rec_enable_changed (void *src) +StreamView::rec_enable_changed () { Gtkmm2ext::UI::instance()->call_slot (mem_fun (*this, &StreamView::setup_rec_box)); } @@ -611,161 +326,6 @@ StreamView::transport_changed() Gtkmm2ext::UI::instance()->call_slot (mem_fun (*this, &StreamView::setup_rec_box)); } -void -StreamView::setup_rec_box () -{ - // cerr << _trackview.name() << " streamview SRB\n"; - - if (_trackview.session().transport_rolling()) { - - // cerr << "\trolling\n"; - - if (!rec_active && - _trackview.session().record_status() == Session::Recording && - _trackview.get_diskstream()->record_enabled()) { - - if (_trackview.audio_track()->mode() == Normal && use_rec_regions && rec_regions.size() == rec_rects.size()) { - - /* add a new region, but don't bother if they set use_rec_regions mid-record */ - - AudioRegion::SourceList sources; - - for (list::iterator prc = peak_ready_connections.begin(); prc != peak_ready_connections.end(); ++prc) { - (*prc).disconnect(); - } - peak_ready_connections.clear(); - - for (uint32_t n=0; n < _trackview.get_diskstream()->n_channels(); ++n) { - AudioSource *src = (AudioSource *) _trackview.get_diskstream()->write_source (n); - if (src) { - sources.push_back (src); - peak_ready_connections.push_back (src->PeakRangeReady.connect (bind (mem_fun (*this, &StreamView::rec_peak_range_ready), src))); - } - } - - // handle multi - - jack_nframes_t start = 0; - if (rec_regions.size() > 0) { - start = rec_regions.back()->start() + _trackview.get_diskstream()->get_captured_frames(rec_regions.size()-1); - } - - AudioRegion * region = new AudioRegion(sources, start, 1 , "", 0, (Region::Flag)(Region::DefaultFlags | Region::DoNotSaveState), false); - region->set_position (_trackview.session().transport_frame(), this); - rec_regions.push_back (region); - /* catch it if it goes away */ - region->GoingAway.connect (mem_fun (*this, &StreamView::remove_rec_region)); - - /* we add the region later */ - } - - /* start a new rec box */ - - AudioTrack* at; - - at = _trackview.audio_track(); /* we know what it is already */ - AudioDiskstream& ds = at->disk_stream(); - jack_nframes_t frame_pos = ds.current_capture_start (); - gdouble xstart = _trackview.editor.frame_to_pixel (frame_pos); - gdouble xend; - uint32_t fill_color; - - switch (_trackview.audio_track()->mode()) { - case Normal: - xend = xstart; - fill_color = color_map[cRecordingRectFill]; - break; - - case Destructive: - xend = xstart + 2; - fill_color = color_map[cRecordingRectFill]; - /* make the recording rect translucent to allow - the user to see the peak data coming in, etc. - */ - fill_color = UINT_RGBA_CHANGE_A (fill_color, 120); - break; - } - - ArdourCanvas::SimpleRect * rec_rect = new Gnome::Canvas::SimpleRect (*canvas_group); - rec_rect->property_x1() = xstart; - rec_rect->property_y1() = 1.0; - rec_rect->property_x2() = xend; - rec_rect->property_y2() = (double) _trackview.height - 1; - rec_rect->property_outline_color_rgba() = color_map[cRecordingRectOutline]; - rec_rect->property_fill_color_rgba() = fill_color; - - RecBoxInfo recbox; - recbox.rectangle = rec_rect; - recbox.start = _trackview.session().transport_frame(); - recbox.length = 0; - - rec_rects.push_back (recbox); - - screen_update_connection.disconnect(); - screen_update_connection = ARDOUR_UI::instance()->SuperRapidScreenUpdate.connect (mem_fun (*this, &StreamView::update_rec_box)); - rec_updating = true; - rec_active = true; - - } else if (rec_active && - (_trackview.session().record_status() != Session::Recording || - !_trackview.get_diskstream()->record_enabled())) { - - screen_update_connection.disconnect(); - rec_active = false; - rec_updating = false; - - } - - } else { - - // cerr << "\tNOT rolling, rec_rects = " << rec_rects.size() << " rec_regions = " << rec_regions.size() << endl; - - if (!rec_rects.empty() || !rec_regions.empty()) { - - /* disconnect rapid update */ - screen_update_connection.disconnect(); - - for (list::iterator prc = peak_ready_connections.begin(); prc != peak_ready_connections.end(); ++prc) { - (*prc).disconnect(); - } - peak_ready_connections.clear(); - - rec_updating = false; - rec_active = false; - last_rec_peak_frame = 0; - - /* remove temp regions */ - for (list::iterator iter=rec_regions.begin(); iter != rec_regions.end(); ) - { - list::iterator tmp; - - tmp = iter; - ++tmp; - - /* this will trigger the remove_region_view */ - delete *iter; - - iter = tmp; - } - - rec_regions.clear(); - - // cerr << "\tclear " << rec_rects.size() << " rec rects\n"; - - - /* transport stopped, clear boxes */ - for (vector::iterator iter=rec_rects.begin(); iter != rec_rects.end(); ++iter) { - RecBoxInfo &rect = (*iter); - delete rect.rectangle; - } - - rec_rects.clear(); - - } - } -} - - void StreamView::update_rec_box () { @@ -776,7 +336,7 @@ StreamView::update_rec_box () double xstart; double xend; - switch (_trackview.audio_track()->mode()) { + switch (_trackview.track()->mode()) { case Normal: rect.length = at - rect.start; xstart = _trackview.editor.frame_to_pixel (rect.start); @@ -795,12 +355,12 @@ StreamView::update_rec_box () } } -AudioRegionView* -StreamView::find_view (const AudioRegion& region) +RegionView* +StreamView::find_view (const Region& region) { - for (list::iterator i = region_views.begin(); i != region_views.end(); ++i) { + for (list::iterator i = region_views.begin(); i != region_views.end(); ++i) { - if (&(*i)->region == ®ion) { + if (&(*i)->region() == ®ion) { return *i; } } @@ -808,172 +368,51 @@ StreamView::find_view (const AudioRegion& region) } void -StreamView::foreach_regionview (sigc::slot slot) +StreamView::foreach_regionview (sigc::slot slot) { - for (list::iterator i = region_views.begin(); i != region_views.end(); ++i) { + for (list::iterator i = region_views.begin(); i != region_views.end(); ++i) { slot (*i); } } void -StreamView::foreach_crossfadeview (void (CrossfadeView::*pmf)(void)) +StreamView::set_selected_regionviews (RegionSelection& regions) { - for (list::iterator i = crossfade_views.begin(); i != crossfade_views.end(); ++i) { - ((*i)->*pmf) (); - } -} + bool selected; -void -StreamView::rec_peak_range_ready (jack_nframes_t start, jack_nframes_t cnt, Source * src) -{ - // this is called from the peak building thread - - ENSURE_GUI_THREAD(bind (mem_fun (*this, &StreamView::rec_peak_range_ready), start, cnt, src)); - - if (rec_peak_ready_map.size() == 0 || start+cnt > last_rec_peak_frame) { - last_rec_peak_frame = start + cnt; - } - - rec_peak_ready_map[src] = true; - - if (rec_peak_ready_map.size() == _trackview.get_diskstream()->n_channels()) { - this->update_rec_regions (); - rec_peak_ready_map.clear(); - } -} - -void -StreamView::update_rec_regions () -{ - if (use_rec_regions) { - - uint32_t n = 0; - - for (list::iterator iter = rec_regions.begin(); iter != rec_regions.end(); n++) { - - list::iterator tmp; - - tmp = iter; - ++tmp; - - if (!canvas_item_visible (rec_rects[n].rectangle)) { - /* rect already hidden, this region is done */ - iter = tmp; - continue; + // cerr << _trackview.name() << " (selected = " << regions.size() << ")" << endl; + for (list::iterator i = region_views.begin(); i != region_views.end(); ++i) { + + selected = false; + + for (RegionSelection::iterator ii = regions.begin(); ii != regions.end(); ++ii) { + if (*i == *ii) { + selected = true; } - - AudioRegion * region = (*iter); - jack_nframes_t origlen = region->length(); + } + + // cerr << "\tregion " << (*i)->region().name() << " selected = " << selected << endl; + (*i)->set_selected (selected); + } +} - if (region == rec_regions.back() && rec_active) { - - if (last_rec_peak_frame > region->start()) { - - jack_nframes_t nlen = last_rec_peak_frame - region->start(); - - if (nlen != region->length()) { - - region->freeze (); - region->set_position (_trackview.get_diskstream()->get_capture_start_frame(n), this); - region->set_length (nlen, this); - region->thaw ("updated"); - - if (origlen == 1) { - /* our special initial length */ - add_region_view_internal (region, false); - } - - /* also update rect */ - ArdourCanvas::SimpleRect * rect = rec_rects[n].rectangle; - gdouble xend = _trackview.editor.frame_to_pixel (region->position() + region->length()); - rect->property_x2() = xend; - } - } - - } else { - - jack_nframes_t nlen = _trackview.get_diskstream()->get_captured_frames(n); - - if (nlen != region->length()) { - - if (region->source(0).length() >= region->start() + nlen) { - - region->freeze (); - region->set_position (_trackview.get_diskstream()->get_capture_start_frame(n), this); - region->set_length (nlen, this); - region->thaw ("updated"); - - if (origlen == 1) { - /* our special initial length */ - add_region_view_internal (region, false); - } - - /* also hide rect */ - ArdourCanvas::Item * rect = rec_rects[n].rectangle; - rect->hide(); - - } - } - } - - iter = tmp; +void +StreamView::get_selectables (jack_nframes_t start, jack_nframes_t end, list& results) +{ + for (list::iterator i = region_views.begin(); i != region_views.end(); ++i) { + if ((*i)->region().coverage(start, end) != OverlapNone) { + results.push_back (*i); } } } void -StreamView::show_all_xfades () +StreamView::get_inverted_selectables (Selection& sel, list& results) { - foreach_crossfadeview (&CrossfadeView::show); - crossfades_visible = true; -} - -void -StreamView::hide_all_xfades () -{ - foreach_crossfadeview (&CrossfadeView::hide); - crossfades_visible = false; -} - -void -StreamView::hide_xfades_involving (AudioRegionView& rv) -{ - for (list::iterator i = crossfade_views.begin(); i != crossfade_views.end(); ++i) { - if ((*i)->crossfade.involves (rv.region)) { - (*i)->fake_hide (); + for (list::iterator i = region_views.begin(); i != region_views.end(); ++i) { + if (!sel.regions.contains (*i)) { + results.push_back (*i); } } } -void -StreamView::reveal_xfades_involving (AudioRegionView& rv) -{ - for (list::iterator i = crossfade_views.begin(); i != crossfade_views.end(); ++i) { - if ((*i)->crossfade.involves (rv.region) && (*i)->visible()) { - (*i)->show (); - } - } -} - -void -StreamView::color_handler (ColorID id, uint32_t val) -{ - switch (id) { - case cAudioTrackBase: - if (_trackview.is_audio_track()) { - canvas_rect->property_fill_color_rgba() = val; - } - break; - case cAudioBusBase: - if (!_trackview.is_audio_track()) { - canvas_rect->property_fill_color_rgba() = val; - } - break; - case cAudioTrackOutline: - canvas_rect->property_outline_color_rgba() = val; - break; - - default: - break; - } -} diff --git a/gtk2_ardour/streamview.h b/gtk2_ardour/streamview.h index 00ec2d93f2..5a0e10974f 100644 --- a/gtk2_ardour/streamview.h +++ b/gtk2_ardour/streamview.h @@ -1,5 +1,5 @@ /* - Copyright (C) 2001 Paul Davis + Copyright (C) 2001, 2006 Paul Davis This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -14,8 +14,6 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - $Id$ */ #ifndef __ardour_streamview_h__ @@ -37,141 +35,116 @@ namespace Gdk { namespace ARDOUR { class Route; - class AudioDiskstream; + class Diskstream; class Crossfade; class PeakData; - class AudioRegion; + class Region; class Source; } struct RecBoxInfo { - ArdourCanvas::SimpleRect* rectangle; - jack_nframes_t start; - jack_nframes_t length; + ArdourCanvas::SimpleRect* rectangle; + jack_nframes_t start; + jack_nframes_t length; }; class PublicEditor; class Selectable; -class AudioTimeAxisView; -class AudioRegionView; -class AudioRegionSelection; +class RouteTimeAxisView; +class RegionView; +class RegionSelection; class CrossfadeView; class Selection; class StreamView : public sigc::trackable { - public: - StreamView (AudioTimeAxisView&); - ~StreamView (); +public: + virtual ~StreamView (); - void set_waveform_shape (WaveformShape); + RouteTimeAxisView& trackview() { return _trackview; } - AudioTimeAxisView& trackview() { return _trackview; } + void attach (); void set_zoom_all(); - int set_height (gdouble); int set_position (gdouble x, gdouble y); + virtual int set_height (gdouble); - int set_samples_per_unit (gdouble spp); - gdouble get_samples_per_unit () { return _samples_per_unit; } - - int set_amplitude_above_axis (gdouble app); - gdouble get_amplitude_above_axis () { return _amplitude_above_axis; } - - void set_show_waveforms (bool yn); - void set_show_waveforms_recording (bool yn) { use_rec_regions = yn; } + virtual int set_samples_per_unit (gdouble spp); + gdouble get_samples_per_unit () { return _samples_per_unit; } ArdourCanvas::Item* canvas_item() { return canvas_group; } - sigc::signal AudioRegionViewAdded; - enum ColorTarget { RegionColor, StreamBaseColor }; - void apply_color (Gdk::Color&, ColorTarget t); - void set_selected_regionviews (AudioRegionSelection&); + Gdk::Color get_region_color () const { return region_color; } + void apply_color (Gdk::Color&, ColorTarget t); + + RegionView* find_view (const ARDOUR::Region&); + void foreach_regionview (sigc::slot slot); + + void set_selected_regionviews (RegionSelection&); void get_selectables (jack_nframes_t start, jack_nframes_t end, list&); void get_inverted_selectables (Selection&, list& results); - Gdk::Color get_region_color () const { return region_color; } - void foreach_regionview (sigc::slot slot); - void foreach_crossfadeview (void (CrossfadeView::*pmf)(void)); - - void attach (); + void add_region_view (ARDOUR::Region*); + void region_layered (RegionView*); - void region_layered (AudioRegionView*); + sigc::signal RegionViewAdded; + +protected: + StreamView (RouteTimeAxisView&); - AudioRegionView* find_view (const ARDOUR::AudioRegion&); +//private: (FIXME?) - void show_all_xfades (); - void hide_all_xfades (); - void hide_xfades_involving (AudioRegionView&); - void reveal_xfades_involving (AudioRegionView&); + void transport_changed(); + void rec_enable_changed(); + void sess_rec_enable_changed(); + virtual void setup_rec_box () = 0; + void update_rec_box (); + virtual void update_rec_regions () = 0; + + virtual void add_region_view_internal (ARDOUR::Region*, bool wait_for_waves) = 0; + virtual void remove_region_view (ARDOUR::Region* ); + void remove_rec_region (ARDOUR::Region*); - private: - AudioTimeAxisView& _trackview; + void display_diskstream (ARDOUR::Diskstream* ); + virtual void undisplay_diskstream (); + virtual void redisplay_diskstream () = 0; + void diskstream_changed (); + + void playlist_state_changed (ARDOUR::Change); + virtual void playlist_changed (ARDOUR::Diskstream* ); + virtual void playlist_modified (); + + virtual void color_handler (ColorID, uint32_t) = 0; - ArdourCanvas::Group* canvas_group; + + RouteTimeAxisView& _trackview; + ArdourCanvas::Group* canvas_group; ArdourCanvas::SimpleRect* canvas_rect; /* frame around the whole thing */ - typedef list AudioRegionViewList; - AudioRegionViewList region_views; - - typedef list CrossfadeViewList; - CrossfadeViewList crossfade_views; + typedef list RegionViewList; + RegionViewList region_views; double _samples_per_unit; - double _amplitude_above_axis; - sigc::connection screen_update_connection; - vector rec_rects; - list rec_regions; - bool rec_updating; - bool rec_active; - bool use_rec_regions; - list peak_ready_connections; - jack_nframes_t last_rec_peak_frame; - map rec_peak_ready_map; + sigc::connection screen_update_connection; + vector rec_rects; + list rec_regions; + bool rec_updating; + bool rec_active; + bool use_rec_regions; - void update_rec_box (); - void transport_changed(); - void rec_enable_changed(void* src = 0); - void sess_rec_enable_changed(); - void setup_rec_box (); - void rec_peak_range_ready (jack_nframes_t start, jack_nframes_t cnt, ARDOUR::Source* src); - void update_rec_regions (); - - void add_region_view (ARDOUR::Region*); - void add_region_view_internal (ARDOUR::Region*, bool wait_for_waves); - void remove_region_view (ARDOUR::Region* ); - void remove_rec_region (ARDOUR::Region*); - void remove_audio_region_view (ARDOUR::AudioRegion* ); - void remove_audio_rec_region (ARDOUR::AudioRegion*); - - void display_diskstream (ARDOUR::AudioDiskstream* ); - void undisplay_diskstream (); - void redisplay_diskstream (); - void diskstream_changed (void* ); - void playlist_state_changed (ARDOUR::Change); - void playlist_changed (ARDOUR::AudioDiskstream* ); - void playlist_modified (); - - bool crossfades_visible; - void add_crossfade (ARDOUR::Crossfade*); - void remove_crossfade (ARDOUR::Crossfade*); - - /* XXX why are these different? */ - - Gdk::Color region_color; - uint32_t stream_base_color; - - void color_handler (ColorID, uint32_t); + Gdk::Color region_color; ///< Contained region color + uint32_t stream_base_color; ///< Background color vector playlist_connections; - sigc::connection playlist_change_connection; + sigc::connection playlist_change_connection; }; #endif /* __ardour_streamview_h__ */ + diff --git a/gtk2_ardour/taperegionview.cc b/gtk2_ardour/tape_region_view.cc similarity index 58% rename from gtk2_ardour/taperegionview.cc rename to gtk2_ardour/tape_region_view.cc index 641d067350..bd5ce8af02 100644 --- a/gtk2_ardour/taperegionview.cc +++ b/gtk2_ardour/tape_region_view.cc @@ -30,7 +30,7 @@ #include #include -#include "taperegionview.h" +#include "tape_region_view.h" #include "audio_time_axis.h" #include "gui_thread.h" @@ -42,72 +42,33 @@ using namespace PBD; using namespace Editing; using namespace ArdourCanvas; -TapeAudioRegionView::TapeAudioRegionView (ArdourCanvas::Group *parent, AudioTimeAxisView &tv, +const TimeAxisViewItem::Visibility TapeAudioRegionView::default_tape_visibility + = TimeAxisViewItem::Visibility ( + TimeAxisViewItem::ShowNameHighlight | + TimeAxisViewItem::ShowFrame | + TimeAxisViewItem::HideFrameRight | + TimeAxisViewItem::FullWidthNameHighlight); + +TapeAudioRegionView::TapeAudioRegionView (ArdourCanvas::Group *parent, RouteTimeAxisView &tv, AudioRegion& r, double spu, Gdk::Color& basic_color) : AudioRegionView (parent, tv, r, spu, basic_color, - TimeAxisViewItem::Visibility (TimeAxisViewItem::ShowNameHighlight| - TimeAxisViewItem::ShowFrame| - TimeAxisViewItem::HideFrameLR| - TimeAxisViewItem::FullWidthNameHighlight)) + TimeAxisViewItem::Visibility ((r.position() != 0) ? default_tape_visibility : + TimeAxisViewItem::Visibility (default_tape_visibility|TimeAxisViewItem::HideFrameLeft))) { } void -TapeAudioRegionView::init (double amplitude_above_axis, Gdk::Color& basic_color, bool wfw) +TapeAudioRegionView::init (Gdk::Color& basic_color, bool wfw) { - XMLNode *node; - - editor = 0; - valid = true; - in_destructor = false; - _amplitude_above_axis = amplitude_above_axis; - zero_line = 0; - wait_for_waves = wfw; - _height = 0; - - _flags = 0; - - if ((node = region.extra_xml ("GUI")) != 0) { - set_flags (node); - } else { - _flags = WaveformVisible; - store_flags (); - } - - fade_in_handle = 0; - fade_out_handle = 0; - gain_line = 0; - sync_mark = 0; - - compute_colors (basic_color); - - create_waves (); - - name_highlight->set_data ("regionview", this); - - reset_width_dependent_items ((double) region.length() / samples_per_unit); - - set_height (trackview.height); - - region_muted (); - region_resized (BoundsChanged); - set_waveview_data_src(); - region_locked (); - - /* no events, no state changes */ - - set_colors (); - - // ColorChanged.connect (mem_fun (*this, &AudioRegionView::color_handler)); + AudioRegionView::init(basic_color, wfw); /* every time the wave data changes and peaks are ready, redraw */ - - for (uint32_t n = 0; n < region.n_channels(); ++n) { - region.source(n).PeaksReady.connect (bind (mem_fun(*this, &TapeAudioRegionView::update), n)); + for (uint32_t n = 0; n < audio_region().n_channels(); ++n) { + audio_region().source(n).PeaksReady.connect (bind (mem_fun(*this, &TapeAudioRegionView::update), n)); } } @@ -129,7 +90,7 @@ TapeAudioRegionView::update (uint32_t n) /* this triggers a cache invalidation and redraw in the waveview */ - waves[n]->property_data_src() = ®ion; + waves[n]->property_data_src() = &_region; } void diff --git a/gtk2_ardour/taperegionview.h b/gtk2_ardour/tape_region_view.h similarity index 86% rename from gtk2_ardour/taperegionview.h rename to gtk2_ardour/tape_region_view.h index 3e23e0fc19..ed3852e3a9 100644 --- a/gtk2_ardour/taperegionview.h +++ b/gtk2_ardour/tape_region_view.h @@ -23,23 +23,25 @@ #include -#include "regionview.h" +#include "audio_region_view.h" class TapeAudioRegionView : public AudioRegionView { public: TapeAudioRegionView (ArdourCanvas::Group *, - AudioTimeAxisView&, + RouteTimeAxisView&, ARDOUR::AudioRegion&, double initial_samples_per_unit, Gdk::Color& base_color); ~TapeAudioRegionView (); protected: - void init (double amplitude_above_axis, Gdk::Color& base_color, bool wait_for_waves); + void init (Gdk::Color& base_color, bool wait_for_waves); void set_frame_color (); void update (uint32_t n); + + static const TimeAxisViewItem::Visibility default_tape_visibility; }; #endif /* __gtk_ardour_tape_audio_region_view_h__ */ diff --git a/gtk2_ardour/time_axis_view.cc b/gtk2_ardour/time_axis_view.cc index b5ab5baa10..6261241139 100644 --- a/gtk2_ardour/time_axis_view.cc +++ b/gtk2_ardour/time_axis_view.cc @@ -128,6 +128,7 @@ TimeAxisView::TimeAxisView (ARDOUR::Session& sess, PublicEditor& ed, TimeAxisVie controls_table.attach (name_hbox, 0, 4, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); controls_table.show_all (); + controls_table.set_no_show_all (); controls_vbox.pack_start (controls_table, false, false); controls_vbox.show (); @@ -661,8 +662,6 @@ TimeAxisView::show_selection (TimeSelection& ts) void TimeAxisView::reshow_selection (TimeSelection& ts) { - cerr << name() << ": reshow selection" << endl; - show_selection (ts); for (vector::iterator i = children.begin(); i != children.end(); ++i) { @@ -882,7 +881,7 @@ TimeAxisView::reset_height() set_height_pixels (height); for (vector::iterator i = children.begin(); i != children.end(); ++i) { - (*i)->set_height ((TrackHeight)(*i)->height); + (*i)->set_height_pixels ((TrackHeight)(*i)->height); } } diff --git a/gtk2_ardour/time_axis_view.h b/gtk2_ardour/time_axis_view.h index c607c78166..31ff3d84ee 100644 --- a/gtk2_ardour/time_axis_view.h +++ b/gtk2_ardour/time_axis_view.h @@ -54,7 +54,7 @@ namespace Gtk { } class PublicEditor; -class AudioRegionSelection; +class RegionSelection; class TimeSelection; class PointSelection; class TimeAxisViewItem; @@ -183,7 +183,7 @@ class TimeAxisView : public virtual AxisView virtual bool cut_copy_clear (Selection&, Editing::CutCopyOp) { return false; } virtual bool paste (jack_nframes_t, float times, Selection&, size_t nth) { return false; } - virtual void set_selected_regionviews (AudioRegionSelection&) {} + virtual void set_selected_regionviews (RegionSelection&) {} virtual void set_selected_points (PointSelection&) {} virtual ARDOUR::Region* find_next_region (jack_nframes_t pos, ARDOUR::RegionPoint, int32_t dir) { diff --git a/gtk2_ardour/time_axis_view_item.cc b/gtk2_ardour/time_axis_view_item.cc index abab306a84..28fafcaa09 100644 --- a/gtk2_ardour/time_axis_view_item.cc +++ b/gtk2_ardour/time_axis_view_item.cc @@ -137,8 +137,12 @@ TimeAxisViewItem::TimeAxisViewItem(const string & it_name, ArdourCanvas::Group& uint32_t outline_what = 0x1|0x2|0x4|0x8; - if (visibility & HideFrameLR) { - outline_what &= ~(0x1 | 0x2); + if (visibility & HideFrameLeft) { + outline_what &= ~(0x1); + } + + if (visibility & HideFrameRight) { + outline_what &= ~(0x2); } if (visibility & HideFrameTB) { diff --git a/gtk2_ardour/time_axis_view_item.h b/gtk2_ardour/time_axis_view_item.h index b23350eef7..9ddb06876a 100644 --- a/gtk2_ardour/time_axis_view_item.h +++ b/gtk2_ardour/time_axis_view_item.h @@ -316,9 +316,10 @@ class TimeAxisViewItem : public Selectable ShowNameHighlight = 0x2, ShowNameText = 0x4, ShowHandles = 0x8, - HideFrameLR = 0x10, - HideFrameTB = 0x20, - FullWidthNameHighlight = 0x40 + HideFrameLeft = 0x10, + HideFrameRight = 0x20, + HideFrameTB = 0x40, + FullWidthNameHighlight = 0x80 }; /** diff --git a/gtk2_ardour/utils.cc b/gtk2_ardour/utils.cc index 91cb7ad58b..ef90c34755 100644 --- a/gtk2_ardour/utils.cc +++ b/gtk2_ardour/utils.cc @@ -215,7 +215,7 @@ get_font_for_style (string widgetname) { Gtk::Window window (WINDOW_TOPLEVEL); Gtk::Label foobar; - Glib::RefPtr

Bo+o?D_4SxjY=oBL`4XfJ+I7YPPw-fL? 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é-m$*=@w@jf<3j|aFH}C2$|H+TaztgIMO_#p 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%0D~t?5J}fglB}tH$da~#Iqpp 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