diff options
author | xleroy <xleroy@fca1b0fc-160b-0410-b1d3-a4f43f01ea2e> | 2013-07-29 12:10:11 +0000 |
---|---|---|
committer | xleroy <xleroy@fca1b0fc-160b-0410-b1d3-a4f43f01ea2e> | 2013-07-29 12:10:11 +0000 |
commit | 41b7ecb127b93b1aecc29a298ec21dc94603e6fa (patch) | |
tree | 287ce1cbf88caf973534715c7816d57b9089b265 /arm/Asm.v | |
parent | 4bf8b331372388dc9cb39154c986c918df9e071c (diff) | |
download | compcert-kvx-41b7ecb127b93b1aecc29a298ec21dc94603e6fa.tar.gz compcert-kvx-41b7ecb127b93b1aecc29a298ec21dc94603e6fa.zip |
Optimize integer divisions by positive constants, turning them into
multiply-high and shifts.
git-svn-id: https://yquem.inria.fr/compcert/svn/compcert/trunk@2300 fca1b0fc-160b-0410-b1d3-a4f43f01ea2e
Diffstat (limited to 'arm/Asm.v')
-rw-r--r-- | arm/Asm.v | 28 |
1 files changed, 20 insertions, 8 deletions
@@ -157,9 +157,11 @@ Inductive instruction : Type := | Pstr: ireg -> ireg -> shift_addr -> instruction (**r int32 store *) | Pstrb: ireg -> ireg -> shift_addr -> instruction (**r int8 store *) | Pstrh: ireg -> ireg -> shift_addr -> instruction (**r int16 store *) - | Psdiv: ireg -> ireg -> ireg -> instruction (**r signed division *) + | Psdiv: instruction (**r signed division *) + | Psmull: ireg -> ireg -> ireg -> ireg -> instruction (**r signed multiply long *) | Psub: ireg -> ireg -> shift_op -> instruction (**r integer subtraction *) - | Pudiv: ireg -> ireg -> ireg -> instruction (**r unsigned division *) + | Pudiv: instruction (**r unsigned division *) + | Pumull: ireg -> ireg -> ireg -> ireg -> instruction (**r unsigned multiply long *) (* Floating-point coprocessor instructions (VFP double scalar operations) *) | Pfcpyd: freg -> freg -> instruction (**r float move *) | Pfabsd: freg -> freg -> instruction (**r float absolute value *) @@ -559,18 +561,28 @@ Definition exec_instr (f: function) (i: instruction) (rs: regset) (m: mem) : out exec_store Mint8unsigned (Val.add rs#r2 (eval_shift_addr sa rs)) r1 rs m | Pstrh r1 r2 sa => exec_store Mint16unsigned (Val.add rs#r2 (eval_shift_addr sa rs)) r1 rs m - | Psdiv rd r1 r2 => - match Val.divs rs#r1 rs#r2 with - | Some v => Next (nextinstr (rs#rd <- v)) m + | Psdiv => + match Val.divs rs#IR0 rs#IR1 with + | Some v => Next (nextinstr (rs#IR0 <- v + #IR1 <- Vundef #IR2 <- Vundef + #IR3 <- Vundef #IR12 <- Vundef)) m | None => Stuck end + | Psmull rdl rdh r1 r2 => + Next (nextinstr (rs#rdl <- (Val.mul rs#r1 rs#r2) + #rdh <- (Val.mulhs rs#r1 rs#r2))) m | Psub r1 r2 so => Next (nextinstr (rs#r1 <- (Val.sub rs#r2 (eval_shift_op so rs)))) m - | Pudiv rd r1 r2 => - match Val.divu rs#r1 rs#r2 with - | Some v => Next (nextinstr (rs#rd <- v)) m + | Pudiv => + match Val.divu rs#IR0 rs#IR1 with + | Some v => Next (nextinstr (rs#IR0 <- v + #IR1 <- Vundef #IR2 <- Vundef + #IR3 <- Vundef #IR12 <- Vundef)) m | None => Stuck end + | Pumull rdl rdh r1 r2 => + Next (nextinstr (rs#rdl <- (Val.mul rs#r1 rs#r2) + #rdh <- (Val.mulhu rs#r1 rs#r2))) m (* Floating-point coprocessor instructions *) | Pfcpyd r1 r2 => Next (nextinstr (rs#r1 <- (rs#r2))) m |