在通过引用传递的函子中崩溃调整堆栈分配的ArrayXf的大小

时间:2019-05-29 21:06:18

标签: crash pass-by-reference eigen

我有毛茸茸的代码,该代码在通过引用传递的数组调整大小时崩溃。我想问一下是否有一些明显的原因被我忽略了,然后再尝试自己找出原因:

void myFunc(Eigen::ArrayXf& a){ a.resize(100); }

{
   Eigen::ArrayXf aa(5);
   myFunc(aa); 
}
  1. 使用ArrayXf aa(5);,当删除旧存储时会发生崩溃(下面是第一个堆栈跟踪)。

  2. 如果我将aa保留为未初始化(ArrayXf aa;),则大小调整成功(我认为不能删除),但是当aa超出范围时会发生崩溃(下面的第二个堆栈跟踪)。

  3. 如果我立即将aa初始化为新大小(ArrayXf aa(100);),则调整大小不会执行任何操作,也不会崩溃。

为确保它与对齐方式无关,我正在使用-DEIGEN_MAX_ALIGN_BYTES=0进行编译。

明显有问题吗?

我正在将Eigen 3.3.4与gcc 7.4和-std=gnu++1z(c ++ 17)结合使用。


用于从非零原始大小调整大小的堆栈跟踪(正在调整aa的大小):

    | Source "/usr/include/eigen3/Eigen/src/Core/CwiseNullaryOp.h", line 517, in resize
    |   515: PlainObjectBase<Derived>::setZero(Index newSize)
    |   516: {
    | > 517:   resize(newSize);
    |   518:   return setConstant(Scalar(0));
    |   519: }
    | Source "/usr/include/eigen3/Eigen/src/Core/PlainObjectBase.h", line 319, in resize
    |   317:         m_storage.resize(size, 1, size);
    |   318:       else
    | > 319:         m_storage.resize(size, size, 1);
    |   320:       #ifdef EIGEN_INITIALIZE_COEFFS
    |   321:         if(size_changed) EIGEN_INITIALIZE_COEFFS_IF_THAT_OPTION_IS_ENABLED
    | Source "/usr/include/eigen3/Eigen/src/Core/DenseStorage.h", line 555, in conditional_aligned_delete_auto<float, true>
    |   553:       if(size != m_rows*_Cols)
    |   554:       {
    | > 555:         internal::conditional_aligned_delete_auto<T,(_Options&DontAlign)==0>(m_data, _Cols*m_rows);
    |   556:         if (size)
    |   557:           m_data = internal::conditional_aligned_new_auto<T,(_Options&DontAlign)==0>(size);
    | Source "/usr/include/eigen3/Eigen/src/Core/util/Memory.h", line 416, in conditional_aligned_free<true>
    |   414:   if(NumTraits<T>::RequireInitialization)
    |   415:     destruct_elements_of_array<T>(ptr, size);
    | > 416:   conditional_aligned_free<Align>(ptr);
    |   417: }
    | Source "/usr/include/eigen3/Eigen/src/Core/util/Memory.h", line 230, in aligned_free
    |   228: template<bool Align> EIGEN_DEVICE_FUNC inline void conditional_aligned_free(void *ptr)
    |   229: {
    | > 230:   aligned_free(ptr);
    |   231: }
    | Source "/usr/include/eigen3/Eigen/src/Core/util/Memory.h", line 179, in handmade_aligned_free
    |   177:     std::free(ptr);
    |   178:   #else
    | > 179:     handmade_aligned_free(ptr);
    |   180:   #endif
    |   181: }
      Source "/usr/include/eigen3/Eigen/src/Core/util/Memory.h", line 98, in psdCurve [0x7f1c39ac790f]
         95: /** \internal Frees memory allocated with handmade_aligned_malloc */
         96: inline void handmade_aligned_free(void *ptr)
         97: {
      >  98:   if (ptr) std::free(*(reinterpret_cast<void**>(ptr) - 1));
         99: }
        100: 
        101: /** \internal
#0    Source "/build/glibc-OTsEL5/glibc-2.27/malloc/malloc.c", line 3103, in __libc_free [0x7f1c341a598d]
Segmentation fault (Address not mapped to object [0x1d])

用于从零原始大小调整大小的堆栈跟踪(当aa超出范围时):

    | Source "/usr/include/eigen3/Eigen/src/Core/Array.h", line 45, in ~PlainObjectBase
    |    43:   */
    |    44: template<typename _Scalar, int _Rows, int _Cols, int _Options, int _MaxRows, int _MaxCols>
    | >  45: class Array
    |    46:   : public PlainObjectBase<Array<_Scalar, _Rows, _Cols, _Options, _MaxRows, _MaxCols> >
    |    47: {
    | Source "/usr/include/eigen3/Eigen/src/Core/PlainObjectBase.h", line 98, in ~DenseStorage
    |    96: #else
    |    97: template<typename Derived>
    | >  98: class PlainObjectBase : public internal::dense_xpr_base<Derived>::type
    |    99: #endif
    |   100: {
    | Source "/usr/include/eigen3/Eigen/src/Core/DenseStorage.h", line 542, in conditional_aligned_delete_auto<float, true>
    |   540:     }
    |   541: #endif
    | > 542:     EIGEN_DEVICE_FUNC ~DenseStorage() { internal::conditional_aligned_delete_auto<T,(_Options&DontAlign)==0>(m_data, _Cols*m_rows); }
    |   543:     EIGEN_DEVICE_FUNC void swap(DenseStorage& other) { std::swap(m_data,other.m_data); std::swap(m_rows,other.m_rows); }
    |   544:     EIGEN_DEVICE_FUNC Index rows(void) const {return m_rows;}
    | Source "/usr/include/eigen3/Eigen/src/Core/util/Memory.h", line 416, in conditional_aligned_free<true>
    |   414:   if(NumTraits<T>::RequireInitialization)
    |   415:     destruct_elements_of_array<T>(ptr, size);
    | > 416:   conditional_aligned_free<Align>(ptr);
    |   417: }
    | Source "/usr/include/eigen3/Eigen/src/Core/util/Memory.h", line 230, in aligned_free
    |   228: template<bool Align> EIGEN_DEVICE_FUNC inline void conditional_aligned_free(void *ptr)
    |   229: {
    | > 230:   aligned_free(ptr);
    |   231: }
      Source "/usr/include/eigen3/Eigen/src/Core/util/Memory.h", line 177, in psdAnalysisFinished [0x559b6c49c931]
        174: EIGEN_DEVICE_FUNC inline void aligned_free(void *ptr)
        175: {
        176:   #if (EIGEN_DEFAULT_ALIGN_BYTES==0) || EIGEN_MALLOC_ALREADY_ALIGNED
      > 177:     std::free(ptr);
        178:   #else
        179:     handmade_aligned_free(ptr);
        180:   #endif
#4  | Source "/build/glibc-OTsEL5/glibc-2.27/malloc/malloc.c", line 3124, in _int_free
      Source "/build/glibc-OTsEL5/glibc-2.27/malloc/malloc.c", line 4278, in __libc_free [0x7fa3a40e4e74]
#3    Source "/build/glibc-OTsEL5/glibc-2.27/malloc/malloc.c", line 5350, in malloc_printerr [0x7fa3a40dd909]
#2    Source "../sysdeps/posix/libc_fatal.c", line 181, in __stack_chk_fail [0x7fa3a40d6896]
#1    Source "/build/glibc-OTsEL5/glibc-2.27/stdlib/abort.c", line 79, in abort [0x7fa3a408d800]
#0    Source "../sysdeps/unix/sysv/linux/raise.c", line 51, in raise [0x7fa3a408be97]
Aborted (Signal sent by tkill() 1509 1000)

0 个答案:

没有答案