Legion Runtime
Loading...
Searching...
No Matches
types.h
Go to the documentation of this file.
1/* Copyright 2026 Stanford University, NVIDIA Corporation
2 *
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16#ifndef __LEGION_TYPES_H__
17#define __LEGION_TYPES_H__
18
24#include <cassert>
25#include <limits>
26#include <optional>
27#include <functional>
28
29#include "realm.h"
30#include "realm/id.h"
31#include "realm/dynamic_templates.h"
32#include "legion/api/config.h"
33
34// Sanity check that the build knows what it is doing
35static_assert(
36 REALM_MAX_DIM == LEGION_MAX_DIM,
37 "LEGION_MAX_DIM and REALM_MAX_DIM must be the same");
38
39#ifdef LEGION_REDOP_COMPLEX
40#ifdef LEGION_REDOP_HALF
41#define COMPLEX_HALF
42#endif
43#include "mathtypes/complex.h"
44#endif
45
46#ifdef LEGION_REDOP_HALF
47#include "mathtypes/half.h"
48#endif
49
50#ifndef LEGION_DEPRECATED
51// This is from before Legion required c++17
52#define LEGION_DEPRECATED(x) [[deprecated(x)]]
53#endif
54
55// clang-format off
56// Macros for disabling and re-enabling deprecated warnings
57#if defined(__PGIC__)
58// PGI has to go first because it also responds to GCC defines
59#define LEGION_DISABLE_DEPRECATED_WARNINGS \
60 _Pragma("warning (push)") \
61 _Pragma("diag_suppress 1445")
62#define LEGION_REENABLE_DEPRECATED_WARNINGS \
63 _Pragma("warning (pop)")
64#elif defined(__GNUC__)
65#define LEGION_DISABLE_DEPRECATED_WARNINGS \
66 _Pragma("GCC diagnostic push") \
67 _Pragma("GCC diagnostic ignored \"-Wdeprecated-declarations\"")
68#define LEGION_REENABLE_DEPRECATED_WARNINGS \
69 _Pragma("GCC diagnostic pop")
70#elif defined(__clang__)
71#define LEGION_DISABLE_DEPRECATED_WARNINGS \
72 _Pragma("clang diagnostic push") \
73 _Pragma("clang diagnostic ignored \"-Wdeprecated-declarations\"")
74#define LEGION_REENABLE_DEPRECATED_WARNINGS \
75 _Pragma("clang diagnostic pop")
76#elif defined(__INTEL_COMPILER) || defined(__INTEL_LLVM_COMPILER)
77#define LEGION_DISABLE_DEPRECATED_WARNINGS \
78 _Pragma("warning push") \
79 _Pragma("warning disable 1478")
80#define LEGION_REENABLE_DEPRECATED_WARNINGS \
81 _Pragma("warning pop")
82#else
83#warning "Don't know how to suppress deprecated warnings for this compiler"
84#define LEGION_DISABLE_DEPRECATED_WARNINGS
85#define LEGION_REENABLE_DEPRECATED_WARNINGS
86#endif
87// clang-format on
88
89#ifdef LEGION_DEBUG
90#define legion_assert(expr) assert(expr)
91#ifndef NDEBUG
92#define legion_no_skip_assert(expr) assert(expr)
93#else
94#error \
95 "Why are you trying to build a debug version of Legion while also defining NDEBUG?"
96#endif
97template<typename T1, typename T2>
98inline T1 legion_safe_cast(T2* ptr)
99{
100 T1 result = dynamic_cast<T1>(ptr);
101 legion_assert(result != nullptr);
102 return result;
103}
104#else // !LEGION_DEBUG
105#define legion_assert(expr) ((void)0)
106#define legion_no_skip_assert(expr) ((void)(expr))
107template<typename T1, typename T2>
108inline T1 legion_safe_cast(T2* ptr)
109{
110 return static_cast<T1>(ptr);
111}
112#endif
113
118namespace Legion {
119
120 // Pull C types into the C++ namespace
121 typedef ::realm_id_t IDType;
122 typedef ::legion_privilege_mode_t PrivilegeMode;
123 typedef ::legion_allocate_mode_t AllocateMode;
124 typedef ::legion_coherence_property_t CoherenceProperty;
125 typedef ::legion_region_flags_t RegionFlags;
126 typedef ::legion_projection_type_t ProjectionType;
127 typedef ::legion_partition_kind_t PartitionKind;
128 typedef ::legion_external_resource_t ExternalResource;
129 typedef ::legion_timing_measurement_t TimingMeasurement;
130 typedef ::legion_dependence_type_t DependenceType;
131 typedef ::legion_mappable_type_id_t MappableType;
132 typedef ::legion_file_mode_t LegionFileMode;
133 typedef ::legion_execution_constraint_t ExecutionConstraintKind;
134 typedef ::legion_layout_constraint_t LayoutConstraintKind;
135 typedef ::legion_equality_kind_t EqualityKind;
136 typedef ::legion_dimension_kind_t DimensionKind;
137 typedef ::legion_isa_kind_t ISAKind;
138 typedef ::legion_resource_constraint_t ResourceKind;
139 typedef ::legion_launch_constraint_t LaunchKind;
140 typedef ::legion_specialized_constraint_t SpecializedKind;
141 typedef ::legion_unbounded_pool_scope_t UnboundPoolScope;
142 typedef ::legion_projection_type_t HandleType;
143 typedef ::legion_address_space_t AddressSpace;
144 typedef ::legion_task_priority_t TaskPriority;
145 typedef ::legion_task_priority_t RealmPriority;
146 typedef ::legion_garbage_collection_priority_t GCPriority;
147 typedef ::legion_color_t Color;
148 typedef ::legion_field_id_t FieldID;
149 typedef ::legion_trace_id_t TraceID;
150 typedef ::legion_mapper_id_t MapperID;
151 typedef ::legion_context_id_t ContextID;
152 typedef ::legion_instance_id_t InstanceID;
153 typedef ::legion_index_tree_id_t IndexTreeID;
154 typedef ::legion_generation_id_t GenerationID;
155 typedef ::legion_type_handle TypeHandle;
156 typedef ::legion_projection_id_t ProjectionID;
157 typedef ::legion_sharding_id_t ShardingID;
158 typedef ::legion_concurrent_id_t ConcurrentID;
159 typedef ::legion_exception_handler_id_t ExceptionHandlerID;
160 typedef ::legion_region_tree_id_t RegionTreeID;
161 typedef ::legion_distributed_id_t DistributedID;
162 typedef ::legion_address_space_t AddressSpaceID;
163 typedef ::legion_tunable_id_t TunableID;
164 typedef ::legion_local_variable_id_t LocalVariableID;
165 typedef ::legion_mapping_tag_id_t MappingTagID;
166 typedef ::legion_semantic_tag_t SemanticTag;
167 typedef ::legion_variant_id_t VariantID;
168 typedef ::legion_code_descriptor_id_t CodeDescriptorID;
169 typedef ::legion_unique_id_t UniqueID;
170 typedef ::legion_version_id_t VersionID;
171 typedef ::legion_projection_epoch_id_t ProjectionEpochID;
172 typedef ::legion_task_id_t TaskID;
173 typedef ::legion_layout_constraint_id_t LayoutConstraintID;
174 typedef ::legion_shard_id_t ShardID;
175 typedef ::legion_provenance_id_t ProvenanceID;
176 typedef ::legion_internal_color_t LegionColor;
177 typedef ::legion_reduction_op_id_t ReductionOpID;
178 typedef ::legion_custom_serdez_id_t CustomSerdezID;
179 typedef ::legion_coord_t coord_t;
180
181 // Pull Realm types into the Legion namespace
182 typedef Realm::Runtime RealmRuntime;
183 typedef Realm::Machine Machine;
184 typedef Realm::Memory Memory;
185 typedef Realm::Processor Processor;
186 typedef Realm::ProcessorGroup ProcessorGroup;
187 typedef Realm::CodeDescriptor CodeDescriptor;
188 typedef Realm::Reservation Reservation;
189 typedef Realm::CompletionQueue CompletionQueue;
190 typedef Realm::ReductionOpUntyped ReductionOp;
191 typedef Realm::CustomSerdezUntyped SerdezOp;
192 typedef Realm::Machine::ProcessorMemoryAffinity ProcessorMemoryAffinity;
193 typedef Realm::Machine::MemoryMemoryAffinity MemoryMemoryAffinity;
194 typedef Realm::DynamicTemplates::TagType TypeTag;
195 typedef Realm::Logger Logger;
196 template<int DIM, typename T = coord_t>
197 using Point = Realm::Point<DIM, T>;
198 template<int DIM, typename T = coord_t>
199 using Rect = Realm::Rect<DIM, T>;
200 template<int DIM, typename T = coord_t>
201 using DomainT = Realm::IndexSpace<DIM, T>;
202 template<int M, int N, typename T = coord_t>
203 using Transform = Realm::Matrix<M, N, T>;
204
205 // Forward declarations of types in the public interface
206 class IndexSpace;
207 template<int DIM, typename T>
208 class IndexSpaceT;
209 class IndexPartition;
210 template<int DIM, typename T>
211 class IndexPartitionT;
212 class FieldSpace;
213 class LogicalRegion;
214 template<int DIM, typename T>
215 class LogicalRegionT;
216 class LogicalPartition;
217 template<int DIM, typename T>
218 class LogicalPartitionT;
219 class IndexAllocator;
220 class FieldAllocator;
221 class UntypedBuffer;
222 class ArgumentMap;
223 class Lock;
224 struct LockRequest;
225 class Grant;
226 class PhaseBarrier;
227 struct RegionRequirement;
228 struct OutputRequirement;
229 struct IndexSpaceRequirement;
230 struct FieldSpaceRequirement;
231 struct TaskLauncher;
232 struct IndexTaskLauncher;
233 typedef IndexTaskLauncher IndexLauncher; // for backwards compatibility
234 struct InlineLauncher;
235 struct CopyLauncher;
236 struct AcquireLauncher;
237 struct ReleaseLauncher;
238 struct FillLauncher;
239 struct LayoutConstraintRegistrar;
240 struct TaskVariantRegistrar;
241 struct PoolBounds;
242 class Future;
243 class FutureMap;
244 class Predicate;
245 class PhysicalRegion;
246 class OutputRegion;
247 class ExternalResources;
248 class UntypedDeferredValue;
249 template<typename>
250 class DeferredValue;
251 template<typename, bool>
252 class DeferredReduction;
253 template<typename, int, typename, bool>
254 class DeferredBuffer;
255 template<typename COORD_T>
256 class UntypedDeferredBuffer;
257 template<PrivilegeMode, typename, int, typename, typename, bool>
258 class FieldAccessor;
259 template<typename, bool, int, typename, typename, bool>
260 class ReductionAccessor;
261 template<typename, int, typename, typename, bool>
262 class PaddingAccessor;
263#ifdef LEGION_MULTI_REGION_ACCESSOR
264 template<typename, int, typename, typename, bool, bool, int>
265 class MultiRegionAccessor;
266#endif
267 template<typename, int, typename, typename>
269 namespace ArraySyntax {
270 template<typename, PrivilegeMode>
272 template<typename>
274 } // namespace ArraySyntax
275 class PieceIterator;
276 template<int, typename>
277 class PieceIteratorT;
278 template<PrivilegeMode, typename, int, typename>
279 class SpanIterator;
280 struct InputArgs;
282 class ProjectionFunctor;
283 class ShardingFunctor;
284 class ExceptionHandler;
285 class Task;
286 class Copy;
287 class InlineMapping;
288 class Acquire;
289 class Release;
290 class Close;
291 class Fill;
292 class Partition;
293 class MustEpoch;
295 class Runtime;
296 class LegionHandshake;
297 class MPILegionHandshake;
298 // Helper for saving instantiated template functions
299 struct SerdezRedopFns;
300 // Some typedefs for making things nicer for users with C++11 support
301 template<typename FT, int N, typename T = ::legion_coord_t>
302 using GenericAccessor = Realm::GenericAccessor<FT, N, T>;
303 template<typename FT, int N, typename T = ::legion_coord_t>
304 using AffineAccessor = Realm::AffineAccessor<FT, N, T>;
305 template<typename FT, int N, typename T = ::legion_coord_t>
306 using MultiAffineAccessor = Realm::MultiAffineAccessor<FT, N, T>;
307 class LegionTaskWrapper;
308 class LegionSerialization;
309 class CObjectWrapper;
310 class DomainPoint;
311 class Domain;
312 class ISAConstraint;
314 class ResourceConstraint;
315 class LaunchConstraint;
319 class MemoryConstraint;
320 class FieldConstraint;
321 class PaddingConstraint;
322 class OrderingConstraint;
323 class TilingConstraint;
326 class OffsetConstraint;
327 class PointerConstraint;
330 class Mappable;
331 class Task;
332 class Copy;
333 class Fill;
334 class InlineMapping;
335 class Acquire;
336 class Release;
337 class Partition;
338 class Close;
339 class MustEpoch;
340
341 // A class for preventing serialization of Legion objects
342 // which cannot be serialized
343 class Unserializable { };
344 class Serializer;
345 class Deserializer;
346
347 // Typedefs that are needed everywhere
348 typedef std::map<CustomSerdezID, const Realm::CustomSerdezUntyped*>
349 SerdezOpTable;
350 typedef std::map<Realm::ReductionOpID, Realm::ReductionOpUntyped*>
351 ReductionOpTable;
352 typedef void (*SerdezInitFnptr)(const ReductionOp*, void*&, size_t&);
353 typedef void (*SerdezFoldFnptr)(
354 const ReductionOp*, void*&, size_t&, const void*);
355 using SerdezInitFunc =
356 std::function<void(const ReductionOp*, void*&, size_t&)>;
357 using SerdezFoldFunc =
358 std::function<void(const ReductionOp*, void*&, size_t&, const void*)>;
359 typedef std::map<Realm::ReductionOpID, SerdezRedopFns> SerdezRedopTable;
360
361 typedef void (*RegistrationCallbackFnptr)(
362 Machine machine, Runtime* rt, const std::set<Processor>& local_procs);
363 using RegistrationCallback =
364 std::function<void(Machine, Runtime*, const std::set<Processor>&)>;
365 typedef void (*RegistrationWithArgsCallbackFnptr)(
366 const RegistrationCallbackArgs& args);
367 using RegistrationWithArgsCallback =
368 std::function<void(const RegistrationCallbackArgs&)>;
369 typedef LogicalRegion (*RegionProjectionFnptr)(
370 LogicalRegion parent, const DomainPoint&, Runtime* rt);
371 typedef LogicalRegion (*PartitionProjectionFnptr)(
372 LogicalPartition parent, const DomainPoint&, Runtime* rt);
373
374 // Forward declarations for the mapping namespace
375 namespace Mapping {
376 class PhysicalInstance;
377 class CollectiveView;
378 class MapperEvent;
379 class ProfilingRequestSet;
380 class Mapper;
381 class MapperRuntime;
382 class AutoLock;
383 class DefaultMapper;
384 class ShimMapper;
385 class TestMapper;
386 class DebugMapper;
387 class ReplayMapper;
388
389 // The following types are effectively overlaid on the Realm versions
390 // to allow for Legion-specific profiling measurements
391 enum ProfilingMeasurementID {
392 PMID_LEGION_FIRST = Realm::PMID_REALM_LAST,
393 PMID_RUNTIME_OVERHEAD,
394 };
395 } // namespace Mapping
396
397 namespace Internal {
398 class LocalLock;
399 class AutoLock;
400 class AutoTryLock;
401 class LgEvent; // base event type for legion
402 class ApEvent; // application event
403 class ApUserEvent; // application user event
404 class ApBarrier; // application barrier
405 class RtEvent; // runtime event
406 class RtUserEvent; // runtime user event
407 class RtBarrier;
408
409 struct RegionUsage;
410 class Collectable;
411 class FieldAllocatorImpl;
412 class ArgumentMapImpl;
413 class FutureCreateInstanceRequest;
414 class FutureMapFutureRequest;
415 class FutureImpl;
416 class FutureInstance;
417 class FutureMapImpl;
418 class ReplFutureMapImpl;
419 class PhysicalRegionImpl;
420 class OutputRegionImpl;
421 class ExternalResourcesImpl;
422 class PieceIteratorImpl;
423 class GrantImpl;
424 class PredicateImpl;
425 class HandshakeImpl;
426 typedef HandshakeImpl LegionHandshakeImpl;
427 class MessageManager;
428 class ShutdownManager;
429 class ProcessorManager;
430 class MemoryManager;
431 class MemoryPool;
432 class VirtualChannel;
433 class MessageManager;
434 class ShutdownManager;
435 class TaskImpl;
436 class VariantImpl;
437 class LayoutConstraints;
438 class ProjectionFunction;
439 class ShardingFunction;
440 class Runtime;
441
442 class Provenance;
443 class Operation;
444 class MemoizableOp;
445 class PredicatedOp;
446 class MapOp;
447 class CopyOp;
448 class IndexCopyOp;
449 class PointCopyOp;
450 class FenceOp;
451 class FrameOp;
452 class CreationOp;
453 class DeletionOp;
454 class InternalOp;
455 class CloseOp;
456 class MergeCloseOp;
457 class PostCloseOp;
458 class RefinementOp;
459 class ResetOp;
460 class AcquireOp;
461 class ReleaseOp;
462 class DynamicCollectiveOp;
463 class FuturePredOp;
464 class NotPredOp;
465 class AndPredOp;
466 class OrPredOp;
467 class MustEpochOp;
468 class PendingPartitionOp;
469 class DependentPartitionOp;
470 class PointDepPartOp;
471 class FillOp;
472 class IndexFillOp;
473 class PointFillOp;
474 class DiscardOp;
475 class AttachOp;
476 class IndexAttachOp;
477 class PointAttachOp;
478 class DetachOp;
479 class IndexDetachOp;
480 class PointDetachOp;
481 class TimingOp;
482 class TunableOp;
483 class AllReduceOp;
484 class BeginOp;
485 class CompleteOp;
486 class RecurrentOp;
487 class ExternalMappable;
488 class RemoteOp;
489 class RemoteMapOp;
490 class RemoteCopyOp;
491 class RemoteCloseOp;
492 class RemoteAcquireOp;
493 class RemoteReleaseOp;
494 class RemoteFillOp;
495 class RemotePartitionOp;
496 class RemoteReplayOp;
497 class RemoteSummaryOp;
498 template<typename OP>
500 template<typename OP>
502 struct PointwiseDependence;
503
504 class ExternalTask;
505 class TaskOp;
506 class RemoteTaskOp;
507 class SingleTask;
508 class MultiTask;
509 class IndividualTask;
510 class PointTask;
511 class ShardTask;
512 class IndexTask;
513 class SliceTask;
514 class RemoteTask;
515
516 class TaskContext;
517 class InnerContext;
518 class TopLevelContext;
519 class ReplicateContext;
520 class RemoteContext;
521 class LeafContext;
522
523 class LogicalTrace;
524 class TraceBeginOp;
525 class TraceRecurrentOp;
526 class TraceCompleteOp;
527 class PhysicalTrace;
528 class TraceViewSet;
529 class TraceConditionSet;
530 class PhysicalTemplate;
531 class ShardedPhysicalTemplate;
532 class Instruction;
533 class GetTermEvent;
534 class ReplayMapping;
535 class CreateApUserEvent;
536 class TriggerEvent;
537 class MergeEvent;
538 class AssignFenceCompletion;
539 class IssueCopy;
540 class IssueFill;
541 class IssueAcross;
542 class GetOpTermEvent;
543 class SetOpSyncEvent;
544 class SetEffects;
545 class CompleteReplay;
546 class AcquireReplay;
547 class ReleaseReplay;
548 class BarrierArrival;
549 class BarrierAdvance;
550 class TraceRecognizer;
551 class TraceHashRecorder;
552
553 class CopyAcrossExecutor;
554 class CopyAcrossUnstructured;
555 class IndexSpaceExpression;
556 class IndexSpaceOperation;
557 template<int DIM, typename T>
559 template<int DIM, typename T>
561 template<int DIM, typename T>
563 template<int DIM, typename T>
565 class ExpressionTrieNode;
566 class IndexTreeNode;
567 class IndexSpaceNode;
568 template<int DIM, typename T>
570 class IndexPartNode;
571 template<int DIM, typename T>
573 class FieldSpaceNode;
574 class RegionTreeNode;
575 class RegionNode;
576 class PartitionNode;
577 class ColorSpaceIterator;
578 template<int DIM, typename T>
580 class KDTree;
581 template<int DIM, typename T, typename RT = void>
582 class KDNode;
583 class EqKDTree;
584 template<int DIM, typename T>
586
587 class RegionTreePath;
588 class PathTraverser;
589 class NodeTraverser;
590
591 class LogicalState;
592 class LogicalAnalysis;
593 class PhysicalAnalysis;
594 class ValidInstAnalysis;
595 class InvalidInstAnalysis;
596 class AntivalidInstAnalysis;
597 class RegistrationAnalysis;
598 class CollectiveAnalysis;
599 class UpdateAnalysis;
600 class CopyAcrossAnalysis;
601 class AcquireAnalysis;
602 class ReleaseAnalysis;
603 class OverwriteAnalysis;
604 class FilterAnalysis;
605 class EquivalenceSet;
606 class EqSetTracker;
607 class VersionManager;
608 class VersionInfo;
609 class ProjectionNode;
610 class ProjectionRegion;
611 class ProjectionPartition;
612 class RefinementTracker;
613 class RegionRefinementTracker;
614 class PartitionRefinementTracker;
615 class CopyFillGuard;
616 class CopyFillAggregator;
617
618 class Collectable;
619 class ImplicitReferenceTracker;
620 class DistributedCollectable;
621 class LayoutDescription;
622 class InstanceManager; // base class for all instances
623 class CopyAcrossHelper;
624 class LogicalView; // base class for instance and reduction
625 class InstanceKey;
626 class InstanceView;
627 class CollectableView; // pure virtual class
628 class IndividualView;
629 class NodeView;
630 class SpaceView;
631 class PartitionView;
632 class CollectiveView;
633 class MaterializedView;
634 class ReplicatedView;
635 class ReductionView;
636 class AllreduceView;
637 class DeferredView;
638 class FillView;
639 class PhiView;
640 class MappingRef;
641 class InstanceRef;
642 class InstanceSet;
643 class InnerTaskView;
644 class VirtualManager;
645 class PhysicalManager;
646 class InstanceBuilder;
647
648 class RegionAnalyzer;
649 class RegionMapper;
650
651 struct LogicalUser;
652 struct PhysicalUser;
653 struct LogicalTraceInfo;
654 struct TraceInfo;
655 struct PhysicalTraceInfo;
656 struct UniqueInst;
657 class TreeCloseImpl;
658 class TreeClose;
659 struct CloseInfo;
660 struct FieldDataDescriptor;
661 class ProjectionSummary;
662 class ProjectionInfo;
663
664 class LegionProfiler;
665 class LegionProfInstance;
666
667 class MappingCallInfo;
668 class MapperManager;
669 class SerializingManager;
670 class ConcurrentManager;
671
672 class ShardedMapping;
673 class ReplIndividualTask;
674 class ReplIndexTask;
675 class ReplMergeCloseOp;
676 class ReplRefinementOp;
677 class ReplResetOp;
678 class ReplFillOp;
679 class ReplIndexFillOp;
680 class ReplDiscardOp;
681 class ReplCopyOp;
682 class ReplIndexCopyOp;
683 class ReplDeletionOp;
684 class ReplPendingPartitionOp;
685 class ReplDependentPartitionOp;
686 class ReplPredicateImpl;
687 class ReplMustEpochOp;
688 class ReplTimingOp;
689 class ReplTunableOp;
690 class ReplAllReduceOp;
691 class ReplFenceOp;
692 class ReplMapOp;
693 class ReplAttachOp;
694 class ReplIndexAttachOp;
695 class ReplDetachOp;
696 class ReplIndexDetachOp;
697 class ReplAcquireOp;
698 class ReplReleaseOp;
699 class ReplTraceOp;
700 class ReplTraceBeginOp;
701 class ReplTraceRecurrentOp;
702 class ReplTraceCompleteOp;
703 class ShardMapping;
704 class CollectiveMapping;
705 class ShardManager;
706 class ImplicitShardManager;
707 class ShardCollective;
708 class GatherCollective;
709 template<bool>
711 template<typename T>
713 template<typename T>
715 template<typename T, bool>
717 class CrossProductCollective;
718 class ShardingGatherCollective;
719 class FieldDescriptorExchange;
720 class FieldDescriptorGather;
721 class FutureBroadcast;
722 class FutureExchange;
723 class FutureNameExchange;
724 class MustEpochMappingBroadcast;
725 class MustEpochMappingExchange;
726 class PredicateCollective;
727 class UnorderedExchange;
728 class ShardRendezvous;
729 class ProjectionTreeExchange;
730 class TimeoutMatchExchange;
731 class ConcurrentAllreduce;
732 class BufferBroadcast;
733 class CreateCollectiveFillView;
734
735 // The invalid color
736 constexpr LegionColor INVALID_COLOR =
737 std::numeric_limits<LegionColor>::max();
738 // This is only needed internally
739 typedef Realm::RegionInstance PhysicalInstance;
740 typedef Realm::CopySrcDstField CopySrcDstField;
741 typedef unsigned long long CollectiveID;
742 typedef unsigned long long IndexSpaceExprID;
743 typedef uint64_t LamportClock;
744 struct ContextCoordinate;
745 typedef ContextCoordinate TraceLocalID;
746 class TaskTreeCoordinates;
747 // Helper for encoding templates
748 struct NT_TemplateHelper : public Realm::DynamicTemplates::ListProduct2<
749 Realm::DIMCOUNTS, Realm::DIMTYPES> {
750 typedef Realm::DynamicTemplates::ListProduct2<
751 Realm::DIMCOUNTS, Realm::DIMTYPES>
752 SUPER;
753 public:
754 template<int N, typename T>
755 __LEGION_CUDA_HD__ static inline constexpr TypeTag encode_tag(void)
756 {
757 constexpr TypeTag type =
758 SUPER::template encode_tag<Realm::DynamicTemplates::Int<N>, T>();
759 static_assert(type != 0, "All types should be non-zero for Legion");
760 return type;
761 }
762 template<int N, typename T>
763 static inline void check_type(const TypeTag t)
764 {
765 legion_assert((encode_tag<N, T>() == t));
766 }
767 struct DimHelper {
768 public:
769 template<typename N, typename T>
770 static inline void demux(int* result)
771 {
772 *result = N::N;
773 }
774 };
775 static inline int get_dim(const TypeTag t)
776 {
777 int result = 0;
778 SUPER::demux<DimHelper>(t, &result);
779 return result;
780 }
781 };
782 // Pull some of the mapper types into the internal space
783 typedef Mapping::Mapper Mapper;
784 typedef Mapping::MapperEvent MapperEvent;
785 typedef Mapping::PhysicalInstance MappingInstance;
786 typedef Mapping::CollectiveView MappingCollective;
787 typedef Mapping::ProfilingMeasurementID ProfilingMeasurementID;
788 } // namespace Internal
789
790 // Magical typedefs
791 typedef Internal::TaskContext* Context;
792 // More magical typedefs for the mapping namespace
793 namespace Mapping {
794 typedef Internal::MappingCallInfo* MapperContext;
795 typedef Internal::InstanceManager* PhysicalInstanceImpl;
796 typedef Internal::CollectiveView* CollectiveViewImpl;
797 // This type import is experimental to facilitate coordination and
798 // synchronization between different mappers and may be revoked later
799 // as we develop new abstractions for mappers to interact
800 typedef Internal::LocalLock LocalLock;
801 }; // namespace Mapping
802
803 // Events are locks are important enough that we want them inlined everywhere
804 // so we pull these classes and implementations into this header file so
805 // that everyone will have access to them.
806 namespace Internal {
807
808 // Legion derived event types
809 class LgEvent : public Realm::Event {
810 public:
811 static const LgEvent NO_LG_EVENT;
812 public:
813 LgEvent(void) noexcept { id = 0; }
814 LgEvent(const LgEvent& rhs) = default;
815 explicit LgEvent(const Realm::Event e) { id = e.id; }
816 public:
817 inline LgEvent& operator=(const LgEvent& rhs) = default;
818 public:
819 // Override the wait method so we can have our own implementation
820 inline void wait(void) const;
821 inline void wait_faultaware(bool& poisoned, bool from_application) const;
822 inline bool is_barrier(void) const;
823 protected:
824 void begin_wait(Context ctx, bool from_application) const;
825 void end_wait(Context ctx, bool from_application) const;
826 void begin_mapper_call_wait(MappingCallInfo* call) const;
827 void record_event_wait(Realm::Backtrace& bt, ProvenanceID pid) const;
828 void record_event_trigger(LgEvent precondition) const;
829 };
830
831 class PredEvent : public LgEvent {
832 public:
833 static const PredEvent NO_PRED_EVENT;
834 public:
835 PredEvent(void) noexcept : LgEvent() { }
836 PredEvent(const PredEvent& rhs) = default;
837 explicit PredEvent(const Realm::Event& e) : LgEvent(e) { }
838 public:
839 inline PredEvent& operator=(const PredEvent& rhs) = default;
840 };
841
842 class PredUserEvent : public PredEvent {
843 public:
844 static const PredUserEvent NO_PRED_USER_EVENT;
845 public:
846 PredUserEvent(void) noexcept : PredEvent() { }
847 PredUserEvent(const PredUserEvent& rhs) = default;
848 explicit PredUserEvent(const Realm::UserEvent& e) : PredEvent(e) { }
849 public:
850 inline PredUserEvent& operator=(const PredUserEvent& rhs) = default;
851 inline operator Realm::UserEvent() const
852 {
853 Realm::UserEvent e;
854 e.id = id;
855 return e;
856 }
857 };
858
859 class ApEvent : public LgEvent {
860 public:
861 static const ApEvent NO_AP_EVENT;
862 public:
863 ApEvent(void) noexcept : LgEvent() { }
864 ApEvent(const ApEvent& rhs) = default;
865 explicit ApEvent(const Realm::Event& e) : LgEvent(e) { }
866 explicit ApEvent(const PredEvent& e) { id = e.id; }
867 public:
868 inline ApEvent& operator=(const ApEvent& rhs) = default;
869 inline bool has_triggered_faultignorant(void) const
870 {
871 bool poisoned = false;
872 return has_triggered_faultaware(poisoned);
873 }
874 inline void wait_faultaware(bool& poisoned) const
875 {
876 return LgEvent::wait_faultaware(poisoned, true /*application*/);
877 }
878 inline void wait_faultignorant(void) const
879 {
880 bool poisoned = false;
881 LgEvent::wait_faultaware(poisoned, true /*application*/);
882 }
883 private:
884 // Make these private because we always want to be conscious of faults
885 // when testing or waiting on application events
886 inline bool has_triggered(void) const { return LgEvent::has_triggered(); }
887 inline void wait(void) const { LgEvent::wait(); }
888 };
889
890 class ApUserEvent : public ApEvent {
891 public:
892 static const ApUserEvent NO_AP_USER_EVENT;
893 public:
894 ApUserEvent(void) noexcept : ApEvent() { }
895 ApUserEvent(const ApUserEvent& rhs) = default;
896 explicit ApUserEvent(const Realm::UserEvent& e) : ApEvent(e) { }
897 public:
898 inline ApUserEvent& operator=(const ApUserEvent& rhs) = default;
899 inline operator Realm::UserEvent() const
900 {
901 Realm::UserEvent e;
902 e.id = id;
903 return e;
904 }
905 };
906
907 class ApBarrier : public ApEvent {
908 public:
909 static const ApBarrier NO_AP_BARRIER;
910 public:
911 ApBarrier(void) noexcept : ApEvent(), timestamp(0) { }
912 ApBarrier(const ApBarrier& rhs) = default;
913 explicit ApBarrier(const Realm::Barrier& b)
914 : ApEvent(b), timestamp(b.timestamp)
915 { }
916 public:
917 inline ApBarrier& operator=(const ApBarrier& rhs) = default;
918 inline operator Realm::Barrier() const
919 {
920 Realm::Barrier b;
921 b.id = id;
922 b.timestamp = timestamp;
923 return b;
924 }
925 public:
926 inline bool get_result(void* value, size_t value_size) const
927 {
928 Realm::Barrier b;
929 b.id = id;
930 b.timestamp = timestamp;
931 return b.get_result(value, value_size);
932 }
933 inline void destroy_barrier(void)
934 {
935 Realm::Barrier b;
936 b.id = id;
937 b.timestamp = timestamp;
938 b.destroy_barrier();
939 }
940 public:
941 Realm::Barrier::timestamp_t timestamp;
942 };
943
944 class RtEvent : public LgEvent {
945 public:
946 static const RtEvent NO_RT_EVENT;
947 public:
948 RtEvent(void) noexcept : LgEvent() { }
949 RtEvent(const RtEvent& rhs) = default;
950 explicit RtEvent(const Realm::Event& e) : LgEvent(e) { }
951 explicit RtEvent(const PredEvent& e) { id = e.id; }
952 public:
953 inline RtEvent& operator=(const RtEvent& rhs) = default;
954 };
955
956 class RtUserEvent : public RtEvent {
957 public:
958 static const RtUserEvent NO_RT_USER_EVENT;
959 public:
960 RtUserEvent(void) noexcept : RtEvent() { }
961 RtUserEvent(const RtUserEvent& rhs) = default;
962 explicit RtUserEvent(const Realm::UserEvent& e) : RtEvent(e) { }
963 public:
964 inline RtUserEvent& operator=(const RtUserEvent& rhs) = default;
965 inline operator Realm::UserEvent() const
966 {
967 Realm::UserEvent e;
968 e.id = id;
969 return e;
970 }
971 };
972
973 class RtBarrier : public RtEvent {
974 public:
975 static const RtBarrier NO_RT_BARRIER;
976 public:
977 RtBarrier(void) noexcept : RtEvent(), timestamp(0) { }
978 RtBarrier(const RtBarrier& rhs) = default;
979 explicit RtBarrier(const Realm::Barrier& b)
980 : RtEvent(b), timestamp(b.timestamp)
981 { }
982 public:
983 inline RtBarrier& operator=(const RtBarrier& rhs) = default;
984 inline operator Realm::Barrier() const
985 {
986 Realm::Barrier b;
987 b.id = id;
988 b.timestamp = timestamp;
989 return b;
990 }
991 public:
992 inline bool get_result(void* value, size_t value_size) const
993 {
994 Realm::Barrier b;
995 b.id = id;
996 b.timestamp = timestamp;
997 return b.get_result(value, value_size);
998 }
999 inline RtBarrier get_previous_phase(void)
1000 {
1001 Realm::Barrier b;
1002 b.id = id;
1003 return RtBarrier(b.get_previous_phase());
1004 }
1005 inline void destroy_barrier(void)
1006 {
1007 Realm::Barrier b;
1008 b.id = id;
1009 b.timestamp = timestamp;
1010 b.destroy_barrier();
1011 }
1012 public:
1013 Realm::Barrier::timestamp_t timestamp;
1014 };
1015
1016 // Local lock for accelerating lock taking
1018 public:
1019 inline LocalLock(void) { }
1020 public:
1021 LocalLock(const LocalLock& rhs) = delete;
1022 inline ~LocalLock(void) { }
1023 public:
1024 LocalLock& operator=(const LocalLock& rhs) = delete;
1025 private:
1026 // These are only accessible via AutoLock
1027 friend class AutoLock;
1028 friend class AutoTryLock;
1029 friend class Mapping::AutoLock;
1030 inline RtEvent lock(void) { return RtEvent(wrlock()); }
1031 inline RtEvent wrlock(void) { return RtEvent(reservation.wrlock()); }
1032 inline RtEvent rdlock(void) { return RtEvent(reservation.rdlock()); }
1033 inline bool trylock(void) { return reservation.trylock(); }
1034 inline bool trywrlock(void) { return reservation.trywrlock(); }
1035 inline bool tryrdlock(void) { return reservation.tryrdlock(); }
1036 inline void unlock(void) { reservation.unlock(); }
1037 private:
1038 inline void advise_sleep_entry(Realm::UserEvent guard)
1039 {
1040 reservation.advise_sleep_entry(guard);
1041 }
1042 inline void advise_sleep_exit(void) { reservation.advise_sleep_exit(); }
1043 protected:
1044 Realm::FastReservation reservation;
1045 };
1046
1047 // External global variable references
1048 // With the exception fo the runtime singleton all of these should
1049 // only be thread-local or logggers
1050 // This is the pointer to the runtime singleton
1051 inline Runtime* runtime = nullptr;
1052 // One more global variable for the spy_logging_level which says
1053 // which level of legion spy logging we are doing, put this here
1054 // so that we inline it into everything
1055 enum SpyLoggingLevel {
1056 NO_SPY_LOGGING,
1057 LIGHT_SPY_LOGGING,
1058 HEAVY_SPY_LOGGING,
1059 EQ_SPY_LOGGING,
1060 };
1061#ifdef LEGION_SPY
1062 inline SpyLoggingLevel spy_logging_level = HEAVY_SPY_LOGGING;
1063#else
1064 inline SpyLoggingLevel spy_logging_level = NO_SPY_LOGGING;
1065#endif
1066 // Nasty global variable for TLS support of figuring out
1067 // our context implicitly
1068 // This one is only set for application tasks
1069 inline thread_local TaskContext* implicit_context = nullptr;
1070 // Mapper context if we're inside of a mapper call
1071 inline thread_local MappingCallInfo* implicit_mapper_call = nullptr;
1072 // Implicit thread-local profiler
1073 inline thread_local LegionProfInstance* implicit_profiler = nullptr;
1074 // Another nasty global variable for tracking the fast
1075 // reservations that we are holding
1076 inline thread_local AutoLock* local_lock_list = nullptr;
1077 // Track the enclosing task context that we're in for error reporting
1078 // This is only set for some internal meta-tasks
1079 inline thread_local DistributedID implicit_enclosing_context = 0;
1080 // The implicit operation if it exists, this is only set for certain
1081 // meta-tasks that correspond to pipeline stages that permit us to
1082 // take a fault in them so we prune out that operation
1083 inline thread_local Operation* implicit_operation = nullptr;
1084 // The implicit provenance if we're inside of a call into Legion
1085 // from an application task or in a meta-task derviced from a
1086 // particular operation
1087 inline thread_local ProvenanceID implicit_provenance = 0;
1088 // One more nasty global variable that we use for tracking
1089 // the provenance of meta-task operations for profiling
1090 // purposes, this has no bearing on correctness
1091 inline thread_local ::legion_unique_id_t implicit_unique_op_id = 0;
1092 // Use this global variable to track name of the "finish event"
1093 // for whatever (meta-)task we're running on at the moment.
1094 // It should always be the case that the owner node of the
1095 // "finish" event" is the same as the node we're on.
1096 inline thread_local LgEvent implicit_fevent = {};
1097 // Use this to track if we're inside of a registration
1098 // callback function which we know to be deduplicated
1099 enum RegistrationCallbackMode {
1100 NO_REGISTRATION_CALLBACK = 0,
1101 LOCAL_REGISTRATION_CALLBACK = 1,
1102 GLOBAL_REGISTRATION_CALLBACK = 2,
1103 };
1104 inline thread_local RegistrationCallbackMode inside_registration_callback =
1105 NO_REGISTRATION_CALLBACK;
1106 // This data structure tracks references to any live
1107 // temporary index space expressions that have been
1108 // handed back by the region tree inside the execution
1109 // of a meta-task or a runtime API call. It also tracks
1110 // changes to remote distributed collectable that can be
1111 // delayed and batched together.
1112 inline thread_local ImplicitReferenceTracker* implicit_reference_tracker =
1113 nullptr;
1114#ifdef LEGION_DEBUG_CALLERS
1115 thread_local LgTaskID implicit_task_kind;
1116 thread_local LgTaskID implicit_task_caller;
1117#endif
1118 extern Realm::Logger log_legion;
1119 extern Realm::Logger log_allocation;
1120 extern Realm::Logger log_migration;
1121 extern Realm::Logger log_prof;
1122 extern Realm::Logger log_garbage;
1123 extern Realm::Logger log_spy;
1124 extern Realm::Logger log_shutdown;
1125 extern Realm::Logger log_tracing;
1126 extern Realm::Logger log_auto_trace;
1127 extern Realm::Logger log_registration;
1128
1130 // AutoLock
1132 // An auto locking class for taking a lock and releasing it when
1133 // the object goes out of scope
1134 class AutoLock {
1135 public:
1136 inline AutoLock(LocalLock& r, bool excl = true)
1137 : local_lock(r), previous(local_lock_list), exclusive(excl), held(true)
1138 {
1139#ifdef LEGION_DEBUG_REENTRANT_LOCKS
1140 if (previous != nullptr)
1141 previous->check_for_reentrant_locks(&local_lock, this);
1142#endif
1143 if (exclusive)
1144 {
1145 RtEvent ready = local_lock.wrlock();
1146 while (ready.exists())
1147 {
1148 ready.wait();
1149 ready = local_lock.wrlock();
1150 }
1151 }
1152 else
1153 {
1154 RtEvent ready = local_lock.rdlock();
1155 while (ready.exists())
1156 {
1157 ready.wait();
1158 ready = local_lock.rdlock();
1159 }
1160 }
1161 local_lock_list = this;
1162 }
1163 protected:
1164 // Helper constructor for AutoTryLock and Mapping::AutoLock
1165 inline AutoLock(bool excl, LocalLock& r)
1166 : local_lock(r), previous(local_lock_list), exclusive(excl), held(false)
1167 {
1168 local_lock_list = this;
1169#ifdef LEGION_DEBUG_REENTRANT_LOCKS
1170 if (previous != nullptr)
1171 previous->check_for_reentrant_locks(&local_lock, this);
1172#endif
1173 }
1174 public:
1175 AutoLock(AutoLock&& rhs) = delete;
1176 AutoLock(const AutoLock& rhs) = delete;
1177 inline ~AutoLock(void)
1178 {
1179 if (held)
1180 local_lock.unlock();
1181 legion_assert(local_lock_list == this);
1182 local_lock_list = previous;
1183 }
1184 public:
1185 AutoLock& operator=(AutoLock&& rhs) = delete;
1186 AutoLock& operator=(const AutoLock& rhs) = delete;
1187 public:
1188 inline void release(void)
1189 {
1190 legion_assert(held);
1191 local_lock.unlock();
1192 held = false;
1193 }
1194 inline void reacquire(void)
1195 {
1196 legion_assert(!held);
1197#ifdef LEGION_DEBUG_REENTRANT_LOCKS
1198 local_lock_list->check_for_reentrant_locks(&local_lock, this);
1199#endif
1200 if (exclusive)
1201 {
1202 RtEvent ready = local_lock.wrlock();
1203 while (ready.exists())
1204 {
1205 ready.wait();
1206 ready = local_lock.wrlock();
1207 }
1208 }
1209 else
1210 {
1211 RtEvent ready = local_lock.rdlock();
1212 while (ready.exists())
1213 {
1214 ready.wait();
1215 ready = local_lock.rdlock();
1216 }
1217 }
1218 held = true;
1219 }
1220 public:
1221 inline void advise_sleep_entry(Realm::UserEvent guard) const
1222 {
1223 if (held)
1224 local_lock.advise_sleep_entry(guard);
1225 if (previous != nullptr)
1226 previous->advise_sleep_entry(guard);
1227 }
1228 inline void advise_sleep_exit(void) const
1229 {
1230 if (held)
1231 local_lock.advise_sleep_exit();
1232 if (previous != nullptr)
1233 previous->advise_sleep_exit();
1234 }
1235#ifdef LEGION_DEBUG_REENTRANT_LOCKS
1236 inline void check_for_reentrant_locks(
1237 LocalLock* to_acquire, const AutoLock* acquirer) const
1238 {
1239 legion_assert((to_acquire != &local_lock) || (this == acquirer));
1240 if (previous != nullptr)
1241 previous->check_for_reentrant_locks(to_acquire, acquirer);
1242 }
1243#endif
1244 protected:
1245 LocalLock& local_lock;
1246 AutoLock* const previous;
1247 const bool exclusive;
1248 bool held;
1249 };
1250
1251 // AutoTryLock is an extension of AutoLock that supports try lock
1252 class AutoTryLock : public AutoLock {
1253 public:
1254 inline AutoTryLock(LocalLock& r, bool excl = true) : AutoLock(excl, r)
1255 {
1256 if (exclusive)
1257 ready = local_lock.wrlock();
1258 else
1259 ready = local_lock.rdlock();
1260 held = !ready.exists();
1261 }
1262 AutoTryLock(const AutoTryLock& rhs) = delete;
1263 public:
1264 AutoTryLock& operator=(const AutoTryLock& rhs) = delete;
1265 public:
1266 // Allow an easy test for whether we got the lock or not
1267 inline bool has_lock(void) const { return held; }
1268 inline RtEvent try_next(void) const { return ready; }
1269 protected:
1270 RtEvent ready;
1271 };
1272
1273 //--------------------------------------------------------------------------
1274 inline void LgEvent::wait(void) const
1275 //--------------------------------------------------------------------------
1276 {
1277 if (!exists())
1278 return;
1279#ifdef DEBUG_LEGION_CALLERS
1280 LgTaskID local_kind = implicit_task_kind;
1281 LgTaskID local_caller = implicit_task_caller;
1282#endif
1283 // Save the mapper call locally
1284 MappingCallInfo* local_call = nullptr;
1285 std::swap(local_call, implicit_mapper_call);
1286 // If we're in a mapper call, notify the mapper that we're waiting
1287 // Do this first in case we get a re-entrant wait (e.g. because
1288 // SerializingManager::pause_mapper_call takes and lock and we might
1289 // end up coming back around here to wait on that event too)
1290 if (local_call != NULL)
1291 begin_mapper_call_wait(local_call);
1292 // Save whether we are in a registration callback
1293 RegistrationCallbackMode local_callback = NO_REGISTRATION_CALLBACK;
1294 std::swap(local_callback, inside_registration_callback);
1295 // Save the reference tracker that we have
1296 ImplicitReferenceTracker* local_tracker = nullptr;
1297 std::swap(local_tracker, implicit_reference_tracker);
1298 // Save the context locally
1299 TaskContext* local_ctx = nullptr;
1300 std::swap(local_ctx, implicit_context);
1301 // Save the operation locally
1302 Operation* local_op = nullptr;
1303 std::swap(local_op, implicit_operation);
1304 // Save the provenance
1305 ProvenanceID local_provenance = 0;
1306 std::swap(local_provenance, implicit_provenance);
1307 // Save the enclosing context
1308 DistributedID local_did = 0;
1309 std::swap(local_did, implicit_enclosing_context);
1310 // Save the implicit fevent
1311 LgEvent local_fevent;
1312 std::swap(local_fevent, implicit_fevent);
1313 // Save the task provenance information
1314 UniqueID local_uid = 0;
1315 std::swap(local_uid, implicit_unique_op_id);
1316 // Check to see if we have any local locks to notify
1317 if (local_lock_list != nullptr)
1318 {
1319 // Make a copy of the local locks here
1320 AutoLock* local_lock_list_copy = nullptr;
1321 std::swap(local_lock_list_copy, local_lock_list);
1322 // Make a user event and notify all the thread locks
1323 const Realm::UserEvent done = Realm::UserEvent::create_user_event();
1324 local_lock_list_copy->advise_sleep_entry(done);
1325 begin_wait(local_ctx, false /*from application*/);
1326 // Now we can do the wait (Realm checks for external waits itself now)
1327 Realm::Event::wait();
1328 // Restore our implicit fevent in case we have profiling to do
1329 // Must restore implicit_fevent before calling end_wait
1330 implicit_fevent = local_fevent;
1331 end_wait(local_ctx, false /*from application*/);
1332 // When we wake up, notify that we are done and exited the wait
1333 local_lock_list_copy->advise_sleep_exit();
1334 // Trigger the user-event
1335 done.trigger();
1336 // Restore our local lock list
1337 local_lock_list = local_lock_list_copy;
1338 // If we're profiling we need to record that we triggered this
1339 // event as it will help us hook up the critical path for
1340 // local lock acquires
1341 if (implicit_profiler != nullptr)
1342 {
1343 // Have to do this recording after the wait because it might
1344 // end up waiting on an event too and don't want to cause
1345 // a stack overflow with repeated calls into wait
1346 const LgEvent to_trigger(done);
1347 to_trigger.record_event_trigger(LgEvent::NO_LG_EVENT);
1348 // Record the backtrace too
1349 Realm::Backtrace bt;
1350 bt.capture_backtrace();
1351 record_event_wait(bt, local_provenance);
1352 }
1353 }
1354 else // Just do the normal wait
1355 {
1356 begin_wait(local_ctx, false /*from application*/);
1357 // Realm checks for external waits itself now
1358 Realm::Event::wait();
1359 // Restore our implicit fevent in case we have profiling to do
1360 // Must restore implicit_fevent before calling end_wait
1361 implicit_fevent = local_fevent;
1362 end_wait(local_ctx, false /*from application*/);
1363 if (implicit_profiler != nullptr)
1364 {
1365 // Have to do this recording after the wait because it might
1366 // end up waiting on an event too and don't want to cause
1367 // a stack overflow with repeated calls into wait
1368 Realm::Backtrace bt;
1369 bt.capture_backtrace();
1370 record_event_wait(bt, local_provenance);
1371 }
1372 }
1373 // Write the context back
1374 implicit_context = local_ctx;
1375 // Write the mapper call back
1376 implicit_mapper_call = local_call;
1377 // Write the operation back
1378 implicit_operation = local_op;
1379 // Write the provenance back
1380 implicit_provenance = local_provenance;
1381 // Write the enclosing context back
1382 implicit_enclosing_context = local_did;
1383 // Write the provenance information back
1384 implicit_unique_op_id = local_uid;
1385#ifdef DEBUG_LEGION_CALLERS
1386 implicit_task_kind = local_kind;
1387 implicit_task_caller = local_caller;
1388#endif
1389 // Write the registration callback information back
1390 inside_registration_callback = local_callback;
1391#ifdef DEBUG_LEGION
1392 assert(implicit_reference_tracker == nullptr);
1393#endif
1394 // Write the local reference tracker back
1395 implicit_reference_tracker = local_tracker;
1396 }
1397
1398 //--------------------------------------------------------------------------
1399 inline void LgEvent::wait_faultaware(bool& poisoned, bool from_app) const
1400 //--------------------------------------------------------------------------
1401 {
1402 if (!exists())
1403 return;
1404 if (has_triggered_faultaware(poisoned))
1405 return;
1406#ifdef DEBUG_LEGION_CALLERS
1407 LgTaskID local_kind = implicit_task_kind;
1408 LgTaskID local_caller = implicit_task_caller;
1409#endif
1410 // Save the mapper call locally
1411 MappingCallInfo* local_call = nullptr;
1412 std::swap(local_call, implicit_mapper_call);
1413 // If we're in a mapper call, notify the mapper that we're waiting
1414 // Do this first in case we get a re-entrant wait (e.g. because
1415 // SerializingManager::pause_mapper_call takes and lock and we might
1416 // end up coming back around here to wait on that event too)
1417 if (local_call != NULL)
1418 begin_mapper_call_wait(local_call);
1419 // Save whether we are in a registration callback
1420 RegistrationCallbackMode local_callback = NO_REGISTRATION_CALLBACK;
1421 std::swap(local_callback, inside_registration_callback);
1422 // Save the reference tracker that we have
1423 ImplicitReferenceTracker* local_tracker = nullptr;
1424 std::swap(local_tracker, implicit_reference_tracker);
1425 // Save the context locally
1426 TaskContext* local_ctx = nullptr;
1427 std::swap(local_ctx, implicit_context);
1428 // Save the operation locally
1429 Operation* local_op = nullptr;
1430 std::swap(local_op, implicit_operation);
1431 // Save the provenance
1432 ProvenanceID local_provenance = 0;
1433 std::swap(local_provenance, implicit_provenance);
1434 // Save the enclosing context
1435 DistributedID local_did = 0;
1436 std::swap(local_did, implicit_enclosing_context);
1437 // Save the fevent
1438 LgEvent local_fevent;
1439 std::swap(local_fevent, implicit_fevent);
1440 // Save the task provenance information
1441 UniqueID local_uid = 0;
1442 std::swap(local_uid, implicit_unique_op_id);
1443 // Check to see if we have any local locks to notify
1444 if (local_lock_list != nullptr)
1445 {
1446 // Make a copy of the local locks here
1447 AutoLock* local_lock_list_copy = nullptr;
1448 std::swap(local_lock_list_copy, local_lock_list);
1449 // Make a user event and notify all the thread locks
1450 const Realm::UserEvent done = Realm::UserEvent::create_user_event();
1451 local_lock_list_copy->advise_sleep_entry(done);
1452 begin_wait(local_ctx, from_app);
1453 // Now we can do the wait (Realm checks for external waits itself now)
1454 Realm::Event::wait_faultaware(poisoned);
1455 // Restore our implicit fevent in case we have profiling to do
1456 // Must restore implicit_fevent before calling end_wait
1457 implicit_fevent = local_fevent;
1458 end_wait(local_ctx, from_app);
1459 // When we wake up, notify that we are done and exited the wait
1460 local_lock_list_copy->advise_sleep_exit();
1461 // Trigger the user-event
1462 done.trigger();
1463 // Restore our local lock list
1464 local_lock_list = local_lock_list_copy;
1465 // If we're profiling we need to record that we triggered this
1466 // event as it will help us hook up the critical path for
1467 // local lock acquires
1468 if (implicit_profiler != nullptr)
1469 {
1470 // Have to do this recording after the wait because it might
1471 // end up waiting on an event too and don't want to cause
1472 // a stack overflow with repeated calls into wait
1473 const LgEvent to_trigger(done);
1474 to_trigger.record_event_trigger(LgEvent::NO_LG_EVENT);
1475 // Record the backtrace too
1476 Realm::Backtrace bt;
1477 bt.capture_backtrace();
1478 record_event_wait(bt, local_provenance);
1479 }
1480 }
1481 else // Just do the normal wait
1482 {
1483 begin_wait(local_ctx, from_app);
1484 // Realm checks for external waits itself now
1485 Realm::Event::wait_faultaware(poisoned);
1486 // Restore our implicit fevent in case we have profiling to do
1487 // Must restore implicit_fevent before calling end_wait
1488 implicit_fevent = local_fevent;
1489 end_wait(local_ctx, from_app);
1490 if (implicit_profiler != nullptr)
1491 {
1492 // Have to do this recording after the wait because it might
1493 // end up waiting on an event too and don't want to cause
1494 // a stack overflow with repeated calls into wait
1495 Realm::Backtrace bt;
1496 bt.capture_backtrace();
1497 record_event_wait(bt, local_provenance);
1498 }
1499 }
1500 // Write the context back
1501 implicit_context = local_ctx;
1502 // Write the mapper call back
1503 implicit_mapper_call = local_call;
1504 // Write the operation back
1505 implicit_operation = local_op;
1506 // Write the provenance back
1507 implicit_provenance = local_provenance;
1508 // Write the enclosing context back
1509 implicit_enclosing_context = local_did;
1510 // Write the provenance information back
1511 implicit_unique_op_id = local_uid;
1512#ifdef DEBUG_LEGION_CALLERS
1513 implicit_task_kind = local_kind;
1514 implicit_task_caller = local_caller;
1515#endif
1516 // Write the registration callback information back
1517 inside_registration_callback = local_callback;
1518#ifdef DEBUG_LEGION
1519 assert(implicit_reference_tracker == nullptr);
1520#endif
1521 // Write the local reference tracker back
1522 implicit_reference_tracker = local_tracker;
1523 }
1524
1525 //--------------------------------------------------------------------------
1526 inline bool LgEvent::is_barrier(void) const
1527 //--------------------------------------------------------------------------
1528 {
1529 const Realm::ID identity(id);
1530 return identity.is_barrier();
1531 }
1532
1533 } // namespace Internal
1534} // namespace Legion
1535
1536#define FRIEND_ALL_RUNTIME_CLASSES \
1537 friend class Legion::Runtime; \
1538 friend class Legion::Mapping::MapperRuntime; \
1539 friend class Internal::Runtime; \
1540 friend class Internal::FutureCreateInstanceRequest; \
1541 friend class Internal::FutureMapFutureRequest; \
1542 friend class Internal::FutureImpl; \
1543 friend class Internal::FutureMapImpl; \
1544 friend class Internal::PhysicalRegionImpl; \
1545 friend class Internal::ExternalResourcesImpl; \
1546 friend class Internal::TaskImpl; \
1547 friend class Internal::VariantImpl; \
1548 friend class Internal::ProcessorManager; \
1549 friend class Internal::MemoryManager; \
1550 friend class Internal::Operation; \
1551 friend class Internal::PredicatedOp; \
1552 friend class Internal::MapOp; \
1553 friend class Internal::CopyOp; \
1554 friend class Internal::IndexCopyOp; \
1555 friend class Internal::PointCopyOp; \
1556 friend class Internal::FenceOp; \
1557 friend class Internal::DynamicCollectiveOp; \
1558 friend class Internal::FuturePredOp; \
1559 friend class Internal::CreationOp; \
1560 friend class Internal::DeletionOp; \
1561 friend class Internal::CloseOp; \
1562 friend class Internal::MergeCloseOp; \
1563 friend class Internal::PostCloseOp; \
1564 friend class Internal::RefinementOp; \
1565 friend class Internal::ResetOp; \
1566 friend class Internal::AcquireOp; \
1567 friend class Internal::ReleaseOp; \
1568 friend class Internal::PredicateImpl; \
1569 friend class Internal::NotPredOp; \
1570 friend class Internal::AndPredOp; \
1571 friend class Internal::OrPredOp; \
1572 friend class Internal::MustEpochOp; \
1573 friend class Internal::PendingPartitionOp; \
1574 friend class Internal::DependentPartitionOp; \
1575 friend class Internal::PointDepPartOp; \
1576 friend class Internal::FillOp; \
1577 friend class Internal::IndexFillOp; \
1578 friend class Internal::PointFillOp; \
1579 friend class Internal::DiscardOp; \
1580 friend class Internal::AttachOp; \
1581 friend class Internal::IndexAttachOp; \
1582 friend class Internal::ReplIndexAttachOp; \
1583 friend class Internal::PointAttachOp; \
1584 friend class Internal::DetachOp; \
1585 friend class Internal::IndexDetachOp; \
1586 friend class Internal::ReplIndexDetachOp; \
1587 friend class Internal::PointDetachOp; \
1588 friend class Internal::TimingOp; \
1589 friend class Internal::TunableOp; \
1590 friend class Internal::AllReduceOp; \
1591 friend class Internal::TraceRecurrentOp; \
1592 friend class Internal::ExternalMappable; \
1593 friend class Internal::ExternalTask; \
1594 friend class Internal::TaskOp; \
1595 friend class Internal::SingleTask; \
1596 friend class Internal::MultiTask; \
1597 friend class Internal::IndividualTask; \
1598 friend class Internal::PointTask; \
1599 friend class Internal::IndexTask; \
1600 friend class Internal::SliceTask; \
1601 friend class Internal::ReplIndividualTask; \
1602 friend class Internal::ReplIndexTask; \
1603 friend class Internal::ReplFillOp; \
1604 friend class Internal::ReplIndexFillOp; \
1605 friend class Internal::ReplDiscardOp; \
1606 friend class Internal::ReplCopyOp; \
1607 friend class Internal::ReplIndexCopyOp; \
1608 friend class Internal::ReplDeletionOp; \
1609 friend class Internal::ReplPendingPartitionOp; \
1610 friend class Internal::ReplDependentPartitionOp; \
1611 friend class Internal::ReplMustEpochOp; \
1612 friend class Internal::ReplMapOp; \
1613 friend class Internal::ReplTimingOp; \
1614 friend class Internal::ReplTunableOp; \
1615 friend class Internal::ReplAllReduceOp; \
1616 friend class Internal::ReplFenceOp; \
1617 friend class Internal::ReplAttachOp; \
1618 friend class Internal::ReplDetachOp; \
1619 friend class Internal::ReplAcquireOp; \
1620 friend class Internal::ReplReleaseOp; \
1621 friend class Internal::MemoizableOp; \
1622 template<typename OP> \
1623 friend class Internal::Memoizable; \
1624 friend class Internal::ShardManager; \
1625 friend class Internal::IndexSpaceNode; \
1626 template<int, typename> \
1627 friend class Internal::IndexSpaceNodeT; \
1628 friend class Internal::IndexPartNode; \
1629 friend class Internal::FieldSpaceNode; \
1630 friend class Internal::RegionTreeNode; \
1631 friend class Internal::RegionNode; \
1632 friend class Internal::PartitionNode; \
1633 friend class Internal::LogicalView; \
1634 friend class Internal::InstanceView; \
1635 friend class Internal::DeferredView; \
1636 friend class Internal::ReductionView; \
1637 friend class Internal::MaterializedView; \
1638 friend class Internal::FillView; \
1639 friend class Internal::LayoutDescription; \
1640 friend class Internal::InstanceManager; \
1641 friend class Internal::PhysicalManager; \
1642 friend class Internal::MapperManager; \
1643 friend class Internal::InstanceRef; \
1644 friend class Internal::HandshakeImpl; \
1645 friend class Internal::ArgumentMapImpl; \
1646 friend class Internal::FutureMapImpl; \
1647 friend class Internal::ReplFutureMapImpl; \
1648 friend class Internal::TaskContext; \
1649 friend class Internal::InnerContext; \
1650 friend class Internal::TopLevelContext; \
1651 friend class Internal::RemoteContext; \
1652 friend class Internal::LeafContext; \
1653 friend class Internal::ReplicateContext; \
1654 friend class Internal::InstanceBuilder; \
1655 friend class Internal::FutureNameExchange; \
1656 friend class Internal::MustEpochMappingExchange; \
1657 friend class Internal::MustEpochMappingBroadcast; \
1658 friend class Internal::MappingCallInfo; \
1659 friend class CObjectWrapper;
1660
1661#endif // __LEGION_TYPES_H__
Definition mapping.h:240
Definition constraints.h:689
Definition mapping.h:292
Definition constraints.h:202
Definition mapping.h:185
Definition constraints.h:640
Definition geometry.h:159
Definition geometry.h:34
Definition exception.h:175
Definition constraints.h:240
Definition constraints.h:475
Definition mapping.h:312
Definition constraints.h:61
Definition mapping.h:216
Definition types.h:907
Definition types.h:859
Definition types.h:890
Definition types.h:1134
Definition types.h:1252
Definition types.h:585
Definition types.h:572
Definition types.h:569
Definition types.h:560
Definition types.h:582
Definition types.h:809
Definition types.h:1017
Definition types.h:499
Definition types.h:831
Definition types.h:842
Definition types.h:501
Definition types.h:973
Definition types.h:944
Definition types.h:956
Definition types.h:714
Definition constraints.h:167
Definition constraints.h:881
Definition interop.h:38
Definition data.h:260
Definition data.h:189
Definition interop.h:101
Definition mapping.h:42
Definition mapping.h:3096
Definition mapping.h:490
Definition mapping.h:526
Definition mapping.h:642
Definition mapping.h:414
Definition constraints.h:422
Definition mapping.h:377
Definition constraints.h:737
Definition constraints.h:538
Definition constraints.h:830
Definition mapping.h:342
Definition physical_region.h:236
Definition physical_region.h:275
Definition functors.h:381
Definition constraints.h:783
Definition constraints.h:95
Definition functors.h:45
Definition mapping.h:264
Definition constraints.h:132
Definition runtime.h:108
Definition functors.h:286
Definition physical_region.h:607
Definition constraints.h:357
Definition mapping.h:112
Definition constraints.h:942
Definition constraints.h:592
Definition types.h:268
Definition types.h:343
Definition accessors.h:29
Definition runtime.h:46
Definition runtime.h:56