Bug #90077 Decode of some PIT on Pipeline_stats_member_message are not endian safe
Submitted: 14 Mar 2018 16:37 Modified: 3 Jul 2018 15:29
Reporter: Nuno Carvalho Email Updates:
Status: Closed Impact on me:
None 
Category:MySQL Server: Group Replication Severity:S3 (Non-critical)
Version:8.0.2 OS:Any
Assigned to: CPU Architecture:Any

[14 Mar 2018 16:37] Nuno Carvalho
Description:
231 void Pipeline_stats_member_message::decode_payload(const unsigned char *buffer,
232                                                    const unsigned char *end) {
233   DBUG_ENTER("Pipeline_stats_member_message::decode_payload");
...
270       case PIT_TRANSACTIONS_NEGATIVE_CERTIFIED:
271         if (slider + payload_item_length <= end) {
272           uint64 transactions_negative_certified_aux = *slider;
273           slider += payload_item_length;
274           m_transactions_negative_certified =
275               (int64)transactions_negative_certified_aux;
276         }
277         break;
278 
279       case PIT_TRANSACTIONS_ROWS_VALIDATING:
280         if (slider + payload_item_length <= end) {
281           uint64 transactions_rows_validating_aux = *slider;
282           slider += payload_item_length;
283           m_transactions_rows_validating =
284               (int64)transactions_rows_validating_aux;
285         }
286         break;
...
304       case PIT_TRANSACTIONS_LOCAL_ROLLBACK:
305         if (slider + payload_item_length <= end) {
306           uint64 transactions_local_rollback_aux = *slider;
307           slider += payload_item_length;
308           m_transactions_local_rollback =
309               (int64)transactions_local_rollback_aux;
310         }
311         break;

The above PITs do use the direct value from the buffer without convert them to a common endian.
The above PITs are encoded with:
215   uint64 transactions_local_rollback_aux =
216       (uint64)m_transactions_local_rollback;
217   encode_payload_item_int8(buffer, PIT_TRANSACTIONS_LOCAL_ROLLBACK,
218                            transactions_local_rollback_aux);
which does:
240 void Plugin_gcs_message::encode_payload_item_int8(
241     std::vector<unsigned char> *buffer, uint16 type, ulonglong value) const {
242   DBUG_ENTER("Plugin_gcs_message::encode_payload_item_int8");
243   unsigned char buf[8];
244 
245   encode_payload_item_type_and_length(buffer, type, 8);
246   int8store(buf, value);
247   buffer->insert(buffer->end(), buf, buf + 8);
248 
249   DBUG_VOID_RETURN;
250 }

So the decoding must be done using uint8korr(), example:
uint64 transactions_negative_certified_aux = uint8korr(slider);

Please see Plugin_gcs_message::decode_payload_item_int8() for more details.

How to repeat:
Please see above.

Suggested fix:
Please see above.
[3 Jul 2018 15:29] David Moss
Posted by developer:
 
Thank you for your feedback, this has been fixed in upcoming versions and the following was added to the 8.0.12 changelog:
The PIT_TRANSACTIONS_NEGATIVE_CERTIFIED, the PIT_TRANSACTIONS_ROWS_VALIDATING and the PIT_TRANSACTIONS_LOCAL_ROLLBACK member messages were not being correctly decoded.