UMEHOSHI ITA TOP PAGE COMPUTER SHIEN LAB
#ifndef _MY_SYS_H /* Guard against multiple inclusion */ #define _MY_SYS_H #include "my_beep.h" extern int core_once_count1_val; // 0になるまでコアタイマでダウンカウント extern int core_once_count2_val; extern int core_once_count3_val; void init_main(); void init_interrupt(); #endif /* _MY_SYS_H */
/*
* ウメ・エディット・プログラム実現用のシステム部分
* 起動関連の処理
* タイマ関連 割り込み関連の初期指定
* PWMの初期化ルーチン
* ADコンバータの初期化ルーチン
*/
#include <xc.h>
#include <stdio.h>
#include <proc/p32mx270f256b.h>
#include "my_app.h"
#include "my_usb_cmd.h"
#include "my_adc.h"
#include "my_uart.h"
#include "my_sys.h"
#include "common.h"
/*****************************************************
* グローバル変数
****************************************************/
unsigned int temp;// デバック確認用
// ESP32-WROOM-32Dの起動時のメッセージ出力を止める細工を20201005に追加
int core_once_count1_val = 880; // 0になるまでコアタイマでダウンカウント(1秒)
int core_once_count2_val = 1760; // 0になるまでコアタイマでダウンカウント(2秒)
int core_once_count3_val = 2640; // 0になるまでコアタイマでダウンカウント(3秒)
int core_once_count4_val = 3520; // 0になるまでコアタイマでダウンカウント(4秒)
// 割り込みルーチンとウメシステム情報のテーブル
void (*handlers_table[(0x1000>>2)-4])(void) __attribute__ (( persistent, address(_PTR_HANDLERS) ));
// RAMのプログラミングや情報記憶域領域
char ram_area1[0x3000] __attribute__ (( persistent, address(_PTR_RAM_AREA1) ));
char ram_area2[0x1000] __attribute__ (( persistent, address(_PTR_RAM_AREA2) ));
char ram_area3[0x0F00] __attribute__ (( persistent, address(_PTR_RAM_AREA3) ));
// 割り込みルーチンとウメシステム情報のテーブルの先頭ポインタ
void (**handlers)(void)= (void (**)(void) )handlers_table;
static int led_D1=0;//LED D1の初期値
int power_on_flag = 0; // パワーオンリセットで1、リセット時は0 追加[2023-4]
/* =============================================================================
* main内部の最初に呼ばれる。( SYS_Initialize ( NULL );の前で呼ばれる)
* =============================================================================
*/
void init_main()
{
//ANSELB:指定ビット0にするとデジタル、1でアナログ(デフォルト)として使う。
ANSELBCLR = 0x0000E3BC; //15,14,13,9,8,7,5,4,3,2を0にする。
// 1110 0011 1011 1100
ANSELBCLR = ~0x00000DB3; // 0への指定ビットをデジタルとして使う
ODCB = 0x0; // オープンドレインを使わない。
// TRISB 1にすると入力、0にすると出力
TRISBCLR = 0x0000E22C; // 出力指定 1110 0010 0010 1100
TRISBSET = 0x00000190;// 入力指定 0000 0001 1001 0000
// CPU 命令アクセスバスエラービット バスエラー例外を無効にする
((__BMXCONbits_t *)& BMXCON )->BMXERRIS = 0;
// バスマトリクス調停モードビット モード0
((__BMXCONbits_t *)& BMXCON )->BMXARB = 0;
// メモリ構成の設定 「0x80004000」?をプログラミング用に使う
BMXDKPBA = 0x00004000;//16 KB のカーネルデータ 「0x80004000」
BMXDUDBA = BMXDKPBA+0x0000C000;//48 KB のカーネルプログラム
BMXDUPBA = BMXDUDBA;//ユーザデータのサイズ = 0、ユーザプログラムのサイズ = 0
// メモリ構成の設定はここまで
extern void init_handle_area ();//ハンドラ・テーブル と ユー・ラム・エリア 初期用
// このソースの最後で、「ウメ・エディットプログラム」インターフェイス用に定義!)
init_handle_area (); // ハンドラ・テーブル と ユー・ラム・エリア 初期
// (各種インターフェイス用記憶域、割込みテーブルの初期化などが初期化)
}
/*******************************************************************************
*
* 各割込みのサンプル関数
*
******************************************************************************/
void dummy_function() { }// ダミー関数
void dummy_init_function() {// handlers[_IDX_INIT_SUB_FUNC]デフォルト値
_RB15 = led_D1; // D1 LED の初期設定
asm("NOP");
}// ダミー関数
volatile unsigned int core_wait_down_count __attribute__((section("sfrs")));
//uint8_t core_wait_down_count;//割り込みで変更される変数は、上記の宣言が必要
// 上記を使った待機関数(コアタイマの割り込みでカウントされる変数を利用して待機する。)
void core_wait(int cnt0){
if(core_wait_down_count == 0){
core_wait_down_count= cnt0;
}
while(core_wait_down_count > 0){
}
}
// onに変化してからn回連続onが続いた時に1を、そうでなければ0を返す。
// また、それを記憶する変数(押し続けても、1回しかtrueにならない分、少し遅れる)
static int switch2 = 0;
int is_on_sw2(int n){ // default コアタイマで呼び出している。
static int push = 0;
static int cnt = 0;
push = (PORTB & 0x80) == 0;
if( switch2 != push ){
cnt++;
} else {
cnt = 0;
}
if(cnt == n) {
switch2 = push;//しっかり変化したと判断(n回分の遅れが生じる)
return switch2;
}
return switch2;
}
// SW2の状態を返すグローバル関数 (押すと1になる)●
int get_switch2_state(){
return switch2;
}
void core_timer_sub_1()// 初期サンプルのビープ振動処理, SW2チェック--------------
{
// 起動時時SW2操作の分岐や、ESP32-WROOM-32Dの起動時のメッセージ出力を止める細工
if(core_once_count1_val != 0) core_once_count1_val--;
if(core_once_count2_val != 0) core_once_count2_val--;
if(core_once_count3_val != 0) core_once_count3_val--;
if(core_once_count4_val != 0) core_once_count4_val--;
if(core_wait_down_count != 0) core_wait_down_count--;
//別途に1秒時にUART受信あれば、UARTへ改行を送信して2秒間のUART受信を無視している
if(core_once_count3_val==1){//3秒のタイミングで1回だけ実行
U1STAbits.OERR = 0;
if( _RB7 == 0 || _UME_THROUGH_MODE){//約2秒後の瞬間
// _RB7 がLow(SW2が押されていいる)または、スルーモード指定がある?
//_RB15 = ! _RB15;// // D1 LED 反転 (点燈から消灯へ)
_RB15 = 0; // :202503 (消灯へ)
asm("NOP");
// UARTスルーモードへ移行
handlers[_IDX_MY_APP_TASKS] = (void *)My_APP_Tasks_Through;
APP_State_Reset();
init_outBuffers(); //USB出力用リングバッファ関連変数 の初期化
ringbuf_reset(&uartSndBuf);
ringbuf_reset(&uartRecBuf);
clear_beep_code();
// 下記のフロー制御を使うとESP32-WROOM-32Dのesptool.pyが使えない
//U1MODEbits.RTSMD = 0; // UxRTS ピンモード選択をフロー制御モード
//U1MODEbits.UEN = 2;//UxTX、UxRX、UxCTS、UxRTS ピンを有効にして使う
}
}
if(core_once_count4_val==1 && _RB7 == 0){//_RB7 がLow(SW2が押されていいる)
// UART のコマンドモードへ移行
//_RB15 = ! _RB15;// // D1 LED 反転 (点燈から消灯へ)
_RB15 = 0; // :202503 (消灯へ)
asm("NOP");
handlers[_IDX_MY_APP_TASKS] = (void *)My_APP_Tasks;
init_outBuffers(); //USB出力用リングバッファ関連変数 の初期化
handlers[_IDX_DEF_POLLS_UART] = handlers[_IDX_CMD_POLLS_UART];
// RN42のプログラム転送で、下記のフロー制御が必要
U1MODEbits.RTSMD = 0; // UxRTS ピンモード選択をフロー制御モード
U1MODEbits.UEN = 2;//UxTX、UxRX、UxCTS、UxRTS ピンを有効にして使う
}
void base_beep();// この関数内部で、ブザーの振動のON/OFF制御をしている。
base_beep();// ビープ音の音色(グローバル変数beep_onでブザーをON、OFFしている。)
void beep_code_switching();// グローバル変数beep_onを変更してON/OFF指示
beep_code_switching();// 4bitコードを音にする。 (初期は440Hzビープ)
int is_on_sw2(int n);
is_on_sw2(50); // スイッチ SW2の監視関数
//temp = get_switch2_state(); //SW2の状態取得可能。
}
// コアタイマーサンプル関数-------------------------------------------------------
void core_timer_umeFunc_1(){
unsigned long ct_count = _CP0_GET_COUNT();
unsigned long period = _UM_CP0_SET_COMPARE;
handlers[_IDX_CORE_TIMER_SUB_FUNC](); // 上記core_timer_sub_1()がデフォルト.
// update the Compare period
period += ct_count;
_CP0_SET_COMPARE(period);
IFS0CLR = _IFS0_CTIF_MASK; // 割り込み要求フラグをクリア
}
// Timer1 の割り込みから呼びだされるサンプル関数----------------------------------
void timer1_umeFunc1_1(){
IFS0CLR = 0x00000010; // Clear the timer interrupt status flag
void beep_cycle_switching();
beep_cycle_switching(); // サウンド再生時の音の長さ制御がデフォルト
}
// Timer2 の割り込みから呼びだされるサンプル関数----------------------------------
void timer2_umeFunc1_1(){
IFS0CLR = 0x00000200; // Clear the timer interrupt status flag
}
// 各コンペアの割り込み関数
void compare5_umeFunc(){
IFS0CLR= _IFS0_OC5IF_MASK; // Clear the OC5 interrupt flag
}
void compare1_umeFunc(){
IFS0CLR= _IFS0_OC1IF_MASK; // Clear the OC1 interrupt flag
}
void compare3_umeFunc(){
IFS0CLR= _IFS0_OC3IF_MASK; // Clear the OC3 interrupt flag
}
void compare4_umeFunc(){
IFS0CLR= _IFS0_OC4IF_MASK; // Clear the OC4 interrupt flag
}
// Timer4 の割り込みから呼びだされるサンプル関数---------------------------------
void timer4_sample()//デファオルと0.05ミリ秒
{
static int count=0;
if(++count == 10000){//0.5秒ごと
_RB15 = ! _RB15;//点滅周期:1秒.
count = 0;
}
}
// Timer5 の割り込みから呼びだされるサンプル関数---------------------------------
void timer5_sample()//デファオルと0.05ミリ秒
{
static int count=0;
if(++count == 10000){//0.5秒ごと
_RB15 = ! _RB15;//点滅周期:1秒.
count = 0;
}
}
/*******************************************************************************
*
* 割込みの初期化関数
*
******************************************************************************/
// コアタイマーサンプル用初期化---------------------------------------------------
void init_core_timer_1(){
_CP0_SET_COUNT(0);//コアタイマを0にセット(CP0の9番レジスタ)
_CP0_SET_COMPARE(_UM_CP0_SET_COMPARE);// コンペアレジスタに値設定(コアタイマがそれに達すると割り込み)
_CP0_BIC_DEBUG(_CP0_DEBUG_COUNTDM_MASK);// halt core timer and program at a debug breakpoint
IFS0CLR = _IFS0_CTIF_MASK;// clear core timer interrupt flag
IPC0SET = (7 << _IPC0_CTIP_POSITION);// set core time interrupt priority of 7
IPC0SET = (3 << _IPC0_CTIS_POSITION);// set core time interrupt subpriority of 0
IEC0CLR = _IEC0_CTIE_MASK;
IEC0SET = (1 << _IEC0_CTIE_POSITION);// enable core timer interrupt
IEC0CLR = _IEC0_CTIE_MASK;// disable interrupt
IEC0SET = _IEC0_CTIE_MASK; // Enable(割込み許可)
}
// Timer1 の初期化 -----デフォルトで音符の長さ指定に使用---------------------------
void init_timer_1(){
T1CON =0x00000000;//typeA,16bit, [1:1プリスケール
TMR1=0x00000000; //16bitタイマの設定値(レジスタがカウントアップ)
PR1=20000-1; // 0.0005 = 200000*(1/40e6) -1これは約0.5ミリ秒
IPC1SET = 0x0000000C; // Set priority level = 3
IPC1SET = 0x00000001; // Set sub-priority level = 1
IFS0CLR = 0x00000010; // Clear the timer interrupt status flag
IEC0SET = 0x00000010;//T1IE Timer1 Enable(割込み許可)
//T1CONSET =0x8000; // Start timer1
}
// Timer2 の初期化 ------デフォルトでPWMのタイミングカウンターに使用----------------
void init_timer_2(){
T2CONbits.ON = 0;// typeBでON
T2CONbits.SIDL = 0;// デバイスがアイドルモードに移行しても動作を継続する
T2CONbits.TGATE = 0;// ゲート時間積算を無効にする
T2CONbits.TCKPS = 0;// タイマ入力クロック [1:1]プリスケール値
// TCKPS 3bit:111
T2CONbits.T32 = 0;//TMRxとTMRyは別々の16ビットタイマを構成する
T2CONbits.TCS = 0;//内部の周辺モジュール用クロック
T2CON =0x00000000;//typeB,16bit, [1:1]プリスケール
//T2CON =0x00000070;//typeB,16bit, [1:256]プリスケール
TMR2=0x0000; //16bitタイマの設定値(レジスタがカウントアップ)
PR2=0x0FFFF; //16bit周期レジスタビット設定
IPC2SET = 0x0000000C; // Set priority level = 3
IPC2SET = 0x00000001; // Set sub-priority level = 1
IFS0CLR = 0x00000200; // Clear the timer interrupt status flag
IEC0SET = 0x00000200;//T2IE Timer2 Enable(割込み許可)
//T2CONSET =0x8000; // Start timer2
}
//モータ用パルス幅変調モードの初期設定(PWM の設定)
void init_compare()// IDX_INIT_PWD
{
//CN6(左側)前方向デューティ比用Output Compare Output5 の設定
RPB2Rbits.RPB2R = 0x6; // RB2をOC5の出力にする。
OC5CONbits.SIDL = 0; // アイドルモード中も動作を継続する
OC5CONbits.OC32 = 0; //OCxR<15:0> およびOCxRS<15:0> を使って16 ビットタイマ源と比較する
OC5CONbits.OCTSEL = 0; // Timer2 をこの出力コンペア モジュールのクロック源として使う
OC5CONbits.OCM = 6; // OC1 をPWM モードにし、フォルトピンを無効にする
IPC5bits.OC5IP = 5;// Set OC1 interrupt priority to 5
IPC5bits.OC5IS = 2;// Set Subpriority to 3, maximum
IFS0CLR= _IFS0_OC5IF_MASK; // Clear the OC5 interrupt flag
//IEC0SET= _IEC0_OC5IE_MASK; // Enable Interrupt
//CN6(左側)後ろ方向デューティ比用Output Compare Output1 の設定
RPB3Rbits.RPB3R = 0x5; // RB3をOC1の出力にする
OC1CONbits.SIDL = 0; // アイドルモード中も動作を継続する
OC1CONbits.OC32 = 0; //OCxR<15:0> およびOCxRS<15:0> を使って16 ビットタイマ源と比較する
OC1CONbits.OCTSEL = 0; // Timer2 をこの出力コンペア モジュールのクロック源として使う
OC1CONbits.OCM = 6; // OC1 をPWM モードにし、フォルトピンを無効にする
IPC1bits.OC1IP = 5;// Set OC1 interrupt priority to 5
IPC1bits.OC1IS = 2;// Set Subpriority to 3, maximum
IFS0CLR= _IFS0_OC1IF_MASK; // Clear the OC1 interrupt
//IEC0SET= _IEC0_OC1IE_MASK; // Enable Interrupt
//CN7(右側)前方向デューティ比用Output Compare Output4 の設定
RPB13Rbits.RPB13R = 0x5; // RB13をOC4の出力にする。
OC4CONbits.SIDL = 0; // アイドルモード中も動作を継続する
OC4CONbits.OC32 = 0; //OCxR<15:0> およびOCxRS<15:0> を使って16 ビットタイマ源と比較する
OC4CONbits.OCTSEL = 0; // Timer2 をこの出力コンペア モジュールのクロック源として使う
OC4CONbits.OCM = 6; // OC1 をPWM モードにし、フォルトピンを無効にする
IPC4bits.OC4IP = 5;// Set OC1 interrupt priority to 5
IPC4bits.OC4IS = 2;// Set Subpriority to 3, maximum
IFS0CLR= _IFS0_OC3IF_MASK; // Clear the OC3 interrupt
//IEC0SET= _IEC0_OC3IE_MASK; // Enable Interrupt
//CN7(右側)後ろ方向デューティ比用Output Compare Output3 の設定
RPB14Rbits.RPB14R = 0x5; // RB14をOC3の出力にする。
OC3CONbits.SIDL = 0; // アイドルモード中も動作を継続する
OC3CONbits.OC32 = 0; //OCxR<15:0> およびOCxRS<15:0> を使って16 ビットタイマ源と比較する
OC3CONbits.OCTSEL = 0; // Timer2 をこの出力コンペア モジュールのクロック源として使う
OC3CONbits.OCM = 6; // OC1 をPWM モードにし、フォルトピンを無効にする
IPC3bits.OC3IP = 5;// Set OC1 interrupt priority to 5
IPC3bits.OC3IS = 2;// Set Subpriority to 3, maximum
IFS0CLR= _IFS0_OC4IF_MASK; // Clear the OC4 interrupt flag
//IEC0SET= _IEC0_OC4IE_MASK; // Enable Interrupt
OC5R = 0;//_UME_CN6_OC5R;//0;//出力コンペアx コンペアレジスタ・・
OC5RS = _UME_CN6_OC5RS;//出力コンペアx セカンダリコンペアレジスタ設定用(デューティー比 )
OC1R = 0;//_UME_CN6_OC1R;//出力コンペアx コンペアレジスタ・・
OC1RS = _UME_CN6_OC1RS;//出力コンペアx セカンダリコンペアレジスタ設定用(デューティー比 )
OC4R = 0;//_UME_CN7_OC4R;//0;//出力コンペアx コンペアレジスタ・・
OC4RS = _UME_CN7_OC4RS;//出力コンペアx セカンダリコンペアレジスタ設定用(デューティー比 )
OC3R = 0;//_UME_CN7_OC3R;//0;//出力コンペアx コンペアレジスタ・・
OC3RS = _UME_CN7_OC3RS;//出力コンペアx セカンダリコンペアレジスタ設定用(デューティー比 )
//各出力コンペア モジュールを有効にする
OC5CONbits.ON = 1; // RB2のOC5の出力をON(CN6の前方向)
OC1CONbits.ON = 1; // RB3のOC1の出力をON(CN6の後ろ方向)
OC4CONbits.ON = 1; // RB13のOC4の出力をON(CN7の前方向)
OC3CONbits.ON = 1; // RB14のOC3の出力をON(CN7の後ろ方向)
}
// 現在未使用( PWM を使わないでモータを前進させる初期化)
void init_not_compare(){
// ビット操作命令をポートに対して行う場合、ポートから全ての bit を読み出し、
// 指定のビットをセットしてから、ポートに書き戻す。
// その直後にビット操作命令がきた場合、ポートに書き戻したデータが確定しない
// まま読み出しが起こり、ビットが反転する可能性がある。よって間にNOPを追加する。
OC5CONbits.ON = 0; // RB2のOC5の出力をON(CN6)
OC1CONbits.ON = 0; // RB3のOC1の出力をON(CN6)
OC4CONbits.ON = 0; // RB13のOC4の出力をON(CN7)
OC3CONbits.ON = 0; // RB14のOC3の出力をON(CN7)
_RB2 = 0;// CN6 1-2
__asm__("NOP");
_RB3 = 0;// CN6 3-4
asm("NOP");
_RB14 = 0;// CN7 1-2
asm("NOP");
_RB13 = 0;// CN7 3-4
// 上記でNOPをなくすと、上記は動作しなかった。
// 上記は、下記のように作る方が良い。
PORTBCLR = 0x600c;//0b0110 0000 0000 1100;
//PORTBSET = 0x2004;//0b0010 0000 0000 0100;
}
// Timer4,5 の初期化 -------------------------------------------------------------
void init_timer_4_5(){
// ---- Timer4を使う指定 ここから
T4CON =0x00000000;//typeB,16bit, [1:1]プリスケール
TMR4=0x00000000; //16bitタイマの設定値(レジスタがカウントアップ)
PR4=1999; // =0.0005/(1/40e6)-1 これは0.05ミリ秒
IPC4bits.T4IP = 6; // Set priority level = 6(2番に大きな優先度)
IPC4bits.T4IS = 0;// Set sub-priority level = 3(最大値)
IFS0bits.T4IF = 0;// Clear the timer interrupt status flag
IEC0bits.T4IE = 1;// Timer4 Enable(割込み許可)
//T4CONbits.ON = 1;// Start timer4
// ---- Timer4を使う指定 ここまで
// ---- Timer5を使う指定 ここから
T5CON =0x00000000;//typeB,16bit, [1:1]プリスケール
TMR5=0x00000000; //16bitタイマの設定値(レジスタがカウントアップ)
PR5=2000-1; // =0.0005/(1/40e6) -1これは約0.05ミリ秒
IPC5bits.T5IP = 1; // Set priority level = 1(最小値)
IPC5bits.T5IS = 3;// Set sub-priority level = 0(最小値)
IFS0bits.T5IF = 0;// Clear the timer interrupt status flag
IEC0bits.T5IE = 1;// Timer5 Enable(割込み許可)
//T5CONbits.ON = 1;// Start timer5
// ---- Timer5を使う指定 ここまで
}
// CN6 CN7 をPWMモードで使うかの切り替え
void set_pwd_mode(int flag){
if(flag){
handlers[_IDX_INIT_COMPARE] = init_compare; // PWM 関連の初期化
} else {
handlers[_IDX_INIT_COMPARE] = init_not_compare;// PWM を使わない設定
}
handlers[_IDX_INIT_COMPARE]();
}
/* =============================================================================
* 割り込みハンドラなどの初期化ルーチンをまとめた関数
* main()関数内のループ直前で呼ばれる。(SYS_Initialize ( NULL );の後で呼ばれる。))
*/
void init_interrupt()
{
//コアタイマに関する初期化 init_core_timer_1();のような処理が登録が実行される。
handlers[_IDX_INIT_CORE_TIMER]();
// Timer1 初期化
handlers[_IDX_INIT_TIMER_1]();
// Timer2 初期化 PWD の周期設定
handlers[_IDX_INIT_TIMER_2]();// init_timer_2();
// モータなどで使うPWMなど Output Compare Outputの初期化
_init_compare(); //handlers[_IDX_INIT_COMPARE]();
// Timer3、ADC 初期化
handlers[_IDX_INIT_ADC_1]();
handlers[_IDX_INIT_TIMER_3]();
// Timer4,5 初期化
handlers[_IDX_INIT_TIMER_4_5]();
// UART1 の設定init_uart()
handlers[_IDX_INIT_UART1]();
_RB9 = 0; // RTS(Request to Send (送信要求) ) の出力端子
asm("nop");
_RB8 = 0; // CTS(Clear to Send (送信可) ) の入力端子
asm("nop");
// 以下を1にすると、スルーモードで起動する。
_UME_THROUGH_MODE = 0;
//_UME_THROUGH_MODE = 1;// 実験の為スルーモード指定
//(ESP32-WROOM-32D取り付け時,上記設定でSW2を押す操作を押さないと、Basicが起動 )
// PB2にクロックを出力させて、周波数測定する時の設定
// RPB2Rbits.RPB2R=0x07;// PB2を REFCLKO (50000Hz)に、ピン割り当てする。
// REFOCONbits.OE = 1; // REFERENCE OSCILLATOR CONTROL REGISTER
if( power_on_flag == 1){//追加[2023-4]
power_on_start();//追加[2023-4]
}
else //追加[2023-4]-----以下から
{ // パワーオンでない場合(リセット)で実行する関数
void (* func)(void) = (void *) 0x9D020000;
if( *((uint32_t *)func) != 0xffffffff ){// EEPROMの記憶内容が0xffでない?
func();
}
} //追加[2023-4]-----以上までから
//UMEHOSHI ITA アプリ用「初期ルーチン」デフォルトでは dummy_init_function関数
_init_sub_func(); // handlers[_IDX_INIT_SUB_FUNC]の実行
} // end of void init_interrupt()
// main()関数内のループ直前で呼ばれる。(SYS_Initialize ( NULL );の後で呼ばれる。))
/* =============================================================================
* 割り込みハンドラ
* =============================================================================
/*
* 優先度が同じで副優先度がより高い割り込みが発生しても、
* サービス中の副優先度の低い割り込みは保留されません。
* しかし、同じ優先度を持つ2つの割り込みが保留中である場合、
* 副優先度が高い方の割り込みが先に処理されます
*/
// ------ コアタイマの割込みベクタの定義
// (下記のIPL7SOFTが優先度で、このソースでは、「IPC0SET」の設定と連動が必要な設定)
void __ISR(_CORE_TIMER_VECTOR, IPL7SOFT) CTInterruptHandler(void)
{ // システムクロック2つで、1カウントするカウンターが使われる。
handlers[_IDX_CORE_TIMER_FUNC](); // デフォルトは440Hzのビープスイッチング
}
void __ISR(_TIMER_1_VECTOR,IPL3SOFT)Timer1Handler(void)
{
handlers[_IDX_TIMER_1_FUNC](); // 音符長制御
}
void __ISR(_TIMER_2_VECTOR,IPL3SOFT)Timer2Handler(void)
{
//UMEHOSHI ITA アプリ用Timer2ルーチン デフォルトでは dummy関数がセット
handlers[_IDX_TIMER_2_FUNC]();
}
// RB5 CN6[1-2]
void __ISR(_OUTPUT_COMPARE_5_VECTOR, IPL5SOFT) OC5_IntHandler (void)
{
// コンペア割り込み OC5用
handlers[_IDX_COMPARE_5_FUNC]();
}
// RB3 CN6[3-4]
void __ISR(_OUTPUT_COMPARE_1_VECTOR, IPL5SOFT) OC1_IntHandler (void)
{
handlers[_IDX_COMPARE_1_FUNC]();
}
// RB14 CN7[1-2]
void __ISR(_OUTPUT_COMPARE_3_VECTOR, IPL5SOFT) OC3_IntHandler (void)
{
handlers[_IDX_COMPARE_3_FUNC]();
}
// RB13[3-4]
void __ISR(_OUTPUT_COMPARE_4_VECTOR, IPL5SOFT) OC4_IntHandler (void)
{
handlers[_IDX_COMPARE_4_FUNC]();
}
void __ISR(_TIMER_3_VECTOR,IPL6SOFT)Timer3Handler(void)
{
((void (*)(struct ADC_BUFF*))handlers[_IDX_TIMER_3_FUNC])(p_buff);
}
void __ISR(_ADC_VECTOR,IPL7SOFT)ADC1Handler(void)
{
((void (*)(struct ADC_BUFF*))handlers[_IDX_ADC_1_FUNC])( p_buff );
}
void __ISR(_TIMER_4_VECTOR, IPL6SOFT) Timer4Handler(void)
{
IFS0bits.T4IF = 0; // Clear the OC4 interrupt flag(この設定は次の割込みを可能にする).
handlers[_IDX_TIMER_4_FUNC](); //timer4_sample()//デファオルと0.05ミリ秒
}
void __ISR(_TIMER_5_VECTOR, IPL1SOFT) Timer5Handler(void)
{
IFS0bits.T5IF = 0; // Clear the OC5 interrupt flag(この設定は次の割込みを可能にする)
handlers[_IDX_TIMER_5_FUNC](); // timer5_sample()//デファオルと0.05ミリ秒
}
// _TIMER_45_VECTOR と_TIMER_5_VECTOR は同じ20の番号になっているので、下記を定義するとエラー
//void __ISR(_TIMER_45_VECTOR, IPL7SOFT) Timer45Handler(void)
//{
// IFS0bits.T5IF = 0; // Clear the OC5 interrupt flag(この設定は次の割込みを可能にする)
// handlers[_IDX_TIMER_5_FUNC](); // timer5_sample()//デファオルと0.05ミリ秒
//}
/* =============================================================================
* 起動時(リセット)直後に実行する。
* ウメ・エディット・プログラムを実現するハンドラの初期化
* 各種インターフェイス用記憶域、割込みテーブルの初期化
* =============================================================================
*/
//void init_handlers (){//以前
void init_handle_area ()
{
__RCONbits_t *rcon = (__RCONbits_t*) & RCON;//RCON: リセット制御レジスタ
uint32_t t32 = (uint32_t) handlers;// 0xA0004000が記憶
temp = sizeof(handlers[0]);//4が記憶
temp = sizeof(handlers);//4が記憶
t32 = (uint32_t) ram_area1;// 0xA0005000が記憶
temp = sizeof(ram_area1);//0x3000がセット
ram_area1[sizeof(ram_area1)-1]=0;//←これを行わないと、ram_area1領域ができない。
ram_area2[sizeof(ram_area2)-1]=0;
ram_area3[sizeof(ram_area3)-1]=0;
led_D1 = 0; // D1 LED の初期点灯の予約
// EEPROM操作関連 追加[2023-4]
handlers[_IDX_NVM_ERASE_PAGE]=(void *)NVM_erase_page;
handlers[_IDX_NVM_WRITE_WORD]=(void *)NVM_write_word;
extern int reply_boot_message_status;
reply_boot_message_status = 0;// :202503 追加
// パワーONに関係なく初期化できる上記へ移動 :202503
core_once_count1_val = 880; // 0になるまでコアタイマでダウンカウント(1秒)
core_once_count2_val = 1760; // 0になるまでコアタイマでダウンカウント(2秒)
core_once_count3_val = 2640; // 0になるまでコアタイマでダウンカウント(3秒)
core_once_count4_val = 3520; // 0になるまでコアタイマでダウンカウント(4秒)
// 上記4秒指定を追加:202503
if (_RB7 == 0 || rcon->POR == 1) {//パワーオン時(リセット無関係)処理=======
// SW2 (RB7)が押されている。または、パワーオン リセットが発生
// (リセットだけでは実行しない処理)
// 起動時(リセット)直後でSW2を押すことでも実行。
extern bool usb_recieved_flag;// :202503 追加( treuでUSBに送信可能状態)
usb_recieved_flag = false;//一度でもUSBから受信があったら true
// パワーONに関係なく初期化できる上記へ移動 :202503
//core_once_count1_val = 880; // 0になるまでコアタイマでダウンカウント(1秒)
//core_once_count2_val = 1760; // 0になるまでコアタイマでダウンカウント(2秒)
//core_once_count3_val = 2640; // 0になるまでコアタイマでダウンカウント(3秒)
//core_once_count4_val = 3520; // 0になるまでコアタイマでダウンカウント(4秒)
// コア・タイマーの初期化
handlers[_IDX_INIT_CORE_TIMER] = init_core_timer_1;
handlers[_IDX_CORE_TIMER_FUNC] = core_timer_umeFunc_1;//コア・タイマー処理
_UM_CP0_SET_COMPARE = 22727u;//1/40e6*22727*2=0.00113635秒周期(440Hzブザー用)
handlers[_IDX_CORE_TIMER_SUB_FUNC] = core_timer_sub_1;
// スイッチ SW2 状態取得 ---------------------------------------------------
handlers[_IDX_SWITCH2_STATE] = (void (*)(void) ) get_switch2_state;
handlers[_IDX_CORE_WAIT] = (void (*)(void) ) core_wait;
handlers[_IDX_EXTERNAL_0_VECTOR]= dummy_function; // INT0用 20240313追加
handlers[_IDX_OUTPUT_COMPARE_2_VECTOR]= dummy_function; // OC20用 20240313追加
extern void set_int_var(int specified_id, int value);
handlers[_IDX_SET_INT_VAR]= (void *)set_int_var; // :202503 追加
_UME_THROUGH_MODE = 0; // スルーモード
_UME_USB_CDC_DATE = 115200;//USB のボーレート
// BEEP関連
extern uint8_t my_beep_area[];
_UM_PTR_BEEP_AREA = my_beep_area;
_UM_PTR_GOTO_BEEP = my_beep_area;
// Timer関連
handlers[_IDX_TIMER_1_FUNC] = timer1_umeFunc1_1;//TIMER1
handlers[_IDX_INIT_TIMER_1] = init_timer_1;
handlers[_IDX_TIMER_4_FUNC] = timer4_sample;
handlers[_IDX_TIMER_5_FUNC] = timer5_sample;
handlers[_IDX_INIT_TIMER_4_5] = init_timer_4_5;
//_HANDLES[_IDX_INIT_TIMER_4_5] = init_timer_4_5;
// compare関連
handlers[_IDX_COMPARE_1_FUNC] =compare1_umeFunc;
handlers[_IDX_COMPARE_3_FUNC] =compare3_umeFunc;
handlers[_IDX_COMPARE_4_FUNC] =compare4_umeFunc;
handlers[_IDX_COMPARE_5_FUNC] =compare5_umeFunc;
// PWM関連の初期設定 & Timer2
//_UME_CN6_OC5R = 0;
_UME_CN6_OC5RS = 0;//0x0ffff; // CN6 PWM 前方向へのデューティー比
//_UME_CN6_OC1R =0;
_UME_CN6_OC1RS = 0; // CN6 PWM 後ろ方向へのデューティー比
//_UME_CN7_OC4R = 0;
_UME_CN7_OC4RS = 0;//0x0ffff; // CN7 PWM 前方向へのデューティー比
//_UME_CN7_OC3R = 0;
_UME_CN7_OC3RS = 0x00; // CN7 PWM 前方向へのデューティー比
handlers[_IDX_TIMER_2_FUNC] = timer2_umeFunc1_1;
handlers[_IDX_INIT_TIMER_2] = init_timer_2;
handlers[_IDX_INIT_COMPARE] = init_not_compare;// PWM を使わない設定
//handlers[_IDX_INIT_COMPARE] = init_compare; // PWM 関連の初期化
_UME_CONFIG = 0x0006; // BEEP デフォルトON, エラーBEEP通知ON
// ADC関連 & Timer3
handlers[_IDX_ADC_1_FUNC] = adc_umeFunc1_1;
handlers[_IDX_INIT_ADC_1] = init_adc;
handlers[_IDX_TIMER_3_FUNC] = (void *)adc_usb_out;
handlers[_IDX_INIT_TIMER_3] = init_timer_3;
handlers[_IDX_ENCODE_ADC_BUFF] = (void *)encode_adc_buff;
// UART1 関連
handlers[_IDX_INIT_UART1] = init_uart;
handlers[_IDX_RECV_UART1] = (void *)recv_uart1;
handlers[_IDX_SEND_UART1] = (void *)send_uart1;
handlers[_IDX_MY_APP_TASKS] = (void *)My_APP_Tasks;
handlers[_IDX_DEF_POLLS_UART] = (void *)recive_and_send_uart_with_polling;
handlers[_IDX_CMD_POLLS_UART] = (void *)uart_cmd_mode_polling;
handlers[_IDX_ISR_POLLS_UART] = (void *)uart_isr_buff_polling;
// この関数内の最後で実行する「_handls_user_set_func()」の初期化
handlers[_IDX_HANDLE_USER_SET_FUNC] = dummy_function;//何もしない
extern int reply_boot_message();// :202503追加
handlers[_IDX_REPLY_BOOT_MESSAGE]= (void *)reply_boot_message;
//ウメ・エディットプログラムの初期化(_init_sub_func();の実行)
handlers[_IDX_INIT_SUB_FUNC] = dummy_init_function;
// USBからの置き換え可能な受信処理--------------------------------------------
_RECIVE_USB_FUNC = dummy_recive;
// ADC関連 -----------------------------------------------------------------
handlers[_IDX_GET_PTR_ADC_BUFF] = (void (*)(void) ) get_ptr_adc_buff;
handlers[_IDX_SET_ADC_EXE] = (void (*)(void) ) set_adc_exe;
handlers[_IDX_SET_ADC_MODE] = (void (*)(void) ) set_adc_mode;
// 以下は、「ウメ・エディットプログラム」での利用を可能にするためのマクロ
// USBを介した文字列出力関連 -------------------------------------------------
handlers[_IDX_API_REQUEST_ACC_OUTBUFF] = (void (*)(void) ) request_acc_outbuff;
handlers[_IDX_API_RELEASE_ACC_OUTBUFF] = (void (*)(void) ) release_acc_outbuff;
handlers[_IDX_API_SEND_CHAR] = (void (*)(void) ) send_char;
handlers[_IDX_API_SET_BREAK_BUFFER] = (void (*)(void) ) setBreakBuffer;
handlers[_IDX_API_SEND_STRING] = (void (*)(void) ) send_string;
handlers[_IDX_API_SEND_HEX_LOW] = (void (*)(void) ) send_hex_low;
handlers[_IDX_API_SEND_HEX_HI] = (void (*)(void) ) send_hex_hi;
handlers[_IDX_API_SEND_DECIMAL] = (void (*)(void) ) send_decimal;
handlers[_IDX_API_GET_CAPACITY] = (void (*)(void) ) get_capacity;
handlers[_IDX_API_SEND_16BYTE] = (void (*)(void) ) send_16byte;
handlers[_IDX_SEND_PADDING_UINT] = (void (*)(void) ) send_padding_uint;
handlers[_IDX_SEND_FLOAT] = (void (*)(void) ) send_float;
handlers[_IDX_SEND_EXPONENT] = (void (*)(void) ) send_exponent;
handlers[_IDX_SEND_UME_ID] = (void (*)(void) ) send_ume_id;
// UART1 関連 --------------------------------------------------------------
handlers[_IDX_API_REQUEST_ACC_UARTBUFF] = (void (*)(void) ) request_acc_uartbuff;
handlers[_IDX_API_RELEASE_ACC_UARTBUFF] = (void (*)(void) ) release_acc_uartbuff;
handlers[_IDX_GET_UART_CAPACITY] = (void (*)(void) ) get_uart1_capacity;
handlers[_IDX_SEND_STR_UART1] = (void (*)(void) ) send_string_to_uart1;
// ブザー関連 --------------------------------------------------------------
handlers[_IDX_SET_BEEP_PERIOD] = (void (*)(void) ) set_beep_period;
void set_beep_sound_node(int , uint8_t ,uint8_t, uint8_t);
handlers[_IDX_SET_BEEP_SOUND_NODE] = (void (*)(void) ) set_beep_sound_node;
void set_switching_period(int period);
handlers[_IDX_SET_SWITCHING_PERIOD] = (void (*)(void) ) set_switching_period;
void set_beep_code(uint8_t );
handlers[_IDX_SET_BEEP_CODE] = (void (*)(void) ) set_beep_code;
void clear_beep_code();
handlers[_IDX_CLEAR_BEEP_CODE] = (void (*)(void) ) clear_beep_code;
handlers[_IDX_DEBUG_POINT] = (void (*)(void) ) debug_point;
// DEBUG 関連定義------------------------------------------------------------
handlers[_IDX_DEBUG_COUNT]=(void (*)(void) ) debug_count;
handlers[_IDX_DEBUG_HEX4]=(void (*)(void) ) debug_hex4;
handlers[_IDX_DEBUG_HEX8]=(void (*)(void) ) debug_hex8;
handlers[_IDX_DEBUG_HEX16]=(void (*)(void) ) debug_hex16;
handlers[_IDX_DEBUG_HEX32]=(void (*)(void) ) debug_hex32;
// -------------------------------------------------------------------------
handlers[_IDX_SET_PWD_MODE]=(void (*)(void) ) set_pwd_mode;
rcon->POR = 0;
//PORは、POWER ON 時に1になる。リセット時には1にならない。
// 上記を行った後、リセットでは上記を行わなないようにクリアする
led_D1 = 1; // D1 LED の初期点灯の予約
power_on_flag = 1;//追加[2023-4]
}//パワーオン時(リセット無関係)処理==============================ここまで
_handle_user_set_func();//ユーザのhandlers設定関数(デフォルトでled_D1により点灯)
}