annotate core/RTAudioCommandLine.cpp @ 269:ac8eb07afcf5

Oxygen text added to each render.cpp file for the default projects. Text includes project explanation from Wiki, edited in places. Empty project added as a default project. Doxyfile updated. Each of the project locations added to INPUT configuration option. Consider just watching the whole project file so all new projects are automatically pulled through.
author Robert Jack <robert.h.jack@gmail.com>
date Tue, 17 May 2016 15:40:16 +0100
parents 1fd334f64f0a
children c55c6f6c233c
rev   line source
andrewm@5 1 /*
andrewm@5 2 * RTAudioCommandLine.cpp
andrewm@5 3 *
andrewm@5 4 * Created on: Nov 8, 2014
andrewm@5 5 * Author: parallels
andrewm@5 6 */
andrewm@5 7
andrewm@5 8 #include <iostream>
andrewm@5 9 #include <cstdlib>
andrewm@5 10 #include <cstring>
andrewm@5 11 #include <getopt.h>
andrewm@45 12 #include "../include/BeagleRT.h"
giuliomoro@24 13
giuliomoro@171 14 #define OPT_PRU_FILE 1000
giuliomoro@171 15 #define OPT_PGA_GAIN_LEFT 1001
giuliomoro@171 16 #define OPT_PGA_GAIN_RIGHT 1002
giuliomoro@171 17
andrewm@5 18
andrewm@47 19 enum {
andrewm@47 20 kAmplifierMutePin = 61 // P8-26 controls amplifier mute
andrewm@47 21 };
andrewm@47 22
andrewm@5 23 // Default command-line options for RTAudio
andrewm@5 24 struct option gDefaultLongOptions[] =
andrewm@5 25 {
andrewm@5 26 {"period", 1, NULL, 'p'},
andrewm@5 27 {"verbose", 0, NULL, 'v'},
andrewm@50 28 {"use-analog", 1, NULL, 'N'},
andrewm@50 29 {"use-digital", 1, NULL, 'G'},
giuliomoro@19 30 {"analog-channels", 1, NULL, 'C'},
andrewm@50 31 {"digital-channels", 1, NULL, 'B'},
andrewm@5 32 {"mute-speaker", 1, NULL, 'M'},
andrewm@5 33 {"dac-level", 1, NULL, 'D'},
andrewm@5 34 {"adc-level", 1, NULL, 'A'},
giuliomoro@171 35 {"pga-gain-left", 1, NULL, OPT_PGA_GAIN_LEFT},
giuliomoro@171 36 {"pga-gain-right", 1, NULL, OPT_PGA_GAIN_RIGHT},
andrewm@5 37 {"hp-level", 1, NULL, 'H'},
andrewm@50 38 {"receive-port", 1, NULL, 'R'},
andrewm@50 39 {"transmit-port", 1, NULL, 'T'},
andrewm@50 40 {"server-name", 1, NULL, 'S'},
andrewm@45 41 {"pru-file", 1, NULL, OPT_PRU_FILE},
andrewm@5 42 {NULL, 0, NULL, 0}
andrewm@5 43 };
giuliomoro@24 44
andrewm@50 45 const char gDefaultShortOptions[] = "p:vN:M:C:D:A:H:G:B:R:T:S:";
andrewm@5 46
andrewm@45 47 // This function sets the default settings for the BeagleRTInitSettings structure
andrewm@45 48 void BeagleRT_defaultSettings(BeagleRTInitSettings *settings)
andrewm@5 49 {
andrewm@5 50 // Set default values for settings
giuliomoro@178 51 settings->periodSize = 16;
andrewm@45 52 settings->useAnalog = 1;
andrewm@45 53 settings->useDigital = 1;
andrewm@45 54 settings->numAnalogChannels = 8;
andrewm@45 55 settings->numDigitalChannels = 16;
andrewm@45 56
andrewm@5 57 settings->beginMuted = 0;
andrewm@5 58 settings->dacLevel = DEFAULT_DAC_LEVEL;
andrewm@5 59 settings->adcLevel = DEFAULT_ADC_LEVEL;
giuliomoro@171 60 for(int n = 0; n < 2; n++)
giuliomoro@171 61 settings->pgaGain[n] = DEFAULT_PGA_GAIN;
andrewm@5 62 settings->headphoneLevel = DEFAULT_HP_LEVEL;
andrewm@45 63
andrewm@5 64 settings->verbose = 0;
andrewm@45 65 settings->pruFilename[0] = '\0';
andrewm@45 66
andrewm@45 67 // These two deliberately have no command-line flags by default.
andrewm@45 68 // A given program might prefer one mode or another, but it's unlikely
andrewm@45 69 // the user would want to switch at runtime
andrewm@45 70 settings->interleave = 1;
andrewm@45 71 settings->analogOutputsPersist = 1;
andrewm@45 72
andrewm@5 73 settings->codecI2CAddress = CODEC_I2C_ADDRESS;
andrewm@45 74 settings->receivePort = 9998;
andrewm@45 75 settings->transmitPort = 9999;
giuliomoro@24 76 strcpy(settings->serverName, "127.0.0.1");
andrewm@5 77 settings->ampMutePin = kAmplifierMutePin;
andrewm@5 78 }
andrewm@5 79
andrewm@5 80 // This function drops in place of getopt() in the main() function
andrewm@5 81 // and handles the initialisation of the RTAudio settings using
andrewm@5 82 // standard command-line arguments. System default arguments will
andrewm@5 83 // be stored in settings, otherwise arguments will be returned
andrewm@5 84 // as getopt() normally does.
andrewm@5 85
andrewm@45 86 int BeagleRT_getopt_long(int argc, char *argv[], const char *customShortOptions, const struct option *customLongOptions, BeagleRTInitSettings *settings)
andrewm@5 87 {
andrewm@5 88 static int firstRun = 1;
andrewm@5 89 static char totalShortOptions[256];
andrewm@5 90 static struct option totalLongOptions[256];
andrewm@5 91
andrewm@5 92 int c;
andrewm@5 93
andrewm@5 94 // Prep total option string the first time this is
andrewm@5 95 // run. As a getopt() substitute, it will be called repeatedly working its
andrewm@5 96 // way through argc and argv.
andrewm@5 97 if(firstRun) {
andrewm@5 98 firstRun = 0;
andrewm@5 99
andrewm@5 100 // Copy short options into one string
andrewm@5 101 strcpy(totalShortOptions, gDefaultShortOptions);
andrewm@5 102 strncat(totalShortOptions, customShortOptions, 256 - strlen(gDefaultShortOptions) - 1);
andrewm@5 103
andrewm@5 104 // Copy long options into one array
andrewm@5 105 int n = 0;
andrewm@5 106 while(1) {
andrewm@5 107 if(gDefaultLongOptions[n].name == NULL)
andrewm@5 108 break;
andrewm@5 109 totalLongOptions[n].name = gDefaultLongOptions[n].name;
andrewm@5 110 totalLongOptions[n].has_arg = gDefaultLongOptions[n].has_arg;
andrewm@5 111 totalLongOptions[n].flag = gDefaultLongOptions[n].flag;
andrewm@5 112 totalLongOptions[n].val = gDefaultLongOptions[n].val;
andrewm@5 113 n++;
andrewm@5 114 }
andrewm@5 115
andrewm@5 116 // Copy custom options into the array, if present
andrewm@5 117 if(customLongOptions == 0) {
andrewm@5 118 // Terminate the array
andrewm@5 119 totalLongOptions[n].name = NULL;
andrewm@5 120 totalLongOptions[n].has_arg = 0;
andrewm@5 121 totalLongOptions[n].flag = NULL;
andrewm@5 122 totalLongOptions[n].val = 0;
andrewm@5 123 }
andrewm@5 124 else {
andrewm@5 125 int customIndex = 0;
andrewm@5 126 while(n < 256) {
andrewm@5 127 if(customLongOptions[customIndex].name == NULL)
andrewm@5 128 break;
andrewm@5 129 totalLongOptions[n].name = customLongOptions[customIndex].name;
andrewm@5 130 totalLongOptions[n].has_arg = customLongOptions[customIndex].has_arg;
andrewm@5 131 totalLongOptions[n].flag = customLongOptions[customIndex].flag;
andrewm@5 132 totalLongOptions[n].val = customLongOptions[customIndex].val;
andrewm@5 133 n++;
andrewm@5 134 customIndex++;
andrewm@5 135 }
andrewm@5 136
andrewm@5 137 // Terminate the array
andrewm@5 138 totalLongOptions[n].name = NULL;
andrewm@5 139 totalLongOptions[n].has_arg = 0;
andrewm@5 140 totalLongOptions[n].flag = NULL;
andrewm@5 141 totalLongOptions[n].val = 0;
andrewm@5 142 }
andrewm@5 143 }
andrewm@5 144
andrewm@5 145 while(1) {
andrewm@5 146 if ((c = getopt_long(argc, argv, totalShortOptions, totalLongOptions, NULL)) < 0)
andrewm@5 147 return c;
andrewm@5 148
andrewm@5 149 switch (c) {
andrewm@5 150 case 'p':
andrewm@5 151 settings->periodSize = atoi(optarg);
andrewm@5 152 if(settings->periodSize < 1)
andrewm@5 153 settings->periodSize = 1;
andrewm@5 154 break;
andrewm@5 155 case 'v':
andrewm@5 156 settings->verbose = 1;
andrewm@5 157 break;
andrewm@50 158 case 'N':
giuliomoro@19 159 settings->useAnalog = atoi(optarg);
andrewm@5 160 break;
andrewm@50 161 case 'G':
giuliomoro@19 162 settings->useDigital = atoi(optarg);
giuliomoro@240 163 if(settings->useDigital == 0){
giuliomoro@240 164 settings->numDigitalChannels = 0;
giuliomoro@240 165 }
giuliomoro@16 166 break;
andrewm@12 167 case 'C':
giuliomoro@19 168 settings->numAnalogChannels = atoi(optarg);
giuliomoro@19 169 if(settings->numAnalogChannels >= 8)
giuliomoro@19 170 settings->numAnalogChannels = 8;
giuliomoro@19 171 else if(settings->numAnalogChannels >= 4)
giuliomoro@19 172 settings->numAnalogChannels = 4;
andrewm@12 173 else
giuliomoro@19 174 settings->numAnalogChannels = 2;
andrewm@12 175 break;
andrewm@50 176 case 'B':
giuliomoro@19 177 settings->numDigitalChannels = atoi(optarg);
giuliomoro@19 178 if(settings->numDigitalChannels >= 16)
giuliomoro@19 179 settings->numDigitalChannels = 16;
giuliomoro@19 180 else if (settings->numDigitalChannels < 1){
giuliomoro@19 181 settings->numDigitalChannels = 0;
giuliomoro@19 182 settings->useDigital = 0; //TODO: this actually works only if -G 0 is specified after -g 1.
giuliomoro@19 183 //No worries, though: disabling numDigital will only prevent the pins from being exported.
giuliomoro@16 184 }
giuliomoro@16 185 break;
andrewm@5 186 case 'M':
andrewm@5 187 settings->beginMuted = atoi(optarg);
andrewm@5 188 break;
andrewm@5 189 case 'D':
andrewm@5 190 settings->dacLevel = atof(optarg);
andrewm@5 191 break;
andrewm@5 192 case 'A':
andrewm@5 193 settings->adcLevel = atof(optarg);
andrewm@5 194 break;
andrewm@5 195 case 'H':
andrewm@5 196 settings->headphoneLevel = atof(optarg);
andrewm@5 197 break;
andrewm@50 198 case 'R':
giuliomoro@24 199 settings->receivePort = atoi(optarg);
giuliomoro@24 200 break;
andrewm@50 201 case 'T':
giuliomoro@24 202 settings->transmitPort = atoi(optarg);
giuliomoro@24 203 break;
andrewm@50 204 case 'S':
giuliomoro@24 205 if(strlen(optarg)<MAX_SERVERNAME_LENGTH)
giuliomoro@24 206 strcpy(settings->serverName, optarg);
giuliomoro@24 207 else
giuliomoro@24 208 std::cerr << "Warning: server name is too long (>" << MAX_SERVERNAME_LENGTH << " characters)."
giuliomoro@24 209 " Using default severName Instead ( " << settings->serverName << " ).\n";
giuliomoro@24 210 break;
giuliomoro@29 211 case OPT_PRU_FILE:
andrewm@45 212 if(strlen(optarg) < MAX_PRU_FILENAME_LENGTH)
giuliomoro@16 213 strcpy(settings->pruFilename, optarg);
giuliomoro@16 214 else
giuliomoro@16 215 std::cerr << "Warning: filename for the PRU code is too long (>" << MAX_PRU_FILENAME_LENGTH << " characters). Using embedded PRU code instead\n";
giuliomoro@16 216 break;
giuliomoro@171 217 case OPT_PGA_GAIN_LEFT:
giuliomoro@171 218 settings->pgaGain[0] = atof(optarg);
giuliomoro@171 219 break;
giuliomoro@171 220 case OPT_PGA_GAIN_RIGHT:
giuliomoro@171 221 settings->pgaGain[1] = atof(optarg);
giuliomoro@171 222 break;
andrewm@5 223 case '?':
andrewm@5 224 default:
andrewm@5 225 return c;
andrewm@5 226 }
andrewm@5 227 }
andrewm@5 228 }
andrewm@5 229
andrewm@5 230 // This function prints standard usage information for default arguments
andrewm@5 231 // Call from within your own usage function
andrewm@5 232 void BeagleRT_usage()
andrewm@5 233 {
giuliomoro@19 234 std::cerr << " --period [-p] period: Set the hardware period (buffer) size in analog samples\n";
giuliomoro@16 235 std::cerr << " --dac-level [-D] dBs: Set the DAC output level (0dB max; -63.5dB min)\n";
giuliomoro@16 236 std::cerr << " --adc-level [-A] dBs: Set the ADC input level (0dB max; -12dB min)\n";
giuliomoro@171 237 std::cerr << " --pga-gain-left dBs: Set the Programmable Gain Amplifier for the left audio channel (0dBmin; 59.5dB max; default: 16dB)\n";
giuliomoro@171 238 std::cerr << " --pga-gain-right dBs: Set the Programmable Gain Amplifier for the right audio channel (0dBmin; 59.5dB max; default: 16dB)\n";
giuliomoro@16 239 std::cerr << " --hp-level [-H] dBs: Set the headphone output level (0dB max; -63.5dB min)\n";
giuliomoro@16 240 std::cerr << " --mute-speaker [-M] val: Set whether to mute the speaker initially (default: no)\n";
andrewm@52 241 std::cerr << " --use-analog [-N] val: Set whether to use ADC/DAC analog (default: yes)\n";
andrewm@52 242 std::cerr << " --use-digital [-G] val: Set whether to use digital GPIO channels (default: yes)\n";
giuliomoro@19 243 std::cerr << " --analog-channels [-C] val: Set the number of ADC/DAC channels (default: 8)\n";
andrewm@52 244 std::cerr << " --digital-channels [-B] val: Set the number of GPIO channels (default: 16)\n";
andrewm@52 245 std::cerr << " --receive-port [-R] val: Set the receive port (default: 9998)\n";
andrewm@52 246 std::cerr << " --transmit-port [-T] val: Set the transmit port (default: 9999)\n";
andrewm@52 247 std::cerr << " --server-name [-S] val: Set the destination server name (default: '127.0.0.1')\n";
giuliomoro@24 248 std::cerr << " --pru-file val: Set an optional external file to use for the PRU binary code\n";
giuliomoro@16 249 std::cerr << " --verbose [-v]: Enable verbose logging information\n";
andrewm@5 250 }
giuliomoro@16 251