Tutorial S7-1200/1500 via OPC UA

PLC-Lab can access via OPC UA a Siemens S7-1200/1500 or PLCSIM Advanced configured as OPC UA server. For this, some prerequisites must be given in the TIA project.

PLC-Lab supports the device OPC UA as of version


OPC UA is primarily present in PLC-Lab to access CodeSys V3 controllers. Since the current Siemens CPUs of the S7-1200/1500 series can also be configured as OPC UA servers, they can also be accessed via OPC UA.

The following steps are necessary in the TIA project so that PLC-Lab can access the S7 controller via OPC UA

  • Create the DB "PlcLabConnector" with the following content:
DATA_BLOCK "PlcLabConnector"
{ S7_Optimized_Access := 'TRUE' }
      SIZE_AREA_I_ARRAY : Int;
      SIZE_AREA_Q_ARRAY : Int;
      SIZE_I_ARRAY : Int;
      SIZE_Q_ARRAY : Int;
      Inputs : Array[0..1023] of Byte;
      Outputs : Array[0..1023] of Byte;
      AreaInputs : Array[0..9] of Struct
         CntBytes : Word;
         Addr : Word;
         IoOfs : Word;
      AreaOutputs : Array[0..9] of Struct
         CntBytes : Word;
         Addr : Word;
         IoOfs : Word;

   SIZE_I_ARRAY := 1024;
   SIZE_Q_ARRAY := 1024;
  • Create the function "PlcLabOpcUaSync" with the following content:
FUNCTION "PlcLabOpcUaSync" : Void
{ S7_Optimized_Access := 'TRUE' }
      Inputs : Bool;
      Outputs : Bool;

      a : Int;
      b : Int;
      value : Byte;

    IF #Inputs THEN
        //Write sensor data of PLC-Lab to the PLC Inputs
        FOR #a := 0 TO  "PlcLabConnector".SIZE_AREA_I_ARRAY-1 DO
            IF "PlcLabConnector".AreaInputs[#a].CntBytes = 0 THEN //nothing to do anymore
            FOR #b := 0 TO WORD_TO_INT("PlcLabConnector".AreaInputs[#a].CntBytes) DO
                //BytePtr["PlcLabConnector".AreaInputs[#a].IoOfs + #b] := "PlcLabConnector".Inputs["PlcLabConnector".AreaInputs[#a].Addr + #b];
                #value := "PlcLabConnector".Inputs[ WORD_TO_INT("PlcLabConnector".AreaInputs[#a].Addr) + #b];
                POKE(area := 16#81,
                     dbNumber := 0,
                     byteOffset := WORD_TO_INT("PlcLabConnector".AreaInputs[#a].IoOfs) + #b,
                     value := #value);

    IF #Outputs THEN
        //Write PLC outputs to the PLC-Lab outputs
        FOR #a := 0 TO "PlcLabConnector".SIZE_AREA_Q_ARRAY-1 DO
            IF "PlcLabConnector".AreaOutputs[#a].CntBytes = 0 THEN //nothing to do anymore 
            FOR #b := 0 TO WORD_TO_INT("PlcLabConnector".AreaOutputs[#a].CntBytes) DO
                //read the output-byte
                #value := PEEK(area := 16#82,
                               dbNumber := 0,
                               byteOffset :=  WORD_TO_INT("PlcLabConnector".AreaOutputs[#a].IoOfs) + #b);
                //write into the PLC-Lab data
                "PlcLabConnector".Outputs[ WORD_TO_INT("PlcLabConnector".AreaOutputs[#a].Addr) + #b] := #value;
  • Calling the function "PlcLabOpcUaSync" inside the network 1 of the OB1.

  • Activation of the OPC UA Server inside the properties of the S7 CPU.

  • Selecting the necessary OPC UA runtime-license inside the properties of the S7 CPU.


The code snippet of the DB "PlcLabConnector" can be saved in the file "PlcLabConnector.db" using a text editor. The code snippet of the "PlcLabOpcUaSync" function must be stored in a file named "PlcLabOpcUaSync.scl". The two files can be inserted in an existing TIA project in the "External source files" node. Then generate the blocks using the context menu and the menu item "Generate blocks from source". This is also shown in the following example.

Start of the TIA portal from Siemens and configuration of the PLC

In the first step, a new project is created in the Siemens TIA Portal, an existing project can also be opened. In the example a new project is created and a CPU 1511 (i.e. a S7-1500) is set as CPU.

The used CPU with firmware version 2.6 has the required OPC UA functionality. The CPU is inserted by pressing the "Add" button.

After switching to the project view, an input module (DI) and an output module (DQ) are added to the CPU. In the example, two inputs and one output are to be used, so one DI16 and DQ16 module is sufficient.

Both modules have the start address 0 and thus address the input bytes IB0 and IB1 as well as QB0 and QB1.

Configuration of the OPC UA functionality of the CPU

Since PLC-Lab shall access the S7-CPU via OPC UA, the S7-CPU has to be configured as OPC UA server. To do this, double-click on the CPU to display the properties of the CPU. Within the node "OPC UA" select the node "Server" and choose the option "Activate OPC UA-Server".

Now the node "Runtime licenses" is selected and in the section "OPC UA" the license required for the CPU is selected. In the example the license marked "small" is required for the CPU 1511.

Now the configuration of the CPU is complete.

Import of the code snippets as external sources

The next step is to insert the DB "PlcLabConnector" and the function "PlcLabOpcUaSync" into the project. To do this, the above code snippet of the DB is first copied to the clipboard, copied to a text editor (e.g. the Windows editor) and then saved in the file with the name "PlcLabConnector.db". The same procedure for the function then follows. Again, the code snippet is copied to the clipboard, pasted into an editor and then saved in the file with the name "PlcLabOpcUaSync.scl".

In the TIA project, select the "External source files" node and double-click the "Add New External File" item.

As a result, the file selection dialog appears where the two previously created files can be selected and added.

Now you can generate the blocks from these two files. First select both sources and bring up the context menu. In the context menu the menu item "Generate blocks from source" is executed.

After that the DB "PlcLabConnector" and the function "PlcLabOpcUaSync" are available within the program blocks.

The numbers of the blocks can differ from project to project. It is important that the DB has the designation "PlcLabConnector " and the function is designated "PlcLabOpcUaSync".

Calling the function "PlcLabOpcUaSync" in network 1 of OB1

Finally, the function "PlcLabOpcUaSync" in network 1 of OB1 must be called up. Then all requirements for the communication between PLC-Lab and the PLC via OPC UA are fulfilled. The call can be seen in the figure. The display type FBD was set in OB1. The display type is not relevant.

Both inputs of the function are set to the constant "true".

The PLC program for this example inside the OB1

Since all requirements for the communication between PLC-Lab and the S7-CPU via OPC UA are available, the PLC program for the small example can now be created in network 2 of OB1.

Here, input I0.0 "Start" is to set output Q0.0 "LampStart". Resetting is performed via the negated input I0.1 "Stop". The S/R flip-flop and its assignment is shown below.

Transferring the PLC program and configuration to the S7 PLC

Now the PLC can be connected to the PC and the PLC program and configuration can be transferred. If the PLCSIM Advanced is used, it is started and the "PLCSIM Virtual Eth. Adapter" is set as "Online Access".

If PLCSIM Advanced is used, make sure that the option "Support simulation during block compilation" is selected in the "Protection" section of the project properties.

Starting PLC-Lab and creating the new OPC UA-device

Now PLC-Lab is started and a new project is created. The next step is to create the OPC UA device with the data for communication. For this purpose, the button shown below is clicked in the symbol table.

The dialog "Create new device or connection" is displayed. Select "OPC UA" as device type and enter a name for the device.

After confirmation, another dialog appears where the connection settings are to be made. Among other things, the IP address of the S7-CPU to be addressed, the port address and the polling rate for reading in milliseconds must be set here.


The IP address of the OPC UA server to be addressed, in the example the IP address of the CPU.


By default, the port address 4840 is specified here. This only needs to be changed if a different port address is set in the OPC UA Server.

Poll rate reading operands

The polling rate in milliseconds indicates how often the status of operands is read from the PLC. In the example the value 50ms is set.

Name of container-variable

The variable name of the container on the PLC side is permanently set to the name "PlcLabConnector". For this reason it was also important that the data block in the TIA project has this name. From this container, the data of PLC-Lab are read or written into it.

Address mode

Since the example communicates with a S7-PLC, the "Address mode for S7-systems from Siemens" must be set as the addressing type. Otherwise the access to the operands or their values will not be correct. Especially for word and double word operands. After creating the device, this cannot be changed anymore.

Below is the setting of the dialog for the example.

Click "OK" to accept the settings and close the dialog.

Creating the symbols of the operands

Three operands are required for the example. The symbols are to be created in the symbol table for these operands. First the device has to be selected, in the example the device "OpcUaS7".

Afterwards, the symbols can be inserted using the button with the plus symbol.

The creating of the symbols is shown below.

Creating the first switch-object

For the example, two switch objects are required, which are to be configured as pushbuttons. The two are taken from the section "Switches"->"Switches not illuminated". First the first switch object.

After the switch has been placed, its properties can be seen within the table with the properties of the objects. In the example, the operand to which the switch object is connected is to be specified first. This is influenced when the switch is activated. There are several possibilities for specifying the operand:

First option "Autocompletion": In the first option, in the cell for the operand, the device name followed by a period is specified first; in the example, this is "OpcUaS7.". Then use the key combination Ctrl + Space. As a result, all symbols of this device are now displayed in a list. Select the symbol you want to use with the cursor keys (../up or down) and confirm with the return key. The selected symbol is then entered as an operand. These steps are shown below:

Second option "drag & drop": With the second option, you select the line of the operand in the symbol table and then drop it on the description of the operand property or the properties editor using drag & drop.

Third option "drag & drop" to the switch object: Now for the third option. In this case, you also select the operand from the symbol table and then drag and drop it. But here the target is the switch. This means that the operand is dropped directly on the object. For switch objects, the operand you have inserted is automatically inserted as the operand that is affected by the switch.


The advantage of the options 2 and 3 is that the symbol of the operand is automatically used to label the switch object.

When you have used one of the options, the switch is connected to the symbol "Start" and thus to the I0.0. Now the switch object must be defined as a push-button. Furthermore, "Start" should appear as text with a font size of "12" in the switch object. The properties required for this are shown below:

Drawing the second push-button

Now we move on to the second switch object that we need. We want to create this switch from a copy of the first switch. Select the first switch and press Ctrl + D. A copy of the selected switch is then placed next to the source object.

To display the properties of the new switch in the table, click on a free space in the draw-window and then select the new switch with the mouse. Now the properties are displayed and can be changed.

Since the button is to be set as an opener, the property "Button is an opener" is selected.

In the next step you have to adjust the operand of the switch. This is supposed to be the "Stop" push-button. We will do this using the third option described above. The operand with the symbol "Stop" in the symbol table is dropped over the switch object using drag & drop.

This action also changes the label because the symbol of the new operand is used as the label of the switch object.

Drawing a lamp

Finally, we need a lamp object to signal the "Start" state. For this purpose, select a green indicator light in the object selection "Lamps->Indicator lights".

The lamp can then be placed on the drawing board.

In the next step, assign the operand with the symbol "Lamp" to the object. This is also done via drag & drop on the object.

Now you have set the operand as a lamp operand. You can remove the caption from the lamp.

This means that no more text is displayed in the object.

After these actions, the drawing board looks as follows:

The PLC-Lab project is now complete.

Start der Simulation

Since the S7-PLC is already connected and is in the operating mode "run", the simulation can also be started in PLC-Lab. For this purpose, the following button is pressed in PLC-Lab:

PLC-Lab then tries to establish the connection via OPC UA. Once the connection has been established, the display in the lower area of PLC-Lab changes as follows:

Testing the PLC program

In the next step the buttons in PLC-Lab can be pressed and the reaction of the PLC program can be observed. In the following picture the start button was pressed. As a result, output Q0.0 is set to status 1 and the lamp lights up.

In this way, even more extensive PLC programs can be tested by operating the system in PLC-Lab and observing the effects in the programming tool.


The example was used to show how a TIA-project can be supplemented so that PLC-Lab can access the S7-PLC to be programmed via OPC UA, thus enabling simulation via a virtual system in PLC-Lab.