TOPPERS「活用アイデア」・「アプリケーション開発」コンテスト
は、2011年から毎年実施されています。
https://www.toppers.jp/contest.html
「アプケーション開発」は、ソースコードの公開を前提としています。
「活用アイデア」でも、その後実現したソースコードなどもある。探しながら紹介。
なお、この記事は、TOPPERSプロジェクトの公式見解ではなく、
小川清 の 技術者個人の考えに基づいています。
目的(purpose)
TOPPERS開発アイデア・アプリケーション開発コンテスト受賞作品には、良質な算譜、技術的に崇高な志向、目的を達成するための意思などが感じられる。広く、source codeを表示して紹介し、次の応募作品を促す。
#成果(outcome)
応募作品の算譜を眺めると、その技術者の得意分野や技法を感じることができる。応募作品のソースコードを使ってみようという気になる。ソースコードを一度コンパイルしたくなる。自分も良い作品を作ろうという気になる。
TOPPERS活用アイデア・アプリケーション開発コンテスト受賞作品紹介(12)第五回(2015)アプリケーション開発部門 金賞
##ATK2 RCカー(Nios2版) 本田晋也(名古屋大学)
##応募資料(application material)等
コンテスト応募資料
https://www.toppers.jp/docs/contest/2015/ATK2_RCカー(Nios2版).pdf
PIC24FJ64GB004 小型マイコン基板 SBDBT5V http://www.runele.com/ca1/2/
ベースボード 松浦商事
Download
ソースコード TOPPERSのContributed Softwareとして入手可能
http://dev.toppers.jp/trac_user/contrib/browser/rc_os_nios2
SBDBT用ファームウェア
http://runningele.web.fc2.com/ps3/sbxbt_ps3_src_140113.zip
QuratusII
• Altera社のWebサイトからQurartusII Webエディション 14.1をダウロード
• DE0用のハードウェアデザイン
• Terasicのサイトからダウンロード可能(DE0_Nano_QSYS_DEMOを使用)
算譜(source code)
#include "Os.h"
#include "t_syslog.h"
#include "t_stdlib.h"
#include "sysmod/serial.h"
#include "sysmod/syslog.h"
#include "rc_car.h"
#include "sysmod/banner.h"
#include "target_sysmod.h"
#include "target_serial.h"
#include "prc_sil.h"
#include "de0_nano.h"
#include "comuart.h"
#include "nces_can.h"
#include "rcb3.h"
/*
○仕様
・コマンド
SBXBTの PS3コントローラ/USBゲームパッドUART変換ファームウェア
(http://runningele.web.fc2.com/) でサポートしているRCB3に対応
している.
・起動時
全てのLEDを0.5秒周期で3秒点滅させる.
・ボタン操舵
左・右 ボタン
・ステアリングのニュートラルを調整.
・ボタンを押すと方向指示器がON,離すとOFF
上ボタン
・ドライブにする.
下ボタン
・リバースににする.
L1/R1
・方向指示器をON/OFFする.
L2/R2
・モータ制御のゲインを変更
×
・ブレーキ
△
・ハザード
○
・メインヘッドライトON/OFF
□
・ニュートラルにする.
*/
/*
ボディ系コマンドCANメッセージ仕様
送信周期 : 50ms
メッセージID : 16
メッセージ長 : 11bit
offset bits bit assign
ヘッドライト1 : 0 : 1 : 1:ON 0:OFF
ヘッドライト2 : 1 : 1 : 1:ON 0:OFF
ヘッドライト3 : 2 : 1 : 1:ON 0:OFF
ブレーキランプ : 3 : 1 : 1:ON 0:OFF
バックランプ : 4 : 1 : 1:ON 0:OFF
ブザー : 5 : 1 : 1:ON 0:OFF 2:BLINK
ウィンカーL : 8 : 2 : 1:ON 0:OFF 2:BLINK
ウィンカーR : 10 : 2 : 1:ON 0:OFF 2:BLINK
ハザードランプ : 12 : 1 : 1:ON 0:OFF 2:BLINK
制御系コマンドCANメッセージ仕様
送信周期 : メッセージ到達毎
メッセージID : 3
メッセージ長 : 64bit
*/
/*
* 各種パラメータ定義
*/
/*
* CAN関連 : ボディ系コマンド用CANメッセージID
*/
#define BODY_CAN_MSG_ID 16
/*
* CAN関連 : 制御系コマンド用CANメッセージID
*/
#define CONT_CMD_CAN_MSG_ID 3
/*
* CAN関連 : ボディ系コマンド用CAN送受信メールボックスID
*/
#define BODY_CAN_MSG_RMB 1
#define BODY_CAN_MSG_TMB 1
/*
* CAN関連 : 制御系コマンド用CANメッセージ用CAN送受信メールボックスID
*/
#define CONT_CMD_CAN_MSG_RMB 0
#define CONT_CMD_CAN_MSG_TMB 0
/*
* 制御系 : ニュートラル時のステアリング角度の初期値
*/
#define STEER_NEUTRAL_INIT 0
/*
* 制御系 : 起動時のボディー系の接続テスト用設定
*/
#define INIT_BODY_BLINK_COUNT 3
#define INIT_BODY_BLINK_CYCLE_MS 500
/*
* 制御系 : 起動周期
*/
#define RC_CONTRL_TASK_CYCLE_MS 10
/*
* 制御系 : CAN送信周期
*/
#define BODY_CAN_SEND_CYCLE_MS 500
#define SPEED_GAIN_INIT 10
#define SPEED_GAIN_MIN 1
#define SPEED_GAIN_MAX 20
/*
* 未整理
*/
/*
* 内部データバッファ
*/
static volatile uint8 command_tbl[8]; /* コマンド引渡しテーブル */
/*
* ファイル名,行番号の参照用の変数
*/
extern const char8 *fatal_file_name; /* ファイル名 */
extern sint32 fatal_line_num; /* 行番号 */
/*
* APIエラーログマクロ
*
* ErrorHookが有効の場合はErrorHookから
* エラーログを出力し, ErrorHookが無効の場合は
* 以下のマクロよりエラーログ出力を行う
*/
#if defined(CFG_USE_ERRORHOOK)
#define error_log(api) (api)
#else /* !defined( CFG_USE_ERRORHOOK ) */
#define error_log(api) \
{ \
StatusType ercd; \
ercd = api; /* 各API実行 */ \
if (ercd != E_OK) { \
syslog(LOG_INFO, "Error:%d", atk2_strerror(ercd)); \
} \
}
#endif /* defined( CFG_USE_ERRORHOOK ) */
void
set_led(uint8 pattern){
sil_wrw_iop((void *)LED_PIO_BASE, pattern);
}
uint8
get_dipsw(void){
return (uint8)sil_rew_iop((void *)DIPSW_PIO_BASE);
}
volatile boolean IsBodyOnECU = FALSE;
volatile boolean IsOpeOnECU = FALSE;
volatile boolean IsCntOnECU = FALSE;
void
appmode_error(void){
volatile int i;
uint8 pattern = 0;
while(1){
for(i = 0; i < 1000000; i++);
set_led(pattern);
pattern = ~pattern;
}
}
/*
* ユーザメイン関数
*
* アプリケーションモードの判断と,カーネル起動
*/
sint32
main(void)
{
AppModeType crt_app_mode;
uint8 dipsw;
crt_app_mode = AppMode_ALL;
dipsw = get_dipsw();
switch (dipsw & 0x7) {
case 0x00:
appmode_error();
break;
case 0x01:
crt_app_mode = AppMode_Body;
IsBodyOnECU = TRUE;
break;
case 0x02:
crt_app_mode = AppMode_Cnt;
IsCntOnECU = TRUE;
break;
case 0x04:
crt_app_mode = AppMode_Ope;
IsOpeOnECU = TRUE;
break;
case 0x01|0x02:
crt_app_mode = AppMode_Body_Cnt;
IsBodyOnECU = TRUE;
IsCntOnECU = TRUE;
break;
case 0x01|0x04:
crt_app_mode = AppMode_Body_Ope;
IsBodyOnECU = TRUE;
IsOpeOnECU = TRUE;
break;
case 0x02|0x04:
crt_app_mode = AppMode_Cnt_Ope;
IsCntOnECU = TRUE;
IsOpeOnECU = TRUE;
break;
case 0x07:
crt_app_mode = AppMode_ALL;
IsBodyOnECU = TRUE;
IsCntOnECU = TRUE;
IsOpeOnECU = TRUE;
break;
default:
appmode_error();
break;
}
/*
* カーネル起動
*/
StartOS(crt_app_mode);
while (1) {
}
}
//////////////////////////////////////////////////////////////////////////
/*
*
* ボディー制御関連
*
*/
/*
* ボディーECUへの状態指示構造体
*/
typedef struct {
uint8 headlight1;
uint8 headlight2;
uint8 headlight3;
uint8 breaklamp;
uint8 backlamp;
uint8 buzzer;
uint8 blinker_l;
uint8 blinker_r;
uint8 hazardlamp;
}BODY_CONT_INFO;
/*
* ボディーのアイテムのON/OFFマクロ
*/
#define BODY_CONT_ON 1
#define BODY_CONT_OFF 0
#define BODY_CONT_BLINK 2
/*
* ボディーECUへの状態指示用変数
*/
volatile BODY_CONT_INFO g_body_cont_info;
void
set_tlu01(unsigned int pattern){
sil_wrw_iop((void *)TLU01_PIO_BASE, pattern);
}
unsigned int
get_tlu01(void){
return (sil_rew_iop((void *)TLU01_PIO_BASE));
}
/*
* tlu01_set() で指示する値
*/
#define BLINKER_L_NO 0
#define BLINKER_R_NO 1
#define BREAK_LAMP_NO 2
#define HEAD_LAMP1_NO 3
#define HEAD_LAMP2_NO 4 /* 未実装 */
#define HEAD_LAMP3_NO 5 /* 未実装 */
#define BACK_LAMP_NO 6
#define BUZZER_NO 7
#define TLU01_PORT_MIN 0
#define TLU01_PORT_MAX 7
static const uint8 tlu01_pinfo[8] ={
0x01,
0x40,
0x08|0x20, //BREAK
0x04|0x10,
0x10,
0x00,
0x80,
0x02, //BUZZER
};
void
tlu01_set(uint8 no, boolean on)
{
uint32 wk;
uint16 pattern;
if (no > TLU01_PORT_MAX) {
return;
}
pattern = tlu01_pinfo[no - 1];
wk = get_tlu01();
if (on) {
wk |= pattern;
}
else {
wk &= ~pattern;
}
set_tlu01(wk);
}
/*
* TLU01との接続の初期化
*/
void
tlu01_init(void)
{
/* 全消灯 */
sil_wrw_iop((void *)TLU01_PIO_BASE, 0x00);
}
#define BLINK_CYCLE_MS 500
volatile int buzzer_state = 0;
void
UnpackBodyContCanMsg(uint8 *p_rx_data)
{
g_body_cont_info.headlight1 = (p_rx_data[0] & 0x80)? BODY_CONT_ON : BODY_CONT_OFF;
g_body_cont_info.headlight2 = (p_rx_data[0] & 0x40)? BODY_CONT_ON : BODY_CONT_OFF;
g_body_cont_info.headlight3 = (p_rx_data[0] & 0x20)? BODY_CONT_ON : BODY_CONT_OFF;
g_body_cont_info.breaklamp = (p_rx_data[0] & 0x10)? BODY_CONT_ON : BODY_CONT_OFF;
g_body_cont_info.backlamp = (p_rx_data[0] & 0x08)? BODY_CONT_ON : BODY_CONT_OFF;
g_body_cont_info.buzzer = (p_rx_data[0] & 0x06) >> 1;
g_body_cont_info.blinker_l = (p_rx_data[1] & 0xc0) >> 6;
g_body_cont_info.blinker_r = (p_rx_data[1] & 0x30) >> 4;
g_body_cont_info.hazardlamp = (p_rx_data[1] & 0x08)? BODY_CONT_ON : BODY_CONT_OFF;
}
TASK(RCBodyTask){
int cnt = 0;
uint32 pattern;
boolean blink_on = FALSE;
uint8 rx_data[8];
uint8 rx_size;
syslog(LOG_NOTICE, "RCBodyTask : Start!");
tlu01_init();
while(1){
WaitEvent(RCBodyEvt); /* 10msの作業時間待ち */
ClearEvent(RCBodyEvt);
/*
* 制御系が別ECUならCANからメッセージを取得する.
*/
if (!IsCntOnECU) {
NcanGetRxData(0, BODY_CAN_MSG_RMB, &rx_data[0], &rx_size );
if (rx_size != 0) {
/* 受信メッセージの解析 */
UnpackBodyContCanMsg(rx_data);
}
}
pattern = 0;
/* ON/OFF処理 */
pattern |= (g_body_cont_info.headlight1 == BODY_CONT_ON)? tlu01_pinfo[HEAD_LAMP1_NO] : 0x00;
pattern |= (g_body_cont_info.breaklamp == BODY_CONT_ON)? tlu01_pinfo[BREAK_LAMP_NO] : 0x00;
pattern |= (g_body_cont_info.backlamp == BODY_CONT_ON)? tlu01_pinfo[BACK_LAMP_NO] : 0x00;
if(g_body_cont_info.hazardlamp == BODY_CONT_OFF){
pattern |= (g_body_cont_info.blinker_l == BODY_CONT_ON)? tlu01_pinfo[BLINKER_L_NO] : 0x00;
pattern |= (g_body_cont_info.blinker_r == BODY_CONT_ON)? tlu01_pinfo[BLINKER_R_NO] : 0x00;
}
if(blink_on == TRUE){
/* 点滅処理 */
if (g_body_cont_info.hazardlamp == BODY_CONT_ON){
pattern |= tlu01_pinfo[BLINKER_L_NO]|tlu01_pinfo[BLINKER_R_NO];
}else{
if (g_body_cont_info.blinker_l == BODY_CONT_BLINK){
pattern |= tlu01_pinfo[BLINKER_L_NO];
}
if (g_body_cont_info.blinker_r == BODY_CONT_BLINK){
pattern |= tlu01_pinfo[BLINKER_R_NO];
}
}
}
if(cnt++ == BLINK_CYCLE_MS/10){
cnt = 0;
blink_on = (blink_on)? FALSE : TRUE;
}
if(buzzer_state == 1){
set_tlu01(pattern|tlu01_pinfo[BUZZER_NO]);
}
else{
set_tlu01(pattern);
}
}
}
ALARMCALLBACK(BuzzerCycAlmCb)
{
static uint8 buzzer_on = 0;
static uint8 pre_buzzer = BODY_CONT_OFF;
static uint32 cnt = 0;
if (pre_buzzer != g_body_cont_info.buzzer){
pre_buzzer = g_body_cont_info.buzzer;
cnt = 0;
}
if(g_body_cont_info.buzzer == BODY_CONT_ON){
cnt++;
if (cnt < 500) {
if(buzzer_on == 0){
buzzer_on = 1;
buzzer_state = 1;
set_tlu01(get_tlu01() | tlu01_pinfo[BUZZER_NO]);
}else{
buzzer_on = 0;
buzzer_state = 0;
set_tlu01(get_tlu01() & ~tlu01_pinfo[BUZZER_NO]);
}
}
if(cnt > 1000){
cnt = 0;
}
}
}
///////////////////////////////////////////////////////////////////////////////////////////////////////
/*
* 操作系関連
*/
/*
* 制御系へのコマンド更新通知用変数(同一ECU時)
*/
volatile boolean UpDateCntrolCmd = FALSE;
/*
* 操作タスク
*/
TASK(RCOperatorTask)
{
unsigned char c;
syslog(LOG_INFO, "RCOperatorTask : Start!");
comuart_init();
while(1){
WaitCOMUartEvent();
while(comuart_receive(&c, 1)) {
if (rcb3_AddReceivedByte(c)) {
UpDateCntrolCmd = TRUE;
// syslog(LOG_NOTICE, "%d,%d,%d,%d,%d,%d", g_rcb3_rmsg[1], g_rcb3_rmsg[2], g_rcb3_rmsg[3], g_rcb3_rmsg[4], g_rcb3_rmsg[5], g_rcb3_rmsg[6]);
/*
* RCControlTaskが別ECUの場合はCANで送信
*/
if (!IsCntOnECU) {
NcanSetTxData(0, CONT_CMD_CAN_MSG_TMB, CONT_CMD_CAN_MSG_ID, &g_rcb3_rmsg[0], RCB3_MSG_LEN);
}
}
}
}
}
///////////////////////////////////////////////////////////////////////////////////////////////////////
/*
*
* 制御系関連
*
*/
float g_steer_neutral = STEER_NEUTRAL_INIT;
float g_angle = 0;
typedef enum{
SHIFT_N,
SHIFT_D,
SHIFT_R,
}SHIFT_STATE;
/*
* 制御関連の変数
*/
volatile boolean g_blinker_l_blink = FALSE;
volatile boolean g_blinker_r_blink = FALSE;
volatile boolean g_isBrake = FALSE;
volatile int g_accelerator = 0;
volatile int g_speed_gain = SPEED_GAIN_INIT;
volatile SHIFT_STATE g_ShiftState = SHIFT_N;
/*
* PS3コントローラのアナログボタンのパラメータ
*/
#define PS3ANALOG_MAX 63
#define PS3ANALOG_MIN -64
void
AdjustSteerNeturalL(void)
{
if(g_steer_neutral < 30) {
g_steer_neutral++;
g_angle++;
syslog(LOG_NOTICE, "Adjust steer neutral = %d.%d", (int)g_steer_neutral, (int)(g_steer_neutral*100) % 100);
}
}
/*
* ステアリングニュートラルを右側に
*/
void
AdjustSteerNeturalR(void)
{
if(g_steer_neutral > -30) {
g_steer_neutral--;
g_angle--;
syslog(LOG_NOTICE, "Adjust steer neutral = %d.%d", (int)g_steer_neutral, (int)(g_steer_neutral*100) % 100);
}
}
/*
* 左アナログコントローラの左右動作
* ステアリングを操作
*/
void
onPS3AnalogL_LR(void)
{
float angle;
float cur_analog = p_g_cur_ps3analog[NO_PS3ANALOG_L_LR];
if ((cur_analog <= PS3ANALOG_MAX) && (cur_analog >= PS3ANALOG_MIN)) {
/* 左 30 から 右 -30 範囲 */
angle = -(cur_analog/2);
angle += g_steer_neutral;
if (angle != g_angle) {
g_angle = angle;
if(g_angle > 0){
syslog(LOG_NOTICE, "Steer angle = %d.%d", (int)g_angle, (int)(g_angle*100) % 100);
}
else {
syslog(LOG_NOTICE, "Steer angle = %d.%d", (int)g_angle, (int)(-g_angle*100) % 100);
}
}
}
}
/*
* 左アナログコントローラの上下動作
*/
void
onPS3AnalogL_UD(void)
{
}
/*
* 右アナログコントローラの左右動作
*/
void
onPS3AnalogR_LR(void)
{
}
/*
* 右アナログコントローラの上下動作
* 上 - 方向
* 下 + 方向
*/
void
onPS3AnalogR_UD(void)
{
float cur_analog = p_g_cur_ps3analog[NO_PS3ANALOG_R_UD];
g_accelerator = cur_analog;
if(cur_analog <= 0){
g_body_cont_info.backlamp = BODY_CONT_OFF;
g_body_cont_info.buzzer = BODY_CONT_OFF;
}
else {
// g_accelerator = -cur_analog;
// syslog(LOG_NOTICE, "Curanalog = %d.%d", (int)cur_analog, (int)(-cur_analog*100) % 100);
g_body_cont_info.backlamp = BODY_CONT_ON;
g_body_cont_info.buzzer = BODY_CONT_ON;
}
}
/*
* PS3コントローラのデジタルボタン毎の処理
*/
#define TOGGLE_ON_OFF(item) item = (item == BODY_CONT_ON)? BODY_CONT_OFF : BODY_CONT_ON;
/*
* × : ブレーキ
*/
void
onPS3ButtonCrossEdgeOn(void) {
g_isBrake = TRUE;
// SetDriveSpeed(0);
g_body_cont_info.breaklamp = BODY_CONT_ON;
}
void
onPS3ButtonCrossEdgeOff(void) {
g_isBrake = FALSE;
g_body_cont_info.breaklamp = BODY_CONT_OFF;
}
/*
* △ : ハザード
*/
void
onPS3ButtonTriangleEdgeOn(void) {
TOGGLE_ON_OFF(g_body_cont_info.hazardlamp);
}
void
onPS3ButtonTriangleEdgeOff(void) {
}
/*
* ○ : メインヘッドライト(ヘッドライト1) 切り替え
*/
void
onPS3ButtonNoughtEdgeOn(void) {
TOGGLE_ON_OFF(g_body_cont_info.headlight1);
}
void
onPS3ButtonNoughtEdgeOff(void) {
}
/*
* □ : ギア切り替え
*/
void
onPS3ButtonSquareEdgeOn(void) {
syslog(LOG_NOTICE, "Shift N");
g_ShiftState = SHIFT_N;
g_body_cont_info.backlamp = BODY_CONT_OFF;
g_body_cont_info.buzzer = BODY_CONT_OFF;
#if 0
TOGGLE_ON_OFF(g_body_cont_info.headlight3);
#endif
}
void
onPS3ButtonSquareEdgeOff(void) {
}
/*
* 左ボタン : ステアリングのニュートラルを調整
*/
void
onPS3ButtonLeftEdgeOn(void) {
AdjustSteerNeturalL();
g_body_cont_info.blinker_l = BODY_CONT_ON;
}
void
onPS3ButtonLeftEdgeOff(void) {
g_body_cont_info.blinker_l = (g_blinker_l_blink)? BODY_CONT_BLINK : BODY_CONT_OFF;
}
/*
* 右ボタン : ステアリングのニュートラルを調整
*/
void
onPS3ButtonRightEdgeOn(void) {
AdjustSteerNeturalR();
g_body_cont_info.blinker_r = BODY_CONT_ON;
}
void
onPS3ButtonRightEdgeOff(void) {
g_body_cont_info.blinker_r = (g_blinker_r_blink)? BODY_CONT_BLINK : BODY_CONT_OFF;
}
/*
* 上ボタン : ステアリングをニュートラルにする
*/
void
onPS3ButtonUpEdgeOn(void) {
g_steer_neutral = STEER_NEUTRAL_INIT;
g_angle = STEER_NEUTRAL_INIT;
g_body_cont_info.blinker_l = BODY_CONT_ON;
g_body_cont_info.blinker_r = BODY_CONT_ON;
#if 0
if(g_isBrake){
syslog(LOG_NOTICE, "Shift D");
g_ShiftState = SHIFT_D;
g_body_cont_info.backlamp = BODY_CONT_OFF;
g_body_cont_info.buzzer = BODY_CONT_OFF;
}else{
syslog(LOG_NOTICE, "Shift D : error");
}
#endif
#if 0
InitSteerNetural();
g_body_cont_info.blinker_l = BODY_CONT_ON;
g_body_cont_info.blinker_r = BODY_CONT_ON;
#endif
}
void
onPS3ButtonUpEdgeOff(void) {
g_body_cont_info.blinker_l = (g_blinker_l_blink)? BODY_CONT_BLINK : BODY_CONT_OFF;
g_body_cont_info.blinker_r = (g_blinker_r_blink)? BODY_CONT_BLINK : BODY_CONT_OFF;
}
/*
* 下ボタン : モータ制御のゲインを初期値にする
*/
void
onPS3ButtonDownEdgeOn(void) {
#if 0
if(g_isBrake){
syslog(LOG_NOTICE, "Shift R");
g_ShiftState = SHIFT_R;
g_body_cont_info.backlamp = BODY_CONT_ON;
g_body_cont_info.buzzer = BODY_CONT_ON;
}else{
syslog(LOG_NOTICE, "Shift R : error");
}
#endif
g_speed_gain = SPEED_GAIN_INIT;
g_body_cont_info.blinker_l = BODY_CONT_ON;
g_body_cont_info.blinker_r = BODY_CONT_ON;
#if 0
char str[30];
g_speed_gain = MOTOR_GAIN_INIT;
SetDriveSpeed(g_speed/g_speed_gain);
g_body_cont_info.blinker_l = BODY_CONT_ON;
g_body_cont_info.blinker_r = BODY_CONT_ON;
sprintf(str, "Adjust speed gain = %d \r\n", g_speed_gain);
uart_PSendString(RC_OUTPUT_PORT, str);
#endif
}
void
onPS3ButtonDownEdgeOff(void) {
#if 0
g_body_cont_info.blinker_l = (g_blinker_l_blink)? BODY_CONT_BLINK : BODY_CONT_OFF;
g_body_cont_info.blinker_r = (g_blinker_r_blink)? BODY_CONT_BLINK : BODY_CONT_OFF;
#endif
}
/*
* L1/R1 : 方向指示器のON/OFF
*/
void
onPS3ButtonL1EdgeOn(void){
if (g_blinker_l_blink) {
g_blinker_l_blink = FALSE;
/* ボディーへの指示がONの場合は他の機能がONにしているため何もしない */
if (!(g_body_cont_info.blinker_l == BODY_CONT_ON)) {
g_body_cont_info.blinker_l = BODY_CONT_OFF;
}
} else {
g_blinker_l_blink = TRUE;
/* ボディーへの指示がONの場合は他の機能がONにしているため何もしない */
if (!(g_body_cont_info.blinker_l == BODY_CONT_ON)) {
g_body_cont_info.blinker_l = BODY_CONT_BLINK;
}
}
}
void
onPS3ButtonL1EdgeOff(void) {
}
void
onPS3ButtonR1EdgeOn(void){
if (g_blinker_r_blink) {
g_blinker_r_blink = FALSE;
/* ボディーへの指示がONの場合は他の機能がONにしているため何もしない */
if (!(g_body_cont_info.blinker_r == BODY_CONT_ON)) {
g_body_cont_info.blinker_r = BODY_CONT_OFF;
}
} else {
g_blinker_r_blink = TRUE;
/* ボディーへの指示がONの場合は他の機能がONにしているため何もしない */
if (!(g_body_cont_info.blinker_r == BODY_CONT_ON)) {
g_body_cont_info.blinker_r = BODY_CONT_BLINK;
}
}
}
void
onPS3ButtonR1EdgeOff(void) {
}
/*
* L2/R2 : モータ制御のゲインを変更
*/
void
onPS3ButtonL2EdgeOn(void){
if(g_speed_gain > SPEED_GAIN_MIN){
g_speed_gain--;
}
g_body_cont_info.blinker_l = BODY_CONT_ON;
#if 0
AdjustSpeedGainD();
g_body_cont_info.blinker_l = BODY_CONT_ON;
#endif
}
void
onPS3ButtonL2EdgeOff(void){
#if 0
g_body_cont_info.blinker_l = (g_blinker_l_blink)? BODY_CONT_BLINK : BODY_CONT_OFF;
#endif
}
void
onPS3ButtonR2EdgeOn(void){
if (g_speed_gain < SPEED_GAIN_MAX){
g_speed_gain++;
g_body_cont_info.blinker_r = BODY_CONT_ON;
}
#if 0
AdjustSpeedGainU();
g_body_cont_info.blinker_r = BODY_CONT_ON;
#endif
}
void
onPS3ButtonR2EdgeOff(void){
#if 0
g_body_cont_info.blinker_r = (g_blinker_r_blink)? BODY_CONT_BLINK : BODY_CONT_OFF;
#endif
}
/*
* ボタンの変化検出のためのマクロ
*/
#define PS3BUTTON_EDGE_ON(no) ((p_g_pre_ps3button[no] == FALSE) && (p_g_cur_ps3button[no] == TRUE))
#define PS3BUTTON_EDGE_OFF(no) ((p_g_pre_ps3button[no] == TRUE) && (p_g_cur_ps3button[no] == FALSE))
#define PS3ANALOG_CHANGE(no) (p_g_pre_ps3analog[no] != p_g_cur_ps3analog[no])
/*
* PS3コントローラからのイベントの処理
*/
void
onMsgPS3(void) {
if (PS3BUTTON_EDGE_OFF(NO_PS3BUTTON_CROSS)){
onPS3ButtonCrossEdgeOff();
}
if (PS3BUTTON_EDGE_ON(NO_PS3BUTTON_TRIANGLE)){
onPS3ButtonTriangleEdgeOn();
}
if (PS3BUTTON_EDGE_OFF(NO_PS3BUTTON_TRIANGLE)){
onPS3ButtonTriangleEdgeOff();
}
if (PS3BUTTON_EDGE_ON(NO_PS3BUTTON_NOUGHT)){
onPS3ButtonNoughtEdgeOn();
}
if (PS3BUTTON_EDGE_OFF(NO_PS3BUTTON_NOUGHT)){
onPS3ButtonNoughtEdgeOff();
}
if (PS3BUTTON_EDGE_ON(NO_PS3BUTTON_SQUARE)){
onPS3ButtonSquareEdgeOn();
}
if (PS3BUTTON_EDGE_OFF(NO_PS3BUTTON_SQUARE)){
onPS3ButtonSquareEdgeOff();
}
if (PS3BUTTON_EDGE_ON(NO_PS3BUTTON_LEFT)){
onPS3ButtonLeftEdgeOn();
}
if (PS3BUTTON_EDGE_OFF(NO_PS3BUTTON_LEFT)){
onPS3ButtonLeftEdgeOff();
}
if (PS3BUTTON_EDGE_ON(NO_PS3BUTTON_RIGHT)){
onPS3ButtonRightEdgeOn();
}
if (PS3BUTTON_EDGE_OFF(NO_PS3BUTTON_RIGHT)){
onPS3ButtonRightEdgeOff();
}
if (PS3BUTTON_EDGE_ON(NO_PS3BUTTON_UP)){
onPS3ButtonUpEdgeOn();
}
if (PS3BUTTON_EDGE_OFF(NO_PS3BUTTON_UP)){
onPS3ButtonUpEdgeOff();
}
if (PS3BUTTON_EDGE_ON(NO_PS3BUTTON_DOWN)){
onPS3ButtonDownEdgeOn();
}
if (PS3BUTTON_EDGE_OFF(NO_PS3BUTTON_DOWN)){
onPS3ButtonDownEdgeOff();
}
if (PS3BUTTON_EDGE_ON(NO_PS3BUTTON_CROSS)){
onPS3ButtonCrossEdgeOn();
}
if (PS3BUTTON_EDGE_ON(NO_PS3BUTTON_L1)){
onPS3ButtonL1EdgeOn();
}
if (PS3BUTTON_EDGE_ON(NO_PS3BUTTON_R1)){
onPS3ButtonR1EdgeOn();
}
if (PS3BUTTON_EDGE_ON(NO_PS3BUTTON_L2)){
onPS3ButtonL2EdgeOn();
}
if (PS3BUTTON_EDGE_OFF(NO_PS3BUTTON_L2)){
onPS3ButtonL2EdgeOff();
}
if (PS3BUTTON_EDGE_ON(NO_PS3BUTTON_R2)){
onPS3ButtonR2EdgeOn();
}
if (PS3BUTTON_EDGE_OFF(NO_PS3BUTTON_R2)){
onPS3ButtonR2EdgeOff();
}
if (PS3ANALOG_CHANGE(NO_PS3ANALOG_L_LR)) {
onPS3AnalogL_LR();
}
if (PS3ANALOG_CHANGE(NO_PS3ANALOG_L_UD)) {
onPS3AnalogL_UD();
}
if (PS3ANALOG_CHANGE(NO_PS3ANALOG_R_LR)) {
onPS3AnalogR_LR();
}
if (PS3ANALOG_CHANGE(NO_PS3ANALOG_R_UD)) {
onPS3AnalogR_UD();
}
}
/*
* 周期送信とするか
*/
boolean g_body_can_msg_cyclic = FALSE;
void
body_can_msg_send(void)
{
uint8 tx_data[8];
/* 前回送付の状態 */
static BODY_CONT_INFO g_pre_body_cont_info;
/* 状態指示に変化が無ければ送信しない */
if (!g_body_can_msg_cyclic){
if((g_body_cont_info.headlight1 == g_pre_body_cont_info.headlight1) &&
(g_body_cont_info.headlight2 == g_pre_body_cont_info.headlight2) &&
(g_body_cont_info.headlight3 == g_pre_body_cont_info.headlight3) &&
(g_body_cont_info.breaklamp == g_pre_body_cont_info.breaklamp) &&
(g_body_cont_info.backlamp == g_pre_body_cont_info.backlamp) &&
(g_body_cont_info.buzzer == g_pre_body_cont_info.buzzer) &&
(g_body_cont_info.blinker_l == g_pre_body_cont_info.blinker_l) &&
(g_body_cont_info.blinker_r == g_pre_body_cont_info.blinker_r) &&
(g_body_cont_info.hazardlamp == g_pre_body_cont_info.hazardlamp)) {
return;
}
}
/* 送信メッセージを生成 */
tx_data[0] = ((g_body_cont_info.headlight1 << 7) & 0x80) |
((g_body_cont_info.headlight2 << 6) & 0x40) |
((g_body_cont_info.headlight3 << 5) & 0x20) |
((g_body_cont_info.breaklamp << 4) & 0x10) |
((g_body_cont_info.backlamp << 3) & 0x08) |
((g_body_cont_info.buzzer << 1) & 0x06);
tx_data[1] = ((g_body_cont_info.blinker_l << 6) & 0xc0) |
((g_body_cont_info.blinker_r << 4) & 0x30) |
((g_body_cont_info.hazardlamp << 3) & 0x08);
NcanSetTxData(0, BODY_CAN_MSG_RMB, BODY_CAN_MSG_ID, tx_data, 2);
g_pre_body_cont_info = g_body_cont_info;
}
/*
* 起動時のボディーの接続確認
*
* 全LED点滅とブザーを鳴らす.
*/
void
body_check(void)
{
int loop, tcnt;
uint8 status = BODY_CONT_ON;
for(loop = 0; loop < INIT_BODY_BLINK_COUNT*2; loop++) {
g_body_cont_info.headlight1 = status;
g_body_cont_info.headlight2 = status;
g_body_cont_info.headlight3 = status;
g_body_cont_info.breaklamp = status;
g_body_cont_info.backlamp = status;
g_body_cont_info.buzzer = status;
g_body_cont_info.blinker_l = status;
g_body_cont_info.blinker_r = status;
tcnt = 0;
if (!IsBodyOnECU){
body_can_msg_send();
}
while(1) {
WaitEvent(RCOperatorEvt);
ClearEvent(RCOperatorEvt);
tcnt++;
if (tcnt == INIT_BODY_BLINK_CYCLE_MS/10) {
break;
}
}
status = (status == BODY_CONT_ON)? BODY_CONT_OFF : BODY_CONT_ON;
}
}
void
rcb3_error(){
static int cnt = 0;
syslog(LOG_NOTICE, "error 0x%x : 0x%x, 0x%x, 0x%x, 0x%x, 0x%x, 0x%x, 0x%x, 0x%x \r\n", cnt++, g_rcb3_rmsg[0], g_rcb3_rmsg[1], g_rcb3_rmsg[2], g_rcb3_rmsg[3], g_rcb3_rmsg[4], g_rcb3_rmsg[5], g_rcb3_rmsg[6], g_rcb3_rmsg[7]);
}
void
com_error(){
syslog(LOG_NOTICE, "com error");
}
/*
* 制御タスク
*/
TASK(RCControlTask)
{
uint32 cycle = 0;
syslog(LOG_INFO, "RCControlTask : Start!");
uint8 rx_data[8];
uint8 rx_size;
int loop;
boolean result;
body_check();
while(1){
/* 10m待ち */
WaitEvent(RCControlEvt);
ClearEvent(RCControlEvt);
/*
* RCOperatorTaskが別ECUの場合はCANで受信
*/
if (!IsOpeOnECU){
NcanGetRxData(0, CONT_CMD_CAN_MSG_RMB, &rx_data[0], &rx_size);
if (rx_size != 0) {
result = FALSE;
for (loop = 0; loop < rx_size; loop++){
result = rcb3_AddReceivedByte(rx_data[loop]);
}
if (result) {
onMsgPS3();
}
else {
syslog(LOG_NOTICE, "RCControlTask : Received Can data Error!\r\n");
}
}
}
else {
/*
* 同一ECUの場合
*/
if (UpDateCntrolCmd == TRUE){
onMsgPS3();
UpDateCntrolCmd = FALSE;
}
}
/*
* RCBodyTaskが別ECUの場合はCANで送信
*/
if (!IsBodyOnECU) {
if (cycle++ == (BODY_CAN_SEND_CYCLE_MS/RC_CONTRL_TASK_CYCLE_MS)) {
body_can_msg_send();
cycle = 0;
}
}
}
}
//////////////////////////////////////////////////////////////////////////
/*
*
* パワトレ関係
*
*/
#define UEC_TO_PWMCNT(usec) (usec*PWM_CLK_MH)
/* 100nsec 単位との変換 */
#define M100NSEC_TO_PWMCNT(m100nsec) ((m100nsec*PWM_CLK_MH)/10)
#define SERVO_N 1570
//#define SERVO_RMAX 1830
//#define SERVO_LMAX 1400
#define SERVO_RMAX 1870
#define SERVO_LMAX 1330
void
servo_setangle(int angle) {
sil_wrw_iop((void *)PWM1_ADDR, UEC_TO_PWMCNT(angle));
}
#define ESC_N 15000
#define ESC_DMAX 14000
#define ESC_RMAX 16500
#define ESC_DTH 14500
#define ESC_RTH 15800
#define ESC_BREAK 16200
void
RCPowerTrainTaskWait_20msec(void){
ClearEvent(RCPowerTrainEvt);
WaitEvent(RCPowerTrainEvt);
ClearEvent(RCPowerTrainEvt);
WaitEvent(RCPowerTrainEvt);
ClearEvent(RCPowerTrainEvt);
}
void
esc_setspeed(int speed){
sil_wrw_iop((void *)PWM2_ADDR, M100NSEC_TO_PWMCNT(speed));
}
void
esc_dbrak(void){
esc_setspeed(ESC_BREAK);
}
void
esc_rbrak(void){
esc_setspeed(ESC_DTH);
RCPowerTrainTaskWait_20msec();
RCPowerTrainTaskWait_20msec();
esc_setspeed(ESC_BREAK);
}
void
esc_neutral(void){
esc_setspeed(ESC_N);
}
void
esc_reverse(void){
esc_neutral();
RCPowerTrainTaskWait_20msec();
RCPowerTrainTaskWait_20msec();
}
void
esc_change_drive_to_reverse(void){
esc_setspeed(ESC_BREAK);
RCPowerTrainTaskWait_20msec();
esc_neutral();
RCPowerTrainTaskWait_20msec();
}
TASK(RCPowerTrainTask){
int servo_pwm;
static boolean pre_g_isBrake = FALSE;
static SHIFT_STATE pre_g_ShiftState = SHIFT_N;
static int pre_g_accelerator = 0;
int esc_pwm_100nsec = 0;
syslog(LOG_INFO, "RCPowerTrainTask : Start!");
/* 周期設定 : 20m周期 */
sil_wrw_iop((void *)PWM_MAX_ADDR, UEC_TO_PWMCNT(20000));
/* ニュートラル */
esc_neutral();
servo_setangle(SERVO_N);
syslog(LOG_INFO, "RCPowerTrainTask : neutral");
while(1){
WaitEvent(RCPowerTrainEvt); /* 10msの作業時間待ち */
ClearEvent(RCPowerTrainEvt);
/*
* サーボの設定
* 左 32 から 右 -32 範囲
*/
/*
SERVO_LMAX SERVO_N SERVO_RMAX
1400 1570 1830
32 0 -32
*/
if(g_angle >= 0){
/* 左側操舵の場合 */
servo_pwm = SERVO_N - ((((SERVO_N - SERVO_LMAX) * 100) / (32 * 100)) * g_angle);
}
else {
/* 右側操舵の場合 */
servo_pwm = SERVO_N + ((((SERVO_RMAX - SERVO_N) * 100) / (32 * 100)) * (-g_angle));
}
servo_setangle(servo_pwm);
if(pre_g_isBrake != g_isBrake) {
/* ブレーキの状態が変化した場合 */
pre_g_isBrake = g_isBrake;
if (g_isBrake == FALSE) {
/* ノンブレーキ状態 */
syslog(LOG_INFO, "To non-braking");
if (g_ShiftState == SHIFT_R) {
esc_reverse();
}
}
else if (g_isBrake == TRUE) {
/* ブレーキ状態 */
syslog(LOG_INFO, "To braking");
if (pre_g_accelerator > 0){
esc_dbrak();
}
else {
esc_rbrak();
}
}
}
if (g_accelerator < 0){
g_ShiftState = SHIFT_D;
pre_g_ShiftState = SHIFT_D;
}
if (g_accelerator == 0){
g_ShiftState = SHIFT_N;
}
if (g_accelerator > 0){
if (pre_g_ShiftState == SHIFT_D){
esc_change_drive_to_reverse();
syslog(LOG_INFO, "RCPowerTrainTask : change drive to reverse");
}
g_ShiftState = SHIFT_R;
pre_g_ShiftState = SHIFT_R;
}
#if 0
if(pre_g_ShiftState != g_ShiftState) {
pre_g_ShiftState = g_ShiftState;
if(g_ShiftState == SHIFT_D){
esc_pwm_100nsec = ESC_DTH;
}else if(g_ShiftState == SHIFT_R){
esc_pwm_100nsec = ESC_RTH;
esc_reverse();
}
}
#endif
if(g_isBrake == TRUE){
/* ブレーキ状態 */
}else{
/* ノンブレーキ状態 */
if(g_ShiftState == SHIFT_N){
/* ニュートラル */
esc_neutral();
} else {
/* ニュートラル以外 */
/*
*
*/
if(g_accelerator == 0){
esc_pwm_100nsec = ESC_N;
}else{
if (g_ShiftState == SHIFT_D){
esc_pwm_100nsec = ESC_DTH + ((((ESC_DTH - ESC_DMAX)/64) * g_accelerator));
// * g_speed_gain/SPEED_GAIN_INIT
}
if (g_ShiftState == SHIFT_R){
esc_pwm_100nsec = ESC_RTH + ((((ESC_RMAX - ESC_RTH)/64) * g_accelerator));
// * g_speed_gain/SPEED_GAIN_INIT
}
}
esc_setspeed(esc_pwm_100nsec);
}
}
pre_g_accelerator = g_accelerator;
}
}
//////////////////////////////////////////////////////////////////////////
/*
* LED制御系
*/
static uint8 led0_enable = FALSE;
static uint8 led7_enable = FALSE;
void
set_led7(boolean enable){
led7_enable = enable;
}
void
set_led0(boolean enable){
led0_enable = enable;
}
#define PWM_CYCLE_100US 100
#define LED_SHIFT_CYCLE 10
#define PWM_MAX 100
int led_duty[8];
ALARMCALLBACK(ActiveLEDCycCb){
static int pwm_cyccnt = 0;
uint8 pattern = 0;
static int center_led = 6;
static int direction = 1; /* 1:right, 0:left */
static int led_shift_cnt = 0;
int i;
/* 100usec毎に呼び出される */
/* PWM周期 */
if (pwm_cyccnt++ >= PWM_CYCLE_100US){
pwm_cyccnt = 0;
}
if (pwm_cyccnt == 0) {
if(led_shift_cnt++ == LED_SHIFT_CYCLE){
led_shift_cnt = 0;
for(i = 0; i < 7; i++){
int pwm = PWM_MAX;
if (center_led > i){
pwm = PWM_MAX >> ((center_led - i) + 1);
}
else if (center_led < i){
pwm = PWM_MAX >> ((i - center_led) + 1);
}
else if (center_led == i){
pwm = PWM_MAX;
}
led_duty[i] = pwm;
}
if(direction == 1){
/* right */
if (--center_led <= 1){
direction = 0;
}
}
else {
/* left */
if (++center_led >= 6){
direction = 1;
}
}
}
}
for(i = 1; i < 7; i++){
if (pwm_cyccnt < led_duty[i]) {
pattern |= 1 << i;
}
}
if (led0_enable) {
pattern |= 0x01;
}
if (led7_enable) {
pattern |= 0x80;
}
set_led(pattern);
}
//////////////////////////////////////////////////////////////////////////
/*
* CANの初期化ルーチン
*/
void
can_init(void){
/*
* モードによらず全てのメールボックスを初期化する
*/
NcanInit(0);
NcanSetMailBoxInfo(0, BODY_CAN_MSG_TMB, DIR_SEND, 0, BODY_CAN_MSG_ID, 0, 0);
NcanSetMailBoxInfo(0, CONT_CMD_CAN_MSG_TMB, DIR_SEND, 0, CONT_CMD_CAN_MSG_ID, 0, 0);
NcanSetMailBoxInfo(0, BODY_CAN_MSG_RMB, DIR_RECV, 0, BODY_CAN_MSG_ID, 0, 0);
NcanSetMailBoxInfo(0, CONT_CMD_CAN_MSG_RMB, DIR_RECV, 0, CONT_CMD_CAN_MSG_ID, 0, 0);
NcanEnable(0);
}
//////////////////////////////////////////////////////////////////////////
/*
* スタートアップフックルーチン
*/
void
StartupHook(void)
{
syslog_initialize();
syslog_msk_log(LOG_UPTO(LOG_INFO));
InitSerial();
print_banner();
can_init();
rcb3_Init();
}
/*
* シャットダウンフックルーチン
*/
void
ShutdownHook(StatusType Error)
{
/* 終了ログ出力 */
syslog(LOG_INFO, "");
syslog(LOG_INFO, "Sample System ShutDown");
syslog(LOG_INFO, "ShutDownCode:%s", atk2_strerror(Error));
syslog(LOG_INFO, "");
if (Error == E_OS_SYS_ASSERT_FATAL) {
syslog(LOG_INFO, "fatal_file_name:%s", fatal_file_name);
syslog(LOG_INFO, "fatal_line_num:%d", fatal_line_num);
}
TermSerial();
}
//////////////////////////////////////////////////////////////////////////
/*
* コマンド受信処理
*/
static uint8
GetCommand(void)
{
uint8 command; /* コマンド受信バッファ */
/*
* コマンドを受信するまでループ
*/
command = '\0';
do {
WaitEvent(MainEvt); /* 10msウェイト */
ClearEvent(MainEvt);
RecvPolSerialChar(&command); /* 受信バッファポーリング */
if (command == '\n') {
command = '\0';
}
} while (command == '\0');
return(command);
} /* GetCommand */
/*
* メインタスク
*
* ユーザコマンドの受信と,コマンドごとの処理実行
*/
TASK(MainTask)
{
uint8 command;
uint8 task_no;
uint32 i;
/*
* タスク番号・コマンドバッファ初期化
*/
task_no = (uint8) (0);
for (i = 0U; i < (sizeof(command_tbl) / sizeof(command_tbl[0])); i++) {
command_tbl[i] = 0U;
}
syslog(LOG_INFO, "Main Task : start!");
#if 0
NcanSetMailBoxInfo(0, 0, DIR_RECV, 0, 3, 0, 0);
NcanSetMailBoxInfo(0, 0, DIR_SEND, 0, 4, 0, 0);
NcanEnable(0);
while(1){
WaitEvent(MainEvt); /* 10msの作業時間待ち */
ClearEvent(MainEvt);
NcanGetRxData(0, 0, &rx_data[0], &rx_size );
if (rx_size != 0) {
syslog(LOG_INFO, "Main Task : can receive 0x%x, 0x%x", rx_data[0], rx_data[1]);
}
i++;
if(i == 200){
syslog(LOG_INFO, "Main Task : alive");
i = 0;
tx_data[0] = cnt++;
tx_data[1] = 0x02;
NcanSetTxData(0, 0, 4, tx_data, 2);
}
}
#endif
/*
* コマンド実行ループ
*/
while (1) {
WaitEvent(MainEvt); /* 10msの作業時間待ち */
ClearEvent(MainEvt);
/*
* 入力コマンド取得
*/
syslog(LOG_INFO, "Input Command:");
command = GetCommand();
/*
* 入力コマンドチェック
*/
if ((command <= (uint8) (0x1fU)) || (command >= (uint8) (0x80U))) {
syslog(LOG_INFO, "Not ASCII character");
}
else {
syslog(LOG_INFO, "%c", command);
/*
* コマンド判別
*/
switch (command) {
case '1':
default:
/* 上記のコマンド以外の場合,処理を行わない */
break;
}
}
}
/*
* ここにはこない
*/
syslog(LOG_INFO, "MainTask TERMINATE");
error_log(TerminateTask());
} /* TASK( MainTask ) */
/*
* エラーフックルーチン
*/
#ifdef CFG_USE_ERRORHOOK
void
ErrorHook(StatusType Error)
{
/*
* エラー要因ごとのパラメータログ出力
*/
switch (OSErrorGetServiceId()) {
case OSServiceId_ActivateTask:
syslog(LOG_INFO, "Error:%s=ActivateTask(%d)", atk2_strerror(Error), OSError_ActivateTask_TaskID());
break;
case OSServiceId_TerminateTask:
syslog(LOG_INFO, "Error:%s=TerminateTask()", atk2_strerror(Error));
break;
case OSServiceId_ChainTask:
syslog(LOG_INFO, "Error:%s=ChainTask(%d)", atk2_strerror(Error), OSError_ChainTask_TaskID());
break;
case OSServiceId_Schedule:
syslog(LOG_INFO, "Error:%s=Schedule()", atk2_strerror(Error));
break;
case OSServiceId_GetTaskID:
syslog(LOG_INFO, "Error:%s=GetTaskID(0x%p)", atk2_strerror(Error), OSError_GetTaskID_TaskID());
break;
case OSServiceId_GetTaskState:
syslog(LOG_INFO, "Error:%s=GetTaskState(%d, 0x%p)", atk2_strerror(Error),
OSError_GetTaskState_TaskID(), OSError_GetTaskState_State());
break;
case OSServiceId_EnableAllInterrupts:
syslog(LOG_INFO, "Error:%s=EnableAllInterrupts()", atk2_strerror(Error));
break;
case OSServiceId_DisableAllInterrupts:
syslog(LOG_INFO, "Error:%s=DisableAllInterrupts()", atk2_strerror(Error));
break;
case OSServiceId_ResumeAllInterrupts:
syslog(LOG_INFO, "Error:%s=ResumeAllInterrupts()", atk2_strerror(Error));
break;
case OSServiceId_SuspendAllInterrupts:
syslog(LOG_INFO, "Error:%s=SuspendAllInterrupts()", atk2_strerror(Error));
break;
case OSServiceId_ResumeOSInterrupts:
syslog(LOG_INFO, "Error:%s=ResumeOSInterrupts()", atk2_strerror(Error));
break;
case OSServiceId_SuspendOSInterrupts:
syslog(LOG_INFO, "Error:%s=SuspendOSInterrupts()", atk2_strerror(Error));
break;
case OSServiceId_GetISRID:
syslog(LOG_INFO, "Error:%s=GetISRID()", atk2_strerror(Error));
break;
case OSServiceId_GetResource:
syslog(LOG_INFO, "Error:%s=GetResource(%d)", atk2_strerror(Error), OSError_GetResource_ResID());
break;
case OSServiceId_ReleaseResource:
syslog(LOG_INFO, "Error:%s=ReleaseResource(%d)", atk2_strerror(Error), OSError_ReleaseResource_ResID());
break;
case OSServiceId_SetEvent:
syslog(LOG_INFO, "Error:%s=SetEvent(%d, 0x%x)", atk2_strerror(Error),
OSError_SetEvent_TaskID(), OSError_SetEvent_Mask());
break;
case OSServiceId_ClearEvent:
syslog(LOG_INFO, "Error:%s=ClearEvent(0x%x)", atk2_strerror(Error), OSError_ClearEvent_Mask());
break;
case OSServiceId_GetEvent:
syslog(LOG_INFO, "Error:%s=GetEvent(%d, 0x%p)", atk2_strerror(Error),
OSError_GetEvent_TaskID(), OSError_GetEvent_Event());
break;
case OSServiceId_WaitEvent:
syslog(LOG_INFO, "Error:%s=WaitEvent(0x%x)", atk2_strerror(Error), OSError_WaitEvent_Mask());
break;
case OSServiceId_GetAlarmBase:
syslog(LOG_INFO, "Error:%s=GetAlarmBase(0x%p)", atk2_strerror(Error), OSError_GetAlarmBase_AlarmID());
break;
case OSServiceId_GetAlarm:
syslog(LOG_INFO, "Error:%s=GetAlarm(%d, 0x%p)", atk2_strerror(Error),
OSError_GetAlarm_AlarmID(), OSError_GetAlarm_Tick());
break;
case OSServiceId_SetRelAlarm:
syslog(LOG_INFO, "Error:%s=SetRelAlarm(%d, %d, %d)", atk2_strerror(Error),
OSError_SetRelAlarm_AlarmID(), OSError_SetRelAlarm_increment(), OSError_SetRelAlarm_cycle());
break;
case OSServiceId_SetAbsAlarm:
syslog(LOG_INFO, "Error:%s=SetAbsAlarm(%d, %d, %d)", atk2_strerror(Error),
OSError_SetAbsAlarm_AlarmID(), OSError_SetAbsAlarm_start(), OSError_SetAbsAlarm_cycle());
break;
case OSServiceId_CancelAlarm:
syslog(LOG_INFO, "Error:%s=CancelAlarm(%d)", atk2_strerror(Error), OSError_CancelAlarm_AlarmID());
break;
case OSServiceId_StartScheduleTableRel:
syslog(LOG_INFO, "Error:%s=StartScheduleTableRel(%d, %d)", atk2_strerror(Error),
OSError_StartScheduleTableRel_ScheduleTableID(), OSError_StartScheduleTableRel_Offset());
break;
case OSServiceId_StartScheduleTableAbs:
syslog(LOG_INFO, "Error:%s=StartScheduleTableAbs(%d, %d)", atk2_strerror(Error),
OSError_StartScheduleTableAbs_ScheduleTableID(), OSError_StartScheduleTableAbs_Start());
break;
case OSServiceId_StopScheduleTable:
syslog(LOG_INFO, "Error:%s=StopScheduleTable(%d)", atk2_strerror(Error), OSError_StopScheduleTable_ScheduleTableID());
break;
case OSServiceId_NextScheduleTable:
syslog(LOG_INFO, "Error:%s=NextScheduleTable(%d, %d)", atk2_strerror(Error),
OSError_NextScheduleTable_ScheduleTableID_From(), OSError_NextScheduleTable_ScheduleTableID_To());
break;
case OSServiceId_GetScheduleTableStatus:
syslog(LOG_INFO, "Error:%s=GetScheduleTableStatus(%d, 0x%p)", atk2_strerror(Error),
OSError_GetScheduleTableStatus_ScheduleTableID(), OSError_GetScheduleTableStatus_ScheduleStatus());
break;
case OSServiceId_GetActiveApplicationMode:
syslog(LOG_INFO, "Error:%s=GetActiveApplicationMode()", atk2_strerror(Error));
break;
case OSServiceId_StartOS:
syslog(LOG_INFO, "Error:%s=StartOS()", atk2_strerror(Error));
break;
case OSServiceId_ShutdownOS:
syslog(LOG_INFO, "Error:%s=ShutdownOS()", atk2_strerror(Error));
break;
case OSServiceId_IncrementCounter:
syslog(LOG_INFO, "Error:%s=IncrementCounter(%d)", atk2_strerror(Error), OSError_IncrementCounter_CounterID());
break;
case OSServiceId_TaskMissingEnd:
syslog(LOG_INFO, "Error:%s=MissingEnd()", atk2_strerror(Error));
break;
default:
syslog(LOG_INFO, "Error:%s=UnKnownFunc()", atk2_strerror(Error));
break;
}
} /* ErrorHook */
#endif /* CFG_USE_ERRORHOOK */
/*
* プレタスクフックルーチン
*
* 空ルーチンを呼出す
*/
#ifdef CFG_USE_PRETASKHOOK
void
PreTaskHook(void)
{
} /* PreTaskHook */
#endif /* CFG_USE_PRETASKHOOK */
/*
* ポストタスクフックルーチン
*
* 空ルーチンを呼出す
*/
#ifdef CFG_USE_POSTTASKHOOK
void
PostTaskHook(void)
{
} /* PostTaskHook */
#endif /* CFG_USE_POSTTASKHOOK */
/*
* プロテクションフックルーチン
*/
#ifdef CFG_USE_PROTECTIONHOOK
ProtectionReturnType
ProtectionHook(StatusType FatalError)
{
StatusType ercd;
syslog(LOG_INFO, "");
syslog(LOG_INFO, "ProtectionHook");
if (FatalError == E_OS_STACKFAULT) {
syslog(LOG_INFO, "E_OS_STACKFAULT");
ercd = PRO_SHUTDOWN;
}
else if (FatalError == E_OS_PROTECTION_EXCEPTION) {
syslog(LOG_INFO, "E_OS_PROTECTION_EXCEPTION");
ercd = PRO_IGNORE;
}
else {
ercd = PRO_SHUTDOWN;
}
return(ercd);
}
#endif /* CFG_USE_PROTECTIONHOOK */
source
参考資料(reference)
「TOPPERS活用アイデア・アプリケーション開発コンテスト受賞作品紹介」まとめ
https://qiita.com/kaizen_nagoya/items/72b882d96b2841f25faf
TOPPERS活用アイデア・アプリケーション開発コンテストを振り返る
https://researchmap.jp/joxkbxlck-1778110/
「応募すると何が嬉しい」TOPPERS活用アイデア・ アプリケーション開発コンテスト
https://www.slideshare.net/kaizenjapan/ss-78528931
「TOPPERS活用アイデア・アプリケーション開発コンテスト」への道
文書履歴(document history)
ver. 0.10 初稿 20180624
ver. 0.02 ありがとう追記 20230413
最後までおよみいただきありがとうございました。
いいね 💚、フォローをお願いします。
Thank you very much for reading to the last sentence.
Please press the like icon 💚 and follow me for your happy life.