akira.keiのアイコン画像
akira.kei 2025年01月25日作成 (2025年01月26日更新) © GPL-3.0+
セットアップや使用方法 セットアップや使用方法 Lチカ Lチカ 閲覧数 169
akira.kei 2025年01月25日作成 (2025年01月26日更新) © GPL-3.0+ セットアップや使用方法 セットアップや使用方法 Lチカ Lチカ 閲覧数 169

8ピンPICのPIC16F18313を使う(その3)ついにLチカ

<前の記事 : 次の記事>

LEDの接続はしない

まずは今回の「Lチカ」だが実際にはLEDは接続せず、オシロスコープでピンの電圧をモニタする。このLEDを接続したつもりになるピンの選定だが、電源とPICkit4の通信ライン(ICSP)とリセットで8ピンのうち5ピンを使っているし、動作(速度)モニタのためにCLKOUT(RA4)するので、結局RA2とRA5しか空いてないことになる。
8ピン PIC

Pragma Config

前記事に書いたように PIC16F18313 では多彩な内部クロックが選定できるが、Configuration Wordに対して適切な指定をすれば、main関数に何もクロック関連設定を書かなくてもいい。MPLAB Xの「Production」メニュー内の「Set Configuration Word」を選ぶと、下の方に設定画面が出る。この画面で適切な内容を選択して左側にある「Insert Source Code in Editor」ボタンを押すと、ソースコード内に「#pragma config」ステートメントが挿入される。ヘッダファイルとして「pragma_config.h」を用意してその中にこれを記述するようにした。第一Config Wordは以下のように設定する。

// CONFIG1 #pragma config FEXTOSC = OFF // 外部クロック無効 #pragma config RSTOSC = HFINT1 // 1MHz内部クロック #pragma config CLKOUTEN = ON // RA4にFosc/4を出力 #pragma config CSWEN = OFF // NOSCやNDIV設定無効 #pragma config FCMEN = OFF // Fail-Safe無効

第二Config Wordは以下だ。単純なプログラムでバッテリー駆動しない場合はほとんどの安全機能はOFFでいい。

#pragma config MCLRE = ON // MCLR使用 #pragma config PWRTE = OFF // PowerUp Timer無効 #pragma config WDTE = OFF // Watchdog Timer無効 #pragma config LPBOREN = OFF // Low Power電圧降下リセット無効 #pragma config BOREN = OFF // 電圧降下リセット無効 #pragma config BORV = LOW // (任意) #pragma config PPS1WAY = ON // PPS設定は1度だけ #pragma config STVREN = OFF // スタック溢れリセット無効 #pragma config DEBUG = OFF // デバッグ無効

趣味の電子工作の場合は第三、第四Config Wordは全てOFF指定だ。特にLVPは「常に」ONかOFFにするのかどちらかに決めておいた方がいい。プログラマにLVP専用のSnapを使う場合は常にONだが、PICkitの場合は常にOFFの方がトラブルが少ないように思える。

// CONFIG3 #pragma config WRT = OFF // 書き込みプロテクト無効 #pragma config LVP = OFF // 低電圧プログラムモード無効 // CONFIG4 #pragma config CP = OFF // コードプロテクト無効 #pragma config CPD = OFF // データプロテクト無効

main関数

main関数の冒頭(宣言部)は以下になる。xc8コンパイラ使用なら「xc.h」が必須、Config Wordをまとめたヘッダファイルの指定とdelay関数のための_XTAL_FREQも指定が必要だ。

#include <xc.h> #include "pragma_config.h" #define _XTAL_FREQ 1000000

Lチカとしてのループは以下のようにdelay_ms関数を使った。RA2とRA5にLEDが接続されていると想定して、交互にLEDが光るようにした。ANSELAレジスタはクリアしなくても問題は無いが念のため。トグル機能は関数化しても良い(する必要性は感じないが)。

void main(void) { unsigned char flg=1; ANSELA=0; TRISAbits.TRISA2=0; TRISAbits.TRISA5=0; while(1) { if(flg) { LATAbits.LATA2=1; LATAbits.LATA5=0; } else { LATAbits.LATA2=0; LATAbits.LATA5=1; } flg=1-flg; __delay_ms(500); } }

上(黄色)がRA2、下(水色)がRA5であり交互に50%デューティ1Hz周期で点滅する。
Lチカ

ただ実際にはこういう点滅はプログラム制御ではなく、ハードウェア(タイマー)を使った方が頭が良さそうだ。

いやちょっと待てよ…

どうせdelay関数を使うならトグル動作は要らなかったなw フラグを排除してループ内に展開し、遅延時間(us_tmp)を調整したら、きちんと1Hz周期で点滅出来た。OSCTUNEで微調整すればかなり良いところまで行けそう。

#include <xc.h> #include "pragma_config.h" #define _XTAL_FREQ 1000000 #define us_tmp 986 void main(void) { ANSELA=0; TRISAbits.TRISA2=0; TRISAbits.TRISA5=0; while(1) { LATAbits.LATA2=1; LATAbits.LATA5=0; __delay_ms(499); __delay_us(us_tmp); LATAbits.LATA2=0; LATAbits.LATA5=1; __delay_ms(499); __delay_us(us_tmp); } }
1
akira.keiのアイコン画像
機械系エンジニアだが電子工作を趣味としている。週末はひとりバーベキュー。
ログインしてコメントを投稿する