Audacity  2.2.2
AudioIO.cpp
Go to the documentation of this file.
1 /**********************************************************************
2 
3  Audacity: A Digital Audio Editor
4 
5  AudioIO.cpp
6 
7  Copyright 2000-2004:
8  Dominic Mazzoni
9  Joshua Haberman
10  Markus Meyer
11  Matt Brubeck
12 
13  This program is free software; you can redistribute it and/or modify it
14  under the terms of the GNU General Public License as published by the Free
15  Software Foundation; either version 2 of the License, or (at your option)
16  any later version.
17 
18 ********************************************************************//****************************************************************//****************************************************************//****************************************************************//*******************************************************************/
406 
407 #include "Audacity.h"
408 #include "Experimental.h"
409 #include "AudioIO.h"
410 #include "float_cast.h"
411 
412 #include <cfloat>
413 #include <math.h>
414 #include <stdlib.h>
415 #include <algorithm>
416 
417 #ifdef __WXMSW__
418 #include <malloc.h>
419 #endif
420 
421 #ifdef HAVE_ALLOCA_H
422 #include <alloca.h>
423 #endif
424 
425 #if USE_PORTMIXER
426 #include "portmixer.h"
427 #endif
428 
429 #include <wx/log.h>
430 #include <wx/textctrl.h>
431 #include <wx/timer.h>
432 #include <wx/intl.h>
433 #include <wx/debug.h>
434 #include <wx/sstream.h>
435 #include <wx/txtstrm.h>
436 
437 #include "AudacityApp.h"
438 #include "AudacityException.h"
439 #include "Mix.h"
440 #include "MixerBoard.h"
441 #include "Resample.h"
442 #include "RingBuffer.h"
443 #include "prefs/GUISettings.h"
444 #include "Prefs.h"
445 #include "Project.h"
446 #include "TimeTrack.h"
447 #include "WaveTrack.h"
448 #include "AutoRecovery.h"
449 
450 #include "prefs/QualityPrefs.h"
451 #include "toolbars/ControlToolBar.h"
452 #include "widgets/Meter.h"
453 #include "widgets/ErrorDialog.h"
454 #include "widgets/Warning.h"
455 
456 #ifdef EXPERIMENTAL_MIDI_OUT
457  #define MIDI_SLEEP 10 /* milliseconds */
458  // how long do we think the thread that fills MIDI buffers,
459  // if it is separate from the portaudio thread,
460  // might be delayed due to other threads?
461  #ifdef USE_MIDI_THREAD
462  #define THREAD_LATENCY 10 /* milliseconds */
463  #else
464  #define THREAD_LATENCY 0 /* milliseconds */
465  #endif
466  #define ROUND(x) (int) ((x)+0.5)
467  //#include <string.h>
468  #include "../lib-src/portmidi/pm_common/portmidi.h"
469  #include "../lib-src/portaudio-v19/src/common/pa_util.h"
470  #include "NoteTrack.h"
471 #endif
472 
473 #ifdef EXPERIMENTAL_AUTOMATED_INPUT_LEVEL_ADJUSTMENT
474  #define LOWER_BOUND 0.0
475  #define UPPER_BOUND 1.0
476 #endif
477 
478 using std::max;
479 using std::min;
480 
481 std::unique_ptr<AudioIO> ugAudioIO;
483 
484 wxDEFINE_EVENT(EVT_AUDIOIO_PLAYBACK, wxCommandEvent);
485 wxDEFINE_EVENT(EVT_AUDIOIO_CAPTURE, wxCommandEvent);
486 wxDEFINE_EVENT(EVT_AUDIOIO_MONITOR, wxCommandEvent);
487 
488 // static
491 std::vector<long> AudioIO::mCachedPlaybackRates;
493 std::vector<long> AudioIO::mCachedCaptureRates;
494 std::vector<long> AudioIO::mCachedSampleRates;
495 double AudioIO::mCachedBestRateIn = 0.0;
497 
498 enum {
499  // This is the least positive latency we can
500  // specify to Pm_OpenOutput, 1 ms, which prevents immediate
501  // scheduling of events:
503 };
504 
505 #ifdef EXPERIMENTAL_SCRUBBING_SUPPORT
506 
507 #include "tracks/ui/Scrubbing.h"
508 
509 #ifdef __WXGTK__
510  // Might #define this for a useful thing on Linux
511  #undef REALTIME_ALSA_THREAD
512 #else
513  // never on the other operating systems
514  #undef REALTIME_ALSA_THREAD
515 #endif
516 
517 #ifdef REALTIME_ALSA_THREAD
518 #include "pa_linux_alsa.h"
519 #endif
520 
521 
522 /*
523 This work queue class, with the aid of the playback ring
524 buffers, coordinates three threads during scrub play:
525 
526 The UI thread which specifies scrubbing intervals to play,
527 
528 The Audio thread which consumes those specifications a first time
529 and fills the ring buffers with samples for play,
530 
531 The PortAudio thread which consumes from the ring buffers, then
532 also consumes a second time from this queue,
533 to figure out how to update mTime
534 
535 -- which the UI thread, in turn, uses to redraw the play head indicator
536 in the right place.
537 
538 Audio produces samples for PortAudio, which consumes them, both in
539 approximate real time. The UI thread might go idle and so the others
540 might catch up, emptying the queue and causing scrub to go silent.
541 The UI thread will not normally outrun the others -- because InitEntry()
542 limits the real time duration over which each enqueued interval will play.
543 So a small, fixed queue size should be adequate.
544 */
546 {
547  ScrubQueue(double t0, double t1, wxLongLong startClockMillis,
548  double rate, long maxDebt,
549  const ScrubbingOptions &options)
550  : mTrailingIdx(0)
551  , mMiddleIdx(1)
552  , mLeadingIdx(1)
553  , mRate(rate)
554  , mLastScrubTimeMillis(startClockMillis)
555  , mMaxDebt { maxDebt }
556  , mUpdating()
557  {
558  const auto s0 = std::max(options.minSample, std::min(options.maxSample,
559  sampleCount(lrint(t0 * mRate))
560  ));
561  const auto s1 = sampleCount(lrint(t1 * mRate));
562  Duration dd { *this };
563  auto actualDuration = std::max(sampleCount{1}, dd.duration);
564  auto success = mEntries[mMiddleIdx].Init(nullptr,
565  s0, s1, actualDuration, options);
566  if (success)
567  ++mLeadingIdx;
568  else {
569  // If not, we can wait to enqueue again later
570  dd.Cancel();
571  }
572 
573  // So the play indicator starts out unconfused:
574  {
575  Entry &entry = mEntries[mTrailingIdx];
576  entry.mS0 = entry.mS1 = s0;
577  entry.mPlayed = entry.mDuration = 1;
578  }
579  }
581 
582  double LastTimeInQueue() const
583  {
584  // Needed by the main thread sometimes
585  wxMutexLocker locker(mUpdating);
586  const Entry &previous = mEntries[(mLeadingIdx + Size - 1) % Size];
587  return previous.mS1.as_double() / mRate;
588  }
589 
590  // This is for avoiding deadlocks while starting a scrub:
591  // Audio stream needs to be unblocked
592  void Nudge()
593  {
594  wxMutexLocker locker(mUpdating);
595  mNudged = true;
596  mAvailable.Signal();
597  }
598 
599  bool Producer(double end, const ScrubbingOptions &options)
600  {
601  // Main thread indicates a scrubbing interval
602 
603  // MAY ADVANCE mLeadingIdx, BUT IT NEVER CATCHES UP TO mTrailingIdx.
604 
605  wxMutexLocker locker(mUpdating);
606  bool result = true;
607  unsigned next = (mLeadingIdx + 1) % Size;
608  if (next != mTrailingIdx)
609  {
610  auto current = &mEntries[mLeadingIdx];
611  auto previous = &mEntries[(mLeadingIdx + Size - 1) % Size];
612 
613  // Use the previous end as NEW start.
614  const auto s0 = previous->mS1;
615  Duration dd { *this };
616  const auto &origDuration = dd.duration;
617  if (origDuration <= 0)
618  return false;
619 
620  auto actualDuration = origDuration;
621  const sampleCount s1 ( options.enqueueBySpeed
622  ? s0.as_double() +
623  lrint(origDuration.as_double() * end) // end is a speed
624  : lrint(end * mRate) // end is a time
625  );
626  auto success =
627  current->Init(previous, s0, s1, actualDuration, options);
628  if (success)
629  mLeadingIdx = next;
630  else {
631  dd.Cancel();
632  return false;
633  }
634 
635  // Fill up the queue with some silence if there was trimming
636  wxASSERT(actualDuration <= origDuration);
637  if (actualDuration < origDuration) {
638  next = (mLeadingIdx + 1) % Size;
639  if (next != mTrailingIdx) {
640  previous = &mEntries[(mLeadingIdx + Size - 1) % Size];
641  current = &mEntries[mLeadingIdx];
642  current->InitSilent(*previous, origDuration - actualDuration);
643  mLeadingIdx = next;
644  }
645  else
646  // Oops, can't enqueue the silence -- so do what?
647  ;
648  }
649 
650  mAvailable.Signal();
651  return result;
652  }
653  else
654  {
655  // ??
656  // Queue wasn't long enough. Write side (UI thread)
657  // has overtaken the trailing read side (PortAudio thread), despite
658  // my comments above! We lose some work requests then.
659  // wxASSERT(false);
660  return false;
661  }
662  }
663 
664  void Transformer(sampleCount &startSample, sampleCount &endSample,
665  sampleCount &duration,
666  Maybe<wxMutexLocker> &cleanup)
667  {
668  // Audio thread is ready for the next interval.
669 
670  // MAY ADVANCE mMiddleIdx, WHICH MAY EQUAL mLeadingIdx, BUT DOES NOT PASS IT.
671 
672  bool checkDebt = false;
673  if (!cleanup) {
674  cleanup.create(mUpdating);
675 
676  // Check for cancellation of work only when re-enetering the cricial section
677  checkDebt = true;
678  }
679  while(!mNudged && mMiddleIdx == mLeadingIdx)
680  mAvailable.Wait();
681 
682  mNudged = false;
683 
684  auto now = ::wxGetLocalTimeMillis();
685 
686  if (checkDebt &&
687  mLastTransformerTimeMillis >= 0 && // Not the first time for this scrub
688  mMiddleIdx != mLeadingIdx) {
689  // There is work in the queue, but if Producer is outrunning us, discard some,
690  // which may make a skip yet keep playback better synchronized with user gestures.
691  const auto interval = (now - mLastTransformerTimeMillis).ToDouble() / 1000.0;
692  //const Entry &previous = mEntries[(mMiddleIdx + Size - 1) % Size];
693  const auto deficit =
694  static_cast<long>(interval * mRate) - // Samples needed in the last time interval
695  mCredit; // Samples done in the last time interval
696  mCredit = 0;
697  mDebt += deficit;
698  auto toDiscard = mDebt - mMaxDebt;
699  while (toDiscard > 0 && mMiddleIdx != mLeadingIdx) {
700  // Cancel some debt (discard some NEW work)
701  auto &entry = mEntries[mMiddleIdx];
702  auto &dur = entry.mDuration;
703  if (toDiscard >= dur) {
704  // Discard entire queue entry
705  mDebt -= dur;
706  toDiscard -= dur;
707  dur = 0; // So Consumer() will handle abandoned entry correctly
708  mMiddleIdx = (mMiddleIdx + 1) % Size;
709  }
710  else {
711  // Adjust the start time
712  auto &start = entry.mS0;
713  const auto end = entry.mS1;
714  const auto ratio = toDiscard.as_double() / dur.as_double();
715  const sampleCount adjustment(
716  std::abs((end - start).as_long_long()) * ratio
717  );
718  if (start <= end)
719  start += adjustment;
720  else
721  start -= adjustment;
722 
723  mDebt -= toDiscard;
724  dur -= toDiscard;
725  toDiscard = 0;
726  }
727  }
728  }
729 
730  if (mMiddleIdx != mLeadingIdx) {
731  // There is still work in the queue, after cancelling debt
732  Entry &entry = mEntries[mMiddleIdx];
733  startSample = entry.mS0;
734  endSample = entry.mS1;
735  duration = entry.mDuration;
736  mMiddleIdx = (mMiddleIdx + 1) % Size;
737  mCredit += duration;
738  }
739  else {
740  // We got the shut-down signal, or we got nudged, or we discarded all the work.
741  startSample = endSample = duration = -1L;
742  }
743 
744  if (checkDebt)
746  }
747 
748  double Consumer(unsigned long frames)
749  {
750  // Portaudio thread consumes samples and must update
751  // the time for the indicator. This finds the time value.
752 
753  // MAY ADVANCE mTrailingIdx, BUT IT NEVER CATCHES UP TO mMiddleIdx.
754 
755  wxMutexLocker locker(mUpdating);
756 
757  // Mark entries as partly or fully "consumed" for
758  // purposes of mTime update. It should not happen that
759  // frames exceed the total of samples to be consumed,
760  // but in that case we just use the t1 of the latest entry.
761  while (1)
762  {
763  Entry *pEntry = &mEntries[mTrailingIdx];
764  auto remaining = pEntry->mDuration - pEntry->mPlayed;
765  if (frames >= remaining)
766  {
767  // remaining is not more than frames
768  frames -= remaining.as_size_t();
769  pEntry->mPlayed = pEntry->mDuration;
770  }
771  else
772  {
773  pEntry->mPlayed += frames;
774  break;
775  }
776  const unsigned next = (mTrailingIdx + 1) % Size;
777  if (next == mMiddleIdx)
778  break;
779  mTrailingIdx = next;
780  }
782  }
783 
784 private:
785  struct Entry
786  {
788  : mS0(0)
789  , mS1(0)
790  , mGoal(0)
791  , mDuration(0)
792  , mPlayed(0)
793  {}
794 
795  bool Init(Entry *previous, sampleCount s0, sampleCount s1,
796  sampleCount &duration /* in/out */,
797  const ScrubbingOptions &options)
798  {
799  const bool &adjustStart = options.adjustStart;
800 
801  wxASSERT(duration > 0);
802  double speed =
803  (std::abs((s1 - s0).as_long_long())) / duration.as_double();
804  bool adjustedSpeed = false;
805 
806  auto minSpeed = std::min(options.minSpeed, options.maxSpeed);
807  wxASSERT(minSpeed == options.minSpeed);
808 
809  // May change the requested speed and duration
810  if (!adjustStart && speed > options.maxSpeed)
811  {
812  // Reduce speed to the maximum selected in the user interface.
813  speed = options.maxSpeed;
814  mGoal = s1;
815  adjustedSpeed = true;
816  }
817  else if (!adjustStart &&
818  previous &&
819  previous->mGoal >= 0 &&
820  previous->mGoal == s1)
821  {
822  // In case the mouse has not moved, and playback
823  // is catching up to the mouse at maximum speed,
824  // continue at no less than maximum. (Without this
825  // the final catch-up can make a slow scrub interval
826  // that drops the pitch and sounds wrong.)
827  minSpeed = options.maxSpeed;
828  mGoal = s1;
829  adjustedSpeed = true;
830  }
831  else
832  mGoal = -1;
833 
834  if (speed < minSpeed) {
835  // Trim the duration.
836  duration = std::max(0L, lrint(speed * duration.as_double() / minSpeed));
837  speed = minSpeed;
838  adjustedSpeed = true;
839  }
840 
842  // Mixers were set up to go only so slowly, not slower.
843  // This will put a request for some silence in the work queue.
844  adjustedSpeed = true;
845  speed = 0.0;
846  }
847 
848  // May change s1 or s0 to match speed change or stay in bounds of the project
849 
850  if (adjustedSpeed && !adjustStart)
851  {
852  // adjust s1
853  const sampleCount diff = lrint(speed * duration.as_double());
854  if (s0 < s1)
855  s1 = s0 + diff;
856  else
857  s1 = s0 - diff;
858  }
859 
860  bool silent = false;
861 
862  // Adjust s1 (again), and duration, if s1 is out of bounds,
863  // or abandon if a stutter is too short.
864  // (Assume s0 is in bounds, because it equals the last scrub's s1 which was checked.)
865  if (s1 != s0)
866  {
867  auto newDuration = duration;
868  const auto newS1 = std::max(options.minSample, std::min(options.maxSample, s1));
869  if(s1 != newS1)
870  newDuration = std::max( sampleCount{ 0 },
871  sampleCount(
872  duration.as_double() * (newS1 - s0).as_double() /
873  (s1 - s0).as_double()
874  )
875  );
876  // When playback follows a fast mouse movement by "stuttering"
877  // at maximum playback, don't make stutters too short to be useful.
878  if (options.adjustStart && newDuration < options.minStutter)
879  return false;
880  else if (newDuration == 0) {
881  // Enqueue a silent scrub with s0 == s1
882  silent = true;
883  s1 = s0;
884  }
885  else if (s1 != newS1) {
886  // Shorten
887  duration = newDuration;
888  s1 = newS1;
889  }
890  }
891 
892  if (adjustStart && !silent)
893  {
894  // Limit diff because this is seeking.
895  const sampleCount diff =
896  lrint(std::min(options.maxSpeed, speed) * duration.as_double());
897  if (s0 < s1)
898  s0 = s1 - diff;
899  else
900  s0 = s1 + diff;
901  }
902 
903  mS0 = s0;
904  mS1 = s1;
905  mPlayed = 0;
906  mDuration = duration;
907  return true;
908  }
909 
910  void InitSilent(const Entry &previous, sampleCount duration)
911  {
912  mGoal = previous.mGoal;
913  mS0 = mS1 = previous.mS1;
914  mPlayed = 0;
915  mDuration = duration;
916  }
917 
918  double GetTime(double rate) const
919  {
920  return
921  (mS0.as_double() +
922  (mS1 - mS0).as_double() * mPlayed.as_double() / mDuration.as_double())
923  / rate;
924  }
925 
926  // These sample counts are initialized in the UI, producer, thread:
930  // This field is initialized in the UI thread too, and
931  // this work queue item corresponds to exactly this many samples of
932  // playback output:
934 
935  // The middleman Audio thread does not change these entries, but only
936  // changes indices in the queue structure.
937 
938  // This increases from 0 to mDuration as the PortAudio, consumer,
939  // thread catches up. When they are equal, this entry can be discarded:
941  };
942 
943  struct Duration {
944  Duration (ScrubQueue &queue_) : queue(queue_) {}
946  {
947  if(!cancelled)
949  }
950 
951  void Cancel() { cancelled = true; }
952 
954  const wxLongLong clockTime { ::wxGetLocalTimeMillis() };
955  const sampleCount duration { static_cast<long long>
956  (queue.mRate * (clockTime - queue.mLastScrubTimeMillis).ToDouble() / 1000.0)
957  };
958  bool cancelled { false };
959  };
960 
961  enum { Size = 10 };
963  unsigned mTrailingIdx;
964  unsigned mMiddleIdx;
965  unsigned mLeadingIdx;
966  const double mRate;
968 
969  wxLongLong mLastTransformerTimeMillis { -1LL };
972  const long mMaxDebt;
973 
974  mutable wxMutex mUpdating;
975  mutable wxCondition mAvailable { mUpdating };
976  bool mNudged { false };
977 };
978 #endif
979 
980 #ifdef EXPERIMENTAL_MIDI_OUT
981 // return the system time as a double
982 static double streamStartTime = 0; // bias system time to small number
983 
984 static double SystemTime(bool usingAlsa)
985 {
986 #ifdef __WXGTK__
987  if (usingAlsa) {
988  struct timespec now;
989  // CLOCK_MONOTONIC_RAW is unaffected by NTP or adj-time
990  clock_gettime(CLOCK_MONOTONIC_RAW, &now);
991  //return now.tv_sec + now.tv_nsec * 0.000000001;
992  return (now.tv_sec + now.tv_nsec * 0.000000001) - streamStartTime;
993  }
994 #else
995  static_cast<void>(usingAlsa);//compiler food.
996 #endif
997 
998  return PaUtil_GetTime() - streamStartTime;
999 }
1000 #endif
1001 
1002 const int AudioIO::StandardRates[] = {
1003  8000,
1004  11025,
1005  16000,
1006  22050,
1007  32000,
1008  44100,
1009  48000,
1010  88200,
1011  96000,
1012  176400,
1013  192000,
1014  352800,
1015  384000
1016 };
1018  sizeof(AudioIO::StandardRates[0]);
1019 const int AudioIO::RatesToTry[] = {
1020  8000,
1021  9600,
1022  11025,
1023  12000,
1024  15000,
1025  16000,
1026  22050,
1027  24000,
1028  32000,
1029  44100,
1030  48000,
1031  88200,
1032  96000,
1033  176400,
1034  192000,
1035  352800,
1036  384000
1037 };
1038 const int AudioIO::NumRatesToTry = sizeof(AudioIO::RatesToTry) /
1039  sizeof(AudioIO::RatesToTry[0]);
1040 
1041 int audacityAudioCallback(const void *inputBuffer, void *outputBuffer,
1042  unsigned long framesPerBuffer,
1043  const PaStreamCallbackTimeInfo *timeInfo,
1044  PaStreamCallbackFlags statusFlags, void *userData );
1045 
1047 //
1048 // class AudioThread - declaration and glue code
1049 //
1051 
1052 #ifdef __WXMAC__
1053 
1054 // On Mac OS X, it's better not to use the wxThread class.
1055 // We use our own implementation based on pthreads instead.
1056 
1057 #include <pthread.h>
1058 #include <time.h>
1059 
1060 class AudioThread {
1061  public:
1062  typedef int ExitCode;
1063  AudioThread() { mDestroy = false; mThread = NULL; }
1064  virtual ExitCode Entry();
1065  void Create() {}
1066  void Delete() {
1067  mDestroy = true;
1068  pthread_join(mThread, NULL);
1069  }
1070  bool TestDestroy() { return mDestroy; }
1071  void Sleep(int ms) {
1072  struct timespec spec;
1073  spec.tv_sec = 0;
1074  spec.tv_nsec = ms * 1000 * 1000;
1075  nanosleep(&spec, NULL);
1076  }
1077  static void *callback(void *p) {
1078  AudioThread *th = (AudioThread *)p;
1079  return (void *)th->Entry();
1080  }
1081  void Run() {
1082  pthread_create(&mThread, NULL, callback, this);
1083  }
1084  private:
1085  bool mDestroy;
1086  pthread_t mThread;
1087 
1088 };
1089 
1090 #else
1091 
1092 // The normal wxThread-derived AudioThread class for all other
1093 // platforms:
1094 class AudioThread /* not final */ : public wxThread {
1095  public:
1096  AudioThread():wxThread(wxTHREAD_JOINABLE) {}
1097  ExitCode Entry() override;
1098 };
1099 
1100 #endif
1101 
1102 #ifdef EXPERIMENTAL_MIDI_OUT
1103 class MidiThread final : public AudioThread {
1104  public:
1105  ExitCode Entry() override;
1106 };
1107 #endif
1108 
1109 
1111 //
1112 // UI Thread Context
1113 //
1115 
1117 {
1118  ugAudioIO.reset(safenew AudioIO());
1119  gAudioIO = ugAudioIO.get();
1120  gAudioIO->mThread->Run();
1121 #ifdef EXPERIMENTAL_MIDI_OUT
1122 #ifdef USE_MIDI_THREAD
1123  gAudioIO->mMidiThread->Run();
1124 #endif
1125 #endif
1126 
1127  // Make sure device prefs are initialized
1128  if (gPrefs->Read(wxT("AudioIO/RecordingDevice"), wxT("")) == wxT("")) {
1129  int i = AudioIO::getRecordDevIndex();
1130  const PaDeviceInfo *info = Pa_GetDeviceInfo(i);
1131  if (info) {
1132  gPrefs->Write(wxT("/AudioIO/RecordingDevice"), DeviceName(info));
1133  gPrefs->Write(wxT("/AudioIO/Host"), HostName(info));
1134  }
1135  }
1136 
1137  if (gPrefs->Read(wxT("AudioIO/PlaybackDevice"), wxT("")) == wxT("")) {
1138  int i = AudioIO::getPlayDevIndex();
1139  const PaDeviceInfo *info = Pa_GetDeviceInfo(i);
1140  if (info) {
1141  gPrefs->Write(wxT("/AudioIO/PlaybackDevice"), DeviceName(info));
1142  gPrefs->Write(wxT("/AudioIO/Host"), HostName(info));
1143  }
1144  }
1145 
1146  gPrefs->Flush();
1147 }
1148 
1150 {
1151  ugAudioIO.reset();
1152 }
1153 
1154 wxString DeviceName(const PaDeviceInfo* info)
1155 {
1156  wxString infoName = wxSafeConvertMB2WX(info->name);
1157 
1158  return infoName;
1159 }
1160 
1161 wxString HostName(const PaDeviceInfo* info)
1162 {
1163  wxString hostapiName = wxSafeConvertMB2WX(Pa_GetHostApiInfo(info->hostApi)->name);
1164 
1165  return hostapiName;
1166 }
1167 
1168 bool AudioIO::ValidateDeviceNames(const wxString &play, const wxString &rec)
1169 {
1170  const PaDeviceInfo *pInfo = Pa_GetDeviceInfo(AudioIO::getPlayDevIndex(play));
1171  const PaDeviceInfo *rInfo = Pa_GetDeviceInfo(AudioIO::getRecordDevIndex(rec));
1172 
1173  if (!pInfo || !rInfo || pInfo->hostApi != rInfo->hostApi) {
1174  return false;
1175  }
1176 
1177  return true;
1178 }
1179 
1181 {
1185  mPortStreamV19 = NULL;
1186 
1187 #ifdef EXPERIMENTAL_MIDI_OUT
1188  mMidiStream = NULL;
1189  mMidiThreadFillBuffersLoopRunning = false;
1190  mMidiThreadFillBuffersLoopActive = false;
1191  mMidiStreamActive = false;
1192  mSendMidiState = false;
1193  mIterator = NULL;
1194 
1195  mNumFrames = 0;
1196  mNumPauseFrames = 0;
1197 #endif
1198 
1199 #ifdef EXPERIMENTAL_AUTOMATED_INPUT_LEVEL_ADJUSTMENT
1200  mAILAActive = false;
1201 #endif
1202  mStreamToken = 0;
1203 
1204  mLastPaError = paNoError;
1205 
1206  mLastRecordingOffset = 0.0;
1207  mNumCaptureChannels = 0;
1208  mPaused = false;
1210 
1211  mListener = NULL;
1212  mUpdateMeters = false;
1213  mUpdatingMeters = false;
1214 
1215  mOwningProject = NULL;
1216  mOutputMeter = NULL;
1217 
1218  PaError err = Pa_Initialize();
1219 
1220  if (err != paNoError) {
1221  wxString errStr = _("Could not find any audio devices.\n");
1222  errStr += _("You will not be able to play or record audio.\n\n");
1223  wxString paErrStr = LAT1CTOWX(Pa_GetErrorText(err));
1224  if (!paErrStr.IsEmpty())
1225  errStr += _("Error: ")+paErrStr;
1226  // XXX: we are in libaudacity, popping up dialogs not allowed! A
1227  // long-term solution will probably involve exceptions
1228  AudacityMessageBox(errStr, _("Error Initializing Audio"), wxICON_ERROR|wxOK);
1229 
1230  // Since PortAudio is not initialized, all calls to PortAudio
1231  // functions will fail. This will give reasonable behavior, since
1232  // the user will be able to do things not relating to audio i/o,
1233  // but any attempt to play or record will simply fail.
1234  }
1235 
1236 #ifdef EXPERIMENTAL_MIDI_OUT
1237  PmError pmErr = Pm_Initialize();
1238 
1239  if (pmErr != pmNoError) {
1240  wxString errStr =
1241  _("There was an error initializing the midi i/o layer.\n");
1242  errStr += _("You will not be able to play midi.\n\n");
1243  wxString pmErrStr = LAT1CTOWX(Pm_GetErrorText(pmErr));
1244  if (!pmErrStr.empty())
1245  errStr += _("Error: ") + pmErrStr;
1246  // XXX: we are in libaudacity, popping up dialogs not allowed! A
1247  // long-term solution will probably involve exceptions
1248  AudacityMessageBox(errStr, _("Error Initializing Midi"), wxICON_ERROR|wxOK);
1249 
1250  // Same logic for PortMidi as described above for PortAudio
1251  }
1252 
1253 #ifdef USE_MIDI_THREAD
1254  mMidiThread = std::make_unique<MidiThread>();
1255  mMidiThread->Create();
1256 #endif
1257 
1258 #endif
1259 
1260  // Start thread
1261  mThread = std::make_unique<AudioThread>();
1262  mThread->Create();
1263 
1264 #if defined(USE_PORTMIXER)
1265  mPortMixer = NULL;
1266  mPreviousHWPlaythrough = -1.0;
1268 #else
1269  mEmulateMixerOutputVol = true;
1270  mMixerOutputVol = 1.0;
1271  mInputMixerWorks = false;
1272 #endif
1273 
1275 
1276 #ifdef EXPERIMENTAL_SCRUBBING_SUPPORT
1277  mScrubQueue = NULL;
1278  mScrubDuration = 0;
1279  mSilentScrub = false;
1280 #endif
1281 }
1282 
1284 {
1285 #if defined(USE_PORTMIXER)
1286  if (mPortMixer) {
1287  #if __WXMAC__
1288  if (Px_SupportsPlaythrough(mPortMixer) && mPreviousHWPlaythrough >= 0.0)
1289  Px_SetPlaythrough(mPortMixer, mPreviousHWPlaythrough);
1290  mPreviousHWPlaythrough = -1.0;
1291  #endif
1292  Px_CloseMixer(mPortMixer);
1293  mPortMixer = NULL;
1294  }
1295 #endif
1296 
1297  // FIXME: ? TRAP_ERR. Pa_Terminate probably OK if err without reporting.
1298  Pa_Terminate();
1299 
1300 #ifdef EXPERIMENTAL_MIDI_OUT
1301  Pm_Terminate();
1302 
1303  /* Delete is a "graceful" way to stop the thread.
1304  (Kill is the not-graceful way.) */
1305 
1306 #ifdef USE_MIDI_THREAD
1307  mMidiThread->Delete();
1308  mMidiThread.reset();
1309 #endif
1310 
1311 #endif
1312 
1313  /* Delete is a "graceful" way to stop the thread.
1314  (Kill is the not-graceful way.) */
1315 
1316  // This causes reentrancy issues during application shutdown
1317  // wxTheApp->Yield();
1318 
1319  mThread->Delete();
1320  mThread.reset();
1321 
1322  gAudioIO = nullptr;
1323 }
1324 
1325 void AudioIO::SetMixer(int inputSource)
1326 {
1327 #if defined(USE_PORTMIXER)
1328  int oldRecordSource = Px_GetCurrentInputSource(mPortMixer);
1329  if ( inputSource != oldRecordSource )
1330  Px_SetCurrentInputSource(mPortMixer, inputSource);
1331 #endif
1332 }
1333 void AudioIO::SetMixer(int inputSource, float recordVolume,
1334  float playbackVolume)
1335 {
1336  mMixerOutputVol = playbackVolume;
1337 
1338 #if defined(USE_PORTMIXER)
1339  PxMixer *mixer = mPortMixer;
1340 
1341  if( mixer )
1342  {
1343  float oldRecordVolume = Px_GetInputVolume(mixer);
1344  float oldPlaybackVolume = Px_GetPCMOutputVolume(mixer);
1345 
1346  SetMixer(inputSource);
1347  if( oldRecordVolume != recordVolume )
1348  Px_SetInputVolume(mixer, recordVolume);
1349  if( oldPlaybackVolume != playbackVolume )
1350  Px_SetPCMOutputVolume(mixer, playbackVolume);
1351 
1352  return;
1353  }
1354 #endif
1355 }
1356 
1357 void AudioIO::GetMixer(int *recordDevice, float *recordVolume,
1358  float *playbackVolume)
1359 {
1360 #if defined(USE_PORTMIXER)
1361 
1362  PxMixer *mixer = mPortMixer;
1363 
1364  if( mixer )
1365  {
1366  *recordDevice = Px_GetCurrentInputSource(mixer);
1367 
1368  if (mInputMixerWorks)
1369  *recordVolume = Px_GetInputVolume(mixer);
1370  else
1371  *recordVolume = 1.0f;
1372 
1374  *playbackVolume = mMixerOutputVol;
1375  else
1376  *playbackVolume = Px_GetPCMOutputVolume(mixer);
1377 
1378  return;
1379  }
1380 
1381 #endif
1382 
1383  *recordDevice = 0;
1384  *recordVolume = 1.0f;
1385  *playbackVolume = mMixerOutputVol;
1386 }
1387 
1389 {
1390  return mInputMixerWorks;
1391 }
1392 
1394 {
1395  return mEmulateMixerOutputVol;
1396 }
1397 
1399 {
1400 #if defined(USE_PORTMIXER)
1401 
1402  wxArrayString deviceNames;
1403 
1404  if( mPortMixer )
1405  {
1406  int numSources = Px_GetNumInputSources(mPortMixer);
1407  for( int source = 0; source < numSources; source++ )
1408  deviceNames.Add(wxString(wxSafeConvertMB2WX(Px_GetInputSourceName(mPortMixer, source))));
1409  }
1410  else
1411  {
1412  wxLogDebug(wxT("AudioIO::GetInputSourceNames(): PortMixer not initialised!"));
1413  }
1414 
1415  return deviceNames;
1416 
1417 #else
1418 
1419  wxArrayString blank;
1420 
1421  return blank;
1422 
1423 #endif
1424 }
1425 
1427 {
1428  // This should not happen, but it would screw things up if it did.
1429  // Vaughan, 2010-10-08: But it *did* happen, due to a bug, and nobody
1430  // caught it because this method just returned. Added wxASSERT().
1431  wxASSERT(!IsStreamActive());
1432  if (IsStreamActive())
1433  return;
1434 
1435  // get the selected record and playback devices
1436  const int playDeviceNum = getPlayDevIndex();
1437  const int recDeviceNum = getRecordDevIndex();
1438 
1439  // If no change needed, return
1440  if (mCachedPlaybackIndex == playDeviceNum &&
1441  mCachedCaptureIndex == recDeviceNum)
1442  return;
1443 
1444  // cache playback/capture rates
1447  mCachedSampleRates = GetSupportedSampleRates(playDeviceNum, recDeviceNum);
1448  mCachedPlaybackIndex = playDeviceNum;
1449  mCachedCaptureIndex = recDeviceNum;
1450  mCachedBestRateIn = 0.0;
1451 
1452 #if defined(USE_PORTMIXER)
1453 
1454  // if we have a PortMixer object, close it down
1455  if (mPortMixer) {
1456  #if __WXMAC__
1457  // on the Mac we must make sure that we restore the hardware playthrough
1458  // state of the sound device to what it was before, because there isn't
1459  // a UI for this (!)
1460  if (Px_SupportsPlaythrough(mPortMixer) && mPreviousHWPlaythrough >= 0.0)
1461  Px_SetPlaythrough(mPortMixer, mPreviousHWPlaythrough);
1462  mPreviousHWPlaythrough = -1.0;
1463  #endif
1464  Px_CloseMixer(mPortMixer);
1465  mPortMixer = NULL;
1466  }
1467 
1468  // that might have given us no rates whatsoever, so we have to guess an
1469  // answer to do the next bit
1470  int numrates = mCachedSampleRates.size();
1471  int highestSampleRate;
1472  if (numrates > 0)
1473  {
1474  highestSampleRate = mCachedSampleRates[numrates - 1];
1475  }
1476  else
1477  { // we don't actually have any rates that work for Rec and Play. Guess one
1478  // to use for messing with the mixer, which doesn't actually do either
1479  highestSampleRate = 44100;
1480  // mCachedSampleRates is still empty, but it's not used again, so
1481  // can ignore
1482  }
1483  mInputMixerWorks = false;
1484  mEmulateMixerOutputVol = true;
1485  mMixerOutputVol = 1.0;
1486 
1487  int error;
1488  // This tries to open the device with the samplerate worked out above, which
1489  // will be the highest available for play and record on the device, or
1490  // 44.1kHz if the info cannot be fetched.
1491 
1492  PaStream *stream;
1493 
1494  PaStreamParameters playbackParameters;
1495 
1496  playbackParameters.device = playDeviceNum;
1497  playbackParameters.sampleFormat = paFloat32;
1498  playbackParameters.hostApiSpecificStreamInfo = NULL;
1499  playbackParameters.channelCount = 1;
1500  if (Pa_GetDeviceInfo(playDeviceNum))
1501  playbackParameters.suggestedLatency =
1502  Pa_GetDeviceInfo(playDeviceNum)->defaultLowOutputLatency;
1503  else
1504  playbackParameters.suggestedLatency = DEFAULT_LATENCY_CORRECTION/1000.0;
1505 
1506  PaStreamParameters captureParameters;
1507 
1508  captureParameters.device = recDeviceNum;
1509  captureParameters.sampleFormat = paFloat32;;
1510  captureParameters.hostApiSpecificStreamInfo = NULL;
1511  captureParameters.channelCount = 1;
1512  if (Pa_GetDeviceInfo(recDeviceNum))
1513  captureParameters.suggestedLatency =
1514  Pa_GetDeviceInfo(recDeviceNum)->defaultLowInputLatency;
1515  else
1516  captureParameters.suggestedLatency = DEFAULT_LATENCY_CORRECTION/1000.0;
1517 
1518  // try opening for record and playback
1519  error = Pa_OpenStream(&stream,
1520  &captureParameters, &playbackParameters,
1521  highestSampleRate, paFramesPerBufferUnspecified,
1522  paClipOff | paDitherOff,
1523  audacityAudioCallback, NULL);
1524 
1525  if (!error) {
1526  // Try portmixer for this stream
1527  mPortMixer = Px_OpenMixer(stream, 0);
1528  if (!mPortMixer) {
1529  Pa_CloseStream(stream);
1530  error = true;
1531  }
1532  }
1533 
1534  // if that failed, try just for record
1535  if( error ) {
1536  error = Pa_OpenStream(&stream,
1537  &captureParameters, NULL,
1538  highestSampleRate, paFramesPerBufferUnspecified,
1539  paClipOff | paDitherOff,
1540  audacityAudioCallback, NULL);
1541 
1542  if (!error) {
1543  mPortMixer = Px_OpenMixer(stream, 0);
1544  if (!mPortMixer) {
1545  Pa_CloseStream(stream);
1546  error = true;
1547  }
1548  }
1549  }
1550 
1551  // finally, try just for playback
1552  if ( error ) {
1553  error = Pa_OpenStream(&stream,
1554  NULL, &playbackParameters,
1555  highestSampleRate, paFramesPerBufferUnspecified,
1556  paClipOff | paDitherOff,
1557  audacityAudioCallback, NULL);
1558 
1559  if (!error) {
1560  mPortMixer = Px_OpenMixer(stream, 0);
1561  if (!mPortMixer) {
1562  Pa_CloseStream(stream);
1563  error = true;
1564  }
1565  }
1566  }
1567 
1568  // FIXME: TRAP_ERR errors in HandleDeviceChange not reported.
1569  // if it's still not working, give up
1570  if( error )
1571  return;
1572 
1573  // Set input source
1574 #if USE_PORTMIXER
1575  int sourceIndex;
1576  if (gPrefs->Read(wxT("/AudioIO/RecordingSourceIndex"), &sourceIndex)) {
1577  if (sourceIndex >= 0) {
1578  //the current index of our source may be different because the stream
1579  //is a combination of two devices, so update it.
1580  sourceIndex = getRecordSourceIndex(mPortMixer);
1581  if (sourceIndex >= 0)
1582  SetMixer(sourceIndex);
1583  }
1584  }
1585 #endif
1586 
1587  // Determine mixer capabilities - if it doesn't support control of output
1588  // signal level, we emulate it (by multiplying this value by all outgoing
1589  // samples)
1590 
1591  mMixerOutputVol = Px_GetPCMOutputVolume(mPortMixer);
1592  mEmulateMixerOutputVol = false;
1593  Px_SetPCMOutputVolume(mPortMixer, 0.0);
1594  if (Px_GetPCMOutputVolume(mPortMixer) > 0.1)
1595  mEmulateMixerOutputVol = true;
1596  Px_SetPCMOutputVolume(mPortMixer, 0.2f);
1597  if (Px_GetPCMOutputVolume(mPortMixer) < 0.1 ||
1598  Px_GetPCMOutputVolume(mPortMixer) > 0.3)
1599  mEmulateMixerOutputVol = true;
1600  Px_SetPCMOutputVolume(mPortMixer, mMixerOutputVol);
1601 
1602  float inputVol = Px_GetInputVolume(mPortMixer);
1603  mInputMixerWorks = true; // assume it works unless proved wrong
1604  Px_SetInputVolume(mPortMixer, 0.0);
1605  if (Px_GetInputVolume(mPortMixer) > 0.1)
1606  mInputMixerWorks = false; // can't set to zero
1607  Px_SetInputVolume(mPortMixer, 0.2f);
1608  if (Px_GetInputVolume(mPortMixer) < 0.1 ||
1609  Px_GetInputVolume(mPortMixer) > 0.3)
1610  mInputMixerWorks = false; // can't set level accurately
1611  Px_SetInputVolume(mPortMixer, inputVol);
1612 
1613  Pa_CloseStream(stream);
1614 
1615 
1616  #if 0
1617  wxPrintf("PortMixer: Playback: %s Recording: %s\n",
1618  mEmulateMixerOutputVol? "emulated": "native",
1619  mInputMixerWorks? "hardware": "no control");
1620  #endif
1621 
1622  mMixerOutputVol = 1.0;
1623 
1624 #endif // USE_PORTMIXER
1625 }
1626 
1628 {
1629  switch(format) {
1630  case int16Sample:
1631  return paInt16;
1632  case int24Sample:
1633  return paInt24;
1634  case floatSample:
1635  default:
1636  return paFloat32;
1637  }
1638 }
1639 
1640 bool AudioIO::StartPortAudioStream(double sampleRate,
1641  unsigned int numPlaybackChannels,
1642  unsigned int numCaptureChannels,
1643  sampleFormat captureFormat)
1644 {
1645 #ifdef EXPERIMENTAL_MIDI_OUT
1646  mNumFrames = 0;
1647  mNumPauseFrames = 0;
1648  // we want this initial value to be way high. It should be
1649  // sufficient to assume AudioTime is zero and therefore
1650  // mSystemMinusAudioTime is SystemTime(), but we'll add 1000s
1651  // for good measure. On the first callback, this should be
1652  // reduced to SystemTime() - mT0, and note that mT0 is always
1653  // positive.
1654  mSystemMinusAudioTimePlusLatency =
1655  mSystemMinusAudioTime = SystemTime(mUsingAlsa) + 1000;
1656  mAudioOutLatency = 0.0; // set when stream is opened
1657  mCallbackCount = 0;
1658  mAudioFramesPerBuffer = 0;
1659 #endif
1661 
1662  // PRL: Protection from crash reported by David Bailes, involving starting
1663  // and stopping with frequent changes of active window, hard to reproduce
1664  if (!mOwningProject)
1665  return false;
1666 
1667  mInputMeter.Release();
1668  mOutputMeter = NULL;
1669 
1670  mLastPaError = paNoError;
1671  // pick a rate to do the audio I/O at, from those available. The project
1672  // rate is suggested, but we may get something else if it isn't supported
1673  mRate = GetBestRate(numCaptureChannels > 0, numPlaybackChannels > 0, sampleRate);
1674 
1675  // July 2016 (Carsten and Uwe)
1676  // BUG 193: Tell PortAudio sound card will handle 24 bit (under DirectSound) using
1677  // userData.
1678  int captureFormat_saved = captureFormat;
1679  // Special case: Our 24-bit sample format is different from PortAudio's
1680  // 3-byte packed format. So just make PortAudio return float samples,
1681  // since we need float values anyway to apply the gain.
1682  // ANSWER-ME: So we *never* actually handle 24-bit?! This causes mCapture to
1683  // be set to floatSample below.
1684  // JKC: YES that's right. Internally Audacity uses float, and float has space for
1685  // 24 bits as well as exponent. Actual 24 bit would require packing and
1686  // unpacking unaligned bytes and would be inefficient.
1687  // ANSWER ME: is floatSample 64 bit on 64 bit machines?
1688  if (captureFormat == int24Sample)
1689  captureFormat = floatSample;
1690 
1691  mNumPlaybackChannels = numPlaybackChannels;
1692  mNumCaptureChannels = numCaptureChannels;
1693 
1694  bool usePlayback = false, useCapture = false;
1695  PaStreamParameters playbackParameters{};
1696  PaStreamParameters captureParameters{};
1697 
1698  double latencyDuration = DEFAULT_LATENCY_DURATION;
1699  gPrefs->Read(wxT("/AudioIO/LatencyDuration"), &latencyDuration);
1700 
1701  if( numPlaybackChannels > 0)
1702  {
1703  usePlayback = true;
1704 
1705  // this sets the device index to whatever is "right" based on preferences,
1706  // then defaults
1707  playbackParameters.device = getPlayDevIndex();
1708 
1709  const PaDeviceInfo *playbackDeviceInfo;
1710  playbackDeviceInfo = Pa_GetDeviceInfo( playbackParameters.device );
1711 
1712  if( playbackDeviceInfo == NULL )
1713  return false;
1714 
1715  // regardless of source formats, we always mix to float
1716  playbackParameters.sampleFormat = paFloat32;
1717  playbackParameters.hostApiSpecificStreamInfo = NULL;
1718  playbackParameters.channelCount = mNumPlaybackChannels;
1719 
1721  playbackParameters.suggestedLatency =
1722  playbackDeviceInfo->defaultLowOutputLatency;
1723  else
1724  playbackParameters.suggestedLatency = latencyDuration/1000.0;
1725 
1727  }
1728 
1729  if( numCaptureChannels > 0)
1730  {
1731  useCapture = true;
1732  mCaptureFormat = captureFormat;
1733 
1734  const PaDeviceInfo *captureDeviceInfo;
1735  // retrieve the index of the device set in the prefs, or a sensible
1736  // default if it isn't set/valid
1737  captureParameters.device = getRecordDevIndex();
1738 
1739  captureDeviceInfo = Pa_GetDeviceInfo( captureParameters.device );
1740 
1741  if( captureDeviceInfo == NULL )
1742  return false;
1743 
1744  captureParameters.sampleFormat =
1746 
1747  captureParameters.hostApiSpecificStreamInfo = NULL;
1748  captureParameters.channelCount = mNumCaptureChannels;
1749 
1751  captureParameters.suggestedLatency =
1752  captureDeviceInfo->defaultHighInputLatency;
1753  else
1754  captureParameters.suggestedLatency = latencyDuration/1000.0;
1755 
1757  }
1758 
1759  SetMeters();
1760 
1761 #ifdef USE_PORTMIXER
1762 #ifdef __WXMSW__
1763  //mchinen nov 30 2010. For some reason Pa_OpenStream resets the input volume on windows.
1764  //so cache and restore after it.
1765  //The actual problem is likely in portaudio's pa_win_wmme.c OpenStream().
1766  float oldRecordVolume = Px_GetInputVolume(mPortMixer);
1767 #endif
1768 #endif
1769 
1770  // July 2016 (Carsten and Uwe)
1771  // BUG 193: Possibly tell portAudio to use 24 bit with DirectSound.
1772  int userData = 24;
1773  int* lpUserData = (captureFormat_saved == int24Sample) ? &userData : NULL;
1774 
1775  mLastPaError = Pa_OpenStream( &mPortStreamV19,
1776  useCapture ? &captureParameters : NULL,
1777  usePlayback ? &playbackParameters : NULL,
1778  mRate, paFramesPerBufferUnspecified,
1779  paNoFlag,
1780  audacityAudioCallback, lpUserData );
1781 
1782 
1783 #if USE_PORTMIXER
1784 #ifdef __WXMSW__
1785  Px_SetInputVolume(mPortMixer, oldRecordVolume);
1786 #endif
1787  if (mPortStreamV19 != NULL && mLastPaError == paNoError) {
1788 
1789  #ifdef __WXMAC__
1790  if (mPortMixer) {
1791  if (Px_SupportsPlaythrough(mPortMixer)) {
1792  bool playthrough = false;
1793 
1794  mPreviousHWPlaythrough = Px_GetPlaythrough(mPortMixer);
1795 
1796  // Bug 388. Feature not supported.
1797  //gPrefs->Read(wxT("/AudioIO/Playthrough"), &playthrough, false);
1798  if (playthrough)
1799  Px_SetPlaythrough(mPortMixer, 1.0);
1800  else
1801  Px_SetPlaythrough(mPortMixer, 0.0);
1802  }
1803  }
1804  #endif
1805  }
1806 #endif
1807 
1808 #ifdef EXPERIMENTAL_MIDI_OUT
1809  // We use audio latency to estimate how far ahead of DACS we are writing
1810  if (mPortStreamV19 != NULL && mLastPaError == paNoError) {
1811  const PaStreamInfo* info = Pa_GetStreamInfo(mPortStreamV19);
1812  // this is an initial guess, but for PA/Linux/ALSA it's wrong and will be
1813  // updated with a better value:
1814  mAudioOutLatency = info->outputLatency;
1815  mSystemMinusAudioTimePlusLatency += mAudioOutLatency;
1816  }
1817 #endif
1818 
1819  return (mLastPaError == paNoError);
1820 }
1821 
1822 void AudioIO::StartMonitoring(double sampleRate)
1823 {
1824  if ( mPortStreamV19 || mStreamToken )
1825  return;
1826 
1827  bool success;
1828  long captureChannels;
1829  auto captureFormat = QualityPrefs::SampleFormatChoice();
1830  gPrefs->Read(wxT("/AudioIO/RecordChannels"), &captureChannels, 2L);
1831  gPrefs->Read(wxT("/AudioIO/SWPlaythrough"), &mSoftwarePlaythrough, false);
1832  int playbackChannels = 0;
1833 
1835  playbackChannels = 2;
1836 
1837  // FIXME: TRAP_ERR StartPortAudioStream (a PaError may be present)
1838  // but StartPortAudioStream function only returns true or false.
1839  mUsingAlsa = false;
1840  success = StartPortAudioStream(sampleRate, (unsigned int)playbackChannels,
1841  (unsigned int)captureChannels,
1842  captureFormat);
1843  // TODO: Check return value of success.
1844  (void)success;
1845 
1846  wxCommandEvent e(EVT_AUDIOIO_MONITOR);
1847  e.SetEventObject(mOwningProject);
1848  e.SetInt(true);
1849  wxTheApp->ProcessEvent(e);
1850 
1851  // FIXME: TRAP_ERR PaErrorCode 'noted' but not reported in StartMonitoring.
1852  // Now start the PortAudio stream!
1853  // TODO: ? Factor out and reuse error reporting code from end of
1854  // AudioIO::StartStream?
1855  mLastPaError = Pa_StartStream( mPortStreamV19 );
1856 
1857  // Update UI display only now, after all possibilities for error are past.
1858  if ((mLastPaError == paNoError) && mListener) {
1859  // advertise the chosen I/O sample rate to the UI
1860  mListener->OnAudioIORate((int)mRate);
1861  }
1862 }
1863 
1864 int AudioIO::StartStream(const WaveTrackConstArray &playbackTracks,
1865  const WaveTrackArray &captureTracks,
1866 #ifdef EXPERIMENTAL_MIDI_OUT
1867  const NoteTrackArray &midiPlaybackTracks,
1868 #endif
1869  double t0, double t1,
1870  const AudioIOStartStreamOptions &options)
1871 {
1872  mLostSamples = 0;
1873  mLostCaptureIntervals.clear();
1874  mDetectDropouts =
1875  gPrefs->Read( WarningDialogKey(wxT("DropoutDetected")), true ) != 0;
1876  auto cleanup = finally ( [this] { ClearRecordingException(); } );
1877 
1878  if( IsBusy() )
1879  return 0;
1880 
1881  const auto &sampleRate = options.rate;
1882 
1883  // We just want to set mStreamToken to -1 - this way avoids
1884  // an extremely rare but possible race condition, if two functions
1885  // somehow called StartStream at the same time...
1886  mStreamToken--;
1887  if (mStreamToken != -1)
1888  return 0;
1889 
1890  // TODO: we don't really need to close and reopen stream if the
1891  // format matches; however it's kind of tricky to keep it open...
1892  //
1893  // if (sampleRate == mRate &&
1894  // playbackChannels == mNumPlaybackChannels &&
1895  // captureChannels == mNumCaptureChannels &&
1896  // captureFormat == mCaptureFormat) {
1897 
1898  if (mPortStreamV19) {
1899  StopStream();
1900  while(mPortStreamV19)
1901  wxMilliSleep( 50 );
1902  }
1903 
1904 #ifdef __WXGTK__
1905  // Detect whether ALSA is the chosen host, and do the various involved MIDI
1906  // timing compensations only then.
1907  mUsingAlsa = (gPrefs->Read(wxT("/AudioIO/Host"), wxT("")) == "ALSA");
1908 #endif
1909 
1910  gPrefs->Read(wxT("/AudioIO/SWPlaythrough"), &mSoftwarePlaythrough, false);
1911  gPrefs->Read(wxT("/AudioIO/SoundActivatedRecord"), &mPauseRec, false);
1912  int silenceLevelDB;
1913  gPrefs->Read(wxT("/AudioIO/SilenceLevel"), &silenceLevelDB, -50);
1914  int dBRange;
1915  dBRange = gPrefs->Read(ENV_DB_KEY, ENV_DB_RANGE);
1916  if(silenceLevelDB < -dBRange)
1917  {
1918  silenceLevelDB = -dBRange + 3; // meter range was made smaller than SilenceLevel
1919  gPrefs->Write(ENV_DB_KEY, dBRange); // so set SilenceLevel reasonable
1920  gPrefs->Flush();
1921  }
1922  mSilenceLevel = (silenceLevelDB + dBRange)/(double)dBRange; // meter goes -dBRange dB -> 0dB
1923 
1924  if ( !captureTracks.empty() ) {
1925  // It does not make sense to apply the time warp during overdub recording,
1926  // which defeats the purpose of making the recording synchronized with
1927  // the existing audio. (Unless we figured out the inverse warp of the
1928  // captured samples in real time.)
1929  // So just quietly ignore the time track.
1930  mTimeTrack = nullptr;
1931  }
1932  else {
1933  mTimeTrack = options.timeTrack;
1934  }
1935 
1936  mListener = options.listener;
1937  mRate = sampleRate;
1938  mT0 = t0;
1939  mT1 = t1;
1940  mTime = t0;
1941  mSeek = 0;
1943  mCaptureTracks = captureTracks;
1944  mPlaybackTracks = playbackTracks;
1945 #ifdef EXPERIMENTAL_MIDI_OUT
1946  mMidiPlaybackTracks = midiPlaybackTracks;
1947 #endif
1948 
1949  bool commit = false;
1950  auto cleanupTracks = finally([&]{
1951  if (!commit) {
1952  // Don't keep unnecessary shared pointers to tracks
1953  mPlaybackTracks.clear();
1954  mCaptureTracks.clear();
1955 #ifdef EXPERIMENTAL_MIDI_OUT
1956  mMidiPlaybackTracks.clear();
1957 #endif
1958  }
1959  });
1960 
1964 
1965  mPlaybackBuffers.reset();
1966  mPlaybackMixers.reset();
1967  mCaptureBuffers.reset();
1968  mResample.reset();
1969 
1970  double playbackTime = 4.0;
1971 
1972 #ifdef EXPERIMENTAL_MIDI_OUT
1973  streamStartTime = 0;
1974  streamStartTime = SystemTime(mUsingAlsa);
1975 #endif
1976 
1977 #ifdef EXPERIMENTAL_SCRUBBING_SUPPORT
1978  bool scrubbing = (options.pScrubbingOptions != nullptr);
1979 
1980  // Scrubbing is not compatible with looping or recording or a time track!
1981  if (scrubbing)
1982  {
1983  const auto &scrubOptions = *options.pScrubbingOptions;
1984 
1985  if (mCaptureTracks.size() > 0 ||
1986  mPlayMode == PLAY_LOOPED ||
1987  mTimeTrack != NULL ||
1988  scrubOptions.maxSpeed < ScrubbingOptions::MinAllowedScrubSpeed()) {
1989  wxASSERT(false);
1990  scrubbing = false;
1991  }
1992  else {
1993  playbackTime = lrint(scrubOptions.delay * sampleRate) / sampleRate;
1995  }
1996  }
1997 #endif
1998 
1999  // mWarpedTime and mWarpedLength are irrelevant when scrubbing,
2000  // else they are used in updating mTime,
2001  // and when not scrubbing or playing looped, mTime is also used
2002  // in the test for termination of playback.
2003 
2004  // with ComputeWarpedLength, it is now possible the calculate the warped length with 100% accuracy
2005  // (ignoring accumulated rounding errors during playback) which fixes the 'missing sound at the end' bug
2006  mWarpedTime = 0.0;
2007 #ifdef EXPERIMENTAL_SCRUBBING_SUPPORT
2008  if (scrubbing)
2009  mWarpedLength = 0.0;
2010  else
2011 #endif
2012  {
2013  if (mTimeTrack)
2014  // Following gives negative when mT0 > mT1
2016  else
2017  mWarpedLength = mT1 - mT0;
2018  // PRL allow backwards play
2019  mWarpedLength = fabs(mWarpedLength);
2020  }
2021 
2022  //
2023  // The RingBuffer sizes, and the max amount of the buffer to
2024  // fill at a time, both grow linearly with the number of
2025  // tracks. This allows us to scale up to many tracks without
2026  // killing performance.
2027  //
2028 
2029  // (warped) playback time to produce with each filling of the buffers
2030  // by the Audio thread (except at the end of playback):
2031  // usually, make fillings fewer and longer for less CPU usage.
2032  // But for useful scrubbing, we can't run too far ahead without checking
2033  // mouse input, so make fillings more and shorter.
2034  // What Audio thread produces for playback is then consumed by the PortAudio
2035  // thread, in many smaller pieces.
2036  wxASSERT( playbackTime >= 0 );
2037  mPlaybackSamplesToCopy = playbackTime * mRate;
2038 
2039  // Capacity of the playback buffer.
2040  mPlaybackRingBufferSecs = 10.0;
2041 
2042  mCaptureRingBufferSecs = 4.5 + 0.5 * std::min(size_t(16), mCaptureTracks.size());
2043  mMinCaptureSecsToCopy = 0.2 + 0.2 * std::min(size_t(16), mCaptureTracks.size());
2044 
2045  unsigned int playbackChannels = 0;
2046  unsigned int captureChannels = 0;
2047  sampleFormat captureFormat = floatSample;
2048 
2049  if (playbackTracks.size() > 0
2050 #ifdef EXPERIMENTAL_MIDI_OUT
2051  || midiPlaybackTracks.size() > 0
2052 #endif
2053  )
2054  playbackChannels = 2;
2055 
2057  playbackChannels = 2;
2058 
2059  if( captureTracks.size() > 0 )
2060  {
2061  // For capture, every input channel gets its own track
2062  captureChannels = mCaptureTracks.size();
2063  // I don't deal with the possibility of the capture tracks
2064  // having different sample formats, since it will never happen
2065  // with the current code. This code wouldn't *break* if this
2066  // assumption was false, but it would be sub-optimal. For example,
2067  // if the first track was 16-bit and the second track was 24-bit,
2068  // we would set the sound card to capture in 16 bits and the second
2069  // track wouldn't get the benefit of all 24 bits the card is capable
2070  // of.
2071  captureFormat = mCaptureTracks[0]->GetSampleFormat();
2072 
2073  // Tell project that we are about to start recording
2074  if (mListener)
2076  }
2077 
2078  bool successAudio;
2079 
2080  successAudio = StartPortAudioStream(sampleRate, playbackChannels,
2081  captureChannels, captureFormat);
2082 #ifdef EXPERIMENTAL_MIDI_OUT
2083 
2084  // TODO: it may be that midi out will not work unless audio in or out is
2085  // active -- this would be a bug and may require a change in the
2086  // logic here.
2087 
2088  bool successMidi = true;
2089 
2090  if(!mMidiPlaybackTracks.empty()){
2091  successMidi = StartPortMidiStream();
2092  }
2093 
2094  // On the other hand, if MIDI cannot be opened, we will not complain
2095 #endif
2096 
2097  if (!successAudio) {
2098  if (mListener && captureChannels > 0)
2100  mStreamToken = 0;
2101 
2102  // Don't cause a busy wait in the audio thread after stopping scrubbing
2104 
2105  return 0;
2106  }
2107 
2108  //
2109  // The (audio) stream has been opened successfully (assuming we tried
2110  // to open it). We now proceed to
2111  // allocate the memory structures the stream will need.
2112  //
2113 
2114  bool bDone;
2115  do
2116  {
2117  bDone = true; // assume success
2118  try
2119  {
2120  if( mNumPlaybackChannels > 0 ) {
2121  // Allocate output buffers. For every output track we allocate
2122  // a ring buffer of five seconds
2123  auto playbackBufferSize =
2124  (size_t)lrint(mRate * mPlaybackRingBufferSecs);
2125  auto playbackMixBufferSize =
2127 
2130 
2131  const Mixer::WarpOptions &warpOptions =
2132 #ifdef EXPERIMENTAL_SCRUBBING_SUPPORT
2133  scrubbing
2137  :
2138 #endif
2139  Mixer::WarpOptions(mTimeTrack);
2140 
2141  for (unsigned int i = 0; i < mPlaybackTracks.size(); i++)
2142  {
2143  mPlaybackBuffers[i] = std::make_unique<RingBuffer>(floatSample, playbackBufferSize);
2144 
2145  // MB: use normal time for the end time, not warped time!
2146  WaveTrackConstArray tracks;
2147  tracks.push_back(mPlaybackTracks[i]);
2148  mPlaybackMixers[i] = std::make_unique<Mixer>
2149  (tracks,
2150  // Don't throw for read errors, just play silence:
2151  false,
2152  warpOptions,
2153  mT0, mT1, 1,
2154  playbackMixBufferSize, false,
2155  mRate, floatSample, false);
2156  mPlaybackMixers[i]->ApplyTrackGains(false);
2157  }
2158  }
2159 
2160  if( mNumCaptureChannels > 0 )
2161  {
2162  // Allocate input buffers. For every input track we allocate
2163  // a ring buffer of five seconds
2164  auto captureBufferSize = (size_t)(mRate * mCaptureRingBufferSecs + 0.5);
2165 
2166  // In the extraordinarily rare case that we can't even afford 100 samples, just give up.
2167  if(captureBufferSize < 100)
2168  {
2170  AudacityMessageBox(_("Out of memory!"));
2171  return 0;
2172  }
2173 
2176  mFactor = sampleRate / mRate;
2177 
2178  for( unsigned int i = 0; i < mCaptureTracks.size(); i++ )
2179  {
2180  mCaptureBuffers[i] = std::make_unique<RingBuffer>
2181  ( mCaptureTracks[i]->GetSampleFormat(),
2182  captureBufferSize );
2183  mResample[i] = std::make_unique<Resample>(true, mFactor, mFactor); // constant rate resampling
2184  }
2185  }
2186  }
2187  catch(std::bad_alloc&)
2188  {
2189  // Oops! Ran out of memory. This is pretty rare, so we'll just
2190  // try deleting everything, halving our buffer size, and try again.
2191  StartStreamCleanup(true);
2192  mPlaybackRingBufferSecs *= 0.5;
2194  mCaptureRingBufferSecs *= 0.5;
2195  mMinCaptureSecsToCopy *= 0.5;
2196  bDone = false;
2197 
2198  // In the extraordinarily rare case that we can't even afford 100 samples, just give up.
2199  auto playbackBufferSize = (size_t)lrint(mRate * mPlaybackRingBufferSecs);
2200  auto playbackMixBufferSize = mPlaybackSamplesToCopy;
2201  if(playbackBufferSize < 100 || playbackMixBufferSize < 100)
2202  {
2204  AudacityMessageBox(_("Out of memory!"));
2205  return 0;
2206  }
2207  }
2208  } while(!bDone);
2209 
2210  if (mNumPlaybackChannels > 0)
2211  {
2213  // Setup for realtime playback at the rate of the realtime
2214  // stream, not the rate of the track.
2215  em.RealtimeInitialize(mRate);
2216 
2217  // The following adds a NEW effect processor for each logical track and the
2218  // group determination should mimic what is done in audacityAudioCallback()
2219  // when calling RealtimeProcess().
2220  int group = 0;
2221  for (size_t i = 0, cnt = mPlaybackTracks.size(); i < cnt; i++)
2222  {
2223  const WaveTrack *vt = gAudioIO->mPlaybackTracks[i].get();
2224 
2225  unsigned chanCnt = 1;
2226  if (vt->GetLinked())
2227  {
2228  i++;
2229  chanCnt++;
2230  }
2231 
2232  // Setup for realtime playback at the rate of the realtime
2233  // stream, not the rate of the track.
2234  em.RealtimeAddProcessor(group++, chanCnt, mRate);
2235  }
2236  }
2237 
2238 #ifdef EXPERIMENTAL_AUTOMATED_INPUT_LEVEL_ADJUSTMENT
2239  AILASetStartTime();
2240 #endif
2241 
2242  if (options.pStartTime)
2243  {
2244  // Calculate the NEW time position
2245  mTime = std::max(mT0, std::min(mT1, *options.pStartTime));
2246  // Reset mixer positions for all playback tracks
2247  unsigned numMixers = mPlaybackTracks.size();
2248  for (unsigned ii = 0; ii < numMixers; ++ii)
2249  mPlaybackMixers[ii]->Reposition(mTime);
2250  if(mTimeTrack)
2252  else
2253  mWarpedTime = mTime - mT0;
2254  }
2255 
2256 #ifdef EXPERIMENTAL_SCRUBBING_SUPPORT
2257  if (scrubbing)
2258  {
2259  const auto &scrubOptions = *options.pScrubbingOptions;
2260  mScrubQueue =
2261  std::make_unique<ScrubQueue>(mT0, mT1, scrubOptions.startClockTimeMillis,
2262  sampleRate, 2 * scrubOptions.minStutter,
2263  scrubOptions);
2264  mScrubDuration = 0;
2265  mSilentScrub = false;
2266  }
2267  else
2268  mScrubQueue.reset();
2269 #endif
2270 
2271  // We signal the audio thread to call FillBuffers, to prime the RingBuffers
2272  // so that they will have data in them when the stream starts. Having the
2273  // audio thread call FillBuffers here makes the code more predictable, since
2274  // FillBuffers will ALWAYS get called from the Audio thread.
2276 
2277  while( mAudioThreadShouldCallFillBuffersOnce == true ) {
2278  if (mScrubQueue)
2279  mScrubQueue->Nudge();
2280  wxMilliSleep( 50 );
2281  }
2282 
2283  if(mNumPlaybackChannels > 0 || mNumCaptureChannels > 0) {
2284 
2285 #ifdef REALTIME_ALSA_THREAD
2286  // PRL: Do this in hope of less thread scheduling jitter in calls to
2287  // audacityAudioCallback.
2288  // Not needed to make audio playback work smoothly.
2289  // But needed in case we also play MIDI, so that the variable "offset"
2290  // in AudioIO::MidiTime() is a better approximation of the duration
2291  // between the call of audacityAudioCallback and the actual output of
2292  // the first audio sample.
2293  // (Which we should be able to determine from fields of
2294  // PaStreamCallbackTimeInfo, but that seems not to work as documented with
2295  // ALSA.)
2296  if (mUsingAlsa)
2297  // Perhaps we should do this only if also playing MIDI ?
2298  PaAlsa_EnableRealtimeScheduling( mPortStreamV19, 1 );
2299 #endif
2300 
2301  //
2302  // Generate a unique value each time, to be returned to
2303  // clients accessing the AudioIO API, so they can query if they
2304  // are the ones who have reserved AudioIO or not.
2305  //
2306  // It is important to set this before setting the portaudio stream in
2307  // motion -- otherwise it may play an unspecified number of leading
2308  // zeroes.
2310 
2311  // This affects the AudioThread (not the portaudio callback).
2312  // Probably not needed so urgently before portaudio thread start for usual
2313  // playback, since our ring buffers have been primed already with 4 sec
2314  // of audio, but then we might be scrubbing, so do it.
2316 
2317  // Now start the PortAudio stream!
2318  PaError err;
2319  err = Pa_StartStream( mPortStreamV19 );
2320 
2321  if( err != paNoError )
2322  {
2323  mStreamToken = 0;
2325  if (mListener && mNumCaptureChannels > 0)
2328  AudacityMessageBox(LAT1CTOWX(Pa_GetErrorText(err)));
2329  return 0;
2330  }
2331  }
2332 
2333  // Update UI display only now, after all possibilities for error are past.
2334  if (mListener) {
2335  // advertise the chosen I/O sample rate to the UI
2336  mListener->OnAudioIORate((int)mRate);
2337  }
2338 
2339  if (mNumPlaybackChannels > 0)
2340  {
2341  wxCommandEvent e(EVT_AUDIOIO_PLAYBACK);
2342  e.SetEventObject(mOwningProject);
2343  e.SetInt(true);
2344  wxTheApp->ProcessEvent(e);
2345  }
2346 
2347  if (mNumCaptureChannels > 0)
2348  {
2349  wxCommandEvent e(EVT_AUDIOIO_CAPTURE);
2350  e.SetEventObject(mOwningProject);
2351  e.SetInt(true);
2352  wxTheApp->ProcessEvent(e);
2353  }
2354 
2355  // Enable warning popups for unfound aliased blockfiles.
2357 
2358  commit = true;
2359  return mStreamToken;
2360 }
2361 
2362 void AudioIO::StartStreamCleanup(bool bOnlyBuffers)
2363 {
2364  if (mNumPlaybackChannels > 0)
2365  {
2367  }
2368 
2369  mPlaybackBuffers.reset();
2370  mPlaybackMixers.reset();
2371  mCaptureBuffers.reset();
2372  mResample.reset();
2373 
2374  if(!bOnlyBuffers)
2375  {
2376  Pa_AbortStream( mPortStreamV19 );
2377  Pa_CloseStream( mPortStreamV19 );
2378  mPortStreamV19 = NULL;
2379  mStreamToken = 0;
2380  }
2381 
2382 #ifdef EXPERIMENTAL_SCRUBBING_SUPPORT
2383  mScrubQueue.reset();
2384 #endif
2385 
2386 
2387  // Don't cause a busy wait in the audio thread after stopping scrubbing
2389 }
2390 
2391 #ifdef EXPERIMENTAL_MIDI_OUT
2392 
2393 PmTimestamp MidiTime(void *WXUNUSED(info))
2394 {
2395  return gAudioIO->MidiTime();
2396 }
2397 
2398 // Set up state to iterate NoteTrack events in sequence.
2399 // Sends MIDI control changes up to the starting point mT0
2400 // if send is true. Output is delayed by offset to facilitate
2401 // looping (each iteration is delayed more).
2402 void AudioIO::PrepareMidiIterator(bool send, double offset)
2403 {
2404  int i;
2405  int nTracks = mMidiPlaybackTracks.size();
2406  // instead of initializing with an Alg_seq, we use begin_seq()
2407  // below to add ALL Alg_seq's.
2408  mIterator = std::make_unique<Alg_iterator>(nullptr, false);
2409  // Iterator not yet intialized, must add each track...
2410  for (i = 0; i < nTracks; i++) {
2411  NoteTrack *t = mMidiPlaybackTracks[i].get();
2412  Alg_seq_ptr seq = &t->GetSeq();
2413  // mark sequence tracks as "in use" since we're handing this
2414  // off to another thread and want to make sure nothing happens
2415  // to the data until playback finishes. This is just a sanity check.
2416  seq->set_in_use(true);
2417  mIterator->begin_seq(seq, t, t->GetOffset() + offset);
2418  }
2419  GetNextEvent(); // prime the pump for FillMidiBuffers
2420 
2421  // Start MIDI from current cursor position
2422  mSendMidiState = true;
2423  while (mNextEvent &&
2424  mNextEventTime < mT0 + offset) {
2425  if (send) OutputEvent();
2426  GetNextEvent();
2427  }
2428  mSendMidiState = false;
2429 }
2430 
2431 bool AudioIO::StartPortMidiStream()
2432 {
2433  int i;
2434  int nTracks = mMidiPlaybackTracks.size();
2435  // Only start MIDI stream if there is an open track
2436  if (nTracks == 0)
2437  return false;
2438 
2439  //wxPrintf("StartPortMidiStream: mT0 %g mTime %g\n",
2440  // gAudioIO->mT0, gAudioIO->mTime);
2441 
2442  /* get midi playback device */
2443  PmDeviceID playbackDevice = Pm_GetDefaultOutputDeviceID();
2444  wxString playbackDeviceName = gPrefs->Read(wxT("/MidiIO/PlaybackDevice"),
2445  wxT(""));
2446  mSynthLatency = gPrefs->Read(wxT("/MidiIO/SynthLatency"),
2448  if (wxStrcmp(playbackDeviceName, wxT("")) != 0) {
2449  for (i = 0; i < Pm_CountDevices(); i++) {
2450  const PmDeviceInfo *info = Pm_GetDeviceInfo(i);
2451  if (!info) continue;
2452  if (!info->output) continue;
2453  wxString interf = wxSafeConvertMB2WX(info->interf);
2454  wxString name = wxSafeConvertMB2WX(info->name);
2455  interf.Append(wxT(": ")).Append(name);
2456  if (wxStrcmp(interf, playbackDeviceName) == 0) {
2457  playbackDevice = i;
2458  }
2459  }
2460  } // (else playback device has Pm_GetDefaultOuputDeviceID())
2461 
2462  /* open output device */
2463  mLastPmError = Pm_OpenOutput(&mMidiStream,
2464  playbackDevice,
2465  NULL,
2466  0,
2467  &::MidiTime,
2468  NULL,
2470  if (mLastPmError == pmNoError) {
2471  mMidiStreamActive = true;
2472  mMidiPaused = false;
2473  mMidiLoopPasses = 0;
2474  mMidiOutputComplete = false;
2475  mMaxMidiTimestamp = 0;
2476  PrepareMidiIterator();
2477 
2478  // It is ok to call this now, but do not send timestamped midi
2479  // until after the first audio callback, which provides necessary
2480  // data for MidiTime().
2481  Pm_Synchronize(mMidiStream); // start using timestamps
2482  // start midi output flowing (pending first audio callback)
2483  mMidiThreadFillBuffersLoopRunning = true;
2484  }
2485  return (mLastPmError == pmNoError);
2486 }
2487 #endif
2488 
2490 {
2491  return mOwningProject == NULL || mOwningProject == project;
2492 }
2493 
2495 {
2496  if (!mOwningProject || mOwningProject == project)
2497  {
2498  if (meter)
2499  {
2500  mInputMeter = meter;
2501  mInputMeter->Reset(mRate, true);
2502  }
2503  else
2504  mInputMeter.Release();
2505  }
2506 }
2507 
2509 {
2510  if (!mOwningProject || mOwningProject == project)
2511  {
2512  mOutputMeter = meter;
2513  if (mOutputMeter)
2514  {
2515  mOutputMeter->Reset(mRate, true);
2516  }
2517  }
2518 }
2519 
2521 {
2522  if (mInputMeter)
2523  mInputMeter->Reset(mRate, true);
2524  if (mOutputMeter)
2525  mOutputMeter->Reset(mRate, true);
2526 
2527  AudacityProject* pProj = GetActiveProject();
2528  MixerBoard* pMixerBoard = pProj->GetMixerBoard();
2529  if (pMixerBoard)
2530  pMixerBoard->ResetMeters(true);
2531 
2532  mUpdateMeters = true;
2533 }
2534 
2536 {
2537  auto cleanup = finally ( [this] { ClearRecordingException(); } );
2538 
2539  if( mPortStreamV19 == NULL
2540 #ifdef EXPERIMENTAL_MIDI_OUT
2541  && mMidiStream == NULL
2542 #endif
2543  )
2544  return;
2545 
2546  if( Pa_IsStreamStopped( mPortStreamV19 )
2547 #ifdef EXPERIMENTAL_MIDI_OUT
2548  && !mMidiStreamActive
2549 #endif
2550  )
2551  return;
2552 
2553  wxMutexLocker locker(mSuspendAudioThread);
2554 
2555  // No longer need effects processing
2556  if (mNumPlaybackChannels > 0)
2557  {
2559  }
2560 
2561  //
2562  // We got here in one of two ways:
2563  //
2564  // 1. The user clicked the stop button and we therefore want to stop
2565  // as quickly as possible. So we use AbortStream(). If this is
2566  // the case the portaudio stream is still in the Running state
2567  // (see PortAudio state machine docs).
2568  //
2569  // 2. The callback told PortAudio to stop the stream since it had
2570  // reached the end of the selection. The UI thread discovered
2571  // this by noticing that AudioIO::IsActive() returned false.
2572  // IsActive() (which calls Pa_GetStreamActive()) will not return
2573  // false until all buffers have finished playing, so we can call
2574  // AbortStream without losing any samples. If this is the case
2575  // we are in the "callback finished state" (see PortAudio state
2576  // machine docs).
2577  //
2578  // The moral of the story: We can call AbortStream safely, without
2579  // losing samples.
2580  //
2581  // DMM: This doesn't seem to be true; it seems to be necessary to
2582  // call StopStream if the callback brought us here, and AbortStream
2583  // if the user brought us here.
2584  //
2585 
2587  if (mScrubQueue)
2588  mScrubQueue->Nudge();
2589 
2590  // Audacity can deadlock if it tries to update meters while
2591  // we're stopping PortAudio (because the meter updating code
2592  // tries to grab a UI mutex while PortAudio tries to join a
2593  // pthread). So we tell the callback to stop updating meters,
2594  // and wait until the callback has left this part of the code
2595  // if it was already there.
2596  mUpdateMeters = false;
2597  while(mUpdatingMeters) {
2598  ::wxSafeYield();
2599  wxMilliSleep( 50 );
2600  }
2601 
2602  // Turn off HW playthrough if PortMixer is being used
2603 
2604  #if defined(USE_PORTMIXER)
2605  if( mPortMixer ) {
2606  #if __WXMAC__
2607  if (Px_SupportsPlaythrough(mPortMixer) && mPreviousHWPlaythrough >= 0.0)
2608  Px_SetPlaythrough(mPortMixer, mPreviousHWPlaythrough);
2609  mPreviousHWPlaythrough = -1.0;
2610  #endif
2611  }
2612  #endif
2613 
2614  if (mPortStreamV19) {
2615  Pa_AbortStream( mPortStreamV19 );
2616  Pa_CloseStream( mPortStreamV19 );
2617  mPortStreamV19 = NULL;
2618  }
2619 
2620  if (mNumPlaybackChannels > 0)
2621  {
2622  wxCommandEvent e(EVT_AUDIOIO_PLAYBACK);
2623  e.SetEventObject(mOwningProject);
2624  e.SetInt(false);
2625  wxTheApp->ProcessEvent(e);
2626  }
2627 
2628  if (mNumCaptureChannels > 0)
2629  {
2630  wxCommandEvent e(mStreamToken == 0 ? EVT_AUDIOIO_MONITOR : EVT_AUDIOIO_CAPTURE);
2631  e.SetEventObject(mOwningProject);
2632  e.SetInt(false);
2633  wxTheApp->ProcessEvent(e);
2634  }
2635 
2636 #ifdef EXPERIMENTAL_MIDI_OUT
2637  /* Stop Midi playback */
2638  if ( mMidiStream ) {
2639 
2640  mMidiStreamActive = false;
2641 
2642 #ifdef USE_MIDI_THREAD
2643  mMidiThreadFillBuffersLoopRunning = false; // stop output to stream
2644  // but output is in another thread. Wait for output to stop...
2645  while (mMidiThreadFillBuffersLoopActive) {
2646  wxMilliSleep(1);
2647  }
2648 #endif
2649 
2650  mMidiOutputComplete = true;
2651 
2652  // now we can assume "ownership" of the mMidiStream
2653  // if output in progress, send all off, etc.
2654  AllNotesOff();
2655  // AllNotesOff() should be sufficient to stop everything, but
2656  // in Linux, if you Pm_Close() immediately, it looks like
2657  // messages are dropped. ALSA then seems to send All Sound Off
2658  // and Reset All Controllers messages, but not all synthesizers
2659  // respond to these messages. This is probably a bug in PortMidi
2660  // if the All Off messages do not get out, but for security,
2661  // delay a bit so that messages can be delivered before closing
2662  // the stream. Add 2ms of "padding" to avoid any rounding errors.
2663  while (mMaxMidiTimestamp + 2 > MidiTime()) {
2664  wxMilliSleep(1); // deliver the all-off messages
2665  }
2666  Pm_Close(mMidiStream);
2667  mMidiStream = NULL;
2668  mIterator->end();
2669 
2670  // set in_use flags to false
2671  int nTracks = mMidiPlaybackTracks.size();
2672  for (int i = 0; i < nTracks; i++) {
2673  NoteTrack *t = mMidiPlaybackTracks[i].get();
2674  Alg_seq_ptr seq = &t->GetSeq();
2675  seq->set_in_use(false);
2676  }
2677 
2678  mIterator.reset(); // just in case someone tries to reference it
2679  }
2680 #endif
2681 
2682  // If there's no token, we were just monitoring, so we can
2683  // skip this next part...
2684  if (mStreamToken > 0) {
2685  // In either of the above cases, we want to make sure that any
2686  // capture data that made it into the PortAudio callback makes it
2687  // to the target WaveTrack. To do this, we ask the audio thread to
2688  // call FillBuffers one last time (it normally would not do so since
2689  // Pa_GetStreamActive() would now return false
2691 
2692  while( mAudioThreadShouldCallFillBuffersOnce == true )
2693  {
2694  // LLL: Experienced recursive yield here...once.
2695  wxGetApp().Yield(true); // Pass true for onlyIfNeeded to avoid recursive call error.
2696  if (mScrubQueue)
2697  mScrubQueue->Nudge();
2698  wxMilliSleep( 50 );
2699  }
2700 
2701  //
2702  // Everything is taken care of. Now, just free all the resources
2703  // we allocated in StartStream()
2704  //
2705 
2706  if (mPlaybackTracks.size() > 0)
2707  {
2708  mPlaybackBuffers.reset();
2709  mPlaybackMixers.reset();
2710  }
2711 
2712  //
2713  // Offset all recorded tracks to account for latency
2714  //
2715  if (mCaptureTracks.size() > 0)
2716  {
2717  mCaptureBuffers.reset();
2718  mResample.reset();
2719 
2720  //
2721  // We only apply latency correction when we actually played back
2722  // tracks during the recording. If we did not play back tracks,
2723  // there's nothing we could be out of sync with. This also covers the
2724  // case that we do not apply latency correction when recording the
2725  // first track in a project.
2726  //
2727  double latencyCorrection = DEFAULT_LATENCY_CORRECTION;
2728  gPrefs->Read(wxT("/AudioIO/LatencyCorrection"), &latencyCorrection);
2729 
2730  double recordingOffset =
2731  mLastRecordingOffset + latencyCorrection / 1000.0;
2732 
2733  for (unsigned int i = 0; i < mCaptureTracks.size(); i++) {
2734  // The calls to Flush, and (less likely) Clear and InsertSilence,
2735  // may cause exceptions because of exhaustion of disk space.
2736  // Stop those exceptions here, or else they propagate through too
2737  // many parts of Audacity that are not effects or editing
2738  // operations. GuardedCall ensures that the user sees a warning.
2739 
2740  // Also be sure to Flush each track, at the top of the guarded call,
2741  // relying on the guarantee that the track will be left in a flushed
2742  // state, though the append buffer may be lost.
2743 
2744  // If the other track operations fail their strong guarantees, then
2745  // the shift for latency correction may be skipped.
2746  GuardedCall( [&] {
2747  WaveTrack* track = mCaptureTracks[i].get();
2748 
2749  // use NOFAIL-GUARANTEE that track is flushed,
2750  // PARTIAL-GUARANTEE that some initial length of the recording
2751  // is saved.
2752  // See comments in FillBuffers().
2753  track->Flush();
2754 
2755  if (mPlaybackTracks.size() > 0)
2756  { // only do latency correction if some tracks are being played back
2757  WaveTrackArray playbackTracks;
2759  // we need to get this as mPlaybackTracks does not contain tracks being recorded into
2760  playbackTracks = p->GetTracks()->GetWaveTrackArray(false);
2761  bool appendRecord = false;
2762  for (unsigned int j = 0; j < playbackTracks.size(); j++)
2763  { // find if we are recording into an existing track (append-record)
2764  WaveTrack* trackP = playbackTracks[j].get();
2765  if( track == trackP )
2766  {
2767  if( track->GetStartTime() != mT0 ) // in a NEW track if these are equal
2768  {
2769  appendRecord = true;
2770  break;
2771  }
2772  }
2773  }
2774  if( appendRecord )
2775  { // append-recording
2776  if (recordingOffset < 0)
2777  // use STRONG-GUARANTEE
2778  track->Clear(mT0, mT0 - recordingOffset); // cut the latency out
2779  else
2780  // use STRONG-GUARANTEE
2781  track->InsertSilence(mT0, recordingOffset); // put silence in
2782  }
2783  else
2784  { // recording into a NEW track
2785  // gives NOFAIL-GUARANTEE though we only need STRONG
2786  track->SetOffset(track->GetStartTime() + recordingOffset);
2787  if(track->GetEndTime() < 0.)
2788  {
2789  // Bug 96: Only warn for the first track.
2790  if( i==0 )
2791  {
2792  AudacityMessageDialog m(NULL, _(
2793 "Latency Correction setting has caused the recorded audio to be hidden before zero.\nAudacity has brought it back to start at zero.\nYou may have to use the Time Shift Tool (<---> or F5) to drag the track to the right place."),
2794  _("Latency problem"), wxOK);
2795  m.ShowModal();
2796  }
2797  // gives NOFAIL-GUARANTEE though we only need STRONG
2798  track->SetOffset(0.);
2799  }
2800  }
2801  }
2802  } );
2803  }
2804 
2805  for (auto &interval : mLostCaptureIntervals) {
2806  auto &start = interval.first;
2807  if (mPlaybackTracks.size() > 0)
2808  // only do latency correction if some tracks are being played back
2809  start += recordingOffset;
2810  auto duration = interval.second;
2811  for (auto &track : mCaptureTracks) {
2812  GuardedCall([&] {
2813  track->SyncLockAdjust(start, start + duration);
2814  });
2815  }
2816  }
2817 
2819  ControlToolBar *bar = p->GetControlToolBar();
2820  bar->CommitRecording();
2821  }
2822  }
2823 
2824  if (mInputMeter)
2825  mInputMeter->Reset(mRate, false);
2826 
2827  if (mOutputMeter)
2828  mOutputMeter->Reset(mRate, false);
2829 
2830  MixerBoard* pMixerBoard = mOwningProject->GetMixerBoard();
2831  if (pMixerBoard)
2832  pMixerBoard->ResetMeters(false);
2833 
2834  mInputMeter.Release();
2835  mOutputMeter = NULL;
2836  mOwningProject = NULL;
2837 
2838  if (mListener && mNumCaptureChannels > 0)
2840 
2841  //
2842  // Only set token to 0 after we're totally finished with everything
2843  //
2844  mStreamToken = 0;
2845 
2846  mNumCaptureChannels = 0;
2848 
2849  mPlaybackTracks.clear();
2850  mCaptureTracks.clear();
2851 #ifdef HAVE_MIDI
2852  mMidiPlaybackTracks.clear();
2853 #endif
2854 
2855 #ifdef EXPERIMENTAL_SCRUBBING_SUPPORT
2856  mScrubQueue.reset();
2857 #endif
2858 
2859  if (mListener) {
2860  // Tell UI to hide sample rate
2862  }
2863 
2864  // Don't cause a busy wait in the audio thread after stopping scrubbing
2866 }
2867 
2868 void AudioIO::SetPaused(bool state)
2869 {
2870  if (state != mPaused)
2871  {
2872  if (state)
2873  {
2875  }
2876  else
2877  {
2879  }
2880  }
2881 
2882  mPaused = state;
2883 }
2884 
2886 {
2887  return mPaused;
2888 }
2889 
2890 #ifdef EXPERIMENTAL_SCRUBBING_SUPPORT
2892  (double endTimeOrSpeed, const ScrubbingOptions &options)
2893 {
2894  if (mScrubQueue)
2895  return mScrubQueue->Producer(endTimeOrSpeed, options);
2896  else
2897  return false;
2898 }
2899 
2901 {
2902  if (mScrubQueue)
2903  return mScrubQueue->LastTimeInQueue();
2904  else
2905  return -1.0;
2906 }
2907 
2908 #endif
2909 
2911 {
2912  if (mStreamToken != 0)
2913  return true;
2914 
2915  return false;
2916 }
2917 
2919 {
2920  bool isActive = false;
2921  // JKC: Not reporting any Pa error, but that looks OK.
2922  if( mPortStreamV19 )
2923  isActive = (Pa_IsStreamActive( mPortStreamV19 ) > 0);
2924 
2925 #ifdef EXPERIMENTAL_MIDI_OUT
2926  if( mMidiStreamActive && !mMidiOutputComplete )
2927  isActive = true;
2928 #endif
2929  return isActive;
2930 }
2931 
2933 {
2934  return (this->IsStreamActive() && this->IsAudioTokenActive(token));
2935 }
2936 
2938 {
2939  return ( token > 0 && token == mStreamToken );
2940 }
2941 
2943 {
2944  return ( mPortStreamV19 && mStreamToken==0 );
2945 }
2946 
2947 double AudioIO::LimitStreamTime(double absoluteTime) const
2948 {
2949  // Allows for forward or backward play
2950  if (ReversedTime())
2951  return std::max(mT1, std::min(mT0, absoluteTime));
2952  else
2953  return std::max(mT0, std::min(mT1, absoluteTime));
2954 }
2955 
2956 double AudioIO::NormalizeStreamTime(double absoluteTime) const
2957 {
2958  // dmazzoni: This function is needed for two reasons:
2959  // One is for looped-play mode - this function makes sure that the
2960  // position indicator keeps wrapping around. The other reason is
2961  // more subtle - it's because PortAudio can query the hardware for
2962  // the current stream time, and this query is not always accurate.
2963  // Sometimes it's a little behind or ahead, and so this function
2964  // makes sure that at least we clip it to the selection.
2965  //
2966  // msmeyer: There is also the possibility that we are using "cut preview"
2967  // mode. In this case, we should jump over a defined "gap" in the
2968  // audio.
2969 
2970 #ifdef EXPERIMENTAL_SCRUBBING_SUPPORT
2971  // Limit the time between t0 and t1 if not scrubbing.
2972  // Should the limiting be necessary in any play mode if there are no bugs?
2973  if (mPlayMode != PLAY_SCRUB)
2974 #endif
2975  absoluteTime = LimitStreamTime(absoluteTime);
2976 
2977  if (mCutPreviewGapLen > 0)
2978  {
2979  // msmeyer: We're in cut preview mode, so if we are on the right
2980  // side of the gap, we jump over it.
2981  if (absoluteTime > mCutPreviewGapStart)
2982  absoluteTime += mCutPreviewGapLen;
2983  }
2984 
2985  return absoluteTime;
2986 }
2987 
2989 {
2990  if( !IsStreamActive() )
2991  return BAD_STREAM_TIME;
2992 
2993  return NormalizeStreamTime(mTime);
2994 }
2995 
2996 
2997 std::vector<long> AudioIO::GetSupportedPlaybackRates(int devIndex, double rate)
2998 {
2999  if (devIndex == -1)
3000  { // weren't given a device index, get the prefs / default one
3001  devIndex = getPlayDevIndex();
3002  }
3003 
3004  // Check if we can use the cached rates
3005  if (mCachedPlaybackIndex != -1 && devIndex == mCachedPlaybackIndex
3006  && (rate == 0.0 || make_iterator_range(mCachedPlaybackRates).contains(rate)))
3007  {
3008  return mCachedPlaybackRates;
3009  }
3010 
3011  std::vector<long> supported;
3012  int irate = (int)rate;
3013  const PaDeviceInfo* devInfo = NULL;
3014  int i;
3015 
3016  devInfo = Pa_GetDeviceInfo(devIndex);
3017 
3018  if (!devInfo)
3019  {
3020  wxLogDebug(wxT("GetSupportedPlaybackRates() Could not get device info!"));
3021  return supported;
3022  }
3023 
3024  // LLL: Remove when a proper method of determining actual supported
3025  // DirectSound rate is devised.
3026  const PaHostApiInfo* hostInfo = Pa_GetHostApiInfo(devInfo->hostApi);
3027  bool isDirectSound = (hostInfo && hostInfo->type == paDirectSound);
3028 
3029  PaStreamParameters pars;
3030 
3031  pars.device = devIndex;
3032  pars.channelCount = 1;
3033  pars.sampleFormat = paFloat32;
3034  pars.suggestedLatency = devInfo->defaultHighOutputLatency;
3035  pars.hostApiSpecificStreamInfo = NULL;
3036 
3037  // JKC: PortAudio Errors handled OK here. No need to report them
3038  for (i = 0; i < NumRatesToTry; i++)
3039  {
3040  // LLL: Remove when a proper method of determining actual supported
3041  // DirectSound rate is devised.
3042  if (!(isDirectSound && RatesToTry[i] > 200000))
3043  if (Pa_IsFormatSupported(NULL, &pars, RatesToTry[i]) == 0)
3044  supported.push_back(RatesToTry[i]);
3045  }
3046 
3047  if (irate != 0 && !make_iterator_range(supported).contains(irate))
3048  {
3049  // LLL: Remove when a proper method of determining actual supported
3050  // DirectSound rate is devised.
3051  if (!(isDirectSound && RatesToTry[i] > 200000))
3052  if (Pa_IsFormatSupported(NULL, &pars, irate) == 0)
3053  supported.push_back(irate);
3054  }
3055 
3056  return supported;
3057 }
3058 
3059 std::vector<long> AudioIO::GetSupportedCaptureRates(int devIndex, double rate)
3060 {
3061  if (devIndex == -1)
3062  { // not given a device, look up in prefs / default
3063  devIndex = getRecordDevIndex();
3064  }
3065 
3066  // Check if we can use the cached rates
3067  if (mCachedCaptureIndex != -1 && devIndex == mCachedCaptureIndex
3068  && (rate == 0.0 || make_iterator_range(mCachedCaptureRates).contains(rate)))
3069  {
3070  return mCachedCaptureRates;
3071  }
3072 
3073  std::vector<long> supported;
3074  int irate = (int)rate;
3075  const PaDeviceInfo* devInfo = NULL;
3076  int i;
3077 
3078  devInfo = Pa_GetDeviceInfo(devIndex);
3079 
3080  if (!devInfo)
3081  {
3082  wxLogDebug(wxT("GetSupportedCaptureRates() Could not get device info!"));
3083  return supported;
3084  }
3085 
3086  double latencyDuration = DEFAULT_LATENCY_DURATION;
3087  long recordChannels = 1;
3088  gPrefs->Read(wxT("/AudioIO/LatencyDuration"), &latencyDuration);
3089  gPrefs->Read(wxT("/AudioIO/RecordChannels"), &recordChannels);
3090 
3091  // LLL: Remove when a proper method of determining actual supported
3092  // DirectSound rate is devised.
3093  const PaHostApiInfo* hostInfo = Pa_GetHostApiInfo(devInfo->hostApi);
3094  bool isDirectSound = (hostInfo && hostInfo->type == paDirectSound);
3095 
3096  PaStreamParameters pars;
3097 
3098  pars.device = devIndex;
3099  pars.channelCount = recordChannels;
3100  pars.sampleFormat = paFloat32;
3101  pars.suggestedLatency = latencyDuration / 1000.0;
3102  pars.hostApiSpecificStreamInfo = NULL;
3103 
3104  for (i = 0; i < NumRatesToTry; i++)
3105  {
3106  // LLL: Remove when a proper method of determining actual supported
3107  // DirectSound rate is devised.
3108  if (!(isDirectSound && RatesToTry[i] > 200000))
3109  if (Pa_IsFormatSupported(&pars, NULL, RatesToTry[i]) == 0)
3110  supported.push_back(RatesToTry[i]);
3111  }
3112 
3113  if (irate != 0 && !make_iterator_range(supported).contains(irate))
3114  {
3115  // LLL: Remove when a proper method of determining actual supported
3116  // DirectSound rate is devised.
3117  if (!(isDirectSound && RatesToTry[i] > 200000))
3118  if (Pa_IsFormatSupported(&pars, NULL, irate) == 0)
3119  supported.push_back(irate);
3120  }
3121 
3122  return supported;
3123 }
3124 
3125 std::vector<long> AudioIO::GetSupportedSampleRates(int playDevice, int recDevice, double rate)
3126 {
3127  // Not given device indices, look up prefs
3128  if (playDevice == -1) {
3129  playDevice = getPlayDevIndex();
3130  }
3131  if (recDevice == -1) {
3132  recDevice = getRecordDevIndex();
3133  }
3134 
3135  // Check if we can use the cached rates
3136  if (mCachedPlaybackIndex != -1 && mCachedCaptureIndex != -1 &&
3137  playDevice == mCachedPlaybackIndex &&
3138  recDevice == mCachedCaptureIndex &&
3139  (rate == 0.0 || make_iterator_range(mCachedSampleRates).contains(rate)))
3140  {
3141  return mCachedSampleRates;
3142  }
3143 
3144  auto playback = GetSupportedPlaybackRates(playDevice, rate);
3145  auto capture = GetSupportedCaptureRates(recDevice, rate);
3146  int i;
3147 
3148  // Return only sample rates which are in both arrays
3149  std::vector<long> result;
3150 
3151  for (i = 0; i < (int)playback.size(); i++)
3152  if (make_iterator_range(capture).contains(playback[i]))
3153  result.push_back(playback[i]);
3154 
3155  // If this yields no results, use the default sample rates nevertheless
3156 /* if (result.IsEmpty())
3157  {
3158  for (i = 0; i < NumStandardRates; i++)
3159  result.Add(StandardRates[i]);
3160  }*/
3161 
3162  return result;
3163 }
3164 
3170 {
3171  auto rates = GetSupportedSampleRates();
3172 
3173  if (make_iterator_range(rates).contains(44100))
3174  return 44100;
3175 
3176  if (make_iterator_range(rates).contains(48000))
3177  return 48000;
3178 
3179  // if there are no supported rates, the next bit crashes. So check first,
3180  // and give them a "sensible" value if there are no valid values. They
3181  // will still get an error later, but with any luck may have changed
3182  // something by then. It's no worse than having an invalid default rate
3183  // stored in the preferences, which we don't check for
3184  if (rates.empty()) return 44100;
3185 
3186  return rates.back();
3187 }
3188 
3189 double AudioIO::GetBestRate(bool capturing, bool playing, double sampleRate)
3190 {
3191  // Check if we can use the cached value
3192  if (mCachedBestRateIn != 0.0 && mCachedBestRateIn == sampleRate) {
3193  return mCachedBestRateOut;
3194  }
3195 
3196  // In order to cache the value, all early returns should instead set retval
3197  // and jump to finished
3198  double retval;
3199 
3200  std::vector<long> rates;
3201  if (capturing) wxLogDebug(wxT("AudioIO::GetBestRate() for capture"));
3202  if (playing) wxLogDebug(wxT("AudioIO::GetBestRate() for playback"));
3203  wxLogDebug(wxT("GetBestRate() suggested rate %.0lf Hz"), sampleRate);
3204 
3205  if (capturing && !playing) {
3206  rates = GetSupportedCaptureRates(-1, sampleRate);
3207  }
3208  else if (playing && !capturing) {
3209  rates = GetSupportedPlaybackRates(-1, sampleRate);
3210  }
3211  else { // we assume capturing and playing - the alternative would be a
3212  // bit odd
3213  rates = GetSupportedSampleRates(-1, -1, sampleRate);
3214  }
3215  /* rem rates is the array of hardware-supported sample rates (in the current
3216  * configuration), sampleRate is the Project Rate (desired sample rate) */
3217  long rate = (long)sampleRate;
3218 
3219  if (make_iterator_range(rates).contains(rate)) {
3220  wxLogDebug(wxT("GetBestRate() Returning %.0ld Hz"), rate);
3221  retval = rate;
3222  goto finished;
3223  /* the easy case - the suggested rate (project rate) is in the list, and
3224  * we can just accept that and send back to the caller. This should be
3225  * the case for most users most of the time (all of the time on
3226  * Win MME as the OS does resampling) */
3227  }
3228 
3229  /* if we get here, there is a problem - the project rate isn't supported
3230  * on our hardware, so we can't us it. Need to come up with an alternative
3231  * rate to use. The process goes like this:
3232  * * If there are no rates to pick from, we're stuck and return 0 (error)
3233  * * If there are some rates, we pick the next one higher than the requested
3234  * rate to use.
3235  * * If there aren't any higher, we use the highest available rate */
3236 
3237  if (rates.empty()) {
3238  /* we're stuck - there are no supported rates with this hardware. Error */
3239  wxLogDebug(wxT("GetBestRate() Error - no supported sample rates"));
3240  retval = 0.0;
3241  goto finished;
3242  }
3243  int i;
3244  for (i = 0; i < (int)rates.size(); i++) // for each supported rate
3245  {
3246  if (rates[i] > rate) {
3247  // supported rate is greater than requested rate
3248  wxLogDebug(wxT("GetBestRate() Returning next higher rate - %.0ld Hz"), rates[i]);
3249  retval = rates[i];
3250  goto finished;
3251  }
3252  }
3253 
3254  wxLogDebug(wxT("GetBestRate() Returning highest rate - %.0ld Hz"), rates.back());
3255  retval = rates.back(); // the highest available rate
3256  goto finished;
3257 
3258 finished:
3259  mCachedBestRateIn = sampleRate;
3260  mCachedBestRateOut = retval;
3261  return retval;
3262 }
3263 
3264 
3266 //
3267 // Audio Thread Context
3268 //
3270 
3271 AudioThread::ExitCode AudioThread::Entry()
3272 {
3273  while( !TestDestroy() )
3274  {
3275  // Set LoopActive outside the tests to avoid race condition
3278  {
3279  gAudioIO->FillBuffers();
3281  }
3283  {
3284  gAudioIO->FillBuffers();
3285  }
3287 
3289  // Rely on the Wait() in ScrubQueue::Transformer()
3290  // This allows the scrubbing update interval to be made very short without
3291  // playback becoming intermittent.
3292  }
3293  else {
3294  // Perhaps this too could use a condition variable, for available space in the
3295  // ring buffer, instead of a polling loop? But no harm in doing it this way.
3296  Sleep(10);
3297  }
3298  }
3299 
3300  return 0;
3301 }
3302 
3303 
3304 #ifdef EXPERIMENTAL_MIDI_OUT
3305 MidiThread::ExitCode MidiThread::Entry()
3306 {
3307  while( !TestDestroy() )
3308  {
3309  // Set LoopActive outside the tests to avoid race condition
3310  gAudioIO->mMidiThreadFillBuffersLoopActive = true;
3311  if( gAudioIO->mMidiThreadFillBuffersLoopRunning &&
3312  // mNumFrames signals at least one callback, needed for MidiTime()
3313  gAudioIO->mNumFrames > 0)
3314  {
3315  gAudioIO->FillMidiBuffers();
3316  }
3317  gAudioIO->mMidiThreadFillBuffersLoopActive = false;
3318  Sleep(MIDI_SLEEP);
3319  }
3320  return 0;
3321 }
3322 #endif
3323 
3325 {
3326  auto commonlyAvail = mPlaybackBuffers[0]->AvailForPut();
3327  for (unsigned i = 1; i < mPlaybackTracks.size(); ++i)
3328  commonlyAvail = std::min(commonlyAvail,
3329  mPlaybackBuffers[i]->AvailForPut());
3330  return commonlyAvail;
3331 }
3332 
3334 {
3335  auto commonlyAvail = mCaptureBuffers[0]->AvailForGet();
3336  for (unsigned i = 1; i < mCaptureTracks.size(); ++i)
3337  commonlyAvail = std::min(commonlyAvail,
3338  mCaptureBuffers[i]->AvailForGet());
3339  return commonlyAvail;
3340 }
3341 
3342 #if USE_PORTMIXER
3343 int AudioIO::getRecordSourceIndex(PxMixer *portMixer)
3344 {
3345  int i;
3346  wxString sourceName = gPrefs->Read(wxT("/AudioIO/RecordingSource"), wxT(""));
3347  int numSources = Px_GetNumInputSources(portMixer);
3348  for (i = 0; i < numSources; i++) {
3349  if (sourceName == wxString(wxSafeConvertMB2WX(Px_GetInputSourceName(portMixer, i))))
3350  return i;
3351  }
3352  return -1;
3353 }
3354 #endif
3355 
3356 int AudioIO::getPlayDevIndex(const wxString &devNameArg)
3357 {
3358  wxString devName(devNameArg);
3359  // if we don't get given a device, look up the preferences
3360  if (devName.IsEmpty())
3361  {
3362  devName = gPrefs->Read(wxT("/AudioIO/PlaybackDevice"), wxT(""));
3363  }
3364 
3365  wxString hostName = gPrefs->Read(wxT("/AudioIO/Host"), wxT(""));
3366  PaHostApiIndex hostCnt = Pa_GetHostApiCount();
3367  PaHostApiIndex hostNum;
3368  for (hostNum = 0; hostNum < hostCnt; hostNum++)
3369  {
3370  const PaHostApiInfo *hinfo = Pa_GetHostApiInfo(hostNum);
3371  if (hinfo && wxString(wxSafeConvertMB2WX(hinfo->name)) == hostName)
3372  {
3373  for (PaDeviceIndex hostDevice = 0; hostDevice < hinfo->deviceCount; hostDevice++)
3374  {
3375  PaDeviceIndex deviceNum = Pa_HostApiDeviceIndexToDeviceIndex(hostNum, hostDevice);
3376 
3377  const PaDeviceInfo *dinfo = Pa_GetDeviceInfo(deviceNum);
3378  if (dinfo && DeviceName(dinfo) == devName && dinfo->maxOutputChannels > 0 )
3379  {
3380  // this device name matches the stored one, and works.
3381  // So we say this is the answer and return it
3382  return deviceNum;
3383  }
3384  }
3385 
3386  // The device wasn't found so use the default for this host.
3387  // LL: At this point, preferences and active no longer match.
3388  return hinfo->defaultOutputDevice;
3389  }
3390  }
3391 
3392  // The host wasn't found, so use the default output device.
3393  // FIXME: TRAP_ERR PaErrorCode not handled well (this code is similar to input code
3394  // and the input side has more comments.)
3395 
3396  PaDeviceIndex deviceNum = Pa_GetDefaultOutputDevice();
3397 
3398  // Sometimes PortAudio returns -1 if it cannot find a suitable default
3399  // device, so we just use the first one available
3400  //
3401  // LL: At this point, preferences and active no longer match
3402  //
3403  // And I can't imagine how far we'll get specifying an "invalid" index later
3404  // on...are we certain "0" even exists?
3405  if (deviceNum < 0) {
3406  wxASSERT(false);
3407  deviceNum = 0;
3408  }
3409 
3410  return deviceNum;
3411 }
3412 
3413 int AudioIO::getRecordDevIndex(const wxString &devNameArg)
3414 {
3415  wxString devName(devNameArg);
3416  // if we don't get given a device, look up the preferences
3417  if (devName.IsEmpty())
3418  {
3419  devName = gPrefs->Read(wxT("/AudioIO/RecordingDevice"), wxT(""));
3420  }
3421 
3422  wxString hostName = gPrefs->Read(wxT("/AudioIO/Host"), wxT(""));
3423  PaHostApiIndex hostCnt = Pa_GetHostApiCount();
3424  PaHostApiIndex hostNum;
3425  for (hostNum = 0; hostNum < hostCnt; hostNum++)
3426  {
3427  const PaHostApiInfo *hinfo = Pa_GetHostApiInfo(hostNum);
3428  if (hinfo && wxString(wxSafeConvertMB2WX(hinfo->name)) == hostName)
3429  {
3430  for (PaDeviceIndex hostDevice = 0; hostDevice < hinfo->deviceCount; hostDevice++)
3431  {
3432  PaDeviceIndex deviceNum = Pa_HostApiDeviceIndexToDeviceIndex(hostNum, hostDevice);
3433 
3434  const PaDeviceInfo *dinfo = Pa_GetDeviceInfo(deviceNum);
3435  if (dinfo && DeviceName(dinfo) == devName && dinfo->maxInputChannels > 0 )
3436  {
3437  // this device name matches the stored one, and works.
3438  // So we say this is the answer and return it
3439  return deviceNum;
3440  }
3441  }
3442 
3443  // The device wasn't found so use the default for this host.
3444  // LL: At this point, preferences and active no longer match.
3445  return hinfo->defaultInputDevice;
3446  }
3447  }
3448 
3449  // The host wasn't found, so use the default input device.
3450  // FIXME: TRAP_ERR PaErrorCode not handled well in getRecordDevIndex()
3451  PaDeviceIndex deviceNum = Pa_GetDefaultInputDevice();
3452 
3453  // Sometimes PortAudio returns -1 if it cannot find a suitable default
3454  // device, so we just use the first one available
3455  // PortAudio has an error reporting function. We should log/report the error?
3456  //
3457  // LL: At this point, preferences and active no longer match
3458  //
3459  // And I can't imagine how far we'll get specifying an "invalid" index later
3460  // on...are we certain "0" even exists?
3461  if (deviceNum < 0) {
3462  // JKC: This ASSERT will happen if you run with no config file
3463  // This happens once. Config file will exist on the next run.
3464  // TODO: Look into this a bit more. Could be relevant to blank Device Toolbar.
3465  wxASSERT(false);
3466  deviceNum = 0;
3467  }
3468 
3469  return deviceNum;
3470 }
3471 
3473 {
3474  wxStringOutputStream o;
3475  wxTextOutputStream s(o, wxEOL_UNIX);
3476  wxString e(wxT("\n"));
3477 
3478  if (IsStreamActive()) {
3479  return wxT("Stream is active ... unable to gather information.");
3480  }
3481 
3482 
3483  // FIXME: TRAP_ERR PaErrorCode not handled. 3 instances in GetDeviceInfo().
3484  int recDeviceNum = Pa_GetDefaultInputDevice();
3485  int playDeviceNum = Pa_GetDefaultOutputDevice();
3486  int cnt = Pa_GetDeviceCount();
3487 
3488  wxLogDebug(wxT("Portaudio reports %d audio devices"),cnt);
3489 
3490  s << wxT("==============================") << e;
3491  s << wxT("Default recording device number: ") << recDeviceNum << e;
3492  s << wxT("Default playback device number: ") << playDeviceNum << e;
3493 
3494  wxString recDevice = gPrefs->Read(wxT("/AudioIO/RecordingDevice"), wxT(""));
3495  wxString playDevice = gPrefs->Read(wxT("/AudioIO/PlaybackDevice"), wxT(""));
3496  int j;
3497 
3498  // This gets info on all available audio devices (input and output)
3499  if (cnt <= 0) {
3500  s << wxT("No devices found\n");
3501  return o.GetString();
3502  }
3503 
3504  const PaDeviceInfo* info;
3505 
3506  for (j = 0; j < cnt; j++) {
3507  s << wxT("==============================") << e;
3508 
3509  info = Pa_GetDeviceInfo(j);
3510  if (!info) {
3511  s << wxT("Device info unavailable for: ") << j << wxT("\n");
3512  continue;
3513  }
3514 
3515  wxString name = DeviceName(info);
3516  s << wxT("Device ID: ") << j << e;
3517  s << wxT("Device name: ") << name << e;
3518  s << wxT("Host name: ") << HostName(info) << e;
3519  s << wxT("Recording channels: ") << info->maxInputChannels << e;
3520  s << wxT("Playback channels: ") << info->maxOutputChannels << e;
3521  s << wxT("Low Recording Latency: ") << info->defaultLowInputLatency << e;
3522  s << wxT("Low Playback Latency: ") << info->defaultLowOutputLatency << e;
3523  s << wxT("High Recording Latency: ") << info->defaultHighInputLatency << e;
3524  s << wxT("High Playback Latency: ") << info->defaultHighOutputLatency << e;
3525 
3526  auto rates = GetSupportedPlaybackRates(j, 0.0);
3527 
3528  s << wxT("Supported Rates:") << e;
3529  for (int k = 0; k < (int) rates.size(); k++) {
3530  s << wxT(" ") << (int)rates[k] << e;
3531  }
3532 
3533  if (name == playDevice && info->maxOutputChannels > 0)
3534  playDeviceNum = j;
3535 
3536  if (name == recDevice && info->maxInputChannels > 0)
3537  recDeviceNum = j;
3538 
3539  // Sometimes PortAudio returns -1 if it cannot find a suitable default
3540  // device, so we just use the first one available
3541  if (recDeviceNum < 0 && info->maxInputChannels > 0){
3542  recDeviceNum = j;
3543  }
3544  if (playDeviceNum < 0 && info->maxOutputChannels > 0){
3545  playDeviceNum = j;
3546  }
3547  }
3548 
3549  bool haveRecDevice = (recDeviceNum >= 0);
3550  bool havePlayDevice = (playDeviceNum >= 0);
3551 
3552  s << wxT("==============================") << e;
3553  if(haveRecDevice){
3554  s << wxT("Selected recording device: ") << recDeviceNum << wxT(" - ") << recDevice << e;
3555  }else{
3556  s << wxT("No recording device found for '") << recDevice << wxT("'.") << e;
3557  }
3558  if(havePlayDevice){
3559  s << wxT("Selected playback device: ") << playDeviceNum << wxT(" - ") << playDevice << e;
3560  }else{
3561  s << wxT("No playback device found for '") << playDevice << wxT("'.") << e;
3562  }
3563 
3564  std::vector<long> supportedSampleRates;
3565 
3566  if(havePlayDevice && haveRecDevice){
3567  supportedSampleRates = GetSupportedSampleRates(playDeviceNum, recDeviceNum);
3568 
3569  s << wxT("Supported Rates:") << e;
3570  for (int k = 0; k < (int) supportedSampleRates.size(); k++) {
3571  s << wxT(" ") << (int)supportedSampleRates[k] << e;
3572  }
3573  }else{
3574  s << wxT("Cannot check mutual sample rates without both devices.") << e;
3575  return o.GetString();
3576  }
3577 
3578 #if defined(USE_PORTMIXER)
3579  if (supportedSampleRates.size() > 0)
3580  {
3581  int highestSampleRate = supportedSampleRates.back();
3582  bool EmulateMixerInputVol = true;
3583  bool EmulateMixerOutputVol = true;
3584  float MixerInputVol = 1.0;
3585  float MixerOutputVol = 1.0;
3586 
3587  int error;
3588 
3589  PaStream *stream;
3590 
3591  PaStreamParameters playbackParameters;
3592 
3593  playbackParameters.device = playDeviceNum;
3594  playbackParameters.sampleFormat = paFloat32;
3595  playbackParameters.hostApiSpecificStreamInfo = NULL;
3596  playbackParameters.channelCount = 1;
3597  if (Pa_GetDeviceInfo(playDeviceNum)){
3598  playbackParameters.suggestedLatency =
3599  Pa_GetDeviceInfo(playDeviceNum)->defaultLowOutputLatency;
3600  }
3601  else{
3602  playbackParameters.suggestedLatency = DEFAULT_LATENCY_CORRECTION/1000.0;
3603  }
3604 
3605  PaStreamParameters captureParameters;
3606 
3607  captureParameters.device = recDeviceNum;
3608  captureParameters.sampleFormat = paFloat32;;
3609  captureParameters.hostApiSpecificStreamInfo = NULL;
3610  captureParameters.channelCount = 1;
3611  if (Pa_GetDeviceInfo(recDeviceNum)){
3612  captureParameters.suggestedLatency =
3613  Pa_GetDeviceInfo(recDeviceNum)->defaultLowInputLatency;
3614  }else{
3615  captureParameters.suggestedLatency = DEFAULT_LATENCY_CORRECTION/1000.0;
3616  }
3617 
3618  error = Pa_OpenStream(&stream,
3619  &captureParameters, &playbackParameters,
3620  highestSampleRate, paFramesPerBufferUnspecified,
3621  paClipOff | paDitherOff,
3622  audacityAudioCallback, NULL);
3623 
3624  if (error) {
3625  error = Pa_OpenStream(&stream,
3626  &captureParameters, NULL,
3627  highestSampleRate, paFramesPerBufferUnspecified,
3628  paClipOff | paDitherOff,
3629  audacityAudioCallback, NULL);
3630  }
3631 
3632  if (error) {
3633  s << wxT("Received ") << error << wxT(" while opening devices") << e;
3634  return o.GetString();
3635  }
3636 
3637  PxMixer *PortMixer = Px_OpenMixer(stream, 0);
3638 
3639  if (!PortMixer) {
3640  s << wxT("Unable to open Portmixer") << e;
3641  Pa_CloseStream(stream);
3642  return o.GetString();
3643  }
3644 
3645  s << wxT("==============================") << e;
3646  s << wxT("Available mixers:") << e;
3647 
3648  // FIXME: ? PortMixer errors on query not reported in GetDeviceInfo
3649  cnt = Px_GetNumMixers(stream);
3650  for (int i = 0; i < cnt; i++) {
3651  wxString name = wxSafeConvertMB2WX(Px_GetMixerName(stream, i));
3652  s << i << wxT(" - ") << name << e;
3653  }
3654 
3655  s << wxT("==============================") << e;
3656  s << wxT("Available recording sources:") << e;
3657  cnt = Px_GetNumInputSources(PortMixer);
3658  for (int i = 0; i < cnt; i++) {
3659  wxString name = wxSafeConvertMB2WX(Px_GetInputSourceName(PortMixer, i));
3660  s << i << wxT(" - ") << name << e;
3661  }
3662 
3663  s << wxT("==============================") << e;
3664  s << wxT("Available playback volumes:") << e;
3665  cnt = Px_GetNumOutputVolumes(PortMixer);
3666  for (int i = 0; i < cnt; i++) {
3667  wxString name = wxSafeConvertMB2WX(Px_GetOutputVolumeName(PortMixer, i));
3668  s << i << wxT(" - ") << name << e;
3669  }
3670 
3671  // Determine mixer capabilities - it it doesn't support either
3672  // input or output, we emulate them (by multiplying this value
3673  // by all incoming/outgoing samples)
3674 
3675  MixerOutputVol = Px_GetPCMOutputVolume(PortMixer);
3676  EmulateMixerOutputVol = false;
3677  Px_SetPCMOutputVolume(PortMixer, 0.0);
3678  if (Px_GetPCMOutputVolume(PortMixer) > 0.1)
3679  EmulateMixerOutputVol = true;
3680  Px_SetPCMOutputVolume(PortMixer, 0.2f);
3681  if (Px_GetPCMOutputVolume(PortMixer) < 0.1 ||
3682  Px_GetPCMOutputVolume(PortMixer) > 0.3)
3683  EmulateMixerOutputVol = true;
3684  Px_SetPCMOutputVolume(PortMixer, MixerOutputVol);
3685 
3686  MixerInputVol = Px_GetInputVolume(PortMixer);
3687  EmulateMixerInputVol = false;
3688  Px_SetInputVolume(PortMixer, 0.0);
3689  if (Px_GetInputVolume(PortMixer) > 0.1)
3690  EmulateMixerInputVol = true;
3691  Px_SetInputVolume(PortMixer, 0.2f);
3692  if (Px_GetInputVolume(PortMixer) < 0.1 ||
3693  Px_GetInputVolume(PortMixer) > 0.3)
3694  EmulateMixerInputVol = true;
3695  Px_SetInputVolume(PortMixer, MixerInputVol);
3696 
3697  Pa_CloseStream(stream);
3698 
3699  s << wxT("==============================") << e;
3700  s << wxT("Recording volume is ") << (EmulateMixerInputVol? wxT("emulated"): wxT("native")) << e;
3701  s << wxT("Playback volume is ") << (EmulateMixerOutputVol? wxT("emulated"): wxT("native")) << e;
3702 
3703  Px_CloseMixer(PortMixer);
3704 
3705  } //end of massive if statement if a valid sample rate has been found
3706 #endif
3707  return o.GetString();
3708 }
3709 
3710 #ifdef EXPERIMENTAL_MIDI_OUT
3711 // FIXME: When EXPERIMENTAL_MIDI_IN is added (eventually) this should also be enabled -- Poke
3712 wxString AudioIO::GetMidiDeviceInfo()
3713 {
3714  wxStringOutputStream o;
3715  wxTextOutputStream s(o, wxEOL_UNIX);
3716  wxString e(wxT("\n"));
3717 
3718  if (IsStreamActive()) {
3719  return wxT("Stream is active ... unable to gather information.");
3720  }
3721 
3722 
3723  // XXX: May need to trap errors as with the normal device info
3724  int recDeviceNum = Pm_GetDefaultInputDeviceID();
3725  int playDeviceNum = Pm_GetDefaultOutputDeviceID();
3726  int cnt = Pm_CountDevices();
3727 
3728  wxLogDebug(wxT("PortMidi reports %d MIDI devices"), cnt);
3729 
3730  s << wxT("==============================") << e;
3731  s << wxT("Default recording device number: ") << recDeviceNum << e;
3732  s << wxT("Default playback device number: ") << playDeviceNum << e;
3733 
3734  wxString recDevice = gPrefs->Read(wxT("/MidiIO/RecordingDevice"), wxT(""));
3735  wxString playDevice = gPrefs->Read(wxT("/MidiIO/PlaybackDevice"), wxT(""));
3736 
3737  // This gets info on all available audio devices (input and output)
3738  if (cnt <= 0) {
3739  s << wxT("No devices found\n");
3740  return o.GetString();
3741  }
3742 
3743  for (int i = 0; i < cnt; i++) {
3744  s << wxT("==============================") << e;
3745 
3746  const PmDeviceInfo* info = Pm_GetDeviceInfo(i);
3747  if (!info) {
3748  s << wxT("Device info unavailable for: ") << i << e;
3749  continue;
3750  }
3751 
3752  wxString name = wxSafeConvertMB2WX(info->name);
3753  wxString hostName = wxSafeConvertMB2WX(info->interf);
3754 
3755  s << wxT("Device ID: ") << i << e;
3756  s << wxT("Device name: ") << name << e;
3757  s << wxT("Host name: ") << hostName << e;
3758  s << wxT("Supports output: ") << info->output << e;
3759  s << wxT("Supports input: ") << info->input << e;
3760  s << wxT("Opened: ") << info->opened << e;
3761 
3762  if (name == playDevice && info->output)
3763  playDeviceNum = i;
3764 
3765  if (name == recDevice && info->input)
3766  recDeviceNum = i;
3767 
3768  // XXX: This is only done because the same was applied with PortAudio
3769  // If PortMidi returns -1 for the default device, use the first one
3770  if (recDeviceNum < 0 && info->input){
3771  recDeviceNum = i;
3772  }
3773  if (playDeviceNum < 0 && info->output){
3774  playDeviceNum = i;
3775  }
3776  }
3777 
3778  bool haveRecDevice = (recDeviceNum >= 0);
3779  bool havePlayDevice = (playDeviceNum >= 0);
3780 
3781  s << wxT("==============================") << e;
3782  if (haveRecDevice) {
3783  s << wxT("Selected MIDI recording device: ") << recDeviceNum << wxT(" - ") << recDevice << e;
3784  } else {
3785  s << wxT("No MIDI recording device found for '") << recDevice << wxT("'.") << e;
3786  }
3787  if (havePlayDevice) {
3788  s << wxT("Selected MIDI playback device: ") << playDeviceNum << wxT(" - ") << playDevice << e;
3789  } else {
3790  s << wxT("No MIDI playback device found for '") << playDevice << wxT("'.") << e;
3791  }
3792 
3793  // Mention our conditional compilation flags for Alpha only
3794 #ifdef IS_ALPHA
3795 
3796  s << wxT("==============================") << e;
3797 #ifdef EXPERIMENTAL_MIDI_OUT
3798  s << wxT("EXPERIMENTAL_MIDI_OUT is enabled") << e;
3799 #else
3800  s << wxT("EXPERIMENTAL_MIDI_OUT is NOT enabled") << e;
3801 #endif
3802 #ifdef EXPERIMENTAL_MIDI_IN
3803  s << wxT("EXPERIMENTAL_MIDI_IN is enabled") << e;
3804 #else
3805  s << wxT("EXPERIMENTAL_MIDI_IN is NOT enabled") << e;
3806 #endif
3807 
3808 #endif
3809 
3810  return o.GetString();
3811 }
3812 #endif
3813 
3814 // This method is the data gateway between the audio thread (which
3815 // communicates with the disk) and the PortAudio callback thread
3816 // (which communicates with the audio device).
3818 {
3819  unsigned int i;
3820 
3821  auto delayedHandler = [this] ( AudacityException * pException ) {
3822  // In the main thread, stop recording
3823  // This is one place where the application handles disk
3824  // exhaustion exceptions from wave track operations, without rolling
3825  // back to the last pushed undo state. Instead, partial recording
3826  // results are pushed as a NEW undo state. For this reason, as
3827  // commented elsewhere, we want an exception safety guarantee for
3828  // the output wave tracks, after the failed append operation, that
3829  // the tracks remain as they were after the previous successful
3830  // (block-level) appends.
3831 
3832  // Note that the Flush in StopStream() may throw another exception,
3833  // but StopStream() contains that exception, and the logic in
3834  // AudacityException::DelayedHandlerAction prevents redundant message
3835  // boxes.
3836  StopStream();
3837  DefaultDelayedHandlerAction{}( pException );
3838  };
3839 
3840  if (mPlaybackTracks.size() > 0)
3841  {
3842  // Though extremely unlikely, it is possible that some buffers
3843  // will have more samples available than others. This could happen
3844  // if we hit this code during the PortAudio callback. To keep
3845  // things simple, we only write as much data as is vacant in
3846  // ALL buffers, and advance the global time by that much.
3847  // MB: subtract a few samples because the code below has rounding errors
3848  auto nAvailable = (int)GetCommonlyAvailPlayback() - 10;
3849 
3850  //
3851  // Don't fill the buffers at all unless we can do the
3852  // full mMaxPlaybackSecsToCopy. This improves performance
3853  // by not always trying to process tiny chunks, eating the
3854  // CPU unnecessarily.
3855  //
3856  // The exception is if we're at the end of the selected
3857  // region - then we should just fill the buffer.
3858  //
3859  if (nAvailable >= (int)mPlaybackSamplesToCopy ||
3860  (mPlayMode == PLAY_STRAIGHT &&
3861  nAvailable > 0 &&
3862  mWarpedTime+(nAvailable/mRate) >= mWarpedLength))
3863  {
3864  // Limit maximum buffer size (increases performance)
3865  auto available =
3866  std::min<size_t>( nAvailable, mPlaybackSamplesToCopy );
3867 
3868  // msmeyer: When playing a very short selection in looped
3869  // mode, the selection must be copied to the buffer multiple
3870  // times, to ensure, that the buffer has a reasonable size
3871  // This is the purpose of this loop.
3872  // PRL: or, when scrubbing, we may get work repeatedly from the
3873  // scrub queue.
3874  bool done = false;
3875  Maybe<wxMutexLocker> cleanup;
3876  do {
3877  // How many samples to produce for each channel.
3878  auto frames = available;
3879  bool progress = true;
3880 #ifdef EXPERIMENTAL_SCRUBBING_SUPPORT
3881  if (mPlayMode == PLAY_SCRUB)
3882  // scrubbing does not use warped time and length
3883  frames = limitSampleBufferSize(frames, mScrubDuration);
3884  else
3885 #endif
3886  {
3887  double deltat = frames / mRate;
3888  if (mWarpedTime + deltat > mWarpedLength)
3889  {
3890  frames = (mWarpedLength - mWarpedTime) * mRate;
3891  // Don't fall into an infinite loop, if loop-playing a selection
3892  // that is so short, it has no samples: detect that case
3893  progress =
3894  !(mPlayMode == PLAY_LOOPED &&
3895  mWarpedTime == 0.0 && frames == 0);
3896  mWarpedTime = mWarpedLength;
3897  }
3898  else
3899  mWarpedTime += deltat;
3900  }
3901 
3902  if (!progress)
3903  frames = available;
3904 
3905  for (i = 0; i < mPlaybackTracks.size(); i++)
3906  {
3907  // The mixer here isn't actually mixing: it's just doing
3908  // resampling, format conversion, and possibly time track
3909  // warping
3910  decltype(mPlaybackMixers[i]->Process(frames))
3911  processed = 0;
3912  samplePtr warpedSamples;
3913  //don't do anything if we have no length. In particular, Process() will fail an wxAssert
3914  //that causes a crash since this is not the GUI thread and wxASSERT is a GUI call.
3915 
3916  // don't generate either if scrubbing at zero speed.
3917 #ifdef EXPERIMENTAL_SCRUBBING_SUPPORT
3918  const bool silent = (mPlayMode == PLAY_SCRUB) && mSilentScrub;
3919 #else
3920  const bool silent = false;
3921 #endif
3922 
3923  if (progress && !silent && frames > 0)
3924  {
3925  processed = mPlaybackMixers[i]->Process(frames);
3926  wxASSERT(processed <= frames);
3927  warpedSamples = mPlaybackMixers[i]->GetBuffer();
3928  const auto put = mPlaybackBuffers[i]->Put
3929  (warpedSamples, floatSample, processed);
3930  // wxASSERT(put == processed);
3931  // but we can't assert in this thread
3932  wxUnusedVar(put);
3933  }
3934 
3935  //if looping and processed is less than the full chunk/block/buffer that gets pulled from
3936  //other longer tracks, then we still need to advance the ring buffers or
3937  //we'll trip up on ourselves when we start them back up again.
3938  //if not looping we never start them up again, so its okay to not do anything
3939  // If scrubbing, we may be producing some silence. Otherwise this should not happen,
3940  // but makes sure anyway that we produce equal
3941  // numbers of samples for all channels for this pass of the do-loop.
3942  if(processed < frames && mPlayMode != PLAY_STRAIGHT)
3943  {
3944  mSilentBuf.Resize(frames, floatSample);
3945  ClearSamples(mSilentBuf.ptr(), floatSample, 0, frames);
3946  const auto put = mPlaybackBuffers[i]->Put
3947  (mSilentBuf.ptr(), floatSample, frames - processed);
3948  // wxASSERT(put == frames - processed);
3949  // but we can't assert in this thread
3950  wxUnusedVar(put);
3951  }
3952  }
3953 
3954  available -= frames;
3955  wxASSERT(available >= 0);
3956 
3957  switch (mPlayMode)
3958  {
3959 #ifdef EXPERIMENTAL_SCRUBBING_SUPPORT
3960  case PLAY_SCRUB:
3961  {
3962  mScrubDuration -= frames;
3963  wxASSERT(mScrubDuration >= 0);
3964  done = (available == 0);
3965  if (!done && mScrubDuration <= 0)
3966  {
3967  sampleCount startSample, endSample;
3968  mScrubQueue->Transformer(startSample, endSample, mScrubDuration, cleanup);
3969  if (mScrubDuration < 0)
3970  {
3971  // Can't play anything
3972  // Stop even if we don't fill up available
3973  mScrubDuration = 0;
3974  done = true;
3975  }
3976  else
3977  {
3978  mSilentScrub = (endSample == startSample);
3979  if (!mSilentScrub)
3980  {
3981  double startTime, endTime, speed;
3982  startTime = startSample.as_double() / mRate;
3983  endTime = endSample.as_double() / mRate;
3984  auto diff = (endSample - startSample).as_long_long();
3985  speed = double(std::abs(diff)) / mScrubDuration.as_double();
3986  for (i = 0; i < mPlaybackTracks.size(); i++)
3987  mPlaybackMixers[i]->SetTimesAndSpeed(startTime, endTime, speed);
3988  }
3989  }
3990  }
3991  }
3992  break;
3993 #endif
3994  case PLAY_LOOPED:
3995  {
3996  done = !progress || (available == 0);
3997  // msmeyer: If playing looped, check if we are at the end of the buffer
3998  // and if yes, restart from the beginning.
3999  if (mWarpedTime >= mWarpedLength)
4000  {
4001  for (i = 0; i < mPlaybackTracks.size(); i++)
4002  mPlaybackMixers[i]->Restart();
4003  mWarpedTime = 0.0;
4004  }
4005  }
4006  break;
4007  default:
4008  done = true;
4009  break;
4010  }
4011  } while (!done);
4012  }
4013  } // end of playback buffering
4014 
4015  if (!mRecordingException &&
4016  mCaptureTracks.size() > 0)
4017  GuardedCall( [&] {
4018  // start record buffering
4019  auto commonlyAvail = GetCommonlyAvailCapture();
4020 
4021  //
4022  // Determine how much this will add to captured tracks
4023  //
4024  double deltat = commonlyAvail / mRate;
4025 
4027  deltat >= mMinCaptureSecsToCopy)
4028  {
4029  // Append captured samples to the end of the WaveTracks.
4030  // The WaveTracks have their own buffering for efficiency.
4031  AutoSaveFile blockFileLog;
4032  auto numChannels = mCaptureTracks.size();
4033 
4034  for( i = 0; i < numChannels; i++ )
4035  {
4036  auto avail = commonlyAvail;
4037  sampleFormat trackFormat = mCaptureTracks[i]->GetSampleFormat();
4038 
4039  AutoSaveFile appendLog;
4040 
4041  if( mFactor == 1.0 )
4042  {
4043  SampleBuffer temp(avail, trackFormat);
4044  const auto got =
4045  mCaptureBuffers[i]->Get(temp.ptr(), trackFormat, avail);
4046  // wxASSERT(got == avail);
4047  // but we can't assert in this thread
4048  wxUnusedVar(got);
4049  // see comment in second handler about guarantee
4050  mCaptureTracks[i]-> Append(temp.ptr(), trackFormat, avail, 1,
4051  &appendLog);
4052  }
4053  else
4054  {
4055  size_t size = lrint(avail * mFactor);
4056  SampleBuffer temp1(avail, floatSample);
4057  SampleBuffer temp2(size, floatSample);
4058  const auto got =
4059  mCaptureBuffers[i]->Get(temp1.ptr(), floatSample, avail);
4060  // wxASSERT(got == avail);
4061  // but we can't assert in this thread
4062  wxUnusedVar(got);
4063  /* we are re-sampling on the fly. The last resampling call
4064  * must flush any samples left in the rate conversion buffer
4065  * so that they get recorded
4066  */
4067  const auto results =
4068  mResample[i]->Process(mFactor, (float *)temp1.ptr(), avail,
4069  !IsStreamActive(), (float *)temp2.ptr(), size);
4070  size = results.second;
4071  // see comment in second handler about guarantee
4072  mCaptureTracks[i]-> Append(temp2.ptr(), floatSample, size, 1,
4073  &appendLog);
4074  }
4075 
4076  if (!appendLog.IsEmpty())
4077  {
4078  blockFileLog.StartTag(wxT("recordingrecovery"));
4079  blockFileLog.WriteAttr(wxT("id"), mCaptureTracks[i]->GetAutoSaveIdent());
4080  blockFileLog.WriteAttr(wxT("channel"), (int)i);
4081  blockFileLog.WriteAttr(wxT("numchannels"), numChannels);
4082  blockFileLog.WriteSubTree(appendLog);
4083  blockFileLog.EndTag(wxT("recordingrecovery"));
4084  }
4085  }
4086 
4087  if (mListener && !blockFileLog.IsEmpty())
4088  mListener->OnAudioIONewBlockFiles(blockFileLog);
4089  }
4090  // end of record buffering
4091  },
4092  // handler
4093  [this] ( AudacityException *pException ) {
4094  if ( pException ) {
4095  // So that we don't attempt to fill the recording buffer again
4096  // before the main thread stops recording
4098  return ;
4099  }
4100  else
4101  // Don't want to intercept other exceptions (?)
4102  throw;
4103  },
4104  delayedHandler
4105  );
4106 }
4107 
4109 {
4110  if (IsBusy())
4111  return;
4112 
4113  mListener = listener;
4114 }
4115 
4116 #ifdef EXPERIMENTAL_MIDI_OUT
4117 
4118 static Alg_update gAllNotesOff; // special event for loop ending
4119 // the fields of this event are never used, only the address is important
4120 
4121 double AudioIO::UncorrectedMidiEventTime()
4122 {
4123  double time;
4124  if (mTimeTrack)
4125  time =
4126  mTimeTrack->ComputeWarpedLength(mT0, mNextEventTime - MidiLoopOffset())
4127  + mT0 + (mMidiLoopPasses * mWarpedLength);
4128  else
4129  time = mNextEventTime;
4130 
4131  return time + PauseTime();
4132 }
4133 
4134 void AudioIO::OutputEvent()
4135 {
4136  int channel = (mNextEvent->chan) & 0xF; // must be in [0..15]
4137  int command = -1;
4138  int data1 = -1;
4139  int data2 = -1;
4140 
4141  double eventTime = UncorrectedMidiEventTime();
4142 
4143  // 0.0005 is for rounding
4144  double time = eventTime + 0.0005 -
4145  (mSynthLatency * 0.001);
4146 
4147  time += 1; // MidiTime() has a 1s offset
4148  // state changes have to go out without delay because the
4149  // midi stream time gets reset when playback starts, and
4150  // we don't want to leave any control changes scheduled for later
4151  if (time < 0 || mSendMidiState) time = 0;
4152  PmTimestamp timestamp = (PmTimestamp) (time * 1000); /* s to ms */
4153 
4154  // The special event gAllNotesOff means "end of playback, send
4155  // all notes off on all channels"
4156  if (mNextEvent == &gAllNotesOff) {
4157  bool looping = (mPlayMode == gAudioIO->PLAY_LOOPED);
4158  AllNotesOff(looping);
4159  if (looping) {
4160  // jump back to beginning of loop
4161  ++mMidiLoopPasses;
4162  PrepareMidiIterator(false, MidiLoopOffset());
4163  } else {
4164  mNextEvent = NULL;
4165  }
4166  return;
4167  }
4168 
4169  // if mNextEvent's channel is visible, play it, visibility can
4170  // be updated while playing. Be careful: if we have a note-off,
4171  // then we must not pay attention to the channel selection
4172  // or mute/solo buttons because we must turn the note off
4173  // even if the user changed something after the note began
4174  // Note that because multiple tracks can output to the same
4175  // MIDI channels, it is not a good idea to send "All Notes Off"
4176  // when the user presses the mute button. We have no easy way
4177  // to know what notes are sounding on any given muted track, so
4178  // we'll just wait for the note-off events to happen.
4179  // Also note that note-offs are only sent when we call
4180  // mIterator->request_note_off(), so notes that are not played
4181  // will note generate random note-offs. There is the interesting
4182  // case that if the playback is paused, all-notes-off WILL be sent
4183  // and if playback resumes, the pending note-off events WILL also
4184  // be sent (but if that is a problem, there would also be a problem
4185  // in the non-pause case.
4186  if (((mNextEventTrack->IsVisibleChan(channel)) &&
4187  // only play if note is not muted:
4188  !((mHasSolo || mNextEventTrack->GetMute()) &&
4189  !mNextEventTrack->GetSolo())) ||
4190  (mNextEvent->is_note() && !mNextIsNoteOn)) {
4191  // Note event
4192  if (mNextEvent->is_note() && !mSendMidiState) {
4193  // Pitch and velocity
4194  data1 = mNextEvent->get_pitch();
4195  if (mNextIsNoteOn) {
4196  data2 = mNextEvent->get_loud(); // get velocity
4197  int offset = mNextEventTrack->GetVelocity();
4198  data2 += offset; // offset comes from per-track slider
4199  // clip velocity to insure a legal note-on value
4200  data2 = (data2 < 1 ? 1 : (data2 > 127 ? 127 : data2));
4201  // since we are going to play this note, we need to get a note_off
4202  mIterator->request_note_off();
4203 
4204 #ifdef AUDIO_IO_GB_MIDI_WORKAROUND
4205  mPendingNotesOff.push_back(std::make_pair(channel, data1));
4206 #endif
4207  }
4208  else {
4209  data2 = 0; // 0 velocity means "note off"
4210 #ifdef AUDIO_IO_GB_MIDI_WORKAROUND
4211  auto end = mPendingNotesOff.end();
4212  auto iter = std::find(
4213  mPendingNotesOff.begin(), end, std::make_pair(channel, data1) );
4214  if (iter != end)
4215  mPendingNotesOff.erase(iter);
4216 #endif
4217  }
4218  command = 0x90; // MIDI NOTE ON (or OFF when velocity == 0)
4219  // Update event
4220  } else if (mNextEvent->is_update()) {
4221  // this code is based on allegrosmfwr.cpp -- it could be improved
4222  // by comparing attribute pointers instead of string compares
4223  Alg_update_ptr update = (Alg_update_ptr) mNextEvent;
4224  const char *name = update->get_attribute();
4225 
4226  if (!strcmp(name, "programi")) {
4227  // Instrument change
4228  data1 = update->parameter.i;
4229  data2 = 0;
4230  command = 0xC0; // MIDI PROGRAM CHANGE
4231  } else if (!strncmp(name, "control", 7)) {
4232  // Controller change
4233 
4234  // The number of the controller being changed is embedded
4235  // in the parameter name.
4236  data1 = atoi(name + 7);
4237  // Allegro normalizes controller values
4238  data2 = ROUND(update->parameter.r * 127);
4239  command = 0xB0;
4240  } else if (!strcmp(name, "bendr")) {
4241  // Bend change
4242 
4243  // Reverse Allegro's post-processing of bend values
4244  int temp = ROUND(0x2000 * (update->parameter.r + 1));
4245  if (temp > 0x3fff) temp = 0x3fff; // 14 bits maximum
4246  if (temp < 0) temp = 0;
4247  data1 = temp & 0x7f; // low 7 bits
4248  data2 = temp >> 7; // high 7 bits
4249  command = 0xE0; // MIDI PITCH BEND
4250  } else if (!strcmp(name, "pressurer")) {
4251  // Pressure change
4252  data1 = (int) (update->parameter.r * 127);
4253  if (update->get_identifier() < 0) {
4254  // Channel pressure
4255  data2 = 0;
4256  command = 0xD0; // MIDI CHANNEL PRESSURE
4257  } else {
4258  // Key pressure
4259  data2 = data1;
4260  data1 = update->get_identifier();
4261  command = 0xA0; // MIDI POLY PRESSURE
4262  }
4263  }
4264  }
4265  if (command != -1) {
4266  // keep track of greatest timestamp used
4267  if (timestamp > mMaxMidiTimestamp) {
4268  mMaxMidiTimestamp = timestamp;
4269  }
4270  Pm_WriteShort(mMidiStream, timestamp,
4271  Pm_Message((int) (command + channel),
4272  (long) data1, (long) data2));
4273  /* wxPrintf("Pm_WriteShort %lx (%p) @ %d, advance %d\n",
4274  Pm_Message((int) (command + channel),
4275  (long) data1, (long) data2),
4276  mNextEvent, timestamp, timestamp - Pt_Time()); */
4277  }
4278  }
4279 }
4280 
4281 void AudioIO::GetNextEvent()
4282 {
4283  mNextEventTrack = NULL; // clear it just to be safe
4284  // now get the next event and the track from which it came
4285  double nextOffset;
4286  if (!mIterator) {
4287  mNextEvent = NULL;
4288  return;
4289  }
4290  auto midiLoopOffset = MidiLoopOffset();
4291  mNextEvent = mIterator->next(&mNextIsNoteOn,
4292  (void **) &mNextEventTrack,
4293  &nextOffset, mT1 + midiLoopOffset);
4294 
4295  mNextEventTime = mT1 + midiLoopOffset + 1;
4296  if (mNextEvent) {
4297  mNextEventTime = (mNextIsNoteOn ? mNextEvent->time :
4298  mNextEvent->get_end_time()) + nextOffset;;
4299  }
4300  if (mNextEventTime > (mT1 + midiLoopOffset)){ // terminate playback at mT1
4301  mNextEvent = &gAllNotesOff;
4302  mNextEventTime = mT1 + midiLoopOffset - ALG_EPS;
4303  mNextIsNoteOn = true; // do not look at duration
4304  mIterator->end();
4305  mIterator.reset(); // debugging aid
4306  }
4307 }
4308 
4309 
4310 bool AudioIO::SetHasSolo(bool hasSolo)
4311 {
4312  mHasSolo = hasSolo;
4313  return mHasSolo;
4314 }
4315 
4316 
4317 void AudioIO::FillMidiBuffers()
4318 {
4319  // Keep track of time paused. If not paused, fill buffers.
4320  if (gAudioIO->IsPaused()) {
4321  if (!gAudioIO->mMidiPaused) {
4322  gAudioIO->mMidiPaused = true;
4323  gAudioIO->AllNotesOff(); // to avoid hanging notes during pause
4324  }
4325  return;
4326  }
4327 
4328  if (gAudioIO->mMidiPaused) {
4329  gAudioIO->mMidiPaused = false;
4330  }
4331 
4332  bool hasSolo = false;
4333  auto numPlaybackTracks = gAudioIO->mPlaybackTracks.size();
4334  for(unsigned t = 0; t < numPlaybackTracks; t++ )
4335  if( gAudioIO->mPlaybackTracks[t]->GetSolo() ) {
4336  hasSolo = true;
4337  break;
4338  }
4339  auto numMidiPlaybackTracks = gAudioIO->mMidiPlaybackTracks.size();
4340  for(unsigned t = 0; t < numMidiPlaybackTracks; t++ )
4341  if( gAudioIO->mMidiPlaybackTracks[t]->GetSolo() ) {
4342  hasSolo = true;
4343  break;
4344  }
4345  SetHasSolo(hasSolo);
4346  // If we compute until mNextEventTime > current audio track time,
4347  // we would have a built-in compute-ahead of mAudioOutLatency, and
4348  // it's probably good to compute MIDI when we compute audio (so when
4349  // we stop, both stop about the same time).
4350  double time = AudioTime(); // compute to here
4351  // But if mAudioOutLatency is very low, we might need some extra
4352  // compute-ahead to deal with mSynthLatency or even this thread.
4353  double actual_latency = (MIDI_SLEEP + THREAD_LATENCY +
4354  MIDI_MINIMAL_LATENCY_MS + mSynthLatency) * 0.001;
4355  if (actual_latency > mAudioOutLatency) {
4356  time += actual_latency - mAudioOutLatency;
4357  }
4358  while (mNextEvent &&
4359  UncorrectedMidiEventTime() < time) {
4360  OutputEvent();
4361  GetNextEvent();
4362  }
4363 
4364  // test for end
4365  double realTime = gAudioIO->MidiTime() * 0.001 -
4366  gAudioIO->PauseTime();
4367  realTime -= 1; // MidiTime() runs ahead 1s
4368 
4369  // XXX Is this still true now? It seems to break looping --Poke
4370  //
4371  // The TrackPanel::OnTimer() method updates the time position
4372  // indicator every 200ms, so it tends to not advance the
4373  // indicator to the end of the selection (mT1) but instead stop
4374  // up to 200ms before the end. At this point, output is shut
4375  // down and the indicator is removed, but for a brief time, the
4376  // indicator is clearly stopped before reaching mT1. To avoid
4377  // this, we do not set mMidiOutputComplete until we are actually
4378  // 0.22s beyond mT1 (even though we stop playing at mT1). This
4379  // gives OnTimer() time to wake up and draw the final time
4380  // position at mT1 before shutting down the stream.
4381  const double loopDelay = 0.220;
4382 
4383  double timeAtSpeed;
4384  if (gAudioIO->mTimeTrack)
4385  timeAtSpeed = gAudioIO->mTimeTrack->SolveWarpedLength(gAudioIO->mT0, realTime);
4386  else
4387  timeAtSpeed = realTime;
4388 
4389  gAudioIO->mMidiOutputComplete =
4390  (gAudioIO->mPlayMode == gAudioIO->PLAY_STRAIGHT && // PRL: what if scrubbing?
4391  timeAtSpeed >= gAudioIO->mT1 + loopDelay);
4392  // !gAudioIO->mNextEvent);
4393 }
4394 
4395 double AudioIO::PauseTime()
4396 {
4397  return mNumPauseFrames / mRate;
4398 }
4399 
4400 
4401 // MidiTime() is an estimate in milliseconds of the current audio
4402 // output (DAC) time + 1s. In other words, what audacity track time
4403 // corresponds to the audio (including pause insertions) at the output?
4404 //
4405 PmTimestamp AudioIO::MidiTime()
4406 {
4407  // note: the extra 0.0005 is for rounding. Round down by casting to
4408  // unsigned long, then convert to PmTimeStamp (currently signed)
4409 
4410  // PRL: the time correction is really Midi latency achieved by different
4411  // means than specifying it to Pm_OpenStream. The use of the accumulated
4412  // sample count generated by the audio callback (in AudioTime()) might also
4413  // have the virtue of keeping the Midi output synched with audio.
4414 
4415  PmTimestamp ts;
4416  // subtract latency here because mSystemMinusAudioTime gets us
4417  // to the current *write* time, but we're writing ahead by audio output
4418  // latency (mAudioOutLatency).
4419  double now = SystemTime(mUsingAlsa);
4420  ts = (PmTimestamp) ((unsigned long)
4421  (1000 * (now + 1.0005 -
4422  mSystemMinusAudioTimePlusLatency)));
4423  // wxPrintf("AudioIO::MidiTime() %d time %g sys-aud %g\n",
4424  // ts, now, mSystemMinusAudioTime);
4425  return ts + MIDI_MINIMAL_LATENCY_MS;
4426 }
4427 
4428 
4429 void AudioIO::AllNotesOff(bool looping)
4430 {
4431 #ifdef __WXGTK__
4432  bool doDelay = !looping;
4433 #else
4434  bool doDelay = false;
4435  static_cast<void>(looping);// compiler food.
4436 #endif
4437 
4438  // to keep track of when MIDI should all be delivered,
4439  // update mMaxMidiTimestamp to now:
4440  PmTimestamp now = MidiTime();
4441  if (mMaxMidiTimestamp < now) {
4442  mMaxMidiTimestamp = now;
4443  }
4444 #ifdef AUDIO_IO_GB_MIDI_WORKAROUND
4445  // PRL:
4446  // Send individual note-off messages for each note-on not yet paired.
4447 
4448  // RBD:
4449  // Even this did not work as planned. My guess is ALSA does not use
4450  // a "stable sort" for timed messages, so that when a note-off is
4451  // added later at the same time as a future note-on, the order is
4452  // not respected, and the note-off can go first, leaving a stuck note.
4453  // The workaround here is to use mMaxMidiTimestamp to ensure that
4454  // note-offs come at least 1ms later than any previous message
4455 
4456  // PRL:
4457  // I think we should do that only when stopping or pausing, not when looping
4458  // Note that on Linux, MIDI always uses ALSA, no matter whether portaudio
4459  // uses some other host api.
4460 
4461  mMaxMidiTimestamp += 1;
4462  for (const auto &pair : mPendingNotesOff) {
4463  Pm_WriteShort(mMidiStream,
4464  (doDelay ? mMaxMidiTimestamp : 0),
4465  Pm_Message(
4466  0x90 + pair.first, pair.second, 0));
4467  mMaxMidiTimestamp++; // allow 1ms per note-off
4468  }
4469  mPendingNotesOff.clear();
4470 
4471  // Proceed to do the usual messages too.
4472 #endif
4473 
4474  for (int chan = 0; chan < 16; chan++) {
4475  Pm_WriteShort(mMidiStream,
4476  (doDelay ? mMaxMidiTimestamp : 0),
4477  Pm_Message(0xB0 + chan, 0x7B, 0));
4478  mMaxMidiTimestamp++; // allow 1ms per all-notes-off
4479  }
4480 }
4481 
4482 #endif
4483 
4484 // Automated Input Level Adjustment - Automatically tries to find an acceptable input volume
4485 #ifdef EXPERIMENTAL_AUTOMATED_INPUT_LEVEL_ADJUSTMENT
4486 void AudioIO::AILAInitialize() {
4487  gPrefs->Read(wxT("/AudioIO/AutomatedInputLevelAdjustment"), &mAILAActive, false);
4488  gPrefs->Read(wxT("/AudioIO/TargetPeak"), &mAILAGoalPoint, AILA_DEF_TARGET_PEAK);
4489  gPrefs->Read(wxT("/AudioIO/DeltaPeakVolume"), &mAILAGoalDelta, AILA_DEF_DELTA_PEAK);
4490  gPrefs->Read(wxT("/AudioIO/AnalysisTime"), &mAILAAnalysisTime, AILA_DEF_ANALYSIS_TIME);
4491  gPrefs->Read(wxT("/AudioIO/NumberAnalysis"), &mAILATotalAnalysis, AILA_DEF_NUMBER_ANALYSIS);
4492  mAILAGoalDelta /= 100.0;
4493  mAILAGoalPoint /= 100.0;
4494  mAILAAnalysisTime /= 1000.0;
4495  mAILAMax = 0.0;
4496  mAILALastStartTime = max(0.0, mT0);
4497  mAILAClipped = false;
4498  mAILAAnalysisCounter = 0;
4499  mAILAChangeFactor = 1.0;
4500  mAILALastChangeType = 0;
4501  mAILATopLevel = 1.0;
4502  mAILAAnalysisEndTime = -1.0;
4503 }
4504 
4505 void AudioIO::AILADisable() {
4506  mAILAActive = false;
4507 }
4508 
4509 bool AudioIO::AILAIsActive() {
4510  return mAILAActive;
4511 }
4512 
4513 void AudioIO::AILASetStartTime() {
4514  mAILAAbsolutStartTime = Pa_GetStreamTime(mPortStreamV19);
4515  wxPrintf("START TIME %f\n\n", mAILAAbsolutStartTime);
4516 }
4517 
4518 double AudioIO::AILAGetLastDecisionTime() {
4519  return mAILAAnalysisEndTime;
4520 }
4521 
4522 void AudioIO::AILAProcess(double maxPeak) {
4524  if (proj && mAILAActive) {
4525  if (mInputMeter && mInputMeter->IsClipping()) {
4526  mAILAClipped = true;
4527  wxPrintf("clipped");
4528  }
4529 
4530  mAILAMax = max(mAILAMax, maxPeak);
4531 
4532  if ((mAILATotalAnalysis == 0 || mAILAAnalysisCounter < mAILATotalAnalysis) && mTime - mAILALastStartTime >= mAILAAnalysisTime) {
4533  putchar('\n');
4534  mAILAMax = mInputMeter ? mInputMeter->ToLinearIfDB(mAILAMax) : 0.0;
4535  double iv = (double) Px_GetInputVolume(mPortMixer);
4536  unsigned short changetype = 0; //0 - no change, 1 - increase change, 2 - decrease change
4537  wxPrintf("mAILAAnalysisCounter:%d\n", mAILAAnalysisCounter);
4538  wxPrintf("\tmAILAClipped:%d\n", mAILAClipped);
4539  wxPrintf("\tmAILAMax (linear):%f\n", mAILAMax);
4540  wxPrintf("\tmAILAGoalPoint:%f\n", mAILAGoalPoint);
4541  wxPrintf("\tmAILAGoalDelta:%f\n", mAILAGoalDelta);
4542  wxPrintf("\tiv:%f\n", iv);
4543  wxPrintf("\tmAILAChangeFactor:%f\n", mAILAChangeFactor);
4544  if (mAILAClipped || mAILAMax > mAILAGoalPoint + mAILAGoalDelta) {
4545  wxPrintf("too high:\n");
4546  mAILATopLevel = min(mAILATopLevel, iv);
4547  wxPrintf("\tmAILATopLevel:%f\n", mAILATopLevel);
4548  //if clipped or too high
4549  if (iv <= LOWER_BOUND) {
4550  //we can't improve it more now
4551  if (mAILATotalAnalysis != 0) {
4552  mAILAActive = false;
4553  proj->TP_DisplayStatusMessage(_("Automated Recording Level Adjustment stopped. It was not possible to optimize it more. Still too high."));
4554  }
4555  wxPrintf("\talready min vol:%f\n", iv);
4556  }
4557  else {
4558  float vol = (float) max(LOWER_BOUND, iv+(mAILAGoalPoint-mAILAMax)*mAILAChangeFactor);
4559  Px_SetInputVolume(mPortMixer, vol);
4560  wxString msg;
4561  msg.Printf(_("Automated Recording Level Adjustment decreased the volume to %f."), vol);
4562  proj->TP_DisplayStatusMessage(msg);
4563  changetype = 1;
4564  wxPrintf("\tnew vol:%f\n", vol);
4565  float check = Px_GetInputVolume(mPortMixer);
4566  wxPrintf("\tverified %f\n", check);
4567  }
4568  }
4569  else if ( mAILAMax < mAILAGoalPoint - mAILAGoalDelta ) {
4570  //if too low
4571  wxPrintf("too low:\n");
4572  if (iv >= UPPER_BOUND || iv + 0.005 > mAILATopLevel) { //condition for too low volumes and/or variable volumes that cause mAILATopLevel to decrease too much
4573  //we can't improve it more
4574  if (mAILATotalAnalysis != 0) {
4575  mAILAActive = false;
4576  proj->TP_DisplayStatusMessage(_("Automated Recording Level Adjustment stopped. It was not possible to optimize it more. Still too low."));
4577  }
4578  wxPrintf("\talready max vol:%f\n", iv);
4579  }
4580  else {
4581  float vol = (float) min(UPPER_BOUND, iv+(mAILAGoalPoint-mAILAMax)*mAILAChangeFactor);
4582  if (vol > mAILATopLevel) {
4583  vol = (iv + mAILATopLevel)/2.0;
4584  wxPrintf("\tTruncated vol:%f\n", vol);
4585  }
4586  Px_SetInputVolume(mPortMixer, vol);
4587  wxString msg;
4588  msg.Printf(_("Automated Recording Level Adjustment increased the volume to %.2f."), vol);
4589  proj->TP_DisplayStatusMessage(msg);
4590  changetype = 2;
4591  wxPrintf("\tnew vol:%f\n", vol);
4592  float check = Px_GetInputVolume(mPortMixer);
4593  wxPrintf("\tverified %f\n", check);
4594  }
4595  }
4596 
4597  mAILAAnalysisCounter++;
4598  //const PaStreamInfo* info = Pa_GetStreamInfo(mPortStreamV19);
4599  //double latency = 0.0;
4600  //if (info)
4601  // latency = info->inputLatency;
4602  //mAILAAnalysisEndTime = mTime+latency;
4603  mAILAAnalysisEndTime = Pa_GetStreamTime(mPortStreamV19) - mAILAAbsolutStartTime;
4604  mAILAMax = 0;
4605  wxPrintf("\tA decision was made @ %f\n", mAILAAnalysisEndTime);
4606  mAILAClipped = false;
4607  mAILALastStartTime = mTime;
4608 
4609  if (changetype == 0)
4610  mAILAChangeFactor *= 0.8; //time factor
4611  else if (mAILALastChangeType == changetype)
4612  mAILAChangeFactor *= 1.1; //concordance factor
4613  else
4614  mAILAChangeFactor *= 0.7; //discordance factor
4615  mAILALastChangeType = changetype;
4616  putchar('\n');
4617  }
4618 
4619  if (mAILAActive && mAILATotalAnalysis != 0 && mAILAAnalysisCounter >= mAILATotalAnalysis) {
4620  mAILAActive = false;
4621  if (mAILAMax > mAILAGoalPoint + mAILAGoalDelta)
4622  proj->TP_DisplayStatusMessage(_("Automated Recording Level Adjustment stopped. The total number of analyses has been exceeded without finding an acceptable volume. Still too high."));
4623  else if (mAILAMax < mAILAGoalPoint - mAILAGoalDelta)
4624  proj->TP_DisplayStatusMessage(_("Automated Recording Level Adjustment stopped. The total number of analyses has been exceeded without finding an acceptable volume. Still too low."));
4625  else {
4626  wxString msg;
4627  msg.Printf(_("Automated Recording Level Adjustment stopped. %.2f seems an acceptable volume."), Px_GetInputVolume(mPortMixer));
4628  proj->TP_DisplayStatusMessage(msg);
4629  }
4630  }
4631  }
4632 }
4633 #endif
4634 
4636 //
4637 // PortAudio callback thread context
4638 //
4640 
4641 #define MAX(a,b) ((a) > (b) ? (a) : (b))
4642 
4643 static void DoSoftwarePlaythrough(const void *inputBuffer,
4644  sampleFormat inputFormat,
4645  unsigned inputChannels,
4646  float *outputBuffer,
4647  int len)
4648 {
4649  for (unsigned int i=0; i < inputChannels; i++) {
4650  samplePtr inputPtr = ((samplePtr)inputBuffer) + (i * SAMPLE_SIZE(inputFormat));
4651  samplePtr outputPtr = ((samplePtr)outputBuffer) + (i * SAMPLE_SIZE(floatSample));
4652 
4653  CopySamples(inputPtr, inputFormat,
4654  (samplePtr)outputPtr, floatSample,
4655  len, true, inputChannels, 2);
4656  }
4657 
4658  // One mono input channel goes to both output channels...
4659  if (inputChannels == 1)
4660  for (int i=0; i < len; i++)
4661  outputBuffer[2*i + 1] = outputBuffer[2*i];
4662 }
4663 
4664 int audacityAudioCallback(const void *inputBuffer, void *outputBuffer,
4665  unsigned long framesPerBuffer,
4666 // If there were more of these conditionally used arguments, it
4667 // could make sense to make a NEW macro that looks like this:
4668 // USEDIF( EXPERIMENTAL_MIDI_OUT, timeInfo )
4669 #ifdef EXPERIMENTAL_MIDI_OUT
4670  const PaStreamCallbackTimeInfo *timeInfo,
4671 #else
4672  const PaStreamCallbackTimeInfo * WXUNUSED(timeInfo),
4673 #endif
4674  const PaStreamCallbackFlags statusFlags, void * WXUNUSED(userData) )
4675 {
4676  auto numPlaybackChannels = gAudioIO->mNumPlaybackChannels;
4677  auto numPlaybackTracks = gAudioIO->mPlaybackTracks.size();
4678  auto numCaptureChannels = gAudioIO->mNumCaptureChannels;
4679  int callbackReturn = paContinue;
4680  void *tempBuffer = alloca(framesPerBuffer*sizeof(float)*
4681  MAX(numCaptureChannels,numPlaybackChannels));
4682  float *tempFloats = (float*)tempBuffer;
4683 
4684  // output meter may need samples untouched by volume emulation
4685  float *outputMeterFloats;
4686  outputMeterFloats =
4687  (outputBuffer && gAudioIO->mEmulateMixerOutputVol &&
4688  gAudioIO->mMixerOutputVol != 1.0) ?
4689  (float *)alloca(framesPerBuffer*numPlaybackChannels * sizeof(float)) :
4690  (float *)outputBuffer;
4691 
4692 #ifdef EXPERIMENTAL_MIDI_OUT
4693  if (gAudioIO->mCallbackCount++ == 0) {
4694  // This is effectively mSystemMinusAudioTime when the buffer is empty:
4695  gAudioIO->mStartTime = SystemTime(gAudioIO->mUsingAlsa) - gAudioIO->mT0;
4696  // later, mStartTime - mSystemMinusAudioTime will tell us latency
4697  }
4698 
4699  /* GSW: Save timeInfo in case MidiPlayback needs it */
4700  gAudioIO->mAudioCallbackClockTime = PaUtil_GetTime();
4701 
4702  /* for Linux, estimate a smooth audio time as a slowly-changing
4703  offset from system time */
4704  // rnow is system time as a double to simplify math
4705  double rnow = SystemTime(gAudioIO->mUsingAlsa);
4706  // anow is next-sample-to-be-computed audio time as a double
4707  double anow = gAudioIO->AudioTime();
4708 
4709  if (gAudioIO->mUsingAlsa) {
4710  // timeInfo's fields are not all reliable.
4711 
4712  // enow is audio time estimated from our clock synchronization protocol,
4713  // which produces mSystemMinusAudioTime. But we want the estimate
4714  // to drift low, so we steadily increase mSystemMinusAudioTime to
4715  // simulate a fast system clock or a slow audio clock. If anow > enow,
4716  // we'll update mSystemMinusAudioTime to keep in sync. (You might think
4717  // we could just use anow as the "truth", but it has a lot of jitter,
4718  // so we are using enow to smooth out this jitter, in fact to < 1ms.)
4719  // Add worst-case clock drift using previous framesPerBuffer:
4720  const auto increase =
4721  gAudioIO->mAudioFramesPerBuffer * 0.0002 / gAudioIO->mRate;
4722  gAudioIO->mSystemMinusAudioTime += increase;
4723  gAudioIO->mSystemMinusAudioTimePlusLatency += increase;
4724  double enow = rnow - gAudioIO->mSystemMinusAudioTime;
4725 
4726 
4727  // now, use anow instead if it is ahead of enow
4728  if (anow > enow) {
4729  gAudioIO->mSystemMinusAudioTime = rnow - anow;
4730  // Update our mAudioOutLatency estimate during the first 20 callbacks.
4731  // During this period, the buffer should fill. Once we have a good
4732  // estimate of mSystemMinusAudioTime (expected in fewer than 20 callbacks)
4733  // we want to stop the updating in case there is clock drift, which would
4734  // cause the mAudioOutLatency estimation to drift as well. The clock drift
4735  // in the first 20 callbacks should be negligible, however.
4736  if (gAudioIO->mCallbackCount < 20) {
4737  gAudioIO->mAudioOutLatency = gAudioIO->mStartTime -
4738  gAudioIO->mSystemMinusAudioTime;
4739  }
4740  gAudioIO->mSystemMinusAudioTimePlusLatency =
4741  gAudioIO->mSystemMinusAudioTime + gAudioIO->mAudioOutLatency;
4742  }
4743  }
4744  else {
4745  // If not using Alsa, rely on timeInfo to have meaningful values that are
4746  // more precise than the output latency value reported at stream start.
4747  gAudioIO->mSystemMinusAudioTime = rnow - anow;
4748  gAudioIO->mSystemMinusAudioTimePlusLatency =
4749  gAudioIO->mSystemMinusAudioTime +
4750  (timeInfo->outputBufferDacTime - timeInfo->currentTime);
4751  }
4752 
4753  gAudioIO->mAudioFramesPerBuffer = framesPerBuffer;
4754  if (gAudioIO->IsPaused()
4755  // PRL: Why was this added? Was it only because of the mysterious
4756  // initial leading zeroes, now solved by setting mStreamToken early?
4757  || gAudioIO->mStreamToken <= 0
4758  )
4759  gAudioIO->mNumPauseFrames += framesPerBuffer;
4760 
4761  // PRL: Note that when there is a separate MIDI thread, it is effectively
4762  // blocked until the first visit to this line during a playback, and will
4763  // not read gAudioIO->mSystemMinusAudioTimePlusLatency sooner:
4764  gAudioIO->mNumFrames += framesPerBuffer;
4765 
4766 #ifndef USE_MIDI_THREAD
4767  if (gAudioIO->mMidiStream)
4768  gAudioIO->FillMidiBuffers();
4769 #endif
4770 
4771 #endif
4772 
4773  unsigned int i;
4774 
4775  /* Send data to recording VU meter if applicable */
4776 
4777  if (gAudioIO->mInputMeter &&
4778  !gAudioIO->mInputMeter->IsMeterDisabled() &&
4779  inputBuffer) {
4780  // get here if meters are actually live , and being updated
4781  /* It's critical that we don't update the meters while StopStream is
4782  * trying to stop PortAudio, otherwise it can lead to a freeze. We use
4783  * two variables to synchronize:
4784  * mUpdatingMeters tells StopStream when the callback is about to enter
4785  * the code where it might update the meters, and
4786  * mUpdateMeters is how the rest of the code tells the callback when it
4787  * is allowed to actually do the updating.
4788  * Note that mUpdatingMeters must be set first to avoid a race condition.
4789  */
4790  gAudioIO->mUpdatingMeters = true;
4791  if (gAudioIO->mUpdateMeters) {
4793  gAudioIO->mInputMeter->UpdateDisplay(numCaptureChannels,
4794  framesPerBuffer,
4795  (float *)inputBuffer);
4796  else {
4798  (samplePtr)tempFloats, floatSample,
4799  framesPerBuffer * numCaptureChannels);
4800  gAudioIO->mInputMeter->UpdateDisplay(numCaptureChannels,
4801  framesPerBuffer,
4802  tempFloats);
4803  }
4804  }
4805  gAudioIO->mUpdatingMeters = false;
4806  } // end recording VU meter update
4807 
4808  // Stop recording if 'silence' is detected
4809  //
4810  // LL: We'd gotten a little "dangerous" with the control toolbar calls
4811  // here because we are not running in the main GUI thread. Eventually
4812  // the toolbar attempts to update the active project's status bar.
4813  // But, since we're not in the main thread, we can get all manner of
4814  // really weird failures. Or none at all which is even worse, since
4815  // we don't know a problem exists.
4816  //
4817  // By using CallAfter(), we can schedule the call to the toolbar
4818  // to run in the main GUI thread after the next event loop iteration.
4819  if(gAudioIO->mPauseRec && inputBuffer && gAudioIO->mInputMeter) {
4820  if(gAudioIO->mInputMeter->GetMaxPeak() < gAudioIO->mSilenceLevel ) {
4821  if(!gAudioIO->IsPaused()) {
4823  ControlToolBar *bar = p->GetControlToolBar();
4824  bar->CallAfter(&ControlToolBar::Pause);
4825  }
4826  }
4827  else {
4828  if(gAudioIO->IsPaused()) {
4830  ControlToolBar *bar = p->GetControlToolBar();
4831  bar->CallAfter(&ControlToolBar::Pause);
4832  }
4833  }
4834  }
4835  if( gAudioIO->mPaused )
4836  {
4837  if (outputBuffer && numPlaybackChannels > 0)
4838  {
4839  ClearSamples((samplePtr)outputBuffer, floatSample,
4840  0, framesPerBuffer * numPlaybackChannels);
4841 
4842  if (inputBuffer && gAudioIO->mSoftwarePlaythrough) {
4844  numCaptureChannels,
4845  (float *)outputBuffer, (int)framesPerBuffer);
4846  }
4847  }
4848 
4849  return paContinue;
4850  }
4851 
4852  if (gAudioIO->mStreamToken > 0)
4853  {
4854  //
4855  // Mix and copy to PortAudio's output buffer
4856  //
4857 
4858  if( outputBuffer && (numPlaybackChannels > 0) )
4859  {
4860  bool cut = false;
4861  bool linkFlag = false;
4862 
4863  float *outputFloats = (float *)outputBuffer;
4864  for( i = 0; i < framesPerBuffer*numPlaybackChannels; i++)
4865  outputFloats[i] = 0.0;
4866 
4867  if (inputBuffer && gAudioIO->mSoftwarePlaythrough) {
4869  numCaptureChannels,
4870  (float *)outputBuffer, (int)framesPerBuffer);
4871  }
4872 
4873  // Copy the results to outputMeterFloats if necessary
4874  if (outputMeterFloats != outputFloats) {
4875  for (i = 0; i < framesPerBuffer*numPlaybackChannels; ++i) {
4876  outputMeterFloats[i] = outputFloats[i];
4877  }
4878  }
4879 
4880 #ifdef EXPERIMENTAL_SCRUBBING_SUPPORT
4881  // While scrubbing, ignore seek requests
4883  gAudioIO->mSeek = 0.0;
4884  else
4885 #endif
4886  if (gAudioIO->mSeek)
4887  {
4888  int token = gAudioIO->mStreamToken;
4889  wxMutexLocker locker(gAudioIO->mSuspendAudioThread);
4890  if (token != gAudioIO->mStreamToken)
4891  // This stream got destroyed while we waited for it
4892  return paAbort;
4893 
4894  // Pause audio thread and wait for it to finish
4897  {
4898  wxMilliSleep( 50 );
4899  }
4900 
4901  // Calculate the NEW time position
4904  gAudioIO->mSeek = 0.0;
4905 
4906  // Reset mixer positions and flush buffers for all tracks
4907  if(gAudioIO->mTimeTrack)
4908  // Following gives negative when mT0 > mTime
4911  (gAudioIO->mT0, gAudioIO->mTime);
4912  else
4914  gAudioIO->mWarpedTime = std::abs(gAudioIO->mWarpedTime);
4915 
4916  // Reset mixer positions and flush buffers for all tracks
4917  for (i = 0; i < numPlaybackTracks; i++)
4918  {
4919  gAudioIO->mPlaybackMixers[i]->Reposition(gAudioIO->mTime);
4920  const auto toDiscard =
4921  gAudioIO->mPlaybackBuffers[i]->AvailForGet();
4922  const auto discarded =
4923  gAudioIO->mPlaybackBuffers[i]->Discard( toDiscard );
4924  // wxASSERT( discarded == toDiscard );
4925  // but we can't assert in this thread
4926  wxUnusedVar(discarded);
4927  }
4928 
4929  // Reload the ring buffers
4932  {
4933  wxMilliSleep( 50 );
4934  }
4935 
4936  // Reenable the audio thread
4938 
4939  return paContinue;
4940  }
4941 
4942  unsigned numSolo = 0;
4943  for(unsigned t = 0; t < numPlaybackTracks; t++ )
4944  if( gAudioIO->mPlaybackTracks[t]->GetSolo() )
4945  numSolo++;
4946 #ifdef EXPERIMENTAL_MIDI_OUT
4947  auto numMidiPlaybackTracks = gAudioIO->mMidiPlaybackTracks.size();
4948  for( unsigned t = 0; t < numMidiPlaybackTracks; t++ )
4949  if( gAudioIO->mMidiPlaybackTracks[t]->GetSolo() )
4950  numSolo++;
4951 #endif
4952 
4953  const WaveTrack **chans = (const WaveTrack **) alloca(numPlaybackChannels * sizeof(WaveTrack *));
4954  float **tempBufs = (float **) alloca(numPlaybackChannels * sizeof(float *));
4955  for (unsigned int c = 0; c < numPlaybackChannels; c++)
4956  {
4957  tempBufs[c] = (float *) alloca(framesPerBuffer * sizeof(float));
4958  }
4959 
4961  em.RealtimeProcessStart();
4962 
4963  bool selected = false;
4964  int group = 0;
4965  int chanCnt = 0;
4966  decltype(framesPerBuffer) maxLen = 0;
4967  for (unsigned t = 0; t < numPlaybackTracks; t++)
4968  {
4969  const WaveTrack *vt = gAudioIO->mPlaybackTracks[t].get();
4970 
4971  chans[chanCnt] = vt;
4972 
4973  if (linkFlag)
4974  linkFlag = false;
4975  else {
4976  cut = false;
4977 
4978  // Cut if somebody else is soloing
4979  if (numSolo>0 && !vt->GetSolo())
4980  cut = true;
4981 
4982  // Cut if we're muted (unless we're soloing)
4983  if (vt->GetMute() && !vt->GetSolo())
4984  cut = true;
4985 
4986  linkFlag = vt->GetLinked();
4987  selected = vt->GetSelected();
4988 
4989  // If we have a mono track, clear the right channel
4990  if (!linkFlag)
4991  {
4992  memset(tempBufs[1], 0, framesPerBuffer * sizeof(float));
4993  }
4994  }
4995 
4996 #define ORIGINAL_DO_NOT_PLAY_ALL_MUTED_TRACKS_TO_END
4997 #ifdef ORIGINAL_DO_NOT_PLAY_ALL_MUTED_TRACKS_TO_END
4998  decltype(framesPerBuffer) len = 0;
4999  // this is original code prior to r10680 -RBD
5000  if (cut)
5001  {
5002  len = gAudioIO->mPlaybackBuffers[t]->Discard(framesPerBuffer);
5003  // keep going here.
5004  // we may still need to issue a paComplete.
5005  }
5006  else
5007  {
5008  len = gAudioIO->mPlaybackBuffers[t]->Get((samplePtr)tempBufs[chanCnt],
5009  floatSample,
5010  framesPerBuffer);
5011  if (len < framesPerBuffer)
5012  // Pad with zeroes to the end, in case of a short channel
5013  memset((void*)&tempBufs[chanCnt][len], 0,
5014  (framesPerBuffer - len) * sizeof(float));
5015 
5016  chanCnt++;
5017  }
5018 
5019  // PRL: Bug1104:
5020  // There can be a difference of len in different loop passes if one channel
5021  // of a stereo track ends before the other! Take a max!
5022  maxLen = std::max(maxLen, len);
5023 
5024 
5025  if (linkFlag)
5026  {
5027  continue;
5028  }
5029 #else
5030  // This code was reorganized so that if all audio tracks
5031  // are muted, we still return paComplete when the end of
5032  // a selection is reached.
5033  // Vaughan, 2011-10-20: Further comments from Roger, by off-list email:
5034  // ...something to do with what it means to mute all audio tracks. E.g. if you
5035  // mute all and play, does the playback terminate immediately or play
5036  // silence? If it terminates immediately, does that terminate any MIDI
5037  // playback that might also be going on? ...Maybe muted audio tracks + MIDI,
5038  // the playback would NEVER terminate. ...I think the #else part is probably preferable...
5039  size_t len;
5040  if (cut)
5041  {
5042  len =
5043  gAudioIO->mPlaybackBuffers[t]->Discard(framesPerBuffer);
5044  } else
5045  {
5046  len =
5047  gAudioIO->mPlaybackBuffers[t]->Get((samplePtr)tempFloats,
5048  floatSample,
5049  framesPerBuffer);
5050  }
5051 #endif
5052 
5053  // Last channel seen now
5054  len = maxLen;
5055 
5056  if( !cut && selected )
5057  {
5058  len = em.RealtimeProcess(group, chanCnt, tempBufs, len);
5059  }
5060  group++;
5061 
5062  // If our buffer is empty and the time indicator is past
5063  // the end, then we've actually finished playing the entire
5064  // selection.
5065  // msmeyer: We never finish if we are playing looped
5066  // PRL: or scrubbing.
5067  if (len == 0 &&
5069  if ((gAudioIO->ReversedTime()
5070  ? gAudioIO->mTime <= gAudioIO->mT1
5071  : gAudioIO->mTime >= gAudioIO->mT1))
5072  // PRL: singalling MIDI output complete is necessary if
5073  // not USE_MIDI_THREAD, otherwise it's harmlessly redundant
5074 #ifdef EXPERIMENTAL_MIDI_OUT
5075  gAudioIO->mMidiOutputComplete = true,
5076 #endif
5077  callbackReturn = paComplete;
5078  }
5079 
5080  if (cut) // no samples to process, they've been discarded
5081  continue;
5082 
5083  for (int c = 0; c < chanCnt; c++)
5084  {
5085  vt = chans[c];
5086 
5087  if (vt->GetChannel() == Track::LeftChannel ||
5088  vt->GetChannel() == Track::MonoChannel)
5089  {
5090  float gain = vt->GetChannelGain(0);
5091 
5092  // Output volume emulation: possibly copy meter samples, then
5093  // apply volume, then copy to the output buffer
5094  if (outputMeterFloats != outputFloats)
5095  for (decltype(len) i = 0; i < len; ++i)
5096  outputMeterFloats[numPlaybackChannels*i] +=
5097  gain*tempFloats[i];
5098 
5100  gain *= gAudioIO->mMixerOutputVol;
5101 
5102  for(decltype(len) i = 0; i < len; i++)
5103  outputFloats[numPlaybackChannels*i] += gain*tempBufs[c][i];
5104  }
5105 
5106  if (vt->GetChannel() == Track::RightChannel ||
5107  vt->GetChannel() == Track::MonoChannel)
5108  {
5109  float gain = vt->GetChannelGain(1);
5110 
5111  // Output volume emulation (as above)
5112  if (outputMeterFloats != outputFloats)
5113  for (decltype(len) i = 0; i < len; ++i)
5114  outputMeterFloats[numPlaybackChannels*i+1] +=
5115  gain*tempFloats[i];
5116 
5118  gain *= gAudioIO->mMixerOutputVol;
5119 
5120  for(decltype(len) i = 0; i < len; i++)
5121  outputFloats[numPlaybackChannels*i+1] += gain*tempBufs[c][i];
5122  }
5123  }
5124 
5125  chanCnt = 0;
5126  }
5127  // Poke: If there are no playback tracks, then the earlier check
5128  // about the time indicator being passed the end won't happen;
5129  // do it here instead (but not if looping or scrubbing)
5130  if (numPlaybackTracks == 0 &&
5132  {
5133  if ((gAudioIO->ReversedTime()
5134  ? gAudioIO->mTime <= gAudioIO->mT1
5135  : gAudioIO->mTime >= gAudioIO->mT1)) {
5136 
5137  // PRL: singalling MIDI output complete is necessary if
5138  // not USE_MIDI_THREAD, otherwise it's harmlessly redundant
5139 #ifdef EXPERIMENTAL_MIDI_OUT
5140  gAudioIO->mMidiOutputComplete = true,
5141 #endif
5142  callbackReturn = paComplete;
5143  }
5144  }
5145 
5146 #ifdef EXPERIMENTAL_SCRUBBING_SUPPORT
5147  // Update the current time position, for scrubbing
5148  // "Consume" only as much as the ring buffers produced, which may
5149  // be less than framesPerBuffer (during "stutter")
5151  gAudioIO->mTime = gAudioIO->mScrubQueue->Consumer(maxLen);
5152 #endif
5153 
5154  em.RealtimeProcessEnd();
5155 
5156  gAudioIO->mLastPlaybackTimeMillis = ::wxGetLocalTimeMillis();
5157 
5158  //
5159  // Clip output to [-1.0,+1.0] range (msmeyer)
5160  //
5161  for( i = 0; i < framesPerBuffer*numPlaybackChannels; i++)
5162  {
5163  float f = outputFloats[i];
5164  if (f > 1.0)
5165  outputFloats[i] = 1.0;
5166  else if (f < -1.0)
5167  outputFloats[i] = -1.0;
5168  }
5169 
5170  // Same for meter output
5171  if (outputMeterFloats != outputFloats)
5172  {
5173  for (i = 0; i < framesPerBuffer*numPlaybackChannels; ++i)
5174  {
5175  float f = outputMeterFloats[i];
5176  if (f > 1.0)
5177  outputMeterFloats[i] = 1.0;
5178  else if (f < -1.0)
5179  outputMeterFloats[i] = -1.0;
5180  }
5181  }
5182  }
5183 
5184  //
5185  // Copy from PortAudio to our input buffers.
5186  //
5187 
5188  if( inputBuffer && (numCaptureChannels > 0) )
5189  {
5190  // If there are no playback tracks, and we are recording, then the
5191  // earlier checks for being passed the end won't happen, so do it here.
5192  if (gAudioIO->mTime >= gAudioIO->mT1) {
5193  callbackReturn = paComplete;
5194  }
5195 
5196  // The error likely from a too-busy CPU falling behind real-time data
5197  // is paInputOverflow
5198  bool inputError =
5199  (statusFlags & (paInputOverflow))
5200  && !(statusFlags & paPrimingOutput);
5201 
5202  // But it seems it's easy to get false positives, at least on Mac
5203  // So we have not decided to enable this extra detection yet in
5204  // production
5205 
5206  size_t len = framesPerBuffer;
5207  for(unsigned t = 0; t < numCaptureChannels; t++)
5208  len = std::min( len,
5209  gAudioIO->mCaptureBuffers[t]->AvailForPut());
5210 
5211  if (gAudioIO->mSimulateRecordingErrors && 100LL * rand() < RAND_MAX)
5212  // Make spurious errors for purposes of testing the error
5213  // reporting
5214  len = 0;
5215 
5216  // A different symptom is that len < framesPerBuffer because
5217  // the other thread, executing FillBuffers, isn't consuming fast
5218  // enough from mCaptureBuffers; maybe it's CPU-bound, or maybe the
5219  // storage device it writes is too slow
5220  if (gAudioIO->mDetectDropouts &&
5221  ((gAudioIO->mDetectUpstreamDropouts && inputError) ||
5222  len < framesPerBuffer) ) {
5223  // Assume that any good partial buffer should be written leftmost
5224  // and zeroes will be padded after; label the zeroes.
5225  auto start = gAudioIO->mTime + len / gAudioIO->mRate;
5226  auto duration = (framesPerBuffer - len) / gAudioIO->mRate;
5227  auto interval = std::make_pair( start, duration );
5228  gAudioIO->mLostCaptureIntervals.push_back( interval );
5229  }
5230 
5231  if (len < framesPerBuffer)
5232  {
5233  gAudioIO->mLostSamples += (framesPerBuffer - len);
5234  wxPrintf(wxT("lost %d samples\n"), (int)(framesPerBuffer - len));
5235  }
5236 
5237  if (len > 0) {
5238  for(unsigned t = 0; t < numCaptureChannels; t++) {
5239 
5240  // dmazzoni:
5241  // Un-interleave. Ugly special-case code required because the
5242  // capture channels could be in three different sample formats;
5243  // it'd be nice to be able to call CopySamples, but it can't
5244  // handle multiplying by the gain and then clipping. Bummer.
5245 
5246  switch(gAudioIO->mCaptureFormat) {
5247  case floatSample: {
5248  float *inputFloats = (float *)inputBuffer;
5249  for( i = 0; i < len; i++)
5250  tempFloats[i] =
5251  inputFloats[numCaptureChannels*i+t];
5252  } break;
5253  case int24Sample:
5254  // We should never get here. Audacity's int24Sample format
5255  // is different from PortAudio's sample format and so we
5256  // make PortAudio return float samples when recording in
5257  // 24-bit samples.
5258  wxASSERT(false);
5259  break;
5260  case int16Sample: {
5261  short *inputShorts = (short *)inputBuffer;
5262  short *tempShorts = (short *)tempBuffer;
5263  for( i = 0; i < len; i++) {
5264  float tmp = inputShorts[numCaptureChannels*i+t];
5265  if (tmp > 32767)
5266  tmp = 32767;
5267  if (tmp < -32768)
5268  tmp = -32768;
5269  tempShorts[i] = (short)(tmp);
5270  }
5271  } break;
5272  } // switch
5273 
5274  const auto put =
5275  gAudioIO->mCaptureBuffers[t]->Put(
5276  (samplePtr)tempBuffer, gAudioIO->mCaptureFormat, len);
5277  // wxASSERT(put == len);
5278  // but we can't assert in this thread
5279  wxUnusedVar(put);
5280  }
5281  }
5282  }
5283 
5284  // Update the current time position if not scrubbing
5285  // (Already did it above, for scrubbing)
5286 #ifdef EXPERIMENTAL_SCRUBBING_SUPPORT
5288 #endif
5289  {
5290  double delta = framesPerBuffer / gAudioIO->mRate;
5291  if (gAudioIO->ReversedTime())
5292  delta *= -1.0;
5293  if (gAudioIO->mTimeTrack)
5294  // MB: this is why SolveWarpedLength is needed :)
5295  gAudioIO->mTime =
5297  else
5298  gAudioIO->mTime += delta;
5299  }
5300 
5301  // Wrap to start if looping
5303  {
5304  while (gAudioIO->ReversedTime()
5305  ? gAudioIO->mTime <= gAudioIO->mT1
5306  : gAudioIO->mTime >= gAudioIO->mT1)
5307  {
5308  // LL: This is not exactly right, but I'm at my wits end trying to
5309  // figure it out. Feel free to fix it. :-)
5310  // MB: it's much easier than you think, mTime isn't warped at all!
5312  }
5313  }
5314 
5315  // Record the reported latency from PortAudio.
5316  // TODO: Don't recalculate this with every callback?
5317 
5318  // 01/21/2009: Disabled until a better solution presents itself.
5319  #if 0
5320  // As of 06/17/2006, portaudio v19 returns inputBufferAdcTime set to
5321  // zero. It is being worked on, but for now we just can't do much
5322  // but follow the leader.
5323  //
5324  // 08/27/2006: too inconsistent for now...just leave it a zero.
5325  //
5326  // 04/16/2008: Looks like si->inputLatency comes back with something useful though.
5327  // This rearranged logic uses si->inputLatency, but if PortAudio fixes inputBufferAdcTime,
5328  // this code won't have to be modified to use it.
5329  // Also avoids setting mLastRecordingOffset except when simultaneously playing and recording.
5330  //
5331  if (numCaptureChannels > 0 && numPlaybackChannels > 0) // simultaneously playing and recording
5332  {
5333  if (timeInfo->inputBufferAdcTime > 0)
5334  gAudioIO->mLastRecordingOffset = timeInfo->inputBufferAdcTime - timeInfo->outputBufferDacTime;
5335  else if (gAudioIO->mLastRecordingOffset == 0.0)
5336  {
5337  const PaStreamInfo* si = Pa_GetStreamInfo( gAudioIO->mPortStreamV19 );
5338  gAudioIO->mLastRecordingOffset = -si->inputLatency;
5339  }
5340  }
5341  #endif
5342  } // if mStreamToken > 0
5343  else {
5344  // No tracks to play, but we should clear the output, and
5345  // possibly do software playthrough...
5346 
5347  if( outputBuffer && (numPlaybackChannels > 0) ) {
5348  float *outputFloats = (float *)outputBuffer;
5349  for( i = 0; i < framesPerBuffer*numPlaybackChannels; i++)
5350  outputFloats[i] = 0.0;
5351 
5352  if (inputBuffer && gAudioIO->mSoftwarePlaythrough) {
5354  numCaptureChannels,
5355  (float *)outputBuffer, (int)framesPerBuffer);
5356  }
5357 
5358  // Copy the results to outputMeterFloats if necessary
5359  if (outputMeterFloats != outputFloats) {
5360  for (i = 0; i < framesPerBuffer*numPlaybackChannels; ++i) {
5361  outputMeterFloats[i] = outputFloats[i];
5362  }
5363  }
5364  }
5365 
5366  }
5367  /* Send data to playback VU meter if applicable */
5368  if (gAudioIO->mOutputMeter &&
5370  outputMeterFloats) {
5371  // Get here if playback meter is live
5372  /* It's critical that we don't update the meters while StopStream is
5373  * trying to stop PortAudio, otherwise it can lead to a freeze. We use
5374  * two variables to synchronize:
5375  * mUpdatingMeters tells StopStream when the callback is about to enter
5376  * the code where it might update the meters, and
5377  * mUpdateMeters is how the rest of the code tells the callback when it
5378  * is allowed to actually do the updating.
5379  * Note that mUpdatingMeters must be set first to avoid a race condition.
5380  */
5381  gAudioIO->mUpdatingMeters = true;
5382  if (gAudioIO->mUpdateMeters) {
5383  gAudioIO->mOutputMeter->UpdateDisplay(numPlaybackChannels,
5384  framesPerBuffer,
5385  outputMeterFloats);
5386 
5387  //v Vaughan, 2011-02-25: Moved this update back to TrackPanel::OnTimer()
5388  // as it helps with playback issues reported by Bill and noted on Bug 258.
5389  // The problem there occurs if Software Playthrough is on.
5390  // Could conditionally do the update here if Software Playthrough is off,
5391  // and in TrackPanel::OnTimer() if Software Playthrough is on, but not now.
5392  // PRL 12 Jul 2015: and what was in TrackPanel::OnTimer is now handled by means of event
5393  // type EVT_TRACK_PANEL_TIMER
5394  //AudacityProject* pProj = GetActiveProject();
5395  //MixerBoard* pMixerBoard = pProj->GetMixerBoard();
5396  //if (pMixerBoard)
5397  // pMixerBoard->UpdateMeters(gAudioIO->GetStreamTime(),
5398  // (pProj->mLastPlayMode == loopedPlay));
5399  }
5400  gAudioIO->mUpdatingMeters = false;
5401  } // end playback VU meter update
5402 
5403  return callbackReturn;
5404 }
virtual void OnAudioIOStartRecording()=0
size_t GetCommonlyAvailCapture()
Get the number of audio samples ready in all of the recording buffers.
Definition: AudioIO.cpp:3333
double LimitStreamTime(double absoluteTime) const
Clamps the given time to be between mT0 and mT1.
Definition: AudioIO.cpp:2947
void StartTag(const wxString &name) override
bool GetSolo() const
Definition: Track.h:383
AudioIO uses the PortAudio library to play and record sound.
Definition: AudioIO.h:147
A ToolBar that has the main Transport buttons.
AudacityPrefs * gPrefs
Definition: Prefs.cpp:73
wxArrayString GetInputSourceNames()
Get the list of inputs to the current mixer device.
Definition: AudioIO.cpp:1398
void StopStream()
Stop recording, playback or input monitoring.
Definition: AudioIO.cpp:2535
GrowableSampleBuffer & Resize(size_t count, sampleFormat format)
Definition: SampleFormat.h:101
double ComputeWarpedLength(double t0, double t1) const
Compute the duration (in seconds at playback) of the specified region of the track.
Definition: TimeTrack.cpp:160
bool OutputMixerEmulated()
Find out if the output level control is being emulated via software attenuation.
Definition: AudioIO.cpp:1393
size_t RealtimeProcess(int group, unsigned chans, float **buffers, size_t numSamples)
void Transformer(sampleCount &startSample, sampleCount &endSample, sampleCount &duration, Maybe< wxMutexLocker > &cleanup)
Definition: AudioIO.cpp:664
sampleCount maxSample
Definition: Scrubbing.h:44
double mMinCaptureSecsToCopy
Definition: AudioIO.h:673
std::unique_ptr< AudioIO > ugAudioIO
Definition: AudioIO.cpp:481
double GetTime(double rate) const
Definition: AudioIO.cpp:918
static std::vector< long > mCachedSampleRates
Definition: AudioIO.h:751
Duration(ScrubQueue &queue_)
Definition: AudioIO.cpp:944
root of a hierarchy of classes that are thrown and caught by Audacity.
TimeTrack * timeTrack
Definition: AudioIO.h:127
void WriteAttr(const wxString &name, const wxString &value) override
#define ENV_DB_KEY
Definition: GUISettings.h:15
double GetStreamTime()
During playback, the (unwarped) track time most recently played.
Definition: AudioIO.cpp:2988
bool IsEmpty() const
static double mCachedBestRateIn
Definition: AudioIO.h:752
static int mNextStreamToken
Definition: AudioIO.h:648
bool GetSelected() const
Definition: Track.h:275
bool IsStreamActive()
Returns true if the audio i/o is running at all, but not during cleanup.
Definition: AudioIO.cpp:2918
void SetMissingAliasedFileWarningShouldShow(bool b)
Changes the behavior of missing aliased blockfiles warnings.
enum AudioIO::@3 mPlayMode
void reinit(Integral count, bool initialize=false)
Definition: MemoryX.h:117
bool mDetectDropouts
Definition: AudioIO.h:804
sampleCount mScrubDuration
Definition: AudioIO.h:792
static std::vector< long > GetSupportedSampleRates(int playDevice=-1, int recDevice=-1, double rate=0.0)
Get a list of sample rates the current input/output device combination supports.
Definition: AudioIO.cpp:3125
void RealtimeAddProcessor(int group, unsigned chans, float rate)
wxString WarningDialogKey(const wxString &internalDialogName)
Definition: Warning.cpp:115
void CopySamples(samplePtr src, sampleFormat srcFormat, samplePtr dst, sampleFormat dstFormat, unsigned int len, bool highQuality, unsigned int srcStride, unsigned int dstStride)
bool IsAvailable(AudacityProject *projecT)
Function to automatically set an acceptable volume.
Definition: AudioIO.cpp:2489
bool mDetectUpstreamDropouts
Definition: AudioIO.h:816
volatile bool mUpdatingMeters
Definition: AudioIO.h:703
float mMixerOutputVol
Definition: AudioIO.h:719
#define USE_MIDI_THREAD
Definition: AudioIO.h:109
void SetMeters()
Set the current VU meters - this should be done once after each call to StartStream currently...
Definition: AudioIO.cpp:2520
double LastTimeInQueue() const
Definition: AudioIO.cpp:582
wxLongLong mLastScrubTimeMillis
Definition: AudioIO.cpp:967
#define SAMPLE_SIZE(SampleFormat)
Definition: Types.h:198
double Consumer(unsigned long frames)
Definition: AudioIO.cpp:748
double mTime
Current time position during playback, in seconds. Between mT0 and mT1.
Definition: AudioIO.h:657
sampleCount mGoal
Definition: AudioIO.cpp:929
bool mInputMixerWorks
Can we control the hardware input level?
Definition: AudioIO.h:718
bool mSoftwarePlaythrough
Definition: AudioIO.h:677
unsigned mTrailingIdx
Definition: AudioIO.cpp:963
bool GetLinked() const
Definition: Track.h:278
sampleCount mDuration
Definition: AudioIO.cpp:933
double GetLastTimeInScrubQueue() const
return the ending time of the last enqueued scrub interval.
Definition: AudioIO.cpp:2900
bool IsAudioTokenActive(int token)
Returns true if the stream is active, or even if audio I/O is busy cleaning up its data or writing to...
Definition: AudioIO.cpp:2937
double as_double() const
Definition: Types.h:88
~AudioIO()
Definition: AudioIO.cpp:1283
double NormalizeStreamTime(double absoluteTime) const
Normalizes the given time, clamping it and handling gaps from cut preview.
Definition: AudioIO.cpp:2956
const TimeTrack * mTimeTrack
Definition: AudioIO.h:742
int AudacityMessageBox(const wxString &message, const wxString &caption=AudacityMessageBoxCaptionStr(), long style=wxOK|wxCENTRE, wxWindow *parent=NULL, int x=wxDefaultCoord, int y=wxDefaultCoord)
Definition: ErrorDialog.h:92
Definition: MemoryX.h:204
void Clear(double t0, double t1) override
Definition: WaveTrack.cpp:678
void StartStreamCleanup(bool bOnlyBuffers=false)
Clean up after StartStream if it fails.
Definition: AudioIO.cpp:2362
void FillBuffers()
Definition: AudioIO.cpp:3817
double GetEndTime() const override
Get the time at which the last clip in the track ends, plus recorded stuff.
Definition: WaveTrack.cpp:1873
MeterPanel * mOutputMeter
Definition: AudioIO.h:701
float GetChannelGain(int channel) const
Definition: WaveTrack.cpp:440
ArrayOf< std::unique_ptr< RingBuffer > > mPlaybackBuffers
Definition: AudioIO.h:643
virtual void OnAudioIOStopRecording()=0
bool IsBusy()
Returns true if audio i/o is busy starting, stopping, playing, or recording.
Definition: AudioIO.cpp:2910
wxString DeviceName(const PaDeviceInfo *info)
Definition: AudioIO.cpp:1154
ScrubbingOptions * pScrubbingOptions
Definition: AudioIO.h:139
MeterPanel is a panel that paints the meter used for monitoring or playback.
Definition: Meter.h:97
static int GetOptimalSupportedSampleRate()
Get a supported sample rate which can be used a an optimal default.
Definition: AudioIO.cpp:3169
Entry mEntries[Size]
Definition: AudioIO.cpp:962
const double mRate
Definition: AudioIO.cpp:966
static int getPlayDevIndex(const wxString &devName=wxEmptyString)
get the index of the device selected in the preferences.
Definition: AudioIO.cpp:3356
void StartMonitoring(double sampleRate)
Start up Portaudio for capture and recording as needed for input monitoring and software playthrough ...
Definition: AudioIO.cpp:1822
float mSilenceLevel
Definition: AudioIO.h:680
ArrayOf< std::unique_ptr< Resample > > mResample
Definition: AudioIO.h:640
Wrap wxMessageDialog so that caption IS translatable.
Definition: ErrorDialog.h:129
void WriteSubTree(const AutoSaveFile &value)
MixerBoard * GetMixerBoard()
Definition: Project.h:516
bool InputMixerWorks()
Find out if the input hardware level control is available.
Definition: AudioIO.cpp:1388
sampleFormat mCaptureFormat
Definition: AudioIO.h:683
GrowableSampleBuffer mSilentBuf
Definition: AudioIO.h:731
wxString HostName(const PaDeviceInfo *info)
Definition: AudioIO.cpp:1161
ArrayOf< std::unique_ptr< Mixer > > mPlaybackMixers
Definition: AudioIO.h:646
void DeinitAudioIO()
Definition: AudioIO.cpp:1149
bool Init(Entry *previous, sampleCount s0, sampleCount s1, sampleCount &duration, const ScrubbingOptions &options)
Definition: AudioIO.cpp:795
std::unique_ptr< ScrubQueue > mScrubQueue
Definition: AudioIO.h:788
#define safenew
Definition: Audacity.h:230
#define BAD_STREAM_TIME
Definition: AudioIO.h:79
double mWarpedTime
Definition: AudioIO.h:662
size_t limitSampleBufferSize(size_t bufferSize, sampleCount limit)
Definition: Types.h:178
void InsertSilence(double t, double len) override
Definition: WaveTrack.cpp:1385
static int mCachedPlaybackIndex
Definition: AudioIO.h:747
wxMutex mSuspendAudioThread
Definition: AudioIO.h:785
#define DEFAULT_LATENCY_CORRECTION
Definition: AudioIO.h:85
wxAtomicInt mRecordingException
Definition: AudioIO.h:797
#define ENV_DB_RANGE
Definition: GUISettings.h:16
AudacityProject provides the main window, with tools and tracks contained within it.
Definition: Project.h:176
void SetPlaybackMeter(AudacityProject *project, MeterPanel *meter)
Definition: AudioIO.cpp:2508
static std::vector< long > mCachedPlaybackRates
Definition: AudioIO.h:748
double GetStartTime() const override
Get the time at which the first clip in the track starts.
Definition: WaveTrack.cpp:1853
bool mPaused
True if audio playback is paused.
Definition: AudioIO.h:675
void GetMixer(int *inputSource, float *inputVolume, float *playbackVolume)
Definition: AudioIO.cpp:1357
static double MaxAllowedScrubSpeed()
Definition: Scrubbing.h:64
void EndTag(const wxString &name) override
ArrayOf< std::unique_ptr< RingBuffer > > mCaptureBuffers
Definition: AudioIO.h:641
int format
Definition: ExportPCM.cpp:56
bool ReversedTime() const
True if the end time is before the start time.
Definition: AudioIO.h:516
volatile int mStreamToken
Definition: AudioIO.h:647
MeterPanel * GetCaptureMeter()
Definition: Project.cpp:5097
unsigned mMiddleIdx
Definition: AudioIO.cpp:964
WaveTrackArray mCaptureTracks
Definition: AudioIO.h:642
#define DEFAULT_SYNTH_LATENCY
Definition: AudioIO.h:82
bool mEmulateMixerOutputVol
Definition: AudioIO.h:710
bool Producer(double end, const ScrubbingOptions &options)
Definition: AudioIO.cpp:599
std::vector< std::shared_ptr< WaveTrack > > WaveTrackArray
Definition: AudioIO.h:65
PaStream * mPortStreamV19
Definition: AudioIO.h:676
struct holding stream options, including a pointer to the TimeTrack and AudioIOListener and whether t...
Definition: AudioIO.h:114
sampleCount mS0
Definition: AudioIO.cpp:927
static std::vector< long > mCachedCaptureRates
Definition: AudioIO.h:750
void ClearRecordingException()
Definition: AudioIO.h:800
std::vector< std::shared_ptr< const WaveTrack > > WaveTrackConstArray
Definition: AudioIO.h:66
bool IsMeterDisabled() const
Find out if the level meter is disabled or not.
Definition: Meter.cpp:1773
ScrubQueue(double t0, double t1, wxLongLong startClockMillis, double rate, long maxDebt, const ScrubbingOptions &options)
Definition: AudioIO.cpp:547
double mCaptureRingBufferSecs
Definition: AudioIO.h:671
bool IsPaused()
Find out if playback / recording is currently paused.
Definition: AudioIO.cpp:2885
void UpdateDisplay(unsigned numChannels, int numFrames, float *sampleData)
Update the meters with a block of audio data.
Definition: Meter.cpp:886
const wxLongLong clockTime
Definition: AudioIO.cpp:954
IteratorRange< Iterator > make_iterator_range(const Iterator &i1, const Iterator &i2)
Definition: MemoryX.h:677
const long mMaxDebt
Definition: AudioIO.cpp:972
Entry()
Definition: AudioIO.cpp:787
sampleFormat
Definition: Types.h:188
#define lrint(dbl)
Definition: float_cast.h:136
int audacityAudioCallback(const void *inputBuffer, void *outputBuffer, unsigned long framesPerBuffer, const PaStreamCallbackTimeInfo *timeInfo, PaStreamCallbackFlags statusFlags, void *userData)
char * samplePtr
Definition: Types.h:203
A Track that contains audio waveform data.
Definition: WaveTrack.h:60
double GetBestRate(bool capturing, bool playing, double sampleRate)
Return a valid sample rate that is supported by the current I/O device(s).
Definition: AudioIO.cpp:3189
WaveTrackArray GetWaveTrackArray(bool selectionOnly, bool includeMuted=true)
Definition: Track.cpp:1344
bool EnqueueScrub(double endTimeOrSpeed, const ScrubbingOptions &options)
enqueue a NEW scrub play interval, using the last end as the NEW start, to be played over the same du...
Definition: AudioIO.cpp:2892
void RealtimeInitialize(double rate)
void HandleDeviceChange()
update state after changing what audio devices are selected
Definition: AudioIO.cpp:1426
if(pTrack &&pTrack->GetDisplay()!=WaveTrack::Spectrum)
AudacityProject * mOwningProject
Definition: AudioIO.h:699
EffectManager is the class that handles effects and effect categories.
Definition: EffectManager.h:45
static PaSampleFormat AudacityToPortAudioSampleFormat(sampleFormat format)
Definition: AudioIO.cpp:1627
int min(int a, int b)
wxLongLong mLastPlaybackTimeMillis
Definition: AudioIO.h:689
AudioIOListener * mListener
Definition: AudioIO.h:733
volatile bool mAudioThreadShouldCallFillBuffersOnce
Definition: AudioIO.h:685
samplePtr ptr() const
Definition: SampleFormat.h:81
wxCondition mAvailable
Definition: AudioIO.cpp:975
unsigned int mNumPlaybackChannels
Definition: AudioIO.h:682
#define LAT1CTOWX(X)
Definition: Internat.h:180
R GuardedCall(const F1 &body, const F2 &handler=F2::Default(), const F3 &delayedHandler={})
double mSeek
Definition: AudioIO.h:669
std::vector< std::shared_ptr< NoteTrack > > NoteTrackArray
Definition: Track.h:53
unsigned int mNumCaptureChannels
Definition: AudioIO.h:681
static EffectManager & Get()
size_t GetCommonlyAvailPlayback()
Get the number of audio samples free in all of the playback buffers.
Definition: AudioIO.cpp:3324
wxLongLong mLastTransformerTimeMillis
Definition: AudioIO.cpp:969
void TP_DisplayStatusMessage(const wxString &msg) override
Definition: Project.cpp:5349
std::unique_ptr< AudioThread > mThread
Definition: AudioIO.h:634
wxWeakRef< MeterPanel > mInputMeter
Definition: AudioIO.h:700
void SetCaptureMeter(AudacityProject *project, MeterPanel *meter)
Definition: AudioIO.cpp:2494
unsigned long long mLostSamples
Definition: AudioIO.h:684
static void DoSoftwarePlaythrough(const void *inputBuffer, sampleFormat inputFormat, unsigned inputChannels, float *outputBuffer, int len)
Definition: AudioIO.cpp:4643
int StartStream(const WaveTrackConstArray &playbackTracks, const WaveTrackArray &captureTracks, double t0, double t1, const AudioIOStartStreamOptions &options)
Start recording or playing back audio.
Definition: AudioIO.cpp:1864
unsigned mLeadingIdx
Definition: AudioIO.cpp:965
sampleCount mS1
Definition: AudioIO.cpp:928
virtual void OnAudioIONewBlockFiles(const AutoSaveFile &blockFileLog)=0
double mRate
Audio playback rate in samples per second.
Definition: AudioIO.h:651
void Reset(double sampleRate, bool resetClipping)
This method is thread-safe! Feel free to call from a different thread (like from an audio I/O callbac...
Definition: Meter.cpp:826
double maxSpeed
Definition: Scrubbing.h:53
Monitors record play start/stop and new blockfiles. Has callbacks for these events.
bool mUpdateMeters
Definition: AudioIO.h:702
void SetMixer(int inputSource)
Definition: AudioIO.cpp:1325
_("Move Track &Down")+wxT("\t")+(GetActiveProject() -> GetCommandManager() ->GetKeyFromName(wxT("TrackMoveDown")).Raw()), OnMoveTrack) POPUP_MENU_ITEM(OnMoveTopID, _("Move Track to &Top")+wxT("\t")+(GetActiveProject() ->GetCommandManager() ->GetKeyFromName(wxT("TrackMoveTop")).Raw()), OnMoveTrack) POPUP_MENU_ITEM(OnMoveBottomID, _("Move Track to &Bottom")+wxT("\t")+(GetActiveProject() ->GetCommandManager() ->GetKeyFromName(wxT("TrackMoveBottom")).Raw()), OnMoveTrack)#define SET_TRACK_NAME_PLUGIN_SYMBOLclass SetTrackNameCommand:public AudacityCommand
AudioIO * gAudioIO
Definition: AudioIO.cpp:482
ControlToolBar * GetControlToolBar()
Definition: Project.cpp:4996
volatile double mLastRecordingOffset
Definition: AudioIO.h:696
void SetListener(AudioIOListener *listener)
Definition: AudioIO.cpp:4108
const wxChar * name
Definition: Distortion.cpp:94
sampleCount mCredit
Definition: AudioIO.cpp:970
bool IsMonitoring()
Returns true if we're monitoring input (but not recording or playing actual audio) ...
Definition: AudioIO.cpp:2942
double minSpeed
Definition: Scrubbing.h:52
static int mCachedCaptureIndex
Definition: AudioIO.h:749
static const int NumStandardRates
How many standard sample rates there are.
Definition: AudioIO.h:385
AUDACITY_DLL_API AudacityProject * GetActiveProject()
Definition: Project.cpp:308
void ClearSamples(samplePtr dst, sampleFormat format, size_t start, size_t len)
bool mUsingAlsa
Definition: AudioIO.h:744
double mWarpedLength
Definition: AudioIO.h:667
double mCutPreviewGapLen
Definition: AudioIO.h:729
static std::vector< long > GetSupportedCaptureRates(int devIndex=-1, double rate=0.0)
Get a list of sample rates the input (recording) device supports.
Definition: AudioIO.cpp:3059
sampleCount minSample
Definition: Scrubbing.h:45
void SetOffset(double o) override
Definition: WaveTrack.cpp:224
double mT0
Playback starts at offset of mT0, which is measured in seconds.
Definition: AudioIO.h:653
double mCutPreviewGapStart
Definition: AudioIO.h:728
MeterPanel * GetPlaybackMeter()
Definition: Project.cpp:5083
virtual void OnAudioIORate(int rate)=0
wxString GetDeviceInfo()
Get diagnostic information on all the available audio I/O devices.
Definition: AudioIO.cpp:3472
static double mCachedBestRateOut
Definition: AudioIO.h:753
double SolveWarpedLength(double t0, double length) const
Compute how much unwarped time must have elapsed if length seconds of warped time has elapsed...
Definition: TimeTrack.cpp:165
bool enqueueBySpeed
Definition: Scrubbing.h:47
bool GetMute() const
Definition: Track.h:382
static const int StandardRates[]
Array of common audio sample rates.
Definition: AudioIO.h:383
std::vector< std::pair< double, double > > mLostCaptureIntervals
Definition: AudioIO.h:803
AudioIOListener * listener
Definition: AudioIO.h:128
void InitAudioIO()
Definition: AudioIO.cpp:1116
sampleCount mDebt
Definition: AudioIO.cpp:971
static const int NumRatesToTry
How many sample rates to try.
Definition: AudioIO.h:513
volatile bool mAudioThreadFillBuffersLoopActive
Definition: AudioIO.h:687
AudacityApp & wxGetApp()
static sampleFormat SampleFormatChoice()
#define DEFAULT_LATENCY_DURATION
Definition: AudioIO.h:84
TrackList * GetTracks()
Definition: Project.h:192
sampleCount mPlayed
Definition: AudioIO.cpp:940
static const int RatesToTry[]
Array of audio sample rates to try to use.
Definition: AudioIO.h:511
void RealtimeFinalize()
double mFactor
Definition: AudioIO.h:649
size_t as_size_t() const
Definition: Types.h:92
PaError mLastPaError
Definition: AudioIO.h:697
const sampleCount duration
Definition: AudioIO.cpp:955
void ResetMeters(const bool bResetClipping)
size_t mPlaybackSamplesToCopy
Definition: AudioIO.h:672
void SetPaused(bool state)
Pause and un-pause playback and recording.
Definition: AudioIO.cpp:2868
static std::vector< long > GetSupportedPlaybackRates(int DevIndex=-1, double rate=0.0)
Get a list of sample rates the output (playback) device supports.
Definition: AudioIO.cpp:2997
void RealtimeSuspend()
#define MAX(a, b)
Definition: AudioIO.cpp:4641
bool StartPortAudioStream(double sampleRate, unsigned int numPlaybackChannels, unsigned int numCaptureChannels, sampleFormat captureFormat)
Opens the portaudio stream(s) used to do playback or recording (or both) through. ...
Definition: AudioIO.cpp:1640
Definition: AudioIO.cpp:785
static bool ValidateDeviceNames(const wxString &play, const wxString &rec)
Ensure selected device names are valid.
Definition: AudioIO.cpp:1168
void RealtimeProcessEnd()
double mT1
Playback ends at offset of mT1, which is measured in seconds. Note that mT1 may be less than mT0 duri...
Definition: AudioIO.h:655
ExitCode Entry() override
Definition: AudioIO.cpp:3271
void create(Args &&...args)
Definition: MemoryX.h:251
volatile bool mAudioThreadFillBuffersLoopRunning
Definition: AudioIO.h:686
virtual int GetChannel() const override
Definition: WaveTrack.cpp:236
bool mPauseRec
True if Sound Activated Recording is enabled.
Definition: AudioIO.h:679
void SetRecordingException()
Definition: AudioIO.h:798
bool mSilentScrub
Definition: AudioIO.h:791
static int getRecordDevIndex(const wxString &devName=wxEmptyString)
get the index of the supplied (named) recording device, or the device selected in the preferences if ...
Definition: AudioIO.cpp:3413
WaveTrackConstArray mPlaybackTracks
Definition: AudioIO.h:644
void InitSilent(const Entry &previous, sampleCount duration)
Definition: AudioIO.cpp:910
void Flush()
Flush must be called after last Append.
Definition: WaveTrack.cpp:1650
static double MinAllowedScrubSpeed()
Definition: Scrubbing.h:66
friend int audacityAudioCallback(const void *inputBuffer, void *outputBuffer, unsigned long framesPerBuffer, const PaStreamCallbackTimeInfo *timeInfo, PaStreamCallbackFlags statusFlags, void *userData)
void RealtimeProcessStart()
a class wrapping reading and writing of arbitrary data in text or binary format to a file...
Definition: AutoRecovery.h:76
bool mSimulateRecordingErrors
Definition: AudioIO.h:812
wxDEFINE_EVENT(EVT_AUDIOIO_PLAYBACK, wxCommandEvent)
A Track that is used for Midi notes. (Somewhat old code).
double mPlaybackRingBufferSecs
Definition: AudioIO.h:670
Defined different on Mac and other platforms (on Mac it does not use wxWidgets wxThread), this class sits in a thread loop reading and writing audio.
Definition: AudioIO.cpp:1094