Serial port parity change

Hi Gents,

I am new to this so do pardon me if this question has been asked a million times before...

Basically, I am using a Mega to control numerous serially controlled modules (OSDs, DVR, etc) and I am new to the Arduino family, and wanted a quick tip on how to change the parity of individual ports? I need to change Serial1 to 38400, odd parity, and I think the standard setting is None.

Any help is much appreciated.

See section 22.3 of the ATmega 1280/2560 for background.
See section 22.9.4: UCSRnC – USART Control and Status Register n C

Bits 4 and 5 of register UCSRnC control parity: 0b00=none, 0b10 = Even, 0b11 = Odd

For Serial, Serial1, Serial2, and Serial3 that would probably be: UCSR0C, UCSR1C, UCSR2C, UCSR3C

Serial.begin(9600);
UCSR0C = (UCSR0C & 0xCF) | (0b10 << 4);  // Enable even parity

Serial2.begin(9600);
UCSR2C = (UCSR2C & 0xCF) | (0b11 << 4);  // Enable odd parity

Many thanks for the help. I assume I just drop this into the 'setup' part of the sketch and all should work?

I will try it out and see what happens.

notorious:
Many thanks for the help. I assume I just drop this into the 'setup' part of the sketch and all should work?

I think it will probably work if you just put the setting of parity mode after .begin().

It is one thing to enable the parity options for just sending characters with proper even or odd parity. However I don't think the existing serial functions will help you in detecting parity errors on incoming characters without modification of the serial library? Perhaps someone more knowledgeable can comment on that?

Lefty

retrolefty:
It is one thing to enable the parity options for just sending characters with proper even or odd parity. However I don't think the existing serial functions will help you in detecting parity errors on incoming characters without modification of the serial library? Perhaps someone more knowledgeable can comment on that?

From my reading of the ATmega datasheet and the HardwareSerial.cpp source it looks like any receive overrun, parity, or framing error is ignored. To check for such errors the code would have to read the UCSRnA register before reading the character from the UDRn register. The receive interrupt service routines just read the data register (UDRn) and shoves the character into the buffer.

Rewrote the library HardwareSerial. Now there is support for Number of data bits, parity, and the Number of stop bits. Please check the library for the presence of compatibility with older models of the controllers.

HardwareSerial.h (2.38 KB)

HardwareSerial.cpp (12.9 KB)

Corrected function of parity, checked all the transmitters in the mega 2560.

HardwareSerial.zip (4.64 KB)

johnwasser:

retrolefty:
It is one thing to enable the parity options for just sending characters with proper even or odd parity. However I don't think the existing serial functions will help you in detecting parity errors on incoming characters without modification of the serial library? Perhaps someone more knowledgeable can comment on that?

From my reading of the ATmega datasheet and the HardwareSerial.cpp source it looks like any receive overrun, parity, or framing error is ignored. To check for such errors the code would have to read the UCSRnA register before reading the character from the UDRn register. The receive interrupt service routines just read the data register (UDRn) and shoves the character into the buffer.

That was what I thought. The Arduino serial software support is deficient in this regard by ignoring all possible receiver detectable error types and just stuffing whatever was received into the receive buffer. As such the Arduino hardware serial library should not be considered as supporting 'robust' industry standards for asynchronous serial communications. That is unfortunate because the AVR hardware does support such error detection.

Lefty