Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
21 commits
Select commit Hold shift + click to select a range
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: 2 additions & 1 deletion .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ on:
branches:
- main
- develop
- "**"
jobs:
test:
runs-on: ubuntu-latest
Expand All @@ -22,7 +23,7 @@ jobs:
- name: Print env
run: env | sort
- name: Setup Gradle
uses: gradle/actions/setup-gradle@017a9effdb900e5b5b2fddfb590a105619dca3c3 # v4.4.2
uses: gradle/actions/setup-gradle@v5
with:
gradle-version: '8.13'
- name: Test Library
Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/publish.yml
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ jobs:
- name: Print env
run: env | sort
- name: Setup Gradle
uses: gradle/actions/setup-gradle@017a9effdb900e5b5b2fddfb590a105619dca3c3 # v4.4.2
uses: gradle/actions/setup-gradle@v5
with:
gradle-version: '8.13'
- name: Publish package
Expand Down
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ build
.idea/

bin/
**/bin/

out.log

Expand Down
1 change: 0 additions & 1 deletion Dockerfile-build
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,6 @@ WORKDIR /build

ADD ./asn1_codec/asn1c_combined/generated-files/2024.tar.gz /build
ADD ./CMakeLists.txt /build
ADD ./run-lib.sh /build
COPY ./src /build/src/

ENV CC=/usr/bin/clang
Expand Down
23 changes: 21 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -61,8 +61,7 @@ A native, dynamic library, `libasnapplication.so`, is generated from asn1c gener
The Java library, `j2735-2024-ffm-lib`, includes code generated by the [Jextract tool](https://github.com/openjdk/jextract).

Native method calls and native data structures are handled inside a Java thread-scoped "Arena".
Arenas are FFM's way of limiting the scope and lifetime of memory used by native methods, to prevent memory leaks
and security issues.
Arenas are FFM's way of limiting the scope and lifetime of memory used by native methods, to prevent memory leaks and security issues.
See: [docs.oracle.com: Memory Segments and Arenas](https://docs.oracle.com/en/java/javase/22/core/memory-segments-and-arenas.html#GUID-01CE34E8-7BCB-4540-92C4-E127C1F62711)

Java FFM bindings are generated by running the Jextract tool on the [src/convert.h](src/convert.h) header file.
Expand Down Expand Up @@ -99,6 +98,14 @@ The Java source code from jextract is copied to the `generated-jextract` folder.

The Windows library doesn't have an automated build process. It can be recreated using Visual Studio 2022 (not VSCode) with the Clang compiler for Windows. Some edits to the generated C files are required to build for Windows. Follow the instructions here: [C codec edits for Windows](generated-files/README.md). And then build via CMake in Visual Studio. The `CMakeSettings.json` file contains the Visual Studio configuration to use CMake with the clang compiler.

After regenerating the native libraries to the `lib` folder, also be sure to copy them to the [j2735-2024-ffm-lib/src/test/resources/j2735ffm](j2735-2024-ffm-lib/src/test/resources/j2735ffm) folder since they are required for the unit tests in that Java project via:

```bash
cd lib
cp libasnapplication.so ../j2735-2024-ffm-lib/src/test/resources/j2735ffm/
cp asnapplication.dll ../j2735-2024-ffm-lib/src/test/resources/j2735ffm/
```

## Unit Tests

The unit tests can be run in either Linux or Windows.
Expand Down Expand Up @@ -143,7 +150,19 @@ Content types are:
| UPER hex | text/plain |
| XER | application/xml |

### Demo API Open API Documentation

Swagger UI documentation for the Demo REST API is available at:

http://localhost:4000/swagger-ui.html

The OpenAPI specification is available in JSON format at:

http://localhost:4000/api-docs

or in YAML format at:

http://localhost:4000/api-docs.yaml



Expand Down
3 changes: 2 additions & 1 deletion generated-files/.gitignore
Original file line number Diff line number Diff line change
@@ -1,2 +1,3 @@
*.c
*.h
*.h
2024/*
6 changes: 5 additions & 1 deletion generated-files/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,15 @@ C files extracted from the zip archive from asn1_codec are extracted here for us
Not persisted to version control.

To compile for Windows run the script `prepare-for-windows.sh` script to remove files
related to GeneralizedTime, and edit the file `pdu_collection.c` to remove the lines:
related to GeneralizedTime, and edit the file `pdu_collection.c` to comment out the lines:

```c
extern struct asn_TYPE_descriptor_s asn_DEF_Period;
extern struct asn_TYPE_descriptor_s asn_DEF_AggregatedSingleTariffClassSession;
extern struct asn_TYPE_descriptor_s asn_DEF_DetectedChargeObject;

&asn_DEF_AggregatedSingleTariffClassSession,
&asn_DEF_DetectedChargeObject,
&asn_DEF_Period,
```

13 changes: 12 additions & 1 deletion j2735-2024-api/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ plugins {
id 'java'
id 'java-library'
id "io.freefair.lombok" version "8.10.2"
id 'org.springframework.boot' version '3.3.5'
id 'org.springframework.boot' version '3.5.6'
id 'io.spring.dependency-management' version '1.1.6'
}

Expand All @@ -21,6 +21,17 @@ dependencies {
testImplementation 'org.junit.jupiter:junit-jupiter:5.10.3'
implementation 'commons-io:commons-io:2.18.0'
implementation 'org.springframework.boot:spring-boot-starter-web'

// Springdoc 2.8, requires Spring Boot 3.5
// Ref: https://springdoc.org/#what-is-the-compatibility-matrix-of-springdoc-openapi-with-spring-boot
implementation 'org.springdoc:springdoc-openapi-starter-webmvc-ui:2.8.13'

// Needed for springdoc to read javadocs
// Ref: https://springdoc.org/#javadoc-support
implementation 'com.github.therapi:therapi-runtime-javadoc:0.15.0'
annotationProcessor 'com.github.therapi:therapi-runtime-javadoc-scribe:0.15.0'


compileOnly 'org.projectlombok:lombok'
annotationProcessor 'org.projectlombok:lombok'
testImplementation 'org.springframework.boot:spring-boot-starter-test'
Expand Down
8 changes: 8 additions & 0 deletions j2735-2024-api/http-tests/api-docs.http
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
### OPEN API Docs in JSON format
GET http://localhost:4000/api-docs

### OPEN API Docs in YAML format
GET http://localhost:4000/api-docs.yaml

### Swagger HTML Doce
GET http://localhost:4000/swagger-ui.html
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@
public class ApiConfiguration {
long textBufferSize;
long uperBufferSize;
long errorBufferSize;
String libraryPath;
String windowsLibraryPath;
}
26 changes: 24 additions & 2 deletions j2735-2024-api/src/main/java/j2735api/ApiController.java
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@
import static org.springframework.http.MediaType.TEXT_PLAIN_VALUE;

/**
* HTTP Methods for converting J2735 MessageFrames between XER, JER and UPER
* HTTP Methods for converting J2735 MessageFrames between XER and UPER
* @author Ivan Yourshaw
*/
@RestController
Expand All @@ -53,6 +53,12 @@ public String healthCheck() {
return "I am in good health, thanks for checking.";
}


/**
* Convert a J2735 MessageFrame in XER format to UPER format
* @param xer The J2735 MessageFrame in XER format
* @return The J2735 MessageFrame in UPER format as a byte array
*/
@PostMapping(
value = "/xer/uper/bin",
consumes = APPLICATION_XML_VALUE,
Expand All @@ -61,6 +67,13 @@ public byte[] xerToUper(@RequestBody String xer) {
return codec.xerToUper(xer);
}



/**
* Convert a J2735 MessageFrame in XER format to UPER format
* @param xer The J2735 MessageFrame in XER format
* @return The J2735 MessageFrame in UPER format as a Base64 encoded string
*/
@PostMapping(
value = "/xer/uper/hex",
consumes = APPLICATION_XML_VALUE,
Expand All @@ -74,7 +87,11 @@ public String xerToUperHex(@RequestBody String xer) {




/**
* Convert a J2735 MessageFrame in UPER format to XER format
* @param request The HttpServletRequest containing the J2735 MessageFrame in UPER format as a byte array
* @return The J2735 MessageFrame in XER format
*/
@PostMapping(
value = "/uper/bin/xer",
consumes = APPLICATION_OCTET_STREAM_VALUE,
Expand All @@ -90,6 +107,11 @@ public String uperToXer(HttpServletRequest request) {
}
}

/**
* Convert a J2735 MessageFrame in UPER format to XER format
* @param uperHex The J2735 MessageFrame in UPER format as a Hex encoded string
* @return The J2735 MessageFrame in XER format
*/
@PostMapping(
value = "/uper/hex/xer",
consumes = TEXT_PLAIN_VALUE,
Expand Down
1 change: 1 addition & 0 deletions j2735-2024-api/src/main/java/j2735api/CodecConfig.java
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@ public MessageFrameCodec messageFrameCodec() {
return new MessageFrameCodec(
config.getTextBufferSize(),
config.getUperBufferSize(),
config.getErrorBufferSize(),
libPath
);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,17 +15,18 @@
*/
package j2735api;

import io.swagger.v3.oas.annotations.OpenAPIDefinition;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;


@SpringBootApplication
@OpenAPIDefinition
public class J2735ApiApplication {

public static void main(String[] args) {
SpringApplication.run(j2735api.J2735ApiApplication.class, args);
}



}
7 changes: 7 additions & 0 deletions j2735-2024-api/src/main/resources/application.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,15 @@ spring.application.name: j2735-2024-api
server.port: 4000
spring.main.web-application-type: servlet

springdoc.swagger-ui.path: /swagger-ui.html
springdoc.api-docs.path: /api-docs

j2735.api:
# Use a large default value for text encoding, because the XML encodings for some messages,
# such as MAPs and TIMs, can be quite large
text-buffer-size: 262144
# UPER binary is a more compact encoding, so we can use a smaller buffer size.
uper-buffer-size: 8192
error-buffer-size: 256
library-path: /home/libasnapplication.so
windows-library-path: C:/temp/asnapplication.dll
2 changes: 1 addition & 1 deletion j2735-2024-api/src/main/resources/logback.xml
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@
</encoder>
</appender>

<root level="INFO">
<root level="DEBUG">
<appender-ref ref="STDOUT" />
</root>
</configuration>
7 changes: 4 additions & 3 deletions j2735-2024-ffm-lib/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ plugins {
}

group = 'usdot.jpo.ode'
version = '2.0.0'
version = '2.0.1'



Expand All @@ -16,13 +16,14 @@ repositories {
}

dependencies {
implementation 'org.slf4j:slf4j-api:2.0.16'

// Use JUnit Jupiter for testing.
testImplementation 'org.junit.jupiter:junit-jupiter:5.10.3'
testRuntimeOnly 'org.junit.platform:junit-platform-launcher'
implementation 'org.slf4j:slf4j-api:2.0.16'
testImplementation 'org.slf4j:slf4j-simple:2.0.16'
testImplementation 'org.hamcrest:hamcrest:3.0'
implementation 'commons-io:commons-io:2.20.0'
testImplementation 'commons-io:commons-io:2.20.0'
}

publishing {
Expand Down
20 changes: 9 additions & 11 deletions j2735-2024-ffm-lib/src/main/java/generated/__fsid_t.java
Original file line number Diff line number Diff line change
Expand Up @@ -2,17 +2,15 @@

package generated;

import static java.lang.foreign.MemoryLayout.PathElement.groupElement;
import static java.lang.foreign.MemoryLayout.PathElement.sequenceElement;

import java.lang.foreign.Arena;
import java.lang.foreign.GroupLayout;
import java.lang.foreign.MemoryLayout;
import java.lang.foreign.MemorySegment;
import java.lang.foreign.SegmentAllocator;
import java.lang.foreign.SequenceLayout;
import java.lang.invoke.VarHandle;
import java.util.function.Consumer;
import java.lang.invoke.*;
import java.lang.foreign.*;
import java.nio.ByteOrder;
import java.util.*;
import java.util.function.*;
import java.util.stream.*;

import static java.lang.foreign.ValueLayout.*;
import static java.lang.foreign.MemoryLayout.PathElement.*;

/**
* {@snippet lang=c :
Expand Down
Loading