# Function to convert values to the appropriate data types
def convert_to_boolean(value):
return value.lower() in ['true', '1', 'yes', 't', 'y']
P6-J Pm-Um-Em Design -Part 1
1 Introduction
The FRS work process is divided into six parts:
Index | Description |
---|---|
Part 1 | Assign IO to CCM and CM |
Part 2 | Mode of Operation, Steps, and Transitions |
Part 3 | Build CCM-Step-Interaction-Matrix |
Part 4 | Review Build CCM-Step-Interaction-Matrix Dynamically |
Part 5 | Review the pCode and Dictionary |
Part 6 | Build and Modify DSS and SOP |
This document can be applied to the following modeles from ISA106 standard:
Pm: Plant Module
Um: Unit Module
Em: Equipment Module
This document will provide guidelines for implementing the communication between Pm, Um and Em.
1.1 Overview
The Pm, Um, and Em can drive each other as a parent-child, The parent requests a mode of operation of the child, and the child communicates back to Um its MoO as its status.
The following cases are allowed where
Case | Parent | Child | Parent==<Child | Comment |
---|---|---|---|---|
Plant - Unit | Pm | Um | PmVRT ==< UmR350 | Plant ==< Unit |
Unit - Equipment | Um | Em | UmR350 ==< EmP350A | Unit ==< EM |
Unit-Equipment | Um | Em | UmR350 ==< EmP350AB | Unit ==< Nested EM |
Equipment - Equipment | Em | Em | EmP350AB ==< Emp350A | Nested EM ==< EM A |
Equipment - Equipment | Em | Em | EmP350AB ==< Emp350B | Nested EM ==< EM B |
Table 1: Pm =< Um =< Em Relationship
Please note that only Em-to-Em communication is recommended. The Pm controlling another PM or Um controlling another Um is doable, however, it is not recommended.
1.2 Definitions
- Um_MoO: The Current Um Mode of Operation sequential number (1,2,..)
- Em_MoO: The Current Em Mode of Operation sequential number (1,2,..)
- Um_Step: This is the current active step of the Um. In the SBC only one step is active at the time.
- Em_Step: This is the current active step of the Em.
- Um_Requested: The Um_Requested is calculated as the desired Em_MoO . It is calculated when the Um_Step is changed.
- Um_Request: The Um_Request is calculated based on the current Um_Requested and Em_Status.
- Em_Status: The current Em_MoO is sent to Um at each cycle
1.3 Strategy
To illustrate parent-child communication let’s use the following:
UM Strategy
- Um receives the current Em_status
- Um Calculate new Um_Step based on the transition and Em_Status using SFC rules
- Um calculates the Um_Request based on Um_Step and Em_Status
- UM send Um_Request to Em
Em Strategy
- Em upon receiving Um_Request using SFC rules
- Em calculates the new Em_Status and sends it back to Um
The above process can be summarized as the following:
1.3.1 UM =< EM Strategy
Please note the following:
- Um_Requested is assigned to one of the Em_MoO valid ranges. This is what UM Requests from EM or Em Mode of Operation target.
- Um_Request is calculated using Um_requested and Em_Status.
Get Em_Status from Em
Um_Step is selected using SFC rules Um_Step = fn_Um_SFC(Um_Step)
The transition should have the following code
- Em_Status > 0 and Em_status == Um_Request and not Um_Error:
Calculate the Um_Requested = fn_Um_Requested(Um_Step)
Calculate the Um_Request | Um_Request_Action = fn_Um_Request(Um_Requested, Em_Status)
Um_Request_Action is defined as:
-1 : Error Move Um_Step to its Default Position
0 : Wait Em is moving it step but has not finished its target Mode of Operation
1: All OK and Em has reached it target Mode of Operation
Send Um_Request to Em
Based on the value of Um_Request_Action do the following:
- Um_Timer_Exceeded = False
- if Um_Request_Action == 1:
- Reset the Um_Timer
- Um_Timer = 0
- elif Um_Request_Action == 0:
- Um_Timer +=1
- if Um_Timer > Um_Timer_Max:
- Um_Timer_Exceeded = True
- if Um_Request_Action == -1 or Um_Error or Um_Timer_Exceeded :
- Jump to Um_Default_Step
- Um_Default_Step = fn_Um_Default_Step(Um_Step) ### Um Functions
Index | Function | Inputs | Outputs | Comments |
---|---|---|---|---|
UM-A | fn_Um_SFC | Um_Step | Um_Step_New | SFC (Simulation) |
UM-B | fn_Um_Requested | Um_Step | Um_Requested | Next EM_MoO |
UM-C | fn_Um_Request | Um_Request Em_Status | Um_Request Um_Request_Action | Convert Um_Requested to Um_Request |
Um-D | fn_Um_Default_Step | Um_Step | Um_Step_New | Default Step |
Table 2. List of UM_Functions
1.3.2 EM =< UM Strategy
Get Um_Request form Um
if Um_Request > 0 and Em_Status > 0 and not Em_Error:
- Em_Step is jumped to Um_Requested Mode of Operation
- EM_Step = fn_Em_MoO_Next(Um_Request)
elif Em_Status < 0:
- Em_Step = fn_Em_MoO_Next(1)
Calculate Em_Status
- Em_Status = fn_Em_Status(Em_Step,Em_Error)
Send Em_Status to Um
Index | Function | Inputs | Outputs | Comments |
---|---|---|---|---|
EM-A | fn_Em_MoO_Next | Um_Request | Em_Step_New | Jump to New Mode of Operation |
EM-B | fn_Em_SFC | Em_Step | Em_Step_New | SFC (Simulation) |
EM-C | fn_Em_Status | Em_Step EM_Error | Em_Status | | Calculate EM_Status |
Table 3. List of EM Functions
1.4 EM SFC Implementation Rules
These are the rules of step movement in the EM
- Mode of Operation are defined for the EM SFC
- Mode of Operation should have a name, normally (ready, OOS Out of Service, run, etc)
- Mode of Operation should have an integer assigned to such as (1,2,3) this is referred to as Em_MoO
- Em_Status has the following definitions:
- 1,2,.. the Em_Step is that at the last step within Mode of Operation
- -1, -2, .. refers to the Em_Mode of Operation but EM_Step within Mode of Operation has not reached its final step.
- -100,-200,-300 refers to error in that step
- The EM_Steps defined within an EM Mode of Operation can transition to a step below or above but NOT to step in another Mode of operation.
- The following command should enable to jump from any step to the 1st step of another Mode of Operation
- Em_Step = Fn_Em_MoO_Next(Em_MoO)
- Where
- Em_MoO: The Mode of Operation to JUMP to
- Fn_Em_MoO_Next: A function to enable jumping from one MoO to another MoO
- Em_Step: The Em_MoO first step
- Only from the last step in a mode of operation step can JUMP to another mode of operation.
- The transition between EM steps within a Mode of Operation is normally set to “A” for Automatic
- It is recommended that you normally change the mode of operation sequentially
1.5 Python Overview
The Python code developed for the implementation of FRS is summarized below:
1.5.1 Python dictionaries.
Dictionary is one of the built-in data types in Python. Python’s dictionary is example of mapping type. A mapping object ‘maps’ value of one object with another.
In a language dictionary we have pairs of word and corresponding meaning. Two parts of pair are key (word) and value (meaning). Similarly, Python dictionary is also a collection of key-value pairs.
Each key is separated from its value by a colon (:), the items are separated by commas, and the whole thing is enclosed in curly braces. An empty dictionary without any items is written with just two curly braces, like this: {}.
In many ways, the dictionary (or “dict”) is the core data structure of Python, analogous to matrices in MATLAB or data-frames in R. Dictionaries are not unique to Python, most languages support them, often calling them associative arrays, hashes, or maps. Here’s an example of a small dictionary:
simple_dict = {‘a’:1, ‘b’:2, ‘c’:3}
Here simple_dict maps three letters (strings) to numbers (integers), and we can retrieve the integers whenever needed using the strings:
i = simple_dict[‘a’]
print(i)
The square bracket “access” operator lets us plug a key into the dictionary and return a value (or an error if the key is not in the dictionary).
1.6 Case Study
Let’s use UmR350 and EmP350A as an example:
1.6.1 UmR350 Mode of Operation and Steps Definition
UmR350 has the following Mode of Operation and Steps:
Um Mode of Operation | Um_Steps | Um Steps Description | Um_MoO |
---|---|---|---|
Ready | MW | Maintenance Wait | 1 |
Ready | PW | Process Wait | 1 |
Init | FILL | Fill Reactor | 2 |
Init | RCYL | Recycle | 2 |
Init | HEAT | HEAT | 2 |
Run | RUN | Run | 3 |
CSD | SD | Control Shut-Down | 4 |
Table 4: UmR350 Mode of Operation and Steps Definition Table
1.6.2 EmP350A Mode of Operation and Steps
EmP350A has the following Mode of Operation and Steps:
Em Mode of Operation |
Em Step |
EM Step Description |
Em_Status |
---|---|---|---|
OOS | StopMotor | Stop Motor | -1 |
OOS | CloseSucBV | Close Suction BV | -1 |
OOS | CloseDisBV | Close Discharge BV | -1 |
OOS | OutOfServ | Out Of Service | 1 |
Ready | StopMotor | Stop Motor | -2 |
Ready | OpenSucBV | Open Suction BV | -2 |
Ready | CloseDisBV | Close Discharge BV | -2 |
Ready | Ready | Ready | 2 |
Run | OpenDiscBV | Open Dischare BV | -3 |
Run | OpenSucBV | Open Suction BV | -3 |
Run | StartMotor | Start Motor | -3 |
Run | Run | Run | 3 |
Table 5. EmP350A Mode of Operation and Steps
This Em has 3 CCM
Suction Block Valve (BV)
Pump Motor
Discharge Block Valve (BV)
In the above table, the Em_Status is calculated based on its location step within the MoO.
Negative Number represent the MoO of ABS(Em_Status) but Steps in MoO are not finished.
Note that the some of names name in the above table are duplicated, therefor using the recommended Em Step naming convention from CDL book of convention will yield to the following:
Em Step Name: mNN + sMM + Description
Where
mNN: Defined as m for the mode of operation and NN as a sequential Number (1,2,..)
sMM: Defined as s for the step and MM as a sequential Number (1,2,..)
Em Mode of Operation | Em Step | Em Step Description | Em_Status |
---|---|---|---|
OOS | m01s01_StopMotor | Stop Motor | -1 |
OOS | m01s02_CloseSucBV | Close Suction BV | -1 |
OOS | m01s03_CloseDisBV | Close Discharge BV | -1 |
OOS | m01s04_OutOfServ | Out Of Service | 1 |
Ready | m02s01_StopMotor | Stop Motor | -2 |
Ready | m02s02_OpenSucBV | Open Suction BV | -2 |
Ready | m02s03_CloseDisBV | Close Discharge BV | -2 |
Ready | m02s04_Ready | Ready | 2 |
Run | m03s01_OpenDiscBV | Open Discharge BV | -3 |
Run | m03s02_OpenSucBV | Open Suction BV | -3 |
Run | m03s03_StartMotor | Start Motor | -3 |
Run | m03s04_Run | Run | 3 |
Table 6. EmP350A Mode of Operation and Steps (CDL Recommended)
In the above table, the Em_Status is calculated based on its location step within the MoO.
In case of error where Step actions are executed but the OR of all verify test yields to False, the Em_status is set to
Index | Em_Status Value | Description |
---|---|---|
1 | -101,-102,-103,-104 | Error in MoO 1 |
2 | -201.-202,-203,-204 | Error in MoO 2 |
3 | -301,-302,-303,-304 | Error in MoO 3 |
4 | -900 | Error |
Table 7: Em_MoO and Step information Table (CDL Requirement)
The Em_Status is set with following formula
Em_Status = Em_MoO * -100 + Em_Step_Number in Mode of Operation
Index | Mode of Operation | Em_MoO | Em_Status Value | Description |
---|---|---|---|---|
1 | OOS | 1 | -101,-102,-103,-104 | Error in MoO 1 |
2 | Ready | 2 | -201.-202,-203,-204 | Error in MoO 2 |
3 | Init | 3 | -301,-302,-303,-304 | Error in MoO 3 |
4 | -900 | Error |
Table 8: Em_MoO and Error numbering
1.6.3 Um and Em Interaction Matrix
The Um and Em Interaction matrix is shown below
Um Mode of Operation | Um_MoO | Um_Steps | Em_MoO 1:OOS |
Em_MoO 2:Ready |
Em_MoO 3:Run |
---|---|---|---|---|---|
Ready | 1 | MW | X | ||
Ready | 1 | PW | X | ||
Init | 2 | FILL | X | ||
Init | 2 | RCYL | X | ||
Init | 2 | HEAT | X | ||
Run | 3 | RUN | X | ||
CSD | 4 | SD | X |
Table 9. Um-Step to Em-MoO Table
In the above interaction matrix, the first two columns represent
Um Mode of operation
Um Step
The reminding columns represent the Em Mode of Operation.
For example, if Um step is RCYL then the Em Mode of Operation should change to Run
The “X” represents the desired interaction between the Um Steps and the Em Mode of operation. The “X” can be changed to the Em Mode of Operation sequential Number (1,2,..)
Um Mode of Operation | Em_MoO | Um_Steps | Em_MoO 1:OOS |
Em_MoO 2:Ready |
Em_MoO 3:Run |
---|---|---|---|---|---|
Ready | 1 | MW | 1 | ||
Ready | 1 | PW | 2 | ||
Init | 2 | FILL | 2 | ||
Init | 2 | RCYL | 3 | ||
Init | 2 | HEAT | 3 | ||
Run | 3 | RUN | 3 | ||
CSD | 4 | SD | 1 |
Table10. Um-Step to Em-MoO Sequential Number Table
The parent (Um) sends a Request (Em Mode of Operation Sequential Number) to the Child (Em), The Child (Em) module will move to the first step of the Em mode of Operation and execute all steps in that mode of operation. Then it sends the Status (Em Current mode of operation) back to the Parent(Um).
1.6.4 Communication between UM and EM
the Em in this example have three valid MoO. The Um_Requested can be assigned to one of the valid Em_MoO. So, there are 9 possibilities between Um_Requested and Em_Status.
The table below shows the Um_Requested, EM_Status , and Um_request.
Index | Um_Requested | Em_Status | Um_Request | Action Type |
---|---|---|---|---|
1 | 1- OOS | 1-OOS | 1 | None |
2 | 2-Ready | 1 | Decrease | |
3 | 3-Run | 2 | Decrease | |
4 | 2-Ready | 1-OOS | 2 | Increase |
5 | 2-Ready | 2 | None | |
6 | 3-Run | 2 | Decrease | |
7 | 3-Run | 1-OOS | 2 | Increase |
8 | 2-Ready | 3 | Increase | |
9 | 3-Run | 3 | None |
Table 11. Um-Requested to Um-Request Table
For Example, if Em_Status is currently set to 3-Run and Um_Requested is requesting 1-OOS then the following will take place:
The Um_Requested is 1-OOS however the Em_Status is 3-Run or the index 3 of the matrix above.
Per the matrix above the recommended Um_Request is 2 (Index 3) this is sent to Em and Um waits until Em_Status is changed to 2.
When the Um_Requested is 1-OOS and Em_Status is 2 (Index 2 of matrix above) then the Um_Request of 1 can be sent to Em
The Em_Status will be changed to 1
2 UM Communication to EM Algorithms
The simulation program requires the following functions
# Function to exit the program gracefully
def exit_program():
print("\nProgram terminated by the user.")
exit()
The following algorithms are defined here:
2.1 UM Module at each cycle:
Get Em_Status from Em
Um_Step is selected using SFC rules Um_Step = fn_Um_SFC(Um_Step)
The transition should have the following code
- Em_Status > 0 and Em_status == Um_Request and not Um_Error:
Calculate the Um_Requested = fn_Um_Requested(Um_Step)
Calculate the Um_Request | Um_Request_Action = fn_Um_Request(Um_Requested, Em_Status)
Um_Request_Action is defined as:
-1 : Error Move Um_Step to its Default Position
0 : Wait Em is moving it step but has not finished its target Mode of Operation
1: All OK and Em has reached it target Mode of Operation
Send Um_Request to Em
Based on the value of Um_Request_Action do the following:
- Um_Timer_Exceeded = False
- if Um_Request_Action == 1:
- Reset the Um_Timer
- Um_Timer = 0
- elif Um_Request_Action == 0:
- Um_Timer +=1
- if Um_Timer > Um_Timer_Max:
- Um_Timer_Exceeded = True
- if Um_Request_Action == -1 or Um_Error or Um_Timer_Exceeded :
- Jump to Um_Default_Step
- Um_Default_Step = fn_Um_Default_Step(Um_Step) ### Um Functions
Index | Function | Inputs | Outputs | Comments |
---|---|---|---|---|
UM-A | fn_Um_SFC | Um_Step | Um_Step_New | SFC (Simulation) |
UM-B | fn_Um_Requested | Um_Step | Um_Requested | Next EM_MoO |
UM-C | fn_Um_Request | Um_Request Em_Status | Um_Request Um_Request_Action | Convert Um_Requested to Um_Request |
Um-D | fn_Um_Default_Step | Um_Step | Um_Step_New | Default Step |
Table 12. List of UM functions Table
2.2 Um Functions
2.2.1 Function fn_Um_SFC(Um_Active_Step)
# +----------------------------------------------------------------------------+
# | Code: Function Um-A |
# | Function: fn_Um_SFC(Um_Active_Step) |
# | Input: Um_Active_Step |
# | Output: Um_Step |
# +----------------------------------------------------------------------------+
#
# Objective: Based on Um_Active_Step it calculates Um_Step
# assume A for each transitions
#
def fn_Um_SFC(Um_Active_Step,fn_print):
= {'MW': 'PW',
Um_SFC_Dict 'PW': 'FILL',
'FILL': 'RCYL',
'RCYL': 'HEAT',
'HEAT': 'RUN' ,
'RUN': 'CSD',
'CSD': 'PW' }
# Assign Um_Step to 'MW"
= 'MW'
Um_Step
if Um_Active_Step in Um_SFC_Dict:
= Um_SFC_Dict[Um_Active_Step]
Um_Step
if fn_print : print('A - fn_Um_SFC input Um_Active_Step:',Um_Active_Step)
if fn_print : print('A - fn_Um_SFC output Um_Step :',Um_Step)
return Um_Step
2.2.2 Test of Function fn_Um_SFC(Um_Step)
# +----------------------------------------------------------------------------+
# | Code : Function Um-A Test |
# | Function: fn_Um_SFC(Um_Active_Step) |
# | Input: Um_Active_Step |
# | Output: Um_Step |
# +----------------------------------------------------------------------------+
print()
print(' # +--------------------------------------------------------------------------+ ')
print(' # | Function: fn_Um_SFC(Um_Active_Step) |')
print(' # | Input: Um_Step |')
print(' # | Output: Um_Requested |')
print(' # +--------------------------------------------------------------------------+')
#
print(' # Objective: Based on Um_Active_Step it calculates Um_Step')
print(' # assume A for each transitions ')
#
print()
# Define all valid Um_Steps and ass 'Not' to check the function
={1: 'MW',
Test_fn_Um_SFC_Dict2: 'PW',
3: 'FILL',
4: 'RCYL',
5: 'HEAT',
6: 'RUN',
7: 'CSD',
8: 'Not Defined'}
# print the header
= True
fn_print = False
table_print
if table_print:
print()
print("| Index | Um_Active_Step | Um_Step |")
print("|:-----:|:-------:|:--------|")
= 0
i
for key in Test_fn_Um_SFC_Dict:
#
#
= Test_fn_Um_SFC_Dict[key]
Um_Active_Step
= fn_Um_SFC(Um_Active_Step,fn_print)
Um_Step
= i + 1
i
if table_print: print("|" , i ," | ", Um_Active_Step, " | ",Um_Step, "| ")
# +--------------------------------------------------------------------------+
# | Function: fn_Um_SFC(Um_Active_Step) |
# | Input: Um_Step |
# | Output: Um_Requested |
# +--------------------------------------------------------------------------+
# Objective: Based on Um_Active_Step it calculates Um_Step
# assume A for each transitions
A - fn_Um_SFC input Um_Active_Step: MW
A - fn_Um_SFC output Um_Step : PW
A - fn_Um_SFC input Um_Active_Step: PW
A - fn_Um_SFC output Um_Step : FILL
A - fn_Um_SFC input Um_Active_Step: FILL
A - fn_Um_SFC output Um_Step : RCYL
A - fn_Um_SFC input Um_Active_Step: RCYL
A - fn_Um_SFC output Um_Step : HEAT
A - fn_Um_SFC input Um_Active_Step: HEAT
A - fn_Um_SFC output Um_Step : RUN
A - fn_Um_SFC input Um_Active_Step: RUN
A - fn_Um_SFC output Um_Step : CSD
A - fn_Um_SFC input Um_Active_Step: CSD
A - fn_Um_SFC output Um_Step : PW
A - fn_Um_SFC input Um_Active_Step: Not Defined
A - fn_Um_SFC output Um_Step : MW
2.2.3 Function fn_Um_Requested(Um_Step)
The python Code is developed as function and then tested with a script
- function: fn_Um_Requested(Um_Step)
- Input: Um_Step
- Output: Um_Requested
# +----------------------------------------------------------------------------+
# | Code: Function Um-B |
# | Function: fn_Um_Requested(Um_Step) |
# | Input: Um_Step |
# | Output: Um_Requested |
# +----------------------------------------------------------------------------+
def fn_Um_Requested(Um_Step,fn_print):
= {'MW': {'Em_MoO': 1 , 'Em_MoO_Name': 'OOS'},
Um_Requested_Dict 'PW': {'Em_MoO': 2 , 'Em_MoO_Name': 'Ready'},
'FILL': {'Em_MoO': 2 , 'Em_MoO_Name': 'Ready'},
'RCYL': {'Em_MoO': 3 , 'Em_MoO_Name': 'Run'},
'HEAT': {'Em_MoO': 3 , 'Em_MoO_Name': 'Run'},
'RUN': {'Em_MoO': 3 , 'Em_MoO_Name': 'Run'},
'CSD': {'Em_MoO': 1 , 'Em_MoO_Name': 'OOS'} }
if Um_Step in Um_Requested_Dict:
= Um_Requested_Dict.get(Um_Step,{}).get('Em_MoO')
Um_Requested = Um_Requested_Dict.get(Um_Step,{}).get('Em_MoO_Name')
Um_Requested_Name
else:
= -999
Um_Requested ='[Not-Found]'
Um_Requested_Name
if fn_print : print('B - fn_Um_Requested input Um_Step:',Um_Step)
if fn_print : print('B - fn_Um_Requested output Um_Requested :',Um_Requested)
if fn_print : print('B - fn_Um_Requested output Um_Requested_Name :',Um_Requested_Name)
return Um_Requested,Um_Requested_Name
2.2.4 Test of Function fn_Um_Requested(Um_Step)
# +----------------------------------------------------------------------------+
# | Code: Function Um-B - TEST |
# | Function: fn_Um_Requested(Um_Step) |
# | Input: Um_Step |
# | Output: Um_Requested |
# +----------------------------------------------------------------------------+
print()
print(' +----------------------------------------------------------------------------+ ')
print(' # | Code: Function Um-B - TEST |')
print(' # | Function: fn_Um_Requested(Um_Step) |')
print(' # | Input: Um_Step |')
print(' # | Output: Um_Requested |')
print(' # +--------------------------------------------------------------------------+')
print()
# Define all valid Um_Steps and ass 'Not' to check the function
={1: 'MW',
Test_fn_Um_Requested_Dict2: 'PW',
3: 'FILL',
4: 'RCYL',
5: 'HEAT',
6: 'RUN',
7: 'CSD',
8: 'Not'}
# print the header
= True
fn_print = False
table_print
if table_print:
print()
print("| Index | Um_Step | Um_Requested | Em_MoO_Name")
print("|:-----:|:-------:|:--------|:--------|")
= 0
i
for key in Test_fn_Um_Requested_Dict:
#
#
= Test_fn_Um_Requested_Dict[key]
Um_Step= fn_Um_Requested(Um_Step,fn_print)
results
= results[0]
Um_Requested = results[1]
Um_Requested_Name
= i + 1
i if table_print:
print("|" , i ," | ", Um_Step, " | ",Um_Requested, "| ", Um_Requested_Name," |")
+----------------------------------------------------------------------------+
# | Code: Function Um-B - TEST |
# | Function: fn_Um_Requested(Um_Step) |
# | Input: Um_Step |
# | Output: Um_Requested |
# +--------------------------------------------------------------------------+
B - fn_Um_Requested input Um_Step: MW
B - fn_Um_Requested output Um_Requested : 1
B - fn_Um_Requested output Um_Requested_Name : OOS
B - fn_Um_Requested input Um_Step: PW
B - fn_Um_Requested output Um_Requested : 2
B - fn_Um_Requested output Um_Requested_Name : Ready
B - fn_Um_Requested input Um_Step: FILL
B - fn_Um_Requested output Um_Requested : 2
B - fn_Um_Requested output Um_Requested_Name : Ready
B - fn_Um_Requested input Um_Step: RCYL
B - fn_Um_Requested output Um_Requested : 3
B - fn_Um_Requested output Um_Requested_Name : Run
B - fn_Um_Requested input Um_Step: HEAT
B - fn_Um_Requested output Um_Requested : 3
B - fn_Um_Requested output Um_Requested_Name : Run
B - fn_Um_Requested input Um_Step: RUN
B - fn_Um_Requested output Um_Requested : 3
B - fn_Um_Requested output Um_Requested_Name : Run
B - fn_Um_Requested input Um_Step: CSD
B - fn_Um_Requested output Um_Requested : 1
B - fn_Um_Requested output Um_Requested_Name : OOS
B - fn_Um_Requested input Um_Step: Not
B - fn_Um_Requested output Um_Requested : -999
B - fn_Um_Requested output Um_Requested_Name : [Not-Found]
2.2.5 Function fn_Um_Request(Um_Requested,Em_Status)
The python Code is developed as function and then tested with a script
- function: fn_Um_Request(Um_Requested,Em_Status)
- Input: Um_Requested
- Input: Em_Status
- Output: Um_Request
- Output: Um_Request_Action
# +-------------------------------------------------------------------------------+
# | Code: Function Um-C |
# | function: fn_Um_Request(Um_Requested,Em_Status,fn_print) |
# | Input: Um_Requested |
# | Input: Em_Status |
# | Constant: Um_MoO_Max |
# | Constant: Em_MoO_Max |
# | Output: Um_Request |
# | Output: Um_Request_Action |
# | 0: send to EM |
# | 1: Start the Timer |
# | -1: Move to Default step |
# | Output: Um_Request_Message |
# +-------------------------------------------------------------------------------+
def fn_Um_Request(Um_Requested, Em_Status,fn_print):
= 10
Um_MoO_Max = 10
Em_MoO_Max
# Set default value
= -1
Um_Request_Action
if Um_Requested == 0 or Em_Status == 0 or Em_Status > Em_MoO_Max or Um_Requested > Um_MoO_Max:
# Case A
# ------------------------------------------------------------------------
= -900
Um_Request = -1
Um_Request_Action ='Error - Move to Default Step'
Um_Request_Message
elif Em_Status > 0 and Um_Requested > 0 :
# Case B
# ------------------------------------------------------------------------
if Um_Requested == Em_Status :
# No Change
= Em_Status
Um_Request = 1
Um_Request_Action ='Em_MoO: No Change'
Um_Request_Message
elif Um_Requested > Em_Status and Em_Status > 0 :
# Increase
= Em_Status + 1
Um_Request = 1
Um_Request_Action ='Em_MoO: Increase'
Um_Request_Message
elif Um_Requested < Em_Status and Em_Status > 0 :
# Decrease
= Em_Status - 1
Um_Request= 1
Um_Request_Action ='Em_MoO: Decrease'
Um_Request_Message
elif -99 < Em_Status < 0 :
# Case C
# ------------------------------------------------------------------------
= Um_Requested
Um_Request = 0
Um_Request_Action ='Wait for EM to Move to 1,2,3'
Um_Request_Message else:
# Case D
# ------------------------------------------------------------------------
if Em_Status < -99 and Em_Status != -900:
= Um_Requested
Um_Request = -1
Um_Request_Action ='Error - Move to Default Step'
Um_Request_Message elif Em_Status == -900 :
= Um_Requested
Um_Request = -1
Um_Request_Action ='Error - Move to Default Step'
Um_Request_Message
else:
= Um_Requested
Um_Request = -1
Um_Request_Action ='Error - Move to Default Step'
Um_Request_Message
if fn_print : print('C - fn_Um_Request input Um_Requested:',Um_Requested)
if fn_print : print('C - fn_Um_Request input Em_Status:',Em_Status)
if fn_print : print('C - fn_Um_Request output Um_Request :',Um_Request)
if fn_print : print('C - fn_Um_Request output Um_Request_Action :',Um_Request_Action)
if fn_print : print('C - fn_Um_Request output Um_Request_Message :',Um_Request_Message)
return Um_Request,Um_Request_Action,Um_Request_Message
2.2.6 Test of Function fn_Um_Requested(Um_Request,Em_Status)
The calculation of Em_Status is divided into five different methods
- A: Process zero – Either Em_Status or Um_Request* are set to zero or out of range
- B: Calculate the Em_Step is at end of the EM Mode of operation so move as No Change, Increase and decrease
- C: Em_Step is not finished a Em Mode of Operation
- D: Process Error
- E: Process major error
# +-------------------------------------------------------------------------------+
# | Code: Test Function Um-C |
# | function: fn_Um_Request(Um_Requested,Em_Status) |
# | Input: Um_Requested |
# | Input: Em_Status |
# | Output: Um_Request |
# +-------------------------------------------------------------------------------+
print()
print(' +----------------------------------------------------------------------+ ')
print(' # | Code: Test Function Um-C | ')
print(' # | function: fn_Um_Request(Um_Requested,Em_Status) | ')
print(' # | Input: Um_Requested | ')
print(' # | Input: Em_Status | ')
print(' # | Output: Um_Request | ')
print(' # | Output: Um_Request_Action | ')
print(' # +--------------------------------------------------------------------+')
print()
# Test Pattern
# Case Um_Requested EM_Status
# ------- ------------ -----------
# Case-A1 0 -1
# Case-A2 0 0
# Case-A3 0 1
# Case-A4 1 0
# Case-A5 99 1
# Case-A6 1 99
# Case Um_Requested EM_Status
# ------- ------------ -----------
# Case-B1 1 1 No Change
# Case-B2 1 2 Decrease
# Case-B3 2 1 Increase
# Case Um_Requested EM_Status
# ------- ------------ -----------
# Case-C1 1 -1 Wait
# Case Um_Requested EM_Status
# ------- ------------ -----------
# Case-D1 2 -101 Em Error
# Case-D2 3 -900 Error
# Case Um_Requested EM_Status
# Case Um_Requested EM_Status
# ------- ------------ -----------
# Case-E1 999 1 UM undefined
# Case-E2 1 999 EM undefined
= {'Case-A1': {'Um_Requested': 0, 'Em_Status': -1},
Test_Um_Requested_Dict 'Case-A2': {'Um_Requested': 0, 'Em_Status': 0},
'Case-A3': {'Um_Requested': 0, 'Em_Status': 1},
'Case-A4': {'Um_Requested': 1, 'Em_Status': 0},
'Case-A5': {'Um_Requested': 99, 'Em_Status': 1},
'Case-A6': {'Um_Requested': 1, 'Em_Status': 99},
'Case-B1': {'Um_Requested': 1, 'Em_Status': 1},
'Case-B2': {'Um_Requested': 1, 'Em_Status': 2},
'Case-B3': {'Um_Requested': 2, 'Em_Status': 1},
'Case-C1': {'Um_Requested': 1, 'Em_Status': -1},
'Case-D1': {'Um_Requested': 2, 'Em_Status': -101},
'Case-D2': {'Um_Requested': 3, 'Em_Status': -900},
'Case-E1': {'Um_Requested': 999, 'Em_Status': 1},
'Case-E2': {'Um_Requested': 1, 'Em_Status': 999}}
# print the header
= True
fn_print = False
table_print
if table_print:
print("|Case | Um_Requested | Em_Status | Um_Request | Um_Request_Action | Message |")
print("|:----|:------------:|:---------:|:-----------|:-----------|")
=0
i
for case in Test_Um_Requested_Dict:
= Test_Um_Requested_Dict.get(case,{}).get('Um_Requested')
Um_Requested = Test_Um_Requested_Dict.get(case,{}).get('Em_Status')
Em_Status
= fn_Um_Request(Um_Requested, Em_Status,fn_print)
Results
= Results[0]
Um_Request = Results[1]
Um_Request_Action = Results[2]
Um_Request_Message
if table_print:
=i+1
iprint("| ", case, " | ",Um_Requested, " | ", Em_Status , " | ",Um_Request," |", Um_Request_Action , " | ", Um_Request , " | ",Um_Request_Message ," |")
+----------------------------------------------------------------------+
# | Code: Test Function Um-C |
# | function: fn_Um_Request(Um_Requested,Em_Status) |
# | Input: Um_Requested |
# | Input: Em_Status |
# | Output: Um_Request |
# | Output: Um_Request_Action |
# +--------------------------------------------------------------------+
C - fn_Um_Request input Um_Requested: 0
C - fn_Um_Request input Em_Status: -1
C - fn_Um_Request output Um_Request : -900
C - fn_Um_Request output Um_Request_Action : -1
C - fn_Um_Request output Um_Request_Message : Error - Move to Default Step
C - fn_Um_Request input Um_Requested: 0
C - fn_Um_Request input Em_Status: 0
C - fn_Um_Request output Um_Request : -900
C - fn_Um_Request output Um_Request_Action : -1
C - fn_Um_Request output Um_Request_Message : Error - Move to Default Step
C - fn_Um_Request input Um_Requested: 0
C - fn_Um_Request input Em_Status: 1
C - fn_Um_Request output Um_Request : -900
C - fn_Um_Request output Um_Request_Action : -1
C - fn_Um_Request output Um_Request_Message : Error - Move to Default Step
C - fn_Um_Request input Um_Requested: 1
C - fn_Um_Request input Em_Status: 0
C - fn_Um_Request output Um_Request : -900
C - fn_Um_Request output Um_Request_Action : -1
C - fn_Um_Request output Um_Request_Message : Error - Move to Default Step
C - fn_Um_Request input Um_Requested: 99
C - fn_Um_Request input Em_Status: 1
C - fn_Um_Request output Um_Request : -900
C - fn_Um_Request output Um_Request_Action : -1
C - fn_Um_Request output Um_Request_Message : Error - Move to Default Step
C - fn_Um_Request input Um_Requested: 1
C - fn_Um_Request input Em_Status: 99
C - fn_Um_Request output Um_Request : -900
C - fn_Um_Request output Um_Request_Action : -1
C - fn_Um_Request output Um_Request_Message : Error - Move to Default Step
C - fn_Um_Request input Um_Requested: 1
C - fn_Um_Request input Em_Status: 1
C - fn_Um_Request output Um_Request : 1
C - fn_Um_Request output Um_Request_Action : 1
C - fn_Um_Request output Um_Request_Message : Em_MoO: No Change
C - fn_Um_Request input Um_Requested: 1
C - fn_Um_Request input Em_Status: 2
C - fn_Um_Request output Um_Request : 1
C - fn_Um_Request output Um_Request_Action : 1
C - fn_Um_Request output Um_Request_Message : Em_MoO: Decrease
C - fn_Um_Request input Um_Requested: 2
C - fn_Um_Request input Em_Status: 1
C - fn_Um_Request output Um_Request : 2
C - fn_Um_Request output Um_Request_Action : 1
C - fn_Um_Request output Um_Request_Message : Em_MoO: Increase
C - fn_Um_Request input Um_Requested: 1
C - fn_Um_Request input Em_Status: -1
C - fn_Um_Request output Um_Request : 1
C - fn_Um_Request output Um_Request_Action : 0
C - fn_Um_Request output Um_Request_Message : Wait for EM to Move to 1,2,3
C - fn_Um_Request input Um_Requested: 2
C - fn_Um_Request input Em_Status: -101
C - fn_Um_Request output Um_Request : 2
C - fn_Um_Request output Um_Request_Action : -1
C - fn_Um_Request output Um_Request_Message : Error - Move to Default Step
C - fn_Um_Request input Um_Requested: 3
C - fn_Um_Request input Em_Status: -900
C - fn_Um_Request output Um_Request : 3
C - fn_Um_Request output Um_Request_Action : -1
C - fn_Um_Request output Um_Request_Message : Error - Move to Default Step
C - fn_Um_Request input Um_Requested: 999
C - fn_Um_Request input Em_Status: 1
C - fn_Um_Request output Um_Request : -900
C - fn_Um_Request output Um_Request_Action : -1
C - fn_Um_Request output Um_Request_Message : Error - Move to Default Step
C - fn_Um_Request input Um_Requested: 1
C - fn_Um_Request input Em_Status: 999
C - fn_Um_Request output Um_Request : -900
C - fn_Um_Request output Um_Request_Action : -1
C - fn_Um_Request output Um_Request_Message : Error - Move to Default Step
Case | Um_Requested | Em_Status | Um_Request | Um_Request_Action | Um_Request | Message |
---|---|---|---|---|---|---|
Case-A1 | 0 | -1 | -900 | -1 | -900 | Error - Move to Default Step |
Case-A2 | 0 | 0 | -900 | -1 | -900 | Error - Move to Default Step |
Case-A3 | 0 | 1 | -900 | -1 | -900 | Error - Move to Default Step |
Case-A4 | 1 | 0 | -900 | -1 | -900 | Error - Move to Default Step |
Case-A5 | 99 | 1 | -900 | -1 | -900 | Error - Move to Default Step |
Case-A6 | 1 | 99 | -900 | -1 | -900 | Error - Move to Default Step |
Case-B1 | 1 | 1 | 1 | 1 | 1 | Em_MoO: No Change |
Case-B2 | 1 | 2 | 1 | 1 | 1 | Em_MoO: Decrease |
Case-B3 | 2 | 1 | 2 | 1 | 2 | Em_MoO: Increase |
Case-C1 | 1 | -1 | 1 | 0 | 1 | Wait for EM to Move to 1,2,3 |
Case-D1 | 2 | -101 | 2 | -1 | 2 | Error - Move to Default Step |
Case-D2 | 3 | -900 | 3 | -1 | 3 | Error - Move to Default Step |
Case-E1 | 999 | 1 | -900 | -1 | -900 | Error - Move to Default Step |
Case-E2 | 1 | 999 | -900 | -1 | -900 | Error - Move to Default Step |
2.2.7 Function fn_Um_Default_Step(Um_Step)
The python code is developed as function and then tested with a script:
- function: fn_Um_Default_Step(Um_Step)
- Input: Um_Step
- Output: Um_Step_Default
# +-------------------------------------------------------------------------------+
# | Code: Function Um-D |
# | Function: fn_Um_Default_Step(Um_Step) |
# | Input: Um_Step |
# | Output: Em_First_Step |
# +-------------------------------------------------------------------------------+
def fn_Um_Default_Step(Um_Step, fn_print):
= {'MW': 'MW',
Um_default_Step_dict 'PW': 'CSD',
'FILL':'CSD',
'RCYL': 'CSD',
'HEAT': 'CSD',
'RUN': 'CSD',
'CSD': 'CSD'}
if Um_Step in Um_default_Step_dict:
= Um_default_Step_dict[Um_Step]
Um_Step_Default else:
= 'CSD'
Um_Step_Default
if fn_print : print('D - fn_Um_Default_Step input Um_Step:',Um_Step)
if fn_print : print('D - fn_Um_Default_Step output Um_Step_Default :',Um_Step_Default)
return Um_Step_Default
2.2.8 Test of Function fn_Um_Default_Step(Um_Step)
# +-------------------------------------------------------------------------------+
# | Code: Test Function Um-D |
# | Function: fn_Um_Default_Step |
# | Input: Um_Step |
# | Output: Em_First_Step |
# +-------------------------------------------------------------------------------+
print()
print(' +----------------------------------------------------------------------+ ')
print(' # | Code: Test Function UM-D |')
print(' # | Function: fn_Um_Default_Step |')
print(' # | Input: Um_Step |')
print(' # | Output: Um_Step_Default |')
print(' # +--------------------------------------------------------------------+')
print()
={1: 'MW',
Test_fn_Um_Default_Step_Dict2: 'PW',
3: 'FILL',
4: 'RCYL',
5: 'HEAT',
6: 'RUN',
7: 'CSD',
8: 'Not'}
= 0
i # print the header
= True
fn_print = False
table_print
if table_print:
print()
print("| Index | Em_Step | Em_Step_Error | Em_Status")
print("|:-----:|:-------:|:--------------|:--------|")
for key in Test_fn_Um_Default_Step_Dict:
= Test_fn_Um_Default_Step_Dict[key]
Um_Step
= fn_Um_Default_Step(Um_Step,fn_print)
Um_Step_Default
if table_print:
= i + 1
i print("|" , i ," | ", Um_Step, " | ",Um_Step_Default, " |")
+----------------------------------------------------------------------+
# | Code: Test Function UM-D |
# | Function: fn_Um_Default_Step |
# | Input: Um_Step |
# | Output: Um_Step_Default |
# +--------------------------------------------------------------------+
D - fn_Um_Default_Step input Um_Step: MW
D - fn_Um_Default_Step output Um_Step_Default : MW
D - fn_Um_Default_Step input Um_Step: PW
D - fn_Um_Default_Step output Um_Step_Default : CSD
D - fn_Um_Default_Step input Um_Step: FILL
D - fn_Um_Default_Step output Um_Step_Default : CSD
D - fn_Um_Default_Step input Um_Step: RCYL
D - fn_Um_Default_Step output Um_Step_Default : CSD
D - fn_Um_Default_Step input Um_Step: HEAT
D - fn_Um_Default_Step output Um_Step_Default : CSD
D - fn_Um_Default_Step input Um_Step: RUN
D - fn_Um_Default_Step output Um_Step_Default : CSD
D - fn_Um_Default_Step input Um_Step: CSD
D - fn_Um_Default_Step output Um_Step_Default : CSD
D - fn_Um_Default_Step input Um_Step: Not
D - fn_Um_Default_Step output Um_Step_Default : CSD
2.2.9 Function fn_Um_Step_MoO(Um_Step)
The python code is developed as function and then tested with a script:
- function: fn_Um_Step_MoO(Um_Step)
- Input: Um_Step
- Output: Um_MoO
# +-------------------------------------------------------------------------------+
# | Code: Function Um-E |
# | Function: fn_Um_Step_MoO(Um_Step) |
# | Input: Um_Step |
# | Output: Um_MoO |
# +-------------------------------------------------------------------------------+
def fn_Um_Step_MoO(Um_Step, fn_print):
= {'MW': 'm01_Ready',
Um_Step_MoO_dict 'PW': 'm01_Ready',
'FILL':'m02_Init',
'RCYL': 'm02_Init',
'HEAT': 'm02_Init',
'RUN': 'm03_Run',
'CSD': 'm02_Init'}
if Um_Step in Um_Step_MoO_dict:
= Um_Step_MoO_dict[Um_Step]
Um_MoO else:
= 'm01_Ready'
Um_MoO
if fn_print : print('E - fn_Um_Step_MoO input Um_Step:',Um_Step)
if fn_print : print('E - fn_Um_Step_MoO output Um_MoO :',Um_MoO)
return Um_MoO
2.2.10 Test of Function fn_Um_Step_MoO(Um_Step)
# +-------------------------------------------------------------------------------+
# | Code: Test Function Um-E |
# | Function: fn_Um_Step_MoO |
# | Input: Um_Step |
# | Output: Um_MoO |
# +-------------------------------------------------------------------------------+
print()
print(' +----------------------------------------------------------------------+ ')
print(' # | Code: Test Function Um-E |')
print(' # | Function: fn_Um_Step_MoO |')
print(' # | Input: Um_Step |')
print(' # | Output: Um_MoO |')
print(' # +--------------------------------------------------------------------+')
print()
={1: 'MW',
Test_fn_Um_Step_MoO_Dict2: 'PW',
3: 'FILL',
4: 'RCYL',
5: 'HEAT',
6: 'RUN',
7: 'CSD',
8: 'Not'}
= 0
i
# print the header
= True
fn_print = False
table_print
if table_print:
print()
print("| Index | Um_Step | Um_MoO | ")
print("|:-----:|:-------:|:-------|")
for key in Test_fn_Um_Step_MoO_Dict:
= Test_fn_Um_Step_MoO_Dict[key]
Um_Step
= fn_Um_Step_MoO(Um_Step, fn_print)
Um_MoO
if table_print:
= i + 1
i print("|" , i ," | ", Um_Step, " | ",Um_MoO, " |")
+----------------------------------------------------------------------+
# | Code: Test Function Um-E |
# | Function: fn_Um_Step_MoO |
# | Input: Um_Step |
# | Output: Um_MoO |
# +--------------------------------------------------------------------+
E - fn_Um_Step_MoO input Um_Step: MW
E - fn_Um_Step_MoO output Um_MoO : m01_Ready
E - fn_Um_Step_MoO input Um_Step: PW
E - fn_Um_Step_MoO output Um_MoO : m01_Ready
E - fn_Um_Step_MoO input Um_Step: FILL
E - fn_Um_Step_MoO output Um_MoO : m02_Init
E - fn_Um_Step_MoO input Um_Step: RCYL
E - fn_Um_Step_MoO output Um_MoO : m02_Init
E - fn_Um_Step_MoO input Um_Step: HEAT
E - fn_Um_Step_MoO output Um_MoO : m02_Init
E - fn_Um_Step_MoO input Um_Step: RUN
E - fn_Um_Step_MoO output Um_MoO : m03_Run
E - fn_Um_Step_MoO input Um_Step: CSD
E - fn_Um_Step_MoO output Um_MoO : m02_Init
E - fn_Um_Step_MoO input Um_Step: Not
E - fn_Um_Step_MoO output Um_MoO : m01_Ready
3 Em Communication Algorithm
The Em communicates with Um using Em_Status. The Em_Status communicates with Um using the following rules:
Mode of Operation Phase is completed - Em_Status is set to its Em_MoO (1,2,..)
Mode of Operation Phase is in progress - Em_Status is set to its Em_MoO * -1 (-1,-2,..) variables
The Verification in Step has failed - Em_Status is set to its (Em_MoO*-100) + Step Number in MoO (-101,-102m..)
Index | Em_active_step | Em_status | Em_Status_Error |
---|---|---|---|
1 | m01s01_StopMotor | -1 | -101 |
2 | m01s02_CloseSucBV | -1 | -102 |
3 | m01s03_CloseDisBV | -1 | -103 |
4 | m01s04_OutOfServ | 1 | -104 |
5 | m02s01_StopMotor | -2 | -201 |
6 | m02s02_OpenSucBV | -2 | -202 |
7 | m02s03_CloseDisBV | -2 | -203 |
8 | m02s04_Ready | 2 | -204 |
9 | m03s01_OpenDiscBV | -3 | -301 |
10 | m03s02_OpenSucBV | -3 | -302 |
11 | m03s03_StartMotor | -3 | -303 |
12 | m03s04_Run | 3 | -304 |
Table 12. The EM_Step list
The following algorithms are defined
- Calculate Em_Status from Em_Step: fn_Em_Status(Em_Step,Em_Step_Error)
- Calculate first step of the Em Mode of Operation
- Calculate Em_Status
- Send Em_Status to Um
3.1 EM Module at each cycle:
Get Um_Request from Um
Em_Step is selected using SFC rules
Call fn_Em_Status(Em_Step,Em_Step_Error)
- Input: Em_Step
- Input: Em_Step_Error
- Output: Em_Status
- Output: Em_Status_Action
– 0 == All OK Send Em_Status to Um – 1 == MoO not finished – Send Em_Status to UM to start timer – -1 == Error
send Em_Status to UM
if Em_Status_Action = 0 or Um_Requested == 0 :
- call fn_Em_MoO_Next(Um_Requested)
- Input: Um_Request
- Output: Sel_Em_Step
force Em_Step >> Sel_Em_Step
elif Em_Status_Action = 1 :
- wait else:
- call fn_Em_MoO_Next(0)
- Input: 0
- Output: Sel_Em_Step force Em_Step >> Sel_Em_Step
The Python code in the Um module are ## Um Functions
3.2 EM functions
3.2.1 Function fn_Em_Status(Em_Step,Em_Step_Error)
The python Code is developed as function and then tested with a script
- function: fn_Em_Status(Em_Step,Em_Step_Error)
- Input: Em_Step
- Input: Em_Step_Error
- Output: Em_Status
# +-------------------------------------------------------------------------------+
# | Code: Function Em-A |
# | Function : Fn_Em_Status |
# | Purpose: Calculate Fn_Em_Status from Em_Step |
# | Input: Um_Step |
# | Output: Um_Status |
# | Output: Em_Status_Action |
# +-------------------------------------------------------------------------------+
def fn_Em_Status(Em_Step,Em_Step_Error, fn_print):
# Em_Step: EM Step Name
# Em_Step_Error: True == Error detected | False == No Error
={'m01s01_StopMotor': {'Em_Status': -1, 'Em_Status_Error': -101},
Em_Status_Dict'm01s02_CloseSucBV': {'Em_Status': -1, 'Em_Status_Error': -102},
'm01s03_CloseDisBV':{'Em_Status': -1, 'Em_Status_Error': -103},
'm01s04_OutOfServ': {'Em_Status': 1, 'Em_Status_Error': -104},
'm02s01_StopMotor': {'Em_Status': -2, 'Em_Status_Error': -201},
'm02s02_OpenSucBV': {'Em_Status': -2, 'Em_Status_Error': -202},
'm02s03_CloseDisBV': {'Em_Status': -2, 'Em_Status_Error': -203},
'm02s04_Ready': {'Em_Status': 2, 'Em_Status_Error': -204},
'm03s01_OpenDiscBV':{'Em_Status': -3, 'Em_Status_Error': -301},
'm03s02_OpenSucBV': {'Em_Status': -3, 'Em_Status_Error': -302},
'm03s03_StartMotor': {'Em_Status': -3, 'Em_Status_Error': -303},
'm03s04_Run': {'Em_Status': 3, 'Em_Status_Error': -304},
'NotDefined': {'Em_Status': -900, 'Em_Status_Error': -900}}
= -900
Em_Status = -1
Em_Status_Action
if Em_Step_Error :
# True == Error
= Em_Status_Dict.get(Em_Step,{}).get('Em_Status_Error')
Em_Status = -1
Em_Status_Action else:
# False == No Error
= Em_Status_Dict.get(Em_Step,{}).get('Em_Status')
Em_Status
# Ensure Em_Status is not None
if Em_Status is None:
= -1 # Assign a default action appropriately
Em_Status_Action else:
if Em_Status > 0:
= 1
Em_Status_Action elif -99 < Em_Status < 0:
= 0
Em_Status_Action else:
= -1
Em_Status_Action
if fn_print : print('A - fn_Em_Status input Em_Step:',Em_Step)
if fn_print : print('A - fn_Em_Status input Em_Step_Error:',Em_Step_Error)
if fn_print : print('A - fn_Em_Status output Em_Status :',Em_Status)
if fn_print : print('A - fn_Em_Status output Em_Status_Action :',Em_Status_Action)
return Em_Status, Em_Status_Action
3.2.2 Test of Function fn_Em_Status(Em_Step,Em_Step_Error)
# +-------------------------------------------------------------------------------+
# | Code: Test Function Em-A |
# | Function : Fn_Em_Status |
# | Purpose: Calculate Fn_Em_Status from Em_Step |
# | Input: Um_Step |
# | Output: Um_MoO |
# +-------------------------------------------------------------------------------+
print()
print(' +----------------------------------------------------------------------+ ')
print(' # | Code: Test Function Em-A | ')
print(' # | Function : Fn_Em_Status | ')
print(' # | Purpose: Calculate Fn_Em_Status from Em_Step | ')
print(' # | Input: Um_Step | ')
print(' # | Output: Um_MoO | ')
print(' # +--------------------------------------------------------------------+')
print()
= {10: 'm01s01_StopMotor',
Test_Fn_Em_Status_Dict 15: 'm01s02_CloseSucBV',
20: 'm01s03_CloseDisBV',
25: 'm01s04_OutOfServ',
30: 'm02s01_StopMotor',
35: 'm02s02_OpenSucBV',
40: 'm02s03_CloseDisBV',
45: 'm02s04_Ready',
50: 'm03s01_OpenDiscBV',
55: 'm03s02_OpenSucBV',
60: 'm03s03_StartMotor',
65: 'm03s04_Run',
70: 'NotDefined'}
# print the header
= True
fn_print = False
table_print
if table_print:
print()
print("| Index | Em_Step | Em_Step_Error | Em_Status | Em_Status_Action |")
print("|:-----:|:-------:|:--------------|:--------|:--------|")
= 0
i
for Em_Step_Error in [False,True]:
for key in Test_Fn_Em_Status_Dict:
= Test_Fn_Em_Status_Dict[key]
Em_Step
= fn_Em_Status(Em_Step,Em_Step_Error,fn_print)
Results = Results[0]
Em_Status = Results[1]
Em_Status_Action
if table_print:
= i + 1
i print("|" , i ," | ", Em_Step, " | ",Em_Step_Error, " | ", Em_Status," | ", Em_Status_Action," |")
+----------------------------------------------------------------------+
# | Code: Test Function Em-A |
# | Function : Fn_Em_Status |
# | Purpose: Calculate Fn_Em_Status from Em_Step |
# | Input: Um_Step |
# | Output: Um_MoO |
# +--------------------------------------------------------------------+
A - fn_Em_Status input Em_Step: m01s01_StopMotor
A - fn_Em_Status input Em_Step_Error: False
A - fn_Em_Status output Em_Status : -1
A - fn_Em_Status output Em_Status_Action : 0
A - fn_Em_Status input Em_Step: m01s02_CloseSucBV
A - fn_Em_Status input Em_Step_Error: False
A - fn_Em_Status output Em_Status : -1
A - fn_Em_Status output Em_Status_Action : 0
A - fn_Em_Status input Em_Step: m01s03_CloseDisBV
A - fn_Em_Status input Em_Step_Error: False
A - fn_Em_Status output Em_Status : -1
A - fn_Em_Status output Em_Status_Action : 0
A - fn_Em_Status input Em_Step: m01s04_OutOfServ
A - fn_Em_Status input Em_Step_Error: False
A - fn_Em_Status output Em_Status : 1
A - fn_Em_Status output Em_Status_Action : 1
A - fn_Em_Status input Em_Step: m02s01_StopMotor
A - fn_Em_Status input Em_Step_Error: False
A - fn_Em_Status output Em_Status : -2
A - fn_Em_Status output Em_Status_Action : 0
A - fn_Em_Status input Em_Step: m02s02_OpenSucBV
A - fn_Em_Status input Em_Step_Error: False
A - fn_Em_Status output Em_Status : -2
A - fn_Em_Status output Em_Status_Action : 0
A - fn_Em_Status input Em_Step: m02s03_CloseDisBV
A - fn_Em_Status input Em_Step_Error: False
A - fn_Em_Status output Em_Status : -2
A - fn_Em_Status output Em_Status_Action : 0
A - fn_Em_Status input Em_Step: m02s04_Ready
A - fn_Em_Status input Em_Step_Error: False
A - fn_Em_Status output Em_Status : 2
A - fn_Em_Status output Em_Status_Action : 1
A - fn_Em_Status input Em_Step: m03s01_OpenDiscBV
A - fn_Em_Status input Em_Step_Error: False
A - fn_Em_Status output Em_Status : -3
A - fn_Em_Status output Em_Status_Action : 0
A - fn_Em_Status input Em_Step: m03s02_OpenSucBV
A - fn_Em_Status input Em_Step_Error: False
A - fn_Em_Status output Em_Status : -3
A - fn_Em_Status output Em_Status_Action : 0
A - fn_Em_Status input Em_Step: m03s03_StartMotor
A - fn_Em_Status input Em_Step_Error: False
A - fn_Em_Status output Em_Status : -3
A - fn_Em_Status output Em_Status_Action : 0
A - fn_Em_Status input Em_Step: m03s04_Run
A - fn_Em_Status input Em_Step_Error: False
A - fn_Em_Status output Em_Status : 3
A - fn_Em_Status output Em_Status_Action : 1
A - fn_Em_Status input Em_Step: NotDefined
A - fn_Em_Status input Em_Step_Error: False
A - fn_Em_Status output Em_Status : -900
A - fn_Em_Status output Em_Status_Action : -1
A - fn_Em_Status input Em_Step: m01s01_StopMotor
A - fn_Em_Status input Em_Step_Error: True
A - fn_Em_Status output Em_Status : -101
A - fn_Em_Status output Em_Status_Action : -1
A - fn_Em_Status input Em_Step: m01s02_CloseSucBV
A - fn_Em_Status input Em_Step_Error: True
A - fn_Em_Status output Em_Status : -102
A - fn_Em_Status output Em_Status_Action : -1
A - fn_Em_Status input Em_Step: m01s03_CloseDisBV
A - fn_Em_Status input Em_Step_Error: True
A - fn_Em_Status output Em_Status : -103
A - fn_Em_Status output Em_Status_Action : -1
A - fn_Em_Status input Em_Step: m01s04_OutOfServ
A - fn_Em_Status input Em_Step_Error: True
A - fn_Em_Status output Em_Status : -104
A - fn_Em_Status output Em_Status_Action : -1
A - fn_Em_Status input Em_Step: m02s01_StopMotor
A - fn_Em_Status input Em_Step_Error: True
A - fn_Em_Status output Em_Status : -201
A - fn_Em_Status output Em_Status_Action : -1
A - fn_Em_Status input Em_Step: m02s02_OpenSucBV
A - fn_Em_Status input Em_Step_Error: True
A - fn_Em_Status output Em_Status : -202
A - fn_Em_Status output Em_Status_Action : -1
A - fn_Em_Status input Em_Step: m02s03_CloseDisBV
A - fn_Em_Status input Em_Step_Error: True
A - fn_Em_Status output Em_Status : -203
A - fn_Em_Status output Em_Status_Action : -1
A - fn_Em_Status input Em_Step: m02s04_Ready
A - fn_Em_Status input Em_Step_Error: True
A - fn_Em_Status output Em_Status : -204
A - fn_Em_Status output Em_Status_Action : -1
A - fn_Em_Status input Em_Step: m03s01_OpenDiscBV
A - fn_Em_Status input Em_Step_Error: True
A - fn_Em_Status output Em_Status : -301
A - fn_Em_Status output Em_Status_Action : -1
A - fn_Em_Status input Em_Step: m03s02_OpenSucBV
A - fn_Em_Status input Em_Step_Error: True
A - fn_Em_Status output Em_Status : -302
A - fn_Em_Status output Em_Status_Action : -1
A - fn_Em_Status input Em_Step: m03s03_StartMotor
A - fn_Em_Status input Em_Step_Error: True
A - fn_Em_Status output Em_Status : -303
A - fn_Em_Status output Em_Status_Action : -1
A - fn_Em_Status input Em_Step: m03s04_Run
A - fn_Em_Status input Em_Step_Error: True
A - fn_Em_Status output Em_Status : -304
A - fn_Em_Status output Em_Status_Action : -1
A - fn_Em_Status input Em_Step: NotDefined
A - fn_Em_Status input Em_Step_Error: True
A - fn_Em_Status output Em_Status : -900
A - fn_Em_Status output Em_Status_Action : -1
3.2.3 Function fn_Em_MoO_Next(Um_Request)
The python code is developed as function and then tested with a script:
- function: fn_Em_MoO_Next(Um_Request)
- Input: Um_Request
- Output: Em_Step
# +-------------------------------------------------------------------------------+
# | Code: Function Em-B |
# | Function: fn_Em_MoO_Next (Um_Request) |
# | Input: Um_Request |
# | Output: Em_Step_Selected |
# +-------------------------------------------------------------------------------+
def fn_Em_MoO_Next (Um_Request, fn_print):
= {1: 'm01s01_StopMotor',2: 'm02s01_StopMotor',3: 'm03s01_OpenDiscBV'}
Em_MoD_Next_Dict
# Um_Request == 0 means re-start EM
='Not-Defined'
Sel_Em_Step for key in Em_MoD_Next_Dict:
if key == Um_Request:
= Em_MoD_Next_Dict[key]
Sel_Em_Step
if Sel_Em_Step == 'Not-Defined':
= Em_MoD_Next_Dict[1]
Sel_Em_Step
if fn_print : print('B - fn_Em_MoO_Next input Um_Request:',Um_Request)
if fn_print : print('B - fn_Em_MoO_Next output Sel_Em_Step :',Sel_Em_Step)
return Sel_Em_Step
3.2.4 Test of Function fn_Em_MoO_Next (Um_Request)
# +-------------------------------------------------------------------------------+
# | Code: Test Function Em-B |
# | Function: fn_Em_MoO_Next (Um_Request) |
# | Input: Um_Request |
# | Output: Sel_Em_Step |
# +-------------------------------------------------------------------------------+
print()
print(' +----------------------------------------------------------------------+ ')
print(' # | Code: Test Function EM-B |')
print(' # | Function: fn_Em_MoO_Next (Um_Request) |')
print(' # | Input: Um_Request |')
print(' # | Output: Sel_Em_Step |')
print(' # +--------------------------------------------------------------------+')
print()
= {0,1,2,3,4,-999}
Test_fn_Em_MoO_Next_Dict
# print the header
# print the header
= True
fn_print = False
table_print
if table_print:
print()
print("| Index | Um_Request | Sel_EM_Step |")
print("|:-----:|:-------:|:-------------|")
= 0
i
for key in Test_fn_Em_MoO_Next_Dict:
= key
Um_Request = fn_Em_MoO_Next(Um_Request,fn_print)
Sel_EM_Step
if table_print:
= i + 1
i print("| ",i ," | " , Um_Request , " | ", Sel_EM_Step, " |")
+----------------------------------------------------------------------+
# | Code: Test Function EM-B |
# | Function: fn_Em_MoO_Next (Um_Request) |
# | Input: Um_Request |
# | Output: Sel_Em_Step |
# +--------------------------------------------------------------------+
B - fn_Em_MoO_Next input Um_Request: 0
B - fn_Em_MoO_Next output Sel_Em_Step : m01s01_StopMotor
B - fn_Em_MoO_Next input Um_Request: 1
B - fn_Em_MoO_Next output Sel_Em_Step : m01s01_StopMotor
B - fn_Em_MoO_Next input Um_Request: 2
B - fn_Em_MoO_Next output Sel_Em_Step : m02s01_StopMotor
B - fn_Em_MoO_Next input Um_Request: 3
B - fn_Em_MoO_Next output Sel_Em_Step : m03s01_OpenDiscBV
B - fn_Em_MoO_Next input Um_Request: 4
B - fn_Em_MoO_Next output Sel_Em_Step : m01s01_StopMotor
B - fn_Em_MoO_Next input Um_Request: -999
B - fn_Em_MoO_Next output Sel_Em_Step : m01s01_StopMotor
3.2.5 Function fn_Em_SFC(Em_Step)
# +----------------------------------------------------------------------------+
# | Code: Function Um-C |
# | Function: fn_Em_SFC(Em_Step) |
# | Input: Em_Step |
# | Output: Em_Step_New |
# +----------------------------------------------------------------------------+
#
# Objective: Based on Em_Step it calculates Em_Step
# assume A for each transitions
#
def fn_Em_SFC(Em_Step, fn_print):
={'m01s01_StopMotor': 'm01s02_CloseSucBV',
Em_SFC_Dict'm01s02_CloseSucBV': 'm01s03_CloseDisBV',
'm01s03_CloseDisBV':'m01s04_OutOfServ',
'm01s04_OutOfServ': 'm01s04_OutOfServ',
'm02s01_StopMotor': 'm02s02_OpenSucBV',
'm02s02_OpenSucBV': 'm02s03_CloseDisBV',
'm02s03_CloseDisBV': 'm02s04_Ready',
'm02s04_Ready': 'm02s04_Ready',
'm03s01_OpenDiscBV': 'm03s02_OpenSucBV',
'm03s02_OpenSucBV': 'm03s03_StartMotor',
'm03s03_StartMotor': 'm03s04_Run',
'm03s04_Run': 'm03s04_Run',
'NotDefined':'m01s01_StopMotor'}
# Assign Em_Step to 1st step
= 'm01s02_CloseSucBV'
Em_Step_New
if Em_Step in Em_SFC_Dict:
= Em_SFC_Dict[Em_Step]
Em_Step_New
if fn_print : print('C - fn_Em_SFC input Em_Step:',Em_Step)
if fn_print : print('C - fn_Em_SFC output Em_Step_New :',Em_Step_New)
return Em_Step_New
3.2.6 Test of Function fn_Em_SFC(Em_Step)
# +----------------------------------------------------------------------------+
# | Code : Function Em-C Test |
# | Function: fn_Em_SFC(Um_Active_Step) |
# | Input: Em_Step |
# | Output: Um_Step_New |
# +----------------------------------------------------------------------------+
print()
print(' # +--------------------------------------------------------------------+ ')
print(' # | Function: fn_Em_SFC(Em_Step) |')
print(' # | Input: Em_Step |')
print(' # | Output: Em_Step_New |')
print(' # +--------------------------------------------------------------------+')
#
print(' # Objective: Based on Em_Step it calculates Em_Step_New')
print(' # assume A for each transitions ')
#
print()
# Define all valid Um_Steps and assign '999' to check the function
={10: 'm01s01_StopMotor',
Test_fn_Em_SFC_Dict15: 'm01s02_CloseSucBV',
20: 'm01s03_CloseDisBV',
30: 'm01s04_OutOfServ',
40: 'm02s01_StopMotor',
50: 'm02s02_OpenSucBV',
60: 'm02s03_CloseDisBV',
70: 'm02s04_Ready',
80:'m03s01_OpenDiscBV',
90: 'm03s02_OpenSucBV',
100: 'm03s03_StartMotor',
105: 'm03s04_Run',
999: 'NotDefined'}
# print the header
= True
fn_print = False
table_print
if table_print:
print()
print("| Index | EM_Step_Number | Em_Step | Em_Step_New | Action")
print("|:-----:|:-------:|:--------|:--------|:--------|")
= 0
i
= "Next Step"
test_message for key in Test_fn_Em_SFC_Dict:
#
#
= Test_fn_Em_SFC_Dict[key]
Em_Step
= fn_Em_SFC(Em_Step, fn_print)
Em_Step_New
= "Next Step"
test_message
if Em_Step == Em_Step_New:
= "Wait for Um_Request"
test_message
if table_print:
= i + 1
i print("|" , i ," | ", key," | ", Em_Step, " | ",Em_Step_New, " | ", test_message, "|")
# +--------------------------------------------------------------------+
# | Function: fn_Em_SFC(Em_Step) |
# | Input: Em_Step |
# | Output: Em_Step_New |
# +--------------------------------------------------------------------+
# Objective: Based on Em_Step it calculates Em_Step_New
# assume A for each transitions
C - fn_Em_SFC input Em_Step: m01s01_StopMotor
C - fn_Em_SFC output Em_Step_New : m01s02_CloseSucBV
C - fn_Em_SFC input Em_Step: m01s02_CloseSucBV
C - fn_Em_SFC output Em_Step_New : m01s03_CloseDisBV
C - fn_Em_SFC input Em_Step: m01s03_CloseDisBV
C - fn_Em_SFC output Em_Step_New : m01s04_OutOfServ
C - fn_Em_SFC input Em_Step: m01s04_OutOfServ
C - fn_Em_SFC output Em_Step_New : m01s04_OutOfServ
C - fn_Em_SFC input Em_Step: m02s01_StopMotor
C - fn_Em_SFC output Em_Step_New : m02s02_OpenSucBV
C - fn_Em_SFC input Em_Step: m02s02_OpenSucBV
C - fn_Em_SFC output Em_Step_New : m02s03_CloseDisBV
C - fn_Em_SFC input Em_Step: m02s03_CloseDisBV
C - fn_Em_SFC output Em_Step_New : m02s04_Ready
C - fn_Em_SFC input Em_Step: m02s04_Ready
C - fn_Em_SFC output Em_Step_New : m02s04_Ready
C - fn_Em_SFC input Em_Step: m03s01_OpenDiscBV
C - fn_Em_SFC output Em_Step_New : m03s02_OpenSucBV
C - fn_Em_SFC input Em_Step: m03s02_OpenSucBV
C - fn_Em_SFC output Em_Step_New : m03s03_StartMotor
C - fn_Em_SFC input Em_Step: m03s03_StartMotor
C - fn_Em_SFC output Em_Step_New : m03s04_Run
C - fn_Em_SFC input Em_Step: m03s04_Run
C - fn_Em_SFC output Em_Step_New : m03s04_Run
C - fn_Em_SFC input Em_Step: NotDefined
C - fn_Em_SFC output Em_Step_New : m01s01_StopMotor
3.2.7 Function fn_Em_Step_MoO(Em_Step)
# +----------------------------------------------------------------------------+
# | Code: Function Em-D |
# | Function: fn_Em_Step_MoO(Em_Step) |
# | Input: Em_Step |
# | Output: Em_MoO |
# +----------------------------------------------------------------------------+
#
# Objective: Based on Em_Step it calculates Em_Step
# assume A for each transitions
#
def fn_Em_Step_MoO(Em_Step, fn_print):
={'m01s01_StopMotor': 'm01_OOS',
Em_SFC_Dict'm01s02_CloseSucBV': 'm01_OOS',
'm01s03_CloseDisBV':'m01_OOS',
'm01s04_OutOfServ': 'm01_OOS',
'm02s01_StopMotor': 'm02_Ready',
'm02s02_OpenSucBV': 'm02_Ready',
'm02s03_CloseDisBV': 'm02_Ready',
'm02s04_Ready': 'm02_Ready',
'm03s01_OpenDiscBV': 'm03_Run',
'm03s02_OpenSucBV': 'm03_Run',
'm03s03_StartMotor': 'm03_Run',
'm03s04_Run': 'm03_Run',
'NotDefined':'m01_OOS'}
# Assign Em_Step to 1st step
= 'm01_OOS'
Em_MoO
if Em_Step in Em_SFC_Dict:
= Em_SFC_Dict[Em_Step]
Em_MoO
if fn_print : print('D - fn_Em_Step_MoO input Em_Step:',Em_Step)
if fn_print : print('D - fn_Em_Step_MoO output Em_MoO :',Em_MoO)
return Em_MoO
3.2.8 Test of Function fn_Em_Step_MoO(Em_Step)
# +----------------------------------------------------------------------------+
# | Code : Function Em-D Test |
# | Function: fn_Em_Step_MoO(EM_Step) |
# | Input: Em_Step |
# | Output: Em_MoO |
# +----------------------------------------------------------------------------+
print()
print(' # +--------------------------------------------------------------------+ ')
print(' # | Function: fn_Em_Step_MoO(Em_Step) |')
print(' # | Input: Em_Step |')
print(' # | Output: Em_MoO |')
print(' # +--------------------------------------------------------------------+')
#
print(' # Objective: Based on Em_Step it calculates Em_Step_New')
print(' # assume A for each transitions ')
#
print()
# Define all valid Um_Steps and assign '999' to check the function
={10: 'm01s01_StopMotor',
Test_fn_Em_Step_MoO_Dict15: 'm01s02_CloseSucBV',
20: 'm01s03_CloseDisBV',
30: 'm01s04_OutOfServ',
40: 'm02s01_StopMotor',
50: 'm02s02_OpenSucBV',
60: 'm02s03_CloseDisBV',
70: 'm02s04_Ready',
80: 'm03s01_OpenDiscBV',
90: 'm03s02_OpenSucBV',
100: 'm03s03_StartMotor',
105: 'm03s04_Run',
999: 'NotDefined'}
# print the header
= True
fn_print = False
table_print
if table_print:
print()
print("| Index | Em_Step | EM_MoO ")
print("|:-----:|:-------:|:--------|")
= 0
i
for key in Test_fn_Em_Step_MoO_Dict:
#
#
= Test_fn_Em_Step_MoO_Dict[key]
Em_Step
= fn_Em_Step_MoO(Em_Step, fn_print)
Em_MoO
if table_print:
= i + 1
i
print("|" , i ," | ", Em_Step, " | ",Em_MoO, " | ")
# +--------------------------------------------------------------------+
# | Function: fn_Em_Step_MoO(Em_Step) |
# | Input: Em_Step |
# | Output: Em_MoO |
# +--------------------------------------------------------------------+
# Objective: Based on Em_Step it calculates Em_Step_New
# assume A for each transitions
D - fn_Em_Step_MoO input Em_Step: m01s01_StopMotor
D - fn_Em_Step_MoO output Em_MoO : m01_OOS
D - fn_Em_Step_MoO input Em_Step: m01s02_CloseSucBV
D - fn_Em_Step_MoO output Em_MoO : m01_OOS
D - fn_Em_Step_MoO input Em_Step: m01s03_CloseDisBV
D - fn_Em_Step_MoO output Em_MoO : m01_OOS
D - fn_Em_Step_MoO input Em_Step: m01s04_OutOfServ
D - fn_Em_Step_MoO output Em_MoO : m01_OOS
D - fn_Em_Step_MoO input Em_Step: m02s01_StopMotor
D - fn_Em_Step_MoO output Em_MoO : m02_Ready
D - fn_Em_Step_MoO input Em_Step: m02s02_OpenSucBV
D - fn_Em_Step_MoO output Em_MoO : m02_Ready
D - fn_Em_Step_MoO input Em_Step: m02s03_CloseDisBV
D - fn_Em_Step_MoO output Em_MoO : m02_Ready
D - fn_Em_Step_MoO input Em_Step: m02s04_Ready
D - fn_Em_Step_MoO output Em_MoO : m02_Ready
D - fn_Em_Step_MoO input Em_Step: m03s01_OpenDiscBV
D - fn_Em_Step_MoO output Em_MoO : m03_Run
D - fn_Em_Step_MoO input Em_Step: m03s02_OpenSucBV
D - fn_Em_Step_MoO output Em_MoO : m03_Run
D - fn_Em_Step_MoO input Em_Step: m03s03_StartMotor
D - fn_Em_Step_MoO output Em_MoO : m03_Run
D - fn_Em_Step_MoO input Em_Step: m03s04_Run
D - fn_Em_Step_MoO output Em_MoO : m03_Run
D - fn_Em_Step_MoO input Em_Step: NotDefined
D - fn_Em_Step_MoO output Em_MoO : m01_OOS
Please contact us if you need more information.