object-introspection/test/integration/pointers.toml
Jake Hillion 71e734b120 tbv2: calculate total memory footprint
Add the option to calculate total size (inclusive size) by wrapping the
existing iterator. This change provides a new iterator, `SizedIterator`, which
wraps an existing iterator and adds a new field `size` to the output element.

This is achieved with a two pass algorithm on the existing iterator:
1. Gather metadata for each element. This includes the total size up until that
   element and the range of elements that should be included in the size.
2. Return the result from the underlying iterator with the additional
   field.

This algorithm is `O(N)` time on the number of elements in the iterator and
`O(N)` time, storing 16 bytes per element. This isn't super expensive but is a
lot more than the current algorithm which requires close to constant space.
Because of this I've implemented it as a wrapper on the iterator rather than on
by default, though it is now on in every one of our integration test cases.

Test plan:
- Added to the integration tests for full coverage.
2024-01-04 09:21:35 +00:00

276 lines
9.0 KiB
TOML

includes = ["vector"]
definitions = '''
struct PrimitivePtrs {
int a;
int *b;
void *c; // No dynamic size, we can't know what it points to!
};
struct VectorPtr {
std::vector<int> *vec;
};
'''
[cases]
[cases.int]
skip = "top-level pointers are skipped over" # https://github.com/facebookexperimental/object-introspection/issues/19
param_types = ["int*"]
setup = "return new int(1);"
cli_options = ["-fchase-raw-pointers"]
expect_json = '''[{
"typeName": "int *",
"staticSize": 8,
"dynamicSize": 4,
"NOT": {"pointer": 0},
"members": [
{
"typeName": "int",
"staticSize": 4,
"dynamicSize": 0
}
]
}]'''
[cases.int_no_follow]
skip = "top-level pointers are skipped over" # https://github.com/facebookexperimental/object-introspection/issues/19
param_types = ["int*"]
setup = "return new int(1);"
expect_json = '''[{
"typeName": "int *",
"staticSize": 8,
"dynamicSize": 0,
"NOT": {"pointer": 0},
"NOT": "members"
}]'''
[cases.int_null]
skip = "top-level pointers are skipped over" # https://github.com/facebookexperimental/object-introspection/issues/19
param_types = ["int*"]
setup = "return nullptr;"
expect_json = '''[{
"typeName": "int *",
"staticSize": 8,
"dynamicSize": 0,
"pointer": 0,
"NOT": "members"
}]'''
[cases.void]
skip = "top-level pointers are skipped over" # https://github.com/facebookexperimental/object-introspection/issues/19
param_types = ["void*"]
setup = "return new int(1);"
cli_options = ["-fchase-raw-pointers"]
expect_json = '''[{
"typeName": "void *",
"staticSize": 8,
"dynamicSize": 0,
"NOT": {"pointer": 0},
"NOT": "members"
}]'''
[cases.void_no_follow]
skip = "top-level pointers are skipped over" # https://github.com/facebookexperimental/object-introspection/issues/19
param_types = ["void*"]
setup = "return new int(1);"
expect_json = '''[{
"typeName": "void *",
"staticSize": 8,
"dynamicSize": 0,
"NOT": {"pointer": 0},
"NOT": "members"
}]'''
[cases.void_null]
skip = "top-level pointers are skipped over" # https://github.com/facebookexperimental/object-introspection/issues/19
param_types = ["void*"]
setup = "return nullptr;"
expect_json = '''[{
"typeName": "void *",
"staticSize": 8,
"dynamicSize": 0,
"pointer": 0,
"NOT": "members"
}]'''
[cases.vector]
skip = "top-level pointers are skipped over" # https://github.com/facebookexperimental/object-introspection/issues/19
param_types = ["std::vector<int>*"]
setup = "return new std::vector<int>{1,2,3};"
cli_options = ["-fchase-raw-pointers"]
expect_json = '''[{
"typeName": "std::vector<int> *",
"staticSize": 8,
"dynamicSize": 36,
"NOT": {"pointer": 0},
"members": [
{
"typeName": "std::vector<int>",
"staticSize": 24,
"dynamicSize": 12
}
]
}]'''
[cases.vector_no_follow]
skip = "top-level pointers are skipped over" # https://github.com/facebookexperimental/object-introspection/issues/19
param_types = ["std::vector<int>*"]
setup = "return new std::vector<int>{1,2,3};"
expect_json = '''[{
"typeName": "std::vector<int> *",
"staticSize": 8,
"dynamicSize": 0,
"NOT": {"pointer": 0},
"NOT": "members"
}]'''
[cases.vector_null]
skip = "BAD DATA SEGMENT!!! top-level pointers are skipped over" # https://github.com/facebookexperimental/object-introspection/issues/19
param_types = ["std::vector<int>*"]
setup = "return nullptr;"
expect_json = '''[{
"typeName": "std::vector<int> *",
"staticSize": 8,
"dynamicSize": 0,
"pointer": 0,
"NOT": "members"
}]'''
[cases.struct_primitive_ptrs]
oil_disable = "oil can't chase raw pointers safely"
param_types = ["const PrimitivePtrs&"]
setup = "return PrimitivePtrs{0, new int(0), new int(0)};"
cli_options = ["-fchase-raw-pointers"]
expect_json = '''[{
"staticSize":24,
"dynamicSize":4,
"exclusiveSize":4,
"members":[
{"name":"a", "staticSize":4, "exclusiveSize":4, "dynamicSize":0},
{"name":"b", "staticSize":8, "exclusiveSize":8, "dynamicSize":4},
{"name":"c", "staticSize":8, "exclusiveSize":8, "dynamicSize":0}
]}]'''
[cases.struct_primitive_ptrs_no_follow]
param_types = ["const PrimitivePtrs&"]
setup = "return PrimitivePtrs{0, new int(0), new int(0)};"
expect_json = '''[{
"staticSize":24,
"dynamicSize":0,
"exclusiveSize":4,
"size":24,
"members":[
{"name":"a", "staticSize":4, "dynamicSize":0, "exclusiveSize":4, "size":4},
{"name":"b", "staticSize":8, "dynamicSize":0, "exclusiveSize":8, "size":8},
{"name":"c", "staticSize":8, "dynamicSize":0, "exclusiveSize":8, "size":8}
]}]'''
[cases.struct_primitive_ptrs_null]
param_types = ["const PrimitivePtrs&"]
setup = "return PrimitivePtrs{0, nullptr, nullptr};"
cli_options = ["-fchase-raw-pointers"]
expect_json = '''[{
"staticSize":24,
"dynamicSize":0,
"exclusiveSize":4,
"size":24,
"members":[
{"name":"a", "staticSize":4, "dynamicSize":0, "exclusiveSize":4, "size":4},
{"name":"b", "staticSize":8, "dynamicSize":0, "exclusiveSize":8, "size":8},
{"name":"c", "staticSize":8, "dynamicSize":0, "exclusiveSize":8, "size":8}
]}]'''
[cases.struct_vector_ptr]
oil_disable = "oil can't chase raw pointers safely"
param_types = ["const VectorPtr&"]
setup = "return VectorPtr{new std::vector<int>{1,2,3}};"
cli_options = ["-fchase-raw-pointers"]
expect_json = '''[{
"staticSize":8,
"dynamicSize":36,
"members":[
{"name":"vec", "staticSize":8, "dynamicSize":36}
]}]'''
[cases.struct_vector_ptr_no_follow]
param_types = ["const VectorPtr&"]
setup = "return VectorPtr{new std::vector<int>{1,2,3}};"
expect_json = '''[{
"staticSize":8,
"dynamicSize":0,
"exclusiveSize":0,
"size":8,
"members":[
{"name":"vec", "staticSize":8, "dynamicSize":0, "exclusiveSize":8, "size":8}
]}]'''
[cases.struct_vector_ptr_null]
param_types = ["const VectorPtr&"]
setup = "return VectorPtr{nullptr};"
cli_options = ["-fchase-raw-pointers"]
expect_json = '''[{
"staticSize":8,
"dynamicSize":0,
"exclusiveSize":0,
"size":8,
"members":[
{"name":"vec", "staticSize":8, "dynamicSize":0, "exclusiveSize":8, "size":8}
]}]'''
[cases.vector_of_pointers]
oil_disable = "oil can't chase raw pointers safely"
param_types = ["const std::vector<int*>&"]
setup = "return {{new int(1), nullptr, new int(3)}};"
cli_options = ["-fchase-raw-pointers"]
expect_json = '''[{
"staticSize":24,
"dynamicSize":32,
"length":3,
"capacity":3,
"elementStaticSize":8,
"members":[
{"staticSize":8, "dynamicSize":4, "NOT": {"pointer":0}},
{"staticSize":8, "dynamicSize":0, "pointer":0},
{"staticSize":8, "dynamicSize":4, "NOT": {"pointer":0}}
]}]'''
[cases.vector_of_pointers_no_follow]
skip = "pointer field is missing from results" # https://github.com/facebookexperimental/object-introspection/issues/21
param_types = ["const std::vector<int*>&"]
setup = "return {{new int(1), nullptr, new int(3)}};"
expect_json = '''[{
"staticSize":24,
"dynamicSize":24,
"length":3,
"capacity":3,
"elementStaticSize":8,
"members":[
{"staticSize":8, "dynamicSize":0, "NOT": {"pointer":0}},
{"staticSize":8, "dynamicSize":0, "pointer":0},
{"staticSize":8, "dynamicSize":0, "NOT": {"pointer":0}}
]}]'''
[cases.feature_flag_disabled]
param_types = ["const PrimitivePtrs&"]
setup = "return PrimitivePtrs{0, new int(0), new int(0)};"
cli_options = ["-fchase-raw-pointers", "-Fchase-raw-pointers"]
expect_json = '''[{
"staticSize":24,
"dynamicSize":0,
"exclusiveSize":4,
"size":24,
"members":[
{"name":"a", "staticSize":4, "dynamicSize":0, "exclusiveSize":4, "size":4},
{"name":"b", "staticSize":8, "dynamicSize":0, "exclusiveSize":8, "size":8},
{"name":"c", "staticSize":8, "dynamicSize":0, "exclusiveSize":8, "size":8}
]}]'''
[cases.feature_config]
oil_disable = "oil can't chase raw pointers safely"
param_types = ["const std::vector<int*>&"]
setup = "return {{new int(1), nullptr, new int(3)}};"
config_prefix = 'features = ["chase-raw-pointers"]'
expect_json = '''[{
"staticSize":24,
"dynamicSize":32,
"length":3,
"capacity":3,
"elementStaticSize":8,
"members":[
{"staticSize":8, "dynamicSize":4, "NOT": {"pointer":0}},
{"staticSize":8, "dynamicSize":0, "pointer":0},
{"staticSize":8, "dynamicSize":4, "NOT": {"pointer":0}}
]}]'''