eae-basic-fb

Compare original and translation side by side

🇺🇸

Original

English
🇨🇳

Translation

Chinese

EAE Basic Function Block Creation

EAE基础功能块创建

Create or modify Basic FBs with state machine logic (ECC) and Structured Text algorithms.
CRITICAL RULE: ALWAYS use this skill for ANY operation on Basic FB files.
  • Creating new Basic FBs
  • Modifying existing Basic FBs (adding events, variables, states, algorithms)
  • NEVER directly edit
    .fbt
    files outside of this skill
Basic FB = State Machine + Algorithms
  • ECC (Execution Control Chart) for state transitions
  • Algorithms in ST (Structured Text) for computation
  • No internal FBNetwork (unlike Composite)
创建或修改带有状态机逻辑(ECC)和结构化文本(ST)算法的基础功能块(Basic FB)。
重要规则: 对Basic FB文件执行任何操作时,必须使用本技能。
  • 创建新的Basic FB
  • 修改现有Basic FB(添加事件、变量、状态、算法)
  • 切勿在本技能之外直接编辑
    .fbt
    文件
基础功能块(Basic FB)= 状态机 + 算法
  • ECC(执行控制图)用于状态转换
  • 采用ST(结构化文本)算法进行计算
  • 无内部FBNetwork(与复合功能块不同)

Quick Start

快速开始

User: Create a Basic FB called Calculator in MyLibrary that multiplies two REALs
Claude: [Creates .fbt with ECC + REQ algorithm: Result := Value1 * Value2]
用户:在MyLibrary中创建一个名为Calculator的Basic FB,用于计算两个REAL类型数值的乘积
Claude:[创建包含ECC和REQ算法的.fbt文件:Result := Value1 * Value2]

Triggers

触发方式

  • /eae-basic-fb
  • /eae-basic-fb --register-only
    - Register existing Basic FB (used by eae-fork orchestration)
  • "create basic FB"
  • "modify basic FB"
  • "add event to basic FB"
  • "add variable to basic FB"
  • "create block with algorithm"
  • "create state machine FB"

  • /eae-basic-fb
  • /eae-basic-fb --register-only
    - 注册现有Basic FB(由eae-fork编排工具使用)
  • "创建基础功能块"
  • "修改基础功能块"
  • "为基础功能块添加事件"
  • "为基础功能块添加变量"
  • "创建带算法的功能块"
  • "创建状态机功能块"

Register-Only Mode (for eae-fork Orchestration)

仅注册模式(用于eae-fork编排)

When called with
--register-only
, this skill skips file creation and only performs dfbproj registration. This mode is used by eae-fork to complete the fork workflow after file transformation.
/eae-basic-fb --register-only {BlockName} {Namespace}
What --register-only does:
  1. Registers in dfbproj - Adds ItemGroup entries for Basic FB visibility
What --register-only does NOT do:
  • Create IEC61499 files (.fbt, etc.) - already done by eae-fork
  • Update namespaces - already done by eae-fork
当使用
--register-only
调用时,本技能会跳过文件创建,仅执行dfbproj注册。该模式由eae-fork用于在文件转换完成后完成分支工作流。
/eae-basic-fb --register-only {BlockName} {Namespace}
--register-only的作用:
  1. 在dfbproj中注册 - 添加ItemGroup条目以确保Basic FB可见
--register-only不执行的操作:
  • 创建IEC61499文件(.fbt等)- 已由eae-fork完成
  • 更新命名空间 - 已由eae-fork完成

Usage

使用方法

bash
undefined
bash
undefined

Register a forked Basic FB

注册分支后的Basic FB

python ../eae-skill-router/scripts/register_dfbproj.py MyBasicFB SE.ScadapackWWW --type basic
python ../eae-skill-router/scripts/register_dfbproj.py MyBasicFB SE.ScadapackWWW --type basic

Verify registration

验证注册

python ../eae-skill-router/scripts/register_dfbproj.py MyBasicFB SE.ScadapackWWW --type basic --verify

---
python ../eae-skill-router/scripts/register_dfbproj.py MyBasicFB SE.ScadapackWWW --type basic --verify

---

Modification Workflow

修改工作流

When modifying an existing Basic FB:
  1. Read the existing
    .fbt
    file to understand current structure
  2. Identify what needs to be added/changed
  3. Generate new hex IDs for any new Events or VarDeclarations
  4. Update the
    .fbt
    file with the changes
  5. Update event-variable associations (
    <With Var="...">
    ) if needed
  6. Add new ECC states/transitions if adding new events
  7. Add/update algorithms if needed

修改现有Basic FB时:
  1. 读取现有的
    .fbt
    文件,了解当前结构
  2. 确定需要添加/修改的内容
  3. 为任何新的Event或VarDeclaration生成新的十六进制ID
  4. 更新
    .fbt
    文件中的更改
  5. 如有需要,更新事件-变量关联(
    <With Var="...">
  6. 如果添加新事件,添加新的ECC状态/转换
  7. 如有需要,添加/更新算法

Files Generated

生成的文件

FilePurpose
{Name}.fbt
Main block with ECC + algorithms
{Name}.doc.xml
Documentation
{Name}.meta.xml
Metadata
Location:
IEC61499/

文件用途
{Name}.fbt
包含ECC和算法的主功能块文件
{Name}.doc.xml
文档文件
{Name}.meta.xml
元数据文件
位置:
IEC61499/

Workflow

工作流

  1. Generate GUID for FBType
  2. Generate hex IDs for each Event and VarDeclaration
  3. Create
    .fbt
    with:
    • <!DOCTYPE FBType SYSTEM "../LibraryElement.dtd">
    • <Identification Standard="61499-2" />
    • Standard events (INIT/REQ/INITO/CNF)
    • ECC with START, INIT, REQ states
    • Algorithms in ST
  4. Create
    .doc.xml
    and
    .meta.xml
  5. Register in
    .dfbproj

  1. 为FBType生成GUID
  2. 为每个Event和VarDeclaration生成十六进制ID
  3. 创建
    .fbt
    文件,包含:
    • <!DOCTYPE FBType SYSTEM "../LibraryElement.dtd">
    • <Identification Standard="61499-2" />
    • 标准事件(INIT/REQ/INITO/CNF)
    • 包含START、INIT、REQ状态的ECC
    • ST算法
  4. 创建
    .doc.xml
    .meta.xml
    文件
  5. .dfbproj
    中注册

Basic FB Template

基础功能块模板

xml
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE FBType SYSTEM "../LibraryElement.dtd">
<FBType Name="{BlockName}" Namespace="{YourNamespace}"
        GUID="{NEW-GUID}" Comment="{Description}">
  <Identification Standard="61499-2" />
  <VersionInfo Organization="{Org}" Version="0.0" Author="{Author}"
               Date="{MM/DD/YYYY}" Remarks="Initial version" />
  <CompilerInfo />
  <InterfaceList>
    <EventInputs>
      <Event ID="{HEX-ID}" Name="INIT" Comment="Initialization Request">
        <With Var="QI" />
      </Event>
      <Event ID="{HEX-ID}" Name="REQ" Comment="Normal Execution Request">
        <With Var="QI" />
        <!-- Add With Var for each input used in REQ -->
      </Event>
    </EventInputs>
    <EventOutputs>
      <Event ID="{HEX-ID}" Name="INITO" Comment="Initialization Confirm">
        <With Var="QO" />
      </Event>
      <Event ID="{HEX-ID}" Name="CNF" Comment="Execution Confirmation">
        <With Var="QO" />
        <!-- Add With Var for each output produced -->
      </Event>
    </EventOutputs>
    <InputVars>
      <VarDeclaration ID="{HEX-ID}" Name="QI" Type="BOOL"
                      Comment="Input event qualifier" />
      <!-- Add custom inputs here -->
    </InputVars>
    <OutputVars>
      <VarDeclaration ID="{HEX-ID}" Name="QO" Type="BOOL"
                      Comment="Output event qualifier" />
      <!-- Add custom outputs here -->
    </OutputVars>
  </InterfaceList>
  <BasicFB>
    <ECC>
      <ECState Name="START" Comment="Initial State" x="552.9412" y="429.4117" />
      <ECState Name="INIT" Comment="Initialization" x="923.5294" y="141.1765">
        <ECAction Algorithm="INIT" Output="INITO" />
      </ECState>
      <ECState Name="REQ" Comment="Normal execution" x="217.647" y="752.9412">
        <ECAction Algorithm="REQ" Output="CNF" />
      </ECState>
      <ECTransition Source="START" Destination="INIT" Condition="INIT"
                    x="923.5294" y="429.4117" />
      <ECTransition Source="INIT" Destination="START" Condition="1"
                    x="552.9412" y="141.1765" />
      <ECTransition Source="START" Destination="REQ" Condition="REQ"
                    x="552.9412" y="600.0" />
      <ECTransition Source="REQ" Destination="START" Condition="1"
                    x="217.647" y="429.4117" />
    </ECC>
    <Algorithm Name="INIT" Comment="Initialization algorithm">
      <ST><![CDATA[QO := QI;]]></ST>
    </Algorithm>
    <Algorithm Name="REQ" Comment="Normally executed algorithm">
      <ST><![CDATA[QO := QI;
(* Add your logic here *)]]></ST>
    </Algorithm>
  </BasicFB>
</FBType>
Note: Basic FB does NOT have
Format="2.0"
attribute.

xml
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE FBType SYSTEM "../LibraryElement.dtd">
<FBType Name="{BlockName}" Namespace="{YourNamespace}"
        GUID="{NEW-GUID}" Comment="{Description}">
  <Identification Standard="61499-2" />
  <VersionInfo Organization="{Org}" Version="0.0" Author="{Author}"
               Date="{MM/DD/YYYY}" Remarks="Initial version" />
  <CompilerInfo />
  <InterfaceList>
    <EventInputs>
      <Event ID="{HEX-ID}" Name="INIT" Comment="Initialization Request">
        <With Var="QI" />
      </Event>
      <Event ID="{HEX-ID}" Name="REQ" Comment="Normal Execution Request">
        <With Var="QI" />
        <!-- Add With Var for each input used in REQ -->
      </Event>
    </EventInputs>
    <EventOutputs>
      <Event ID="{HEX-ID}" Name="INITO" Comment="Initialization Confirm">
        <With Var="QO" />
      </Event>
      <Event ID="{HEX-ID}" Name="CNF" Comment="Execution Confirmation">
        <With Var="QO" />
        <!-- Add With Var for each output produced -->
      </Event>
    </EventOutputs>
    <InputVars>
      <VarDeclaration ID="{HEX-ID}" Name="QI" Type="BOOL"
                      Comment="Input event qualifier" />
      <!-- Add custom inputs here -->
    </InputVars>
    <OutputVars>
      <VarDeclaration ID="{HEX-ID}" Name="QO" Type="BOOL"
                      Comment="Output event qualifier" />
      <!-- Add custom outputs here -->
    </OutputVars>
  </InterfaceList>
  <BasicFB>
    <ECC>
      <ECState Name="START" Comment="Initial State" x="552.9412" y="429.4117" />
      <ECState Name="INIT" Comment="Initialization" x="923.5294" y="141.1765">
        <ECAction Algorithm="INIT" Output="INITO" />
      </ECState>
      <ECState Name="REQ" Comment="Normal execution" x="217.647" y="752.9412">
        <ECAction Algorithm="REQ" Output="CNF" />
      </ECState>
      <ECTransition Source="START" Destination="INIT" Condition="INIT"
                    x="923.5294" y="429.4117" />
      <ECTransition Source="INIT" Destination="START" Condition="1"
                    x="552.9412" y="141.1765" />
      <ECTransition Source="START" Destination="REQ" Condition="REQ"
                    x="552.9412" y="600.0" />
      <ECTransition Source="REQ" Destination="START" Condition="1"
                    x="217.647" y="429.4117" />
    </ECC>
    <Algorithm Name="INIT" Comment="Initialization algorithm">
      <ST><![CDATA[QO := QI;]]></ST>
    </Algorithm>
    <Algorithm Name="REQ" Comment="Normally executed algorithm">
      <ST><![CDATA[QO := QI;
(* Add your logic here *)]]></ST>
    </Algorithm>
  </BasicFB>
</FBType>
注意: Basic FB不包含
Format="2.0"
属性。

ECC (Execution Control Chart)

ECC(执行控制图)

The ECC defines the state machine:
ECC用于定义状态机:

Standard States

标准状态

StatePurposeActions
STARTInitial stateNone
INITInitializationRun INIT algorithm, fire INITO
REQNormal executionRun REQ algorithm, fire CNF
状态用途操作
START初始状态
INIT初始化运行INIT算法,触发INITO
REQ正常执行运行REQ算法,触发CNF

Standard Transitions

标准转换

FromToCondition
STARTINIT
INIT
event received
INITSTART
1
(unconditional)
STARTREQ
REQ
event received
REQSTART
1
(unconditional)
来源目标条件
STARTINIT接收到
INIT
事件
INITSTART
1
(无条件)
STARTREQ接收到
REQ
事件
REQSTART
1
(无条件)

Adding Custom States

添加自定义状态

xml
<ECState Name="CUSTOM_STATE" Comment="Custom state" x="800" y="500">
  <ECAction Algorithm="CUSTOM_ALG" Output="CUSTOM_EVENT" />
</ECState>
<ECTransition Source="START" Destination="CUSTOM_STATE"
              Condition="CUSTOM_INPUT_EVENT" x="700" y="450" />

xml
<ECState Name="CUSTOM_STATE" Comment="Custom state" x="800" y="500">
  <ECAction Algorithm="CUSTOM_ALG" Output="CUSTOM_EVENT" />
</ECState>
<ECTransition Source="START" Destination="CUSTOM_STATE"
              Condition="CUSTOM_INPUT_EVENT" x="700" y="450" />

Algorithms (Structured Text)

算法(结构化文本)

Algorithms are written in ST (Structured Text):
xml
<Algorithm Name="REQ" Comment="Calculation algorithm">
  <ST><![CDATA[
QO := QI;
Result := Value1 * Value2;
]]></ST>
</Algorithm>
算法采用ST(结构化文本)编写:
xml
<Algorithm Name="REQ" Comment="Calculation algorithm">
  <ST><![CDATA[
QO := QI;
Result := Value1 * Value2;
]]></ST>
</Algorithm>

ST Syntax Basics

ST语法基础

st
(* Assignment *)
Result := Value1 + Value2;

(* Conditional *)
IF Condition THEN
  Output := TRUE;
ELSE
  Output := FALSE;
END_IF;

(* Loop *)
FOR i := 0 TO 10 DO
  Array[i] := 0;
END_FOR;

st
(* 赋值 *)
Result := Value1 + Value2;

(* 条件判断 *)
IF Condition THEN
  Output := TRUE;
ELSE
  Output := FALSE;
END_IF;

(* 循环 *)
FOR i := 0 TO 10 DO
  Array[i] := 0;
END_FOR;

Event-Variable Associations

事件-变量关联

Use
<With Var="...">
to associate variables with events:
xml
<Event Name="REQ" Comment="Request">
  <With Var="QI" />      <!-- Always include QI -->
  <With Var="Value1" />  <!-- Input used in REQ -->
  <With Var="Value2" />  <!-- Input used in REQ -->
</Event>

<Event Name="CNF" Comment="Confirm">
  <With Var="QO" />      <!-- Always include QO -->
  <With Var="Result" />  <!-- Output produced by REQ -->
</Event>

使用
<With Var="...">
将变量与事件关联:
xml
<Event Name="REQ" Comment="Request">
  <With Var="QI" />      <!-- Always include QI -->
  <With Var="Value1" />  <!-- Input used in REQ -->
  <With Var="Value2" />  <!-- Input used in REQ -->
</Event>

<Event Name="CNF" Comment="Confirm">
  <With Var="QO" />      <!-- Always include QO -->
  <With Var="Result" />  <!-- Output produced by REQ -->
</Event>

dfbproj Registration

dfbproj注册

xml
<ItemGroup>
  <None Include="{Name}.doc.xml">
    <DependentUpon>{Name}.fbt</DependentUpon>
  </None>
  <None Include="{Name}.meta.xml">
    <DependentUpon>{Name}.fbt</DependentUpon>
  </None>
</ItemGroup>
<ItemGroup>
  <Compile Include="{Name}.fbt">
    <IEC61499Type>Basic</IEC61499Type>
  </Compile>
</ItemGroup>

xml
<ItemGroup>
  <None Include="{Name}.doc.xml">
    <DependentUpon>{Name}.fbt</DependentUpon>
  </None>
  <None Include="{Name}.meta.xml">
    <DependentUpon>{Name}.fbt</DependentUpon>
  </None>
</ItemGroup>
<ItemGroup>
  <Compile Include="{Name}.fbt">
    <IEC61499Type>Basic</IEC61499Type>
  </Compile>
</ItemGroup>

Common Rules

通用规则

See common-rules.md for:
  • ID generation
  • DOCTYPE references
  • dfbproj registration patterns

请参考common-rules.md了解:
  • ID生成规则
  • DOCTYPE引用规则
  • dfbproj注册模式

Example: Multiplier Block

示例:乘法器功能块

xml
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE FBType SYSTEM "../LibraryElement.dtd">
<FBType Name="Multiplier" Namespace="MyLibrary"
        GUID="a1b2c3d4-e5f6-7890-abcd-ef1234567890" Comment="Multiplies two values">
  <Identification Standard="61499-2" />
  <VersionInfo Organization="MyOrg" Version="1.0" Author="Claude"
               Date="01/16/2026" Remarks="Initial" />
  <CompilerInfo />
  <InterfaceList>
    <EventInputs>
      <Event ID="1234567890ABCDEF" Name="INIT" Comment="Initialize">
        <With Var="QI" />
      </Event>
      <Event ID="ABCDEF1234567890" Name="REQ" Comment="Calculate">
        <With Var="QI" />
        <With Var="Value1" />
        <With Var="Value2" />
      </Event>
    </EventInputs>
    <EventOutputs>
      <Event ID="FEDCBA0987654321" Name="INITO" Comment="Init done">
        <With Var="QO" />
      </Event>
      <Event ID="0987654321FEDCBA" Name="CNF" Comment="Result ready">
        <With Var="QO" />
        <With Var="Result" />
      </Event>
    </EventOutputs>
    <InputVars>
      <VarDeclaration ID="1111111111111111" Name="QI" Type="BOOL" />
      <VarDeclaration ID="2222222222222222" Name="Value1" Type="REAL" />
      <VarDeclaration ID="3333333333333333" Name="Value2" Type="REAL" />
    </InputVars>
    <OutputVars>
      <VarDeclaration ID="4444444444444444" Name="QO" Type="BOOL" />
      <VarDeclaration ID="5555555555555555" Name="Result" Type="REAL" />
    </OutputVars>
  </InterfaceList>
  <BasicFB>
    <ECC>
      <ECState Name="START" x="550" y="430" />
      <ECState Name="INIT" x="920" y="140">
        <ECAction Algorithm="INIT" Output="INITO" />
      </ECState>
      <ECState Name="REQ" x="220" y="750">
        <ECAction Algorithm="REQ" Output="CNF" />
      </ECState>
      <ECTransition Source="START" Destination="INIT" Condition="INIT" x="920" y="430" />
      <ECTransition Source="INIT" Destination="START" Condition="1" x="550" y="140" />
      <ECTransition Source="START" Destination="REQ" Condition="REQ" x="550" y="600" />
      <ECTransition Source="REQ" Destination="START" Condition="1" x="220" y="430" />
    </ECC>
    <Algorithm Name="INIT">
      <ST><![CDATA[QO := QI;]]></ST>
    </Algorithm>
    <Algorithm Name="REQ">
      <ST><![CDATA[QO := QI;
Result := Value1 * Value2;]]></ST>
    </Algorithm>
  </BasicFB>
</FBType>

xml
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE FBType SYSTEM "../LibraryElement.dtd">
<FBType Name="Multiplier" Namespace="MyLibrary"
        GUID="a1b2c3d4-e5f6-7890-abcd-ef1234567890" Comment="Multiplies two values">
  <Identification Standard="61499-2" />
  <VersionInfo Organization="MyOrg" Version="1.0" Author="Claude"
               Date="01/16/2026" Remarks="Initial" />
  <CompilerInfo />
  <InterfaceList>
    <EventInputs>
      <Event ID="1234567890ABCDEF" Name="INIT" Comment="Initialize">
        <With Var="QI" />
      </Event>
      <Event ID="ABCDEF1234567890" Name="REQ" Comment="Calculate">
        <With Var="QI" />
        <With Var="Value1" />
        <With Var="Value2" />
      </Event>
    </EventInputs>
    <EventOutputs>
      <Event ID="FEDCBA0987654321" Name="INITO" Comment="Init done">
        <With Var="QO" />
      </Event>
      <Event ID="0987654321FEDCBA" Name="CNF" Comment="Result ready">
        <With Var="QO" />
        <With Var="Result" />
      </Event>
    </EventOutputs>
    <InputVars>
      <VarDeclaration ID="1111111111111111" Name="QI" Type="BOOL" />
      <VarDeclaration ID="2222222222222222" Name="Value1" Type="REAL" />
      <VarDeclaration ID="3333333333333333" Name="Value2" Type="REAL" />
    </InputVars>
    <OutputVars>
      <VarDeclaration ID="4444444444444444" Name="QO" Type="BOOL" />
      <VarDeclaration ID="5555555555555555" Name="Result" Type="REAL" />
    </OutputVars>
  </InterfaceList>
  <BasicFB>
    <ECC>
      <ECState Name="START" x="550" y="430" />
      <ECState Name="INIT" x="920" y="140">
        <ECAction Algorithm="INIT" Output="INITO" />
      </ECState>
      <ECState Name="REQ" x="220" y="750">
        <ECAction Algorithm="REQ" Output="CNF" />
      </ECState>
      <ECTransition Source="START" Destination="INIT" Condition="INIT" x="920" y="430" />
      <ECTransition Source="INIT" Destination="START" Condition="1" x="550" y="140" />
      <ECTransition Source="START" Destination="REQ" Condition="REQ" x="550" y="600" />
      <ECTransition Source="REQ" Destination="START" Condition="1" x="220" y="430" />
    </ECC>
    <Algorithm Name="INIT">
      <ST><![CDATA[QO := QI;]]></ST>
    </Algorithm>
    <Algorithm Name="REQ">
      <ST><![CDATA[QO := QI;
Result := Value1 * Value2;]]></ST>
    </Algorithm>
  </BasicFB>
</FBType>

Scripts

脚本

This skill includes Python scripts for autonomous validation and operation:
ScriptPurposeUsageExit Codes
validate_ecc.py
Verify ECC state machine correctness
python scripts/validate_ecc.py <file.fbt>
0=pass, 1=error, 10=validation failed, 11=pass with warnings
validate_st_algorithm.py
Check ST algorithm consistency (basic checks)
python scripts/validate_st_algorithm.py <file.fbt>
0=pass, 1=error, 10=validation failed, 11=pass with warnings
本技能包含用于自动验证和操作的Python脚本:
脚本用途使用方法退出码
validate_ecc.py
验证ECC状态机的正确性
python scripts/validate_ecc.py <file.fbt>
0=通过,1=错误,10=验证失败,11=通过但有警告
validate_st_algorithm.py
检查ST算法的一致性(基础检查)
python scripts/validate_st_algorithm.py <file.fbt>
0=通过,1=错误,10=验证失败,11=通过但有警告

Validation Workflow

验证工作流

Recommended: Validate automatically after creating or modifying a Basic FB:
bash
undefined
推荐: 创建或修改Basic FB后自动执行验证:
bash
undefined

Validate ECC state machine (checks reachability, transitions, algorithms)

验证ECC状态机(检查可达性、转换、算法)

python scripts/validate_ecc.py path/to/MyBlock.fbt
python scripts/validate_ecc.py path/to/MyBlock.fbt

Validate ST algorithms (checks variable references, algorithm consistency)

验证ST算法(检查变量引用、算法一致性)

python scripts/validate_st_algorithm.py path/to/MyBlock.fbt
python scripts/validate_st_algorithm.py path/to/MyBlock.fbt

Generic validation (basic XML structure)

通用验证(基础XML结构)

python ../eae-skill-router/scripts/validate_block.py --type basic path/to/MyBlock.fbt

**Example: validate_ecc.py**

```bash
python ../eae-skill-router/scripts/validate_block.py --type basic path/to/MyBlock.fbt

**示例:validate_ecc.py**

```bash

Basic validation

基础验证

python scripts/validate_ecc.py MyBlock.fbt
python scripts/validate_ecc.py MyBlock.fbt

Verbose output with detailed information

详细输出,包含详细信息

python scripts/validate_ecc.py MyBlock.fbt --verbose
python scripts/validate_ecc.py MyBlock.fbt --verbose

JSON output for automation/CI

以JSON格式输出,用于自动化/CI流程

python scripts/validate_ecc.py MyBlock.fbt --json
python scripts/validate_ecc.py MyBlock.fbt --json

CI mode (JSON only, no human messages)

CI模式(仅输出JSON,无人类可读消息)

python scripts/validate_ecc.py MyBlock.fbt --ci

**What validate_ecc.py checks:**
- ✅ All states are reachable from START
- ✅ All event inputs have at least one transition
- ✅ All transitions reference valid algorithms
- ✅ No circular dependencies in state machine
- ✅ Standard states present (START, INIT, REQ if applicable)
- ⚠️ States without outgoing transitions (warnings)
- ⚠️ Event inputs not used in transitions (warnings)

**Example: validate_st_algorithm.py**

```bash
python scripts/validate_ecc.py MyBlock.fbt --ci

**validate_ecc.py检查内容:**
- ✅ 所有状态均可从START状态到达
- ✅ 所有输入事件至少有一个转换
- ✅ 所有转换引用的算法均存在
- ✅ 状态机无循环依赖
- ✅ 包含标准状态(START、INIT、REQ,如适用)
- ⚠️ 无输出转换的状态(警告)
- ⚠️ 未在转换中使用的输入事件(警告)

**示例:validate_st_algorithm.py**

```bash

Validate algorithms

验证算法

python scripts/validate_st_algorithm.py MyBlock.fbt --verbose

**What validate_st_algorithm.py checks:**
- ✅ Algorithm names match ECC references
- ✅ Variables referenced in algorithms are declared
- ⚠️ Empty algorithms (warnings)
- ⚠️ Potentially undefined variables (warnings, may be false positives)
- ⚠️ Unused algorithms (warnings)

**Note:** Full ST syntax validation is performed by the EAE compiler. These scripts catch common mistakes early to save compilation cycles.
python scripts/validate_st_algorithm.py MyBlock.fbt --verbose

**validate_st_algorithm.py检查内容:**
- ✅ 算法名称与ECC引用匹配
- ✅ 算法中引用的变量均已声明
- ⚠️ 空算法(警告)
- ⚠️ 可能未定义的变量(警告,可能为误报)
- ⚠️ 未使用的算法(警告)

**注意:** 完整的ST语法验证由EAE编译器执行。这些脚本可提前发现常见错误,节省编译时间。

Generate IDs

生成ID

bash
python ../eae-skill-router/scripts/generate_ids.py --hex 6 --guid 1

bash
python ../eae-skill-router/scripts/generate_ids.py --hex 6 --guid 1

Integration with Validation Skills

与验证技能的集成

Naming Validation

命名验证

Use eae-naming-validator to ensure compliance with SE Application Design Guidelines:
Key Naming Rules for Basic FB:
  • FB name: camelCase (e.g.,
    scaleLogic
    ,
    stateDevice
    ,
    motorControl
    )
  • Interface variables: PascalCase (e.g.,
    PermitOn
    ,
    FeedbackOn
    ,
    Value
    )
  • Internal variables: camelCase (e.g.,
    error
    ,
    outMinActiveLast
    ,
    timerActive
    )
  • Events: SNAKE_CASE (e.g.,
    INIT
    ,
    REQ
    ,
    CUSTOM_EVENT
    )
  • Algorithms: Match corresponding events (e.g., INIT algorithm, REQ algorithm)
Validate naming before creation:
bash
undefined
使用eae-naming-validator确保符合SE应用设计指南:
Basic FB的关键命名规则:
  • FB名称:采用小驼峰式(camelCase),例如:
    scaleLogic
    stateDevice
    motorControl
  • 接口变量:采用大驼峰式(PascalCase),例如:
    PermitOn
    FeedbackOn
    Value
  • 内部变量:采用小驼峰式(camelCase),例如:
    error
    outMinActiveLast
    timerActive
  • 事件:采用蛇形大写(SNAKE_CASE),例如:
    INIT
    REQ
    CUSTOM_EVENT
  • 算法:与对应事件名称匹配(例如:INIT算法、REQ算法)
创建前验证命名:
bash
undefined

Validate FB and variable names

验证FB和变量名称

python ../eae-naming-validator/scripts/validate_names.py
--app-dir IEC61499
--artifact-type BasicFB
--name scaleLogic

**Reference:** EAE_ADG EIO0000004686.06, Section 1.5
python ../eae-naming-validator/scripts/validate_names.py
--app-dir IEC61499
--artifact-type BasicFB
--name scaleLogic

**参考:** EAE_ADG EIO0000004686.06,第1.5节

Performance Analysis

性能分析

Use eae-performance-analyzer to estimate CPU load:
bash
undefined
使用eae-performance-analyzer估算CPU负载:
bash
undefined

Analyze ST algorithm complexity

分析ST算法复杂度

python ../eae-performance-analyzer/scripts/estimate_cpu_load.py
--app-dir IEC61499
--platform soft-dpac-windows

**What to Check:**
- ST algorithm complexity (cyclomatic complexity)
- Execution time estimates
- CPU load percentage

---
python ../eae-performance-analyzer/scripts/estimate_cpu_load.py
--app-dir IEC61499
--platform soft-dpac-windows

**检查内容:**
- ST算法复杂度(圈复杂度)
- 执行时间估算
- CPU负载百分比

---

Best Practices from EAE ADG

EAE应用设计指南(ADG)中的最佳实践

1. Naming Conventions (SE ADG Section 1.5)

1. 命名规范(SE ADG第1.5节)

Basic FB Naming:
  • Use camelCase:
    scaleLogic
    ,
    stateDevice
    ,
    motorControl
  • Use descriptive names that indicate purpose
  • Avoid generic names:
    block1
    ,
    fb
    ,
    logic
Variable Naming:
  • Interface variables (inputs/outputs): PascalCase →
    PermitOn
    ,
    FeedbackOn
    ,
    SetPoint
  • Internal variables (local to FB): camelCase →
    error
    ,
    outMinActiveLast
    ,
    timerActive
  • Hungarian notation for complex types:
    strConfig
    ,
    arrBuffer
    ,
    eState
Event Naming:
  • Use SNAKE_CASE:
    INIT
    ,
    REQ
    ,
    CUSTOM_EVENT
    ,
    START_OPERATION
  • Standard events: INIT/INITO for initialization, REQ/CNF for requests
  • Avoid generic names:
    E1
    ,
    DO
    ,
    OUT
Algorithm Naming:
  • Match corresponding event names: INIT algorithm, REQ algorithm
  • For custom states: Use descriptive names like
    calculateAverage
    ,
    checkLimits
Reference: EAE_ADG EIO0000004686.06, Section 1.5
Basic FB命名:
  • 采用小驼峰式(camelCase):
    scaleLogic
    stateDevice
    motorControl
  • 使用能表明用途的描述性名称
  • 避免通用名称:
    block1
    fb
    logic
变量命名:
  • 接口变量(输入/输出):大驼峰式(PascalCase)→
    PermitOn
    FeedbackOn
    SetPoint
  • 内部变量(FB本地变量):小驼峰式(camelCase)→
    error
    outMinActiveLast
    timerActive
  • 复杂类型采用匈牙利命名法:
    strConfig
    arrBuffer
    eState
事件命名:
  • 采用蛇形大写(SNAKE_CASE):
    INIT
    REQ
    CUSTOM_EVENT
    START_OPERATION
  • 标准事件:INIT/INITO用于初始化,REQ/CNF用于请求处理
  • 避免通用名称:
    E1
    DO
    OUT
算法命名:
  • 与对应事件名称匹配:INIT算法、REQ算法
  • 自定义状态:使用描述性名称,如
    calculateAverage
    checkLimits
参考: EAE_ADG EIO0000004686.06,第1.5节

2. ECC Design Principles

2. ECC设计原则

State Machine Guidelines:
  • Keep states focused (single responsibility)
  • Use START state as the central hub
  • Always include INIT/INITO pattern for initialization
  • Use conditional transitions sparingly (prefer simple event-driven logic)
  • Document complex transitions in comments
Standard Pattern:
START ← → INIT (on INIT event, run INIT algorithm, fire INITO)
START ← → REQ (on REQ event, run REQ algorithm, fire CNF)
状态机指南:
  • 保持状态聚焦(单一职责)
  • 将START状态作为中心枢纽
  • 始终包含INIT/INITO模式用于初始化
  • 尽量少用条件转换(优先选择简单的事件驱动逻辑)
  • 为复杂转换添加注释
标准模式:
START ← → INIT(接收到INIT事件时,运行INIT算法,触发INITO)
START ← → REQ(接收到REQ事件时,运行REQ算法,触发CNF)

3. ST Algorithm Best Practices

3. ST算法最佳实践

Algorithm Structure:
  • Always set QO := QI at the beginning
  • Keep algorithms simple (cyclomatic complexity <10 typical)
  • Use clear variable names
  • Add comments for complex logic
  • Avoid deeply nested IF statements (max 3 levels)
Example:
st
(* INIT Algorithm *)
QO := QI;
error := FALSE;
result := 0.0;

(* REQ Algorithm *)
QO := QI;
IF QI THEN
  result := inputValue * scaleFactor;
  IF result > maxLimit THEN
    result := maxLimit;
    error := TRUE;
  END_IF;
ELSE
  error := TRUE;
END_IF;
算法结构:
  • 始终以
    QO := QI
    开头
  • 保持算法简洁(圈复杂度通常<10)
  • 使用清晰的变量名称
  • 为复杂逻辑添加注释
  • 避免深度嵌套的IF语句(最多3层)
示例:
st
(* INIT算法 *)
QO := QI;
error := FALSE;
result := 0.0;

(* REQ算法 *)
QO := QI;
IF QI THEN
  result := inputValue * scaleFactor;
  IF result > maxLimit THEN
    result := maxLimit;
    error := TRUE;
  END_IF;
ELSE
  error := TRUE;
END_IF;

4. Event-Variable Associations

4. 事件-变量关联

With Var Guidelines:
  • Always include QI with input events
  • Always include QO with output events
  • Associate all inputs used in the algorithm with the triggering event
  • Associate all outputs produced by the algorithm with the output event

With Var指南:
  • 输入事件始终包含QI
  • 输出事件始终包含QO
  • 将算法中使用的所有输入变量与触发事件关联
  • 将算法生成的所有输出变量与输出事件关联

Anti-Patterns

反模式

1. Naming Anti-Patterns

1. 命名反模式

Wrong Casing for Basic FB
xml
<!-- BAD: Using PascalCase for Basic FB -->
<FBType Name="MotorControl" ...>
Correct camelCase
xml
<FBType Name="motorControl" ...>
Inconsistent Variable Casing
xml
<!-- Interface variables should be PascalCase -->
<VarDeclaration Name="permitOn" Type="BOOL" />  <!-- BAD: should be "PermitOn" -->

<!-- Internal variables should be camelCase -->
<VarDeclaration Name="Error" Type="BOOL" />  <!-- BAD: should be "error" if internal -->
Generic Event Names
xml
<Event Name="E1" />  <!-- BAD: non-descriptive -->
<Event Name="DO" />  <!-- BAD: generic -->
Descriptive Event Names
xml
<Event Name="START_OPERATION" />
<Event Name="CALCULATE_RESULT" />
Basic FB大小写错误
xml
<!-- 错误:Basic FB使用大驼峰式 -->
<FBType Name="MotorControl" ...>
正确的小驼峰式
xml
<FBType Name="motorControl" ...>
变量大小写不一致
xml
<!-- 接口变量应采用大驼峰式 -->
<VarDeclaration Name="permitOn" Type="BOOL" />  <!-- 错误:应为"PermitOn" -->

<!-- 内部变量应采用小驼峰式 -->
<VarDeclaration Name="Error" Type="BOOL" />  <!-- 错误:如果是内部变量,应为"error" -->
通用事件名称
xml
<Event Name="E1" />  <!-- 错误:无描述性 -->
<Event Name="DO" />  <!-- 错误:过于通用 -->
描述性事件名称
xml
<Event Name="START_OPERATION" />
<Event Name="CALCULATE_RESULT" />

2. ECC Anti-Patterns

2. ECC反模式

Missing START State
xml
<ECC>
  <!-- BAD: No START state -->
  <ECState Name="INIT" x="500" y="350" />
</ECC>
START State Required
xml
<ECC>
  <ECState Name="START" x="550" y="430" />
  <ECState Name="INIT" x="920" y="140">
    <ECAction Algorithm="INIT" Output="INITO" />
  </ECState>
</ECC>
Unreachable States
xml
<ECC>
  <ECState Name="START" x="550" y="430" />
  <ECState Name="ORPHAN" x="800" y="500">
    <ECAction Algorithm="ORPHAN_ALG" Output="OUT" />
  </ECState>
  <!-- NO transitions to ORPHAN state - unreachable! -->
</ECC>
Algorithm/Event Mismatch
xml
<ECState Name="REQ" x="220" y="750">
  <ECAction Algorithm="INIT" Output="CNF" />  <!-- BAD: INIT algorithm in REQ state -->
</ECState>
Matching Algorithm Names
xml
<ECState Name="REQ" x="220" y="750">
  <ECAction Algorithm="REQ" Output="CNF" />
</ECState>
缺少START状态
xml
<ECC>
  <!-- 错误:无START状态 -->
  <ECState Name="INIT" x="500" y="350" />
</ECC>
必须包含START状态
xml
<ECC>
  <ECState Name="START" x="550" y="430" />
  <ECState Name="INIT" x="920" y="140">
    <ECAction Algorithm="INIT" Output="INITO" />
  </ECState>
</ECC>
不可达状态
xml
<ECC>
  <ECState Name="START" x="550" y="430" />
  <ECState Name="ORPHAN" x="800" y="500">
    <ECAction Algorithm="ORPHAN_ALG" Output="OUT" />
  </ECState>
  <!-- 无指向ORPHAN状态的转换 - 不可达! -->
</ECC>
算法/事件不匹配
xml
<ECState Name="REQ" x="220" y="750">
  <ECAction Algorithm="INIT" Output="CNF" />  <!-- 错误:REQ状态中使用INIT算法 -->
</ECState>
算法名称匹配
xml
<ECState Name="REQ" x="220" y="750">
  <ECAction Algorithm="REQ" Output="CNF" />
</ECState>

3. ST Algorithm Anti-Patterns

3. ST算法反模式

Missing QO Assignment
xml
<Algorithm Name="REQ">
  <ST><![CDATA[
(* BAD: Forgot to set QO := QI *)
Result := Value1 * Value2;
]]></ST>
</Algorithm>
Always Set QO
xml
<Algorithm Name="REQ">
  <ST><![CDATA[
QO := QI;
Result := Value1 * Value2;
]]></ST>
</Algorithm>
Overly Complex Algorithms
st
(* BAD: Cyclomatic complexity > 15, deeply nested *)
IF condition1 THEN
  IF condition2 THEN
    IF condition3 THEN
      IF condition4 THEN
        (* 4+ levels of nesting - hard to read *)
      END_IF;
    END_IF;
  END_IF;
END_IF;
Refactor Complex Logic
st
(* Use early returns or break into multiple algorithms *)
IF NOT condition1 THEN
  error := TRUE;
  RETURN;
END_IF;

IF NOT condition2 THEN
  error := TRUE;
  RETURN;
END_IF;

(* Main logic here *)
Undefined Variables
xml
<Algorithm Name="REQ">
  <ST><![CDATA[
QO := QI;
Result := UnknownVar * 2;  (* UnknownVar not declared! *)
]]></ST>
</Algorithm>
缺少QO赋值
xml
<Algorithm Name="REQ">
  <ST><![CDATA[
(* 错误:忘记设置QO := QI *)
Result := Value1 * Value2;
]]></ST>
</Algorithm>
始终设置QO
xml
<Algorithm Name="REQ">
  <ST><![CDATA[
QO := QI;
Result := Value1 * Value2;
]]></ST>
</Algorithm>
过于复杂的算法
st
(* 错误:圈复杂度>15,嵌套过深 *)
IF condition1 THEN
  IF condition2 THEN
    IF condition3 THEN
      IF condition4 THEN
        (* 4层及以上嵌套 - 难以阅读 *)
      END_IF;
    END_IF;
  END_IF;
END_IF;
重构复杂逻辑
st
(* 使用提前返回或拆分为多个算法 *)
IF NOT condition1 THEN
  error := TRUE;
  RETURN;
END_IF;

IF NOT condition2 THEN
  error := TRUE;
  RETURN;
END_IF;

(* 主逻辑在此 *)
未定义变量
xml
<Algorithm Name="REQ">
  <ST><![CDATA[
QO := QI;
Result := UnknownVar * 2;  (* UnknownVar未声明! *)
]]></ST>
</Algorithm>

4. Event-Variable Association Anti-Patterns

4. 事件-变量关联反模式

Missing With Var
xml
<Event Name="REQ">
  <With Var="QI" />
  <!-- BAD: Algorithm uses Value1 and Value2 but they're not associated -->
</Event>
<Algorithm Name="REQ">
  <ST><![CDATA[
Result := Value1 * Value2;  (* Value1, Value2 should be in With Var *)
]]></ST>
</Algorithm>
Complete With Var Associations
xml
<Event Name="REQ">
  <With Var="QI" />
  <With Var="Value1" />
  <With Var="Value2" />
</Event>

缺少With Var
xml
<Event Name="REQ">
  <With Var="QI" />
  <!-- 错误:算法使用Value1和Value2,但未关联 -->
</Event>
<Algorithm Name="REQ">
  <ST><![CDATA[
Result := Value1 * Value2;  (* Value1、Value2应包含在With Var中 *)
]]></ST>
</Algorithm>
完整的With Var关联
xml
<Event Name="REQ">
  <With Var="QI" />
  <With Var="Value1" />
  <With Var="Value2" />
</Event>

Verification Checklist

验证检查清单

Before committing your Basic FB:
Naming (run eae-naming-validator):
  • FB name is camelCase
  • Interface variables are PascalCase
  • Internal variables are camelCase
  • Events are SNAKE_CASE
Structure:
  • Root element is
    <FBType>
    (NOT
    <AdapterType>
    )
  • Uses
    Standard="61499-2"
    (NOT
    61499-1
    )
  • Has
    <BasicFB>
    element (NOT
    <FBNetwork>
    )
  • Has
    <ECC>
    with START state
ECC Validation (run validate_ecc.py):
  • All states reachable from START
  • All event inputs have transitions
  • All algorithms referenced in ECActions exist
  • No orphaned states
ST Algorithm Validation (run validate_st_algorithm.py):
  • All algorithms set QO := QI
  • All referenced variables are declared
  • Cyclomatic complexity <10 (typical)
  • No undefined variables
Event-Variable Associations:
  • INIT event has
    <With Var="QI" />
  • INITO event has
    <With Var="QO" />
  • All inputs used in algorithms are associated with triggering event
  • All outputs produced are associated with output event
Performance (run eae-performance-analyzer):
  • ST algorithm complexity is reasonable
  • Estimated CPU load <70% (soft dPAC)
Scripts Validation:
  • python scripts/validate_ecc.py {Name}.fbt
    exits with 0
  • python scripts/validate_st_algorithm.py {Name}.fbt
    exits with 0
Registration:
  • Registered in .dfbproj with
    IEC61499Type="Basic"
  • .doc.xml and .meta.xml files created and registered

提交Basic FB前,请检查以下内容:
命名(运行eae-naming-validator):
  • FB名称采用小驼峰式(camelCase)
  • 接口变量采用大驼峰式(PascalCase)
  • 内部变量采用小驼峰式(camelCase)
  • 事件采用蛇形大写(SNAKE_CASE)
结构:
  • 根元素为
    <FBType>
    (而非
    <AdapterType>
  • 使用
    Standard="61499-2"
    (而非
    61499-1
  • 包含
    <BasicFB>
    元素(而非
    <FBNetwork>
  • 包含带有START状态的
    <ECC>
ECC验证(运行validate_ecc.py):
  • 所有状态均可从START状态到达
  • 所有输入事件均有转换
  • ECAction中引用的所有算法均存在
  • 无孤立状态
ST算法验证(运行validate_st_algorithm.py):
  • 所有算法均设置
    QO := QI
  • 所有引用的变量均已声明
  • 圈复杂度<10(通常情况)
  • 无未定义变量
事件-变量关联:
  • INIT事件包含
    <With Var="QI" />
  • INITO事件包含
    <With Var="QO" />
  • 算法中使用的所有输入变量均与触发事件关联
  • 生成的所有输出变量均与输出事件关联
性能(运行eae-performance-analyzer):
  • ST算法复杂度合理
  • 估算CPU负载<70%(软dPAC平台)
脚本验证:
  • python scripts/validate_ecc.py {Name}.fbt
    退出码为0
  • python scripts/validate_st_algorithm.py {Name}.fbt
    退出码为0
注册:
  • 在.dfbproj中注册,且
    IEC61499Type="Basic"
  • 已创建并注册.doc.xml和.meta.xml文件

Related Skills

相关技能

SkillWhen to Use
eae-naming-validatorValidate naming compliance (camelCase for Basic FB)
eae-performance-analyzerEstimate CPU load from ST algorithms
eae-composite-fbCreate composite FBs with FBNetwork
eae-catCreate CAT blocks with HMI
eae-datatypeCreate custom data types for variables

技能使用场景
eae-naming-validator验证命名合规性(Basic FB采用小驼峰式)
eae-performance-analyzer估算ST算法的CPU负载
eae-composite-fb创建带有FBNetwork的复合功能块
eae-cat创建带有HMI的CAT功能块
eae-datatype为变量创建自定义数据类型

Templates

模板

  • basic-fb.xml
  • doc.xml
  • meta.xml
  • basic-fb.xml
  • doc.xml
  • meta.xml