inkwell/values/
enums.rs

1use llvm_sys::core::{LLVMGetTypeKind, LLVMGetValueKind, LLVMIsAInstruction, LLVMTypeOf};
2use llvm_sys::prelude::LLVMValueRef;
3use llvm_sys::{LLVMTypeKind, LLVMValueKind};
4
5use crate::types::{AnyTypeEnum, BasicTypeEnum};
6use crate::values::traits::AsValueRef;
7use crate::values::{
8    ArrayValue, FloatValue, FunctionValue, InstructionValue, IntValue, MetadataValue, PhiValue, PointerValue,
9    ScalableVectorValue, StructValue, VectorValue,
10};
11
12use std::convert::TryFrom;
13use std::ffi::CStr;
14use std::fmt::{self, Display};
15
16use super::AnyValue;
17
18macro_rules! enum_value_set {
19    ($enum_name:ident: $($args:ident),*) => (
20        #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
21        pub enum $enum_name<'ctx> {
22            $(
23                $args($args<'ctx>),
24            )*
25        }
26
27        unsafe impl AsValueRef for $enum_name<'_> {
28            fn as_value_ref(&self) -> LLVMValueRef {
29                match *self {
30                    $(
31                        $enum_name::$args(ref t) => t.as_value_ref(),
32                    )*
33                }
34            }
35        }
36
37        $(
38            impl<'ctx> From<$args<'ctx>> for $enum_name<'ctx> {
39                fn from(value: $args) -> $enum_name {
40                    $enum_name::$args(value)
41                }
42            }
43
44            impl<'ctx> PartialEq<$args<'ctx>> for $enum_name<'ctx> {
45                fn eq(&self, other: &$args<'ctx>) -> bool {
46                    self.as_value_ref() == other.as_value_ref()
47                }
48            }
49
50            impl<'ctx> PartialEq<$enum_name<'ctx>> for $args<'ctx> {
51                fn eq(&self, other: &$enum_name<'ctx>) -> bool {
52                    self.as_value_ref() == other.as_value_ref()
53                }
54            }
55
56            impl<'ctx> TryFrom<$enum_name<'ctx>> for $args<'ctx> {
57                type Error = ();
58
59                fn try_from(value: $enum_name<'ctx>) -> Result<Self, Self::Error> {
60                    match value {
61                        $enum_name::$args(ty) => Ok(ty),
62                        _ => Err(()),
63                    }
64                }
65            }
66        )*
67    );
68}
69
70enum_value_set! {AggregateValueEnum: ArrayValue, StructValue}
71enum_value_set! {AnyValueEnum: ArrayValue, IntValue, FloatValue, PhiValue, FunctionValue, PointerValue, StructValue, VectorValue, ScalableVectorValue, InstructionValue, MetadataValue}
72enum_value_set! {BasicValueEnum: ArrayValue, IntValue, FloatValue, PointerValue, StructValue, VectorValue, ScalableVectorValue}
73enum_value_set! {BasicMetadataValueEnum: ArrayValue, IntValue, FloatValue, PointerValue, StructValue, VectorValue, ScalableVectorValue, MetadataValue}
74
75impl<'ctx> AnyValueEnum<'ctx> {
76    /// Get a value from an [LLVMValueRef].
77    ///
78    /// # Safety
79    ///
80    /// The ref must be valid and of supported enum type options ([LLVMTypeKind]).
81    pub unsafe fn new(value: LLVMValueRef) -> Self {
82        match LLVMGetTypeKind(LLVMTypeOf(value)) {
83            LLVMTypeKind::LLVMFloatTypeKind
84            | LLVMTypeKind::LLVMFP128TypeKind
85            | LLVMTypeKind::LLVMDoubleTypeKind
86            | LLVMTypeKind::LLVMHalfTypeKind
87            | LLVMTypeKind::LLVMX86_FP80TypeKind
88            | LLVMTypeKind::LLVMPPC_FP128TypeKind => AnyValueEnum::FloatValue(FloatValue::new(value)),
89            LLVMTypeKind::LLVMIntegerTypeKind => AnyValueEnum::IntValue(IntValue::new(value)),
90            LLVMTypeKind::LLVMStructTypeKind => AnyValueEnum::StructValue(StructValue::new(value)),
91            LLVMTypeKind::LLVMPointerTypeKind => match LLVMGetValueKind(value) {
92                LLVMValueKind::LLVMFunctionValueKind => AnyValueEnum::FunctionValue(FunctionValue::new(value).unwrap()),
93                _ => AnyValueEnum::PointerValue(PointerValue::new(value)),
94            },
95            LLVMTypeKind::LLVMArrayTypeKind => AnyValueEnum::ArrayValue(ArrayValue::new(value)),
96            LLVMTypeKind::LLVMVectorTypeKind => AnyValueEnum::VectorValue(VectorValue::new(value)),
97            #[cfg(any(
98                feature = "llvm11-0",
99                feature = "llvm12-0",
100                feature = "llvm13-0",
101                feature = "llvm14-0",
102                feature = "llvm15-0",
103                feature = "llvm16-0",
104                feature = "llvm17-0",
105                feature = "llvm18-0"
106            ))]
107            LLVMTypeKind::LLVMScalableVectorTypeKind => {
108                AnyValueEnum::ScalableVectorValue(ScalableVectorValue::new(value))
109            },
110            LLVMTypeKind::LLVMFunctionTypeKind => AnyValueEnum::FunctionValue(FunctionValue::new(value).unwrap()),
111            LLVMTypeKind::LLVMVoidTypeKind => {
112                if LLVMIsAInstruction(value).is_null() {
113                    panic!("Void value isn't an instruction.");
114                }
115                AnyValueEnum::InstructionValue(InstructionValue::new(value))
116            },
117            LLVMTypeKind::LLVMMetadataTypeKind => panic!("Metadata values are not supported as AnyValue's."),
118            _ => panic!("The given type is not supported."),
119        }
120    }
121
122    pub fn get_type(&self) -> AnyTypeEnum<'ctx> {
123        unsafe { AnyTypeEnum::new(LLVMTypeOf(self.as_value_ref())) }
124    }
125
126    pub fn is_array_value(self) -> bool {
127        matches!(self, AnyValueEnum::ArrayValue(_))
128    }
129
130    pub fn is_int_value(self) -> bool {
131        matches!(self, AnyValueEnum::IntValue(_))
132    }
133
134    pub fn is_float_value(self) -> bool {
135        matches!(self, AnyValueEnum::FloatValue(_))
136    }
137
138    pub fn is_phi_value(self) -> bool {
139        matches!(self, AnyValueEnum::PhiValue(_))
140    }
141
142    pub fn is_function_value(self) -> bool {
143        matches!(self, AnyValueEnum::FunctionValue(_))
144    }
145
146    pub fn is_pointer_value(self) -> bool {
147        matches!(self, AnyValueEnum::PointerValue(_))
148    }
149
150    pub fn is_struct_value(self) -> bool {
151        matches!(self, AnyValueEnum::StructValue(_))
152    }
153
154    pub fn is_vector_value(self) -> bool {
155        matches!(self, AnyValueEnum::VectorValue(_))
156    }
157
158    pub fn is_scalable_vector_value(self) -> bool {
159        matches!(self, AnyValueEnum::ScalableVectorValue(_))
160    }
161
162    pub fn is_instruction_value(self) -> bool {
163        matches!(self, AnyValueEnum::InstructionValue(_))
164    }
165
166    pub fn into_array_value(self) -> ArrayValue<'ctx> {
167        if let AnyValueEnum::ArrayValue(v) = self {
168            v
169        } else {
170            panic!("Found {:?} but expected the ArrayValue variant", self)
171        }
172    }
173
174    pub fn into_int_value(self) -> IntValue<'ctx> {
175        if let AnyValueEnum::IntValue(v) = self {
176            v
177        } else {
178            panic!("Found {:?} but expected the IntValue variant", self)
179        }
180    }
181
182    pub fn into_float_value(self) -> FloatValue<'ctx> {
183        if let AnyValueEnum::FloatValue(v) = self {
184            v
185        } else {
186            panic!("Found {:?} but expected the FloatValue variant", self)
187        }
188    }
189
190    pub fn into_phi_value(self) -> PhiValue<'ctx> {
191        if let AnyValueEnum::PhiValue(v) = self {
192            v
193        } else {
194            panic!("Found {:?} but expected the PhiValue variant", self)
195        }
196    }
197
198    pub fn into_function_value(self) -> FunctionValue<'ctx> {
199        if let AnyValueEnum::FunctionValue(v) = self {
200            v
201        } else {
202            panic!("Found {:?} but expected the FunctionValue variant", self)
203        }
204    }
205
206    pub fn into_pointer_value(self) -> PointerValue<'ctx> {
207        if let AnyValueEnum::PointerValue(v) = self {
208            v
209        } else {
210            panic!("Found {:?} but expected the PointerValue variant", self)
211        }
212    }
213
214    pub fn into_struct_value(self) -> StructValue<'ctx> {
215        if let AnyValueEnum::StructValue(v) = self {
216            v
217        } else {
218            panic!("Found {:?} but expected the StructValue variant", self)
219        }
220    }
221
222    pub fn into_vector_value(self) -> VectorValue<'ctx> {
223        if let AnyValueEnum::VectorValue(v) = self {
224            v
225        } else {
226            panic!("Found {:?} but expected the VectorValue variant", self)
227        }
228    }
229
230    pub fn into_scalable_vector_value(self) -> ScalableVectorValue<'ctx> {
231        if let AnyValueEnum::ScalableVectorValue(v) = self {
232            v
233        } else {
234            panic!("Found {:?} but expected the ScalableVectorValue variant", self)
235        }
236    }
237
238    pub fn into_instruction_value(self) -> InstructionValue<'ctx> {
239        if let AnyValueEnum::InstructionValue(v) = self {
240            v
241        } else {
242            panic!("Found {:?} but expected the InstructionValue variant", self)
243        }
244    }
245}
246
247impl<'ctx> BasicValueEnum<'ctx> {
248    /// Get a value from an [LLVMValueRef].
249    ///
250    /// # Safety
251    ///
252    /// The ref must be valid and of supported enum type options ([LLVMTypeKind]).
253    pub unsafe fn new(value: LLVMValueRef) -> Self {
254        match LLVMGetTypeKind(LLVMTypeOf(value)) {
255            LLVMTypeKind::LLVMFloatTypeKind
256            | LLVMTypeKind::LLVMFP128TypeKind
257            | LLVMTypeKind::LLVMDoubleTypeKind
258            | LLVMTypeKind::LLVMHalfTypeKind
259            | LLVMTypeKind::LLVMX86_FP80TypeKind
260            | LLVMTypeKind::LLVMPPC_FP128TypeKind => BasicValueEnum::FloatValue(FloatValue::new(value)),
261            LLVMTypeKind::LLVMIntegerTypeKind => BasicValueEnum::IntValue(IntValue::new(value)),
262            LLVMTypeKind::LLVMStructTypeKind => BasicValueEnum::StructValue(StructValue::new(value)),
263            LLVMTypeKind::LLVMPointerTypeKind => BasicValueEnum::PointerValue(PointerValue::new(value)),
264            LLVMTypeKind::LLVMArrayTypeKind => BasicValueEnum::ArrayValue(ArrayValue::new(value)),
265            LLVMTypeKind::LLVMVectorTypeKind => BasicValueEnum::VectorValue(VectorValue::new(value)),
266            #[cfg(any(
267                feature = "llvm11-0",
268                feature = "llvm12-0",
269                feature = "llvm13-0",
270                feature = "llvm14-0",
271                feature = "llvm15-0",
272                feature = "llvm16-0",
273                feature = "llvm17-0",
274                feature = "llvm18-0"
275            ))]
276            LLVMTypeKind::LLVMScalableVectorTypeKind => {
277                BasicValueEnum::ScalableVectorValue(ScalableVectorValue::new(value))
278            },
279            _ => unreachable!("The given type is not a basic type."),
280        }
281    }
282
283    /// Get the name of the `BasicValueEnum`.
284    pub fn get_name(&self) -> &CStr {
285        match self {
286            BasicValueEnum::ArrayValue(v) => v.get_name(),
287            BasicValueEnum::IntValue(v) => v.get_name(),
288            BasicValueEnum::FloatValue(v) => v.get_name(),
289            BasicValueEnum::PointerValue(v) => v.get_name(),
290            BasicValueEnum::StructValue(v) => v.get_name(),
291            BasicValueEnum::VectorValue(v) => v.get_name(),
292            BasicValueEnum::ScalableVectorValue(v) => v.get_name(),
293        }
294    }
295
296    /// Set name of the `BasicValueEnum`.
297    pub fn set_name(&self, name: &str) {
298        match self {
299            BasicValueEnum::ArrayValue(v) => v.set_name(name),
300            BasicValueEnum::IntValue(v) => v.set_name(name),
301            BasicValueEnum::FloatValue(v) => v.set_name(name),
302            BasicValueEnum::PointerValue(v) => v.set_name(name),
303            BasicValueEnum::StructValue(v) => v.set_name(name),
304            BasicValueEnum::VectorValue(v) => v.set_name(name),
305            BasicValueEnum::ScalableVectorValue(v) => v.set_name(name),
306        }
307    }
308
309    pub fn get_type(&self) -> BasicTypeEnum<'ctx> {
310        unsafe { BasicTypeEnum::new(LLVMTypeOf(self.as_value_ref())) }
311    }
312
313    pub fn is_array_value(self) -> bool {
314        matches!(self, BasicValueEnum::ArrayValue(_))
315    }
316
317    pub fn is_int_value(self) -> bool {
318        matches!(self, BasicValueEnum::IntValue(_))
319    }
320
321    pub fn is_float_value(self) -> bool {
322        matches!(self, BasicValueEnum::FloatValue(_))
323    }
324
325    pub fn is_pointer_value(self) -> bool {
326        matches!(self, BasicValueEnum::PointerValue(_))
327    }
328
329    pub fn is_struct_value(self) -> bool {
330        matches!(self, BasicValueEnum::StructValue(_))
331    }
332
333    pub fn is_vector_value(self) -> bool {
334        matches!(self, BasicValueEnum::VectorValue(_))
335    }
336
337    pub fn is_scalable_vector_value(self) -> bool {
338        matches!(self, BasicValueEnum::ScalableVectorValue(_))
339    }
340
341    pub fn into_array_value(self) -> ArrayValue<'ctx> {
342        if let BasicValueEnum::ArrayValue(v) = self {
343            v
344        } else {
345            panic!("Found {:?} but expected the ArrayValue variant", self)
346        }
347    }
348
349    pub fn into_int_value(self) -> IntValue<'ctx> {
350        if let BasicValueEnum::IntValue(v) = self {
351            v
352        } else {
353            panic!("Found {:?} but expected the IntValue variant", self)
354        }
355    }
356
357    pub fn into_float_value(self) -> FloatValue<'ctx> {
358        if let BasicValueEnum::FloatValue(v) = self {
359            v
360        } else {
361            panic!("Found {:?} but expected the FloatValue variant", self)
362        }
363    }
364
365    pub fn into_pointer_value(self) -> PointerValue<'ctx> {
366        if let BasicValueEnum::PointerValue(v) = self {
367            v
368        } else {
369            panic!("Found {:?} but expected PointerValue variant", self)
370        }
371    }
372
373    pub fn into_struct_value(self) -> StructValue<'ctx> {
374        if let BasicValueEnum::StructValue(v) = self {
375            v
376        } else {
377            panic!("Found {:?} but expected the StructValue variant", self)
378        }
379    }
380
381    pub fn into_vector_value(self) -> VectorValue<'ctx> {
382        if let BasicValueEnum::VectorValue(v) = self {
383            v
384        } else {
385            panic!("Found {:?} but expected the VectorValue variant", self)
386        }
387    }
388
389    pub fn into_scalable_vector_value(self) -> ScalableVectorValue<'ctx> {
390        if let BasicValueEnum::ScalableVectorValue(v) = self {
391            v
392        } else {
393            panic!("Found {:?} but expected the ScalableVectorValue variant", self)
394        }
395    }
396}
397
398impl<'ctx> AggregateValueEnum<'ctx> {
399    /// Get a value from an [LLVMValueRef].
400    ///
401    /// # Safety
402    ///
403    /// The ref must be valid and of supported aggregate type enum options ([LLVMTypeKind]).
404    pub unsafe fn new(value: LLVMValueRef) -> Self {
405        match LLVMGetTypeKind(LLVMTypeOf(value)) {
406            LLVMTypeKind::LLVMArrayTypeKind => AggregateValueEnum::ArrayValue(ArrayValue::new(value)),
407            LLVMTypeKind::LLVMStructTypeKind => AggregateValueEnum::StructValue(StructValue::new(value)),
408            _ => unreachable!("The given type is not an aggregate type."),
409        }
410    }
411
412    pub fn is_array_value(self) -> bool {
413        matches!(self, AggregateValueEnum::ArrayValue(_))
414    }
415
416    pub fn is_struct_value(self) -> bool {
417        matches!(self, AggregateValueEnum::StructValue(_))
418    }
419
420    pub fn into_array_value(self) -> ArrayValue<'ctx> {
421        if let AggregateValueEnum::ArrayValue(v) = self {
422            v
423        } else {
424            panic!("Found {:?} but expected the ArrayValue variant", self)
425        }
426    }
427
428    pub fn into_struct_value(self) -> StructValue<'ctx> {
429        if let AggregateValueEnum::StructValue(v) = self {
430            v
431        } else {
432            panic!("Found {:?} but expected the StructValue variant", self)
433        }
434    }
435}
436
437impl<'ctx> BasicMetadataValueEnum<'ctx> {
438    pub(crate) unsafe fn new(value: LLVMValueRef) -> Self {
439        match LLVMGetTypeKind(LLVMTypeOf(value)) {
440            LLVMTypeKind::LLVMFloatTypeKind
441            | LLVMTypeKind::LLVMFP128TypeKind
442            | LLVMTypeKind::LLVMDoubleTypeKind
443            | LLVMTypeKind::LLVMHalfTypeKind
444            | LLVMTypeKind::LLVMX86_FP80TypeKind
445            | LLVMTypeKind::LLVMPPC_FP128TypeKind => BasicMetadataValueEnum::FloatValue(FloatValue::new(value)),
446            LLVMTypeKind::LLVMIntegerTypeKind => BasicMetadataValueEnum::IntValue(IntValue::new(value)),
447            LLVMTypeKind::LLVMStructTypeKind => BasicMetadataValueEnum::StructValue(StructValue::new(value)),
448            LLVMTypeKind::LLVMPointerTypeKind => BasicMetadataValueEnum::PointerValue(PointerValue::new(value)),
449            LLVMTypeKind::LLVMArrayTypeKind => BasicMetadataValueEnum::ArrayValue(ArrayValue::new(value)),
450            LLVMTypeKind::LLVMVectorTypeKind => BasicMetadataValueEnum::VectorValue(VectorValue::new(value)),
451            #[cfg(any(
452                feature = "llvm11-0",
453                feature = "llvm12-0",
454                feature = "llvm13-0",
455                feature = "llvm14-0",
456                feature = "llvm15-0",
457                feature = "llvm16-0",
458                feature = "llvm17-0",
459                feature = "llvm18-0"
460            ))]
461            LLVMTypeKind::LLVMScalableVectorTypeKind => {
462                BasicMetadataValueEnum::ScalableVectorValue(ScalableVectorValue::new(value))
463            },
464            LLVMTypeKind::LLVMMetadataTypeKind => BasicMetadataValueEnum::MetadataValue(MetadataValue::new(value)),
465            _ => unreachable!("Unsupported type"),
466        }
467    }
468
469    pub fn is_array_value(self) -> bool {
470        matches!(self, BasicMetadataValueEnum::ArrayValue(_))
471    }
472
473    pub fn is_int_value(self) -> bool {
474        matches!(self, BasicMetadataValueEnum::IntValue(_))
475    }
476
477    pub fn is_float_value(self) -> bool {
478        matches!(self, BasicMetadataValueEnum::FloatValue(_))
479    }
480
481    pub fn is_pointer_value(self) -> bool {
482        matches!(self, BasicMetadataValueEnum::PointerValue(_))
483    }
484
485    pub fn is_struct_value(self) -> bool {
486        matches!(self, BasicMetadataValueEnum::StructValue(_))
487    }
488
489    pub fn is_vector_value(self) -> bool {
490        matches!(self, BasicMetadataValueEnum::VectorValue(_))
491    }
492
493    pub fn is_scalable_vector_value(self) -> bool {
494        matches!(self, BasicMetadataValueEnum::ScalableVectorValue(_))
495    }
496
497    pub fn is_metadata_value(self) -> bool {
498        matches!(self, BasicMetadataValueEnum::MetadataValue(_))
499    }
500
501    pub fn into_array_value(self) -> ArrayValue<'ctx> {
502        if let BasicMetadataValueEnum::ArrayValue(v) = self {
503            v
504        } else {
505            panic!("Found {:?} but expected the ArrayValue variant", self)
506        }
507    }
508
509    pub fn into_int_value(self) -> IntValue<'ctx> {
510        if let BasicMetadataValueEnum::IntValue(v) = self {
511            v
512        } else {
513            panic!("Found {:?} but expected the IntValue variant", self)
514        }
515    }
516
517    pub fn into_float_value(self) -> FloatValue<'ctx> {
518        if let BasicMetadataValueEnum::FloatValue(v) = self {
519            v
520        } else {
521            panic!("Found {:?} but expected FloatValue variant", self)
522        }
523    }
524
525    pub fn into_pointer_value(self) -> PointerValue<'ctx> {
526        if let BasicMetadataValueEnum::PointerValue(v) = self {
527            v
528        } else {
529            panic!("Found {:?} but expected the PointerValue variant", self)
530        }
531    }
532
533    pub fn into_struct_value(self) -> StructValue<'ctx> {
534        if let BasicMetadataValueEnum::StructValue(v) = self {
535            v
536        } else {
537            panic!("Found {:?} but expected the StructValue variant", self)
538        }
539    }
540
541    pub fn into_vector_value(self) -> VectorValue<'ctx> {
542        if let BasicMetadataValueEnum::VectorValue(v) = self {
543            v
544        } else {
545            panic!("Found {:?} but expected the VectorValue variant", self)
546        }
547    }
548
549    pub fn into_scalable_vector_value(self) -> ScalableVectorValue<'ctx> {
550        if let BasicMetadataValueEnum::ScalableVectorValue(v) = self {
551            v
552        } else {
553            panic!("Found {:?} but expected the ScalableVectorValue variant", self)
554        }
555    }
556
557    pub fn into_metadata_value(self) -> MetadataValue<'ctx> {
558        if let BasicMetadataValueEnum::MetadataValue(v) = self {
559            v
560        } else {
561            panic!("Found {:?} but expected MetaData variant", self)
562        }
563    }
564}
565
566impl<'ctx> From<BasicValueEnum<'ctx>> for AnyValueEnum<'ctx> {
567    fn from(value: BasicValueEnum<'ctx>) -> Self {
568        unsafe { AnyValueEnum::new(value.as_value_ref()) }
569    }
570}
571
572impl<'ctx> From<BasicValueEnum<'ctx>> for BasicMetadataValueEnum<'ctx> {
573    fn from(value: BasicValueEnum<'ctx>) -> Self {
574        unsafe { BasicMetadataValueEnum::new(value.as_value_ref()) }
575    }
576}
577
578impl<'ctx> TryFrom<AnyValueEnum<'ctx>> for BasicValueEnum<'ctx> {
579    type Error = ();
580
581    fn try_from(value: AnyValueEnum<'ctx>) -> Result<Self, Self::Error> {
582        use AnyValueEnum::*;
583        Ok(match value {
584            ArrayValue(av) => av.into(),
585            IntValue(iv) => iv.into(),
586            FloatValue(fv) => fv.into(),
587            PointerValue(pv) => pv.into(),
588            StructValue(sv) => sv.into(),
589            VectorValue(vv) => vv.into(),
590            ScalableVectorValue(vv) => vv.into(),
591            MetadataValue(_) | PhiValue(_) | FunctionValue(_) | InstructionValue(_) => return Err(()),
592        })
593    }
594}
595
596impl<'ctx> TryFrom<AnyValueEnum<'ctx>> for BasicMetadataValueEnum<'ctx> {
597    type Error = ();
598
599    fn try_from(value: AnyValueEnum<'ctx>) -> Result<Self, Self::Error> {
600        use AnyValueEnum::*;
601        Ok(match value {
602            ArrayValue(av) => av.into(),
603            IntValue(iv) => iv.into(),
604            FloatValue(fv) => fv.into(),
605            PointerValue(pv) => pv.into(),
606            StructValue(sv) => sv.into(),
607            VectorValue(vv) => vv.into(),
608            ScalableVectorValue(vv) => vv.into(),
609            MetadataValue(mv) => mv.into(),
610            PhiValue(_) | FunctionValue(_) | InstructionValue(_) => return Err(()),
611        })
612    }
613}
614
615impl<'ctx> TryFrom<BasicMetadataValueEnum<'ctx>> for BasicValueEnum<'ctx> {
616    type Error = ();
617
618    fn try_from(value: BasicMetadataValueEnum<'ctx>) -> Result<Self, Self::Error> {
619        use BasicMetadataValueEnum::*;
620        Ok(match value {
621            ArrayValue(av) => av.into(),
622            IntValue(iv) => iv.into(),
623            FloatValue(fv) => fv.into(),
624            PointerValue(pv) => pv.into(),
625            StructValue(sv) => sv.into(),
626            VectorValue(vv) => vv.into(),
627            ScalableVectorValue(vv) => vv.into(),
628            MetadataValue(_) => return Err(()),
629        })
630    }
631}
632
633impl Display for AggregateValueEnum<'_> {
634    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
635        write!(f, "{}", self.print_to_string())
636    }
637}
638
639impl Display for AnyValueEnum<'_> {
640    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
641        write!(f, "{}", self.print_to_string())
642    }
643}
644
645impl Display for BasicValueEnum<'_> {
646    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
647        write!(f, "{}", self.print_to_string())
648    }
649}
650
651impl Display for BasicMetadataValueEnum<'_> {
652    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
653        write!(f, "{}", self.print_to_string())
654    }
655}