51单片机在读取IO口数据前如果没有加一个高电平(0xff),那么对没有上拉电阻的IO口可能有什么影响? 100
准确地说,我是从2012年的秋天开始接触DS1302这个芯片的。时年大四,正在做电子专业的专业实习。我们的题目是“智能家居”,其中用到了DS1302这个芯片。当时做下来只是知道了这个东西是干什么用的,至于怎么用,可以说是完全没弄明白。但当时在网上找了相关的资料,也下载了一些前辈写的程序,当时扔到Proteus上去仿真,大概知道了改哪条语句可以实现什么功能什么的。时隔一年以后,已经是毕业的人了。刚刚到公司报道,工作还比较闲,晚上或周末就有时间学点电路什么的,就又把DS1302翻了出来。这期间买了IC和关键的32.768kHz的晶振。于是就把电路给搭了出来。这次算是一次入门,虽然没能完全搞透,但知道了以下几点:
1.DS1302的驱动分为往里写和往外读;
2.片内集成了一部分RAM,这部分内容是不受晶振影响的;个人观点,这部分应用很鸡肋。
3.往里写数据和往外读数据的时候,IO口方向(input或output)是不同的:在写数据的时候是先发8位的地址位,再发8位的时间信息(或将要写入RAM的内容),此过程中,IO口方向一直是output。而读数据时,同样也是要先发8位的地址位,但之后要将IO口状态改为input,这时将开始允许从DS1302传来信息。这里我只是说允许信息过来,而不是说接收信息,因为信息是一位一位传过来的,要加以整理并储存下来才算是接受,这是软件对应上的事情,但不考虑这些的话,至少此时是有信息过来的,只是你如何读取并保存的问题。
最近斥资2000元添购了我人生的第一台示波器。要说示波器大家都很熟悉,学电的没有没用过的。但有自己的示波器的人恐怕不多。为什么要强调一下是“我”的示波器呢,这里不免啰嗦几句,谈谈我对中国现行教育的一点看法。
我的大学后半程算是在专业知识上下了些工夫的。这从我两届大学生电子设计竞赛和优秀毕业设计等荣誉上可以验证。当然,我现在仍要本着学习的态度在这个行业里发展自我,但我认为我在大学里接受到的专业技能方面的资源肯定是大于其他同学的,我经常出入实验室,示波器,函数发生器也总用,但都是在老师的指导下使用,老师说这个东西要测一下,就去测。至于如果想做一些自己想做的实验,总是觉得不是很方便。我的母校在我大二的时候,将模电实验室的示波器全部更新成数字示波器,这些示波器在高校中应该说算数一数二了,但很遗憾,在实验课之外,这些家伙鲜有人问津。
近几年我的母校有了很多的课外实践活动,老师和同学们都开始热衷做项目。也有相当的一部分实验资源被共享出来。这是好事。但对于学生来说,不可一味地埋头在一个项目中,要挑起头做实验,广泛地涉猎,而老师要做的就是引导。
闲话至此。买了示波器以后做的第一个实验是TDA2030功率放大器的性能测定。发现了不少问题,由于本篇主要讲DS1302,所以暂不总结关于TDA2030的东西。第二个实验就是观测DS1302的通讯波形。这次终于让我搞懂了它。以下为DS1302的学习心得:
通过示波器观察通讯信号的波形是一种必要的手段,尤其是当电路不能正常工作的时候。不能正常工作首先可以去判断硬件方面是不是OK。一些论坛上有人认为晶振不起振是硬件的问题,个人认为并非是这样。举个例子:用DS1302与某单片机连接,为单片机烧写给DS1302写入时间信息的软件,正常动作以后,改烧写只能读数据的软件,(此过程中DS1302一直有电)发现也可正常读数,但给DS1302断电再上电,却发现不能正常读数。用万用表测晶振两端电压,应该是一端为高电平一端为低电平,证明晶振没有起振吗?是和晶振两端的电容有关吗?
晶振这里没有起振是显然的,但却不一定是硬件的问题。上例中重新上电以后,单片机没有执行给DS1302写入命令的指令,也就造成DS1302上秒寄存器的最高位可能不是0,这一位决定了DS1302是计数还是暂停,为1的话,DS1302是不计数的。当然,是否确实如此还需验证。关于晶振还有就是其两端电容究竟用多大,有的资料写用6pF,有的说用30pF,还有说可以不用的。后两种我没试过,第一种是OK的。另两种会再以后确认一下是否可以。这里有一点,匹配的电容和走时的精准度是有关系的。这里不要妄信一些论坛上是一些人说什么晶振质量不好,什么芯片质量不好的混话。
我测了一下晶振一端的波形,如下图
图1 DS1302晶振一侧波形(1通道)
没有示波器的话用万用表量也可以,电压值是多少并不是关键问题,主要是晶振两端对地的电压如果相等,那么基本可以断定晶振是正常工作的。这也说明,在软件方面,至少写秒寄存器这部分是OK的。
可能还有人会纠结上拉电阻的问题。有的电路图上三条通信线RST(也称OE)、SDA和CLK都有上拉电阻(10k左右),有的就只是在SDA线上加了上拉电阻。这里建议大家去研究研究IO口的输入输出状态相关的知识(可以参照本博客中另一篇关于STC12C5410学习笔记的文章,本文不再赘述)。只说一句,现在除了89C51、89C52这种很入门级的单片机,基本都可以通过设定相应的寄存器去控制各个IO口的状态。由于RST和CLK这两条线对单片机来说都是输出线,这样一般都会将这两个IO口设定成内部上拉的模式,所以一般外部就不用再加电阻了。但SDA不同,以为读和写数据时,SDA的IO口方向一个是输入一个是输出,输出的话也是用内部上拉模式,但输入的话一般会选择高阻模式,此时没有内部上拉电阻,所以要外接一个上拉电阻来给DS1302这边提供高电平和电流。这个上拉电阻不要太小,我试过加120Ω的上拉电阻,在51单片机上运行,波形完全走样。但在arduino上运行似乎还好。原因有可能是两者IO口低输出时的对地等效电阻不同。很多资料上都是用的10kΩ的上拉电阻,我测试后也是好用的。
本文中的测试波形都是在arduino平台上测试得到的,arduino有个好处就是有个很方便的串口查看器,在电脑上可以轻松读取串口上送多来的信息。但好像目前在工业上的应用很有限,尤其是国内,主要是一些年轻的电子爱好者或一些搞机械或者搞美术的创客们用的多一点。它就是可以设定IO口方向的。但文本给出的程序代码主要是基于51单片机的,而且是89C52这种不带IO方向设定功能的。原因就是我也很想搞清楚没有IO口方向控制时,单片机怎么区分输出和输入的操作。我会一边测试一边写这篇笔记。首先来看看正常工作的波形是什么样的:
图2 读取一次完整时间信息的波形(SDA和CLK)
图2所示是读取一次完整时间信息的SDA和CLK的波形。通道1表示SDA,通道2表示CLK,从左至右可以看出CLK明显被分成7份,这些依次代表对秒、分、时、日、月、星期、年这7个信息读取时的CLK,对应的通道1是SDA(数据)信息。注意,这里都是读操作。我将读取秒的那部分波形展开,如图3.
图3 秒信息读取的时序图