ADCのExampleは「ADC_SAR_Seq_DieTemp_PSoC4」だ
ADC SAR Seqコンポーネントを使うが、機能がいろいろある(まあまあ設定が複雑)ので
ADCを使う前にこのExampleはやっておいたほうがいいかな?
ADCのコンバート完了は割込みで通知されるので
ADC_SAR_SEQ_IRQ_StartEx()というマクロ関数で割込みハンドラを指定するが
ADC SAR SeqコンポーネントのDATASHEET(ADC_SAR_SEQ_P4_v2_0.pdf)の後ろの方に書いてあるので
Exampleをやっておかないとなかなか分かりずらい
ぴゅんぴゅん2号のコントローラーでテスト
Arduinoベースのぴゅんぴゅん2号用に作ったコントローラー(http://dad8893.blogspot.jp/2014/08/2.html)を使って
POTの読み取りをADCで、プッシュスイッチはDebuncerというチャタリングを除去するコンポーネントがあったのでこれも使ってテストした
PSoC CreatorのTopDesign
ADC SAR SeqコンポーネントのConfigure
ADCの入力をSingle ended(差動入力ではない普通の入力)にすると
「Single ended result format」がグレイアウトして出力値がSignedでしか出力できなくなった
ということは12bitのうち11bitしか使えないので0 - 2048までの値しかとれない
DATASHEET(ADC_SAR_SEQ_P4_v2_0.pdf)をざっと読んだ感じではunsignedで12bitフルには使えなさそうだ
ADCのChannelの個別の設定はChannelsタブで設定
読み取り値はUARTで出力してPCのTeratermで受信した
まあまあきっちり動いてくれているようだ
<main.c>
/* ========================================
*
* Copyright YOUR COMPANY, THE YEAR
* All Rights Reserved
* UNPUBLISHED, LICENSED SOFTWARE.
*
* CONFIDENTIAL AND PROPRIETARY INFORMATION
* WHICH IS THE PROPERTY OF your company.
*
* ========================================
*/
#include <project.h>
#include <stdio.h>
#define CH0_N (0x00u)
#define CH1_N (0x01u)
#define CH2_N (0x02u)
volatile uint32 dataReady = 0u;
volatile int16 result[ADC_SAR_SEQ_TOTAL_CHANNELS_NUM];
volatile int switchCount1 = 0;
volatile int switchCount2 = 0;
/******************************************************************************
* Function Name: ADC_SAR_SEQ_ISR_LOC
*******************************************************************************
*
* Summary:
* Handle Interrupt Service Routine. Source - ADC SAR Seq.
*
******************************************************************************/
CY_ISR(ADC_SAR_SEQ_ISR_LOC)
{
uint32 intr_status;
uint32 range_status;
/* Read interrupt status registers */
intr_status = ADC_SAR_SEQ_SAR_INTR_MASKED_REG;
/* Check for End of Scan interrupt */
if((intr_status & ADC_SAR_SEQ_EOS_MASK) != 0u)
{
/* Read range detect status */
range_status = ADC_SAR_SEQ_SAR_RANGE_INTR_MASKED_REG;
/* Verify that the conversion result met the condition Low_Limit <= Result < High_Limit */
if((range_status & (uint32)(1ul << CH0_N)) != 0u)
{
result[CH0_N] = ADC_SAR_SEQ_GetResult16(CH0_N);
}
if((range_status & (uint32)(1ul << CH1_N)) != 0u)
{
result[CH1_N] = ADC_SAR_SEQ_GetResult16(CH1_N);
}
if((range_status & (uint32)(1ul << CH2_N)) != 0u)
{
result[CH2_N] = ADC_SAR_SEQ_GetResult16(CH2_N);
}
/* Clear range detect status */
ADC_SAR_SEQ_SAR_RANGE_INTR_REG = range_status;
dataReady |= ADC_SAR_SEQ_EOS_MASK;
}
/* Clear handled interrupt */
ADC_SAR_SEQ_SAR_INTR_REG = intr_status;
}
CY_ISR(SW_1_ISR)
{
switchCount1++;
}
CY_ISR(SW_2_ISR)
{
switchCount2++;
}
int main()
{
char uartLine[250];
/* Initialize the UART */
UART_Start();
UART_PutCRLF();
UART_PutCRLF();
UART_PutString("Starting Controller measurement...");
UART_PutCRLF();
/* Init and start sequencing SAR ADC */
ADC_SAR_SEQ_Start();
ADC_SAR_SEQ_StartConvert();
/* Enable interrupt and set interrupt handler to local routine */
ADC_SAR_SEQ_IRQ_StartEx(ADC_SAR_SEQ_ISR_LOC);
SW_1_Int_StartEx(SW_1_ISR);
SW_2_Int_StartEx(SW_2_ISR);
CyGlobalIntEnable;
for(;;)
{
/* When conversion of sequencing channels has completed */
if((dataReady & ADC_SAR_SEQ_EOS_MASK) != 0u)
{
/* Get voltage, measured by ADC */
dataReady &= ~ADC_SAR_SEQ_EOS_MASK;
//res = ADC_SAR_SEQ_CountsTo_mVolts(CH0_N, result[CH0_N]);
/* Print voltage value to UART */
sprintf(
uartLine, "ADC: %4d %4d %4d SW: %d %d",
result[CH0_N], result[CH1_N], result[CH2_N], switchCount1, switchCount2
);
UART_PutString(uartLine);
UART_PutCRLF();
//CyDelay(100);
}
}
}
/* [] END OF FILE */
一瞬はまったのでメモ
PSoC 4 Pionner KitでUARTを使ってPCとシリアル通信させるときは
UART:TXとして指定したPINとJ8 pin 9 (PSoC 5LP P12[6])を
ジャンプワイヤで物理的に接続しないと動かない
0 件のコメント:
コメントを投稿