source: trunk/coin-functions @ 1593

Last change on this file since 1593 was 1593, checked in by lou, 11 years ago

Release scripts *_new_release rewritten for new script architecture. Upgrades
and bug fixes for coin-functions, *_new_stable, set_externals. Correctly handle
multilevel project names (e.g., CHiPPS/Alps), CppAD version numbering.

File size: 16.4 KB
Line 
1
2# Utility function definitions for the various COIN scripts.
3
4# Copyright (c) 2010 Lou Hafer  Simon Fraser University
5# All Rights Reserved.
6# This file is distributed under the Common Public License.
7# It is part of the BuildTools project in COIN-OR (www.coin-or.org)
8#
9# $Id$
10
11# Functions to disassemble svn URLs and extract relevant bits, and utilities
12# to find the best (most recent) stable and release URLs, calculate libtool
13# version numbers, and compare URLs for compatibility based on major and minor
14# version. Complicated because we have to account for trunk/stable/release and
15# for the variant syntax of Data and ThirdParty URLs. For your normal project,
16# it's
17#   https://projects.coin-or.org/svn/ProjName/trunk
18#   https://projects.coin-or.org/svn/ProjName/stable/M.m
19#   https://projects.coin-or.org/svn/ProjName/releases/M.m.r
20# with the proviso that sometimes it's
21#   https://projects.coin-or.org/svn/ProjName/SubProj/trunk
22# etc.
23# For ThirdParty, it's just like a normal project, except the prefix string
24# is longer:
25#   https://projects.coin-or.org/svn/BuildTools/ThirdParty/ProjName
26# Data is the real pain, with this form:
27#  https://projects.coin-or.org/svn/Data/trunk/ProjName
28#  https://projects.coin-or.org/svn/Data/stable/M.m/ProjName
29#  https://projects.coin-or.org/svn/Data/releases/M.m.r/ProjName
30
31# Extract the COIN base from the URL, up to svn. Just in case it ever changes.
32# usage: baseURL=`extractBaseURL $svnURL`
33
34extractBaseURL ()
35{
36  exbu_baseURL=`echo $1 | sed -n -e 's|\(.*/svn\)/.*$|\1|p'`
37  echo "$exbu_baseURL"
38}
39
40
41# Extract branch type (trunk/stable/release) from the URL.
42# usage: branchType=`extractTypeFromURL $svnURL`
43
44extractTypeFromURL ()
45{
46  etfu_type="invalid"
47  case "$1" in
48    */trunk* ) etfu_type=trunk ;;
49    */stable/* ) etfu_type=stable ;;
50    */releases/* ) etfu_type=releases ;;
51  esac
52  echo $etfu_type
53}
54
55# Determine if this is a `normal' URL, defined as not Data, ThirdParty, or
56# BuildTools itself. ThirdParty lives in BuildTools as of 100628, so the
57# condition is redundant. Returns yes or no.
58# usage: isNormal=`isNormalURL $svnURL`
59
60isNormalURL ()
61{ case $1 in
62    */BuildTools/* | */ThirdParty/* | */Data/* )
63       echo "no"
64       ;;
65    *) echo "yes"
66       ;;
67  esac
68}
69
70# Extract the project from a svn URL. The trick, for `normal' projects, is to
71# handle CHiPPS, which has CHiPPS/Alps, Bcps, Blis. We can't assume the
72# project name does not contain '/'. The heuristic is to look for everything
73# between svn and one of trunk, stable, releases, or end of line.
74# usage: projName=`extractProjFromURL $svnURL`
75
76extractProjFromURL ()
77{
78  epfu_URL="$1"
79  epfu_projPat='\([^/][^/]*\)'
80  epfu_sfxPat='.*$'
81  case "$epfu_URL" in
82    */Data/trunk/* )
83        epfu_pfxPat=svn/Data/trunk/
84        ;;
85    */Data/stable/* | */Data/releases/* )
86        epfu_pfxPat='svn/Data/[^/][^/]*/[0-9][0-9.]*/'
87        ;;
88    */ThirdParty/* )
89        epfu_pfxPat=svn/BuildTools/ThirdParty/
90        ;;
91    *)  epfu_type=`extractTypeFromURL $epfu_URL`
92        epfu_pfxPat='svn/'
93        epfu_projPat='\(.*\)'
94        case $epfu_type in
95          trunk | stable | releases )
96              epfu_sfxPat=$epfu_type'.*$'
97              ;;
98          * )
99              epfu_sfxPat='$'
100              ;;
101        esac
102        ;;
103  esac
104  epfu_projName=`echo $epfu_URL | sed -n -e 's|.*/'$epfu_pfxPat$epfu_projPat$epfu_sfxPat'|\1|p'`
105  epfu_projName=`echo $epfu_projName | sed -e 's|/$||'`
106  echo "$epfu_projName"
107}
108
109# Extract the tail (directory) from a URL that specifies an external. Relevant
110# only for normal projects, where the external will be a subdirectory
111# of the project. Returns null for Data / ThirdParty / BuildTools.
112# usage: projName=`extractTailFromExt $extURL`
113
114extractTailFromExt ()
115{
116  etfe_tail=
117  case "$1" in
118    */Data/* )
119        ;;
120    */BuildTools/ThirdParty/* )
121        ;;
122    */BuildTools/* )
123        ;;
124    *)
125        etfe_pfxPat=
126        case "$1" in
127          */trunk/* )
128              etfe_pfxPat='.*/trunk/'
129              ;;
130          */stable/* )
131              etfe_pfxPat='.*/stable/[0-9][0-9.]*/'
132              ;;
133          */releases/* )
134              etfe_pfxPat='.*/releases/[0-9][0-9.]*/'
135              ;;
136        esac
137        etfe_tail=`echo $1 | sed -n -e 's|'$etfe_pfxPat'\(.*\)|\1|p'`
138        ;;
139  esac
140  echo "$etfe_tail"
141}
142
143
144# CppAD uses a version string of the form YYYMMDD.rr. What a pain in the ass.
145# Hence the scattered exceptions below.
146# Extract the entire version string from a stable or release URL. Returns a
147# null string if handed a trunk URL or if there's no version in the URL. The
148# version number must have at least major.minor to match.
149# usage: version=`extractVersionFromURL $svnURL`
150
151extractVersionFromURL ()
152{
153  evfu_URL="$1"
154  if expr "$evfu_URL" : '.*/stable/.*' >/dev/null 2>&1 ||
155     expr "$evfu_URL" : '.*/releases/.*' >/dev/null 2>&1 ; then
156    if expr "$evfu_URL" : '.*/CppAD/.*' >/dev/null 2>&1 ; then
157      evfu_verPat='\([0-9][0-9.]*\)'
158    else
159      evfu_verPat='\([0-9][0-9]*\.[0-9][0-9.]*\)'
160    fi
161    evfu_sfxPat='.*$'
162    evfu_proj=`extractProjFromURL $evfu_URL`
163    case "$evfu_URL" in
164      */Data/stable/* | */Data/releases/* )
165          evfu_pfxPat='svn/Data/[^/][^/]*/'
166          ;;
167      */ThirdParty/* )
168          evfu_pfxPat='svn/BuildTools/ThirdParty/[^/][^/]*/[^/][^/]*/'
169          ;;
170      *)
171          evfu_pfxPat='svn/'$evfu_proj'/[^/][^/]*/'
172          ;;
173    esac
174    evfu_verVer=`echo $1 | sed -n -e 's|.*/'$evfu_pfxPat$evfu_verPat$evfu_sfxPat'|\1|p'`
175    echo "$evfu_verVer"
176  else
177    echo ""
178  fi
179}
180
181# Replace the entire version string from a stable or release URL. A trunk
182# URL will be unmodified. newRev will not be accessed unless the URL is a
183# release. The version must have at least major.minor to match.
184# usage: newURL=`replaceVersionInURL $oldURL $newMajor $newMinor $newRev`
185# and just for CppAD,
186# usage: newURL=`replaceVersionInURL $oldURL $newMajor $newRev`
187
188replaceVersionInURL ()
189{
190  if expr "$1" : '.*/CppAD/.*' >/dev/null 2>&1 ; then
191    isCppAD=yes
192  else
193    isCppAD=no
194  fi
195  if test $isCppAD = no ; then
196    rviu_verPat='[0-9][0-9]*\.[0-9][0-9.]*'
197  else
198    rviu_verPat='[0-9][0-9.]*'
199  fi
200
201  if expr "$1" : '.*/stable/.*' >/dev/null 2>&1 ; then
202    if test $isCppAD = no ; then
203      rviu_newVersion=$2.$3
204    else
205      rviu_newVersion=$2
206    fi
207  elif expr "$1" : '.*/releases/.*' >/dev/null 2>&1 ; then
208    if test $isCppAD = no ; then
209      rviu_newVersion=$2.$3.$4
210    else
211      rviu_newVersion=$2.$3
212    fi
213  else
214    rviu_newVersion=
215    rviu_newURL=$1
216  fi
217  if test -n "$rviu_newVersion" ; then
218    rviu_newURL=`echo $1 | sed -n -e 's|^\(.*\)/'$rviu_verPat'\(.*\)$|\1/'$rviu_newVersion'\2|p'`
219  fi
220  echo $rviu_newURL
221}
222
223# Extract the major version number from a stable or release URL. Returns -1 if
224# handed a trunk URL or if there's no version in the URL
225# usage: majVer=`extractMajorFromURL $svnURL`
226
227extractMajorFromURL ()
228{
229  ejfu_URL="$1"
230  if expr "$ejfu_URL" : '.*/stable/.*' >/dev/null 2>&1 ||
231     expr "$ejfu_URL" : '.*/releases/.*' >/dev/null 2>&1 ; then
232    ejfu_majPat='\([0-9][0-9]*\)'
233    if expr "$ejfu_URL" : '.*/CppAD/.*' >/dev/null 2>&1 ; then
234      ejfu_sfxPat='.*$'
235    else
236      ejfu_sfxPat='\.[0-9][0-9]*.*$'
237    fi
238    ejfu_proj=`extractProjFromURL $ejfu_URL`
239    case "$ejfu_URL" in
240      */Data/stable/* | */Data/releases/* )
241          ejfu_pfxPat='svn/Data/[^/][^/]*/'
242          ;;
243      */ThirdParty/* )
244          ejfu_pfxPat='svn/BuildTools/ThirdParty/[^/][^/]*/[^/][^/]*/'
245          ;;
246      *)
247          ejfu_pfxPat='svn/'$ejfu_proj'/[^/][^/]*/'
248          ;;
249    esac
250    ejfu_majVer=`echo $ejfu_URL | sed -n -e 's|.*/'$ejfu_pfxPat$ejfu_majPat$ejfu_sfxPat'|\1|p'`
251    echo "$ejfu_majVer"
252  else
253    echo "-1"
254  fi
255}
256
257# Extract the minor version number from a stable or release URL. Returns -1 if
258# handed a trunk URL or if there's no version in the URL.
259# The CppAD form (YYYYMMDD.rr) doesn't have a minor version number.
260# usage: minVer=`extractMinorFromURL $svnURL`
261
262extractMinorFromURL ()
263{
264  emfu_URL="$1"
265  if expr "$emfu_URL" : '.*/CppAD/.*' >/dev/null 2>&1 ; then
266    echo "-1"
267  elif expr "$emfu_URL" : '.*/stable/.*' >/dev/null 2>&1 ||
268       expr "$emfu_URL" : '.*/releases/.*' >/dev/null 2>&1 ; then
269    emfu_minPat='[0-9][0-9]*\.\([0-9][0-9]*\)'
270    emfu_sfxPat='.*$'
271    emfu_proj=`extractProjFromURL $emfu_URL`
272    case "$emfu_URL" in
273      */Data/stable/* | */Data/releases/* )
274          emfu_pfxPat='svn/Data/[^/][^/]*/'
275          ;;
276      */ThirdParty/* )
277          emfu_pfxPat='svn/BuildTools/ThirdParty/[^/][^/]*/[^/][^/]*/'
278          ;;
279      *)
280          emfu_pfxPat='svn/'$emfu_proj'/[^/][^/]*/'
281          ;;
282    esac
283    emfu_minVer=`echo $emfu_URL | sed -n -e 's|.*/'$emfu_pfxPat$emfu_minPat$emfu_sfxPat'|\1|p'`
284    echo "$emfu_minVer"
285  else
286    echo "-1"
287  fi
288}
289
290# Extract the release (revision) number from a release URL. Returns -1 if
291# handed a trunk or stable URL
292# usage: minVer=`extractReleaseFromURL $svnURL`
293
294extractReleaseFromURL ()
295{
296  erfu_URL="$1"
297  if expr "$erfu_URL" : '.*/releases/.*' >/dev/null 2>&1 ; then
298    if expr "$erfu_URL" : '.*/CppAD/.*' >/dev/null 2>&1 ; then
299      erfu_relPat='[0-9][0-9]*\.\([0-9][0-9]*\)'
300    else
301      erfu_relPat='[0-9][0-9]*\.[0-9][0-9]*\.\([0-9][0-9]*\)'
302    fi
303    erfu_sfxPat='.*$'
304    erfu_proj=`extractProjFromURL $erfu_URL`
305    case "$erfu_URL" in
306      */Data/releases/* )
307          erfu_pfxPat='svn/Data/[^/][^/]*/'
308          ;;
309      */ThirdParty/* )
310          erfu_pfxPat='svn/BuildTools/ThirdParty/[^/][^/]*/[^/][^/]*/'
311          ;;
312      *)
313          erfu_pfxPat='svn/'$erfu_proj'/[^/][^/]*/'
314          ;;
315    esac
316    erfu_relVer=`echo $erfu_URL | sed -n -e 's|.*/'$erfu_pfxPat$erfu_relPat$erfu_sfxPat'|\1|p'`
317    echo "$erfu_relVer"
318  else
319    echo "-1"
320  fi
321}
322
323# Now some functions to locate the highest-numbered stable or release.
324
325# Return the URL of the most recent stable branch matching the parameters.
326# A value of -1 for major or minor version is interpreted as `highest number'
327# Returns an empty string if no suitable stable branch exists.
328# usage: stableURL=`bestStable <URL> <major>`
329
330bestStable ()
331{ bstb_URL=$1
332  bstb_majVer=$2
333
334  # Construct a URL to send to the repository to list the stable branches.
335
336  bstb_baseURL=`extractBaseURL $bstb_URL`
337  bstb_proj=`extractProjFromURL $bstb_URL`
338
339  case "$bstb_URL" in
340    */Data/* )
341        bstb_listURL=$bstb_baseURL/Data/stable
342        ;;
343    */ThirdParty/* )
344        bstb_listURL=$bstb_baseURL/BuildTools/ThirdParty/$bstb_proj/stable
345        ;;
346    * )
347        bstb_listURL=$bstb_baseURL/$bstb_proj/stable
348        ;;
349  esac
350
351  bstb_rawls=`svn list $bstb_listURL | sort -nr -t. -k1,1 -k2,2`
352
353  # echo "Raw ls: $bstb_rawls"
354
355  # Filter the list of stable branches to remove any that do not match the
356  # requested major version. Note that there's a / at the end of each URL.
357
358  if test "$bstb_majVer" = "-1" ; then
359    bstb_verPat='[0-9][0-9.]*/'
360  elif expr "$bstb_URL" : '.*/CppAD/.*' >/dev/null 2>&1 ; then
361    bstb_verPat=$bstb_majVer'/'
362  else
363    bstb_verPat=$bstb_majVer'\.[0-9][0-9]*'
364  fi
365  bstb_filter=
366  for bstb_ver in $bstb_rawls ; do
367    if  expr "$bstb_ver" : $bstb_verPat >/dev/null 2>&1 ; then
368      bstb_filter="$bstb_filter $bstb_ver"
369    fi
370  done
371
372  # echo "Filtered ls: $bstb_filter"
373
374  # If there are any candidates left ...
375
376  bstb_bestURL=
377  if test -n "$bstb_filter" ; then
378
379    # If we're dealing with Data, we have to work a bit harder to find our
380    # project. See if any of the filtered candidates contain the correct
381    # project.
382
383    if expr "$bstb_URL" : '.*/Data/.*' >/dev/null 2>&1 ; then
384      bstb_projPat='.*'$bstb_proj'/.*'
385      # echo "Pattern: $bstb_projPat"
386      for bstb_ver in $bstb_filter ; do
387        if  expr "$bstb_ver" : $bstb_verPat >/dev/null 2>&1 ; then
388          # echo "  url: $bstb_listURL/$bstb_ver"
389          bstb_svnls2="`svn list $bstb_listURL/$bstb_ver`"
390          # echo "  result: $bstb_svnls2"
391          if expr "$bstb_svnls2" : $bstb_projPat >/dev/null 2>&1 ; then
392            bstb_best=$bstb_ver
393            # echo "  best: $bstb_best"
394            break
395          fi
396        fi
397      done
398      bstb_bestURL=$bstb_listURL/$bstb_best$bstb_proj
399    else
400      bstb_bestURL=`echo $bstb_filter | sed -n -e 's|\([^/]*/\).*$|\1|p'`
401      bstb_bestURL=$bstb_listURL/$bstb_bestURL
402    fi
403
404  fi
405
406  echo $bstb_bestURL
407}
408
409# Return the URL of the most recent release matching the parameters. Returns
410# null if no suitable release exists.
411# A value of -1 for major or minor version is interpreted as `highest number'
412# A value of -1 for major version means that minor version is ignored.
413# usage: releaseURL=`bestRelease <URL> <major> <minor>`
414
415bestRelease ()
416{ bstb_URL=$1
417  bstb_majVer=$2
418  bstb_minVer=$3
419
420  # Construct a URL to send to the repository to list the releases.
421
422  bstb_baseURL=`extractBaseURL $bstb_URL`
423  bstb_proj=`extractProjFromURL $bstb_URL`
424
425  case "$bstb_URL" in
426    */Data/* )
427        bstb_listURL=$bstb_baseURL/Data/releases
428        ;;
429    */ThirdParty/* )
430        bstb_listURL=$bstb_baseURL/BuildTools/ThirdParty/$bstb_proj/releases
431        ;;
432    * )
433        bstb_listURL=$bstb_baseURL/$bstb_proj/releases
434        ;;
435  esac
436
437  bstb_rawls=`svn list $bstb_listURL | sort -nr -t. -k1,1 -k2,2 -k3,3`
438
439  # echo "Raw ls: $bstb_rawls"
440
441  # Filter the list of releases to remove any that do not match the
442  # requested major and minor version.
443
444  if expr "$bstb_URL" : '.*/CppAD/.*' >/dev/null 2>&1 ; then
445    isCppAD=yes
446  else
447    isCppAD=no
448  fi
449
450  if test "$bstb_majVer" = "-1" ; then
451    bstb_verPat='[0-9][0-9.]*/'
452  else
453    bstb_verPat=$bstb_majVer
454    if test $isCppAD = no &&
455       test "$bstb_minVer" != "-1" ; then
456      bstb_verPat="${bstb_verPat}\.$bstb_minVer"
457    fi
458    bstb_verPat="${bstb_verPat}"'\.[0-9][0-9]*/'
459  fi
460
461  # echo "Version pattern: $bstb_verPat"
462  bstb_filter=
463  for bstb_ver in $bstb_rawls ; do
464    if  expr "$bstb_ver" : $bstb_verPat >/dev/null 2>&1 ; then
465      bstb_filter="$bstb_filter $bstb_ver"
466    fi
467  done
468
469  # echo "Filtered ls: $bstb_filter"
470
471  # If there are any candidates left ...
472
473  bstb_bestURL=
474  if test -n "$bstb_filter" ; then
475
476    # If we're dealing with Data, we have to work a bit harder to find our
477    # project. See if any of the filtered candidates contain the correct
478    # project.
479
480    if expr "$bstb_URL" : '.*/Data/.*' >/dev/null 2>&1 ; then
481      bstb_projPat='.*'$bstb_proj'/.*'
482      # echo "Pattern: $bstb_projPat"
483      for bstb_ver in $bstb_filter ; do
484        if  expr "$bstb_ver" : $bstb_verPat >/dev/null 2>&1 ; then
485          # echo "  url: $bstb_listURL/$bstb_ver"
486          bstb_svnls2="`svn list $bstb_listURL/$bstb_ver`"
487          # echo "  result: $bstb_svnls2"
488          if expr "$bstb_svnls2" : $bstb_projPat >/dev/null 2>&1 ; then
489            bstb_best=$bstb_ver
490            # echo "  best: $bstb_best"
491            break
492          fi
493        fi
494      done
495      bstb_bestURL=$bstb_listURL/$bstb_best$bstb_proj
496    else
497      bstb_bestURL=`echo $bstb_filter | sed -n -e 's|\([^/]*/\).*$|\1|p'`
498      bstb_bestURL=$bstb_listURL/$bstb_bestURL
499    fi
500
501  fi
502
503  echo $bstb_bestURL
504}
505
506# Count the total number of stable branches for the project for the specified
507# major version number (libtool age). A major version number of -1 means all
508# stable branches (libtool current; see next function). Returns 0 if handed
509# a trunk url, or if the url is Data or BuildTools itself.
510# usage: calcLibtoolAge <svnURL> <major>
511
512calcLibtoolAge ()
513{ cltc_URL=$1
514  cltc_majVer=$2
515
516  # Construct a URL to send to the repository to list the stable branches.
517
518  cltc_baseURL=`extractBaseURL $cltc_URL`
519  cltc_proj=`extractProjFromURL $cltc_URL`
520
521  case "$cltc_URL" in
522    */Data/* )
523        cltc_listURL=
524        ;;
525    */ThirdParty/* )
526        cltc_listURL=$cltc_baseURL/BuildTools/ThirdParty/$cltc_proj/stable
527        ;;
528    */BuildTools/* )
529        cltc_listURL=
530        ;;
531    * )
532        cltc_listURL=$cltc_baseURL/$cltc_proj/stable
533        ;;
534  esac
535
536  # Run an ls and filter for standard stable branches (M.m or YYYYMMDD)
537
538  if test -n "$cltc_listURL" ; then
539    cltc_rawls=`svn list $cltc_listURL | sed -n -e '/[0-9][0-9.]/p'`
540
541    # echo "Raw ls: $cltc_rawls"
542
543    # Filter the list of stable branches to remove any that do not match the
544    # requested major version. -1 means `any major version', hence no filter.
545
546    if test "$cltc_majVer" != "-1" ; then
547      if expr "$cltc_URL" : '.*/CppAD/.*' >/dev/null 2>&1 ; then
548        cltc_verPat=$cltc_majVer
549      else
550        cltc_verPat=$cltc_majVer'\.[0-9][0-9]*'
551      fi
552    else
553      cltc_verPat='[0-9][0-9.]*'
554    fi
555    cltc_filter=
556    for cltc_ver in $cltc_rawls ; do
557      if  expr "$cltc_ver" : $cltc_verPat >/dev/null 2>&1 ; then
558        cltc_filter="$cltc_filter $cltc_ver"
559      fi
560    done
561
562    # echo "Filtered ls: $cltc_filter"
563
564    cltc_cnt=`echo $cltc_filter | wc -w | sed -e 's/ //g'`
565  else
566    cltc_cnt=0
567  fi
568
569  echo $cltc_cnt
570}
571
572# Function to compare the versions in a pair of URLs for equality. The criteria
573# is that the major and minor versions match. In theory, the release should
574# not matter. Probably should be a parameter.
575# usage: compareURLVersions <url1> <url2>
576
577compareURLVersions ()
578{
579  url1_major=`extractMajorFromURL $1`
580  url1_minor=`extractMinorFromURL $1`
581  url2_major=`extractMajorFromURL $2`
582  url2_minor=`extractMinorFromURL $2`
583
584  if test $url1_major = $url2_major &&
585     test $url1_minor = $url2_minor ; then
586    echo "yes"
587  else
588    echo "no"
589  fi
590}
591
Note: See TracBrowser for help on using the repository browser.