Code covered by the BSD License  

Highlights from
ECRobotInstaller – Simplified installation of tools for Embedded Coder Robot

image thumbnail

ECRobotInstaller – Simplified installation of tools for Embedded Coder Robot

by

 

02 Sep 2009 (Updated )

Simplifies the installation of ECRobot, a Simulink platform for LEGO Mindstorms NXT code generation

download_ecrobot_tools(downloadOption, programList)
function download_ecrobot_tools(downloadOption, programList)
% DOWNLOAD_ECROBOT_TOOLS
%
%   DOWNLOAD_ECROBOT_TOOLS automatically downloads all the programs
%   necessary for running ECRobot (the embedded coder robot for LEGO
%   Mindstorms NXT), and saves them in an archive directory. It does 
%   *not* install any of the programs. 
% 
%   DOWNLOAD_ECROBOT_TOOLS('force') forces all the programs to be downloaded
%   anew. By default, DOWNLOAD_ECROBOT_TOOLS skips downloading a file
%   if it already exists in the archive directory.
%
%   DOWNLOAD_ECROBOT_TOOLS('force', programlist) forces only the specified programs 
%   to be downloaded. programlist should be a cell array of strings. Valid values 
%   for the strings are: 'cygwin', 'gnuarm', 'legousb', 'firmware', 'nxttool', 
%   'ecrobot', 'nxtosek'
%
%   Notes on usage:
%
%   1) The archive directory is specified in ECROBOT_INSTALL_CONFIG.M. To see 
%      the location of this directory, type 'ecrobot_install_config' at the 
%      MATLAB command prompt
%
%   2) Configuration information for the download (e.g., URLs, filenames) is 
%      also specified in ECROBOT_INSTALL_CONFIG.M 
%
%   3) It is safe to run DOWNLOAD_ECROBOT_TOOLS multiple times, since by 
%      default it checks to see if a file has already been downloaded.

%   Copyright 2009 The MathWorks, Inc.

% ECRobotInstaller version 1.3: (April-02-2010)
%   * Updated Cygwin download to use the new --packages and --categories 
%     options (for cygwin setup.exe version 2.693)
% ECRobotInstaller version 1.35: 
%   * Added double quotes to the Cygwin setup.exe command to allow download
%     directory to have spaces
%   * Augmented output of download_cygwin() in case of error
% ECRobotInstaller version 1.36: 
%   * Added the config.Cygwin_quiet_download option to allow users to
%     specify a proxy server during Cygwin download.
% ECRobotInstaller version 1.37: (Jan-01-2011)
%   * Added "libintl3" to the list of cygwin packages to be installed
%    (this is required by GNU ARM Compiler ver 4.0.2, which in turn is 
%     required by ECRobot). 
%   * Added the input parameters (downloadOption, programList) for 
%     forcing downloads of all or specific programs

    if ~(exist('ecrobot_install_config', 'file') == 2)
        fprintf('Unable to find ecrobot_install_config.m\n');
        return;
    end
    
    if nargin == 0      
        programFlags = parseOverrideList({});
    else % nargin > 0
       if ~(ischar(downloadOption) && strcmpi(downloadOption,'force'))
           fprintf('First input parameter is required to be ''force''\n');
           return;
       end               
       if nargin == 1
           programFlags = parseOverrideList({'cygwin', 'gnuarm', 'legousb', 'firmware', 'nxttool', 'ecrobot', 'nxtosek'});           
       else % nargin > 1
           programFlags = parseOverrideList(programList);
       end       
    end
        
    % if there is an error, no need to do any cleanup (such as closing a 
    % log file). Let the caller handle it.
    
    config = ecrobot_install_config;
    verifyConfig(config, 'fields', @visibleLog);
    verifyArchiveDir(config.ArchiveDir, @visibleLog);

    config.ForceDownload = programFlags;
        
    fprintf('All the downloads will be stored in:\n  %s\n',config.ArchiveDir);
    resp = lower(input('Please confirm [y/n]: ', 's'));
    if ~(length(resp)>=1 && (strcmp(resp,'y') || strcmp(resp, 'yes')))
        visibleLog('Downloading aborted\n');
        return;
    end
    
    download_nxt_firmware(config);
    download_nxt_tools(config);
    download_nxtosek(config);
    download_ecrobot(config);
    download_cygwin(config);
    download_gnutools(config);
    download_lego_usb_driver(config);
   
end

%% Logging functions
function visibleLog(varargin)
    fprintf(1, varargin{:});
end

%% 
function download_cygwin(config)
package_dir = fullfile(config.ArchiveDir, config.Cygwin_PackageDirectory);
setup_exe = fullfile(package_dir, 'setup.exe');
cygwin_rootdir = fullfile(tempdir, 'cygwin');

if ~isdir(package_dir)
    mkdir(package_dir);
else % directory already exists
    visibleLog('\n Cygwin: Package directory (%s) already exists\n', package_dir);
    
    if config.ForceDownload.cygwin        
        visibleLog('\n Cygwin: Deleting package directory to force a new download ...\n');
        rmdir(package_dir, 's');
    end
end

download_file('Cygwin', 572, 'http://www.cygwin.com/setup.exe', setup_exe, config.ForceDownload.cygwin);

% Download base package
% 1) We need to specify --root as well, otherwise, it will just use
%    whatever is listed as the root mountpoint in the windows registry
% 2) Each time we run the following command, it will re-fetch setup.ini
%    & thereby wipe out any changes we made.

visibleLog(' Cygwin: Downloading base package ... (~ 18 MB) \n');
fprintf('     If the Cygwin download seems "stuck", there may be an open Cygwin dialog box in the background\n');
cmd = ['"' setup_exe '"' ...
       ' --download ' ...
       ' --root ' '"'  cygwin_rootdir '"' ...
       ' --site ' '"' config.Cygwin_URL '"' ...
       ' --local-package-dir ' '"' package_dir '"' ...
       ' --categories Base ' ...
       ' --packages make,libintl3 ' ...
       ' --no-shortcuts ' ...
      ];

if config.Cygwin_quiet_download
    cmd = [cmd  ' --quiet-mode '];
end

[status,logData] = system(cmd);
addedPackages = regexpi(logData, '\nAdded manual package');
foundMakePackage = ~isempty(regexpi(logData, '\nAdded manual package make'));

if status || (numel(addedPackages) == 0)
    visibleLog('  Unable to download Cygwin base package\n');
    visibleLog('  Number of added packagpes = %d\n', numel(addedPackages));
    visibleLog('####### Output of Cygwin setup.exe\n');
    disp(logData)
    visibleLog('####### End output of Cygwin setup.exe\n');
elseif ~foundMakePackage
    visibleLog('  Unexpected error: Cygwin make package was not downloaded\n');
    visibleLog('####### Output of Cygwin setup.exe\n');
    disp(logData)
    visibleLog('####### End output of Cygwin setup.exe\n');    
else
    visibleLog(' Cygwin: successfully downloaded (%d packages added)\n', numel(addedPackages));
end

% cygwin_url_string = lower(urlencode(config.Cygwin_URL));
% % equivalent to the following:
% % cygwin_url_string = strrep(strrep(config.Cygwin_URL, ':', '%3a'), '/', '%2f');
% sitedir = fullfile(package_dir, cygwin_url_string);
end

%% -----------------

function download_ecrobot(config)
    download_file('ECRobot', 6602, config.ECRobot_URL, fullfile(config.ArchiveDir , config.ECRobot_ZIPFile), config.ForceDownload.ecrobot);
end

function download_nxtosek(config)
    download_file('nxtOSEK', 7660, config.NXTOSEK_URL, fullfile(config.ArchiveDir , config.NXTOSEK_ZIPFile), config.ForceDownload.nxtosek);
end

function download_gnutools(config)
    download_file('GNU ARM compiler', 25453, config.GnuTools_URL, ...
        fullfile(config.ArchiveDir , config.GnuTools_EXEFile), config.ForceDownload.gnuarm);
end

function download_lego_usb_driver(config)
    download_file('LEGO USB Driver', 7296, config.LEGOUSBDriver_URL, fullfile(config.ArchiveDir , config.LEGOUSBDriver_ZIPFile), config.ForceDownload.legousb);
end

function download_nxt_firmware(config)
    download_file('NXT Firmware', 472, config.NXTEnhancedFirmware_URL, fullfile(config.ArchiveDir , config.NXTEnhancedFirmware_ZIPFile), config.ForceDownload.firmware);
end

function download_nxt_tools(config)
    download_file('NeXTTool', 83, config.NXTTOOL_URL, fullfile(config.ArchiveDir , config.NXTTOOL_ZIPFile), config.ForceDownload.nxttool);
end


function download_file(tag, expectedSizeKB, url, filename, forceDownload)

    fprintf('\n');
    if exist(filename, 'file')==2
        visibleLog(' %s: %s already exists\n', tag, filename);
        if forceDownload
            visibleLog(' %s: Forcing a new download ...\n', tag);
        else
            return;
        end
    end
    
    try
        expectedSizeMB = expectedSizeKB/1024;
        visibleLog(' %s: Downloading ... (~ %.1f MB) \n', tag, expectedSizeMB);
        urlwrite(url, filename);
        visibleLog(' %s: successfully downloaded %s\n', tag ,filename);
    catch %#ok<CTCH>
        le = lasterror;         %#ok<LERR>
        visibleLog(' %s: unable to download %s\n', tag, filename);
        visibleLog(' %s\n', le.message);
    end    
end

Contact us