I have the following class holding an std::vector
as a resizable "buffer" for data.
class packet
{
public:
struct PacketHeader
{
size_t dataSize = 0;
size_t paddedDataSize = 0;
} header_;
const unsigned char* data() const
{
return &data_[0];
}
unsigned char* data()
{
return &data_[0];
}
/// changes the size of the data vector
void resize(size_t sz)
{
header_.dataSize = sz;
// check if padding is needed
if (sz % AES_BLOCK_SIZE != 0){
auto padding = AES_BLOCK_SIZE - (sz % AES_BLOCK_SIZE);
data_.resize(sz + padding);
for (int i = 1; i <= padding; i++)
{
data_[(sz + padding) - i] = '\0';
}
header_.paddedDataSize = sz + padding;
} else{
data_.resize(sz);
}
}
private:
std::vector<unsigned char> data_;
};
Then I'm performing some AES encryption on the data before transfering them over the network, which requires another temporary buffer of the same size to generate the ciphertext, which then has to be copied back into the vector.
void TcpConnection::send_packet(packet& pkg)
{
// I cut out all the unrelevant lines of code
// We need a temporary buffer for the encryption
unsigned char* enc_out = (unsigned char*)malloc(pkg.header_.paddedDataSize);
// AES-128 bit CBC encryption
aes_cbc_encrypt(pkg.data(), enc_out, pkg.header_.paddedDataSize);
// now I need to copy all the data back from the temporary buffer into the objects vector
memcpy(pkg.data(), enc_out, pkg.header_.paddedDataSize);
free(enc_out);
io_service_.post([this, pkg]() { transmit(pkg); });
}
This seems like a rather expensive task. Isn't there a better way, to kind of let the vector take ownership of the temporary buffer (did I understand it correctly that these new std::move
and rvalue move semantics are used for this kind of stuff?)