android - Error: "Fatal signal 11 (SIGSEGV), code 1" when passing Mat object from java to jni function -
i running video camera using opencv
function. pass mat
object jni
function works awhile, them error:
10-10 13:03:17.978: a/libc(28693): fatal signal 11 (sigsegv), code 1, fault addr 0x9 in tid 28791 (thread-5418)
java code runs camera , calls jni function:
package com.adhamenaya; import java.util.arraylist; import org.opencv.android.baseloadercallback; import org.opencv.android.camerabridgeviewbase; import org.opencv.android.camerabridgeviewbase.cvcameraviewframe; import org.opencv.android.camerabridgeviewbase.cvcameraviewlistener2; import org.opencv.android.loadercallbackinterface; import org.opencv.android.opencvloader; import org.opencv.core.mat; //import org.opencv.highgui.highgui; import org.opencv.imgproc.imgproc; import android.app.activity; import android.os.bundle; import android.os.handler; import android.util.log; import android.view.motionevent; import android.view.surfaceview; import android.view.view; import android.view.view.ontouchlistener; import android.view.windowmanager; public class mainactivity extends activity implements cvcameraviewlistener2, ontouchlistener { private static final string tag = "ocvsample::activity"; private mat mrgba; private mat mgray; private camerabridgeviewbase mopencvcameraview; private arraylist<mat> mats = new arraylist<mat>(); private baseloadercallback mloadercallback = new baseloadercallback(this) { @override public void onmanagerconnected(int status) { switch (status) { case loadercallbackinterface.success: { log.i(tag, "opencv loaded successfully"); mopencvcameraview.enableview(); mopencvcameraview.setontouchlistener(mainactivity.this); } break; default: { super.onmanagerconnected(status); } break; } } }; public mainactivity() { log.i(tag, "instantiated new " + this.getclass()); } @override protected void oncreate(bundle savedinstancestate) { log.i(tag, "called oncreate"); super.oncreate(savedinstancestate); native.loadlibs(); mopencvcameraview = (camerabridgeviewbase) findviewbyid(r.id.cam_view); mopencvcameraview.setvisibility(surfaceview.visible); mopencvcameraview.setcvcameraviewlistener(this); native.setup(mfacecascadefile, mnosecascadefile, mlandmarks); } @override public void onpause() { super.onpause(); if (mopencvcameraview != null) mopencvcameraview.disableview(); } @override public void onresume() { super.onresume(); opencvloader.initasync(opencvloader.opencv_version_2_4_3, this, mloadercallback); } public void ondestroy() { super.ondestroy(); if (mopencvcameraview != null) mopencvcameraview.disableview(); } public void oncameraviewstarted(int width, int height) { mgray = new mat(); mrgba = new mat(); } public void oncameraviewstopped() { } public mat oncameraframe(cvcameraviewframe inputframe) { mrgba = inputframe.rgba(); imgproc.cvtcolor(mrgba, mgray, imgproc.color_bgra2gray); native.runjni(mfacecascadefile, mnosecascadefile, mlandmarks, mrgba.getnativeobjaddr()); return mrgba; } @override public boolean ontouch(view v, motionevent event) { // todo auto-generated method stub return false; } }
jni function:
jniexport jbytearray jnicall java_com_adhamenaya_native_runjni(jnienv * env, jobject obj, jstring facecascadefile, jstring nosecascadefile, jstring landmarks, jlong frame) { cv::mat& inframe = *(cv::mat*) frame; if (!gsys.loadfacecascade(facecascadefnamestr)) { log("could not load face cascade"); gsys.loadfacecascade(facecascadefnamestr); } else { log("face cascade: ok"); } if (!gsys.loadnosecascade(nosecascadefnamestr)) { log("could not load nose cascade"); gsys.loadnosecascade(nosecascadefnamestr); } else { log("nose cascade: ok"); } gsys.setframerate(30); gsys.setprogramstate(detect); clock_t tin, tout = 0; cv::flip(inframe, inframe, 0); cv::transpose(inframe, inframe); dlib::shape_predictor pose_model; dlib::deserialize(landmarksstr) >> pose_model; gsys.setcurrentframe(inframe); tin = clock(); trigger_hr(gsys, faces, pose_model); // process frame size_t spm; float motionstrengthx, motionstrengthy; float phiyaw = -0xffffffff, thetapitch = -0xffffffff; if (faces.size()) { faces[0].getspm(gsys, spm, motionstrengthx, motionstrengthy); faces[0].getfacepose(phiyaw, thetapitch); } tout = tout + clock() - tin; if ((gsys.getframecount() % 30) == 29) { double secs_between_frames = (double) (tout) / (clocks_per_sec * 30.0f); printf("fps = %2.2f\n", 1.0f / secs_between_frames); log("fps = %2.2f ", 1.0f / secs_between_frames); tout = 0; } char spmtext[100]; //sprintf(spmtext, // "spm = %zu, p = %2.2f, t = %2.2f, ms-x = %2.2f, ms-y = %2.2f", spm, // phiyaw, thetapitch, motionstrengthx, motionstrengthy); log("spm = %zu, p = %2.2f, t = %2.2f, ms-x = %2.2f, ms-y = %2.2f", spm, phiyaw, thetapitch, motionstrengthx, motionstrengthy); std::string str; str = "spm="; jbytearray arr = env->newbytearray(str.length()); env->setbytearrayregion(arr, 0, str.length(), (jbyte*) str.c_str()); return arr; }
kindly me.
after 2 days of searching online, figure out problem because of 'memory leak', , happens when reading frames video , send them jni
function, without releasing frames after finishing working on them, have frames in memory.
what did move mat object in c++
code outside scope of function , make class scope object, not create new object each time function called.
also, called:
inframe.release();
to free memory after finishing working on it.
Comments
Post a Comment