Go Down

Topic: Dual VNH5019 Motor Shield (Read 857 times) previous topic - next topic

vleud101

Jun 05, 2013, 02:15 pm Last Edit: Jun 05, 2013, 03:06 pm by vleud101 Reason: 1
Dear members from the Arduino forum,

I just received this week my Dual VNH5019 Motor Shield (From polulu). The shield works perfectly with my Arduino Uno, but i have problems with my Arduino mega (2560). I get the error M1 fault. I read what the error means, shortcut etc.

I just wonder if more people has the same problem.. (i already did some research [google] but not much hits).

I just the next libarary file from the shield: https://github.com/pololu/Dual-VNH5019-Motor-Shield

Now i hope somebody can help me out.

Kind Regards,

Dave
____
The code:

Demo.pde

Code: [Select]
#include "DualVNH5019MotorShield.h"

DualVNH5019MotorShield md;

void stopIfFault()
{
 if (md.getM1Fault())
 {
   Serial.println("M1 fault");
   while(1);
 }
 if (md.getM2Fault())
 {
   Serial.println("M2 fault");
   while(1);
 }
}

void setup()
{
 Serial.begin(115200);
 Serial.println("Dual VNH5019 Motor Shield");
 md.init();
}

void loop()
{
 for (int i = 0; i <= 400; i++)
 {
   md.setM1Speed(i);
   stopIfFault();
   if (i%200 == 100)
   {
     Serial.print("M1 current: ");
     Serial.println(md.getM1CurrentMilliamps());
   }
   delay(2);
 }
 
 for (int i = 400; i >= -400; i--)
 {
   md.setM1Speed(i);
   stopIfFault();
   if (i%200 == 100)
   {
     Serial.print("M1 current: ");
     Serial.println(md.getM1CurrentMilliamps());
   }
   delay(2);
 }
 
 for (int i = -400; i <= 0; i++)
 {
   md.setM1Speed(i);
   stopIfFault();
   if (i%200 == 100)
   {
     Serial.print("M1 current: ");
     Serial.println(md.getM1CurrentMilliamps());
   }
   delay(2);
 }

 for (int i = 0; i <= 400; i++)
 {
   md.setM2Speed(i);
   stopIfFault();
   if (i%200 == 100)
   {
     Serial.print("M2 current: ");
     Serial.println(md.getM2CurrentMilliamps());
   }
   delay(2);
 }
 
 for (int i = 400; i >= -400; i--)
 {
   md.setM2Speed(i);
   stopIfFault();
   if (i%200 == 100)
   {
     Serial.print("M2 current: ");
     Serial.println(md.getM2CurrentMilliamps());
   }
   delay(2);
 }
 
 for (int i = -400; i <= 0; i++)
 {
   md.setM2Speed(i);
   stopIfFault();
   if (i%200 == 100)
   {
     Serial.print("M2 current: ");
     Serial.println(md.getM2CurrentMilliamps());
   }
   delay(2);
 }
}


DualVNH5019MotorShield.cpp
Code: [Select]

#include "DualVNH5019MotorShield.h"

// Constructors ////////////////////////////////////////////////////////////////

DualVNH5019MotorShield::DualVNH5019MotorShield()
{
 //Pin map
 _INA1 = 2;
 _INB1 = 4;
 _EN1DIAG1 = 6;
 _CS1 = A0;
 _INA2 = 7;
 _INB2 = 8;
 _EN2DIAG2 = 12;
 _CS2 = A1;
}

DualVNH5019MotorShield::DualVNH5019MotorShield(unsigned char INA1, unsigned char INB1, unsigned char EN1DIAG1, unsigned char CS1,
                                              unsigned char INA2, unsigned char INB2, unsigned char EN2DIAG2, unsigned char CS2)
{
 //Pin map
 //PWM1 and PWM2 cannot be remapped because the library assumes PWM is on timer1
 _INA1 = INA1;
 _INB1 = INB1;
 _EN1DIAG1 = EN1DIAG1;
 _CS1 = CS1;
 _INA2 = INA2;
 _INB2 = INB2;
 _EN2DIAG2 = EN2DIAG2;
 _CS2 = CS2;
}

// Public Methods //////////////////////////////////////////////////////////////
void DualVNH5019MotorShield::init()
{
// Define pinMode for the pins and set the frequency for timer1.

 pinMode(_INA1,OUTPUT);
 pinMode(_INB1,OUTPUT);
 pinMode(_PWM1,OUTPUT);
 pinMode(_EN1DIAG1,INPUT);
 pinMode(_CS1,INPUT);
 pinMode(_INA2,OUTPUT);
 pinMode(_INB2,OUTPUT);
 pinMode(_PWM2,OUTPUT);
 pinMode(_EN2DIAG2,INPUT);
 pinMode(_CS2,INPUT);
 #if defined(__AVR_ATmega168__)|| defined(__AVR_ATmega328P__)
 // Timer 1 configuration
 // prescaler: clockI/O / 1
 // outputs enabled
 // phase-correct PWM
 // top of 400
 //
 // PWM frequency calculation
 // 16MHz / 1 (prescaler) / 2 (phase-correct) / 400 (top) = 20kHz
 TCCR1A = 0b10100000;
 TCCR1B = 0b00010001;
 ICR1 = 400;
 #endif
}
// Set speed for motor 1, speed is a number betwenn -400 and 400
void DualVNH5019MotorShield::setM1Speed(int speed)
{
 unsigned char reverse = 0;
 
 if (speed < 0)
 {
   speed = -speed;  // Make speed a positive quantity
   reverse = 1;  // Preserve the direction
 }
 if (speed > 400)  // Max PWM dutycycle
   speed = 400;
 #if defined(__AVR_ATmega168__)|| defined(__AVR_ATmega328P__)
 OCR1A = speed;
 #else
 analogWrite(_PWM1,speed * 51 / 80); // default to using analogWrite, mapping 400 to 255
 #endif
 if (speed == 0)
 {
   digitalWrite(_INA1,LOW);   // Make the motor coast no
   digitalWrite(_INB1,LOW);   // matter which direction it is spinning.
 }
 else if (reverse)
 {
   digitalWrite(_INA1,LOW);
   digitalWrite(_INB1,HIGH);
 }
 else
 {
   digitalWrite(_INA1,HIGH);
   digitalWrite(_INB1,LOW);
 }
}

// Set speed for motor 2, speed is a number betwenn -400 and 400
void DualVNH5019MotorShield::setM2Speed(int speed)
{
 unsigned char reverse = 0;
 
 if (speed < 0)
 {
   speed = -speed;  // make speed a positive quantity
   reverse = 1;  // preserve the direction
 }
 if (speed > 400)  // Max
   speed = 400;
 #if defined(__AVR_ATmega168__)|| defined(__AVR_ATmega328P__)
 OCR1B = speed;
 #else
 analogWrite(_PWM2,speed * 51 / 80); // default to using analogWrite, mapping 400 to 255
 #endif
 if (speed == 0)
 {
   digitalWrite(_INA2,LOW);   // Make the motor coast no
   digitalWrite(_INB2,LOW);   // matter which direction it is spinning.
 }
 else if (reverse)
 {
   digitalWrite(_INA2,LOW);
   digitalWrite(_INB2,HIGH);
 }
 else
 {
   digitalWrite(_INA2,HIGH);
   digitalWrite(_INB2,LOW);
 }
}

// Set speed for motor 1 and 2
void DualVNH5019MotorShield::setSpeeds(int m1Speed, int m2Speed)
{
 setM1Speed(m1Speed);
 setM2Speed(m2Speed);
}

// Brake motor 1, brake is a number between 0 and 400
void DualVNH5019MotorShield::setM1Brake(int brake)
{
 // normalize brake
 if (brake < 0)
 {
   brake = -brake;
 }
 if (brake > 400)  // Max brake
   brake = 400;
 digitalWrite(_INA1, LOW);
 digitalWrite(_INB1, LOW);
 #if defined(__AVR_ATmega168__)|| defined(__AVR_ATmega328P__)
 OCR1A = brake;
 #else
 analogWrite(_PWM1,brake * 51 / 80); // default to using analogWrite, mapping 400 to 255
 #endif
}

// Brake motor 2, brake is a number between 0 and 400
void DualVNH5019MotorShield::setM2Brake(int brake)
{
 // normalize brake
 if (brake < 0)
 {
   brake = -brake;
 }
 if (brake > 400)  // Max brake
   brake = 400;
 digitalWrite(_INA2, LOW);
 digitalWrite(_INB2, LOW);
 #if defined(__AVR_ATmega168__)|| defined(__AVR_ATmega328P__)
 OCR1B = brake;
 #else
 analogWrite(_PWM2,brake * 51 / 80); // default to using analogWrite, mapping 400 to 255
 #endif
}

// Brake motor 1 and 2, brake is a number between 0 and 400
void DualVNH5019MotorShield::setBrakes(int m1Brake, int m2Brake)
{
 setM1Brake(m1Brake);
 setM2Brake(m2Brake);
}

// Return motor 1 current value in milliamps.
unsigned int DualVNH5019MotorShield::getM1CurrentMilliamps()
{
 // 5V / 1024 ADC counts / 144 mV per A = 34 mA per count
 return analogRead(_CS1) * 34;
}

// Return motor 2 current value in milliamps.
unsigned int DualVNH5019MotorShield::getM2CurrentMilliamps()
{
 // 5V / 1024 ADC counts / 144 mV per A = 34 mA per count
 return analogRead(_CS2) * 34;
}

// Return error status for motor 1
unsigned char DualVNH5019MotorShield::getM1Fault()
{
 return !digitalRead(_EN1DIAG1);
}

// Return error status for motor 2
unsigned char DualVNH5019MotorShield::getM2Fault()
{
 return !digitalRead(_EN2DIAG2);
}



DualVNH5019MotorShield.h
Code: [Select]
#ifndef DualVNH5019MotorShield_h
#define DualVNH5019MotorShield_h

#include <Arduino.h>

class DualVNH5019MotorShield
{
 public:  
   // CONSTRUCTORS
   DualVNH5019MotorShield(); // Default pin selection.
   DualVNH5019MotorShield(unsigned char INA1, unsigned char INB1, unsigned char EN1DIAG1, unsigned char CS1,
                          unsigned char INA2, unsigned char INB2, unsigned char EN2DIAG2, unsigned char CS2); // User-defined pin selection.
   
   // PUBLIC METHODS
   void init(); // Initialize TIMER 1, set the PWM to 20kHZ.
   void setM1Speed(int speed); // Set speed for M1.
   void setM2Speed(int speed); // Set speed for M2.
   void setSpeeds(int m1Speed, int m2Speed); // Set speed for both M1 and M2.
   void setM1Brake(int brake); // Brake M1.
   void setM2Brake(int brake); // Brake M2.
   void setBrakes(int m1Brake, int m2Brake); // Brake both M1 and M2.
   unsigned int getM1CurrentMilliamps(); // Get current reading for M1.
   unsigned int getM2CurrentMilliamps(); // Get current reading for M2.
   unsigned char getM1Fault(); // Get fault reading from M1.
   unsigned char getM2Fault(); // Get fault reading from M2.
   
 private:
   unsigned char _INA1;
   unsigned char _INB1;
   static const unsigned char _PWM1 = 9;
   unsigned char _EN1DIAG1;
   unsigned char _CS1;
   unsigned char _INA2;
   unsigned char _INB2;
   static const unsigned char _PWM2 = 10;
   unsigned char _EN2DIAG2;
   unsigned char _CS2;
   
};

#endif

codlink

M1 fault means that your power supply is not sufficient. 

http://forum.pololu.com/viewtopic.php?f=15&t=4830
//LiNK

vleud101

Hi, at first point thanks for replying and trying to help me out/

I already read that topic on pololu.

I have a power supply of 30 Ampere at 12V. I already try-ed to use a separated power supply at the Arduino and the driver without success.. same error.

I try to figure out what the pin difference is between the Mega and the Uno, i see some timers are different but if that is the problem.. i don't know.

Go Up
 


Please enter a valid email to subscribe

Confirm your email address

We need to confirm your email address.
To complete the subscription, please click the link in the email we just sent you.

Thank you for subscribing!

Arduino
via Egeo 16
Torino, 10131
Italy