Merge pull request #4298 from JensNockert/byteswap
Add support for byteswap intrinsics
This commit is contained in:
commit
0873553680
5 changed files with 46 additions and 0 deletions
|
|
@ -2446,6 +2446,12 @@ fn declare_intrinsics(llmod: ModuleRef) -> HashMap<~str, ValueRef> {
|
|||
T_fn(~[T_i32(), T_i1()], T_i32()));
|
||||
let cttz64 = decl_cdecl_fn(llmod, ~"llvm.cttz.i64",
|
||||
T_fn(~[T_i64(), T_i1()], T_i64()));
|
||||
let bswap16 = decl_cdecl_fn(llmod, ~"llvm.bswap.i16",
|
||||
T_fn(~[T_i16()], T_i16()));
|
||||
let bswap32 = decl_cdecl_fn(llmod, ~"llvm.bswap.i32",
|
||||
T_fn(~[T_i32()], T_i32()));
|
||||
let bswap64 = decl_cdecl_fn(llmod, ~"llvm.bswap.i64",
|
||||
T_fn(~[T_i64()], T_i64()));
|
||||
|
||||
let intrinsics = HashMap();
|
||||
intrinsics.insert(~"llvm.gcroot", gcroot);
|
||||
|
|
@ -2498,6 +2504,9 @@ fn declare_intrinsics(llmod: ModuleRef) -> HashMap<~str, ValueRef> {
|
|||
intrinsics.insert(~"llvm.cttz.i16", cttz16);
|
||||
intrinsics.insert(~"llvm.cttz.i32", cttz32);
|
||||
intrinsics.insert(~"llvm.cttz.i64", cttz64);
|
||||
intrinsics.insert(~"llvm.bswap.i16", bswap16);
|
||||
intrinsics.insert(~"llvm.bswap.i32", bswap32);
|
||||
intrinsics.insert(~"llvm.bswap.i64", bswap64);
|
||||
|
||||
return intrinsics;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1267,6 +1267,21 @@ fn trans_intrinsic(ccx: @crate_ctxt, decl: ValueRef, item: @ast::foreign_item,
|
|||
let cttz = ccx.intrinsics.get(~"llvm.cttz.i64");
|
||||
Store(bcx, Call(bcx, cttz, ~[x, y]), fcx.llretptr)
|
||||
}
|
||||
~"bswap16" => {
|
||||
let x = get_param(decl, first_real_arg);
|
||||
let cttz = ccx.intrinsics.get(~"llvm.bswap.i16");
|
||||
Store(bcx, Call(bcx, cttz, ~[x]), fcx.llretptr)
|
||||
}
|
||||
~"bswap32" => {
|
||||
let x = get_param(decl, first_real_arg);
|
||||
let cttz = ccx.intrinsics.get(~"llvm.bswap.i32");
|
||||
Store(bcx, Call(bcx, cttz, ~[x]), fcx.llretptr)
|
||||
}
|
||||
~"bswap64" => {
|
||||
let x = get_param(decl, first_real_arg);
|
||||
let cttz = ccx.intrinsics.get(~"llvm.bswap.i64");
|
||||
Store(bcx, Call(bcx, cttz, ~[x]), fcx.llretptr)
|
||||
}
|
||||
_ => {
|
||||
// Could we make this an enum rather than a string? does it get
|
||||
// checked earlier?
|
||||
|
|
|
|||
|
|
@ -140,6 +140,8 @@ fn type_uses_for(ccx: @crate_ctxt, fn_id: def_id, n_tps: uint)
|
|||
~"ctlz8" | ~"ctlz16" | ~"ctlz32" | ~"ctlz64" => 0,
|
||||
~"cttz8" | ~"cttz16" | ~"cttz32" | ~"cttz64" => 0,
|
||||
|
||||
~"bswap16" | ~"bswap32" | ~"bswap64" => 0,
|
||||
|
||||
// would be cool to make these an enum instead of strings!
|
||||
_ => fail ~"unknown intrinsic in type_use"
|
||||
};
|
||||
|
|
|
|||
|
|
@ -3224,6 +3224,18 @@ fn check_intrinsic_type(ccx: @crate_ctxt, it: @ast::foreign_item) {
|
|||
(0u, ~[arg(ast::by_copy, ty::mk_i64(tcx))],
|
||||
ty::mk_i64(tcx))
|
||||
}
|
||||
~"bswap16" => {
|
||||
(0u, ~[arg(ast::by_copy, ty::mk_i16(tcx))],
|
||||
ty::mk_i16(tcx))
|
||||
}
|
||||
~"bswap32" => {
|
||||
(0u, ~[arg(ast::by_copy, ty::mk_i32(tcx))],
|
||||
ty::mk_i32(tcx))
|
||||
}
|
||||
~"bswap64" => {
|
||||
(0u, ~[arg(ast::by_copy, ty::mk_i64(tcx))],
|
||||
ty::mk_i64(tcx))
|
||||
}
|
||||
ref other => {
|
||||
tcx.sess.span_err(it.span, ~"unrecognized intrinsic function: `" +
|
||||
(*other) + ~"`");
|
||||
|
|
|
|||
|
|
@ -28,6 +28,10 @@ extern mod rusti {
|
|||
fn cttz16(x: i16) -> i16;
|
||||
fn cttz32(x: i32) -> i32;
|
||||
fn cttz64(x: i64) -> i64;
|
||||
|
||||
fn bswap16(x: i16) -> i16;
|
||||
fn bswap32(x: i32) -> i32;
|
||||
fn bswap64(x: i64) -> i64;
|
||||
}
|
||||
|
||||
fn main() {
|
||||
|
|
@ -109,4 +113,8 @@ fn main() {
|
|||
assert(cttz32(-1i32) == 0i32);
|
||||
assert(cttz64(-1i64) == 0i64);
|
||||
|
||||
assert(bswap16(0x0A0Bi16) == 0x0B0Ai16);
|
||||
assert(bswap32(0x0ABBCC0Di32) == 0x0DCCBB0Ai32);
|
||||
assert(bswap64(0x0122334455667708i64) == 0x0877665544332201i64);
|
||||
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue