2012-09-17 101 views
1

我在使用两个带有arduino板的软件串行端口从两个传感器获取数据时遇到了问题。我注意到一个类似的问题可能之前已经问过,但答案表明它不能完成,我完全清楚它可以基于这里的示例(http://arduino.cc/en/Tutorial/TwoPortReceive)!在Arduino上使用软件串口接收两个端口

我正在使用arduino以太网。我试图从中获取数据的设备包括来自sparkfun的GPS和IMU。

我可以从任何设备上使用软件串行端口获取数据,但只要添加第二个软件串行端口,两个端口都不会工作。我无法使用硬件串行端口,因为它正在被其他设备使用。

我的代码是完全同样的例子:

#include <SoftwareSerial.h> 

SoftwareSerial portOne(7,8); 
SoftwareSerial portTwo(5,6); 

void setup() 
{ 
    Serial.begin(9600); 


    portOne.begin(9600); 
    portTwo.begin(9600); 
} 

void loop() 
{ 

    portOne.listen(); 
    while (portOne.available() > 0) { 
    char inByte = portOne.read(); 
    Serial.write(inByte); 
    } 

    delay(500); 

    portTwo.listen(); 
    while (portTwo.available() > 0) { 
    char inByte = portTwo.read(); 
    Serial.write(inByte); 
    } 

    Serial.println(); 
} 

有任何想法吗?

+0

灿你给我们提供了有关它不起作用的更多信息吗? – Jeff

+0

我以某种方式得到它的工作,你必须设置引脚状态,即接收引脚作为输入和传输引脚作为输出。 – Dyps

回答

1

引用的示例一次只能主动监听一个端口。推荐的解决方案是升级到具有4个硬件串行端口的Arduino Mega(https://www.sparkfun.com/products/11061)。

为了同时支持两个软件串口需要大量的CPU资源。这也是一个困难的设计和过多的编程时间,远远超过58美元+运输的成本。

再次看着你的代码,我发现你立即检查你的portOne.listen命令后的字符。在9600波特时,第一个字符到达需要大约1ms,你的while测试已经完成,并且portTwo.listen命令在第一个字符到达之前就已经执行了。

出于测试目的,请尝试在portOne.listen命令之后添加1-2 ms的延迟并查看是否有字符。

作为一个例子(未经测试和注意,如果端口的一个不与任何字符间的间隙发送的字符,所述第一而永远不会失败,防止读取portTwo字符):

void loop() 
{ 

    portOne.listen(); 
    delay(2); 
    while (portOne.available() > 0) { 
     char inByte = portOne.read(); 
     Serial.write(inByte); 
     delay(1); 
    } 

    portTwo.listen(); 
    delay(2); 
    while (portTwo.available() > 0) { 
     char inByte = portTwo.read(); 
     Serial.write(inByte); 
     delay(1); 
    } 
    Serial.println(); 
} 
+0

你是说,上面的代码不起作用?我一次只能在一个端口上收听。 – Dyps

+0

我应该说我没有试过这样做。只要你打开端口1,接收数据,关闭端口1,打开端口2,接收数据,关闭端口2,然后重复,我就会工作。它仍然会使用更多的微型资源,然后使用两个硬件端口,但取决于微载和其他固件,这可能不是问题。 – Jeff

3

此代码将无法正常工作,或如果它工作的话,它的效果会很差。 SoftwareSerial只有一个内部缓冲区。是的,您可以拥有多个SoftwareSerial对象,但其中只有一个控制内部缓冲区。当任何RX引脚被置位时,会产生一个中断,但只有listen()的RX引脚被检测到一个起始位。

真正需要的是在中断从起始位出现时检查多个引脚的能力。然后你必须设置指向适当数据结构的指针。这将是复杂的,但可能的。或者只是放弃中断驱动的接收,然后旋转检查两个/所有的RX引脚,然后根据您看到的引脚开始接收。应该警告说,这段代码有很多头发,你需要一台示波器才能使它工作。

我有类似的问题,这就是为什么我找到了你的传感器。在与我的同事交谈之后,我们决定按循环顺序阅读我们的传感器。我们的传感器报告传感器的当前状态,而不是特定的事件,所以如果我们丢失了一些报告就没关系。因此,我们将从端口1读取数据,然后从端口2读取数据,然后从端口1读取数据。我们的传感器会吐出一行文字,因此我们知道何时切换到下一个传感器。

+1

感谢您的回答。您能否提供一些代码来演示您的旋转订单概念? – Dyps

0

不要使用,而......

用途:

{  portOne.listen(); 

    if (PortOne.available()) { 
     ricevo = myPort1.read(); } 

    // delay(2); // ridiculos waiting time 
    // delay(1); // extra ridiculos waiting time 

超过500毫秒是一个太大的时间切换,没有时间.....