IEC 61850 Protocol API User Manual
IEC 61850 Protocol API User Manual
Pty Ltd
This PDF Document contains internal hyperlinks for ease of navigation. For example, click on any item listed in the Table of Contents to go to that page.
Copyright: All rights reserved. None of the information contained in this document may be reproduced or stored in a database or retrieval system or disclosed to others without written authorization by SystemCORP Pty Ltd. The information in this document is subject to change without prior notice and should not be construed as a commitment by SystemCORP Pty Ltd. SystemCORP Pty Ltd do not assume responsibility for any errors, which may be in this document.
Documentation Control
Author: Revision: Revision History: Balaji Sreenivasan / Blake Myers / Oscar Naval
1.02
1.00 Initial Release 1.01 Minor changes: Sections 3.1, 4.0, general corrections 1.02 References to Appendix page 10, Misc. re-wording grammar/spelling
Page 2 of 46
Table of Contents
1
1.1 1.2 1.3
Introduction..................................................................................................................4
IEC 61850 ........................................................................................................................................ 4 Document Reference ....................................................................................................................... 6 List of Abbreviations ......................................................................................................................... 7
2
2.1 2.2
Overview .....................................................................................................................9
Protocol Integration Stack API Overview ....................................................................................10 Protocol Integration Stack Configuration Overview .....................................................................10
4
4.1 4.2
6
6.1 6.2 6.3 6.4
Appendix ...................................................................................................................26
7.1 7.2 7.3 7.3.1 7.3.2 7.3.3 7.4 IEC 61850 Error Codes..................................................................................................................26 IEC 61850 Data Types ...................................................................................................................28 Examples........................................................................................................................................29 Server Source ................................................................................................................................29 CID File for Server..........................................................................................................................36 Client Source..................................................................................................................................45 Schema for the Private Elements...................................................................................................46
Page 3 of 46
Introduction
1 Introduction
A Substation Automation System (SAS) has depended upon the development and availability of microprocessorbased systems. Thus, the substation equipment evolved from simple electro-mechanical devices to robust digital devices. This in turn provided the possibility of implementing SAS using several intelligent electronic devices (IEDs) to perform the required functions (e.g. protection, local and remote monitoring and control). Consequently, the need arose for efficient communication protocols among the IEDs. Until recently, specific proprietary communication protocols developed by each manufacturer have been used requiring complicated and costly protocol converters when using IEDs from different vendors. The industrys experiences have demonstrated the need for developing a standard communication protocol, which would support interoperability of IEDs from different manufacturers. Interoperability is the ability to operate on the same network or communication path sharing information and commands. Interoperability should not be confused with interchange-ability of IEDs (i.e. the ability to replace an IED supplied by one manufacturer with an IED supplied by another manufacturer without having to change other elements in the system). Interchange-ability is beyond the scope of a communication standard. Interoperability is a common goal for electric utilities, equipment vendors and standardisation bodies. All communications must allow for the seamless integration of IEDs that allow devices from multiple vendors to be integrated together. A consensus must be found between IED manufacturers and users in a way that such devices can freely exchange information. As a result the International Electro-technical Commission (IEC) has published the IEC 61850 standard (in 10 parts, see Document Reference list). SystemCORP Pty Ltd has a Protocol Integration Stack (PIS) that will allow you to build custom client/server applications via SystemCORPs API that meets the functional and performance communications requirements compliant with the IEC 61850 standards, therefore supporting current IEDs, future IEDs, and further substation technological developments regardless of the vendor.
Substation
Page 4 of 46
Introduction
The GOOSE messages contain information that allow the receiving device to know that a status has changed and the time of the last status change. The time of the last status change allows a receiving device to set local timers relating to a given event. A newly activated device, upon power-up or reinstatement to service, will send current data (status) or values as the initial GOOSE message. Moreover, all devices sending GOOSE messages will continue to send the message with a long cycle time, even if no status/value change has occurred. This ensures that devices that have been activated recently will know the current status values of their peer devices. [IEC 61850-7-2] MMS services and protocol are specified to operate over full OSI and TCP compliant communications profiles. The use of MMS allows provisions for supporting both centralized and distributed architectures. This standard includes the exchange of real-time data indications, control operations, report notification. The Manufacturing Message Specification (MMS) protocol suite provides the information modelling methods and services required by the Abstract Communication Service Interface (ACSI). This mapping of ACSI to MMS defines how the concepts, objects, and services of the ACSI are to be implemented using MMS concepts, objects, and services. This allows interoperability across functions implemented by different IEDs regardless of the manufacturer. [IEC 61850-7-2, IEC 61850-8-1] SNTP (Simple Network Time Protocol) is a time synchronization protocol providing time synchronization with other IEDs. SNTP protocol is widely used in synchronizing computer systems within a network. The SNTPservers themselves are synchronized to timeservers traceable to international standards. UTC time accuracy from SNTP systems is usually in the millisecond range. SNTP provides the current time, the current number of leap seconds, and the warning flags marking the introduction of a leap second correction. [ICE 61850-8-1] The transmission of Sampled Values (SV) requires special attention with regard to the time constraints. The model provides transmission of sampled values in an organized and time controlled way so that the combined jitter of sampling and transmission is minimized to a degree that an unambiguous allocation of the samples, times, and sequence is provided. The SV model applies to the exchange of values of a dataset. The data of the dataset are of the common data class Sampled Analog Value (SV as defined in IEC 61850-7-3). A buffer structure is defined for the transmission of the sampled values. The information exchange is based on a publisher/subscriber mechanism. The publisher writes the values in a local buffer at the sending side. The subscriber reads the values from a local buffer at the receiving side. A time stamp is added to the values, so that the subscriber can check the timeliness of the values. The communication system is responsible to update the local buffers of the subscribers. A sampled value control (SVC) in the publisher is used to control the communication procedure. [IEC 61850-7-2] In general, the IEC 61850 approach is to blend the strengths of the following three methods: functional decomposition, data flow, and information modelling. Functional decomposition is used to understand the logical relationship between components of a distributed function, and is presented in terms of logical nodes that describe the functions, sub-functions and functional interfaces. Data flow is used to understand the communication interfaces that must support the exchange of information between distributed functional components and the functional performance requirements. Information modelling is used to define the abstract syntax and semantics of the information exchanged, and is presented in terms of data object classes and types, attributes, abstract object methods (services), and their relationships.
Page 5 of 46
Introduction
Page 6 of 46
Introduction
DAType = Data Attribute Type DO DPS DS DTD DUT FAT FC GI GoCB = Data Object = Double Point Status information = DATA-SET = Document Type Definition = Device Under Test = Factory Acceptance Test = Functional Constraint = General Interrogation = GOOSE Control Block
GOOSE = Generic Object Oriented Substation Events GSE GSSE GsCB HMI ICD IEC IED INS IP LCB LD LN MC MCAA MICS MMS = Generic Substation Event = Generic Substation Status Event = GSSE Control Block = Human Machine Interface = IED Capability Description = International Electro-technical Commission = Intelligent Electronic Device = Integer Status = Internet Protocol = Log Control Block = Logical Device = Logical Node = Multi-Cast = Multicast Application Association = Model Implementation Conformance Statement = Manufacturing Message Specification (ISO 9506 series)
MSVCB = Multicast Sampled Value Control Block OSI PC = Open System Interconnection = Physical Connection
Page 7 of 46
IEC 61850 Protocol API User Manual PD PICS PIS PIXIT RTOS RTU SAS SAT SAV SBO = Physical Device = Protocol Implementation Conformance Statement = Protocol Integration Stack = Protocol Implementation eXtra Information for Testing = Real Time Operating System = Remote Terminal Unit = Substation Automation System = Site Acceptance Test = Sampled Analogue Value (IEC 61850-9 series) = Select Before Operate
Introduction
SCADA = Supervisory Control And Data Acquisition SCD SCL SCSM SGCB SoE SPS SSD SUT SV SVC TCP TPAA URCB = Substation Configuration Description. = Substation Configuration Language = Specific Communication Service Mapping = Setting Group Control Block = Sequence-of-Events = Single Point Status information = System Specification Description = System Under Test = Sampled Values = Sampled Value Control = Transport Control Protocol = Two Party Application Association = Unbuffered Report Control Block
USVCB = Unicast Sampled Value Control Block UTC VT WDS XML = Coordinated Universal Time = Voltage Transducer = WebCAN Designer Studio = eXtensible Markup Language
Page 8 of 46
Overview
2 Overview
User Application
API The API Calls and Call-backs access the data within the data module via the Data Attribute (DA) ID. Call-backs Calls
IEC 61850
SCL File
The SCL File contains the object model that holds the Data Attribute (DA) IDs used to indentify each data object.
The Protocol Integration Stack (PIC) accesses the Network Interface Card via the Operating system. An independent SNTP Client sets the Operating System time.
Set time
SNTP Client
Ethernet
Page 9 of 46
Overview
User Application
API
Object B
Write (B)
DA Y
DA Z
The user application objects are read, written or updated using the call-back functions with Data Attribute (DA) ID.
2.2
An SCL configuration must be provided to the PIS-010 for it to configure an IEC 61850 data template. The SCL uses Private Elements as part of the Data Attribute Information (DAI). Private Elements describe and link user application objects, which are part of the user application, with IEC 61850 Data Attributes (DA). This can also be described as the mapping mechanism between user application and the IEC 61850 stack. Use either the SystemCORP WebCAN ICD Designer or any third-party tool that can read the XML schema to generate the SCL file. The WebCAN ICD Designer uses SystemCorp_Generic as Private Elements. Example Server Program is in Appendix 7.3.1. Also, see Appendix 7.3.2 CID File for Server for an example SCL (a CID Configured IED Description) file created by the SystemCORP WebCAN ICD Designer. Example Client Program is in Appendix 7.3.3.
Page 10 of 46
User Object: X
Using Private Elements, the 61850 data attributes can than be mapped by any user configuration tool into objects such as a DNP 3 Index, IEC 101 Information Object Address, Modbus Register and any other user specific object as the Private Element as part of the configuration.
3.1.1
<DAI name="stVal"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="1" Field2="1" Field3="1" Field4="0" Field5="0" xmlns:SystemCorp_Generic= "http://www.systemcorp.com.au/61850/SCL/Generic"/> </Private> </DAI>
3.1.2
<DOI name="SPCSO1"> <SDI name="Oper"> <DAI name="ctlVal"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="1" Field2="2" Field3="1" Field4="0" Field5="0" xmlns:SystemCorp_Generic= "http://www.systemcorp.com.au/61850/SCL/Generic"/>
Page 11 of 46
Note: Both the above examples shows a xmlns:SystemCorp_Generic http link that is not active. It is an XML name space (xmlns) used for validation only according to the IEC 61850 specification. Field Attributes: Both the SPS and SPC examples above use the SystemCorp_Generic:GenericPrivateObject Field attributes. Field1 to Field5 are used to identify the mapping between IEC 61850 data attributes and the user data objects. The meaning and contents of this field attributes has to be defined by the application programmer. For example, using the DK61 Development Kit the Field meanings and contents are: Field # Field1 Meaning: For DIP switches 1 through 8 = For the 8LEDs = Field2 Content (value): 1, 2, 3, 4, 5, 6, 7, or 8 1, 2, 3, 4, 5, 6, 7, or 8
Field3
Field4 Field5
For DIP switches (Digital Inputs) = 1 For LEDs (Digital Outputs) = 2 Value = 1 Status = 2 Time = 3 Unused Unused
3.2
Once loaded the user Data Attributes can be accessed via read, write, update functions by specifying the DA ID that is assigned to the required DA.
Page 12 of 46
Protocol Stack
4 Protocol Stack
This section describes the interface provided between the PIS-010 and user application. The API is divided into two categories listed below. Client/Server Management Data Attributes Access
When integrating the IEC 61850 stack into a third party software application the programmer is provided with callback functions described below. No programming inside the stack software is required. Integration work is required linking the stack to the Ethernet driver environment of the target system. The tables below summaries all API functions needed for interfacing a user application to the PIS-10 IEC 61850 stack. The Client/Server Management functions are No API Purpose IEC61850_Create 1 API to create a client or server object with call-backs for reading, writing and updating data objects IEC61850_LoadSCLFile 2 API to read the SCL XML file to get the configuration of server or client IEC61850_Start 3 API to start the server or client 4 5 IEC61850_Stop IEC61850_Free API to stop the server or client API to delete a client or server object created
The Data Attributes Access functions are No API Purpose IEC61850_Read 1 Read the value of a specified data attribute IEC61850_Write 2 Write the value to a specified data attribute IEC61850_Update 3 Update the value of a specified data attribute
User Objects are managed by using call-back functions. In case of server the read and write call-back must be provided by the user application when using the IEC61850_Create function so that PIS-010 call these functions when it reads are writes. In case of client, the IEC61850_Update function call-back provided during the client creation is used to update the user objects. The following sections provided data flow between PIS-010 and a user application.
Page 13 of 46
Protocol Stack
4.1
Server
The section describes how the data is exchanged between PIS-010 and server user application.
Server Calls:
IEC61850_Create
Call-backs:
IEC61850_LoadSCLFile
IEC61850_Start
My_User_Write
Read
My_User_Read
IEC61850_Stop
IEC61850_Free
Page 14 of 46
Protocol Stack
Read Value
Response
Response
New Value
Update API
Boolean: False
LOG
The SCD file defines all subscribers for GOOSE services. GOOSE messages are then automatically generated by the PIS-10 stack.
Page 15 of 46
Protocol Stack
4.2
Client
The section describes how the data is exchanged between PIS-010 and client user application.
Client:
IEC61850_Create
Call-backs:
IEC61850_LoadSCLFile
IEC61850_Start
IEC61850_Read IEC61850_Write
My_User_Update
New Value
IEC61850_Stop
IEC61850_Free
Page 16 of 46
Protocol Stack
Read API
Response
Boolean: True
Return
Boolean: True
Write API
Response
Return
Update Call-back
Boolean: False
The SCD file defines all GOOSE services as subscriber. The PIS-10 stack then processes all incoming GOOSE messages accordingly.
Page 17 of 46
Error codes in Appendix 7.1 (See IEC 61850-7-2:2003 section 5.5.3.4 for Read Write and Update callbacks returned service error codes.).
5.1
Client/Server Management
Data Structures struct IEC61850_Parameters Create Server/client parameters structure. Typedefs typedef struct IEC61850_Struct * IEC61850 Pointer to a IEC 61850 object. typedef int(* IEC61850_ReadCallback )(IEC61850_ObjectID *ptObjectID, IEC61850_ObjectData *ptReturnedValue) Read Callback definition. This function should return a value from the available IEC61850_CallbackReturnServiceErrorCodes. typedef int(* IEC61850_WriteCallback )(IEC61850_ObjectID *ptObjectID, const IEC61850_ObjectData ptNewValue) Write callback definition. This function should return a value from the avaliable IEC61850_CallbackReturnServiceErrorCodes. typedef void( IEC61850_UpdateCallback )(IEC61850_ObjectID const IEC61850_ObjectData ptNewValue) Update callback definition. ptObjectID,
Enumerations enum IEC61850_ClientServerFlag {IEC61850_SERVER = 0, IEC61850_-CLIENT = 1} Server/client parameter. Functions IEC61850 _IEC61850_Create (IEC61850_Parameters *ptParameters, int *errorCode) Create a New IEC61850 object. void _IEC61850_Free (IEC61850 clientServerObject) Free memory used by IEC 61850 object. int _IEC61850_LoadSCLFile (IEC61850 clientServer, char *SCLFileName) Load a SCL file into the IEC 61850. int _IEC61850_Start (IEC61850 clientServer) Start IEC61850 object communications. int _IEC61850_Stop (IEC61850 clientServer) Stop IEC61850 object communications.
Page 18 of 46
5.1.1
Enumerator: IEC61850_SERVER This IEC61850 Object is a Client IEC61850_CLIENT This IEC61850 Object is a Server
5.1.2
Function Documentation
Page 19 of 46
Page 20 of 46
Example Usage: error = IEC61850_Stop(myServer); // Stops myServer if(error != IEC61850_ERROR_NONE) { printf("Cant stop server: %i",error); }
5.2
Data IO
Data Structures struct IEC61850_ObjectID This structure holds the identification of a IEC61850 data object. This is an example structure that matches the PIS10 schema. This can be customised to suit your requirements. struct IEC61850_ObjectData A Data object structure used to exchange data objects between IEC61850 object and application. Typedefs typedef unsigned int tIEC61850Quality IEC61850 Quality data type. (as specified in IEC61850_DATATYPE_TIMESTAMP). IEC 61850 Data Type Enumerations in Appendix 7.2
Functions int _IEC61850_Update (IEC61850 server, IEC61850_ObjectID *ptObjectID, const IEC61850_ObjectData *ptNewValue) Update a given Object of tObjectID with value of ptNewValue. int _IEC61850_Read (IEC61850 client, IEC61850_ObjectID *ptObjectID, IEC61850_ObjectData *ptReturnedValue) Read a value to a given Object ID via the client. int _IEC61850_Write (IEC61850 client, IEC61850_ObjectID ptObjectID, const IEC61850_ObjectData *ptNewValue) Write a value to a given Object ID via the client.
Page 21 of 46
5.2.1
Function Documentation
Returns: IEC61850_ERROR_NONE on success otherwise error code Example Usage: IEC61850_ObjectData Value; IEC61850_ObjectID Object; Unsigned32 u32Counter; // Load Data Value.ucType = IEC61850_DATATYPE_INT32; Value.uiBitLength = sizeof(u32Counter)*8; Value.pvData = &u32Counter; // Load ID Object.uiNumber = 43; error = IEC61850_Read(myServer,&Object,&Value); // Read object with uiNumber = 43 if(error != IEC61850_ERROR_NONE) { printf("error has occured: %i",error); } else { printf("Count = %u",u32Counter); }
5.2.1.2 int _ IEC61850_Update (IEC61850 server IEC61850_ObjectID * ptObjectID, const IEC61850_ObjectData * ptNewValue)
Update a given Object of tObjectID with value of ptNewValue. Parameters: server Server/Client object to update ptObjectID Pointer to Object ID that has been updated ptNewValue Pointer to Object Data structure that hold the new value of the object Returns: IEC61850_ERROR_NONE on success otherwise error code
Page 22 of 46
IEC 61850 Protocol API User Manual Example Usage: IEC61850_ObjectData Value; IEC61850_ObjectID Object; Unsigned32 u32Counter; u32Counter = 34; // Load Data Value.ucType = IEC61850_DATATYPE_INT32; Value.uiBitLength = sizeof(u32Counter)*8; Value.pvData = &u32Counter; // Load ID Object.uiNumber = 596; error = IEC61850_Update(myServer, &Object, &Value); // Update object with uiNumber = 596 with value of 34 if(error != IEC61850_ERROR_NONE) { printf("Update failed: %i",error); }
5.2.1.3 API int _ IEC61850_Write (IEC61850 client,IEC61850_ObjectID * ptObjectID, const IEC61850_ObjectData * ptNewValue)
Write a value to a given Object ID via the client. Parameters: client Client object to write to ptObjectID Pointer to Object ID structure that is to be written ptNewValue Pointer to Object Data structure that hold the new value of the tObjectID Returns: IEC61850_ERROR_NONE on success otherwise error code Example Usage: IEC61850_ObjectData Value; IEC61850_ObjectID Object; char bFlag; bFlag = 1; // Set flag equal to True // Load Data Value.ucType = IEC61850_DATATYPE_BOOLEAN; Value.uiBitLength = sizeof(bFlag)*8; Value.pvData = &bFlag; // Load ID Object.uiNumber = 36; error = IEC61850_Write(myServer, &Object, &Value); // Update object with uiNumber = 36 with value of TRUE if(error != IEC61850_ERROR_NONE) { printf("Write has failed: %i",error); }
Page 23 of 46
6
6.1
A Data object structure. Used to exchange data objects between IEC61850 object and application.
Data Fields Void* pvData unsigned char ucType unsigned int uiBitLength Pointer to data of length equal to uiBitLength bits Type of data. Values can from IEC61850_DataTypes Bit Length of data at pvData (NOTE: This is in Bits! So one octel equal to 8)
A Data object structure. Used to exchange data objects between IEC61850 object and application.
This structure hold the identification of a IEC61850 data object. This is an example structure that matches the PIS10 schema. This can be customised to suit your requirements.
Page 24 of 46
Page 25 of 46
Appendix
7 Appendix
7.1 IEC 61850 Error Codes
enum IEC61850_ErrorCodes Enumerator: IEC61850_ERROR_NONE IEC61850_ERROR_INVALID_PARAMETERS IEC61850_ERROR_NO_MEMORY IEC61850_ERROR_SCL_FILE_OPEN_FAILED IEC61850_ERROR_SERVICE_FAILED IEC61850_ERROR_SCL_SYNTAX_ERROR SCL IEC61850_ERROR_SCL_IO_ERROR SCL IEC61850_ERROR_SCL_NO_IED_CONNECTEDAP IEC61850_ERROR_TYPE_MISMATCH 0 -1 -2 -3 -4 -5 -6 -7 -8 Everything was ok Supplied parameters are invalided Allocation of memory has failed Provided SCL file failed to load Service failed to start File Failed to parse due to syntax error File Failed to parse due IO error Cant find a matching Connected AP for this IED The Type you are trying to write/update does not match the type in the server/client The licence file is not valid or present The given Object ID was not found in the loaded SCL file There is no ready connection to given Object ID LN Type specified in the LN element was not found in the data template The Dataset specified in a the control block was not found The GSE Communication access point specified in a the control block was not found The Sampled Value Communication access point specified in a the control block was not found The SCL contains a Invalid MAC address Service failed to initialise Sampled Value Service failed to initialise Unable to create a service access point for the MMS server Missing or invalid Data type name in Data Type Template Missing or invalid Data type ID in Data Type Template Missing or invalid Data set Name Missing or Invalid IED element name (e.g. name attribute for IED, LD, LN, DOI, SDI or DAI)
IEC61850_ERROR_SCL_DATASET_NOT_FOUND IEC61850_ERROR_SCL_GSE_COMM_NOT_FOUND
-13 -14
IEC61850_ERROR_SCL_SV_COMM_NOT_FOUND
-15
Page 26 of 46
IEC 61850 Protocol API User Manual IEC61850_ERROR_SCL_COMM_NAME IEC61850_ERROR_INVALID_STATE -24 -25
Appendix
Missing or Invalid Communication element name The function cannot be performed while the client/server object is in the current state
enum IEC61850_CallbackReturnServiceErrorCodes Enumerator: IEC61850_CB_ERROR_NONE IEC61850_CB_ERROR_INSTANCE_NOT_AVAILABLE 0 -1 Everything when OK Action failed due to instance being not available Action failed due to access violation Action failed due to inconsistent parameter value Action failed due to data locked by other client Action failed data type conflict Action failed due to server constraint
IEC61850_CB_ERROR_ACCESS_VIOLATION IEC61850_CB_ERROR_PARAMETER_VALUE_INCONSISTENT
-2 -3
-4 -5 -6
Page 27 of 46
Appendix
Page 28 of 46
Appendix
7.3 Examples
7.3.1 Server Source
/****************************************************** This is 61850 Demo Souce Code The DIP Switch and LED's are used as Inputs and Outputs Please refer to power point presentation "61850 ICD Editor DK61.pps" To run SV61850.EXE <FILENAME.ICD> e.g DK61.ICD ******************************************************/ #include <clib.h> #include <stdio.h> #include <mem.h> /* Only SystemCORP Generic is supported in the protcol */ #define SUPPORTED_PROTOCOL IEC61850_SYSTEMCORP_GENERIC /* Include IEC 61850 API */ #include "IEC61850API.h" //#define DEBUG_SV61850 1 /* Maximum Object types */ #define OBJECT_TYPES
/* Total Objects in each object type */ #define OBJECTS 8 /* SC143 Input Output Address Location */ #define IO_ADDR 0xC00 /* Input Output Handler Task Priority */ #define IOHANDLER_PRIO 120 /* Input Output Handler Task Stack Size */ #define TASK_STACKSIZE 1024 /* Object Types */ enum { DIGITAL_INPUT DIGITAL_OUTPUT }eObjectTypes; enum { DIGINPUT_INDEX DIGOUTPUT_INDEX }eObjectIndex; /* Object Information enum { VALUE_INDEX QUALITY_INDEX TIME_STAMP_INDEX }eObjectInfoIndex; /* NTP Time Stamp */ typedef struct { unsigned long int unsigned long int }tNTPTimeStamp;
= 1, = 2,
= 0, = 1, Index */ = 1, = 2, = 3,
Page 29 of 46
Appendix
/* Objects */ typedef struct tag_DK61Object { unsigned char unsigned char unsigned char unsigned short int tNTPTimeStamp }tDK61Object; /* Full Quality */ typedef struct tag_FullQuality { unsigned char unsigned char unsigned char unsigned char unsigned char }tFullQuality;
/* /* /* /* /*
Object Number */ Object Type */ Object Value */ Object Quality */ Obect Time */
/* /* /* /* /*
/* Local Database */ tDK61Object atObj[OBJECT_TYPES][OBJECTS]; /* IO Handler Task Stack */ static unsigned int IOHandler_stack[TASK_STACKSIZE]; /* IO Handler Function */ void huge IOHandler(void); /* Read Callback function */ int MyReadFunction(IEC61850_ObjectID * ptObjectID, IEC61850_ObjectData * ptReturnedValue); /* Write Callback function */ int MyWriteFunction(IEC61850_ObjectID * ptObjectID, const IEC61850_ObjectData * ptNewValue); /* Create Local Database */ void CreateLocalDatabase(void); /* Function to convert time to 61850 Time */ void ConvertTo61850Time(tNTPTimeStamp *ptObjectTime); /* IO Handler Task Definition Block */ static TaskDefBlock IOHandlerTask = { IOHandler, {'I','O','H','L'}, &IOHandler_stack[TASK_STACKSIZE], TASK_STACKSIZE*sizeof(int), 0, IOHANDLER_PRIO, 0, 0,0,0,0 }; /* IEC61850 Server */ IEC61850 myServer /* Main Function */ int main(int argc, char *argv[]) { IEC61850_Parameters int int TimeDate_Structure tServerParam error taskID tTimeDate = = = = {0}; IEC61850_ERROR_NONE; -1; {0}; // Server Parameters // Error // Task ID
// // // // // // //
a name: 4 chars top of stack size of stack attributes, not supported now priority 20(high) ... 127(low) time slice (if any), not supported now mailbox depth, not supported now
= 0;
Page 30 of 46
Appendix
This is a Server Assign Read Callback function Assign Write Callback function No Update callback for Server
printf("\r\n Server Start"); error = IEC61850_Start(myServer); // Starts myServer if(error != IEC61850_ERROR_NONE) { printf(" Failed : %i",error); break; } }while(0); /* Dummy while loop to avoid nested If's */ /* Create Local Database */ CreateLocalDatabase(); /* Check for Any Error */ if(error == IEC61850_ERROR_NONE) { /* Create and Start IO Handler Task */ error = RTX_Create_Task(&taskID , &IOHandlerTask); if(error != 0) { printf("\r\n IO Handler task Create Failed : %i", error); } /* Do not Exit */ while(1) { RTX_Sleep_Time(30000); } } else { /* If any errors in Create and Starting the Server */
Page 31 of 46
Appendix
/* For all Object Types */ for(ucObjTypeCnt = 0; ucObjTypeCnt < OBJECT_TYPES; ucObjTypeCnt++) { Object.uiField2 = ucObjTypeCnt + 1; // Object Type /* Each Object within Object Type */ for(ucObjects = 0; ucObjects < OBJECTS; { /* Assign Object Number */ atObj[ucObjTypeCnt][ucObjects].ucObjectNo /* Assign Object Type DIP Switch : 1 , LED : 2 */ atObj[ucObjTypeCnt][ucObjects].ucObjectType Object.uiField1 = ucObjects + 1; = ucObjTypeCnt + 1; = ucObjects + 1; // Object Number ucObjects++)
/* Initialise Value to 0 */ atObj[ucObjTypeCnt][ucObjects].ucObjectValue = 0; Object.uiField3 = VALUE_INDEX; UpdateValue.pvData = &atObj[ucObjTypeCnt][ucObjects].ucObjectValue; UpdateValue.ucType = IEC61850_DATATYPE_BOOLEAN; UpdateValue.uiBitLength = 8; /* Send Update for Value */ IEC61850_Update(myServer, &Object, &UpdateValue); if(Object.uiField2 == DIGITAL_INPUT) { /* Initialise Quality */ atObj[ucObjTypeCnt][ucObjects].usiObjectQuality = (IEC61850_QUALITY_FAILURE | IEC61850_QUALITY_INVALID | IEC61850_QUALITY_OLDDATA | IEC61850_QUALITY_QUESTIONABLE ); Object.uiField3 UpdateValue.pvData UpdateValue.ucType UpdateValue.uiBitLength = = = = QUALITY_INDEX; &atObj[ucObjTypeCnt][ucObjects].usiObjectQuality; IEC61850_DATATYPE_QUALITY; IEC61850_QUALITY_BITSIZE;
/* Send Update for Quality */ IEC61850_Update(myServer, &Object, &UpdateValue); /* Initialise Time */ ConvertTo61850Time(&atObj[ucObjTypeCnt][ucObjects].tObjectTime); Object.uiField3 = TIME_STAMP_INDEX; UpdateValue.pvData = &atObj[ucObjTypeCnt][ucObjects].tObjectTime; UpdateValue.ucType = IEC61850_DATATYPE_TIMESTAMP; UpdateValue.uiBitLength = IEC61850_TIMESTAMP_BITSIZE; /* Send Update for Time Stamp */ IEC61850_Update(myServer, &Object, &UpdateValue);
Page 32 of 46
Appendix
/* Read Callback Function */ int MyReadFunction(IEC61850_ObjectID * ptObjectID, IEC61850_ObjectData * ptReturnedValue) { unsigned char ucObjects = 0; unsigned char ucFound = 0; /* Each Object within Object type */ for(ucObjects = 0; ucObjects < OBJECTS; ucObjects++) { /* Check if the Field matches */ if((ptObjectID->uiField1 == atObj[DIGINPUT_INDEX][ucObjects].ucObjectNo) && ((ptObjectID->uiField2 == atObj[DIGINPUT_INDEX][ucObjects].ucObjectType))) { if(ptObjectID->uiField3 == VALUE_INDEX) { /* Return Value */ memcpy(ptReturnedValue->pvData, &atObj[DIGINPUT_INDEX][ucObjects].ucObjectValue,(ptReturnedValue->uiBitLength/8)); ucFound = 1; } if(ucFound) break; if(ptObjectID->uiField3 == QUALITY_INDEX) { /* Return Value */ memcpy(ptReturnedValue->pvData, &atObj[DIGINPUT_INDEX][ucObjects].usiObjectQuality,2); ucFound = 1; } if(ucFound) break; if(ptObjectID->uiField3 == TIME_STAMP_INDEX) { /* Return Value */ memcpy(ptReturnedValue->pvData, &atObj[DIGINPUT_INDEX][ucObjects].tObjectTime,(IEC61850_TIMESTAMP_BITSIZE/8)); ucFound = 1; } if(ucFound) break; } if(ucFound) break; } return (0); }
/* Write Function */ int MyWriteFunction(IEC61850_ObjectID * ptObjectID, const IEC61850_ObjectData * ptNewValue) { // static unsigned char ucPrevLED = 0; unsigned char ucLED = 0; unsigned char ucObjects = 0; unsigned char blLEDChange = 0; unsigned char ucFound = 0; /* Each Object within Object type */ for(ucObjects = 0; ucObjects < OBJECTS; {
ucObjects++)
Page 33 of 46
Appendix
/* Check if the Field matches */ if((ptObjectID->uiField1 == atObj[DIGOUTPUT_INDEX][ucObjects].ucObjectNo) && ((ptObjectID->uiField2 == atObj[DIGOUTPUT_INDEX][ucObjects].ucObjectType))) { if(ptObjectID->uiField3 == VALUE_INDEX) { /* Get the Value of the */ memcpy(&ucLED, ptNewValue->pvData, sizeof(unsigned char)); /* Check if the LED has changed */ if(atObj[DIGOUTPUT_INDEX][ucObjects].ucObjectValue != ucLED) { /* Set the Value */ atObj[DIGOUTPUT_INDEX][ucObjects].ucObjectValue = ucLED; blLEDChange = 1; ucFound = 1; } } } if(ucFound) break; } /* LED Changed */ if(blLEDChange) { ucLED = 0; /* Get all the values of the LED */ for(ucObjects = 0; ucObjects < OBJECTS; ucObjects++) { /* Form Byte to Output */ ucLED = (ucLED | (atObj[DIGOUTPUT_INDEX][ucObjects].ucObjectValue << ucObjects)); } #ifdef DEBUG_SV61850 printf("\r\n Write LED : %X ", ucLED); #endif /* Output the LED */ outportb(IO_ADDR,ucLED); } return(0); } /* IO Handler Task */ void huge IOHandler(void) { unsigned char unsigned char unsigned char IEC61850_ObjectData IEC61850_ObjectID unsigned char unsigned short int tNTPTimeStamp while(1) {
= = = = = = = =
// // // // // // // //
DIP Switch Value Previous DIP Swithc Value Total Objects Value to send on Change ID of the Object Local Object Value Local Quality Local Time Stamp
// Indefinite Loop
/* Read DIP Switch Value */ ucDIPValue = inportb(IO_ADDR); /* If previous value does not match current value */ if(ucPrevDIPValue != ucDIPValue) { #ifdef DEBUG_SV61850 printf("\r\n DIP Value : %X", ucDIPValue); #endif /* Check which swithc has changed */ for(nucObjects = 0; nucObjects < OBJECTS; nucObjects++) { /* Get the Values which have changed */ ucObjectVal = ((ucDIPValue & (1 << nucObjects)) >> nucObjects); if(ucObjectVal != atObj[0][nucObjects].ucObjectValue) { #ifdef DEBUG_SV61850
Page 34 of 46
Appendix
atObj[0][nucObjects].ucObjectNo, ucObjectVal); // Object Number // Object Type
= &ucObjectVal; = IEC61850_DATATYPE_BOOLEAN; = 8;
/* Object Value Index */ Object.uiField3 = VALUE_INDEX; /* Update Value in the database */ atObj[0][nucObjects].ucObjectValue = ucObjectVal;
/* No way to determine if DIP Switch failed so */ usiQuality = 0; UpdateValue.pvData = &usiQuality; UpdateValue.ucType = IEC61850_DATATYPE_QUALITY; UpdateValue.uiBitLength = IEC61850_QUALITY_BITSIZE; Object.uiField3 = QUALITY_INDEX; /* Update Quality in the database */ atObj[0][nucObjects].usiObjectQuality = usiQuality;
/* Send Update for Quality */ IEC61850_Update(myServer, &Object, &UpdateValue); /* Send Time */ /* Convert to 61850 Time */ ConvertTo61850Time(&tNTPTime); UpdateValue.pvData = &tNTPTime; UpdateValue.ucType = IEC61850_DATATYPE_TIMESTAMP; UpdateValue.uiBitLength = IEC61850_TIMESTAMP_BITSIZE; Object.uiField3 = TIME_STAMP_INDEX; /* Update Time in the database */ memcpy(&atObj[0][nucObjects].tObjectTime, &tNTPTime, sizeof(tNTPTimeStamp)); /* Send Update for Time Stamp */ IEC61850_Update(myServer, &Object, &UpdateValue); } } ucPrevDIPValue = } RTX_Sleep_Time(1000); } } /* Convert to 61850 Time */ void ConvertTo61850Time(tNTPTimeStamp *ptObjectTime) { TimeDate_Structure tTimeDate = {0}; struct time tTime = {0}; struct date tDate = {0}; unsigned long int uliDigit = 0; unsigned long int uliMicrosec = 0; RTX_Get_TimeDate (&tTimeDate); tTime.ti_hour tTime.ti_min tTime.ti_sec tDate.da_day tDate.da_mon tDate.da_year = tTimeDate.hr; = tTimeDate.min; = tTimeDate.sec; = tTimeDate.dy; = tTimeDate.mn; = tTimeDate.yr + 2000; ucDIPValue;
Page 35 of 46
Appendix
//Load Seconds since 1 Jan 1900 ptObjectTime->uliSeconds = dostounix(&tDate, &tTime) - 18000; // Calculate Number of second ptObjectTime->uliFractionsOfSecond = 0; for(uliDigit = 0x80000000L; uliDigit > 0; uliDigit = uliDigit /2) // Loop down throught 2^-1 to 2^-16 { uliMicrosec = uliMicrosec * 2; if(uliMicrosec >= 1000000L) { ptObjectTime->uliFractionsOfSecond } } ptObjectTime->uliFractionsOfSecond = (ptObjectTime->uliFractionsOfSecond & 0xFFFFFF00L) | IEC61850_TIMEQUALITY_ACCURACY_UNSPECIFIED | IEC61850_TIMEQUALITY_LEAP_SECOND_KNOWN; // Set Time accurcy and Leap Second Known } // Check for a muilt of fraction
7.3.2
<?xml version="1.0" encoding="UTF-8"?> <SCL xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns="http://www.iec.ch/61850/2003/SCL"> <Header id="" version="3"/> <Communication> <SubNetwork name="SubNetworkName"> <ConnectedAP iedName="DK61" apName="SubstationRing1"> <Address> <P type="OSI-AP-Title">1,1,9999,1</P> <P type="OSI-AE-Qualifier">12</P> <P type="OSI-PSEL">00000001</P> <P type="OSI-SSEL">0001</P> <P type="OSI-TSEL">0001</P> <P type="IP">192.168.1.124</P> <P type="IP-SUBNET">255.255.255.0</P> <P type="IP-GATEWAY">192.168.1.1</P> </Address> <GSE ldInst="LDevice1" cbName="GSE_CB_GOOSE"> <Address> <P type="MAC-Address">01-0C-CD-01-00-00</P> <P type="VLAN-PRIORITY">4</P> <P type="VLAN-ID">0</P> <P type="APPID">0</P> </Address> </GSE> </ConnectedAP> </SubNetwork> </Communication> <IED type="RTUType" manufacturer="SystemCORP Pty Ltd" configVersion="1.0" name="DK61"> <Services/> <AccessPoint name="SubstationRing1"> <Server timeout="30"> <Authentication/> <LDevice inst="LDevice1" desc=""> <LN0 lnClass="LLN0" inst="" lnType="LLN0_0"> <DataSet name="Indicate_DataSet"> <FCDA ldInst="LDevice1" prefix="DIPS_" lnClass="GGIO" lnInst="1" doName="Ind1" fc="ST"/> <FCDA ldInst="LDevice1" prefix="DIPS_" lnClass="GGIO" lnInst="1" doName="Ind2" fc="ST"/> <FCDA ldInst="LDevice1" prefix="DIPS_" lnClass="GGIO" lnInst="1" doName="Ind3" fc="ST"/> <FCDA ldInst="LDevice1" prefix="DIPS_" lnClass="GGIO" lnInst="1" doName="Ind4" fc="ST"/> </DataSet> <DataSet name="Goose_Alarm_DataSet"> <FCDA ldInst="LDevice1" prefix="DIPS_" lnClass="GGIO" lnInst="2" doName="Alm5" daName="stVal" fc="ST"/> <FCDA ldInst="LDevice1" prefix="DIPS_" lnClass="GGIO" lnInst="2" doName="Alm5" daName="q" fc="ST"/>
Page 36 of 46
Appendix
<FCDA ldInst="LDevice1" prefix="DIPS_" lnClass="GGIO" lnInst="2" doName="Alm5"
daName="t" fc="ST"/> <FCDA ldInst="LDevice1" prefix="DIPS_" lnClass="GGIO" lnInst="2" doName="Alm6" daName="stVal" fc="ST"/> <FCDA ldInst="LDevice1" prefix="DIPS_" lnClass="GGIO" lnInst="2" doName="Alm6" daName="q" fc="ST"/> <FCDA ldInst="LDevice1" prefix="DIPS_" lnClass="GGIO" lnInst="2" doName="Alm6" daName="t" fc="ST"/> <FCDA ldInst="LDevice1" prefix="DIPS_" lnClass="GGIO" lnInst="2" doName="Alm7" daName="stVal" fc="ST"/> <FCDA ldInst="LDevice1" prefix="DIPS_" lnClass="GGIO" lnInst="2" doName="Alm7" daName="q" fc="ST"/> <FCDA ldInst="LDevice1" prefix="DIPS_" lnClass="GGIO" lnInst="2" doName="Alm7" daName="t" fc="ST"/> <FCDA ldInst="LDevice1" prefix="DIPS_" lnClass="GGIO" lnInst="2" doName="Alm8" daName="stVal" fc="ST"/> <FCDA ldInst="LDevice1" prefix="DIPS_" lnClass="GGIO" lnInst="2" doName="Alm8" daName="q" fc="ST"/> <FCDA ldInst="LDevice1" prefix="DIPS_" lnClass="GGIO" lnInst="2" doName="Alm8" daName="t" fc="ST"/> </DataSet> <ReportControl rptID="MyRepURCB_ID" confRev="0" datSet="Indicate_DataSet" name="UNBUFFERED_RCB" desc="Unbuf RCB"> <TrgOps dchg="true" qchg="true" dupd="true"/> <OptFields seqNum="true" timeStamp="true" dataSet="true" reasonCode="true" entryID="true" configRef="true"/> </ReportControl> <GSEControl type="GOOSE" appID="GSE_CB_ID" confRev="0" datSet="Goose_Alarm_DataSet" name="GSE_CB_GOOSE" desc="For GOOSE"/> </LN0> <LN lnClass="GGIO" inst="1" prefix="DIPS_" lnType="GGIO_0"> <DOI name="Ind1"> <DAI name="stVal"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="1" Field2="1" Field3="1" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> <DAI name="q"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="1" Field2="1" Field3="2" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> <DAI name="t"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="1" Field2="1" Field3="3" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> </DOI> <DOI name="Ind2"> <DAI name="stVal"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="2" Field2="1" Field3="1" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> <DAI name="q"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="2" Field2="1" Field3="2" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> <DAI name="t"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="2" Field2="1" Field3="3" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> </DOI> <DOI name="Ind3"> <DAI name="stVal"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="3" Field2="1" Field3="1" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> <DAI name="q"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="3" Field2="1" Field3="2" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI>
Page 37 of 46
Appendix
<DAI name="t"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="3" Field2="1" Field3="3" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> </DOI> <DOI name="Ind4"> <DAI name="stVal"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="4" Field2="1" Field3="1" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> <DAI name="q"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="4" Field2="1" Field3="2" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> <DAI name="t"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="4" Field2="1" Field3="3" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> </DOI> </LN> <LN lnClass="GGIO" inst="2" prefix="DIPS_" lnType="GGIO_10"> <DOI name="Alm5"> <DAI name="stVal"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="5" Field2="1" Field3="1" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> <DAI name="q"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="5" Field2="1" Field3="2" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> <DAI name="t"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="5" Field2="1" Field3="3" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> </DOI> <DOI name="Alm6"> <DAI name="stVal"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="6" Field2="1" Field3="1" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> <DAI name="q"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="6" Field2="1" Field3="2" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> <DAI name="t"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="6" Field2="1" Field3="3" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> </DOI> <DOI name="Alm7"> <DAI name="stVal"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="7" Field2="1" Field3="1" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> <DAI name="q"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="7" Field2="1" Field3="2" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> <DAI name="t"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="7" Field2="1" Field3="3" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> </DOI>
Page 38 of 46
Appendix
<DOI name="Alm8"> <DAI name="stVal"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="8" Field2="1" Field3="1" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> <DAI name="q"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="8" Field2="1" Field3="2" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> <DAI name="t"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="8" Field2="1" Field3="3" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> </DOI> </LN> <LN lnClass="GGIO" inst="3" prefix="LEDO_" lnType="GGIO_17"> <DOI name="SPCSO1"> <SDI name="Oper"> <DAI name="ctlVal"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="1" Field2="2" Field3="1" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> </SDI> <DAI name="ctlModel" valKind="Set"> <Val>direct-with-normal-security</Val> </DAI> </DOI> <DOI name="SPCSO2"> <SDI name="Oper"> <DAI name="ctlVal"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="2" Field2="2" Field3="1" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> </SDI> <DAI name="ctlModel" valKind="Set"> <Val>direct-with-normal-security</Val> </DAI> </DOI> <DOI name="SPCSO3"> <SDI name="Oper"> <DAI name="ctlVal"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="3" Field2="2" Field3="1" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> </SDI> <DAI name="ctlModel" valKind="Set"> <Val>direct-with-normal-security</Val> </DAI> </DOI> <DOI name="SPCSO4"> <SDI name="Oper"> <DAI name="ctlVal"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="4" Field2="2" Field3="1" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> </SDI> <DAI name="ctlModel" valKind="Set"> <Val>direct-with-normal-security</Val> </DAI> </DOI> <DOI name="SPCSO5"> <SDI name="Oper"> <DAI name="ctlVal"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="5" Field2="2" Field3="1" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> </SDI> <DAI name="ctlModel" valKind="Set">
Page 39 of 46
Appendix
<Val>direct-with-normal-security</Val> </DAI> </DOI> <DOI name="SPCSO6"> <SDI name="Oper"> <DAI name="ctlVal"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="6" Field2="2" Field3="1" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> </SDI> <DAI name="ctlModel" valKind="Set"> <Val>direct-with-normal-security</Val> </DAI> </DOI> <DOI name="SPCSO7"> <SDI name="Oper"> <DAI name="ctlVal"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="7" Field2="2" Field3="1" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> </SDI> <DAI name="ctlModel" valKind="Set"> <Val>direct-with-normal-security</Val> </DAI> </DOI> <DOI name="SPCSO8"> <SDI name="Oper"> <DAI name="ctlVal"> <Private type="SystemCorp_Generic"> <SystemCorp_Generic:GenericPrivateObject Field1="8" Field2="2" Field3="1" Field4="0" Field5="0" xmlns:SystemCorp_Generic="http://www.systemcorp.com.au/61850/SCL/Generic"/></Private> </DAI> </SDI> <DAI name="ctlModel" valKind="Set"> <Val>direct-with-normal-security</Val> </DAI> </DOI> </LN> </LDevice> </Server> </AccessPoint> </IED> <DataTypeTemplates> <LNodeType lnClass="LLN0" id="LLN0_0"> <DO name="Mod" type="INC_1"/> <DO name="Beh" type="INS_2"/> <DO name="Health" type="INS_3"/> <DO name="NamPlt" type="LPL_0"/> </LNodeType> <LNodeType lnClass="GGIO" id="GGIO_0"> <DO name="Mod" type="INC_0"/> <DO name="Beh" type="INS_0"/> <DO name="Health" type="INS_1"/> <DO name="NamPlt" type="LPL_1"/> <DO name="Ind1" type="SPS_0"/> <DO name="Ind2" type="SPS_0"/> <DO name="Ind3" type="SPS_0"/> <DO name="Ind4" type="SPS_0"/> </LNodeType> <LNodeType lnClass="GGIO" id="GGIO_1"> <DO name="Mod" type="INC_2"/> <DO name="Beh" type="INS_4"/> <DO name="Health" type="INS_5"/> <DO name="NamPlt" type="LPL_2"/> <DO name="Alm1" type="SPS_1"/> <DO name="Alm2" type="SPS_1"/> <DO name="Alm3" type="SPS_1"/> <DO name="Alm4" type="SPS_1"/> </LNodeType> <LNodeType lnClass="GGIO" id="GGIO_2"> <DO name="Mod" type="INC_2"/> <DO name="Beh" type="INS_4"/> <DO name="Health" type="INS_5"/> <DO name="NamPlt" type="LPL_2"/>
Page 40 of 46
Appendix
Page 41 of 46
Appendix
Page 42 of 46
Appendix
Page 43 of 46
Appendix
Page 44 of 46
Appendix
7.3.3
Client Source
#include "IEC61850API.h" void main() { // Create Client IEC61850 myClient; IEC61850_Parameters tClientParam; int error; tClientParam.ClientServerFlag = IEC61850_CLIENT; tClientParam.ptReadCallback = NULL; tClientParam.ptWriteCallback = NULL; tClientParam.ptUpdateCallback = UpdateFunction; myClient = IEC61850_Create(&tClientParam,&error); //Create a client if(myClient == NULL) { printf("Client Failed to create:%i",error); } error = IEC61850_LoadSCLFile(myClient,"myIDE.scd"); if(error != IEC61850_ERROR_NONE) { printf("Loading error has occured: %i",error); } error = IEC61850_Start(myClient); if(error != IEC61850_ERROR_NONE) { printf("Failed to start client: %i",error); } // Do something else // ... // Read in a value IEC61850_ObjectData Value; IEC61850_ObjectID Object; Unsigned32 u32Counter; // Load Data Value.ucType = IEC61850_DATATYPE_INT32; Value.uiBitLength = sizeof(u32Counter)*8; Value.pvData = &u32Counter; // Load Object ID Object.uiNumber = 43; error = IEC61850_Read(myClient, &Object, &Value); if(error != IEC61850_ERROR_NONE) { printf("error has occured: %i",error); } else { printf("Count = %u",u32Counter); } // Do something else // ... u32Counter = u32Counter/2; // Half the value given and write it back error = IEC61850_Write(myServer, &Object, &Value); if(error != IEC61850_ERROR_NONE) { printf("Write has failed: %i",error); } // Do something else // ... // Shutting down client error = IEC61850_Stop(myClient); if(error != IEC61850_ERROR_NONE) {
Page 45 of 46
Appendix
// Update Function void UpdateFunction(IEC61850_ObjectID * ptObjectID,const IEC61850_ObjectData * ptNewValue) { if(ptNewValue->ucType = IEC61850_DATATYPE_INT32) // I am only interested in 32 bit integers { printf("Update on Object %i with value of %i", ptObjectID-> uiNumber, *(Unsigned32 *)(ptNewValue->pvData)); }
Page 46 of 46