2: 2016-03-30 (水) 18:10:04 takaboo ソース 現: 2016-04-12 (火) 18:04:08 takaboo ソース
Line 18: Line 18:
FreeRTOS関連。 FreeRTOS関連。
-[[ディレイ>#zedbb449]]~ -[[ディレイ>#zedbb449]]~
-正確な時間待ちや経過時間計測。+正確な時間待ちや経過時間計測。できるだけ使用頻度の低いMPUのリソースを使用。
-[[CRCチェックサム>#i0bff965]]~ -[[CRCチェックサム>#i0bff965]]~
-+Dynamixel V.2プロトコルで使用されるチェックサム。
-[[内蔵フラッシュ>#k264c73f]]~ -[[内蔵フラッシュ>#k264c73f]]~
マイコンに内蔵されたフラッシュメモリの書き換え。 マイコンに内蔵されたフラッシュメモリの書き換え。
--[[I2C>#]]~+-[[I2C>#e900926e]]~
外部のI2C対応デバイスとの通信。 外部のI2C対応デバイスとの通信。
--[[SPI>#]]~+-[[SPI>#g2fae75f]]~
外部のSPI対応デバイスとの通信。 外部のSPI対応デバイスとの通信。
--[[Dynamixelクライアント>#]]~ +-[[Dynamixel V.1ホスト>#y6cc2b6f]]~
-マイコンボード自体をDynamixelシリーズの様にクライアントとして機能。要FreeRTOS。 +
--[[Dynamixelホスト>#]]~+
外部のDynamixelシリーズと通信。要FreeRTOS。 外部のDynamixelシリーズと通信。要FreeRTOS。
 +-[[Dynamixel V.1クライアント>#s17315d5]]~
 +マイコンボード自体をDynamixelシリーズの様にクライアントとして機能。要FreeRTOS。
それ以外に処理系に依存しにくい体裁として、変数型の宣言の際は概ね以下を使用する事とします。 それ以外に処理系に依存しにくい体裁として、変数型の宣言の際は概ね以下を使用する事とします。
Line 42: Line 42:
***FreeRTOS [#uc14acff] ***FreeRTOS [#uc14acff]
FreeRTOSをCortex-M0コア用としてコンパイル及びライブラリ化し「TARGET/FREERTOS_CM0」フォルダに収録しています。必要に応じて同梱の「FreeRTOSConfig.h」を編集してライブラリを再構築する事もできます。~ FreeRTOSをCortex-M0コア用としてコンパイル及びライブラリ化し「TARGET/FREERTOS_CM0」フォルダに収録しています。必要に応じて同梱の「FreeRTOSConfig.h」を編集してライブラリを再構築する事もできます。~
-FreeRTOS自体は自信のプログラムの状態にかかわらず自由にリンクして使う事ができますので、OSが必要になった段階で適用の可否を判断したとしても影響が過大になることは少ないでしょう。~+FreeRTOS自体は自身のプログラムの状態にかかわらず自由にリンクして使う事ができますので、OSが必要になった段階で適用の可否を判断したとしても影響が過大になることは少ないでしょう。~
詳細は[[FreeRTOSのサイト>http://www.freertos.org/]]に委ねます。 詳細は[[FreeRTOSのサイト>http://www.freertos.org/]]に委ねます。
Line 48: Line 48:
正確な時間を元に時間待ちや経過時間を計測します。元となるクロックはMRT(Multi-Rate Timer)を使用しているため、各APIを定期的にコールする際は67秒以内(2147483647/32MHz)に行う必要があります。 正確な時間を元に時間待ちや経過時間を計測します。元となるクロックはMRT(Multi-Rate Timer)を使用しているため、各APIを定期的にコールする際は67秒以内(2147483647/32MHz)に行う必要があります。
-****delay_us [#o27b86b3] +****Delay_us [#o27b86b3] 
- extern void delay_us (uint32_t *mydelaybuf, uint32_t us); +マイクロ秒単位の時間待ちを行う。 
-****delay_ms [#ye3400d5] + void Delay_us (uint32_t *mydelaybuf, uint32_t us); 
- extern void delay_ms (uint32_t *mydelaybuf, uint32_t ms); +-パラメータ 
-****gettick_ms [#ta6cc319] +--uint32_t *'''mydelaybuf''' 
- extern uint32_t gettick_ms (uint32_t *mytickbuf); +~API内で使用されるカウンタ情報のポインタ~ 
-****delay_csw [#rd28843e] +APIが初回に呼び出される際は変数は必ず0に初期化しておく必要がある 
- extern void (*delay_csw) (void);+--uint32_t '''us''' 
 +~時間待ちする時間 
 +-戻り値 
 +~なし~ 
 +-使用例 
 +#html{{ 
 +<pre class="brush: c;"> 
 +#include <wl_delay.h> 
 + 
 +int main (void) { 
 +  uint32_t t = 0; 
 +  while (1) { 
 +   Delay_us (&t, 2000); 
 +  } 
 +
 +</pre> 
 +}} 
 + 
 +****Delay_ms [#ye3400d5] 
 +ミリ秒単位の時間待ちを行う。 
 + void Delay_ms (uint32_t *mydelaybuf, uint32_t ms); 
 +-パラメータ 
 +--uint32_t *'''mydelaybuf''' 
 +~API内で使用されるカウンタ情報のポインタ~ 
 +APIが初回に呼び出される際は変数は必ず0に初期化しておく必要がある 
 +--uint32_t '''ms''' 
 +~時間待ちする時間 
 +-戻り値 
 +~なし~ 
 +-使用例 
 +#html{{ 
 +<pre class="brush: c;"> 
 +#include <wl_delay.h> 
 + 
 +int main (void) { 
 +  uint32_t t = 0; 
 +  while (1) { 
 +   Delay_ms (&t, 1000); 
 +  } 
 +
 +</pre> 
 +}} 
 + 
 +****Delay_GetTick [#ta6cc319] 
 +本APIが始めて呼び出されてからの経過時間をミリ秒で返す。 
 + uint32_t Delay_GetTick (uint32_t *mytickbuf); 
 +-パラメータ 
 +--uint32_t *'''mytickbuf''' 
 +~API内で使用されるカウンタ情報のポインタ~ 
 +APIが初回に呼び出される際は変数は必ず0に初期化しておく必要がある 
 +-戻り値 
 +~経過時間~ 
 +-使用例 
 +#html{{ 
 +<pre class="brush: c;"> 
 +#include <wl_delay.h> 
 + 
 +void delay (uint32_t ms) { 
 +  uint32_t t = 0, target; 
 +  target = Delay_GetTick (&tt) + ms; 
 +  while (target > Delay_GetTick (&t)) ; 
 +
 + 
 +int main (void) { 
 +  while (1) { 
 +   delay (1000); 
 +  } 
 +
 +</pre> 
 +}} 
 + 
 +****Delay_csw [#rd28843e] 
 +API内の時間待ちの間に呼び出されるコールバックルーチンへのポインタを指定。~ 
 +デフォルトはNULLが指定されているため呼び出されない。 
 + void (*Delay_csw) (void); 
***CRCチェックサム [#i0bff965] ***CRCチェックサム [#i0bff965]
-X^16+X^15+X^2+1の多項式に限定したチェックサムを算出します。DynamixelプロトコルV2に使用されるチェックサムを目的としているため、それ以外のCRCを算出する用途には使えません。+X^16+X^15+X^2+1の多項式に限定した16ビット幅のチェックサムを算出します。DynamixelプロトコルV2に使用されるチェックサムを目的としているため、それ以外のCRCを算出する用途には使えません。
-なお、内蔵ペリフェラルもしくはソフトウェアによるCRCの算出が選択できます。+なお、APIの引数に応じて内蔵ペリフェラルもしくはソフトウェアによるCRCの算出が選択されます。~ 
 +また、CRCを算出する対象データの指定方法を複数用意しているのは、長大なデータが指定された場合の無駄なループ時間を削減する事が目的ですので、通常は CRC_Write か CRC_Writes で十分です。
-****ushpfunc [#p84a9123] 
- typedef uint8_t (*ushpfunc) (uint8_t c); 
****CRC_Init [#le5c5ca8] ****CRC_Init [#le5c5ca8]
- extern void CRC_Init (void);+CRCの計算に必要な事前処理を行う。 
 + void CRC_Init (void); 
 +-パラメータ 
 +~なし 
 +-戻り値 
 +~なし 
****CRC_SetSeed [#x02d7f5e] ****CRC_SetSeed [#x02d7f5e]
- extern void CRC_SetSeed (uint16_t *pCRC, uint16_t d);+CRCの初期値を設定する。 
 + void CRC_SetSeed (uint16_t *pCRC, uint16_t d); 
 +-パラメータ 
 +--uint16_t *'''pCRC''' 
 +~CRCの計算結果を保存する変数のポインタ。~ 
 +NULLを指定するとペリフェラルを使用した計算とみなす。 
 +--uint16_t '''d''' 
 +~CRCの初期値~ 
 +-戻り値 
 +~なし 
****CRC_Write [#o40f7223] ****CRC_Write [#o40f7223]
- extern void CRC_Write (uint16_t *pCRC, uint8_t d);+指定1バイトのCRCを算出する。 
 + void CRC_Write (uint16_t *pCRC, uint8_t d); 
 +-パラメータ 
 +--uint16_t *'''pCRC''' 
 +~CRCの計算結果を保存する変数のポインタ。~ 
 +NULLを指定するとペリフェラルを使用した計算とみなす。 
 +--uint8_t '''d''' 
 +~CRCを計算する対象データ 
 +-戻り値 
 +~なし 
****CRC_Writes [#u4cb3db5] ****CRC_Writes [#u4cb3db5]
- extern void CRC_Writes (uint16_t *pCRC, uint8_t *src, uint16_t len);+指定バイト数のCRCを算出する。 
 + void CRC_Writes (uint16_t *pCRC, uint8_t *src, uint16_t len); 
 +-パラメータ 
 +--uint16_t *'''pCRC''' 
 +~CRCの計算結果を保存する変数のポインタ。~ 
 +NULLを指定するとペリフェラルを使用した計算とみなす。 
 +--uint8_t *'''src''' 
 +~CRCを計算する対象データのポインタ 
 +--uint16_t '''len''' 
 +~CRCを計算する対象データのバイト数 
 +-戻り値 
 +~なし 
****CRC_Writes2 [#l6898efe] ****CRC_Writes2 [#l6898efe]
- extern void CRC_Writes2 (uint16_t *pCRC, uint8_t *dest, uint8_t *src, uint16_t len);+指定バイト数のCRCを算出しながらデータをコピーする。 
 + void CRC_Writes2 (uint16_t *pCRC, uint8_t *dest, uint8_t *src, uint16_t len); 
 +-パラメータ 
 +--uint16_t *'''pCRC''' 
 +~CRCの計算結果を保存する変数のポインタ。~ 
 +NULLを指定するとペリフェラルを使用した計算とみなす。 
 +--uint8_t *'''dest''' 
 +~srcのコピー先のポインタ 
 +--uint8_t *'''src''' 
 +~CRCを計算する対象データのポインタ 
 +--uint16_t '''len''' 
 +~CRCを計算する対象データのバイト数 
 +-戻り値 
 +~なし 
****CRC_Writes3 [#sf65d945] ****CRC_Writes3 [#sf65d945]
- extern void CRC_Writes3 (uint16_t *pCRC, ushpfunc pf, uint8_t *src, uint16_t len);+コールバックルーチンを呼び出しながら指定バイト数のCRCを算出する。 
 + void CRC_Writes3 (uint16_t *pCRC, uint8_t (*pf) (uint8_t), uint8_t *src, uint16_t len); 
 +-パラメータ 
 +--uint16_t *'''pCRC''' 
 +~CRCの計算結果を保存する変数のポインタ。~ 
 +NULLを指定するとペリフェラルを使用した計算とみなす。 
 +--uint8_t (*'''pf''') (uint8_t) 
 +~コールバックルーチンのポインタ 
 +--uint8_t *'''src''' 
 +~CRCを計算する対象データ 
 +--uint16_t '''len''' 
 +~CRCを計算する対象データのバイト数 
 +-戻り値 
 +~なし 
****CRC_Get [#qa44eba5] ****CRC_Get [#qa44eba5]
 +算出したCRCを取得する。~
 +なお、ソフトウェアによる算出を選択している場合は、本APIを使用せずとも変数にCRCが保存されている。
 uint16_t CRC_Get (uint16_t *pCRC);  uint16_t CRC_Get (uint16_t *pCRC);
 +-使用例
 +#html{{
 +<pre class="brush: c;">
 +#include <wl_crc.h>
 +
 +uint8_t data[] =  {0,1,2,3,4,5,6,7,8,9};
 +
 +uint16_t crc_hard (void) {
 +  CRC_SetSeed (NULL, 0);
 +  CRC_Writes (NULL, dat, sizeof (dat));
 +  return CRC_Get (NULL);
 +}
 +
 +uint16_t crc_soft (void) {
 +  uint16_t crc;
 +  CRC_SetSeed (&crc, 0);
 +  CRC_Writes (&crc, dat, sizeof (dat));
 +  return CRC_Get (&crc);
 +}
 +
 +int main (void) {
 +  CRC_Init ();
 +  crc1 ();
 +  crc2 ();
 +}
 +</pre>
 +}}
 +
***内蔵フラッシュ [#k264c73f] ***内蔵フラッシュ [#k264c73f]
 +****FLASH_Init [#g1e801f9]
 +ペリフェラルの初期化。
 + void FLASH_Init (void);
 +
****FLASH_Write [#q20989cf] ****FLASH_Write [#q20989cf]
 +指定されたフラッシュのアドレスへ指定されたバイト数のデータを書き込む。~
 +なお、コードが書き込まれた領域を侵さないアドレスを指定しなくてはならないが、本APIではそれらを判断しないまま消去及び書き込み処理を行う。
 bool FLASH_Write (uint32_t destaddr, uint8_t *dat8, uint32_t DataLengthByte);  bool FLASH_Write (uint32_t destaddr, uint8_t *dat8, uint32_t DataLengthByte);
 +***I2C [#e900926e]
 +***SPI [#g2fae75f]
 +***Dynamixel V.1ホスト [#y6cc2b6f]
 +本APIを使用する事でマイコンから直接アクチュエータが制御できます。
 +
 +****DX_OpenPort [#qc5d9135]
 +MPUのペリフェラルを初期化し、デバイスと通信できるようにする。
 + TDeviceID DX_OpenPort (const TDX_UsartFunc *us, uint32_t baud);
 +-パラメータ~
 +--const TDX_UsartFunc *'''us'''
 +--uint32_t '''baud'''
 +
 + typedef struct {
 +  uint8_t  *txbuff;
 +  uint32_t  txbufflength;
 +  uint8_t  *rxbuff;
 +  uint32_t  rxbufflength;
 + 
 +  uint32_t (*init) (uint32_t baudrate, uint8_t *txbuf, uint16_t txl, uint8_t *rxbuf, uint16_t rxl);
 +  uint32_t (*setbaudrate) (uint32_t);
 +  uint16_t (*rx_buff) (void);
 +  void (*rx_purge) (void);
 +  int (*putsb) (const uint8_t *, int);
 +  char (*getch) (void);
 + } TDX_UsartFunc;
 +
 +****DX_ClosePort [#v55bdc69]
 +宣言のみで使用できない。
 + bool DX_ClosePort (TDeviceID dvid);
 +
 +****DX_SetBaudrate [#pcf9495d]
 +ホストのボーレートを変更する。
 + bool DX_SetBaudrate (TDeviceID dvid, uint32_t baud);
 +
 +****DX_Active [#g2528f89]
 +ホストの通信機能が使用できるかを判断する。
 + bool DX_Active (TDeviceID dvid);
 +
 +****DX_SetTimeOutOffset [#e6714aa4]
 +デバイスからの応答の待ち時間のオフセット時間を指定。
 + void DX_SetTimeOutOffset (TDeviceID dvid, uint32_t t);
 +
 +****DX_TxPacket [#f5834acf]
 +任意のインストラクションパケットを送信する。~
 +コントロールテーブルを読み書きするAPIではサポートしていないパケットを送信する際に使用する事を目的としているため、不用意な使用は禁物。
 + bool DX_TxPacket (TDeviceID dvid, uint8_t id, TDXInstruction inst, uint8_t *param, uint32_t len, TDXErrCode *err);
 +
 +****DX_RxPacket [#k267f5b1]
 +ステータスパケットを受信する。~
 +コントロールテーブルを読み書きするAPIではサポートしていないパケットを送信した際にステータスパケットを受信する事を目的としているため、不用意な使用は禁物。
 + bool DX_RxPacket (TDeviceID dvid, uint8_t *rdata, uint32_t rdatasize, uint32_t *rlen, uint32_t timeout, TDXErrCode *err);
 +
 +****DX_ReadBlockData [#b63fc912]
 + bool DX_ReadBlockData (TDeviceID dvid, uint8_t id, uint16_t adr, uint8_t *rdata, uint32_t len, TDXErrCode *err);
 +****DX_ReadByteData [#o94606c9]
 +指定されたID・アドレスから1バイトの情報を読み出す。~
 + bool DX_ReadByteData (TDeviceID dvid, uint8_t id, uint16_t adr, uint8_t *rdata, TDXErrCode *err) {
 +
 +****DX_ReadWordData [#p29180cd]
 +指定されたID・アドレスから2バイトの情報を読み出す。~
 + bool DX_ReadWordData (TDeviceID dvid, uint8_t id, uint16_t adr, uint16_t *rdata, TDXErrCode *err) {
 +
 +****DX_ReadLongData [#o299bc6a]
 +指定されたID・アドレスから4バイトの情報を読み出す。~
 + bool DX_ReadLongData (TDeviceID dvid, uint8_t id, uint16_t adr, uint32_t *rdata, TDXErrCode *err) {
 +
 +****DX_WriteBlockData [#e0c7f55d]
 + bool DX_WriteBlockData (TDeviceID dvid, uint8_t id, uint16_t adr, uint8_t *dat, uint32_t len, TDXErrCode *err);
 +****DX_WriteByteData [#sb237648]
 +指定されたID・アドレスへ1バイトの情報を書き込む。~
 + bool DX_WriteByteData (TDeviceID dvid, uint8_t id, uint16_t adr, uint8_t dat, TDXErrCode *err) {
 +
 +****DX_WriteWordData [#sac477e6]
 +指定されたID・アドレスへ2バイトの情報を書き込む。~
 + bool DX_WriteWordData (TDeviceID dvid, uint8_t id, uint16_t adr, uint16_t dat, TDXErrCode *err) {
 +
 +****DX_WriteLongData [#eec903c0]
 +指定されたID・アドレスへ4バイトの情報を書き込む。~
 + bool DX_WriteLongData (TDeviceID dvid, uint8_t id, uint16_t adr, uint32_t dat, TDXErrCode *err) {
 +
 +****DX_ReadSyncData [#a7e72fb2]
 + bool DX_ReadSyncData (TDeviceID dvid, uint8_t *dat, uint32_t size, uint8_t *retdat, TDXErrCode *err);
 +****DX_WriteSyncData [#l1b6d662]
 + bool DX_WriteSyncData (TDeviceID dvid, uint8_t addr, uint16_t isize, uint8_t *dat, uint32_t size, TDXErrCode *err);
 +****DX_Ping [#cafa9999]
 + bool DX_Ping (TDeviceID dvid, uint8_t id, TDXErrCode *err);
 +****DX_Ping2 [#wdc57187]
 + bool DX_Ping2 (TDeviceID dvid, uint32_t *num, TDXAlarmStatus *AlarmStatus, TDXErrCode *err);
 +****DX_Reset [#wb4237c7]
 + bool DX_Reset (TDeviceID dvid, uint8_t id, TDXErrCode *err);
 +
 +***Dynamixel V.1クライアント [#s17315d5]
 +
 +****DX_Config [#sc3f2057]
 +コントロールテーブルの定義・基本シリアル通信API・各イベントにおけるコールバックルーチンを指定し、クライアント機能の初期設定を行う。~
 + bool DX_Config (TDX_ConfParam *pDX_ConfParam);
 +-パラメータ~
 +TDX_ConfParam *'''pDX_ConfParam'''~
 + typedef struct {
 +  struct {
 +   void *MemDefault;
 +   uint16_t CtrlTableSize;
 +   void (*wdt_feed) (void);
 +   void (*sys_reset) (void);
 +   uint32_t nvm_address;
 +   uint32_t nvm_size;
 +  } sys;
 +  struct {
 +   uint32_t (*us_init) (uint32_t);
 +   void (*us_deinit) (void);
 +   uint32_t (*us_setbaudrate) (uint32_t);
 +   uint16_t (*us_tx_buff) (void);
 +   uint16_t (*us_rx_buff) (void);
 +   void (*us_tx_purge) (void);
 +   void (*us_rx_purge) (void);
 +   int (*us_putsb) (const uint8_t *, int);
 +   char (*us_getc) (void);
 +  } us;
 +  struct {
 +   bool (*ValidPrevMapRange) (const void *pNewControlTable, uint8_t u_st, uint8_t u_len);
 +   bool (*ValidNextMapRange) (const void *pNewControlTable);
 +   void (*InitNVMValue) (void *pControlTable, const void *pNVMData);
 +   void (*ReadAction) (void *pCtrlTable);
 +   void (*WriteAction) (const void *pNewCtrlTable, void *pCtrlTable, bool force);
 +  } mem;
 + } TDX_ConfParam;
 +
 +****DX_ClientCommTask [#i4fc2a05]
 +初期設定の条件に従ってホストとの通信機能を行う。~
 +FreeRTOSの1つのタスクから呼び出す事。
 + void DX_ClientCommTask (void);
 +
 +****DX_WriteMem [#td20cea0]
 +通信タスク以外からコントロールテーブルへアクセスする。
 + bool DX_WriteMem (uint8_t adr, uint8_t *data, uint8_t size);
 +
 +****DX_ReadMem [#u5c70e57]
 +通信タスク以外からコントロールテーブルへアクセスする。
 + bool DX_ReadMem (uint8_t adr, uint8_t *data, uint8_t size);


トップ   差分 リロード印刷に適した表示   全ページ一覧 単語検索 最新ページの一覧   最新ページのRSS 1.0 最新ページのRSS 2.0 最新ページのRSS Atom