Hi, I am currently trying to build my own circuit to drive a bipolar stepper motor (or rather 3 of them) on a breadboard. So far i build an H-Bridge for every coil, with IRF9540N and IRF520N mosfets. Then i connected the gate of each N-channel mosfet with the gate of the P-channel mosfet on the same side and this directly to the arduino uno, so i only need two pins for each h-bridge and, at least that is my thought, i could assure that not both mosfets on one side are on. I tested it and it worked for some days, but then one motor started stuttering, then another one. I discovered that some N channel mosfets were suddenly always conducting. My guess is that they overheated, because when one side switches from high to low shortly both n and p mosfets on that side conduct. I mean the n channels sometimes (i didnt recognize any pattern) got rather hot. But still barely touchable, so i cant really imagine this killing them. I would be rather thankful if somebody had any idea what was happening or if it was a mistake i already fixed but forgot about that damaged them.
Also i dont know if i need pull-down/up resistors in this setup (or if the connection to the arduino prevents leaving the gates in a floating state) or if a resistor between the arduino and the gates would be useful or just slows the switch time.
As a power supply i am using a bench power supply currently set to 3 A (max rating of the motors) and 5 V.
Thanks for any help in advance, but please bear in mind that i am a total beginner.
Edit:
#include <util/delay.h>
#include "registers.h"
// bit macros
#define biton(register, bit) *register |= (1 << bit)
#define bitoff(register, bit) *register &= ~(1 << bit)
#define readbit(register, bit) (*register & (1 << bit))
// stepper motor functions
struct stepper
{
// keeps track of next step to know which coils are needed
int iStepPos;
// microcontroller Port for controlling the coils
volatile unsigned char *pPort;
// bits in port
char cCoil1Forwards;
char cCoil1Backwards;
char cCoil2Forwards;
char cCoil2Backwards;
};
// stepper functions
void
initStepper (struct stepper *motor, volatile unsigned char *pDDR,
volatile unsigned char *pPort, char cBitCoil1Forwards,
char cBitCoil1Backwards, char cBitCoil2Forwards,
char cBitCoil2Backwards)
{
// set coil pins to write
biton (pDDR, cBitCoil1Forwards);
biton (pDDR, cBitCoil1Backwards);
biton (pDDR, cBitCoil2Forwards);
biton (pDDR, cBitCoil2Backwards);
// initialize vars in struct motor
motor->pPort = pPort;
motor->cCoil1Forwards = cBitCoil1Forwards;
motor->cCoil1Backwards = cBitCoil1Backwards;
motor->cCoil2Forwards = cBitCoil2Forwards;
motor->cCoil2Backwards = cBitCoil2Backwards;
motor->iStepPos = 0;
motor->dTimeOfLastStep = 0;
// set all coils to starting value
bitoff (motor->pPort, cBitCoil1Forwards);
bitoff (motor->pPort, cBitCoil1Backwards);
bitoff (motor->pPort, cBitCoil2Forwards);
bitoff (motor->pPort, cBitCoil2Backwards);
}
void
step (struct stepper *motor, char bClockwise)
{
//TODO: upgrade to halfstep`
`
#define NROFSTEPS ((200 / 50) - 1)
// set iStepPos depending on direction and if cycle is compleded reset
// to the other end of the cycle
if (bClockwise > 0) // clockwise
{
if (motor->iStepPos < NROFSTEPS)
{
motor->iStepPos++;
}
else
{
motor->iStepPos = 0;
}
}
else // counterclockwise
{
if (motor->iStepPos > 0)
{
motor->iStepPos--;
}
else
{
motor->iStepPos = NROFSTEPS;
}
}
// depending on sign of step execute the next or the previous step
switch (motor->iStepPos)
{
case 0:
bitoff (motor->pPort, motor->cCoil2Backwards);
biton (motor->pPort, motor->cCoil1Forwards);
break;
case 1:
bitoff (motor->pPort, motor->cCoil1Forwards);
biton (motor->pPort, motor->cCoil2Forwards);
break;
case 2:
bitoff (motor->pPort, motor->cCoil2Forwards);
biton (motor->pPort, motor->cCoil1Backwards);
break;
case 3:
bitoff (motor->pPort, motor->cCoil1Backwards);
biton (motor->pPort, motor->cCoil2Backwards);
break;
}
}
int main ()
{
// init stepper
struct stepper test;
initStepper (&test, DDRD, PORTD, 0, 1, 2, 3);
//do one turn for testing
for (int i = 0; i < 200; i++)
{
step(&test; 1);
_delay_ms(3); //3 is not final, but the minimum that works and will be adjusted to match intended speed
}
}
registers.h contains only define statements for register names like this:
#define PORTB ((volatile unsigned char *)0x25)
I wrote it before I discovered avr/io.h.
Schematic of the h bridge I currently have:
Stepper motor datasheet:
