MCPcopy Create free account
hub / github.com/NthTensor/Forte / poll

Method poll

src/scope.rs:700–846  ·  view source on GitHub ↗

Polls the future. # Safety `this` must be a pointer produced by `Arc::into_raw` on an `Arc `. This call takes ownership of exactly one strong reference count for that allocation, consuming it via `Arc::from_raw` internally. The caller must hold "ownership" of one such strong reference.

(this: NonNull<()>, worker: &Worker)

Source from the content-addressed store, hash-verified

698 // after creating it.
699 state: AtomicU32::new(WOKEN),
700 scheduler,
701 })
702 }
703
704 /// Converts an `Arc<ScopeFutureJob>` into a job ref that can be queued on a
705 /// thread pool. The ref-count is not decremented, ensuring that the job
706 /// remains alive while this job ref exists.
707 ///
708 /// Forgetting this job ref will cause a memory leak.
709 fn into_job_ref(self: Arc<Self>) -> JobRef {
710 // SAFETY: Pointers created by `Arc::into_raw` are never null.
711 let job_pointer = unsafe {
712 NonNull::new_unchecked(Arc::into_raw(self).cast_mut().cast())
713 };
714
715 // SAFETY: `JobRef::new` requires us to show that `execute` will only be
716 // called on the resulting `JobRef` where it is sound to call `poll` on
717 // `job_pointer`.
718 //
719 // `Poll` has two obligations:
720 //
721 // * `job_pointer` must have been produced by `Arc::into_raw` on an
722 // `Arc<Self>`.
723 //
724 // We produced `job_pointer` this way just above.
725 //
726 // * We must hold ownership of exactly one strong reference count for
727 // the allocation.
728 //
729 // We start with an `Arc<Self>`, so we must own a strong reference.
730 // Calling `Arc::into_raw` transfers the strong count of `self` onto
731 // `job_pointer` without decrementing it. Therefore, when `execute`
732 // is called, there will still be a strong reference for it to
733 // consume.
734 //
735 // `JobRef::new` also requires that `poll` not unwind. See the
736 // doc-comment for `poll` for an argument as to why this is the case.
737 unsafe { JobRef::new(job_pointer, Self::poll) }
738 }
739
740 /// Schedules this job to be polled, by converting it into a `JobRef` and
741 /// handing that to the job's own `scheduler`. The `worker` param should be
742 /// the same as calling `Worker::with_current`.
743 fn schedule(self: Arc<Self>, worker: Option<&Worker>) {
744 // Clone a strong reference so the allocation, and therefore the
745 // `scheduler` field, stays alive for the entire `schedule` call.
746 //
747 // `into_job_ref` consumes `self` via `Arc::into_raw`, moving our strong
748 // reference into the `JobRef` *without* decrementing the count. The act
749 // of calling `schedule` enqueues that `JobRef`, after which another
750 // worker may execute and drop it before `schedule` returns. Holding
751 // `this` keeps an independent strong reference alive until the end of
752 // this function, so borrowing `this.scheduler` across the call cannot
753 // dangle.
754 let this = Arc::clone(&self);
755 let job_ref = self.into_job_ref();
756 this.scheduler.schedule(job_ref, worker);
757 }

Callers 1

block_onMethod · 0.80

Calls 5

halt_unwindingFunction · 0.85
getMethod · 0.80
store_panicMethod · 0.80
scheduleMethod · 0.45
wake_by_refMethod · 0.45

Tested by

no test coverage detected