diff --git a/AstroEQ/AstroEQ.ino b/AstroEQ/AstroEQ.ino
index a5d71b5474103896a7d72d0b6a2fc8705eb50829..ca8b8d65b067f3bf8897c3acd6823908d9c9b0e2 100644
--- a/AstroEQ/AstroEQ.ino
+++ b/AstroEQ/AstroEQ.ino
@@ -9,7 +9,7 @@
  
   Works with EQ5, HEQ5, and EQ6 mounts (Not EQ3-2, they have a different gear ratio)
  
-  Current Verison: 3.6
+  Current Verison: 4.0
 */
 
 #include "synta.h"
@@ -32,6 +32,9 @@
 // sVal = aVal / Worm Gear Teeth
 // where worm gear teeth is how many teeth on the main worm gear. E.g. for an HEQ5 this is 135
 //
+// scalar = reduces the number reported to EQMOD, whilst not affecting mount behavior.
+// This is required if aVal is roughly greater than 10000000 (ten million). Numbers larger than this will overflow calculation limits and result in weird behaviour.
+//
 // mount specifics can be found here: http://tech.groups.yahoo.com/group/EQMOD/database?method=reportRows&tbl=5
 //
 // Summary of mounts (Untested):
@@ -85,6 +88,8 @@ Synta synta(1281,26542080,190985,16,184320,10);
 
 unsigned long gotoPosn[2] = {0,0}; //where to slew to
 unsigned int timerOVF[2];
+unsigned long timerCountRate;
+unsigned long minTimerOVF;
 
 //Pins
 const char resetPin[2] = {A1,A0};
@@ -242,7 +247,7 @@ void decodeCommand(char command, char* packetIn){ //each command is axis specifi
     case 'K': //stop the motor, return empty response
     
     
-        motorStop(0); //No specific response, just stop the motor (Feel free to customise motorStop function to suit your needs
+        motorStop(synta.axis()); //No specific response, just stop the motor (Feel free to customise motorStop function to suit your needs
       
       
         responseData = 0;
@@ -257,7 +262,11 @@ void decodeCommand(char command, char* packetIn){ //each command is axis specifi
         responseData = 0;
         break;
     case 'I': //set slew speed, return empty response (this sets the speed to move at if in slew mode)
-        synta.cmd.IVal(synta.axis(), synta.hexToLong(packetIn)); //set the speed container (convert string to long first)
+        responseData = synta.hexToLong(packetIn);
+        if (responseData > 650L){
+          responseData = 650L; //minimum speed to prevent timer overrun
+        }
+        synta.cmd.IVal(synta.axis(), responseData); //set the speed container (convert string to long first)
         
         //This will be different if you use a different motor code
         calculateRate(); //Used to convert speed into the number of 0.5usecs per step. Result is stored in TimerOVF
@@ -312,22 +321,18 @@ void calculateRate(){
   //
   //whether to use highspeed move or not is determined by the GVal;
   //
-  //clocks per step = 16000000 * seconds per step
+  //clocks per step = timerCountRate * seconds per step
   
   unsigned long rate;
-  unsigned long clockRate = 1600000L; //1/10th the actual clock to prevent numbers getting too big for an unsigned long
   if((synta.cmd.GVal(synta.axis()) == 2)||(synta.cmd.GVal(synta.axis()) == 1)){ //Normal Speed
-    rate = clockRate * synta.cmd.IVal(synta.axis());
+    rate = timerCountRate * synta.cmd.IVal(synta.axis());
     rate /= synta.cmd.bVal(synta.axis());
   } else if ((synta.cmd.GVal(synta.axis()) == 0)||(synta.cmd.GVal(synta.axis()) == 3)){ //High Speed
-    rate = clockRate * synta.cmd.IVal(synta.axis());
+    rate = timerCountRate * synta.cmd.IVal(synta.axis());
     rate /= synta.cmd.bVal(synta.axis());
     rate /= synta.cmd.gVal(synta.axis());
   }
-  char check[100] = {0};
-  sprintf(check,"%ld,%ld,%ld,%ld\n",clockRate,synta.cmd.IVal(synta.axis()),synta.cmd.bVal(synta.axis()),rate);
-  Serial1.print(check);
-  rate *= 10; //corrects for clock rate being set to 1/10th of the required to prevent numbers getting too big for an unsigned long.
+  rate *= 10; //corrects for timer count rate being set to 1/10th of the required to prevent numbers getting too big for an unsigned long.
   //Now truncate to an unsigned int with a sensible max value (the int is to avoid register issues with the 16 bit timer)
   if(rate < 539){ //We do 65535 - result as timer counts up from this number to 65536 then interrupts
     timerOVF[synta.axis()] = 64997L;
@@ -340,11 +345,7 @@ void calculateRate(){
 
 void slewMode(){
   digitalWrite(dirPin[synta.axis()],synta.cmd.dir(synta.axis())); //set the direction
-  if(timerOVF[synta.axis()] < 38000L){
-    accellerate(64); //accellerate to calculated rate in 64 steps
-  } else {
-    accellerate(32); //accellerate to calculated rate in 32 steps (faster to avoid missing serial messages)
-  }
+  accellerate(32,synta.axis()); //accellerate to calculated rate in 32 steps
   if(synta.axis()){
     TCNT4 = timerOVF[synta.axis()];
     TIMSK4 |= (1<<TOIE4); //Enable timer interrupt
@@ -357,34 +358,21 @@ void slewMode(){
 
 void gotoMode(){
   digitalWrite(dirPin[synta.axis()],synta.cmd.dir(synta.axis())); //set the direction
-  synta.cmd.IVal(synta.axis(), 176L);
-  calculateRate();
   unsigned int temp = 0;
-  byte accellerateSteps;
-  if (synta.cmd.HVal(synta.axis()) < 32){
-    synta.cmd.HVal(synta.axis(), 32); //This will cause a small error on VERY TINY Goto's though in reality should never be an issue.
+  if (synta.cmd.HVal(synta.axis()) < (40/synta.scalar())){
+    synta.cmd.HVal(synta.axis(), (40/synta.scalar())); //This will cause a small error on VERY TINY Goto's though in reality should never be an issue.
   }
-  if (synta.cmd.HVal(synta.axis()) < 64){
-    synta.cmd.HVal(synta.axis(),(synta.cmd.HVal(synta.axis()) - 16));
-    accellerateSteps = 16;
-  } else if(synta.cmd.HVal(synta.axis()) < 96){
-    synta.cmd.HVal(synta.axis(),(synta.cmd.HVal(synta.axis()) - 32));
-    accellerateSteps = 32;
-  } else if(synta.cmd.HVal(synta.axis()) < 128){
-    synta.cmd.HVal(synta.axis(),(synta.cmd.HVal(synta.axis()) - 48));
-    accellerateSteps = 48;
+  gotoPosn[synta.axis()] = synta.cmd.jVal(synta.axis()) + (synta.cmd.stepDir(synta.axis()) * synta.cmd.HVal(synta.axis())); //current position
+  
+  if (synta.cmd.HVal(synta.axis()) < (100/synta.scalar())){
+    synta.cmd.IVal(synta.axis(), 320L);
+    calculateRate();
+    accellerate(20,synta.axis()); //accellerate to calculated rate in 20 steps
   } else {
-    synta.cmd.HVal(synta.axis(),(synta.cmd.HVal(synta.axis()) - 64));
-    accellerateSteps = 64;
+    synta.cmd.IVal(synta.axis(), 176L); //Higher speed slew
+    calculateRate();
+    accellerate(64,synta.axis()); //accellerate to calculated rate in 64 steps
   }
-  gotoPosn[synta.axis()] = synta.cmd.jVal(synta.axis()) + (synta.cmd.stepDir(synta.axis()) * synta.cmd.HVal(synta.axis())); //current position
-  /*if(synta.cmd.HVal(synta.axis()) < 124){ //there are 496 steps of decelleration, so we need to find the correct part of the decelleration curve
-    //find point in decelleration curve (timerOVF[synta.axis()] -= 76; for each step)
-    temp = 124 - synta.cmd.HVal(synta.axis()); //number of decelleration steps into the curve
-    temp *= 304;
-    timerOVF[synta.axis()] -= temp;
-  }*/
-  accellerate(accellerateSteps); //accellerate to calculated rate in 64 steps
   synta.cmd.gotoEn(synta.axis(),1);
   if(synta.axis()){
     TCNT4 = timerOVF[synta.axis()];
@@ -396,37 +384,19 @@ void gotoMode(){
   synta.cmd.stopped(synta.axis(),0);
 }
 
-void motorStop(boolean caller){
-      if(synta.axis()){ //switch off correct axis
-        TIMSK4 &= ~(1<<TOIE4); //disable timer
-      } else {
-        TIMSK3 &= ~(1<<TOIE3); //disable timer
-      }
-      synta.cmd.gotoEn(synta.axis(),0); //Cancel goto mode
-      synta.cmd.stopped(synta.axis(),1); //mark as stopped
-      /*
-  if(!synta.cmd.stopped(synta.axis())){ //only has an effect if not already stopped
-    if(!caller && !synta.cmd.gotoEn(synta.axis())){ //If not in goto mode, then decellerate
-      synta.cmd.HVal(synta.axis(), (64997 - timerOVF[synta.axis()])); //work out where in decelleration curve we are to know how many steps to run
-      synta.cmd.HVal(synta.axis(), (synta.cmd.HVal(synta.axis()) / 76)); //19 0.5us's per step
-      synta.cmd.HVal(synta.axis(), (496 - synta.cmd.HVal(synta.axis()))); //find steps
-      gotoPosn[synta.axis()] = synta.cmd.jVal(synta.axis()) + (synta.cmd.stepDir(synta.axis()) * synta.cmd.HVal(synta.axis())); //current position
-      synta.cmd.gotoEn(synta.axis(),1); //Enter short goto mode stint
-    } else if (caller){ //otherwise, if decelleration complete, stop.
-      if(synta.axis()){ //switch off correct axis
-        TIMSK4 &= ~(1<<TOIE4); //disable timer
-      } else {
-        TIMSK3 &= ~(1<<TOIE3); //disable timer
-      }
-      synta.cmd.gotoEn(synta.axis(),0); //Cancel goto mode
-      synta.cmd.stopped(synta.axis(),1); //mark as stopped
-    } else if (synta.cmd.gotoEn(synta.axis())){ //otherwise, abort GOTO and decellerate.
-      synta.cmd.HVal(synta.axis(), (64997 - timerOVF[synta.axis()])); //work out where in decelleration curve we are to know how many steps to run
-      synta.cmd.HVal(synta.axis(), (synta.cmd.HVal(synta.axis()) / 76)); //76 0.5us's per step
-      synta.cmd.HVal(synta.axis(), (496 - synta.cmd.HVal(synta.axis()))); //find steps
-      gotoPosn[synta.axis()] =  synta.cmd.jVal(synta.axis()) + (synta.cmd.stepDir(synta.axis()) * synta.cmd.HVal(synta.axis())); //current position
-    }
-  }*/
+void motorStop(byte motor){
+  if(motor){ //switch off correct axis
+    TIMSK4 &= ~(1<<TOIE4); //disable timer
+  } else {
+    TIMSK3 &= ~(1<<TOIE3); //disable timer
+  }
+  if (synta.cmd.gotoEn(motor)){
+    synta.cmd.gotoEn(motor,0); //Cancel goto mode
+    decellerate(20,motor); //last 20 steps are decelleration. motorStop() is called 20 steps early to account for this.
+  } else {
+    decellerate(100,motor); //decellerate in 100 steps.
+  }
+  synta.cmd.stopped(motor,1); //mark as stopped
 }
 
 void motorEnable(){
@@ -434,22 +404,70 @@ void motorEnable(){
   synta.cmd.FVal(synta.axis(),1);
 }
 
-void accellerate(byte accellerateSteps){
+void decellerate(byte decellerateSteps, byte motor){
+  //x steps to slow down to minTimerOVF
+  unsigned long rate = 65535L - timerOVF[motor]; //rate is the number of clocks between steps at maximum speed.
+  unsigned long speedPerStep = (timerOVF[motor] - minTimerOVF);
+  speedPerStep /= decellerateSteps;
+  if (synta.cmd.bVal(motor) < 160000){//convert the number of clock cycles into uS.
+    speedPerStep >>= 1;
+  } else {
+    speedPerStep >>= 4;
+  }
+  if (speedPerStep == 0){
+    speedPerStep = 1; //just in case - prevents rounding from resulting in no accelleration at all.
+  }
+  unsigned int microDelay;
+  if (synta.cmd.bVal(motor) < 160000){
+    microDelay = rate >> 1; //number of uS to wait for current speed (rate is in 1/2ths of a microsecond)
+  } else {
+    microDelay = rate >> 4; //number of uS to wait for current speed (rate is in 1/16ths of a microsecond)
+  }
+  for(int i = 0;i < decellerateSteps;i++){
+    delayMicroseconds(microDelay);
+    if(synta.axis()){ //Step
+      writeSTEP2(HIGH);
+      delayMicroseconds(15);
+      writeSTEP2(LOW);
+    } else {
+      writeSTEP1(HIGH);
+      delayMicroseconds(15);
+      writeSTEP1(LOW);
+    }
+    microDelay += speedPerStep;
+  }
+  //Now at minimum speed, so safe to stop.
+}
+  
+void accellerate(byte accellerateSteps, byte motor){
   //x steps to speed up to timerOVF[synta.axis()]
-  unsigned int speedPerStep = (timerOVF[synta.axis()] - 10036L) / accellerateSteps; //Initial Speed is 10036
-  unsigned int microDelay = 27750L; //number of uS to wait for initial speed
+  unsigned long rate = 65535L - minTimerOVF; //rate is the number of clocks between steps at minimum speed.
+  unsigned long speedPerStep = (timerOVF[motor] - minTimerOVF);
+  speedPerStep /= accellerateSteps;
+  if (synta.cmd.bVal(motor) < 160000){//convert the number of clock cycles into uS.
+    speedPerStep >>= 1;
+  } else {
+    speedPerStep >>= 4;
+  }
+  if (speedPerStep == 0){
+    speedPerStep = 1; //just in case - prevents rounding from resulting in no accelleration at all.
+  }
+  unsigned int microDelay;
+  if (synta.cmd.bVal(motor) < 160000){
+    microDelay = rate >> 1; //number of uS to wait for initial speed (rate is in 1/2ths of a microsecond)
+  } else {
+    microDelay = rate >> 4; //number of uS to wait for initial speed (rate is in 1/16ths of a microsecond)
+  }
   for(int i = 0;i < accellerateSteps;i++){
-    for(byte j = 0;j < 2;j++){
-      delayMicroseconds(microDelay - 2);
-      if(synta.axis()){ //Step
-        writeSTEP2(HIGH);
-        delayMicroseconds(2);
-        writeSTEP2(LOW);
-      } else {
-        writeSTEP1(HIGH);
-        delayMicroseconds(2);
-        writeSTEP1(LOW);
-      }
+    delayMicroseconds(microDelay);
+    if(synta.axis()){ //Step
+      writeSTEP2(HIGH);
+      delayMicroseconds(15);
+      writeSTEP2(LOW);
+    } else {
+      writeSTEP1(HIGH);
+      delayMicroseconds(15);
+      writeSTEP1(LOW);
     }
     microDelay -= speedPerStep;
   }
@@ -468,13 +486,30 @@ void configureTimer(){
   //Disable compare interrupt (only interested in overflow)
   TIMSK3 &= ~((1<<OCIE3A) | (1<<OCIE3B) | (1<<OCIE3C));
   TIMSK4 &= ~((1<<OCIE4A) | (1<<OCIE4B) | (1<<OCIE4C));
-  //Set prescaler to F_CPU/1
-  TCCR3B &= ~(1<<CS32); //0
-  TCCR3B |= (1<<CS30);//1
-  TCCR3B &= ~(1<<CS31);//0
-  TCCR4B &= ~(1<<CS42); //0
-  TCCR4B |= (1<<CS40);//1
-  TCCR4B &= ~(1<<CS41);//0
+  if (synta.cmd.bVal(synta.axis()) < 160000){
+    timerCountRate = 200000;
+    //Set prescaler to F_CPU/8
+    TCCR3B &= ~(1<<CS32); //0
+    TCCR3B |= (1<<CS31);//1
+    TCCR3B &= ~(1<<CS30);//0
+    TCCR4B &= ~(1<<CS42); //0
+    TCCR4B |= (1<<CS41);//1
+    TCCR4B &= ~(1<<CS40);//0
+  } else {
+    timerCountRate = 1600000;
+    //Set prescaler to F_CPU/1
+    TCCR3B &= ~(1<<CS32); //0
+    TCCR3B &= ~(1<<CS31);//0
+    TCCR3B |= (1<<CS30);//1
+    TCCR4B &= ~(1<<CS42); //0
+    TCCR4B &= ~(1<<CS41);//0
+    TCCR4B |= (1<<CS40);//1
+  }
+  Serial1.println((unsigned long)timerCountRate);
+  unsigned long rate = timerCountRate * 650L; //min rate of just under the sidereal rate
+  rate /= synta.cmd.bVal(synta.axis());
+  rate *= 10; //corrects for timer count rate being set to 1/10th of the required to prevent numbers getting too big for an unsigned long.
+  minTimerOVF = 65535L - rate;
 }
 
 /*Timer Interrupt Vector*/
@@ -508,10 +543,8 @@ void motorStep(byte motor){
       if(synta.cmd.gotoEn(motor)){
         long stepsLeft = gotoPosn[motor] - synta.cmd.jVal(motor);
         stepsLeft *= synta.cmd.stepDir(motor);
-        if(stepsLeft <= 0){
-          motorStop(1);
-        } else if (stepsLeft < 124){
-          //timerOVF[motor] -= 304; //decelleration region
+        if(stepsLeft <= (20/synta.scalar())){
+          motorStop(motor); //will decellerate the rest of the way
         }
       }
     }
@@ -523,10 +556,8 @@ void motorStep(byte motor){
       if(synta.cmd.gotoEn(motor)){
         long stepsLeft = gotoPosn[motor] - synta.cmd.jVal(motor);
         stepsLeft *= synta.cmd.stepDir(motor);
-        if(stepsLeft <= 0){
-          motorStop(1);
-        } else if (stepsLeft < 124){
-          //timerOVF[motor] -= 304; //decelleration region
+        if(stepsLeft <= (20/synta.scalar())){
+          motorStop(motor);
         }
       }
     }
diff --git a/README b/README
index 92c924fcff2adff08aeb30edeb6688daa59e0d59..292a5cc1df1514652e8e7fddf51e6854922fec74 100644
--- a/README
+++ b/README
@@ -29,5 +29,5 @@ Also if you have problems getting the numbers to work, open an issue thread and
  
   Works with EQ3, EQ5, HEQ5, and EQ6 mounts. Along With custom mounts.
  
-  Current Verison: 3.6 
+  Current Verison: 4.0
 */
\ No newline at end of file