gpt4 book ai didi

java - 使用 RXTX 和 Java 继续与串行设备通信

转载 作者:行者123 更新时间:2023-11-30 11:38:09 24 4
gpt4 key购买 nike

我需要修改 RXTX“基于事件的双向通信”(参见 http://rxtx.qbang.org/wiki/index.php/Event_based_two_way_Communication),以便我能够将关于其先前消息的特定响应写回串行设备。

我通过发送第一个命令开始通信。到目前为止一切正常。现在我从串行设备得到了答案。我用进一步的命令对答案使用react。但是我不能再写了,因为写线程已经结束了。

有人知道如何处理这个吗?非常感谢!

public class TwoWaySerialComm {
public TwoWaySerialComm() {
super();
}

public static void main(String[] args) {
try {

// 0. call connect()
(new TwoWaySerialComm()).connect("COM1");

} catch (Exception e) {
e.printStackTrace();
}
}

void connect(String portName) throws Exception {

// 1. get CommPortIdentifier, open etc...

// 2. then do
InputStream in = serialPort.getInputStream();
OutputStream out = serialPort.getOutputStream();

// 4. start writer thread
(new Thread(new SerialWriter(out))).start();

// 5. instantiate SerialReader
serialPort.addEventListener(new SerialReader(in));
serialPort.notifyOnDataAvailable(true);

}

public static class SerialWriter implements Runnable {

OutputStream out;

public SerialWriter(OutputStream out) {
this.out = out;
}

public void run() {
try {

// establish a communication by sending the first command. the serial device will answer!
String toSend = "blablabla";
this.out.write(toSend);

// thread ended???

}

public static class SerialReader implements SerialPortEventListener {

private InputStream in;

public SerialReader(InputStream in) {
this.in = in;

}

public void serialEvent(SerialPortEvent arg0) {

// event occurs beacause device answers after writing.

int data;

try {

StringBuffer sb = new StringBuffer();
String LineOfData=null;

while ((data = in.read()) > -1) {

if (data == '\n') {
break;
}

sb.append(Integer.toHexString(data));
LineOfData = sb.toString();

}
// I store the answer and send it to an EventIterpreter. Regarding the answer, it creates an appropriate response itselves.
EventInterpreter e = new EventInterpreter(LineOfData);
String result = e.getData

HERE >> // Now I want to send this response back to the device. But the thread is already ended.


} catch (IOException e) {
e.printStackTrace();
System.exit(-1);
}
}

}

}

最佳答案

不要让运行 SerialWriter 的线程完成。

在原始示例中,您会注意到 run() 方法中有一个 while (System.in.read() != -1) SerialWriter。这很重要。运行它的线程在 read()阻塞,然后,一旦它有一些数据要读取,它就会做一些工作,然后循环回来到同一个地方,等待更多的输入。这是一个不应该在正常情况下完成的线程。

至关重要的是,作者的非守护线程正在运行这一事实意味着,当您的主线程(JVM 用于启动程序的线程)用完 connect() 方法中的语句时,JVM 不会立即关闭。

串口在它自己的线程上给你回电话

serialPort 调用监听器的 public void serialEvent(SerialPortEvent) 方法时,它会在自己的线程上执行此操作

您现在的任务是尽快离开串行端口的线程。基本上,读取数据,将其保存在缓冲区中,您的另一个线程可以在缓冲区中随意解析和处理它,同时让 serialPort 继续处理通信。当它在自己的线程上调用你时,你当然不应该尝试写入串行端口。它没有回复你的状态,因为它在等你完成!

您希望“作者”线程“等待”,直到有内容要回复

您可以通过提供“锁定”对象来安排它。由于现在是现代,请使用:

import java.util.concurrent.locks.*;

// accessible to both reader and writer
...
Lock lock = new ReentrantLock();
Condition dataAvailable = lock.newCondition();
byte[] buffer;

// in the writer
...
public void run() {
while(true) {
lock.lock();
try {
dataAvailable.await(); // writer thread dozes
doStuff(buffer);
} finally {
lock.unlock();
}
}
}


// in the reader
...
public void onEvent() {
lock.lock();
try {
buffer = readData();
dataAvailable.signal(); // writer thread wakes up
} finally {
lock.unlock();
}
}

读一本关于并发的好书

并发是棘手的。你会想读 Java Concurrency in Practice .

当您尝试剪切'n'粘贴上面的代码示例时,您会注意到 Condition#await() 抛出 InterruptedException。具体如何处理超出了这个答案的范围。 :-) while(true) 也有点狡猾。

关于java - 使用 RXTX 和 Java 继续与串行设备通信,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13724740/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com