courses:system_design:project_management:design_reuse

Design Reuse

Design Reuse

Notes

Reuse means to fall back on existing problem solutions.

Every design engineer will try to apply previous VHDL code to the current situation. This is fairly simple because all details of the implementation are already known and consequently the code can be easily changed.

  • Continuous growth of complexity (approx. 60% per year)
  • Limited increase of designer productivity (approx. 20% per year)
  • ⇒ Gap between technology and product capabilities
  • Reuse:
    • Readily available solutions for specific problems (micro controllers, bus interfaces, signal processors, etc.)
    • Reduced amount of verification effort
    • Prerequisite for System-on-a-Chip (SoC)

Notes

Reuse of previous designed modules on a bigger scale has become a necessity since the designer productivity can not keep pace with the advances in the field of technology.

Currently, the complexity of integrated circuits increases at a rate of approximately 60% per year whereas the designer productivity increases just by 20%. The only way to fill this gap is to reduce the design effort by reusing existing solutions.

  • Traditional approach: copy, paste and modify
    • Difficult to maintain
    • Risk of bug propagation
  • Reuse concepts
    • System specific constant definition in packages
    • Standard data types at interface
    • Internal use of problem specific data types for runtime error checking
    • Subprograms for common features: easy scalability → unconstrained formal parameters; flexibility → embedding in architectures
    • Self contained modules for complex functions
  • General requirements
    • Technology independency
    • Tool independency (simulation, synthesis)
    • Parameterization with constants and generics
    • Detailed documentation

Notes

Old designs, however, can not simply be collected in a reuse library to provide the desired standard solutions.

As developers that are not familiar with the internals shall be able to use the parts of the library, the documentation must be extremely detailed.

Additionally, the code must be written with reusability in mind because modifications might consume more time than a complete redesign.

This means that the VHDL must not rely on short term settings like technology or tool features.

Possible applications have to be covered via parameterizable behavior, i.e. the code itself needs not to be modified. Thus, simple structures and standard solutions have the biggest reuse potential.

library IEEE;
use IEEE.std_logic_1164.all;
-- synopsys packages
use IEEE.std_logic_arith.all;
use IEEE.std_logic_unsigned.all;
entity ZERO_COUNT is
  port(DATA_IN: in std_logic_vector (7 downto 0);
       CNT, ONES : out
             std_logic_vector (3 downto 0));
end ZERO_COUNT;
architecture RTL of ZERO_COUNT is
begin
   CNT_PROC : process(DATA_IN)
     variable CNT_TEMP : integer range 0 to 8;
   begin
     CNT_TEMP := 0;
     for I in 0 to 7 loop
       If DATA_IN(I) =0then
          CNT_TEMP := CNT_TEMP + 1;
       end if;
   end loop;
   CNT<= conv_std_logic_vector(CNT_TEMP,4);
   ONES<= 8-conv_std_logic_vector(CNT_TEMP,4);
 end process;
end RTL;

Bad Example

  • Use of Synopsys packages
    • not standardized (quasi-standard)
    • might not be available in other tools
  • Hard coded values (vector ranges)
    • not usable in applications with different bus width

Notes

The difference in design philosophy shall be demonstrated at an example module that has to count the number of ’0’ and ’1’ elements in a bit vector.

The first version is a straight forward implementation of the specification. Synopsys packages are used for bit vector arithmetic based on ’std_logic_vector’.

Although these packages are frequently used in industry, they are not standardized. Because the vector widths from the actual task are hard coded, it is not possible to place an identical module in a different environment.

library IEEE;
use IEEE.std_logic_1164.all; use IEEE.numeric_std.all;
package BITCOUNT is
  procedure COUNT(VECTOR: in std_logic_vector;
        VALUE: in std_logic;
        signal RESULT: out std_logic_vector);
end BITCOUNT;
package body BITCOUNT is
  procedure COUNT(VECTOR: in std_logic_vector;
        VALUE: in std_logic;
        signal RESULT: out std_logic_vector) is
     variable COUNT: integer;
     variable MAXVALUE: unsigned(RESULT’length-1 downto 0);
  begin
   COUNT := 0; MAXVALUE := (others =>1);
   for I in VECTOR’range loop
     if VECTOR(I) = VALUE then
       COUNT := COUNT + 1;
     end if;
  end loop;
  if COUNT > MAXVALUE then
     RESULT <= (others =>1);
  else
     RESULT <= std_logic_vector(to_unsigned(
                                COUNT, RESULT’length));
  end if;
 end COUNT;
end BITCOUNT;
  • Standardized packages
  • Counter functionality as subprogram
    • Synchronous / combinational circuit
    • Unconstrained formal parameters
  • Hardcoded ranges replaced by VHDL attributes
  • Overflow handling in case the output vector is too small

Notes

The counting of specific values within a vector is a very basic function that should be implemented as a subprogram.

This subprogram should be placed in a package in order to make it easily accessible.

Subprograms may use unconstrained formal parameters which allows for parameterizability without much of additional effort.

library IEEE;
use IEEE.std_logic_1164.all;
use WORK.BITCOUNT.all;
 
entity ZERO_COUNT is
   generic(D_WIDTH : integer := 8;
           C_WIDTH : integer := 4;
           COUNT_1S : integer range 0 to 1 := 1);
port(DATA_IN : in
           std_logic_vector(D_WIDTH-1 downto 0);
     CNT, ONES : out
           std_logic_vector(C_WIDTH-1 downto 0));
end ZERO_COUNT;
 
architecture RTL of ZERO_COUNT is
begin
  COUNT(DATA_IN, ’0’, CNT);
 
   CNT_ONES: if COUNT_1S=1 generate
     COUNT(DATA_IN, ’1’, ONES);
   end generate CNT_ONES;
end RTL;
  • Parameterized interface via generics
  • Additional generic to control module behavior
  • if … generate statement to avoid unnecessary hardware overhead

Notes

In order to fulfil the requirements, an entity/architecture pair must be created that shows the specified behavior.

The new entity has generic parameters that may be used to define port width.

Their default values allow a drop in replacement of the old design without the necessity of a generic map.

While the first two parameters are used to set the data width, the third parameter COUNT_1S affects the behavior of the module.

It allows to turn of the counting of ’1’ elements.

The ’if … generate’ construct is used to reduce the amount of hardware that gets synthesized.


Chapters of System Design > Project Management