⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 user_interface.c

📁 dspic开发控制程序,有助开发pic单片机程序
💻 C
📖 第 1 页 / 共 2 页
字号:
/**********************************************************************
 *	程序说明
 *  
 *  该文件包含所有的执行用户接口的代码,用户接口函数由慢速事件调用,每100mSec
 *	执行一次。
 *	按照操作状态的变化调用不同的显示屏幕,函数process_switches()采用去抖动按钮,
 *	确定参数快速递增时按键按下的时间,并通过按钮使系统在不同的状态切换。
 *	函数save_parameter()把参数从flash内存读到RAM,修改参数然后再把它写回内存。
 *	函数process_parameters()对要存储的参数做比例或单位变换。
 * 
 **********************************************************************/

#include "general.h"
#include "hardware.h"
#include "defs.h"
#include "extern_globals.h"

#ifdef DEVELOPMODE
/*********************************************************************/

// 串行数据传送的ASCII缓冲,数据存储再程序内存中,采用dsPIC的PSV特征获取数据。
 struct parameter_data 
	{
    	char *line_msg;   //屏幕上行1参数信息
		  char *quick_msg;	//信息缩写
   	};
 struct fault_data
	{
		char *fault_msg;
	};

const struct fault_data fault_data [] =
{
	{"Press S2 to continue ..."},
	{"Failed to Start"},
	{"Over Current"},
	{"Over Voltage"},
	{"Hardware Trip"},
	{"Over Speed"},
	{"Sensorless Lost"},
	{"Motor Stalled"}
};

const unsigned char help_info[5][14]=
{
	{0,25,32,41,50,50,50,50,50,50,50,50,50,50},
	{26,27,28,29,33,34,35,36,37,38,39,42,50,50},
	{2,3,4,5,6,7,8,9,10,30,31,40,43,44},
	{1,11,12,17,18,19,20,21,22,23,24,50,50,50},
	{13,14,15,16,50,50,50,50,50,50,50,50,50,50},
};

 const struct parameter_data parameter_data [] =	
{
// Line msg,        Quick msg 
{"DIRECTION       ","DD"},//0
{"CONTROL MODE    ","CM"},//1
{"Lock Pos.1 Time ","LP1T"},//2
{"Lock Pos.2  Time","LP2T"},//3
{"Lock Pos.1 Dem. ","LP1D"},//4
{"Lock Pos.2 Dem. ","LP2D"},//5
{"Ramp Start Speed","RSS"},//6
{"Ramp End Speed  ","RES"},//7
{"Ramp Start Dem. ","RSD"},//8
{"Ramp End Dem.   ","RED"},//9
{"Ramp Duration   ","RD"},//10
{"Phase Adv. Enable Spd ","PAES"},//11
{"Phase Adv. Slope","PAS"},//12
{"Stall Time Limit","STL"},//13
{"Over Speed Limit","OSL"},//14
{"Over Volts Limit","OVL"},//15
{"Over Current Lim","OCL"},//16
{"Current P Gain  ","CKP"},//17
{"Current I Gain  ","CKI"},//18
{"Current D Gain  ","CKD"},//19
{"Speed P Gain    ","SKP"},//20
{"Speed I Gain    ","SKI"},//21
{"Voltage Demand  ","VD"},//22
{"Volts P Gain    ","VKP"},//23
{"Volts I Gain    ","VKI"},//24
{"No. Motor Poles ","MP"},//25
{"Current Scale X ","CSX"},//26
{"Current Scale / ","CSD"},//27
{"Volts Scale X   ","VSX"},//28
{"Volts Scale /   ","VSD"},//29
{"Tolerance Check ","TC"},//30
{"Auto Re-acquire ","ARA"},//31
{"Blanking Count  ","BC"},//32
{"Zero X Level Thd","ZXL"},//33
{"Acquire Threshld","AT"},//34
{"Acquire Level Td","AL"},//35
{"Rotation Timeout","RT"},//36
{"Pot / for Duty  ","PDD"},//37
{"Pot / for Currnt","PDC"},//38
{"Pot X for Speed ","PXS"},//39
{"Starting Control","SC"},//40
{"Windmilling Dem.","WD"},//41
{"Braking Ramp T  ","BRT"},//42
{"Acquire Method  ","AM"},//43
{"ZeroX Enable Spd","ZXES"},//44
};

const unsigned char ParaHeader[] = 
			{"\r\nParameter Description\tParameter Abbreviation\tParameter Value\r\n"};

 const struct parameter_data HelpMsg_data [] =	
{	
	{"For Motor Parameters\t","Use '?M'"},
	{"For Starting Parameters\t", "Use '?S'"},
	{"For Control Parameters\t", "Use '?C'"},
	{"For Limit Parameters\t", "Use '?L'"},
	{"For Board Parameters\t", "Use '?B'"},
};

const unsigned char ErrorMsg[] = {"\r\nIncorrect Command! Use '??' For command set.\r\n"};
const unsigned char MotorParaHeader[] = {"Motor Parameters:\r\n"};
const unsigned char LimitParaHeader[] = {"Limit Parameters:\r\n"};
const unsigned char StartingParaHeader[] = {"Starting Parameters:\r\n"};
const unsigned char BoardParaHeader[] = {"Board Parameters:\r\n"};
const unsigned char ControlParaHeader[] = {"Control Parameters:\r\n"};
const unsigned char RunMessage[] = {"\r\n\r\n Speed = 2200 r.p.m.  DutyCycle = 72% Peak Current = 0245 mA \r\n"};
const unsigned char FaultMessage[] = {"\r\n\r\n Fault = Failed to Start \r\n"};

const unsigned char RunMsg1[] = {"Speed in rpm = "};
const unsigned char RunMsg2[] = {" % DutyCycle = "}; 
#endif

#ifndef DEVELOPMODE
volatile unsigned int user_parameters[64] __attribute__((aligned(64),far,section(".const,r")))=
#endif
#ifdef DEVELOPMODE
unsigned int user_parameters[45] = 
#endif
{	
	//BACKWARDS,
	FORWARDS,
	CLOSED_VOLTS,	//速度控制模式->参见defs.h
	50,				// 首次锁位置时间,单位10mSec(中等速率时间)
	50,				// 第二次锁位置时间,单位10mSec(中等速率时间)
	50,				// 锁定位置1所需的数值百分比
	50,				// 锁定位置2所需的数值百分比
	100,			// 加速的起始速度,单位RPM
	2000,			// 加速的终止速度,单位RPM
	52,				// 加速起始所需的数值百分比
	68,				// 加速终止所需的数值百分比
	100,			// 开始加速持续时间,单位10mSec(中等速率时间)
	1500,			// 开始速度相位超前(缺省1500)
	25,				// 缓升相位超前,单位RPMP,1/1000
	100,			// 失速时间极限,单位10mSec(中等速率时间)
	3500,			// 过速跳闸,单位RPM,缺省(3500)
	500,			// 过压跳闸,单位1/10 V
	100,			// 过流极限,单位1/10 A
	900,			// 电流环P增益
	100,			// 电流环I增益
	0,				// 电流环D增益
	2500,			// 速度环P增益
	40,				// 速度环I增益
	490,			// 制动刹车所需的电压,单位1/10 V
	10000,		// 电压环P增益
	5000,			// 电压环I增益
	8,				// 马达的级数
	100,			// 电流放大比例系数Ix
	539,			// 电流缩小比例系数I/
	//239,
	100,			// 电压放大比例系数Vx
	//10,
	1305,			// 电压缩小比例系数V/
	//910,
	90,				// 跑飞检查公差百分比
	1,				// 如果跑飞自动获取
	1,				// 熄火时间长度用于过零检测
	2,				// 在过零检测前> 或 < VDC/2所需的采样数
	12,  			// 用于上升沿检测的ADC值
	6,				// 上升沿检测完成之前VPH采样数
	5,				// 旋转时间到,单位10mSec(中等速率时间)
	1,				// 用于把读到的ADC值转成占空比的除数
	8,				// 用于把读到的ADC值转成I项所需的除数
	3,				// 用于把读到的ADC值转成所需的转速,单位rpm
	1,				// 1=采用电压控制, 0=采用电流控制
	20,				// 自转制动所需的数值百分比
	1,				// 加速制动持续时间,单位10mSec(中等速率时间)
	0,				// 获取位置采用的方法 1 (=0) 或者方法 2 (=1)
	400};			// 采用方法 1 过零检测使能时的速度

// 电流放大、缩小比例系数用于把ADC读数转换为电流或电压:
// 如Vibus = 12.87V , 乘以比例系数100则结果为1287。

// 对于低电压模块:
// VX=100 V/=1305 则比例系数为 13.05 V/V
// 如果LK11&12开路,IX=100 I/=539 则比例系数为 5.39A/V 
// 如果LK11&12短路,IX=10  I/=119 则比例系数为 11.9A/V 

// 对于高电压模块:
// VX=10  V/910 则比例系数为 91.0 V/V
// 如果LK11&12开路,IX=100 I/=108 则比例系数为 1.08A/V 
// 如果LK11&12短路,IX=100 I/=239 则比例系数为 2.39A/V 

// 跑飞检查容许公差常设为不小于25% 

/*********************************************************************/

#ifdef DEVELOPMODE
void GetMsgIndex(void);
void SendCRLF(void);
void SendErrorMsg(void);
void CheckHelp(void);
void SendHelpMsg(void);
void SendMsg(void);
void SendValue(unsigned int k);
void SaveValue(void);
void InitUart(void);
void SendHelpInfo(unsigned char Tab);
void SendMotorPara(void);
void SendLimitPara(void);
void SendControlPara(void);
void SendBoardPara(void);
void SendStartingPara(void);
void SendHeader(void);
void SendTab(void);
void SendRunMsg(void);
void SendFaultMsg(void);
void send_run(void);
void send_fault(void);
void serial_handler(void);
#endif

void process_switches(void);
void save_parameter(void);
void process_parameters(void);
void debounce_switches(void);
void uint_to_string(unsigned int, unsigned char *);

extern void erase_flash_row(unsigned int);
extern void program_flash(unsigned int, unsigned int);

struct interface_flags {
				unsigned EDIT_PARAM : 1;
				unsigned EDIT_MENU :	1;
				unsigned PARAM_CHANGING	: 1;
				unsigned S4_RISING :1;
				unsigned S5_RISING :1;
				unsigned S6_RISING :1;
				unsigned S7_RISING :1;
				unsigned RUN_FRAME :1;
				unsigned UNUSED : 8;
};

struct interface_flags interface_flags;

//键盘处理子程序
void process_switches(void)
{
	static unsigned char initializing_timer=20;
	static unsigned char previous_valid_switch_states=0xFF;
	static unsigned char key_hold_timer=0;
	static unsigned int param_increment=1;

	if (initializing_timer==1)	run_state=STANDBY;
	if (initializing_timer) initializing_timer--;


	if (((previous_valid_switch_states & 0x08)==FALSE) && (valid_switch_states & 0x08))
		interface_flags.S7_RISING=TRUE;
	else
		interface_flags.S7_RISING=FALSE;

	previous_valid_switch_states=valid_switch_states;


	switch(run_state)
	{
		case INITIALIZING: break;

		case STANDBY:	if (interface_flags.S7_RISING)
							{
								DISABLE_INTERRUPTS;
								control_flags2.ROTATION_CHECK=TRUE;
								control_flags2.WINDMILLING=FALSE;
								control_flags2.RETRY_FLAG=FALSE;
								control_flags.LOCK1=FALSE;
								control_flags.LOCK2=FALSE;
								control_flags.RAMP=FALSE;
								control_flags.SENSORLESS=FALSE;
								control_flags.ACQUIRE2=FALSE;
								control_flags.ACQUIRE1=FALSE;
								control_flags.DIR=user_parameters[0];
								ENABLE_INTERRUPTS;
								run_state=STARTING;
								interface_flags.EDIT_MENU=FALSE;
								interface_flags.RUN_FRAME=0;
								fault_count = 0;
							}
							if (interface_flags.S4_RISING)
								interface_flags.EDIT_MENU=TRUE;
							break;

		case STARTING:	if (interface_flags.S7_RISING)
							{
								DISABLE_FIRING;
								control_flags.SENSORLESS=FALSE;
								control_flags.ACQUIRE2=FALSE;
								IEC0bits.T1IE=FALSE;
								IEC0bits.T2IE=FALSE;
								run_state=STANDBY;
							}
							break;

		case RUNNING: 	if (interface_flags.S7_RISING)
							{
								DISABLE_FIRING;
								control_flags.SENSORLESS=FALSE;
								control_flags.ACQUIRE2=FALSE;
								IEC0bits.T1IE=FALSE;
								IEC0bits.T2IE=FALSE;
								run_state=STANDBY;
							}
							if (interface_flags.S4_RISING)
								interface_flags.RUN_FRAME= !interface_flags.RUN_FRAME;
							break;
		case FAULT:		if (interface_flags.S7_RISING)
							{
								trip_state=NO_TRIP;
								DISABLE_INTERRUPTS;
								control_flags.LOCK1=FALSE;
								control_flags.LOCK2=FALSE;
								control_flags.RAMP=FALSE;
								control_flags.SENSORLESS=FALSE;
								control_flags.ACQUIRE1=FALSE;
								control_flags.ACQUIRE2=FALSE;
								IEC0bits.T1IE=FALSE;
								IEC0bits.T2IE=FALSE;
								ENABLE_INTERRUPTS;
								period_measurement=1000;
								//FAULT_RESET=TRUE;
								//FAULT_RESET=FALSE;
								run_state=STANDBY;
							}
							if (interface_flags.S4_RISING)
								interface_flags.EDIT_MENU=TRUE;
							break;
		default:			break;
	}

	return;
}

//参数处理子程序,
void process_parameters(void)
{
	unsigned long ltemp,ltemp2;

	switch (param)
	{
		case 0:	control_flags.DIR=user_parameters[0];
					break;
		case 4:	//用电压控制
					if (user_parameters[40])
						hold1_demand=(unsigned int)((unsigned long)user_parameters[4])*FULL_DUTY/100;
					else //用电流控制
					{
						ltemp=((unsigned long)(current_trip-ibus_offset));
						ltemp*=((unsigned long)user_parameters[4]);
						hold1_demand=(unsigned int)(ltemp/100);
					}	
					break;
		case 5:	//用电压控制
					if (user_parameters[40])
						hold2_demand=(unsigned int)((unsigned long)user_parameters[5])*FULL_DUTY/100;
					else //用电流控制
					{
						ltemp=(unsigned long)(current_trip-ibus_offset);
						ltemp*=((unsigned long)user_parameters[5]);
						hold2_demand=(unsigned int)(ltemp/100);
					}	
					break;
		case 8:	//用电压控制
					if (user_parameters[40])
						ramp_start_demand=(unsigned int)((unsigned long)user_parameters[8])*FULL_DUTY/100;
					else //用电流控制
					{
						ltemp=(unsigned long)(current_trip-ibus_offset);
						ltemp*=((unsigned long)user_parameters[8]);
						ramp_start_demand=(unsigned int)(ltemp/100);
					}
					ramp_demand_delta=(signed int)(ramp_end_demand-ramp_start_demand);
					break;

		case 9:	//用电压控制
					if (user_parameters[40])
						ramp_end_demand=(unsigned int)((unsigned long)user_parameters[9])*FULL_DUTY/100;
					else //用电流控制
					{
						ltemp=(unsigned long)(current_trip-ibus_offset);
						ltemp*=((unsigned long)user_parameters[9]);
						ramp_end_demand=(unsigned int)(ltemp/100);
					}
					ramp_demand_delta=(signed int)(ramp_end_demand-ramp_start_demand);
					break;

		case 10: ramp_time=user_parameters[10];
					break;
		case 17:	iloop_p_gain=(int)user_parameters[17];
					break;
		case 18: iloop_i_gain=(int)user_parameters[18];
					break;
		case 19: iloop_d_gain=(int)user_parameters[19];
					break;
		case 20:	wloop_p_gain=(int)user_parameters[20];
					break;
		case 21:	wloop_i_gain=(int)user_parameters[21];
					break;
		case 23:	vloop_p_gain=(int)user_parameters[23];
					break;
		case 24:	vloop_i_gain=(int)user_parameters[24];
					break;
		case 6:	
		case 7:
		case 25:
		case 44: 
					//计算步率
					ltemp=((unsigned long)user_parameters[6]*(unsigned long)user_parameters[25])/20;
					//保证ramp_start_rate不会超出最大值
					if ((COUNTER_RATE/ltemp) > 65535)
					{	
						ramp_start_rate=65535;
						ramp_start_speed=COUNTER_RATE*20/(65535*(unsigned long)user_parameters[25]);
					}
					else
					{
						ramp_start_rate=(unsigned int)(COUNTER_RATE/ltemp);
						ramp_start_speed=user_parameters[6];
					}
					ltemp=((unsigned long)user_parameters[7]*(unsigned long)user_parameters[25])/20;
					//保证ramp_end_rate不会超出最大值
					if ((COUNTER_RATE/ltemp) > 65535)	
						ramp_end_rate=65535;
					else
						ramp_end_rate=(unsigned int)(COUNTER_RATE/ltemp);

					ramp_speed_delta=(int)(user_parameters[7]-user_parameters[6]);

					//采用获取方法1时,过零检测使能,计算步率
					ltemp=((unsigned long)user_parameters[44]*(unsigned long)user_parameters[25])/20;
					if ((COUNTER_RATE/ltemp) > 65535)
						acquire1_enable_rate=65535;
					else
						acquire1_enable_rate=(unsigned int)(COUNTER_RATE/ltemp);
					break;
		case 16:

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -