1#![allow(unused)] use crate::{
4 Finaly, Generator, LazySequentializer, LockNature, LockResult, Phase, Phased, Sequential,
5 Sequentializer, StaticInfo, Uninit, UniqueLazySequentializer,
6};
7use core::cell::UnsafeCell;
8use core::fmt::{self, Debug, Display, Formatter};
9use core::hint::unreachable_unchecked;
10use core::marker::PhantomData;
11use core::mem::MaybeUninit;
12use core::ops::{Deref, DerefMut};
13
14#[cfg(debug_mode)]
15use crate::CyclicPanic;
16
17#[cfg(any(feature = "parking_lot_core", debug_mode))]
18use std::panic::RefUnwindSafe;
19
20pub(crate) trait LazyPolicy {
22 fn shall_init(_: Phase) -> bool;
24 fn is_accessible(p: Phase) -> bool;
26 fn post_init_is_accessible(p: Phase) -> bool;
28 fn initialized_is_accessible(p: Phase) -> bool;
30}
31
32pub(crate) struct UnInited<T>(UnsafeCell<MaybeUninit<T>>);
35
36impl<T: Finaly> Finaly for UnInited<T> {
37 #[inline(always)]
38 fn finaly(&self) {
39 unsafe { &*self.get() }.finaly();
45 }
46}
47
48impl<T> UnInited<T> {
49 pub const INIT: Self = Self(UnsafeCell::new(MaybeUninit::uninit()));
50}
51
52pub(crate) struct Primed<T>(UnsafeCell<T>);
55
56impl<T: Uninit> Finaly for Primed<T> {
57 #[inline(always)]
58 fn finaly(&self) {
59 unsafe { &mut *self.0.get() }.uninit();
65 }
66}
67
68impl<T> Primed<T> {
69 pub const fn prime(v: T) -> Self {
70 Self(UnsafeCell::new(v))
71 }
72}
73
74pub(crate) struct DropedUnInited<T>(UnsafeCell<MaybeUninit<T>>);
77
78impl<T> Finaly for DropedUnInited<T> {
79 #[inline(always)]
80 fn finaly(&self) {
81 unsafe { self.get().drop_in_place() };
87 }
88}
89
90impl<T> DropedUnInited<T> {
91 pub const INIT: Self = Self(UnsafeCell::new(MaybeUninit::uninit()));
92}
93
94pub(crate) trait LazyData {
99 type Target;
100 fn get(&self) -> *mut Self::Target;
101 unsafe fn init(&self, v: Self::Target);
105 fn init_mut(&mut self, v: Self::Target);
106}
107
108impl<T> LazyData for UnInited<T> {
109 type Target = T;
110 #[inline(always)]
111 fn get(&self) -> *mut T {
112 self.0.get() as *mut T
113 }
114 #[inline(always)]
115 unsafe fn init(&self, v: T) {
116 self.get().write(v)
117 }
118 #[inline(always)]
119 fn init_mut(&mut self, v: T) {
120 *self.0.get_mut() = MaybeUninit::new(v)
121 }
122}
123
124impl<T> LazyData for DropedUnInited<T> {
125 type Target = T;
126 #[inline(always)]
127 fn get(&self) -> *mut T {
128 self.0.get() as *mut T
129 }
130 #[inline(always)]
131 unsafe fn init(&self, v: T) {
132 self.get().write(v)
133 }
134 #[inline(always)]
135 fn init_mut(&mut self, v: T) {
136 *self.0.get_mut() = MaybeUninit::new(v)
137 }
138}
139
140impl<T> LazyData for Primed<T> {
141 type Target = T;
142 #[inline(always)]
143 fn get(&self) -> *mut T {
144 self.0.get()
145 }
146 #[inline(always)]
147 unsafe fn init(&self, v: T) {
148 *self.get() = v
149 }
150 #[inline(always)]
151 fn init_mut(&mut self, v: T) {
152 *self.0.get_mut() = v
153 }
154}
155
156#[derive(Copy, Clone, Eq, PartialEq, Hash, Debug)]
158pub struct AccessError {
159 pub phase: Phase,
160}
161
162impl Display for AccessError {
163 fn fmt(&self, ft: &mut Formatter<'_>) -> fmt::Result {
164 write!(ft, "Error: inaccessible lazy in {}", self.phase)
165 }
166}
167
168#[cfg(feature = "parking_lot_core")]
169impl std::error::Error for AccessError {}
170
171pub(crate) struct GenericLazySeq<T, M> {
172 value: T,
173 sequentializer: M,
174}
175
176pub(crate) struct GenericLockedLazySeq<T, M> {
177 value: T,
178 sequentializer: M,
179}
180
181pub(crate) struct GenericLazy<T, F, M, S> {
185 seq: GenericLazySeq<T, M>,
186 generator: F,
187 phantom: PhantomData<S>,
188 #[cfg(debug_mode)]
189 _info: Option<StaticInfo>,
190}
191
192unsafe impl<T: LazyData, M: Sync> Sync for GenericLazySeq<T, M> where <T as LazyData>::Target: Sync {}
197unsafe impl<T: LazyData, M: Sync> Send for GenericLazySeq<T, M> where <T as LazyData>::Target: Send {}
198
199#[cfg(any(feature = "parking_lot_core", debug_mode))]
200impl<T: LazyData, M: RefUnwindSafe> RefUnwindSafe for GenericLazySeq<T, M> where
201 <T as LazyData>::Target: RefUnwindSafe
202{
203}
204
205unsafe impl<T: LazyData, M: Sync> Sync for GenericLockedLazySeq<T, M> where
210 <T as LazyData>::Target: Send
211{
212}
213unsafe impl<T: LazyData, M: Sync> Send for GenericLockedLazySeq<T, M> where
214 <T as LazyData>::Target: Send
215{
216}
217
218#[cfg(any(feature = "parking_lot_core", debug_mode))]
219impl<T: LazyData, M: RefUnwindSafe> RefUnwindSafe for GenericLockedLazySeq<T, M> where
220 <T as LazyData>::Target: RefUnwindSafe
221{
222}
223
224impl<T, F, M, S> GenericLazy<T, F, M, S> {
225 #[inline(always)]
226 pub const unsafe fn new(generator: F, sequentializer: M, value: T) -> Self {
251 Self {
252 seq: GenericLazySeq {
253 value,
254 sequentializer,
255 },
256 generator,
257 phantom: PhantomData,
258 #[cfg(debug_mode)]
259 _info: None,
260 }
261 }
262 #[inline(always)]
263 pub const unsafe fn new_with_info(
288 generator: F,
289 sequentializer: M,
290 value: T,
291 _info: StaticInfo,
292 ) -> Self {
293 Self {
294 seq: GenericLazySeq {
295 value,
296 sequentializer,
297 },
298 generator,
299 phantom: PhantomData,
300 #[cfg(debug_mode)]
301 _info: Some(_info),
302 }
303 }
304 #[inline(always)]
305 pub fn sequentializer(this: &Self) -> &M {
307 &this.seq.sequentializer
308 }
309 #[inline(always)]
310 pub fn get_raw_data(this: &Self) -> &T {
312 &this.seq.value
313 }
314}
315impl<'a, T, F, M, S> GenericLazy<T, F, M, S>
316where
317 T: 'a + LazyData,
318 M: 'a,
319 M: LazySequentializer<'a, GenericLazySeq<T, M>>,
320 F: 'a + Generator<T::Target>,
321 S: 'a + LazyPolicy,
322{
323 #[inline(always)]
329 pub unsafe fn get_unchecked(&'a self) -> &'a T::Target {
330 &*self.seq.value.get()
331 }
332
333 #[inline(always)]
336 pub fn try_get(&'a self) -> Result<&'a T::Target, AccessError> {
337 check_access::<*mut T::Target, S>(
338 self.seq.value.get(),
339 Phased::phase(&self.seq.sequentializer),
340 )
341 .map(|ptr| unsafe { &*ptr })
342 }
343
344 #[inline(always)]
350 pub fn get(&'a self) -> &'a T::Target {
351 self.try_get().unwrap()
352 }
353
354 #[inline(always)]
360 pub unsafe fn get_mut_unchecked(&'a mut self) -> &'a mut T::Target {
361 &mut *self.seq.value.get()
362 }
363
364 #[inline(always)]
367 pub fn try_get_mut(&'a mut self) -> Result<&'a mut T::Target, AccessError> {
368 check_access::<*mut T::Target, S>(
369 self.seq.value.get(),
370 Phased::phase(&self.seq.sequentializer),
371 )
372 .map(|ptr| unsafe { &mut *ptr })
373 }
374
375 #[inline(always)]
381 pub fn get_mut(&'a mut self) -> &'a mut T::Target {
382 self.try_get_mut().unwrap()
383 }
384
385 #[inline(always)]
391 pub unsafe fn init_then_get_unchecked(&'a self) -> &'a T::Target {
392 self.init();
393 self.get_unchecked()
394 }
395 #[inline(always)]
398 pub fn init_then_try_get(&'a self) -> Result<&'a T::Target, AccessError> {
399 let phase = self.init();
400 post_init_check_access::<*mut T::Target, S>(self.seq.value.get(), phase)
401 .map(|ptr| unsafe { &*ptr })
402 }
403 #[inline(always)]
406 pub fn init_then_get(&'a self) -> &'a T::Target {
407 Self::init_then_try_get(self).unwrap()
408 }
409 #[inline(always)]
410 pub fn init(&'a self) -> Phase {
413 may_debug(
414 || {
415 <M as LazySequentializer<'a, GenericLazySeq<T, M>>>::init(
416 &self.seq,
417 S::shall_init,
418 |data: &T| {
419 let d = Generator::generate(&self.generator);
423 unsafe { data.init(d) };
424 },
425 )
426 },
427 #[cfg(debug_mode)]
428 &self._info,
429 )
430 }
431}
432
433impl<T, F, M, S> GenericLazy<T, F, M, S>
434where
435 M: UniqueLazySequentializer<GenericLazySeq<T, M>>,
436 T: LazyData,
437 S: LazyPolicy,
438 F: Generator<T::Target>,
439{
440 #[inline(always)]
441 pub unsafe fn only_init_then_get_mut_unchecked(&mut self) -> &mut T::Target {
447 self.only_init_unique();
448 &mut *self.seq.value.get()
449 }
450
451 #[inline(always)]
452 pub fn only_init_then_try_get_mut(&mut self) -> Result<&mut T::Target, AccessError> {
455 let phase = self.only_init_unique();
456 post_init_check_access::<*mut T::Target, S>(self.seq.value.get(), phase)
457 .map(|ptr| unsafe { &mut *ptr })
458 }
459
460 #[inline(always)]
461 pub fn only_init_then_get_mut(&mut self) -> &mut T::Target {
464 Self::only_init_then_try_get_mut(self).unwrap()
465 }
466
467 #[inline(always)]
468 pub fn only_init_unique(&mut self) -> Phase {
471 let generator = &self.generator;
472 let seq = &mut self.seq;
473 <M as UniqueLazySequentializer<GenericLazySeq<T, M>>>::init_unique(
474 seq,
475 S::shall_init,
476 |data: &mut T| {
477 let d = Generator::generate(generator);
481 unsafe { data.init_mut(d) };
482 },
483 )
484 }
485}
486
487unsafe impl<T: LazyData, M> Sequential for GenericLazySeq<T, M> {
489 type Data = T;
490 type Sequentializer = M;
491 #[inline(always)]
492 fn sequentializer(this: &Self) -> &Self::Sequentializer {
493 &this.sequentializer
494 }
495 #[inline(always)]
496 fn sequentializer_data_mut(this: &mut Self) -> (&mut Self::Sequentializer, &mut Self::Data) {
497 (&mut this.sequentializer, &mut this.value)
498 }
499 #[inline(always)]
500 fn data(this: &Self) -> &Self::Data {
501 &this.value
502 }
503}
504
505#[must_use = "If unused the write lock is immediatly released"]
506pub(crate) struct WriteGuard<T>(T);
507
508impl<T> Deref for WriteGuard<T>
509where
510 T: Deref,
511 <T as Deref>::Target: LazyData,
512{
513 type Target = <<T as Deref>::Target as LazyData>::Target;
514 #[inline(always)]
515 fn deref(&self) -> &Self::Target {
516 unsafe { &*(*self.0).get() }
517 }
518}
519impl<T> DerefMut for WriteGuard<T>
520where
521 T: Deref,
522 <T as Deref>::Target: LazyData,
523{
524 #[inline(always)]
525 fn deref_mut(&mut self) -> &mut Self::Target {
526 unsafe { &mut *(*self.0).get() }
527 }
528}
529
530impl<T> Phased for WriteGuard<T>
531where
532 T: Phased,
533{
534 #[inline(always)]
535 fn phase(this: &Self) -> Phase {
536 Phased::phase(&this.0)
537 }
538}
539
540impl<T> Debug for WriteGuard<T>
541where
542 T: Deref,
543 <T as Deref>::Target: LazyData,
544 <<T as Deref>::Target as LazyData>::Target: Debug,
545{
546 fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
547 f.debug_tuple("WriteGuard").field(&*self).finish()
548 }
549}
550
551#[must_use = "If unused the read lock is immediatly released"]
552#[derive(Clone)]
553pub(crate) struct ReadGuard<T>(T);
554
555impl<T> Deref for ReadGuard<T>
556where
557 T: Deref,
558 <T as Deref>::Target: LazyData,
559{
560 type Target = <<T as Deref>::Target as LazyData>::Target;
561 #[inline(always)]
562 fn deref(&self) -> &Self::Target {
563 unsafe { &*(*self.0).get() }
564 }
565}
566
567impl<T> Debug for ReadGuard<T>
568where
569 T: Deref,
570 <T as Deref>::Target: LazyData,
571 <<T as Deref>::Target as LazyData>::Target: Debug,
572{
573 fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
574 f.debug_tuple("ReadGuard").field(&*self).finish()
575 }
576}
577
578impl<T, U> From<WriteGuard<T>> for ReadGuard<U>
579where
580 U: From<T>,
581{
582 #[inline(always)]
583 fn from(v: WriteGuard<T>) -> Self {
584 Self(v.0.into())
585 }
586}
587
588impl<T> Phased for ReadGuard<T>
589where
590 T: Phased,
591{
592 #[inline(always)]
593 fn phase(this: &Self) -> Phase {
594 Phased::phase(&this.0)
595 }
596}
597
598#[cfg(any(feature = "parking_lot_core", debug_mode))]
599impl<T: LazyData> RefUnwindSafe for ReadGuard<T> where <T as LazyData>::Target: RefUnwindSafe {}
600
601#[cfg(any(feature = "parking_lot_core", debug_mode))]
602impl<T: LazyData> RefUnwindSafe for WriteGuard<T> where <T as LazyData>::Target: RefUnwindSafe {}
603
604pub(crate) struct GenericLockedLazy<T, F, M, S> {
608 seq: GenericLockedLazySeq<T, M>,
609 generator: F,
610 phantom: PhantomData<S>,
611 #[cfg(debug_mode)]
612 _info: Option<StaticInfo>,
613}
614
615impl<T, F, M, S> GenericLockedLazy<T, F, M, S> {
616 #[inline(always)]
617 pub const unsafe fn new(generator: F, sequentializer: M, value: T) -> Self {
642 Self {
643 seq: GenericLockedLazySeq {
644 value,
645 sequentializer,
646 },
647 generator,
648 phantom: PhantomData,
649 #[cfg(debug_mode)]
650 _info: None,
651 }
652 }
653 #[inline(always)]
654 pub const unsafe fn new_with_info(
679 generator: F,
680 sequentializer: M,
681 value: T,
682 _info: StaticInfo,
683 ) -> Self {
684 Self {
685 seq: GenericLockedLazySeq {
686 value,
687 sequentializer,
688 },
689 generator,
690 phantom: PhantomData,
691 #[cfg(debug_mode)]
692 _info: Some(_info),
693 }
694 }
695 #[inline(always)]
696 pub fn sequentializer(this: &Self) -> &M {
698 &this.seq.sequentializer
699 }
700}
701impl<'a, T, F, M, S> GenericLockedLazy<T, F, M, S>
702where
703 T: 'a + LazyData,
704 M: 'a,
705 M: LazySequentializer<'a, GenericLockedLazySeq<T, M>>,
706 F: 'a + Generator<T::Target>,
707 S: 'a + LazyPolicy,
708 M::ReadGuard: Phased,
709 M::WriteGuard: Phased,
710{
711 #[inline(always)]
717 pub unsafe fn get_mut_unchecked(&'a mut self) -> &'a mut T::Target {
718 &mut *self.seq.value.get()
719 }
720
721 #[inline(always)]
724 pub fn try_get_mut(&'a mut self) -> Result<&'a mut T::Target, AccessError> {
725 check_access::<*mut T::Target, S>(
726 self.seq.value.get(),
727 Phased::phase(&self.seq.sequentializer),
728 )
729 .map(|ptr| unsafe { &mut *ptr })
730 }
731
732 #[inline(always)]
738 pub fn get_mut(&'a mut self) -> &'a mut T::Target {
739 self.try_get_mut().unwrap()
740 }
741 #[inline(always)]
748 pub unsafe fn fast_read_lock_unchecked(this: &'a Self) -> Option<ReadGuard<M::ReadGuard>> {
749 <M as Sequentializer<'a, GenericLockedLazySeq<T, M>>>::try_lock(
750 &this.seq,
751 |_| LockNature::Read,
752 M::INITIALIZED_HINT,
753 )
754 .map(|l| {
755 if let LockResult::Read(l) = l {
756 ReadGuard(l)
757 } else {
758 unreachable_unchecked()
759 }
760 })
761 }
762 #[inline(always)]
767 pub fn fast_try_read_lock(
768 this: &'a Self,
769 ) -> Option<Result<ReadGuard<M::ReadGuard>, AccessError>> {
770 unsafe { Self::fast_read_lock_unchecked(this) }
771 .map(checked_access::<ReadGuard<M::ReadGuard>, S>)
772 }
773
774 #[inline(always)]
781 pub fn fast_read_lock(this: &'a Self) -> Option<ReadGuard<M::ReadGuard>> {
782 Self::fast_try_read_lock(this).map(|r| r.unwrap())
783 }
784
785 #[inline(always)]
791 pub unsafe fn read_lock_unchecked(this: &'a Self) -> ReadGuard<M::ReadGuard> {
792 if let LockResult::Read(l) = <M as Sequentializer<'a, GenericLockedLazySeq<T, M>>>::lock(
793 &this.seq,
794 |_| LockNature::Read,
795 M::INITIALIZED_HINT,
796 ) {
797 ReadGuard(l)
798 } else {
799 unreachable_unchecked()
800 }
801 }
802
803 #[inline(always)]
807 pub fn try_read_lock(this: &'a Self) -> Result<ReadGuard<M::ReadGuard>, AccessError> {
808 checked_access::<ReadGuard<M::ReadGuard>, S>(unsafe { Self::read_lock_unchecked(this) })
809 }
810
811 #[inline(always)]
817 pub fn read_lock(this: &'a Self) -> ReadGuard<M::ReadGuard> {
818 Self::try_read_lock(this).unwrap()
819 }
820
821 #[inline(always)]
828 pub unsafe fn fast_write_lock_unchecked(this: &'a Self) -> Option<WriteGuard<M::WriteGuard>> {
829 <M as Sequentializer<'a, GenericLockedLazySeq<T, M>>>::try_lock(
830 &this.seq,
831 |_| LockNature::Write,
832 M::INITIALIZED_HINT,
833 )
834 .map(|l| {
835 if let LockResult::Write(l) = l {
836 WriteGuard(l)
837 } else {
838 unreachable_unchecked()
839 }
840 })
841 }
842
843 #[inline(always)]
848 pub fn fast_try_write_lock(
849 this: &'a Self,
850 ) -> Option<Result<WriteGuard<M::WriteGuard>, AccessError>> {
851 unsafe { Self::fast_write_lock_unchecked(this) }
852 .map(checked_access::<WriteGuard<M::WriteGuard>, S>)
853 }
854
855 #[inline(always)]
862 pub fn fast_write_lock(this: &'a Self) -> Option<WriteGuard<M::WriteGuard>> {
863 Self::fast_try_write_lock(this).map(|r| r.unwrap())
864 }
865
866 #[inline(always)]
872 pub unsafe fn write_lock_unchecked(this: &'a Self) -> WriteGuard<M::WriteGuard> {
873 if let LockResult::Write(l) = <M as Sequentializer<'a, GenericLockedLazySeq<T, M>>>::lock(
874 &this.seq,
875 |_| LockNature::Write,
876 M::INITIALIZED_HINT,
877 ) {
878 WriteGuard(l)
879 } else {
880 unreachable_unchecked()
881 }
882 }
883
884 #[inline(always)]
888 pub fn try_write_lock(this: &'a Self) -> Result<WriteGuard<M::WriteGuard>, AccessError> {
889 checked_access::<WriteGuard<M::WriteGuard>, S>(unsafe { Self::write_lock_unchecked(this) })
890 }
891
892 #[inline(always)]
898 pub fn write_lock(this: &'a Self) -> WriteGuard<M::WriteGuard> {
899 Self::try_write_lock(this).unwrap()
900 }
901
902 #[inline(always)]
903 pub unsafe fn init_then_read_lock_unchecked(this: &'a Self) -> ReadGuard<M::ReadGuard> {
910 let r = may_debug(
911 || {
912 <M as LazySequentializer<'a, GenericLockedLazySeq<T, M>>>::init_then_read_guard(
913 &this.seq,
914 S::shall_init,
915 |data: &T| {
916 let d = Generator::generate(&this.generator);
920 #[allow(unused_unsafe)]
921 unsafe {
922 data.init(d)
923 };
924 },
925 )
926 },
927 #[cfg(debug_mode)]
928 &this._info,
929 );
930 ReadGuard(r)
931 }
932
933 #[inline(always)]
938 pub fn init_then_try_read_lock(this: &'a Self) -> Result<ReadGuard<M::ReadGuard>, AccessError> {
939 post_init_checked_access::<ReadGuard<M::ReadGuard>, S>(unsafe {
940 Self::init_then_read_lock_unchecked(this)
941 })
942 }
943
944 #[inline(always)]
951 pub fn init_then_read_lock(this: &'a Self) -> ReadGuard<M::ReadGuard> {
952 Self::init_then_try_read_lock(this).unwrap()
953 }
954
955 #[inline(always)]
963 pub unsafe fn fast_init_then_read_lock_unchecked(
964 this: &'a Self,
965 ) -> Option<ReadGuard<M::ReadGuard>> {
966 may_debug(
967 || {
968 <M as LazySequentializer<'a, GenericLockedLazySeq<T, M>>>::try_init_then_read_guard(
969 &this.seq,
970 S::shall_init,
971 |data: &T| {
972 let d = Generator::generate(&this.generator);
976 #[allow(unused_unsafe)]
977 unsafe {
978 data.init(d)
979 };
980 },
981 )
982 },
983 #[cfg(debug_mode)]
984 &this._info,
985 )
986 .map(ReadGuard)
987 }
988
989 #[inline(always)]
990 pub fn fast_init_then_try_read_lock(
996 this: &'a Self,
997 ) -> Option<Result<ReadGuard<M::ReadGuard>, AccessError>> {
998 unsafe { Self::fast_init_then_read_lock_unchecked(this) }
999 .map(post_init_checked_access::<ReadGuard<M::ReadGuard>, S>)
1000 }
1001
1002 #[inline(always)]
1003 pub fn fast_init_then_read_lock(this: &'a Self) -> Option<ReadGuard<M::ReadGuard>> {
1011 Self::fast_init_then_try_read_lock(this).map(|r| r.unwrap())
1012 }
1013
1014 #[inline(always)]
1015 pub unsafe fn init_then_write_lock_unchecked(this: &'a Self) -> WriteGuard<M::WriteGuard> {
1021 let r = may_debug(
1022 || {
1023 <M as LazySequentializer<'a, GenericLockedLazySeq<T, M>>>::init_then_write_guard(
1024 &this.seq,
1025 S::shall_init,
1026 |data: &T| {
1027 let d = Generator::generate(&this.generator);
1031 #[allow(unused_unsafe)]
1032 unsafe {
1033 data.init(d)
1034 };
1035 },
1036 )
1037 },
1038 #[cfg(debug_mode)]
1039 &this._info,
1040 );
1041 WriteGuard(r)
1042 }
1043
1044 #[inline(always)]
1045 pub fn init_then_try_write_lock(
1049 this: &'a Self,
1050 ) -> Result<WriteGuard<M::WriteGuard>, AccessError> {
1051 post_init_checked_access::<WriteGuard<M::WriteGuard>, S>(unsafe {
1052 Self::init_then_write_lock_unchecked(this)
1053 })
1054 }
1055 #[inline(always)]
1056 #[inline(always)]
1060 pub fn init_then_write_lock(this: &'a Self) -> WriteGuard<M::WriteGuard> {
1061 Self::init_then_try_write_lock(this).unwrap()
1062 }
1063
1064 #[inline(always)]
1065 pub unsafe fn fast_init_then_write_lock_unchecked(
1072 this: &'a Self,
1073 ) -> Option<WriteGuard<M::WriteGuard>> {
1074 may_debug(
1075 || {
1076 <M as LazySequentializer<'a, GenericLockedLazySeq<T, M>>>::try_init_then_write_guard(
1077 &this.seq,
1078 S::shall_init,
1079 |data: &T| {
1080 let d = Generator::generate(&this.generator);
1084 #[allow(unused_unsafe)]
1085 unsafe { data.init(d) };
1086 },
1087 )
1088 },
1089 #[cfg(debug_mode)]
1090 &this._info,
1091 )
1092 .map(WriteGuard)
1093 }
1094 #[inline(always)]
1099 pub fn fast_init_then_try_write_lock(
1100 this: &'a Self,
1101 ) -> Option<Result<WriteGuard<M::WriteGuard>, AccessError>> {
1102 unsafe { Self::fast_init_then_write_lock_unchecked(this) }
1103 .map(post_init_checked_access::<WriteGuard<M::WriteGuard>, S>)
1104 }
1105 #[inline(always)]
1112 pub fn fast_init_then_write_lock(this: &'a Self) -> Option<WriteGuard<M::WriteGuard>> {
1113 Self::fast_init_then_try_write_lock(this).map(|r| r.unwrap())
1114 }
1115}
1116
1117impl<T, F, M, S> GenericLockedLazy<T, F, M, S>
1118where
1119 M: UniqueLazySequentializer<GenericLockedLazySeq<T, M>>,
1120 T: LazyData,
1121 S: LazyPolicy,
1122 F: Generator<T::Target>,
1123{
1124 #[inline(always)]
1125 pub unsafe fn only_init_then_get_mut_unchecked(&mut self) -> &mut T::Target {
1131 self.only_init_unique();
1132 &mut *self.seq.value.get()
1133 }
1134 #[inline(always)]
1135 pub fn only_init_then_try_get_mut(&mut self) -> Result<&mut T::Target, AccessError> {
1138 let phase = self.only_init_unique();
1139 check_access::<*mut T::Target, S>(self.seq.value.get(), phase)
1140 .map(|ptr| unsafe { &mut *ptr })
1141 }
1142 #[inline(always)]
1143 pub fn only_init_then_get_mut(&mut self) -> &mut T::Target {
1146 Self::only_init_then_try_get_mut(self).unwrap()
1147 }
1148 #[inline(always)]
1149 pub fn only_init_unique(&mut self) -> Phase {
1152 let generator = &self.generator;
1153 let seq = &mut self.seq;
1154 <M as UniqueLazySequentializer<GenericLockedLazySeq<T, M>>>::init_unique(
1155 seq,
1156 S::shall_init,
1157 |data: &mut T| {
1158 let d = Generator::generate(generator);
1162 unsafe { data.init_mut(d) };
1163 },
1164 )
1165 }
1166}
1167
1168unsafe impl<T: LazyData, M> Sequential for GenericLockedLazySeq<T, M> {
1170 type Data = T;
1171 type Sequentializer = M;
1172 #[inline(always)]
1173 fn sequentializer(this: &Self) -> &Self::Sequentializer {
1174 &this.sequentializer
1175 }
1176 #[inline(always)]
1177 fn sequentializer_data_mut(this: &mut Self) -> (&mut Self::Sequentializer, &mut Self::Data) {
1178 (&mut this.sequentializer, &mut this.value)
1179 }
1180 #[inline(always)]
1181 fn data(this: &Self) -> &Self::Data {
1182 &this.value
1183 }
1184}
1185impl<F, T, M, S> Deref for GenericLockedLazy<T, F, M, S> {
1186 type Target = T;
1187 #[inline(always)]
1188 fn deref(&self) -> &T {
1190 &self.seq.value
1191 }
1192}
1193impl<T, M> Deref for GenericLockedLazySeq<T, M> {
1194 type Target = T;
1195 #[inline(always)]
1196 fn deref(&self) -> &T {
1198 &self.value
1199 }
1200}
1201
1202impl<F, T, M: Phased, S> Phased for GenericLockedLazy<T, F, M, S> {
1203 #[inline(always)]
1204 fn phase(this: &Self) -> Phase {
1205 Phased::phase(&this.seq.sequentializer)
1206 }
1207}
1208impl<F, T, M: Phased, S> Phased for GenericLazy<T, F, M, S> {
1209 #[inline(always)]
1210 fn phase(this: &Self) -> Phase {
1211 Phased::phase(&this.seq.sequentializer)
1212 }
1213}
1214
1215#[inline(always)]
1216fn may_debug<R, F: FnOnce() -> R>(f: F, #[cfg(debug_mode)] info: &Option<StaticInfo>) -> R {
1217 #[cfg(not(debug_mode))]
1218 {
1219 f()
1220 }
1221 #[cfg(debug_mode)]
1222 {
1223 match std::panic::catch_unwind(std::panic::AssertUnwindSafe(|| f())) {
1224 Ok(r) => r,
1225 Err(x) => {
1226 if x.is::<CyclicPanic>() {
1227 match info {
1228 Some(info) => panic!("Circular initialization of {:#?}", info),
1229 None => panic!("Circular lazy initialization detected"),
1230 }
1231 } else {
1232 std::panic::resume_unwind(x)
1233 }
1234 }
1235 }
1236 }
1237}
1238
1239#[inline(always)]
1240fn check_access<T, S: LazyPolicy>(l: T, phase: Phase) -> Result<T, AccessError> {
1241 if S::is_accessible(phase) {
1242 Ok(l)
1243 } else {
1244 Err(AccessError { phase })
1245 }
1246}
1247
1248#[inline(always)]
1249fn checked_access<T: Phased, S: LazyPolicy>(l: T) -> Result<T, AccessError> {
1250 let phase = Phased::phase(&l);
1251 check_access::<T, S>(l, phase)
1252}
1253#[inline(always)]
1254fn post_init_check_access<T, S: LazyPolicy>(l: T, phase: Phase) -> Result<T, AccessError> {
1255 if S::post_init_is_accessible(phase) {
1256 Ok(l)
1257 } else {
1258 Err(AccessError { phase })
1259 }
1260}
1261
1262#[inline(always)]
1263fn post_init_checked_access<T: Phased, S: LazyPolicy>(l: T) -> Result<T, AccessError> {
1264 let phase = Phased::phase(&l);
1265 post_init_check_access::<T, S>(l, phase)
1266}