A port of the original Windows-only Profinet scanner by Eiwanger, now compatible with Linux using CMake and libpcap.
- Overview
- Features
- Usage
- CLI Options
- Used PROFINET protocols
- Build (Linux)
- Build (OpenWrt APK)
- Thanks
This program scans for Profinet devices in a local subnet (Layer 2) or across a range of IP addresses (Layer 3). It sends Profinet DCP calls, listens for device responses, and performs additional RPC endpoint mapper requests for each discovered device. Results are printed as a human-readable summary to stdout.
Originally created as a Visual Studio Express console application for Windows, this port enables Linux compatibility and uses libpcap for packet capture.
The Linux port and code migration were performed by AI (GitHub Copilot), based on the original implementation and documentation.
- Layer 2 scan: Profinet DCP call in local subnet
- Layer 3 scan: IP range scan with detailed device info
- Automatic RPC endpoint mapper requests for discovered devices
- Human-readable scan summary output to stdout
- Extensive code comments for learning and reference
Run the scanner from the build directory. Example:
./build/SendPacket/pn_scannerThe program supports interactive mode (default) and non-interactive CLI mode.
- Interactive mode (default):
./build/SendPacket/pn_scanner
- Show help:
./build/SendPacket/pn_scanner --help
- List interfaces:
./build/SendPacket/pn_scanner --list-interfaces
--help
Show help message and exit.
--list-interfaces
Print available capture interfaces and exit.
--interface <index|name>
Select interface by 1-based index (from --list-interfaces) or interface name.
--mode <local|remote>
Select scan mode: local uses PROFINET DCP (Layer 2) and remote uses DCE/RPC (Layer 3).
--target <a.b.c.d[-e]>
Remote target IP or range. Required when --mode remote is used.
Examples: 192.168.0.10, 192.168.0.10-20
--duration <seconds>
Stop the scan after the given number of seconds (applies to the overall run).
--interactive
Force prompt-based mode (also the default when no parameters are provided).Examples:
# Local (DCP) scan (non-interactive)
./build/SendPacket/pn_scanner --interface 1 --mode local
# Real world example
sudo ./build/SendPacket/pn_scanner --interface enp0s31f6 --mode local
Send pn_dcp
listening on enp0s31f6 for pn_dcp...
23:29:49.003030 len:144 00:07:05:32:7e:aa
DCP IP: 0.0.0.0
DCP NameOfStation: testxasensorf28b
DCP DeviceVendorValue: iTEMP TMT86
DCP VendorID: 0x0011
DCP DeviceID: 0xa3ff
# Remote scan (DCE/RPC) (non-interactive)
./build/SendPacket/pn_scanner --interface eth0 --mode remote --target 192.168.0.10-20
# Real world example
./build/SendPacket/pn_scanner --interface eth0 --mode remote --target 192.168.1.110 --duration 2
Send RPC lookup endpointmapper first call
listening on eth0 for IP/RPC...
10:47:08.420661 len:338 192.168.1.110
Scan duration reached; stopping early.
Scan results (stdout):
Device
IP: 192.168.1.110
MAC: 00:15:5d:67:b6:76
Name:
Type: Switch series IE-SW-ALM
Annotation: Switch series IE-SW-ALM 2682370000 1 V 1 37 0
Order ID: 2682370000
SW Version: V 1.37.0
HW Revision: 1
Vendor ID: 0x0000
Device ID: 0x0000
UDP Port: 34964- Profinet DCP (Layer 2)
- Ethernet
- IP
- UDP
- DCE/RPC (Layer 3)
Install prerequisites:
sudo apt install libpcap-devConfigure and build:
cmake -S . -B build # configure the project and generate build files
cmake --build build -j # build all targets using parallel jobsThe resulting binary will be in build/SendPacket/pn_scanner.
This repository now contains a local OpenWrt feed package in openwrt-feed/pn-scanner/.
The intended workflow is to keep the package files here and let an OpenWrt buildroot
consume them through a linked local feed configured in the OpenWrt tree.
Example OpenWrt tree used during development:
~/src/openwrtCreate or edit feeds.conf in the OpenWrt tree and add a local linked feed:
cd ~/src/openwrt
cp -n feeds.conf.default feeds.conf
printf '\nsrc-link profinet ~/src/profinet_scanner_prototype/openwrt-feed\n' >> feeds.confUpdate the feed metadata and install the package into the OpenWrt package tree:
cd ~/src/openwrt
./scripts/feeds update profinet
./scripts/feeds install -f -p profinet pn-scannerFor local development builds from the current checkout, use the package-local
source override supported by openwrt-feed/pn-scanner/Makefile:
cd ~/src/openwrt
make package/feeds/profinet/pn-scanner/clean V=s
make package/feeds/profinet/pn-scanner/compile LOCAL_SOURCE_DIR=~/src/profinet_scanner_prototype V=sThis compiles the package from the current repository checkout instead of downloading the pinned git source.
For normal OpenWrt package generation, enable pn-scanner in make menuconfig
or pass the package selection on the command line, then run the usual package build:
cd ~/src/openwrt
make menuconfig
# Network ---> pn-scanner
make package/compile V=sIf the package is selected in the OpenWrt configuration and CONFIG_USE_APK=y is enabled,
OpenWrt will generate an .apk in the package output directories under bin/packages/.
Notes:
- The package definition is stored in
openwrt-feed/pn-scanner/Makefile. LOCAL_SOURCE_DIR=~/src/profinet_scanner_prototypeis only for local development. If it is omitted, OpenWrt uses the pinned upstream git source declared in the package Makefile.- The package builds from a dedicated
openwrt-build/subdirectory in this repository whenLOCAL_SOURCE_DIRis active. - If an earlier failed
USE_SOURCE_DIRrun polluted dependency build directories, clean the affected package in the OpenWrt tree before rebuilding.
This port is based on the original Windows-only program by Eiwanger: https://github.com/Eiwanger/profinet_scanner_prototype
Special thanks to Eiwanger for the original implementation and documentation.