c++functiontemplatesoverloadingfirst-chance-exception

Exception being raised as I enter into function before code can be executed


As always, I'm probably missing something obvious here. I can't post the entire source code, because it's work-related but I have a templated Matrix class with a mulMM (multiply Matrix by Matrix) function and a mulMT function (multiply matrix by transpose matrix). That already exists in the code. I am trying to add a mulMT function that specializes for single precision Floating point values. I have a similar specialization, mulMM which shares the same first two function parameters. Here is some example code:

#ifdef TARGET_x86_SSE4

template <> 
Matrix<Float>&  Matrix<Float>::mulMM (const Matrix<Float>& mat1, 
                                      const Matrix<Float>& mat2);

template <> 
Matrix<Float>&  Matrix<Float>::mulMT (const Matrix<Float>& mat1, 
                                      const Matrix<Float>& mat2,
                                      const bool softmax);

#endif // no SSE4: use template generic

template <class BT> 
Matrix<BT>&  Matrix<BT>::mulMM (const Matrix<BT>& mat1, 
                                const Matrix<BT>& mat2) {
  // Function code
}

template <class BT> 
Matrix<BT>&  Matrix<BT>::mulMT (const Matrix<BT>& mat1, 
                                const Matrix<BT>& mat2,
                                const bool softmax) {
  // Function code
}

Then, in a separate file:

#ifdef TARGET_x86_SSE4

template <> 
Matrix<Float>&  Matrix<Float>::mulMM (const Matrix<Float>& mat1, 
                                      const Matrix<Float>& mat2) {
  // Function code
}

template <> 
Matrix<Float>&  Matrix<Float>::mulMT (const Matrix<Float>& mat1, 
                                      const Matrix<Float>& mat2, 
                                      const bool softmax) {
  // Function code
}

When I invoke the code, the mulMM correctly pulls in the values of the input matrices, but when I invoke mulMT, I wind up with random numbers for the dimensions of the matrix. Using the debugger, I can see that the matrix is properly defined when coming in, but as soon as I've stepped into the function, the values are all wrong. Here is some example code I'm using:

MatrixFloat mA(4, 5);
MatrixFloat mB(5, 4);
// Code to initialize mA and mB's values.

MatrixFloat mR = mR.mulMM(mA, mB)
// This works fine and correctly find the values for the product.

MatrixFloat mC(4, 4)
// Code to initialize mC
mR = mR.mulMT(mC, mC)
// This fails with a memory access error and stepping into the function reveals 
// that this seems to be because mC has dimensions of 84376 x 1 or thereabouts

I have tried making the two values into MT different. I've verified that, when my mulMT for Floats isn't present, the generic one works. I don't know why this is doing what it's doing.

Edit: In an effort to prove that the code inside the Float specialization was not the issue, I commented it out. Everything worked. I uncommented the code. Everything still works. I'm thinking that maybe Visual Studio just got confused and did not recompile something.

Further Edit: OK... this is very strange. When debugging, when I first step into mulMT, it drops me onto the line with const bool softmax) {. If I try F10, I get the exception. If I hit F11, it drops me into ChkStk.asm. If I exit out of that file, I'm able to access the inside of the function and everything is allocated correctly. In fact, as long as I don't recompile my test program, I can step through or run as many times as I like without error. However, if I make a change to my test program and recompile, the behavior comes back.

I am even more confused than I was at the start.

Edit: OK, after two days with no issues, it's come up again. I think that it is not, as I thought before, something involving the values changing. Instead, it's something happening before the parameters are actually instantiated. Thing is, I don't know why still, other than that this is the only function I have which drops me into stkchk.asm if I hit F11 after entering the function.

First-chance exception at 0x00789adc in UnitTest.exe: 0xC0000005: Access violation reading location 0xabababab. is the exception I get. Earlier in the function, I make an almost identical call, only varying which variables are used with the operator. Oddly enough, a try-catch block around the call does nothing to prevent the program from crashing.


Solution

  • I figured out what was going wrong. The exception was indeed happening inside of the function. Visual Studio was optimizing away the function, so unless I had a break point inside of it, it would just step over all of it. If the function ran properly, it ran properly. If there was any exception inside, it failed. Still no idea why the try catch block didn't catch it, but I'm not sweating it.

    Thank you everyone for your attempts to help. And thank you, @JBL for being right in the end.