Skip to content
This repository has been archived by the owner on Nov 17, 2023. It is now read-only.

[FEATURE] Add Java build using JavaCPP to map the C API #19797

Open
wants to merge 6 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
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
61 changes: 61 additions & 0 deletions .github/workflows/java.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,61 @@
name: java
on:
push:
paths:
- java/**
pull_request:
paths:
- java/**
workflow_dispatch:
env:
CI_DEPLOY_NEED_CUDA: 1
CI_DEPLOY_NEED_GRADLE: 1
CI_DEPLOY_MODULE: ${{ github.workflow }}
CI_DEPLOY_PLATFORM: ${{ github.job }}
CI_DEPLOY_USERNAME: ${{ secrets.CI_DEPLOY_USERNAME }}
CI_DEPLOY_PASSWORD: ${{ secrets.CI_DEPLOY_PASSWORD }}
jobs:
linux-x86_64:
runs-on: ubuntu-16.04
container: centos:7
strategy:
matrix:
include:
- ext: ""
options: ""
- ext: "-gpu"
options: "-x test"
steps:
- run: yum -y install epel-release
- run: yum -y install openblas-devel openblas-static
- uses: bytedeco/javacpp-presets/.github/actions/deploy-centos@aa134b6146dda5829e3e911ab96e1e6d48ade9a6
macosx-x86_64:
runs-on: macos-10.15
# strategy:
# matrix:
# include:
# - ext: ""
# options: ""
# - ext: "-gpu"
# options: "-x test"
steps:
- run: brew install gcc openblas
- run: brew unlink gcc && brew link gcc
- uses: bytedeco/javacpp-presets/.github/actions/deploy-macosx@aa134b6146dda5829e3e911ab96e1e6d48ade9a6
windows-x86_64:
runs-on: windows-2019
strategy:
matrix:
include:
- ext: ""
options: ""
- ext: "-gpu"
options: "-x test"
steps:
- uses: al-cheb/configure-pagefile-action@7e234852c937eea04d6ee627c599fb24a5bfffee
with:
minimum-size: 8GB
maximum-size: 16GB
disk-root: "C:"
- run: C:\msys64\usr\bin\pacman -S --noconfirm mingw-w64-x86_64-openblas
- uses: bytedeco/javacpp-presets/.github/actions/deploy-windows@aa134b6146dda5829e3e911ab96e1e6d48ade9a6
2 changes: 1 addition & 1 deletion cmake/ChooseBlas.cmake
Original file line number Diff line number Diff line change
Expand Up @@ -80,7 +80,7 @@ set(FORTRAN_DIR \\\"\$\{CMAKE_Fortran_IMPLICIT_LINK_DIRECTORIES\}\\\")
COMMAND ${CMAKE_COMMAND} .
)
set(FORTRAN_DIR "")
include(build/temp/FortranDir.cmake)
include(${CMAKE_CURRENT_BINARY_DIR}/temp/FortranDir.cmake)
find_library(FORTRAN_LIB NAMES gfortran HINTS ${FORTRAN_DIR})
message("FORTRAN_DIR is ${FORTRAN_DIR}")
message("FORTRAN_LIB is ${FORTRAN_LIB}")
Expand Down
32 changes: 32 additions & 0 deletions java/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
<!--- 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 -->

<!--- http://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. -->

MXNet Java Package
====================
This directory and nested files contain MXNet Java package and language binding.

## Installation
To install requirements for MXNet Java package, visit MXNet [Install Instruction](https://mxnet.apache.org/get_started)

## Running the unit tests
For running unit tests, you will need the [Gradle build system](https://gradle.org/). To install:
* https://gradle.org/install/

Once ```gradle``` is installed, run the following from MXNet java subdirectory (please make sure the installation path of ```gradle``` is included in your ```$PATH``` environment variable):
```
gradle clean build test -Dorg.gradle.jvmargs=-Xmx2048m
```
171 changes: 171 additions & 0 deletions java/build.gradle
Original file line number Diff line number Diff line change
@@ -0,0 +1,171 @@
plugins {
id 'java-library'
id 'org.bytedeco.gradle-javacpp-build' version '1.5.5-SNAPSHOT'
id 'maven-publish'
id 'signing'
}

group = 'org.apache'
version = '2.0-SNAPSHOT'

repositories {
mavenLocal()
mavenCentral()
maven { url 'https://oss.sonatype.org/content/repositories/snapshots/' }
maven { url 'https://repository.apache.org/content/groups/snapshots/' }
}

configurations {
all {
resolutionStrategy.cacheChangingModulesFor 0, 'seconds'
}
javacppPlatform
javacppPlatformGpu
}

dependencies {
api "org.bytedeco:javacpp:$javacppVersion"
javacppPlatform "org.bytedeco:javacpp-platform:$javacppVersion"
javacppPlatform "$group:mxnet:$version:linux-x86_64"
javacppPlatform "$group:mxnet:$version:macosx-x86_64"
javacppPlatform "$group:mxnet:$version:windows-x86_64"
javacppPlatformGpu "$group:mxnet:$version:linux-x86_64-gpu"
// javacppPlatformGpu "$group:mxnet:$version:macosx-x86_64-gpu"
javacppPlatformGpu "$group:mxnet:$version:windows-x86_64-gpu"
testRuntimeOnly "org.bytedeco:javacpp:$javacppVersion:$javacppPlatform"
testImplementation 'junit:junit:4.13.1'
}

tasks.withType(org.bytedeco.gradle.javacpp.BuildTask) {
includePath = ["$buildDir/$javacppPlatform$javacppPlatformExtension/include"]
linkPath = ["$buildDir/$javacppPlatform$javacppPlatformExtension/lib"]
preloadPath = ["$buildDir/$javacppPlatform$javacppPlatformExtension/bin"]
}

javacppBuildCommand {
buildCommand = ['bash', 'build.sh']
}

javacppBuildParser {
classOrPackageNames = ['org.apache.mxnet.internal.c_api.presets.*']
outputDirectory = file("$buildDir/generated/sources/javacpp/")
}

javacppBuildCompiler {
copyLibs = true
}

task copyLicenses(type: Copy) {
from(["$projectDir/..", "$projectDir/../tools/dependencies/"]) {
include 'DISCLAIMER-WIP'
include 'LICENSE'
include 'NOTICE'
include 'LICENSE.binary.dependencies'
}
into "$buildDir/resources/main/META-INF"
}

jar {
dependsOn copyLicenses
manifest {
attributes 'Class-Path': configurations.runtimeClasspath.collect { it.getName() }.join(' ')
}
}

javadoc {
failOnError = false
options.links = ['http://bytedeco.org/javacpp/apidocs']
}

//doesn't work with Gradle 5.x
//java {
// withJavadocJar()
// withSourcesJar()
//}

task javadocJar(type: Jar, dependsOn: javadoc) {
classifier = 'javadoc'
from javadoc.destinationDir
}

task sourcesJar(type: Jar, dependsOn: classes) {
classifier = 'sources'
from sourceSets.main.allSource
}

artifacts {
archives javadocJar
archives sourcesJar
}

def pomClosure = {
name = 'Apache MXNet Java'
delegate.description = 'Apache MXNet Java package and language binding'
url = 'https://mxnet.apache.org/'
licenses {
license {
name = 'Apache License, Version 2.0'
url = 'http://www.apache.org/licenses/LICENSE-2.0'
distribution = 'repo'
}
}
developers {
developer {
name = 'Contributors'
email = '[email protected]'
organization = 'Apache MXNet'
organizationUrl = 'https://mxnet.apache.org/'
}
}
scm {
url = 'https://github.com/apache/incubator-mxnet'
connection = 'scm:git:git://github.com/apache/incubator-mxnet.git'
developerConnection = 'scm:git:ssh://[email protected]/apache/incubator-mxnet.git'
}
}

publishing {
publications {
mavenJava(MavenPublication) {
from components.java
artifacts = [jar, javacppJar, javadocJar, sourcesJar] +
javacppBuild.existingArtifacts(configurations.javacppPlatform) +
javacppBuild.existingArtifacts(configurations.javacppPlatformGpu)
pom pomClosure
}
mavenJavacppPlatform(MavenPublication) {
groupId project.group
artifactId project.name + "-platform"
artifacts = [javacppPlatformJar, javacppPlatformJavadocJar, javacppPlatformSourcesJar]
pom pomClosure
pom.withXml javacppBuild.xmlAction(configurations.javacppPlatform)
}
mavenJavacppPlatformGpu(MavenPublication) {
groupId project.group
artifactId project.name + "-platform-gpu"
artifacts = [javacppPlatformJar, javacppPlatformJavadocJar, javacppPlatformSourcesJar]
pom pomClosure
pom.withXml javacppBuild.xmlAction(configurations.javacppPlatformGpu, "-gpu")
}
}
repositories {
maven {
def releasesRepoUrl = 'https://oss.sonatype.org/service/local/staging/deploy/maven2/'
def snapshotsRepoUrl = 'https://repository.apache.org/content/groups/snapshots/'
url = version.endsWith('SNAPSHOT') ? snapshotsRepoUrl : releasesRepoUrl
credentials {
username System.getenv('CI_DEPLOY_USERNAME')
password System.getenv('CI_DEPLOY_PASSWORD')
}
}
}
}

signing {
useGpgCmd()
if (!version.endsWith('SNAPSHOT')) {
sign publishing.publications.mavenJava
sign publishing.publications.mavenJavacppPlatform
sign publishing.publications.mavenJavacppPlatformGpu
}
}
37 changes: 37 additions & 0 deletions java/build.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
#!/bin/bash
set -e

if [[ -n "$MXNET_LIBRARY_PATH" ]]; then
echo Found MXNET_LIBRARY_PATH=$MXNET_LIBRARY_PATH
mkdir -p build/$PLATFORM$PLATFORM_EXTENSION/lib
cp -RLf ../include build/$PLATFORM$PLATFORM_EXTENSION/include
cp $MXNET_LIBRARY_PATH build/$PLATFORM$PLATFORM_EXTENSION/lib
exit 0
fi

mkdir -p build/$PLATFORM$PLATFORM_EXTENSION/cmake
pushd build/$PLATFORM$PLATFORM_EXTENSION/cmake

if [[ -d "C:/msys64" ]] && [[ -z ${OpenBLAS_home:-} ]]; then
export OpenBLAS_HOME=C:/msys64/mingw64/include/OpenBLAS/
export OpenBLAS=C:/msys64/mingw64/lib/
fi

CMAKE_FLAGS=
if [[ -d "${VCINSTALLDIR:-}" ]] && which ninja; then
export CC="cl.exe"
export CXX="cl.exe"
CMAKE_FLAGS="-G Ninja -DCMAKE_CUDA_FLAGS=-Xcompiler=-bigobj"
fi

GPU_FLAGS="-DUSE_CUDA=OFF"
if [[ "$PLATFORM_EXTENSION" == *gpu ]]; then
GPU_FLAGS="-DUSE_CUDA=ON -DMXNET_CUDA_ARCH=3.5"
fi

cmake $CMAKE_FLAGS -DCMAKE_BUILD_TYPE=Distribution -DCMAKE_INSTALL_PREFIX=$(pwd)/.. -DCMAKE_INSTALL_LIBDIR=lib $GPU_FLAGS -DUSE_OPENCV=OFF $(dirs +1)/..
cmake $(dirs +1)/..
cmake --build . --parallel $(getconf _NPROCESSORS_ONLN)
cmake --install .

popd
12 changes: 12 additions & 0 deletions java/settings.gradle
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
pluginManagement {
repositories {
mavenLocal()
mavenCentral()
maven { url 'https://oss.sonatype.org/content/repositories/snapshots/' }
gradlePluginPortal()
}
}

rootProject.name = 'mxnet'

gradle.rootProject { ext.javacppVersion = '1.5.5-SNAPSHOT' }
66 changes: 66 additions & 0 deletions java/src/main/java/org/apache/mxnet/internal/c_api/mxnet.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,66 @@
/*
* 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
*
* http://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.mxnet.internal.c_api.presets;

import org.bytedeco.javacpp.annotation.Platform;
import org.bytedeco.javacpp.annotation.Properties;
import org.bytedeco.javacpp.tools.Info;
import org.bytedeco.javacpp.tools.InfoMap;
import org.bytedeco.javacpp.tools.InfoMapper;

/**
*
* @author Samuel Audet
*/
@Properties(
value = {
@Platform(
value = {"linux", "macosx", "windows"},
compiler = "cpp11",
define = {"DMLC_USE_CXX11 1", "MSHADOW_USE_CBLAS 1", "MSHADOW_IN_CXX11 1", "MSHADOW_USE_CUDA 0", "MSHADOW_USE_F16C 0", "MXNET_USE_TVM_OP 0"},
include = {"dlpack/dlpack.h", "mxnet/c_api.h", "mxnet/runtime/c_runtime_api.h", "nnvm/c_api.h"},
link = "mxnet",
linkpath = {"/usr/lib64/", "/usr/lib/", "/usr/local/lib/"},
preload = {"[email protected]", "[email protected]", "[email protected]"},
preloadpath = {"/usr/local/lib/gcc/10/", "/usr/local/lib/gcc/9/", "/usr/local/lib/gcc/8/",
"/usr/local/lib/gcc/7/", "/usr/local/lib/gcc/6/", "/usr/local/lib/gcc/5/"}
),
@Platform(
value = "windows",
link = "libmxnet",
preload = {"libwinpthread-1", "libgcc_s_seh-1", "libgfortran-5", "libgfortran-4", "libgfortran-3", "libopenblas"},
preloadpath = "C:/msys64/mingw64/bin/"
)
},
target = "org.apache.mxnet.internal.c_api",
global = "org.apache.mxnet.internal.c_api.global.mxnet"
)
public class mxnet implements InfoMapper {

public void map(InfoMap infoMap) {
infoMap.put(new Info("MSHADOW_USE_F16C", "MXNET_USE_TVM_OP").define(false))
.put(new Info("DLPACK_EXTERN_C", "DLPACK_DLL", "MXNET_EXTERN_C", "MXNET_DLL", "NNVM_DLL", "MXNDArrayCreateEx").cppTypes().annotations())
.put(new Info("MXNDArrayCreateSparseEx64", "MXNDArrayGetAuxNDArray64", "MXNDArrayGetAuxType64",
"MXNDArrayGetShape64", "MXSymbolInferShape64", "MXSymbolInferShapePartial64").skip())
.put(new Info("NDArrayHandle", "FunctionHandle", "AtomicSymbolCreator", "CachedOpHandle", "SymbolHandle", "AtomicSymbolHandle", "ExecutorHandle",
"DataIterCreator", "DataIterHandle", "DatasetCreator", "DatasetHandle", "BatchifyFunctionCreator", "BatchifyFunctionHandle","KVStoreHandle",
"RecordIOHandle", "RtcHandle", "CudaModuleHandle", "CudaKernelHandle", "ProfileHandle", "DLManagedTensorHandle", "ContextHandle",
"EngineFnPropertyHandle", "EngineVarHandle", "MXNetFunctionHandle", "MXNetObjectHandle", "OpHandle", "SymbolHandle", "GraphHandle",
"OptimizerCreator", "OptimizerHandle", "PredictorHandle").cast().javaNames("Pointer").valueTypes("Pointer").pointerTypes("PointerPointer"));
}
}
Loading