Windows版 iTRONサービスコールの作成 (時間管理機能)
(その3)

周期起動ハンドラを登録・生成する

周期起動ハンドラを登録または生成するサービスコールは以下のとおりです。


サービスコール名説明
def_cyc

周期起動ハンドラを登録します。(Ver3.0のみ)

cre_cyc

周期ハンドラID番号を指定して周期起動ハンドラを生成します。(Ver4.0のみ)

acre_cyc

周期ハンドラID番号を自動割付けで周期起動ハンドラを生成します。(Ver4.0のみ)

del_cyc

周期ハンドラを削除します。(Ver4.0のみ)

周期起動ハンドラを登録する (Ver3.0のみ)

周期起動ハンドラを登録するには以下のサービスコールを使用します。



    ER 	def_cyc( HNO cycno, const T_DCYC *pk_dcyc )
	

引数説明
cycno

周期ハンドラ番号。

pk_dcyc

周期ハンドラ定義情報構造体のポインタ。

戻り値説明
E_OK

正常終了。

E_ID

範囲外の周期ハンドラID番号。

E_PAR

パラメータエラー。


周期ハンドラ定義情報構造体(T_DCYC)は以下のとおりです。

メンバ名説明
exinf

拡張情報。

cycatr

周期ハンドラ属性。

周期ハンドラの起動方法を指定します。

  • TA_ASMの場合、アセンブリ言語用インターフェースで起動します。
  • TA_HLNGの場合、高級言語用インターフェースで起動します。
cychdr

周期ハンドラのアドレス。

cycact

周期ハンドラの活性状態。

周期ハンドラの起動・停止を指定します。

  • TCY_OFFの場合、周期ハンドラの停止します。
  • TCY_ONの場合、周期ハンドラの起動します。
cyctim

周期起動時間間隔。

・サービスコールのソースコードは以下のようになります。


/****************************************************************************/
/*!
 *  @brief  周期ハンドラ定義.
 *
 *  @param  [in]    cycno   周期ハンドラ番号.
 *  @param  [in]    pk_dcyc 周期ハンドラ定義情報.
 *
 *  @retval エラーコード.
 */
ER      def_cyc( HNO cycno, const T_DCYC *pk_dcyc )
{
    ER          ercd;
    WICYCOBJ    obj;

    //! 引数が不正な場合はエラーにする.
    if( !pk_dcyc ){
        return E_PAR;
    }
    //! 周期ハンドラ定義情報をコピーする.
    memset( &obj, 0, sizeof(WICYCOBJ) );
    obj.Attribute = pk_dcyc->cycatr;
    obj.CycAdr    = pk_dcyc->cychdr;
    obj.Active    = (pk_dcyc->cycact & TCY_ON) ? TRUE : FALSE;
    obj.ExtInfo   = pk_dcyc->exinf;
    obj.CycleTime = ((DWORDLONG)(pk_dcyc->cyctim.utime) << 32) + (DWORDLONG)(pk_dcyc->cyctim.ltime);

    wi_CommonLock();

    //! 周期ハンドラを登録する.
    ercd = wi_DefineCycleHadler( cycno, &obj, TRUE );

    wi_CommonUnlock();
    return ercd;
}
	

周期起動ハンドラの定義情報をコピーして、登録済みIDの場合の上書きを許可して周期ハンドラの登録関数を呼び出します。

周期ハンドラID番号を指定して周期起動ハンドラを生成する (Ver4.0のみ)

周期ハンドラID番号を指定して周期起動ハンドラを生成するには以下のサービスコールを使用します。



    ER cre_cyc( ID cycid, const T_CCYC *pk_ccyc )
	

引数説明
cycid

周期ハンドラID番号。

pk_ccyc

周期ハンドラ生成情報構造体のポインタ。

戻り値説明
E_OK

正常終了。

E_ID

範囲外の周期ハンドラID番号。

E_PAR

パラメータエラー。

E_OBJ

指定した周期ハンドラID番号は登録済み。


周期ハンドラ生成情報構造体(T_CCYC)は以下のとおりです。

メンバ名説明
cycatr

周期ハンドラ属性。

周期ハンドラの起動方法を指定します。

  • TA_ASMの場合、アセンブリ言語用インターフェースで起動します。
  • TA_HLNGの場合、高級言語用インターフェースで起動します。

TA_STAを指定した場合、周期ハンドラ生成後、周期ハンドラを起動します。

TA_PHSを指定した場合、周期ハンドラの起動位相を有効にします。(本ライブラリでは指定できません。)

exinf

拡張情報。

cychdr

周期ハンドラのアドレス。

cyctim

周期起動時間間隔。

cycphs

周期起動位相。(本ライブラリでは使用しません。)


・サービスコールのソースコードは以下のようになります。


/****************************************************************************/
/*!
 *  @brief  周期ハンドラの生成.
 *
 *  @param  [in]    cycid   周期ハンドラID番号.
 *  @param  [in]    pk_ccyc 周期ハンドラ生成情報構造体のポインタ.
 *
 *  @retval エラーコード.
 */
ER      cre_cyc( ID cycid, const T_CCYC *pk_ccyc )
{
    ER          ercd;
    WICYCOBJ    obj;

    //! 引数が不正な場合はエラーにする.
    if( !pk_ccyc ){
        return E_PAR;
    }
    //! 周期ハンドラ定義情報をコピーする.
    memset( &obj, 0, sizeof(WICYCOBJ) );
    obj.Attribute = pk_ccyc->cycatr;
    obj.CycAdr    = pk_ccyc->cychdr;
    obj.Active    = (pk_ccyc->cycatr & TA_STA) ? TRUE : FALSE;
    obj.ExtInfo   = pk_ccyc->exinf;
    obj.CycleTime = ((DWORDLONG)(pk_ccyc->cyctim.utime) << 32) + (DWORDLONG)(pk_ccyc->cyctim.ltime);
    obj.CyclePhs  = ((DWORDLONG)(pk_ccyc->cycphs.utime) << 32) + (DWORDLONG)(pk_ccyc->cycphs.ltime);

    wi_CommonLock();

    //! 周期ハンドラを登録する.
    ercd = wi_DefineCycleHadler( cycid, &obj, FALSE );

    wi_CommonUnlock();
    return ercd;
}
	

周期起動ハンドラの生成情報をコピーして、登録済みIDの場合の上書きを禁止して周期ハンドラの登録関数を呼び出します。

周期ハンドラID番号を自動割付けで周期起動ハンドラを生成する (Ver4.0のみ)

周期ハンドラID番号を自動割付けで周期起動ハンドラを生成するには以下のサービスコールを使用します。



    ER acre_cyc( const T_CCYC *pk_ccyc )
	

引数説明
pk_ccyc

周期ハンドラ生成情報構造体のポインタ。

戻り値説明
E_PAR

パラメータエラー。

E_NOID

ID番号不足。

上記以外の正数

生成した周期ハンドラのID番号。(正常終了)


・サービスコールのソースコードは以下のようになります。


/****************************************************************************/
/*!
 *  @brief  周期ハンドラの生成 (ID番号自動割り付け).
 *
 *  @param  [in]    pk_ccyc 周期ハンドラ生成情報構造体のポインタ.
 *
 *  @retval 生成した周期ハンドラのハンドラIDまたはエラーコード.
 */
ER      acre_cyc( const T_CCYC *pk_ccyc )
{
    ER_ID       ercd;
    ID          cycid;
    WICYCOBJ    obj;

    //! 引数が不正な場合はエラーにする.
    if( !pk_ccyc ){
        return E_PAR;
    }
    //! 周期ハンドラ定義情報をコピーする.
    memset( &obj, 0, sizeof(WICYCOBJ) );
    obj.Attribute = pk_ccyc->cycatr;
    obj.CycAdr    = pk_ccyc->cychdr;
    obj.Active    = (pk_ccyc->cycatr & TA_STA) ? TRUE : FALSE;
    obj.ExtInfo   = pk_ccyc->exinf;
    obj.CycleTime = ((DWORDLONG)(pk_ccyc->cyctim.utime) << 32) + (DWORDLONG)(pk_ccyc->cyctim.ltime);
    obj.CyclePhs  = ((DWORDLONG)(pk_ccyc->cycphs.utime) << 32) + (DWORDLONG)(pk_ccyc->cycphs.ltime);

    wi_CommonLock();

    for( cycid = 1; cycid < TMAX_MAXCYC; cycid++ ){

        //! 周期ハンドラを登録する.
        ercd = wi_DefineCycleHadler( cycid, &obj, FALSE );
        if( ercd == E_OK ){
            ercd = cycid;
            break;
        }
    }
    if( ercd == E_OBJ ){
        ercd  = E_NOID;
    }
    wi_CommonUnlock();
    return ercd;
}
	

周期ハンドラID番号を自動割付けで周期起動ハンドラを生成する関数は以下のような処理を行います。

  • cre_cyc()と同様に、サービスコールのエントリ関数内で引数の構造体のメンバをコピーし、登録済みIDの場合の上書きを禁止して周期起動ハンドラ登録関数を呼び出します。
  • 生成する周期起動ハンドラのID番号を1~TMAX_MAXCYCに+1づつカウントアップして、空いているID番号を探して周期起動ハンドラを生成します。
  • 周期起動ハンドラが生成できた場合、戻り値を生成した周期起動ハンドラのID番号にして処理を終了します。
  • 1~TMAX_MAXCYCの全てのID番号が使用中の場合、エラーコードが「E_OBJ(周期起動ハンドラ登録済み)」となるので、これを「E_NOID(ID番号不足)」に置き換えてエラー終了します。

周期起動ハンドラ登録関数

周期起動ハンドラ登録関数のソースコードは以下のとおりです。



/****************************************************************************/
/*!
 *  @brief  周期ハンドラ定義.
 *
 *  @param  [in]    no      周期ハンドラ番号.
 *  @param  [in]    obj     周期ハンドラ・オブジェクト構造体のポインタ.
 *  @param  [in]    ovr     TRUE = 登録済みIDに上書き.
 *
 *  @retval エラーコード.
 */
ER      wi_DefineCycleHadler( INT no, const WICYCOBJ *obj, BOOL ovr )
{
    ER          ercd;
    WICYCOBJ    *p;

    p = (WICYCOBJ *)wi_GetObject( no, ObjList );
    if( p ){
        //! 登録済みハンドラに上書き禁止の場合はエラー終了にする.
        if( !ovr ){
            return E_OBJ;
        }
        //! 既に登録しているハンドラ番号の場合は登録を上書きする.
        p->Hdr.Id    = no;
        p->Attribute = obj->Attribute;
        p->CycAdr    = obj->CycAdr;
        p->Active    = obj->Active;
        p->ExtInfo   = obj->ExtInfo;
        p->CycleTime = obj->CycleTime;
        p->StartTime = wi_GetSystemTime();
        return E_OK;
    }
    //! 周期ハンドラ・オブジェクトを作成する.
    p = (WICYCOBJ *)wi_CreateObject( no, TMAX_MAXCYC, sizeof(WICYCOBJ), obj, ObjList, &ercd );
    if( !p ){
        return ercd;
    }
    //! リストに周期ハンドラを追加する.
    wi_AddObject( (WIHDR *)p, &ObjList );
    return E_OK;
}
	

周期起動ハンドラ登録関数は以下のような処理を行います。

  • 既に生成されている周期ハンドラ番号の場合、上書きが許可されていれば、既存の周期ハンドラ・オブジェクト構造体に、新たに登録する周期ハンドラ・オブジェクト構造体を上書きします。上書きが許可されていない場合はエラーで終了します。
  • 生成されていない周期ハンドラ番号の場合、新しい周期ハンドラ・オブジェクトを生成します。
  • 周期ハンドラ・リストに生成した周期ハンドラ・オブジェクトをリンクして処理を終了します。

周期ハンドラを削除する

周期ハンドラを削除するには以下のサービスコールを使用します。



    ER del_cyc( ID cycid )
	

引数説明
cycid

周期ハンドラID番号。

戻り値説明
E_OK

正常終了。

E_ID

範囲外の周期ハンドラID番号。

E_NOEXS

指定した周期ハンドラID番号は登録されていない。


・サービスコールのソースコードは以下のようになります。


/****************************************************************************/
/*!
 *  @brief  周期ハンドラの削除.
 *
 *  @param  [in]    cycid   周期ハンドラID番号.
 *
 *  @retval エラーコード.
 */
ER      del_cyc( ID cycid )
{
    ER ercd;

    wi_CommonLock();

    //! 周期ハンドラを削除する.
    ercd = wi_DeleteCycleHadler( cycid );

    wi_CommonUnlock();
    return ercd;
}
	

削除する周期ハンドラのID番号を引数として周期ハンドラ削除関数を呼び出します。

周期ハンドラ削除関数

周期ハンドラ削除関数のソースコードは以下のとおりです。



/****************************************************************************/
/*!
 *  @brief  周期ハンドラの削除.
 *
 *  @param  [in]    no      周期ハンドラ番号.
 *
 *  @retval エラーコード.
 */
ER      wi_DeleteCycleHadler( INT no )
{
    ER          ercd;
    WICYCOBJ    *p;

    //! 周期ハンドラ番号のオブジェクトを取得する.
    p = (WICYCOBJ *)wi_FindObject( no, TMAX_MAXCYC, ObjList, &ercd );
    if( !p ){
        return ercd;
    }
    //! リストから該当する周期ハンドラを取り除く.
    wi_DelObject( (WIHDR *)p, &ObjList );

    //! 周期ハンドラ・オブジェクト構造体を解放する.
    SAFE_RELEASE( p );
    return E_OK;
}
	

周期ハンドラ削除関数は以下のような処理を行います。

  • 引数で指定された周期ハンドラ番号に該当する周期ハンドラ・オブジェクトを取り出します。
  • 周期ハンドラ・オブジェクトのリストから削除するオブジェクトを外します。
  • 周期ハンドラ・オブジェクトのために確保したメモリを解放して処理を終了します。


Windowsは米国Microsoft Corporationの登録商標です。