forsyde / forsyde-deep

Other
1 stars 2 forks source link

Simulation with Modelsim #24

Open HWoidt opened 8 years ago

HWoidt commented 8 years ago

Issue by ingo-sander Thursday Jan 14, 2016 at 14:42 GMT Originally opened as https://gits-15.sys.kth.se/ingo/forsyde-deep/issues/24


There seems to be a bug in the simulation with Modelsim.

When I simulate the counter example then Modelsim produces an error. I have not analyzed it further, but it might have to do with reset or the clock input. So, please ensure that a Modelsim simulation generates the trace for the clock signal and resets all flip-flops at the beginning of the simulation.

Here comes the code for the counter:

{-# LANGUAGE TemplateHaskell #-}

module CounterHW (Direction, counterSys) where

import ForSyDe.Deep
import Data.Int

type Direction = Bit

nextStateFun :: ProcFun (Int8 -> Direction -> Int8)
nextStateFun = $(newProcFun
   [d| nextState state dir
          = if dir == H then
              if state < 9 then state + 1
              else 0
            else
              if state == 0 then 9
              else state - 1
     |])

counterProc :: Signal Direction -> Signal Int8 
counterProc = scanldSY "counterProc" nextStateFun 0

counterSys :: SysDef (Signal Direction -> Signal Int8)
counterSys = newSysDef counterProc "Counter" ["direction"] ["number"] 

And here is the simulation output:

ingo@s2135:counter7Seg> ghci CounterHW.hs 
GHCi, version 7.10.3: http://www.haskell.org/ghc/  :? for help
[1 of 1] Compiling CounterHW        ( CounterHW.hs, interpreted )

CounterHW.hs:26:70: Warning: Tab character
Ok, modules loaded: CounterHW.
*CounterHW> simulate counterSys [L,H,H,H,H,L,L,L,L]
[0,9,0,1,2,3,2,1,0]
*CounterHW> let vhdlSim = writeAndModelsimVHDL Nothing counterSys
*CounterHW> vhdlSim [L,H,H,H,H,L,L,L,L]
Running: vmap forsyde /home/ingo/.cabal/share/x86_64-linux-ghc-7.10.3/ForSyDe-Deep-0.2.0/lib/modelsim
Modifying modelsim.ini
Running: vlib Counter_lib/modelsim
Running: vcom -93 -quiet -nologo -work Counter_lib/modelsim Counter_lib/Counter_lib.vhd
Running: vmap Counter_lib Counter_lib/modelsim
Modifying modelsim.ini
Running: vlib work/modelsim
Running: vcom -93 -quiet -nologo -work work/modelsim -just e work/Counter.vhd
Running: vcom -93 -quiet -nologo -work work/modelsim -just a work/Counter.vhd
Running: vmap work work/modelsim
Modifying modelsim.ini
Running: vcom -93 -quiet -nologo -work work test/Counter_tb.vhd
Running: vsim -c -std_output /tmp/tb_out1804289383846930886.txt -quiet -do run 90 ns; exit work.Counter_tb
Reading /opt/altera/13.0/modelsim_ae/tcl/vsim/pref.tcl 

#10.1d

# vsim -do {run 90 ns; exit} -c -quiet -std_output /tmp/tb_out1804289383846930886.txt work.Counter_tb 
# //  ModelSim ALTERA 10.1d Nov  2 2012 Linux 3.13.0-74-generic
# //
# //  Copyright 1991-2012 Mentor Graphics Corporation
# //  All Rights Reserved.
# //
# //  THIS WORK CONTAINS TRADE SECRET AND PROPRIETARY INFORMATION
# //  WHICH IS THE PROPERTY OF MENTOR GRAPHICS CORPORATION OR ITS
# //  LICENSORS AND IS SUBJECT TO LICENSE TERMS.
# //
# run 90 ns 
# ** Fatal: (vsim-3421) Value -129 for return value is out of range -128 to 127.
#    Time: 0 ps  Iteration: 0  Process: /counter_tb/totest/\counterProc_NxtSt\/line__49 File: work/Counter.vhd
# Fatal error in Subprogram \nextState_0\ at work/Counter.vhd line 44
# 
# HDL call sequence:
# Stopped at work/Counter.vhd 44 Subprogram \nextState_0\
# called from  work/Counter.vhd 50 Block \counterProc_NxtSt\
# 
#  exit 
[]
HWoidt commented 8 years ago

Comment by HWoidt Thursday Jan 21, 2016 at 15:32 GMT


This issue is a bit more involved than initially thought:

There is a simulation mismatch between Haskell and VHDL concerning the Integer types:

For this specific example, the bug originates in the fact, that all processes are executed once initially. That way the nextState function is called once with the initial value of the delayOut signal, and not with the one assigned by the reset statement (if reset then delay = 0...).

This nextState function is not formally correct VHDL as it produces an invalid output for the valid (although not normally attainable) input of -128. This specific input value is the default initial value for the Integer type.

There are some options for solving this:

  1. Fix the simulation mismatch: Implement the Int8 type using numeric_std.unsigned instead of Integer in VHDL. This has the correct semantics regarding the Haskell-Int8 type and would make this simulate correctly in this context.
  2. Fix the initial values of all signals connected to the delay element. This would need to have some way of tracing the netlist and catch all the important signals.
  3. fix the example to behave correctly for out-of range values less then 0 (which doesn't solve the underlying issue):
nextStateFun = $(newProcFun
   [d| nextState state dir
          = if dir == H then
              if state < 9 then state + 1
              else 0
            else
              if state <= 0 then 9
              else state - 1
     |])

I currently have no estimate of the amount of work needed for either 1. or 2.