This is an automated email from the ASF dual-hosted git repository.

hutcheb pushed a commit to branch plc4j/profinet
in repository https://gitbox.apache.org/repos/asf/plc4x.git

commit 36b3260cc1d99b869b8302bd3094300f28dc40f6
Author: Ben Hutcheson <[email protected]>
AuthorDate: Sun Sep 11 11:15:59 2022 -0600

    chore(plc4j/profinet): escape the device name and type within the 
connection string
---
 .../profinet/discovery/ProfinetPlcDiscoverer.java  | 610 +++++++--------------
 1 file changed, 192 insertions(+), 418 deletions(-)

diff --git 
a/plc4j/drivers/profinet/src/main/java/org/apache/plc4x/java/profinet/discovery/ProfinetPlcDiscoverer.java
 
b/plc4j/drivers/profinet/src/main/java/org/apache/plc4x/java/profinet/discovery/ProfinetPlcDiscoverer.java
index f0a1a3a43..5701f7c9c 100644
--- 
a/plc4j/drivers/profinet/src/main/java/org/apache/plc4x/java/profinet/discovery/ProfinetPlcDiscoverer.java
+++ 
b/plc4j/drivers/profinet/src/main/java/org/apache/plc4x/java/profinet/discovery/ProfinetPlcDiscoverer.java
@@ -18,8 +18,7 @@
  */
 package org.apache.plc4x.java.profinet.discovery;
 
-import org.apache.commons.codec.DecoderException;
-import org.apache.commons.codec.binary.Hex;
+import org.apache.plc4x.java.api.exceptions.PlcException;
 import org.apache.plc4x.java.api.messages.PlcDiscoveryItem;
 import org.apache.plc4x.java.api.messages.PlcDiscoveryItemHandler;
 import org.apache.plc4x.java.api.messages.PlcDiscoveryRequest;
@@ -48,30 +47,20 @@ import java.util.*;
 import java.util.concurrent.CompletableFuture;
 import java.util.concurrent.ExecutorService;
 import java.util.concurrent.Executors;
-import java.util.function.Function;
 
 public class ProfinetPlcDiscoverer implements PlcDiscoverer {
 
     private static final EtherType PN_EtherType = 
EtherType.getInstance((short) 0x8892);
-    private static final EtherType LLDP_EtherType = 
EtherType.getInstance((short) 0x88cc);
 
     // The constants for the different block names and their actual meaning.
     private static final String DEVICE_TYPE_NAME = 
"DEVICE_PROPERTIES_OPTION-1";
     private static final String DEVICE_NAME_OF_STATION = 
"DEVICE_PROPERTIES_OPTION-2";
-    private static final String PLC4X_LLDP_IDENTIFIER = "PLC4X PROFINET 
Controller Client";
-    private static final String PLC4X_LLDP_PORT = "port001.plc4x";
     private static final String DEVICE_ID = "DEVICE_PROPERTIES_OPTION-3";
     private static final String DEVICE_ROLE = "DEVICE_PROPERTIES_OPTION-4";
     private static final String DEVICE_OPTIONS = "DEVICE_PROPERTIES_OPTION-5";
     private static final String DEVICE_INSTANCE = "DEVICE_PROPERTIES_OPTION-7";
     private static final String IP_OPTION_IP = "IP_OPTION-2";
 
-    ExecutorService pool = Executors.newSingleThreadExecutor();
-    Map<MacAddress, PcapHandle> openHandles = new HashMap<>();
-    List<PlcDiscoveryItem> values = new ArrayList<>();
-
-    Set<Timer> periodicTimers = new HashSet<>();
-
     private final Logger logger = 
LoggerFactory.getLogger(ProfinetPlcDiscoverer.class);
 
     @Override
@@ -79,49 +68,200 @@ public class ProfinetPlcDiscoverer implements 
PlcDiscoverer {
         return discoverWithHandler(discoveryRequest, null);
     }
 
-    public void openDiscoverHandles() {
+    public CompletableFuture<PlcDiscoveryResponse> 
discoverWithHandler(PlcDiscoveryRequest discoveryRequest, 
PlcDiscoveryItemHandler handler) {
+        CompletableFuture<PlcDiscoveryResponse> future = new 
CompletableFuture<>();
+        Set<PcapHandle> openHandles = new HashSet<>();
+        List<PlcDiscoveryItem> values = new ArrayList<>();
         try {
             for (PcapNetworkInterface dev : Pcaps.findAllDevs()) {
                 // It turned out on some MAC network devices without any ip 
addresses
                 // the compiling of the filter expression was causing errors. 
As
                 // currently there was no other way to detect this, this check 
seems
                 // to be sufficient.
-                if (dev.getAddresses().size() == 0) {
+                if(dev.getAddresses().size() == 0) {
                     continue;
                 }
                 if (!dev.isLoopBack()) {
                     for (LinkLayerAddress linkLayerAddress : 
dev.getLinkLayerAddresses()) {
                         org.pcap4j.util.MacAddress macAddress = 
(org.pcap4j.util.MacAddress) linkLayerAddress;
                         PcapHandle handle = dev.openLive(65536, 
PcapNetworkInterface.PromiscuousMode.PROMISCUOUS, 10);
-                        openHandles.put(toPlc4xMacAddress(macAddress), handle);
+                        openHandles.add(handle);
+
+                        ExecutorService pool = 
Executors.newSingleThreadExecutor();
 
-                        // Only react on PROFINET DCP or LLDP packets targeted 
at our current MAC address.
+                        // Only react on PROFINET DCP packets targeted at our 
current MAC address.
                         handle.setFilter(
-                            "(((ether proto 0x8100) or (ether proto 0x8892)) 
and (ether dst " + Pcaps.toBpfString(macAddress) + ")) or (ether proto 0x88cc)",
+                            "((ether proto 0x8100) or (ether proto 0x8892)) 
and (ether dst " + Pcaps.toBpfString(macAddress) + ")",
                             BpfProgram.BpfCompileMode.OPTIMIZE);
+
+                        PacketListener listener =
+                            packet -> {
+                                // EthernetPacket is the highest level of 
abstraction we can be expecting.
+                                // Everything inside this we will have to 
decode ourselves.
+                                if (packet instanceof EthernetPacket) {
+                                    EthernetPacket ethernetPacket = 
(EthernetPacket) packet;
+                                    boolean isPnPacket = false;
+                                    // I have observed some times the ethernet 
packets being wrapped inside a VLAN
+                                    // Packet, in this case we simply unpack 
the content.
+                                    if (ethernetPacket.getPayload() instanceof 
Dot1qVlanTagPacket) {
+                                        Dot1qVlanTagPacket vlanPacket = 
(Dot1qVlanTagPacket) ethernetPacket.getPayload();
+                                        if 
(PN_EtherType.equals(vlanPacket.getHeader().getType())) {
+                                            isPnPacket = true;
+                                        }
+                                    } else if 
(PN_EtherType.equals(ethernetPacket.getHeader().getType())) {
+                                        isPnPacket = true;
+                                    }
+
+                                    // It's a PROFINET packet.
+                                    if (isPnPacket) {
+                                        ReadBuffer reader = new 
ReadBufferByteBased(ethernetPacket.getRawData());
+                                        try {
+                                            Ethernet_Frame ethernetFrame = 
Ethernet_Frame.staticParse(reader);
+                                            PnDcp_Pdu pdu;
+                                            // Access the pdu data (either 
directly or by
+                                            // unpacking the content of the 
VLAN packet.
+                                            if (ethernetFrame.getPayload() 
instanceof Ethernet_FramePayload_VirtualLan) {
+                                                
Ethernet_FramePayload_VirtualLan vlefpl = (Ethernet_FramePayload_VirtualLan) 
ethernetFrame.getPayload();
+                                                pdu = 
((Ethernet_FramePayload_PnDcp) vlefpl.getPayload()).getPdu();
+                                            } else {
+                                                pdu = 
((Ethernet_FramePayload_PnDcp) ethernetFrame.getPayload()).getPdu();
+                                            }
+                                            // Inspect the PDU itself
+                                            // (in this case we only process 
identify response packets)
+                                            if (pdu instanceof 
PnDcp_Pdu_IdentifyRes) {
+                                                PnDcp_Pdu_IdentifyRes 
identifyResPDU = (PnDcp_Pdu_IdentifyRes) pdu;
+
+                                                Map<String, PnDcp_Block> 
blocks = new HashMap<>();
+                                                for (PnDcp_Block block : 
identifyResPDU.getBlocks()) {
+                                                    String blockName = 
block.getOption().name() + "-" + block.getSuboption().toString();
+                                                    blocks.put(blockName, 
block);
+                                                }
+
+                                                // The mac address of the 
device we found
+                                                org.pcap4j.util.MacAddress 
srcAddr = ethernetPacket.getHeader().getSrcAddr();
+                                                // The mac address of the 
local network device
+                                                org.pcap4j.util.MacAddress 
dstAddr = ethernetPacket.getHeader().getDstAddr();
+
+                                                String deviceTypeName = 
"unknown";
+                                                if 
(blocks.containsKey(DEVICE_TYPE_NAME)) {
+                                                    
PnDcp_Block_DevicePropertiesDeviceVendor block = 
(PnDcp_Block_DevicePropertiesDeviceVendor) blocks.get(DEVICE_TYPE_NAME);
+                                                    deviceTypeName = new 
String(block.getDeviceVendorValue()).replace(" ", "%20");
+                                                }
+
+                                                String deviceName = "unknown";
+                                                if 
(blocks.containsKey(DEVICE_NAME_OF_STATION)) {
+                                                    
PnDcp_Block_DevicePropertiesNameOfStation block = 
(PnDcp_Block_DevicePropertiesNameOfStation) blocks.get(DEVICE_NAME_OF_STATION);
+                                                    deviceName = new 
String(block.getNameOfStation()).replace(" ", "%20");
+                                                }
+
+                                                String role = "unknown";
+                                                if 
(blocks.containsKey(DEVICE_ROLE)) {
+                                                    role = "";
+                                                    
PnDcp_Block_DevicePropertiesDeviceRole block = 
(PnDcp_Block_DevicePropertiesDeviceRole) blocks.get(DEVICE_ROLE);
+                                                    if 
(block.getPnioSupervisor()) {
+                                                        role += ",SUPERVISOR";
+                                                    }
+                                                    if 
(block.getPnioMultidevive()) {
+                                                        role += ",MULTIDEVICE";
+                                                    }
+                                                    if 
(block.getPnioController()) {
+                                                        role += ",CONTROLLER";
+                                                    }
+                                                    if (block.getPnioDevice()) 
{
+                                                        role += ",DEVICE";
+                                                    }
+                                                    // Cut off the first comma
+                                                    if (role.length() > 0) {
+                                                        role = 
role.substring(1);
+                                                    } else {
+                                                        role = "unknown";
+                                                    }
+                                                }
+
+                                                String remoteIpAddress = 
"unknown";
+                                                String remoteSubnetMask = 
"unknown";
+                                                if 
(blocks.containsKey(IP_OPTION_IP)) {
+                                                    PnDcp_Block_IpParameter 
block = (PnDcp_Block_IpParameter) blocks.get(IP_OPTION_IP);
+                                                    try {
+                                                        InetAddress addr = 
InetAddress.getByAddress(block.getIpAddress());
+                                                        remoteIpAddress = 
addr.getHostAddress();
+                                                        InetAddress netMask = 
InetAddress.getByAddress(block.getSubnetMask());
+                                                        remoteSubnetMask = 
netMask.getHostAddress();
+                                                    } catch 
(UnknownHostException e) {
+                                                        remoteIpAddress = 
"invalid";
+                                                    }
+                                                }
+
+                                                // Get the Vendor Id and the 
Device Id
+                                                String vendorId = "unknown";
+                                                String deviceId = "unknown";
+                                                if 
(blocks.containsKey(DEVICE_ID)) {
+                                                    
PnDcp_Block_DevicePropertiesDeviceId block = 
(PnDcp_Block_DevicePropertiesDeviceId) blocks.get(DEVICE_ID);
+                                                    vendorId = 
String.format("%04X", block.getVendorId());
+                                                    deviceId = 
String.format("%04X", block.getDeviceId());
+                                                }
+
+                                                Map<String, String> options = 
new HashMap<>();
+                                                options.put("remoteIpAddress", 
remoteIpAddress);
+                                                
options.put("remoteSubnetMask", remoteSubnetMask);
+                                                
options.put("remoteMacAddress", srcAddr.toString());
+                                                options.put("localMacAddress", 
dstAddr.toString());
+                                                options.put("deviceTypeName", 
deviceTypeName);
+                                                options.put("deviceName", 
deviceName);
+                                                options.put("vendorId", 
vendorId);
+                                                options.put("deviceId", 
deviceId);
+                                                options.put("role", role);
+                                                String name = deviceTypeName + 
" - " + deviceName;
+                                                PlcDiscoveryItem value = new 
DefaultPlcDiscoveryItem(
+                                                    
ProfinetDriver.DRIVER_CODE, RawSocketTransport.TRANSPORT_CODE,
+                                                    remoteIpAddress, options, 
name, Collections.emptyMap());
+                                                values.add(value);
+
+                                                // If we have a discovery 
handler, pass it to the handler callback
+                                                if (handler != null) {
+                                                    handler.handle(value);
+                                                }
+
+                                                logger.debug("Found new 
device: '{}' with connection-url '{}'",
+                                                    value.getName(), 
value.getConnectionUrl());
+                                            }
+                                        } catch (ParseException e) {
+                                            logger.error("Got error decoding 
packet", e);
+                                        }
+                                    }
+                                }
+                            };
+                        Task t = new Task(handle, listener);
+                        pool.execute(t);
+
+                        // Construct and send the search request.
+                        Ethernet_Frame identificationRequest = new 
Ethernet_Frame(
+                            // Pre-Defined PROFINET discovery MAC address
+                            new MacAddress(new byte[]{0x01, 0x0E, (byte) 0xCF, 
0x00, 0x00, 0x00}),
+                            toPlc4xMacAddress(macAddress),
+                            new 
Ethernet_FramePayload_VirtualLan(VirtualLanPriority.BEST_EFFORT, false, 0,
+                                new Ethernet_FramePayload_PnDcp(
+                                    new 
PnDcp_Pdu_IdentifyReq(PnDcp_FrameId.DCP_Identify_ReqPDU.getValue(),
+                                        1,
+                                        256,
+                                        Collections.singletonList(
+                                            new PnDcp_Block_ALLSelector()
+                                        )))));
+                        WriteBufferByteBased buffer = new 
WriteBufferByteBased(34);
+                        identificationRequest.serialize(buffer);
+                        Packet packet = 
EthernetPacket.newPacket(buffer.getData(), 0, 34);
+                        handle.sendPacket(packet);
                     }
                 }
             }
-        } catch (NotOpenException | PcapNativeException e) {
+        } catch (IllegalRawDataException | NotOpenException | 
PcapNativeException | SerializationException e) {
             logger.error("Got an exception while processing raw socket data", 
e);
-            for (Map.Entry<MacAddress, PcapHandle> entry : 
openHandles.entrySet()) {
-                PcapHandle openHandle = entry.getValue();
-                try {
-                    openHandle.breakLoop();
-                    openHandle.close();
-                } catch (NotOpenException error) {
-                    logger.info("Handle already closed.");
-                }
-            }
-            for (Timer timer : periodicTimers) {
-                timer.cancel();
-                timer.purge();
+            future.completeExceptionally(new PlcException("Got an internal 
error while performing discovery"));
+            for (PcapHandle openHandle : openHandles) {
+                openHandle.close();
             }
+            return future;
         }
-    }
-
-    public CompletableFuture<PlcDiscoveryResponse> 
setDiscoveryEndTimer(PlcDiscoveryRequest discoveryRequest, long delay) {
-        CompletableFuture<PlcDiscoveryResponse> future = new 
CompletableFuture<>();
 
         // Create a timer that completes the future after a given time with 
all the responses it found till then.
         Timer timer = new Timer("Discovery Timeout");
@@ -129,387 +269,14 @@ public class ProfinetPlcDiscoverer implements 
PlcDiscoverer {
             public void run() {
                 PlcDiscoveryResponse response =
                     new DefaultPlcDiscoveryResponse(discoveryRequest, 
PlcResponseCode.OK, values);
-                for (Map.Entry<MacAddress, PcapHandle> entry : 
openHandles.entrySet()) {
-                    PcapHandle openHandle = entry.getValue();
-                    try {
-                        openHandle.breakLoop();
-                        openHandle.close();
-                    } catch (Exception e) {
-                        logger.error("Error occurred while closing handle");
-                    }
-
-                }
-                for (Timer timer : periodicTimers) {
-                    timer.cancel();
-                    timer.purge();
-                }
                 future.complete(response);
-            }
-        }, delay);
-
-        return future;
-    }
-
-    public PacketListener createListener(PcapHandle handle, 
PlcDiscoveryItemHandler handler) {
-        PacketListener listener =
-            packet -> {
-                // EthernetPacket is the highest level of abstraction we can 
be expecting.
-                // Everything inside this we will have to decode ourselves.
-                if (packet instanceof EthernetPacket) {
-                    EthernetPacket ethernetPacket = (EthernetPacket) packet;
-                    boolean isPnPacket = false;
-                    // I have observed sometimes the ethernet packets being 
wrapped inside a VLAN
-                    // Packet, in this case we simply unpack the content.
-                    if (ethernetPacket.getPayload() instanceof 
Dot1qVlanTagPacket) {
-                        Dot1qVlanTagPacket vlanPacket = (Dot1qVlanTagPacket) 
ethernetPacket.getPayload();
-                        if 
(PN_EtherType.equals(vlanPacket.getHeader().getType()) || 
LLDP_EtherType.equals(vlanPacket.getHeader().getType())) {
-                            isPnPacket = true;
-                        }
-                    } else if 
(PN_EtherType.equals(ethernetPacket.getHeader().getType()) || 
LLDP_EtherType.equals(ethernetPacket.getHeader().getType())) {
-                        isPnPacket = true;
-                    }
-
-                    // It's a PROFINET or LLDP packet.
-                    if (isPnPacket) {
-                        ReadBuffer reader = new 
ReadBufferByteBased(ethernetPacket.getRawData());
-                        try {
-                            Ethernet_Frame ethernetFrame = 
Ethernet_Frame.staticParse(reader);
-
-                            // Access the pdu data (either directly or by
-                            // unpacking the content of the VLAN packet.
-                            if (ethernetFrame.getPayload() instanceof 
Ethernet_FramePayload_VirtualLan) {
-                                Ethernet_FramePayload_VirtualLan vlefpl = 
(Ethernet_FramePayload_VirtualLan) ethernetFrame.getPayload();
-                                if (vlefpl.getPayload() instanceof 
Ethernet_FramePayload_PnDcp) {
-                                    PnDcp_Pdu pdu = 
((Ethernet_FramePayload_PnDcp) vlefpl.getPayload()).getPdu();
-                                    processPnDcp(pdu, ethernetPacket, handler);
-                                } else if (vlefpl.getPayload() instanceof 
Ethernet_FramePayload_LLDP) {
-                                    Lldp_Pdu pdu = 
((Ethernet_FramePayload_LLDP) vlefpl.getPayload()).getPdu();
-                                    processLldp(pdu, ethernetPacket, handler);
-                                }
-                            } else if (ethernetFrame.getPayload() instanceof 
Ethernet_FramePayload_PnDcp) {
-                                PnDcp_Pdu pdu = ((Ethernet_FramePayload_PnDcp) 
ethernetFrame.getPayload()).getPdu();
-                                processPnDcp(pdu, ethernetPacket, handler);
-                            } else if (ethernetFrame.getPayload() instanceof 
Ethernet_FramePayload_LLDP) {
-                                Lldp_Pdu pdu = ((Ethernet_FramePayload_LLDP) 
ethernetFrame.getPayload()).getPdu();
-                                processLldp(pdu, ethernetPacket, handler);
-                            }
-
-                        } catch (ParseException e) {
-                            logger.error("Got error decoding packet", e);
-                        }
-                    }
-                }
-            };
-        return listener;
-    }
-
-    public CompletableFuture<PlcDiscoveryResponse> 
discoverWithHandler(PlcDiscoveryRequest discoveryRequest, 
PlcDiscoveryItemHandler handler) {
-        openDiscoverHandles();
-        startListener(handler);
-        startLldpPoll(5000L);
-        startPnDcpPoll(30000L);
-        CompletableFuture<PlcDiscoveryResponse> future = 
setDiscoveryEndTimer(discoveryRequest, 10000L);
-        return future;
-    }
-
-    public void ongoingDiscoverWithHandler(PlcDiscoveryRequest 
discoveryRequest, PlcDiscoveryItemHandler handler, long lldpPeriod, long 
dcpPeriod) {
-        openDiscoverHandles();
-        startListener(handler);
-        startLldpPoll(lldpPeriod);
-        startPnDcpPoll(dcpPeriod);
-    }
-
-    private void processPnDcp(PnDcp_Pdu pdu, EthernetPacket ethernetPacket, 
PlcDiscoveryItemHandler handler) {
-        // Inspect the PDU itself
-        // (in this case we only process identify response packets)
-        if (pdu instanceof PnDcp_Pdu_IdentifyRes) {
-            PnDcp_Pdu_IdentifyRes identifyResPDU = (PnDcp_Pdu_IdentifyRes) pdu;
-
-            Map<String, PnDcp_Block> blocks = new HashMap<>();
-            for (PnDcp_Block block : identifyResPDU.getBlocks()) {
-                String blockName = block.getOption().name() + "-" + 
block.getSuboption().toString();
-                blocks.put(blockName, block);
-            }
-
-            // The mac address of the device we found
-            org.pcap4j.util.MacAddress srcAddr = 
ethernetPacket.getHeader().getSrcAddr();
-            // The mac address of the local network device
-            org.pcap4j.util.MacAddress dstAddr = 
ethernetPacket.getHeader().getDstAddr();
-
-            String deviceTypeName = "unknown";
-            if (blocks.containsKey(DEVICE_TYPE_NAME)) {
-                PnDcp_Block_DevicePropertiesDeviceVendor block = 
(PnDcp_Block_DevicePropertiesDeviceVendor) blocks.get(DEVICE_TYPE_NAME);
-                deviceTypeName = new 
String(block.getDeviceVendorValue()).replace(" ", "%20");
-            }
-
-            String deviceName = "unknown";
-            if (blocks.containsKey(DEVICE_NAME_OF_STATION)) {
-                PnDcp_Block_DevicePropertiesNameOfStation block = 
(PnDcp_Block_DevicePropertiesNameOfStation) blocks.get(DEVICE_NAME_OF_STATION);
-                deviceName = new String(block.getNameOfStation()).replace(" ", 
"%20");
-            }
-
-            String role = "unknown";
-            if (blocks.containsKey(DEVICE_ROLE)) {
-                role = "";
-                PnDcp_Block_DevicePropertiesDeviceRole block = 
(PnDcp_Block_DevicePropertiesDeviceRole) blocks.get(DEVICE_ROLE);
-                if (block.getPnioSupervisor()) {
-                    role += ",SUPERVISOR";
-                }
-                if (block.getPnioMultidevive()) {
-                    role += ",MULTIDEVICE";
-                }
-                if (block.getPnioController()) {
-                    role += ",CONTROLLER";
-                }
-                if (block.getPnioDevice()) {
-                    role += ",DEVICE";
-                }
-                // Cut off the first comma
-                if (role.length() > 0) {
-                    role = role.substring(1);
-                } else {
-                    role = "unknown";
-                }
-            }
-
-            String remoteIpAddress = "unknown";
-            String remoteSubnetMask = "unknown";
-            if (blocks.containsKey(IP_OPTION_IP)) {
-                PnDcp_Block_IpParameter block = (PnDcp_Block_IpParameter) 
blocks.get(IP_OPTION_IP);
-                try {
-                    InetAddress addr = 
InetAddress.getByAddress(block.getIpAddress());
-                    remoteIpAddress = addr.getHostAddress();
-                    InetAddress netMask = 
InetAddress.getByAddress(block.getSubnetMask());
-                    remoteSubnetMask = netMask.getHostAddress();
-                } catch (UnknownHostException e) {
-                    remoteIpAddress = "invalid";
+                for (PcapHandle openHandle : openHandles) {
+                    openHandle.close();
                 }
             }
+        }, 5000L);
 
-            // Get the Vendor Id and the Device Id
-            String vendorId = "unknown";
-            String deviceId = "unknown";
-            if (blocks.containsKey(DEVICE_ID)) {
-                PnDcp_Block_DevicePropertiesDeviceId block = 
(PnDcp_Block_DevicePropertiesDeviceId) blocks.get(DEVICE_ID);
-                vendorId = String.format("%04X", block.getVendorId());
-                deviceId = String.format("%04X", block.getDeviceId());
-            }
-
-            Map<String, String> options = new HashMap<>();
-            options.put("remoteIpAddress", remoteIpAddress);
-            options.put("remoteSubnetMask", remoteSubnetMask);
-            options.put("remoteMacAddress", srcAddr.toString());
-            options.put("localMacAddress", dstAddr.toString());
-            options.put("deviceTypeName", deviceTypeName);
-            options.put("deviceName", deviceName);
-            options.put("vendorId", vendorId);
-            options.put("deviceId", deviceId);
-            options.put("role", role);
-            String name = deviceTypeName + " - " + deviceName;
-            PlcDiscoveryItem value = new DefaultPlcDiscoveryItem(
-                ProfinetDriver.DRIVER_CODE, RawSocketTransport.TRANSPORT_CODE,
-                remoteIpAddress, options, name, Collections.emptyMap());
-            values.add(value);
-
-            // If we have a discovery handler, pass it to the handler callback
-            if (handler != null) {
-                handler.handle(value);
-            }
-
-            logger.debug("Found new device: '{}' with connection-url '{}'",
-                value.getName(), value.getConnectionUrl());
-        }
-    }
-
-    private void processLldp(Lldp_Pdu pdu, EthernetPacket ethernetPacket, 
PlcDiscoveryItemHandler handler) {
-        logger.debug("Found new lldp device: '' with connection-url ''");
-    }
-
-    public void startPnDcpPoll(long period) {
-        for (Map.Entry<MacAddress, PcapHandle> entry : openHandles.entrySet()) 
{
-            PcapHandle handle = entry.getValue();
-            MacAddress macAddress = entry.getKey();
-            // Construct and send the search request.
-
-            Function<Object, Boolean> pnDcpTimer =
-                message -> {
-                    Ethernet_Frame identificationRequest = new Ethernet_Frame(
-                        // Pre-Defined PROFINET discovery MAC address
-                        new MacAddress(new byte[]{0x01, 0x0E, (byte) 0xCF, 
0x00, 0x00, 0x00}),
-                        macAddress,
-                        new 
Ethernet_FramePayload_VirtualLan(VirtualLanPriority.BEST_EFFORT, false, 0,
-                            new Ethernet_FramePayload_PnDcp(
-                                new 
PnDcp_Pdu_IdentifyReq(PnDcp_FrameId.DCP_Identify_ReqPDU.getValue(),
-                                    1,
-                                    256,
-                                    Collections.singletonList(
-                                        new PnDcp_Block_ALLSelector()
-                                    )))));
-                    WriteBufferByteBased buffer = new WriteBufferByteBased(34);
-                    try {
-                        identificationRequest.serialize(buffer);
-                    } catch (SerializationException e) {
-                        throw new RuntimeException(e);
-                    }
-                    Packet packet = null;
-                    try {
-                        packet = EthernetPacket.newPacket(buffer.getData(), 0, 
34);
-                    } catch (IllegalRawDataException e) {
-                        throw new RuntimeException(e);
-                    }
-                    try {
-                        handle.sendPacket(packet);
-                    } catch (PcapNativeException e) {
-                        throw new RuntimeException(e);
-                    } catch (NotOpenException e) {
-                        throw new RuntimeException(e);
-                    }
-                    return null;
-            };
-
-            Timer timer = new Timer();
-            periodicTimers.add(timer);
-
-            // Schedule to run after every 3 second(3000 millisecond)
-            timer.scheduleAtFixedRate(
-                new PeriodicTask(handle, pnDcpTimer),
-                0,
-                period);
-        }
-    }
-
-    public void startListener(PlcDiscoveryItemHandler handler) {
-        for (Map.Entry<MacAddress, PcapHandle> entry : openHandles.entrySet()) 
{
-            PcapHandle handle = entry.getValue();
-            MacAddress macAddress = entry.getKey();
-            // Construct and send the search request.
-
-            Function<Object, Boolean> pnDcpTimer =
-                message -> {
-                    PacketListener listener = createListener(handle, handler);
-                    try {
-                        handle.loop(-1, listener);
-                    } catch (InterruptedException e) {
-                        logger.error("Got error handling raw socket", e);
-                        Thread.currentThread().interrupt();
-                    } catch (PcapNativeException | NotOpenException e) {
-                        logger.error("Got error handling raw socket", e);
-                    }
-                    return null;
-                };
-
-            Timer timer = new Timer();
-            periodicTimers.add(timer);
-
-            // Schedule to run after every 3 second(3000 millisecond)
-            timer.schedule(
-                new PeriodicTask(handle, pnDcpTimer),
-                5000,
-                15000);
-        }
-    }
-
-
-
-    public void startLldpPoll(long period) {
-        for (Map.Entry<MacAddress, PcapHandle> entry : openHandles.entrySet()) 
{
-            PcapHandle handle = entry.getValue();
-            MacAddress macAddress = entry.getKey();
-
-            Function<Object, Boolean> lldpTimer =
-                message -> {
-                    // Construct and send the LLDP Probe
-                    TlvOrgSpecificProfibus portStatus = new 
TlvOrgSpecificProfibus(
-                        new TlvProfibusSubTypePortStatus(0x00)
-                    );
-
-                    TlvOrgSpecificProfibus chassisMac = new 
TlvOrgSpecificProfibus(
-                        new TlvProfibusSubTypeChassisMac(macAddress)
-                    );
-
-                    TlvOrgSpecificIeee8023 ieee = new TlvOrgSpecificIeee8023(
-                        (short) 0x01,
-                        (short) 0x03,
-                        0x0020,
-                        0x0010
-                    );
-
-                    Ethernet_Frame identificationRequest = null;
-                    try {
-                        identificationRequest = new Ethernet_Frame(
-                            // Pre-Defined LLDP discovery MAC address
-                            new MacAddress(new byte[]{0x01, (byte) 0x80, 
(byte) 0xc2, 0x00, 0x00, 0x0e}),
-                            macAddress,
-                            new Ethernet_FramePayload_LLDP(
-                                new Lldp_Pdu(
-                                    Arrays.asList(
-                                        new TlvChassisId(
-                                            PLC4X_LLDP_IDENTIFIER.length() + 1,
-                                            (short) 7,
-                                            PLC4X_LLDP_IDENTIFIER
-                                        ),
-                                        new TlvPortId(
-                                            PLC4X_LLDP_PORT.length() + 1,
-                                            (short) 7,
-                                            PLC4X_LLDP_PORT
-                                        ),
-                                        new TlvTimeToLive(2, 20),
-                                        new TlvOrganizationSpecific(
-                                            portStatus.getLengthInBytes(),
-                                            portStatus
-                                        ),
-                                        new TlvOrganizationSpecific(
-                                            chassisMac.getLengthInBytes(),
-                                            chassisMac
-                                        ),
-                                        new TlvOrganizationSpecific(
-                                            ieee.getLengthInBytes(),
-                                            ieee
-                                        ),
-                                        new TlvManagementAddress(
-                                            12,
-                                            ManagementAddressSubType.IPV4,
-                                            new 
IpAddress(Hex.decodeHex("c0a85a6e")),
-                                            (short) 0x03,
-                                            0x01L,
-                                            (short) 0x00
-                                        ),
-                                        new EndOfLldp(0)
-                                    )
-                                )));
-                    } catch (DecoderException e) {
-                        throw new RuntimeException(e);
-                    }
-                    WriteBufferByteBased buffer = new 
WriteBufferByteBased(identificationRequest.getLengthInBytes());
-                    try {
-                        identificationRequest.serialize(buffer);
-                    } catch (SerializationException e) {
-                        throw new RuntimeException(e);
-                    }
-                    Packet packet = null;
-                    try {
-                        packet = EthernetPacket.newPacket(buffer.getData(), 0, 
identificationRequest.getLengthInBytes());
-                    } catch (IllegalRawDataException e) {
-                        throw new RuntimeException(e);
-                    }
-                    try {
-                        handle.sendPacket(packet);
-                    } catch (PcapNativeException e) {
-                        throw new RuntimeException(e);
-                    } catch (NotOpenException e) {
-                        throw new RuntimeException(e);
-                    }
-                    return null;
-                };
-            Timer timer = new Timer();
-            periodicTimers.add(timer);
-
-            // Schedule to run after every 3 second(3000 millisecond)
-            timer.scheduleAtFixedRate(
-                new PeriodicTask(handle, lldpTimer),
-                0,
-                period);
-        }
+        return future;
     }
 
     private static MacAddress toPlc4xMacAddress(org.pcap4j.util.MacAddress 
pcap4jMacAddress) {
@@ -517,28 +284,35 @@ public class ProfinetPlcDiscoverer implements 
PlcDiscoverer {
         return new MacAddress(new byte[]{address[0], address[1], address[2], 
address[3], address[4], address[5]});
     }
 
-    private static class PeriodicTask extends TimerTask {
+    private static class Task implements Runnable {
 
-        private final Logger logger = 
LoggerFactory.getLogger(PeriodicTask.class);
+        private final Logger logger = LoggerFactory.getLogger(Task.class);
 
         private final PcapHandle handle;
-        private final Function<Object, Boolean> operator;
+        private final PacketListener listener;
 
-        public PeriodicTask(PcapHandle handle, Function<Object, Boolean> 
operator) {
+        public Task(PcapHandle handle, PacketListener listener) {
             this.handle = handle;
-            this.operator = operator;
+            this.listener = listener;
         }
 
         @Override
         public void run() {
-            operator.apply(null);
+            try {
+                handle.loop(10, listener);
+            } catch (InterruptedException e) {
+                logger.error("Got error handling raw socket", e);
+                Thread.currentThread().interrupt();
+            } catch (PcapNativeException | NotOpenException e) {
+                logger.error("Got error handling raw socket", e);
+            }
         }
-
     }
 
     public static void main(String[] args) throws Exception {
         ProfinetPlcDiscoverer discoverer = new ProfinetPlcDiscoverer();
         discoverer.discover(null);
+
         Thread.sleep(10000);
     }
 


Reply via email to