GithubHelp home page GithubHelp logo

rtlabs-com / p-net Goto Github PK

View Code? Open in Web Editor NEW
442.0 36.0 190.0 6.04 MB

PROFINET device stack for embedded devices

Home Page: http://www.rt-labs.com

License: Other

CMake 1.32% C 84.98% C++ 13.34% Shell 0.36%
profinet fieldbus communication-protocol industrial-automation c

p-net's Introduction

Evaluation version

This repository contains an evaluation version of P-Net, a P-Net stack for Profinet Device implementations. It is especially well suited for embedded systems where resources are limited and efficiency is crucial. It is written in C and can be run on an RTOS such as rt-kernel, FreeRTOS, or on Linux.

It does not contain any ports and cannot be built without adding additional sources.

See readme for more information on the complete version of the stack and the releases for binary downloads for common targets.

This version of P-Net can be used for evaluation purposes only. Contact [email protected] if you intend to use this stack in a product or if you need assistance during evaluation. The commercial version of this stack is supplied with full sources.

p-net's People

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

p-net's Issues

Wrong read response for I&M0Filterdata (=index 0xF840)

This needs implementation

See pf_put_im_0_filter_data()

Maybe the DAP module should be plugged automatically?

See 7.3.2.3 in "Application Layer services for decentralized periphery"

Found with Automated RT Tester :

  • BEHAVIOR_SCENARIO_1
  • BEHAVIOR_SCENARIO_2
  • BEHAVIOR_SCENARIO_10 (runs fast)
  • MANUAL_BEHAVIOR_RESET_TO_FACTORY
  • AR_ASE- IP_UDP_RPC_I&M_EPM scenario 1

expose endianness and float representation

The API seems to lack the ability to get the endianness and float format information from e.g. the connect requests. With the stack not executing any data manipulation (which I think is the right design choice), the application layer would need to know these details to properly assess the content. For now I'm working with S7-1500 which appears to always leverage little endian and IEEE float representation but as the protocol supports different options I would want the app to be able to react to different scenarios.

UDP sockets are not reliably closed

For the UDP communication with the master sockets will be opened.
When the session is terminated, this socket must be closed.
For this purpose the following 2 lines are implemented in pf_cmrpc_cmdev_state_ind:

p-net/src/device/pf_cmrpc.c

Lines 2891 to 2892 in cd66dfd

os_udp_close(p_sess->socket);
pf_session_release(p_sess);

But sessions are terminated at other points of the code as well and without calling os_udp_close. E.g. in the following lines of pf_cmrpc_dce_packet:

p-net/src/device/pf_cmrpc.c

Lines 2751 to 2754 in cd66dfd

if ((p_sess != NULL) && (p_sess->kill_session == true))
{
pf_session_release(p_sess);
}

In this case the UDP socket will not be closed and all information about this socket will be deleted. As a result the socket will stay opened forever. (And this causes issues on by platform.)

So I recommend to remove the call of os_udp_close from pf_cmrpc_cmdev_state_ind and add it before the following call of memset in pf_session_release:

memset(p_sess, 0, sizeof(*p_sess));

The code could be something simple like:
if (p_sess->socket > 0) { os_udp_close(p_sess->socket); }

Issue : Station 'rt-labs-dev' : 81813F02-PBNIO: DCP no RealStationName

Hi

I am facing an issue - the device is not discoverable. and i am getting this error.
"Station 'rt-labs-dev' : 81813F02-PBNIO: DCP no RealStationName"

Setup Environment:

  1. Rsapberry pi as PLC with codesys runtime package running.
  2. Codesys development
  3. p-net stack with sample app is running under VN ubuntu 18.04 LTS

I have captured the issue snap shots for the reference.

  1. Codesys service status (on Raspberry pi system)
    raspberryPI_as_plc_codesys_service_statis

  2. Raspberrypi Tab : systemInfo capture text:
    Raspberrypi_tab_systemInfo.txt

  3. No real Station Capture:
    norealStation Name

Earlier it was working and i saw all the network traffic including power-up sequence and cyclic data traffic ..In last week suddenly it started giving this issue. I am not able to understand where was the issue. Do you have any input on this issue?
Note: I have re-imaged the raspberry pi , but still it did not help.

Regards
Rayapati

how to evaluate this p-net io stack and what is the environment it requires

First i am working on this this library . I would like to know what is the environment i need to setup.
My environment -
Host OS -is windows 10
Guest OS - ubuntu18.04 on oracle VB guest OS. I am using ubuntu as my device IO.

Codesys IDE with Rasberry pi runtime is on windows10 and ubuntu as my device io.
As per the documentation, Rasberry PI hardware is required as IO Controller. But i did not have this hardware.

  1. P-net library : able to build and run it. but i found that the button files are not created for some reason.

cfeuser@cfeuser-VirtualBox:~/pnet/profinet/p-net/build$ sudo ./pn_dev -v
[sudo] password for cfeuser:

** Starting Profinet demo application **
Verbosity level: 1
Ethernet interface: enp0s3
MAC address: 08:00:27:6E:99:77
Station name: rt-labs-dev
LED file:
Button1 file:
Button2 file:
IP address: 10.0.2.15
Netmask: 255.255.255.0
Gateway: 10.0.2.1

Waiting for connect request from IO-controller

Can any one please suggest me how to verify this without having rasberry PI hardware.

Thanks
Raj

Not running in CentOS7.7 enviornment

Hi
I am running this app in CentOS7.7 on Virtual box environment. The image i selected as minimal for CentOS.
CentOS:
static address static ip address to 192.168.0.12,255.255.255.0,gateway - 192.168.0.1,inetrface: enp0s3, Bridge adapter
PLC(RASPberry Pi) : static ip address to 192.168.0.10,255.255.255.0,gateway - 192.168.0.1,inetrface: eth0,
HOST OS (win10) : static ip address to 192.168.0.11,255.255.255.0,gateway - 192.168.0.1

CentOS7 7 error

I am getting the above error.

The same thing i am running successfully in VB Ubuntu 18.04 enviornment. With the same configuration.

When application is running on CentOS and the moment when i start the codesys service on raspberry pi. this error is coming.
Do you have any input on this.

when i run the set_network_parameters script i am getting the same error.
Regards
Raj

SPLITTED (DCP Test Cases of Automated RT Tester do not pass)

I do not want to overload you with the issues or changes, so just an ideas for improving your software:

When I started the tests with Automated RT Tester against the p-net stack, none of the test passed.
So I went through them, and for now just only the DCP tests I have resolved somehow. But probably my code changes goes against your program philosophy, maybe it would be better to notice you where are the (some of the) problems and the possible solutions:

  • Chaning and storing the IP addres and station name (mainly in the pf_cmina.c file):
    • The tester changes the IP address and/or the station name of the device in two forms - permanently and temporarily. The variable temp in the pf_cmina_dcp_set_ind() function shows it. When the change is permanent, the os_set_ip_suite() function is called, which is OK. But when the change is temporary, it means (according to documentation) that the IP suite or name must be changed, BUT also the default value of 0.0.0.0 and/or empty name must be stored, so after the device restart, the device responds with 0.0.0.0 etc. In your stack the IP suite and name change is postponed by setting the flag net->cmina_commit_ip_suite. But it works (sometimes) for the permanent change only. There is also another problem when the tester changes the values permanently and immediately after that temporarily, the stack is confused what is changing.
  • I have solved it by the way that I call the os_set_ip_suite() (with the extra temp flag) function immediately in the case PF_DCP_SUB_IP_PAR: and the other cases (lines 316, 334, 360), but it is probably far from your program philosophy to do it that way. The postponed call of os_set_ip_suite() in the pf_cmina_dcp_set_commit() function I have commented out.
  • There is another issue in the same function pf_cmina_dcp_set_ind(). The values of IP suite and/or station name must be checked for validity. So some check in the case PF_DCP_SUB_IP_PAR: (line 316), case PF_DCP_SUB_IP_SUITE: (line 334), case PF_DCP_SUB_DEV_PROP_NAME: (line 360) are needed. The stack should response with an error for invalid IP address, netmask, gateway or name. I have implemented some simple functions for that, maybe it would help you:
/**
 * @internal
 * Check the validity of IP address and subnet mask
 * In case of invalid values log to Error.
 * @param p_ip_suite       In: pointer to IP suite structure to be checked
 * @return  false  if the values are incorrect
 *          true if IP address and subnet mask are valid
 */
static bool pf_cmina_ip_suite_is_valid(
  const pf_ip_suite_t *p_ip_suite)
{
  bool ret                     = true;
  const uint32_t ip_addr       = p_ip_suite->ip_addr;
  const uint32_t ip_mask       = p_ip_suite->ip_mask;
  const uint32_t ip_gateway    = p_ip_suite->ip_gateway;
  const uint32_t network_class = (ip_addr >> 24);
  const uint32_t masked_addr   = ip_addr & ~(ip_mask);

  if (network_class < 128) /* network class A */
  {
    if (masked_addr >= (256 * 256 * 256))
    {
      ret = false;
    }
  }
  else if (network_class < 192) /* network class B */
  {
    if (masked_addr >= (256 * 256))
    {
      ret = false;
    }
  }
  else if (network_class < 224) /* network class C */
  {
    if (masked_addr >= (256))
    {
      ret = false;
    }
  }
  else /* network class D or E */
  {
    ret = false;
  }

  /* check the gateway - must be in the same subnet */
  if (ip_gateway != 0)
  {
    const uint32_t inv_masked_addr = ip_addr & ip_mask;
    const uint32_t inv_masked_gw   = ip_gateway & ip_mask;
    if (inv_masked_addr != inv_masked_gw)
    {
      ret = false;
    }
  }
  
  if (ret == false) /* display error */
  {
    LOG_WARNING(PF_DCP_LOG, "CMINA(%d): invalid IP suite:\n\taddr %d.%d.%d.%d mask %d.%d.%d.%d gw %d.%d.%d.%d\n",
                __LINE__,
                (ip_addr >> 24) & 0xFF,
                (ip_addr >> 16) & 0xFF,
                (ip_addr >> 8) & 0xFF,
                (ip_addr) & 0xFF,
                (ip_mask >> 24) & 0xFF,
                (ip_mask >> 16) & 0xFF,
                (ip_mask >> 8) & 0xFF,
                (ip_mask) & 0xFF,
                (ip_gateway >> 24) & 0xFF,
                (ip_gateway >> 16) & 0xFF,
                (ip_gateway >> 8) & 0xFF,
                (ip_gateway) & 0xFF);

  }
  return ret;
}

/**
 * @internal
 * Check the validity of station name.
 * Only several checks are done now.
 * Valid name is formed by:
 
 - 1 or more labels, separated by [.]
 - Total length is 1 to 240
 - Label length is 1 to 63
 - Labels consist of [a-z0-9-]
 - Labels do not start with [-]
 - Labels do not end with [-]
 - Labels do not use multiple concatenated [-] except for IETF RFC 5890
 - The first label does not have the form "port-xyz" or "port-xyz-abcde" with a, b, c, d, e,
   x, y, z = 0...9, to avoid wrong similarity with the field AliasNameValue
 - Station-names do not have the form a.b.c.d with a, b, c, d = 0...999
 
 * @param net         In: The p-net stack instance
 * @param p_name      In: Station name to be checked
 * @param name_length In: name length
 * @return  false  if the name is bad formed
 *          true if the name is valid
 */
static bool pf_cmina_name_of_station_is_valid(
  const pnet_t *net, 
  const char *p_name, 
  uint16_t name_length)
{
  if (name_length >= sizeof(net->cmina_temp_dcp_ase.name_of_station))
  {
    return false;
  }
  if (p_name[0] == '-')
  {
    return false;
  }

  /* check the port-xyz label */
  if(name_length >= 6)
  {
    if (strncmp(p_name, "port-", 5) == 0)
    {
      if (isdigit(p_name[5]))
      {
        return false;
      }
    }
  }

  /* go through labels */
  uint32_t n_numeric_labels = 0;
  uint32_t n_consecutive_numeric_labels = 0;
  uint16_t src_pos = 0;
  char last_c = 0;
  while (src_pos < name_length)
  {
    bool b_is_digit_only = true;
    char prev_c = 0;
    while (src_pos < name_length)
    {
      const char c = p_name[src_pos];
      last_c = c;
      src_pos++;
      if (isdigit(c))
      {
        ; /* digit is valid character, do nothing */
      }
      else if (islower(c) || c == '-')
      {
        b_is_digit_only = false;
      }
      else if (c == '.') /* end of label */
      {
        if (prev_c == 0) /* only dot in label? */
        {
          b_is_digit_only = false;
        }
        break;
      }
      else /* invalid character */
      {
        return false;
      }
      prev_c = c;
    }
    if (b_is_digit_only)
    {
      n_consecutive_numeric_labels++;
      n_numeric_labels++;
    }
    else
    {
      n_consecutive_numeric_labels = 0;
    }
  }

  /* check the last character here to better utilize the cache */
  if (last_c == '-')
  {
    return false;
  }

  /* check the invalid label a.b.c.d where abcd are digits only */
  if (n_consecutive_numeric_labels == 4 &&
      n_numeric_labels == 4 &&
      isdigit(last_c)) /* the last character must be a digit */
  {
    return false;
  }

  return true;
}

These functions are not optimal nor complete, but maybe they will be helpfull.

  • The DCP Identify (5) Request All (Block Option All Selector 255) response is probably bad formed. The Automated RT Tester does not expect the MAC address block (I don't know why). It is an error for it. But when the tester asks for MAC address, it must be given. So I have commented out the device_options[] entry in file pf_dcp.c, line 104
    // {PF_DCP_OPT_IP, PF_DCP_SUB_IP_MAC},
    and also the skip flag on the line 306
      case PF_DCP_SUB_IP_MAC:
//         skip = true;
         break;

which solved the problem (The Request All does not iterate through the device_options[], but the particular request for MAC address will not be skipped).

  • At the end of the pf_dcp_get_req() function, when there is an error, the response probably should be instead of yours
    ret = pf_dcp_put_block(p_dst, p_dst_pos, dst_max, opt, sub, true, 0, sizeof(block_error), &block_error);

something like

ret = pf_dcp_put_block(p_dst,
                              p_dst_pos,
                              dst_max,
                              PF_DCP_OPT_CONTROL,
                              PF_DCP_SUB_CONTROL_RESPONSE,
                              true,
                              ((uint16_t)(opt) << 8) | ((uint16_t)(sub)),
                              sizeof(block_error),
                              &block_error);

It means the error control block should be composed od ...CONTROL and ...CONTROL_RESPONSE values, with the option and suboption set inside it.

A lot of text, I know, so other issues I will leave for the next time :-)

Sample App GSDML

Dear Hans-Erik,

Would it be possible to upload a sample GSDML file that matches the code in the sample_app directory?

Kind regards,

Sven-Erik

Error when transferring high amount of data

With Profinet up to 1440 bytes of data can be transferred.
But due to an invalid data type of buffer_length in struct pf_ppm_t, this size cannot be achieved.
When the Ethernet packet to be transferred becomes bigger than ~255 byte, the code fails and just a fragment of the packet is transferred.
The data type of this variable should be changed from uint8_t to uint16_t.

uint8_t buffer_length;

Can you confirm?

Error when using many parameters

When parameters are declared for sub-modules, the set values are transferred from the PLC to the device during the connection request using write requests. When the size of all parameters to be transferred is bigger than one Ethernet frame, this write request is fragmented.
Receiving these fragmented write requests seems to work, but if the required response becomes bigger than one Ethernet frame, the stack fails. The reason seems to be, that no measure is implemented in pf_cmrpc_dce_packet to handle this situation. I assume the correct reaction would be to send the response fragmented as well, but this is not implemented.
I tried to limit the size by setting "MaxSupportedRecordSize" in the GSDML file to a small value (e.g. 1024), but this violates the GSDML-specification and the GSDML file will be rejected when I try to load it in my S7 project. (I'm using an S7 CPU 1212C with TIA V16.)

IN Cent OS The application is not running

Hi
Earlier i have posted one issue reference - #73
Environment :
I am running this app in CentOS7.7 on Virtual box environment. The image i selected as minimal for CentOS.
CentOS:
static address static ip address to 192.168.0.13,255.255.255.0,gateway - 192.168.0.1,inetrface: enp0s3, Bridge adapter
PLC(RASPberry Pi) : static ip address to 192.168.0.10,255.255.255.0,gateway - 192.168.0.1,inetrface: eth0,
HOST OS (win10) : static ip address to 192.168.0.11,255.255.255.0,gateway - 192.168.0.1

IO Modules configuration
IO module configuration

Now i took the correct script and run the App in centos - i did not get any error wit this script.
snap shot
App_running_on_censtOS7 7

Reference Snap shot - codesys IDE with wrieshark image capture
Error Status of the device: 16C9A049(Host Unreachable_in_device Status)
The device is identified with correct IP and proper station name. But for sore reason the ARP is not reachable to device(captured the wireshark traffic) . The connection response is not going back to PLC controller from device.
Host Unreachable_in_device Status

Do you have any inputs on this scenario, that will be helpful for me.
I am able to run the application in Ubuntu environment without any issue.

Regards
Rayapati

Windows build failed

Hi,

I'm trying to build this under windows with VS2015 and Cmake3.15.5. When cmake gets into the sample_app directory it gives the following error and stops:

-- Configuring done
CMake Error at sample_app/CMakeLists.txt:14 (add_executable):
No SOURCES given to target: pn_dev

CMake Generate step failed. Build files cannot be regenerated correctly.

Is there something else I need to set? It looks like that file is looking for ${APP_SOURCES} on that line which I can't seem to locate anywhere else.

Thanks,
Jay

I want to implement a C language service to read data from PLC over Profinet

I am looking for some help on how to use this library to write a sample C service to connect to PLC (hardware) and read data from Slot-1/Subslot-1/channel.

I want to read this data for every 5 sec from PLC using my C language service.
Does this library support TCP communication or not ?

Is it possible with this library ?

Input Output Max Size

Hello,
After doing some tests with only 1 slot, I noticed that the max size I can use is 230 bytes for inputs and 244 bytes for outputs. I read on the internet that the max size for profinet is 1440 bytes total and 244 IN/OUT per slot. So why 230 bytes for inputs in this case?

Also I noticed that when using more than 1 slot then I have to divide the 230 and 244 bytes by the number of slots I am using. Is there a way to increase that size limit?

I already modified the GSDML file like this but it did not help. There must be something else?

Thank you.

More than 2 slots.

Hello,
What do I need to do to be able to have more than 2 slots active. When modifying the sample_app and the GSDML file to be able to have inputs and outputs in 3 slots, when I start the sample_app, it gives me these errors:
[ERROR] CMDEV(527): Out of slot resources for api 0 slot 3
[ERROR] CMDEV(604): Out of slot resources for api 0
[ERROR] CMDEV(638): No module in slot 3
[ERROR] APP: Could not plug 0, 3, 1

Return error value for write request 0xaff1

Hello, I am testing your stack with the Automated RT tester. I have several issues, but for beginning, just some simple:

in the pf_cmrpc.c file, line 1744 shall be

pf_set_error(p_stat, PNET_ERROR_CODE_WRITE, PNET_ERROR_DECODE_PNIO, PNET_ERROR_CODE_1_CMRPC, PNET_ERROR_CODE_2_CMRPC_AR_UUID_UNKNOWN);

the error code is PNET_ERROR_CODE_WRITE, not PNET_ERROR_CODE_READ, otherwise the tester complains about invalid data returned. (Testing an invalid write request and the Behavior test 1).

And one typo in the pf_cmdev.c file, line 2766 and 2771, there is two times the condition

else if (p_exp_sub->data_descriptor[data_ix].length_iops != 1)

the second one (on line 2771) probably shall be

else if (p_exp_sub->data_descriptor[data_ix].length_iocs != 1)

i.e. testing of IOPS and IOCS lengths.

Nevertheless, your stack is an excelent piece of work!

Protocol violation during IODWrite Request with a single Block

When establishing a connection, one of the necessary steps is to handle Write Requests. When these requests are done as Multiple Write, everything seems to work fine.
But when such a write request has just one block, the communication fails.
Reason is, that the response contains the right data, but the trasnmitted data length is 0.

Reason for this issue seems to be the last parameter in line 1897 (pf_cmrpc.c). Currently a pointer to the starting position of the response (&res_start_pos) is used which does not make sense. When using p_res_pos instead (simmilar to the multi-write branch), everything seems to work fine...

pf_put_write_result(p_sess->get_info.is_big_endian, &write_result, res_len, p_res, &res_start_pos);

Can you confirm?

Compilation fails on linux due to compiler warning

Dear Hans-Erik,

The source code fails to build on Linux (raspbian) due to a compiler warning:

The 'fix' for now is removing: -Werror from line 34 in: cmake/Linux.cmake
so: set(CMAKE_C_FLAGS "-Wall -Wextra -Wno-unused-parameter -Werror")
becomes: set(CMAKE_C_FLAGS "-Wall -Wextra -Wno-unused-parameter")

The compiler warning is caused by line 41-45 of src/osal/linux/osal_udp.c:

local = (struct sockaddr_in) {
.sin_family = AF_INET,
.sin_addr.s_addr = htonl(addr),
.sin_port = htons(port),
};

The sin struct appears to be missing a field initializer.

Kind regards,

Sven-Erik

cannot find pnet_export.h

The pnet_export.h file is included in the pnet_api.h file. I searched for this file in the repo but cannot find it.

Include MAC address when creating new UUID

The creation of a new UUID for an outgoing request (like Application Ready) does not create UUIDs that are really unique:

p-net/src/device/pf_cmrpc.c

Lines 313 to 324 in 6b83eb3

/* Set activity UUID. Will be overwritten for incoming requests. */
p_sess->activity_uuid.data1 = net->cmrpc_session_number++;
p_sess->activity_uuid.data2 = 0x1234;
p_sess->activity_uuid.data3 = 0x5678;
p_sess->activity_uuid.data4[0] = 0x01;
p_sess->activity_uuid.data4[1] = 0x02;
p_sess->activity_uuid.data4[2] = 0x03;
p_sess->activity_uuid.data4[3] = 0x04;
p_sess->activity_uuid.data4[4] = 0x05;
p_sess->activity_uuid.data4[5] = 0x06;
p_sess->activity_uuid.data4[6] = 0x07;
p_sess->activity_uuid.data4[7] = 0x08;

As an improvement I would recommend to include at least the MAC address and if possible some timestamp. Additionally the UUID should follow the spec (see https://en.wikipedia.org/wiki/Universally_unique_identifier).

So would recommend something like this:
p_sess->activity_uuid.data1 = os_get_current_time_us ();
p_sess->activity_uuid.data2 = net->cmrpc_session_number >> 16;
p_sess->activity_uuid.data3 = 0x1000 | ((net->cmrpc_session_number >> 8) & 0x00ff);
p_sess->activity_uuid.data4[0] = 0x80;
p_sess->activity_uuid.data4[1] = net->cmrpc_session_number & 0xff;
p_sess->activity_uuid.data4[2] = net->fspm_cfg.eth_addr.addr [0];
p_sess->activity_uuid.data4[3] = net->fspm_cfg.eth_addr.addr [1];
p_sess->activity_uuid.data4[4] = net->fspm_cfg.eth_addr.addr [2];
p_sess->activity_uuid.data4[5] = net->fspm_cfg.eth_addr.addr [3];
p_sess->activity_uuid.data4[6] = net->fspm_cfg.eth_addr.addr [4];
p_sess->activity_uuid.data4[7] = net->fspm_cfg.eth_addr.addr [5];
net->cmrpc_session_number++;

The timestamp does not follow the spec, but the one of my S7 doesn't as well.
With an RTC timestamp you could build an even better UUID, but this could be an issue on some embedded systems.

Invalid Frame when using VLAN IDs unequal 0

When using VLAN IDs unequal to 0, an invalid frame will be created when sending IO data.
Before line 117 in pf_ppm.c the VLAN type ID should be added to the frame with the following lines:
u16 = OS_ETHTYPE_VLAN;
u16 = htons(u16);
memcpy(&p_payload[pos], &u16, sizeof(u16));
pos += sizeof(u16);

u16 = p_header->vlan_id & 0x0FFF;

Additionally I would ask, whether it is correct that no VLAN tag is added if the VLAN ID is set to 0. Even if the ID is zero, the tag contains priority information. E.g. the Siemens CPUs send the a VLAN tag with ID 0 and Prio 6. So I would recommend to additionally remove the following conditions to ensure that a VLAN tag is always added:

if (p_iocr->param.iocr_tag_header.vlan_id != 0)

if (p_header->vlan_id != 0)

Input or Output only slots

Hello,
Using the sample app, I was able to succesfully test Profinet communication with Codesys as a Profinet Master. I was also able to use different slots for communication by modifying the GSDML file and the main_linux.c file

Here's what I get in Codesys. "8 bits IN 8 bits Out" in slot 3 working fine:
image

But when I try to add "8 bits IN" in slot 1, I get this error when the PLC connects to the Profinet Stack: "[ERROR] CMDEV(1604): api 0 exp slot 1 subslot 1 and dir 2 not found"

Here's what I changed in main_linux.c:
image
image

And here's what I changed in GSDML file:
image
image

I must be missing something?

Same problem if I try to add "8 bits OUT" in slot 2. I get this error:
"[ERROR] CMDEV(1604): api 0 exp slot 2 subslot 1 and dir 1 not found"

What am I doing wrong?

Fails when using many slots

If setting
#define PNET_MAX_MODULES 17
(and modify the GSDML file accordingly) it is still only possible to use 9 input+output modules with the sample app.

When using slot 1-9 in Codesys everything works fine, but when using slot 1-10 this is the output:

Parameter write call-back. AREP: 1 API: 0 Slot: 9 Subslot: 1 Index: 123 Sequence: 18 Length: 4
  Bytes: 00 00 00 00 
Parameter write call-back. AREP: 1 API: 0 Slot: 9 Subslot: 1 Index: 124 Sequence: 19 Length: 4
  Bytes: 00 00 00 00 
Parameter write call-back. AREP: 1 API: 0 Slot: 10 Subslot: 1 Index: 123 Sequence: 20 Length: 4
  Bytes: 00 00 00 00 
Parameter write call-back. AREP: 1 API: 0 Slot: 10 Subslot: 1 Index: 124 Sequence: 21 Length: 4
  Bytes: 00 00 00 00 
[ERROR] CMRPC(2498): Unknown packet_type 1
[ERROR] CMRPC(2498): Unknown packet_type 1
Callback on event PNET_EVENT_ABORT. Error class: 253 Error code: 6
Aborting the application

Does not implement DCP alias

Reported by users

There is the Automated RT Tester case DCP_ALIAS for this (requires additional hardware for testing?)

AR UUID in release response is wrong

Found with Automated RT:

  • BEHAVIOR_SCENARIO_3
  • BEHAVIOR_SCENARIO_6
  • BEHAVIOR_SCENARIO_11
  • MANUAL_CHECKING_OF_SENDING_RTC_FRAMES
  • DIAGNOSIS
  • VLAN scenario 1
  • VLAN scenario 2

Out of resources after implicit read

With the PLC in stopped mode, it is possible to do modifications of IP address and station name of the IO-device. This is done via DCP, but the controller is first doing an implicit read to find out details on the IO-device.

A new session is allocated for the implicit reads, but is never closed down. After a while there will be "out of resources"

Error in communication

Dear All,

Thank you for fixing the code related to the connection issues. The PLC&TIA14 is now able to connect to the p-net software, however I have the following observation making me believe something is still off:

The PLC status alternates between 'connected' and 'connection error'.

The error reporting on the p-net side is:
[ERROR] PPM(479): iocs_len is zero
[ERROR] PPM(479): iocs_len is zero
[ERROR] PPM(479): iocs_len is zero
ABORT err_cls 253 err_code 5

OR

[ERROR] PPM(479): iocs_len is zero
[ERROR] PPM(479): iocs_len is zero
[ERROR] PPM(479): iocs_len is zero
ABORT err_cls 0 err_code 6

This seems to be resolvable by setting the 'max missed packet count' to 16 at the PLC side. So it appears a timing problem.

Kind regards,

Sven-Erik Haitjema

Why do I need "RecordDataList" for a slot to work?

Hello,
When using the sample_app with the supplied GSDML file, I can see the connection working fine with Codesys:
image

But if I comment out the "RecordDataList" part in the GSDML file like this, communication does not work anymore.
image
image
And I get this error:
ABORT err_cls 253 err_code 18

What else do I need to do to make it work without the "RecordDataList"?

I am trying to have multiple slots. A couple of "Input Only" slots and a couple of "Output Only" slots.
I think this should be a simple task but I am struggling.

I figured how to increase the PNET_MAX_MODULES in order to have more slots but now I need to figure out how to get more bytes IN/OUT per slots and get rid of the "RecordDataList".

Thank you

Notify user of data value change

A request from an end users stand-point is one of the following:

  • Have a flag indicating that the data has changed
  • Have a callback that triggers an event to inform the application that the data has changed for a given slot/subslot.

Wrong error code for CControl timeout

The stack responds with wrong error code if the controller stops communicating. It should be different error codes depending on where in the start-up sequence the error occurs.

Found with Automated RT Tester BEHAVIOR_SCENARIO_5 and BEHAVIOR_SCENARIO_8A

Devices fails to connect to SIEMENS PLC

When trying to connect to a SIEMENS PLC the Write Response would append the response twice
Bad_Write_Response

To correct this the write response should be written only when the requestor is a doing a WRITE_MULTIPLE. Otherwise generate response string and append afterwards. File to be edited is pf_cmrpc.c function pf_cmrpc_rm_write_ind
Bad_Write_Response_Correction

How to run sample app in docker container(SWARM environment)

Hi

I want run the sample app in docker container(SWARM) and configure/connect with PLC.
When i run the application in Docker i can not use system IP address to configure in PLC because docker container will it own ip address(ex: 10.0.0.1) and this ip address can not be exposed to host machine(as it is protected by docker SWARM).

In general docker services will expose port to host machine for any communication with host machine. Since profinet does not have port configured and we should use only ip address to communicate with plc, what are the alternatives to solve this problem?

Thanks for your help appreciated.

Regards
Raj

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.