Próbuję wysterować silnik BLDC 3-f przy pomocy ATmega32 na podstawie poniższego kodu: #include <avr/interrupt.h> #include <avr/io.h> #include <util/twi.h> //Motoradresse #define MOTOR_ADR 0x70 //PHASE1 (U) #define UH_DDR DDRB |= (1<<3); #define UH_ON TCCR2A |= (1<<COM2A1); #define UH_OFF TCCR2A &= ~(1<<COM2A1); //PHASE1 (U) #define UL_DDR DDRB |= (1<<1); #define UL_ON PORTB |= (1<<1); #define UL_OFF PORTB &= ~(1<<1); //PHASE2 (V) #define VH_DDR DDRD |= (1<<5); #define VH_ON TCCR0A |= (1<<COM0B1); #define VH_OFF TCCR0A &= ~(1<<COM0B1); //PHASE2 (V) #define VL_DDR DDRB |= (1<<2); #define VL_ON PORTB |= (1<<2); #define VL_OFF PORTB &= ~(1<<2); //PHASE3 (W) #define WH_DDR DDRD |= (1<<3); #define WH_ON TCCR2A |= (1<<COM2B1); #define WH_OFF TCCR2A &= ~(1<<COM2B1); //PHASE3 (W) #define WL_DDR DDRC |= (1<<3); #define WL_ON PORTC |= (1<<3); #define WL_OFF PORTC &= ~(1<<3); #define PHASE_ALL_OFF UH_OFF;UL_OFF;VH_OFF;VL_OFF;WH_OFF;WL_OFF; #define SENSE_U ADMUX = 0; #define SENSE_V ADMUX = 1; #define SENSE_W ADMUX = 2; #define SENSE_H (ACSR&(1<<ACO)) #define START_PWM 5 volatile unsigned long i2c_timeout = 0; volatile unsigned char rx_pwm = 0; volatile unsigned char rotor_state = 0; volatile unsigned char rotor_run = 0; //############################################################################ void next_commutate_state (unsigned char startup) //############################################################################ { switch (rotor_state) { case (0): if(!SENSE_H || startup) { WH_OFF; UH_ON; SENSE_W; rotor_state = 1; TCNT1 = 1; } break; case (1): if(SENSE_H || startup) { VL_OFF; WL_ON; SENSE_V; rotor_state = 2; TCNT1 = 1; } break; case (2): if(!SENSE_H || startup) { UH_OFF; VH_ON; SENSE_U; rotor_state = 3; TCNT1 = 1; } break; case (3): if(SENSE_H || startup) { WL_OFF; UL_ON; SENSE_W; rotor_state = 4; TCNT1 = 1; } break; case (4): if(!SENSE_H || startup) { VH_OFF; WH_ON; SENSE_V; rotor_state = 5; TCNT1 = 1; } break; case (5): if(SENSE_H || startup) { UL_OFF; VL_ON; SENSE_U; rotor_state = 0; TCNT1 = 1; } break; } } //############################################################################ //back EMF zero crossing detection ISR (ANALOG_COMP_vect) //############################################################################ { if(rotor_run == 200) next_commutate_state (0); rotor_run++; if(rotor_run > 200) { rotor_run = 200; } } //############################################################################ ISR (TIMER1_OVF_vect) //############################################################################ { next_commutate_state (1); rotor_run = 0; OCR2A = START_PWM; OCR2B = START_PWM; OCR0B = START_PWM; } //############################################################################ ISR (TWI_vect) //############################################################################ { switch (TWSR & 0xF8) //TW_STATUS { //Adresse empfangen case TW_SR_SLA_ACK: TWCR |= (1<<TWINT); return; //Daten empfangen case TW_SR_DATA_ACK: rx_pwm = TWDR; TWCR |= (1<<TWINT); i2c_timeout = 0; return; //Bus-Fehler zurücksetzen case TW_NO_INFO: TWCR |=(1<<TWSTO) | (1<<TWINT); //Bus-Fehler zurücksetzen case TW_BUS_ERROR: TWCR |=(1<<TWSTO) | (1<<TWINT); } //Reset TW TWCR =(1<<TWEA) | (1<<TWINT) | (1<<TWEN) | (1<<TWIE); } //############################################################################ //Hauptprogramm int main (void) //############################################################################ { //Watchdog on WDTCSR = (1<<WDCE) | (1<<WDE); //Motordriver output UH_DDR; VH_DDR; WH_DDR; UL_DDR; VL_DDR; WL_DDR; //PWM for UH, VH and WH (>32KHz) TCCR0A |= (1<<COM0B1|1<<WGM01|1<<WGM00); TCCR0B |= (1<<CS00); TCCR2A |= (1<<COM2A1|1<<COM2B1|1<<WGM21|1<<WGM20); TCCR2B |= (1<<CS20); //TIMER1 for start commutation or Back EMF lost TCCR1B |= (1<<CS11); TIMSK1 |= (1<<TOIE1); PHASE_ALL_OFF; //Comperator init for back EMF ADCSRB |= (1<<ACME); DIDR1 |= (1<<AIN0D); ACSR |= (1<<ACIE); //I2C Init TWAR = MOTOR_ADR & 0xFE; TWCR = (1<<TWINT)|(1<<TWEA)|(1<<TWEN)|(1<<TWIE); //Interrupts enabel sei(); while(1) { asm("wdr"); if(rx_pwm > START_PWM) { ACSR |= (1<<ACIE); TIMSK1 |= (1<<TOIE1); if(rotor_run == 200) { OCR2A = rx_pwm; OCR2B = rx_pwm; OCR0B = rx_pwm; } i2c_timeout++; if(i2c_timeout>100000) { rx_pwm = 0; } } else { PHASE_ALL_OFF; ACSR&=~(1<<ACIE); TIMSK1 &= ~(1<<TOIE1); } } } Jest on dedykowany pod Atmege48/88/168 i mam problem z przerzuceniem go na 32 :( Czy ktoś mógłby mi pomóc w tej sprawie :?: Byłbym bardzo wdzięczny. Poniżej znajduje się schemat układu.
2
3
4
5
6
+12V
BLMC Brushless motor control
+12V
R1
270
+12V
RESET
A
1k
VCC
29
PC0(ADC0/PCINT8)
PC1(ADC1/PCINT9)
PC2(ADC2/PCINT10)
PC3(ADC3/PCINT11)
PC4(ADC4/SDA/PCINT12)
PC5(ADC5/SCL/PCINT13)
PB6(XTAL1/TOSC1/PCINT6)
ADC6
ADC7
PB7(XTAL2/TOSC2/PCINT7)
PD0(RXD/PCINT16)
PD1(TXD/PCINT17)
VCC
PD2(INT0/PCINT18)
VCC
PD3(INT1/OC2B/PCINT19)
PD4(T0/XCK/PCINT20)
AVCC
PD5(T1/OC0B/PCINT21)
AREF
PD6(AIN0/OC0A/PCINT22)
PD7(AIN1/PCINT23)
C15
100n
Q7
7
8
12MHz
4
6
GND
R22 33
18
20
B
23
24
25
26
27
28
19
22
PB0(ICP1/CLKO/PCINT0)
PB1(OC1A/PCINT1)
PB2(SS/OC1B/PCINT2)
PB3(MOSI/OC2A/PCINT3)
PB4(MISO/PCINT4)
PB5(SCK/PCINT5)
12
13
14
15
16
17
PC6(/RESET/PCINT14)
R23
22p
C8
22p
C9
MOSI/UH
IC3
10k
C1
100n
21
AGND
3
5
GND
GND
R4
C13
B_EMF_U
B_EMF_V
B_EMF_W
WL
SDA
SCL
100n
Q1
IRFR5305
T1
BC846
U
Q2
IRFR1205
33
UL
R3
R2
10k
GND
GND GND GND
30
31
32
1
2
9
10
11
+12V
+12V
WH
VH
SUMME_UVW
R5
270
+12V
1k
C12
UL
VL
MOSI/UH
MISO
SCK
VH
R8
100n
Q3
IRFR5305
T2
BC846
V
Q4
IRFR1205
33
VL
R7
GND
R6
10k
ATMEGA48/88/168-AU
GND
C
R25 100
3
2
1
TP1
TP2
TP3
TP4
TP5
SCK
MISO
MOSI/UH
RESET
SDA
SCL
R24 100
GND GND GND
+12V
JP1
GND
R9
270
+12V
GND
Power Supply 5V
BACK_EMF
C11
B_EMF_W
+12V
B_EMF_V
VCC
78L05
C14
D
C2
100n 100n
C3 C4
IC1
2,2µ
WH
U
C10
R21 4k7
R20 4k7
Q5
IRFR5305
T3
BC846
W
Q6
IRFR1205
33
WL
R11
R13 4k7
100µ
R12
100n
GND
SUMME_UVW
GND
1k
ATMEL APPNOTE 444 Page 7
B_EMF_U
OUT
+
IN
Voltage divider/low pass filter
+12V
A
B
C
R10
10k
R14 4k7
V
GND GND GND
W
R19 4k7
R15 4k7
10k 10k 10k
D
2,2µ
R18 R17 R16
GND
C5 C6 C7
100n 100n 100n
GND GND GND GND GND GND
1
ATMEL APPNOTE AVR443 PAGE 4
1
2
3
2011-11-18 06:24:18 C:\Documents and Settings\PawelG\Pulpit\ULC_BLMC_LAYOUT_V1\ULC_BLMC.sch (Sheet: 1/1)
4
5
6