×

INDI Library v2.0.7 is Released (01 Apr 2024)

Bi-monthly release with minor bug fixes and improvements

EQMOD: Custom device support - solving with SlewTo function call

  • Posts: 48
  • Thank you received: 0
HI

I made some progress with my custom tracker using an FPGA and coupling the drivers for it into EQMOD.

It seems when i select a coordinate in the "sky-map" and select GoTo in kstar, the SlewTo gets called. there are a couple if things that i noticed that I do not understand and was hoping to get some expert opinion on. It could be a configuration issue from my end. I added some extra info at the end of the message if that helps answer some part of the questions I am about to ask.

1. Selecting slew speed.
I see that there are a couple of code paths for it. If the encoder function is greater than lowspeedmargine=20000, high speed is selected. the code falls back to minperiod which is set to 6, otherwise, it selects a low-speed of 18. the commend would suggest -
/* highperiod = RA 450X DE (+5) 200x, low period 32x */
not really sure how we are asserting 18 is equivalent to 32x and 6 is x450. Maybe someone can clarify.
I modified the code to reflect what i believe should be the 32x and 450x. Before i commit the changes, i just wanted to check if I have missed something or not.

Also, why is the DE and the RA high-speed slew rates different?

reference file: github.com/rsarwar87/indi-3rdparty/blob/...eqmod/skywatcher.cpp
diff --git a/indi-eqmod/skywatcher.cpp b/indi-eqmod/skywatcher.cpp
index a0c0a480..9e012c9a 100644
--- a/indi-eqmod/skywatcher.cpp
+++ b/indi-eqmod/skywatcher.cpp
@@ -995,8 +995,20 @@ void Skywatcher::SlewTo(SkywatcherAxis axis, int32_t deltaencoder)
 {
     SkywatcherAxisStatus newstatus;
     bool useHighSpeed  = false;
-    uint32_t lowperiod = 18, lowspeedmargin = 20000, breaks = 400;
+    uint32_t period = 0, lowperiod = 18, lowspeedmargin = 20000, breaks = 400;
     /* highperiod = RA 450X DE (+5) 200x, low period 32x */
+    if (axis == Axis1)
+    {
+      period =
+        static_cast<uint32_t>(((SKYWATCHER_STELLAR_DAY * DEStepsWorm)/ static_cast<double>(DESteps360)) / 32);
+      lowperiod = 7;
+    }
+    else
+    {
+      period =
+        static_cast<uint32_t>(((SKYWATCHER_STELLAR_DAY * RAStepsWorm)/ static_cast<double>(RASteps360)) / 32);
+      lowperiod = 14;
+    }
     newstatus.slewmode = GOTO;
     if (deltaencoder >= 0)
         newstatus.direction = FORWARD;
@@ -1016,9 +1028,9 @@ void Skywatcher::SlewTo(SkywatcherAxis axis, int32_t deltaencoder)
     {
         SetMotion(axis, newstatus);
         if (useHighSpeed)
-            SetSpeed(axis, minperiods[axis], &newstatus);
+            SetSpeed(axis, period/lowperiod, &newstatus);
         else
-            SetSpeed(axis, lowperiod, &newstatus);
+            SetSpeed(axis, period, &newstatus);
         SetTarget(axis, deltaencoder);
 #ifdef _KOHERON
         if (!koheron_interface->SwpCmdStartMotion(axis, false, false, true))

2. the deltaraencoder and deltadeencoder values.
I noticed that when I select a coordinate on the backward direction, instead of taking the shortest path to that position, i.e. driving the motors backward, the motor always go in the forward direction, thereby do rotation > 180 degrees. When i checked the log files I noticed something even odd.
The full RAStep360=4608000. therefore it delta RA is greater than 360 deg; sometimes more than 720 deg. I understand these are calculated in eqmodbase.cpp which i have not touched. and since the device side driver do a modulus of the value, it all works out, but the motor does rotations > 180 degree instead of going backwards. Now is that now it is supposed to behave or have i missed a configuration somewhere?

I could add a modulus on the delta-encoders values, check if it is more than half of the xxStep360 to correct it in the SlewTo function, but I wanted to check with the experts what I am missing.
void Skywatcher::SlewTo(int32_t deltaraencoder, int32_t deltadeencoder)
 {
 
     LOGF_DEBUG("%s() : deltaRA = %d deltaDE = %d", __FUNCTION__, deltaraencoder, deltadeencoder);
+    deltaraencoder = deltaraencoder % RASteps360;
+    deltadeencoder = deltadeencoder % DESteps360;
+    deltaraencoder = (deltaraencoder > RASteps360 / 2) ? deltaraencoder - RASteps360 : deltaraencoder;
+    deltadeencoder = (deltadeencoder > DESteps360 / 2) ? deltadeencoder - DESteps360 : deltadeencoder;
     SlewTo(Axis1, deltaraencoder);
     SlewTo(Axis2, deltadeencoder);
indi_eqmod_telescope_18:02:13.log:DEBUG	659.592703 sec	: SlewTo() : deltaRA = 9046448 deltaDE = 4653041
indi_eqmod_telescope_18:02:13.log:DEBUG	718.630034 sec	: SlewTo() : deltaRA = 4611160 deltaDE = 4608000
indi_eqmod_telescope_18:27:37.log:DEBUG	136.235714 sec	: SlewTo() : deltaRA = 7235566 deltaDE = 5410220
indi_eqmod_telescope_18:27:37.log:DEBUG	172.776143 sec	: SlewTo() : deltaRA = 4609940 deltaDE = 9216000
indi_eqmod_telescope_18:34:41.log:DEBUG	25.215249 sec	: SlewTo() : deltaRA = 4559796 deltaDE = 10225027
indi_eqmod_telescope_18:34:41.log:DEBUG	97.324505 sec	: SlewTo() : deltaRA = 4611858 deltaDE = 9216000
indi_eqmod_telescope_18:34:41.log:DEBUG	119.688529 sec	: SlewTo() : deltaRA = 4725851 deltaDE = 9155639
indi_eqmod_telescope_18:34:41.log:DEBUG	191.901964 sec	: SlewTo() : deltaRA = 4611821 deltaDE = 9216000
indi_eqmod_telescope_18:49:31.log:DEBUG	21.016397 sec	: SlewTo() : deltaRA = 4373949 deltaDE = 9113967
indi_eqmod_telescope_18:49:31.log:DEBUG	92.630694 sec	: SlewTo() : deltaRA = 4611830 deltaDE = 9216000
indi_eqmod_telescope_18:51:41.log:DEBUG	54.708978 sec	: SlewTo() : deltaRA = 4827902 deltaDE = 9246140
indi_eqmod_telescope_18:51:41.log:DEBUG	61.401553 sec	: SlewTo() : deltaRA = 4608359 deltaDE = 9216000
indi_eqmod_telescope_18:51:41.log:DEBUG	74.594590 sec	: SlewTo() : deltaRA = 4732772 deltaDE = 9330643
indi_eqmod_telescope_18:51:41.log:DEBUG	90.763735 sec	: SlewTo() : deltaRA = 4345055 deltaDE = 9386074
indi_eqmod_telescope_18:51:41.log:DEBUG	159.359545 sec	: SlewTo() : deltaRA = 4611625 deltaDE = 9216000
indi_eqmod_telescope_18:51:41.log:DEBUG	185.151453 sec	: SlewTo() : deltaRA = 4716304 deltaDE = 9266592
indi_eqmod_telescope_18:51:41.log:DEBUG	234.951276 sec	: SlewTo() : deltaRA = 4849678 deltaDE = 8985747
indi_eqmod_telescope_18:51:41.log:DEBUG	303.852993 sec	: SlewTo() : deltaRA = 4611634 deltaDE = 9216000
INFO	54.701343 sec	: Starting Goto RA=12.5294 DE=46.8621 (current RA=13.6746 DE=49.2168)
INFO	54.701463 sec	: Aligned Eqmod Goto RA=12.5294 DE=46.8621 (target RA=12.5294 DE=46.8621)
INFO	54.701496 sec	: Setting Eqmod Goto RA=12.5294 DE=46.8621 (target RA=12.5294 DE=46.8621)
DEBUG	54.701536 sec	: StopRA() : calling RA StopWaitMotor
DEBUG	54.705307 sec	: StopDE() : calling DE StopWaitMotor
INFO	54.708907 sec	: Slewing mount: RA increment = 4827902, DE increment = 9246140
DEBUG	54.708978 sec	: SlewTo() : deltaRA = 4827902 deltaDE = 9246140
INFO	54.721523 sec	: Slewing to RA: 12:31:46 - DEC: 46:51:44
DEBUG	55.297444 sec	: IsRARunning() = true
DEBUG	56.321382 sec	: IsRARunning() = true
DEBUG	57.332179 sec	: IsRARunning() = true
DEBUG	58.345821 sec	: IsRARunning() = true
DEBUG	59.361949 sec	: IsRARunning() = true
DEBUG	60.381628 sec	: IsRARunning() = true
DEBUG	61.401150 sec	: IsRARunning() = false
DEBUG	61.401206 sec	: IsDERunning() = false
INFO	61.401228 sec	: Iterative Goto (1): RA diff = 6.71 arcsecs DE diff = 0.03 arcsecs
INFO	61.401295 sec	: Iterative goto (1): slew mount to RA increment = 4608359, DE increment = 9216000
DEBUG	61.401553 sec	: SlewTo() : deltaRA = 4608359 deltaDE = 9216000
DEBUG	62.440639 sec	: IsRARunning() = false
DEBUG	62.440674 sec	: IsDERunning() = false
INFO	62.440687 sec	: Iterative Goto (2): RA diff = 1.02 arcsecs DE diff = 0.03 arcsecs
DEBUG	62.443064 sec	: StartRATracking() : trackspeed = 15.0411 arcsecs/s, computed rate = 1
DEBUG	62.443108 sec	: SetRARate() : rate = 1
DEBUG	62.446795 sec	: StartDETracking() : trackspeed = 0 arcsecs/s, computed rate = 0
INFO	62.449028 sec	: Telescope slew is complete. Tracking TRACK_SIDEREAL...
INFO	74.583685 sec	: Starting Goto RA=11.8801 DE=37.9056 (current RA=12.5297 DE=46.8621)
INFO	74.583836 sec	: Aligned Eqmod Goto RA=11.8801 DE=37.9056 (target RA=11.8801 DE=37.9056)
INFO	74.583892 sec	: Setting Eqmod Goto RA=11.8801 DE=37.9056 (target RA=11.8801 DE=37.9056)
DEBUG	74.583958 sec	: StopRA() : calling RA StopWaitMotor
DEBUG	74.587933 sec	: StopDE() : calling DE StopWaitMotor
INFO	74.594530 sec	: Slewing mount: RA increment = 4732772, DE increment = 9330643
DEBUG	74.594590 sec	: SlewTo() : deltaRA = 4732772 deltaDE = 9330643
INFO	74.604375 sec	: Slewing to RA: 11:52:48 - DEC: 37:54:20
DEBUG	74.648346 sec	: IsRARunning() = true
DEBUG	75.661371 sec	: IsRARunning() = true
DEBUG	76.673641 sec	: IsRARunning() = true
DEBUG	77.693330 sec	: IsRARunning() = true
DEBUG	78.708531 sec	: IsRARunning() = true
DEBUG	79.723843 sec	: IsRARunning() = false
DEBUG	79.723890 sec	: IsDERunning() = false
INFO	79.723906 sec	: Iterative Goto (1): RA diff = 4.19 arcsecs DE diff = 0.09 arcsecs
DEBUG	79.727987 sec	: StartRATracking() : trackspeed = 15.0411 arcsecs/s, computed rate = 1
DEBUG	79.728040 sec	: SetRARate() : rate = 1
DEBUG	79.731062 sec	: StartDETracking() : trackspeed = 0 arcsecs/s, computed rate = 0
INFO	79.733387 sec	: Telescope slew is complete. Tracking TRACK_SIDEREAL...


Implementation:
The source fort he FPGA DRV8825 controller as well as the software drivers on the onboard ARM core is located in:
github.com/rsarwar87/koheron-sdk/tree/ma...ars_zx3/star-tracker

The client library for communicating with the device is in the /libclient directory. this has all the functional commands and some extra. This is linked to EQMOD, which then substitutes the relevant SkywatcherCommand. For this i forked the eqmod project and added codes to it to enable making the calls. you can grep for _KOHERON or koheron_interface to find the relevant snippets. no changes in the workflow/algorithm of eqmod were made.
github.com/rsarwar87/indi-3rdparty/blob/master/indi-eqmod/

Thanks

Rashed
Last edit: 3 years 9 months ago by Rashed.
3 years 9 months ago #56939

Please Log in or Create an account to join the conversation.

  • Posts: 226
  • Thank you received: 88
Hi,
Concerning goto slew speeds, the period figures (6 or 18) are related to the motor firmware, this is explained in the motor firmware protocol on page 2 (compute T1 period). I believe the min period values may be obtained from the firmware with a specific command, but this is not implemented in the indi-eqmod driver. The low speed period have been determined from the EQ6 firmware directly and corresponds to the min period for which the controller starts and stops motors without using an acceleration/deceleration ramp. Lastly the comments concerned my homemade board and mount (the Dec axis did not have the same ratio than the RA axis, furthermore it could not achieve the same high speed), so don't care about it.
Concerning deltara/deencoders, I'm not sure to understand what you mean with "backward direction". The skywatcher.cpp driver will run the motor as it has been asked, you could check it with the motion buttons. It does not always go in the forward direction. In eqmodbase.cpp which receives the goto command with the astronomical coordinates, you should take care of performing some flip if you don't want to hit the pier, thus it sometimes takes the longest path.
Is this the point you were talking about ?
By the way, nice work to implement such a protocol on a FPGA, it is much easier on a PIC...
The following user(s) said Thank You: Rashed
3 years 8 months ago #57223

Please Log in or Create an account to join the conversation.

  • Posts: 48
  • Thank you received: 0
Thanks for answering. i noticed that the eqmod repo has your name on the commits. I was not sure if I should have posted here or on github

I can achieve 1200x with a gear ratio of 5:1 on 24v supply, But i have no desire to spin it that fast. I am not using the HighSpeed mode in my design so i needed to work it out.. Thank you for the explanation, i believe it gives me an idea for a workaround. But i think i have solved that for now.

It works fine with the motion buttons, and they work fine.
If you look at Line 1005 in my fork of the repo, you will notice it is checking the sign of the int32_t encoders to determine if they are going forward or backward. If you notice the log below, which were produced by pointing to different areas on the sky-map, you will notice that they are always positive and sometimes more than one rotation.

I believe you are right, the problem I am referring to is coming from EQMod::Goto , which is where the encoder values are generated.

Since I believe you are a developer for this, i was hoping you could name the obvious cultpits that i can track down. However I have not made any changes to the eqmodbase.cpp file.

The only thing i can think of is that the calculation is using zeroDEEncoder which is DEStepInit in the skywatcher.cpp.
EDIT: This value is initialized to zero by the firmware i designed. or if the design has already been initilized, as will be the case for me, the value is set to 0x800000
indi_eqmod_telescope_18:02:13.log:DEBUG	659.592703 sec	: SlewTo() : deltaRA = 9046448 deltaDE = 4653041
indi_eqmod_telescope_18:02:13.log:DEBUG	718.630034 sec	: SlewTo() : deltaRA = 4611160 deltaDE = 4608000
indi_eqmod_telescope_18:27:37.log:DEBUG	136.235714 sec	: SlewTo() : deltaRA = 7235566 deltaDE = 5410220
indi_eqmod_telescope_18:27:37.log:DEBUG	172.776143 sec	: SlewTo() : deltaRA = 4609940 deltaDE = 9216000
indi_eqmod_telescope_18:34:41.log:DEBUG	25.215249 sec	: SlewTo() : deltaRA = 4559796 deltaDE = 10225027
indi_eqmod_telescope_18:34:41.log:DEBUG	97.324505 sec	: SlewTo() : deltaRA = 4611858 deltaDE = 9216000
indi_eqmod_telescope_18:34:41.log:DEBUG	119.688529 sec	: SlewTo() : deltaRA = 4725851 deltaDE = 9155639
indi_eqmod_telescope_18:34:41.log:DEBUG	191.901964 sec	: SlewTo() : deltaRA = 4611821 deltaDE = 9216000
indi_eqmod_telescope_18:49:31.log:DEBUG	21.016397 sec	: SlewTo() : deltaRA = 4373949 deltaDE = 9113967
indi_eqmod_telescope_18:49:31.log:DEBUG	92.630694 sec	: SlewTo() : deltaRA = 4611830 deltaDE = 9216000
indi_eqmod_telescope_18:51:41.log:DEBUG	54.708978 sec	: SlewTo() : deltaRA = 4827902 deltaDE = 9246140
indi_eqmod_telescope_18:51:41.log:DEBUG	61.401553 sec	: SlewTo() : deltaRA = 4608359 deltaDE = 9216000
indi_eqmod_telescope_18:51:41.log:DEBUG	74.594590 sec	: SlewTo() : deltaRA = 4732772 deltaDE = 9330643
indi_eqmod_telescope_18:51:41.log:DEBUG	90.763735 sec	: SlewTo() : deltaRA = 4345055 deltaDE = 9386074
indi_eqmod_telescope_18:51:41.log:DEBUG	159.359545 sec	: SlewTo() : deltaRA = 4611625 deltaDE = 9216000
indi_eqmod_telescope_18:51:41.log:DEBUG	185.151453 sec	: SlewTo() : deltaRA = 4716304 deltaDE = 9266592
indi_eqmod_telescope_18:51:41.log:DEBUG	234.951276 sec	: SlewTo() : deltaRA = 4849678 deltaDE = 8985747
indi_eqmod_telescope_18:51:41.log:DEBUG	303.852993 sec	: SlewTo() : deltaRA = 4611634 deltaDE = 9216000


everyone has got their preferred technology due to experience and background. I work more efficiently with an FPGA. But yes, for someone who does not know how to program and fpga or a PIC, the learning curve with an fpga makes it more reasonable to pick PIC.

but I am working out a single device that controls motor firmware directly, connects to camera and guidescipe (in the future). The FPGA i am using has an arm core which is running the webserver needed to communicate with the eqmod. FPGA essentially connects to the DRV8825 basd on the registers containing the required parameters. these registers are mapped to the ARM core running a linux (/dev/mem) and is populated by the webserver. and the camera over USB and hands it over to the ARM core
Last edit: 3 years 8 months ago by Rashed.
3 years 8 months ago #57228

Please Log in or Create an account to join the conversation.

  • Posts: 48
  • Thank you received: 0
Quick question:

why is RAInit and DAInit hardcoded to initialized to 0x800000 in Line 332 , when the device has already been initialized prior to running EQmod (which is what is happening in my case, as the device is initialized using a python script in the current dev state). I understand the skywatcher protocol only supports up to 24 bit, but that value is more than my total step count. Should it not be DESteps360/2?

This also means zeroDEEncoder is initialized to 0x800000, i.e. not zero which I initially thought.

I plan to connect gdb to eqmod to track it all down next weekend and report back - but in the meantime, any advice would be helpful

EDIT:
actually RA/DAInit should be initialised to 0x0. May i ask why an offset of 0x800000 was chosen?
Anyway, i changed the value to DESteps360/2. This is because the counter on the FPGA only counts till DESteps360 after which it flips back to 0. and it seems to be working fine now.

need to check meridian flip later on.
But still would like to know why that value is initialized to 0x800000 which is half of the full range of a 24-bit uint32_t. i.e. why is it not zero? and why kstar crashes when i set the value as zero.
Last edit: 3 years 8 months ago by Rashed.
3 years 8 months ago #57236

Please Log in or Create an account to join the conversation.

  • Posts: 226
  • Thank you received: 88
The initialization of both encoder values to 0x800000 comes from the skywatcher firmware, and particularly the hand controller: this is how it works, and it has been kept as is in case you start with the hand controller, unplug it and jump to serial port control. I don't think that the motor firmware performs any computations on each step to make a modulus or whatever, it just adds or substracts one to the microstep counter and eventually go to 0x000000 or 0xFFFFFF on overflow. These are 8bit PIC processors and this involves 3 operations/tests in the interrupt routine which is largely enough. All the modulus are made in the driver (eqmodbase) or the hand controller (which are PIC24 16 bit processors). Actually the encoder values are considered as unsigned int.
Is this kstars or indi-eqmod which is crashing ?
3 years 8 months ago #57364

Please Log in or Create an account to join the conversation.

  • Posts: 48
  • Thank you received: 0
Thank you for the explanation.

So what happens when the firmware is started using eqmod, hence the initialization was done with the current stepper counter (which I assume is not 0x80000), and then eqmod crashed requiring a restart of the software stack? The firmware, unless power-cycled, will register itself to have been already initialized, but will have a different init counter then the 0x80000 asserted by your code. Just curious

regarding the crash when initialized with zero value, it is kstar that crashes when a goto command is issued. Although eqmod does not die, it does behave oddly, i can see all the logs associated with EQMod::Goto up until the call to Skywatcher::SlewTo function - this member never gets called.
Last edit: 3 years 8 months ago by Rashed.
3 years 8 months ago #57391

Please Log in or Create an account to join the conversation.

Time to create page: 0.499 seconds