Main Content

CERT C++: DCL55-CPP

Avoid information leakage when passing a class object across a trust boundary

Since R2022b

Description

Rule Definition

Avoid information leakage when passing a class object across a trust boundary.1

Polyspace Implementation

The rule checker checks for Information leakage due to structure padding.

Examples

expand all

Issue

Information leakage due to structure padding occurs when sending a pointer to a data structure across a trust boundary without first initializing any padding bits in the data structure.

Risk

Class objects can contain padding bits. Because padding bits are defined by implementation, the layout of a class object can be unique between different compilers and architectures. Padding bits can be present at any location within a class object instance.

Sensitive information such as personal data, passwords, or pointers to kernel data structures can remain within the padding bits if the data is not properly initialized. If a class object is sent across a trust barrier, the sensitive data stored within padding bits can be exposed.

Fix

Verify that no sensitive data is contained within the padding bits before sending a class object instance across a trust boundary. Explicitly declare padding bits as fields within the class object or serialize the data before external use.

Example – Possible Leak of Sensitive Data Via Structure Padding

In this example, the structure test contains padding bits in order to properly align class data members. These padding bits may contain sensitive data which could be leaked when the data is copied to user space.

#include <cstddef> 

struct example {
	int car;
	char model;
	int vin;
};

extern int send_to_external(void* dest, void* src, std::size_t size);

void processData(void* user_buffer) {
	example test{};
	test.car = 1;
	test.model = 2;
	test.vin = 3;

	send_to_external(user_buffer, &test, sizeof(test));//Noncompliant
} 
Correction – Serialize Data Structure Before Copy

Serialize the data structure before you copy it to an untrusted context so no padding bits contain sensitive data.

#include <cstddef>
#include <cstring> 

struct example {
	int car;
	char model;
	int vin;
};

extern int send_to_external(void* dest, void* src, std::size_t size);

void processData(void* user_buffer) {
	example test{ 1, 2, 3 };

	unsigned char buff[sizeof(test)];
	std::size_t offset = 0;

	std::memcpy(buff + offset, &test.car, sizeof(test.car));
	offset += sizeof(test.car);
	std::memcpy(buff + offset, &test.model, sizeof(test.model));
	offset += sizeof(test.model);
	std::memcpy(buff + offset, &test.vin, sizeof(test.vin));
	offset += sizeof(test.vin);

	send_to_external(user_buffer, buff, offset /* size of info copied */);
}

Check Information

Group: Rule 01. Declarations and Initialization (DCL)

Version History

Introduced in R2022b


1 This software has been created by MathWorks incorporating portions of: the “SEI CERT-C Website,” © 2017 Carnegie Mellon University, the SEI CERT-C++ Web site © 2017 Carnegie Mellon University, ”SEI CERT C Coding Standard – Rules for Developing safe, Reliable and Secure systems – 2016 Edition,” © 2016 Carnegie Mellon University, and “SEI CERT C++ Coding Standard – Rules for Developing safe, Reliable and Secure systems in C++ – 2016 Edition” © 2016 Carnegie Mellon University, with special permission from its Software Engineering Institute.

ANY MATERIAL OF CARNEGIE MELLON UNIVERSITY AND/OR ITS SOFTWARE ENGINEERING INSTITUTE CONTAINED HEREIN IS FURNISHED ON AN "AS-IS" BASIS. CARNEGIE MELLON UNIVERSITY MAKES NO WARRANTIES OF ANY KIND, EITHER EXPRESSED OR IMPLIED, AS TO ANY MATTER INCLUDING, BUT NOT LIMITED TO, WARRANTY OF FITNESS FOR PURPOSE OR MERCHANTABILITY, EXCLUSIVITY, OR RESULTS OBTAINED FROM USE OF THE MATERIAL. CARNEGIE MELLON UNIVERSITY DOES NOT MAKE ANY WARRANTY OF ANY KIND WITH RESPECT TO FREEDOM FROM PATENT, TRADEMARK, OR COPYRIGHT INFRINGEMENT.

This software and associated documentation has not been reviewed nor is it endorsed by Carnegie Mellon University or its Software Engineering Institute.