LumiGuide / haskell-opencv

Haskell binding to OpenCV-3.x
Other
154 stars 44 forks source link

matAdd test fails on MacOS #123

Closed davetapley closed 5 years ago

davetapley commented 6 years ago

With #122 in stack build will complete, but stack test fails with:

      Core
    OpenCV Error: Sizes of input arguments do not match (The operation is neither 'array op array' (where arrays have the same size and the same number of channels), nor 'array op scalar', nor 'scalar op array') in arithm_op, file /tmp/opencv-20171226-51925-1cq7659/opencv-3.4.0/modules/core/src/arithm.cpp, line 659
        ArrayOps
          matAdd      different shapes:             libc++abi.dylib: terminating with uncaught exception of type cv::Exception: /tmp/opencv-20171226-51925-1cq7659/opencv-3.4.0/modules/core/src/arithm.cpp:659: error: (-209) The operation is neither 'array op array' (where arrays have the same size and the same number of channels), nor 'array op scalar', nor 'scalar op array' in function arithm_op

    test-opencv: SignalException 6
basvandijk commented 5 years ago

I can confirm the error on OS X. Note that I'm building with Nix.

The C++ exception is thrown here in OpenCV.

The question is why doesn't our exception handler catch it?

Note that the test succeeds in Linux.

@roelvandijk any ideas?

basvandijk commented 5 years ago

Getting closer:

Our process is getting signal 6 which is the SIGABRT signal. So somewhere the abort system call is called.

If we dig further we can see that abort is called in the definition of CV_THROW:

#if defined __GNUC__ && !defined __EXCEPTIONS
...
#define CV_THROW(A) abort()
...
#else
...
#define CV_THROW(A) throw A
...
#endif

We obviously need the second definition that actually throws the exception so that we can catch it.

I think the next question is figuring out why __EXCEPTIONS is undefined on OS X.

basvandijk commented 5 years ago

The __EXCEPTIONS pragma is described in the GCC docs.

Since we're building with clang the following note on the __EXCEPTIONS pragma in the clang 3.6.3 release notes might be relevant.

basvandijk commented 5 years ago

(Note I'm using clang-5.0.2).

It could be that OpenCV is using the correct definition of CV_THROW that actually throws the exception but that we are running into a similar problem as reported here.

basvandijk commented 5 years ago

More information: to find out which definition of CV_THROW was used I modified OpenCV to print which one is choosen:

sed 's/#define CV_THROW(A) abort()/#define CV_THROW(A) fprintf(stderr, "CV_THROW: calling abort..."); abort()/' \
  -i modules/core/include/opencv2/core/base.hpp
sed 's/#define CV_THROW(A) throw A/#define CV_THROW(A) fprintf(stderr, "CV_THROW: calling throw..."); throw A/' \
  -i modules/core/include/opencv2/core/base.hpp

When I run the test-suite again with this change I see the following:

nix-build -A haskellPackages.opencv
...
Test suite test-opencv: RUNNING...
opencv
  Calib3d
    calibrationMatrixValues identity:              OK
    findFundamentalMat - no points:                OK
    findFundamentalMat:                            OK
    computeCorrespondEpilines:                     OK
  Core
    ArrayOps
      matAdd      different shapes:                
        CV_THROW: calling throw...libc++abi.dylib: 
        terminating with uncaught exception of type 
        cv::Exception: OpenCV(3.4.3) 
        /tmp/nix-build-opencv-3.4.3.drv-0/source/modules/core/src/arithm.cpp:659: 
        error: (-209:Sizes of input arguments do not match) 
        The operation is neither 'array op array' (where arrays have the same size and the same number of channels), nor 'array op scalar', nor 'scalar op array' in function 'arithm_op'

test-opencv: SignalException 6
Test suite test-opencv: FAIL

So throw is actually called.

basvandijk commented 5 years ago

I created a minimal isolated test-case for this at:

https://github.com/basvandijk/darwin-cxx-exception-bug

basvandijk commented 5 years ago

After discussing this on GHC-devs Adam Sandberg Eriksson mentioned that there's an existing GHC ticket #11829 that describes the same problem. I can confirm that the work-around in the ticket fixes this issue.