実機のハードウェアリセットを実現する為のモジュールです。
所謂ソフトウェアリセットというやつです。
最も上位(ルート)に位置するものとして、
いつでもリセットを掛けれるようにという想定のものです。
独断と偏見により L + R + START + SERECT をリセットコマンドとしてます。
プラットフォームGBA、NDSではお馴染み(?)。
任意のボタンの組み合わせでもって、
押された瞬間のみのエッジを検出する時の参考にはなると思います。
main.c
/*--------------------------------------------------------------------------------- Reset routine test version 0.01 Oct 17, 2009 (C)2009 REGEKATSU ---------------------------------------------------------------------------------*/ #include <nds.h> #include <stdio.h> #include "Reset.h" typedef enum{ MAIN_INIT, MAIN_RESET, MAIN_LOOP }MAIN_SEQ; typedef struct{ u16 act; }MainSeq; static MainSeq st_main = {MAIN_INIT}; //--------------------------------------------------------------------------------- int main(void){ //--------------------------------------------------------------------------------- u32 count = 0;//サンプルプログラム用 consoleDemoInit(); while(1){ swiWaitForVBlank(); scanKeys(); switch(st_main.act){ case MAIN_INIT: //初期化処理 //プログラムの最初のみ実行する処理をここに記述する printf("Reset routine test\n\n" "version 0.01\n" "Oct 17, 2009\n\n" "(C)2009 REGEKATSU\n\n\n" "VBLANK COUNTER:\n"); st_main.act = MAIN_RESET; break; case MAIN_RESET: //クリア処理 //各モジュールの変数などを初期値へ戻す //クリア処理の実態は Reset_Exec 関数内部へ集約して行う Reset_Exec(); count = 0;//サンプルプログラム用 st_main.act = MAIN_LOOP; break; case MAIN_LOOP: //サンプルプログラム用 printf("\x01b[2K\r"); printf("\x01b[1A%d", count); count++; //リセット成立時(同時押し成立の瞬間のみ)、 MAIN_RESET へ状態遷移する if(Reset_IsReset()){ st_main.act = MAIN_RESET; } break; } } } //---------------------------------------------------------------------------------
Reset.h
/*--------------------------------------------------------------------------------- Reset routine header version 0.01 Oct 17, 2009 (C)2009 REGEKATSU ---------------------------------------------------------------------------------*/ #ifndef _RESET_H_ #define _RESET_H_ #ifdef __cplusplus extern "C" { #endif bool Reset_IsReset(void); void Reset_Exec(void); #ifdef __cplusplus } #endif #endif // _RESET_H_
ResetPrivate.h
/*--------------------------------------------------------------------------------- Reset routine private header version 0.01 Oct 17, 2009 (C)2009 REGEKATSU ---------------------------------------------------------------------------------*/ #ifndef _RESET_PRIVATE_H_ #define _RESET_PRIVATE_H_ #include "nds/ndstypes.h" #include "nds/arm9/input.h" //各モジュール変数を初期化する為、 //ここにモジュール毎のパブリックヘッダを記述する。 //プライベートヘッダとするのは、 //メイン関数に他モジュールの情報を隠蔽するのが目的。 #ifdef __cplusplus extern "C" { #endif #ifdef __cplusplus } #endif #endif // _RESET_PRIVATE_H_
Reset.c
/*--------------------------------------------------------------------------------- Reset routine test software reset (L + R + SELECT + START) sample version 0.01 Oct 17, 2009 (C)2009 REGEKATSU ---------------------------------------------------------------------------------*/ #include "ResetPrivate.h" //--------------------------------------------------------------------------------- bool Reset_IsReset(void){ //--------------------------------------------------------------------------------- bool ans = false; u32 keys; if(keysDown() & (KEY_L | KEY_R | KEY_SELECT | KEY_START)){ keys = keysDown() | keysHeld(); keys = keys & (KEY_L | KEY_R | KEY_SELECT | KEY_START); if(keys == (KEY_L | KEY_R | KEY_SELECT | KEY_START)){ ans = true; } } return ans; } //--------------------------------------------------------------------------------- void Reset_Exec(void){ //--------------------------------------------------------------------------------- // 同時押し(L + R + SELECT + START) 成立時に実行される処理をここへ記述する。 } //---------------------------------------------------------------------------------