blob: 94abce22ba268aeecbfe7b504c49f2a99d522dec [file] [log] [blame]
/*
* Copyright (C) 2025 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#ifndef SRC_PROTOVM_NODE_H_
#define SRC_PROTOVM_NODE_H_
#include <type_traits>
#include <variant>
#include "src/base/intrusive_tree.h"
#include "src/protovm/owned_ptr.h"
#include "src/protovm/scalar.h"
namespace perfetto {
namespace protovm {
struct Node;
namespace internal {
struct MapNode {
struct Traits {
using KeyType = uint64_t;
static constexpr size_t NodeOffset() {
static_assert(std::is_standard_layout_v<MapNode>);
return offsetof(MapNode, node);
}
static const KeyType& GetKey(const MapNode& n) { return n.key; }
};
MapNode(uint64_t k, OwnedPtr<Node> v) : key{k}, value{std::move(v)} {}
base::IntrusiveTreeNode node{};
uint64_t key;
OwnedPtr<Node> value;
};
} // namespace internal
using IntrusiveMap =
base::IntrusiveTree<internal::MapNode, internal::MapNode::Traits>;
struct Node {
using MapNode = internal::MapNode;
struct Bytes {
OwnedPtr<void> data;
size_t size;
};
struct Empty {};
struct MappedRepeatedField {
IntrusiveMap key_to_node;
};
struct IndexedRepeatedField {
IntrusiveMap index_to_node;
// Flag needed to track the merge state of indexed repeated field
// (see implementation of Merge operation in RW proto)
bool has_been_merged;
};
struct Message {
IntrusiveMap field_id_to_node;
};
template <class T>
T* GetIf() {
return std::get_if<T>(&value);
}
template <class T>
const T* GetIf() const {
return std::get_if<T>(&value);
}
const char* GetTypeName() const;
std::variant<Bytes,
Empty,
IndexedRepeatedField,
MapNode,
MappedRepeatedField,
Message,
Scalar>
value;
};
Node& GetOuterNode(Node::MapNode& map_node);
} // namespace protovm
} // namespace perfetto
#endif // SRC_PROTOVM_NODE_H_