function results = piltest(Config, varargin)
%PILTEST   Test suite for processor-in-the-loop (PIL) target connectivity configurations. 
%
%   PILTEST(Config) runs a test suite to verify a custom PIL target connectivity configuration. 
%   For each test in the suite, the function runs normal and PIL mode executions and compares the results. 
%   The function produces an error if it detects differences between normal and PIL mode results.
% 
%   For Simulink simulation, Config is one of these:
%       - A model name.
%       - A model configuration set (Simulink.ConfigSet).
%       - A model configuration set reference (Simulink.ConfigSetRef).
% 
%   For MATLAB execution, Config is a coder.EmbeddedCodeConfig object.
% 
%   The function obtains the following PIL settings from Config:
%       - SystemTargetFile (Simulink only)
%       - TargetHWDeviceType
%       - Relevant Toolchain or TMF settings
% 
%   PILTEST(Config, 'ConfigParams', {'...'}) obtains additional PIL settings from Config.
%   Use the optional cell array of character vectors to specify the additional settings.
% 
%   PILTEST(Config, 'TestPoint', testName) runs specific tests from the test suite. Use one of these values for testName:
%
%       For Simulink coder workflows:
%       - 'verifyPILBlock' - For normal mode results, run a simulation of a Simulink model with a subsystem. 
%       For PIL results, replace subsystem with a PIL block.
%       - 'verifyModelBlock' - For normal mode results, run simulations of a Simulink model with a Model block in normal mode. 
%       For PIL mode results, run simulations of a Simulink model with a Model block in PIL mode by looping over both 
%       standalone and model reference code interfaces. In addition to this, the test also loops over both 'C' and 'C++'
%       Target Languages. The C++ target language iteration makes use of the 'C++ Class' Code interface packaging.
%       - 'verifyTopModel' - Run simulations of a top-model in normal and PIL modes.
%       - 'verifyExecutionOnTarget' - Run simulations of a Simulink model with a Model block in normal and PIL modes, 
%       using standalone and model reference code interfaces. For PIL mode, the function introduces a deliberate mismatch. 
%       The function compares normal and PIL mode results. If it does not detect the deliberate mismatch, it produces an error.
%       - 'verifyTopModelSILPILSwitching' - Same as verifyTopModel but instead of running just PIL simulation mode, 
%       runs SIL and PIL simulations modes to ensure that SIL/PIL switching is supported.
%       - 'verifyModelBlockSILPILSwitching' - Same as verifyModelBlock for C Target Language but instead of running just 
%       PIL simulation mode, runs SIL and PIL simulations modes to ensure that SIL/PIL switching is supported.
%       - 'all' (default) - Run all tests from the test suite.
%
%       For MATLAB coder workflows:
%       - 'verifyPILConfig' - Executes a MATLAB function for a given set of input values and compares the results to
%         a PIL mode execution of the same function and input. values. This test also loops of both C and C++ target languages. 
% 
%   For example: 
% 
%   Simulink simulation:
%       piltest(myPILConfigModel)
%       piltest(myPILConfiguredmodel, 'ConfigParams', {'ProdLongLongMode'})
% 
%   MATLAB execution: 
%       cfg = coder.config('lib');
%       hwImpl = coder.HardwareImplementation;
%       hwImpl.TargetHWDeviceType = 'Atmel->AVR';
%       cfg.HardwareImplementation = hwImpl;
%       cfg.Toolchain = 'AVR tools for Arduino'; 
% 
%   piltest(cfg)


% Copyright 2016-2017 The MathWorks, Inc.
        
    if nargin > 0
        Config = convertStringsToChars(Config);
    end
    
    if nargin > 1
        [varargin{:}] = convertStringsToChars(varargin{:});
    end
    
    if isa(Config,'coder.EmbeddedCodeConfig')
        % PIL API unit test for MATLAB Coder workflow. Supported 'Config'
        % value:
        % - coder.EmbeddedCodeConfig object
        test = coder.internal.piltest.MLPILTest(Config, varargin{:});
        results = testRunner(test);
                        
    elseif (isa(Config,'Simulink.ConfigSet') || ...
            isa(Config,'Simulink.ConfigSetRef') || ...
            exist(Config,'file')==4)
        % PIL API unit test for Simulink Coder workflow. Supported 'Config'
        % values:
        % - Model Configuration Set
        % - Model Configuration Set Reference
        % - Model Name
        test = coder.internal.piltest.SLPILTest(Config, varargin{:});
        results = testRunner(test);
    else
        % Error for unsupported 'Config' input
        DAStudio.error('Connectivity:piltest:PILTestUnsupportedInput');        
    end
    
    disp(results);
end


