搜索
bottom↓
回复: 140

教你如何用C++写AVR程序

[复制链接]

出0入0汤圆

发表于 2009-6-20 22:10:10 | 显示全部楼层 |阅读模式
教你如何用C++写单片机程序
关键词:C++   面向对象     单片机

从大一就开始学习单片机,学51,AVR编程都使用C语言的风格,即面向过程,只要能画出程序流程图,程序基本就born了。我热衷于编程,尤其是C++,当时想有没有一天,C++的类和对象也能出现在单片机中?
历经世事沧桑,事到如今,我终于有机会,和大家一起学习使用真正面向对象的C++来控制单片机。目前单片机编译器大部分只支持C语言,C++还不够普及,但我们有理由相信,有着更先进的面向对象的理念,有更加平易近人的类和继承,C++必将取代C,成为单片机程序的主流。试看将来环球单片机,必是C++的世界!
下面大家跟着我来一起学习怎么用C++给单片机编程序!本文要求大家玩过AVR单片机,有过C语言编程经验,而且要对VC6.0开发环境有一定了解。
必备软件:VC6.0(用于编辑源程序),WinAVR(用于生成Makefile,支持AVR系列单片机),Proteus(用于仿真调试)。
     首先,你的电脑上要装有VC6.0,进入后选菜单【file】---【new】新建工程,如图1选择Makefile工程,输入工程名称,路径,点确定。

                                                                图1_新建工程
一路OK建好工程,界面如图2。这个工程是专门写makefile脚本的,你如果学AVR单片机使用avr-gcc那应该对makefile有一定了解,如果想多了解一点详见http://baike.baidu.com/view/974566.html?wtp=tt(呵呵,百度百科)。
你还需要安装WINAVR,这是个免费软件,网上很多资源,这个软件很容易安装,一路Next就可以啦!为了使用方便,我的WINAVR安装到了C盘根目录下的WINAVR文件夹。安装好后,可以直接用它来编辑源代码,今天我就不讲它的使用方法了,只讲怎么生成makefile。自我感觉用熟悉的VC6.0环境编写程序心情很愉快,大家还是跟我一起来,打造舒服的编辑环境!建好工程编译成功的界面如图2所示。


                                                                        图2_工程界面
建好的工程里可以写C++代码了,下面是我要以图3的电路图写一个控制LED亮灭的程序。这个用C很easy,是吧?用Proteus仿真大家应该都会我就不罗嗦了,效果可以看本期附带的视频。

                              图3_电路图

在工程界面中,点【file】---【new】,选“C++ Source File”,如图4所示,在file一栏中输main点OK,注意一定是main,不要写错,一会就知道为什么了。然后进入编辑页面,我们就可以用C++编写源代码了,呵呵,程序如下,是个非常简单的类LED,短短几行程序展现了一个全新的面貌:没有了C语言的那些函数堆,取而代之的是高效美观的类和对象。

                                 图4_新建文件
源代码:
#include <avr/io.h>
class LED
{
public:
        LED()
        {
                DDRB|=0x01;
                PORTB&=~0x01;
        }
        ~LED()
        {
                DDRB&=~0x01;
                PORTB&=~0x01;
        }
        void LEDon(void)
        {
                PORTB&=~0x01;
        }
        void LEDoff(void)
        {
                PORTB|=0x01;
        }
        void LEDdelay(void)
        {
                unsigned int a,b;
                for(a=10000;a;a--)
                        for(b=3000;b;b--);
        }
};
int main(void)
{
        LED led1;
        while(1)
        {
                led1.LEDoff();
                led1.LEDdelay();
                led1.LEDon();
                led1.LEDdelay();
        }
}
编写完后,还需要对工程进行一些配置,大家要沉着冷静,跟我一步一步走,不要贪图路旁的景色。打开菜单【Project】--&#61664;【Settings】,在“Build Command Line”中填入“make”,OK,如图5所示。

                              图5_ProjectSettings

然后打开菜单【Tools】-&#61664;【Options】,选“Derectories”标签页,在下拉菜单“Show Directories For”选“Executable Files”,将Winavr的可执行程序路径添加到VC6.0中,这里需要两条:  winavr安装路径\bin     和       winavr安装路径\utils\bin就行啦,如图6所示。

                              图6_ToolsOptions
马上就要成功了,但还有最关键的一项没做,就是写一个makefile。这里我们就用winavr自带的工具mfile来完成。从开始菜单找到winavr,一个个找,看到mfile,单击打开,界面如图7所示。

图7_mfile界面
将它保存到工程文件夹下,慢慢修改。有很多选项需要改,大家也不必全都搞懂,一般直接用现成的就行,我就是一直用我一开始生成好的makefile,一劳永逸,使用时要遵守规则就行了,比如,我们工程里的源程序文件名为main,这是为了让Makefile认出来,以便进行编译。如果改成别的名字,Makefile就会找不到主文件而报错。如果你想用别的名字,也可以,在Makefile里找到一行(目标文件):

# Target file name (without extension).
TARGET = main

将“TARGET=”后面改成你的文件名(不要加后缀)就可以了。
后面不远处有如下几行(源代码文件):
# List C source files here. (C dependencies are automatically generated.)
SRC =
# List C++ source files here. (C dependencies are automatically generated.)
CPPSRC =  $(TARGET).cpp

这就把源代码加入了Makefile的识别文件里,之后就可以对其进行编译、链接了。
还有一个选项是选择单片机型号:

# MCU name
MCU = atmega8

你也可以改成其他型号,如atmega16,atmega128等等。

还有一个选项选择编译器:

CC = avr-gcc

由于我们要用C++编译器,所以改成

CC = avr-g++

就行啦!
建议大家自己学习一下这些选项,我附带的资料中makefile大家也可以直接拿来用。
完成上述这些,我们该松口气了吧?
在VC6.0中,习惯性地按F7,激动人心的时刻到了, 0 errors,0 warnings.!!!多么熟悉的面孔!祝贺你,已经成功编写了第一个C++源程序!其重大意义不亚于我们第一个helloworld程序!好了,我们烧录到单片机中,用proteus仿真下结果,哈哈一切正常!
        这只是抛砖引玉的一个简单例子,大家如果熟练运用,就可以用类来编写更加高效简洁的代码,去控制电机,液晶屏,点阵,蜂鸣器,AD……甚至完全可以写一个操作系统,这是后话了。祝大家学习愉快!



作者简介:
赵永科,男,1988年生于名不见经传的一个小山村——南故邑,2007年考入燕山大学,并加入燕山大学无线电爱好者协会,开始了搞电子研发,对 51、AVR等单片机比较熟悉,多次在校级科技活动中获奖,并报名参加了2009年NEC杯全国电子设计大赛。现任燕山大学无线电爱好者协会会长,热衷于钻研技术,学习刻苦,拿过N-1次一等奖学金。
“软件是硬件的灵魂”,刚刚看了点操作系统,感觉很多东西都可以用面向对象的方法解决,简单的如一个实时时钟,我们把它当成一个类去操作就会比调用复杂的函数堆方便。尤其需要几个人分头完成工作时,类的保护机制也保证操作者不会发生冲突。今天这个例子是很简单的例子,大家完全可以写自己的类CLED,CBUZZER,CTIMER……写成像MFC这样标准库该多有意思!
如果想同我交流请联系zhaoyongke@yeah.net

阿莫论坛20周年了!感谢大家的支持与爱护!!

月入3000的是反美的。收入3万是亲美的。收入30万是移民美国的。收入300万是取得绿卡后回国,教唆那些3000来反美的!

出0入0汤圆

 楼主| 发表于 2009-6-20 22:12:25 | 显示全部楼层

图一 (原文件名:图1_新建工程.JPG)


图2 (原文件名:图2_工程界面.JPG)


图3 (原文件名:图3_电路图.JPG)


图4 (原文件名:图4_新建文件.JPG)


图5 (原文件名:图5_ProjectSettings.JPG)


图6 (原文件名:图6_ToolsOptions.JPG)


图7 (原文件名:图7_mfile界面.JPG)

出0入0汤圆

发表于 2009-6-20 23:04:04 | 显示全部楼层
看了一点点,楼主如真要这么写,恐怕成员函数都成了内联函数,如果类比较大的话,那会占用更多的flash。不过这里的语句都很少很小,成为内联函数恰到好处。

出0入18汤圆

发表于 2009-6-20 23:25:58 | 显示全部楼层
在很多的地方C语言还是很有优势的,使用简单,学习入门简单,虽然我也觉得c++用在单片机里将是另一个世界,但是也要看是什么程序了!!!没有必要所有的都用c++,配合使用很好的呀!!!

出0入0汤圆

发表于 2009-6-20 23:29:51 | 显示全部楼层
【3楼】 dengxiaofeng 天下的人

C++基本上兼容C,建立CPP文件,想用C的地方就用C,想用C++的地方就用C++。

其实很多人对C++都存在误解。用C++,并不代表全部都是类。C++中还是一样需要用到过程结构的。

出0入0汤圆

发表于 2009-6-20 23:39:41 | 显示全部楼层
支持C++

出0入0汤圆

发表于 2009-6-20 23:50:32 | 显示全部楼层
不错,记号一下,有空试试

出0入0汤圆

发表于 2009-6-21 00:11:51 | 显示全部楼层
记得以前写过一个简单的C++程序,把串口封装成一个类,要发送数据时,只需要:USART<<OutputData;就行了。其实和C一样,都是函数调用,只是C++更加形象一点。

出0入0汤圆

 楼主| 发表于 2009-6-23 13:37:49 | 显示全部楼层
#include <avr/io.h>
#include <usart.h>
#include <util/delay.h>
#include <class1602.h>
int main(void)
{
        PORTB|=0x80;
        My1602 a;
        a<<"Hello kkk!This is C++\n";
        a<<100;
        a<<" ";
        a<<200;
        a<<"    ";
        a<<300;
        _delay_ms(1000);
        while(1)
        {
                for(int i=0;i<10;i++)
                {
                        a.left();
                }
                _delay_ms(1000);
                for(int i=0;i<10;i++)
                {
                        a.right();
                }
                _delay_ms(1000);
        }
}

出0入0汤圆

 楼主| 发表于 2009-6-23 13:53:30 | 显示全部楼层
刚刚写好一个1602的类,说明如下:

私有成员变量:


buffer     unsigned char型数组,长度80

hang       unsigned char型变量,代表当前行数(1 or 2)



私有成员函数(外部不能直接使用,以防出错):

void write_cmd(unsigned char c);

void write_data(unsigned char d);



公有成员函数:


void clear(void);清屏


void setbuffer(char *d);设置缓冲区


void showbuffer(void);显示缓冲区


int operator<<(int t);在1602上显示整型数


char * operator<<(char  *d);在1602上显示字符串


void left(void );左移

void right(void);右移

(原文件名:class1602.JPG)

出0入0汤圆

 楼主| 发表于 2009-6-23 13:54:46 | 显示全部楼层
如有需要源代码请与我联系,一起开发属于自己  的标准类库吧!

出0入0汤圆

发表于 2009-6-23 14:36:48 | 显示全部楼层
不错,想学习下。

出0入0汤圆

发表于 2009-6-26 14:00:24 | 显示全部楼层
受益匪浅啊,顶了!

出0入0汤圆

 楼主| 发表于 2009-6-27 23:55:22 | 显示全部楼层
一个通用类CTime,可以跨平台的。注释掉的为在PC上测试用的


#ifndef classtime_kkk_h
#define classtime_kkk_h 1
class CTime
{
public:
        CTime()
        {
                year=0,month=0,day=0,week=0,hour=0,minute=0,second=0;
                validate();
        }
        CTime(char *s)
        {
                year=*s++;
                month=*s++;
                day=*s++;
                week=*s++;
                hour=*s++;
                minute=*s++;
                second=*s++;
                validate();
        }
        ~CTime()
        {}
        CTime& operator<<(CTime& ntime);
        CTime& operator>>(CTime& ntime);
        CTime& operator<<(char *d);
        char getsecond(void)
        {
                return second;
        }
        char getminute(void)
        {
                return minute;
        }
        char gethour(void)
        {
                return hour;
        }
        char getday(void)
        {
                return day;
        }
        char getmonth(void)
        {
                return month;
        }
        char getyear(void)
        {
                return year;
        }
        char getweek(void)
        {
                return week;
        }
        void setsecond(char d)
        {
                second=d;
        }
        void setminute(char d)
        {
                minute=d;
        }
        void sethour(char d)
        {
                hour=d;
        }
        void setday(char d)
        {
                day=d;
        }
        void setmonth(char d)
        {
                month=d;
        }
        void setyear(char d)
        {
                year=d;
        }
        void setweek(char d)
        {
                week=d;
        }
//        void display(void)
        //{
                //cout<<"Year:"<<(int)year<<endl;
//                cout<<"Month:"<<(int)month<<endl;
//                cout<<"Day:"<<(int)day<<endl;
//                cout<<"Week:"<<(int)week<<endl;
//                cout<<"Hour:"<<(int)hour<<endl;
//                cout<<"Minute:"<<(int)minute<<endl;
//                cout<<"Second:"<<(int)second<<endl;
//        }
private:
        void validate(void);
        char year,month,day,week,hour,minute,second;
};
void CTime::validate(void)
{
        if(second>=60 || second<0)
        {
                second=0;
        }
        if(minute>=60 || minute<0)
        {
                minute=0;
        }
        if(hour>=24||hour<0)
        {
                hour=0;
        }
        if(day>=31 || day<=0)
        {
                day=1;
        }
        if(month>12 || month<=0)
        {
                month=1;
        }
        if(year<0)
        {
                year=0;
        }
        if(week>7 || week<0)
        {
                week=0;
        }
}
CTime& CTime::operator<<(CTime& ntime)
{
        second=ntime.getsecond();
        minute=ntime.getminute();
        hour=ntime.gethour();
        day=ntime.getday();
        month=ntime.getmonth();
        year=ntime.getyear();
        week=ntime.getweek();
        validate();
        return *this;
}
CTime& CTime::operator>>(CTime& ntime)
{
        ntime.setsecond(second);
        ntime.setminute(minute);
        ntime.sethour(hour);
        ntime.setday(day);
        ntime.setmonth(month);
        ntime.setyear(year);
        ntime.setweek(week);
        ntime.validate();
        return *this;
}
CTime& CTime::operator<<(char *d)
{
        second=*d++;
        minute=*d++;
        hour=*d++;
        day=*d++;
        month=*d++;
        year=*d++;
        week=*d++;
        validate();
        return *this;
}

#endif

出0入0汤圆

 楼主| 发表于 2009-6-27 23:57:38 | 显示全部楼层
这也是一个通用类,便于数组操作。


这个32byte的数组时干什么用的呢?

和上面的CTime有什么联系呢???




#ifndef _CRam_kkk_h
#define _CRam_kkk_h 1
class CRam
{
public:
        CRam()
        {
                for(int i=0;i<32;i++)
                {
                        ram=0;
                }
        }
        ~CRam()
        {}
        char & operator[](char index);
private:
        char ram[32];
};
char & CRam::operator [](char index)
{
        return ram[index];
}

#endif



欲知详情,下回分解

出0入0汤圆

 楼主| 发表于 2009-8-21 02:43:13 | 显示全部楼层
好久没写C++了,这两天忙全国电子设计大赛,感觉好多模块如果用C++来写,会好很多

出0入0汤圆

发表于 2009-8-21 07:58:14 | 显示全部楼层
不错,支持一个
头像被屏蔽

出0入0汤圆

发表于 2010-1-26 12:04:34 | 显示全部楼层
以下蓝色文字由坛主:armok 于:2010-01-26,12:04:34 加入。
<font color=black>请发贴人注意:
本贴放在这分区不合适,即将移走
原来分区:[3033]燕山大学无线电爱好者协会
即将移去的分区:[1000]AVR (原ourAVR.com) 技术论坛
移动执行时间:自本贴发表0小时后

任何的疑问或咨询,请可随时联系站长。谢谢你的支持!
</font>
头像被屏蔽

出0入0汤圆

发表于 2010-1-26 12:04:43 | 显示全部楼层
好资料。

出0入0汤圆

发表于 2010-1-26 19:35:41 | 显示全部楼层
MARK

出0入0汤圆

发表于 2010-1-26 20:38:57 | 显示全部楼层
杀鸡不用牛刀

出0入0汤圆

发表于 2010-1-28 21:07:24 | 显示全部楼层
发展的趋势谁也挡不了的。。。

出0入4汤圆

发表于 2010-1-28 21:51:57 | 显示全部楼层
学习

出0入0汤圆

发表于 2010-1-28 22:01:11 | 显示全部楼层
足迹

出0入0汤圆

发表于 2010-1-28 22:41:10 | 显示全部楼层
很好!支持一下!

出0入0汤圆

发表于 2010-1-28 23:29:08 | 显示全部楼层
mark

出0入0汤圆

发表于 2010-1-28 23:33:30 | 显示全部楼层
谢谢分享,MARK

出425入0汤圆

发表于 2010-1-29 09:04:46 | 显示全部楼层
年纪大了,学新的东西理解能力强多了,但记忆力跟不上,C还没有熟练,C++有很多新的内容吗?

出0入0汤圆

发表于 2010-1-29 09:19:16 | 显示全部楼层
mark

出0入0汤圆

发表于 2010-1-29 09:36:55 | 显示全部楼层
mark

出0入0汤圆

发表于 2010-1-29 17:51:56 | 显示全部楼层
就是类库太少了

出0入0汤圆

发表于 2010-2-12 23:18:55 | 显示全部楼层
mark

出0入0汤圆

 楼主| 发表于 2010-2-15 13:15:47 | 显示全部楼层
作者复出,准备为C++的普及贡献自己个人的力量。

出425入0汤圆

发表于 2010-2-23 10:06:38 | 显示全部楼层
我受了你的鼓动,假期啃了一下《易学C++》点击此处下载 ourdev_534935.pdf(文件大小:2.25M) (原文件名:易学C++.pdf),发现C++要学习很多新的东西。这些新的东西都要学习吗?要写STC  89C51之类的单片机程序,有编译器支持吗?

出425入0汤圆

发表于 2010-2-24 09:13:18 | 显示全部楼层
我今天花了1个多小时,找到了可以用的“IAR FOR 8051”的D版了,版本号是7.51的。支持C++。IAR也有for AVR的。坊间传说IAR是最好的编译器,大家有需要吗?我可以跟大家共享。我想用IAR代替GCC,做上面的测试,楼主你看行不?

出0入0汤圆

发表于 2010-2-24 09:26:55 | 显示全部楼层
Mark!

出425入0汤圆

发表于 2010-2-26 14:26:01 | 显示全部楼层
公司决定,今后主要用AVR,放弃用STC。

出0入0汤圆

 楼主| 发表于 2010-2-26 14:58:39 | 显示全部楼层
IAR for AVR偶没用过,装了几次没成功,如果能共享最好了!

出0入0汤圆

发表于 2010-2-26 16:04:18 | 显示全部楼层
mark

出0入0汤圆

发表于 2010-2-26 16:48:44 | 显示全部楼层
收藏

出0入0汤圆

发表于 2010-2-26 16:58:05 | 显示全部楼层
收藏

出0入0汤圆

发表于 2010-2-26 19:59:34 | 显示全部楼层
学习了

出425入0汤圆

发表于 2010-2-27 14:57:29 | 显示全部楼层
就是本坛的。http://www.ourdev.cn/bbs/bbs_content.jsp?bbs_sn=1372922&bbs_page_no=1&search_mode=1&search_text=IAR
我的安装过程有些不一样。我改bat的数据,得到serial.txt。也在CMD中生成是sn.txt。在安装过程中,我用serial.txt的licence number 和licence key。完成后,再运行licence manager ,>install,把sn.txt的licence key 输入。就可以得到这个画面。
(原文件名:Snap1.jpg)

出0入0汤圆

 楼主| 发表于 2010-2-28 13:38:49 | 显示全部楼层
偶试试看

出0入0汤圆

发表于 2010-2-28 15:08:15 | 显示全部楼层
路过

出0入0汤圆

 楼主| 发表于 2010-2-28 15:10:01 | 显示全部楼层
to:guolun
帮帮忙,出错了!

(原文件名:er.JPG)

出0入0汤圆

发表于 2010-2-28 15:15:16 | 显示全部楼层
mark!

出425入0汤圆

发表于 2010-3-1 13:34:15 | 显示全部楼层
看这里的回复,http://www.ourdev.cn/bbs/bbs_content.jsp?bbs_sn=1372922&bbs_page_no=1&bbs_id=1000

出0入0汤圆

发表于 2010-3-1 14:32:45 | 显示全部楼层
在128上运行通过,类操作正常,但不知为什么延时总是不起作用!

出0入0汤圆

 楼主| 发表于 2010-3-2 12:56:55 | 显示全部楼层
to:guolun
试过了,仍然不行,郁闷了。
不会是系统的问题吧!

出0入0汤圆

 楼主| 发表于 2010-3-2 13:39:37 | 显示全部楼层
to:lzllong

你的这个问题可能是由于延时太短,将数改大一些试试!

出425入0汤圆

发表于 2010-3-2 16:22:23 | 显示全部楼层
我详细说说安装步骤:
1. 把keygen文件夹copy到C盘。
2. 在dos画面,运行iarid.exe,得到本机的id。是十六进制的数。抄下它。
3. 修改keygen文件夹的iar.bat文件,上面抄下的id换掉iar.bat文件的0x12345.保存。
4. 双击iar.bat。得到serial.txt。
5. 装iar时,使用第三个installserial(1、2、3个都是相同的),在这个installserial下面,把key:后面的内容(到#为止,后面的内容应该是"EWAVR" version "2.25_WIN", no expiration date, exclusive)copy到安装画面的key大框中。
6. 安装完成后,运行激活程序。下一步,下一步,下一步,my computer,下一步,完成。  

根据你的出错画面提示,重点查第5步,你选对了number没有?选对了key没有?

出0入0汤圆

 楼主| 发表于 2010-3-2 18:28:18 | 显示全部楼层
这下成功了,呵呵,谢谢guolun大哥!

出0入0汤圆

 楼主| 发表于 2010-3-3 12:50:34 | 显示全部楼层
昨晚在IAR上试了试,可以运行我们的C++程序,特发此贴。详细步骤如下:

1.建立工程

(原文件名:new.JPG)
保存到你的工程文件夹,如iarcpp\
选择C++工程的main,这样就建立了以C++为主的工程,并生成一个main.cpp源文件。

出0入0汤圆

 楼主| 发表于 2010-3-3 12:52:21 | 显示全部楼层
2.在main.cpp中添加代码,我的源程序如下(基于mega16的)
//main.cpp
//author:kkk
//date:2010-3-2
#include <iom16.h>
class led
{
public:
  led()
  {
    DDRB=0xff;
    PORTB=0xaa;
  }
  ~led()
  {
    DDRD=0xff;
    PORTD=0xf0;
  }
};
int main()
{
  led a;
  return 0;
}

出0入0汤圆

 楼主| 发表于 2010-3-3 12:56:27 | 显示全部楼层
3.配置工程。如下图

(原文件名:option.JPG)

点击option,进入工程选项。
然后在target页中设置如下:(默认的情况下,编译会报错,这个一定要改)

(原文件名:target.JPG)

出0入0汤圆

发表于 2010-3-3 13:01:30 | 显示全部楼层
mark

出0入0汤圆

 楼主| 发表于 2010-3-3 13:02:07 | 显示全部楼层
为了生成hex文件,我们还要改动上图中左侧linker------output页内容如下

(原文件名:linker.JPG)

出0入0汤圆

 楼主| 发表于 2010-3-3 13:09:52 | 显示全部楼层
4.然后,编译,按F7

生成的hex在工程文件夹\Debug\exe\1.hex
我们用proteus仿真一下!

这里只是演示,只放一个单片机,其IO口高低电平状态分别由红蓝方块显示。结果如图

(原文件名:pro.JPG)

这里显示B口电平状态为0xaa,代表我们的led类构造函数成功执行;
D口电平状态为0xf0,代表代码中return 0;结束时析构函数正确执行。

成功!

出0入0汤圆

发表于 2010-3-3 13:21:51 | 显示全部楼层
MARK

出425入0汤圆

发表于 2010-3-5 10:21:00 | 显示全部楼层
按zhaoyongke的方法,可以实现。现在深入探讨。在“project”-“edit configuration”,有“debug”和“release”选项。调试完成后是不是要选“release”生成最终的代码?

出0入0汤圆

 楼主| 发表于 2010-3-5 12:38:35 | 显示全部楼层
to:guolun

当你选择release之后,需要按照我上面的方法再次设置,hex文件可以换个名如2.hex。

编译后一样可以正常使用。看下图:

(原文件名:2hex.JPG)


(原文件名:1hex.JPG)

可以看出,debug版本生成的1.hex要比release版本生成的2.hex长,这是因为release版本去掉了调试信息。

出0入0汤圆

 楼主| 发表于 2010-3-5 12:45:34 | 显示全部楼层
注意生成的2.hex在工程文件夹\Release\Exe\

出0入0汤圆

发表于 2010-3-5 13:00:52 | 显示全部楼层
学习了

出0入0汤圆

发表于 2010-3-5 13:32:12 | 显示全部楼层
学习一下

出0入0汤圆

发表于 2010-3-5 14:00:10 | 显示全部楼层
标记

出425入0汤圆

发表于 2010-3-6 08:28:42 | 显示全部楼层
我觉得在studio调试程序很舒服,在IAR调试,没有那么直观。大家看看如何设置,让源代码在studio里面调试,就像GCC那样,那就爽啦。

出0入0汤圆

 楼主| 发表于 2010-3-6 11:56:55 | 显示全部楼层
解决了

选择工程时,注意下图选择AVR Studio 兼容模式

(原文件名:avrstudioproject.JPG)

编译,生成d90文件即可

(原文件名:output_d90.JPG)

然后打开AVR Studio
选择File --》Open
选择我们生成的d90文件,这时会提示保存工程文件,这个工程就是AVR Studio工程(.aps),如下图所示

(原文件名:save.JPG)

出0入0汤圆

 楼主| 发表于 2010-3-6 11:59:11 | 显示全部楼层
这时就可以用AVR Studio调试程序了!如图

(原文件名:tiaoshi.JPG)

出0入0汤圆

发表于 2010-3-6 12:55:54 | 显示全部楼层
学习了。。。。

出0入0汤圆

 楼主| 发表于 2010-3-6 20:51:43 | 显示全部楼层
#ifndef _kkk_1602_h
#define _kkk_1602_h
#include <usart.h>
class My1602
{
#define rs_0 (PORTC&=~0x04)
#define rs_1 (PORTC|=0x04)
#define rw_0 (PORTC&=~0x02)
#define rw_1 (PORTC|=0x02)
#define e_0 (PORTC&=~0x01)
#define e_1 (PORTC|=0x01)
#define comdir    (DDRC)
#define datadir   (DDRB)
#define dataread (PINB)
#define datawrite (PORTB)
public:
        My1602()
        {
                hang=1;
                datadir=0xff;
                comdir|=0x07;
                datawrite=0x00;
                PORTC&=~0x07;
                for(int i=0;i<80;i++)
                {
                        buffer=0x20;
                }
                        _delay_ms(3);
                        write_cmd(0x38);
                        _delay_ms(1);
                        write_cmd(0x38);
                        _delay_ms(1);
                        write_cmd(0x0e);
                        _delay_ms(1);
                        write_cmd(0x06);
                        _delay_ms(1);
        }
        ~My1602()
        {
//                DDRD=0x00;
//                DDRB&=~0x07;
//                PORTD=0x00;
//                PORTB&=~0x07;
        }
        void clear(void)
        {
                        write_cmd(0x01);
                        _delay_us(10);       
        }
        void setbuffer(const char *d)
        {
                int i;
                for(i=0;*d;i++,d++)
                {
                        buffer=*d;
                }
                for(;i<80;i++)
                {
                        buffer=' ';
                }
        }
        void showbuffer(void)
        {
                        write_cmd(0x01);
                        _delay_us(10);
                        for(int i=0;i<40;i++)
                        {
                                write_data(buffer);
                                _delay_us(10);
                        }
                        write_cmd(0x80+0x40);
                        for(int i=0;i<40;i++)
                        {
                                write_data(buffer[i+40]);
                                _delay_us(10);
                        }
        }
        int operator<<(int t)
        {
                char s[10];
                int2char(s,t);
                *this<<s;
                return t;
        }
        char * operator<<(char  *d)
        {
                char *t=d;
                while(*d)
                        {
                                if(*d=='\n')
                                {
                                        if(hang==1)
                                        {
                                                write_cmd(0xc0);
                                                hang=2;
                                        }
                                        else
                                        {
                                                write_cmd(0x80);
                                                hang=1;
                                        }
                                        d++;
                                        continue;
                                }
                                write_data(*d++);
                        }
                return t;
        }
        void left(void )
        {
                write_cmd(0x05);
                {                       
                        write_cmd(0x1c);
                        _delay_ms(300);
                }       
        }
        void right(void)
        {
                write_cmd(0x05);
                {                       
                        write_cmd(0x18);
                        _delay_ms(300);
                }
        }
private:
        void write_cmd(unsigned char c)
        {
                rs_0;
                rw_0;
                datadir=0xff;
                datawrite=c;
                e_1;
                _delay_us(1);
                e_0;
        }
        void write_data(unsigned char d)
        {
                rs_1;
                rw_0;
                datawrite=d;
                e_1;
                _delay_us(1);
                e_0;
        }
        unsigned char buffer[80];
        unsigned char hang;
};
#endif

出0入0汤圆

发表于 2010-3-6 22:37:50 | 显示全部楼层
标记

出0入0汤圆

发表于 2010-3-6 23:53:25 | 显示全部楼层
学习了,谢谢!

出0入0汤圆

发表于 2010-3-8 15:03:16 | 显示全部楼层
标记下

出0入0汤圆

发表于 2010-3-8 15:47:15 | 显示全部楼层
标记

出425入0汤圆

发表于 2010-3-17 18:38:11 | 显示全部楼层
最近很忙,也抽时间学习钱能的C++课程。还没有入门呢。

出0入0汤圆

发表于 2010-3-20 12:50:10 | 显示全部楼层
Just Mark

出0入0汤圆

发表于 2010-3-20 13:59:01 | 显示全部楼层
MARK,,DING...

出0入0汤圆

发表于 2010-4-23 19:23:17 | 显示全部楼层
mark

出0入0汤圆

发表于 2010-4-23 21:03:49 | 显示全部楼层
mark

出0入0汤圆

发表于 2010-4-23 21:10:32 | 显示全部楼层
学习

出0入0汤圆

发表于 2010-4-23 21:16:31 | 显示全部楼层
mark,学习。。。。

出0入0汤圆

发表于 2010-4-24 13:55:14 | 显示全部楼层
mark

出0入0汤圆

发表于 2010-5-4 11:41:08 | 显示全部楼层
学习了。

出0入0汤圆

发表于 2010-5-4 14:59:22 | 显示全部楼层
mark

出0入0汤圆

发表于 2010-5-5 12:19:45 | 显示全部楼层
学习了

出0入0汤圆

发表于 2010-5-5 12:24:13 | 显示全部楼层
mark

出0入0汤圆

发表于 2010-6-2 17:14:10 | 显示全部楼层
强帖留名

出0入50汤圆

发表于 2010-6-3 11:30:38 | 显示全部楼层
mark

出0入0汤圆

发表于 2010-6-3 11:52:23 | 显示全部楼层
学习。。

出0入0汤圆

发表于 2010-6-3 13:26:11 | 显示全部楼层
非常棒,谢谢楼主。

出0入0汤圆

发表于 2010-6-3 13:59:57 | 显示全部楼层
ding

出0入0汤圆

发表于 2010-6-4 10:28:58 | 显示全部楼层
mark!

出0入0汤圆

发表于 2010-6-5 11:07:20 | 显示全部楼层
mark!

出0入0汤圆

发表于 2010-6-5 11:15:44 | 显示全部楼层
good idear...

出0入0汤圆

发表于 2010-6-5 16:29:45 | 显示全部楼层
正在找这方面的。谢谢。

出0入0汤圆

发表于 2010-6-5 19:12:19 | 显示全部楼层
真是挺厉害

出0入0汤圆

发表于 2010-6-5 19:33:37 | 显示全部楼层
mark 一下,最近学习C++

出0入0汤圆

发表于 2010-6-5 19:59:04 | 显示全部楼层
不错!

出0入0汤圆

发表于 2010-6-5 20:07:35 | 显示全部楼层
不错!
回帖提示: 反政府言论将被立即封锁ID 在按“提交”前,请自问一下:我这样表达会给举报吗,会给自己惹麻烦吗? 另外:尽量不要使用Mark、顶等没有意义的回复。不得大量使用大字体和彩色字。【本论坛不允许直接上传手机拍摄图片,浪费大家下载带宽和论坛服务器空间,请压缩后(图片小于1兆)才上传。压缩方法可以在微信里面发给自己(不要勾选“原图),然后下载,就能得到压缩后的图片】。另外,手机版只能上传图片,要上传附件需要切换到电脑版(不需要使用电脑,手机上切换到电脑版就行,页面底部)。
您需要登录后才可以回帖 登录 | 注册

本版积分规则

手机版|Archiver|amobbs.com 阿莫电子技术论坛 ( 粤ICP备2022115958号, 版权所有:东莞阿莫电子贸易商行 创办于2004年 (公安交互式论坛备案:44190002001997 ) )

GMT+8, 2024-4-28 06:48

© Since 2004 www.amobbs.com, 原www.ourdev.cn, 原www.ouravr.com

快速回复 返回顶部 返回列表