EENG 383

Lab 8 - Microphone

Lab: 8
Status Live

InLab 8

Some self guided activities.

Lab 8 assignment

Write a program that determines the frequency of a sin wave audio input provided by a whistle or audio function generator (like Keuwlsoft Dual Channel Function Generator for Android or Tone Generator Audio Frequency for iPhone). In order to ensure that you have usable data, your algorithm will wait until the sound level measured by the microphone exceeds a upper or lower sound threshold level as shown in the following image.


When enabled, the ISR will have the responsibility to: Main will be polling this flag and when it is true will go on to determine the period of the waveform as follows.

Since the microphone was sampled every 25µs by the ISR, the average number of indicies between consecutive positive edge crossing times 25µs, is equal to the period. You will represent your answer in microseconds, this will allow you to perform all your math using integers.

If you are having issues where the compiler complains that the PIC is "out of memory", move your large arrays out of main and make them global. Also, you do NOT need to make the zero crossing array have 512 entries. You should assume that someone whistling will produce a sine wave about 1.8kHz. In the example presented below, this creates 10 zero crossing. Doubling this value should be more than enough zero crossing for any realistic whistle.

ISR Details
Write the ISR to operate as a state machine using the following state diagram.


Use an enumerated type to define the states. You could use something like the following declaration.
typedef enum  {MIC_IDLE, MIC_WAIT_FOR_TRIGGER, MIC_ACQUIRE} myTMR0states_t;
The ISR should use the switch/case structure to move between states. Your ISR will need several static variable to keep track of the state and the buffer index.

When you first get your program working, you will notice that your program reports the waveform periods lower than the input period. I will focus on period in this discussion because you will use the period information to fix this problem. For example, my program reports that a waveform with period 2500 µs (400 Hz) has a period of 2037 µs. This is difference of 463 µs represents time spent in the ISR. I want you to compensate for this time spent in the ISR by adjusting the initial count value of the TMR0 ISR by a fudge factor. The factor is not 463 µs, because this amount of time was distributed across the number of ISR calls made during one period of the input waveform. You should be able to calculate exact how many timer counts to include in your fudge factor. When you get it right, your program should be able to get within 50Hz of the true waveform.

At start-up your program should present a splash screen - this would be a great place for some ASCII art. The splash screen should also contain connection instruction for the development board; for this assignment tell the user there are no jumpers to install! When you press "?" at the terminal you should be greeted with the following menu.
------------------------------
?: Help menu
o: k
Z: Reset processor
z: Clear the terminal
T/t: Increase/decrease threshold 138 - 118
f: gather 512 samples from the microphone and calculate the frequency
------------------------------