Skip to content

Commit 227391e

Browse files
committed
Added more int, float, and pointer const methods
1 parent f6f367f commit 227391e

File tree

6 files changed

+177
-13
lines changed

6 files changed

+177
-13
lines changed

src/builder.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -697,6 +697,7 @@ impl Builder {
697697

698698
// REVIEW: How does LLVM treat out of bound index? Maybe we should return an Option?
699699
// or is that only in bounds GEP
700+
// REVIEW: Should this be AggregatePointerValue?
700701
pub fn build_extract_value(&self, value: &AggregateValue, index: u32, name: &str) -> BasicValueEnum {
701702
let c_string = CString::new(name).expect("Conversion to CString failed unexpectedly");
702703

@@ -707,6 +708,7 @@ impl Builder {
707708
BasicValueEnum::new(value)
708709
}
709710

711+
// REVIEW: Should this be AggregatePointerValue instead of just PointerValue?
710712
pub fn build_insert_value(&self, value: &BasicValue, ptr: &PointerValue, index: u32, name: &str) -> InstructionValue {
711713
let c_string = CString::new(name).expect("Conversion to CString failed unexpectedly");
712714

src/types/float_type.rs

Lines changed: 14 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
1-
use llvm_sys::core::{LLVMConstReal, LLVMConstNull, LLVMHalfType, LLVMFloatType, LLVMDoubleType, LLVMFP128Type, LLVMPPCFP128Type};
1+
use llvm_sys::core::{LLVMConstReal, LLVMConstNull, LLVMHalfType, LLVMFloatType, LLVMDoubleType, LLVMFP128Type, LLVMPPCFP128Type, LLVMConstRealOfString};
22
use llvm_sys::prelude::LLVMTypeRef;
33

4-
use std::ffi::CStr;
4+
use std::ffi::{CString, CStr};
55

66
use context::ContextRef;
77
use types::traits::AsTypeRef;
@@ -42,6 +42,18 @@ impl FloatType {
4242
FloatValue::new(value)
4343
}
4444

45+
// REVIEW: What happens when string is invalid? Nullptr?
46+
// REVIEW: Difference of LLVMConstRealOfStringAndSize?
47+
pub fn const_float_from_string(&self, string: &str) -> FloatValue {
48+
let c_string = CString::new(string).expect("Conversion to CString failed unexpectedly");
49+
50+
let value = unsafe {
51+
LLVMConstRealOfString(self.as_type_ref(), c_string.as_ptr())
52+
};
53+
54+
FloatValue::new(value)
55+
}
56+
4557
pub fn const_null_ptr(&self) -> PointerValue {
4658
self.float_type.const_null_ptr()
4759
}

src/types/int_type.rs

Lines changed: 14 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
1-
use llvm_sys::core::{LLVMInt1Type, LLVMInt8Type, LLVMInt16Type, LLVMInt32Type, LLVMInt64Type, LLVMConstInt, LLVMConstNull, LLVMConstAllOnes, LLVMIntType, LLVMGetIntTypeWidth};
1+
use llvm_sys::core::{LLVMInt1Type, LLVMInt8Type, LLVMInt16Type, LLVMInt32Type, LLVMInt64Type, LLVMConstInt, LLVMConstNull, LLVMConstAllOnes, LLVMIntType, LLVMGetIntTypeWidth, LLVMConstIntOfString};
22
use llvm_sys::prelude::LLVMTypeRef;
33

4-
use std::ffi::CStr;
4+
use std::ffi::{CString, CStr};
55

66
use context::ContextRef;
77
use types::traits::AsTypeRef;
@@ -85,6 +85,18 @@ impl IntType {
8585
IntValue::new(value)
8686
}
8787

88+
// REVIEW: What happens when string is invalid? Nullptr?
89+
// REVIEW: Difference of LLVMConstIntOfStringAndSize?
90+
pub fn const_int_from_string(&self, string: &str, radix: u8) -> IntValue {
91+
let c_string = CString::new(string).expect("Conversion to CString failed unexpectedly");
92+
93+
let value = unsafe {
94+
LLVMConstIntOfString(self.as_type_ref(), c_string.as_ptr(), radix)
95+
};
96+
97+
IntValue::new(value)
98+
}
99+
88100
pub fn const_all_ones(&self) -> IntValue {
89101
let value = unsafe {
90102
LLVMConstAllOnes(self.as_type_ref())

src/values/float_value.rs

Lines changed: 35 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,11 @@
1-
use llvm_sys::core::{LLVMConstFNeg, LLVMConstFAdd, LLVMConstFSub, LLVMConstFMul, LLVMConstFDiv, LLVMConstFRem, LLVMConstFPCast};
1+
use llvm_sys::core::{LLVMConstFNeg, LLVMConstFAdd, LLVMConstFSub, LLVMConstFMul, LLVMConstFDiv, LLVMConstFRem, LLVMConstFPCast, LLVMConstFPToUI, LLVMConstFPToSI, LLVMConstFPTrunc, LLVMConstFPExt};
22
use llvm_sys::prelude::LLVMValueRef;
33

44
use std::ffi::CStr;
55

6-
use types::FloatType;
7-
use types::AsTypeRef;
6+
use types::{AsTypeRef, FloatType, IntType};
87
use values::traits::AsValueRef;
9-
use values::{InstructionValue, Value, MetadataValue};
8+
use values::{InstructionValue, IntValue, Value, MetadataValue};
109

1110
#[derive(Debug, PartialEq, Eq)]
1211
pub struct FloatValue {
@@ -114,6 +113,38 @@ impl FloatValue {
114113
FloatValue::new(value)
115114
}
116115

116+
pub fn const_to_unsigned_int(&self, int_type: &IntType) -> IntValue {
117+
let value = unsafe {
118+
LLVMConstFPToUI(self.as_value_ref(), int_type.as_type_ref())
119+
};
120+
121+
IntValue::new(value)
122+
}
123+
124+
pub fn const_to_signed_int(&self, int_type: &IntType) -> IntValue {
125+
let value = unsafe {
126+
LLVMConstFPToSI(self.as_value_ref(), int_type.as_type_ref())
127+
};
128+
129+
IntValue::new(value)
130+
}
131+
132+
pub fn const_truncate(&self, float_type: &FloatType) -> FloatValue {
133+
let value = unsafe {
134+
LLVMConstFPTrunc(self.as_value_ref(), float_type.as_type_ref())
135+
};
136+
137+
FloatValue::new(value)
138+
}
139+
140+
pub fn const_extend(&self, float_type: &FloatType) -> FloatValue {
141+
let value = unsafe {
142+
LLVMConstFPExt(self.as_value_ref(), float_type.as_type_ref())
143+
};
144+
145+
FloatValue::new(value)
146+
}
147+
117148
pub fn has_metadata(&self) -> bool {
118149
self.float_value.has_metadata()
119150
}

src/values/int_value.rs

Lines changed: 61 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
use llvm_sys::core::{LLVMConstNot, LLVMConstNeg, LLVMConstNSWNeg, LLVMConstNUWNeg, LLVMConstAdd, LLVMConstNSWAdd, LLVMConstNUWAdd, LLVMConstSub, LLVMConstNSWSub, LLVMConstNUWSub, LLVMConstMul, LLVMConstNSWMul, LLVMConstNUWMul, LLVMConstUDiv, LLVMConstSDiv, LLVMConstSRem, LLVMConstURem, LLVMConstIntCast, LLVMConstXor, LLVMConstOr, LLVMConstAnd, LLVMConstExactSDiv, LLVMConstShl, LLVMConstLShr, LLVMConstAShr, LLVMConstUIToFP, LLVMConstSIToFP, LLVMConstIntToPtr};
1+
use llvm_sys::core::{LLVMConstNot, LLVMConstNeg, LLVMConstNSWNeg, LLVMConstNUWNeg, LLVMConstAdd, LLVMConstNSWAdd, LLVMConstNUWAdd, LLVMConstSub, LLVMConstNSWSub, LLVMConstNUWSub, LLVMConstMul, LLVMConstNSWMul, LLVMConstNUWMul, LLVMConstUDiv, LLVMConstSDiv, LLVMConstSRem, LLVMConstURem, LLVMConstIntCast, LLVMConstXor, LLVMConstOr, LLVMConstAnd, LLVMConstExactSDiv, LLVMConstShl, LLVMConstLShr, LLVMConstAShr, LLVMConstUIToFP, LLVMConstSIToFP, LLVMConstIntToPtr, LLVMConstTrunc, LLVMConstSExt, LLVMConstZExt, LLVMConstTruncOrBitCast, LLVMConstSExtOrBitCast, LLVMConstZExtOrBitCast, LLVMConstBitCast};
22
use llvm_sys::prelude::LLVMValueRef;
33

44
use std::ffi::CStr;
@@ -284,6 +284,66 @@ impl IntValue {
284284
PointerValue::new(value)
285285
}
286286

287+
pub fn const_truncate(&self, int_type: &IntType) -> IntValue {
288+
let value = unsafe {
289+
LLVMConstTrunc(self.as_value_ref(), int_type.as_type_ref())
290+
};
291+
292+
IntValue::new(value)
293+
}
294+
295+
// TODO: More descriptive name
296+
pub fn const_s_extend(&self, int_type: &IntType) -> IntValue {
297+
let value = unsafe {
298+
LLVMConstSExt(self.as_value_ref(), int_type.as_type_ref())
299+
};
300+
301+
IntValue::new(value)
302+
}
303+
304+
// TODO: More descriptive name
305+
pub fn const_z_ext(&self, int_type: &IntType) -> IntValue {
306+
let value = unsafe {
307+
LLVMConstZExt(self.as_value_ref(), int_type.as_type_ref())
308+
};
309+
310+
IntValue::new(value)
311+
}
312+
313+
pub fn const_truncate_or_bit_cast(&self, int_type: &IntType) -> IntValue {
314+
let value = unsafe {
315+
LLVMConstTruncOrBitCast(self.as_value_ref(), int_type.as_type_ref())
316+
};
317+
318+
IntValue::new(value)
319+
}
320+
321+
// TODO: More descriptive name
322+
pub fn const_s_extend_or_bit_cast(&self, int_type: &IntType) -> IntValue {
323+
let value = unsafe {
324+
LLVMConstSExtOrBitCast(self.as_value_ref(), int_type.as_type_ref())
325+
};
326+
327+
IntValue::new(value)
328+
}
329+
330+
// TODO: More descriptive name
331+
pub fn const_z_ext_or_bit_cast(&self, int_type: &IntType) -> IntValue {
332+
let value = unsafe {
333+
LLVMConstZExtOrBitCast(self.as_value_ref(), int_type.as_type_ref())
334+
};
335+
336+
IntValue::new(value)
337+
}
338+
339+
pub fn const_bit_cast(&self, int_type: &IntType) -> IntValue {
340+
let value = unsafe {
341+
LLVMConstBitCast(self.as_value_ref(), int_type.as_type_ref())
342+
};
343+
344+
IntValue::new(value)
345+
}
346+
287347
pub fn has_metadata(&self) -> bool {
288348
self.int_value.has_metadata()
289349
}

src/values/ptr_value.rs

Lines changed: 51 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,14 @@
1+
use llvm_sys::core::{LLVMConstGEP, LLVMConstInBoundsGEP, LLVMConstPtrToInt, LLVMConstPointerCast, LLVMConstAddrSpaceCast};
12
use llvm_sys::prelude::LLVMValueRef;
23

34
use std::ffi::CStr;
45

5-
use types::PointerType;
6-
use values::traits::AsValueRef;
7-
use values::{InstructionValue, Value, MetadataValue};
6+
use types::{AsTypeRef, IntType, PointerType};
7+
use values::{AsValueRef, InstructionValue, IntValue, Value, MetadataValue};
88

99
#[derive(Debug, PartialEq, Eq)]
1010
pub struct PointerValue {
11-
ptr_value: Value
11+
ptr_value: Value,
1212
}
1313

1414
impl PointerValue {
@@ -63,6 +63,53 @@ impl PointerValue {
6363
pub fn set_metadata(&self, metadata: &MetadataValue, kind_id: u32) {
6464
self.ptr_value.set_metadata(metadata, kind_id)
6565
}
66+
67+
// REVIEW: Should this be on array value too?
68+
pub fn const_gep(&self, ordered_indexes: &[&IntValue]) -> PointerValue {
69+
let mut index_values: Vec<LLVMValueRef> = ordered_indexes.iter()
70+
.map(|val| val.as_value_ref())
71+
.collect();
72+
let value = unsafe {
73+
LLVMConstGEP(self.as_value_ref(), index_values.as_mut_ptr(), index_values.len() as u32)
74+
};
75+
76+
PointerValue::new(value)
77+
}
78+
79+
pub fn const_in_bounds_gep(&self, ordered_indexes: &[&IntValue]) -> PointerValue {
80+
let mut index_values: Vec<LLVMValueRef> = ordered_indexes.iter()
81+
.map(|val| val.as_value_ref())
82+
.collect();
83+
let value = unsafe {
84+
LLVMConstInBoundsGEP(self.as_value_ref(), index_values.as_mut_ptr(), index_values.len() as u32)
85+
};
86+
87+
PointerValue::new(value)
88+
}
89+
90+
pub fn const_to_int(&self, int_type: &IntType) -> IntValue {
91+
let value = unsafe {
92+
LLVMConstPtrToInt(self.as_value_ref(), int_type.as_type_ref())
93+
};
94+
95+
IntValue::new(value)
96+
}
97+
98+
pub fn const_cast(&self, ptr_type: &PointerType) -> PointerValue {
99+
let value = unsafe {
100+
LLVMConstPointerCast(self.as_value_ref(), ptr_type.as_type_ref())
101+
};
102+
103+
PointerValue::new(value)
104+
}
105+
106+
pub fn const_address_space_cast(&self, ptr_type: &PointerType) -> PointerValue {
107+
let value = unsafe {
108+
LLVMConstAddrSpaceCast(self.as_value_ref(), ptr_type.as_type_ref())
109+
};
110+
111+
PointerValue::new(value)
112+
}
66113
}
67114

68115
impl AsValueRef for PointerValue {

0 commit comments

Comments
 (0)