add java ut

This commit is contained in:
zhengjun10 2021-12-24 16:26:24 +08:00
parent 22c25ec10e
commit 7add1df108
12 changed files with 315 additions and 21 deletions

View File

@ -110,7 +110,16 @@ build_lite_x86_64_jni_and_jar() {
# build jar
${LITE_JAVA_PATH}/java/gradlew clean -p ${LITE_JAVA_PATH}/
${LITE_JAVA_PATH}/java/gradlew releaseJar -p ${LITE_JAVA_PATH}/
if [[ "${ENABLE_ASAN}" == "ON" || "${ENABLE_ASAN}" == "on" ]] ; then
${LITE_JAVA_PATH}/java/gradlew releaseJar -p ${LITE_JAVA_PATH}/ -x test
else
if [[ "${MSLITE_ENABLE_TESTCASES}" == "ON" || "${MSLITE_ENABLE_TESTCASES}" == "on" ]] ; then
export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:${LITE_JAVA_PATH}/native/libs/linux_x86/
${LITE_JAVA_PATH}/java/gradlew releaseJar -p ${LITE_JAVA_PATH}/
else
${LITE_JAVA_PATH}/java/gradlew releaseJar -p ${LITE_JAVA_PATH}/ -x test
fi
fi
cp ${LITE_JAVA_PATH}/build/lib/jar/*.jar ${BASEPATH}/output/tmp/${pkg_name}/runtime/lib/
# package
@ -415,7 +424,7 @@ build_aar() {
${LITE_JAVA_PATH}/java/gradlew build -p ${LITE_JAVA_PATH}/java/common
# build new java api module
${LITE_JAVA_PATH}/java/gradlew clean -p ${LITE_JAVA_PATH}/
${LITE_JAVA_PATH}/java/gradlew build -p ${LITE_JAVA_PATH}/
${LITE_JAVA_PATH}/java/gradlew build -p ${LITE_JAVA_PATH}/ -x test
# build aar
local npu_bak=${MSLITE_ENABLE_NPU}

View File

@ -21,12 +21,19 @@ allprojects {
apply plugin: 'java'
dependencies {
testImplementation 'junit:junit:4.13'
implementation fileTree(dir: "libs", include: ["*.jar"])
implementation project(':linux_x86')
}
archivesBaseName = 'mindspore-lite-java'
test {
dependsOn 'cleanTest'
useJUnit()
}
task releaseJar(type: Jar) {
from('java/common/build/classes/java/main')
from('java/linux_x86/build/classes/java/main')

View File

@ -74,7 +74,6 @@ set(JNI_SRC
${NEW_NATIVE_DIR}/model.cpp
${NEW_NATIVE_DIR}/ms_context.cpp
${NEW_NATIVE_DIR}/ms_tensor.cpp
${NEW_NATIVE_DIR}/train_config.cpp
${NEW_NATIVE_DIR}/version.cpp
)
@ -91,7 +90,10 @@ endif()
if(SUPPORT_TRAIN)
set(LITE_TRAIN_SO_NAME mindspore-lite-train minddata-lite)
set(JNI_TRAIN_SRC ${CMAKE_CURRENT_SOURCE_DIR}/runtime/train_session.cpp)
set(JNI_TRAIN_SRC
${CMAKE_CURRENT_SOURCE_DIR}/runtime/train_session.cpp
${NEW_NATIVE_DIR}/train_config.cpp
)
add_library(mindspore-lite-train-jni SHARED ${JNI_TRAIN_SRC})
if(PLATFORM_ARM64 OR PLATFORM_ARM32)
find_library(log-lib log)

View File

@ -36,8 +36,8 @@ public class Graph {
* @param file model file.
* @return load status.
*/
public boolean Load(String file) {
this.graphPtr = load(file);
public boolean load(String file) {
this.graphPtr = loadModel(file);
return this.graphPtr != 0L;
}
@ -58,7 +58,7 @@ public class Graph {
graphPtr = 0;
}
private native long load(String file);
private native long loadModel(String file);
private native boolean free(long graphPtr);
}

View File

@ -17,11 +17,13 @@
package com.mindspore;
import java.nio.ByteBuffer;
import java.util.List;
public class MSTensor {
static {
System.loadLibrary("mindspore-lite-jni");
}
private long tensorPtr;
/**
@ -46,8 +48,9 @@ public class MSTensor {
* @param tensorName tensor name
* @param buffer tensor buffer
*/
public MSTensor(String tensorName, ByteBuffer buffer) {
this.tensorPtr = createTensor(tensorName, buffer);
public static MSTensor createTensor(String tensorName, int dataType, int[] tensorShape, ByteBuffer buffer) {
long tensorPtr = createTensorByNative(tensorName, dataType, tensorShape, buffer);
return new MSTensor(tensorPtr);
}
/**
@ -111,6 +114,9 @@ public class MSTensor {
* @return whether set data success.
*/
public boolean setData(byte[] data) {
if (data == null) {
return false;
}
return this.setData(this.tensorPtr, data, data.length);
}
@ -164,7 +170,8 @@ public class MSTensor {
return tensorPtr;
}
private native long createTensor(String tensorName, ByteBuffer buffer);
private static native long createTensorByNative(String tensorName, int dataType, int[] tesorShape,
ByteBuffer buffer);
private native int[] getShape(long tensorPtr);

View File

@ -47,6 +47,9 @@ public class Model {
* @return build status.
*/
public boolean build(Graph graph, MSContext context, TrainCfg cfg) {
if (graph == null || context == null || cfg == null) {
return false;
}
modelPtr = this.buildByGraph(graph.getGraphPtr(), context.getMSContextPtr(), cfg.getTrainCfgPtr());
return modelPtr != 0;
}
@ -63,6 +66,9 @@ public class Model {
*/
public boolean build(final MappedByteBuffer buffer, int modelType, MSContext context, char[] dec_key,
String dec_mode) {
if (context == null) {
return false;
}
modelPtr = this.buildByBuffer(buffer, modelType, context.getMSContextPtr(), dec_key, dec_mode);
return modelPtr != 0;
}
@ -76,6 +82,9 @@ public class Model {
* @return model build status.
*/
public boolean build(final MappedByteBuffer buffer, int modelType, MSContext context) {
if (context == null) {
return false;
}
modelPtr = this.buildByBuffer(buffer, modelType, context.getMSContextPtr(), null, "");
return modelPtr != 0;
}
@ -92,6 +101,9 @@ public class Model {
* @return model build status.
*/
public boolean build(String modelPath, int modelType, MSContext context, char[] dec_key, String dec_mode) {
if (context == null) {
return false;
}
modelPtr = this.buildByPath(modelPath, modelType, context.getMSContextPtr(), dec_key, dec_mode);
return modelPtr != 0;
}
@ -105,6 +117,9 @@ public class Model {
* @return build status.
*/
public boolean build(String modelPath, int modelType, MSContext context) {
if (context == null) {
return false;
}
modelPtr = this.buildByPath(modelPath, modelType, context.getMSContextPtr(), null, "");
return modelPtr != 0;
}
@ -135,6 +150,9 @@ public class Model {
* @return Whether the resize is successful.
*/
public boolean resize(List<MSTensor> inputs, int[][] dims) {
if (inputs == null || dims == null) {
return false;
}
long[] inputsArray = new long[inputs.size()];
for (int i = 0; i < inputs.size(); i++) {
inputsArray[i] = inputs.get(i).getMSTensorPtr();
@ -230,6 +248,9 @@ public class Model {
* @return Whether the model features is successfully update.
*/
public boolean updateFeatureMaps(List<MSTensor> features) {
if (features == null) {
return false;
}
long[] inputsArray = new long[features.size()];
for (int i = 0; i < features.size(); i++) {
inputsArray[i] = features.get(i).getMSTensorPtr();
@ -294,4 +315,4 @@ public class Model {
private native List<Long> getFeatureMaps(long modelPtr);
private native boolean updateFeatureMaps(long modelPtr, long[] newFeatures);
}
}

View File

@ -20,7 +20,7 @@
#include "include/api/serialization.h"
#include "include/api/types.h"
extern "C" JNIEXPORT jlong JNICALL Java_com_mindspore_Graph_load(JNIEnv *env, jobject thiz, jstring ms_file) {
extern "C" JNIEXPORT jlong JNICALL Java_com_mindspore_Graph_loadModel(JNIEnv *env, jobject thiz, jstring ms_file) {
auto graph = new (std::nothrow) mindspore::Graph();
if (graph == nullptr) {
MS_LOGE("Model new failed");
@ -35,3 +35,13 @@ extern "C" JNIEXPORT jlong JNICALL Java_com_mindspore_Graph_load(JNIEnv *env, jo
}
return jlong(graph);
}
extern "C" JNIEXPORT void JNICALL Java_com_mindspore_Graph_free(JNIEnv *env, jobject thiz, jlong graph_ptr) {
auto *pointer = reinterpret_cast<void *>(graph_ptr);
if (pointer == nullptr) {
MS_LOGE("Model pointer from java is nullptr");
return;
}
auto *lite_graph_ptr = static_cast<mindspore::Graph *>(pointer);
delete (lite_graph_ptr);
}

View File

@ -46,7 +46,6 @@ extern "C" JNIEXPORT jlong JNICALL Java_com_mindspore_Model_buildByGraph(JNIEnv
return jlong(nullptr);
}
cfg.reset(c_cfg_ptr);
auto model = new (std::nothrow) mindspore::Model();
if (model == nullptr) {
MS_LOGE("Model new failed");
@ -225,6 +224,9 @@ jlong GetTensorByInOutName(JNIEnv *env, jlong model_ptr, jstring tensor_name, bo
} else {
tensor = lite_model_ptr->GetOutputByTensorName(env->GetStringUTFChars(tensor_name, JNI_FALSE));
}
if (tensor.impl() == nullptr) {
return jlong(nullptr);
}
auto tensor_ptr = std::make_unique<mindspore::MSTensor>(tensor);
if (tensor_ptr == nullptr) {
MS_LOGE("Make ms tensor failed");

View File

@ -258,20 +258,28 @@ extern "C" JNIEXPORT jstring JNICALL Java_com_mindspore_MSTensor_tensorName(JNIE
return env->NewStringUTF(ms_tensor_ptr->Name().c_str());
}
extern "C" JNIEXPORT jlong JNICALL Java_com_mindspore_MSTensor_createTensor(JNIEnv *env, jobject thiz,
jstring tensor_name, jobject buffer) {
auto *p_data = reinterpret_cast<jbyte *>(env->GetDirectBufferAddress(buffer)); // get buffer pointer
jlong data_len = env->GetDirectBufferCapacity(buffer); // get buffer capacity
extern "C" JNIEXPORT jlong JNICALL Java_com_mindspore_MSTensor_createTensorByNative(JNIEnv *env, jobject thiz,
jstring tensor_name, jint data_type,
jintArray tensor_shape,
jobject buffer) {
auto *p_data = reinterpret_cast<jbyte *>(env->GetDirectBufferAddress(buffer));
jlong data_len = env->GetDirectBufferCapacity(buffer);
if (p_data == nullptr) {
MS_LOGE("GetDirectBufferAddress return null");
return false;
}
char *tensor_data(new char[data_len]);
char *tensor_data = new char[data_len];
memcpy(tensor_data, p_data, data_len);
int tensor_size = static_cast<jint>(data_len / sizeof(float));
std::vector<int64_t> shape = {tensor_size};
auto size = static_cast<int>(env->GetArrayLength(tensor_shape));
std::vector<int64_t> c_shape(size);
jint *shape_pointer = env->GetIntArrayElements(tensor_shape, nullptr);
for (int i = 0; i < size; i++) {
c_shape[i] = static_cast<int64_t>(shape_pointer[i]);
}
env->ReleaseIntArrayElements(tensor_shape, shape_pointer, JNI_ABORT);
auto tensor =
mindspore::MSTensor::CreateTensor(env->GetStringUTFChars(tensor_name, JNI_FALSE),
mindspore::DataType::kNumberTypeFloat32, shape, tensor_data, data_len);
static_cast<mindspore::DataType>(data_type), c_shape, tensor_data, data_len);
return jlong(tensor);
}

View File

@ -0,0 +1,27 @@
package com.mindspore;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.JUnit4;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
@RunWith(JUnit4.class)
public class GraphTest {
@Test
public void testLoadFailed() {
Graph g = new Graph();
assertFalse(g.load("./1.ms"));
}
@Test
public void testLoadSuccess() {
Graph g = new Graph();
String pro = System.getProperty("user.dir");
System.out.println("output:"+pro);
assertTrue(g.load("../test/ut/src/runtime/kernel/arm/test_data/nets/lenet_train.ms"));
g.free();
}
}

View File

@ -0,0 +1,201 @@
package com.mindspore;
import com.mindspore.config.DataType;
import com.mindspore.config.DeviceType;
import com.mindspore.config.MSContext;
import com.mindspore.config.TrainCfg;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.JUnit4;
import java.io.IOException;
import java.io.RandomAccessFile;
import java.nio.ByteBuffer;
import java.nio.FloatBuffer;
import java.nio.MappedByteBuffer;
import java.nio.channels.FileChannel;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertTrue;
@RunWith(JUnit4.class)
public class ModelTest {
@Test
public void testBuildByGraphSuccess() {
Graph g = new Graph();
assertTrue(g.load("../test/ut/src/runtime/kernel/arm/test_data/nets/lenet_train.ms"));
MSContext context = new MSContext();
context.init(1, 0);
context.addDeviceInfo(DeviceType.DT_CPU, false, 0);
TrainCfg cfg = new TrainCfg();
cfg.init();
Model liteModel = new Model();
boolean isSuccess = liteModel.build(g, context, cfg);
assertTrue(isSuccess);
liteModel.free();
}
@Test
public void testBuildByGraphFailed() {
Graph g = new Graph();
assertTrue(g.load("../test/ut/src/runtime/kernel/arm/test_data/nets/lenet_train.ms"));
MSContext context = new MSContext();
TrainCfg cfg = new TrainCfg();
Model liteModel = new Model();
boolean isSuccess = liteModel.build(g, context, cfg);
assertFalse(isSuccess);
liteModel.free();
}
@Test
public void testBuildByFileSuccess() {
String modelFile = "../test/ut/src/runtime/kernel/arm/test_data/nets/lenet_tod_infer.ms";
MSContext context = new MSContext();
context.init(1, 0);
context.addDeviceInfo(DeviceType.DT_CPU, false, 0);
Model liteModel = new Model();
boolean isSuccess = liteModel.build(modelFile, 0, context);
assertTrue(isSuccess);
liteModel.free();
}
@Test
public void testBuildByBufferSuccess() {
String fileName = "../test/ut/src/runtime/kernel/arm/test_data/nets/lenet_tod_infer.ms";
FileChannel fc = null;
MappedByteBuffer byteBuffer = null;
try {
fc = new RandomAccessFile(fileName, "r").getChannel();
byteBuffer = fc.map(FileChannel.MapMode.READ_ONLY, 0, fc.size()).load();
} catch (IOException e) {
e.printStackTrace();
}
assertNotNull(byteBuffer);
MSContext context = new MSContext();
context.init(1, 0);
context.addDeviceInfo(DeviceType.DT_CPU, false, 0);
Model liteModel = new Model();
boolean isSuccess = liteModel.build(byteBuffer, 0, context);
assertTrue(isSuccess);
liteModel.free();
}
@Test
public void testBuildByFileFailed() {
String modelFile = "../test/ut/src/runtime/kernel/arm/test_data/nets/lenet_tod_infer.ms";
MSContext context = new MSContext();
Model liteModel = new Model();
boolean isSuccess = liteModel.build(modelFile, 0, context);
assertFalse(isSuccess);
liteModel.free();
}
@Test
public void testPredictFailed() {
String modelFile = "../test/ut/src/runtime/kernel/arm/test_data/nets/lenet_tod_infer.ms";
MSContext context = new MSContext();
context.init(1, 0);
context.addDeviceInfo(DeviceType.DT_CPU, false, 0);
Model liteModel = new Model();
boolean isSuccess = liteModel.build(modelFile, 0, context);
assertTrue(isSuccess);
isSuccess = liteModel.predict();
assertFalse(isSuccess);
liteModel.free();
}
@Test
public void testPredictSuccess() {
String modelFile = "../test/ut/src/runtime/kernel/arm/test_data/nets/lenet_tod_infer.ms";
MSContext context = new MSContext();
context.init(1, 0);
context.addDeviceInfo(DeviceType.DT_CPU, false, 0);
Model liteModel = new Model();
boolean isSuccess = liteModel.build(modelFile, 0, context);
assertTrue(isSuccess);
List<MSTensor> msTensorList = liteModel.getInputs();
assertEquals(1, msTensorList.size());
for (MSTensor msTensor : msTensorList) {
byte[] temp = new byte[msTensor.elementsNum()];
msTensor.setData(temp);
}
isSuccess = liteModel.predict();
assertFalse(isSuccess);
List<MSTensor> outputs = liteModel.getOutputs();
for (MSTensor output : outputs) {
System.out.println("output-------" + output.tensorName());
}
System.out.println("");
MSTensor output = liteModel.getOutputByTensorName("Default/network-WithLossCell/_backbone-LeNet5/fc3-Dense" +
"/BiasAdd-op121");
assertEquals(80, output.size());
output = liteModel.getOutputByTensorName("Default/network-WithLossCell/_loss_fn-L1Loss/ReduceMean-op112");
assertEquals(0, output.size());
List<MSTensor> inputs = liteModel.getInputs();
for (MSTensor input : inputs) {
System.out.println(input.tensorName());
}
liteModel.free();
}
@Test
public void testResize() {
String modelFile = "../test/ut/src/runtime/kernel/arm/test_data/nets/lenet_tod_infer.ms";
MSContext context = new MSContext();
context.init(1, 0);
context.addDeviceInfo(DeviceType.DT_CPU, false, 0);
Model liteModel = new Model();
boolean isSuccess = liteModel.build(modelFile, 0, context);
List<MSTensor> inputs = liteModel.getInputs();
int[][] newShape = {{2, 32, 32, 1}};
System.out.println();
isSuccess = liteModel.resize(inputs, newShape);
assertTrue(isSuccess);
newShape[0][3] = 3;
isSuccess = liteModel.resize(inputs, newShape);
assertFalse(isSuccess);
liteModel.free();
}
@Test
public void testFeatureMap() {
String modelFile = "../test/ut/src/runtime/kernel/arm/test_data/nets/lenet_train.ms";
Graph g = new Graph();
assertTrue(g.load(modelFile));
MSContext context = new MSContext();
context.init(1, 0);
context.addDeviceInfo(DeviceType.DT_CPU, false, 0);
TrainCfg cfg = new TrainCfg();
cfg.init();
Model liteModel = new Model();
boolean isSuccess = liteModel.build(g, context, cfg);
assertTrue(isSuccess);
int[] tensorShape = {6, 5, 5, 1};
float[] tensorData = new float[6 * 5 * 5];
Arrays.fill(tensorData, 0);
ByteBuffer byteBuf = ByteBuffer.allocateDirect(6 * 5 * 5 * 4);
FloatBuffer floatBuf = byteBuf.asFloatBuffer();
floatBuf.put(tensorData);
MSTensor newTensor = MSTensor.createTensor("conv1.weight", DataType.kNumberTypeFloat32, tensorShape, byteBuf);
List<MSTensor> msTensors = new ArrayList<>();
msTensors.add(newTensor);
isSuccess = liteModel.updateFeatureMaps(msTensors);
assertTrue(isSuccess);
List<MSTensor> weights = liteModel.getFeatureMaps();
for (MSTensor weight : weights) {
if (weight.tensorName().equals("conv1.weight")) {
float[] weightData = weight.getFloatData();
assertEquals(0L, weightData[0], 0.0);
break;
}
}
newTensor.free();
liteModel.free();
}
}