source: branches/stable/SOURCE_TOOLS/remake_after_change.pl

Last change on this file was 17877, checked in by westram, 5 years ago
  • Property svn:executable set to *
File size: 8.7 KB
Line 
1#!/usr/bin/perl
2
3use strict;
4use warnings;
5
6# ----------------------------------------
7
8my @shared = (
9              'AWT',
10              'ARBDB',
11              'CORE',
12              'WINDOW',
13             );
14my %shared = map { $_ => 1; } @shared;
15
16# ----------------------------------------
17
18my %dir2dirs = (
19
20                'AISC'     => 'NAMES_COM PROBE_COM',
21                'AISC_COM' => 'AISC',
22                'GL'       => 'GL/glAW GL/glpng',
23
24               );
25
26my %dir2libs = (
27
28                'NAMES_COM' => 'NAMES_COM/client.a NAMES_COM/common.a NAMES_COM/server.a',
29                'PROBE_COM' => 'PROBE_COM/client.a PROBE_COM/common.a PROBE_COM/server.a',
30                'GL/glAW'   => 'GL/glAW/libglAW.a',
31                'GL/glpng'  => 'GL/glpng/libglpng_arb.a',
32                'ptpan'     => 'ptpan/PROBE.a',
33
34               );
35
36my %dir2targets = (
37
38                   'AISC_MKPTPS'  => 'all',
39                   'bin'          => 'all',
40                   'BINDEP'       => 'all',
41                   'BUGEX'        => 'all',
42                   'dep_graphs'   => 'dep_graph',
43                   'GDE'          => 'gde',
44                   'GDEHELP'      => 'help menus',
45                   'HELP_SOURCE'  => 'help',
46                   'INCLUDE'      => 'all',
47                   'lib'          => 'help libs perl',
48                   'PERL2ARB'     => 'perl',
49                   'PERL_SCRIPTS' => 'testperlscripts',
50                   'PROBE_SET'    => 'pst',
51                   'READSEQ'      => 'readseq',
52                   'SL'           => 'all',
53                   'SOURCE_TOOLS' => 'links valgrind_update',
54                   'TEMPLATES'    => 'all',
55                   'TOOLS'        => 'tools',
56                   'UNIT_TESTER'  => 'ut',
57
58                  );
59
60# ----------------------------------------
61
62my $ARBHOME = $ENV{ARBHOME};
63if ((not defined $ARBHOME) or (not -d $ARBHOME)) {
64  die "Need correct \$ARBHOME";
65}
66my $SOURCE_TOOLS = $ARBHOME.'/SOURCE_TOOLS';
67
68sub dir2name($$$) {
69  my ($dir,$prefix,$suffix) = @_;
70
71  if ($dir eq '') { return undef; }
72
73  my $lastname = $dir;
74  if ($dir =~ /\/([^\/]+)$/) { $lastname = $1; }
75
76  my $useddir = ($suffix eq '.so') ? 'lib' : $dir;
77  my $name    = $useddir.'/'.$prefix.$lastname.$suffix;
78
79  return $name;
80}
81
82sub dirs2changedlibs($);
83sub dirs2changedlibs($) {
84  my ($dirs) = @_;
85
86  my @dir = split / /,$dirs;
87  my %libs = ();
88
89  foreach my $dir (@dir) {
90    if (defined $dir2dirs{$dir}) {
91      my $dirs2 = $dir2dirs{$dir};
92      my $libs2 = dirs2changedlibs($dirs2);
93      foreach (split / /,$libs2) { $libs{$_} = 1; }
94    }
95    elsif (defined $dir2libs{$dir}) {
96      my $libs = $dir2libs{$dir};
97      foreach (split / /,$libs) { $libs{$_} = 1; }
98    }
99    else {
100      my $prefix = '';
101      my $suffix = '.a';
102
103      if (defined $shared{$dir}) {
104        $prefix = 'lib';
105        $suffix = '.so';
106      }
107
108      my $libname = dir2name($dir,$prefix,$suffix);
109      $libs{$libname} = 1;
110    }
111  }
112
113  return join(' ',keys %libs);
114}
115
116sub changedlibs2targets($) {
117  my ($changed_lib) = @_;
118
119  my %targets = ();
120  foreach (split / /,$changed_lib) {
121    # all client.a and common.a libs are identical (the libs in PROBE_COM are used in dependencies)
122    if ($_ eq 'NAMES_COM/client.a') { $_ = 'PROBE_COM/client.a'; }
123    if ($_ eq 'NAMES_COM/common.a') { $_ = 'PROBE_COM/common.a'; }
124
125    my $cmd = $SOURCE_TOOLS.'/needed_libs.pl -F -U -I -T '.$_;
126    my $base_targets = `$cmd`;
127    chomp($base_targets);
128    foreach (split / /,$base_targets) { $targets{$_} = 1; }
129  }
130
131  # modify targets
132  my @targets = map {
133    if ($_ =~ /\//) {
134      if ($_ =~ /\.a$/o) {
135        $`.'.dummy';
136      }
137      elsif ($_ =~ /\/([^\/]+)\.o$/o) {
138        my $dir = $`;
139        dir2name($dir,'','.dummy');
140      }
141      else {
142        $_;
143      }
144    }
145    else {
146      'rac_'.$_;
147    }
148  } keys %targets;
149
150  return(join(' ', @targets));
151}
152
153sub dirs2targets($) {
154  my ($dirs) = @_;
155  my %targets = ();
156  foreach (split / /,$dirs) {
157    if (defined $dir2targets{$_}) {
158      my $targets = $dir2targets{$_};
159      foreach (split / /,$targets) { $targets{$_} = 1; }
160    }
161  }
162  return join(' ',keys %targets);
163}
164
165sub config2env() {
166  my $conf = $ARBHOME.'/config.makefile';
167
168  if (not -f $conf) {
169    print "$conf not found.. generating\n";
170    my $cmd = "cd $ARBHOME;make";
171    system($cmd);
172    exit(1);
173  }
174
175  open(CONF,'<'.$conf) || die "can't read '$conf' (Reason: $!)";
176
177  my $OPENGL     = 0;
178  my $UNIT_TESTS = 0;
179
180  foreach (<CONF>) {
181    chomp;
182    if (/^OPENGL\s*:=\s*([0-9]+)/) { $OPENGL = $1; }
183    if (/^UNIT_TESTS\s*:=\s*([0-9]+)/) { $UNIT_TESTS = $1; }
184  }
185  close(CONF);
186
187  print "Using:\n";
188  print "- OPENGL=$OPENGL\n";
189  print "- UNIT_TESTS=$UNIT_TESTS\n";
190
191  if ($OPENGL==1) {
192    $ENV{RNA3D_LIB} = 'RNA3D/RNA3D.a';
193  }
194
195  return $UNIT_TESTS;
196}
197
198sub dump_log($) {
199  my ($log) = @_;
200  print "---------------------------------------- [$log start]\n";
201  open(LOG,'<'.$log) || die "can't read '$log' (Reason: $!)";
202  print <LOG>;
203  close(LOG);
204  print "---------------------------------------- [$log end]\n";
205}
206
207sub system_no_error_or_die($) {
208  my ($cmd) = @_;
209  if (system($cmd)!=0) { die "could not execute '$cmd'"; }
210  if ($? == -1) { die "could not execute '$cmd'"; }
211  if ($? & 127) { die sprintf("child died with signal %d", ($? & 127)); }
212  my $exitcode = ($? >> 8);
213  if ($exitcode!=0) { die "command '$cmd' failed (exitcode=$exitcode)"; }
214}
215
216sub main() {
217  my $dir = `pwd`;
218  chomp($dir);
219
220  if (not defined $ENV{LINK_STATIC}) {
221    print "Warning: LINK_STATIC not defined (assuming 0 - which is wrong for OSX)\n";
222    $ENV{LINK_STATIC} = '0'; # wrong for OSX
223  }
224
225  my $UNIT_TESTS = config2env();
226
227  if (not $dir =~ /^$ARBHOME/) {
228    print "Usage: simply call in any directory inside ARBHOME\n";
229    print "It will assume you changed something there and remake all depending executables\n";
230    print "(In fact this is a lie, it won't work everywhere:)\n";
231
232    die "Not called from inside $ARBHOME";
233  }
234
235  print "remake[3]: Entering directory `$ARBHOME'\n";
236  chdir($ARBHOME);
237
238  $dir = $';
239  $dir =~ s/^\///;
240
241  my $changed_libs = dirs2changedlibs($dir);
242  my $targets;
243  if ($changed_libs eq '') {
244    print "Called in ARBHOME\n";
245    $targets = 'all';
246  }
247  else {
248    $targets = '';
249    while ($targets eq '') {
250      print "Assuming $changed_libs changed\n";
251      $targets = changedlibs2targets($changed_libs);
252      if ($targets eq '') { $targets = dirs2targets($dir); }
253
254      if ($targets eq '') {
255        if ($dir =~ /\//) {
256          my $updir = $`;
257          print "No known targets for $dir - trying $updir\n";
258          $dir = $updir;
259          $changed_libs = dirs2changedlibs($dir);
260        }
261        else {
262          die "No idea what to remake for '$dir'\n ";
263        }
264      }
265    }
266  }
267
268  if ($targets ne '') {
269    my $cores = `cat /proc/cpuinfo | grep processor | wc -l`;
270    if ($cores<1) { $cores = 1; }
271    my $jobs = $cores+1;
272    print "Remaking\n";
273
274    foreach (split / /,$targets) { print " - $_\n"; }
275
276    print "\n";
277
278    my $premake = "make -j$jobs up_by_remake";
279    print "Silent premake: '$premake'\n";
280    my $log = 'silent_premake.log';
281    $premake = "cd $ARBHOME;$premake > $log 2>&1";
282    print "Silent premake: '$premake' (real)\n";
283
284    eval {
285      system_no_error_or_die($premake);
286    };
287    if ($@) {
288      my $err = "Silent premake failed (".$@.")";
289      # print "\nError: $err\n"; (too common. spams compile log. also printed below)
290      dump_log($log);
291      die $err;
292    }
293    else {
294      open(LOG,'<'.$log) || die "can't read '$log' (Reason: $!)";
295      my @warnings = grep /:\swarning:\s/, <LOG>;
296      close(LOG);
297      if (scalar(@warnings)) {
298        print "\nWarnings detected:\n";
299        dump_log($log);
300      }
301    }
302    print "\n";
303
304    my $targets_contain_unittests = 0;
305    my $targets_are_timed = 0;
306
307    my %targets = map { $_ => 1; } split / /,$targets;
308    if (defined $targets{all}) {
309      $targets_contain_unittests = 1;
310      $targets_are_timed         = 1;
311    }
312    if (defined $targets{ut}) {
313      $targets_contain_unittests = 1;
314    }
315
316    my $makecmd;
317    my $makeFlags = " -j$jobs --warn-undefined-variables"; # warn about undefined makefile variables
318    # these variables are known to be undefined:
319    $ENV{WITHPERL} = '';
320    $ENV{TIMED_TARGET} = '';
321    $ENV{ONE_TIMED_TARGET} = '';
322
323    if ($targets_are_timed==1) {
324      $makecmd = "cd $ARBHOME;make $makeFlags $targets";
325    }
326    else {
327      my $timed_target = (($UNIT_TESTS==0) or ($targets_contain_unittests==1)) ? 'timed_target' : 'timed_target_tested';
328      $makecmd = "cd $ARBHOME;make \"TIMED_TARGET=$targets\" $makeFlags $timed_target";
329    }
330
331    print "[Make: '$makecmd']\n";
332    system($makecmd)==0 || die "error executing '$makecmd' (exitcode=$?)\n";
333    print "remake[3]: Leaving directory `$ARBHOME'\n";
334
335    unlink($log);
336  }
337}
338
339main();
Note: See TracBrowser for help on using the repository browser.