It comes with two 7.2V DC motors. stall current is 2.4A.
As most drivers out there can only take 2A, I decided to play safe and buy the official driver board for the chassis:
This board can take up to 4A so it is more then enough. In addition to the usual PWM and direction pins, this board allows me to measure the current using an analog pin.
I was trying to implement a routine to stop the motors when a current higher than normal was detected. This way the arduino would be able to stop the rover if it rams an obstacle and thus save some battery. To know what "a current higher than normal" means, I had to do some stall tests... These were conducted without problems, so I noted the numbers and went to sleep.
I don't know what could have happened but the next day I encountered digital pin 2 (used to set motor 1 direction) burnt. Also PWM pins 9 (where motor 2 PWM was wired) and 10 (where nothing at all was wired!) are damaged and wont send the correct signal but at 100% duty cycle.
In the tests, the higher current registered was 2A. Normally currents wont get past 1A when obstacles are encountered. Probably they won't be greater than 0.7A as I'll operate at 50% duty cycle. But I want to know what went wrong, and how could I prevent it from occurring again. The driver is ok, every channel works as expected, the engines are also good, but I can't risk to damage a new Arduino, even if no more extreme tests are going to be made.
The driver board logic (not the motors) is powered by arduino's 5V. And for each motor channel, there are 3 pins connected:
Its usually a wise precaution to add 1k series resistors on control lines to a high power motor control
chip - limit any fault currents into the microcontroller.
There are various possibilities, from inadequate decoupling to electromagnetic interference (have
you a ground plane?) or just crazy layout (long straggly wires all over the place rather than
twisted pair and star-grounding - breadboarded circuits are often well short of ideal layout).
I'm sure this problem has to do with the driver board because the Arduino was damaged that day. The day before I was using it with another shield, and the day after the driver tests it was broken.
Arduino digital output to driver board Direction pin (x2)
Arduino PWM digital output to driver board PWM pin (x2)
Arduino analog input to driver board current measurement pin (0 to 5V) (x2)
Somehow some amps from the motors got loose that day and ended up in the arduino through any of these wires.
I dont think the analog inputs are involved because the two of them are working ok before and after the incident.
With only the 5V pin and digital outputs remaining, I'd say that the 5V is not the culprit, because it would have damaged the whole arduino, not just some pins. But I'm no expert and as I don't know for certain what happened, I just want to take preemptive measures. I'll be showing this project at university and can't risk being ridiculed by showing a dying rover LOL
So I need your help to better isolate the Arduino from the driver board. My initial proposal:
Separate voltage regulator for the driver board 5V Vcc.
Optocouplers for the PWM and direction pins.
And now my questions:
Can you recommend a good DC buck converter to go from 7.2 V to 5V? LM2596s are on offer now
Can I power the new regulator with the motors battery? I've only two batteries on board, and one is reserved for the arduino.
What can I do about the analog input pin? These can't be optocoupled!
zoomkat:
Can you give a technical description of "burnt" and how you determined that?
It is explained in the first post. I've detected damage in three pins.
digital PIN 2 was used as digital output and after the incident it can't be set to HIGH.
digital PIN 9 was used as PWM and after the incident it can't be used for PWM but at 100% duty cycle
same story for digital PIN 10
About how I determined that: for each faulty wire, I first left them connected to the Arduino pins and changed to different channels in the driver board. I have 4 channels, #1 and #2 were the ones I used for the stall tests, and I changed to #3 and #4 which were not used before. In case the channels #1 and #2 were the ones damaged, the wires would have worked with #3 and #4. They didn't, so I changed to different Arduino pins, and I realized that they worked with all four channels in the driver. That meant the damage was in some Arduino pins and not in the driver.
The motor power supply should not be connected without first connecting the +5V for logic
I think I might have done that. But is that enough to fry some pins?
Other than this, I'll be ordering a dedicated buck regulator for the driver and some optocouplers. I've tested the PWM with optos and even the slow 4N35 works. About the analog input that can't be optocoupled, maybe adding a resistor in series would better protect the pin from high currents? But it might also drop some voltage?
Digital pin 2: it was not burnt. I was activating the pull-up resistor by mistake, so the voltage was 1.77V instead of 5. I'm also using analog pin 2, and because analogWrite can take both A2 and 2 as parameter (I was passing the latter), I had defined a constant for analog pin 2 which was also being used to call pinMode in the setup code. Yeah, I forgot that analog pins don't need to be configured as inputs before reading. The code was something like this:
#define DIRECTION_PIN 2
#define CURRENT_SENSING_PIN 2 //This should have been A2
pinMode(DIRECTION_PIN, OUTPUT); //Setting up digital pin 2 as output
pinMode(CURRENT_SENSING_PIN 2, INPUT); //Trying to set up analog pin 2 as input, but actually setting digital pin 2
digitalWrite(DIRECTION_PIN, HIGH); //Here we're activating pull-up resistor for pin 2!!
Had I used A2 (which is defined as 16) instead of 2 for the analog pin macro, this wouldn't have happened. On the other hand, the API could have been designed to prevent this kind of errors. Namely:
A0, A1 could have been enums instead of constants, and analogRead could have been defined to only accept enums as parameter
Remove the hack to activate the pull-up resistor and replace it with an activatePullUp(int) method instead
What was the API designer thinking? You can't give ints to "artists and designers"! Ints are loaded by the devil
Now about my second problem: PWM pins number 9 and 10. They are not damaged at all. But I'm using the Timer1 library, which as its name implies uses the timer #1 for the interruptions. And this same timer is the one used for the PWM generation for pins 9 and 10. Trying to have interrupts and PWMs on the same timer resulted in PWMs not being generated correctly. Changing from pins 9 or 10 to 11 made my code work, as this pin uses the timer2.