From 130746bc856f5c2eb5672cceb0e1304ee2c95b1e Mon Sep 17 00:00:00 2001 From: johannst Date: Wed, 28 Feb 2024 18:32:44 +0000 Subject: deploy: 7cc72737a0140f5f71e9d83d4f87503eb4c7604f --- src/tiny_vm/tiny_vm.rs.html | 103 +++++++++++++++++++++++++------------------- 1 file changed, 59 insertions(+), 44 deletions(-) (limited to 'src/tiny_vm/tiny_vm.rs.html') diff --git a/src/tiny_vm/tiny_vm.rs.html b/src/tiny_vm/tiny_vm.rs.html index d36abd1..938bc61 100644 --- a/src/tiny_vm/tiny_vm.rs.html +++ b/src/tiny_vm/tiny_vm.rs.html @@ -1,4 +1,5 @@ -tiny_vm.rs - source
1
+tiny_vm.rs - source
+    
1
 2
 3
 4
@@ -696,12 +697,19 @@
 696
 697
 698
+699
+700
+701
+702
+703
+704
+705
 
//! TinyVm example.
 //!
-//! This example introduces as simple 16 bit virtual machine the [`TinyVm`]. The VM consits of
-//! three registers defined in [`TinyReg`], a separate _data_ and _insutrction_ memory and a small
+//! This example introduces a simple 16 bit virtual machine the [`TinyVm`]. The VM consists of
+//! three registers defined in [`TinyReg`], a separate _data_ and _instruction_ memory and a small
 //! set of instructions [`TinyInsn`], sufficient to implement a guest program to compute the
-//! fiibonacci sequence.
+//! Fibonacci sequence.
 //!
 //! The `TinyVm` implements a simple _just-in-time (JIT)_ compiler to demonstrate the
 //! [`juicebox_asm`] crate. Additionally, it implements a reference _interpreter_.
@@ -801,7 +809,7 @@
 ///                    End of basic block, executed N instructions,
 ///                    must re-enter at `pc = R`.
 /// ```
-type JitFn = extern "C" fn(*mut u16, *mut u8) -> JitRet;
+type JitFn = extern "C" fn(*mut u16, *mut u8) -> JitRet;
 
 /// The `TinyVm` virtual machine state.
 pub struct TinyVm {
@@ -842,7 +850,9 @@
             // -- JIT state.
             jit_cache,
             rt: Runtime::new(),
-        }
+            // Confifigure the runtime to generates perf meta data.
+            //rt: Runtime::with_profile(),
+        }
     }
 
     /// Read guest register.
@@ -874,11 +884,11 @@
 
     /// Dump the VM state to stdout.
     pub fn dump(&self) {
-        println!("-- TinyVm state --");
-        println!("  ICNT: {}", self.icnt);
-        println!("  PC  : {:02x}", self.pc - 1);
+        println!("-- TinyVm state --");
+        println!("  ICNT: {}", self.icnt);
+        println!("  PC  : {:02x}", self.pc - 1);
         println!(
-            "  A:{:04x} B:{:04x} C:{:04x}",
+            "  A:{:04x} B:{:04x} C:{:04x}",
             self.read_reg(TinyReg::A),
             self.read_reg(TinyReg::B),
             self.read_reg(TinyReg::C),
@@ -887,16 +897,16 @@
 
     /// Run in interpreter mode until the next [`TinyInsn::Halt`] instruction is hit.
     pub fn interp(&mut self) {
-        'outer: loop {
+        'outer: loop {
             let insn = self.imem[self.pc];
-            //println!("[0x{:02x}] {:?}", self.pc, insn);
+            //println!("[0x{:02x}] {:?}", self.pc, insn);
 
             self.pc = self.pc.wrapping_add(1);
             self.icnt += 1;
 
             match insn {
                 TinyInsn::Halt => {
-                    break 'outer;
+                    break 'outer;
                 }
                 TinyInsn::LoadImm(a, imm) => {
                     self.write_reg(a, imm);
@@ -932,34 +942,39 @@
     /// Run in JIT mode until the next [`TinyInsn::Halt`] instruction is hit. Translate guest
     /// _basic blocks_ on demand.
     pub fn jit(&mut self) {
-        'outer: loop {
-            if let Some(bb_fn) = self.jit_cache[self.pc] {
-                match bb_fn(self.regs.as_mut_ptr(), self.dmem.as_mut_ptr()) {
-                    JitRet(0, insn) => {
-                        self.pc += insn as usize;
-                        self.icnt += insn as usize;
-                        break 'outer;
-                    }
-                    JitRet(insn, reenter_pc) => {
-                        self.pc = reenter_pc as usize;
-                        self.icnt += insn as usize;
-                    }
-                }
+        'outer: loop {
+            let bb_fn = if let Some(bb_fn) = self.jit_cache[self.pc] {
+                bb_fn
             } else {
                 let bb_fn = self.translate_next_bb();
                 self.jit_cache[self.pc] = Some(bb_fn);
-                //println!("[0x{:02x}] translated bb at {:p}", self.pc, bb_fn);
-            }
+                //println!("[0x{:02x}] translated bb at {:p}", self.pc, bb_fn);
+                bb_fn
+            };
+
+            match bb_fn(self.regs.as_mut_ptr(), self.dmem.as_mut_ptr()) {
+                // HALT instruction hit.
+                JitRet(0, insn) => {
+                    self.pc += insn as usize;
+                    self.icnt += insn as usize;
+                    break 'outer;
+                }
+                // End of basic block, re-enter.
+                JitRet(insn, reenter_pc) => {
+                    self.pc = reenter_pc as usize;
+                    self.icnt += insn as usize;
+                }
+            }
         }
     }
 
-    #[cfg(all(any(target_arch = "x86_64", target_os = "linux")))]
+    #[cfg(all(any(target_arch = "x86_64", target_os = "linux")))]
     /// Translate the bb at the current pc and return a JitFn pointer to it.
     fn translate_next_bb(&mut self) -> JitFn {
         let mut bb = Asm::new();
         let mut pc = self.pc;
 
-        'outer: loop {
+        'outer: loop {
             let insn = self.imem[pc];
 
             pc = pc.wrapping_add(1);
@@ -976,7 +991,7 @@
 
             // Generate memory operand into regs for guest register.
             let reg_op = |r: TinyReg| {
-                MemOp::IndirectDisp(Reg64::rdi, (r.idx() * 2).try_into().expect("only 3 regs"))
+                MemOp::IndirectDisp(Reg64::rdi, (r.idx() * 2).try_into().expect("only 3 regs"))
             };
 
             // Generate memory operand into dmem for guest phys address.
@@ -992,7 +1007,7 @@
                     bb.mov(Reg64::rax, Imm64::from(0));
                     bb.mov(Reg64::rdx, Imm64::from(bb_icnt()));
                     bb.ret();
-                    break 'outer;
+                    break 'outer;
                 }
                 TinyInsn::LoadImm(a, imm) => {
                     bb.mov(reg_op(a), Imm16::from(imm));
@@ -1016,7 +1031,7 @@
                     bb.mov(Reg64::rax, Imm64::from(bb_icnt()));
                     bb.mov(Reg64::rdx, Imm64::from(reenter_pc(disp)));
                     bb.ret();
-                    break 'outer;
+                    break 'outer;
                 }
                 TinyInsn::BranchZero(a, disp) => {
                     bb.cmp(reg_op(a), Imm16::from(0u16));
@@ -1029,7 +1044,7 @@
                     bb.mov(Reg64::rdx, Imm64::from(reenter_pc(pc)));
                     bb.bind(&mut skip_next_pc);
                     bb.ret();
-                    break 'outer;
+                    break 'outer;
                 }
             }
         }
@@ -1053,7 +1068,7 @@
     pub fn bind(self, prog: &mut Vec<TinyInsn>) {
         let plen = prog.len();
         let insn = prog.get_mut(self.pc).expect(&format!(
-            "Trying to apply Fixup, but Fixup is out of range pc={} prog.len={}",
+            "Trying to apply Fixup, but Fixup is out of range pc={} prog.len={}",
             self.pc, plen
         ));
 
@@ -1062,7 +1077,7 @@
                 *disp = plen;
             }
             _ => {
-                unimplemented!("Trying to fixup non-branch instruction '{:?}'", *insn);
+                unimplemented!("Trying to fixup non-branch instruction '{:?}'", *insn);
             }
         }
     }
@@ -1190,24 +1205,24 @@
 
 fn main() {
     let use_jit = match std::env::args().nth(1) {
-        Some(a) if a == "-h" || a == "--help" => {
-            println!("Usage: tiny_vm [mode]");
-            println!("");
-            println!("Options:");
-            println!("    mode    if mode is 'jit' then run in jit mode, else in interpreter mode");
+        Some(a) if a == "-h" || a == "--help" => {
+            println!("Usage: tiny_vm [mode]");
+            println!("");
+            println!("Options:");
+            println!("    mode    if mode is 'jit' then run in jit mode, else in interpreter mode");
             std::process::exit(0);
         }
-        Some(a) if a == "jit" => true,
+        Some(a) if a == "jit" => true,
         _ => false,
     };
 
     let mut vm = TinyVm::new(make_tinyvm_fib(42));
 
     if use_jit {
-        println!("Run in jit mode..");
+        println!("Run in jit mode..");
         vm.jit();
     } else {
-        println!("Run in interpreter mode..");
+        println!("Run in interpreter mode..");
         vm.interp();
     }
     vm.dump();
-- 
cgit v1.2.3