1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328
|
function [versionString, versionStructure] = PsychtoolboxVersion
%
% [versionString, versionStructure] = PsychtoolboxVersion
%
% Return a string identifying this release of the Psychtoolbox.
% The first three numbers identify the base version of Psychtoolbox:
%
% - Leftmost (major version): Increments indicate a disruptive change in
% the feature set, application programming interfaces or core design of the
% software, by abrupt introduction of drastic design changes. This should
% never happen, as this would mean a completely new product, entirely
% incompatible with the old software.
%
% - Middle (minor version): Increments indicate very significant
% enhancements or changes in functionality. This would for example happen
% if there would be backwards incompatible changes to the programming
% interface or functionality which may require code adjustments in user
% code or even choosing different hardware or operating systems to run it.
% This will usually only happen every couple of years at most.
%
% - Rightmost (patch level): A counter to distinguish multiple releases
% having the same leftmost and middle version numbers. It increments if we
% cancel support for platforms (Matlab/Octave versions, operating system
% versions, processor architectures etc.). This happens occasionally.
%
% Numeric values of the three integer fields contained in versionString are
% available in fields of the second return argument, "versionStructure".
%
% If Psychtoolbox was installed using Neurodebian or GIT, this source
% is available in the field 'Flavor'.
%
% Using SVN, the field 'Flavor' defines the subtype of Psychtoolbox being used:
%
% * beta: The term 'current' is a synonym for 'beta'. Beta releases are the
% only releases we provide at this point. 'Beta' is a historical name, not
% anything is really much of beta quality about them, they are considered
% the most stable and trustworthy releases.
%
% * trunk: Development prototypes, for testing and debugging by developers
% and really adventureous users, not for production use!
%
% * Psychtoolbox-x.y.z: Old, no longer supported Psychtoolbox versions.
%
% * Debian package: A Psychtoolbox provided by GNU/Debian, Ubuntu or NeuroDebian.
%
% The revision number and the provided URL allows you to visit the developer
% website in the Internet and get direct access to all development logs
% regarding your working copy of Psychtoolbox.
%
% Be aware that execution of the PsychtoolboxVersion command can take a lot
% of time (in the order of multiple seconds to 1 minute).
%
% Most Psychtoolbox mex files now provide a built-in 'Version' command
% which returns version for themselves. The version string for the
% built-in version numbers contains a fourth numeric field named "build".
% The build number is a unique serial number. Mex files distinguished only
% by build numbers were compiled from identical C source files.
%
% _________________________________________________________________________
%
% see also: Screen('Version')
% 2/9/01 awi added fullfile command for platform-independent pathname
% 6/29/02 dgp Use new PsychtoolboxRoot function to cope with user-changed folder names.
% 7/12/04 awi ****** OS X-specific fork from the OS 9 version *******
% Noted mex file versioning.
% 7/26/04 awi Partitioned help and added OS X section. Enhanced
% OS9+Windows section.
% 10/4/05 awi Note here that dgp changed "IsWindows" to "IsWin" at unknown date prior
% between 7/26/04 and 10/4/05.
%
% 5/5/06 mk Tries to query info from Subversion and displays info about last date
% of change, SVN revision and flavor. This code is pretty experimental and
% probably also somewhat fragile. And its sloooow.
% 9/17/06 mk Improvements to parser: We try harder to get the flavor info.
% 10/31/11 mk Update for our new hoster GoogleCode.
% 04/30/12 mk Kill MacOS-9 support.
% 05/27/12 mk Switch over to GitHub hosting.
% 08/06/14 mk Integrate (Neuro)Debian versioning support. Cleanups.
% 10/28/20 mk Add SVN support via Matlabs SVNKit. Clarify versioning scheme.
% 11/04/20 ia Add support for git or manual install methods
global Psychtoolbox
if ~isfield(Psychtoolbox,'version')
Psychtoolbox.version.major=0;
Psychtoolbox.version.minor=0;
Psychtoolbox.version.point=0;
Psychtoolbox.version.string='';
Psychtoolbox.version.flavor='';
Psychtoolbox.version.revision=0;
Psychtoolbox.version.revstring='';
Psychtoolbox.version.websvn = 'https://github.com/Psychtoolbox-3/Psychtoolbox-3';
file=fullfile(PsychtoolboxRoot,'Contents.m');
fileinfo = dir(file); % get the filesystem date of this file
f=fopen(file,'r');
fgetl(f);
s=fgetl(f);
fclose(f);
[cvv,count,errmsg,n]=sscanf(s,'%% Version %d.%d.%d',3);
ss=s(n:end);
contentsdate=ss(min(find(ss-' ')):end); %#ok<MXFND>
Psychtoolbox.version.major=cvv(1);
Psychtoolbox.version.minor=cvv(2);
Psychtoolbox.version.point=cvv(3);
gitfolder = PsychtoolboxRoot();
i=find(filesep==gitfolder);
gitfolder = [gitfolder(1:i(end-1)) '.git'];
if exist(gitfolder ,'dir')
isGIT = true;
else
isGIT = false;
end
if exist([PsychtoolboxRoot '.svn'],'dir')
isSVN = true;
else
isSVN = false;
end
if any(strcmp(PsychtoolboxRoot, {'/usr/share/octave/site/m/psychtoolbox-3/', ...
'/usr/share/matlab/site/m/psychtoolbox-3/', '/usr/share/psychtoolbox-3/'}))
% It is a Debian version of the package
Psychtoolbox.version.flavor = 'Debian package';
[status, result] = system('zcat /usr/share/doc/psychtoolbox-3-common/changelog.Debian.gz| head -1 | sed -e "s/).*/)/g"');
if status == 0
Psychtoolbox.version.revstring = result(1:end-1);
else
Psychtoolbox.version.revstring = 'WARNING: failed to obtain Debian revision';
end
if IsOctave
infourl = 'http://neuro.debian.net/pkgs/octave-psychtoolbox-3.html';
else
infourl = 'http://neuro.debian.net/pkgs/matlab-psychtoolbox-3.html';
end
% Build final version string:
Psychtoolbox.version.string = sprintf('%d.%d.%d - Flavor: %s - %s\nFor more info visit:\n%s', Psychtoolbox.version.major, Psychtoolbox.version.minor, Psychtoolbox.version.point, ...
Psychtoolbox.version.flavor, Psychtoolbox.version.revstring, infourl);
% Old: Retrieve the date of the Debian release:
% Does not work anymore, as date is no longer part of upstream release tags.
% Use contentsdate from Psychtoolbox main help file instead:
Psychtoolbox.date = contentsdate; % sscanf(result, 'psychtoolbox-3 (%*d.%*d.%*d.%d.%*s');
elseif isGIT == true
%assume a GIT install
gitstatus = GetGITInfo(PsychtoolboxRoot);
if ~isempty(gitstatus)
Psychtoolbox.version.flavor = 'GIT Branch';
Psychtoolbox.version.revision = gitstatus.Revision;
Psychtoolbox.version.revstring = gitstatus.Describe;
[r1,r2] = regexp(gitstatus.RemoteRepository{1},'http[^\s]+');
if ~isempty(r1)
remoteURL = gitstatus.RemoteRepository{1}(r1:r2);
else
remoteURL = '';
end
% Build final version string:
Psychtoolbox.version.string = sprintf('%d.%d.%d - Flavor: %s - Commit %s\nFor more info visit:\n%s', ...
Psychtoolbox.version.major, Psychtoolbox.version.minor, Psychtoolbox.version.point, ...
Psychtoolbox.version.flavor, Psychtoolbox.version.revision, remoteURL);
% Cell index of LastCommit where date is stored varies:
for ds=1:numel(gitstatus.LastCommit)
if ~isempty(strfind(gitstatus.LastCommit{ds}, 'Date'))
break;
end
end
date = regexp(gitstatus.LastCommit{ds},'Date:\s+(?<day>\w{3})\s(?<month>\w{3})\s+(?<dayn>\d+)\s(?<time>\d\d\:\d\d:\d\d)\s(?<year>\d{4})','names');
Psychtoolbox.date = sprintf('%s-%s-%s', date.dayn, date.month, date.year);
end
elseif isSVN == false
% assume a manual install
Psychtoolbox.version.flavor = 'Manual Install';
Psychtoolbox.date = fileinfo.date;
Psychtoolbox.version.string=sprintf('%d.%d.%d - Flavor: %s, %s', ...
Psychtoolbox.version.major, Psychtoolbox.version.minor, Psychtoolbox.version.point,...
Psychtoolbox.version.flavor,Psychtoolbox.date);
else
if ~IsOctave && ~verLessThan('matlab', '8.4')
% R2014b and later contain a Java SVN implementation, so lets use
% that to spare the user from having to install a separate svn
% command line client:
% Get svn_client object from Matlab's Java implementation:
svn_client_manager = org.tmatesoft.svn.core.wc.SVNClientManager.newInstance;
svn_client = svn_client_manager.getWCClient();
try
svninfo = svn_client.doInfo(java.io.File(PsychtoolboxRoot()), org.tmatesoft.svn.core.wc.SVNRevision.WORKING);
% Get revision:
Psychtoolbox.version.revision = svninfo.getCommittedRevision().getNumber();
Psychtoolbox.version.revstring = sprintf('Corresponds to SVN Revision %d', Psychtoolbox.version.revision);
% Get flavor:
result = char(svninfo.getURL().getPath());
% First test for end-user branch:
marker = '/Psychtoolbox-3/Psychtoolbox-3/branches/';
startdel = strfind(result, marker) + length(marker);
if isempty(startdel)
% Nope: Search for developer branch aka 'trunk' aka 'master':
marker = '/Psychtoolbox-3/Psychtoolbox-3/';
startdel = strfind(result, marker) + length(marker);
end
findel = min(strfind(result(startdel:length(result)), '/Psychtoolbox')) + startdel - 2;
Psychtoolbox.version.flavor = result(startdel:findel);
% Get date:
date = svninfo.getCommittedDate();
Psychtoolbox.date = sprintf('%d-%02d-%02d', 1900 + date.getYear(), 1 + date.getMonth(), date.getDate());
% SVN status query does not yet work, as it won't detect all
% modifications to the working copy, but only modifications to
% the root folder itself, iow. none at all in almost all cases.
% TODO: Would need to use the doStatus() method which recurses
% over the whole working copy and calls a ISVNStatusHandler for
% each modified item -- Something to figure out, if such
% handlers would be doable easily at all from Matlab...
svn_statusclient = svn_client_manager.getStatusClient();
svnstatus = svn_statusclient.doStatus(java.io.File(PsychtoolboxRoot()), false);
if svnstatus.getContentsStatus() == org.tmatesoft.svn.core.wc.SVNStatusType.STATUS_MODIFIED
Psychtoolbox.version.revstring = sprintf('%s but is *locally modified* !', Psychtoolbox.version.revstring);
end
% Build final version string:
Psychtoolbox.version.string = sprintf('%d.%d.%d - Flavor: %s - %s\nFor more info visit:\n%s', Psychtoolbox.version.major, Psychtoolbox.version.minor, Psychtoolbox.version.point, ...
Psychtoolbox.version.flavor, Psychtoolbox.version.revstring, Psychtoolbox.version.websvn);
catch
fprintf('PsychtoolboxVersion: WARNING - Could not query additional version information from SVN.\n');
Psychtoolbox.version.flavor = 'Unknown';
Psychtoolbox.date = fileinfo.date;
Psychtoolbox.version.string=sprintf('%d.%d.%d - Flavor: %s, %s', ...
Psychtoolbox.version.major, Psychtoolbox.version.minor, Psychtoolbox.version.point,...
Psychtoolbox.version.flavor,Psychtoolbox.date);
end
else
% Fallback: Additional parser code for SVN information. This is slooow!
svncmdpath = GetSubversionPath;
% Find revision string for Psychtoolbox that defines the SVN revision
% to which this working copy corresponds:
if ~IsWin
[status , result] = system([svncmdpath 'svnversion -c ' PsychtoolboxRoot]);
else
[status , result] = dos([svncmdpath 'svnversion -c ' PsychtoolboxRoot]);
end
if status==0
% Parse output of svnversion: Find revision number of the working copy.
colpos=strfind(result, ':');
if isempty(colpos)
Psychtoolbox.version.revision=sscanf(result, '%d',1);
else
cvv = sscanf(result, '%d:%d',2);
Psychtoolbox.version.revision=cvv(2);
end
if isempty(strfind(result, 'M'))
Psychtoolbox.version.revstring = sprintf('Corresponds to SVN Revision %d', Psychtoolbox.version.revision);
else
Psychtoolbox.version.revstring = sprintf('Corresponds to SVN Revision %d but is *locally modified* !', Psychtoolbox.version.revision);
end
% Ok, now find the flavor and such...
if ~IsWin
[status , result] = system([svncmdpath 'svn info --xml ' PsychtoolboxRoot]); %#ok<*ASGLU>
else
[status , result] = dos([svncmdpath 'svn info --xml ' PsychtoolboxRoot]);
end
% First test for end-user branch:
marker = '/github.com/Psychtoolbox-3/Psychtoolbox-3/branches/';
startdel = strfind(result, marker) + length(marker);
if isempty(startdel)
% Nope: Search for developer branch aka 'trunk' aka 'master':
marker = '/github.com/Psychtoolbox-3/Psychtoolbox-3/';
startdel = strfind(result, marker) + length(marker);
end
if isempty(startdel)
% Nope: Retry with a different query for older svn clients:
if ~IsWin
[status , result] = system([svncmdpath 'svn info ' PsychtoolboxRoot]);
else
[status , result] = dos([svncmdpath 'svn info ' PsychtoolboxRoot]);
end
% Retry first test for end-user branch:
marker = '/github.com/Psychtoolbox-3/Psychtoolbox-3/branches/';
startdel = strfind(result, marker) + length(marker);
if isempty(startdel)
% Nope: Retry search for developer branch aka 'trunk' aka 'master':
marker = '/github.com/Psychtoolbox-3/Psychtoolbox-3/';
startdel = strfind(result, marker) + length(marker);
end
end
findel = min(strfind(result(startdel:length(result)), '/Psychtoolbox')) + startdel - 2;
Psychtoolbox.version.flavor = result(startdel:findel);
% Retrieve the date of last commit:
startdel = strfind(result, '<date>') + length('<date>');
findel = max(strfind(result, 'T') - 1);
Psychtoolbox.date = result(startdel:findel);
% Build final version string:
Psychtoolbox.version.string = sprintf('%d.%d.%d - Flavor: %s - %s\nFor more info visit:\n%s', Psychtoolbox.version.major, Psychtoolbox.version.minor, Psychtoolbox.version.point, ...
Psychtoolbox.version.flavor, Psychtoolbox.version.revstring, Psychtoolbox.version.websvn);
else
% Fallback path if svn commands fail for some reason. Output as much as we can.
fprintf('PsychtoolboxVersion: WARNING - Could not query additional version information from SVN -- svn tools not properly installed?!?\n');
Psychtoolbox.version.string=sprintf('%d.%d.%d', Psychtoolbox.version.major, Psychtoolbox.version.minor, Psychtoolbox.version.point);
Psychtoolbox.date=contentsdate;
end
end
end
end
versionString=Psychtoolbox.version.string;
versionStructure=Psychtoolbox.version;
|