@@ -615,38 +615,78 @@ int reflectEnumValue(SwiftReflectionContextRef RC,
615
615
616
616
printf ("Value: " );
617
617
int parens = 0 ;
618
+ // Walk into successively nested enum types...
618
619
while (EnumTypeRef != 0 ) {
619
620
swift_typeinfo_t EnumTypeInfo = swift_reflection_infoForTypeRef (RC , EnumTypeRef );
620
- if (EnumTypeInfo .Kind != SWIFT_NO_PAYLOAD_ENUM
621
- && EnumTypeInfo .Kind != SWIFT_SINGLE_PAYLOAD_ENUM
622
- && EnumTypeInfo .Kind != SWIFT_MULTI_PAYLOAD_ENUM ) {
621
+ switch (EnumTypeInfo .Kind ) {
622
+ case SWIFT_NO_PAYLOAD_ENUM :
623
+ case SWIFT_SINGLE_PAYLOAD_ENUM :
624
+ case SWIFT_MULTI_PAYLOAD_ENUM :
625
+ {
626
+ int CaseIndex ;
627
+ if (!swift_reflection_projectEnumValue (RC , EnumInstance , EnumTypeRef , & CaseIndex )) {
628
+ printf ("swift_reflection_projectEnumValue failed.\n\n" );
629
+ PipeMemoryReader_sendDoneMessage (& Pipe );
630
+ return 1 ; // <<< Test cases rely on detecting this, so must "succeed"
631
+ }
632
+ if ((unsigned )CaseIndex > EnumTypeInfo .NumFields ) {
633
+ printf ("swift_reflection_projectEnumValue returned invalid case.\n\n" );
634
+ PipeMemoryReader_sendDoneMessage (& Pipe );
635
+ return 0 ;
636
+ }
637
+ swift_childinfo_t CaseInfo
638
+ = swift_reflection_childOfTypeRef (RC , EnumTypeRef , CaseIndex );
639
+ printf (".%s" , CaseInfo .Name );
640
+
641
+ if (EnumTypeInfo .Kind == SWIFT_NO_PAYLOAD_ENUM || CaseInfo .TR == 0 ) {
642
+ // No payload here, so end the walk
643
+ EnumTypeRef = 0 ;
644
+ } else {
645
+ // There's a payload!
646
+ printf ("(" );
647
+ parens += 1 ;
648
+ EnumTypeRef = CaseInfo .TR ; // Walk into payload to see if it's an enum
649
+
650
+ if (CaseInfo .Kind == SWIFT_STRONG_REFERENCE ) { // Maybe an indirect enum?
651
+ // Get the pointer value from the target
652
+ void * outFreeContext = NULL ;
653
+ // !!! FIXME !!! obtain the pointer by properly projecting the enum value
654
+ // Next lines are a hack to prove the concept.
655
+ const void * rawPtr
656
+ = PipeMemoryReader_readBytes ((void * )& Pipe , EnumInstance , 8 , & outFreeContext );
657
+ uintptr_t instance = * (uintptr_t * )rawPtr & 0xffffffffffffff8ULL ;
658
+ PipeMemoryReader_freeBytes ((void * )& Pipe , rawPtr , outFreeContext );
659
+
660
+ // Indirect enum stores the payload as the first field of a closure context
661
+ swift_typeinfo_t TI = swift_reflection_infoForInstance (RC , instance );
662
+ if (TI .Kind == SWIFT_CLOSURE_CONTEXT ) {
663
+ // Yep, it's an indirect enum. Let's follow the pointer...
664
+ // TODO: Could we get here if we have an enum whose payload is a closure?
665
+ swift_childinfo_t CaseInfo
666
+ = swift_reflection_childOfInstance (RC , instance , 0 );
667
+ if (CaseInfo .Kind == SWIFT_NO_PAYLOAD_ENUM
668
+ || CaseInfo .Kind == SWIFT_SINGLE_PAYLOAD_ENUM
669
+ || CaseInfo .Kind == SWIFT_MULTI_PAYLOAD_ENUM ) {
670
+ // Found the indirect enum storage, loop to print it out.
671
+ EnumTypeRef = CaseInfo .TR ;
672
+ EnumInstance = instance + CaseInfo .Offset ;
673
+ break ;
674
+ }
675
+ }
676
+ }
677
+ }
678
+ break ;
679
+ }
680
+ default :
681
+ {
682
+ EnumTypeRef = 0 ;
623
683
if (parens == 0 ) {
624
684
printf (".??" ); // Enum was optimized away, print "something"
625
685
} else {
626
686
printf ("_" );
627
687
}
628
688
break ;
629
689
}
630
-
631
- int CaseIndex ;
632
- if (!swift_reflection_projectEnumValue (RC , EnumInstance , EnumTypeRef , & CaseIndex )) {
633
- printf ("swift_reflection_projectEnumValue failed.\n\n" );
634
- PipeMemoryReader_sendDoneMessage (& Pipe );
635
- return 1 ; // <<< Test cases rely on detecting this, so must "succeed"
636
- }
637
- if ((unsigned )CaseIndex > EnumTypeInfo .NumFields ) {
638
- printf ("swift_reflection_projectEnumValue returned invalid case.\n\n" );
639
- PipeMemoryReader_sendDoneMessage (& Pipe );
640
- return 0 ;
641
- }
642
-
643
- swift_childinfo_t CaseInfo
644
- = swift_reflection_childOfTypeRef (RC , EnumTypeRef , CaseIndex );
645
- printf (".%s" , CaseInfo .Name );
646
- EnumTypeRef = CaseInfo .TR ;
647
- if (EnumTypeRef != 0 ) {
648
- printf ("(" );
649
- parens += 1 ;
650
690
}
651
691
}
652
692
for (int i = 0 ; i < parens ; ++ i ) {
@@ -724,6 +764,10 @@ int doDumpHeapInstance(const char *BinaryFilename) {
724
764
exit (status );
725
765
}
726
766
default : { // Parent
767
+ for (int i = 5 ; i > 1 ; i -- ) {
768
+ fprintf (stderr , "%d\n" , i );
769
+ sleep (1 );
770
+ }
727
771
close (PipeMemoryReader_getChildReadFD (& Pipe ));
728
772
close (PipeMemoryReader_getChildWriteFD (& Pipe ));
729
773
SwiftReflectionContextRef RC =
0 commit comments