My personal choice would be to flatten the 2D array first and return a pointer to that, if some other container wasn't available.
I believe someone demonstrated this but it bears repeating:
Not a complete example at all, but I think you should use or build a matrix class.
stupidmatrix (std::size_t rowheight, std::size_t colwidth):
_impl(new int [_rows*_cols])
//If you had an existing 2D-array, you could just allocate a new pointer like this,
//copy the data over, and then delete and reassign the old pointer. Try this assignment
//in a loop:
//newp[row*_rows+i] = oldp[row][i];
int * get ()
int * _impl;
const std::size_t _rows;
const std::size_t _cols;