indilib / indi-3rdparty

INDI 3rd Party drivers repository
https://www.indilib.org/devices.html
GNU Lesser General Public License v2.1
124 stars 208 forks source link

`qhy_ccd_test` segfaults with a QHY268C #954

Open wannabecoffeenerd opened 1 month ago

wannabecoffeenerd commented 1 month ago

Describe the bug qhy_ccd_test segfaults when used with a QHY268C camera when initiating a capture. The same thing happens with kstars/ekos only when capturing an image.

Here are the full logs with a debug build of qhy_ccd_test from the 2.0.8 tag and a gdb backtrace:

➜  indi-qhy git:(v2.0.8-branch) gdb ./qhy_ccd_test
GNU gdb (GDB) 15.1
Copyright (C) 2024 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.
Type "show copying" and "show warranty" for details.
This GDB was configured as "x86_64-pc-linux-gnu".
Type "show configuration" for configuration details.
For bug reporting instructions, please see:
<https://www.gnu.org/software/gdb/bugs/>.
Find the GDB manual and other documentation resources online at:
    <http://www.gnu.org/software/gdb/documentation/>.

For help, type "help".
Type "apropos word" to search for commands related to "word"...
Reading symbols from ./qhy_ccd_test...
(gdb) r
Starting program: /home/<user>/Codes/indi-3rdparty/build/indi-qhy/qhy_ccd_test 

This GDB supports auto-downloading debuginfo from the following URLs:
  <https://debuginfod.archlinux.org>
Enable debuginfod for this session? (y or [n]) y
Debuginfod has been enabled.
To make this setting permanent, add 'set debuginfod enabled on' to .gdbinit.
Downloading separate debug info for /lib64/ld-linux-x86-64.so.2
Downloading separate debug info for system-supplied DSO at 0x7ffff7fc5000                                                                                                                    
[Thread debugging using libthread_db enabled]                                                                                                                                                
Using host libthread_db library "/usr/lib/libthread_db.so.1".
QHY Test CCD using SingleFrameMode, Version: 1.00
-- qhyccd.cpp param
QHYCCD|QHYCCD.CPP|InitQHYCCDResource()|START
QHYCCD|QHYCCD.CPP|InitQHYCCDResource|auto_detect_camera:false,call InitQHYCCDResourceInside
QHYCCD|QHYCCD.CPP|InitQHYCCDResourceInside|START
[New Thread 0x7ffff70006c0 (LWP 47792)]
QHYCCD|QHYCCD.CPP|libusb_version 1.0.27.11882
QHYCCD|QHYCCD.CPP|libusb_init(libqhyccd_context) called...
QHYCCD|QHYCCD.CPP|InitQHYCCDResourceInside|numdev set to 0
QHYCCD|QHYCCD.CPP|InitQHYCCDResourceInside|END
************************** config file path  24.4.1.5 svn: 1  ************************************
QHYCCD|QHYCCD.CPP|InitQHYCCDResource|Load ini filePath = /home/<user>/Codes/indi-3rdparty/build/indi-qhy  fileName = qhyccd.ini
[New Thread 0x7ffff66006c0 (LWP 47793)]
SDK resources initialized.
Number of QHYCCD cameras found: 1 
Application connected to the following camera from the list: Index: 1,  cameraID = QHY268C-849cc34fbbedc488e
Open QHYCCD success.
SetQHYCCDStreamMode set to: 0, success.
[New Thread 0x7ffff5c006c0 (LWP 47854)]
InitQHYCCD success.
GetQHYCCDOverScanArea:
Overscan Area startX x startY : 0 x 0
Overscan Area sizeX  x sizeY  : 10 x 4176
GetQHYCCDEffectiveArea:
Effective Area startX x startY: 0 x 0
Effective Area sizeX  x sizeY : 10 x 4176
GetQHYCCDChipInfo:
Effective Area startX x startY: 0 x 0
Chip  size width x height     : 23.613 x 15.830 [mm]
Pixel size width x height     : 3.760 x 3.760 [um]
Image size width x height     : 6280 x 4210
This is a color camera.
SetQHYCCDParam CONTROL_USBTRAFFIC set to: 10, success.
SetQHYCCDParam CONTROL_GAIN set to: 10, success
SetQHYCCDParam CONTROL_GAIN set to: 140, success.
Default read mode: 0 
Default read mode name PhotoGraphic DSO 
Read mode name PhotoGraphic DSO 
GetQHYCCDChipInfo in this ReadMode: imageW: 6280 imageH: 4210 
Read mode name High Gain Mode 
GetQHYCCDChipInfo in this ReadMode: imageW: 6280 imageH: 4210 
Read mode name Extend Fullwell 
GetQHYCCDChipInfo in this ReadMode: imageW: 6280 imageH: 4210 
Read mode name Extend Fullwell 2CMS 
GetQHYCCDChipInfo in this ReadMode: imageW: 6280 imageH: 4210 
Read mode name PhotoGraphic DSO 2CMS 
GetQHYCCDChipInfo in this ReadMode: imageW: 6280 imageH: 4210 
Read mode name High Gain 2CMS 
GetQHYCCDChipInfo in this ReadMode: imageW: 0 imageH: 0 
Read mode name 12BIT High Speed Mode 
GetQHYCCDChipInfo in this ReadMode: imageW: 6280 imageH: 4210 
SetQHYCCDParam CONTROL_EXPOSURE set to: 1, success.
SetQHYCCDResolution roiStartX x roiStartY: 0 x 0
SetQHYCCDResolution roiSizeX  x roiSizeY : 6280 x 4210
SetQHYCCDBinMode set to: binX: 1, binY: 1, success.
SetQHYCCDParam CONTROL_GAIN set to: 10, success.
ExpQHYCCDSingleFrame(pCamHandle) - start...
[New Thread 0x7ffff52006c0 (LWP 47855)]
ExpQHYCCDSingleFrame(pCamHandle) - end...
ExpQHYCCDSingleFrame success (0).
[Thread 0x7ffff52006c0 (LWP 47855) exited]
Allocated memory for frame: 109991200 [uchar].

Thread 1 "qhy_ccd_test" received signal SIGSEGV, Segmentation fault.
__memset_avx2_unaligned_erms () at ../sysdeps/x86_64/multiarch/memset-vec-unaligned-erms.S:326
326     rep stosb
(gdb) bt
#0  __memset_avx2_unaligned_erms () at ../sysdeps/x86_64/multiarch/memset-vec-unaligned-erms.S:326
#1  0x00007ffff77600cf in QHYBASE::QHYCCDDemosaic(void*, unsigned int, unsigned int, unsigned int, void*, unsigned char) () from /usr/lib/libqhyccd.so.20
#2  0x00007ffff784700c in QHY268C::GetSingleFrame(void*, unsigned int*, unsigned int*, unsigned int*, unsigned int*, unsigned char*) () from /usr/lib/libqhyccd.so.20
#3  0x00007ffff773fd09 in GetQHYCCDSingleFrameInternal(void*, unsigned int*, unsigned int*, unsigned int*, unsigned int*, unsigned char*) () from /usr/lib/libqhyccd.so.20
#4  0x00007ffff774028e in GetQHYCCDSingleFrame () from /usr/lib/libqhyccd.so.20
#5  0x0000555555555fae in main () at /home/<user>/Codes/indi-3rdparty/indi-qhy/qhy_ccd_test.cpp:416
(gdb)

This looks like an error with an AVX2 vectorized memset used on an unaligned buffer based on the backtrace?

I ensured that I have the right version of fxload and that firmware is being properly loaded on the QHY camera and is detected properly with lsusb:

Bus 002 Device 005: ID 1618:c269 QHYCCD QHY268C-V230614

To Reproduce

  1. Build libqhy and indi-qhy in debug mode with version 2.0.8":

    ➜  indi-qhy git:(v2.0.8-branch) cmake -DCMAKE_INSTALL_PREFIX=/usr -DCMAKE_BUILD_TYPE=Debug ../../indi-qhy
    ➜  indi-qhy git:(v2.0.8-branch) make VERBOSE=1 # to ensure debug symbols are included
  2. Ensure QHY camera is connected and detected properly:

    ➜  indi-qhy git:(v2.0.8-branch) lsusb
    Bus 002 Device 005: ID 1618:c269 QHYCCD QHY268C-V230614

Run with gdb:

➜  indi-qhy git:(v2.0.8-branch) gdb ./qhy_ccd_test

Expected behavior qhy_ccd_test should pass without errors.

Desktop (please complete the following information):

wannabecoffeenerd commented 1 month ago

Since the backtrace was pointing to a segfault in the QHY SDK, I downloaded the latest version of the QHY SDK and installed it. Runnng the SingleFrameMode test app, I don't see any errors. Might this suggest that the issue lies in how GetQHYCCDSingleFrame is called here: https://github.com/indilib/indi-3rdparty/blob/master/indi-qhy/qhy_ccd_test.cpp#L416?

Comparing it to what's in QHY SDK's SingleFrameSample.cpp:

ret = GetQHYCCDSingleFrame(camhandle,&w,&h,&bpp,&channels,ImgData);
if(ret == QHYCCD_SUCCESS)
{
    printf("GetQHYCCDSingleFrame succeess! \n");
}
else
{
    printf("GetQHYCCDSingleFrame fail:%d\n",ret);
}

Looks the same and AFAICT how ImgData and pImgData and all the parameters are allocated and passed in are identical with the only minor exception being that the sample uses malloc and qhy_ccd_test uses new []. Not a very actionable comment but hopefully is useful to someone that's more familiar with the code.

wannabecoffeenerd commented 1 month ago

cc @knro for viz