public static IntPtr Initialize() { bool flag = ParticleSystemParallelForJobStruct <T> .jobReflectionData == IntPtr.Zero; if (flag) { ParticleSystemParallelForJobStruct <T> .jobReflectionData = JobsUtility.CreateJobReflectionData(typeof(T), new ParticleSystemParallelForJobStruct <T> .ExecuteJobFunction(ParticleSystemParallelForJobStruct <T> .Execute), null, null); } return(ParticleSystemParallelForJobStruct <T> .jobReflectionData); }
public static IntPtr Initialize() { bool flag = IJobForExtensions.ForJobStruct <T> .jobReflectionData == IntPtr.Zero; if (flag) { IJobForExtensions.ForJobStruct <T> .jobReflectionData = JobsUtility.CreateJobReflectionData(typeof(T), new IJobForExtensions.ForJobStruct <T> .ExecuteJobFunction(IJobForExtensions.ForJobStruct <T> .Execute), null, null); } return(IJobForExtensions.ForJobStruct <T> .jobReflectionData); }
public static IntPtr Initialize() { if (s_JobReflectionData == IntPtr.Zero) { s_JobReflectionData = JobsUtility.CreateJobReflectionData(typeof(T), typeof(T), JobType.ParallelFor, (ExecuteJobFunction)Execute); } return(s_JobReflectionData); }
public static IntPtr GetJobReflectionData() { if (jobReflectionData == IntPtr.Zero) { jobReflectionData = JobsUtility.CreateJobReflectionData( typeof(T), (ExecuteJobFunction)Execute); } return(jobReflectionData); }
public unsafe static JobHandle ScheduleWithInt <T>(this T jobData, int value, JobHandle dependsOn = new JobHandle()) where T : struct, IJobWithInt { JobDataWithInt <T> jobDataWithInt = new JobDataWithInt <T> { value = value, jobData = jobData }; var scheduleParams = new JobsUtility.JobScheduleParameters(UnsafeUtility.AddressOf(ref jobDataWithInt), JobWithIntStruct <T> .Initialize(), dependsOn, ScheduleMode.Batched); return(JobsUtility.Schedule(ref scheduleParams)); }
public static int Main(string[] args) { var result = new AutoRun().Execute(args); #if !UNITY_SINGLETHREADED_JOBS // Currently, Windows (.NET) will exit without requiring other threads to complete // OSX (Mono), on the other hand, requires all other threads to complete JobsUtility.Shutdown(); #endif return(result); }
public static IntPtr Initialize() { if (jobReflectionData == IntPtr.Zero) { // @TODO: Use parallel for job... (Need to expose combine jobs) jobReflectionData = JobsUtility.CreateJobReflectionData(typeof(JobDataWithFiltering), typeof(T), JobType.Single, (ExecuteJobFunction)Execute); } return(jobReflectionData); }
unsafe static public JobHandle ScheduleFilter <T>(this T jobData, NativeList <int> indices, int innerloopBatchCount, JobHandle dependsOn = new JobHandle()) where T : struct, IJobParallelForFilter { JobStructProduce <T> .JobDataWithFiltering fullData; fullData.data = jobData; fullData.outputIndices = indices; fullData.appendCount = -1; var scheduleParams = new JobsUtility.JobScheduleParameters(UnsafeUtility.AddressOf(ref fullData), JobStructProduce <T> .Initialize(), dependsOn, ScheduleMode.Batched); return(JobsUtility.Schedule(ref scheduleParams)); }
public unsafe static void RunWithInt <T>(this T jobData, int value) where T : struct, IJobWithInt { JobDataWithInt <T> jobDataWithInt = new JobDataWithInt <T> { value = value, jobData = jobData }; var scheduleParams = new JobsUtility.JobScheduleParameters(UnsafeUtility.AddressOf(ref jobDataWithInt), JobWithIntStruct <T> .Initialize(), new JobHandle(), ScheduleMode.Run); JobsUtility.Schedule(ref scheduleParams); }
private static unsafe void Execute(ref JobMultiHashMap fullData, IntPtr additionalPtr, IntPtr bufferRangePatchData, ref JobRanges ranges, int jobIndex) { while (true) { int begin; int end; if (!JobsUtility.GetWorkStealingRange(ref ranges, jobIndex, out begin, out end)) { return; } var buckets = (int *)fullData.HashMap.m_Buffer->buckets; var nextPtrs = (int *)fullData.HashMap.m_Buffer->next; var keys = fullData.HashMap.m_Buffer->keys; var values = fullData.HashMap.m_Buffer->values; for (int i = begin; i < end; i++) { int entryIndex = buckets[i]; while (entryIndex != -1) { var key = UnsafeUtility.ReadArrayElement <TKey>(keys, entryIndex); var value = UnsafeUtility.ReadArrayElement <int>(values, entryIndex); int firstValue; NativeMultiHashMapIterator <TKey> it; fullData.HashMap.TryGetFirstValue(key, out firstValue, out it); if (firstValue == value) { #if ENABLE_UNITY_COLLECTIONS_CHECKS JobsUtility.PatchBufferMinMaxRanges(bufferRangePatchData, UnsafeUtility.AddressOf(ref fullData), value, 1); #endif fullData.JobData.ExecuteFirst(value); } else { #if ENABLE_UNITY_COLLECTIONS_CHECKS var startIndex = math.min(firstValue, value); var lastIndex = math.max(firstValue, value); var rangeLength = (lastIndex - startIndex) + 1; JobsUtility.PatchBufferMinMaxRanges(bufferRangePatchData, UnsafeUtility.AddressOf(ref fullData), startIndex, rangeLength); #endif fullData.JobData.ExecuteNext(firstValue, value); } entryIndex = nextPtrs[entryIndex]; } } } }
public static void Initialize() { if (jobReflectionData.Data == IntPtr.Zero) { #if UNITY_2020_2_OR_NEWER || UNITY_DOTSRUNTIME jobReflectionData.Data = JobsUtility.CreateJobReflectionData(typeof(T), (ExecuteJobFunction)Execute); #else jobReflectionData.Data = JobsUtility.CreateJobReflectionData(typeof(T), JobType.Single, (ExecuteJobFunction)Execute); #endif } }
unsafe public static JobHandle Schedule <T>(this T jobData, int arrayLength, JobHandle dependency) where T : struct, IJobFor { // https://unity3d.atlassian.net/browse/DOTSR-1888 // var scheduleParams = new JobsUtility.JobScheduleParameters(UnsafeUtility.AddressOf(ref jobData), JobProducer<T>.Initialize(), dependency, ScheduleMode.Single); // IJobChunk uses both JobsUtility.ScheduleParallelFor and JobsUtility.Schedule, so that could be implemented. // However, it brings this class (which is rarely used) even more out of sync with the Unity.Runtime version, where // the better fix is to implement ScheduleMode.Single var scheduleParams = new JobsUtility.JobScheduleParameters(UnsafeUtility.AddressOf(ref jobData), JobProducer <T> .Initialize(), dependency, ScheduleMode.Parallel); return(JobsUtility.ScheduleParallelFor(ref scheduleParams, arrayLength, arrayLength)); }
public static unsafe JobHandle ScheduleBatch <T>(this T jobData, int arrayLength, int minIndicesPerJobCount, JobHandle dependsOn = new JobHandle()) where T : struct, IJobParallelForBatch { var scheduleParams = new JobsUtility.JobScheduleParameters( UnsafeUtility.AddressOf(ref jobData), JobParallelForBatchProducer <T> .Initialize(), dependsOn, ScheduleMode.Batched); return(JobsUtility.ScheduleParallelFor(ref scheduleParams, arrayLength, minIndicesPerJobCount)); }
private static unsafe JobHandle FinalizeScheduleNoExceptions(bool isParallel, int batchCount, ref JobsUtility.JobScheduleParameters scheduleParams) { if (!isParallel) { return(JobsUtility.Schedule(ref scheduleParams)); } else { return(JobsUtility.ScheduleParallelFor(ref scheduleParams, batchCount, 1)); } }
public void Run3SimpleJobsInSerial() { #if UNITY_SINGLETHREADED_JOBS && UNITY_DOTSPLAYER // Note the safety handles use Persistent, so only track TempJob long heapMem = UnsafeUtility.GetHeapSize(Allocator.TempJob); #endif NativeArray <int> input = new NativeArray <int>(SimpleAddSerial.N, Allocator.TempJob); NativeArray <int> jobResult1 = new NativeArray <int>(SimpleAddSerial.N, Allocator.TempJob); NativeArray <int> jobResult2 = new NativeArray <int>(SimpleAddSerial.N, Allocator.TempJob); NativeArray <int> jobResult3 = new NativeArray <int>(SimpleAddSerial.N, Allocator.TempJob); for (int i = 0; i < SimpleAddSerial.N; ++i) { input[i] = i; } SimpleAddSerial job1 = new SimpleAddSerial() { a = 1, input = input, result = jobResult1 }; SimpleAddSerial job2 = new SimpleAddSerial() { a = 2, input = jobResult1, result = jobResult2 }; SimpleAddSerial job3 = new SimpleAddSerial() { a = 3, input = jobResult2, result = jobResult3 }; #if UNITY_SINGLETHREADED_JOBS && UNITY_DOTSPLAYER Assert.IsFalse(JobsUtility.IsExecutingJob()); #endif JobHandle handle1 = job1.Schedule(); JobHandle handle2 = job2.Schedule(handle1); JobHandle handle3 = job3.Schedule(handle2); handle3.Complete(); #if UNITY_SINGLETHREADED_JOBS && UNITY_DOTSPLAYER Assert.IsFalse(JobsUtility.IsExecutingJob()); #endif for (int i = 0; i < SimpleAddSerial.N; ++i) { Assert.AreEqual(i + 1 + 2 + 3, jobResult3[i]); } jobResult3.Dispose(); #if UNITY_SINGLETHREADED_JOBS && UNITY_DOTSPLAYER long postWork = UnsafeUtility.GetHeapSize(Allocator.TempJob); Assert.IsTrue(heapMem == postWork); // make sure cleanup happened, including DeallocateOnJobCompletion #endif }
/// <summary> /// Schedule the job for execution on worker threads. /// forEachCount is a pointer to the number of iterations, when dependsOn has completed. /// This API is unsafe, it is recommended to use the NativeList based Schedule method instead. /// </summary> /// <param name="jobData"></param> /// <param name="forEachCount"></param> /// <param name="innerloopBatchCount"></param> /// <param name="dependsOn"></param> /// <typeparam name="T"></typeparam> /// <returns></returns> public static unsafe JobHandle Schedule <T>(this T jobData, int *forEachCount, int innerloopBatchCount, JobHandle dependsOn = new JobHandle()) where T : struct, IJobParallelForDefer { #if UNITY_AVOID_REFLECTION return(Schedule(ref jobData, new IntPtr(forEachCount), innerloopBatchCount, dependsOn)); #else var scheduleParams = new JobsUtility.JobScheduleParameters(UnsafeUtility.AddressOf(ref jobData), JobStructDefer <T> .Initialize(), dependsOn, ScheduleMode.Batched); var forEachListPtr = (byte *)forEachCount - sizeof(void *); return(JobsUtility.ScheduleParallelForDeferArraySize(ref scheduleParams, innerloopBatchCount, forEachListPtr, null)); #endif }
public void Complete() { #if !UNITY_SINGLETHREADED_JOBS if (JobsUtility.JobQueue == IntPtr.Zero || JobGroup == IntPtr.Zero) { return; } JobsUtility.Complete(JobsUtility.BatchScheduler, ref this); #endif }
public static IntPtr GetJobReflectionData() { if (jobReflectionData == IntPtr.Zero) { jobReflectionData = JobsUtility.CreateJobReflectionData( typeof(T), JobType.Single, (ExecuteJobFunction)ExecuteProcessParticleSystem); } return(jobReflectionData); }
unsafe internal static JobHandle Schedule <T>(this T jobData, JobHandle dependsOn = new JobHandle()) where T : struct, IJobBurstSchedulable { var reflectionData = JobStruct <T> .jobReflectionData.Data; CheckReflectionDataCorrect(reflectionData); #if UNITY_2020_2_OR_NEWER || UNITY_DOTSRUNTIME var scheduleParams = new JobsUtility.JobScheduleParameters(UnsafeUtility.AddressOf(ref jobData), reflectionData, dependsOn, ScheduleMode.Parallel); #else var scheduleParams = new JobsUtility.JobScheduleParameters(UnsafeUtility.AddressOf(ref jobData), reflectionData, dependsOn, ScheduleMode.Batched); #endif return(JobsUtility.Schedule(ref scheduleParams)); }
public static IntPtr Initialize() { if (jobReflectionData == IntPtr.Zero) { #if UNITY_2020_2_OR_NEWER jobReflectionData = JobsUtility.CreateJobReflectionData(typeof(CollisionEventJobData <T>), typeof(T), (ExecuteJobFunction)Execute); #else jobReflectionData = JobsUtility.CreateJobReflectionData(typeof(CollisionEventJobData <T>), typeof(T), JobType.Single, (ExecuteJobFunction)Execute); #endif } return(jobReflectionData); }
public static unsafe void Run <T>(this T jobData, int arrayLength) where T : struct, IJobParallelFor { var parallelForJobProducer = new JobParallelForProducer <T>() { JobData = jobData, #if ENABLE_UNITY_COLLECTIONS_CHECKS Sentinel = 37 + arrayLength // check that code is patched as expected #endif }; var scheduleParams = new JobsUtility.JobScheduleParameters(UnsafeUtility.AddressOf(ref parallelForJobProducer), JobParallelForProducer <T> .Initialize(),
internal static unsafe JobHandle ScheduleInternal <T>(ref T jobData, EntityQuery query, JobHandle dependsOn, ScheduleMode mode) where T : struct, IJobChunk { ComponentChunkIterator iterator = query.GetComponentChunkIterator(); var unfilteredChunkCount = query.CalculateChunkCountWithoutFiltering(); var prefilterHandle = ComponentChunkIterator.PreparePrefilteredChunkLists(unfilteredChunkCount, iterator.m_MatchingArchetypeList, iterator.m_Filter, dependsOn, mode, out var prefilterData, out var deferredCountData); JobChunkData <T> fullData = new JobChunkData <T> { #if ENABLE_UNITY_COLLECTIONS_CHECKS // All IJobChunk jobs have a EntityManager safety handle to ensure that BeforeStructuralChange throws an error if // jobs without any other safety handles are still running (haven't been synced). safety = new EntitySafetyHandle { m_Safety = query.SafetyManager->GetEntityManagerSafetyHandle() }, #endif Data = jobData, PrefilterData = prefilterData, }; var scheduleParams = new JobsUtility.JobScheduleParameters( UnsafeUtility.AddressOf(ref fullData), JobChunk_Process <T> .Initialize(), prefilterHandle, mode); #if ENABLE_UNITY_COLLECTIONS_CHECKS try { #endif if (mode == ScheduleMode.Batched) { return(JobsUtility.ScheduleParallelForDeferArraySize(ref scheduleParams, 1, deferredCountData, null)); } else { var count = unfilteredChunkCount; return(JobsUtility.ScheduleParallelFor(ref scheduleParams, count, 1)); } #if ENABLE_UNITY_COLLECTIONS_CHECKS } catch (InvalidOperationException e) { prefilterData.Dispose(); throw e; } #endif }
public static IntPtr Initialize() { // IJobParallelFor uses JobType.ParallelFor instead of Single if (jobReflectionData == IntPtr.Zero) { jobReflectionData = JobsUtility.CreateJobReflectionData( typeof(T), JobType.ParallelFor, (ExecuteJobFunction)Execute); } return(jobReflectionData); }
unsafe public static void Run <T>(this T jobData, int arrayLength) where T : struct, IJobParallelForBurstScheduable { var reflectionData = ParallelForJobStructBurstScheduable <T> .jobReflectionData.Data; if (reflectionData == IntPtr.Zero) { throw new InvalidOperationException("Reflection data was not set up by code generation"); } var scheduleParams = new JobsUtility.JobScheduleParameters(UnsafeUtility.AddressOf(ref jobData), reflectionData, new JobHandle(), ScheduleMode.Run); JobsUtility.ScheduleParallelFor(ref scheduleParams, arrayLength, arrayLength); }
unsafe public static JobHandle Schedule <T>(this T jobData, int arrayLength, int innerloopBatchCount, JobHandle dependsOn = new JobHandle()) where T : struct, IJobParallelForBurstScheduable { var reflectionData = ParallelForJobStructBurstScheduable <T> .jobReflectionData.Data; if (reflectionData == IntPtr.Zero) { throw new InvalidOperationException("Reflection data was not set up by code generation"); } var scheduleParams = new JobsUtility.JobScheduleParameters(UnsafeUtility.AddressOf(ref jobData), reflectionData, dependsOn, ScheduleMode.Batched); return(JobsUtility.ScheduleParallelFor(ref scheduleParams, arrayLength, innerloopBatchCount)); }
internal static unsafe JobHandle ScheduleInternal <T>( ref T jobData, EntityQuery query, JobHandle dependsOn, ScheduleMode mode, int batchesPerChunk, bool isParallel = true) where T : struct, IJobEntityBatch { var queryImpl = query._GetImpl(); var queryData = queryImpl->_QueryData; var cachedChunks = queryData->GetMatchingChunkCache(); // Don't schedule the job if there are no chunks to work on var chunkCount = cachedChunks.Length; JobEntityBatchWrapper <T> jobEntityBatchWrapper = new JobEntityBatchWrapper <T> { #if ENABLE_UNITY_COLLECTIONS_CHECKS // All IJobEntityBatch jobs have a EntityManager safety handle to ensure that BeforeStructuralChange throws an error if // jobs without any other safety handles are still running (haven't been synced). safety = new EntitySafetyHandle { m_Safety = queryImpl->SafetyHandles->GetEntityManagerSafetyHandle() }, #endif MatchingArchetypes = queryData->MatchingArchetypes, CachedChunks = cachedChunks, Filter = queryImpl->_Filter, JobData = jobData, JobsPerChunk = batchesPerChunk, IsParallel = isParallel ? 1 : 0 }; var scheduleParams = new JobsUtility.JobScheduleParameters( UnsafeUtility.AddressOf(ref jobEntityBatchWrapper), isParallel ? JobEntityBatchProducer <T> .InitializeParallel() : JobEntityBatchProducer <T> .InitializeSingle(), dependsOn, mode); if (!isParallel) { return(JobsUtility.Schedule(ref scheduleParams)); } else { return(JobsUtility.ScheduleParallelFor(ref scheduleParams, chunkCount * batchesPerChunk, 1)); } }
unsafe static public JobHandle ScheduleBatch <T>(this T jobData, int arrayLength, int minIndicesPerJobCount, JobHandle dependsOn = new JobHandle()) where T : struct, IJobParallelForBatched { #if UNITY_2020_2_OR_NEWER // This was renamed in Unity 2020.2 var scheduleMode = ScheduleMode.Parallel; #else var scheduleMode = ScheduleMode.Batched; #endif var scheduleParams = new JobsUtility.JobScheduleParameters(UnsafeUtility.AddressOf(ref jobData), ParallelForBatchJobStruct <T> .Initialize(), dependsOn, scheduleMode); return(JobsUtility.ScheduleParallelFor(ref scheduleParams, arrayLength, minIndicesPerJobCount)); }
public static IntPtr Initialize() { if (jobReflectionData == IntPtr.Zero) { #if UNITY_2020_2_OR_NEWER jobReflectionData = JobsUtility.CreateJobReflectionData(typeof(T), (ExecuteJobFunction)Execute, null, null); #else jobReflectionData = JobsUtility.CreateJobReflectionData(typeof(T), JobType.ParallelFor, (ExecuteJobFunction)Execute); #endif } return(jobReflectionData); }
internal static IntPtr InitializeSingle() { #if UNITY_2020_2_OR_NEWER && !UNITY_DOTSRUNTIME return(InitializeParallel()); #else if (s_JobReflectionDataSingle == IntPtr.Zero) { s_JobReflectionDataSingle = JobsUtility.CreateJobReflectionData(typeof(JobEntityBatchWrapper <T>), typeof(T), JobType.Single, (ExecuteJobFunction)Execute); } return(s_JobReflectionDataSingle); #endif }
unsafe public static JobHandle Schedule <T, U>(this T jobData, NativeList <U> list, int innerloopBatchCount, JobHandle dependsOn = new JobHandle()) where T : struct, IJobParallelFor where U : struct { var scheduleParams = new JobsUtility.JobScheduleParameters(UnsafeUtility.AddressOf(ref jobData), ParallelForJobStruct <T> .Initialize(), dependsOn, ScheduleMode.Batched); void *atomicSafetyHandlePtr = null; #if ENABLE_UNITY_COLLECTIONS_CHECKS var safety = NativeListUnsafeUtility.GetAtomicSafetyHandle(ref list); atomicSafetyHandlePtr = UnsafeUtility.AddressOf(ref safety); #endif return(JobsUtility.ScheduleParallelForDeferArraySize(ref scheduleParams, innerloopBatchCount, NativeListUnsafeUtility.GetInternalListDataPtrUnchecked(ref list), atomicSafetyHandlePtr)); }