直流无刷电机控制PIC程序(全部整合)

合集下载

直流无刷电机控制PIC程序(最新)

直流无刷电机控制PIC程序(最新)

#include <pic168xa.h> //2008.4.24--14点00分#include <math.h>#include <stdlib.h>int charge_delay,jm,lkk,trial,run_num,protect_num;char m,n,k,s,L,tri;char hall_num; //循环次数char hall_number; //1+3+2+10+8+9=33(一个循环和),hallless_protect()int pwm_hi; // pwm占空比上限int pwm_cycle; // pwm周期int pwm_lo; // pwm占空比下限,由A/D结果确定int pwm_real; // pwm占空比实际int ad_result; // A/D转换结果bit ghy,run_flag; //运行标志---0,未运行,停止bit flag_autohand; //开始为-----自动void delay(delay_num)int delay_num;{int j;for (j=delay_num;j>1;j--){asm("nop");}}union adres{int y1;unsigned char adre[2];}adresult;void para_chushihua(){protect_num=0;trial=0b10110000;tri=0x00;lkk=10;hall_num=0x00;hall_number=0x00;run_flag=0; //运行标志---0,未运行,停止flag_autohand=1; //开始为-----自动pwm_cycle= 240; // pwm周期// pwm_hi=pwm_cycle-5; // pwm占空比上限pwm_hi=pwm_cycle-1; // pwm占空比上限pwm_real=pwm_cycle; // 实际pwm占空比为pwm周期上限pwm_lo=0x0A; //设定下限+++++++++++++++++++++++++++++++++++++++++++++++}void nointerupt_chushihua(){INTCON=0X00; //禁止中断}void Io_chushihua(){// ADCON1=0x8e; //RA0/AN0--VOLTAGE 电压采样,右对齐1 ADCON1=0x86; //设定RA0--RA6设定为I/O口;TRISA =0x09; //RA0---PROTECT保护(电流保护和过温保护)--输出,0--不保护,1--保护;//RA1----PSW1,继电器,输出,0,电源接通//RA2----指示灯,输出0--->>//RA3----按键,加,输入 1//RA4----指示灯,输出0--->>//RA5----RSW1,继电器,输出0,软启充电PORTA=PORTA&0x09; //RA1=0,----输出低电平,PSW1,继电器断//RA2=0,----输出低电平,指示灯灭//RA4=0,----输出低电平,指示灯灭//RA5=0,----输出低电平,RSW1,继电器断RBPU=0; //RB端口内部弱上拉电路禁止TRISB =0xfe; //RB7=1, 空----输入//RB6=1----HA,输入//RB5=1----HB,输入//RB4=1----HC,输入//RB3=1----停,输入,按钮//RB2=1----启,输入,按钮//RB1=1----自/手选择,输入,开关//RB0=0----ST/STOP,输出,控制GAL PORTB=PORTB&0xfe; //RB0=0,----输出低电平,禁止GAL输出TRISC =0x02; //RC7---A1+,PWMA1+,输出0//RC6---A1, 输出0//RC5---B1+,输出0//RC4---B1,输出0//RC3---C1+,输出0//RC2---CCP1(PWM),输出,死区0//RC1----减,输入,按钮 1//RC0---C1,输出0 PORTC=0x06;}void protect(){ //过流和过温保护GIE=0; //关全局中断pwm_real=pwm_hi; //PWM_real----PWM实时值CCPR1L=pwm_real; //设置PWM输出为最大CCPR1H=0x00; //CCP1CON=0x0c; //CCP1选择为PWM工作方式PR2=pwm_cycle; //设置PWM的周期TRISC=TRISC&0xfb; //设置RC2---PWM输出T2CON=0x00; //分频系数=0x00TMR2ON=1; //启用TMR2PORTC=0x00; //PORTB=PORTB&0xfe; //RB0=0,----输出低电平,禁止GAL输出while(1){PORTA^=0b00010100;delay(15000); //延时}}void protect_run(){ //过流和过温保护GIE=0; //关全局中断pwm_real=pwm_hi; //PWM_real----PWM实时值CCPR1L=pwm_real; //设置PWM输出为最大CCPR1H=0x00; //CCP1CON=0x0c; //CCP1选择为PWM工作方式PR2=pwm_cycle; //设置PWM的周期TRISC=TRISC&0xfb; //设置RC2---PWM输出T2CON=0x00; //分频系数=0x00TMR2ON=1; //启用TMR2PORTC=0x00; //PORTB=PORTB&0xfe; //RB0=0,----输出低电平,禁止GAL输出while(1){// PORTA^=0b00010000; //RA4闪动PORTA^=0b00000100; //RA2闪动delay(15000); //延时}}void PWM_chushihua(){// CCPR1L=0xa0;// CCPR1H=0x00;run_num=0;pwm_real=pwm_hi; //PWM_real----PWM实时值CCPR1L=pwm_real; //设置PWM输出为最大CCPR1H=0x00; //CCP1CON=0x0c; //CCP1选择为PWM工作方式PR2=pwm_cycle; //设置PWM的周期TRISC=TRISC&0xfb; //设置RC2---PWM输出T2CON=0x00; //分频系数=0x00TMR2ON=1; //启用TMR2}void open_loopf() //开环运行50次,启动{k=0b00011000; //5 //HA,HB,HC,s=PORTC&0b00000110; //1 0 1, B-C+PORTC=k|s; //delay(8000); //延时k=0b10010000; //4 //HA,HB,HC,s=PORTC&0b00000110; //1 0 0, A+B-PORTC=k|s; //delay(8000); //延时k=0b10000001; //6 //HA,HB,HC,s=PORTC&0b00000110; //1 1 0, C-A+PORTC=k|s; //delay(8000); //延时k=0b00100001; //2 //HA,HB,HC,s=PORTC&0b00000110; //0 1 0, B+C-PORTC=k|s; //delay(8000); //延时k=0b01100000; //3 //HA,HB,HC,s=PORTC&0b00000110; //0 1 1, A-B+PORTC=k|s; //delay(8000); //延时k=0b01001000; //1 //HA,HB,HC,s=PORTC&0b00000110; //0 0 1, C+A-PORTC=k|s; //delay(8000); //延时}void interrupt RB4_int(){char th;run_num++;if(run_num>10){run_num=10;}m=PORTB;//RB7-HA,RB5-HB,RB4-HCm&=0xB0; //1 0 1 1m^=0x90;//A=/A,B=B,C=/C //1 1n=m>>4; //switch(n){ //HA,HB,HC,// case 1: k=0b01001000;break; //0 0 1, C+A-// case 3: k=0b01100000;break; //0 1 1, A-B+// case 2: k=0b00100001;break; //0 1 0, B+C-// case 10:k=0b10000001;break; //1 1 0, C-A+// case 8: k=0b10010000;break; //1 0 0, A+B-// case 9: k=0b00011000;break; //1 0 1, B-C+// default:k=0b00000000; //其它(000,111),0x00,输出为无效case 1: k=0b00011000;break; //1 0 1, B-C+case 3: k=0b01001000;break; //0 0 1, C+A-case 2: k=0b01100000;break; //0 1 1, A-B+case 10:k=0b00100001;break; //0 1 0, B+C-case 8: k=0b10000001;break; //1 1 0, C-A+case 9: k=0b10010000;break; //1 0 0, A+B-default:k=0b00000000; //其它(000,111),0x00,输出为无s=PORTC&0b00000110; //取RC1,RC2状态PORTC=k|s; //输出PORTCif (RB7==0) {trial&=0b00110000;} //RB7=0if (RB5==0) {trial&=0b10010000;} //RB5=0if (RB4==0) {trial&=0b10100000;} //RB4=0if (lkk>1) {lkk--;} //每20次测试一次// tri=n;// if ((tri&=0b00001000)==0) {trial&=0b00110000;} //RB7=0// tri=n;// if ((tri&=0b00000010)==0) {trial&=0b10010000;} //RB5=0// tri=n;// if ((tri&=0b00000001)==0) {trial&=0b10100000;} //RB4=0// if (lkk>2) {lkk--;} //每20次测试一次else{while(trial!=0b00000000){GIE=0; //关全局中断pwm_real=pwm_hi; //PWM_real----PWM实时值CCPR1L=pwm_real; //设置PWM输出为最大CCPR1H=0x00; //CCP1CON=0x0c; //CCP1选择为PWM工作方式PR2=pwm_cycle; //设置PWM的周期TRISC=TRISC&0xfb; //设置RC2---PWM输出T2CON=0x00; //分频系数=0x00TMR2ON=1; //启用TMR2PORTC=0x00; //PORTB=PORTB&0xfe; //RB0=0,----输出低电平,禁止GAL输出while(1){PORTA^=0b00010000; //RA4闪动for (jm=15000;jm>1;jm--){asm("nop");}}}trial=0b10110000;lkk=10;}RBIF=0;}void max_min_compare(){if (pwm_real>pwm_hi) pwm_real=pwm_hi;if (pwm_real<pwm_lo) pwm_real=pwm_lo;}para_chushihua(); //参数初始化nointerupt_chushihua(); //禁止中断初始化Io_chushihua(); //I/O初始化PWM_chushihua(); //PWM初始化RA1=0; //RA1-PSW1发送低电平,接通电源RA5=0; //RA5-RSW1发送低电平,主电路充电延时RA2=0; //RA2,指示灯灭RA4=0; //RA4,指示灯灭delay(100); //主电路充电延时RB0=0; //ST/(-STOP)发送低电平,禁止GAL输出delay(100);RA1=1; //RA1-PSW1发送高电平,接通电源for(charge_delay=0;charge_delay<50;charge_delay++){delay(15000);}RA5=1; //RA5-RSW1发送高电平,主电路充电延时delay(100); //主电路充电延时PP: asm(" nop"); //RBIF=0; //禁止RB4-7中断,清RBIF 标志设定RBIE=0; //禁止RB4-7中断,RBIE设定GIE=0; //关全局中断RA2=0; //RA2,指示灯灭RA4=0; //RA4,指示灯灭run_flag=0; //运行标志---由RB2按钮设置while(run_flag==0) //----------主程序-------------//{ //RB2启动键,低电平有效if (RB2==0) run_flag=1; //运行标志---由RB2按钮设置delay(100); //延时} //while(run_flag==1) //运行,则执行......{int ope; //设定开环运行次数为12次int openloopn; //RB0=1; //ST/(-STOP)发送高电平,开放GAL输出delay(100); //延时RA4=1;// pwm_real=180;pwm_real=230;delay(500); //延时// ope=10; //设定开环运行次数为20次ope=3; //设定开环运行次数为20次for (openloopn=0;openloopn<=ope;openloopn++){ //00 0000000000000000CCPR1L=pwm_real; //设置开环下PWM输出值----130open_loopf(); //开环运行20次,启动} //----------------------- //000000000000000000delay(6000); //延时RBIF=0; //RB4-7中断,RBIF标志设定RBIE=1; //RB4-7中断,RBIE设定GIE=1; //开全局中断RA2=1; //-----------------------pwm_real=pwm_hi; //-----------------------ghl: asm(" nop"); //if ((pwm_real<110)&&(run_num<10)) //如果pwm_real<140,但是run_num<10,表明未动,则{ //protect_run();protect_run();}while(RA0==1) //RA0=1,过流和过温保护{ //delay(150); //调用延时程序protect_num++; //if (protect_num>30)//如果30次保护,则认为是真正保护(过温和过流保护软件滤波){protect();} //过流和过温保护} //protect_num=0; //if(RB1==1) flag_autohand=1; //自/手标志设定,标志设定else flag_autohand=0; //RB1=1---AUTO;自动//RB1=0---HAND;手动//----------------------- if (flag_autohand==1){ //111 11111111111111111if (pwm_real>pwm_lo) pwm_real-=1; //自动else pwm_real=pwm_lo;}//11111111111111111111else{if(RA3==0) //加(低有效), 则{if (pwm_real<pwm_hi) pwm_real+=1;else pwm_real=pwm_hi;}if(RC1==0) //减(低有效),则{if (pwm_real>pwm_lo) pwm_real-=1;else pwm_real=pwm_lo;}}max_min_compare();CCPR1L=pwm_real; //设置PWM输出delay(4500); //调用延时子程序while(RA0==1) //RA0------过流和过温保护输入,高电平保护{ //protect(); //过流和过温保护} //while(RB3==0){ //RB3停机键,低电平有效run_flag=0; //运行标志---由RB3按钮设置}if (run_flag==0) //停机,则跳转至......{for(;pwm_real<pwm_hi;pwm_real++){delay(2000); //至上限否?CCPR1L=pwm_real; //设置PWM输出为最大}RB0=0; //ST/(-STOP)发送低电平,禁止GAL输出para_chushihua(); //参数初始化nointerupt_chushihua(); //禁止中断初始化PWM_chushihua(); //PWM初始化run_num=0;goto PP;}else{// run_num=0;goto ghl;}}// goto PP;}。

pic单片机控制直流电机

pic单片机控制直流电机

实用标准文案目录1 总体设计框架 (3)2 硬件电路设计 (4)2.1 芯片介绍 (4)2.2 驱动电路 (9)2.3 按键控制电路 (10)3 程序编写 .................................................103.1 工作原理 (10)21程序书写过程3.2 ......................................................参考资料 (16)精彩文档.实用标准文案直流电机驱动Abstract 摘要:本文主要内容是利用PIC18F452单片机来控制直流电机,通过L293NE来驱动电机,通过按键来使其正转,反转。

Keywords 关键词:直流电机,PWM,L293NE精彩文档.实用标准文案总体设计框架1硬件电路利用驱动芯片L293D来驱动直流电机,按键则是单独引出。

如图1所示。

软件则是C语言编程。

PI驱C直动1流8电电F路机452图1硬件设计框精彩文档.实用标准文案2硬件电路设计2.1 芯片介绍首先,总体说明硬件电路设计,如图2 原理图,图3 PCB图以及图4板子的图所示。

三个输入信号,如图分别为RD4,RD5,RD6连上光耦的2脚,然后通过光耦的4脚引入L293D的使能引脚(12EN)以及输入引脚(1A,2A),然后L293D的输出引脚(1Y,2Y)通过H-桥型控制电路与直流电机连接。

图2 直流电机控制部分原理图精彩文档.实用标准文案PCB图图3直流电机控制部分成品板图4其中红线圈表示直流电机控制部分。

下面详细介绍各个芯片。

PIC18F452、1外部端口以及内部存储器是相同的。

上图的与PIC18F452PIC18F4580 。

U2精彩文档.实用标准文案2、光耦P521光耦主要的作用是保护单片机。

光耦的结构如图5所示。

图5 光耦P521结构在PCB中(如图6所示),即U7,U9,U10三个光耦,左下方方形孔为1引脚,按逆时针方向,依次为2,3,4引脚。

pic单片机 直流无刷电机控制程序

pic单片机 直流无刷电机控制程序

pic单片机直流无刷电机控制程序下载温馨提示:该文档是我店铺精心编制而成,希望大家下载以后,能够帮助大家解决实际的问题。

文档下载后可定制随意修改,请根据实际需要进行相应的调整和使用,谢谢!并且,本店铺为大家提供各种各样类型的实用资料,如教育随笔、日记赏析、句子摘抄、古诗大全、经典美文、话题作文、工作总结、词语解析、文案摘录、其他资料等等,如想了解不同资料格式和写法,敬请关注!Download tips: This document is carefully compiled by the editor. I hope that after you download them, they can help you solve practical problems. The document can be customized and modified after downloading, please adjust and use it according to actual needs, thank you!In addition, our shop provides you with various types of practical materials, such as educational essays, diary appreciation, sentence excerpts, ancient poems, classic articles, topic composition, work summary, word parsing, copy excerpts, other materials and so on, want to know different data formats and writing methods, please pay attention!Title: PIC单片机直流无刷电机控制程序Introduction在现代工业控制系统中,直流无刷电机的应用越来越广泛。

BLDC控制PIC程序

BLDC控制PIC程序

另一完整版#include "DSP281x_Device.h"#include "DSP281x_Examples.h"//#include "DSP281x_Globalprototypes.h"#include "DSP281x_Device.h"#include "DSP281x_Examples.h"void InitPieCtrl(void);void init_7219(void);void InitSysCtrl(void);void InitPieVectTable(void);void pdelay(void);void delay(void);interrupt void eva_capint1_isr(void);interrupt void eva_capint2_isr(void);interrupt void eva_timer1_isr(void);extern void DSP28x_usDelay(Uint32 Count);unsigned s=500;unsigned state;unsigned i,j;int32 x3=0,speed1,speed2=0;//数组供显示用unsigned K;unsigned y=0;int32 x1=0,x2=0;Uint16 counter=0;//===========PI参数===========float Kpspeed=10,Kispeed=0.01,Kcspeed=0.0046;int Nmin=0,Nmax=1500; //float RKspeed=0,Uspeed=0.0; //int Nref=300,N=0,Iref=0;int Espeed=0;//===============速度PID====================//void SPEED_PI(void) //{//Xispeed:速度调节器积分累积量Espeed=Nref-N;Uspeed=Kpspeed*Espeed+RKspeed;if(Uspeed<0){if((Nmin-Uspeed)>=0)Iref=Nmin;elseIref=(int)Uspeed;}else{if(Nmax-Uspeed<0)Iref=Nmax;elseIref=(int)Uspeed;}RKspeed=Kcspeed*(Iref-(int)Uspeed)+Espeed*Kispeed+RKspeed; Iref=1500-Iref;}//=============增调速=====================//void tiaosujian(void){if(Nref<=0){Nref=0;}else{Nref=Nref-1;}}//=============减调速=====================//void tiaosuzeng(void){if(Nref>=1500){Nref=1500;}else{Nref=Nref+1;}}//=============延时程序=====================//void pdelay(void){for(j=0;j<100;j++){ for (i = 0; i < 5; i++);}}//=============SPI初始化====================//void InitSpi(void){SpiaRegs.SPICCR.all=0x000F; //复位SPI模块,SPICLK 信号上升沿时,数据输出//单个移位序列周期移入,移出的位数为16SpiaRegs.SPICTL.all=0x000E; //SPICLK 信号延时半个周期,主模式,使能发送SpiaRegs.SPIBRR=120;SpiaRegs.SPICCR.bit.SPISWRESET=1; //SPI准备好发送或接收下一个字符//=============MAX7219 Init====================== GpioDataRegs.GPFCLEAR.bit.GPIOF3=1;SpiaRegs.SPIRXBUF=SpiaRegs.SPIRXBUF;SpiaRegs.SPITXBUF=0x09FF;while(SpiaRegs.SPISTS.bit.BUFFULL_FLAG==1){};GpioDataRegs.GPFSET.bit.GPIOF3=1;GpioDataRegs.GPFCLEAR.bit.GPIOF3=1;SpiaRegs.SPIRXBUF=SpiaRegs.SPIRXBUF;SpiaRegs.SPITXBUF=0x0A0A;while(SpiaRegs.SPISTS.bit.BUFFULL_FLAG==1){};GpioDataRegs.GPFSET.bit.GPIOF3=1;GpioDataRegs.GPFCLEAR.bit.GPIOF3=1;SpiaRegs.SPIRXBUF=SpiaRegs.SPIRXBUF;SpiaRegs.SPITXBUF=0x0B03;while(SpiaRegs.SPISTS.bit.BUFFULL_FLAG==1){};GpioDataRegs.GPFSET.bit.GPIOF3=1;GpioDataRegs.GPFCLEAR.bit.GPIOF3=1;SpiaRegs.SPIRXBUF=SpiaRegs.SPIRXBUF;SpiaRegs.SPITXBUF=0x0C01;while(SpiaRegs.SPISTS.bit.BUFFULL_FLAG==1){};GpioDataRegs.GPFSET.bit.GPIOF3=1;GpioDataRegs.GPFCLEAR.bit.GPIOF3=1;SpiaRegs.SPIRXBUF=SpiaRegs.SPIRXBUF;SpiaRegs.SPITXBUF=0x0F00;while(SpiaRegs.SPISTS.bit.BUFFULL_FLAG==1){};GpioDataRegs.GPFSET.bit.GPIOF3=1;}//===========显示子程序=====================//void XianShi(long int m){Uint16 dizhi[4]={0x0100,0x0200,0x0300,0x0400};Uint16 shu[4];int i;for(i=3;i>=0;i--){shu[i]=m%10;m=m/10;GpioDataRegs.GPFCLEAR.bit.GPIOF3=1;SpiaRegs.SPIRXBUF=SpiaRegs.SPIRXBUF;SpiaRegs.SPITXBUF=dizhi[i]|shu[i];while(SpiaRegs.SPISTS.bit.BUFFULL_FLAG==1){};GpioDataRegs.GPFSET.bit.GPIOF3=1;}}//==============EV A初始化子程序=============/void EV A_Timer1(){//EvaRegs.GPTCONA.all=0;EvaRegs.T1CNT=0x0000; //T1CNT(定时器1的计数寄存器)EvaRegs.T1PR=1500;EvaRegs.ACTRA.all = 0x0000; //比较方式寄存器,设置比较器输出引脚的方式EvaRegs.CMPR1 = 500; //全比较寄存器EvaRegs.CMPR2 = 500;EvaRegs.T2CNT=0x0000;EvaRegs.T2PR=0xFFFF;EvaRegs.T2CON.all=0x1740;EvaRegs.EV AIMRA.bit.T1UFINT=1; //EV AIMRA(EV A的中断屏蔽寄存器A).T1PINT(通用定时器1的周期中断使能)EvaRegs.EV AIFRA.bit.T1UFINT=1;//EV AIFRA(EV A的中断标志寄存器.T1PINT(通用定时器1的周期中断标志)//写1清除定时器1的周期中断标志CONA.all = 0x82FF; //比较器控制寄存器EvaRegs.T1CON.all=0x1002;//T1CON=000 10 000 0100 0000EvaRegs.T1CON.bit.TMODE=01;EvaRegs.T1CON.bit.TENABLE=1;EvaRegs.CAPCONA.all = 0;//EvaRegs.CAPCONA.all=0xA0F0;EvaRegs.CAPCONA.bit.CAP12EN = 1; //使能捕获单元1和2EvaRegs.CAPCONA.bit.CAP1EDGE = 3; //选用两边沿EvaRegs.CAPCONA.bit.CAP2EDGE = 3; //选用上两边沿EvaRegs.CAPCONA.bit.CAP12TSEL = 0; //选择定时器2*/EvaRegs.CAPFIFOA.bit.CAP1FIFO = 0; //状态寄存器清零EvaRegs.CAPFIFOA.bit.CAP2FIFO = 0; //状态寄存器清零EvaRegs.EV AIMRC.bit.CAP1INT = 1; //捕获1中断屏蔽位使能EvaRegs.EV AIFRC.bit.CAP1INT = 1; //复位标志位EvaRegs.EV AIMRC.bit.CAP2INT = 1; //捕获1中断屏蔽位使能EvaRegs.EV AIFRC.bit.CAP2INT = 1; //复位标志位}//===============主程序=====================//void main(void){Uint16 num=0;DINT; //关总中断IER=0x0000; //禁止使能IFR=0x0000;InitSysCtrl(); //系统初始化InitGpio();InitSpi();EALLOW;SysCtrlRegs.PLLCR.all=0x0002;SysCtrlRegs.HISPCP.all=0x0000; //HISPCP(高速外设时钟预定标寄存器)//bit0~2=011:高速时钟的频率=SYSCKLOUT/6//高速时钟的频率=25M EDIS;EALLOW; //关闭寄存器保护GpioMuxRegs.GPAMUX.all=0x030F;//将A0-A3设成pwm 口,将A8、A9设成CAP口,将A4、A5设成IO口,做测试用,A10为IO口按键做保护用GpioMuxRegs.GPADIR.bit.GPIOA4=1;GpioMuxRegs.GPADIR.bit.GPIOA5=1;GpioMuxRegs.GPADIR.bit.GPIOA10=0;GpioMuxRegs.GPBMUX.bit.PWM7_GPIOB0=0;GpioMuxRegs.GPBMUX.bit.PWM8_GPIOB1=0;GpioMuxRegs.GPBDIR.bit.GPIOB0=0;GpioMuxRegs.GPBDIR.bit.GPIOB1=0;GpioMuxRegs.GPFMUX.all=0x000f;GpioMuxRegs.GPFMUX.bit.SPICLKA_GPIOF2=1; //选择复用SPISIMO,SPISTE,SPICLKGpioMuxRegs.GPFMUX.bit.SPISIMOA_GPIOF0=1;// GpioMuxRegs.GPFMUX.bit.SPISTEA_GPIOF3=1;GpioMuxRegs.GPFMUX.bit.SPISTEA_GPIOF3=0;GpioMuxRegs.GPFDIR.bit.GPIOF3=1;EDIS;EV A_Timer1();InitPieCtrl(); //初始化PIE控制寄存器InitPieVectTable();//重新映射定时器1的比较中断入口EALLOW;PieVectTable.CAPINT1 = &eva_capint1_isr; //中断使能PieVectTable.CAPINT2 = &eva_capint2_isr; //中断使能PieVectTable.T1UFINT = &eva_timer1_isr; //定时器下溢中断使能EDIS;//使能T1下溢中断:PIE-组2,中断6,使能捕获中断PieCtrlRegs.PIEIER2.bit.INTx6 = 1;PieCtrlRegs.PIEIER3.bit.INTx5 = 1;PieCtrlRegs.PIEIER3.bit.INTx6 = 1;//使能CPU INT2,GP-Timer1的下溢中断连接到该中断,使能捕获中断IER = 0x0006;//全局中断使能,并使能具有更高优先级的实时调试方式EINT; //使能全局中断INTMERTM;//使能全局实时中断DBGMwhile(1){if(GpioDataRegs.GPBDAT.bit.GPIOB0==1){tiaosuzeng();}asm(" nop");asm(" nop");if(GpioDataRegs.GPBDAT.bit.GPIOB1==1){tiaosujian();}asm(" nop");asm(" nop");InitSpi();XianShi(N);num++;if(num==9999){num=0;}DELAY_US(80000L);InitSpi();}}//============捕获1 中断处理================// interrupt void eva_capint1_isr(void){// asm(" RPT #150 || NOP"); //空操作延时GpioMuxRegs.GPAMUX.all = 0x000F;GpioMuxRegs.GPADIR.bit.GPIOA8=0;GpioMuxRegs.GPADIR.bit.GPIOA9=0;if(GpioDataRegs.GPADAT.bit.GPIOA8==0&&GpioDataRegs.GPADAT.bit.GPIOA9==0){ state=0;}if(GpioDataRegs.GPADAT.bit.GPIOA8==1&&GpioDataRegs.GPADAT.bit.GPIOA9==1){state=3;}if(GpioDataRegs.GPADAT.bit.GPIOA8==1&&GpioDataRegs.GPADAT.bit.GPIOA9==0){state=2;}if(GpioDataRegs.GPADAT.bit.GPIOA8==0&&GpioDataRegs.GPADAT.bit.GPIOA9==1){state=1;}// x2=EvaRegs.T2CNT;x2=counter;x3=(long int)(x2-x1);if(x3<0){x3+=65536;}speed1=8330/x3;N=speed1*6;x1=x2;GpioMuxRegs.GPAMUX.all = 0x030F;EvaRegs.EV AIFRC.bit.CAP1INT = 1;PieCtrlRegs.PIEACK.all = PIEACK_GROUP3; }//============捕获2中断处理================// interrupt void eva_capint2_isr(void){//asm(" nop");GpioMuxRegs.GPAMUX.all = 0x000F;GpioMuxRegs.GPADIR.bit.GPIOA8=0;GpioMuxRegs.GPADIR.bit.GPIOA9=0;if(GpioDataRegs.GPADAT.bit.GPIOA8==1&&GpioDataRegs.GPADAT.bit.GPIOA9==0){state=2;}if(GpioDataRegs.GPADAT.bit.GPIOA8==0&&GpioDataRegs.GPADAT.bit.GPIOA9==1){state=1;}if(GpioDataRegs.GPADAT.bit.GPIOA8==0&&GpioDataRegs.GPADAT.bit.GPIOA9==0){ state=0;}if(GpioDataRegs.GPADAT.bit.GPIOA8==1&&GpioDataRegs.GPADAT.bit.GPIOA9==1){state=3;}GpioMuxRegs.GPAMUX.all = 0x030F;EvaRegs.EV AIFRC.bit.CAP2INT = 1;PieCtrlRegs.PIEACK.all = PIEACK_GROUP3;}//============T1下溢中断处理================//interrupt void eva_timer1_isr(void){counter++;SPEED_PI();EvaRegs.CMPR1 = Iref;EvaRegs.CMPR2 = Iref;if(GpioDataRegs.GPADAT.bit.GPIOA10==1){ if(state==0){EvaRegs.ACTRA.all = 0x000A;GpioDataRegs.GPADAT.bit.GPIOA4=1;GpioDataRegs.GPADAT.bit.GPIOA5=1;}if( state==3){EvaRegs.ACTRA.all = 0x00A0;GpioDataRegs.GPADAT.bit.GPIOA4 = 0;GpioDataRegs.GPADAT.bit.GPIOA5 = 0;}if( state==2){EvaRegs.ACTRA.all = 0x0082;GpioDataRegs.GPADAT.bit.GPIOA4=0;GpioDataRegs.GPADAT.bit.GPIOA5=1;}if( state==1){EvaRegs.ACTRA.all = 0x0028;GpioDataRegs.GPADAT.bit.GPIOA4=1;GpioDataRegs.GPADAT.bit.GPIOA5=0;}} //通过以上不同的组合,可以改变I/O口的状态,//GpioDataRegs.GPEDAT.all查看I/O口状态EvaRegs.EV AIFRA.bit.T1UFINT=1;PieCtrlRegs.PIEACK.all=PIEACK_GROUP2; //#define PIEACK_GROUP2 0x0002;}。

基于dsPIC33F的无刷直流电机驱动器软件设计-程序

基于dsPIC33F的无刷直流电机驱动器软件设计-程序
{
COUNT3=0;
if(voltage>overvol)
{
Flags.fine=0;
}
if(current>currentlim)
{
Flags.fine=0;
}
if(voltage<lowvol)
{
Flags.fine=0;
}
// if(temper>temperlim)
// {
// Flags.fine=0;
unsigned int COUNT1=0;
unsigned int COUNT2=0;
unsigned int COUNT3=0;
unsigned int wucha;
unsigned long T;
unsigned long rotspegiv;
unsigned long ZCSPEED2;
unsigned long DutyCycle;
// PDCDUTY=PDCDUTY-DUTYREDUSV;
P1DC1=PDCDUTY;
P1DC2=PDCDUTY;
P1DC3=PDCDUTY;
}
if(Flags.dinweiwanchen==0)
{
P1OVDCON=0x2001;
// P2OVDCON=0x0;
}
else
{
if(COUNT==HuanxiangTIME1)
SpeedIntegral+= SpeedError;
if(SpeedIntegral>9000)
SpeedIntegral = 0;
DutyCycle= (((long)Ksp* SpeedError+ (long)Ksi*SpeedIntegral) >>8);

AN1175_基于PIC16 的无传感器无刷直流电机控制实现

AN1175_基于PIC16 的无传感器无刷直流电机控制实现
1 2 3 4 5 6 7 8
MM8-F
5/6
7/8
W VCC
电机功率驱动器
U_L VDD
R1 2 220
R2
V_L
2
220
R3
W_L
2
220
J3
1 2 3 4 5 6
CONN-SIL6 ICD-Connector
1 MCLR
RA0 RA1
R10
220
VBUS
BUS-Voltage divider
Star-Point reconstruction
2008 Microchip Technology Inc.
在该示例原理图中,采用三个P沟道MOSFET对从+VCC 端流进电机每一相的电流进行控制。另外,还有三个 N 沟道MOSFET对从电机每一相流入地的电流进行控制。 在 N 沟道 MOSFET 和地之间设置有一个小电阻(R7), 用来对流经电机的电流进行检测,其两端的电压与流经
该电阻的电流成正比。三个 BJT 晶体管用来驱动 P 沟道 MOSFET。N沟道MOSFET则由PIC® MCU的I/O引脚进 行驱动。对于较小功率的 MOSFET 和双极型晶体管输 出级,通常不需要 MOSFET 驱动器。
反电势检测
为获得转子当前位置,系统需要采用某种转子位置检测 环节。在有位置传感器的系统中,转子位置的检测是通 过一系列霍尔效应传感器来实现的,霍尔效应传感器能 够感知转子永磁磁极的位置。对于无位置传感器的设 计,则是通过检测磁极何时从非导通相绕组下通过来获 取转子位置信息。在每一个换相周期中,将有一相绕组 处于不导通状态,因此可检测到转子磁极从在该绕组经 过的时刻。以下电路采用自偏置形式,且使用一个比较 器来实现反电势位置检测。

基于dsPIC单片机的无刷直流电机控制系统

基于dsPIC单片机的无刷直流电机控制系统
wa i l , u t e o e s e d r g lt n wa o v n e t ssmp e f r h rm r , p e e u a i s c n e i n o
n a d s o t t i h sa i t m o wi h g b l y h h t i
极的A 相控制信号, 其阴影部分为通 过 自 举得 到
的高端驱动, 毛刺是 由杂散 电感 引起。 为电机 图8
的反电势波形。
图7 I 10 R2 1 的HO LLO 出波 形 ( 1RP ) 输 78 M
通过对 以上的波形分析和L D C 的观察, 表明
本系统是完全可行 的, 在最低速和额定转速之间 电机稳定运转。 改变电机负载时转速的变化也符 合闭环要求。

2雷
浩. 无位 置 传感 器 无 刷 直 流 电动机 控 制 系统 研 究 【 . 中科 D】华
技大学,0 6 20.
I 。I I _ . :
Rf B^伽 黼 1 删 S J O| f 搿 协
3 何礼 高 等. s I 0 电机 与电 源 系列 数 字信 号 控制 器 原理 与应 用 dPC3 F 【 . 京 : 京 航空 航 天 大学 出版社 , 0 7 . M】 北 北 2 0年 4王晓明, 周青 山. 动机 的DS 电 C控制 一 一 微 芯 公司 dP C 用 . sI应 北 京 : 京 航 空 航 天大 学 出版 社 , 0 9 . 北 20年

清时值清断数 l 定器 ,中计值
自带 保护 功能 , 护 引脚 为S 当其 为高 电平 保 D, 时, 封锁I 2 的输出, 10 R 1 通过 采样主电路中的
图 4 I 0 中断服 务 流程 NT 的

基于PIC单片机的永磁无刷直流电机控制系统

基于PIC单片机的永磁无刷直流电机控制系统
您的论文得到两院院士关注
中文核心期刊 《微计算机信息》(嵌入式与 S O C )2005 年第 21 卷第 12-2 期
基于 PIC 单片机的永磁无刷直流电机控制系统
PIC Ba s e d DC Mo to r Co n tro l S ys te m
(1.武汉海军工程大学;2. 无锡总装工程兵科研一所)赵 乾 宏 1 张 静 远 1 兰 士 新 2
PIC16F877A 单片机具有 5 个输入/输出端口,特 别需要指出的是单片机内置了两个 CCP 模块,即输入 捕捉、输出比较、脉宽调制模块。本系统就是利用了 PIC 单片机此脉宽调制模块输出脉宽可调的信号,实 现直流电机调速。
2 基 于 PIC16F877A 单 片 机 的 电 机 控 制系统方案
4 结语
本文首次将监控软件+应用服务器+现场总线以 及浏览器+WEB Server+CGI 两种技术融合到智能家庭
技 网关产品中,较好的解决了传统产品的缺陷。通过本
系统在实际家庭智能网络中的运行表明,该系统达到
术 了设计初期的各项要求,能够通过 Internet 实时控制系 创 统中的智能家电并精确的获取家电状态信息。相信在
数据库发送传送参数指令,现场控制系统接到指令后 进行检索,并返回查询结果给虚拟数据库最后显示在 用户监控界面中。当用户发出控制指令时,无论是在 家庭网络内部还是外部,控制指令都可以通过不同的 网络协议可靠地到达被控对象并完成相应的操作,最 后把执行结果(成功或者失败)返回给指令的发出者。 在一般的 C/S 概念中,客户端是廉价的个人 PC,服务 器是价格昂贵、功能强大的专用 Server。但对于本系统 来讲,嵌入式家庭网关是应用服务器和 Web 服务器的 宿主,而嵌入式系统本身资源有限,所以在事物处理 时不应将过多的任务分配给服务器,避免因服务器负 担过重而使整个网络性能下降,要充分发挥客户端计 算机的作用,合理分配网络资源,提高数据处理的效 率。
  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

#include <pic168xa.h> //2008.4.24--14点00分#include <math.h>#include <stdlib.h>int charge_delay,jm,lkk,trial,run_num,protect_num;char m,n,k,s,L,tri;char hall_num; //循环次数char hall_number; //1+3+2+10+8+9=33(一个循环和),hallless_protect()int pwm_hi; // pwm占空比上限int pwm_cycle; // pwm周期int pwm_lo; // pwm占空比下限,由A/D结果确定int pwm_real; // pwm占空比实际int ad_result; // A/D转换结果bit ghy,run_flag; //运行标志---0,未运行,停止bit flag_autohand; //开始为-----自动void delay(delay_num)int delay_num;{int j;for (j=delay_num;j>1;j--){asm("nop");}}union adres{int y1;unsigned char adre[2];}adresult;void para_chushihua(){protect_num=0;trial=0b10110000;tri=0x00;lkk=10;hall_num=0x00;hall_number=0x00;run_flag=0; //运行标志---0,未运行,停止flag_autohand=1; //开始为-----自动pwm_cycle= 240; // pwm周期// pwm_hi=pwm_cycle-5; // pwm占空比上限pwm_hi=pwm_cycle-1; // pwm占空比上限pwm_real=pwm_cycle; // 实际pwm占空比为pwm周期上限pwm_lo=0x0A; //设定下限+++++++++++++++++++++++++++++++++++++++ ++++++++}void nointerupt_chushihua(){INTCON=0X00; //禁止中断}void Io_chushihua(){// ADCON1=0x8e; //RA0/AN0--VOLTAGE 电压采样,右对齐1ADCON1=0x86; //设定RA0--RA6设定为I/O口;TRISA =0x09; //RA0---PROTECT保护(电流保护和过温保护)--输出,0--不保护,1--保护;//RA1----PSW1,继电器,输出,0,电源接通//RA2----指示灯,输出0--->>//RA3----按键,加,输入 1//RA4----指示灯,输出0--->>//RA5----RSW1,继电器,输出0,软启充电PORTA=PORTA&0x09; //RA1=0,----输出低电平,PSW1,继电器断//RA2=0,----输出低电平,指示灯灭//RA4=0,----输出低电平,指示灯灭//RA5=0,----输出低电平,RSW1,继电器断RBPU=0; //RB端口内部弱上拉电路禁止TRISB =0xfe; //RB7=1, 空----输入//RB6=1----HA,输入//RB5=1----HB,输入//RB4=1----HC,输入//RB3=1----停,输入,按钮//RB2=1----启,输入,按钮//RB1=1----自/手选择,输入,开关//RB0=0----ST/STOP,输出,控制GAL PORTB=PORTB&0xfe; //RB0=0,----输出低电平,禁止GAL输出TRISC =0x02; //RC7---A1+,PWMA1+,输出0//RC6---A1, 输出0//RC5---B1+,输出0//RC4---B1,输出0//RC3---C1+,输出0//RC2---CCP1(PWM),输出,死区0//RC1----减,输入,按钮 1//RC0---C1,输出0 PORTC=0x06;}void protect(){ //过流和过温保护GIE=0; //关全局中断pwm_real=pwm_hi; //PWM_real----PWM实时值CCPR1L=pwm_real; //设置PWM输出为最大CCPR1H=0x00; //CCP1CON=0x0c; //CCP1选择为PWM工作方式PR2=pwm_cycle; //设置PWM的周期TRISC=TRISC&0xfb; //设置RC2---PWM输出T2CON=0x00; //分频系数=0x00TMR2ON=1; //启用TMR2PORTC=0x00; //PORTB=PORTB&0xfe; //RB0=0,----输出低电平,禁止GAL输出while(1){PORTA^=0b00010100;delay(15000); //延时}}void protect_run(){ //过流和过温保护GIE=0; //关全局中断pwm_real=pwm_hi; //PWM_real----PWM实时值CCPR1L=pwm_real; //设置PWM输出为最大CCPR1H=0x00; //CCP1CON=0x0c; //CCP1选择为PWM工作方式PR2=pwm_cycle; //设置PWM的周期TRISC=TRISC&0xfb; //设置RC2---PWM输出T2CON=0x00; //分频系数=0x00TMR2ON=1; //启用TMR2PORTC=0x00; //PORTB=PORTB&0xfe; //RB0=0,----输出低电平,禁止GAL输出while(1){// PORTA^=0b00010000; //RA4闪动PORTA^=0b00000100; //RA2闪动delay(15000); //延时}}void PWM_chushihua(){// CCPR1L=0xa0;// CCPR1H=0x00;run_num=0;pwm_real=pwm_hi; //PWM_real----PWM实时值CCPR1L=pwm_real; //设置PWM输出为最大CCPR1H=0x00; //CCP1CON=0x0c; //CCP1选择为PWM工作方式PR2=pwm_cycle; //设置PWM的周期TRISC=TRISC&0xfb; //设置RC2---PWM输出T2CON=0x00; //分频系数=0x00TMR2ON=1; //启用TMR2}void open_loopf() //开环运行50次,启动{k=0b00011000; //5 //HA,HB,HC,s=PORTC&0b00000110; //1 0 1, B-C+PORTC=k|s; //delay(8000); //延时k=0b10010000; //4 //HA,HB,HC,s=PORTC&0b00000110; //1 0 0, A+B-PORTC=k|s; //delay(8000); //延时k=0b10000001; //6 //HA,HB,HC,s=PORTC&0b00000110; //1 1 0, C-A+PORTC=k|s; //delay(8000); //延时k=0b00100001; //2 //HA,HB,HC,s=PORTC&0b00000110; //0 1 0, B+C-PORTC=k|s; //delay(8000); //延时k=0b01100000; //3 //HA,HB,HC,s=PORTC&0b00000110; //0 1 1, A-B+PORTC=k|s; //delay(8000); //延时k=0b01001000; //1 //HA,HB,HC,s=PORTC&0b00000110; //0 0 1, C+A-PORTC=k|s; //delay(8000); //延时}void interrupt RB4_int(){char th;run_num++;if(run_num>10){run_num=10;}m=PORTB;//RB7-HA,RB5-HB,RB4-HCm&=0xB0; //1 0 1 1 m^=0x90;//A=/A,B=B,C=/C //1 1 n=m>>4; //switch(n){ //HA,HB,HC,// case 1: k=0b01001000;break; //0 0 1, C+A-// case 3: k=0b01100000;break; //0 1 1, A-B+// case 2: k=0b00100001;break; //0 1 0, B+C-// case 10:k=0b10000001;break; //1 1 0, C-A+// case 8: k=0b10010000;break; //1 0 0, A+B-// case 9: k=0b00011000;break; //1 0 1, B-C+// default:k=0b00000000; //其它(000,111),0x00,输出为无效case 1: k=0b00011000;break; //1 0 1, B-C+case 3: k=0b01001000;break; //0 0 1, C+A-case 2: k=0b01100000;break; //0 1 1, A-B+case 10:k=0b00100001;break; //0 1 0, B+C-case 8: k=0b10000001;break; //1 1 0, C-A+case 9: k=0b10010000;break; //1 0 0, A+B-default:k=0b00000000; //其它(000,111),0x00,输出为无效}s=PORTC&0b00000110; //取RC1,RC2状态PORTC=k|s; //输出PORTCif (RB7==0) {trial&=0b00110000;} //RB7=0if (RB5==0) {trial&=0b10010000;} //RB5=0if (RB4==0) {trial&=0b10100000;} //RB4=0if (lkk>1) {lkk--;} //每20次测试一次// tri=n;// if ((tri&=0b00001000)==0) {trial&=0b00110000;} //RB7=0// tri=n;// if ((tri&=0b00000010)==0) {trial&=0b10010000;} //RB5=0// tri=n;// if ((tri&=0b00000001)==0) {trial&=0b10100000;} //RB4=0// if (lkk>2) {lkk--;} //每20次测试一次else{while(trial!=0b00000000){GIE=0; //关全局中断pwm_real=pwm_hi; //PWM_real----PWM 实时值CCPR1L=pwm_real; //设置PWM输出为最大CCPR1H=0x00; //CCP1CON=0x0c; //CCP1选择为PWM工作方式PR2=pwm_cycle; //设置PWM的周期TRISC=TRISC&0xfb; //设置RC2---PWM输出T2CON=0x00; //分频系数=0x00TMR2ON=1; //启用TMR2PORTC=0x00; //PORTB=PORTB&0xfe; //RB0=0,----输出低电平,禁止GAL输出while(1){PORTA^=0b00010000; //RA4闪动for (jm=15000;jm>1;jm--){asm("nop");}}}trial=0b10110000;lkk=10;}RBIF=0;}void max_min_compare(){if (pwm_real>pwm_hi) pwm_real=pwm_hi;if (pwm_real<pwm_lo) pwm_real=pwm_lo;}main(void){para_chushihua(); //参数初始化nointerupt_chushihua(); //禁止中断初始化Io_chushihua(); //I/O初始化PWM_chushihua(); //PWM初始化RA1=0; //RA1-PSW1发送低电平,接通电源RA5=0; //RA5-RSW1发送低电平,主电路充电延时RA2=0; //RA2,指示灯灭RA4=0; //RA4,指示灯灭delay(100); //主电路充电延时RB0=0; //ST/(-STOP)发送低电平,禁止GAL输出delay(100);RA1=1; //RA1-PSW1发送高电平,接通电源for(charge_delay=0;charge_delay<50;charge_delay++){delay(15000);}RA5=1; //RA5-RSW1发送高电平,主电路充电延时delay(100); //主电路充电延时PP: asm(" nop"); //RBIF=0; //禁止RB4-7中断,清RBIF 标志设定RBIE=0; //禁止RB4-7中断,RBIE设定GIE=0; //关全局中断RA2=0; //RA2,指示灯灭RA4=0; //RA4,指示灯灭run_flag=0; //运行标志---由RB2按钮设置while(run_flag==0) //----------主程序-------------//{ //RB2启动键,低电平有效if (RB2==0) run_flag=1; //运行标志---由RB2按钮设置delay(100); //延时} //while(run_flag==1) //运行,则执行......{int ope; //设定开环运行次数为12次int openloopn; //RB0=1; //ST/(-STOP)发送高电平,开放GAL输出delay(100); //延时RA4=1;// pwm_real=180;pwm_real=230;delay(500); //延时// ope=10; //设定开环运行次数为20次ope=3; //设定开环运行次数为20次for (openloopn=0;openloopn<=ope;openloopn++){ //0 00000000000000000CCPR1L=pwm_real; //设置开环下PWM输出值----130open_loopf(); //开环运行20次,启动} //----------------------- //000000000000000000delay(6000); //延时RBIF=0; //RB4-7中断,RBIF标志设定RBIE=1; //RB4-7中断,RBIE设定GIE=1; //开全局中断RA2=1; //----------------------- pwm_real=pwm_hi; //-----------------------ghl: asm(" nop"); //if ((pwm_real<110)&&(run_num<10)) //如果pwm_real<140,但是run_num<10,表明未动,则{ //protect_run();protect_run();}while(RA0==1) //RA0=1,过流和过温保护{ //delay(150); //调用延时程序protect_num++; //if (protect_num>30)//如果30次保护,则认为是真正保护(过温和过流保护软件滤波){protect();} //过流和过温保护} //protect_num=0; //if(RB1==1) flag_autohand=1; //自/手标志设定,标志设定else flag_autohand=0; //RB1=1---AUTO;自动//RB1=0---HAND;手动//----------------------- if (flag_autohand==1){ //11 111111111111111111if (pwm_real>pwm_lo) pwm_real-=1; //自动else pwm_real=pwm_lo;}//11111111111111111111else{if(RA3==0) //加(低有效), 则{if (pwm_real<pwm_hi) pwm_real+=1;else pwm_real=pwm_hi;}if(RC1==0) //减(低有效),则{if (pwm_real>pwm_lo) pwm_real-=1;else pwm_real=pwm_lo;}}max_min_compare();CCPR1L=pwm_real; //设置PWM输出delay(4500); //调用延时子程序while(RA0==1) //RA0------过流和过温保护输入,高电平保护{ //protect(); //过流和过温保护} //while(RB3==0){ //RB3停机键,低电平有效run_flag=0; //运行标志---由RB3按钮设置}if (run_flag==0) //停机,则跳转至......{for(;pwm_real<pwm_hi;pwm_real++){delay(2000); //至上限否?CCPR1L=pwm_real; //设置PWM输出为最大}RB0=0; //ST/(-STOP)发送低电平,禁止GAL输出para_chushihua(); //参数初始化nointerupt_chushihua(); //禁止中断初始化PWM_chushihua(); //PWM初始化run_num=0;goto PP;}else{// run_num=0;goto ghl;}}// goto PP;}。

相关文档
最新文档