我試圖運行一個串行通信示例,以便將數據從Arduino發送到可提供的代碼http://playground.arduino.cc/Interfacing/Cocoa(IOKit/ioctl方法)中的可可應用程序。它可以工作,但是一旦啓動,我無法停止接收器線程。如何關閉可可後臺線程中的串行通信
我已經實現了一個開關按鈕(開始/停止),其在啓動時打開串行端口並啓動接收器線程:
- (IBAction) startButton: (NSButton *) btn {
(…)
error = [self openSerialPort: [SelectPort titleOfSelectedItem] baud:[Baud intValue]];
(…)
[self refreshSerialList:[SelectPort titleOfSelectedItem]];
[self performSelectorInBackground:@selector(incomingTextUpdateThread:) withObject:[NSThread currentThread]];
(…)
}
線程代碼實際上是相同的如示例中,除了我所包含的代碼從接收緩衝區重建串行數據包並將其保存到一個SQLite數據庫:
- (void)incomingTextUpdateThread: (NSThread *) parentThread {
// mark that the thread is running
readThreadRunning = TRUE;
const int BUFFER_SIZE = 100;
char byte_buffer[BUFFER_SIZE]; // buffer for holding incoming data
int numBytes=0; // number of bytes read during read
(…)
// assign a high priority to this thread
[NSThread setThreadPriority:1.0];
// this will loop until the serial port closes
while(TRUE) {
// read() blocks until some data is available or the port is closed
numBytes = (int) read(serialFileDescriptor, byte_buffer, BUFFER_SIZE); // read up to the size of the buffer
if(numBytes>0) {
// format serial data into packets, but first append at start the end of last read
buffer = [[NSMutableString alloc] initWithBytes:byte_buffer length:numBytes encoding:NSASCIIStringEncoding];
if (status == 1 && [ipacket length] != 0) {
[buffer insertString:ipacket atIndex:0];
numBytes = (int) [buffer length];
}
ipacket = [self processSerialData:buffer length:numBytes]; // Recompose data and save to database.
} else {
break; // Stop the thread if there is an error
}
}
// make sure the serial port is closed
if (serialFileDescriptor != -1) {
close(serialFileDescriptor);
serialFileDescriptor = -1;
}
// mark that the thread has quit
readThreadRunning = FALSE;
}
我嘗試關閉該端口在主線程中使用此代碼,也startButton選擇的一部分,遵循提供的示例:
if (serialFileDescriptor != -1) {
[self appendToIncomingText:@"Trying to close the serial port...\n"];
close(serialFileDescriptor);
serialFileDescriptor = -1;
// Revisar... crec que el thread no s'adona que s'ha tancat el file descriptor...
// wait for the reading thread to die
while(readThreadRunning);
// re-opening the same port REALLY fast will fail spectacularly... better to sleep a sec
sleep(0.5);
//[btn setTitle:@"Start"];
[Start setTitle:@"Start"];
}
但似乎接收線程不知道全局變量serialFileDescriptor中的狀態變化。
它是否向您發送人類可讀的純文本或某種二進制數據? NSString及其後代只能用於前者;如果你正在閱讀後者,你應該使用NSMutableData。 – 2013-02-19 20:39:24
此外,假設你的'buffer' /'ipacket'舞蹈是爲了做我認爲正在做的事情,還有更有效的方法來做到這一點。看看'appendString:'或'appendData:'。 – 2013-02-19 20:46:04