Ondrej Hrstka - 2012-02-21

Overview

plcfw is a simple command-line tool to communicate with Siemens S7 PLC using the fetch-write protocol.
It can be used to do a single query of one data block item, or to process a list of queries to various data blocks.
Refer to Siemens document "FETCH/WRITE service in an S7-300/400 CPU via the integrated Ethernet interface" for details about the protocol specification and configuration on the PLC side.

Operations

In general, the, fetch-write protocol supports 2 basic operations:

  • fetch - read data from PLC memory to a computer
  • write - write data from computer to the PLC memory

Memory access modes

Operations can be performed in 4 memory access modes (also referenced as org_ID):

  • data block communication - reads from the internal PLC data blocks, using standard PLC addressing; size of data to be read is given in bytes
  • bit memory address area - reads from the internal PLC memory; size of data to be read is given in bits
  • process image of inputs - reads from the internal PLC memory block which mirrors the inputs
  • process image of outputs - reads from the internal PLC memory block which mirrors the outputs

Datatypes

On top of that, plcfw utility is able to interpret the data read from the PLC memory as several basis datatypes:

  • bool - interprets one bit of a byte as a boolean value; bit number [0 - 7] is required
  • char/byte - no interpretation, one byte of information is displayed as a number from interval [0 - 255]
  • int - 2 bytes of information are interpreted as integer value [-32768 - 32768]; first byte is the more significant; no recalculation is done
  • numeric - 2 bytes of information are interpreted as integer value [-32768 - 32768]; first byte is the more significant; recalculation using given slope and offset is done
  • float - 4 bytes of information are interpreted as float value while recalculation using given slope and offset is done
  • raw - given number of bytes are displayed as a sequence of numbers from interval [0 - 255]; no interpretation is done

List processing

plcfw utility is also able to process lists of requests. The list is given by a test file. There are 3 levels of intelligence of the list processing:

  • no optimization - each variable is processed as single request; this method is optimal for sparse lists where just few values are requested of each data block. See schema:

Data blocks and variables:

<DB1> ++++A+++B++++++++++++++C+D+E+F
<DB2> ++GHI++++++++++++++JK+LM+++++++++N++++O++
<DB3> ++++++++PQR++STU+++++++++

In this schema, '+' marks stand for variables in the PLC memory which we are not interested in, A-U stand for variables we intent to get.
So, 3 data blocks, 21 variables to read.

In "no optimization mode", there will be a separate request for each of these variables A-U, meaning 21 requests together.

  • concatenated - variables are coupled by blocks, so there is always just one request for a data block. In case of sparse data, a lot of bytes are transfered from the PLC with no use. For the schema above, plcfw will compose 3 request, each for one data block:

    Request 1: (A...B..............C.D.E.F) - reads 26 fields from PLC memory

    Request 2: (GHI.............JK.LM.........N....O) - reads 36 fields from PLC memory

    Request 3: (PQR..STU) - reads 8 fields from PLC memory

  • chunks - variables are coupled by blocks, but then chunks are identified and sparse requests are being divided into chunks so large unused data reading is avoided. For the schema above, plcfw will compose 7 requests, each for a data chunk:

    Request 1: (A...B) - reads 5 fields from PLC memory

    Request 2: (C.D.E.F) - reads 8 fields from PLC memory

    Request 3: (GHI) - reads 3 fields from PLC memory

    Request 4: (JK.LM) - reads 5 fields from PLC memory

    Request 5: (N) - reads 1 field from PLC memory

    Request 6: (O) - reads 1 field from PLC memory

    Request 7: (PQR..STU) - reads 9 fields from PLC memory

Note: chunk length can be specified. In the example above, chunk length is 5, so A and B are combined into one request, but N and O are not.

Usage

Synopsis

 plcfw {-m mode | -L command list filename} [options]  -h <PLC hostname>  -p <PLC port> [more ...]

Options

  • -h, --host address - IP address or hostname of target PLC CPU
  • -p, --port port - port where the PLC responds to fetch-write communication
  • -t, --timeout timeout -- timeout in seconds, default is 10; it is used both for socket connection (socket connection is retried once per second for the period given by this timeout) and a fetch-write request
  • -ot, --operation-timeout timeout - full operation timeout in seconds, used in the fork mode to determine how long the parent (configuration) process waits for the child (operation) process; default is 10 times the basic timeout
  • -y, --no-tcp-nodelay - by default, plcfw uses TCP_NODELAY option on socket connect; this parameter toggles it off (not recommended to use it, though)
  • -f, --fork - works in fork mode, parent process reads configuration while child process connects to PLC and does the processing; this is usable to improve the failure protection for automatic monitoring tools
  • -op, --operation {fetch | write} - operation type, either "fetch" or "write", default is "fetch"
  • -m, --mode {bool | char | int | numeric | float | raw} - mode of interpretation, can be ""bool" ("b", "B"), "char" ("c", "C", "byte"), "int" ("i", "I"), "numeric" ("n", "N"), "float" ("f", "F"), "raw" ("r", "R"), see above for details, default is
    "raw"
  • -i, --org-ID {1 | 2 | 3 | 4} - orig ID number, "1" - data block mode, "2" - bit memory mode, "3" - process image input, "4" - process image output, default is "1"
  • -db, --data-block data-block-number - data block number, only valid with org-ID = 1
  • -sa, --start-address start-address - start address in data block or input/output process image
  • -len, --length bytes - length of data to be read, in words (with data block mode) or bytes (otherwise)
  • -bn, --bit-number bit-number - for "bool" mode, the number of bit inside the byte found at start address
  • -sl, --slope slope - slope for value recalculation, for "numeric" or "float" mode, default is "1.0"; result = offset + slope * obtained_value
  • -off, --offset -offset - offset for value recalculation, for "numeric" or "float" mode, default is "0.0"; result = offset + slope * obtained_value
  • -dtmax, --max-dtframe-size size - maximum DT Frame size, see the protocol specification for details
  • -desc, --description description-string - description of a variable; used only in the text printout of results

List processing options:

  • -L, --list-filename filename - filename of operation list
  • -opt, --opt-level level - optimization level for list processing, 0 - no optimization, 1 - concatenated, 2 - chunks; see above for detailed description
  • -chl, --chunk-length length - for optimization level 2 - 'chunks', this argument gives the chunk length; see above for detailed description

Output and verbosity options:

  • -o, --output filename - filename of output file
  • -v, --verbose - verbosity; operation trace is logged to stdout
  • -D, --dump-packets - dumps fetch-write TCP/IP packets to stdout (every request and every response)
  • -H, --help - prints help to stdout

Return value

Return value is 0 if program completed its operations successfully, either non-zero negative number in case of any failure.

Errors

Typical failure is inability to connect to PLC, or malformed fetch-write request, or invalid PLC memory address. Program sends self-explanatory error messages to stderr.

Examples

Note: these examples assume PLC address 10.1.10.101 and port to fetch-write communication 2002, verbose operation with packet dumping and timeout 2 seconds.

Read 21 bytes of raw data from data block 82, address 0:

plcfw -h 10.1.10.101 -p 2002 -db 82 -sa 0 -len 21 -v -D -t 2 -desc "Raw data from data-block 82"

Read device temperature from data block 82, address 0, where it is stored in 4 bytes digit, interpret it with slope 11.0 and offset 33.0:

plcfw -h 10.1.10.101 -p 2002 -m float -db 82 -sa 0 -sl 11.0 -off 33.0 -v -D -t 2 -desc "Device temperature"

Read boolean value of device status from data block 60, address 8, 4-th bit (counted from 0):

plcfw -h 10.1.10.101 -p 2002 -m bool -db 60 -sa 8 -bn 4 -v -D -t 2 -desc "Device status"

Read boolean value of device current from data block 80, address 4, where it is stored as 2 bytes digit, interpret it with slope 1.0 and offset 0.0 (defaults):

plcfw -h 10.1.10.101 -p 2002 -m numeric -db 80 -sa 4 -v -D -t 2 -desc "Device current"

Read all these 4 using a command list file watch.cmd:

plcfw -h 10.1.10.101 -p 2002 -L watch.cmd -t 2

Where file "watch.cmd" contains this:

FETCH -m raw -db 82 -sa 0 -len 21 -desc "Raw data from data-block 82"           
FETCH -m float -db 82 -sa 0 -sl 11.0 -off 33.0 -desc "Device temperature"           
FETCH -m bool -db 60 -sa 8 -bn 4 -desc "Device status"   
FETCH -m numeric -db 80 -sa 4 -desc "Device current"
 

Last edit: Ondrej Hrstka 2012-02-21