#include "play_raw_audio.h" #include "time_utils.h" #include #include #include #include #include #include #include // prototypes for static functions static int play_square_wave(float frequency, float duration); int play_manual_alarm() { int err = 0; for (int i = 0; i < 3; i++) { for (int i = 0; i < 2; i++) { err = play_square_wave(1000.0, 0.2); if (err != 0) { return err; } sleep_ms(200); } sleep_ms(500); } return 0; } // UNUSED // Playing a raw audio file has the downside of depending on a file. int play_raw_audio(char file_name[]) { int pa_error = 0; char content[1024] = ""; int myfd = open(file_name, O_RDONLY); if (myfd == -1) { fprintf(stderr, "Failed to open audio file %s: %s.\n", file_name, strerror(errno)); return 1; } pa_simple* simple = NULL; pa_sample_spec ss; ss.format = PA_SAMPLE_S16LE; ss.rate = 48000; ss.channels = 2; simple = pa_simple_new(NULL, "Audio Playback", PA_STREAM_PLAYBACK, NULL, "playback", &ss, NULL, NULL, &pa_error); int i = 0; while (read(myfd, content, sizeof(content))) { // skip the first 1024 bytes to not play the file header if (i != 0) { pa_simple_write(simple, content, sizeof(content), &pa_error); } i++; } pa_simple_drain(simple, NULL); pa_simple_free(simple); close(myfd); return 0; } // Output a tone with the audio frequency "frequency" // for "duration" number of seconds. // The sound signals are not sine waves but square waves. static int play_square_wave(float frequency, float duration) { const int sample_rate = 44100; const int channel_count = 2; size_t buffer_size = sample_rate * channel_count * duration; short buffer[buffer_size] = {}; pa_simple *s; pa_sample_spec ss = { .format = PA_SAMPLE_S16LE, .rate = sample_rate, .channels = channel_count, }; // number of identical consecutive elements // 5 would look like this: // [0,0,0,0,0,32768,32768,32768,32768,32768,0,...] int array_interval = sample_rate / frequency; bool square_peak = false; for (int i = 0; i < buffer_size; i++) { if (i % array_interval == 0) { // toggle the value (0 or the max value for a short) square_peak = !square_peak; } if (square_peak) { buffer[i] = SHRT_MAX; } else { buffer[i] = 0; } } if (!(s = pa_simple_new(NULL, NULL, PA_STREAM_PLAYBACK, NULL, "playback", &ss, NULL, NULL, &errno))) { fprintf(stderr, "pa_simple_new() failed: %s\n", pa_strerror(errno)); return 1; } if (pa_simple_write(s, buffer, sizeof(buffer), NULL) < 0) { fprintf(stderr, "pa_simple_write() failed: %s\n", pa_strerror(errno)); return 1; } pa_simple_drain(s, NULL); pa_simple_free(s); return 0; }