diff --git a/CHANGELOG b/CHANGELOG
index 9b7a70c8..250f33e6 100644
--- a/CHANGELOG
+++ b/CHANGELOG
@@ -1,5 +1,7 @@
Changes to version 0.8.7
------------------------
+- extended beoglebone demo (write access to GAPC settings, ...)
+- File service: support for wildcard character ('*') in requests
- server: changed signature of WriteAccessHandler: Handler now return MmsDataAccessError instead of boolean value!
- server: added function IedModel_setIedNameForDynamicModel
diff --git a/config/stack_config.h b/config/stack_config.h
index 91322e99..e3b0b2d0 100644
--- a/config/stack_config.h
+++ b/config/stack_config.h
@@ -10,7 +10,7 @@
#define STACK_CONFIG_H_
/* include asserts if set to 1 */
-#define DEBUG 1
+#define DEBUG 0
/* print debugging information with printf if set to 1 */
#define DEBUG_SOCKET 0
@@ -136,7 +136,7 @@
#define CONFIG_IEC61850_SETTING_GROUPS 1
/* default reservation time of a setting group control block in s */
-#define CONFIG_IEC61850_SG_RESVTMS 10
+#define CONFIG_IEC61850_SG_RESVTMS 300
/* default results for MMS identify service */
#define CONFIG_DEFAULT_MMS_VENDOR_NAME "libiec61850.com"
diff --git a/demos/beaglebone/beagle_demo.c b/demos/beaglebone/beagle_demo.c
index 31cc3c6a..82c1ac05 100644
--- a/demos/beaglebone/beagle_demo.c
+++ b/demos/beaglebone/beagle_demo.c
@@ -77,27 +77,27 @@ static void
updateLED1stVal(bool newLedState, uint64_t timeStamp) {
switchLED(LED1, newLedState);
+ IedServer_updateUTCTimeAttributeValue(iedServer, IEDMODEL_GenericIO_GGIO1_SPCSO1_t, timeStamp);
IedServer_updateBooleanAttributeValue(iedServer, IEDMODEL_GenericIO_GGIO1_SPCSO1_stVal, newLedState);
IedServer_updateQuality(iedServer, IEDMODEL_GenericIO_GGIO1_SPCSO1_q, QUALITY_VALIDITY_GOOD | QUALITY_SOURCE_SUBSTITUTED);
- IedServer_updateUTCTimeAttributeValue(iedServer, IEDMODEL_GenericIO_GGIO1_SPCSO1_t, timeStamp);
}
static void
updateLED2stVal(bool newLedState, uint64_t timeStamp) {
switchLED(LED2, newLedState);
+ IedServer_updateUTCTimeAttributeValue(iedServer, IEDMODEL_GenericIO_GGIO1_SPCSO2_t, timeStamp);
IedServer_updateBooleanAttributeValue(iedServer, IEDMODEL_GenericIO_GGIO1_SPCSO2_stVal, newLedState);
IedServer_updateQuality(iedServer, IEDMODEL_GenericIO_GGIO1_SPCSO2_q, QUALITY_VALIDITY_QUESTIONABLE | QUALITY_DETAIL_OSCILLATORY);
- IedServer_updateUTCTimeAttributeValue(iedServer, IEDMODEL_GenericIO_GGIO1_SPCSO2_t, timeStamp);
}
static void
updateLED3stVal(bool newLedState, uint64_t timeStamp) {
switchLED(LED3, newLedState);
+ IedServer_updateUTCTimeAttributeValue(iedServer, IEDMODEL_GenericIO_GGIO1_SPCSO3_t, timeStamp);
IedServer_updateBooleanAttributeValue(iedServer, IEDMODEL_GenericIO_GGIO1_SPCSO3_stVal, newLedState);
IedServer_updateQuality(iedServer, IEDMODEL_GenericIO_GGIO1_SPCSO3_q, QUALITY_VALIDITY_GOOD);
- IedServer_updateUTCTimeAttributeValue(iedServer, IEDMODEL_GenericIO_GGIO1_SPCSO3_t, timeStamp);
}
static ControlHandlerResult
@@ -146,6 +146,62 @@ controlHandlerForBinaryOutput(void* parameter, MmsValue* value, bool test)
return CONTROL_RESULT_OK;
}
+static int ledOnTimeMs = 1000;
+static int ledOffTimeMs = 1000;
+static int32_t opCnt = 0;
+
+static ControlHandlerResult
+controlHandlerForInt32Controls(void* parameter, MmsValue* value, bool test)
+{
+ if (test)
+ return CONTROL_RESULT_OK;
+
+ if (parameter == IEDMODEL_GenericIO_TIM_GAPC1_OpCntRs) {
+ int32_t newValue = MmsValue_toInt32(value);
+
+ opCnt = newValue;
+
+ uint64_t currentTime = Hal_getTimeInMs();
+
+ IedServer_updateUTCTimeAttributeValue(iedServer, IEDMODEL_GenericIO_TIM_GAPC1_OpCntRs_t, currentTime);
+ IedServer_updateInt32AttributeValue(iedServer, IEDMODEL_GenericIO_TIM_GAPC1_OpCntRs_stVal, opCnt);
+ }
+
+ return CONTROL_RESULT_OK;
+}
+
+
+
+static MmsDataAccessError
+int32WriteAccessHandler (DataAttribute* dataAttribute, MmsValue* value, ClientConnection connection, void* parameter)
+{
+ int newValue = MmsValue_toInt32(value);
+
+ /* Check if value is inside of valid range */
+ if (newValue < 0)
+ return DATA_ACCESS_ERROR_OBJECT_VALUE_INVALID;
+
+ if (dataAttribute == IEDMODEL_GenericIO_TIM_GAPC1_OpDlTmms_setVal) {
+
+ printf("New value for TIM_GAPC1.OpDlTmms.setVal = %i\n", newValue);
+
+ ledOffTimeMs = newValue;
+
+ return DATA_ACCESS_ERROR_SUCCESS;
+ }
+
+ if (dataAttribute == IEDMODEL_GenericIO_TIM_GAPC1_RsDlTmms_setVal) {
+
+ printf("New value for TIM_GAPC1.RsDlTmms.setVal = %i\n", newValue);
+
+ ledOnTimeMs = newValue;
+
+ return DATA_ACCESS_ERROR_SUCCESS;
+ }
+
+ return DATA_ACCESS_ERROR_OBJECT_ACCESS_DENIED;
+}
+
int main(int argc, char** argv) {
@@ -153,7 +209,7 @@ int main(int argc, char** argv) {
iedServer = IedServer_create(&iedModel);
- /* Set callback handlers */
+ /* Set control callback handlers */
IedServer_setConnectionIndicationHandler(iedServer, (IedConnectionIndicationHandler) connectionIndicationHandler, NULL);
IedServer_setPerformCheckHandler(iedServer, IEDMODEL_GenericIO_GGIO1_SPCSO1,
@@ -181,11 +237,22 @@ int main(int argc, char** argv) {
IEDMODEL_GenericIO_GGIO1_DPCSO1);
- /* Initialize process values */
+ IedServer_setControlHandler(iedServer, IEDMODEL_GenericIO_TIM_GAPC1_OpCntRs, (ControlHandler) controlHandlerForInt32Controls,
+ IEDMODEL_GenericIO_TIM_GAPC1_OpCntRs);
+ /* Initialize process values */
MmsValue* DPCSO1_stVal = IedServer_getAttributeValue(iedServer, IEDMODEL_GenericIO_GGIO1_DPCSO1_stVal);
MmsValue_setBitStringFromInteger(DPCSO1_stVal, 1); /* set DPC to OFF */
+ /* Intitalize setting values */
+ IedServer_updateInt32AttributeValue(iedServer, IEDMODEL_GenericIO_TIM_GAPC1_OpDlTmms_setVal, ledOffTimeMs);
+ IedServer_updateInt32AttributeValue(iedServer, IEDMODEL_GenericIO_TIM_GAPC1_RsDlTmms_setVal, ledOnTimeMs);
+
+ /* Set callback handler for settings */
+ IedServer_handleWriteAccess(iedServer, IEDMODEL_GenericIO_TIM_GAPC1_OpDlTmms_setVal, int32WriteAccessHandler, NULL);
+ IedServer_handleWriteAccess(iedServer, IEDMODEL_GenericIO_TIM_GAPC1_RsDlTmms_setVal, int32WriteAccessHandler, NULL);
+
+
/* MMS server will be instructed to start listening to client connections. */
IedServer_start(iedServer, 102);
@@ -210,10 +277,21 @@ int main(int argc, char** argv) {
if (automaticOperationMode) {
if (nextLedToggleTime <= currentTime) {
- nextLedToggleTime = currentTime + 1000;
+
+
+ if (ledStateValue)
+ nextLedToggleTime = currentTime + ledOffTimeMs;
+ else
+ nextLedToggleTime = currentTime + ledOnTimeMs;
ledStateValue = !ledStateValue;
+ if (ledStateValue) {
+ opCnt++;
+ IedServer_updateUTCTimeAttributeValue(iedServer, IEDMODEL_GenericIO_TIM_GAPC1_OpCntRs_t, currentTime);
+ IedServer_updateInt32AttributeValue(iedServer, IEDMODEL_GenericIO_TIM_GAPC1_OpCntRs_stVal, opCnt);
+ }
+
updateLED1stVal(ledStateValue, currentTime);
updateLED2stVal(ledStateValue, currentTime);
updateLED3stVal(ledStateValue, currentTime);
diff --git a/demos/beaglebone/beagle_demo.icd b/demos/beaglebone/beagle_demo.icd
index 6169c814..259c21f5 100644
--- a/demos/beaglebone/beagle_demo.icd
+++ b/demos/beaglebone/beagle_demo.icd
@@ -72,6 +72,7 @@
+
@@ -99,6 +100,9 @@
+
+
+
@@ -106,20 +110,22 @@
-
-
-
+
+
+
+
-
+
+
-
-
-
+
+
+
@@ -134,17 +140,65 @@
-
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ EXT:2015
+
+
+
+
+
+
+
+
+
+
-
+
+
+ direct-with-normal-security
+
-
-
-
-
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ status-only
+
+
@@ -152,24 +206,29 @@
+
+
+
+
+
@@ -177,11 +236,13 @@
+
+
@@ -189,6 +250,7 @@
+
@@ -198,6 +260,7 @@
+
@@ -205,13 +268,33 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
@@ -228,6 +311,21 @@
+
+
+ on
+ blocked
+ test
+ test/blocked
+ off
+
+
+
+ unknown
+ forward
+ backward
+ both
+
status-only
@@ -236,6 +334,7 @@
direct-with-enhanced-security
sbo-with-enhanced-security
+
not-supported
bay-control
diff --git a/demos/beaglebone/beaglebone_leds.h b/demos/beaglebone/beaglebone_leds.h
index 2bcfa0d9..61a396c7 100644
--- a/demos/beaglebone/beaglebone_leds.h
+++ b/demos/beaglebone/beaglebone_leds.h
@@ -9,6 +9,9 @@
/* set to 1 if you want to run the demo on a PC */
//#define SIMULATED 1
+
+
+/* select correct file paths to access LEDs - depends on beaglebones linux distro/version */
#if 0
#define LED1 "/sys/class/leds/beaglebone::usr0"
#define LED2 "/sys/class/leds/beaglebone::usr1"
diff --git a/demos/beaglebone/static_model.c b/demos/beaglebone/static_model.c
index 9d2b861b..993db3ec 100644
--- a/demos/beaglebone/static_model.c
+++ b/demos/beaglebone/static_model.c
@@ -76,36 +76,36 @@ LogicalNode iedModel_GenericIO_LLN0 = {
"LLN0",
(ModelNode*) &iedModel_GenericIO,
(ModelNode*) &iedModel_GenericIO_LPHD1,
- (ModelNode*) &iedModel_GenericIO_LLN0_Mod,
+ (ModelNode*) &iedModel_GenericIO_LLN0_Beh,
};
-DataObject iedModel_GenericIO_LLN0_Mod = {
+DataObject iedModel_GenericIO_LLN0_Beh = {
DataObjectModelType,
- "Mod",
+ "Beh",
(ModelNode*) &iedModel_GenericIO_LLN0,
- (ModelNode*) &iedModel_GenericIO_LLN0_Beh,
- (ModelNode*) &iedModel_GenericIO_LLN0_Mod_stVal,
+ (ModelNode*) &iedModel_GenericIO_LLN0_Mod,
+ (ModelNode*) &iedModel_GenericIO_LLN0_Beh_stVal,
0
};
-DataAttribute iedModel_GenericIO_LLN0_Mod_stVal = {
+DataAttribute iedModel_GenericIO_LLN0_Beh_stVal = {
DataAttributeModelType,
"stVal",
- (ModelNode*) &iedModel_GenericIO_LLN0_Mod,
- (ModelNode*) &iedModel_GenericIO_LLN0_Mod_q,
+ (ModelNode*) &iedModel_GenericIO_LLN0_Beh,
+ (ModelNode*) &iedModel_GenericIO_LLN0_Beh_q,
NULL,
0,
IEC61850_FC_ST,
- INT32,
+ ENUMERATED,
0 + TRG_OPT_DATA_CHANGED,
NULL,
0};
-DataAttribute iedModel_GenericIO_LLN0_Mod_q = {
+DataAttribute iedModel_GenericIO_LLN0_Beh_q = {
DataAttributeModelType,
"q",
- (ModelNode*) &iedModel_GenericIO_LLN0_Mod,
- (ModelNode*) &iedModel_GenericIO_LLN0_Mod_t,
+ (ModelNode*) &iedModel_GenericIO_LLN0_Beh,
+ (ModelNode*) &iedModel_GenericIO_LLN0_Beh_t,
NULL,
0,
IEC61850_FC_ST,
@@ -114,11 +114,11 @@ DataAttribute iedModel_GenericIO_LLN0_Mod_q = {
NULL,
0};
-DataAttribute iedModel_GenericIO_LLN0_Mod_t = {
+DataAttribute iedModel_GenericIO_LLN0_Beh_t = {
DataAttributeModelType,
"t",
- (ModelNode*) &iedModel_GenericIO_LLN0_Mod,
- (ModelNode*) &iedModel_GenericIO_LLN0_Mod_ctlModel,
+ (ModelNode*) &iedModel_GenericIO_LLN0_Beh,
+ NULL,
NULL,
0,
IEC61850_FC_ST,
@@ -127,46 +127,33 @@ DataAttribute iedModel_GenericIO_LLN0_Mod_t = {
NULL,
0};
-DataAttribute iedModel_GenericIO_LLN0_Mod_ctlModel = {
- DataAttributeModelType,
- "ctlModel",
- (ModelNode*) &iedModel_GenericIO_LLN0_Mod,
- NULL,
- NULL,
- 0,
- IEC61850_FC_CF,
- ENUMERATED,
- 0,
- NULL,
- 0};
-
-DataObject iedModel_GenericIO_LLN0_Beh = {
+DataObject iedModel_GenericIO_LLN0_Mod = {
DataObjectModelType,
- "Beh",
+ "Mod",
(ModelNode*) &iedModel_GenericIO_LLN0,
(ModelNode*) &iedModel_GenericIO_LLN0_Health,
- (ModelNode*) &iedModel_GenericIO_LLN0_Beh_stVal,
+ (ModelNode*) &iedModel_GenericIO_LLN0_Mod_stVal,
0
};
-DataAttribute iedModel_GenericIO_LLN0_Beh_stVal = {
+DataAttribute iedModel_GenericIO_LLN0_Mod_stVal = {
DataAttributeModelType,
"stVal",
- (ModelNode*) &iedModel_GenericIO_LLN0_Beh,
- (ModelNode*) &iedModel_GenericIO_LLN0_Beh_q,
+ (ModelNode*) &iedModel_GenericIO_LLN0_Mod,
+ (ModelNode*) &iedModel_GenericIO_LLN0_Mod_q,
NULL,
0,
IEC61850_FC_ST,
- INT32,
+ ENUMERATED,
0 + TRG_OPT_DATA_CHANGED,
NULL,
0};
-DataAttribute iedModel_GenericIO_LLN0_Beh_q = {
+DataAttribute iedModel_GenericIO_LLN0_Mod_q = {
DataAttributeModelType,
"q",
- (ModelNode*) &iedModel_GenericIO_LLN0_Beh,
- (ModelNode*) &iedModel_GenericIO_LLN0_Beh_t,
+ (ModelNode*) &iedModel_GenericIO_LLN0_Mod,
+ (ModelNode*) &iedModel_GenericIO_LLN0_Mod_t,
NULL,
0,
IEC61850_FC_ST,
@@ -175,11 +162,11 @@ DataAttribute iedModel_GenericIO_LLN0_Beh_q = {
NULL,
0};
-DataAttribute iedModel_GenericIO_LLN0_Beh_t = {
+DataAttribute iedModel_GenericIO_LLN0_Mod_t = {
DataAttributeModelType,
"t",
- (ModelNode*) &iedModel_GenericIO_LLN0_Beh,
- NULL,
+ (ModelNode*) &iedModel_GenericIO_LLN0_Mod,
+ (ModelNode*) &iedModel_GenericIO_LLN0_Mod_ctlModel,
NULL,
0,
IEC61850_FC_ST,
@@ -188,6 +175,19 @@ DataAttribute iedModel_GenericIO_LLN0_Beh_t = {
NULL,
0};
+DataAttribute iedModel_GenericIO_LLN0_Mod_ctlModel = {
+ DataAttributeModelType,
+ "ctlModel",
+ (ModelNode*) &iedModel_GenericIO_LLN0_Mod,
+ NULL,
+ NULL,
+ 0,
+ IEC61850_FC_CF,
+ ENUMERATED,
+ 0,
+ NULL,
+ 0};
+
DataObject iedModel_GenericIO_LLN0_Health = {
DataObjectModelType,
"Health",
@@ -205,7 +205,7 @@ DataAttribute iedModel_GenericIO_LLN0_Health_stVal = {
NULL,
0,
IEC61850_FC_ST,
- INT32,
+ ENUMERATED,
0 + TRG_OPT_DATA_CHANGED,
NULL,
0};
@@ -357,7 +357,7 @@ DataAttribute iedModel_GenericIO_LPHD1_PhyHealth_stVal = {
NULL,
0,
IEC61850_FC_ST,
- INT32,
+ ENUMERATED,
0 + TRG_OPT_DATA_CHANGED,
NULL,
0};
@@ -440,85 +440,85 @@ LogicalNode iedModel_GenericIO_GGIO1 = {
LogicalNodeModelType,
"GGIO1",
(ModelNode*) &iedModel_GenericIO,
- NULL,
- (ModelNode*) &iedModel_GenericIO_GGIO1_Mod,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1,
+ (ModelNode*) &iedModel_GenericIO_GGIO1_Beh,
};
-DataObject iedModel_GenericIO_GGIO1_Mod = {
+DataObject iedModel_GenericIO_GGIO1_Beh = {
DataObjectModelType,
- "Mod",
+ "Beh",
(ModelNode*) &iedModel_GenericIO_GGIO1,
- (ModelNode*) &iedModel_GenericIO_GGIO1_Beh,
- (ModelNode*) &iedModel_GenericIO_GGIO1_Mod_q,
+ (ModelNode*) &iedModel_GenericIO_GGIO1_Mod,
+ (ModelNode*) &iedModel_GenericIO_GGIO1_Beh_stVal,
0
};
-DataAttribute iedModel_GenericIO_GGIO1_Mod_q = {
+DataAttribute iedModel_GenericIO_GGIO1_Beh_stVal = {
DataAttributeModelType,
- "q",
- (ModelNode*) &iedModel_GenericIO_GGIO1_Mod,
- (ModelNode*) &iedModel_GenericIO_GGIO1_Mod_t,
+ "stVal",
+ (ModelNode*) &iedModel_GenericIO_GGIO1_Beh,
+ (ModelNode*) &iedModel_GenericIO_GGIO1_Beh_q,
NULL,
0,
IEC61850_FC_ST,
- QUALITY,
- 0 + TRG_OPT_QUALITY_CHANGED,
+ ENUMERATED,
+ 0 + TRG_OPT_DATA_CHANGED,
NULL,
0};
-DataAttribute iedModel_GenericIO_GGIO1_Mod_t = {
+DataAttribute iedModel_GenericIO_GGIO1_Beh_q = {
DataAttributeModelType,
- "t",
- (ModelNode*) &iedModel_GenericIO_GGIO1_Mod,
- (ModelNode*) &iedModel_GenericIO_GGIO1_Mod_ctlModel,
+ "q",
+ (ModelNode*) &iedModel_GenericIO_GGIO1_Beh,
+ (ModelNode*) &iedModel_GenericIO_GGIO1_Beh_t,
NULL,
0,
IEC61850_FC_ST,
- TIMESTAMP,
- 0,
+ QUALITY,
+ 0 + TRG_OPT_QUALITY_CHANGED,
NULL,
0};
-DataAttribute iedModel_GenericIO_GGIO1_Mod_ctlModel = {
+DataAttribute iedModel_GenericIO_GGIO1_Beh_t = {
DataAttributeModelType,
- "ctlModel",
- (ModelNode*) &iedModel_GenericIO_GGIO1_Mod,
+ "t",
+ (ModelNode*) &iedModel_GenericIO_GGIO1_Beh,
NULL,
NULL,
0,
- IEC61850_FC_CF,
- ENUMERATED,
+ IEC61850_FC_ST,
+ TIMESTAMP,
0,
NULL,
0};
-DataObject iedModel_GenericIO_GGIO1_Beh = {
+DataObject iedModel_GenericIO_GGIO1_Mod = {
DataObjectModelType,
- "Beh",
+ "Mod",
(ModelNode*) &iedModel_GenericIO_GGIO1,
(ModelNode*) &iedModel_GenericIO_GGIO1_Health,
- (ModelNode*) &iedModel_GenericIO_GGIO1_Beh_stVal,
+ (ModelNode*) &iedModel_GenericIO_GGIO1_Mod_stVal,
0
};
-DataAttribute iedModel_GenericIO_GGIO1_Beh_stVal = {
+DataAttribute iedModel_GenericIO_GGIO1_Mod_stVal = {
DataAttributeModelType,
"stVal",
- (ModelNode*) &iedModel_GenericIO_GGIO1_Beh,
- (ModelNode*) &iedModel_GenericIO_GGIO1_Beh_q,
+ (ModelNode*) &iedModel_GenericIO_GGIO1_Mod,
+ (ModelNode*) &iedModel_GenericIO_GGIO1_Mod_q,
NULL,
0,
IEC61850_FC_ST,
- INT32,
+ ENUMERATED,
0 + TRG_OPT_DATA_CHANGED,
NULL,
0};
-DataAttribute iedModel_GenericIO_GGIO1_Beh_q = {
+DataAttribute iedModel_GenericIO_GGIO1_Mod_q = {
DataAttributeModelType,
"q",
- (ModelNode*) &iedModel_GenericIO_GGIO1_Beh,
- (ModelNode*) &iedModel_GenericIO_GGIO1_Beh_t,
+ (ModelNode*) &iedModel_GenericIO_GGIO1_Mod,
+ (ModelNode*) &iedModel_GenericIO_GGIO1_Mod_t,
NULL,
0,
IEC61850_FC_ST,
@@ -527,11 +527,11 @@ DataAttribute iedModel_GenericIO_GGIO1_Beh_q = {
NULL,
0};
-DataAttribute iedModel_GenericIO_GGIO1_Beh_t = {
+DataAttribute iedModel_GenericIO_GGIO1_Mod_t = {
DataAttributeModelType,
"t",
- (ModelNode*) &iedModel_GenericIO_GGIO1_Beh,
- NULL,
+ (ModelNode*) &iedModel_GenericIO_GGIO1_Mod,
+ (ModelNode*) &iedModel_GenericIO_GGIO1_Mod_ctlModel,
NULL,
0,
IEC61850_FC_ST,
@@ -540,6 +540,19 @@ DataAttribute iedModel_GenericIO_GGIO1_Beh_t = {
NULL,
0};
+DataAttribute iedModel_GenericIO_GGIO1_Mod_ctlModel = {
+ DataAttributeModelType,
+ "ctlModel",
+ (ModelNode*) &iedModel_GenericIO_GGIO1_Mod,
+ NULL,
+ NULL,
+ 0,
+ IEC61850_FC_CF,
+ ENUMERATED,
+ 0,
+ NULL,
+ 0};
+
DataObject iedModel_GenericIO_GGIO1_Health = {
DataObjectModelType,
"Health",
@@ -557,7 +570,7 @@ DataAttribute iedModel_GenericIO_GGIO1_Health_stVal = {
NULL,
0,
IEC61850_FC_ST,
- INT32,
+ ENUMERATED,
0 + TRG_OPT_DATA_CHANGED,
NULL,
0};
@@ -1901,44 +1914,526 @@ DataAttribute iedModel_GenericIO_GGIO1_Ind4_t = {
NULL,
0};
-extern ReportControlBlock iedModel_GenericIO_LLN0_report0;
-extern ReportControlBlock iedModel_GenericIO_LLN0_report1;
-extern ReportControlBlock iedModel_GenericIO_LLN0_report2;
-extern ReportControlBlock iedModel_GenericIO_LLN0_report3;
-extern ReportControlBlock iedModel_GenericIO_LLN0_report4;
-
-ReportControlBlock iedModel_GenericIO_LLN0_report0 = {&iedModel_GenericIO_LLN0, "EventsRCB01", "Events1", false, "Events", 1, 8, 111, 50, 1000, &iedModel_GenericIO_LLN0_report1};
-ReportControlBlock iedModel_GenericIO_LLN0_report1 = {&iedModel_GenericIO_LLN0, "EventsRCB02", "Events1", false, "Events", 1, 8, 111, 50, 1000, &iedModel_GenericIO_LLN0_report2};
-ReportControlBlock iedModel_GenericIO_LLN0_report2 = {&iedModel_GenericIO_LLN0, "EventsRCB03", "Events1", false, "Events", 1, 8, 111, 50, 1000, &iedModel_GenericIO_LLN0_report3};
-ReportControlBlock iedModel_GenericIO_LLN0_report3 = {&iedModel_GenericIO_LLN0, "EventsRCB04", "Events1", false, "Events", 1, 8, 111, 50, 1000, &iedModel_GenericIO_LLN0_report4};
-ReportControlBlock iedModel_GenericIO_LLN0_report4 = {&iedModel_GenericIO_LLN0, "EventsRCB05", "Events1", false, "Events", 1, 8, 111, 50, 1000, NULL};
-
+LogicalNode iedModel_GenericIO_TIM_GAPC1 = {
+ LogicalNodeModelType,
+ "TIM_GAPC1",
+ (ModelNode*) &iedModel_GenericIO,
+ NULL,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Beh,
+};
+DataObject iedModel_GenericIO_TIM_GAPC1_Beh = {
+ DataObjectModelType,
+ "Beh",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Mod,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Beh_stVal,
+ 0
+};
+DataAttribute iedModel_GenericIO_TIM_GAPC1_Beh_stVal = {
+ DataAttributeModelType,
+ "stVal",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Beh,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Beh_q,
+ NULL,
+ 0,
+ IEC61850_FC_ST,
+ ENUMERATED,
+ 0 + TRG_OPT_DATA_CHANGED,
+ NULL,
+ 0};
-IedModel iedModel = {
- "beagle",
- &iedModel_GenericIO,
- &iedModelds_GenericIO_LLN0_Events,
- &iedModel_GenericIO_LLN0_report0,
+DataAttribute iedModel_GenericIO_TIM_GAPC1_Beh_q = {
+ DataAttributeModelType,
+ "q",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Beh,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Beh_t,
NULL,
+ 0,
+ IEC61850_FC_ST,
+ QUALITY,
+ 0 + TRG_OPT_QUALITY_CHANGED,
NULL,
- initializeValues
-};
+ 0};
-static void
-initializeValues()
-{
+DataAttribute iedModel_GenericIO_TIM_GAPC1_Beh_t = {
+ DataAttributeModelType,
+ "t",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Beh,
+ NULL,
+ NULL,
+ 0,
+ IEC61850_FC_ST,
+ TIMESTAMP,
+ 0,
+ NULL,
+ 0};
-iedModel_GenericIO_LLN0_Mod_ctlModel.mmsValue = MmsValue_newIntegerFromInt32(0);
+DataObject iedModel_GenericIO_TIM_GAPC1_Mod = {
+ DataObjectModelType,
+ "Mod",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Str,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Mod_stVal,
+ 0
+};
-iedModel_GenericIO_GGIO1_Mod_ctlModel.mmsValue = MmsValue_newIntegerFromInt32(0);
+DataAttribute iedModel_GenericIO_TIM_GAPC1_Mod_stVal = {
+ DataAttributeModelType,
+ "stVal",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Mod,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Mod_q,
+ NULL,
+ 0,
+ IEC61850_FC_ST,
+ ENUMERATED,
+ 0 + TRG_OPT_DATA_CHANGED,
+ NULL,
+ 0};
-iedModel_GenericIO_GGIO1_SPCSO1_ctlModel.mmsValue = MmsValue_newIntegerFromInt32(1);
+DataAttribute iedModel_GenericIO_TIM_GAPC1_Mod_q = {
+ DataAttributeModelType,
+ "q",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Mod,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Mod_t,
+ NULL,
+ 0,
+ IEC61850_FC_ST,
+ QUALITY,
+ 0 + TRG_OPT_QUALITY_CHANGED,
+ NULL,
+ 0};
-iedModel_GenericIO_GGIO1_SPCSO2_ctlModel.mmsValue = MmsValue_newIntegerFromInt32(2);
+DataAttribute iedModel_GenericIO_TIM_GAPC1_Mod_t = {
+ DataAttributeModelType,
+ "t",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Mod,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Mod_ctlModel,
+ NULL,
+ 0,
+ IEC61850_FC_ST,
+ TIMESTAMP,
+ 0,
+ NULL,
+ 0};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_Mod_ctlModel = {
+ DataAttributeModelType,
+ "ctlModel",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Mod,
+ NULL,
+ NULL,
+ 0,
+ IEC61850_FC_CF,
+ ENUMERATED,
+ 0,
+ NULL,
+ 0};
+
+DataObject iedModel_GenericIO_TIM_GAPC1_Str = {
+ DataObjectModelType,
+ "Str",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Op,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Str_general,
+ 0
+};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_Str_general = {
+ DataAttributeModelType,
+ "general",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Str,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Str_dirGeneral,
+ NULL,
+ 0,
+ IEC61850_FC_ST,
+ BOOLEAN,
+ 0 + TRG_OPT_DATA_CHANGED,
+ NULL,
+ 0};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_Str_dirGeneral = {
+ DataAttributeModelType,
+ "dirGeneral",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Str,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Str_q,
+ NULL,
+ 0,
+ IEC61850_FC_ST,
+ ENUMERATED,
+ 0 + TRG_OPT_DATA_CHANGED,
+ NULL,
+ 0};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_Str_q = {
+ DataAttributeModelType,
+ "q",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Str,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Str_t,
+ NULL,
+ 0,
+ IEC61850_FC_ST,
+ QUALITY,
+ 0 + TRG_OPT_QUALITY_CHANGED,
+ NULL,
+ 0};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_Str_t = {
+ DataAttributeModelType,
+ "t",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Str,
+ NULL,
+ NULL,
+ 0,
+ IEC61850_FC_ST,
+ TIMESTAMP,
+ 0,
+ NULL,
+ 0};
+
+DataObject iedModel_GenericIO_TIM_GAPC1_Op = {
+ DataObjectModelType,
+ "Op",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpDlTmms,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Op_general,
+ 0
+};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_Op_general = {
+ DataAttributeModelType,
+ "general",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Op,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Op_q,
+ NULL,
+ 0,
+ IEC61850_FC_ST,
+ BOOLEAN,
+ 0 + TRG_OPT_DATA_CHANGED,
+ NULL,
+ 0};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_Op_q = {
+ DataAttributeModelType,
+ "q",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Op,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Op_t,
+ NULL,
+ 0,
+ IEC61850_FC_ST,
+ QUALITY,
+ 0 + TRG_OPT_QUALITY_CHANGED,
+ NULL,
+ 0};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_Op_t = {
+ DataAttributeModelType,
+ "t",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_Op,
+ NULL,
+ NULL,
+ 0,
+ IEC61850_FC_ST,
+ TIMESTAMP,
+ 0,
+ NULL,
+ 0};
+
+DataObject iedModel_GenericIO_TIM_GAPC1_OpDlTmms = {
+ DataObjectModelType,
+ "OpDlTmms",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_RsDlTmms,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpDlTmms_setVal,
+ 0
+};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_OpDlTmms_setVal = {
+ DataAttributeModelType,
+ "setVal",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpDlTmms,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpDlTmms_dataNs,
+ NULL,
+ 0,
+ IEC61850_FC_SP,
+ INT32,
+ 0 + TRG_OPT_DATA_CHANGED,
+ NULL,
+ 0};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_OpDlTmms_dataNs = {
+ DataAttributeModelType,
+ "dataNs",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpDlTmms,
+ NULL,
+ NULL,
+ 0,
+ IEC61850_FC_EX,
+ VISIBLE_STRING_255,
+ 0,
+ NULL,
+ 0};
+
+DataObject iedModel_GenericIO_TIM_GAPC1_RsDlTmms = {
+ DataObjectModelType,
+ "RsDlTmms",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_RsDlTmms_setVal,
+ 0
+};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_RsDlTmms_setVal = {
+ DataAttributeModelType,
+ "setVal",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_RsDlTmms,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_RsDlTmms_dataNs,
+ NULL,
+ 0,
+ IEC61850_FC_SP,
+ INT32,
+ 0 + TRG_OPT_DATA_CHANGED,
+ NULL,
+ 0};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_RsDlTmms_dataNs = {
+ DataAttributeModelType,
+ "dataNs",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_RsDlTmms,
+ NULL,
+ NULL,
+ 0,
+ IEC61850_FC_EX,
+ VISIBLE_STRING_255,
+ 0,
+ NULL,
+ 0};
+
+DataObject iedModel_GenericIO_TIM_GAPC1_OpCntRs = {
+ DataObjectModelType,
+ "OpCntRs",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1,
+ NULL,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs_stVal,
+ 0
+};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_stVal = {
+ DataAttributeModelType,
+ "stVal",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs_q,
+ NULL,
+ 0,
+ IEC61850_FC_ST,
+ INT32,
+ 0 + TRG_OPT_DATA_CHANGED,
+ NULL,
+ 0};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_q = {
+ DataAttributeModelType,
+ "q",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs_t,
+ NULL,
+ 0,
+ IEC61850_FC_ST,
+ QUALITY,
+ 0 + TRG_OPT_QUALITY_CHANGED,
+ NULL,
+ 0};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_t = {
+ DataAttributeModelType,
+ "t",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper,
+ NULL,
+ 0,
+ IEC61850_FC_ST,
+ TIMESTAMP,
+ 0,
+ NULL,
+ 0};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper = {
+ DataAttributeModelType,
+ "Oper",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs_ctlModel,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_ctlVal,
+ 0,
+ IEC61850_FC_CO,
+ CONSTRUCTED,
+ 0,
+ NULL,
+ 0};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_ctlVal = {
+ DataAttributeModelType,
+ "ctlVal",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_origin,
+ NULL,
+ 0,
+ IEC61850_FC_CO,
+ BOOLEAN,
+ 0,
+ NULL,
+ 0};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_origin = {
+ DataAttributeModelType,
+ "origin",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_ctlNum,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_origin_orCat,
+ 0,
+ IEC61850_FC_CO,
+ CONSTRUCTED,
+ 0,
+ NULL,
+ 0};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_origin_orCat = {
+ DataAttributeModelType,
+ "orCat",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_origin,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_origin_orIdent,
+ NULL,
+ 0,
+ IEC61850_FC_CO,
+ ENUMERATED,
+ 0,
+ NULL,
+ 0};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_origin_orIdent = {
+ DataAttributeModelType,
+ "orIdent",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_origin,
+ NULL,
+ NULL,
+ 0,
+ IEC61850_FC_CO,
+ OCTET_STRING_64,
+ 0,
+ NULL,
+ 0};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_ctlNum = {
+ DataAttributeModelType,
+ "ctlNum",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_T,
+ NULL,
+ 0,
+ IEC61850_FC_CO,
+ INT8U,
+ 0,
+ NULL,
+ 0};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_T = {
+ DataAttributeModelType,
+ "T",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_Test,
+ NULL,
+ 0,
+ IEC61850_FC_CO,
+ TIMESTAMP,
+ 0,
+ NULL,
+ 0};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_Test = {
+ DataAttributeModelType,
+ "Test",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper,
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_Check,
+ NULL,
+ 0,
+ IEC61850_FC_CO,
+ BOOLEAN,
+ 0,
+ NULL,
+ 0};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_Check = {
+ DataAttributeModelType,
+ "Check",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper,
+ NULL,
+ NULL,
+ 0,
+ IEC61850_FC_CO,
+ CHECK,
+ 0,
+ NULL,
+ 0};
+
+DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_ctlModel = {
+ DataAttributeModelType,
+ "ctlModel",
+ (ModelNode*) &iedModel_GenericIO_TIM_GAPC1_OpCntRs,
+ NULL,
+ NULL,
+ 0,
+ IEC61850_FC_CF,
+ ENUMERATED,
+ 0,
+ NULL,
+ 0};
+
+extern ReportControlBlock iedModel_GenericIO_LLN0_report0;
+extern ReportControlBlock iedModel_GenericIO_LLN0_report1;
+extern ReportControlBlock iedModel_GenericIO_LLN0_report2;
+extern ReportControlBlock iedModel_GenericIO_LLN0_report3;
+extern ReportControlBlock iedModel_GenericIO_LLN0_report4;
+
+ReportControlBlock iedModel_GenericIO_LLN0_report0 = {&iedModel_GenericIO_LLN0, "EventsRCB01", "Events1", false, "Events", 1, 24, 111, 50, 1000, &iedModel_GenericIO_LLN0_report1};
+ReportControlBlock iedModel_GenericIO_LLN0_report1 = {&iedModel_GenericIO_LLN0, "EventsRCB02", "Events1", false, "Events", 1, 24, 111, 50, 1000, &iedModel_GenericIO_LLN0_report2};
+ReportControlBlock iedModel_GenericIO_LLN0_report2 = {&iedModel_GenericIO_LLN0, "EventsRCB03", "Events1", false, "Events", 1, 24, 111, 50, 1000, &iedModel_GenericIO_LLN0_report3};
+ReportControlBlock iedModel_GenericIO_LLN0_report3 = {&iedModel_GenericIO_LLN0, "EventsRCB04", "Events1", false, "Events", 1, 24, 111, 50, 1000, &iedModel_GenericIO_LLN0_report4};
+ReportControlBlock iedModel_GenericIO_LLN0_report4 = {&iedModel_GenericIO_LLN0, "EventsRCB05", "Events1", false, "Events", 1, 24, 111, 50, 1000, NULL};
+
+
+
+
+IedModel iedModel = {
+ "beagle",
+ &iedModel_GenericIO,
+ &iedModelds_GenericIO_LLN0_Events,
+ &iedModel_GenericIO_LLN0_report0,
+ NULL,
+ NULL,
+ initializeValues
+};
+
+static void
+initializeValues()
+{
+
+iedModel_GenericIO_LLN0_Mod_ctlModel.mmsValue = MmsValue_newIntegerFromInt32(0);
+
+iedModel_GenericIO_GGIO1_Mod_ctlModel.mmsValue = MmsValue_newIntegerFromInt32(0);
+
+iedModel_GenericIO_GGIO1_SPCSO1_ctlModel.mmsValue = MmsValue_newIntegerFromInt32(1);
+
+iedModel_GenericIO_GGIO1_SPCSO2_ctlModel.mmsValue = MmsValue_newIntegerFromInt32(2);
iedModel_GenericIO_GGIO1_SPCSO3_ctlModel.mmsValue = MmsValue_newIntegerFromInt32(1);
iedModel_GenericIO_GGIO1_DPCSO1_ctlModel.mmsValue = MmsValue_newIntegerFromInt32(3);
+
+iedModel_GenericIO_TIM_GAPC1_Mod_ctlModel.mmsValue = MmsValue_newIntegerFromInt32(0);
+
+iedModel_GenericIO_TIM_GAPC1_OpDlTmms_dataNs.mmsValue = MmsValue_newVisibleString("EXT:2015");
+
+iedModel_GenericIO_TIM_GAPC1_RsDlTmms_dataNs.mmsValue = MmsValue_newVisibleString("EXT:2015");
+
+iedModel_GenericIO_TIM_GAPC1_OpCntRs_ctlModel.mmsValue = MmsValue_newIntegerFromInt32(1);
}
diff --git a/demos/beaglebone/static_model.h b/demos/beaglebone/static_model.h
index 36a7e0f7..a50ade81 100644
--- a/demos/beaglebone/static_model.h
+++ b/demos/beaglebone/static_model.h
@@ -13,15 +13,15 @@
extern IedModel iedModel;
extern LogicalDevice iedModel_GenericIO;
extern LogicalNode iedModel_GenericIO_LLN0;
+extern DataObject iedModel_GenericIO_LLN0_Beh;
+extern DataAttribute iedModel_GenericIO_LLN0_Beh_stVal;
+extern DataAttribute iedModel_GenericIO_LLN0_Beh_q;
+extern DataAttribute iedModel_GenericIO_LLN0_Beh_t;
extern DataObject iedModel_GenericIO_LLN0_Mod;
extern DataAttribute iedModel_GenericIO_LLN0_Mod_stVal;
extern DataAttribute iedModel_GenericIO_LLN0_Mod_q;
extern DataAttribute iedModel_GenericIO_LLN0_Mod_t;
extern DataAttribute iedModel_GenericIO_LLN0_Mod_ctlModel;
-extern DataObject iedModel_GenericIO_LLN0_Beh;
-extern DataAttribute iedModel_GenericIO_LLN0_Beh_stVal;
-extern DataAttribute iedModel_GenericIO_LLN0_Beh_q;
-extern DataAttribute iedModel_GenericIO_LLN0_Beh_t;
extern DataObject iedModel_GenericIO_LLN0_Health;
extern DataAttribute iedModel_GenericIO_LLN0_Health_stVal;
extern DataAttribute iedModel_GenericIO_LLN0_Health_q;
@@ -44,14 +44,15 @@ extern DataAttribute iedModel_GenericIO_LPHD1_Proxy_stVal;
extern DataAttribute iedModel_GenericIO_LPHD1_Proxy_q;
extern DataAttribute iedModel_GenericIO_LPHD1_Proxy_t;
extern LogicalNode iedModel_GenericIO_GGIO1;
-extern DataObject iedModel_GenericIO_GGIO1_Mod;
-extern DataAttribute iedModel_GenericIO_GGIO1_Mod_q;
-extern DataAttribute iedModel_GenericIO_GGIO1_Mod_t;
-extern DataAttribute iedModel_GenericIO_GGIO1_Mod_ctlModel;
extern DataObject iedModel_GenericIO_GGIO1_Beh;
extern DataAttribute iedModel_GenericIO_GGIO1_Beh_stVal;
extern DataAttribute iedModel_GenericIO_GGIO1_Beh_q;
extern DataAttribute iedModel_GenericIO_GGIO1_Beh_t;
+extern DataObject iedModel_GenericIO_GGIO1_Mod;
+extern DataAttribute iedModel_GenericIO_GGIO1_Mod_stVal;
+extern DataAttribute iedModel_GenericIO_GGIO1_Mod_q;
+extern DataAttribute iedModel_GenericIO_GGIO1_Mod_t;
+extern DataAttribute iedModel_GenericIO_GGIO1_Mod_ctlModel;
extern DataObject iedModel_GenericIO_GGIO1_Health;
extern DataAttribute iedModel_GenericIO_GGIO1_Health_stVal;
extern DataAttribute iedModel_GenericIO_GGIO1_Health_q;
@@ -161,20 +162,59 @@ extern DataObject iedModel_GenericIO_GGIO1_Ind4;
extern DataAttribute iedModel_GenericIO_GGIO1_Ind4_stVal;
extern DataAttribute iedModel_GenericIO_GGIO1_Ind4_q;
extern DataAttribute iedModel_GenericIO_GGIO1_Ind4_t;
+extern LogicalNode iedModel_GenericIO_TIM_GAPC1;
+extern DataObject iedModel_GenericIO_TIM_GAPC1_Beh;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_Beh_stVal;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_Beh_q;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_Beh_t;
+extern DataObject iedModel_GenericIO_TIM_GAPC1_Mod;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_Mod_stVal;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_Mod_q;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_Mod_t;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_Mod_ctlModel;
+extern DataObject iedModel_GenericIO_TIM_GAPC1_Str;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_Str_general;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_Str_dirGeneral;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_Str_q;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_Str_t;
+extern DataObject iedModel_GenericIO_TIM_GAPC1_Op;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_Op_general;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_Op_q;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_Op_t;
+extern DataObject iedModel_GenericIO_TIM_GAPC1_OpDlTmms;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_OpDlTmms_setVal;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_OpDlTmms_dataNs;
+extern DataObject iedModel_GenericIO_TIM_GAPC1_RsDlTmms;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_RsDlTmms_setVal;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_RsDlTmms_dataNs;
+extern DataObject iedModel_GenericIO_TIM_GAPC1_OpCntRs;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_stVal;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_q;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_t;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_ctlVal;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_origin;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_origin_orCat;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_origin_orIdent;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_ctlNum;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_T;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_Test;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_Check;
+extern DataAttribute iedModel_GenericIO_TIM_GAPC1_OpCntRs_ctlModel;
#define IEDMODEL_GenericIO (&iedModel_GenericIO)
#define IEDMODEL_GenericIO_LLN0 (&iedModel_GenericIO_LLN0)
+#define IEDMODEL_GenericIO_LLN0_Beh (&iedModel_GenericIO_LLN0_Beh)
+#define IEDMODEL_GenericIO_LLN0_Beh_stVal (&iedModel_GenericIO_LLN0_Beh_stVal)
+#define IEDMODEL_GenericIO_LLN0_Beh_q (&iedModel_GenericIO_LLN0_Beh_q)
+#define IEDMODEL_GenericIO_LLN0_Beh_t (&iedModel_GenericIO_LLN0_Beh_t)
#define IEDMODEL_GenericIO_LLN0_Mod (&iedModel_GenericIO_LLN0_Mod)
#define IEDMODEL_GenericIO_LLN0_Mod_stVal (&iedModel_GenericIO_LLN0_Mod_stVal)
#define IEDMODEL_GenericIO_LLN0_Mod_q (&iedModel_GenericIO_LLN0_Mod_q)
#define IEDMODEL_GenericIO_LLN0_Mod_t (&iedModel_GenericIO_LLN0_Mod_t)
#define IEDMODEL_GenericIO_LLN0_Mod_ctlModel (&iedModel_GenericIO_LLN0_Mod_ctlModel)
-#define IEDMODEL_GenericIO_LLN0_Beh (&iedModel_GenericIO_LLN0_Beh)
-#define IEDMODEL_GenericIO_LLN0_Beh_stVal (&iedModel_GenericIO_LLN0_Beh_stVal)
-#define IEDMODEL_GenericIO_LLN0_Beh_q (&iedModel_GenericIO_LLN0_Beh_q)
-#define IEDMODEL_GenericIO_LLN0_Beh_t (&iedModel_GenericIO_LLN0_Beh_t)
#define IEDMODEL_GenericIO_LLN0_Health (&iedModel_GenericIO_LLN0_Health)
#define IEDMODEL_GenericIO_LLN0_Health_stVal (&iedModel_GenericIO_LLN0_Health_stVal)
#define IEDMODEL_GenericIO_LLN0_Health_q (&iedModel_GenericIO_LLN0_Health_q)
@@ -197,14 +237,15 @@ extern DataAttribute iedModel_GenericIO_GGIO1_Ind4_t;
#define IEDMODEL_GenericIO_LPHD1_Proxy_q (&iedModel_GenericIO_LPHD1_Proxy_q)
#define IEDMODEL_GenericIO_LPHD1_Proxy_t (&iedModel_GenericIO_LPHD1_Proxy_t)
#define IEDMODEL_GenericIO_GGIO1 (&iedModel_GenericIO_GGIO1)
-#define IEDMODEL_GenericIO_GGIO1_Mod (&iedModel_GenericIO_GGIO1_Mod)
-#define IEDMODEL_GenericIO_GGIO1_Mod_q (&iedModel_GenericIO_GGIO1_Mod_q)
-#define IEDMODEL_GenericIO_GGIO1_Mod_t (&iedModel_GenericIO_GGIO1_Mod_t)
-#define IEDMODEL_GenericIO_GGIO1_Mod_ctlModel (&iedModel_GenericIO_GGIO1_Mod_ctlModel)
#define IEDMODEL_GenericIO_GGIO1_Beh (&iedModel_GenericIO_GGIO1_Beh)
#define IEDMODEL_GenericIO_GGIO1_Beh_stVal (&iedModel_GenericIO_GGIO1_Beh_stVal)
#define IEDMODEL_GenericIO_GGIO1_Beh_q (&iedModel_GenericIO_GGIO1_Beh_q)
#define IEDMODEL_GenericIO_GGIO1_Beh_t (&iedModel_GenericIO_GGIO1_Beh_t)
+#define IEDMODEL_GenericIO_GGIO1_Mod (&iedModel_GenericIO_GGIO1_Mod)
+#define IEDMODEL_GenericIO_GGIO1_Mod_stVal (&iedModel_GenericIO_GGIO1_Mod_stVal)
+#define IEDMODEL_GenericIO_GGIO1_Mod_q (&iedModel_GenericIO_GGIO1_Mod_q)
+#define IEDMODEL_GenericIO_GGIO1_Mod_t (&iedModel_GenericIO_GGIO1_Mod_t)
+#define IEDMODEL_GenericIO_GGIO1_Mod_ctlModel (&iedModel_GenericIO_GGIO1_Mod_ctlModel)
#define IEDMODEL_GenericIO_GGIO1_Health (&iedModel_GenericIO_GGIO1_Health)
#define IEDMODEL_GenericIO_GGIO1_Health_stVal (&iedModel_GenericIO_GGIO1_Health_stVal)
#define IEDMODEL_GenericIO_GGIO1_Health_q (&iedModel_GenericIO_GGIO1_Health_q)
@@ -314,6 +355,45 @@ extern DataAttribute iedModel_GenericIO_GGIO1_Ind4_t;
#define IEDMODEL_GenericIO_GGIO1_Ind4_stVal (&iedModel_GenericIO_GGIO1_Ind4_stVal)
#define IEDMODEL_GenericIO_GGIO1_Ind4_q (&iedModel_GenericIO_GGIO1_Ind4_q)
#define IEDMODEL_GenericIO_GGIO1_Ind4_t (&iedModel_GenericIO_GGIO1_Ind4_t)
+#define IEDMODEL_GenericIO_TIM_GAPC1 (&iedModel_GenericIO_TIM_GAPC1)
+#define IEDMODEL_GenericIO_TIM_GAPC1_Beh (&iedModel_GenericIO_TIM_GAPC1_Beh)
+#define IEDMODEL_GenericIO_TIM_GAPC1_Beh_stVal (&iedModel_GenericIO_TIM_GAPC1_Beh_stVal)
+#define IEDMODEL_GenericIO_TIM_GAPC1_Beh_q (&iedModel_GenericIO_TIM_GAPC1_Beh_q)
+#define IEDMODEL_GenericIO_TIM_GAPC1_Beh_t (&iedModel_GenericIO_TIM_GAPC1_Beh_t)
+#define IEDMODEL_GenericIO_TIM_GAPC1_Mod (&iedModel_GenericIO_TIM_GAPC1_Mod)
+#define IEDMODEL_GenericIO_TIM_GAPC1_Mod_stVal (&iedModel_GenericIO_TIM_GAPC1_Mod_stVal)
+#define IEDMODEL_GenericIO_TIM_GAPC1_Mod_q (&iedModel_GenericIO_TIM_GAPC1_Mod_q)
+#define IEDMODEL_GenericIO_TIM_GAPC1_Mod_t (&iedModel_GenericIO_TIM_GAPC1_Mod_t)
+#define IEDMODEL_GenericIO_TIM_GAPC1_Mod_ctlModel (&iedModel_GenericIO_TIM_GAPC1_Mod_ctlModel)
+#define IEDMODEL_GenericIO_TIM_GAPC1_Str (&iedModel_GenericIO_TIM_GAPC1_Str)
+#define IEDMODEL_GenericIO_TIM_GAPC1_Str_general (&iedModel_GenericIO_TIM_GAPC1_Str_general)
+#define IEDMODEL_GenericIO_TIM_GAPC1_Str_dirGeneral (&iedModel_GenericIO_TIM_GAPC1_Str_dirGeneral)
+#define IEDMODEL_GenericIO_TIM_GAPC1_Str_q (&iedModel_GenericIO_TIM_GAPC1_Str_q)
+#define IEDMODEL_GenericIO_TIM_GAPC1_Str_t (&iedModel_GenericIO_TIM_GAPC1_Str_t)
+#define IEDMODEL_GenericIO_TIM_GAPC1_Op (&iedModel_GenericIO_TIM_GAPC1_Op)
+#define IEDMODEL_GenericIO_TIM_GAPC1_Op_general (&iedModel_GenericIO_TIM_GAPC1_Op_general)
+#define IEDMODEL_GenericIO_TIM_GAPC1_Op_q (&iedModel_GenericIO_TIM_GAPC1_Op_q)
+#define IEDMODEL_GenericIO_TIM_GAPC1_Op_t (&iedModel_GenericIO_TIM_GAPC1_Op_t)
+#define IEDMODEL_GenericIO_TIM_GAPC1_OpDlTmms (&iedModel_GenericIO_TIM_GAPC1_OpDlTmms)
+#define IEDMODEL_GenericIO_TIM_GAPC1_OpDlTmms_setVal (&iedModel_GenericIO_TIM_GAPC1_OpDlTmms_setVal)
+#define IEDMODEL_GenericIO_TIM_GAPC1_OpDlTmms_dataNs (&iedModel_GenericIO_TIM_GAPC1_OpDlTmms_dataNs)
+#define IEDMODEL_GenericIO_TIM_GAPC1_RsDlTmms (&iedModel_GenericIO_TIM_GAPC1_RsDlTmms)
+#define IEDMODEL_GenericIO_TIM_GAPC1_RsDlTmms_setVal (&iedModel_GenericIO_TIM_GAPC1_RsDlTmms_setVal)
+#define IEDMODEL_GenericIO_TIM_GAPC1_RsDlTmms_dataNs (&iedModel_GenericIO_TIM_GAPC1_RsDlTmms_dataNs)
+#define IEDMODEL_GenericIO_TIM_GAPC1_OpCntRs (&iedModel_GenericIO_TIM_GAPC1_OpCntRs)
+#define IEDMODEL_GenericIO_TIM_GAPC1_OpCntRs_stVal (&iedModel_GenericIO_TIM_GAPC1_OpCntRs_stVal)
+#define IEDMODEL_GenericIO_TIM_GAPC1_OpCntRs_q (&iedModel_GenericIO_TIM_GAPC1_OpCntRs_q)
+#define IEDMODEL_GenericIO_TIM_GAPC1_OpCntRs_t (&iedModel_GenericIO_TIM_GAPC1_OpCntRs_t)
+#define IEDMODEL_GenericIO_TIM_GAPC1_OpCntRs_Oper (&iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper)
+#define IEDMODEL_GenericIO_TIM_GAPC1_OpCntRs_Oper_ctlVal (&iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_ctlVal)
+#define IEDMODEL_GenericIO_TIM_GAPC1_OpCntRs_Oper_origin (&iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_origin)
+#define IEDMODEL_GenericIO_TIM_GAPC1_OpCntRs_Oper_origin_orCat (&iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_origin_orCat)
+#define IEDMODEL_GenericIO_TIM_GAPC1_OpCntRs_Oper_origin_orIdent (&iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_origin_orIdent)
+#define IEDMODEL_GenericIO_TIM_GAPC1_OpCntRs_Oper_ctlNum (&iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_ctlNum)
+#define IEDMODEL_GenericIO_TIM_GAPC1_OpCntRs_Oper_T (&iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_T)
+#define IEDMODEL_GenericIO_TIM_GAPC1_OpCntRs_Oper_Test (&iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_Test)
+#define IEDMODEL_GenericIO_TIM_GAPC1_OpCntRs_Oper_Check (&iedModel_GenericIO_TIM_GAPC1_OpCntRs_Oper_Check)
+#define IEDMODEL_GenericIO_TIM_GAPC1_OpCntRs_ctlModel (&iedModel_GenericIO_TIM_GAPC1_OpCntRs_ctlModel)
#endif /* STATIC_MODEL_H_ */
diff --git a/examples/server_example5/server_example5.c b/examples/server_example5/server_example5.c
index 21f5207a..1d6d90ee 100644
--- a/examples/server_example5/server_example5.c
+++ b/examples/server_example5/server_example5.c
@@ -22,7 +22,7 @@ void sigint_handler(int signalId)
}
static MmsDataAccessError
-writeAccessHandler (DataAttribute* dataAttribute, MmsValue* value, ClientConnection connection)
+writeAccessHandler (DataAttribute* dataAttribute, MmsValue* value, ClientConnection connection, void* parameter)
{
if (dataAttribute == IEDMODEL_Inverter_ZINV1_OutVarSet_setMag_f) {
@@ -54,7 +54,7 @@ int main(int argc, char** argv) {
/* Instruct the server that we will be informed if a clients writes to a
* certain variables we are interested in.
*/
- IedServer_handleWriteAccess(iedServer, IEDMODEL_Inverter_ZINV1_OutVarSet_setMag_f, writeAccessHandler);
+ IedServer_handleWriteAccess(iedServer, IEDMODEL_Inverter_ZINV1_OutVarSet_setMag_f, writeAccessHandler, NULL);
if (!IedServer_isRunning(iedServer)) {
printf("Starting server failed! Exit.\n");
diff --git a/src/goose/goose_publisher.c b/src/goose/goose_publisher.c
index cc453865..47b85995 100644
--- a/src/goose/goose_publisher.c
+++ b/src/goose/goose_publisher.c
@@ -201,6 +201,7 @@ prepareGooseBuffer(GoosePublisher self, CommParameters* parameters, const char*
int bufPos = 12;
+#if 1
/* Priority tag - IEEE 802.1Q */
self->buffer[bufPos++] = 0x81;
self->buffer[bufPos++] = 0x00;
@@ -212,6 +213,7 @@ prepareGooseBuffer(GoosePublisher self, CommParameters* parameters, const char*
self->buffer[bufPos++] = tci1; /* Priority + VLAN-ID */
self->buffer[bufPos++] = tci2; /* VLAN-ID */
+#endif
/* EtherType GOOSE */
self->buffer[bufPos++] = 0x88;
@@ -374,6 +376,11 @@ GoosePublisher_publish(GoosePublisher self, LinkedList dataSet)
if (DEBUG_GOOSE_PUBLISHER)
printf("GOOSE_PUBLISHER: send GOOSE message\n");
+ struct timeval tv;
+
+ gettimeofday(&tv,NULL/*&tz*/);
+ printf("GOOSE SEND: %ld %ld\n",tv.tv_sec, tv.tv_usec);
+
Ethernet_sendPacket(self->ethernetSocket, self->buffer, self->payloadStart + payloadLength);
return 0;
diff --git a/src/goose/goose_receiver.c b/src/goose/goose_receiver.c
index 44595d97..201fcf93 100644
--- a/src/goose/goose_receiver.c
+++ b/src/goose/goose_receiver.c
@@ -612,6 +612,13 @@ exit_with_fault:
static void
parseGooseMessage(GooseReceiver self, int numbytes)
{
+ struct timeval tv;
+
+ gettimeofday(&tv,NULL/*&tz*/);
+
+ printf("RCVD GOOSE: %ld %ld\n",tv.tv_sec, tv.tv_usec);
+
+
int bufPos;
bool subscriberFound = false;
uint8_t* buffer = self->buffer;
@@ -752,7 +759,6 @@ GooseReceiver_destroy(GooseReceiver self)
void
GooseReceiver_startThreadless(GooseReceiver self)
{
-
if (self->interfaceId == NULL)
self->ethSocket = Ethernet_createSocket(CONFIG_ETHERNET_INTERFACE_ID, NULL);
else
diff --git a/src/hal/filesystem/linux/file_provider_linux.c b/src/hal/filesystem/linux/file_provider_linux.c
index f95cff5c..c973dd2a 100644
--- a/src/hal/filesystem/linux/file_provider_linux.c
+++ b/src/hal/filesystem/linux/file_provider_linux.c
@@ -123,7 +123,7 @@ FileSystem_getFileInfo(char* filename, uint32_t* fileSize, uint64_t* lastModific
{
struct stat fileStats;
- char fullPath[sizeof(CONFIG_VIRTUAL_FILESTORE_BASEPATH) + 255];
+ char fullPath[sizeof(CONFIG_VIRTUAL_FILESTORE_BASEPATH) + 256];
createFullPathFromFileName(fullPath, filename);
@@ -131,8 +131,8 @@ FileSystem_getFileInfo(char* filename, uint32_t* fileSize, uint64_t* lastModific
return false;
if (lastModificationTimestamp != NULL)
- *lastModificationTimestamp = fileStats.st_mtime * 1000;
- // does not work on older systems --> *lastModificationTimestamp = fileStats.st_ctim.tv_sec * 1000;
+ *lastModificationTimestamp = (uint64_t) (fileStats.st_mtime) * 1000LL;
+ // does not work on older systems --> *lastModificationTimestamp = (uint64_t) (fileStats.st_ctim.tv_sec) * 1000LL;
if (fileSize != NULL)
*fileSize = fileStats.st_size;
diff --git a/src/hal/filesystem/win32/file_provider_win32.c b/src/hal/filesystem/win32/file_provider_win32.c
index 662f5439..8df94e58 100644
--- a/src/hal/filesystem/win32/file_provider_win32.c
+++ b/src/hal/filesystem/win32/file_provider_win32.c
@@ -96,7 +96,7 @@ FileSystem_closeFile(FileHandle handle)
bool
FileSystem_getFileInfo(char* filename, uint32_t* fileSize, uint64_t* lastModificationTimestamp)
{
- char fullPath[sizeof(CONFIG_VIRTUAL_FILESTORE_BASEPATH) + 255];
+ char fullPath[sizeof(CONFIG_VIRTUAL_FILESTORE_BASEPATH) + 256];
createFullPathFromFileName(fullPath, filename);
diff --git a/src/hal/inc/hal_filesystem.h b/src/hal/inc/hal_filesystem.h
index 10272958..f18f6745 100644
--- a/src/hal/inc/hal_filesystem.h
+++ b/src/hal/inc/hal_filesystem.h
@@ -133,6 +133,10 @@ FileSystem_openDirectory(char* directoryName);
/**
* \brief read the next directory entry
*
+ * This function returns the next directory entry. The entry is only a valid pointer as long as the
+ * FileSystem_closeDirectory or another FileSystem_readDirectory function is not called for the given
+ * DirectoryHandle.
+ *
* \param directory the handle to identify the directory
* \param isDirectory return value that indicates if the directory entry is itself a directory (true)
*
diff --git a/src/iec61850/client/client_report_control.c b/src/iec61850/client/client_report_control.c
index 9ed5f615..933a9378 100644
--- a/src/iec61850/client/client_report_control.c
+++ b/src/iec61850/client/client_report_control.c
@@ -611,7 +611,7 @@ IedConnection_setRCBValues(IedConnection self, IedClientError* error, ClientRepo
if (!isBuffered)
goto error_invalid_parameter;
- strcpy(itemId + itemIdLen, "$TimeOfEntry");
+ strcpy(itemId + itemIdLen, "$TimeofEntry");
LinkedList_add(itemIds, copyString(itemId));
LinkedList_add(values, rcb->timeOfEntry);
diff --git a/src/iec61850/inc/iec61850_model.h b/src/iec61850/inc/iec61850_model.h
index f8d36e63..665a2491 100644
--- a/src/iec61850/inc/iec61850_model.h
+++ b/src/iec61850/inc/iec61850_model.h
@@ -407,6 +407,9 @@ IedModel_getLogicalDeviceCount(IedModel* iedModel);
int
LogicalDevice_getLogicalNodeCount(LogicalDevice* logicalDevice);
+ModelNode*
+LogicalDevice_getChildByMmsVariableName(LogicalDevice* logicalDevice, const char* mmsVariableName);
+
bool
LogicalNode_hasFCData(LogicalNode* node, FunctionalConstraint fc);
@@ -416,6 +419,17 @@ LogicalNode_hasBufferedReports(LogicalNode* node);
bool
LogicalNode_hasUnbufferedReports(LogicalNode* node);
+/**
+ * \brief get a data set instance
+ *
+ * \param self the logical node instance of the data set
+ * \param dataSetName the name of the data set
+ *
+ * \return the data set instance or NULL if the data set does not exist
+ */
+DataSet*
+LogicalNode_getDataSet(LogicalNode* self, const char* dataSetName);
+
bool
DataObject_hasFCData(DataObject* dataObject, FunctionalConstraint fc);
diff --git a/src/iec61850/inc/iec61850_server.h b/src/iec61850/inc/iec61850_server.h
index 263f6f52..834a4673 100644
--- a/src/iec61850/inc/iec61850_server.h
+++ b/src/iec61850/inc/iec61850_server.h
@@ -960,11 +960,12 @@ IedServer_observeDataAttribute(IedServer self, DataAttribute* dataAttribute,
* \param the data attribute that has been written by an MMS client.
* \param the value the client want to write to the data attribute
* \param connection the connection object of the client connection that invoked the write operation
+ * \param parameter the user provided parameter
*
* \return true if access is accepted, false if access is denied.
*/
typedef MmsDataAccessError
-(*WriteAccessHandler) (DataAttribute* dataAttribute, MmsValue* value, ClientConnection connection);
+(*WriteAccessHandler) (DataAttribute* dataAttribute, MmsValue* value, ClientConnection connection, void* parameter);
/**
* \brief Install a WriteAccessHandler for a data attribute.
@@ -979,10 +980,11 @@ typedef MmsDataAccessError
* \param dataAttribute the data attribute to monitor
* \param handler the callback function that is invoked if a client tries to write to
* the monitored data attribute.
+ * \param parameter a user provided parameter that is passed to the WriteAccessHandler when called.
*/
void
IedServer_handleWriteAccess(IedServer self, DataAttribute* dataAttribute,
- WriteAccessHandler handler);
+ WriteAccessHandler handler, void* parameter);
typedef enum {
ACCESS_POLICY_ALLOW,
diff --git a/src/iec61850/inc_private/mms_mapping.h b/src/iec61850/inc_private/mms_mapping.h
index 527a72c9..11e7a778 100644
--- a/src/iec61850/inc_private/mms_mapping.h
+++ b/src/iec61850/inc_private/mms_mapping.h
@@ -139,7 +139,7 @@ void
MmsMapping_setConnectionIndicationHandler(MmsMapping* self, IedConnectionIndicationHandler handler, void* parameter);
void
-MmsMapping_installWriteAccessHandler(MmsMapping* self, DataAttribute* dataAttribute, WriteAccessHandler handler);
+MmsMapping_installWriteAccessHandler(MmsMapping* self, DataAttribute* dataAttribute, WriteAccessHandler handler, void* parameter);
MmsDataAccessError
Control_writeAccessControlObject(MmsMapping* self, MmsDomain* domain, char* variableIdOrig,
diff --git a/src/iec61850/inc_private/reporting.h b/src/iec61850/inc_private/reporting.h
index 1f4b1bc2..739bdf22 100644
--- a/src/iec61850/inc_private/reporting.h
+++ b/src/iec61850/inc_private/reporting.h
@@ -29,6 +29,7 @@ typedef struct sReportBufferEntry ReportBufferEntry;
struct sReportBufferEntry {
uint8_t entryId[8];
uint8_t flags; /* bit 0 (1 = isIntegrityReport), bit 1 (1 = isGiReport) */
+ uint64_t timeOfEntry;
int entryLength;
ReportBufferEntry* next;
};
diff --git a/src/iec61850/server/impl/ied_server.c b/src/iec61850/server/impl/ied_server.c
index d630087f..5f418cf6 100644
--- a/src/iec61850/server/impl/ied_server.c
+++ b/src/iec61850/server/impl/ied_server.c
@@ -476,7 +476,7 @@ singleThreadedServerThread(void* parameter)
while (running) {
- if (IedServer_waitReady(self, 100) > 0) {
+ if (IedServer_waitReady(self, 25) > 0) {
MmsServer_handleIncomingMessages(self->mmsServer);
IedServer_performPeriodicTasks(self);
}
@@ -770,26 +770,26 @@ checkForChangedTriggers(IedServer self, DataAttribute* dataAttribute)
#if (CONFIG_IEC61850_REPORT_SERVICE == 1) || (CONFIG_INCLUDE_GOOSE_SUPPORT == 1)
if (dataAttribute->triggerOptions & TRG_OPT_DATA_CHANGED) {
+#if (CONFIG_INCLUDE_GOOSE_SUPPORT == 1)
+ MmsMapping_triggerGooseObservers(self->mmsMapping, dataAttribute->mmsValue);
+#endif
+
#if (CONFIG_IEC61850_REPORT_SERVICE == 1)
MmsMapping_triggerReportObservers(self->mmsMapping, dataAttribute->mmsValue,
REPORT_CONTROL_VALUE_CHANGED);
#endif
+ }
+
+ else if (dataAttribute->triggerOptions & TRG_OPT_QUALITY_CHANGED) {
#if (CONFIG_INCLUDE_GOOSE_SUPPORT == 1)
MmsMapping_triggerGooseObservers(self->mmsMapping, dataAttribute->mmsValue);
#endif
- }
-
- else if (dataAttribute->triggerOptions & TRG_OPT_QUALITY_CHANGED) {
#if (CONFIG_IEC61850_REPORT_SERVICE == 1)
MmsMapping_triggerReportObservers(self->mmsMapping, dataAttribute->mmsValue,
REPORT_CONTROL_QUALITY_CHANGED);
#endif
-
-#if (CONFIG_INCLUDE_GOOSE_SUPPORT == 1)
- MmsMapping_triggerGooseObservers(self->mmsMapping, dataAttribute->mmsValue);
-#endif
}
#endif /* (CONFIG_IEC61850_REPORT_SERVICE== 1) || (CONFIG_INCLUDE_GOOSE_SUPPORT == 1) */
@@ -916,6 +916,7 @@ IedServer_updateBooleanAttributeValue(IedServer self, DataAttribute* dataAttribu
bool currentValue = MmsValue_getBoolean(dataAttribute->mmsValue);
if (currentValue == value) {
+
checkForUpdateTrigger(self, dataAttribute);
}
else {
@@ -993,15 +994,15 @@ IedServer_updateQuality(IedServer self, DataAttribute* dataAttribute, Quality qu
if (oldQuality != (uint32_t) quality) {
MmsValue_setBitStringFromInteger(dataAttribute->mmsValue, (uint32_t) quality);
+#if (CONFIG_INCLUDE_GOOSE_SUPPORT == 1)
+ MmsMapping_triggerGooseObservers(self->mmsMapping, dataAttribute->mmsValue);
+#endif
+
#if (CONFIG_IEC61850_REPORT_SERVICE == 1)
if (dataAttribute->triggerOptions & TRG_OPT_QUALITY_CHANGED)
MmsMapping_triggerReportObservers(self->mmsMapping, dataAttribute->mmsValue,
REPORT_CONTROL_QUALITY_CHANGED);
#endif
-
-#if (CONFIG_INCLUDE_GOOSE_SUPPORT == 1)
- MmsMapping_triggerGooseObservers(self->mmsMapping, dataAttribute->mmsValue);
-#endif
}
@@ -1079,12 +1080,12 @@ IedServer_setWriteAccessPolicy(IedServer self, FunctionalConstraint fc, AccessPo
}
void
-IedServer_handleWriteAccess(IedServer self, DataAttribute* dataAttribute, WriteAccessHandler handler)
+IedServer_handleWriteAccess(IedServer self, DataAttribute* dataAttribute, WriteAccessHandler handler, void* parameter)
{
if (dataAttribute == NULL)
*((int*) NULL) = 1;
- MmsMapping_installWriteAccessHandler(self->mmsMapping, dataAttribute, handler);
+ MmsMapping_installWriteAccessHandler(self->mmsMapping, dataAttribute, handler, parameter);
}
void
diff --git a/src/iec61850/server/mms_mapping/mms_goose.c b/src/iec61850/server/mms_mapping/mms_goose.c
index e4c0678c..8b9d723f 100644
--- a/src/iec61850/server/mms_mapping/mms_goose.c
+++ b/src/iec61850/server/mms_mapping/mms_goose.c
@@ -169,7 +169,6 @@ MmsGooseControlBlock_enable(MmsGooseControlBlock self)
if (!MmsGooseControlBlock_isEnabled(self)) {
-
if (self->dataSetRef != NULL) {
GLOBAL_FREEMEM(self->dataSetRef);
diff --git a/src/iec61850/server/mms_mapping/mms_mapping.c b/src/iec61850/server/mms_mapping/mms_mapping.c
index c82eed03..78fb5dea 100644
--- a/src/iec61850/server/mms_mapping/mms_mapping.c
+++ b/src/iec61850/server/mms_mapping/mms_mapping.c
@@ -50,6 +50,7 @@ typedef struct
{
DataAttribute* attribute;
WriteAccessHandler handler;
+ void* parameter;
} AttributeAccessHandler;
@@ -1761,6 +1762,8 @@ mmsWriteHandler(void* parameter, MmsDomain* domain,
sg->editSgConfirmedHandler(sg->editSgConfirmedHandlerParameter, sg->sgcb,
sg->sgcb->editSG);
+ unselectSettingGroup(sg);
+
return DATA_ACCESS_ERROR_SUCCESS;
}
else
@@ -1828,7 +1831,8 @@ mmsWriteHandler(void* parameter, MmsDomain* domain,
if (matchingValue != NULL) {
MmsDataAccessError handlerResult =
- accessHandler->handler(dataAttribute, matchingValue, (ClientConnection) connection);
+ accessHandler->handler(dataAttribute, matchingValue, (ClientConnection) connection,
+ accessHandler->parameter);
if (handlerResult == DATA_ACCESS_ERROR_SUCCESS)
handlerFound = true;
@@ -1840,8 +1844,8 @@ mmsWriteHandler(void* parameter, MmsDomain* domain,
else { /* if ACCESS_POLICY_DENY only allow direct access to handled data attribute */
if (dataAttribute->mmsValue == cachedValue) {
MmsDataAccessError handlerResult =
- accessHandler->handler(dataAttribute, value, (ClientConnection) connection);
-
+ accessHandler->handler(dataAttribute, value, (ClientConnection) connection,
+ accessHandler->parameter);
if (handlerResult == DATA_ACCESS_ERROR_SUCCESS) {
handlerFound = true;
@@ -1925,7 +1929,7 @@ getAccessHandlerForAttribute(MmsMapping* self, DataAttribute* dataAttribute)
}
void
-MmsMapping_installWriteAccessHandler(MmsMapping* self, DataAttribute* dataAttribute, WriteAccessHandler handler)
+MmsMapping_installWriteAccessHandler(MmsMapping* self, DataAttribute* dataAttribute, WriteAccessHandler handler, void* parameter)
{
AttributeAccessHandler* accessHandler = getAccessHandlerForAttribute(self, dataAttribute);
@@ -1933,6 +1937,7 @@ MmsMapping_installWriteAccessHandler(MmsMapping* self, DataAttribute* dataAttrib
accessHandler = (AttributeAccessHandler*) GLOBAL_MALLOC(sizeof(AttributeAccessHandler));
accessHandler->attribute = dataAttribute;
+ accessHandler->parameter = parameter;
LinkedList_add(self->attributeAccessHandlers, (void*) accessHandler);
}
diff --git a/src/iec61850/server/mms_mapping/reporting.c b/src/iec61850/server/mms_mapping/reporting.c
index 8763d9b3..b3513b0f 100644
--- a/src/iec61850/server/mms_mapping/reporting.c
+++ b/src/iec61850/server/mms_mapping/reporting.c
@@ -214,7 +214,7 @@ ReportControl_getRCBValue(ReportControl* rc, char* elementName)
return MmsValue_getElement(rc->rcbValues, 10);
else if (strcmp(elementName, "EntryID") == 0)
return MmsValue_getElement(rc->rcbValues, 11);
- else if (strcmp(elementName, "TimeOfEntry") == 0)
+ else if (strcmp(elementName, "TimeofEntry") == 0)
return MmsValue_getElement(rc->rcbValues, 12);
else if (strcmp(elementName, "ResvTms") == 0)
return MmsValue_getElement(rc->rcbValues, 13);
@@ -949,7 +949,7 @@ createBufferedReportControlBlock(ReportControlBlock* reportControlBlock,
mmsValue->value.structure.components[11] = MmsValue_newOctetString(8, 8);
namedVariable = (MmsVariableSpecification*) GLOBAL_CALLOC(1, sizeof(MmsVariableSpecification));
- namedVariable->name = copyString("TimeOfEntry");
+ namedVariable->name = copyString("TimeofEntry");
namedVariable->type = MMS_BINARY_TIME;
namedVariable->typeSpec.binaryTime = 6;
rcb->typeSpec.structure.elements[12] = namedVariable;
@@ -1420,7 +1420,6 @@ Reporting_RCBWriteAccessHandler(MmsMapping* self, ReportControl* rc, char* eleme
if (rcbValue != NULL)
MmsValue_update(rcbValue, value);
else {
- printf("AAAAAA\n");
retVal = DATA_ACCESS_ERROR_OBJECT_VALUE_INVALID;
goto exit_function;
}
@@ -1520,7 +1519,7 @@ printReportId(ReportBufferEntry* report)
#endif
static void
-enqueueReport(ReportControl* reportControl, bool isIntegrity, bool isGI)
+enqueueReport(ReportControl* reportControl, bool isIntegrity, bool isGI, uint64_t timeOfEntry)
{
if (DEBUG_IED_SERVER) printf("IED_SERVER: enqueueReport: RCB name: %s (SQN:%u) enabled:%i buffered:%i buffering:%i intg:%i GI:%i\n",
reportControl->name, (unsigned) reportControl->sqNum, reportControl->enabled,
@@ -1746,15 +1745,17 @@ enqueueReport(ReportControl* reportControl, bool isIntegrity, bool isGI)
ReportBufferEntry* entry = (ReportBufferEntry*) entryBufPos;
/* ENTRY_ID is set to system time in ms! */
- uint64_t timestamp = Hal_getTimeInMs();
+ uint64_t entryId = timeOfEntry;
- if (timestamp <= reportControl->lastEntryId)
- timestamp = reportControl->lastEntryId + 1;
+ if (entryId <= reportControl->lastEntryId)
+ entryId = reportControl->lastEntryId + 1;
+
+ entry->timeOfEntry = entryId;
#if (ORDER_LITTLE_ENDIAN == 1)
- memcpyReverseByteOrder(entry->entryId, (uint8_t*) ×tamp, 8);
+ memcpyReverseByteOrder(entry->entryId, (uint8_t*) &entryId, 8);
#else
- memcpy (entry->entryId, (uint8_t*) ×tamp, 8);
+ memcpy (entry->entryId, (uint8_t*) &entryId, 8);
#endif
#if (DEBUG_IED_SERVER == 1)
@@ -1844,7 +1845,7 @@ enqueueReport(ReportControl* reportControl, bool isIntegrity, bool isGI)
if (buffer->oldestReport == NULL)
buffer->oldestReport = buffer->lastEnqueuedReport;
- reportControl->lastEntryId = timestamp;
+ reportControl->lastEntryId = entryId;
}
static void
@@ -1924,7 +1925,15 @@ sendNextReportEntry(ReportControl* self)
goto return_out_of_memory;
if (MmsValue_getBitStringBit(optFlds, 2)) { /* report time stamp */
- if (MemAllocLinkedList_add(reportElements, self->timeOfEntry) == NULL)
+ MmsValue* timeOfEntry = (MmsValue*) MemoryAllocator_allocate(&ma, sizeof(MmsValue));
+
+ if (timeOfEntry == NULL) goto return_out_of_memory;
+
+ timeOfEntry->deleteValue = 0;
+ timeOfEntry->type = MMS_UTC_TIME;
+ MmsValue_setUtcTimeMs(timeOfEntry, report->timeOfEntry);
+
+ if (MemAllocLinkedList_add(reportElements, timeOfEntry) == NULL)
goto return_out_of_memory;
}
@@ -2010,7 +2019,7 @@ sendNextReportEntry(ReportControl* self)
+ ldNameLength
+ variableNameLength + 1;
- char* dataReference = (char*) MemoryAllocator_allocate(&ma, refLen);
+ char* dataReference = (char*) MemoryAllocator_allocate(&ma, refLen + 1);
if (dataReference == NULL) goto return_out_of_memory;
@@ -2214,7 +2223,7 @@ processEventsForReport(ReportControl* rc, uint64_t currentTimeInMs)
/* send current events in event buffer before GI report */
if (rc->triggered) {
if (rc->buffered)
- enqueueReport(rc, false, false);
+ enqueueReport(rc, false, false, currentTimeInMs);
else
sendReport(rc, false, false);
@@ -2224,7 +2233,7 @@ processEventsForReport(ReportControl* rc, uint64_t currentTimeInMs)
updateTimeOfEntry(rc, currentTimeInMs);
if (rc->buffered)
- enqueueReport(rc, false, true);
+ enqueueReport(rc, false, true, currentTimeInMs);
else
sendReport(rc, false, true);
@@ -2242,7 +2251,7 @@ processEventsForReport(ReportControl* rc, uint64_t currentTimeInMs)
/* send current events in event buffer before integrity report */
if (rc->triggered) {
if (rc->buffered)
- enqueueReport(rc, false, false);
+ enqueueReport(rc, false, false, currentTimeInMs);
else
sendReport(rc, false, false);
@@ -2253,7 +2262,7 @@ processEventsForReport(ReportControl* rc, uint64_t currentTimeInMs)
updateTimeOfEntry(rc, currentTimeInMs);
if (rc->buffered)
- enqueueReport(rc, true, false);
+ enqueueReport(rc, true, false, currentTimeInMs);
else
sendReport(rc, true, false);
@@ -2266,7 +2275,7 @@ processEventsForReport(ReportControl* rc, uint64_t currentTimeInMs)
if (currentTimeInMs >= rc->reportTime) {
if (rc->buffered)
- enqueueReport(rc, false, false);
+ enqueueReport(rc, false, false, currentTimeInMs);
else
sendReport(rc, false, false);
diff --git a/src/iec61850/server/model/model.c b/src/iec61850/server/model/model.c
index ad1bd598..6e752faa 100644
--- a/src/iec61850/server/model/model.c
+++ b/src/iec61850/server/model/model.c
@@ -345,6 +345,46 @@ LogicalNode_hasFCData(LogicalNode* node, FunctionalConstraint fc)
return false;
}
+DataSet*
+LogicalNode_getDataSet(LogicalNode* self, const char* dataSetName)
+{
+ assert(self->modelType == LogicalNodeModelType);
+ assert(dataSetName != NULL);
+
+ char dsName[66];
+
+ LogicalDevice* ld = (LogicalDevice*) self->parent;
+
+ if (strlen(dataSetName) > 32) {
+
+ if (DEBUG_IED_SERVER) {
+ printf("IED_SERVER: LogicalNode_getDataSet - data set name %s too long!\n", dataSetName);
+ }
+
+ goto exit_error;
+ }
+
+ StringUtils_createStringInBuffer(dsName, 3, self->name, "$", dataSetName);
+
+ IedModel* iedModel = (IedModel*) ld->parent;
+
+ DataSet* ds = iedModel->dataSets;
+
+ while (ds != NULL) {
+ if (strcmp(ds->logicalDeviceName, ld->name) == 0) {
+ if (strcmp(ds->name, dsName) == 0) {
+ return ds;
+ }
+ }
+
+ ds = ds->sibling;
+ }
+
+
+exit_error:
+ return NULL;
+}
+
int
LogicalDevice_getLogicalNodeCount(LogicalDevice* logicalDevice)
{
@@ -360,6 +400,54 @@ LogicalDevice_getLogicalNodeCount(LogicalDevice* logicalDevice)
return lnCount;
}
+ModelNode*
+LogicalDevice_getChildByMmsVariableName(LogicalDevice* logicalDevice, const char* mmsVariableName)
+{
+
+
+ char fcString[3];
+ char nameRef[65];
+
+ char* separator = strchr(mmsVariableName,'$');
+
+ if (separator == NULL)
+ return NULL;
+
+ if (strlen(separator) > 4) {
+ fcString[0] = separator[1];
+ fcString[1] = separator[2];
+ fcString[2] = 0;
+
+ const char* strpos = mmsVariableName;
+
+ int targetPos = 0;
+
+ while (strpos < separator) {
+ nameRef[targetPos++] = strpos[0];
+ strpos++;
+ }
+
+ nameRef[targetPos++] = '.';
+
+ strpos = separator + 4;
+
+ while (strpos[0] != 0) {
+ nameRef[targetPos++] = strpos[0];
+ strpos++;
+ }
+
+ nameRef[targetPos++] = 0;
+
+ StringUtils_replace(nameRef, '$', '.');
+
+ FunctionalConstraint fc = FunctionalConstraint_fromString(fcString);
+
+ return ModelNode_getChildWithFc((ModelNode*) logicalDevice, nameRef, fc);
+ }
+
+ return NULL;
+}
+
static int
createObjectReference(ModelNode* node, char* objectReference)
{
diff --git a/src/mms/iso_mms/client/mms_client_connection.c b/src/mms/iso_mms/client/mms_client_connection.c
index 90455d98..c91005cd 100644
--- a/src/mms/iso_mms/client/mms_client_connection.c
+++ b/src/mms/iso_mms/client/mms_client_connection.c
@@ -1058,11 +1058,12 @@ mmsClient_getNameListSingleRequest(
ByteBuffer* responseMessage = sendRequestAndWaitForResponse(self, invokeId, payload);
-
-
if (responseMessage != NULL)
moreFollows = mmsClient_parseGetNameListResponse(nameList, self->lastResponse, NULL);
+ if (self->lastResponseError != MMS_ERROR_NONE)
+ *mmsError = self->lastResponseError;
+
releaseResponse(self);
if (self->associationState == MMS_STATE_CLOSED)
diff --git a/src/mms/iso_mms/server/mms_access_result.c b/src/mms/iso_mms/server/mms_access_result.c
index 3b4f033c..59d52ab6 100644
--- a/src/mms/iso_mms/server/mms_access_result.c
+++ b/src/mms/iso_mms/server/mms_access_result.c
@@ -103,12 +103,19 @@ encodeStructuredAccessResult(MmsValue* value, uint8_t* buffer, int bufPos, bool
int
mmsServer_encodeAccessResult(MmsValue* value, uint8_t* buffer, int bufPos, bool encode)
{
- if (value == NULL) // TODO report internal error
- return 0;
+// if (value == NULL) // TODO report internal error
+// return 0;
int size;
switch (value->type) {
+ case MMS_BOOLEAN:
+ if (encode)
+ bufPos = BerEncoder_encodeBoolean(0x83, value->value.boolean, buffer, bufPos);
+ else
+ size = 3;
+ break;
+
case MMS_STRUCTURE:
if (encode)
bufPos = encodeStructuredAccessResult(value, buffer, bufPos, true);
@@ -166,12 +173,7 @@ mmsServer_encodeAccessResult(MmsValue* value, uint8_t* buffer, int bufPos, bool
else
size = BerEncoder_determineEncodedBitStringSize(value->value.bitString.size);
break;
- case MMS_BOOLEAN:
- if (encode)
- bufPos = BerEncoder_encodeBoolean(0x83, value->value.boolean, buffer, bufPos);
- else
- size = 3;
- break;
+
case MMS_BINARY_TIME:
if (encode)
bufPos = BerEncoder_encodeOctetString(0x8c, value->value.binaryTime.buf,
diff --git a/src/mms/iso_mms/server/mms_file_service.c b/src/mms/iso_mms/server/mms_file_service.c
index 03618b45..d0780fb3 100644
--- a/src/mms/iso_mms/server/mms_file_service.c
+++ b/src/mms/iso_mms/server/mms_file_service.c
@@ -214,11 +214,11 @@ mmsServer_handleFileDeleteRequest(
filename[length] = 0;
if (DEBUG_MMS_SERVER)
- printf("mms_file_service.c: Delete file (%s)\n", filename);
+ printf("MMS_SERVER: mms_file_service.c: Delete file (%s)\n", filename);
if (!FileSystem_getFileInfo(filename, NULL, NULL)) {
if (DEBUG_MMS_SERVER)
- printf("mms_file_service.c: File (%s) not found\n", filename);
+ printf("MMS_SERVER: mms_file_service.c: File (%s) not found\n", filename);
mmsServer_createConfirmedErrorPdu(invokeId, response, MMS_ERROR_FILE_FILE_NON_EXISTENT);
return;
@@ -226,7 +226,7 @@ mmsServer_handleFileDeleteRequest(
if (!FileSystem_deleteFile(filename)) {
if (DEBUG_MMS_SERVER)
- printf("mms_file_service.c: Delete file (%s) failed\n", filename);
+ printf("MMS_SERVER: mms_file_service.c: Delete file (%s) failed\n", filename);
mmsServer_createConfirmedErrorPdu(invokeId, response, MMS_ERROR_FILE_FILE_ACCESS_DENIED);
return;
@@ -381,7 +381,7 @@ mmsServer_handleFileReadRequest(
int32_t frsmId = (int32_t) BerDecoder_decodeUint32(buffer, maxBufPos - bufPos, bufPos);
if (DEBUG_MMS_SERVER)
- printf("mmsServer_handleFileReadRequest read request for frsmId: %i\n", frsmId);
+ printf("MMS_SERVER: mmsServer_handleFileReadRequest read request for frsmId: %i\n", frsmId);
MmsFileReadStateMachine* frsm = getFrsm(connection, frsmId);
@@ -436,104 +436,105 @@ encodeFileSpecification(uint8_t tag, char* fileSpecification, uint8_t* buffer, i
}
}
-
-
-static void
-createFileDirectoryResponse(uint32_t invokeId, ByteBuffer* response, char* directoryName, char* continueAfterFileName)
+static int
+addFileEntriesToResponse(uint8_t* buffer, int bufPos, int maxBufSize, char* directoryName, char* continueAfterFileName, bool* moreFollows)
{
- int maxSize = response->maxSize - 3; /* reserve space for moreFollows */
- uint8_t* buffer = response->buffer;
-
- bool moreFollows = false;
-
- int tempStartPos = 30; /* estimated header part with safety margin */
- int tempCurPos = tempStartPos;
- int tempEncoded = 0;
-
- char extendedFileName[300];
+ int directoryNameLength = strlen(directoryName);
DirectoryHandle directory = FileSystem_openDirectory(directoryName);
- if (continueAfterFileName != NULL) {
- if (strlen(continueAfterFileName) == 0)
- continueAfterFileName = NULL;
- }
-
if (directory != NULL) {
bool isDirectory;
char* fileName = FileSystem_readDirectory(directory, &isDirectory);
while (fileName != NULL) {
- if (isDirectory) {
- strcpy(extendedFileName, fileName);
- strcat(extendedFileName, "/");
-
- fileName = extendedFileName;
- }
-
- if (continueAfterFileName != NULL) {
- if (strcmp(continueAfterFileName, fileName) == 0)
- continueAfterFileName = NULL;
- }
- else {
- uint64_t msTime;
+ directoryName[directoryNameLength] = 0;
- char fullPath[CONFIG_MMS_FILE_SERVICE_MAX_FILENAME_LENGTH];
+ if (directoryNameLength > 0)
+ strcat(directoryName, "/");
- if (directoryName != NULL) {
- int directoryLen = strlen(directoryName);
+ strcat(directoryName, fileName);
- strcpy(fullPath, directoryName);
+ if (isDirectory) {
+ bufPos = addFileEntriesToResponse(buffer, bufPos, maxBufSize, directoryName, continueAfterFileName, moreFollows);
- if (directoryName[directoryLen - 1] != CONFIG_SYSTEM_FILE_SEPARATOR) {
- fullPath[directoryLen] = CONFIG_SYSTEM_FILE_SEPARATOR;
- fullPath[directoryLen + 1] = 0;
- }
+ if (*moreFollows == true)
+ break;
+ }
+ else {
+ if (continueAfterFileName != NULL) {
+ if (strcmp(continueAfterFileName, directoryName) == 0)
+ continueAfterFileName = NULL;
+ }
+ else {
+ uint64_t msTime;
- strcat(fullPath, fileName);
- }
- else {
- strncpy(fullPath, fileName, CONFIG_MMS_FILE_SERVICE_MAX_FILENAME_LENGTH - 1);
- fullPath[CONFIG_MMS_FILE_SERVICE_MAX_FILENAME_LENGTH - 1] = 0;
- }
+ uint32_t fileSize;
- uint32_t fileSize;
+ FileSystem_getFileInfo(directoryName, &fileSize, &msTime);
- FileSystem_getFileInfo(fullPath, &fileSize, &msTime);
+ char gtString[30];
- char gtString[30];
+ Conversions_msTimeToGeneralizedTime(msTime, (uint8_t*) gtString);
- Conversions_msTimeToGeneralizedTime(msTime, (uint8_t*) gtString);
+ int fileAttributesSize = encodeFileAttributes(0xa1, fileSize, gtString, NULL, 0);
- int fileAttributesSize = encodeFileAttributes(0xa1, fileSize, gtString, NULL, 0);
+ int filenameSize = encodeFileSpecification(0xa0, directoryName, NULL, 0);
- int filenameSize = encodeFileSpecification(0xa0, fileName, NULL, 0);
+ int dirEntrySize = 2 + fileAttributesSize + filenameSize;
- int dirEntrySize = 2 + fileAttributesSize + filenameSize;
+ int overallEntrySize = 1 + BerEncoder_determineLengthSize(dirEntrySize) + dirEntrySize;
- int overallEntrySize = 1 + BerEncoder_determineLengthSize(dirEntrySize) + dirEntrySize;
+ int bufferSpaceLeft = maxBufSize - bufPos;
- int bufferSpaceLeft = maxSize - tempCurPos;
+ if (overallEntrySize > bufferSpaceLeft) {
+ *moreFollows = true;
+ break;
+ }
- if (overallEntrySize > bufferSpaceLeft) {
- moreFollows = true;
- break;
- }
+ bufPos = BerEncoder_encodeTL(0x30, dirEntrySize, buffer, bufPos); /* SEQUENCE (DirectoryEntry) */
+ bufPos = encodeFileSpecification(0xa0, directoryName, buffer, bufPos); /* fileName */
+ bufPos = encodeFileAttributes(0xa1, fileSize, gtString, buffer, bufPos); /* file attributes */
- tempCurPos = BerEncoder_encodeTL(0x30, dirEntrySize, buffer, tempCurPos); /* SEQUENCE (DirectoryEntry) */
- tempCurPos = encodeFileSpecification(0xa0, fileName, buffer, tempCurPos); /* fileName */
- tempCurPos = encodeFileAttributes(0xa1, fileSize, gtString, buffer, tempCurPos); /* file attributes */
+ }
}
+
fileName = FileSystem_readDirectory(directory, &isDirectory);
}
FileSystem_closeDirectory(directory);
}
- else {
+
+ directoryName[directoryNameLength] = 0;
+
+ return bufPos;
+}
+
+static void
+createFileDirectoryResponse(uint32_t invokeId, ByteBuffer* response, char* directoryName, char* continueAfterFileName)
+{
+ int maxSize = response->maxSize - 3; /* reserve space for moreFollows */
+ uint8_t* buffer = response->buffer;
+
+ bool moreFollows = false;
+
+ int tempStartPos = 30; /* estimated header part with safety margin */
+ int tempCurPos = tempStartPos;
+ int tempEncoded = 0;
+
+ if (continueAfterFileName != NULL) {
+ if (strlen(continueAfterFileName) == 0)
+ continueAfterFileName = NULL;
+ }
+
+ tempCurPos = addFileEntriesToResponse(buffer, tempCurPos, maxSize, directoryName, continueAfterFileName, &moreFollows);
+
+ if (tempCurPos < 0) {
+
if (DEBUG_MMS_SERVER)
- printf("Error opening directory!\n");
+ printf("MMS_SERVER: Error opening directory!\n");
mmsServer_createConfirmedErrorPdu(invokeId, response, MMS_ERROR_FILE_FILE_NON_EXISTENT);
@@ -608,7 +609,7 @@ mmsServer_handleFileRenameRequest(
return;
if (DEBUG_MMS_SERVER)
- printf("currentFileName: (%s)\n", currentFileName);
+ printf("MMS_SERVER: currentFileName: (%s)\n", currentFileName);
break;
@@ -617,12 +618,12 @@ mmsServer_handleFileRenameRequest(
return;
if (DEBUG_MMS_SERVER)
- printf("newFileName: (%s)\n", newFileName);
+ printf("MMS_SERVER: newFileName: (%s)\n", newFileName);
break;
default: /* ignore unknown tag */
if (DEBUG_MMS_SERVER)
- printf("unknown tag: (%02x)\n", tag);
+ printf("MMS_SERVER: unknown tag: (%02x)\n", tag);
bufPos += length;
break;
@@ -637,7 +638,7 @@ mmsServer_handleFileRenameRequest(
else
{
if (DEBUG_MMS_SERVER)
- printf("rename file failed!\n");
+ printf("MMS_SERVER: rename file failed!\n");
mmsServer_createConfirmedErrorPdu(invokeId, response, MMS_ERROR_FILE_OTHER);
}
@@ -655,7 +656,7 @@ mmsServer_handleFileDirectoryRequest(
ByteBuffer* response)
{
if (DEBUG_MMS_SERVER)
- printf("handleFileDirectoryRequest bufPos:%i, maxBufPus:%i\n", bufPos, maxBufPos);
+ printf("MMS_SERVER: handleFileDirectoryRequest bufPos:%i, maxBufPus:%i\n", bufPos, maxBufPos);
char filename[256] = "";
@@ -678,6 +679,11 @@ mmsServer_handleFileDirectoryRequest(
case 0xa0: /* filename */
if (!parseFileName(filename, buffer, &bufPos, bufPos + length, invokeId, response))
return;
+
+ /* check for wildcard character(*) */
+ if ((strcmp(filename, "*") == 0) || (strcmp(filename, "/") == 0) || (strcmp(filename, "\\") == 0))
+ filename[0] = 0;
+
break;
case 0xa1: /* continue-after */
@@ -690,7 +696,7 @@ mmsServer_handleFileDirectoryRequest(
default: /* unrecognized parameter */
if (DEBUG_MMS_SERVER)
- printf("handleFileDirectoryRequest: unrecognized parameter\n");
+ printf("MMS_SERVER: handleFileDirectoryRequest: unrecognized parameter\n");
mmsServer_writeMmsRejectPdu(&invokeId, MMS_ERROR_REJECT_INVALID_PDU, response);
return;
}
diff --git a/src/vs/libiec61850-wo-goose.def b/src/vs/libiec61850-wo-goose.def
index 09c2cdab..54cabdeb 100644
--- a/src/vs/libiec61850-wo-goose.def
+++ b/src/vs/libiec61850-wo-goose.def
@@ -492,4 +492,5 @@ EXPORTS
IedModel_setIedNameForDynamicModel
ControlObjectClient_useConstantT
ControlObjectClient_setOrigin
-
+ LogicalDevice_getChildByMmsVariableName
+ LogicalNode_getDataset
diff --git a/src/vs/libiec61850.def b/src/vs/libiec61850.def
index 9682ddad..73d532e7 100644
--- a/src/vs/libiec61850.def
+++ b/src/vs/libiec61850.def
@@ -516,3 +516,5 @@ EXPORTS
IedModel_setIedNameForDynamicModel
ControlObjectClient_useConstantT
ControlObjectClient_setOrigin
+ LogicalDevice_getChildByMmsVariableName
+ LogicalNode_getDataset
diff --git a/tools/model_generator/genconfig.jar b/tools/model_generator/genconfig.jar
index 75df96c9..3a36f546 100644
Binary files a/tools/model_generator/genconfig.jar and b/tools/model_generator/genconfig.jar differ
diff --git a/tools/model_generator/genmodel.jar b/tools/model_generator/genmodel.jar
index 84d30c65..28621fac 100644
Binary files a/tools/model_generator/genmodel.jar and b/tools/model_generator/genmodel.jar differ
diff --git a/tools/model_generator/src/com/libiec61850/scl/model/DataAttribute.java b/tools/model_generator/src/com/libiec61850/scl/model/DataAttribute.java
index 573183f2..44193d78 100644
--- a/tools/model_generator/src/com/libiec61850/scl/model/DataAttribute.java
+++ b/tools/model_generator/src/com/libiec61850/scl/model/DataAttribute.java
@@ -62,6 +62,9 @@ public class DataAttribute implements DataModelNode {
if (this.fc == null)
this.fc = fc;
+ if (fc != null)
+ this.fc = fc;
+
if ((parent != null) && (parent instanceof DataAttribute))
this.triggerOptions = ((DataAttribute) parent).getTriggerOptions();
else
diff --git a/tools/model_generator/src/com/libiec61850/scl/model/DataObject.java b/tools/model_generator/src/com/libiec61850/scl/model/DataObject.java
index 13a373e0..7a861767 100644
--- a/tools/model_generator/src/com/libiec61850/scl/model/DataObject.java
+++ b/tools/model_generator/src/com/libiec61850/scl/model/DataObject.java
@@ -81,7 +81,16 @@ public class DataObject implements DataModelNode {
daDefinitions = ((DataAttributeType) sclType).getSubDataAttributes();
for (DataAttributeDefinition daDefinition : daDefinitions) {
+
+ if (daDefinition.getFc() == FunctionalConstraint.SE) {
+
+ System.out.println("Add SG DA for corresponding SE DA: ");
+ this.dataAttributes.add(new DataAttribute(daDefinition, typeDeclarations, FunctionalConstraint.SG, this));
+ }
+
this.dataAttributes.add(new DataAttribute(daDefinition, typeDeclarations, null, this));
+
+
}
}