Added Raw C++ benchmarks (#6924)

This commit is contained in:
Derek Bailey
2021-11-15 15:19:03 -08:00
committed by GitHub
parent 0989fc5e59
commit 97a30171cb
5 changed files with 195 additions and 43 deletions

View File

@@ -29,15 +29,14 @@ FetchContent_MakeAvailable(
set(CPP_BENCH_DIR cpp)
set(CPP_FB_BENCH_DIR ${CPP_BENCH_DIR}/flatbuffers)
set(CPP_RAW_BENCH_DIR ${CPP_BENCH_DIR}/raw)
set(CPP_BENCH_FBS ${CPP_FB_BENCH_DIR}/bench.fbs)
set(CPP_BENCH_FB_GEN ${CPP_FB_BENCH_DIR}/bench_generated.h)
set(FlatBenchmark_SRCS
${CPP_BENCH_DIR}/benchmark_main.cpp
${CPP_BENCH_DIR}/bench.h
${CPP_FB_BENCH_DIR}/fb_bench.cpp
${CPP_FB_BENCH_DIR}/fb_bench.h
${CPP_BENCH_FB_GEN}
${CPP_RAW_BENCH_DIR}/raw_bench.cpp
)
# Generate the flatbuffers benchmark code from the flatbuffers schema using

View File

@@ -3,20 +3,48 @@
#include "benchmarks/cpp/bench.h"
#include "benchmarks/cpp/flatbuffers/fb_bench.h"
#include "benchmarks/cpp/raw/raw_bench.h"
static inline void Encode(benchmark::State &state,
std::unique_ptr<Bench> &bench, uint8_t *buffer) {
int64_t length;
for (auto _ : state) {
bench->Encode(buffer, length);
benchmark::DoNotOptimize(length);
}
}
static inline void Decode(benchmark::State &state,
std::unique_ptr<Bench> &bench, uint8_t *buffer) {
int64_t length;
uint8_t *encoded = bench->Encode(buffer, length);
for (auto _ : state) {
void *decoded = bench->Decode(encoded, length);
benchmark::DoNotOptimize(decoded);
}
}
static inline void Use(benchmark::State &state, std::unique_ptr<Bench> &bench,
uint8_t *buffer, int64_t check_sum) {
int64_t length;
uint8_t *encoded = bench->Encode(buffer, length);
void *decoded = bench->Decode(encoded, length);
int64_t sum = 0;
for (auto _ : state) { sum = bench->Use(decoded); }
EXPECT_EQ(sum, check_sum);
}
static void BM_Flatbuffers_Encode(benchmark::State &state) {
const int64_t kBufferLength = 1024;
uint8_t buffer[kBufferLength];
int64_t length;
StaticAllocator allocator(&buffer[0]);
std::unique_ptr<Bench> bench = NewFlatBuffersBench(kBufferLength, &allocator);
for (auto _ : state) {
bench->Encode(buffer, length);
benchmark::DoNotOptimize(length);
}
Encode(state, bench, buffer);
}
BENCHMARK(BM_Flatbuffers_Encode);
@@ -24,17 +52,9 @@ static void BM_Flatbuffers_Decode(benchmark::State &state) {
const int64_t kBufferLength = 1024;
uint8_t buffer[kBufferLength];
int64_t length;
StaticAllocator allocator(&buffer[0]);
std::unique_ptr<Bench> bench = NewFlatBuffersBench(kBufferLength, &allocator);
uint8_t* encoded = bench->Encode(buffer, length);
for (auto _ : state) {
void* decoded = bench->Decode(encoded, length);
benchmark::DoNotOptimize(decoded);
}
Decode(state, bench, buffer);
}
BENCHMARK(BM_Flatbuffers_Decode);
@@ -42,20 +62,35 @@ static void BM_Flatbuffers_Use(benchmark::State &state) {
const int64_t kBufferLength = 1024;
uint8_t buffer[kBufferLength];
int64_t length;
StaticAllocator allocator(&buffer[0]);
std::unique_ptr<Bench> bench = NewFlatBuffersBench(kBufferLength, &allocator);
uint8_t* encoded = bench->Encode(buffer, length);
void* decoded = bench->Decode(encoded, length);
int64_t sum = 0;
for (auto _ : state) {
sum = bench->Use(decoded);
}
EXPECT_EQ(sum , 218812692406581874);
Use(state, bench, buffer, 218812692406581874);
}
BENCHMARK(BM_Flatbuffers_Use);
BENCHMARK(BM_Flatbuffers_Use);
static void BM_Raw_Encode(benchmark::State &state) {
const int64_t kBufferLength = 1024;
uint8_t buffer[kBufferLength];
std::unique_ptr<Bench> bench = NewRawBench();
Encode(state, bench, buffer);
}
BENCHMARK(BM_Raw_Encode);
static void BM_Raw_Decode(benchmark::State &state) {
const int64_t kBufferLength = 1024;
uint8_t buffer[kBufferLength];
std::unique_ptr<Bench> bench = NewRawBench();
Decode(state, bench, buffer);
}
BENCHMARK(BM_Raw_Decode);
static void BM_Raw_Use(benchmark::State &state) {
const int64_t kBufferLength = 1024;
uint8_t buffer[kBufferLength];
std::unique_ptr<Bench> bench = NewRawBench();
Use(state, bench, buffer, 218812692406581874);
}
BENCHMARK(BM_Raw_Use);

View File

@@ -13,35 +13,34 @@ using namespace benchmarks_flatbuffers;
namespace {
struct FlatBufferBench : Bench {
explicit FlatBufferBench(int64_t initial_size,
Allocator *allocator)
explicit FlatBufferBench(int64_t initial_size, Allocator *allocator)
: fbb(initial_size, allocator, false) {}
uint8_t *Encode(void *, int64_t &len) override {
uint8_t *Encode(void *, int64_t &len) {
fbb.Clear();
const int kVectorLength = 3;
Offset<FooBar> vec[kVectorLength];
for(int i = 0; i < kVectorLength; ++i) {
for (int i = 0; i < kVectorLength; ++i) {
Foo foo(0xABADCAFEABADCAFE + i, 10000 + i, '@' + i, 1000000 + i);
Bar bar(foo, 123456 + i, 3.14159f + i, 10000 + i);
auto name = fbb.CreateString("Hello, World!");
auto foobar = CreateFooBar(fbb, &bar, name, 3.1415432432445543543 + i,
'!' + i);
auto foobar =
CreateFooBar(fbb, &bar, name, 3.1415432432445543543 + i, '!' + i);
vec[i] = foobar;
}
auto location = fbb.CreateString("http://google.com/flatbuffers/");
auto foobarvec = fbb.CreateVector(vec, kVectorLength);
auto foobarcontainer = CreateFooBarContainer(fbb, foobarvec, true,
Enum_Bananas, location);
auto foobarcontainer =
CreateFooBarContainer(fbb, foobarvec, true, Enum_Bananas, location);
fbb.Finish(foobarcontainer);
len = fbb.GetSize();
return fbb.GetBufferPointer();
}
int64_t Use(void *decoded) override {
int64_t Use(void *decoded) {
sum = 0;
auto foobarcontainer = GetFooBarContainer(decoded);
sum = 0;
@@ -66,7 +65,7 @@ struct FlatBufferBench : Bench {
return sum;
}
void *Decode(void *buffer, int64_t) override { return buffer; }
void *Decode(void *buffer, int64_t) { return buffer; }
void Dealloc(void *) override{};
FlatBufferBuilder fbb;

View File

@@ -0,0 +1,109 @@
#include "benchmarks/cpp/raw/raw_bench.h"
#include <cstdint>
#include <cstring>
#include <memory>
#include "benchmarks/cpp/bench.h"
namespace {
const int64_t kStringLength = 32;
const int64_t kVectorLength = 3;
enum Enum { Apples, Pears, Bananas };
struct Foo {
int64_t id;
short count;
char prefix;
int length;
};
struct Bar {
Foo parent;
int time;
float ratio;
unsigned short size;
};
struct FooBar {
Bar sibling;
// We have to stick this in, otherwise strlen() will make it slower than
// FlatBuffers:
int name_len;
char name[kStringLength];
double rating;
unsigned char postfix;
};
struct FooBarContainer {
FooBar list[kVectorLength]; // 3 copies of the above
bool initialized;
Enum fruit;
int location_len;
char location[kStringLength];
};
struct RawBench : Bench {
uint8_t *Encode(void *buf, int64_t &len) {
FooBarContainer *fbc = new (buf) FooBarContainer;
strcpy(fbc->location, "http://google.com/flatbuffers/"); // Unsafe eek!
fbc->location_len = (int)strlen(fbc->location);
fbc->fruit = Bananas;
fbc->initialized = true;
for (int i = 0; i < kVectorLength; i++) {
// We add + i to not make these identical copies for a more realistic
// compression test.
auto &foobar = fbc->list[i];
foobar.rating = 3.1415432432445543543 + i;
foobar.postfix = '!' + i;
strcpy(foobar.name, "Hello, World!");
foobar.name_len = (int)strlen(foobar.name);
auto &bar = foobar.sibling;
bar.ratio = 3.14159f + i;
bar.size = 10000 + i;
bar.time = 123456 + i;
auto &foo = bar.parent;
foo.id = 0xABADCAFEABADCAFE + i;
foo.count = 10000 + i;
foo.length = 1000000 + i;
foo.prefix = '@' + i;
}
len = sizeof(FooBarContainer);
return reinterpret_cast<uint8_t *>(fbc);
};
int64_t Use(void *decoded) {
auto foobarcontainer = reinterpret_cast<FooBarContainer *>(decoded);
sum = 0;
Add(foobarcontainer->initialized);
Add(foobarcontainer->location_len);
Add(foobarcontainer->fruit);
for (unsigned int i = 0; i < kVectorLength; i++) {
auto foobar = &foobarcontainer->list[i];
Add(foobar->name_len);
Add(foobar->postfix);
Add(static_cast<int64_t>(foobar->rating));
auto bar = &foobar->sibling;
Add(static_cast<int64_t>(bar->ratio));
Add(bar->size);
Add(bar->time);
auto &foo = bar->parent;
Add(foo.count);
Add(foo.id);
Add(foo.length);
Add(foo.prefix);
}
return sum;
}
void *Decode(void *buf, int64_t) { return buf; }
void Dealloc(void *) override{};
};
} // namespace
std::unique_ptr<Bench> NewRawBench() {
return std::unique_ptr<RawBench>(new RawBench());
}

View File

@@ -0,0 +1,10 @@
#ifndef BENCHMARKS_CPP_RAW_RAW_BENCH_H_
#define BENCHMARKS_CPP_RAW_RAW_BENCH_H_
#include <memory>
#include "benchmarks/cpp/bench.h"
std::unique_ptr<Bench> NewRawBench();
#endif // BENCHMARKS_CPP_RAW_RAW_BENCH_H_