Skip to content

Commit

Permalink
Remove some duplicate code.
Browse files Browse the repository at this point in the history
  • Loading branch information
fruffy-g committed Dec 27, 2023
1 parent 9de09b0 commit 2f7c0df
Show file tree
Hide file tree
Showing 6 changed files with 29 additions and 44 deletions.
9 changes: 7 additions & 2 deletions backends/p4tools/common/lib/format_int.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -269,7 +269,8 @@ std::string insertHexSeparators(const std::string &dataStr) {
return insertSeparators(dataStr, "\\x", 2, false);
}

std::vector<uint8_t> convertBigIntToBytes(const big_int &dataInt, int targetWidthBits) {
std::vector<uint8_t> convertBigIntToBytes(const big_int &dataInt, int targetWidthBits,
bool padLeft) {
/// Chunk size is 8 bits, i.e., a byte.
constexpr uint8_t chunkSize = 8U;

Expand All @@ -282,7 +283,11 @@ std::vector<uint8_t> convertBigIntToBytes(const big_int &dataInt, int targetWidt
auto diff = targetWidthBytes - bytes.size();
if (targetWidthBytes > bytes.size() && diff > 0UL) {
for (size_t i = 0; i < diff; ++i) {
bytes.push_back(0);
if (padLeft) {
bytes.insert(bytes.begin(), 0);
} else {
bytes.push_back(0);
}
}
}
return bytes;
Expand Down
8 changes: 5 additions & 3 deletions backends/p4tools/common/lib/format_int.h
Original file line number Diff line number Diff line change
Expand Up @@ -78,9 +78,11 @@ std::string insertOctalSeparators(const std::string &dataStr);
std::string insertHexSeparators(const std::string &dataStr);

/// Converts a big integer input into a vector of bytes with the size targetWidthBits /8.
/// If the integer value is smaller than the request bit size, padding is added on the right-hand
/// side of the vector (the "least-significant" side).
std::vector<uint8_t> convertBigIntToBytes(const big_int &dataInt, int targetWidthBits);
/// If the integer value is smaller than the request bit size and @param padLeft is false, padding
/// is added on the right-hand side of the vector (the "least-significant" side). Otherwise, padding
/// is added on the left-hand side, (the "most-significant side")
std::vector<uint8_t> convertBigIntToBytes(const big_int &dataInt, int targetWidthBits,
bool padLeft = false);

/// Convert a byte array into a IPv4 string of the form "x.x.x.x".
/// @returns std::nullopt if the conversion fails.
Expand Down
23 changes: 3 additions & 20 deletions backends/p4tools/modules/testgen/targets/bmv2/concolic.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -13,12 +13,12 @@
#include <boost/multiprecision/number.hpp>
#include <boost/multiprecision/traits/explicit_conversion.hpp>

#include "backends/p4tools/common/lib/format_int.h"
#include "backends/p4tools/common/lib/model.h"
#include "ir/irutils.h"
#include "ir/vector.h"
#include "lib/cstring.h"
#include "lib/exceptions.h"
#include "lib/log.h"

#include "backends/p4tools/modules/testgen/lib/concolic.h"
#include "backends/p4tools/modules/testgen/lib/exceptions.h"
Expand All @@ -28,23 +28,6 @@

namespace P4Tools::P4Testgen::Bmv2 {

std::vector<char> Bmv2Concolic::convertBigIntToBytes(big_int &dataInt, int targetWidthBits) {
std::vector<char> bytes;
// Convert the input bit width to bytes and round up.
size_t targetWidthBytes = (targetWidthBits + CHUNK_SIZE - 1) / CHUNK_SIZE;
boost::multiprecision::export_bits(dataInt, std::back_inserter(bytes), CHUNK_SIZE);
// If the number of bytes produced by the export is lower than the desired width pad the byte
// array with zeroes.
auto diff = targetWidthBytes - bytes.size();
if (targetWidthBytes > bytes.size() && diff > 0UL) {
for (size_t i = 0; i < diff; ++i) {
bytes.insert(bytes.begin(), 0);
}
}

return bytes;
}

big_int Bmv2Concolic::computeChecksum(const std::vector<const IR::Expression *> &exprList,
const Model &finalModel, int algo,
Model::ExpressionMap *resolvedExpressions) {
Expand Down Expand Up @@ -80,7 +63,7 @@ big_int Bmv2Concolic::computeChecksum(const std::vector<const IR::Expression *>
TESTGEN_UNIMPLEMENTED("Algorithm %1% not implemented for hash.", algo);
}

std::vector<char> bytes;
std::vector<uint8_t> bytes;
if (!exprList.empty()) {
const auto *concatExpr = exprList.at(0);
for (size_t idx = 1; idx < exprList.size(); idx++) {
Expand All @@ -102,7 +85,7 @@ big_int Bmv2Concolic::computeChecksum(const std::vector<const IR::Expression *>
}
auto dataInt =
IR::getBigIntFromLiteral(finalModel.evaluate(concatExpr, true, resolvedExpressions));
bytes = convertBigIntToBytes(dataInt, concatWidth);
bytes = convertBigIntToBytes(dataInt, concatWidth, true);
}
return checksumFun(bytes.data(), bytes.size());
}
Expand Down
7 changes: 1 addition & 6 deletions backends/p4tools/modules/testgen/targets/bmv2/concolic.h
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ namespace P4Tools::P4Testgen::Bmv2 {
class Bmv2Concolic : public Concolic {
private:
/// In the behavioral model, checksum functions have the following signature.
using ChecksumFunction = std::function<big_int(const char *buf, size_t len)>;
using ChecksumFunction = std::function<big_int(const uint8_t *buf, size_t len)>;

/// Chunk size is 8 bits, i.e., a byte.
static constexpr int CHUNK_SIZE = 8;
Expand Down Expand Up @@ -53,11 +53,6 @@ class Bmv2Concolic : public Concolic {
static const IR::Expression *setAndComputePayload(
const Model &finalModel, ConcolicVariableMap *resolvedConcolicVariables, int payloadSize);

/// Converts a big integer input into a vector of bytes. This byte vector is fed into the
/// hash function.
/// This function mimics the conversion of data structures to bytes in the behavioral model.
static std::vector<char> convertBigIntToBytes(big_int &dataInt, int targetWidthBits);

public:
/// @returns the concolic functions that are implemented for this particular target.
static const ConcolicMethodImpls::ImplList *getBmv2ConcolicMethodImpls();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -91,7 +91,7 @@ static uint32_t table_crc32[256] = {
0x89B8FD09, 0x8D79E0BE, 0x803AC667, 0x84FBDBD0, 0x9ABC8BD5, 0x9E7D9662, 0x933EB0BB, 0x97FFAD0C,
0xAFB010B1, 0xAB710D06, 0xA6322BDF, 0xA2F33668, 0xBCB4666D, 0xB8757BDA, 0xB5365D03, 0xB1F740B4};

uint16_t BMv2Hash::crc16(const char *buf, size_t len) {
uint16_t BMv2Hash::crc16(const uint8_t *buf, size_t len) {
uint16_t remainder = 0x0000;
uint16_t final_xor_value = 0x0000;
for (unsigned int byte = 0; byte < len; byte++) {
Expand All @@ -101,7 +101,7 @@ uint16_t BMv2Hash::crc16(const char *buf, size_t len) {
return reflect<uint16_t>(remainder, 16) ^ final_xor_value;
}

uint32_t BMv2Hash::crc32(const char *buf, size_t len) {
uint32_t BMv2Hash::crc32(const uint8_t *buf, size_t len) {
uint32_t remainder = 0xFFFFFFFF;
uint32_t final_xor_value = 0xFFFFFFFF;
for (unsigned int byte = 0; byte < len; byte++) {
Expand All @@ -111,17 +111,17 @@ uint32_t BMv2Hash::crc32(const char *buf, size_t len) {
return reflect<uint32_t>(remainder, 32) ^ final_xor_value;
}

uint16_t BMv2Hash::crcCCITT(const char *buf, size_t len) {
uint16_t BMv2Hash::crcCCITT(const uint8_t *buf, size_t len) {
uint16_t remainder = 0xFFFF;
uint16_t final_xor_value = 0x0000;
for (unsigned int byte = 0; byte < len; byte++) {
int data = static_cast<unsigned char>(buf[byte]) ^ (remainder >> 8);
int data = static_cast<uint8_t>(buf[byte]) ^ (remainder >> 8);
remainder = table_crcCCITT[data] ^ (remainder << 8);
}
return remainder ^ final_xor_value;
}

uint16_t BMv2Hash::csum16(const char *buf, size_t len) {
uint16_t BMv2Hash::csum16(const uint8_t *buf, size_t len) {
uint64_t sum = 0;
const uint64_t *b = reinterpret_cast<const uint64_t *>(buf);
uint32_t t1, t2;
Expand Down Expand Up @@ -165,7 +165,7 @@ uint16_t BMv2Hash::csum16(const char *buf, size_t len) {
return ntohs(~t3);
}

uint16_t BMv2Hash::xor16(const char *buf, size_t len) {
uint16_t BMv2Hash::xor16(const uint8_t *buf, size_t len) {
uint16_t mask = 0x00ff;
uint16_t final_xor_value = 0x0000;
unsigned int byte = 0;
Expand All @@ -185,7 +185,7 @@ uint16_t BMv2Hash::xor16(const char *buf, size_t len) {
return final_xor_value;
}

uint64_t BMv2Hash::identity(const char *buf, size_t len) {
uint64_t BMv2Hash::identity(const uint8_t *buf, size_t len) {
uint64_t res = 0ULL;
for (size_t i = 0; i < std::min(sizeof(res), len); i++) {
if (i > 0) res <<= 8;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -48,17 +48,17 @@ class BMv2Hash {
}

public:
static uint16_t crc16(const char *buf, size_t len);
static uint16_t crc16(const uint8_t *buf, size_t len);

static uint32_t crc32(const char *buf, size_t len);
static uint32_t crc32(const uint8_t *buf, size_t len);

static uint16_t crcCCITT(const char *buf, size_t len);
static uint16_t crcCCITT(const uint8_t *buf, size_t len);

static uint16_t csum16(const char *buf, size_t len);
static uint16_t csum16(const uint8_t *buf, size_t len);

static uint16_t xor16(const char *buf, size_t len);
static uint16_t xor16(const uint8_t *buf, size_t len);

static uint64_t identity(const char *buf, size_t len);
static uint64_t identity(const uint8_t *buf, size_t len);
};

} // namespace P4Tools::P4Testgen::Bmv2
Expand Down

0 comments on commit 2f7c0df

Please sign in to comment.