[EtherCAT]
2025.12.30, EtherCAT CiA 402 v1.2.
您可以下載 EtherCAT CiA 402 使用手冊文件 這裡.
1. 簡介
1.1 關於 QEC MainDevice (MDevice)
QEC 主站是相容於 86Duino Coding IDE 501+ 的 EtherCAT 主站系統。它提供 EtherCAT 主站和 EtherCAT 從站設備之間的即時 EtherCAT 通訊。除了 86Duino IDE 的 EtherCAT 函式庫外,QEC 主站還提供 Modbus、Ethernet TCP/IP、CAN 匯流排等工業通訊協議,並使用豐富的高階 C/C++ 程式語言進行快速應用開發。
更多 EtherCAT 與 QEC 相關資訊,請參閱 EtherCAT API 使用手冊.
1.1.1 什麼是 86Duino IDE?
86Duino 整合開發環境 (IDE) 軟體可以輕鬆編寫程式碼並上傳到 86Duino 開發板和 QEC 主站裝置。它可以在 Windows、Mac OS X 和 Linux 上運行。環境採用Java編寫,基於 Arduino IDE、Processing、DJGPP 等開源軟體,可從以下連結下載: https://www.qec.tw/software/.

QEC 主站的軟體 86Duino IDE 也提供了一個設定實用程式:86EVA,這是一個圖形使用者介面工具,供使用者編輯 EtherCAT 網路的參數;其功能如下:
- EtherCAT 從站掃描
- 導入 ENI 文件
- 設定 EtherCAT 主站
- 配置 EtherCAT 從站
更多相關資訊,請參閱 86EVA 使用手冊.
1.2 關於 EthercatDevice_CiA402
EthercatDevice_CiA402 是一個通用的 CiA 402 EtherCAT 從站裝置類別,可用於控制任何支援 CiA 402 標準的 EtherCAT 伺服驅動器。
它提供了常用的CiA 402物件的存取函數以及多種CiA 402操作模式和功能組的操作函數,包括:
- 操作模式
- Profile Position (pp)
- Profile Velocity (pv)
- Profile Torque (tq)
- Homing (hm)
- Cyclic Synchronous Position (csp)
- Cyclic Synchronous Velocity (csv)
- Cyclic Synchronous Torque (cst)
- 功能組別
- Touch Probe
實施指令來自 CiA402 驅動設定檔.
基於 EtherCAT 伺服驅動器之 IEC 61800-7-201 使用規範
有關 CiA 402 的更多詳細信息,請參閱以下文件:
- CiA Draft Standard 402: CiA® 402-CANopen Drives and Motion Control Profile.
- CiA402 驅動設定檔的 ETG.6010 實作指令
- 目前使用的 CiA 402 驅動設備的使用手冊
EthercatDevice_CiA402 的類別關係如下圖所示:

- EthercatDevice_CiA402 繼承自 _EthercatDevice_CommonDriver.
有關 EtherCAT Device Class 的詳細資訊,請參閱 EtherCAT Library API 使用手冊.
1.2.1 驅動器與運動控制
裝置控制功能區塊控制驅動器的所有功能(驅動功能與電源區段)。它分為狀態機的裝置控制與操作模式功能。

controlword(控制字組)可控制驅動器的狀態。
驅動器的狀態顯示於 statusword(狀態字組)中。
在遠端模式(remote mode)下,裝置透過 PDO 與 SDO 直接由 CANopen 網路控制。
狀態機由 controlword 與外部訊號從外部進行控制。對 controlword 的寫入存取由選用的硬體訊號「Remote」控制。狀態機也會受到故障(faults)與操作模式(modes of operation)等內部訊號的控制。

1.2.2 狀態機
狀態機描述裝置狀態以及驅動器可能的控制順序。單一狀態代表一種特殊的內部或外部行為。驅動器的狀態也決定了哪些命令會被接受。例如,只有當驅動器處於 OPERATION ENABLE 狀態時,才能啟動點對點(point-to-point)移動。
狀態可使用 controlword 變更,及/或依據內部事件變更。目前的狀態可使用 statusword 讀取。

狀態說明
| 狀態 | 描述 |
| Not Ready to Switch On | 驅動器正在初始化或執行自我測試。煞車(若有)為作動狀態。功能停用。 |
| Switch On Disabled | 初始化完成,參數已設定。基於安全考量未施加高壓電。功能停用。 |
| Ready to Switch On | 可施加高壓電。可修改驅動器參數。功能停用。 |
| Switched On | 已施加高壓電。功率放大器就緒。可修改驅動器參數。功能停用。 |
| Operation Enable | 偵測到故障。驅動功能停用。高壓電是否切斷視應用而定。 |
| Quick Stop Active | 已執行快速停止。電源已移除,功能停用。若要恢復,請傳送 Enable Operation。 |
| Fault Reaction Active | 偵測到故障。正在執行快速停止。電源已移除,功能停用。 |
| Fault | 偵測到故障。驅動功能停用。高壓電是否切斷視應用而定。 |
注意事項:
- 若收到會造成狀態變更的命令,必須完整處理此命令並達到新狀態後,才能處理下一個命令。
- 「驅動功能停用(Drive function is disabled)」表示不供應能量給馬達。不同製造商可能以不同方式達成此狀態。參考值不會被處理。
- 「驅動功能啟用(Drive function is enabled)」表示可供應能量給馬達。參考值(轉矩、速度、位置)會被處理。
- 「發生故障(Fault occurred)」表示驅動器發生了故障。此情況下會轉移至 FAULT REACTION ACTIVE 狀態。在此狀態下,裝置會執行特殊的故障反應。執行此故障反應後,裝置會切換至 FAULT 狀態。此狀態只能透過「Fault Reset」命令離開,但僅限於故障已不再作動的情況。
2. 函式
本節將簡要介紹 EthercatDevice_CiA402 API 使用清單。
| 函式名稱 | 描述 | 可用於回呼(Callback) |
| 初始化相關函式 | ||
attach() | 初始化此 EtherCAT SubDevice 類別的物件。 | |
detach() | 取消初始化此 EtherCAT SubDevice 類別的物件。 | |
isStepper() | 檢查此 EtherCAT SubDevice 是否為步進馬達驅動器。 | O |
| 控制相關函式 | ||
getCiA402Mode() | 取得目前的操作模式。(6061h) | O1 |
setCiA402Mode() | 切換操作模式。(6060h, 6061h, 6502h) | O1, 2 |
getCiA402State() | 取得目前的 CiA 402 狀態。(6041h) | O |
setCiA402State() | 切換 CiA 402 狀態。(6040h, 6041h) | O2 |
enable() | 啟用驅動功能並對馬達供電。(6040h, 6041h) | O2 |
disable() | 停用驅動功能並對馬達斷電。(6040h, 6041h) | O2 |
| 操作相關函式 | ||
setTargetPosition() | 設定目標位置。(607Ah) | O1 |
setTargetVelocity() | 設定目標速度。(60FFh) | O1 |
setTargetTorque() | 設定目標轉矩。(6071h) | O1 |
setProfileAcceleration() | 設定輪廓加速度。(6083h) | O1 |
setProfileDeceleration() | 設定輪廓減速度。(6084h) | O1 |
setMaxAcceleration() | 設定最大加速度。(60C5h) | O1 |
setMaxDeceleration() | 設定最大減速度。(60C6h) | O1 |
setMaxProfileVelocity() | 設定最大輪廓速度。(607Fh) | O1 |
setMotionProfileType() | 設定運動輪廓類型。(6086h) | O1 |
setPositionWindow() | 設定位置窗(position window)。(6067h) | O1 |
setPositionWindowTime() | 設定位置窗時間。(6068h) | O1 |
setPositionOffset() | 設定位置偏移量。(60B0h) | O1 |
setSoftwarePositionLimit() | 設定軟體位置限制。(607Dh) | O1 |
setFollowingErrorWindow() | 設定跟隨誤差窗(following error window)。(6065h) | O1 |
setPositionPolarity() | 設定位置極性。(607Eh) | O1 |
setVelocityWindow() | 設定速度窗(velocity window)。(606Dh) | O1 |
setVelocityWindowTime() | 設定速度窗時間。(606Eh) | O1 |
setVelocityThreshold() | 設定速度閾值。(606Fh) | O1 |
setVelocityOffset() | 設定速度偏移量。(60B1h) | O1 |
setMaxMotorSpeed() | 設定最大馬達轉速。(6080h) | O1 |
setVelocityPolarity() | 設定速度極性。(607Eh) | O1 |
setTorqueOffset() | 設定轉矩偏移量。(60B2h) | O1 |
setMaxTorque() | 設定最大轉矩。(6072h) | O1 |
setPositiveTorqueLimit() | 設定正向轉矩限制。(60E0h) | O1 |
setNegativeTorqueLimit() | 設定負向轉矩限制。(60E1h) | O1 |
setQuickStopDeceleration() | 設定快速停止減速度。(6085h) | O1 |
setQuickStopOptionCode() | 設定快速停止選項碼。(605Ah) | |
setShutdownOptionCode() | 設定關機(shutdown)選項碼。(605Bh) | |
setDisableOperationOptionCode() | 設定停用操作選項碼。(605Ch) | |
setHaltOptionCode() | 設定暫停(halt)選項碼。(605Dh) | |
setFaultReactionOptionCode() | 設定故障反應選項碼。(605Eh) | |
getErrorCode() | 取得錯誤碼。(603Fh) | O1 |
getSupportedDriveModes() | 取得支援的驅動模式。(6502h) | O1 |
getMotorResolution() | 取得馬達解析度。(60EFh) | |
getPositionActualValue() | 取得實際位置值。(6064h) | O1 |
getVelocityActualValue() | 取得實際速度值。(606Ch) | O1 |
getTorqueActualValue() | 取得實際轉矩值。(6077h) | O1 |
getCurrentActualValue() | 取得實際電流值。(6078h) | O1 |
getPositionDemandValue() | 取得位置需求值(position demand value)。(6062h) | O1 |
getPositionDemandInternalValue() | 取得內部位置需求值。(60FCh) | O1 |
getPositionActualInternalValue() | 取得內部實際位置值。(6063h) | O1 |
getAdditionalPositionActualValue() | 取得額外實際位置值。(60E4h) | O1 |
getFollowingErrorActualValue() | 取得實際跟隨誤差值。(60F4h) | O1 |
getVelocityDemandValue() | 取得速度需求值。(606Bh) | O1 |
getTorqueDemandValue() | 取得轉矩需求值。(6074h) | O1 |
getDigitalInputs() | 取得數位輸入。(60FDh) | O1 |
| Profile Position 模式(pp)相關函式 | ||
pp_SetVelocity() | 設定輪廓速度。(6081h) | |
pp_SetAcceleration() | 設定輪廓加速度。(6083h) | |
pp_SetDeceleration() | 設定輪廓減速度。(6084h) | |
pp_SetMotionProfileType() | 設定運動輪廓類型。(6086h) | |
pp_Run() | 移動至目標位置。(6040h, 6041h, 607Ah) | |
pp_IsTargetReached() | 檢查是否已到達目標位置。(6041h) | O |
pp_CheckFollowingError() | 檢查是否發生跟隨誤差。(6041h) | O |
pp_Halt() | 暫停目前的操作。(6040h, 6041h) | |
pp_Resume() | 恢復已暫停的操作。(6040h, 6041h) | |
| Profile Velocity 模式(pv)相關函式 | ||
pv_SetAcceleration() | 設定輪廓加速度。(6083h) | |
pv_SetDeceleration() | 設定輪廓減速度。(6084h) | |
pv_SetMotionProfileType() | 設定運動輪廓類型。(6086h) | |
pv_Run() | 以目標速度連續移動。(6041h, 60FFh) | |
pv_IsTargetReached() | 檢查是否已到達目標速度。(6041h) | O |
pv_CheckZeroSpeed() | 檢查速度是否為零。(6041h) | O |
pv_CheckMaxSlippageError() | 檢查是否發生最大滑差誤差(maximum slippage error)。(6041h) | O |
pv_Halt() | 暫停目前的操作。(6040h, 6041h) | |
pv_Resume() | 恢復已暫停的操作。(6040h, 6041h) | |
| Profile Torque 模式(tq)相關函式 | ||
tq_SetTorqueSlope() | 設定轉矩斜率(torque slope)。(6087h) | |
tq_SetTorqueProfileType() | 設定轉矩輪廓類型。(6088h) | |
tq_SetMotorRatedCurrent() | 設定馬達額定電流。(6075h) | |
tq_SetMotorRatedTorque() | 設定馬達額定轉矩。(6076h) | |
tq_Run() | 以目標轉矩連續驅動。(6041h, 6071h) | |
tq_IsTargetReached() | 檢查是否已到達目標轉矩。(6041h) | O |
tq_Halt() | 暫停目前的操作。(6040h, 6041h) | |
tq_Resume() | 恢復已暫停的操作。(6040h, 6041h) | |
| Homing 模式(hm)相關函式 | ||
hm_SetHomeOffset() | 設定原點偏移量(home offset)。(607Ch) | |
hm_SetHomingMethod() | 設定歸原點方法。(6098h) | |
hm_SetHomingSpeeds() | 設定歸原點速度。(6099h) | |
hm_SetHomingAcceleration() | Set the homing acceleration. (609Ah) | |
hm_Run() | 啟動歸原點操作。(6040h, 6041h) | |
hm_IsAttained() | 檢查歸原點操作的狀態。(6041h) | O |
hm_Stop() | 停止歸原點操作。(6040h, 6041h) | |
| 功能群組「Touch Probe」相關函式 | ||
enableTouchProbe1() | 啟用 touch probe 1。(60B8h, 60B9h, 60D0h) | |
enableTouchProbe2() | 啟用 touch probe 2。(60B8h, 60B9h, 60D0h) | |
disableTouchProbe1() | 停用 touch probe 1。(60B8h, 60B9h) | |
disableTouchProbe2() | 停用 touch probe 2。(60B8h, 60B9h) | |
isTouchProbe1ValueReady() | 檢查 touch probe 1 訊號是否發生正緣或負緣。(60B9h) | O1 |
isTouchProbe2ValueReady() | 檢查 touch probe 2 訊號是否發生正緣或負緣。(60B9h) | O1 |
readTouchProbe1Value() | 讀取 touch probe 位置 1。(60BAh, 60BBh) | O1 |
readTouchProbe2Value() | 讀取 touch probe 位置 2。(60BCh, 60BDh) | O1 |
| 模式專屬流程控制的低階函式 | ||
setHaltBit() | 設定 controlword 中的 halt 位元。(6040h) | O |
isTargetReached() | 檢查是否已到達目標。(6041h) | O |
setModeSpecificBit4() | 設定 controlword 中的第 4 位元。(6040h) | O |
setModeSpecificBit5() | 設定 controlword 中的第 5 位元。(6040h) | O |
setModeSpecificBit6() | 設定 controlword 中的第 6 位元。(6040h) | O |
checkModeSpecificBit12() | 檢查 statusword 中第 12 位元的值。(6041h) | O |
checkModeSpecificBit13() | 檢查 statusword 中第 13 位元的值。(6041h) | O |
- 註 1: 若相關物件已對應(map)至 PDO,此函式可用於回呼函式中。
- 註 2: 在回呼中使用時,此函式會忽略逾時(timeout)參數,且不會等待實際值與設定值相符。
3. 範例
3.1 Profile Position(pp)控制
在支援 Profile Position 模式(pp)的 CiA 402 EtherCAT SubDevice 上實作位置控制。
- 朝正方向移動 10,000 單位的相對距離。
- 朝負方向移動 10,000 單位的相對距離。
以下為範例程式碼。
#include "Ethercat.h"
EthercatMaster master;
EthercatDevice_CiA402 motor;
void setup() {
master.begin();
motor.attach(0, master);
motor.setCiA402Mode(CIA402_PP_MODE);
master.start();
motor.enable();
motor.pp_SetMotionProfileType(0);
motor.pp_SetVelocity(100000);
motor.pp_SetAcceleration(5000);
motor.pp_SetDeceleration(5000);
}
void loop() {
motor.pp_Run(100000, CIA402_PP_RELATIVE, true);
while (motor.pp_IsTargetReached() == 0);
motor.pp_Run(-100000, CIA402_PP_RELATIVE, true);
while (motor.pp_IsTargetReached() == 0);
}3.2 在週期回呼中進行 Profile Position(pp)控制
在週期回呼(cyclic callback)中,於支援 Profile Position 模式(pp)的 CiA 402 EtherCAT SubDevice 上實作位置控制。
- 朝正方向移動 10,000 單位的相對距離。
- 朝負方向移動 10,000 單位的相對距離。
若要在週期回呼中操作,相關物件必須依下列方式對應至 PDO:
- 輸出 PDO(RxPDO)
- 物件 6040h:Controlword
- 物件 607Ah:Target position
- 輸入 PDO(TxPDO)
- 物件 6041h:Statusword
- 物件 6064h:Position actual value
以下為範例程式碼。
#include "Ethercat.h"
EthercatMaster master;
EthercatDevice_CiA402 motor;
#define STATE_SET_COMMAND (0)
#define STATE_CHECK_ACK_SET (1)
#define STATE_CHECK_ACK_CLEAR (2)
#define STATE_WAIT_TARGET_REACHED (3)
int state = STATE_SET_COMMAND;
int toggle = 0;
void MyCyclicCallback()
{
if (motor.getCiA402State() != CIA402_OPERATION_ENABLED)
return;
switch (state) {
case STATE_SET_COMMAND:
toggle = !toggle;
motor.setTargetPosition(100000 * toggle - 100000 * !toggle);
motor.setModeSpecificBit6(true);
motor.setModeSpecificBit5(false);
motor.setModeSpecificBit4(true);
state = STATE_CHECK_ACK_SET;
break;
case STATE_CHECK_ACK_SET:
if (motor.checkModeSpecificBit12()) {
motor.setModeSpecificBit4(false);
state = STATE_CHECK_ACK_CLEAR;
}
break;
case STATE_CHECK_ACK_CLEAR:
if (motor.checkModeSpecificBit12() == 0)
state = STATE_WAIT_TARGET_REACHED;
break;
case STATE_WAIT_TARGET_REACHED:
if (motor.pp_IsTargetReached())
state = STATE_SET_COMMAND;
break;
}
}
void setup() {
master.begin();
motor.attach(0, master);
motor.setCiA402Mode(CIA402_PP_MODE);
/* RxPDO mapping configuration. */
motor.sdoDownload8(0x1C12, 0x00, 0);
motor.sdoDownload8(0x1601, 0x00, 0);
motor.sdoDownload32(0x1601, 0x01, 0x60400010);
motor.sdoDownload32(0x1601, 0x02, 0x607A0020);
motor.sdoDownload8(0x1601, 0x00, 2);
motor.sdoDownload16(0x1C12, 0x01, 0x1601);
motor.sdoDownload8(0x1C12, 0x00, 1);
/* TxPDO mapping configuration. */
motor.sdoDownload8(0x1C13, 0x00, 0);
motor.sdoDownload8(0x1A01, 0x00, 0);
motor.sdoDownload32(0x1A01, 0x01, 0x60410010);
motor.sdoDownload32(0x1A01, 0x02, 0x60640020);
motor.sdoDownload8(0x1A01, 0x00, 2);
motor.sdoDownload16(0x1C13, 0x01, 0x1A01);
motor.sdoDownload8(0x1C13, 0x00, 1);
master.attachCyclicCallback(MyCyclicCallback);
master.start();
motor.enable();
motor.pp_SetMotionProfileType(0);
motor.pp_SetVelocity(100000);
motor.pp_SetAcceleration(5000);
motor.pp_SetDeceleration(5000);
}
void loop() {
// ...
}3.3 Profile Velocity(pv)控制
在支援 Profile Velocity 模式(pv)的 CiA 402 EtherCAT SubDevice 上實作速度控制。
- 以每秒 1,000 單位的速度朝正方向移動 3 秒。
- 以每秒 1,000 單位的速度朝負方向移動 3 秒。
以下為範例程式碼。
#include "Ethercat.h"
EthercatMaster master;
EthercatDevice_CiA402 motor;
void setup() {
master.begin();
motor.attach(0, master);
motor.setCiA402Mode(CIA402_PV_MODE);
master.start();
motor.enable();
motor.pv_SetMotionProfileType(0);
motor.pv_SetAcceleration(5000);
motor.pv_SetDeceleration(5000);
}
void loop() {
motor.pv_Run(1000);
while (motor.pv_IsTargetReached() == 0);
delay(3000);
motor.pv_Run(-1000);
while (motor.pv_IsTargetReached() == 0);
delay(3000);
}3.4 在週期回呼中進行 Profile Velocity(pv)控制
在支援 Profile Velocity 模式(pv)的 CiA 402 EtherCAT SubDevice 上實作速度控制。
- 以每秒 1,000 單位的速度朝正方向移動 3 秒。
- 以每秒 1,000 單位的速度朝負方向移動 3 秒。
若要在週期回呼中操作,相關物件必須依下列方式對應至 PDO:
- 輸出 PDO(RxPDO)
- 物件 6040h:Controlword
- 物件 60FFh:Target velocity
- 輸入 PDO(TxPDO)
- 物件 6041h:Statusword
- 物件 606Ch:Velocity actual value
以下為範例程式碼。
#include "Ethercat.h"
EthercatMaster master;
EthercatDevice_CiA402 motor;
int toggle = 0;
int cycle_count = 3000;
void MyCyclicCallback()
{
if (motor.getCiA402State() != CIA402_OPERATION_ENABLED)
return;
if (++cycle_count < 3000)
return;
cycle_count = 0;
toggle = !toggle;
motor.setTargetVelocity(1000 * toggle - 1000 * !toggle);
}
void setup() {
master.begin();
motor.attach(0, master);
motor.setCiA402Mode(CIA402_PV_MODE);
/* RxPDO mapping configuration. */
motor.sdoDownload8(0x1C12, 0x00, 0);
motor.sdoDownload8(0x1601, 0x00, 0);
motor.sdoDownload32(0x1601, 0x01, 0x60400010);
motor.sdoDownload32(0x1601, 0x02, 0x60FF0020);
motor.sdoDownload8(0x1601, 0x00, 2);
motor.sdoDownload16(0x1C12, 0x01, 0x1601);
motor.sdoDownload8(0x1C12, 0x00, 1);
/* TxPDO mapping configuration. */
motor.sdoDownload8(0x1C13, 0x00, 0);
motor.sdoDownload8(0x1A01, 0x00, 0);
motor.sdoDownload32(0x1A01, 0x01, 0x60410010);
motor.sdoDownload32(0x1A01, 0x02, 0x606C0020);
motor.sdoDownload8(0x1A01, 0x00, 2);
motor.sdoDownload16(0x1C13, 0x01, 0x1A01);
motor.sdoDownload8(0x1C13, 0x00, 1);
master.attachCyclicCallback(MyCyclicCallback);
master.start(1000000);
motor.enable();
motor.pv_SetMotionProfileType(0);
motor.pv_SetAcceleration(5000);
motor.pv_SetDeceleration(5000);
}
void loop() {
// ...
}3.5 Profile Torque(tq)控制
在支援 Profile Torque 模式(tq)的 CiA 402 EtherCAT SubDevice 上實作轉矩控制。
- 維持 50 單位的正向轉矩 3 秒。
- 維持 50 單位的負向轉矩 3 秒。
以下為範例程式碼。
#include "Ethercat.h"
EthercatMaster master;
EthercatDevice_CiA402 motor;
void setup() {
master.begin();
motor.attach(0, master);
motor.setCiA402Mode(CIA402_TQ_MODE);
master.start();
motor.enable();
motor.tq_SetTorqueProfileType(0);
motor.tq_SetTorqueSlope(200);
motor.tq_SetMotorRatedTorque(0);
motor.tq_SetMotorRatedCurrent(0);
}
void loop() {
motor.tq_Run(50);
while (motor.tq_IsTargetReached() == 0);
delay(3000);
motor.tq_Run(-50);
while (motor.tq_IsTargetReached() == 0);
delay(3000);
}3.6 在週期回呼中進行 Profile Torque(tq)控制
在支援 Profile Torque 模式(tq)的 CiA 402 EtherCAT SubDevice 上實作轉矩控制。
- 維持 50 單位的正向轉矩 3 秒。
- 維持 50 單位的負向轉矩 3 秒。
若要在週期回呼中操作,相關物件必須依下列方式對應至 PDO:
- 輸出 PDO(RxPDO)
- 物件 6040h:Controlword
- 物件 6071h:Target torque
- 輸入 PDO(TxPDO)
- 物件 6041h:Statusword
- 物件 6077h:Torque actual value
以下為範例程式碼。
#include "Ethercat.h"
EthercatMaster master;
EthercatDevice_CiA402 motor;
int toggle = 0;
int cycle_count = 3000;
void MyCyclicCallback()
{
if (motor.getCiA402State() != CIA402_OPERATION_ENABLED)
return;
if (++cycle_count < 3000)
return;
cycle_count = 0;
toggle = !toggle;
motor.setTargetTorque(50 * toggle - 50 * !toggle);
}
void setup() {
master.begin();
motor.attach(0, master);
motor.setCiA402Mode(CIA402_TQ_MODE);
/* RxPDO mapping configuration. */
motor.sdoDownload8(0x1C12, 0x00, 0);
motor.sdoDownload8(0x1601, 0x00, 0);
motor.sdoDownload32(0x1601, 0x01, 0x60400010);
motor.sdoDownload32(0x1601, 0x02, 0x60710010);
motor.sdoDownload8(0x1601, 0x00, 2);
motor.sdoDownload16(0x1C12, 0x01, 0x1601);
motor.sdoDownload8(0x1C12, 0x00, 1);
/* TxPDO mapping configuration. */
motor.sdoDownload8(0x1C13, 0x00, 0);
motor.sdoDownload8(0x1A01, 0x00, 0);
motor.sdoDownload32(0x1A01, 0x01, 0x60410010);
motor.sdoDownload32(0x1A01, 0x02, 0x60770010);
motor.sdoDownload8(0x1A01, 0x00, 2);
motor.sdoDownload16(0x1C13, 0x01, 0x1A01);
motor.sdoDownload8(0x1C13, 0x00, 1);
master.attachCyclicCallback(MyCyclicCallback);
master.start(1000000);
motor.enable();
motor.tq_SetTorqueProfileType(0);
motor.tq_SetTorqueSlope(200);
motor.tq_SetMotorRatedTorque(0);
motor.tq_SetMotorRatedCurrent(0);
}
void loop() {
// ...
}3.7 Homing(hm)操作
在符合 CiA 402 的 EtherCAT SubDevice 上啟動 歸原點方法 33(homing method 33) 操作。
以下為範例程式碼。
#include "Ethercat.h"
EthercatMaster master;
EthercatDevice_CiA402 motor;
void setup() {
master.begin();
motor.attach(0, master);
motor.setCiA402Mode(CIA402_HOMING_MODE);
master.start();
motor.enable();
motor.hm_SetHomingMethod(CIA402_HM33);
motor.hm_SetHomeOffset(0);
motor.hm_SetHomingSpeeds(100, 20);
motor.hm_SetHomingAcceleration(100);
motor.hm_Run();
while (motor.hm_IsAttained() == CIA402_HM_RUNNING);
}
void loop() {
// ...
}3.8 在週期回呼中進行週期同步位置(CSP)控制
在 CiA 402 EtherCAT SubDevice 上實作週期同步位置(Cyclic Synchronous Position,CSP)控制。
- 每個週期將目標位置遞增 1,000 單位。
若要在週期回呼中操作,相關物件必須依下列方式對應至 PDO:
- 輸出 PDO(RxPDO)
- 物件 6040h:Controlword
- 物件 607Ah:Target position
- 輸入 PDO(TxPDO)
- 物件 6041h:Statusword
- 物件 6064h:Position actual value
以下為範例程式碼。
#include "Ethercat.h"
EthercatMaster master;
EthercatDevice_CiA402 motor;
int32_t position = 0;
void MyCyclicCallback()
{
if (motor.getCiA402State() != CIA402_OPERATION_ENABLED)
return;
motor.setTargetPosition(position += 1000);
}
void setup() {
master.begin();
motor.attach(0, master);
motor.setDc(1000000);
motor.setCiA402Mode(CIA402_CSP_MODE);
/* RxPDO mapping configuration. */
motor.sdoDownload8(0x1C12, 0x00, 0);
motor.sdoDownload8(0x1601, 0x00, 0);
motor.sdoDownload32(0x1601, 0x01, 0x60400010);
motor.sdoDownload32(0x1601, 0x02, 0x607A0020);
motor.sdoDownload8(0x1601, 0x00, 2);
motor.sdoDownload16(0x1C12, 0x01, 0x1601);
motor.sdoDownload8(0x1C12, 0x00, 1);
/* TxPDO mapping configuration. */
motor.sdoDownload8(0x1C13, 0x00, 0);
motor.sdoDownload8(0x1A01, 0x00, 0);
motor.sdoDownload32(0x1A01, 0x01, 0x60410010);
motor.sdoDownload32(0x1A01, 0x02, 0x60640020);
motor.sdoDownload8(0x1A01, 0x00, 2);
motor.sdoDownload16(0x1C13, 0x01, 0x1A01);
motor.sdoDownload8(0x1C13, 0x00, 1);
master.attachCyclicCallback(MyCyclicCallback);
master.start(1000000, ECAT_SYNC);
motor.setTargetPosition(position = motor.getPositionActualValue());
motor.enable();
}
void loop() {
// ...
}3.9 在週期回呼中進行週期同步速度(CSV)控制
在 CiA 402 EtherCAT SubDevice 上實作週期同步速度(Cyclic Synchronous Velocity,CSV)控制。
- 每個週期將目標速度遞增 1 單位,直到達到 3,000 單位。
- 每個週期將目標速度遞減 1 單位,直到達到 -3,000 單位。
若要在週期回呼中操作,相關物件必須依下列方式對應至 PDO:
- 輸出 PDO(RxPDO)
- 物件 6040h:Controlword
- 物件 60FFh:Target velocity
- 輸入 PDO(TxPDO)
- 物件 6041h:Statusword
- 物件 606Ch:Velocity actual value
以下為範例程式碼。
#include "Ethercat.h"
EthercatMaster master;
EthercatDevice_CiA402 motor;
int32_t velocity = 0;
int toggle = 0;
void MyCyclicCallback()
{
if (motor.getCiA402State() != CIA402_OPERATION_ENABLED)
return;
if (abs(velocity) >= 3000)
toggle = !toggle;
velocity = velocity + toggle - !toggle;
motor.setTargetVelocity(velocity);
}
void setup() {
master.begin();
motor.attach(0, master);
motor.setDc(1000000);
motor.setCiA402Mode(CIA402_CSV_MODE);
/* RxPDO mapping configuration. */
motor.sdoDownload8(0x1C12, 0x00, 0);
motor.sdoDownload8(0x1601, 0x00, 0);
motor.sdoDownload32(0x1601, 0x01, 0x60400010);
motor.sdoDownload32(0x1601, 0x02, 0x60FF0020);
motor.sdoDownload8(0x1601, 0x00, 2);
motor.sdoDownload16(0x1C12, 0x01, 0x1601);
motor.sdoDownload8(0x1C12, 0x00, 1);
/* TxPDO mapping configuration. */
motor.sdoDownload8(0x1C13, 0x00, 0);
motor.sdoDownload8(0x1A01, 0x00, 0);
motor.sdoDownload32(0x1A01, 0x01, 0x60410010);
motor.sdoDownload32(0x1A01, 0x02, 0x606C0020);
motor.sdoDownload8(0x1A01, 0x00, 2);
motor.sdoDownload16(0x1C13, 0x01, 0x1A01);
motor.sdoDownload8(0x1C13, 0x00, 1);
master.attachCyclicCallback(MyCyclicCallback);
master.start(1000000, ECAT_SYNC);
motor.setTargetVelocity(0);
motor.enable();
}
void loop() {
// ...
}3.10 在週期回呼中進行週期同步轉矩(CST)控制
在 CiA 402 EtherCAT SubDevice 上實作週期同步轉矩(Cyclic Synchronous Torque,CST)控制。
- 每個週期將目標轉矩遞增 1 單位,直到達到 50 單位。
- 每個週期將目標轉矩遞減 1 單位,直到達到 -50 單位。
若要在週期回呼中操作,相關物件必須依下列方式對應至 PDO:
- 輸出 PDO(RxPDO)
- 物件 6040h:Controlword
- 物件 6071h:Target torque
- 輸入 PDO(TxPDO)
- 物件 6041h:Statusword
- 物件 6077h:Torque actual value
以下為範例程式碼。
#include "Ethercat.h"
EthercatMaster master;
EthercatDevice_CiA402 motor;
int16_t torque = 0;
int toggle = 0;
void MyCyclicCallback()
{
if (motor.getCiA402State() != CIA402_OPERATION_ENABLED)
return;
if (abs(torque) >= 50)
toggle = !toggle;
torque = torque + toggle - !toggle;
motor.setTargetTorque(torque);
}
void setup() {
master.begin();
motor.attach(0, master);
motor.setDc(1000000);
motor.setCiA402Mode(CIA402_CST_MODE);
/* RxPDO mapping configuration. */
motor.sdoDownload8(0x1C12, 0x00, 0);
motor.sdoDownload8(0x1601, 0x00, 0);
motor.sdoDownload32(0x1601, 0x01, 0x60400010);
motor.sdoDownload32(0x1601, 0x02, 0x60710010);
motor.sdoDownload8(0x1601, 0x00, 2);
motor.sdoDownload16(0x1C12, 0x01, 0x1601);
motor.sdoDownload8(0x1C12, 0x00, 1);
/* TxPDO mapping configuration. */
motor.sdoDownload8(0x1C13, 0x00, 0);
motor.sdoDownload8(0x1A01, 0x00, 0);
motor.sdoDownload32(0x1A01, 0x01, 0x60410010);
motor.sdoDownload32(0x1A01, 0x02, 0x60770010);
motor.sdoDownload8(0x1A01, 0x00, 2);
motor.sdoDownload16(0x1C13, 0x01, 0x1A01);
motor.sdoDownload8(0x1C13, 0x00, 1);
master.attachCyclicCallback(MyCyclicCallback);
master.start(1000000, ECAT_SYNC);
motor.setTargetTorque(0);
motor.enable();
}
void loop() {
// ...
}附錄
A.1 錯誤代碼
對於大多數函式,回傳值小於零表示有錯誤,該值代表錯誤代碼。如果有錯誤代碼,您可以在下面找到錯誤原因和糾正措施。
| 定義 | 代碼 |
ECAT_SUCCESS | 0 |
ECAT_ERR_MODULE_INIT_FAIL | -100 |
ECAT_ERR_MODULE_GET_VERSION_FAIL | -101 |
ECAT_ERR_MODULE_VERSION_MISMATCH | -102 |
ECAT_ERR_MODULE_GENERIC_TRANSFER_INIT_FAIL | -103 |
ECAT_ERR_MASTER_DOWNLOAD_SETTINGS_FAIL | -200 |
ECAT_ERR_MASTER_SET_DEVICE_SETTINGS_FAIL | -201 |
ECAT_ERR_MASTER_GET_GROUP_INFO_FAIL | -202 |
ECAT_ERR_MASTER_GET_MASTER_INFO_FAIL | -203 |
ECAT_ERR_MASTER_GET_DEVICE_INFO_FAIL | -204 |
ECAT_ERR_MASTER_SET_GROUP_SETTINGS_FAIL | -205 |
ECAT_ERR_MASTER_MAPPING_INIT_FAIL | -206 |
ECAT_ERR_MASTER_INTERRUPT_INIT_FAIL | -207 |
ECAT_ERR_MASTER_ACTIVE_FAIL | -208 |
ECAT_ERR_MASTER_ENI_INITCMDS_FAIL | -209 |
ECAT_ERR_MASTER_NO_DEVICE | -210 |
ECAT_ERR_MASTER_ACYCLIC_INIT_FAIL | -300 |
ECAT_ERR_MASTER_ACYCLIC_REQUEST_FAIL | -301 |
ECAT_ERR_MASTER_ACYCLIC_BUSY | -302 |
ECAT_ERR_MASTER_ACYCLIC_TIMEOUT | -303 |
ECAT_ERR_MASTER_ACYCLIC_ERROR | -304 |
ECAT_ERR_MASTER_ACYCLIC_WRONG_STATUS | -405 |
ECAT_ERR_MASTER_GENERIC_SEND_FAIL | -400 |
ECAT_ERR_MASTER_GENERIC_RECV_FAIL | -401 |
ECAT_ERR_MASTER_NOT_BEGIN | -1000 |
ECAT_ERR_MASTER_WRONG_BUFFER_SIZE | -1001 |
ECAT_ERR_MASTER_REDUNDANCY_NO_DC | -1002 |
ECAT_ERR_MASTER_MEMORY_ALLOCATION_FAIL | -1003 |
ECAT_ERR_MASTER_OSLAYER_INIT_FAIL | -1004 |
ECAT_ERR_MASTER_NIC_INIT_FAIL | -1005 |
ECAT_ERR_MASTER_BASE_INIT_FAIL | -1006 |
ECAT_ERR_MASTER_CIA402_INIT_FAIL | -1007 |
ECAT_ERR_MASTER_SETUP_PDO_FAIL | -1008 |
ECAT_ERR_MASTER_SCAN_NETWORK_FAIL | -1009 |
ECAT_ERR_MASTER_START_MASTER_FAIL | -1010 |
ECAT_ERR_MASTER_CYCLETIME_TOO_SMALL | -1011 |
ECAT_ERR_MASTER_DUMP_OUTPUT_PDO_FAIL | -1012 |
ECAT_ERR_MASTER_CONFIG_DEVICE_FAIL | -1013 |
ECAT_ERR_MASTER_CONFIG_MAPPING_FAIL | -1014 |
ECAT_ERR_MASTER_WAIT_BUS_SYNC_TIMEOUT | -1015 |
ECAT_ERR_MASTER_WAIT_MASTER_SYNC_TIMEOUT | -1016 |
ECAT_ERR_MASTER_CYCLIC_START_FAIL | -1017 |
ECAT_ERR_MASTER_WRONG_BUFFER_POINTER | -1018 |
ECAT_ERR_MASTER_ENI_INIT_FAIL | -1050 |
ECAT_ERR_MASTER_ENI_MISMATCH | -1051 |
ECAT_ERR_MASTER_STOPPED | -1100 |
ECAT_ERR_MASTER_STARTED | -1101 |
ECAT_ERR_MASTER_NOT_IN_PREOP | -1102 |
ECAT_ERR_MASTER_NOT_IN_SAFEOP | -1103 |
ECAT_ERR_MASTER_NOT_IN_OP | -1104 |
ECAT_ERR_MASTER_II_TRANSITION_FAIL | -1200 |
ECAT_ERR_MASTER_IP_TRANSITION_FAIL | -1201 |
ECAT_ERR_MASTER_PS_TRANSITION_FAIL | -1202 |
ECAT_ERR_MASTER_SO_TRANSITION_FAIL | -1203 |
ECAT_ERR_DEVICE_NOT_EXIST | -2000 |
ECAT_ERR_DEVICE_NOT_ATTACH | -2001 |
ECAT_ERR_DEVICE_NO_MAILBOX | -2002 |
ECAT_ERR_DEVICE_NO_DC | -2003 |
ECAT_ERR_DEVICE_WRONG_INPUT | -2004 |
ECAT_ERR_DEVICE_MEMORY_ALLOCATION_FAIL | -2005 |
ECAT_ERR_DEVICE_VENDOR_ID_MISMATCH | -2006 |
ECAT_ERR_DEVICE_PRODUCT_CODE_MISMATCH | -2007 |
ECAT_ERR_DEVICE_NO_SUCH_FUNCTION | -2008 |
ECAT_ERR_DEVICE_FUNCTION_NOT_INIT | -2009 |
ECAT_ERR_DEVICE_BUSY | -2010 |
ECAT_ERR_DEVICE_TIMEOUT | -2011 |
ECAT_ERR_DEVICE_NO_DATA | -2012 |
ECAT_ERR_DEVICE_SII_READ_FAIL | -2100 |
ECAT_ERR_DEVICE_SII_WRITE_FAIL | -2101 |
ECAT_ERR_DEVICE_PDO_NOT_EXIST | -2200 |
ECAT_ERR_DEVICE_PDO_OUT_OF_RANGE | -2201 |
ECAT_ERR_DEVICE_FOE_NOT_SUPPORT | -2300 |
ECAT_ERR_DEVICE_FOE_REQUEST_FAIL | -2310 |
ECAT_ERR_DEVICE_FOE_TIMEOUT | -2311 |
ECAT_ERR_DEVICE_FOE_ERROR | -2312 |
ECAT_ERR_DEVICE_FOE_BUFFER_TOO_SMALL | -2313 |
ECAT_ERR_DEVICE_FOE_READ_FAIL | -2314 |
ECAT_ERR_DEVICE_FOE_WRITE_FAIL | -2315 |
ECAT_ERR_DEVICE_COE_SDO_NOT_SUPPORT | -2400 |
ECAT_ERR_DEVICE_COE_SDO_INFO_NOT_SUPPORT | -2401 |
ECAT_ERR_DEVICE_COE_BUSY | -2410 |
ECAT_ERR_DEVICE_COE_REQUEST_FAIL | -2411 |
ECAT_ERR_DEVICE_COE_TIMEOUT | -2412 |
ECAT_ERR_DEVICE_COE_ERROR | -2413 |
ECAT_ERR_DEVICE_CIA402_NOT_EXIST | -2500 |
ECAT_ERR_DEVICE_CIA402_ADD_FAIL | -2501 |
ECAT_ERR_DEVICE_CIA402_TYPE_MISMATCH | -2502 |
ECAT_ERR_DEVICE_CIA402_NO_MODE_SUPPORT | -2503 |
ECAT_ERR_DEVICE_CIA402_WRONG_MODE | -2504 |
ECAT_ERR_DEVICE_CIA402_MODE_NOT_SUPPORT | -2505 |
ECAT_ERR_DEVICE_CIA402_CHANGE_WRONG_STATE | -2506 |
ECAT_ERR_DEVICE_CIA402_WRITE_OBJECT_FAIL | -2507 |
ECAT_ERR_DEVICE_CIA402_NO_SUCH_TOUCH_PROBE | -2580 |
ECAT_ERR_DEVICE_CIA402_NO_SUCH_TOUCH_PROBE_SOURCE | -2581 |
ECAT_ERR_DEVICE_EOE_NOT_SUPPORT | -2600 |
ECAT_ERR_DEVICE_EOE_NO_SUCH_PORT | -2601 |
ECAT_ERR_DEVICE_EOE_TOO_MUCH_CONTENT | -2602 |
ECAT_ERR_DEVICE_EOE_BUSY | -2610 |
ECAT_ERR_DEVICE_EOE_REQUEST_FAIL | -2611 |
ECAT_ERR_DEVICE_EOE_TIMEOUT | -2612 |
ECAT_ERR_GROUP_WRONG_INPUT | -3000 |
ECAT_ERR_GROUP_NOT_ATTACH | -3001 |
A.2 錯誤描述與修正措施
關於錯誤代碼說明和糾正措施。
A.3 SDO Abort Code(SDO 中止碼)
CoE SDO 中止碼定義於 ETG.1000.6:
| 值 | 含義 |
| 0x05030000 | 切換位元未變更。 |
| 0x05040000 | SDO 通訊協定逾時。 |
| 0x05040001 | 用戶端/伺服器命令指定符號無效或未知。 |
| 0x05040005 | 超出記憶體。 |
| 0x06010000 | 不支援物件的存取。 |
| 0x06010001 | 嘗試讀取只能寫入的物件。 |
| 0x06010002 | 嘗試寫入唯讀物件。 |
| 0x06010003 | 子索引無法寫入,SI0 必須為 0 才能進行寫入存取。 |
| 0x06010004 | 不支援 SDO 完全存取長度可變的物件,例如 ENUM 物件類型。 |
| 0x06010005 | 物件長度超出信箱大小。 |
| 0x06010006 | 物件對應至 RxPDO,SDO 下載受阻。 |
| 0x06020000 | 物件不存在於物件目錄中。 |
| 0x06040041 | 物件無法對應至 PDO。 |
| 0x06040042 | 要對應的物件數量和長度會超過 PDO 的長度。 |
| 0x06040043 | 一般參數不相容。 |
| 0x06040047 | 裝置內部不相容。 |
| 0x06060000 | 由於硬體錯誤,存取失敗。 |
| 0x06070010 | 資料類型不符,服務長度參數不符。 |
| 0x06070012 | 資料類型不符,服務長度參數太高。 |
| 0x06070013 | 資料類型不符,服務長度參數太低。 |
| 0x06090011 | 子索引不存在。 |
| 0x06090030 | 超出參數值範圍(僅限寫入存取)。 |
| 0x06090031 | 寫入的參數值太高。 |
| 0x06090032 | 寫入的參數值太低。 |
| 0x06090036 | 最大值小於最小值。 |
| 0x08000000 | 一般性錯誤。 |
| 0x08000020 | 資料無法傳輸或儲存至應用程式。 注意: 這是一般的中止代碼,無法確定原因的詳細資訊。建議使用其中一個更詳細的中止代碼。(0x08000021, 0x08000022) |
| 0x08000021 | 由於本機控制,資料無法傳輸或儲存至應用程式。 注意:「本機控制 」是指應用程式特有的原因。不是指 ESM 特有的控制。 |
| 0x08000022 | 由於目前的裝置狀態,資料無法傳輸或儲存至應用程式。 注意:「裝置狀態」是指 ESM 狀態。 |
| 0x08000023 | 物件字典動態產生失敗或沒有物件字典。 |
A.4 資料類型
ETG.1000.6 中定義的基本資料類型:
| 索引 (十六進制) | 物件類型 | 名稱 |
| 0001 | DEFTYPE | BOOLEAN |
| 0002 | DEFTYPE | INTEGER8 |
| 0003 | DEFTYPE | INTEGER16 |
| 0004 | DEFTYPE | INTEGER32 |
| 0005 | DEFTYPE | UNSIGNED8 |
| 0006 | DEFTYPE | UNSIGNED16 |
| 0007 | DEFTYPE | UNSIGNED32 |
| 0008 | DEFTYPE | REAL32 |
| 0009 | DEFTYPE | VISIBLE_STRING |
| 000A | DEFTYPE | OCTET_STRING |
| 000B | DEFTYPE | UNICODE_STRING |
| 000C | DEFTYPE | TIME_OF_DAY |
| 000D | DEFTYPE | TIME_DIFFERENCE |
| 000F | DEFTYPE | DOMAIN |
| 0010 | DEFTYPE | INTEGER24 |
| 0011 | DEFTYPE | REAL64 |
| 0012 | DEFTYPE | INTEGER40 |
| 0013 | DEFTYPE | INTEGER48 |
| 0014 | DEFTYPE | INTEGER56 |
| 0015 | DEFTYPE | INTEGER64 |
| 0016 | DEFTYPE | UNSIGNED24 |
| 0018 | DEFTYPE | UNSIGNED40 |
| 0019 | DEFTYPE | UNSIGNED48 |
| 001A | DEFTYPE | UNSIGNED56 |
| 001B | DEFTYPE | UNSIGNED64 |
| 001D | DEFTYPE | GUID |
| 001E | DEFTYPE | BYTE |
| 002D | DEFTYPE | BITARR8 |
| 002E | DEFTYPE | BITARR16 |
| 002F | DEFTYPE | BITARR32 |
A.5 關於 CiA DSP 402
CiA DSP 402 代表標準化的 CANopen 裝置設定檔(device profile),適用於伺服控制器、變頻器或步進馬達等數位控制運動產品。
上述所有裝置皆採用符合 CiA 標準草案 DS 301(CANopen Application Layer and Communication Profile)所述的通訊技術。在參考下方文件時應同時參閱此文件 CiA® 402-CANopen Drives and Motion Control Profile.
參考文獻
- ISO 7498, 1984, Information Processing Systems – Open Systems Interconnection – Basic Reference Model
- ISO 11898-1, 1999, Road Vehicles, Interchange of Digital Information – Controller Area Network (CAN) for high-speed Communication
- CiA DS 301, CANopen Application Layer and Communication Profile, Version 4.02, February 2002
- CiA DS 401, CANopen Device Profile I/O Modules, Version 2.1, May 2002
- DRIVECOM Profil Antriebstechnik/Profil 21
- DRIVECOM Profil Antriebstechnik/Servo 22, Jan. 1994
定義與縮寫
| 縮寫 | 定義 |
| CAN | Controller Area Network |
| CiA | CAN in Automation e. V. |
| COB | Communication Object (CAN message). A unit of transportation in a CAN network. Data must be sent across a network inside a COB. |
| COB-ID | COB-Identifier. Identifies a COB uniquely in a network. The identifier determines the priority of that COB in the MAC sub-layer too. |
| PDO | Process Data Object. Object for data exchange between several devices. |
| SDO | Service Data Object. Peer-to-peer communication with access to the object dictionary of a device. |
| pp | Profile Position Mode |
| pv | Profile Velocity Mode |
| vl | Velocity Mode |
| hm | Homing Mode |
| ip | Interpolated Position Mode |
| tq | Profile Torque Mode |
| all | Mandatory for all modes |
| ce | Common entries in the object dictionary |
| dc | Device Control |
| pc | Position Control Function |
A.6 物件字典項目(Object Dictionary Entries)
所有資訊皆遵循 CiA® 402-CANopen Drives and Motion Control Profile.
A.7 歸原點方法(Homing Methods)
所有資訊皆遵循 CiA® 402-CANopen Drives and Motion Control Profile.
86Duino 參考的文本是根據 知識共享署名-相同方式分享 3.0 許可證,部分文本是從 Arduino 參考 修改的。 參考中的代碼示例已發佈到公共領域。
如需更多資訊或樣品申請,請寄信至 info@icop.com.tw、致電最近的 ICOP 分支機構,或聯絡我們的全球官方經銷商。