欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  IT编程

CCS和proteus联动仿真msp430控制四位数码管显示数字

程序员文章站 2022-06-17 15:19:56
文章目录前言一、软件基础二、CCS生成需要的hex文件1.建立工程和设置2.写代码三、proteus搭建电路与载入hex总结前言又是一年电子信息杯,每年单片机都有很多人放弃,我那时在环境搭建上耗了很多时间这里分享一个我很早写的一个数码管显示的代码和整体流程,希望能对后来人有所帮助一、软件基础proteus和CCS(我用的是CCS9.3.0和proteus8.6)下载和安装破解只要在CSDN上搜索就行,这里给出两个链接,如果你按流程安装有问题欢迎评论区指出CCSproteus二、CCS....


前言

又是一年电子信息杯,每年单片机都有很多人放弃,我那时在环境搭建上耗了很多时间
这里分享一个我很早写的一个数码管显示的代码和整体流程,希望能对后来人有所帮助

一、软件基础

proteus和CCS(我用的是CCS9.3.0和proteus8.6)
下载和安装破解只要在CSDN上搜索就行,这里给出两个链接,如果你按流程安装有问题欢迎评论区指出
CCS
proteus

二、CCS生成需要的hex文件

1.建立工程和设置

file→new→CCS project 设置如下,选中芯片msp430g2553,创建工程名字(segdisplay),点击finish
CCS和proteus联动仿真msp430控制四位数码管显示数字
正常建立以后点开main.c文件如下图所示
CCS和proteus联动仿真msp430控制四位数码管显示数字
选中工程,右键,左键单击properties,左键单击Build界面如下所示
CCS和proteus联动仿真msp430控制四位数码管显示数字
点击Steps,如下图所示
直接在Post-build steps中输入

C G T O O L H E X " − i " {CG_TOOL_HEX}" -i " CGTOOLHEX"i"{BuildArtifactFileName}” -o “${BuildArtifactFileBaseName}.hex” -order MS -romwidth 16

在Description中输入

Create flash image: Intel-HEX

CCS和proteus联动仿真msp430控制四位数码管显示数字
点击 左侧build下的MSP430 Hex Utility,勾选Enable MSP430 Hex Utility,如下图所示
CCS和proteus联动仿真msp430控制四位数码管显示数字

点击apply and close。

2.写代码

代码如下(示例):

/* *************************************************************
 * 电子信息杯初赛代码
 *创建date  2019_12_03
 * by hwk HeWenKang@bupt.edu.cn
*********************************************************** */
/* *************************************************************
写于2020_12_11
回看这些代码真是黑历史-=也不知道这个代码能不能正常运行,如果不行多看看引脚定义有没有问题
建议早点看中断内容,脱离轮询的笨办法;在src里面多创建一些文件,按功能分类放;多些注释,养成良好习惯;多用define,增强代码的可移植性;函数命名多用下划线和英文
测频率和占空比可以用定时器捕获,但是proteus仿真有点问题,管脚和代码里对应不上,可能存在进不去中断的情况
单片机路漫漫其修远兮,加油冲冲冲
*********************************************************** */
#include <msp430g2553.h>

/* *************************************************************
 *   1ms延时函数
  *     延时函数,具体延时的值根据主时钟频率改变而改变,调节内部i大小即可
 * by hwk HeWenKang@bupt.edu.cn
*********************************************************** */
void delay_1ms(void)
    {
        unsigned int i;
        for (i = 0; i<40; i++)
        ;
    }

/*******************************************************************
 * nms延时函数
  *     延时函数,具体延时的值根据主时钟频率改变而改变
 * by hwk HeWenKang@bupt.edu.cn
 *******************************************************************/
void delay_nms(unsigned int k)
    {
        unsigned int i = 0;
        for (i = 0; i <k ; i++)
            delay_1ms();
    }

/*******************************************************************
  * 引脚初始化函数
  *  设置引脚输入输出
 * by hwk HeWenKang@bupt.edu.cn
 *******************************************************************/
void GPIO_Init(void)
    {
    P1OUT = 0;//P1初始值为0x00;
    P1DIR|=BIT1+BIT2+BIT3+BIT4+BIT5; // P1.1、p1.2、P1.3、P1.4设为输出(置1)
    P1DIR&=~BIT7;
    P2OUT = 0;//P2初始值为0x00;
    P2DIR|=BIT0+BIT1+BIT2+BIT3+BIT4+BIT5+BIT6+BIT7; // P2设为输出(置1)
    }

/* ******************************************************************
 *   7位数码管数字输出辅助函数
 *  m==3处是小数点,所以比较特殊,原理就是扫频,m是第几位,n是该位数字
 * by hwk HeWenKang@bupt.edu.cn
 *********************************************************************/
void segprintf(unsigned int m,unsigned int n){

       P1OUT=0;
       if(m==1)
       {P1OUT = BIT1;P2OUT =0XFF;
       }
       else if(m==2)
       {P1OUT = BIT2;P2OUT =0XFF;
       }

        else if(m==3)
         { P1OUT = BIT3;P2OUT =0XFF;
         }
         else if(m==4)
         {P1OUT = BIT5;P2OUT =0XFF;
        }
         else
           P1OUT=0;
       if(m==3)
       {  switch(n){
         case 0: P2OUT=BIT1;break;
         case 1: P2OUT=BIT1+BIT2+BIT3+BIT4+BIT7;break;
         case 2: P2OUT=BIT2+BIT5;break;
         case 3: P2OUT=BIT2+BIT3;break;
         case 4: P2OUT=BIT3+BIT4+BIT7;break;
         case 5: P2OUT=BIT3+BIT6;break;
         case 6: P2OUT=BIT6;break;
         case 7: P2OUT=BIT1+BIT2+BIT3+BIT4;break;
         case 8: P2OUT =0;;break;
         case 9: P2OUT=BIT3;break;
         }}
       else
       {
         switch(n){
         case 0: P2OUT=BIT0+BIT1;break;
         case 1: P2OUT=BIT0+BIT1+BIT2+BIT3+BIT4+BIT7;break;
         case 2: P2OUT=BIT0+BIT2+BIT5;break;
         case 3: P2OUT=BIT0+BIT2+BIT3;break;
         case 4: P2OUT=BIT0+BIT3+BIT4+BIT7;break;
         case 5: P2OUT=BIT0+BIT3+BIT6;break;
         case 6: P2OUT=BIT0+BIT6;break;
         case 7: P2OUT=BIT0+BIT1+BIT2+BIT3+BIT4;break;
         case 8: P2OUT =BIT0 ;break;
         case 9: P2OUT=BIT0+BIT3;break;
         }
       }
 delay_nms(1);
// P1OUT=0;
// P2OUT=0;
}

/* ******************************************************************
 *   频率输出函数
 *  待补充
 * by hwk HeWenKang@bupt.edu.cn
 *********************************************************************/
int  frequency(void)
    {
     return(1314);
    }

/* ******************************************************************
 *    占空比输出函数
 *  待补充
* by hwk HeWenKang@bupt.edu.cn
 *********************************************************************/
int  dutycycle(void)
    {
      return (1413);
    }

/* ******************************************************************
 *  7位数码管数字输出函数
 * 输入4位数k,函数取每一位的数,通过函数segprintf(a,b)将每一位在对应位输出
 * by hwk HeWenKang@bupt.edu.cn
 *********************************************************************/
void printfseg(unsigned int k)
{
    unsigned int a;
    unsigned int b;
    b=k/1000;
    a=4;
    segprintf(a,b);
    k=k-1000*b;
    b=k/100;
    a=3;
    segprintf(a,b);
    k=k-100*b;
    b=k/10;
    a=2;
    segprintf(a,b);
    k=k-10*b;
    b=k;
    a=1;
    segprintf(a,b);
}

/* ******************************************************************
 *  主函数
 *尽量把函数写在外面,最好写在别的文件里面然后include,main函数越简单越好
 * by hwk HeWenKang@bupt.edu.cn
 *********************************************************************/
int main(void)
    {
        WDTCTL = WDTPW | WDTHOLD;// 关闭看门狗,我也不知道为什么,但基本上都有这个代码,好像是为了防止程序跑飞
//             BCSCTL1 = CALBC1_1MHZ;
//            DCOCTL = CALDCO_1MHZ;
//            BCSCTL2 = SELM_0 | DIVM_0 | DIVS_3;
        GPIO_Init();
        //定义引脚功能
        unsigned int f=0;
        unsigned int z=0;
        f=frequency();
        z=dutycycle();

        while(1)               //用中断可以节省资源,但是不太会,用轮询方式消耗资源达到效果,反正他不看源代码:(
            {
              while(1)                        //循环A
                {
                    if((P1IN & BIT7) == BIT7)
                       printfseg(f);
                    else
                       {
                           while(1)
                              {
                                  if((P1IN & BIT7) == BIT7)
                                    break;
                                  else
                                         ;
                              }
                           break;
                       }
                }
              while(1)                             //循环B
                  {
                    if((P1IN & BIT7) == BIT7)
                        printfseg(z);
                    else
                        {
                          while(1)
                             {
                              if((P1IN & BIT7) == BIT7)
                                break;
                              else
                                     ;
                             }
                          break;
                        }
                  }
             }        //最大while的后括号
    }


完成以后点击左侧小锤子build 工程,build finish以后显示如下
CCS和proteus联动仿真msp430控制四位数码管显示数字


三、proteus搭建电路与载入hex

这部分比较简单,照着图片找元件搭就行,搭建出来的电路效果如下图所示,我的主页里也给出这个电路的工程文件proteus_seg。
CCS和proteus联动仿真msp430控制四位数码管显示数字

右键芯片,选择编辑元件,选择program file,找到之前在CCS中工程目录debug目录下的.hex文件
CCS和proteus联动仿真msp430控制四位数码管显示数字
CCS和proteus联动仿真msp430控制四位数码管显示数字
打开,确定,然后点左下角运行

CCS和proteus联动仿真msp430控制四位数码管显示数字
CCS和proteus联动仿真msp430控制四位数码管显示数字

总结

代码里面当时测试有一个bug,发现当输入的数字是0开头时,数码管显示会显示不一样的数,就是说如果return的z是0520,显示的就是0336,如果是520,显示的就是0520,这点要注意一下。
然后代码显示是保留2位小数的显示,具体逻辑可以看源代码,注释还行,应该看得懂。

后面还会遇到proteus仿真问题,比如说定时器捕获中断进不去,串口没有输出,这些在烧录硬件时都不会遇到,但是烧录硬件也有它的问题,测试起来没有仿真方便。

最后附上我去年电子信息杯在B站的两个视频,还有很多腾讯视频的视频我就不发了,你们去腾讯视频搜电子信息杯应该就能搜到我们那一级的黑历史。
利用IAR生成.hex文件并在Proteus中运行
2020F134_msp430演示视频_电子信息杯

再强调一下我在代码前面写的一段话
建议早点看中断内容,脱离轮询的笨办法;在src里面多创建一些文件,按功能分类放;多些注释,养成良好习惯;多用define,增强代码的可移植性;函数命名多用下划线和英文
测频率和占空比可以用定时器捕获,但是proteus仿真有点问题,管脚和代码里对应不上,可能存在进不去中断的情况
单片机路漫漫其修远兮,加油冲冲冲

本文地址:https://blog.csdn.net/weixin_43812576/article/details/111087056