我正在尝试使用带有 ATmega32U4 的 Serial.write(buff,len) (通过 USB 虚拟串行端口)发送一堆数据。我最初使用 LUFA 编写了我的应用程序,并且效果很好。但是,我现在将它移植到 Arduino 并且它正在丢弃数据。
相关代码是
void uartTask() {
static unsigned long timer = 0;
if (Serial) { // does the data have somewhere to go?
uint16_t ct = RingBuffer_GetCount(&serialBuffer);
unsigned long curTime = millis();
if (ct > 64 || (timer-curTime > 100)) { // is there data to send?
timer = curTime;
if (serialBuffer.Out + ct <= serialBuffer.End) { // does it loop in our buffer?
ct = Serial.write(serialBuffer.Out, ct); // dump all the date
serialBuffer.Out += ct;
if (serialBuffer.Out == serialBuffer.End)
serialBuffer.Out = serialBuffer.Start; // loop the buffer
}
else { // it looped the ring buffer
uint8_t* loopend = serialBuffer.Out + ct;
uint16_t ct2 = loopend - serialBuffer.End;
uint16_t ct1 = ct - ct2;
uint16_t ct1s = Serial.write(serialBuffer.Out, ct1); // dump first block
if (ct1s == ct1) {
ct2 = Serial.write(serialBuffer.Start, ct2); // dump second block
serialBuffer.Out = serialBuffer.Start + ct2; // update the pointers
ct = ct1+ct2;
}
else {
ct = ct1s;
serialBuffer.Out += ct;
}
}
uint_reg_t CurrentGlobalInt = GetGlobalInterruptMask();
GlobalInterruptDisable();
serialBuffer.Count -= ct; // update the count
SetGlobalInterruptMask(CurrentGlobalInt);
}
if (RingBuffer_GetCount(&serialBuffer) < 256) {
SET(TX_BUSY, LOW); // re-enable the serial port
serialRXEnable();
}
int16_t w;
while ((w = Serial.read()) >= 0) {
Serial_SendByte(w);
}
}
}
ISR(USART1_RX_vect) { // new serial data!
RingBuffer_Insert(&serialBuffer, UDR1 ); // save it
if (serialBuffer.Count > 1000) // are we almost out of space?
SET(TX_BUSY, HIGH); // signal we can't take any more
if (serialBuffer.Count > 1020)
serialRXDisable(); // if our flag is ignored disable the serial port so it doesn't clog things up
}
我在 LUFA 中使用了几乎相同的代码,它从不丢失数据。我在我的电脑上运行 Ubuntu。
这基本上只是一个 USB 到串行转换器。当串行数据到达时,它会触发将数据放入环形缓冲区的中断,该缓冲区稍后会被读取并通过 USB 发送。
我不明白为什么基于 LUFA 的代码可以工作,但 Arduino 却不行。我认为检查 Serial.write() 的返回值会让你知道你的数据是否没有成功。
有什么想法吗?