/      English

Timer (PWM)関連のAHI関数と解説

TWENETライブラリ、Timer (PWM)関連のAHI関数と解説
TWENETライブラリ、Timer (PWM)関連のAHI関数と解説です。

Timer (PWM)

AHI の Timer 関連の API の一部について、ソースコード互換を取る目的で実装しています。

AHI APIについて

vAHI_TimerFineGrainDIOControl()

void vAHI_TimerFineGrainDIOControl(uint8 u8BitMask)

出力ピンを無効化するビットマスクを指定します。TIMER_0 … TIMER_4 に対応するビットのみ有効です。

  • vAHI_TimerEnable()実行前に本関数を呼び出します。
  • vAHI_TimerEnable() のパラメータで出力を有効化していても、ピンを無効化設定されている場合は、出力無効化として取り扱います。

vAHI_TimerAssignPIOPin_MW()

void vAHI_TimerAssignPIOPin_MW(
		uint8 u8_timer_id,
		uint8 u8_pin_id)

TWELITE GOLD専用です。

指定したタイマーデバイス(u8_timer_id)で使用するピンをPIO番号で指定します。

PIO番号には特定のPWMチャネルが紐づいています。またPWMが使用できないPIO番号もあります。指定方法によっては、重複したPWMチャネルを利用するといった矛盾した設定になる場合があります。PIO番号とPWMチャネルの割り当てについては、ピン配置表などを参照してください。

  • u8_timer_idは、対象のタイマーデバイス (E_AHI_DEVICE_TIMER0-4)を指定します。
  • vAHI_TimerFineGrainDIOControl()の設定も有効ですが、出力の有無はvAHI_TImerEnable()bOutputEnableで出力の制御を行います。
  • 出力を行わずタイマー割り込みのみを利用する場合でも、利用するPWMチャネルに対応したピン番号を指定します。

本ライブラリの独自関数です。

vAHI_TimerEnable()

void vAHI_TimerEnable(
    uint8       u8_timer_id,
    uint8       u8Prescale,
    bool_t      bIntRiseEnable,
    bool_t      bIntPeriodEnable,
    bool_t      bOutputEnable)

タイマーを有効化します。

  • bIntRiseEnable==TRUEの場合はbIntPeriodEnable==TRUEとして取り扱います。
  • bOutputEnable==TRUEの設定が行われてもvAHI_TimerFineGrainDIOControl()でピンが無効化されている場合はFALSEとして取り扱います。
  • すでに有効化したタイマーIDに対して、再度本関数を呼び出した場合の動作は不定です。
ハードウェア資源に矛盾がある場合

TWELITE BLUE/RED とのハードウェアの差異から、すべてのタイマーデバイスを同じように利用できるわけではありません。詳しくは後述のピン割当を参照してください。

  • PWM出力が有効になっている場合は、ソフトウェアでのPWM出力エミュレーションを行います。
  • PWM出力が無効になっている場合は、目的がタイマー割り込みと限定されるため、空いているPWM3またはPWM5をピン出力無しで利用します。
  • 上記割当を行ったかどうかを調べるAPIや手続きは用意していません。

vAHI_TimerDisable()

void  vAHI_TimerDisable(uint8 u8_timer_id)

タイマーを無効化します。

  • 出力ポートは入力(プルアップは設定変更しない)に戻します。

vAHI_TimerConfigure()

void vAHI_TimerConfigure(
		uint8       u8_timer_id,
		bool_t      bInvertPwmOutput,
		bool_t      bGateDisable)

タイマーの設定を変更します。

  • bInvertPwmOutputの設定を行います。
  • bGateDisableは無視されます。

vAHI_TimerStartRepeat()

void  vAHI_TimerStartRepeat(
		uint8       u8_timer_id,
	    uint16      u16Hi,
	    uint16      u16Lo)

タイマーを開始します。

  • この関数はタイマー動作中にも呼び出すことができ、PWMのDUTY設定を変更する目的で使用できます。

vAHI_TimerStop()

void  vAHI_TimerStop(uint8 u8_timer_id)

タイマーを停止します。

vAHI_TimerSetLocation()

void vAHI_TimerSetLocation(
		uint8 u8Timer,
		bool_t bLocation,
		bool_t bLocationOverridePWM3andPWM2)

ピンの割当変更を行います。

  • vAHI_TimerEnable()実行前に本関数を呼び出します。

vAHI_TimerXRegisterCallback

PUBLIC void  vAHI_Timer0RegisterCallback(
    PR_HWINT_APPCALLBACK        prTimer0Callback);
PUBLIC void  vAHI_Timer1RegisterCallback(
    PR_HWINT_APPCALLBACK        prTimer1Callback);
PUBLIC void vAHI_Timer2RegisterCallback(
    PR_HWINT_APPCALLBACK        prTimer2Callback);
PUBLIC void vAHI_Timer3RegisterCallback(
    PR_HWINT_APPCALLBACK        prTimer3Callback);
PUBLIC void vAHI_Timer4RegisterCallback(
    PR_HWINT_APPCALLBACK        prTimer4Callback);

割り込みハンドラの登録関数は実装されていません。AppQAPIにより割り込みハンドラが呼び出されます。

独自に割り込みハンドラの定義を行う場合は、以下のWEAK定義のハンドラ関数を実装します。実装についてはAHIcmpt_TImers.cppの実装を参考にしてください。少なくともPWM_ClearStatusFlags(PWM, kPWM_PwmX);を呼び出しておく必要があります。

WEAK void PWM0_DriverIRQHandler(void); // MONO WIRELESS, DEFINED AS WEAK FUNCTION.
WEAK void PWM1_DriverIRQHandler(void);
WEAK void PWM2_DriverIRQHandler(void);
WEAK void PWM3_DriverIRQHandler(void);
WEAK void PWM4_DriverIRQHandler(void);
WEAK void PWM5_DriverIRQHandler(void);
WEAK void PWM6_DriverIRQHandler(void);
WEAK void PWM7_DriverIRQHandler(void);
WEAK void PWM8_DriverIRQHandler(void);
WEAK void PWM9_DriverIRQHandler(void);

上記以外の関数

void vAHI_TimerClockSelect(
    uint8       u8Timer,
    bool_t      bExternalClock,
    bool_t      bInvertClock);
void vAHI_TimerStartSingleShot(
    uint8       u8Timer,
    uint16      u16Hi,
    uint16      u16Lo);

関数定義なし、または、何もしないダミー関数です。

出力ピンについて

  • 出力ピンは vAHI_TimerEnabled()呼び出し時に PWM 用途として初期化されます。
  • 出力ピンはvAHI_TimerDisable()呼び出し時に、入力ポート (プルアップ設定は設定を変えない) として最初期化します。

割り込みについて

周期途中の出力変化点での割り込みには対応しません。周期ごとの割り込みのみに対応します。

割り込みハンドラ

割り込みハンドラは、TWENET 標準の cbToCoNet_u8HwInt() , cbToCoNet_vHwEvent()のみに対応します。別途ハンドラを登録することはできません。

個別のハンドラを定義したい場合はPWMx_IRQHandler()関数を別途定義します。この場合、定義されたハンドラから TWENET へのイベント通知は行いません。

ピン割当

ピン割当は TIMER_ID 毎に個別に設定できますが、TWELITE BLACK ではハードウェアの違いから、割当が困難な場合があります。

標準

AHI TIMER ID01234
SMD PIN##1216131519
AHI DIO##1011121317
PIO##4013121
PWM channel40219

標準で DO1,2 を利用した場合

AHI TIMER ID01234
SMD PIN##12161219
AHI DIO##1011DO0DO117
PIO##400521
PWM channel400N/A9
  • TIMER_1, TIMER_2 の割当が衝突します。
  • TIMER_3 の出力ピンにはハードウェアタイマーの機能がありません。

副割当

AHI TIMER ID01234
SMD PIN##678910
AHI DIO##45678
PIO##768914
PWM channel76891

副割当で DO1,2 を利用した場合

AHI TIMER ID01234
SMD PIN##671910
AHI DIO##45DO0DO18
PIO##760514
PWM channel760N/A1
  • TIMER_3 の出力ピンにはハードウェアタイマーの機能がありません。

その他

ピン割り当てに矛盾が出たときの振る舞い

  • PWM出力設定をしている場合で矛盾が出たピン(そもそもPWM機能がないものなど)は、ソフトウェアでのエミュレーションになります。
    • ソフトウェアでのエミュレーションはシステムタイマー(SysTick)の割り込み処理下で16クロックを1周期として出力を制御します。1Khz で動作する場合は 1000/16 = 約62Hz の PWM 周期です。
  • PWM出力設定をしない場合で矛盾が出たピン(PWM デバイス番号の衝突)は、空いている PWM3 または PWM5 を割り当てます。ピン出力なしの場合でもPWM割り込みは動作します。

本ライブラリのPWM機能を利用しない場合

  • AHI のタイマー関連の API (?AHI_Timer???) を呼び出さないようにしてください。
    • 当該APIを呼び出すことで、AHI互換のための処理オブジェクトを生成します。この状態でfsl_pwm.hに定義されるAPIを呼び出した場合の振る舞いは未定義です。
  • PWM0_IRQHandler()PWM9_IRQHandler()を別途定義してください。これらはweakリンク指定されているので、アプリケーションで定義したweak指定のないものが優先してリンクされます。

スリープ復帰時の振る舞い

  • RAM保持スリープ時は、スリープ直前の PWM 出力状態の状態を復元します。RAM非保持の場合は、通常のDIO初期化を実施します。

関連AHI API

void vAHI_TimerFineGrainDIOControl(
    uint8 u8BitMask);
PUBLIC void vAHI_TimerConfigure(
    uint8       u8Timer,
    bool_t      bInvertPwmOutput,
    bool_t      bGateDisable);
PUBLIC void  vAHI_TimerEnable(
    uint8       u8Timer,
    uint8       u8Prescale,
    bool_t      bIntRiseEnable,
    bool_t      bIntPeriodEnable,
    bool_t      bOutputEnable);
PUBLIC void  vAHI_TimerDisable(
    uint8       u8Timer);
PUBLIC void  vAHI_TimerClockSelect(
    uint8       u8Timer,
    bool_t      bExternalClock,
    bool_t      bInvertClock);
PUBLIC void  vAHI_TimerStartRepeat(
    uint8       u8Timer,
    uint16      u16Hi,
    uint16      u16Lo);
PUBLIC void  vAHI_TimerStop(
    uint8 u8_timer_id);
PUBLIC void vAHI_TimerSetLocation(
    uint8 u8Timer,
    bool_t bLocation,
    bool_t bLocationOverridePWM3andPWM2);

 マクロで関数名が再定義されているものもあります。
 utils.h のタイマーライブラリも上記APIを利用します
ハンドラー定義例

最小限の手続きを含めた定義です。

void PWM0_IRQHandler(void) { PWM_ClearStatusFlags(PWM, kPWM_Pwm0); }
void PWM1_IRQHandler(void) { PWM_ClearStatusFlags(PWM, kPWM_Pwm1); }
void PWM2_IRQHandler(void) { PWM_ClearStatusFlags(PWM, kPWM_Pwm2); }
void PWM3_IRQHandler(void) { PWM_ClearStatusFlags(PWM, kPWM_Pwm3); }
void PWM4_IRQHandler(void) { PWM_ClearStatusFlags(PWM, kPWM_Pwm4); }
void PWM5_IRQHandler(void) { PWM_ClearStatusFlags(PWM, kPWM_Pwm5); }
void PWM6_IRQHandler(void) { PWM_ClearStatusFlags(PWM, kPWM_Pwm6); }
void PWM7_IRQHandler(void) { PWM_ClearStatusFlags(PWM, kPWM_Pwm7); }
void PWM8_IRQHandler(void) { PWM_ClearStatusFlags(PWM, kPWM_Pwm8); }
void PWM9_IRQHandler(void) { PWM_ClearStatusFlags(PWM, kPWM_Pwm9); }
  • この関数定義を行うとTWENETへの割り込み・イベント伝達は行われません。

本ライブラリの実装について

  • AHIcmpt_Timer.cpp には主要な実装コードが含まれます。

  • 上記コードは_periph_pwm.hpp, _periph_pwm.cppを引用しています。これらはプラットフォームドライバ(driver/fs_???)を用いた手続きをまとめたクラスライブラリです。