LPCOpen Platform  v1.03
LPCOpen Platform for NXP LPC Microcontrollers
 All Data Structures Files Functions Variables Typedefs Enumerations Enumerator Macros Groups Pages
AudioOutputHost.c
Go to the documentation of this file.
1 /*
2  * @brief Audio Output Host Example
3  *
4  * @note
5  * Copyright(C) NXP Semiconductors, 2012
6  * Copyright(C) Dean Camera, 2011, 2012
7  * All rights reserved.
8  *
9  * @par
10  * Software that is described herein is for illustrative purposes only
11  * which provides customers with programming information regarding the
12  * LPC products. This software is supplied "AS IS" without any warranties of
13  * any kind, and NXP Semiconductors and its licensor disclaim any and
14  * all warranties, express or implied, including all implied warranties of
15  * merchantability, fitness for a particular purpose and non-infringement of
16  * intellectual property rights. NXP Semiconductors assumes no responsibility
17  * or liability for the use of the software, conveys no license or rights under any
18  * patent, copyright, mask work right, or any other intellectual property rights in
19  * or to any products. NXP Semiconductors reserves the right to make changes
20  * in the software without notification. NXP Semiconductors also makes no
21  * representation or warranty that such application will be suitable for the
22  * specified use without further testing or modification.
23  *
24  * @par
25  * Permission to use, copy, modify, and distribute this software and its
26  * documentation is hereby granted, under NXP Semiconductors' and its
27  * licensor's relevant copyrights in the software, without fee, provided that it
28  * is used in conjunction with NXP Semiconductors microcontrollers. This
29  * copyright, permission, and disclaimer notice must appear in all copies of
30  * this code.
31  */
32 
33 #include "AudioOutputHost.h"
34 
35 /*****************************************************************************
36  * Private types/enumerations/variables
37  ****************************************************************************/
38 
44  .Config = {
45  .DataOUTPipeNumber = 1,
46  .PortNumber = 0,
47  },
48 };
49 
50 /*****************************************************************************
51  * Public types/enumerations/variables
52  ****************************************************************************/
53 
54 /*****************************************************************************
55  * Private functions
56  ****************************************************************************/
57 
58 /* Timer setup for audio waveform */
59 static void Init_Timer(uint32_t freq)
60 {
61  /* Enable timer 1 clock and reset */
63 
64  /* Timer setup for match and interrupt at TICKRATE */
67  Chip_TIMER_SetMatch(LPC_TIMER1, 1, (1000000 / freq));
70 
71  NVIC_SetPriority(TIMER1_IRQn, ((0x01 << 3) | 0x01));
72  /* Enable timer interrupt */
73  NVIC_EnableIRQ(TIMER1_IRQn);
74 }
75 
76 static void DeInitTimer(void)
77 {
79  NVIC_DisableIRQ(TIMER1_IRQn);
80 }
81 
82 /* Configures the board hardware and chip peripherals for the demo's functionality. */
83 static void SetupHardware(void)
84 {
85  Board_Init();
86  USB_Init(Speaker_Audio_Interface.Config.PortNumber, USB_MODE_Host);
87 
88  /* Hardware Initialization */
91 
92  /* Create a stdio stream for the serial port for stdin and stdout */
94 }
95 
96 /*****************************************************************************
97  * Public functions
98  ****************************************************************************/
99 
104 #define USE_TEST_TONE
105 #if defined(__LPC175X_6X__) || defined(__LPC177X_8X__) || defined(__LPC407X_8X__) || defined(__LPC18XX__) || defined(__LPC43XX__)
106 void TIMER1_IRQHandler(void)
107 {
108  uint8_t PrevPipe = Pipe_GetCurrentPipe(Speaker_Audio_Interface.Config.PortNumber);
109  /* Check that the USB bus is ready for the next sample to write */
110  if (Audio_Host_IsReadyForNextSample(&Speaker_Audio_Interface)) {
111  int16_t AudioSample;
112 #if defined(USE_TEST_TONE)
113  static uint8_t SquareWaveSampleCount;
114  static int16_t CurrentWaveValue;
115 
116  /* In test tone mode, generate a square wave at 1/256 of the sample rate */
117  if (SquareWaveSampleCount++ == 0xFF) {
118  CurrentWaveValue ^= 0x8000;
119  }
120 
121  /* Only generate audio if the board button is being pressed */
122  AudioSample = (Buttons_GetStatus() & BUTTONS_BUTTON1) ? CurrentWaveValue : 0;
123 #else
124  /* Audio sample is ADC value scaled to fit the entire range */
125  AudioSample = ((SAMPLE_MAX_RANGE / ADC_MAX_RANGE) * ADC_GetResult());
126 
127 #if defined(MICROPHONE_BIASED_TO_HALF_RAIL)
128  /* Microphone is biased to half rail voltage, subtract the bias from the sample value */
129  AudioSample -= (SAMPLE_MAX_RANGE / 2);
130 #endif /* defined(MICROPHONE_BIASED_TO_HALF_RAIL) */
131 #endif /* defined(USE_TEST_TONE) */
132 
133  Audio_Host_WriteSample16(&Speaker_Audio_Interface, AudioSample);
134  Audio_Host_WriteSample16(&Speaker_Audio_Interface, AudioSample);
135  }
136 
137  Pipe_SelectPipe(Speaker_Audio_Interface.Config.PortNumber, PrevPipe);
138 }
139 
140 #endif /* defined(__LPC17XX__) ... */
141 
148 int main(void)
149 {
150  SetupHardware();
151 
152  DEBUGOUT("Audio Output Host Demo running.\r\n");
153 
154  for (;; ) {
155  Audio_Host_USBTask(&Speaker_Audio_Interface);
156  USB_USBTask(Speaker_Audio_Interface.Config.PortNumber, USB_MODE_Host);
157  }
158 }
159 
160 /* Event handler for the USB_DeviceAttached event. This indicates that a device
161  has been attached to the host, and starts the library USB task to begin the
162  enumeration and USB management process. */
163 void EVENT_USB_Host_DeviceAttached(const uint8_t corenum)
164 {
165  DEBUGOUT(("Device Attached on port %d\r\n"), corenum);
166 }
167 
168 /* Event handler for the USB_DeviceUnattached event. This indicates that a device
169  has been removed from the host, and stops the library USB task management
170  process. */
171 void EVENT_USB_Host_DeviceUnattached(const uint8_t corenum)
172 {
173  DEBUGOUT(("\r\nDevice Unattached on port %d\r\n"), corenum);
174  DeInitTimer();
175 }
176 
177 /* Event handler for the USB_DeviceEnumerationComplete event. This indicates that a
178  device has been successfully enumerated by the host and is now ready to be used
179  by the application. */
180 void EVENT_USB_Host_DeviceEnumerationComplete(const uint8_t corenum)
181 {
182  uint16_t ConfigDescriptorSize;
183  uint8_t ConfigDescriptorData[512];
184 
185  if (USB_Host_GetDeviceConfigDescriptor(corenum, 1, &ConfigDescriptorSize, ConfigDescriptorData,
186  sizeof(ConfigDescriptorData)) != HOST_GETCONFIG_Successful) {
187  DEBUGOUT("Error Retrieving Configuration Descriptor.\r\n");
188 
189  return;
190  }
191 
192  Speaker_Audio_Interface.Config.PortNumber = corenum;
193  if (Audio_Host_ConfigurePipes(&Speaker_Audio_Interface,
194  ConfigDescriptorSize, ConfigDescriptorData) != AUDIO_ENUMERROR_NoError) {
195  DEBUGOUT("Attached Device Not a Valid Audio Output Device.\r\n");
196 
197  return;
198  }
199 
201  DEBUGOUT("Error Setting Device Configuration.\r\n");
202 
203  return;
204  }
205 
206  if (Audio_Host_StartStopStreaming(&Speaker_Audio_Interface, true) != HOST_SENDCONTROL_Successful) {
207  DEBUGOUT("Error Enabling Audio Stream.\r\n");
208 
209  USB_Host_SetDeviceConfiguration(Speaker_Audio_Interface.Config.PortNumber, 0);
210  return;
211  }
212 
213  USB_Audio_SampleFreq_t SampleRate = AUDIO_SAMPLE_FREQ(48000);
214  if (Audio_Host_GetSetEndpointProperty(&Speaker_Audio_Interface, Speaker_Audio_Interface.Config.DataOUTPipeNumber,
216  sizeof(SampleRate), &SampleRate) != HOST_SENDCONTROL_Successful) {
217  DEBUGOUT("Error Setting Audio Sampling Frequency.\r\n");
218 
219  USB_Host_SetDeviceConfiguration(Speaker_Audio_Interface.Config.PortNumber, 0);
220  return;
221  }
222  DEBUGOUT("Audio Device Enumerated.\r\n");
223  Init_Timer(48000);
224 }
225 
226 /* Event handler for the USB_HostError event. This indicates that a hardware error
227  occurred while in host mode. */
228 void EVENT_USB_Host_HostError(const uint8_t corenum, const uint8_t ErrorCode)
229 {
230  USB_Disable(corenum, USB_MODE_Host);
231 
232  DEBUGOUT(("Host Mode Error\r\n"
233  " -- Error port %d\r\n"
234  " -- Error Code %d\r\n" ), corenum, ErrorCode);
235 
236  /* Wait forever */
237  for (;; ) {}
238 }
239 
240 /* Event handler for the USB_DeviceEnumerationFailed event. This indicates that
241  a problem occurred while enumerating an attached USB device. */
242 void EVENT_USB_Host_DeviceEnumerationFailed(const uint8_t corenum,
243  const uint8_t ErrorCode,
244  const uint8_t SubErrorCode)
245 {
246  DEBUGOUT(("Dev Enum Error\r\n"
247  " -- Error port %d\r\n"
248  " -- Error Code %d\r\n"
249  " -- Sub Error Code %d\r\n"
250  " -- In State %d\r\n" ),
251  corenum, ErrorCode, SubErrorCode, USB_HostState[corenum]);
252 }