Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
19 commits
Select commit Hold shift + click to select a range
2559eea
feat(plc4j/slmp): scaffold read-only driver module, generate 3E classes
LivingLikeKrillin Jun 13, 2026
eb82411
feat(plc4j/slmp): add SlmpDataType word-unit value decoding
LivingLikeKrillin Jun 13, 2026
0870c4e
feat(plc4j/slmp): add SlmpTag address parsing and tag handler
LivingLikeKrillin Jun 13, 2026
6151c14
feat(plc4j/slmp): add driver and tcp transport configuration
LivingLikeKrillin Jun 13, 2026
b33a5f2
feat(plc4j/slmp): add 3E TCP message codec and request-build test
LivingLikeKrillin Jun 13, 2026
13f210c
feat(plc4j/slmp): add connection, driver and response mapping
LivingLikeKrillin Jun 13, 2026
5df32de
test(plc4j/slmp): add end-to-end DriverTestsuite and merge IT coverage
LivingLikeKrillin Jun 13, 2026
58393ce
refactor(plc4j/slmp): clarify timeout/correlation semantics, tidy logs
LivingLikeKrillin Jun 13, 2026
e369e24
test(plc4j/slmp): run ParserSerializerTestsuite, fix enum XML form
LivingLikeKrillin Jun 18, 2026
727fc09
chore(plc4j/slmp): integrate driver into project conventions
LivingLikeKrillin Jul 10, 2026
03d5ad4
fix(plc4j/slmp): surface per-tag failures, don't fail the whole read
LivingLikeKrillin Jul 10, 2026
b8066eb
test(plc4j/slmp): cover the documented 0x-prefixed address form
LivingLikeKrillin Jul 10, 2026
2f2c251
docs(plc4j/slmp): add SLMP to the protocol feature-matrix tables
LivingLikeKrillin Jul 10, 2026
6f274d0
docs(plc4j/slmp): describe the 960-word cap as a conservative ceiling
LivingLikeKrillin Jul 11, 2026
4aa7f9a
fix(plc4j/slmp): clear timed-out correlation slot only if still owned
LivingLikeKrillin Jul 11, 2026
edf51cb
chore(plc4j/slmp): tidy import order, javadoc wording and late-drop log
LivingLikeKrillin Jul 11, 2026
237d195
fix(plc4j/slmp): validate quantity, monitoring-timer and request-time…
LivingLikeKrillin Jul 14, 2026
ca1ee64
Merge remote-tracking branch 'origin/develop' into feature/slmp-driver
LivingLikeKrillin Jul 14, 2026
ecace5a
fix(plc4j/slmp): validate device-number range and point-count overflow
LivingLikeKrillin Jul 14, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions RELEASE_NOTES
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,9 @@ New Features
notifications.
- Added a new PlcCertificateAuthentication to the API module.
- Initial version of a new Java UMAS driver.
- Initial version of a new Java SLMP (Mitsubishi MELSEC) driver:
read-only access to word devices (D/W/R) using binary 3E frames
over TCP.
- The 'plc4x' proxy driver now supports TLS as a transport and
requires mandatory username/password authentication
(configured via the new "username" and "password" connection
Expand Down
6 changes: 6 additions & 0 deletions plc4j/drivers/all/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -178,6 +178,12 @@
<version>0.14.0-SNAPSHOT</version>
<scope>runtime</scope>
</dependency>
<dependency>
<groupId>org.apache.plc4x</groupId>
<artifactId>plc4j-driver-slmp</artifactId>
<version>0.14.0-SNAPSHOT</version>
<scope>runtime</scope>
</dependency>

<dependency>
<groupId>org.apache.plc4x</groupId>
Expand Down
267 changes: 267 additions & 0 deletions plc4j/drivers/slmp/pom.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,267 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
Licensed to the Apache Software Foundation (ASF) under one
or more contributor license agreements. See the NOTICE file
distributed with this work for additional information
regarding copyright ownership. The ASF licenses this file
to you under the Apache License, Version 2.0 (the
"License"); you may not use this file except in compliance
with the License. You may obtain a copy of the License at

https://www.apache.org/licenses/LICENSE-2.0

Unless required by applicable law or agreed to in writing,
software distributed under the License is distributed on an
"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
KIND, either express or implied. See the License for the
specific language governing permissions and limitations
under the License.
-->
<project xmlns="http://maven.apache.org/POM/4.1.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.1.0 http://maven.apache.org/xsd/maven-4.1.0.xsd">

<parent>
<groupId>org.apache.plc4x</groupId>
<artifactId>plc4j-drivers</artifactId>
<version>0.14.0-SNAPSHOT</version>
</parent>

<artifactId>plc4j-driver-slmp</artifactId>

<name>PLC4J: Driver: SLMP</name>
<description>Implementation of a PLC4X read-only driver for the SLMP / MELSEC Communication 3E protocol.</description>

<properties>
<project.build.outputTimestamp>2025-08-02T13:55:11Z</project.build.outputTimestamp>
</properties>

<build>
<plugins>
<plugin>
<groupId>org.apache.karaf.tooling</groupId>
<artifactId>karaf-maven-plugin</artifactId>
<executions>
<execution>
<id>generate-feature-xml</id>
<phase>compile</phase>
<goals>
<goal>features-generate-descriptor</goal>
<goal>verify</goal>
</goals>
<configuration>
<enableGeneration>true</enableGeneration>
<aggregateFeatures>true</aggregateFeatures>
</configuration>
</execution>
<execution>
<id>build-kar</id>
<phase>package</phase>
<goals>
<goal>kar</goal>
</goals>
</execution>
</executions>
</plugin>
<!--
Coverage overrides for the SLMP driver module.

Reduced minimum (0.70 instead of 0.80) and the readwrite/with exclusions:
the SlmpConnection async onRead/onConnect/sendRequest paths depend on a live
transport instance and message codec pipeline; these are covered by the
DriverTestsuite integration test (SlmpDriverDriverTestsuiteIT) rather than
unit tests, mirroring the modbus driver's coverage configuration.
-->
<plugin>
<groupId>org.jacoco</groupId>
<artifactId>jacoco-maven-plugin</artifactId>
<executions>
<!--
Append the integration-test (DriverTestsuite) coverage into the same
exec file as the unit tests, so the coverage check sees the connection,
driver and codec classes that are exercised end-to-end by the IT rather
than by unit tests.
-->
<execution>
<id>pre-integration-test</id>
<goals>
<goal>prepare-agent-integration</goal>
</goals>
<configuration>
<propertyName>failsafeArgLine</propertyName>
<destFile>${project.build.directory}/jacoco.exec</destFile>
<append>true</append>
</configuration>
</execution>
<execution>
<id>check-coverage</id>
<phase>verify</phase>
<goals>
<goal>check</goal>
</goals>
<configuration>
<haltOnFailure>true</haltOnFailure>
<excludes>
<exclude>META-INF/versions/**</exclude>
<exclude>module-info.class</exclude>
<exclude>**/*$*Listener.class</exclude>
<exclude>**/readwrite/*.class</exclude>
<exclude>**/with*.class</exclude>
</excludes>
<rules>
<rule implementation="org.jacoco.maven.RuleConfiguration">
<element>BUNDLE</element>
<limits>
<limit implementation="org.jacoco.report.check.Limit">
<counter>INSTRUCTION</counter>
<value>COVEREDRATIO</value>
<minimum>0.70</minimum>
</limit>
</limits>
</rule>
</rules>
</configuration>
</execution>
</executions>
</plugin>
<plugin>
<groupId>org.apache.felix</groupId>
<artifactId>maven-bundle-plugin</artifactId>
<extensions>true</extensions>
<configuration>
<instructions>
<Bundle-SymbolicName>${project.groupId}.${project.artifactId}</Bundle-SymbolicName>
<Bundle-Activator>org.apache.plc4x.java.osgi.DriverActivator</Bundle-Activator>
<Export-Service>org.apache.plc4x.java.api.PlcDriver,org.apache.plc4x.java.slmp.SlmpDriver</Export-Service>
<Import-Package>
*
</Import-Package>
</instructions>
</configuration>
</plugin>
</plugins>
</build>

<dependencies>
<dependency>
<groupId>org.apache.plc4x</groupId>
<artifactId>plc4j-api</artifactId>
<version>0.14.0-SNAPSHOT</version>
</dependency>
<dependency>
<groupId>org.apache.plc4x</groupId>
<artifactId>plc4j-spi-buffers-api</artifactId>
<version>0.14.0-SNAPSHOT</version>
</dependency>
<dependency>
<groupId>org.apache.plc4x</groupId>
<artifactId>plc4j-spi-buffers-byte</artifactId>
<version>0.14.0-SNAPSHOT</version>
</dependency>
<dependency>
<groupId>org.apache.plc4x</groupId>
<artifactId>plc4j-spi-config</artifactId>
<version>0.14.0-SNAPSHOT</version>
</dependency>
<dependency>
<groupId>org.apache.plc4x</groupId>
<artifactId>plc4j-spi-fields</artifactId>
<version>0.14.0-SNAPSHOT</version>
</dependency>
<dependency>
<groupId>org.apache.plc4x</groupId>
<artifactId>plc4j-spi-utils</artifactId>
<version>0.14.0-SNAPSHOT</version>
</dependency>
<dependency>
<groupId>org.apache.plc4x</groupId>
<artifactId>plc4j-spi-values</artifactId>
<version>0.14.0-SNAPSHOT</version>
</dependency>
<dependency>
<groupId>org.apache.plc4x</groupId>
<artifactId>plc4j-spi-drivers</artifactId>
<version>0.14.0-SNAPSHOT</version>
</dependency>
<dependency>
<groupId>org.apache.plc4x</groupId>
<artifactId>plc4j-transports-api</artifactId>
<version>0.14.0-SNAPSHOT</version>
</dependency>
<dependency>
<groupId>org.apache.plc4x</groupId>
<artifactId>plc4j-utils-audit-log-api</artifactId>
<version>0.14.0-SNAPSHOT</version>
</dependency>
<dependency>
<groupId>org.apache.plc4x</groupId>
<artifactId>plc4j-transports-tcp</artifactId>
<version>0.14.0-SNAPSHOT</version>
</dependency>

<!-- Test scope -->
<dependency>
<groupId>org.apache.plc4x</groupId>
<artifactId>plc4j-utils-test-utils</artifactId>
<version>0.14.0-SNAPSHOT</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.apache.plc4x</groupId>
<artifactId>plc4j-transports-test</artifactId>
<version>0.14.0-SNAPSHOT</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.apache.plc4x</groupId>
<artifactId>plc4x-protocols-slmp</artifactId>
<version>0.14.0-SNAPSHOT</version>
<classifier>tests</classifier>
<type>test-jar</type>
<scope>test</scope>
</dependency>
</dependencies>

<profiles>
<profile>
<id>update-generated-code</id>
<build>
<plugins>
<plugin>
<groupId>org.apache.plc4x.plugins</groupId>
<artifactId>plc4x-maven-plugin</artifactId>
<executions>
<execution>
<id>generate-driver</id>
<phase>generate-sources</phase>
<goals>
<goal>generate-driver</goal>
</goals>
<configuration>
<protocolName>slmp</protocolName>
<languageName>java</languageName>
<outputFlavor>read-write</outputFlavor>
<outputDir>src/main/generated</outputDir>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>

<dependencies>
<dependency>
<groupId>org.apache.plc4x</groupId>
<artifactId>plc4x-code-generation-language-java-jp</artifactId>
<version>0.14.0-SNAPSHOT</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>org.apache.plc4x</groupId>
<artifactId>plc4x-protocols-slmp</artifactId>
<version>0.14.0-SNAPSHOT</version>
<scope>provided</scope>
</dependency>
</dependencies>
</profile>
</profiles>

</project>
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
// Licensed to the Apache Software Foundation (ASF) under one
// or more contributor license agreements. See the NOTICE file
// distributed with this work for additional information
// regarding copyright ownership. The ASF licenses this file
// to you under the Apache License, Version 2.0 (the
// "License"); you may not use this file except in compliance
// with the License. You may obtain a copy of the License at
//
// https://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing,
// software distributed under the License is distributed on an
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
// KIND, either express or implied. See the License for the
// specific language governing permissions and limitations
// under the License.
package org.apache.plc4x.java.slmp.readwrite;

/**
* Code generated by code-generation. DO NOT EDIT.
*/
public class Constants {
public static final Integer SLMPDEFAULTPORT = 5007;

public int getSlmpDefaultPort() {
return SLMPDEFAULTPORT;
}
}
Loading
Loading