Compare commits
14 Commits
86eb2b8ba7
...
master
| Author | SHA1 | Date | |
|---|---|---|---|
| 99e072be78 | |||
| 69bba48ce1 | |||
| ea9b099d81 | |||
| 0ece075bb8 | |||
|
|
f068cbb44b | ||
| 77131074e7 | |||
| 66e0b6c71e | |||
| 610d09ee98 | |||
| bb28f0aa03 | |||
| 34959c632d | |||
| 6c45f04448 | |||
| b570a4e7ea | |||
| 50e457f046 | |||
| 3fee70b445 |
@@ -18,33 +18,50 @@ find_package(cxxopts CONFIG)
|
|||||||
|
|
||||||
set(RAPTOR_EAGLEV_LIB raptor_eaglev)
|
set(RAPTOR_EAGLEV_LIB raptor_eaglev)
|
||||||
|
|
||||||
option(STATIC_LIB "Create static '${RAPTOR_EAGLEV_LIB}' library" OFF)
|
option(RAPROT_SHARED_LIB "Create shared '${RAPTOR_EAGLEV_LIB}' library" OFF)
|
||||||
|
|
||||||
set(RAPTOR_EAGLEV_LIB_SRC
|
set(RAPTOR_EAGLEV_LIB_SRC
|
||||||
raptor_eagle_ccd.h raptor_eagle_ccd.cpp
|
raptor_eagle_ccd.h
|
||||||
|
raptor_eagle_ccd.cpp
|
||||||
raptor_eagle_cameralink.h
|
raptor_eagle_cameralink.h
|
||||||
raptor_eagle_exception.h
|
raptor_eagle_exception.h
|
||||||
raptor_eagle_acqproc.cpp)
|
raptor_eagle_acqproc.cpp)
|
||||||
|
|
||||||
if (STATIC_LIB)
|
if (RAPROT_SHARED_LIB)
|
||||||
add_library(${RAPTOR_EAGLEV_LIB} STATIC ${RAPTOR_EAGLEV_LIB_SRC})
|
|
||||||
else()
|
|
||||||
add_library(${RAPTOR_EAGLEV_LIB} SHARED ${RAPTOR_EAGLEV_LIB_SRC})
|
add_library(${RAPTOR_EAGLEV_LIB} SHARED ${RAPTOR_EAGLEV_LIB_SRC})
|
||||||
# add_library(${RAPTOR_EAGLEV_LIB} SHARED
|
else()
|
||||||
# raptor_eagle_ccd.h raptor_eagle_ccd.cpp
|
add_library(${RAPTOR_EAGLEV_LIB} STATIC ${RAPTOR_EAGLEV_LIB_SRC})
|
||||||
# raptor_eagle_cameralink.h
|
|
||||||
# raptor_eagle_exception.h
|
|
||||||
# raptor_eagle_acqproc.cpp)
|
|
||||||
endif()
|
endif()
|
||||||
|
|
||||||
|
# include(FetchContent)
|
||||||
|
# include(ExternalProject)
|
||||||
|
|
||||||
|
# FetchContent_Declare(spdlog
|
||||||
|
# # SOURCE_DIR ${CMAKE_BINARY_DIR}/spdlog
|
||||||
|
# # BINARY_DIR ${CMAKE_BINARY_DIR}/spdlog/build
|
||||||
|
# GIT_REPOSITORY "https://github.com/gabime/spdlog.git"
|
||||||
|
# GIT_TAG "v1.15.0"
|
||||||
|
# GIT_SHALLOW TRUE
|
||||||
|
# GIT_SUBMODULES ""
|
||||||
|
# GIT_PROGRESS TRUE
|
||||||
|
# )
|
||||||
|
# FetchContent_MakeAvailable(spdlog)
|
||||||
|
# FetchContent_GetProperties(spdlog SOURCE_DIR spdlog_SOURCE_DIR)
|
||||||
|
# set(spdlog_INCLUDE_DIR ${spdlog_SOURCE_DIR}/include)
|
||||||
|
|
||||||
|
|
||||||
# to activate spdlog-library support in ADC-library
|
# to activate spdlog-library support in ADC-library
|
||||||
# target_compile_definitions(${RAPTOR_EAGLEV_LIB} PRIVATE USE_ASIO_LIBRARY USE_SPDLOG_LIBRARY USE_OPENSSL_WITH_ASIO)
|
# target_compile_definitions(${RAPTOR_EAGLEV_LIB} PRIVATE USE_ASIO_LIBRARY USE_SPDLOG_LIBRARY USE_OPENSSL_WITH_ASIO)
|
||||||
target_compile_definitions(${RAPTOR_EAGLEV_LIB} PUBLIC USE_ASIO_LIBRARY USE_SPDLOG_LIBRARY)
|
target_compile_definitions(${RAPTOR_EAGLEV_LIB} PUBLIC USE_ASIO_LIBRARY USE_SPDLOG_LIBRARY)
|
||||||
|
target_compile_definitions(${RAPTOR_EAGLEV_LIB} PUBLIC SPDLOG_USE_STD_FORMAT)
|
||||||
|
|
||||||
# !!!!! TEMPORARY !!!!!
|
# !!!!! TEMPORARY !!!!!
|
||||||
target_include_directories(${RAPTOR_EAGLEV_LIB} PUBLIC "../ADC/")
|
target_include_directories(${RAPTOR_EAGLEV_LIB} PUBLIC "../ADC/")
|
||||||
target_include_directories(${RAPTOR_EAGLEV_LIB} PUBLIC ${XCLIB_INCLUDE_DIR} ${CFITSIO_INCLUDE_DIR})
|
target_include_directories(${RAPTOR_EAGLEV_LIB} PUBLIC ${XCLIB_INCLUDE_DIR} ${CFITSIO_INCLUDE_DIR})
|
||||||
target_link_libraries(${RAPTOR_EAGLEV_LIB} PUBLIC Threads::Threads spdlog::spdlog_header_only ${XCLIB_LIBRARIES} ${CFITSIO_LIBRARY})
|
# target_include_directories(${RAPTOR_EAGLEV_LIB} PUBLIC ${spdlog_INCLUDE_DIR})
|
||||||
|
target_include_directories(${RAPTOR_EAGLEV_LIB} PUBLIC spdlog::spdlog_header_only)
|
||||||
|
# target_link_libraries(${RAPTOR_EAGLEV_LIB} PUBLIC Threads::Threads spdlog::spdlog_header_only ${XCLIB_LIBRARIES} ${CFITSIO_LIBRARY})
|
||||||
|
target_link_libraries(${RAPTOR_EAGLEV_LIB} PUBLIC Threads::Threads ${XCLIB_LIBRARIES} ${CFITSIO_LIBRARY})
|
||||||
|
|
||||||
|
|
||||||
set(RAPTOR_EAGLEV_SERVER raptor_eaglev_server)
|
set(RAPTOR_EAGLEV_SERVER raptor_eaglev_server)
|
||||||
@@ -52,12 +69,24 @@ add_executable(${RAPTOR_EAGLEV_SERVER} raptor_eaglev_server.cpp)
|
|||||||
target_link_libraries(${RAPTOR_EAGLEV_SERVER} PUBLIC ${RAPTOR_EAGLEV_LIB} cxxopts::cxxopts)
|
target_link_libraries(${RAPTOR_EAGLEV_SERVER} PUBLIC ${RAPTOR_EAGLEV_LIB} cxxopts::cxxopts)
|
||||||
|
|
||||||
include(GNUInstallDirs)
|
include(GNUInstallDirs)
|
||||||
install(TARGETS ${RAPTOR_EAGLEV_LIB}
|
if (RAPROT_SHARED_LIB) # install shared library and server binary
|
||||||
LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
|
install(TARGETS ${RAPTOR_EAGLEV_LIB} ${RAPTOR_EAGLEV_SERVER}
|
||||||
RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
|
LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
|
||||||
)
|
RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
|
||||||
# install(TARGETS ${RAPTOR_EAGLEV_LIB} ${RAPTOR_EAGLEV_SERVER}
|
)
|
||||||
# LIBRARY DESTINATION "/home/obs/TMP"
|
else()
|
||||||
# ARCHIVE DESTINATION "/home/obs/TMP"
|
install(TARGETS ${RAPTOR_EAGLEV_SERVER}
|
||||||
# RUNTIME DESTINATION "/home/obs/TMP"
|
RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
|
||||||
# )
|
)
|
||||||
|
endif()
|
||||||
|
|
||||||
|
# uninstall target
|
||||||
|
if(NOT TARGET uninstall)
|
||||||
|
configure_file(
|
||||||
|
"${CMAKE_CURRENT_SOURCE_DIR}/cmake_uninstall.cmake.in"
|
||||||
|
"${CMAKE_CURRENT_BINARY_DIR}/cmake_uninstall.cmake"
|
||||||
|
IMMEDIATE @ONLY)
|
||||||
|
|
||||||
|
add_custom_target(uninstall
|
||||||
|
COMMAND ${CMAKE_COMMAND} -P ${CMAKE_CURRENT_BINARY_DIR}/cmake_uninstall.cmake)
|
||||||
|
endif()
|
||||||
|
|||||||
19
cmake_uninstall.cmake.in
Normal file
19
cmake_uninstall.cmake.in
Normal file
@@ -0,0 +1,19 @@
|
|||||||
|
if(NOT EXISTS "@CMAKE_BINARY_DIR@/install_manifest.txt")
|
||||||
|
message(FATAL_ERROR "Cannot find install manifest: @CMAKE_BINARY_DIR@/install_manifest.txt")
|
||||||
|
endif()
|
||||||
|
|
||||||
|
file(READ "@CMAKE_BINARY_DIR@/install_manifest.txt" files)
|
||||||
|
string(REGEX REPLACE "\n" ";" files "${files}")
|
||||||
|
foreach(file ${files})
|
||||||
|
message(STATUS "Uninstalling $ENV{DESTDIR}${file}")
|
||||||
|
if(IS_SYMLINK "$ENV{DESTDIR}${file}" OR EXISTS "$ENV{DESTDIR}${file}")
|
||||||
|
exec_program("@CMAKE_COMMAND@" ARGS "-E remove \"$ENV{DESTDIR}${file}\""
|
||||||
|
OUTPUT_VARIABLE rm_out
|
||||||
|
RETURN_VALUE rm_retval)
|
||||||
|
if(NOT "${rm_retval}" STREQUAL 0)
|
||||||
|
message(FATAL_ERROR "Problem when removing $ENV{DESTDIR}${file}")
|
||||||
|
endif(NOT "${rm_retval}" STREQUAL 0)
|
||||||
|
else()
|
||||||
|
message(STATUS "File $ENV{DESTDIR}${file} does not exist.")
|
||||||
|
endif()
|
||||||
|
endforeach()
|
||||||
@@ -1,5 +1,6 @@
|
|||||||
#include <fitsio.h>
|
#include <fitsio.h>
|
||||||
#include <cmath>
|
#include <cmath>
|
||||||
|
#include <filesystem>
|
||||||
#include "raptor_eagle_ccd.h"
|
#include "raptor_eagle_ccd.h"
|
||||||
|
|
||||||
|
|
||||||
@@ -89,6 +90,11 @@ void RaptorEagleCCD::AcquisitionProcess::start(const std::shared_ptr<acq_params_
|
|||||||
|
|
||||||
isAcqInProgress = false;
|
isAcqInProgress = false;
|
||||||
|
|
||||||
|
_status = STATUS_IDLE;
|
||||||
|
// _status = std::string(CAMERA_ATTR_CAMERA_STATUS_IDLE.begin(), CAMERA_ATTR_CAMERA_STATUS_IDLE.end());
|
||||||
|
|
||||||
|
// _manager->_cameraStatus = CAMERA_ATTR_CAMERA_STATUS_IDLE;
|
||||||
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -147,6 +153,12 @@ void RaptorEagleCCD::AcquisitionProcess::start(const std::shared_ptr<acq_params_
|
|||||||
isAcqInProgress = false;
|
isAcqInProgress = false;
|
||||||
} catch (...) {
|
} catch (...) {
|
||||||
isAcqInProgress = false;
|
isAcqInProgress = false;
|
||||||
|
|
||||||
|
_status = STATUS_IDLE;
|
||||||
|
// _status = std::string(CAMERA_ATTR_CAMERA_STATUS_IDLE.begin(), CAMERA_ATTR_CAMERA_STATUS_IDLE.end());
|
||||||
|
|
||||||
|
// _manager->_cameraStatus = CAMERA_ATTR_CAMERA_STATUS_IDLE;
|
||||||
|
|
||||||
throw;
|
throw;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -155,9 +167,21 @@ void RaptorEagleCCD::AcquisitionProcess::start(const std::shared_ptr<acq_params_
|
|||||||
|
|
||||||
if (_acqParams->filename.empty()) {
|
if (_acqParams->filename.empty()) {
|
||||||
_manager->logWarn("An empty FITS filename is given! Do not save acquired image!");
|
_manager->logWarn("An empty FITS filename is given! Do not save acquired image!");
|
||||||
|
|
||||||
|
_status = STATUS_IDLE;
|
||||||
|
// _status = std::string(CAMERA_ATTR_CAMERA_STATUS_IDLE.begin(), CAMERA_ATTR_CAMERA_STATUS_IDLE.end());
|
||||||
|
|
||||||
|
// _manager->_cameraStatus = CAMERA_ATTR_CAMERA_STATUS_IDLE;
|
||||||
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
_status = STATUS_SAVE;
|
||||||
|
// _status = std::string(CAMERA_ATTR_CAMERA_STATUS_IDLE.begin(), CAMERA_ATTR_CAMERA_STATUS_IDLE.end()) +
|
||||||
|
// std::format(" {}", _acqParams->filename);
|
||||||
|
|
||||||
|
// _manager->_cameraStatus = CAMERA_ATTR_CAMERA_STATUS_SAVE;
|
||||||
|
|
||||||
std::string fname{"!"}; // to overwrite existing file
|
std::string fname{"!"}; // to overwrite existing file
|
||||||
fname += _acqParams->filename;
|
fname += _acqParams->filename;
|
||||||
|
|
||||||
@@ -218,7 +242,9 @@ void RaptorEagleCCD::AcquisitionProcess::start(const std::shared_ptr<acq_params_
|
|||||||
fits_update_key_str(fitsFilePtr, "ORIGIN", "SAO RAS", NULL, &status);
|
fits_update_key_str(fitsFilePtr, "ORIGIN", "SAO RAS", NULL, &status);
|
||||||
fits_update_key_str(fitsFilePtr, "CREATOR", "RaptorEagleV control software", NULL, &status);
|
fits_update_key_str(fitsFilePtr, "CREATOR", "RaptorEagleV control software", NULL, &status);
|
||||||
|
|
||||||
fits_update_key_str(fitsFilePtr, "FILE", _acqParams->filename.c_str(), "Original filename", &status);
|
// fits_update_key_str(fitsFilePtr, "FILE", _acqParams->filename.c_str(), "Original filename", &status);
|
||||||
|
std::filesystem::path pt = _acqParams->filename;
|
||||||
|
fits_update_key_str(fitsFilePtr, "FILE", pt.filename().c_str(), "Original filename", &status);
|
||||||
fits_write_date(fitsFilePtr, &status);
|
fits_write_date(fitsFilePtr, &status);
|
||||||
|
|
||||||
|
|
||||||
@@ -233,6 +259,9 @@ void RaptorEagleCCD::AcquisitionProcess::start(const std::shared_ptr<acq_params_
|
|||||||
|
|
||||||
if (_acqParams->startTime < _acqParams->abortTime) { // acquisition was aborted
|
if (_acqParams->startTime < _acqParams->abortTime) { // acquisition was aborted
|
||||||
std::chrono::duration<double> real_exp = _acqParams->abortTime - _acqParams->startTime;
|
std::chrono::duration<double> real_exp = _acqParams->abortTime - _acqParams->startTime;
|
||||||
|
_manager->logTrace("Acq. start time: {}; acq. abort time: {}", _acqParams->startTime,
|
||||||
|
_acqParams->abortTime);
|
||||||
|
_manager->logDebug("Exposure was stopped! Recompute the exposure duration to {} secs", real_exp.count());
|
||||||
_acqParams->expTime = real_exp.count();
|
_acqParams->expTime = real_exp.count();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -298,11 +327,16 @@ void RaptorEagleCCD::AcquisitionProcess::start(const std::shared_ptr<acq_params_
|
|||||||
}
|
}
|
||||||
|
|
||||||
// permanent keywords (may update keywords from template file!)
|
// permanent keywords (may update keywords from template file!)
|
||||||
char card[80];
|
char card[81];
|
||||||
char kname[8];
|
char kname[9] = " ";
|
||||||
int k_type;
|
int k_type;
|
||||||
|
|
||||||
for (auto& s : _manager->_permanentFitsKeywords) {
|
if (_acqParams->permanentKeywords.size()) {
|
||||||
|
_manager->logDebug("Copy {} permanent keywords", _acqParams->permanentKeywords.size());
|
||||||
|
} else {
|
||||||
|
_manager->logDebug("There is no one permanent keyword! Skip!");
|
||||||
|
}
|
||||||
|
for (auto& s : _acqParams->permanentKeywords) {
|
||||||
fits_parse_template(s.data(), card, &k_type, &status);
|
fits_parse_template(s.data(), card, &k_type, &status);
|
||||||
if (status) { // ignore possible errors
|
if (status) { // ignore possible errors
|
||||||
fits_get_errstatus(status, err_str);
|
fits_get_errstatus(status, err_str);
|
||||||
@@ -317,11 +351,29 @@ void RaptorEagleCCD::AcquisitionProcess::start(const std::shared_ptr<acq_params_
|
|||||||
kname[i] = card[i];
|
kname[i] = card[i];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
_manager->logTrace("Try to update [{}] FITS card (name = '{}')", card, kname);
|
||||||
|
|
||||||
fits_update_card(fitsFilePtr, kname, card, &status);
|
fits_update_card(fitsFilePtr, kname, card, &status);
|
||||||
|
|
||||||
|
if (status) {
|
||||||
|
fits_get_errstatus(status, err_str);
|
||||||
|
_manager->logWarn(
|
||||||
|
"An error occured while updating FITS card (name = '{}') (err = {}, msg = {})! Skip!", kname,
|
||||||
|
status, err_str);
|
||||||
|
} else {
|
||||||
|
_manager->logTrace("The FITS card (name = '{}') was updated successfully", kname);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// keyword from user (may update template file and permanent keywords!)
|
// keyword from user (may update template file and permanent keywords!)
|
||||||
for (auto& s : _manager->_currentFitsKeywords) {
|
if (_acqParams->currentKeywords.size()) {
|
||||||
|
_manager->logDebug("Copy {} current keywords", _acqParams->currentKeywords.size());
|
||||||
|
} else {
|
||||||
|
_manager->logDebug("There is no one current keyword! Skip!");
|
||||||
|
}
|
||||||
|
for (auto& s : _acqParams->currentKeywords) {
|
||||||
fits_parse_template(s.data(), card, &k_type, &status);
|
fits_parse_template(s.data(), card, &k_type, &status);
|
||||||
if (status) { // ignore possible errors
|
if (status) { // ignore possible errors
|
||||||
fits_get_errstatus(status, err_str);
|
fits_get_errstatus(status, err_str);
|
||||||
@@ -336,7 +388,19 @@ void RaptorEagleCCD::AcquisitionProcess::start(const std::shared_ptr<acq_params_
|
|||||||
kname[i] = card[i];
|
kname[i] = card[i];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
_manager->logTrace("Try to update [{}] FITS card (name = '{}')", card, kname);
|
||||||
|
|
||||||
fits_update_card(fitsFilePtr, kname, card, &status);
|
fits_update_card(fitsFilePtr, kname, card, &status);
|
||||||
|
|
||||||
|
if (status) {
|
||||||
|
fits_get_errstatus(status, err_str);
|
||||||
|
_manager->logWarn(
|
||||||
|
"An error occured while updating FITS card (name = '{}') (err = {}, msg = {})! Skip!", kname,
|
||||||
|
status, err_str);
|
||||||
|
} else {
|
||||||
|
_manager->logTrace("The FITS card (name = '{}') was updated successfully", kname);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -359,6 +423,10 @@ void RaptorEagleCCD::AcquisitionProcess::start(const std::shared_ptr<acq_params_
|
|||||||
|
|
||||||
fits_close_file(fitsFilePtr, &status);
|
fits_close_file(fitsFilePtr, &status);
|
||||||
|
|
||||||
|
_status = STATUS_IDLE;
|
||||||
|
// _status = std::string(CAMERA_ATTR_CAMERA_STATUS_IDLE.begin(), CAMERA_ATTR_CAMERA_STATUS_IDLE.end());
|
||||||
|
// _manager->_cameraStatus = CAMERA_ATTR_CAMERA_STATUS_IDLE;
|
||||||
|
|
||||||
fits_get_errstatus(status, err_str);
|
fits_get_errstatus(status, err_str);
|
||||||
|
|
||||||
if (status) {
|
if (status) {
|
||||||
@@ -367,6 +435,8 @@ void RaptorEagleCCD::AcquisitionProcess::start(const std::shared_ptr<acq_params_
|
|||||||
} else {
|
} else {
|
||||||
_manager->logInfo("FITS file '{}' is saved", _acqParams->filename);
|
_manager->logInfo("FITS file '{}' is saved", _acqParams->filename);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
_imageBuffer.release();
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -389,3 +459,36 @@ void RaptorEagleCCD::AcquisitionProcess::stop(bool save)
|
|||||||
_manager->logWarn("There was no active acquisition process! Ignore!");
|
_manager->logWarn("There was no active acquisition process! Ignore!");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
std::string RaptorEagleCCD::AcquisitionProcess::status()
|
||||||
|
{
|
||||||
|
std::lock_guard lock(_statusMutex);
|
||||||
|
|
||||||
|
switch (_status) {
|
||||||
|
case STATUS_IDLE:
|
||||||
|
_statusString = std::format("{}", CAMERA_ATTR_CAMERA_STATUS_IDLE);
|
||||||
|
break;
|
||||||
|
case STATUS_ACQ: {
|
||||||
|
std::chrono::duration<double> curr_exp = std::chrono::utc_clock::now() - _acqParams->startTime;
|
||||||
|
auto remain_exp = _acqParams->expTime - curr_exp.count();
|
||||||
|
if (remain_exp < 0) {
|
||||||
|
_status = STATUS_READ;
|
||||||
|
_statusString = std::format("{} {}", CAMERA_ATTR_CAMERA_STATUS_READ, _acqParams->filename);
|
||||||
|
} else {
|
||||||
|
_statusString = std::format("{} {}", CAMERA_ATTR_CAMERA_STATUS_ACQ, remain_exp);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
case STATUS_READ:
|
||||||
|
_statusString = std::format("{} {}", CAMERA_ATTR_CAMERA_STATUS_READ, _acqParams->filename);
|
||||||
|
break;
|
||||||
|
case STATUS_SAVE:
|
||||||
|
_statusString = std::format("{} {}", CAMERA_ATTR_CAMERA_STATUS_SAVE, _acqParams->filename);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
_statusString = "UNKNOWN"; // is should not be!!!
|
||||||
|
}
|
||||||
|
|
||||||
|
return _statusString;
|
||||||
|
}
|
||||||
|
|||||||
@@ -1,5 +1,7 @@
|
|||||||
#include <cmath>
|
#include <cmath>
|
||||||
|
#include <csignal>
|
||||||
#include <cstring>
|
#include <cstring>
|
||||||
|
#include <filesystem>
|
||||||
|
|
||||||
#include "raptor_eagle_cameralink.h"
|
#include "raptor_eagle_cameralink.h"
|
||||||
#include "raptor_eagle_ccd.h"
|
#include "raptor_eagle_ccd.h"
|
||||||
@@ -410,6 +412,14 @@ bool RaptorEagleCCD::initCamera(int unitmap)
|
|||||||
throw std::system_error(RaptorEagleCCDError::ERROR_INVALID_UNITMAP);
|
throw std::system_error(RaptorEagleCCDError::ERROR_INVALID_UNITMAP);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
std::string status = (*this)[CAMERA_ATTR_CAMERA_STATUS];
|
||||||
|
if (status != CAMERA_ATTR_CAMERA_STATUS_IDLE) {
|
||||||
|
logWarn("It seems camera current status is not IDLE! Abort possible exposure!");
|
||||||
|
(*this)[CAMERA_CMD_ABORT_EXP];
|
||||||
|
// _cameraStatus = CAMERA_ATTR_CAMERA_STATUS_IDLE;
|
||||||
|
}
|
||||||
|
AcquisitionProcess::isAcqInProgress = false; // ??????!!!!!!!!!!!
|
||||||
|
|
||||||
_cameraUnitmap = unitmap;
|
_cameraUnitmap = unitmap;
|
||||||
|
|
||||||
// configure CameraLink serial connection
|
// configure CameraLink serial connection
|
||||||
@@ -472,6 +482,19 @@ bool RaptorEagleCCD::initCamera(int unitmap)
|
|||||||
|
|
||||||
// setTriggerRegisterBit(CL_TRIGGER_MODE_ABORT_CURRENT_EXP_BIT);
|
// setTriggerRegisterBit(CL_TRIGGER_MODE_ABORT_CURRENT_EXP_BIT);
|
||||||
|
|
||||||
|
_permanentFitsKeywords.clear();
|
||||||
|
_currentFitsKeywords.clear();
|
||||||
|
|
||||||
|
|
||||||
|
// xclibApiCall<true>(pxd_eventFieldClose(_cameraUnitmap, SIGUSR2),
|
||||||
|
// std::format("pxd_eventFieldClose({}, {})", _cameraUnitmap, SIGUSR2));
|
||||||
|
|
||||||
|
// xclibApiCall(pxd_eventFieldCreate(_cameraUnitmap, SIGUSR2, NULL),
|
||||||
|
// std::format("pxd_eventFieldCreate({}, {}, NULL)", _cameraUnitmap, SIGUSR2));
|
||||||
|
|
||||||
|
// std::signal(SIGUSR2, [this](int signo) { logDebug("SIGUSR2 SIGNAL IS RECEIVED!!!");
|
||||||
|
// });
|
||||||
|
|
||||||
logInfo("Camera with unitmap '{}' is initialized", _cameraUnitmap);
|
logInfo("Camera with unitmap '{}' is initialized", _cameraUnitmap);
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
@@ -488,8 +511,8 @@ void RaptorEagleCCD::openPIXCI()
|
|||||||
} else {
|
} else {
|
||||||
xclibApiCall(pxd_PIXCIopen("", "DEFAULT", ""), "pxd_PIXCIopen(\"\", \"DEFAULT\", \"\")");
|
xclibApiCall(pxd_PIXCIopen("", "DEFAULT", ""), "pxd_PIXCIopen(\"\", \"DEFAULT\", \"\")");
|
||||||
|
|
||||||
// #include DEFAULT_EPIX_VIDEO_FMT_FILE // exported from XCAP (Linux 64-bit!): bin 1x1, full CCD frame
|
#include DEFAULT_EPIX_VIDEO_FMT_FILE // exported from XCAP (Linux 64-bit!): bin 1x1, full CCD frame
|
||||||
#include "raptor_eagle-v.fmt" // exported from XCAP (Linux 64-bit!): bin 1x1, full CCD frame
|
// #include "raptor_eagle-v.fmt" // exported from XCAP (Linux 64-bit!): bin 1x1, full CCD frame
|
||||||
pxd_videoFormatAsIncludedInit(0);
|
pxd_videoFormatAsIncludedInit(0);
|
||||||
xclibApiCall(pxd_videoFormatAsIncluded(0), "pxd_videoFormatAsIncluded(0)");
|
xclibApiCall(pxd_videoFormatAsIncluded(0), "pxd_videoFormatAsIncluded(0)");
|
||||||
}
|
}
|
||||||
@@ -518,10 +541,11 @@ size_t RaptorEagleCCD::clRead(byte_seq_t& bytes)
|
|||||||
|
|
||||||
// how many byte are available
|
// how many byte are available
|
||||||
xclibApiCall(nbytes = pxd_serialRead(_cameraUnitmap, 0, nullptr, 0),
|
xclibApiCall(nbytes = pxd_serialRead(_cameraUnitmap, 0, nullptr, 0),
|
||||||
std::format("pxd_serialRead({}, 0, NULL, 0)", _cameraUnitmap));
|
std::format("pxd_serialRead({}, 0, NULL, 0)", _cameraUnitmap), spdlog::level::trace);
|
||||||
|
|
||||||
if (!nbytes) {
|
if (!nbytes) {
|
||||||
logWarn("There are no bytes in Rx-buffer! Polling buffer during {} ...", CL_DEFAULT_TIMEOUT);
|
// logWarn("There are no bytes in Rx-buffer! Polling buffer during {} ...", CL_DEFAULT_TIMEOUT);
|
||||||
|
logTrace("There are no bytes in Rx-buffer! Polling buffer during {} ...", CL_DEFAULT_TIMEOUT);
|
||||||
while ((std::chrono::steady_clock::now() - start_tp) <= CL_DEFAULT_TIMEOUT) {
|
while ((std::chrono::steady_clock::now() - start_tp) <= CL_DEFAULT_TIMEOUT) {
|
||||||
std::this_thread::sleep_for(std::chrono::milliseconds(5));
|
std::this_thread::sleep_for(std::chrono::milliseconds(5));
|
||||||
nbytes = pxd_serialRead(_cameraUnitmap, 0, nullptr, 0);
|
nbytes = pxd_serialRead(_cameraUnitmap, 0, nullptr, 0);
|
||||||
@@ -538,7 +562,7 @@ size_t RaptorEagleCCD::clRead(byte_seq_t& bytes)
|
|||||||
|
|
||||||
// here the call is only for logging purpose
|
// here the call is only for logging purpose
|
||||||
xclibApiCall(nbytes = pxd_serialRead(_cameraUnitmap, 0, nullptr, 0),
|
xclibApiCall(nbytes = pxd_serialRead(_cameraUnitmap, 0, nullptr, 0),
|
||||||
std::format("pxd_serialRead({}, 0, NULL, 0)", _cameraUnitmap));
|
std::format("pxd_serialRead({}, 0, NULL, 0)", _cameraUnitmap), spdlog::level::trace);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -550,7 +574,8 @@ size_t RaptorEagleCCD::clRead(byte_seq_t& bytes)
|
|||||||
|
|
||||||
xclibApiCall(pxd_serialRead(_cameraUnitmap, 0, (char*)bytes.data(), nbytes),
|
xclibApiCall(pxd_serialRead(_cameraUnitmap, 0, (char*)bytes.data(), nbytes),
|
||||||
std::format("pxd_serialRead({}, 0, {}, {}) -> [{}]", _cameraUnitmap, (void*)bytes.data(), nbytes,
|
std::format("pxd_serialRead({}, 0, {}, {}) -> [{}]", _cameraUnitmap, (void*)bytes.data(), nbytes,
|
||||||
details::formatByteArr(bytes | std::views::take(nbytes))));
|
details::formatByteArr(bytes | std::views::take(nbytes))),
|
||||||
|
spdlog::level::trace);
|
||||||
|
|
||||||
|
|
||||||
// if (_loggerSPtr->level() == spdlog::level::trace) {
|
// if (_loggerSPtr->level() == spdlog::level::trace) {
|
||||||
@@ -613,7 +638,7 @@ size_t RaptorEagleCCD::clWrite(const byte_seq_t& bytes)
|
|||||||
|
|
||||||
// how many bytes are available in Tx-buffer
|
// how many bytes are available in Tx-buffer
|
||||||
xclibApiCall(nbytes = pxd_serialWrite(_cameraUnitmap, 0, nullptr, 0),
|
xclibApiCall(nbytes = pxd_serialWrite(_cameraUnitmap, 0, nullptr, 0),
|
||||||
std::format("pxd_serialWrite({}, 0, NULL, 0)", _cameraUnitmap));
|
std::format("pxd_serialWrite({}, 0, NULL, 0)", _cameraUnitmap), spdlog::level::trace);
|
||||||
|
|
||||||
if (nbytes) {
|
if (nbytes) {
|
||||||
if (nbytes < (bytes.size() + tr_nbytes)) {
|
if (nbytes < (bytes.size() + tr_nbytes)) {
|
||||||
@@ -628,7 +653,8 @@ size_t RaptorEagleCCD::clWrite(const byte_seq_t& bytes)
|
|||||||
|
|
||||||
xclibApiCall(nbytes = pxd_serialWrite(_cameraUnitmap, 0, (char*)bytes.data(), bytes.size()),
|
xclibApiCall(nbytes = pxd_serialWrite(_cameraUnitmap, 0, (char*)bytes.data(), bytes.size()),
|
||||||
std::format("pxd_serialWrite({}, 0, [{}], {})", _cameraUnitmap, details::formatByteArr(bytes),
|
std::format("pxd_serialWrite({}, 0, [{}], {})", _cameraUnitmap, details::formatByteArr(bytes),
|
||||||
bytes.size()));
|
bytes.size()),
|
||||||
|
spdlog::level::trace);
|
||||||
// xclibApiCall(
|
// xclibApiCall(
|
||||||
// nbytes = pxd_serialWrite(_cameraUnitmap, 0, (char*)bytes.data(), bytes.size()),
|
// nbytes = pxd_serialWrite(_cameraUnitmap, 0, (char*)bytes.data(), bytes.size()),
|
||||||
// std::format("pxd_serialWrite({}, 0, {}, {})", _cameraUnitmap, (void*)bytes.data(), bytes.size()));
|
// std::format("pxd_serialWrite({}, 0, {}, {})", _cameraUnitmap, (void*)bytes.data(), bytes.size()));
|
||||||
@@ -636,16 +662,19 @@ size_t RaptorEagleCCD::clWrite(const byte_seq_t& bytes)
|
|||||||
// send trailing ETX and possible checksum bytes
|
// send trailing ETX and possible checksum bytes
|
||||||
|
|
||||||
if (tr_nbytes > 1) {
|
if (tr_nbytes > 1) {
|
||||||
logDebug("Write trailing ETX and checksum bytes");
|
// logDebug("Write trailing ETX and checksum bytes");
|
||||||
|
logTrace("Write trailing ETX and checksum bytes");
|
||||||
} else {
|
} else {
|
||||||
logDebug("Write trailing ETX byte");
|
// logDebug("Write trailing ETX byte");
|
||||||
|
logTrace("Write trailing ETX byte");
|
||||||
}
|
}
|
||||||
|
|
||||||
xclibApiCall(pxd_serialWrite(_cameraUnitmap, 0, (char*)etx_checksum_bytes, tr_nbytes),
|
xclibApiCall(pxd_serialWrite(_cameraUnitmap, 0, (char*)etx_checksum_bytes, tr_nbytes),
|
||||||
std::format("pxd_serialWrite({}, 0, [{}], {})", _cameraUnitmap,
|
std::format("pxd_serialWrite({}, 0, [{}], {})", _cameraUnitmap,
|
||||||
details::formatByteArr(std::string_view((const char*)etx_checksum_bytes, 2) |
|
details::formatByteArr(std::string_view((const char*)etx_checksum_bytes, 2) |
|
||||||
std::views::take(tr_nbytes)),
|
std::views::take(tr_nbytes)),
|
||||||
tr_nbytes));
|
tr_nbytes),
|
||||||
|
spdlog::level::trace);
|
||||||
// xclibApiCall(
|
// xclibApiCall(
|
||||||
// pxd_serialWrite(_cameraUnitmap, 0, (char*)etx_checksum_bytes, tr_nbytes),
|
// pxd_serialWrite(_cameraUnitmap, 0, (char*)etx_checksum_bytes, tr_nbytes),
|
||||||
// std::format("pxd_serialWrite({}, 0, {}, {})", _cameraUnitmap, (void*)etx_checksum_bytes, tr_nbytes));
|
// std::format("pxd_serialWrite({}, 0, {}, {})", _cameraUnitmap, (void*)etx_checksum_bytes, tr_nbytes));
|
||||||
@@ -936,6 +965,35 @@ void RaptorEagleCCD::startAquisition()
|
|||||||
throw std::system_error(RaptorEagleCCDError::ERROR_EXT_TRIGGER_MODE);
|
throw std::system_error(RaptorEagleCCDError::ERROR_EXT_TRIGGER_MODE);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// check filesystem permissions
|
||||||
|
std::string fname = (*this)[CAMERA_ATTR_FITS_FILENAME];
|
||||||
|
|
||||||
|
std::error_code ec;
|
||||||
|
std::filesystem::path pt(fname);
|
||||||
|
|
||||||
|
if (pt.filename().empty()) {
|
||||||
|
fname = "";
|
||||||
|
} else {
|
||||||
|
auto pt_p = pt.parent_path();
|
||||||
|
if (pt_p.empty()) {
|
||||||
|
pt_p = ".";
|
||||||
|
}
|
||||||
|
|
||||||
|
auto pt_cn = std::filesystem::canonical(pt_p, ec);
|
||||||
|
if (ec) {
|
||||||
|
logError("Invalid FITS-image filename path: {}", pt.c_str());
|
||||||
|
throw std::system_error(RaptorEagleCCDError::ERROR_INVALID_PATH);
|
||||||
|
}
|
||||||
|
|
||||||
|
// still only for POSIX OSes
|
||||||
|
int res = access(pt_cn.c_str(), W_OK | X_OK);
|
||||||
|
if (res == -1) {
|
||||||
|
logError("Invalid FITS-image path! Insufficient filesystem permissions!");
|
||||||
|
throw std::system_error(RaptorEagleCCDError::ERROR_INSUFFICIENT_FILESYSTEM_PERMISSIONS);
|
||||||
|
}
|
||||||
|
|
||||||
|
fname = pt_cn / pt.filename(); // use canonical file path
|
||||||
|
}
|
||||||
|
|
||||||
logInfo("Start acquisition process ...");
|
logInfo("Start acquisition process ...");
|
||||||
|
|
||||||
@@ -959,30 +1017,16 @@ void RaptorEagleCCD::startAquisition()
|
|||||||
.tecSetPoint = (*this)[CAMERA_ATTR_TECPOINT],
|
.tecSetPoint = (*this)[CAMERA_ATTR_TECPOINT],
|
||||||
.tecState = (*this)[CAMERA_ATTR_TECSTATE] == CAMERA_ATTR_TECSTATE_ON ? true : false,
|
.tecState = (*this)[CAMERA_ATTR_TECSTATE] == CAMERA_ATTR_TECSTATE_ON ? true : false,
|
||||||
.pcbTemp = (*this)[CAMERA_ATTR_PCB_TEMP],
|
.pcbTemp = (*this)[CAMERA_ATTR_PCB_TEMP],
|
||||||
.filename = (*this)[CAMERA_ATTR_FITS_FILENAME],
|
// .filename = (*this)[CAMERA_ATTR_FITS_FILENAME],
|
||||||
|
.filename = fname,
|
||||||
.templateFilename = (*this)[CAMERA_ATTR_FITS_TEMPLATE],
|
.templateFilename = (*this)[CAMERA_ATTR_FITS_TEMPLATE],
|
||||||
.permanentKeywords = _permanentFitsKeywords, // copy
|
.permanentKeywords = _permanentFitsKeywords, // copy
|
||||||
.currentKeywords = std::move(_currentFitsKeywords) // move!!!
|
.currentKeywords = std::move(_currentFitsKeywords) // move!!!
|
||||||
}));
|
}));
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
// adjust geometry
|
// adjust geometry
|
||||||
// auto dv = std::div(_dimCCD[0] - acq_pars->roiStartX, acq_pars->binX);
|
|
||||||
// auto width_max = dv.quot + (dv.rem ? 1 : 0);
|
|
||||||
|
|
||||||
// dv = std::div(_dimCCD[1] - acq_pars->roiStartY, acq_pars->binY);
|
|
||||||
// auto height_max = dv.quot + (dv.rem ? 1 : 0);
|
|
||||||
|
|
||||||
// if (acq_pars->roiWidth > width_max) {
|
|
||||||
// // acq_pars->roiWidth = width_max;
|
|
||||||
// logDebug("Adjust ROI width to {}", acq_pars->roiWidth);
|
|
||||||
// // (*this)[CAMERA_ATTR_ROI_WIDTH] = width_max;
|
|
||||||
// }
|
|
||||||
// if (acq_pars->roiHeight > height_max) {
|
|
||||||
// // acq_pars->roiHeight = height_max;
|
|
||||||
// logDebug("Adjust ROI height to {}", acq_pars->roiHeight);
|
|
||||||
// // (*this)[CAMERA_ATTR_ROI_HEIGHT] = height_max;
|
|
||||||
// }
|
|
||||||
|
|
||||||
auto xmax = acq_pars->roiStartX + acq_pars->roiWidth;
|
auto xmax = acq_pars->roiStartX + acq_pars->roiWidth;
|
||||||
auto ymax = acq_pars->roiStartY + acq_pars->roiHeight;
|
auto ymax = acq_pars->roiStartY + acq_pars->roiHeight;
|
||||||
@@ -1025,6 +1069,9 @@ void RaptorEagleCCD::startAquisition()
|
|||||||
xclibApiCall(status = pxd_goneLive(_cameraUnitmap, 0), std::format("pxd_goneLive({}, 0)", _cameraUnitmap));
|
xclibApiCall(status = pxd_goneLive(_cameraUnitmap, 0), std::format("pxd_goneLive({}, 0)", _cameraUnitmap));
|
||||||
if (status == 0) {
|
if (status == 0) {
|
||||||
logError("CANNOT START ACQUIRING!!!");
|
logError("CANNOT START ACQUIRING!!!");
|
||||||
|
sptr->_status = AcquisitionProcess::STATUS_IDLE;
|
||||||
|
} else {
|
||||||
|
sptr->_status = AcquisitionProcess::STATUS_ACQ;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1170,6 +1217,52 @@ void RaptorEagleCCD::initAttrComm()
|
|||||||
|
|
||||||
/* ------- ATTRIBUTES ------- */
|
/* ------- ATTRIBUTES ------- */
|
||||||
|
|
||||||
|
/* CAMERA CURRENT STATUS (READ-ONLY) */
|
||||||
|
|
||||||
|
addAttribute(CAMERA_ATTR_CAMERA_STATUS, [this]() {
|
||||||
|
std::lock_guard lock_guard(_acqProcessesMutex);
|
||||||
|
|
||||||
|
std::string s, s_head;
|
||||||
|
|
||||||
|
if (!_acqProcesses.empty()) {
|
||||||
|
for (auto it = _acqProcesses.begin(); it != _acqProcesses.end();) {
|
||||||
|
if (it->expired()) {
|
||||||
|
it = _acqProcesses.erase(it);
|
||||||
|
} else {
|
||||||
|
auto sptr = it->lock();
|
||||||
|
auto st = sptr->status();
|
||||||
|
if (st.substr(0, CAMERA_ATTR_CAMERA_STATUS_ACQ.size()) ==
|
||||||
|
CAMERA_ATTR_CAMERA_STATUS_ACQ) { // if the camera is acquiring then
|
||||||
|
s_head = st + ","; // return it at the beginning of the status string
|
||||||
|
} else if (st.substr(0, CAMERA_ATTR_CAMERA_STATUS_IDLE.size()) == CAMERA_ATTR_CAMERA_STATUS_IDLE) {
|
||||||
|
// here, cquisition process is already inactive
|
||||||
|
it = _acqProcesses.erase(it);
|
||||||
|
continue;
|
||||||
|
} else {
|
||||||
|
std::ranges::copy(st, std::back_inserter(s));
|
||||||
|
s += ",";
|
||||||
|
}
|
||||||
|
++it;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!s.empty() || !s_head.empty()) {
|
||||||
|
s = s_head + s;
|
||||||
|
// if (_acqProcesses.size() == 1) {
|
||||||
|
s.resize(s.size() - 1); // delete trailing ","
|
||||||
|
// }
|
||||||
|
} else {
|
||||||
|
s = std::string{CAMERA_ATTR_CAMERA_STATUS_IDLE.begin(), CAMERA_ATTR_CAMERA_STATUS_IDLE.end()};
|
||||||
|
}
|
||||||
|
|
||||||
|
logTrace("Return current camera status as {}", s);
|
||||||
|
|
||||||
|
return s;
|
||||||
|
});
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/* CURRENT FITS IMAGE FILENAME AND ITS HEADER TEMPLATE, PERMANENT AND CURRENT USER FITS KEYWORDS */
|
/* CURRENT FITS IMAGE FILENAME AND ITS HEADER TEMPLATE, PERMANENT AND CURRENT USER FITS KEYWORDS */
|
||||||
|
|
||||||
addAttribute(
|
addAttribute(
|
||||||
@@ -1727,7 +1820,7 @@ void RaptorEagleCCD::initAttrComm()
|
|||||||
val = CAMERA_ATTR_STR_INVALID;
|
val = CAMERA_ATTR_STR_INVALID;
|
||||||
}
|
}
|
||||||
|
|
||||||
logTrace("Return readout rate as '()' string", val);
|
logTrace("Return readout rate as '{}' string", val);
|
||||||
|
|
||||||
return val;
|
return val;
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -103,6 +103,8 @@ public:
|
|||||||
static constexpr std::string_view CAMERA_ATTR_PERM_KEYW{"PERM_FITS_KEY"};
|
static constexpr std::string_view CAMERA_ATTR_PERM_KEYW{"PERM_FITS_KEY"};
|
||||||
static constexpr std::string_view CAMERA_ATTR_CURR_KEYW{"CURR_FITS_KEY"};
|
static constexpr std::string_view CAMERA_ATTR_CURR_KEYW{"CURR_FITS_KEY"};
|
||||||
|
|
||||||
|
static constexpr std::string_view CAMERA_ATTR_CAMERA_STATUS{"CAMERA_STATUS"};
|
||||||
|
|
||||||
static constexpr std::string_view CAMERA_CMD_INITCAM{"INITCAM"};
|
static constexpr std::string_view CAMERA_CMD_INITCAM{"INITCAM"};
|
||||||
static constexpr std::string_view CAMERA_CMD_START_EXP{"STARTEXP"};
|
static constexpr std::string_view CAMERA_CMD_START_EXP{"STARTEXP"};
|
||||||
static constexpr std::string_view CAMERA_CMD_STOP_EXP{"STOPEXP"};
|
static constexpr std::string_view CAMERA_CMD_STOP_EXP{"STOPEXP"};
|
||||||
@@ -144,6 +146,14 @@ public:
|
|||||||
// idle
|
// idle
|
||||||
static constexpr std::string_view CAMERA_ATTR_TRIGGER_MODE_IDLE{"IDLE"};
|
static constexpr std::string_view CAMERA_ATTR_TRIGGER_MODE_IDLE{"IDLE"};
|
||||||
|
|
||||||
|
|
||||||
|
// camera status
|
||||||
|
static constexpr std::string_view CAMERA_ATTR_CAMERA_STATUS_IDLE{"IDLE"};
|
||||||
|
static constexpr std::string_view CAMERA_ATTR_CAMERA_STATUS_ACQ{"ACQ"}; // camera is acquiring
|
||||||
|
static constexpr std::string_view CAMERA_ATTR_CAMERA_STATUS_READ{"READING"}; // camera is reading from CCD
|
||||||
|
static constexpr std::string_view CAMERA_ATTR_CAMERA_STATUS_SAVE{"SAVING"}; // camera is saving to FITS file
|
||||||
|
|
||||||
|
|
||||||
RaptorEagleCCD(const adc::traits::adc_input_char_range auto& epix_video_fmt_filename,
|
RaptorEagleCCD(const adc::traits::adc_input_char_range auto& epix_video_fmt_filename,
|
||||||
std::shared_ptr<spdlog::logger> logger = spdlog::null_logger_mt("EAGLE_CCD_NULL_LOGGER"));
|
std::shared_ptr<spdlog::logger> logger = spdlog::null_logger_mt("EAGLE_CCD_NULL_LOGGER"));
|
||||||
|
|
||||||
@@ -199,6 +209,7 @@ private:
|
|||||||
|
|
||||||
void start(const std::shared_ptr<acq_params_t>& params); // asynchronous method!
|
void start(const std::shared_ptr<acq_params_t>& params); // asynchronous method!
|
||||||
void stop(bool save = true);
|
void stop(bool save = true);
|
||||||
|
std::string status();
|
||||||
|
|
||||||
private:
|
private:
|
||||||
inline static std::atomic_bool isAcqInProgress = false;
|
inline static std::atomic_bool isAcqInProgress = false;
|
||||||
@@ -211,6 +222,11 @@ private:
|
|||||||
|
|
||||||
std::future<void> _snapAndCopyFuture;
|
std::future<void> _snapAndCopyFuture;
|
||||||
// std::future<void> _saveFitsFileFuture;
|
// std::future<void> _saveFitsFileFuture;
|
||||||
|
|
||||||
|
std::string _statusString{CAMERA_ATTR_CAMERA_STATUS_IDLE.begin(), CAMERA_ATTR_CAMERA_STATUS_IDLE.end()};
|
||||||
|
enum int8_t { STATUS_IDLE, STATUS_ACQ, STATUS_READ, STATUS_SAVE };
|
||||||
|
std::atomic_int8_t _status = STATUS_IDLE;
|
||||||
|
std::mutex _statusMutex;
|
||||||
};
|
};
|
||||||
|
|
||||||
std::string _epixFmtVideoFilename;
|
std::string _epixFmtVideoFilename;
|
||||||
@@ -236,10 +252,10 @@ private:
|
|||||||
|
|
||||||
// attributes inner variables
|
// attributes inner variables
|
||||||
std::atomic_size_t _frameNumbers;
|
std::atomic_size_t _frameNumbers;
|
||||||
std::string _currentFitsFile; // current acquisition FITS filename
|
std::string _currentFitsFile; // current acquisition FITS filename
|
||||||
std::string _currentTemplateFile; // CFITSIO template filename
|
std::string _currentTemplateFile; // CFITSIO template filename
|
||||||
std::vector<std::string> _currentFitsKeywords; // current acquisition FITS keywords
|
std::vector<std::string> _currentFitsKeywords{}; // current acquisition FITS keywords
|
||||||
std::vector<std::string> _permanentFitsKeywords; // permanent user FITS keywords
|
std::vector<std::string> _permanentFitsKeywords{}; // permanent user FITS keywords
|
||||||
|
|
||||||
// std::list<std::unique_ptr<ushort>> _acqRingBuffer;
|
// std::list<std::unique_ptr<ushort>> _acqRingBuffer;
|
||||||
std::list<std::pair<std::unique_ptr<ushort>, size_t>> _acqRingBuffer;
|
std::list<std::pair<std::unique_ptr<ushort>, size_t>> _acqRingBuffer;
|
||||||
@@ -338,7 +354,9 @@ private:
|
|||||||
// logging helper methods
|
// logging helper methods
|
||||||
|
|
||||||
template <bool NOEXCEPT = false>
|
template <bool NOEXCEPT = false>
|
||||||
void xclibApiCall(int err, const adc::traits::adc_input_char_range auto& func_name)
|
void xclibApiCall(int err,
|
||||||
|
const adc::traits::adc_input_char_range auto& func_name,
|
||||||
|
loglevel_t log_level = spdlog::level::debug)
|
||||||
{
|
{
|
||||||
if (err < 0) {
|
if (err < 0) {
|
||||||
auto s_err = pxd_mesgErrorCode(err);
|
auto s_err = pxd_mesgErrorCode(err);
|
||||||
@@ -354,17 +372,19 @@ private:
|
|||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
if (std::ranges::size(func_name)) {
|
if (std::ranges::size(func_name)) {
|
||||||
logDebug("XCLIB API call ('{}') finished successfully (exitcode = {})", func_name, err);
|
// logDebug("XCLIB API call ('{}') finished successfully (exitcode = {})", func_name, err);
|
||||||
|
logMessage(log_level, "XCLIB API call ('{}') finished successfully (exitcode = {})", func_name, err);
|
||||||
} else {
|
} else {
|
||||||
logDebug("XCLIB API call finished successfully (exitcode = {})", err);
|
// logDebug("XCLIB API call finished successfully (exitcode = {})", err);
|
||||||
|
logMessage(log_level, "XCLIB API call finished successfully (exitcode = {})", err);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
template <bool NOEXCEPT = false>
|
template <bool NOEXCEPT = false>
|
||||||
void xclibApiCall(int err)
|
void xclibApiCall(int err, loglevel_t log_level = spdlog::level::debug)
|
||||||
{
|
{
|
||||||
xclibApiCall<NOEXCEPT>(err, std::string_view(""));
|
xclibApiCall<NOEXCEPT>(err, std::string_view(""), log_level);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -15,7 +15,9 @@ enum class RaptorEagleCCDError : int {
|
|||||||
ERROR_CANNOT_RESET_MICRO,
|
ERROR_CANNOT_RESET_MICRO,
|
||||||
ERROR_CANNOT_RESET_FPGA,
|
ERROR_CANNOT_RESET_FPGA,
|
||||||
ERROR_EXT_TRIGGER_MODE,
|
ERROR_EXT_TRIGGER_MODE,
|
||||||
ERROR_ACQUISITION_IN_PROGRESS
|
ERROR_ACQUISITION_IN_PROGRESS,
|
||||||
|
ERROR_INVALID_PATH,
|
||||||
|
ERROR_INSUFFICIENT_FILESYSTEM_PERMISSIONS
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
@@ -62,6 +64,10 @@ struct RaptorEagleCCDErrorCategory : std::error_category {
|
|||||||
return "try to use software trigger while external trigger mode is enabled";
|
return "try to use software trigger while external trigger mode is enabled";
|
||||||
case RaptorEagleCCDError::ERROR_ACQUISITION_IN_PROGRESS:
|
case RaptorEagleCCDError::ERROR_ACQUISITION_IN_PROGRESS:
|
||||||
return "acquisition is in progress";
|
return "acquisition is in progress";
|
||||||
|
case RaptorEagleCCDError::ERROR_INVALID_PATH:
|
||||||
|
return "invalid filesystem path";
|
||||||
|
case RaptorEagleCCDError::ERROR_INSUFFICIENT_FILESYSTEM_PERMISSIONS:
|
||||||
|
return "insufficient filesystem permissions";
|
||||||
default:
|
default:
|
||||||
return "UNKNOWN ERROR";
|
return "UNKNOWN ERROR";
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -16,7 +16,7 @@ int main(int argc, char* argv[])
|
|||||||
int exit_code = 0;
|
int exit_code = 0;
|
||||||
asio::io_context ctx;
|
asio::io_context ctx;
|
||||||
std::vector<std::thread> threads;
|
std::vector<std::thread> threads;
|
||||||
std::size_t Nthreads = 2;
|
std::size_t Nthreads = 3;
|
||||||
|
|
||||||
/* COMMANDLINE OPTS */
|
/* COMMANDLINE OPTS */
|
||||||
cxxopts::Options options(argv[0], "ADC-library test device network server (ASIO implementation)\n");
|
cxxopts::Options options(argv[0], "ADC-library test device network server (ASIO implementation)\n");
|
||||||
|
|||||||
Reference in New Issue
Block a user