我试图看看这是否更简单。我正在做的是在一个8051微控制器中制作四个UART,其中每个UART都禁止发送,并且每个UART的接收分别通过光电晶体管在端口P0.0到P0.3上进行检测(想想这里的无线)。
为了使这个东西可靠,我觉得我需要多次对端口进行采样以获得正确的数据。我相信8051设置,如果我使用其硬件UART,它会自动采样16x或32x波特率。
下面我的代码在对数据进行采样时做得很好,但问题是它很慢,而且我认为可能有更快的方式用某种布尔运算符对数据进行采样?
这是我的代码:
SAMPLE equ P0 ;port to sample incoming data
MAJ equ 40h ;Where to store majority counts
MAJT equ 20h ;Majority track byte. Were interested in MSB
SCANRATE equ 4h ;# times to scan data before processing it
timer_interrupt:
mov A,SAMPLE ;get sample of data
mov R1,#MAJ
next:
rrc A ;get one bit of sampled data
jnc noincmaj
inc @R1 ;add 1 to that specific bit counter if bit=1
noincmaj:
jc incmaj
dec @R1 ;subtract 1 from that specific bit counter if bit=0
incmaj:
inc R1 ;use next bit counter#
cjne R1,#MAJ+4h,next
;loop ends when desired bit counter# is 5 (we only sample 4 bits)
djnz R7,noprocess
mov R0,#MAJ+3 ;Start at end of data since MSB feeds into value 1st
nextbit:
mov MAJT,@R0 ;Get count of bit counter
mov @R0,#0h ;and clear count
mov C,MAJT.7 ;If count < 1 then bit is set otherwise its cleared
rlc A ;shove result into resulting byte
dec R0 ;go to previous bit counter
cjne R0,#MAJ-1,nextbit ;continue until all bit counters are done
;Accumulator has scanned value
mov R7,#SCANRATE
noprocess:
reti
这是我想要实现的想法的代码模板:
timer_interrupt:
mov R6,SAMPLE ;get sample of data
mov A,OLDDATA
; some_logical_operator_here_on_R6?
mov OLDDATA,A
djnz R7,noprocess
mov A,OLDDATA
;Accumulator has scanned value
mov R7,#SCANRATE
noprocess:
reti
所以我的问题是,使用比我发布的第一个时钟周期少的时钟周期的代码,如何在SCANRATE扫描之后确定在大多数扫描之后是否设置了一个字节中的特定位?/ p>
作为一个具体的例子,我想要问的是,如果SCANRATE是5,并且进入的值按顺序如下:
01010101
11111111
11110000
00001111
11001100
然后我希望最终结果(在设置R7之前)为:
11011101
那么,如果不使用上面的第一个代码,为8051处理器实现这一目标的更简单方法是什么?