Moved template functions to header to avoid linker errors
This commit is contained in:
196
src/sinqAxis.cpp
196
src/sinqAxis.cpp
@ -30,202 +30,6 @@ struct sinqAxisImpl {
|
||||
epicsTimeStamp lastPollTime;
|
||||
};
|
||||
|
||||
template <typename T> struct TypeTag {};
|
||||
|
||||
// Generic fallback - if the compiler tries to compile this function, it fails.
|
||||
template <typename A, typename C, typename T>
|
||||
asynStatus setAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), T writeValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<void>) {
|
||||
static_assert(sizeof(T) == 0, "Unsupported type for setAxisParamImpl");
|
||||
return asynError;
|
||||
}
|
||||
|
||||
template <typename A, typename C>
|
||||
asynStatus setAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), int writeValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<int>) {
|
||||
int indexValue = (axis->pController()->*func)();
|
||||
asynStatus status = axis->setIntegerParam(indexValue, writeValue);
|
||||
if (status != asynSuccess) {
|
||||
return axis->pController()->paramLibAccessFailed(
|
||||
status, indexName, axis->axisNo(), callerFunctionName, lineNumber);
|
||||
}
|
||||
return asynSuccess;
|
||||
}
|
||||
|
||||
template <typename A, typename C>
|
||||
asynStatus setAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), bool writeValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<bool>) {
|
||||
return setAxisParamImpl(axis, controller, indexName, func,
|
||||
static_cast<int>(writeValue), callerFunctionName,
|
||||
lineNumber, TypeTag<int>{});
|
||||
}
|
||||
|
||||
template <typename A, typename C>
|
||||
asynStatus setAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (sinqController::*func)(), double writeValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<double>) {
|
||||
int indexValue = (axis->pController()->*func)();
|
||||
asynStatus status = axis->setDoubleParam(indexValue, writeValue);
|
||||
if (status != asynSuccess) {
|
||||
return axis->pController()->paramLibAccessFailed(
|
||||
status, indexName, axis->axisNo(), callerFunctionName, lineNumber);
|
||||
}
|
||||
return asynSuccess;
|
||||
}
|
||||
|
||||
template <typename A, typename C>
|
||||
asynStatus setAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), char *writeValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<char *>) {
|
||||
int indexValue = (axis->pController()->*func)();
|
||||
asynStatus status = axis->setStringParam(indexValue, writeValue);
|
||||
if (status != asynSuccess) {
|
||||
return axis->pController()->paramLibAccessFailed(
|
||||
status, indexName, axis->axisNo(), callerFunctionName, lineNumber);
|
||||
}
|
||||
return asynSuccess;
|
||||
}
|
||||
|
||||
template <typename A, typename C>
|
||||
asynStatus setAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), const char *writeValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<const char *>) {
|
||||
int indexValue = (axis->pController()->*func)();
|
||||
asynStatus status = axis->setStringParam(indexValue, writeValue);
|
||||
if (status != asynSuccess) {
|
||||
return axis->pController()->paramLibAccessFailed(
|
||||
status, indexName, axis->axisNo(), callerFunctionName, lineNumber);
|
||||
}
|
||||
return asynSuccess;
|
||||
}
|
||||
|
||||
template <typename A, typename C, typename T>
|
||||
asynStatus setAxisParam(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), T writeValue,
|
||||
const char *callerFunctionName, int lineNumber) {
|
||||
return setAxisParamImpl(axis, controller, indexName, func, writeValue,
|
||||
callerFunctionName, lineNumber, TypeTag<T>{});
|
||||
}
|
||||
|
||||
// Generic fallback - if the compiler tries to compile this function, it fails.
|
||||
template <typename A, typename C, typename T>
|
||||
asynStatus getAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), T *readValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<void>) {
|
||||
static_assert(
|
||||
sizeof(T) == 0,
|
||||
"no specialization of getAxisParam exists for the given type");
|
||||
return asynError;
|
||||
}
|
||||
|
||||
template <typename A, typename C>
|
||||
asynStatus getAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), int *readValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<int>) {
|
||||
int indexValue = (axis->pController()->*func)();
|
||||
asynStatus status = axis->pController()->getIntegerParam(
|
||||
axis->axisNo(), indexValue, readValue);
|
||||
if (status != asynSuccess) {
|
||||
return axis->pController()->paramLibAccessFailed(
|
||||
status, indexName, axis->axisNo(), callerFunctionName, lineNumber);
|
||||
}
|
||||
return asynSuccess;
|
||||
}
|
||||
|
||||
template <typename A, typename C>
|
||||
asynStatus getAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), bool *readValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<bool>) {
|
||||
return getAxisParamImpl(axis, indexName, func, (int *)readValue,
|
||||
callerFunctionName, lineNumber);
|
||||
}
|
||||
|
||||
template <typename A, typename C>
|
||||
asynStatus getAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), double *readValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<double>) {
|
||||
int indexValue = (axis->pController()->*func)();
|
||||
asynStatus status = axis->pController()->getDoubleParam(
|
||||
axis->axisNo(), indexValue, readValue);
|
||||
if (status != asynSuccess) {
|
||||
return axis->pController()->paramLibAccessFailed(
|
||||
status, indexName, axis->axisNo(), callerFunctionName, lineNumber);
|
||||
}
|
||||
return asynSuccess;
|
||||
}
|
||||
|
||||
template <typename A, typename C>
|
||||
asynStatus getAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), char *readValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<char>) {
|
||||
|
||||
int maxChars = 200;
|
||||
|
||||
int indexValue = (axis->pController()->*func)();
|
||||
asynStatus status = axis->pController()->getStringParam(
|
||||
axis->axisNo(), indexValue, maxChars, readValue);
|
||||
if (status != asynSuccess) {
|
||||
return axis->pController()->paramLibAccessFailed(
|
||||
status, indexName, axis->axisNo(), callerFunctionName, lineNumber);
|
||||
}
|
||||
return asynSuccess;
|
||||
}
|
||||
|
||||
template <typename A, typename C, size_t N>
|
||||
asynStatus getAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), char (&readValue)[N],
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<char>) {
|
||||
// Decay the array to char*
|
||||
return getAxisParamImpl(axis, controller, indexName, func,
|
||||
static_cast<char *>(readValue), callerFunctionName,
|
||||
lineNumber);
|
||||
}
|
||||
|
||||
template <typename A, typename C>
|
||||
asynStatus getAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), std::string *readValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<std::string>) {
|
||||
int indexValue = (axis->pController()->*func)();
|
||||
|
||||
// Convert the pointer to a reference, since getStringParam expects the
|
||||
// latter.
|
||||
std::string &rReadValue = *readValue;
|
||||
|
||||
asynStatus status = axis->pController()->getStringParam(
|
||||
axis->axisNo(), indexValue, rReadValue);
|
||||
if (status != asynSuccess) {
|
||||
return axis->pController()->paramLibAccessFailed(
|
||||
status, indexName, axis->axisNo(), callerFunctionName, lineNumber);
|
||||
}
|
||||
return asynSuccess;
|
||||
}
|
||||
|
||||
template <typename A, typename C, typename T>
|
||||
asynStatus getAxisParam(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), std::string *readValue,
|
||||
const char *callerFunctionName, int lineNumber) {
|
||||
return getAxisParamImpl(axis, controller, indexName, func, readValue,
|
||||
callerFunctionName, lineNumber, TypeTag<T>{});
|
||||
}
|
||||
|
||||
// =============================================================================
|
||||
|
||||
sinqAxis::sinqAxis(class sinqController *pC, int axisNo)
|
||||
: asynMotorAxis((asynMotorController *)pC, axisNo), pC_(pC) {
|
||||
asynStatus status = asynSuccess;
|
||||
|
198
src/sinqAxis.h
198
src/sinqAxis.h
@ -420,6 +420,84 @@ class epicsShareClass sinqAxis : public asynMotorAxis {
|
||||
// =============================================================================
|
||||
// Helper functions and definitions for the macro setAxisParamChecked
|
||||
|
||||
template <typename T> struct TypeTag {};
|
||||
|
||||
// Generic fallback - if the compiler tries to compile this function, it fails.
|
||||
template <typename A, typename C, typename T>
|
||||
asynStatus setAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), T writeValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<void>) {
|
||||
static_assert(sizeof(T) == 0, "Unsupported type for setAxisParamImpl");
|
||||
return asynError;
|
||||
}
|
||||
|
||||
template <typename A, typename C>
|
||||
asynStatus setAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), int writeValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<int>) {
|
||||
int indexValue = (controller->*func)();
|
||||
asynStatus status = axis->setIntegerParam(indexValue, writeValue);
|
||||
if (status != asynSuccess) {
|
||||
return controller->paramLibAccessFailed(
|
||||
status, indexName, axis->axisNo(), callerFunctionName, lineNumber);
|
||||
}
|
||||
return asynSuccess;
|
||||
}
|
||||
|
||||
template <typename A, typename C>
|
||||
asynStatus setAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), bool writeValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<bool>) {
|
||||
return setAxisParamImpl(axis, controller, indexName, func,
|
||||
static_cast<int>(writeValue), callerFunctionName,
|
||||
lineNumber, TypeTag<int>{});
|
||||
}
|
||||
|
||||
template <typename A, typename C>
|
||||
asynStatus setAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (sinqController::*func)(), double writeValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<double>) {
|
||||
int indexValue = (controller->*func)();
|
||||
asynStatus status = axis->setDoubleParam(indexValue, writeValue);
|
||||
if (status != asynSuccess) {
|
||||
return controller->paramLibAccessFailed(
|
||||
status, indexName, axis->axisNo(), callerFunctionName, lineNumber);
|
||||
}
|
||||
return asynSuccess;
|
||||
}
|
||||
|
||||
template <typename A, typename C>
|
||||
asynStatus setAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), char *writeValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<char *>) {
|
||||
int indexValue = (controller->*func)();
|
||||
asynStatus status = axis->setStringParam(indexValue, writeValue);
|
||||
if (status != asynSuccess) {
|
||||
return controller->paramLibAccessFailed(
|
||||
status, indexName, axis->axisNo(), callerFunctionName, lineNumber);
|
||||
}
|
||||
return asynSuccess;
|
||||
}
|
||||
|
||||
template <typename A, typename C>
|
||||
asynStatus setAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), const char *writeValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<const char *>) {
|
||||
int indexValue = (controller->*func)();
|
||||
asynStatus status = axis->setStringParam(indexValue, writeValue);
|
||||
if (status != asynSuccess) {
|
||||
return controller->paramLibAccessFailed(
|
||||
status, indexName, axis->axisNo(), callerFunctionName, lineNumber);
|
||||
}
|
||||
return asynSuccess;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Helper function to set an integer / double / string parameter for an
|
||||
* axis in the paramLib
|
||||
@ -429,6 +507,7 @@ class epicsShareClass sinqAxis : public asynMotorAxis {
|
||||
*
|
||||
* @tparam T
|
||||
* @param axis
|
||||
* @param controller
|
||||
* @param indexName
|
||||
* @param func
|
||||
* @param writeValue
|
||||
@ -439,7 +518,10 @@ class epicsShareClass sinqAxis : public asynMotorAxis {
|
||||
template <typename A, typename C, typename T>
|
||||
asynStatus setAxisParam(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), T writeValue,
|
||||
const char *callerFunctionName, int lineNumber);
|
||||
const char *callerFunctionName, int lineNumber) {
|
||||
return setAxisParamImpl(axis, controller, indexName, func, writeValue,
|
||||
callerFunctionName, lineNumber, TypeTag<T>{});
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Macro to set an paramLib parameter and error checking the return value
|
||||
@ -455,10 +537,10 @@ asynStatus setAxisParam(A *axis, C *controller, const char *indexName,
|
||||
* expands into the following code:
|
||||
* ```
|
||||
* {
|
||||
* int indexValue = axis->pController()->motorStatusProblem_();
|
||||
* int indexValue = controller->motorStatusProblem_();
|
||||
* asynStatus status = axis->setIntegerParam(indexValue, writeValue);
|
||||
* if (status != asynSuccess) {
|
||||
* return axis->pController()->paramLibAccessFailed(
|
||||
* return controller->paramLibAccessFailed(
|
||||
* status, "motorStatusProblem_", axis->axisNo(), __PRETTY_FUNCTION__,
|
||||
* __LINE__);
|
||||
* }
|
||||
@ -484,6 +566,104 @@ asynStatus setAxisParam(A *axis, C *controller, const char *indexName,
|
||||
// =============================================================================
|
||||
// Helper functions and definitions for the macro getAxisParamChecked
|
||||
|
||||
// Generic fallback - if the compiler tries to compile this function, it fails.
|
||||
template <typename A, typename C, typename T>
|
||||
asynStatus getAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), T *readValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<void>) {
|
||||
static_assert(
|
||||
sizeof(T) == 0,
|
||||
"no specialization of getAxisParam exists for the given type");
|
||||
return asynError;
|
||||
}
|
||||
|
||||
template <typename A, typename C>
|
||||
asynStatus getAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), int *readValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<int>) {
|
||||
int indexValue = (controller->*func)();
|
||||
asynStatus status =
|
||||
controller->getIntegerParam(axis->axisNo(), indexValue, readValue);
|
||||
if (status != asynSuccess) {
|
||||
return controller->paramLibAccessFailed(
|
||||
status, indexName, axis->axisNo(), callerFunctionName, lineNumber);
|
||||
}
|
||||
return asynSuccess;
|
||||
}
|
||||
|
||||
template <typename A, typename C>
|
||||
asynStatus getAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), bool *readValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<bool>) {
|
||||
return getAxisParamImpl(axis, indexName, func, (int *)readValue,
|
||||
callerFunctionName, lineNumber);
|
||||
}
|
||||
|
||||
template <typename A, typename C>
|
||||
asynStatus getAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), double *readValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<double>) {
|
||||
int indexValue = (controller->*func)();
|
||||
asynStatus status =
|
||||
controller->getDoubleParam(axis->axisNo(), indexValue, readValue);
|
||||
if (status != asynSuccess) {
|
||||
return controller->paramLibAccessFailed(
|
||||
status, indexName, axis->axisNo(), callerFunctionName, lineNumber);
|
||||
}
|
||||
return asynSuccess;
|
||||
}
|
||||
|
||||
template <typename A, typename C>
|
||||
asynStatus getAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), char *readValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<char>) {
|
||||
|
||||
int indexValue = (controller->*func)();
|
||||
asynStatus status = controller->getStringParam(
|
||||
axis->axisNo(), indexValue, controller->msgSize(), readValue);
|
||||
if (status != asynSuccess) {
|
||||
return controller->paramLibAccessFailed(
|
||||
status, indexName, axis->axisNo(), callerFunctionName, lineNumber);
|
||||
}
|
||||
return asynSuccess;
|
||||
}
|
||||
|
||||
template <typename A, typename C, size_t N>
|
||||
asynStatus getAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), char (&readValue)[N],
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<char>) {
|
||||
// Decay the array to char*
|
||||
return getAxisParamImpl(axis, controller, indexName, func,
|
||||
static_cast<char *>(readValue), callerFunctionName,
|
||||
lineNumber);
|
||||
}
|
||||
|
||||
template <typename A, typename C>
|
||||
asynStatus getAxisParamImpl(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), std::string *readValue,
|
||||
const char *callerFunctionName, int lineNumber,
|
||||
TypeTag<std::string>) {
|
||||
int indexValue = (controller->*func)();
|
||||
|
||||
// Convert the pointer to a reference, since getStringParam expects the
|
||||
// latter.
|
||||
std::string &rReadValue = *readValue;
|
||||
|
||||
asynStatus status =
|
||||
controller->getStringParam(axis->axisNo(), indexValue, rReadValue);
|
||||
if (status != asynSuccess) {
|
||||
return controller->paramLibAccessFailed(
|
||||
status, indexName, axis->axisNo(), callerFunctionName, lineNumber);
|
||||
}
|
||||
return asynSuccess;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Helper function to set an integer / double / string parameter for an
|
||||
* axis in the paramLib
|
||||
@ -493,6 +673,7 @@ asynStatus setAxisParam(A *axis, C *controller, const char *indexName,
|
||||
*
|
||||
* @tparam T
|
||||
* @param axis
|
||||
* @param controller
|
||||
* @param indexName
|
||||
* @param func
|
||||
* @param readValue
|
||||
@ -506,7 +687,10 @@ asynStatus setAxisParam(A *axis, C *controller, const char *indexName,
|
||||
template <typename A, typename C, typename T>
|
||||
asynStatus getAxisParam(A *axis, C *controller, const char *indexName,
|
||||
int (C::*func)(), T *readValue,
|
||||
const char *callerFunctionName, int lineNumber);
|
||||
const char *callerFunctionName, int lineNumber) {
|
||||
return getAxisParamImpl(axis, controller, indexName, func, readValue,
|
||||
callerFunctionName, lineNumber, TypeTag<T>{});
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Macro to get an paramLib parameter and error checking the return value
|
||||
@ -522,10 +706,10 @@ asynStatus getAxisParam(A *axis, C *controller, const char *indexName,
|
||||
* expands into the following code:
|
||||
* ```
|
||||
* {
|
||||
* int indexValue = axis->pController()->motorStatusProblem_();
|
||||
* asynStatus status = axis->pController()->getIntegerParam(axis->axisNo(),
|
||||
* int indexValue = controller->motorStatusProblem_();
|
||||
* asynStatus status = controller->getIntegerParam(axis->axisNo(),
|
||||
* indexValue, readValue); if (status != asynSuccess) { return
|
||||
* axis->pController()->paramLibAccessFailed( status, "motorStatusProblem_",
|
||||
* controller->paramLibAccessFailed( status, "motorStatusProblem_",
|
||||
* axis->axisNo(), __PRETTY_FUNCTION__,
|
||||
* __LINE__);
|
||||
* }
|
||||
|
@ -380,9 +380,17 @@ class epicsShareClass sinqController : public asynMotorController {
|
||||
*/
|
||||
int outstandingForcedFastPolls();
|
||||
|
||||
// Maximum error message buffer size. This is an empirical value which must
|
||||
// be large enough to avoid overflows for all commands to the device /
|
||||
// responses from it.
|
||||
/**
|
||||
* @brief Return the maximum error message buffer size
|
||||
*
|
||||
* This is an empirical value which must be large enough to avoid overflows
|
||||
* for all commands to the device / responses from it.
|
||||
*
|
||||
* @return uint32_t
|
||||
*/
|
||||
uint32_t msgSize() { return MAXBUF_; }
|
||||
|
||||
// Maximum message size
|
||||
static const uint32_t MAXBUF_ = 200;
|
||||
|
||||
// =========================================================================
|
||||
|
Reference in New Issue
Block a user