打印

已结贴:单片机IO口问题!(和客户讨论的我都快晕死了!)

[复制链接]
4247|17
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
pian_zhou|  楼主 | 2007-7-20 19:03 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
该讨论已经结贴:对话内容已删除!
感谢楼下各位兄弟的讨论和回帖!

这是关于C8051F单片机的IO口输入输出的问题,虽然看起来很简单,但实际上还是有一些小细节,设计时仍要注意。

结论:
1)如果采用推挽输出,则getio的结果总会是setio的值,不能如实反应外部实际状态。
2)如果采用内部弱上拉的开漏输出,则getio前,必须进行setio将端口锁存器置1,或者保证之前setio已经置为了1状态。
   所以最好还是需要一个设置输入输出方向的函数控制。



------------------------
这两天跟一个客户讨论单片机的IO口输入输出问题。
(我开发的一款产品,客户邮件咨询。)
我的解释他总认为不对,大家帮我看看。
我都快晕死了!
大家帮我看看,难道我是真的错了吗?或者我该如何向对方解释?
注:是通过PC软件控制单片机的IO口
    setio函数给IO口赋值,输出操作。
    getio函数获取IO状态。




附:MCU驱动能力图和内部IO结构图






相关帖子

沙发
computer00| | 2007-7-20 19:18 | 只看该作者

按照你最后的回复,你们的IO就不是推挽输出的

至少不是强推挽输出的,也就是说, 输出能力不是很强.


像AVR那样的单片机,是推挽输出的. 如果它输出高,你外面硬是要拉低, 或者它要输出低,
你硬是要拉高,则会导致电流很大,甚至烧毁IO口. 所以它有一个方向控制,当作为输入口
使用时,断开推挽输出. 否则,别人就很难驱动它,也就失去了最输入口的意义。通常来说,
一个输入口输入阻抗越大越好. 理想的IO口,输入阻抗应该是无穷大,就像你前面所说的,
即便是10K的电阻,也能照样驱动它,这样才是理想的IO口。而不是象你所说的,驱不动。


因此你的客户是对的,应该有一个设置方向的配置,设置为输入状态. 除非你们的MCU
比较特殊,高低电平的输出能力都很弱,就可以直接由外部强制拉高或者拉低.

使用特权

评论回复
板凳
ayb_ice| | 2007-7-20 19:20 | 只看该作者

IO有那么难吗...

51自成一体系,没有方向设置,输入前置1再读即可...
其它一般有IO方向寄存器,有方向寄存器,输出寄存器和输入寄存器,使用前设置方向,如一直是输入或输出则只需设置一次即可...

使用特权

评论回复
地板
computer00| | 2007-7-20 19:27 | 只看该作者

事实上,51的将IO置1这个步骤,就已经相当于操作IO口方向了.

使用特权

评论回复
5
hotpower| | 2007-7-20 19:33 | 只看该作者

被客户忽悠了~~~IO做输入就不敢再做输出控制

如果输出LED显示这样"不关人命"的设计是允许的~~~

使用特权

评论回复
6
pian_zhou|  楼主 | 2007-7-20 19:38 | 只看该作者

对2楼 computer00兄弟的回复

对2楼 computer00兄弟的回复:

1.单片机的IO口,软件操作时是不需要专门进行方向控制的。
2.如果外部给VCC,IO口输出低,或者相反的情况下,实际输出状态会不受控。IO口一般也不会烧毁,内部有保护电路。


对5楼hotpower兄弟的回复:

谢谢支持啊,虽然是这么简单的问题,我真的是被整晕了。

注:客户是说想输出控制一个LED指示灯。


使用特权

评论回复
7
gyt| | 2007-7-20 19:53 | 只看该作者

很有意思

使用特权

评论回复
8
computer00| | 2007-7-20 20:01 | 只看该作者

哎....看来你还是没有开窍...

使用特权

评论回复
9
pian_zhou|  楼主 | 2007-7-20 20:08 | 只看该作者

我晕!

我晕倒!
其实computer00在4楼的回答才到点子上了!

--------
computer00 发表于 2007-7-20 20:01 侃单片机 ←返回版面    
8楼: 哎....看来你还是没有开窍... 

使用特权

评论回复
10
古道热肠| | 2007-7-20 20:10 | 只看该作者

弱上拉,强上拉要分清

    建议仔细PDF来问,大喊大叫能解决问题吗?

使用特权

评论回复
11
conwh| | 2007-7-20 20:14 | 只看该作者

这个问题很难

使用特权

评论回复
12
computer00| | 2007-7-20 20:30 | 只看该作者

在这个图中,端口输出使能就是控制IO方向的

在作为输入使用使,必须将端口使能无效.

另外,如果将推挽设置为无效,则就变成了漏极开路输出的形式,这个跟51的P0口一样.
如果再将弱上拉打开,就跟51的P1口一样了。在这两种情况下可以通过往端口写1变成输入模式.


另外,下面那个带史密特整形功能的三态门连法有点怪,怎么两个输入端连在一块,
又没其它控制线???

使用特权

评论回复
13
pian_zhou|  楼主 | 2007-7-20 20:42 | 只看该作者

圈圈看的很仔细啊!

    圈圈看的很仔细啊!

    图片已经被更新!

    因为该IO口也可被用做模拟采样通道。所以你说的这条信号线是有一个输入的。就是模拟和IO口的工作方式选择。
    我们事先会将此IO口配置成数字IO方式,而且配置成推挽输出方式。
    这都是我们的单片机固件程序已经做好了的。
    客户是通过PC的接口函数(通过USB口)使用setio和getio两个函数来写读IO。

使用特权

评论回复
14
567| | 2007-7-20 20:54 | 只看该作者

既然你已经把数字IO配置成了推挽输出方式

既然你已经把数字IO配置成了推挽输出方式,那么你的getio函数就一点用没有了,读入的就是输出值。

使用特权

评论回复
15
computer00| | 2007-7-20 21:01 | 只看该作者

恩,正如楼上所说.

如果要能做输入口的话,就必须再提供一个函数,就是设置为输入口或者输出口的函数。

除非该系统仅做输出使用,不做输入使用. 例如只驱动LED显示,而不做键盘扫描输入等功能.
那就可以不用改为输入口.

使用特权

评论回复
16
pian_zhou|  楼主 | 2007-7-20 22:01 | 只看该作者

楼上的意思,这是推挽方式的局限性,是吗?

我仔细分析了一下,我们的设计的确存在缺陷。

初步结论:
1)如果采用推挽输出,则getio的结果总会是setio的值,不能如实反应外部实际状态。
2)如果采用内部弱上拉的开漏输出,则getio前,必须进行setio置1,或者保证之前setio已经置为了1状态。


14楼,15楼的说法应该是比较准确。
感谢!
谢谢各位的讨论!

-----------------------------
既然你已经把数字IO配置成了推挽输出方式,那么你的getio函数就一点用没有了,读入的就是输出值。

使用特权

评论回复
17
bh_wang| | 2007-7-21 09:25 | 只看该作者

RE:

Read - Always reads ‘0’ if selected as analog input in register P0MDIN. Directly reads Port pin when configured as digital input.

使用特权

评论回复
18
ayb_ice| | 2007-7-21 10:18 | 只看该作者

随便说说

C8051F的IO使用和标准51差别不大。。。
如果IO被配置成模拟IO口,则读写没有意义(不要去读写)。。。
配置成数字IO,则有推挽(20MA),标准(弱上拉)之分,推挽只是输出能力强,注意输出1时不能直接短路,另外弱上拉电路可以被(整体)禁止。。。
最新的如412系列IO电压可以和CPU内核电压不同(独立)。。。
这就C8051F的IO功能,本人使用C8051F已经几年了。。。

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

25

主题

90

帖子

0

粉丝