%% Getting Started with TLM Generator
%
% This example shows how to configure a Simulink(R) model to generate a 
% SystemC(TM)/TLM component using the
% tlmgenerator target for either Simulink Coder or Embedded Coder(TM).
%
% For this example, we use a Simulink model of a FIR filter as the
% basis of the SystemC/TLM generation.
%
% Requirements to run this example:
%
% * SystemC 2.3.1 (includes the TLM library)
% * For code verification, make and a compatible GNU-compiler, gcc, in your path on Linux(R), or Visual Studio(R) compiler in your path on Windows(R)
% 
%
% Note: The example includes a code generation build procedure.
% Simulink does not permit you to build programs in the MATLAB installation
% area. If necessary, change to a working directory that is not in the
% MATLAB installation area prior to starting any build.
 
% Copyright 2005-2014 The MathWorks, Inc.
 
%% 1. Open Preconfigured Model
% To open the *FIR Filter model*, click the *Open Model* button. 
%
%%
open_system('tlmgdemo_intro');
 
%% 2. Set Simulink Coder Target to TLM Generator
%
% *a.* Open the *Configuration Parameters* dialog box by selecting Simulation > Model Configuration Parameters in the model window.
%
% *b.* In the *Configuration Parameters* dialog box, select the *Code Generation* view in the left-hand pane. 
%
% *c.* Under *System target file*, click Browse to select the TLM generator target. You can choose
% tlmgenerator_grt.tlc to use Simulink Coder or tlmgenerator_ert.tlc
% to use Embedded Coder for HDL Code generation. For this example, select
% *tlmgenerator_grt.tlc*.
%
% <<../Introduction_target.png>>
 
 
%% 3. Open TLM Generator View
% In the *Configuration Parameters* dialog box, select the *TLM
% Generator* view in the left-hand pane.
%
% <<../Introduction_gen.png>>
%
% The *TLM Generator* view has five tabs:
% 
% * TLM Mapping
% * TLM Processing
% * TLM Timing
% * TLM Testbench
% * TLM Compilation
%
% You will need to set different generator options in each pane.
%
%% 4. Select TLM Mapping Options
% In the *TLM Mapping* tab, *Socket Mapping* allows you to select the
% number of sockets for input data, output data, and control. 
% Select the option, *Three separate TLM sockets for input data, output data, and control*.
%
%
% <<../Introduction_skt_map.png>>
%
% The TLM Socket options allow you to define three different memory maps for your generated TLM component.
% 
% <<../Introduction_gen_memap.png>>
% 
% For this example, select the following for the input and output data sockets:
% 
% * *Auto-generated memory map* for the input and output data sockets
% * *Individual input and output address offsets* for each data socket. This option generates a TLM component
% with one read register per model output and one write register per model input with individual 
% addresses. Each Simulink model input is bound to its
% corresponding write register and each output is bound to its corresponding read register.
% 
% The other memory map options you may consider are:
%
% * *No memory map*: This option generates a TLM component with only one read and one write register without
% any address. The Simulink model inputs are bound to the write register and the outputs are
% bound to the read register.
% * [Auto-generated memory map with] *Single input and output address
% offsets*: This option generates a TLM component with only one read and one
% write register with one address each. The Simulink model inputs are
% bound to the write register and the outputs are bound to the read
% register.
% 
% When you generate the component with a memory map, you can add a command and status register, a test and
% set register, and tunable parameter registers.
% 
% For this example, select the following for the Control TLM Socket:
%
% * *Include a command and status register in the memory map*. The command and status register
% allows you to write command and read status during SystemC simulation; 
% for example, manual buffering or buffer status.
% * *Include tunable parameter registers in the memory map*.
% Tunable parameter registers allow you to read or write the tunable parameter values.
% 
% Although not used in this example, a test and set register can be used as a mutex when multiple initiators access the component during 
% SystemC simulation. 
%% 5. Select TLM Processing Options
% In the *TLM Generation* pane, select the *TLM Processing* tab. The *Algorithm
% Processing* and the *Interface processing* options allow you to define different
% buffering and processing behaviors for your generated TLM component. 
%
% <<../Introduction_gen_proc.png>>
%
% The algorithm execution options are:
%
% * *SystemC Thread*: The step function algorithm is executed in its own independent SystemC thread.
% * *Callback Function*: The step function algorithm is executed in a callback function called from the interface.
% * *Periodic SystemC Thread*: The step function algorithm is executed in its own time periodic independent SystemC thread.
% 
% The step function timing is determined by the value in the *Algorithm step function timing (ns)* field.
% The algorithm timing is counted with a wait() in the thread. 
% 
% For this example, select *SystemC Thread* and enter 100 in the field for *Algorithm step function timing*. 
% 
% Interface processing options:
%
% * *Create an interrupt request port on the generated TLM component*: This option creates an interrupt 
% port (type signal, bool>) that is triggered every time a set of input has been processed.
%
%
% For this example, select or enter the following choices:
%
% * Select *Create an interrupt request port on the generated TLM component*.

 
%% 6. Select the TLM Timing Options
% Select the *TLM Timing* tab. The  
% *Interface Timing* section allows you to define the timing of the component
% input/output interface and processing thread.
%
% <<../Introduction_gen_time.png>>
%
% For this example, the input and output delays are counted with wait() in
% the interface. Set a time value of 5ns for each of
% the transactions of *Input Data Interface Timing*, *Output Data Interfacing Timing*, and *Control Interface Timing*.
%
%% 7. Select TLM Testbench View
% Select the *TLM Testbench* tab. The TLM Generator
% target can generate a stand-alone SystemC/TLM test bench alongside
% the TLM component to verify the generated algorithm in the
% context of a TLM initiator/target pair. The TLM Testbench view provides
% run-time options for when the test bench code is generated and
% executed. 
%
% <<../Introduction_tb.png>>
%
% With the TLM Testbench options, you can:
%
% * Choose to see verbose messages echoed to the command window during the
% SystemC/TLM execution including TLM transaction and synchronization messages.
% * Indicate that the test bench should execute with or without timing annotations.
% * Indicate whether the initiator controls moving input and output
% datasets between the registers and the buffers or whether the component
% performs the moves automatically.
%
% For this example, select *Generate testbench*, *With timing* for
% *Run-time timing mode*,
% and *Automatic* for both *Input buffer triggering mode* and *Output buffer triggering mode*.
%
% After code generation has successfully occurred for a component and
% test bench, the *Verify TLM Component* button becomes enabled.
% *Verify TLM Component* performs the following:
%
% * Builds the generated code using make and generated makefiles.
% * Runs Simulink to capture input stimulus and expected results.
% * Converts the Simulink data to TLM vectors.
% * Runs the stand-alone SystemC/TLM testbench executable.
% * Converts the TLM results back to Simulink data.
% * Performs a data comparison.
% * Generates a Figure window for any signals that had data mis-compares.
%
% The compilation of the generated files assumes the presence of make and a
% compatible GNU-compiler, gcc, in your path on Linux(R), or Visual
% Studio(R) compiler in your path on Windows(R).
 
%% 8. Select TLM Compilation View
% Select the *TLM Compilation* tab. This pane
% provides options to control the generation of makefiles used to
% compile the generated code.
%
% <<../Introduction_comp.png>>
%
% Compiler Options:
%
% The SystemC and TLM include library path options
% allow you to specify where the makefiles can find the SystemC and TLM
% installations. The default values allow you to use environment variables
% so that updates to your SystemC or TLM installations do not require
% updating your Simulink models. You can set up the environment prior to
% invoking MATLAB or use the MATLAB setenv command.
%
% For this example, these are the environment variable values that were tested with 
% standard OSCI installations located in /tools:
%
% * SYSTEMC_INC_PATH=/tools/systemc-2.3.0/include
% * SYSTEMC_LIB_PATH=/tools/systemc-2.3.0/lib-linux64
% * SYSTEMC_LIB_NAME=libsystemc.a (Linux) or systemc.lib (Windows)
% * TLM_INC_PATH=/tools/systemc-2.3.0/include
%
% Toolchain:
%
% On Windows this option allows you to select a compiler toolchain when multiple
% version of Microsoft Visual Studio are installed on the same machine.
% On Linux this option is fixed on gcc.
%
% Component Naming:
%
% This option allows you to add your own tag to the name of
% the generated component. The generated component name is built according
% to the following cases:
%
% * If a user tag is specified: modelname_usertag_tlm
% * If the user tag field is empty: modelname_tlm
%
% For this example, enter *intro* for user tag.
%
%% 9. Select Report 
% Select *Report* in the left-hand pane.
% For this example, select *Create code generation report* and *Open report automatically*.
% These options generate a html report
% during component generation. The Code generation report details the contents of each generated file.
%
% <<../Introduction_report.png>>
%
% 
%% 10. Save TLM Generator Options
% Click *OK* to apply these
% settings and exit the *Configuration Parameters* dialog box.
 
 
%% 11. Build Model
% In the model window, right-click on the DualFilter block and select
% *C/C++ Code > Generate Code for this Subsystem* in the context menu to start
% TLM component generation.
%
% <<../Introduction_build.png>>
%
% Alternatively, you can execute the following
% command in the MATLAB command window: 
%
% >> rtwbuild('tlmgdemo_intro/DualFilter');
%
% During execution, you will be prompted to select the tunable parameters. 
% The dropdown list of each coefficient allows you to select the storage class
% of the variable. 
% The Storage Class options are:
%
% * *Inlined* - The inlined parameters are not tunable.
% * *SimulinkGlobal* - The SimulinkGlobal variables are tunable.
% 
% *ExportedGlobal*, *ImportedExtern* and *ImportedExternPointer* are not supported
% by the TLM Generation model. 
% 
% 
% <<../Introduction_build_tunparams.png>>
%
%
% The option *Simulink Global* has been selected for this example. Click
% *Build*.
% The TLM generation is completed when you see the following message appear in the
% MATLAB command window:
 
%%
rtwbuild('tlmgdemo_intro/DualFilter');
%% 12. Open Generated Files
% Open the generated files in the MATLAB web browser by 
% clicking on the links in the generated report or in the 
% MATLAB Editor (the generated files and report are located in your current working directory):
%
% * <matlab:open(fullfile('DualFilter_VP','DualFilter_intro_tlm_doc','html','DualFilter_codegen_rpt.html')) DualFilter_VP/DualFilter_intro_tlm_doc/html/DualFilter_codegen_rpt.html>
% * <matlab:open(fullfile('DualFilter_VP','DualFilter_intro_tlm','DualFilter_intro_tlm.xml')) DualFilter_VP/DualFilter_intro_tlm/DualFilter_intro_tlm.xml>
% * <matlab:open(fullfile('DualFilter_VP','DualFilter_intro_tlm','include','DualFilter_intro_tlm_def.h')) DualFilter_VP/DualFilter_intro_tlm/include/DualFilter_intro_tlm_def.h>
% * <matlab:open(fullfile('DualFilter_VP','DualFilter_intro_tlm','include','DualFilter_intro_tlm.h')) DualFilter_VP/DualFilter_intro_tlm/include/DualFilter_intro_tlm.h>
% * <matlab:open(fullfile('DualFilter_VP','DualFilter_intro_tlm','src','DualFilter_intro_tlm.cpp')) DualFilter_VP/DualFilter_intro_tlm/src/DualFilter_intro_tlm.cpp>
% * <matlab:open(fullfile('DualFilter_VP','DualFilter_intro_tlm_tb','include','DualFilter_intro_tlm_tb.h')) DualFilter_VP/DualFilter_intro_tlm_tb/src/DualFilter_intro_tlm_tb.h>
% * <matlab:open(fullfile('DualFilter_VP','DualFilter_intro_tlm_tb','src','DualFilter_intro_tlm_tb.cpp')) DualFilter_VP/DualFilter_intro_tlm_tb/src/DualFilter_intro_tlm_tb.cpp>
% * <matlab:open(fullfile('DualFilter_VP','DualFilter_intro_tlm_tb','src','DualFilter_intro_tlm_tb_main.cpp')) DualFilter_VP/DualFilter_intro_tlm_tb/src/DualFilter_intro_tlm_tb_main.cpp>
 
%% 13. Verify Generated Code
%
% *a.* Open the *Model Configuration Parameters* dialog box by selecting Simulation > Configuration Parameters in the model window.
%
% *b.* In the *Configuration Parameters* dialog box, select the *TLM Generator* view, and then select the *TLM Testbench* tab.
%
% *c.* In the *TLM Testbench* pane, click *Verify TLM Component*, to 
% <matlab:verifyTlmgDemoModel('intro') run the generated testbench>.
%
% <<../Introduction_verif.png>>
%
% Alternatively,you can execute the following command in the MATLAB command window:
% 
%    verifyTlmgDemoModel('intro')
%
% This verify step performs the following actions:
%
% * Builds the generated code.
% * Runs Simulink to capture input stimulus and expected results.
% * Converts the Simulink data to TLM vectors.
% * Runs the stand-alone SystemC/TLM test bench executable.
% * Converts the TLM results back to Simulink data.
% * Performs a data comparison.
% * Generates a Figure window for any signals that had data mis-compares.
 
%% 14. Review Execution Log
% The option to generate test bench allows you to see how
% the test bench initiator threads interact and synchronize with the target.
% Look for the comparison result at the end of the log and verify that
% the data comparison is successful.
%%
%   ### Comparing expected vs. actual results.
%   Data successfully compared for signal tlmg_out1.
%   Data successfully compared for signal tlmg_out2.
%   ### Component verification completed

%%
% This concludes the Getting Started with TLM Generator example.
