Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Rename FFI types, functions and enums in preparation for 1.0 #73

Merged
merged 2 commits into from
Nov 21, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 8 additions & 3 deletions ddcommon-ffi/cbindgen.toml
Original file line number Diff line number Diff line change
Expand Up @@ -4,10 +4,10 @@
language = "C"
tab_width = 2
header = """// Unless explicitly stated otherwise all files in this repository are licensed under the Apache License Version 2.0.
// This product includes software developed at Datadog (https://www.datadoghq.com/). Copyright 2021-Present Datadog, Inc.
"""
// This product includes software developed at Datadog (https://www.datadoghq.com/). Copyright 2021-Present Datadog, Inc."""
include_guard = "DDOG_COMMON_H"
style = "both"
pragma_once = true

no_includes = true
sys_includes = ["stdbool.h", "stddef.h", "stdint.h"]
Expand Down Expand Up @@ -46,9 +46,14 @@ after_includes = """

[export]
prefix = "ddog_"
renaming_overrides_prefixing = true

[export.mangle]
rename_types="SnakeCase"
rename_types = "PascalCase"

[export.rename]
"ParseTagsResult" = "ddog_Vec_Tag_ParseResult"
"PushTagResult" = "ddog_Vec_Tag_PushResult"

[enum]
prefix_with_name = true
Expand Down
24 changes: 12 additions & 12 deletions ddcommon-ffi/src/tags.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,12 +6,12 @@ use ddcommon::tag::{parse_tags, Tag};

#[must_use]
#[no_mangle]
pub extern "C" fn ddog_Vec_tag_new() -> crate::Vec<Tag> {
pub extern "C" fn ddog_Vec_Tag_new() -> crate::Vec<Tag> {
crate::Vec::default()
}

#[no_mangle]
pub extern "C" fn ddog_Vec_tag_drop(_: crate::Vec<Tag>) {}
pub extern "C" fn ddog_Vec_Tag_drop(_: crate::Vec<Tag>) {}

#[repr(C)]
pub enum PushTagResult {
Expand All @@ -20,7 +20,7 @@ pub enum PushTagResult {
}

#[no_mangle]
pub extern "C" fn ddog_PushTagResult_drop(_: PushTagResult) {}
pub extern "C" fn ddog_Vec_Tag_PushResult_drop(_: PushTagResult) {}

/// Creates a new Tag from the provided `key` and `value` by doing a utf8
/// lossy conversion, and pushes into the `vec`. The strings `key` and `value`
Expand All @@ -32,7 +32,7 @@ pub extern "C" fn ddog_PushTagResult_drop(_: PushTagResult) {}
/// `.len` properties claim.
#[must_use]
#[no_mangle]
pub unsafe extern "C" fn ddog_Vec_tag_push(
pub unsafe extern "C" fn ddog_Vec_Tag_push(
vec: &mut crate::Vec<Tag>,
key: CharSlice,
value: CharSlice,
Expand All @@ -59,7 +59,7 @@ pub struct ParseTagsResult {
/// .len property.
#[must_use]
#[no_mangle]
pub unsafe extern "C" fn ddog_Vec_tag_parse(string: CharSlice) -> ParseTagsResult {
pub unsafe extern "C" fn ddog_Vec_Tag_parse(string: CharSlice) -> ParseTagsResult {
let string = string.to_utf8_lossy();
let (tags, error) = parse_tags(string.as_ref());
ParseTagsResult {
Expand All @@ -75,21 +75,21 @@ mod tests {
#[test]
fn empty_tag_name() {
unsafe {
let mut tags = ddog_Vec_tag_new();
let result = ddog_Vec_tag_push(&mut tags, CharSlice::from(""), CharSlice::from("woof"));
let mut tags = ddog_Vec_Tag_new();
let result = ddog_Vec_Tag_push(&mut tags, CharSlice::from(""), CharSlice::from("woof"));
assert!(!matches!(result, PushTagResult::Ok));
}
}

#[test]
fn test_lifetimes() {
let mut tags = ddog_Vec_tag_new();
let mut tags = ddog_Vec_Tag_new();
unsafe {
// make a string here so it has a scoped lifetime
let key = String::from("key1");
{
let value = String::from("value1");
let result = ddog_Vec_tag_push(
let result = ddog_Vec_Tag_push(
&mut tags,
CharSlice::from(key.as_str()),
CharSlice::from(value.as_str()),
Expand All @@ -105,9 +105,9 @@ mod tests {
#[test]
fn test_get() {
unsafe {
let mut tags = ddog_Vec_tag_new();
let mut tags = ddog_Vec_Tag_new();
let result =
ddog_Vec_tag_push(&mut tags, CharSlice::from("sound"), CharSlice::from("woof"));
ddog_Vec_Tag_push(&mut tags, CharSlice::from("sound"), CharSlice::from("woof"));
assert!(matches!(result, PushTagResult::Ok));
assert_eq!(1, tags.len());
assert_eq!("sound:woof", tags.get(0).unwrap().to_string());
Expand All @@ -119,7 +119,7 @@ mod tests {
let dd_tags = "env:staging:east, tags:, env_staging:east"; // contains an error

// SAFETY: CharSlices from Rust strings are safe.
let result = unsafe { ddog_Vec_tag_parse(CharSlice::from(dd_tags)) };
let result = unsafe { ddog_Vec_Tag_parse(CharSlice::from(dd_tags)) };
assert_eq!(2, result.tags.len());
assert_eq!("env:staging:east", result.tags.get(0).unwrap().to_string());
assert_eq!("env_staging:east", result.tags.get(1).unwrap().to_string());
Expand Down
4 changes: 2 additions & 2 deletions ddcommon-ffi/src/vec.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,8 +10,8 @@ use std::mem::ManuallyDrop;

/// Holds the raw parts of a Rust Vec; it should only be created from Rust,
/// never from C.
/// The names ptr and len were chosen to minimize conversion from a previous
/// Buffer type which this has replaced to become more general.
// The names ptr and len were chosen to minimize conversion from a previous
// Buffer type which this has replaced to become more general.
#[repr(C)]
#[derive(Debug)]
pub struct Vec<T: Sized> {
Expand Down
68 changes: 34 additions & 34 deletions examples/ffi/exporter.cpp
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
extern "C" {
#include <datadog/common.h>
#include <datadog/profiling.h>
#include <datadog/common.h>
#include <datadog/profiling.h>
}
#include <cstdint>
#include <cstdio>
Expand All @@ -9,10 +9,10 @@ extern "C" {
#include <memory>
#include <thread>

static ddog_Slice_c_char to_slice_c_char(const char *s) { return {.ptr = s, .len = strlen(s)}; }
static ddog_CharSlice to_slice_c_char(const char *s) { return {.ptr = s, .len = strlen(s)}; }

struct Deleter {
void operator()(ddog_Profile *object) { ddog_Profile_free(object); }
void operator()(ddog_prof_Profile *object) { ddog_prof_Profile_drop(object); }
};

template <typename T> void print_error(const char *s, const T &err) {
Expand All @@ -32,16 +32,16 @@ int main(int argc, char *argv[]) {

const auto service = argv[1];

const ddog_ValueType wall_time = {
const ddog_prof_ValueType wall_time = {
.type_ = DDOG_CHARSLICE_C("wall-time"),
.unit = DDOG_CHARSLICE_C("nanoseconds"),
};

const ddog_Slice_value_type sample_types = {&wall_time, 1};
const ddog_Period period = {wall_time, 60};
std::unique_ptr<ddog_Profile, Deleter> profile{ddog_Profile_new(sample_types, &period, nullptr)};
const ddog_prof_Slice_ValueType sample_types = {&wall_time, 1};
const ddog_prof_Period period = {wall_time, 60};
std::unique_ptr<ddog_prof_Profile, Deleter> profile{ ddog_prof_Profile_new(sample_types, &period, nullptr) };

ddog_Line root_line = {
ddog_prof_Line root_line = {
.function =
{
.name = DDOG_CHARSLICE_C("{main}"),
Expand All @@ -50,71 +50,71 @@ int main(int argc, char *argv[]) {
.line = 0,
};

ddog_Location root_location = {
ddog_prof_Location root_location = {
// yes, a zero-initialized mapping is valid
.mapping = {},
.lines = {&root_line, 1},
};

int64_t value = 10;
const ddog_Label label = {
const ddog_prof_Label label = {
.key = DDOG_CHARSLICE_C("language"),
.str = DDOG_CHARSLICE_C("php"),
};
ddog_Sample sample = {
ddog_prof_Sample sample = {
.locations = {&root_location, 1},
.values = {&value, 1},
.labels = {&label, 1},
};
ddog_Profile_add(profile.get(), sample);
ddog_prof_Profile_add(profile.get(), sample);

ddog_SerializeResult serialize_result = ddog_Profile_serialize(profile.get(), nullptr, nullptr);
if (serialize_result.tag == DDOG_SERIALIZE_RESULT_ERR) {
ddog_prof_Profile_SerializeResult serialize_result = ddog_prof_Profile_serialize(profile.get(), nullptr, nullptr);
if (serialize_result.tag == DDOG_PROF_PROFILE_SERIALIZE_RESULT_ERR) {
print_error("Failed to serialize profile: ", serialize_result.err);
return 1;
}

ddog_EncodedProfile *encoded_profile = &serialize_result.ok;
ddog_prof_EncodedProfile *encoded_profile = &serialize_result.ok;

ddog_Endpoint endpoint =
ddog_Endpoint_agentless(DDOG_CHARSLICE_C("datad0g.com"), to_slice_c_char(api_key));

ddog_Vec_tag tags = ddog_Vec_tag_new();
ddog_PushTagResult tag_result =
ddog_Vec_tag_push(&tags, DDOG_CHARSLICE_C("service"), to_slice_c_char(service));
if (tag_result.tag == DDOG_PUSH_TAG_RESULT_ERR) {
ddog_Vec_Tag tags = ddog_Vec_Tag_new();
ddog_Vec_Tag_PushResult tag_result =
ddog_Vec_Tag_push(&tags, DDOG_CHARSLICE_C("service"), to_slice_c_char(service));
if (tag_result.tag == DDOG_VEC_TAG_PUSH_RESULT_ERR) {
print_error("Failed to push tag: ", tag_result.err);
ddog_PushTagResult_drop(tag_result);
ddog_Vec_Tag_PushResult_drop(tag_result);
return 1;
}

ddog_PushTagResult_drop(tag_result);
ddog_Vec_Tag_PushResult_drop(tag_result);

ddog_NewProfileExporterResult exporter_new_result = ddog_ProfileExporter_new(
ddog_prof_Exporter_NewResult exporter_new_result = ddog_prof_Exporter_new(
DDOG_CHARSLICE_C("exporter-example"),
DDOG_CHARSLICE_C("1.2.3"),
DDOG_CHARSLICE_C("native"),
&tags,
endpoint
);
ddog_Vec_tag_drop(tags);
ddog_Vec_Tag_drop(tags);

if (exporter_new_result.tag == DDOG_NEW_PROFILE_EXPORTER_RESULT_ERR) {
if (exporter_new_result.tag == DDOG_PROF_EXPORTER_NEW_RESULT_ERR) {
print_error("Failed to create exporter: ", exporter_new_result.err);
ddog_NewProfileExporterResult_drop(exporter_new_result);
ddog_prof_Exporter_NewResult_drop(exporter_new_result);
return 1;
}

auto exporter = exporter_new_result.ok;

ddog_File files_[] = {{
ddog_prof_Exporter_File files_[] = {{
.name = DDOG_CHARSLICE_C("auto.pprof"),
.file = ddog_Vec_u8_as_slice(&encoded_profile->buffer),
.file = ddog_Vec_U8_as_slice(&encoded_profile->buffer),
}};

ddog_Slice_file files = {.ptr = files_, .len = sizeof files_ / sizeof *files_};
ddog_prof_Exporter_Slice_File files = {.ptr = files_, .len = sizeof files_ / sizeof *files_};

ddog_Request *request = ddog_ProfileExporter_build(
ddog_prof_Exporter_Request *request = ddog_prof_Exporter_Request_build(
exporter,
encoded_profile->start,
encoded_profile->end,
Expand Down Expand Up @@ -145,16 +145,16 @@ int main(int argc, char *argv[]) {
trigger_cancel_if_request_takes_too_long_thread.detach();

int exit_code = 0;
ddog_SendResult send_result = ddog_ProfileExporter_send(exporter, request, cancel);
if (send_result.tag == DDOG_SEND_RESULT_ERR) {
ddog_prof_Exporter_SendResult send_result = ddog_prof_Exporter_send(exporter, request, cancel);
if (send_result.tag == DDOG_PROF_EXPORTER_SEND_RESULT_ERR) {
print_error("Failed to send profile: ", send_result.err);
exit_code = 1;
} else {
printf("Response code: %d\n", send_result.http_response.code);
}

ddog_NewProfileExporterResult_drop(exporter_new_result);
ddog_SendResult_drop(send_result);
ddog_prof_Exporter_NewResult_drop(exporter_new_result);
ddog_prof_Exporter_SendResult_drop(send_result);
ddog_CancellationToken_drop(cancel);
return exit_code;
}
26 changes: 13 additions & 13 deletions examples/ffi/profiles.c
Original file line number Diff line number Diff line change
Expand Up @@ -11,40 +11,40 @@
* with unit 60 "nanoseconds". Adds one sample with a string label "language".
*/
int main(void) {
const struct ddog_ValueType wall_time = {
const ddog_prof_ValueType wall_time = {
.type_ = DDOG_CHARSLICE_C("wall-time"),
.unit = DDOG_CHARSLICE_C("nanoseconds"),
};
const struct ddog_Slice_value_type sample_types = {&wall_time, 1};
const struct ddog_Period period = {wall_time, 60};
const ddog_prof_Slice_ValueType sample_types = {&wall_time, 1};
const ddog_prof_Period period = {wall_time, 60};

ddog_Profile *profile = ddog_Profile_new(sample_types, &period, NULL);
ddog_prof_Profile *profile = ddog_prof_Profile_new(sample_types, &period, NULL);

struct ddog_Line root_line = {
ddog_prof_Line root_line = {
.function =
(struct ddog_Function){
(struct ddog_prof_Function) {
.name = DDOG_CHARSLICE_C("{main}"),
.filename = DDOG_CHARSLICE_C("/srv/example/index.php"),
},
.line = 0,
};

struct ddog_Location root_location = {
ddog_prof_Location root_location = {
// yes, a zero-initialized mapping is valid
.mapping = (struct ddog_Mapping){0},
.lines = (struct ddog_Slice_line){&root_line, 1},
.mapping = (ddog_prof_Mapping) {0},
.lines = (ddog_prof_Slice_Line) {&root_line, 1},
};
int64_t value = 10;
const struct ddog_Label label = {
const ddog_prof_Label label = {
.key = DDOG_CHARSLICE_C("language"),
.str = DDOG_CHARSLICE_C("php"),
};
struct ddog_Sample sample = {
const ddog_prof_Sample sample = {
.locations = {&root_location, 1},
.values = {&value, 1},
.labels = {&label, 1},
};
ddog_Profile_add(profile, sample);
ddog_Profile_free(profile);
ddog_prof_Profile_add(profile, sample);
ddog_prof_Profile_drop(profile);
return 0;
}
30 changes: 26 additions & 4 deletions profiling-ffi/cbindgen.toml
Original file line number Diff line number Diff line change
Expand Up @@ -4,20 +4,42 @@
language = "C"
tab_width = 2
header = """// Unless explicitly stated otherwise all files in this repository are licensed under the Apache License Version 2.0.
// This product includes software developed at Datadog (https://www.datadoghq.com/). Copyright 2021-Present Datadog, Inc.
"""
// This product includes software developed at Datadog (https://www.datadoghq.com/). Copyright 2021-Present Datadog, Inc."""
include_guard = "DDOG_PROFILING_H"
style = "both"
pragma_once = true

no_includes = true
sys_includes = ["stdbool.h", "stddef.h", "stdint.h"]
includes = ["common.h"]

[export]
prefix = "ddog_"
prefix = "ddog_prof_"
renaming_overrides_prefixing = true

[export.rename]
"ByteSlice" = "ddog_ByteSlice"
"CancellationToken" = "ddog_CancellationToken"
"CharSlice" = "ddog_CharSlice"
"Endpoint" = "ddog_Endpoint"
"HttpStatus" = "ddog_HttpStatus"
"Slice_CChar" = "ddog_Slice_CChar"
"Slice_I64" = "ddog_Slice_I64"
"Slice_U8" = "ddog_Slice_U8"
"Tag" = "ddog_Tag"
"Timespec" = "ddog_Timespec"
"Vec_Tag" = "ddog_Vec_Tag"

"File" = "ddog_prof_Exporter_File"
"NewProfileExporterResult" = "ddog_prof_Exporter_NewResult"
"ProfileExporter" = "ddog_prof_Exporter"
"Request" = "ddog_prof_Exporter_Request"
"SendResult" = "ddog_prof_Exporter_SendResult"
"SerializeResult" = "ddog_prof_Profile_SerializeResult"
"Slice_File" = "ddog_prof_Exporter_Slice_File"

[export.mangle]
rename_types="SnakeCase"
rename_types = "PascalCase"

[enum]
prefix_with_name = true
Expand Down
Loading