57 if (&p1Norm == &p2Norm)
65 auto p1OffsetInBytesOpt = p1Traced.getOffsetInBytes();
66 auto p2OffsetInBytesOpt = p2Traced.getOffsetInBytes();
67 JLM_ASSERT(p1OffsetInBytesOpt.has_value() && p2OffsetInBytesOpt.has_value());
69 if (p1Traced.BasePointer == p2Traced.BasePointer)
75 return QueryOffsets(p1OffsetInBytesOpt, s1, p2OffsetInBytesOpt, s2);
108 const auto & [p1Base, p1Offset] = *p1TraceCollection.
TopOrigins.begin();
109 const auto & [p2Base, p2Offset] = *p2TraceCollection.
TopOrigins.begin();
110 if (p1Base == p2Base)
123 if (*p1OffsetInBytesOpt > 0)
124 minimumP1OffsetFromStart =
125 std::max(minimumP1OffsetFromStart,
static_cast<size_t>(*p1OffsetInBytesOpt));
126 if (*p2OffsetInBytesOpt > 0)
127 minimumP2OffsetFromStart =
128 std::max(minimumP2OffsetFromStart,
static_cast<size_t>(*p2OffsetInBytesOpt));
157 if (p1AllTopsOriginal && p2AllTopsOriginal)
187 std::optional<int64_t> offset1,
189 std::optional<int64_t> offset2,
193 if (!offset1.has_value() || !offset2.has_value())
196 auto difference = *offset2 - *offset1;
201 if (difference >= 0 &&
static_cast<size_t>(difference) >= s1)
205 if (difference <= 0 &&
static_cast<size_t>(-difference) >= s2)
228 if (is<AllocaOperation>(node->GetOperation()))
231 if (is<MallocOperation>(node->GetOperation()))
241 for (
auto [output, offset] : traces.
TopOrigins)
267 if (elementCount.has_value())
273 const auto mallocSize =
275 if (mallocSize.has_value())
285 const std::optional<int64_t> & offsetInBytes)
288 if (!totalSize.has_value())
291 if (!offsetInBytes.has_value())
295 if (*offsetInBytes > 0 &&
static_cast<size_t>(*offsetInBytes) > *totalSize)
298 return *totalSize - *offsetInBytes;
308 if (remainingSize.has_value())
311 if (*remainingSize < s)
318 if (*remainingSize == s && !it->second.has_value())
328 std::optional<size_t> minimumOffset;
329 for (
auto [output, offset] : traces.
TopOrigins)
332 if (!offset.has_value())
338 if (minimumOffset.has_value())
339 minimumOffset = std::min(*minimumOffset,
static_cast<size_t>(*offset));
341 minimumOffset = offset;
344 if (minimumOffset.has_value())
345 return *minimumOffset;
359 if (originSize.has_value() && *originSize < s)
375 const auto offset = it->second;
393 for (
auto [p1Origin, p1Offset] : tc1.
TopOrigins)
399 auto p2Offset = p2Find->second;
410 for (
auto [output, offset] : traceCollection.
TopOrigins)
423 auto & output = *it->first;
427 auto argument = lambda->MapArgument(output);
428 if (std::holds_alternative<rvsdg::LambdaNode::ArgumentVar>(argument))
454 std::queue<const rvsdg::Output *> qu;
455 std::unordered_set<const rvsdg::Output *> added;
460 auto [_, inserted] = added.insert(&p);
468 auto & p = *qu.front();
472 for (
auto & user : p.Users())
476 auto input = gamma->MapInput(user);
479 auto entry = std::get_if<rvsdg::GammaNode::EntryVar>(&input);
482 for (
auto output : entry->branchArgument)
490 auto exitVar = gamma->MapBranchResultExitVar(user);
491 Enqueue(*exitVar.output);
498 auto loopVar = theta->MapInputLoopVar(user);
501 Enqueue(*loopVar.pre);
508 auto loopVar = theta->MapPostLoopVar(user);
509 Enqueue(*loopVar.pre);
510 Enqueue(*loopVar.output);
517 bool do_continue = MatchTypeWithDefault(
518 node->GetOperation(),
522 JLM_ASSERT(user.index() == 0);
523 Enqueue(*node->output(0));
529 JLM_ASSERT(user.index() == 0);
530 Enqueue(*node->output(0));
536 Enqueue(*node->output(0));
547 if (&user == &StoreOperation::AddressInput(*node))
static rvsdg::Input & sizeInput(const rvsdg::Node &node)
static void RemoveTopOriginsWithinTheFirstNBytes(TraceCollection &traces, size_t s, size_t N)
static bool IsOriginalOrigin(const rvsdg::Output &pointer)
~LocalAliasAnalysis() noexcept override
static bool hasOnlyAllocaTopOrigins(const TraceCollection &traceCollection)
bool HasOnlyFullyTraceableTopOrigins(TraceCollection &traces)
AliasQueryResponse Query(const rvsdg::Output &p1, size_t s1, const rvsdg::Output &p2, size_t s2) override
static std::optional< size_t > GetRemainingSize(const rvsdg::Output &basePointer, const std::optional< int64_t > &offsetInBytes)
static void removeArgumentTopOrigins(TraceCollection &traceCollection)
std::unordered_map< const rvsdg::Output *, bool > IsFullyTraceable_
static bool DoTraceCollectionsOverlap(TraceCollection &tc1, size_t s1, TraceCollection &tc2, size_t s2)
static void RemoveTopOriginsSmallerThanSize(TraceCollection &traces, size_t s)
void setMaxTraceCollectionSize(size_t maxTraceCollectionSize)
static bool HasOnlyOriginalTopOrigins(TraceCollection &traces)
static size_t GetMinimumOffsetFromStart(TraceCollection &traces)
size_t getMaxTraceCollectionSize()
bool IsOriginalOriginFullyTraceable(const rvsdg::Output &pointer)
size_t maxTraceCollectionSize_
static void RemoveTopOriginsWithRemainingSizeBelow(TraceCollection &traces, size_t s)
static AliasQueryResponse QueryOffsets(std::optional< int64_t > offset1, size_t s1, std::optional< int64_t > offset2, size_t s2)
static std::optional< size_t > GetOriginalOriginSize(const rvsdg::Output &pointer)
size_t GetTypeAllocSize(const rvsdg::Type &type)
bool TraceAllPointerOrigins(TracedPointerOrigin p, TraceCollection &traceCollection, const size_t maxTraceCollectionSize)
rvsdg::Output & traceOutput(rvsdg::Output &output, const rvsdg::Region *withinRegion)
TracedPointerOrigin TracePointerOriginPrecise(const rvsdg::Output &p)
static std::string ToString(const std::vector< MemoryNodeId > &memoryNodeIds)
std::optional< int64_t > tryGetConstantSignedInteger(const rvsdg::Output &output)
NodeType * TryGetOwnerNode(const rvsdg::Input &input) noexcept
Checks if this is an input to a node of specified type.
std::unordered_map< const rvsdg::Output *, std::optional< int64_t > > TopOrigins