/*
 *	cliptimr.h
 *
 *	ユーティリティ：拡張タイマ
 *
 *	CLiP - Common Library for P/ECE
 *	Copyright (C) 2001-2015 Naoyuki Sawa
 *
 *	* Wed Nov 18 21:37:53 JST 2015 Naoyuki Sawa
 *	- 1st リリース。
 *	- 「ユーティリティ：拡張タイマ」を、(clippce.h,clippce.c)⇒(cliptimr.h,cliptimr.c)へ移動しました。
 *	  移動する事にした理由は、timer_start()とtimer_stop()を、Win32にも対応したからです。
 *	  (clippce.h,clippce.c)はP/ECE専用でありWin32プロジェクトには含められないので、別のファイルへ分離しました。
 */
#ifndef __CLIP_TIMR_H__
#define __CLIP_TIMR_H__

#ifdef  __cplusplus
extern "C" {
#endif//__cplusplus

/****************************************************************************
 *	ユーティリティ：拡張タイマ
 ****************************************************************************/

/* * 拡張タイマ機能を作成した理由は、以下のとおりです。
 *
 *   1. pceTimerSetCallback()は、同時利用可能なチャネルが少ない
 *	pceTimerSetCallback()は、Ch.0-3の4チャネルしか利用できません。
 *	(カーネル1.20においては、Ch.4も利用可能ですが、仕様外です)
 *	拡張タイマは、同時に32の拡張タイマを利用可能です。(2005/09/04現在)
 *	→2005/09/17 16個に減らしました。
 *	→2014/12/28 無制限になりました。					//{{2014/12/28変更:拡張タイマテーブルを、固定割り当て⇒動的割り当てに変更しました。}}
 *
 *   2. pceTimerSetCallback()は、チャネル衝突の回避が困難である
 *	pceTimerSetCallback()は、呼び出し側にてチャネル番号を指定するので、
 *	関連の無い複数のルーチンが同時にタイマを利用する場合、チャネル衝突の回避が困難です。
 *	拡張タイマは、timer_start()から呼び出し側へ拡張タイマIDを返すので、
 *	関連の無い複数のルーチンが同時にタイマを利用する場合も、チャネル衝突は有り得ません。
 *
 * * 拡張タイマ機能は、pceTimerSetCallback()のCh.0を利用しています。(2005/09/04現在)
 *   最初にtimer_start()を呼び出したとき、pceTimerSetCallback()のCh.0を設定します。
 *   以後、ライブラリの終了ルーチンにて自動的にタイマを停止するまで、そのままです。
 *   以下の点に注意してください。
 *
 *   1. pceTimerSetCallback()のCh.0を利用するアプリケーションと併用できません
 *	pceTimerSetCallback()のCh.0を利用するアプリケーションは、timer_start()を利用しないでください。
 *	timer_start()を利用するアプリケーションは、pceTimerSetCallback()のCh.0を利用しないでください。
 *	今後のプログラム作成方針として、アプリケーション、および、CLiPライブラリ内の各モジュールは、
 *	pceTimerSetCallback()のいずれのチャネルも利用せず、timer_start()を利用するようにしてください。
 *	(2005/09/04現在、clipcbxモジュールがpceTimerSetCallback()のCh.0を利用しています。いずれ修正する予定です)
 *
 *   2. timer_start()を呼び出すと、アプリケーション終了まで、一定のオーバーヘッドが発生します
 *	拡張タイマ機能は、pceTimerSetCallback()のCh.0を利用し、1ミリ秒コールバックにてドライブしています。
 *	アプリケーション実行後、初回のtimer_start()にて、pceTimerSetCallback()のCh.0を起動しています。
 *	(2005/09/04現在の実装は、簡単のために、timer_start()が呼ばれる度にpceTimerSetCallback()のCh.0を
 *	 再起動していますが、アプリケーションから見た挙動は、初回呼び出し時のみ起動と見なしても同じです)
 *	timer_start()を呼び出さないアプリケーションでは、拡張タイマ機能のオーバーヘッドは発生しません。
 *	一度でもtimer_start()を呼び出すと、アプリケーション終了まで1ミリ秒コールバックが継続するため、
 *	オーバーヘッドが発生します。(実際には、気にするほどの速度低下では無いかも知れませんが…)
 *	処理速度が重要なアプリケーションにおいては、無駄にtimer_start()を利用しないよう注意してください。
 */

/* 拡張タイマを開始します。
 * [in]
 *	interval	コールバック間隔[ms]。
 *			1以上の値を指定してください。1未満の値を指定すると、エラー終了します。
 *	callback	コールバック関数。
 *			コールバック関数の指定は必須です。NULLを指定すると、エラー終了します。
 *	context		コールバック引数。
 *			アプリケーションにて、自由に設定できます。
 * [out]
 *	戻り値		拡張タイマID。
 *			2005/09/10追記: これまで0〜31を返していましたが、1〜32となるよう変更しました。
 *			アプリケーションが保持している拡張タイマIDの、有効or無効を簡単にするためです。
 *			→2005/09/17 1〜16に減らしました。
 *			→2014/12/28 1〜∞に変更しました。			//{{2014/12/28変更:拡張タイマテーブルを、固定割り当て⇒動的割り当てに変更しました。}}
 * [note]
 *	* 2005/09/04現在、同時に32個までの拡張タイマが利用可能です。
 *	  同時に32個を超える拡張タイマを利用しようとすると、エラー終了します。
 *	  →2005/09/17 16個に減らしました。
 *	  →2014/12/28 無制限になりました。					//{{2014/12/28変更:拡張タイマテーブルを、固定割り当て⇒動的割り当てに変更しました。}}
 *	* 拡張タイマを停止せずに、アプリケーションを終了しても安全です。
 *	  アプリケーション終了時に、ライブラリが適切に拡張タイマを停止します。
 *	* 2005/09/17追記 コールバック引数の指定を追加しました。
 */
int timer_start(int interval, void (*callback)(void* context), void* context);

/* 拡張タイマを停止します。
 * [in]
 *	id		拡張タイマID。
 *			timer_start()から返された拡張タイマIDを指定してください。
 *			不正な拡張タイマIDや、既に停止した拡張タイマIDを指定すると、エラー終了します。
 */
void timer_stop(int id);

#ifdef  __cplusplus
}//extern "C"
#endif//__cplusplus

#endif//__CLIP_TIMR_H__
