Document the new DPF surfaces in one command set, and test the field, half-tree, and multipoint edges.
Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
parent
0d8a5a8131
commit
0dff6df8ed
250 changed files with 12199 additions and 1981 deletions
|
|
@ -67,6 +67,8 @@ inline auto eval_interval_interior(const DpfKey & dpf, IntegralT from_node,
|
|||
dpf.correction_word(level_index-1, 0),
|
||||
dpf.correction_word(level_index-1, 1)
|
||||
};
|
||||
const bool is_last = dpf_type::tree::is_last_level(level_index - 1,
|
||||
dpf.depth);
|
||||
|
||||
auto *prev = memoizer[level_index-1];
|
||||
auto *curr = memoizer[level_index];
|
||||
|
|
@ -74,7 +76,7 @@ inline auto eval_interval_interior(const DpfKey & dpf, IntegralT from_node,
|
|||
// process node which only requires a right traversal
|
||||
if (from_offset == true)
|
||||
{
|
||||
curr[i++] = dpf_type::traverse_interior(prev[j++], cw[1], 1);
|
||||
curr[i++] = dpf_type::traverse_interior(prev[j++], cw[1], 1, is_last);
|
||||
}
|
||||
// process all nodes which require both a left traversal and a right traversal
|
||||
const std::size_t both_end = nodes_at_level - to_offset;
|
||||
|
|
@ -88,7 +90,8 @@ inline auto eval_interval_interior(const DpfKey & dpf, IntegralT from_node,
|
|||
{
|
||||
parents[t] = prev[j + t];
|
||||
}
|
||||
dpf_type::traverse_interior01_x4(parents, cw[0], cw[1], left, right);
|
||||
dpf_type::traverse_interior01_x4(parents, cw[0], cw[1], left, right,
|
||||
is_last);
|
||||
DPF_UNROLL_LOOP
|
||||
for (std::size_t t = 0; t < 4; ++t)
|
||||
{
|
||||
|
|
@ -102,14 +105,15 @@ inline auto eval_interval_interior(const DpfKey & dpf, IntegralT from_node,
|
|||
for (; i < both_end;)
|
||||
{
|
||||
auto cur_node = prev[j++];
|
||||
auto kids = dpf_type::traverse_interior01(cur_node, cw[0], cw[1]);
|
||||
auto kids = dpf_type::traverse_interior01(cur_node, cw[0], cw[1],
|
||||
is_last);
|
||||
curr[i++] = kids[0];
|
||||
curr[i++] = kids[1];
|
||||
}
|
||||
// process node which only requires a left traversal
|
||||
if (to_offset == true)
|
||||
{
|
||||
curr[i] = dpf_type::traverse_interior(prev[j], cw[0], 0);
|
||||
curr[i] = dpf_type::traverse_interior(prev[j], cw[0], 0, is_last);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -135,6 +139,7 @@ inline auto eval_interval_exterior(const DpfKey & dpf, IntegralT from_node,
|
|||
HEDLEY_PRAGMA(GCC diagnostic push)
|
||||
HEDLEY_PRAGMA(GCC diagnostic ignored "-Wignored-attributes")
|
||||
auto cw = std::get<I>(dpf.leaf_nodes).get();
|
||||
HEDLEY_PRAGMA(GCC diagnostic pop)
|
||||
auto *nodes = memoizer[dpf_type::depth];
|
||||
DPF_UNROLL_LOOP
|
||||
for (std::size_t j = 0, k = start; j < nodes_in_interval; ++j, ++k)
|
||||
|
|
@ -151,7 +156,6 @@ HEDLEY_PRAGMA(GCC diagnostic ignored "-Wignored-attributes")
|
|||
sizeof(output_type) * dpf_type::outputs_per_leaf);
|
||||
}
|
||||
}
|
||||
HEDLEY_PRAGMA(GCC diagnostic pop)
|
||||
}
|
||||
|
||||
template <std::size_t I,
|
||||
|
|
@ -175,9 +179,23 @@ void store_interval_leaf(OutputBuffer && outbuf, std::size_t k, const LeafT & le
|
|||
}
|
||||
}
|
||||
|
||||
/// One pass over the leaf-level interior nodes. When the selected output
|
||||
/// @brief One pass over the leaf-level interior nodes. When the selected output
|
||||
/// indices occupy a contiguous PRG-position range, a single batched
|
||||
/// `ExteriorPRG::eval` produces every output's leaf mask.
|
||||
/// @tparam Is is
|
||||
/// @tparam DpfKey DPF key type
|
||||
/// @tparam OutputBuffers tuple of output buffers
|
||||
/// @tparam IntervalMemoizer interval memoizer type
|
||||
/// @tparam IntegralT integral type
|
||||
/// @tparam IIs iis
|
||||
/// @param dpf the DPF key
|
||||
/// @param from_node the `from_node`
|
||||
/// @param to_node the `to_node`
|
||||
/// @param outbufs the named output buffers
|
||||
/// @param memoizer the memoizer built for this key
|
||||
/// @param IIs the `IIs`
|
||||
/// @param start the start of the range
|
||||
/// @throws std::runtime_error if `to_node<from_node`
|
||||
template <std::size_t ...Is,
|
||||
typename DpfKey,
|
||||
typename OutputBuffers,
|
||||
|
|
@ -194,7 +212,10 @@ inline void eval_interval_exterior_fused(const DpfKey & dpf, IntegralT from_node
|
|||
|
||||
using node_type = typename DpfKey::exterior_node;
|
||||
using outputs_tuple = typename DpfKey::concrete_outputs_tuple;
|
||||
HEDLEY_PRAGMA(GCC diagnostic push)
|
||||
HEDLEY_PRAGMA(GCC diagnostic ignored "-Wignored-attributes")
|
||||
using range = leaf_prg_range<node_type, outputs_tuple, Is...>;
|
||||
HEDLEY_PRAGMA(GCC diagnostic pop)
|
||||
|
||||
std::size_t nodes_in_interval = static_cast<std::size_t>(to_node - from_node);
|
||||
auto *nodes = memoizer[DpfKey::depth];
|
||||
|
|
@ -312,7 +333,10 @@ void eval_interval_exterior_all(const DpfKey & dpf, IntegralT from_node,
|
|||
{
|
||||
using node_type = typename DpfKey::exterior_node;
|
||||
using outputs_tuple = typename DpfKey::concrete_outputs_tuple;
|
||||
HEDLEY_PRAGMA(GCC diagnostic push)
|
||||
HEDLEY_PRAGMA(GCC diagnostic ignored "-Wignored-attributes")
|
||||
using range = leaf_prg_range<node_type, outputs_tuple, Is...>;
|
||||
HEDLEY_PRAGMA(GCC diagnostic pop)
|
||||
if constexpr (range::is_contiguous)
|
||||
{
|
||||
eval_interval_exterior_fused<Is...>(dpf, from_node, to_node, outbufs,
|
||||
|
|
@ -397,10 +421,26 @@ auto eval_interval(const DpfKey & dpf, InputT from, InputT to,
|
|||
|
||||
} // namespace internal
|
||||
|
||||
/// Write outputs `I, Is...` for `[from, to]` into `outbufs`.
|
||||
/// @param outbufs Named buffer, or a tuple of buffers when several outputs
|
||||
/// @name Closed-interval evaluation
|
||||
/// @tparam I output index
|
||||
/// @tparam Is the remaining output indices
|
||||
/// @tparam DpfKey DPF key type
|
||||
/// @tparam InputT input domain type
|
||||
/// @param dpf the DPF key
|
||||
/// @param from the inclusive start of the range
|
||||
/// @param to the inclusive end of the range
|
||||
/// @{
|
||||
|
||||
/// @brief Write outputs `I, Is...` for `[from, to]` into `outbufs`.
|
||||
/// @tparam OutputBuffers tuple of output buffers
|
||||
/// @tparam IntervalMemoizer interval memoizer type
|
||||
/// @param dpf the DPF key
|
||||
/// @param from the inclusive start of the range
|
||||
/// @param to the inclusive end of the range
|
||||
/// @param outbufs named buffer, or a tuple of buffers when several outputs
|
||||
/// are selected. Must outlive the returned iterable.
|
||||
/// @param memoizer Workspace sized for at least this interval.
|
||||
/// @param memoizer workspace sized for at least this interval
|
||||
/// @return an iterable over the written outputs
|
||||
template <std::size_t I = 0,
|
||||
std::size_t ...Is,
|
||||
typename DpfKey,
|
||||
|
|
@ -417,7 +457,13 @@ auto eval_interval(const DpfKey & dpf, InputT from, InputT to,
|
|||
return internal::eval_interval<I, Is...>(dpf, dpf.offset_x(from), dpf.offset_x(to), outbufs, memoizer, std::make_index_sequence<1+sizeof...(Is)>());
|
||||
}
|
||||
|
||||
/// Evaluate `[from, to]` into `outbufs`, allocating a basic interval memoizer.
|
||||
/// @brief Evaluate `[from, to]` into `outbufs`, allocating a basic interval memoizer.
|
||||
/// @tparam OutputBuffers tuple of output buffers
|
||||
/// @param dpf the DPF key
|
||||
/// @param from the inclusive start of the range
|
||||
/// @param to the inclusive end of the range
|
||||
/// @param outbufs the named output buffers
|
||||
/// @return an iterable over the written outputs
|
||||
template <std::size_t I = 0,
|
||||
std::size_t ...Is,
|
||||
typename DpfKey,
|
||||
|
|
@ -435,7 +481,12 @@ auto eval_interval(const DpfKey & dpf, InputT from, InputT to,
|
|||
dpf::make_basic_interval_memoizer<DpfKey>(from, to));
|
||||
}
|
||||
|
||||
/// Evaluate `[from, to]` with a caller-supplied memoizer.
|
||||
/// @brief Evaluate `[from, to]` with a caller-supplied memoizer.
|
||||
/// @tparam IntervalMemoizer interval memoizer type
|
||||
/// @param dpf the DPF key
|
||||
/// @param from the inclusive start of the range
|
||||
/// @param to the inclusive end of the range
|
||||
/// @param memoizer the memoizer built for this key
|
||||
/// @return `std::pair` of a new buffer (or tuple of buffers) and an iterable
|
||||
/// into that buffer.
|
||||
template <std::size_t I = 0,
|
||||
|
|
@ -462,7 +513,9 @@ auto eval_interval(const DpfKey & dpf, InputT from, InputT to,
|
|||
return std::make_pair(std::move(outbufs), std::move(iterable));
|
||||
}
|
||||
|
||||
/// Evaluate `[from, to]`, allocating a basic interval memoizer and a buffer.
|
||||
/// @brief Evaluate `[from, to]`, allocating a basic interval memoizer and a buffer.
|
||||
/// @return `std::pair` of a new buffer (or tuple of buffers) and an iterable
|
||||
/// into that buffer.
|
||||
template <std::size_t I = 0,
|
||||
std::size_t ...Is,
|
||||
typename DpfKey,
|
||||
|
|
@ -475,6 +528,8 @@ auto eval_interval(const DpfKey & dpf, InputT from, InputT to)
|
|||
dpf::make_basic_interval_memoizer<DpfKey>(from, to));
|
||||
}
|
||||
|
||||
/// @}
|
||||
|
||||
} // namespace dpf
|
||||
|
||||
#endif // LIBDPF_INCLUDE_DPF_EVAL_INTERVAL_HPP__
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue