1 /*---------------------------------------------------------------------------*
2   Project:  TwlSDK - demos.TWL - spi - mic-3
3   File:     main.c
4 
5   Copyright 2007-2009 Nintendo. All rights reserved.
6 
7   These coded instructions, statements, and computer programs contain
8   proprietary information of Nintendo of America Inc. and/or Nintendo
9   Company Ltd., and are protected by Federal copyright law. They may
10   not be disclosed to third parties or copied or duplicated in any form,
11   in whole or in part, without the prior written consent of Nintendo.
12 
13   $Date:: 2009-09-24#$
14   $Rev: 11063 $
15   $Author: okubata_ryoma $
16  *---------------------------------------------------------------------------*/
17 
18 /*---------------------------------------------------------------------------*
19     A sample that controls microphone sampling.
20 
21     USAGE:
22         UP, DOWN: Control sampling span.
23         LEFT, RIGHT: Control sampling bit range. ( 8-bit, 12-bit, etc.)
24         SEL , STA    : Control loop sampling enable or disable.
25 
26     HOWTO:
27         1. Initialize MIC library and SNDEX library.
28         2. Start automatic sampling of microphone by default configuration.
29         3. When you switch parameters, first, stop sampling. Then, if necessary,
30            switch I2S frequency. After that, edit parameters and start automatic
31            sampling again.
32  *---------------------------------------------------------------------------*/
33 
34 #include    <twl.h>
35 #include    "DEMO.h"
36 
37 /*---------------------------------------------------------------------------*
38     Constant definitions
39  *---------------------------------------------------------------------------*/
40 #define     TEST_BUFFER_SIZE    (1024 * 1024)   // 1 MB
41 #define     RETRY_MAX_COUNT     8
42 
43 /*---------------------------------------------------------------------------*
44     Internal Function Definitions
45  *---------------------------------------------------------------------------*/
46 static void     StartSampling(const MICAutoParam* param);
47 static void     StopSampling(void);
48 static void     AdjustSampling(u32 rate);
49 static SNDEXFrequency   GetI2SFrequency(void);
50 static void     SetI2SFrequency(SNDEXFrequency freq);
51 static void     SwitchI2SFrequency(void);
52 
53 static void     StepUpSamplingRate(void);
54 static void     StepDownSamplingRate(void);
55 static void     SetDrawData(void *address, MICSamplingType type);
56 static void     PrintfVariableData(void);
57 
58 static void     VBlankIntr(void);
59 static void     Init3D(void);
60 static void     Draw3D(void);
61 static void     DrawLine(s16 sx, s16 sy, s16 ex, s16 ey);
62 
63 /*---------------------------------------------------------------------------*
64     Internal Variable Definitions
65  *---------------------------------------------------------------------------*/
66 static MICAutoParam gMicAutoParam;
67 static u8           gDrawData[192];
68 static u8           gMicData[TEST_BUFFER_SIZE] ATTRIBUTE_ALIGN(HW_CACHE_LINE_SIZE);
69 
70 /*---------------------------------------------------------------------------*
71   Name:         TwlMain
72 
73   Description:  Initialization and main loop.
74 
75   Arguments:    None.
76 
77   Returns:      None.
78  *---------------------------------------------------------------------------*/
TwlMain(void)79 void TwlMain(void)
80 {
81     /* Various types of initialization */
82     OS_Init();
83     FX_Init();
84     GX_Init();
85     GX_DispOff();
86     GXS_DispOff();
87 
88     // When in NITRO mode, stopped by Panic
89     DEMOCheckRunOnTWL();
90 
91     /* Initializes display settings */
92     GX_SetBankForLCDC(GX_VRAM_LCDC_ALL);
93     MI_CpuClearFast((void *)HW_LCDC_VRAM, HW_LCDC_VRAM_SIZE);
94     (void)GX_DisableBankForLCDC();
95     MI_CpuFillFast((void *)HW_OAM, 192, HW_OAM_SIZE);
96     MI_CpuClearFast((void *)HW_PLTT, HW_PLTT_SIZE);
97     MI_CpuFillFast((void *)HW_DB_OAM, 192, HW_DB_OAM_SIZE);
98     MI_CpuClearFast((void *)HW_DB_PLTT, HW_DB_PLTT_SIZE);
99 
100     /* 3D-related initialization */
101     Init3D();
102 
103     /* Interrupt settings */
104     OS_SetIrqFunction(OS_IE_V_BLANK, VBlankIntr);
105     (void)OS_EnableIrqMask(OS_IE_V_BLANK);
106     (void)OS_EnableIrq();
107     (void)OS_EnableInterrupts();
108     (void)GX_VBlankIntr(TRUE);
109 
110     /* Initialize related libraries */
111     {
112         (void)PM_SetAmp(PM_AMP_ON);
113         SNDEX_Init();
114         MIC_Init();
115 
116         gMicAutoParam.type      =   MIC_SAMPLING_TYPE_8BIT;
117         gMicAutoParam.buffer    =   (void *)gMicData;
118         gMicAutoParam.size      =   TEST_BUFFER_SIZE;
119         if ((OS_IsRunOnTwl() == TRUE) && (GetI2SFrequency() == SNDEX_FREQUENCY_47610))
120         {
121             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_23810;
122         }
123         else
124         {
125             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_16360;
126         }
127         gMicAutoParam.loop_enable   =   TRUE;
128         gMicAutoParam.full_callback =   NULL;
129         StartSampling((const MICAutoParam*)&gMicAutoParam);
130     }
131 
132     /* Initialize internal variables */
133     MI_CpuFill8(gDrawData, 0x80, sizeof(gDrawData));
134 
135     /* LCD display start */
136     GX_DispOn();
137     GXS_DispOn();
138 
139     /* Debug string output */
140     OS_Printf("mic-3 demo started.\n");
141     OS_Printf("   up/down      -> change sampling rate\n");
142     OS_Printf("   left/right   -> change bit range\n");
143     OS_Printf("   start/select -> change loop setting\n");
144     OS_Printf("\n");
145     PrintfVariableData();
146 
147     /* Empty call for getting key input data (strategy for pressing A Button in the IPL) */
148     (void)PAD_Read();
149 
150     {
151         u16     keyOld  =   0;
152         u16     keyTrg;
153         u16     keyNow;
154 
155         /* Main loop */
156         while (TRUE)
157         {
158             /* Get key input data */
159             keyNow  =   PAD_Read();
160             keyTrg  =   (u16)((keyOld ^ keyNow) & keyNow);
161             keyOld  =   keyNow;
162 
163             /* Change sampling type (bit width) */
164             if (keyTrg & PAD_KEY_LEFT)
165             {
166                 StopSampling();
167                 gMicAutoParam.type
168                     =   (MICSamplingType)((gMicAutoParam.type + MIC_SAMPLING_TYPE_MAX - 1) % MIC_SAMPLING_TYPE_MAX);
169                 StartSampling((const MICAutoParam*)&gMicAutoParam);
170                 PrintfVariableData();
171             }
172             if (keyTrg & PAD_KEY_RIGHT)
173             {
174                 StopSampling();
175                 gMicAutoParam.type
176                         =   (MICSamplingType)((gMicAutoParam.type + 1) % MIC_SAMPLING_TYPE_MAX);
177                 StartSampling((const MICAutoParam*)&gMicAutoParam);
178                 PrintfVariableData();
179             }
180 
181             /* Change sampling rate */
182             if (keyTrg & PAD_KEY_UP)
183             {
184                 StepUpSamplingRate();
185                 PrintfVariableData();
186             }
187             if (keyTrg & PAD_KEY_DOWN)
188             {
189                 StepDownSamplingRate();
190                 PrintfVariableData();
191             }
192 
193             /* Change loop availability when buffer is full */
194             if (keyTrg & (PAD_BUTTON_SELECT | PAD_BUTTON_START))
195             {
196                 StopSampling();
197                 gMicAutoParam.loop_enable = (gMicAutoParam.loop_enable + 1) % 2;
198                 StartSampling((const MICAutoParam*)&gMicAutoParam);
199                 PrintfVariableData();
200             }
201 
202             /* Render waveform */
203             SetDrawData(MIC_GetLastSamplingAddress(), gMicAutoParam.type);
204             Draw3D();
205 
206             /* Waiting for the V-Blank */
207             OS_WaitVBlankIntr();
208         }
209     }
210 }
211 
212 /*---------------------------------------------------------------------------*
213   Name:         StartSampling
214 
215   Description:  Calls the MIC_StartLimitedSampling function and performs error processing.
216 
217   Arguments:    param: Parameters passed to the microphone functions
218 
219   Returns:      None.
220  *---------------------------------------------------------------------------*/
221 static void
StartSampling(const MICAutoParam * param)222 StartSampling(const MICAutoParam* param)
223 {
224     MICResult   result;
225     s32         retry   =   0;
226 
227     while (TRUE)
228     {
229         result  =   MIC_StartLimitedSampling(param);
230         switch (result)
231         {
232         case MIC_RESULT_SUCCESS:            // Success
233             return;
234         case MIC_RESULT_BUSY:               // Another thread is using the microphone
235         case MIC_RESULT_SEND_ERROR:         // PXI queue is full
236             if (++ retry <= RETRY_MAX_COUNT)
237             {
238                 OS_Sleep(1);
239                 continue;
240             }
241             OS_TWarning("Retry count overflow.\n");
242             return;
243         case MIC_RESULT_ILLEGAL_STATUS:     // Not in an autosampling stopped state
244             OS_TWarning("Already started sampling.\n");
245             return;
246         case MIC_RESULT_ILLEGAL_PARAMETER:  // The specified parameter is not supported
247             OS_TWarning("Illegal parameter to start automatic sampling.\n");
248             return;
249         default:                            // Other fatal error
250             OS_Panic("Fatal error (%d).\n", result);
251             /* Never return */
252         }
253     }
254 }
255 
256 /*---------------------------------------------------------------------------*
257   Name:         StopSampling
258 
259   Description:  Calls the MIC_StopLimitedSampling function and performs error processing.
260 
261   Arguments:    None.
262 
263   Returns:      None.
264  *---------------------------------------------------------------------------*/
265 static void
StopSampling(void)266 StopSampling(void)
267 {
268     MICResult   result;
269     s32         retry   =   0;
270 
271     while (TRUE)
272     {
273         result  =   MIC_StopLimitedSampling();
274         switch (result)
275         {
276         case MIC_RESULT_SUCCESS:            // Success
277         case MIC_RESULT_ILLEGAL_STATUS:     // Not in an autosampling state
278             return;
279         case MIC_RESULT_BUSY:               // Microphone in use by other thread
280         case MIC_RESULT_SEND_ERROR:         // PXI queue is full
281             if (++ retry <= RETRY_MAX_COUNT)
282             {
283                 OS_Sleep(1);
284                 continue;
285             }
286             OS_TWarning("Retry count overflow.\n");
287             return;
288         default:                            // Other fatal error
289             OS_Panic("Fatal error (%d).\n", result);
290             /* Never return */
291         }
292     }
293 }
294 
295 /*---------------------------------------------------------------------------*
296   Name:         AdjustSampling
297 
298   Description:  Calls the MIC_AdjustLimitedSampling function and performs error processing.
299 
300   Arguments:    rate: Specifies the sampling period.
301 
302   Returns:      None.
303  *---------------------------------------------------------------------------*/
304 static void
AdjustSampling(u32 rate)305 AdjustSampling(u32 rate)
306 {
307     MICResult   result;
308     s32         retry   =   0;
309 
310     while (TRUE)
311     {
312         result  =   MIC_AdjustLimitedSampling(rate);
313         switch (result)
314         {
315         case MIC_RESULT_SUCCESS:            // Success
316         case MIC_RESULT_ILLEGAL_STATUS:     // Not in an autosampling state
317             return;
318         case MIC_RESULT_BUSY:               // Microphone in use by other thread
319         case MIC_RESULT_SEND_ERROR:         // PXI queue is full
320             if (++ retry <= RETRY_MAX_COUNT)
321             {
322                 OS_Sleep(1);
323                 continue;
324             }
325             OS_TWarning("Retry count overflow.\n");
326             return;
327         case MIC_RESULT_ILLEGAL_PARAMETER:  // The specified parameter is not supported
328             OS_TWarning("Illegal parameter to adjust automatic sampling rate.\n");
329             return;
330         default:                            // Other fatal error
331             OS_Panic("Fatal error (%d).\n", result);
332             /* Never return */
333         }
334     }
335 }
336 
337 #include <twl/ltdmain_begin.h>
338 /*---------------------------------------------------------------------------*
339   Name:         GetI2SFrequency
340 
341   Description:  Gets the I2S operating frequency.
342 
343   Arguments:    None.
344 
345   Returns:      SNDEXFrequency: Returns the I2S operating frequency.
346  *---------------------------------------------------------------------------*/
347 static SNDEXFrequency
GetI2SFrequency(void)348 GetI2SFrequency(void)
349 {
350     SNDEXResult     result;
351     SNDEXFrequency  freq;
352     s32             retry   =   0;
353 
354     while (TRUE)
355     {
356         result  =   SNDEX_GetI2SFrequency(&freq);
357         switch (result)
358         {
359         case SNDEX_RESULT_SUCCESS:          // Success
360             return freq;
361         case SNDEX_RESULT_EXCLUSIVE:        // Exclusion error
362         case SNDEX_RESULT_PXI_SEND_ERROR:   // PXI queue is full
363             if (++ retry <= RETRY_MAX_COUNT)
364             {
365                 OS_Sleep(1);
366                 continue;
367             }
368             OS_TWarning("Retry count overflow.\n");
369             break;
370         case SNDEX_RESULT_BEFORE_INIT:      // Pre-initialization
371         case SNDEX_RESULT_ILLEGAL_STATE:    // Abnormal state
372             OS_TWarning("Illegal state to get I2S frequency.\n");
373             break;
374         case SNDEX_RESULT_FATAL_ERROR:      // Fatal error
375         default:
376             OS_Panic("Fatal error (%d).\n", result);
377             /* Never return */
378         }
379     }
380     return SNDEX_FREQUENCY_32730;
381 }
382 
383 /*---------------------------------------------------------------------------*
384   Name:         SetI2SFrequency
385 
386   Description:  Changes the I2S operating frequency.
387 
388   Arguments:    freq: I2S operating frequency.
389 
390   Returns:      None.
391  *---------------------------------------------------------------------------*/
392 static void
SetI2SFrequency(SNDEXFrequency freq)393 SetI2SFrequency(SNDEXFrequency freq)
394 {
395     SNDEXResult     result;
396     s32             retry   =   0;
397 
398     while (TRUE)
399     {
400         result  =   SNDEX_SetI2SFrequency(freq);
401         switch (result)
402         {
403         case SNDEX_RESULT_SUCCESS:          // Success
404             return;
405         case SNDEX_RESULT_EXCLUSIVE:        // Exclusion error
406         case SNDEX_RESULT_PXI_SEND_ERROR:   // PXI queue is full
407             if (++ retry <= RETRY_MAX_COUNT)
408             {
409                 OS_Sleep(1);
410                 continue;
411             }
412             OS_TWarning("Retry count overflow.\n");
413             return;
414         case SNDEX_RESULT_BEFORE_INIT:      // Pre-initialization
415         case SNDEX_RESULT_ILLEGAL_STATE:    // Abnormal state
416             OS_TWarning("Illegal state to set I2S frequency.\n");
417             return;
418         case SNDEX_RESULT_INVALID_PARAM:    // Abnormal argument
419             OS_TWarning("Could not set I2S frequency into %d.\n", freq);
420             return;
421         case SNDEX_RESULT_FATAL_ERROR:      // Fatal error
422         default:
423             OS_Panic("Fatal error (%d)\n", result);
424             /* Never return */
425         }
426     }
427 }
428 
429 /*---------------------------------------------------------------------------*
430   Name:         SwitchI2SFrequency
431 
432   Description:  Changes the I2S operating frequency in conjunction with the microphone sampling frequency.
433 
434   Arguments:    None.
435 
436   Returns:      None.
437  *---------------------------------------------------------------------------*/
438 static void
SwitchI2SFrequency(void)439 SwitchI2SFrequency(void)
440 {
441     SNDEXFrequency  freq;
442 
443     freq    =   GetI2SFrequency();
444     switch (gMicAutoParam.rate)
445     {
446     case MIC_SAMPLING_RATE_8180:
447     case MIC_SAMPLING_RATE_10910:
448     case MIC_SAMPLING_RATE_16360:
449     case MIC_SAMPLING_RATE_32730:
450         if (freq != SNDEX_FREQUENCY_32730)
451         {
452             SetI2SFrequency(SNDEX_FREQUENCY_32730);
453         }
454         break;
455     case MIC_SAMPLING_RATE_11900:
456     case MIC_SAMPLING_RATE_15870:
457     case MIC_SAMPLING_RATE_23810:
458     case MIC_SAMPLING_RATE_47610:
459         if (freq != SNDEX_FREQUENCY_47610)
460         {
461             SetI2SFrequency(SNDEX_FREQUENCY_47610);
462         }
463         break;
464     }
465 }
466 
467 #include <twl/ltdmain_end.h>
468 
469 /*---------------------------------------------------------------------------*
470   Name:         StepUpSamplingRate
471 
472   Description:  Increases the microphone sampling frequency by one level.
473 
474   Arguments:    None.
475 
476   Returns:      None.
477  *---------------------------------------------------------------------------*/
478 static void
StepUpSamplingRate(void)479 StepUpSamplingRate(void)
480 {
481     if (OS_IsRunOnTwl() == TRUE)
482     {
483         switch (gMicAutoParam.rate)
484         {
485         case MIC_SAMPLING_RATE_8180:    // 32.73k / 4
486             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_10910;
487             break;
488         case MIC_SAMPLING_RATE_10910:   // 32.73k / 3
489             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_11900;
490             break;
491         case MIC_SAMPLING_RATE_11900:   // 47.61k / 4
492             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_15870;
493             break;
494         case MIC_SAMPLING_RATE_15870:   // 47.61k / 3
495             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_16360;
496             break;
497         case MIC_SAMPLING_RATE_16360:   // 32.73k / 2
498             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_23810;
499             break;
500         case MIC_SAMPLING_RATE_23810:   // 47.61k / 2
501             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_32730;
502             break;
503         case MIC_SAMPLING_RATE_32730:   // 32.73k / 1
504             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_47610;
505             break;
506         case MIC_SAMPLING_RATE_47610:   // 47.61k / 1
507         default:
508             /* Do nothing */
509             return;
510         }
511         StopSampling();
512         SwitchI2SFrequency();
513         StartSampling((const MICAutoParam*)&gMicAutoParam);
514     }
515     else
516     {
517         switch (gMicAutoParam.rate)
518         {
519         case MIC_SAMPLING_RATE_8180:    // 32.73k / 4
520             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_10910;
521             break;
522         case MIC_SAMPLING_RATE_10910:   // 32.73k / 3
523             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_11900;
524             break;
525         case MIC_SAMPLING_RATE_11900:   // 47.61k / 4
526             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_15870;
527             break;
528         case MIC_SAMPLING_RATE_15870:   // 47.61k / 3
529             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_16360;
530             break;
531         case MIC_SAMPLING_RATE_16360:   // 32.73k / 2
532             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_23810;
533             break;
534         case MIC_SAMPLING_RATE_23810:   // 47.61k / 2
535         default:
536             /* Do nothing */
537             return;
538         }
539         AdjustSampling(gMicAutoParam.rate);
540     }
541 }
542 
543 /*---------------------------------------------------------------------------*
544   Name:         StepUpSamplingRate
545 
546   Description:  Decreases the microphone sampling frequency by one level.
547 
548   Arguments:    None.
549 
550   Returns:      None.
551  *---------------------------------------------------------------------------*/
552 static void
StepDownSamplingRate(void)553 StepDownSamplingRate(void)
554 {
555     if (OS_IsRunOnTwl() == TRUE)
556     {
557         switch (gMicAutoParam.rate)
558         {
559         case MIC_SAMPLING_RATE_47610:   // 47.61k / 1
560             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_32730;
561             break;
562         case MIC_SAMPLING_RATE_32730:   // 32.73k / 1
563             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_23810;
564             break;
565         case MIC_SAMPLING_RATE_23810:   // 47.61k / 2
566             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_16360;
567             break;
568         case MIC_SAMPLING_RATE_16360:   // 32.73k / 2
569             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_15870;
570             break;
571         case MIC_SAMPLING_RATE_15870:   // 47.61k / 3
572             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_11900;
573             break;
574         case MIC_SAMPLING_RATE_11900:   // 47.61k / 4
575             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_10910;
576             break;
577         case MIC_SAMPLING_RATE_10910:   // 32.73k / 3
578             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_8180;
579             break;
580         case MIC_SAMPLING_RATE_8180:    // 32.73k / 4
581         default:
582             /* Do nothing */
583             return;
584         }
585         StopSampling();
586         SwitchI2SFrequency();
587         StartSampling((const MICAutoParam*)&gMicAutoParam);
588     }
589     else
590     {
591         switch (gMicAutoParam.rate)
592         {
593         case MIC_SAMPLING_RATE_23810:   // 47.61k / 2
594             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_16360;
595             break;
596         case MIC_SAMPLING_RATE_16360:   // 32.73k / 2
597             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_15870;
598             break;
599         case MIC_SAMPLING_RATE_15870:   // 47.61k / 3
600             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_11900;
601             break;
602         case MIC_SAMPLING_RATE_11900:   // 47.61k / 4
603             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_10910;
604             break;
605         case MIC_SAMPLING_RATE_10910:   // 32.73k / 3
606             gMicAutoParam.rate  =   MIC_SAMPLING_RATE_8180;
607             break;
608         case MIC_SAMPLING_RATE_8180:    // 32.73k / 4
609         default:
610             /* Do nothing */
611             return;
612         }
613         AdjustSampling(gMicAutoParam.rate);
614     }
615 }
616 
617 /*---------------------------------------------------------------------------*
618   Name:         SetDrawData
619 
620   Description:  Stores the current newest sampled data in the buffer that puts it on the display.
621 
622 
623   Arguments:    address: Location in main memory where the most recent sampling data was stored by the component
624 
625                 type: Sampling type (bit width)
626 
627   Returns:      None.
628  *---------------------------------------------------------------------------*/
SetDrawData(void * address,MICSamplingType type)629 static void SetDrawData(void *address, MICSamplingType type)
630 {
631     s32     i;
632 
633     /* If sampling has never been performed, do nothing and stop.
634        (Because it would delete memory cache(s) unrelated to the microphone) */
635     if ((address < gMicData) || (address >= (gMicData + TEST_BUFFER_SIZE)))
636     {
637         return;
638     }
639 
640     switch (type)
641     {
642     case MIC_SAMPLING_TYPE_8BIT:
643     case MIC_SAMPLING_TYPE_SIGNED_8BIT:
644         /* In the case of 8-bit sampling */
645         {
646             u8     *p;
647 
648             p = (u8 *)((u32)address - 191);
649             if (p < gMicData)
650             {
651                 p = (u8 *)((u32)p + TEST_BUFFER_SIZE);
652             }
653             DC_InvalidateRange((void *)((u32)p & ~(HW_CACHE_LINE_SIZE - 1)), HW_CACHE_LINE_SIZE);
654             for (i = 0; i < 192; i++)
655             {
656                 gDrawData[i] = *p;
657                 p++;
658                 if ((u32)p >= (u32)(gMicData + TEST_BUFFER_SIZE))
659                 {
660                     p -= TEST_BUFFER_SIZE;
661                 }
662                 if (((u32)p % HW_CACHE_LINE_SIZE) == 0)
663                 {
664                     DC_InvalidateRange(p, HW_CACHE_LINE_SIZE);
665                 }
666             }
667         }
668         break;
669     case MIC_SAMPLING_TYPE_12BIT:
670     case MIC_SAMPLING_TYPE_SIGNED_12BIT:
671     case MIC_SAMPLING_TYPE_12BIT_FILTER_OFF:
672     case MIC_SAMPLING_TYPE_SIGNED_12BIT_FILTER_OFF:
673         /* For 12-bit sampling */
674         {
675             u16    *p;
676 
677             p = (u16 *)((u32)address - 382);
678             if ((u32)p < (u32)gMicData)
679             {
680                 p = (u16 *)((u32)p + TEST_BUFFER_SIZE);
681             }
682             DC_InvalidateRange((void *)((u32)p & ~(HW_CACHE_LINE_SIZE - 1)), HW_CACHE_LINE_SIZE);
683             for (i = 0; i < 192; i++)
684             {
685                 gDrawData[i] = (u8)((*p >> 8) & 0x00ff);
686                 p++;
687                 if ((u32)p >= (u32)(gMicData + TEST_BUFFER_SIZE))
688                 {
689                     p = (u16 *)((u32)p - TEST_BUFFER_SIZE);
690                 }
691                 if (((u32)p % HW_CACHE_LINE_SIZE) == 0)
692                 {
693                     DC_InvalidateRange(p, HW_CACHE_LINE_SIZE);
694                 }
695             }
696         }
697         break;
698     }
699 }
700 
701 /*---------------------------------------------------------------------------*
702   Name:         PrintfVariableData
703 
704   Description:  Print-output the variable sampling settings.
705 
706   Arguments:    None.
707 
708   Returns:      None.
709  *---------------------------------------------------------------------------*/
710 static const char* bitRangeString[MIC_SAMPLING_TYPE_MAX] =
711 {
712     "unsigned 8",
713     "unsigned 12",
714     "signed 8",
715     "signed 12",
716     "unsigned 12 (filter off)",
717     "signed 12 (filter off)"
718 };
719 
720 /*---------------------------------------------------------------------------*/
PrintfVariableData(void)721 static void PrintfVariableData(void)
722 {
723     s32     range = 0;
724 
725     OS_Printf(" sampling-rate: ");
726     switch (gMicAutoParam.rate)
727     {
728     case MIC_SAMPLING_RATE_32730:   OS_Printf("32.73kHz");  break;
729     case MIC_SAMPLING_RATE_16360:   OS_Printf("16.36kHz");  break;
730     case MIC_SAMPLING_RATE_10910:   OS_Printf("10.91kHz");  break;
731     case MIC_SAMPLING_RATE_8180:    OS_Printf(" 8.18kHz");  break;
732     case MIC_SAMPLING_RATE_47610:   OS_Printf("47.61kHz");  break;
733     case MIC_SAMPLING_RATE_23810:   OS_Printf("23.81kHz");  break;
734     case MIC_SAMPLING_RATE_15870:   OS_Printf("15.87kHz");  break;
735     case MIC_SAMPLING_RATE_11900:   OS_Printf("11.90kHz");  break;
736     }
737 
738     OS_Printf(" , loop: %s", (gMicAutoParam.loop_enable ? " on" : "off"));
739 
740     OS_Printf(" , bit-range: %s\n",
741             bitRangeString[gMicAutoParam.type % MIC_SAMPLING_TYPE_MAX]);
742 }
743 
744 /*---------------------------------------------------------------------------*
745   Name:         VBlankIntr
746 
747   Description:  V-Blank interrupt vector.
748 
749   Arguments:    None.
750 
751   Returns:      None.
752  *---------------------------------------------------------------------------*/
VBlankIntr(void)753 static void VBlankIntr(void)
754 {
755     /* Sets the IRQ check flag */
756     OS_SetIrqCheckFlag(OS_IE_V_BLANK);
757 }
758 
759 /*---------------------------------------------------------------------------*
760   Name:         Init3D
761 
762   Description:  Initialization for 3D display
763 
764   Arguments:    None.
765 
766   Returns:      None.
767  *---------------------------------------------------------------------------*/
Init3D(void)768 static void Init3D(void)
769 {
770     G3X_Init();
771     G3X_InitMtxStack();
772     GX_SetGraphicsMode(GX_DISPMODE_GRAPHICS, GX_BGMODE_0, GX_BG0_AS_3D);
773     GX_SetVisiblePlane(GX_PLANEMASK_BG0);
774     G2_SetBG0Priority(0);
775     G3X_AlphaTest(FALSE, 0);
776     G3X_AntiAlias(TRUE);
777     G3X_EdgeMarking(FALSE);
778     G3X_SetFog(FALSE, (GXFogBlend)0, (GXFogSlope)0, 0);
779     G3X_SetClearColor(0, 0, 0x7fff, 63, FALSE);
780     G3_ViewPort(0, 0, 255, 191);
781     G3_MtxMode(GX_MTXMODE_POSITION_VECTOR);
782 }
783 
784 /*---------------------------------------------------------------------------*
785   Name:         Draw3D
786 
787   Description:  Displays waveforms in 3D.
788 
789   Arguments:    None.
790 
791   Returns:      None.
792  *---------------------------------------------------------------------------*/
Draw3D(void)793 static void Draw3D(void)
794 {
795     G3X_Reset();
796     G3_Identity();
797     G3_PolygonAttr(GX_LIGHTMASK_NONE, GX_POLYGONMODE_MODULATE, GX_CULL_NONE, 0, 31, 0);
798 
799     {
800         s32     i;
801 
802         if ((gMicAutoParam.type == MIC_SAMPLING_TYPE_SIGNED_8BIT) ||
803             (gMicAutoParam.type == MIC_SAMPLING_TYPE_SIGNED_12BIT) ||
804             (gMicAutoParam.type == MIC_SAMPLING_TYPE_SIGNED_12BIT_FILTER_OFF))
805         {
806             for (i = 0; i < 191; i++)
807             {
808                 DrawLine((s16)((s8)gDrawData[i]),
809                          (s16)i, (s16)((s8)gDrawData[i + 1]), (s16)(i + 1));
810             }
811         }
812         else
813         {
814             for (i = 0; i < 191; i++)
815             {
816                 DrawLine((s16)(gDrawData[i]), (s16)i, (s16)(gDrawData[i + 1]), (s16)(i + 1));
817             }
818         }
819     }
820 
821     G3_SwapBuffers(GX_SORTMODE_AUTO, GX_BUFFERMODE_W);
822 }
823 
824 /*---------------------------------------------------------------------------*
825   Name:         DrawLine
826 
827   Description:  Renders lines with triangular polygons
828 
829   Arguments:    sx:   x coordinate of line's starting point
830                 sy:   y coordinate of line's starting point
831                 ex:   x coordinate of line's ending point
832                 ey:   y coordinate of line's ending point
833 
834   Returns:      None.
835  *---------------------------------------------------------------------------*/
DrawLine(s16 sx,s16 sy,s16 ex,s16 ey)836 static void DrawLine(s16 sx, s16 sy, s16 ex, s16 ey)
837 {
838     fx16    fsx = (fx16)(((sx - 128) * 0x1000) / 128);
839     fx16    fsy = (fx16)(((96 - sy) * 0x1000) / 96);
840     fx16    fex = (fx16)(((ex - 128) * 0x1000) / 128);
841     fx16    fey = (fx16)(((96 - ey) * 0x1000) / 96);
842 
843     G3_Begin(GX_BEGIN_TRIANGLES);
844     {
845         G3_Color(GX_RGB(31, 31, 31));
846         G3_Vtx(fsx, fsy, 0);
847         G3_Color(GX_RGB(31, 31, 31));
848         G3_Vtx(fex, fey, 0);
849         G3_Color(GX_RGB(31, 31, 31));
850         G3_Vtx(fsx, fsy, 1);
851     }
852     G3_End();
853 }
854 
855 /*---------------------------------------------------------------------------*
856   End of file
857  *---------------------------------------------------------------------------*/
858