Instrument Neutral Distributed Interface INDI 2.2.5
test_telescope_simulator.cpp
Go to the documentation of this file.
1/*
2 Regression test for the telescope simulator: alignment sync points recorded for one mount
3 geometry must not be reused after switching between ALTAZ and an equatorial mount type.
4
5 SPDX-License-Identifier: LGPL-2.1-or-later
6*/
7
8#include <gtest/gtest.h>
9
10#include <cstdio>
11#include <cstdlib>
12#include <string>
13#include <unistd.h>
14
15#include "indilogger.h"
17
18char _me[] = "MockScopeSimDriver";
19char *me = _me;
20
22
24{
25 public:
31
32 // Select a mount type through the regular client path (TELESCOPE_MOUNT_TYPE switch).
33 void selectMountType(const char *type)
34 {
35 const char *types[] = { "ALTAZ", "EQ_FORK", "EQ_GEM" };
36 ISState states[3];
37 char *names[3];
38 for (int i = 0; i < 3; i++)
39 {
40 states[i] = strcmp(types[i], type) == 0 ? ISS_ON : ISS_OFF;
41 names[i] = const_cast<char *>(types[i]);
42 }
43 ASSERT_TRUE(ISNewSwitch(getDeviceName(), "TELESCOPE_MOUNT_TYPE", states, names, 3));
44 }
45
46 bool syncAt(double ra, double dec)
47 {
48 return Sync(ra, dec);
49 }
50
51 void setLocation(double latitude, double longitude)
52 {
53 updateLocation(latitude, longitude, 200);
54 }
55
57 {
58 return GetAlignmentDatabase().back();
59 }
60
62 {
64 entry.ObservationJulianDate = 2461300.5;
65 entry.RightAscension = 9.5;
66 entry.Declination = 45.0;
67 entry.PrivateDataSize = 0;
68 GetAlignmentDatabase().push_back(entry);
69 }
70
71 size_t syncPoints()
72 {
73 return GetAlignmentDatabase().size();
74 }
75};
76
77TEST(TelescopeSimulatorTest, switchingBetweenAltAzAndEquatorialClearsSyncPoints)
78{
80
81 sim.selectMountType("EQ_GEM");
82 sim.addSyncPoint();
83 sim.addSyncPoint();
84 ASSERT_EQ(sim.syncPoints(), 2u);
85
86 // Equatorial -> ALTAZ: RA/Dec-encoded points are meaningless for an Az/Alt mount.
87 sim.selectMountType("ALTAZ");
88 EXPECT_EQ(sim.syncPoints(), 0u);
89
90 // ALTAZ -> equatorial: Az/Alt-encoded points are meaningless for an equatorial mount.
91 sim.addSyncPoint();
92 sim.selectMountType("EQ_FORK");
93 EXPECT_EQ(sim.syncPoints(), 0u);
94}
95
96TEST(TelescopeSimulatorTest, switchingBetweenEquatorialTypesKeepsSyncPoints)
97{
99
100 sim.selectMountType("EQ_GEM");
101 sim.addSyncPoint();
102 ASSERT_EQ(sim.syncPoints(), 1u);
103
104 // EQ_GEM and EQ_FORK use the same encoder RA/Dec encoding.
105 sim.selectMountType("EQ_FORK");
106 EXPECT_EQ(sim.syncPoints(), 1u);
107}
108
109// Re-syncing at (practically) the same place must update the pointing model with the new plate-solved
110// position. Previously the new sync point was silently dropped as a duplicate while Sync() still reported
111// success, so the old position stayed in the model.
112static void checkResyncReplacesOlderPoint(const char *mountType)
113{
115 sim.setLocation(48.2, 16.4);
116 sim.selectMountType(mountType);
117
118 ASSERT_TRUE(sim.syncAt(9.50, 45.00));
119 ASSERT_EQ(sim.syncPoints(), 1u);
120
121 // Same mount position, slightly different solved sky position.
122 ASSERT_TRUE(sim.syncAt(9.51, 45.05));
123 ASSERT_EQ(sim.syncPoints(), 1u);
124 EXPECT_NEAR(sim.lastSyncPoint().RightAscension, 9.51, 1e-9);
125 EXPECT_NEAR(sim.lastSyncPoint().Declination, 45.05, 1e-9);
126}
127
128TEST(TelescopeSimulatorTest, resyncReplacesOlderSyncPointEquatorial)
129{
130 checkResyncReplacesOlderPoint("EQ_GEM");
131}
132
133// No ALTAZ variant here: a freshly constructed simulator points at the zenith, and the math plugin's
134// SanitizePolarEntries() deliberately rewrites sync points above 88 deg altitude, so a zenith sync point
135// cannot be compared directly. The ALTAZ path shares the replacement logic in ScopeSim::Sync().
136
137int main(int argc, char **argv)
138{
139 // Never read or write the user's real ~/.indi driver configuration.
140 // Use a file private to this process so that test runs can happen in parallel.
141 const std::string configFile = "/tmp/test_telescope_simulator_" + std::to_string(getpid()) + "_config.xml";
142 setenv("INDICONFIG", configFile.c_str(), 1);
145 ::testing::InitGoogleTest(&argc, argv);
146 int rc = RUN_ALL_TESTS();
147 std::remove(configFile.c_str());
148 std::remove((configFile + ".default").c_str());
149 return rc;
150}
AlignmentDatabaseType & GetAlignmentDatabase()
Get a reference to the in memory database.
bool syncAt(double ra, double dec)
void setLocation(double latitude, double longitude)
void selectMountType(const char *type)
const AlignmentDatabaseEntry & lastSyncPoint()
The ScopeSim class provides a simple mount simulator of an equatorial mount.
virtual bool ISNewSwitch(const char *dev, const char *name, ISState *states, char *names[], int n) override
Process the client newSwitch command.
virtual bool Sync(double ra, double dec) override
Set the telescope current RA and DEC coordinates to the supplied RA and DEC coordinates.
virtual void ISGetProperties(const char *dev) override
define the driver's properties to the client. Usually, only a minimum set of properties are defined t...
virtual bool updateLocation(double latitude, double longitude, double elevation) override
Update telescope location settings.
virtual bool initProperties() override
Called to initialize basic properties required all the time.
int main()
double ra
double dec
ISState
Switch state.
Definition indiapi.h:148
@ ISS_OFF
Definition indiapi.h:149
@ ISS_ON
Definition indiapi.h:150
#define getDeviceName
uint16_t type
Definition pwc-ioctl.h:0
Entry in the in memory alignment database.
Definition Common.h:152
double RightAscension
Right ascension in decimal hours. N.B. libnova works in decimal degrees so conversion is always neede...
Definition Common.h:190
double Declination
Declination in decimal degrees.
Definition Common.h:193
int PrivateDataSize
This size in bytes of any private data.
Definition Common.h:203
static const loggerConf file_off
Definition indilogger.h:219
void configure(const std::string &outputFile, const loggerConf configuration, const int fileVerbosityLevel, const int screenVerbosityLevel)
Method to configure the logger. Called by the DEBUG_CONF() macro. To make implementation easier,...
static Logger & getInstance()
Method to get a reference to the object (i.e., Singleton) It is a static method.
TEST(TelescopeSimulatorTest, switchingBetweenAltAzAndEquatorialClearsSyncPoints)