Permalink
Browse files

Added command-line support for `--high-performance-mode`, which disab…

…les sleep when running with rtdm and reduces sleepTime when running withpolling. Closes #274.
  • Loading branch information...
giuliomoro committed Oct 6, 2017
1 parent 178f17c commit c0f0c723551b4cdc1fe3683500ff4f0d05cb81a0
Showing with 38 additions and 14 deletions.
  1. +1 −0 .gitignore
  2. +5 −3 core/PRU.cpp
  3. +19 −10 core/RTAudio.cpp
  4. +7 −0 core/RTAudioCommandLine.cpp
  5. +5 −0 include/Bela.h
  6. +1 −1 include/PRU.h
View
@@ -12,3 +12,4 @@
*.js.map
/.plugins/
/updates/
include/pru_rtaudio_bin.h
View
@@ -714,7 +714,7 @@ int PRU::start(char * const filename)
}
// Main loop to read and write data from/to PRU
void PRU::loop(void *userData, void(*render)(BelaContext*, void*))
void PRU::loop(void *userData, void(*render)(BelaContext*, void*), bool highPerformanceMode)
{
// these pointers will be constant throughout the lifetime of pruMemory
@@ -735,6 +735,8 @@ void PRU::loop(void *userData, void(*render)(BelaContext*, void*))
#else
time_ns_t sleepTime = PRU_SAMPLE_INTERVAL_NS * (context->audioInChannels) * context->audioFrames / 4;
#endif
if(highPerformanceMode) // sleep less, more CPU available for us
sleepTime /= 4;
//sleepTime = context->audioFrames / context->audioSampleRate / 4.f * 1000000000.f;
// Before starting, look at the last state of the analog and digital outputs which might
@@ -764,15 +766,15 @@ void PRU::loop(void *userData, void(*render)(BelaContext*, void*))
static uint32_t lastPRUBuffer = 0;
// Poll
while(pru_buffer_comm[PRU_CURRENT_BUFFER] == lastPRUBuffer && !gShouldStop) {
//printf("sleep %d\n", lastPRUBuffer);
task_sleep_ns(sleepTime);
}
lastPRUBuffer = pru_buffer_comm[PRU_CURRENT_BUFFER];
#endif
#ifdef BELA_USE_RTDM
// make sure we always sleep a tiny bit to prevent hanging the board
task_sleep_ns(sleepTime / 2);
if(!highPerformanceMode) // unless the user requested us not to.
task_sleep_ns(sleepTime / 2);
int ret = read(rtdm_fd, NULL, 0);
if(ret < 0)
{
View
@@ -57,7 +57,7 @@ RT_TASK gRTAudioThread;
#ifdef XENOMAI_SKIN_posix
pthread_t gRTAudioThread;
#endif
const char gRTAudioThreadName[] = "bela-audio";
static const char gRTAudioThreadName[] = "bela-audio";
PRU *gPRU = 0;
#ifdef CTAG_FACE_8CH
@@ -70,14 +70,14 @@ PRU *gPRU = 0;
I2c_Codec *gAudioCodec = 0;
#endif
// Flag which tells the audio task to stop
int volatile gShouldStop = false;
int volatile gShouldStop = false; // Flag which tells the audio task to stop
int gRTAudioVerbose = 0; // Verbosity level for debugging
// general settings
char gPRUFilename[MAX_PRU_FILENAME_LENGTH]; // Path to PRU binary file (internal code if empty)_
int gRTAudioVerbose = 0; // Verbosity level for debugging
int gAmplifierMutePin = -1;
int gAmplifierShouldBeginMuted = 0;
static char gPRUFilename[MAX_PRU_FILENAME_LENGTH]; // Path to PRU binary file (internal code if empty)_
static int gAmplifierMutePin = -1;
static int gAmplifierShouldBeginMuted = 0;
static bool gHighPerformanceMode = 0;
static unsigned int gAudioThreadStackSize;
unsigned int gAuxiliaryTaskStackSize;
@@ -158,6 +158,11 @@ int Bela_initAudio(BelaInitSettings *settings, void *userData)
strncpy(gPRUFilename, settings->pruFilename, MAX_PRU_FILENAME_LENGTH);
gUserData = userData;
gHighPerformanceMode = settings->highPerformanceMode;
if(gRTAudioVerbose && gHighPerformanceMode) {
cout << "Starting in high-performance mode\n";
}
// Initialise context data structure
memset(&gContext, 0, sizeof(BelaContext));
@@ -371,7 +376,7 @@ void audioLoop(void *)
rt_printf("_________________Audio Thread!\n");
// All systems go. Run the loop; it will end when gShouldStop is set to 1
gPRU->loop(gUserData, gBelaRender);
gPRU->loop(gUserData, gBelaRender, gHighPerformanceMode);
// Now clean up
// gPRU->waitForFinish();
gPRU->disable();
@@ -510,6 +515,10 @@ void Bela_stopAudio()
#ifdef XENOMAI_SKIN_posix
void* threadReturnValue;
int ret = __wrap_pthread_join(gRTAudioThread, &threadReturnValue);
if(ret)
{
fprintf(stderr, "Failed to join audio thread: (%d) %s\n", ret, strerror(ret));
}
#endif
Bela_stopAllAuxiliaryTasks();
@@ -528,12 +537,12 @@ void Bela_cleanupAudio()
// Clean up the auxiliary tasks
void Bela_deleteAllAuxiliaryTasks();
// Delete the audio task and its interrupt
// Delete the audio task
#ifdef XENOMAI_SKIN_native
rt_task_delete(&gRTAudioThread);
#endif
#ifdef XENOMAI_SKIN_posix
printf("Not sure if we should emulate rt_taks_delete\n");
pthread_cancel(gRTAudioThread);
#endif
if(gPRU != 0)
@@ -21,6 +21,7 @@
#define OPT_DISABLE_CAPE_BUTTON 1005
#define OPT_DETECT_UNDERRUNS 1006
#define OPT_UNIFORM_SAMPLE_RATE 1007
#define OPT_HIGH_PERFORMANCE_MODE 1008
enum {
@@ -55,6 +56,7 @@ struct option gDefaultLongOptions[] =
{"detect-underruns", 1, NULL, OPT_DETECT_UNDERRUNS},
{"disable-led", 0, NULL, OPT_DISABLE_LED},
{"disable-cape-button-monitoring", 0, NULL, OPT_DISABLE_CAPE_BUTTON},
{"high-performance-mode", 0, NULL, OPT_HIGH_PERFORMANCE_MODE},
{"uniform-sample-rate", 0, NULL, OPT_UNIFORM_SAMPLE_RATE},
{NULL, 0, NULL, 0}
};
@@ -91,6 +93,7 @@ void Bela_defaultSettings(BelaInitSettings *settings)
settings->detectUnderruns = 1;
settings->enableLED = 1;
settings->enableCapeButtonMonitoring = 1;
settings->highPerformanceMode = 0;
// These deliberately have no command-line flags by default,
// as it is unlikely the user would want to switch them
@@ -294,6 +297,9 @@ int Bela_getopt_long(int argc, char *argv[], const char *customShortOptions, con
case OPT_DISABLE_CAPE_BUTTON:
settings->enableCapeButtonMonitoring = 0;
break;
case OPT_HIGH_PERFORMANCE_MODE:
settings->highPerformanceMode = 1;
break;
case OPT_UNIFORM_SAMPLE_RATE:
settings->uniformSampleRate = 1;
printf("Uniform sample rate\n");
@@ -331,6 +337,7 @@ void Bela_usage()
std::cerr << " --detect-underruns val: Set whether to warn the user in case of underruns (options: 0 or 1, default: 1)\n";
std::cerr << " --disable-led Disable the blinking LED indicator\n";
std::cerr << " --disable-cape-button-monitoring Disable the monitoring of the Bela cape button (which otherwise stops the running program)\n";
std::cerr << " --high-performance-mode Gives more CPU to the Bela process. The system may become unresponsive and you will have to use the button on the Bela cape when you want to stop it.\n";
std::cerr << " --uniform-sample-rate Internally resample the analog channels so that they match the audio sample rate\n";
std::cerr << " --verbose [-v]: Enable verbose logging information\n";
}
View
@@ -365,6 +365,11 @@ typedef struct {
int enableLED;
/// Whether to monitor the Bela cape button on P9.27 / GPIO3[19]
int enableCapeButtonMonitoring;
/// Whether to use high-performance mode: gives more CPU to
/// the Bela task. The Linux part of the board and the IDE may
/// freeze while the program is running. Use the button on the
/// Bela cape to forcefully stop the running program
int highPerformanceMode;
// These items are application-dependent but should probably be
// determined by the programmer rather than the user
View
@@ -170,7 +170,7 @@ class PRU
int start(char * const filename);
// Loop: read and write data from the PRU and call the user-defined audio callback
void loop(void *userData, void(*render)(BelaContext*, void*));
void loop(void *userData, void(*render)(BelaContext*, void*), bool highPerformanceMode);
// Wait for an interrupt from the PRU indicate it is finished
void waitForFinish();

0 comments on commit c0f0c72

Please sign in to comment.