Subversion Repositories DevTools

Rev

Details | Last modification | View Log | RSS feed

Rev Author Line No. Line
227 dpurdie 1
#! /usr/bin/perl
2
########################################################################
3
# Copyright (C) 1998-2004 ERG Limited, All rights reserved
4
#
5
# Module name   : jats_cbuilder.pl
6
# Module type   : Makefile system
7
# Compiler(s)   : n/a
8
# Environment(s):
9
#
10
# Description   : A script to build a package from a clearcase element
11
#                 The script will:
12
#                   Create a clearcase view
13
#                   Checkout the files
14
#                   Locate the build file
15
#                   Build the packages
16
#                   Install packages
17
#                   Remove the view
18
#
19
#               The script can do a lot of other things too.
20
#
21
#......................................................................#
22
 
23
require 5.6.1;
24
use strict;
25
use warnings;
26
use JatsError;
27
use JatsSystem;
28
use FileUtils;
245 dpurdie 29
use JatsBuildFiles;
30
use ArrayHashUtils;
227 dpurdie 31
 
32
use Pod::Usage;                             # required for help support
33
use Getopt::Long;
34
use File::Find;
35
use File::Copy;
36
use File::Path;
37
use Cwd;
38
use Sys::Hostname;                          # For hostname
39
 
40
my $VERSION = "1.6.0";                      # Update this
41
 
42
#
43
#   Options
44
#
45
my $opt_debug   = $ENV{'GBE_DEBUG'};        # Allow global debug
46
my $opt_verbose = $ENV{'GBE_VERBOSE'};      # Allow global verbose
47
my $opt_help = 0;                           # User help level
48
my $opt_manual = 0;                         # Generate help as a MAN page
49
my @opt_spec;                               # Labels used as a base for the view
50
my $opt_vob;                                # Hint: which VOB to use
51
my $opt_dpkg = 1;                           # Transfer built package to dpkg_archive
52
my $opt_copy = 0;                           # Copy built package to user
53
my $opt_reuse = 0;                          # Re-user view if it exists
54
my $opt_viewname;                           # View Name
55
my $opt_extract;                            # Just create a static view
56
my $opt_extract_files;                      # Just extract files to user - no view
57
my $opt_delete;                             # Just delete the view
58
my @opt_build;                              # build files to use (kludge)
59
my $opt_test;                               # Test the build process - no copy
60
my $opt_cache;                              # Cache external packages
61
my $opt_keep = 0;                           # Keep view if successful
62
my $opt_lock = 0;                           # Lock label before release
63
my $opt_beta;                               # Create beta release
64
my $opt_merge;                              # Merge release
65
my $opt_path;                               # Path for view spec
66
my $opt_runtests = 1;                       # Run unit tests after build
67
my $opt_latest_root;                        # Modify config spec with rule (kludge)
68
my $opt_branch;                             # Create config spec with branch
69
my $opt_debug_build = 0;                    # Build Debug Only
70
my $opt_prod_build = 0;                     # Build ion Only
71
my $opt_view_root = $ENV{'GBE_VIEWBASE'};   # Root of the view
72
my $opt_config_spec;                        # User provided config spec
73
my $opt_prefix = 1;                         # Prefix the view tag with user-name
74
my $opt_tag;                                # View tag insert (build or export or user)
75
 
76
#
77
#   Globals - Provided by the JATS environment
78
#
79
my $USER            = $ENV{'USER'};
80
my $UNIX            = $ENV{'GBE_UNIX'};
81
my $HOME            = $ENV{'HOME'};
82
my $GBE_SANDBOX     = $ENV{'GBE_SANDBOX'};
243 dpurdie 83
my $GBE_ABT         = $ENV{'GBE_ABT'} || '0';
227 dpurdie 84
 
85
#
86
#   Globals
87
#
88
my $MACHINENAME;
89
my $VIEWDIR_ROOT = "c:/clearcase";          # Root of all static views (WIN32)
90
my $VIEWTAG;                                # The view tag
91
my $VIEWDIR;                                # Absolute path to the view
92
my $VIEWPATH;                               # Path relative to clearcase
93
my $user_cwd;
94
my $error = 0;
95
my $label_count = 0;                        # Number of labels to create the view
96
my @label_not_locked;                       # List of unlocked labels
97
my @label_locked;                           # List of labels I locked
98
my @error_list;                             # ClearCmd detected errors
99
 
100
my $UNIX_VOB_PREFIX = '/vobs';
101
my $VOB_PREFIX = $UNIX ? $UNIX_VOB_PREFIX : '';
102
 
103
my $UNIX_VIEW_PREFIX = '/view/';            # Don't know how to determine this value
104
my $WIN32_VIEW_PREFIX = 'o:/';              # Don't know how to determine this value
105
my $VIEW_PREFIX = $UNIX ? $UNIX_VIEW_PREFIX : $WIN32_VIEW_PREFIX ;
106
 
107
my $UNIX_VP_ROOT    = 'jats_cbuilder';
108
my $VOB_SEP         = $UNIX ? '/' : '\\';
109
my $view_prefix     = "${USER}_";
110
 
111
#
112
#   ROOT_VOBS is a list of VOBS too look in first
113
#   If a label is not found in these vobs, then the program will
114
#   look in all vobs. This list is a hint to speed up searching
115
#
116
my $ROOT_VOB;
117
my $root_vob_spec;
118
my @ROOT_VOBS = qw( /LMOS /DPG_SWBase /DPG_SWCode /ProjectCD /MASS_Dev_Bus
119
                    /MASS_Dev_Infra /MOS /MASS_Dataman /MASS_Dev /MASS_Dev_Dataman
120
                    /COTS /GMPTE2005 /GMPTE2005_obe /MPR /MOS );
121
 
122
 
123
#-------------------------------------------------------------------------------
124
# Function        : Mainline Entry Point
125
#
126
# Description     :
127
#
128
# Inputs          :
129
#
130
 
131
#
132
#   Alter some option defaults if we are creating a view within a sandbox
133
#
134
if ( $GBE_SANDBOX )
135
{
136
   $opt_view_root = $GBE_SANDBOX;
137
   $opt_prefix = 0;
138
}
139
 
140
#
141
#   Parse the user options
142
#
143
my $result = GetOptions (
144
                "help+"         => \$opt_help,              # flag, multiple use allowed
145
                "manual"        => \$opt_manual,            # flag, multiple use allowed
146
                "verbose+"      => \$opt_verbose,           # flag, multiple use allowed
147
                "label=s"       => \@opt_spec,              # Array of build specs
148
                "spec=s"        => \@opt_spec,              # Array of build specs
149
                "config=s"      => \$opt_config_spec,       # String
150
                "view=s"        => \$opt_viewname,          # String
151
                "vob=s"         => \$opt_vob,               # String
152
                "dpkg!"         => \$opt_dpkg,              # [no]flag
153
                "copy!"         => \$opt_copy,              # [no]flag
154
                "reuse!"        => \$opt_reuse,             # [no]flag
155
                "extract"       => \$opt_extract,           # flag
156
                "extractfiles"  => \$opt_extract_files,     # flag
157
                "delete"        => \$opt_delete,            # flag
158
                "build=s"       => \@opt_build,             # An array of build
159
                "test!"         => \$opt_test,              # [no]flag
160
                "cache"         => \$opt_cache,             # flag
161
                "keep!"         => \$opt_keep,              # [no]flag
162
                "lock!"         => \$opt_lock,              # [no]flag
163
                "beta!"         => \$opt_beta,              # [no]flag
164
                "merge"         => \$opt_merge,             # [no]flag
165
                "path=s"        => \$opt_path,              # string
166
                "runtests!"     => \$opt_runtests,          # [no]flag
167
                "latestroot=s"  => \$opt_latest_root,       # String
168
                "branch=s"      => \$opt_branch,            # String
169
                "mkbranch=s"    => \$opt_branch,            # String
170
                "prodOnly"      => \$opt_prod_build,        # flag
171
                "debugOnly"     => \$opt_debug_build,       # flag
172
                "root=s"        => \$opt_view_root,         # string
173
                "prefix!"       => \$opt_prefix,            # flag
174
                "tag=s"         => \$opt_tag,               # string
175
                );
176
 
177
                #
178
                #   UPDATE THE DOCUMENTATION AT THE END OF THIS FILE !!!
179
                #
180
 
181
#
182
#   Process help and manual options
183
#
184
pod2usage(-verbose => 0, -message => "Version: $VERSION")  if ($opt_help == 1  || ! $result);
185
pod2usage(-verbose => 1)  if ($opt_help == 2 );
186
pod2usage(-verbose => 2)  if ($opt_manual || ($opt_help > 2));
187
 
188
InitFileUtils();
189
 
190
#
191
#   Configure the error reporting process now that we have the user options
192
#
193
ErrorConfig( 'name'    => 'RELEASE',
194
             'verbose' => $opt_verbose );
195
 
196
#
197
#   Validate user options
198
#   Use either -label or one command line argument
199
#
200
Error ("Unexpected command line arguments present.","Cannot mix -label and command line label" )
201
    if ( $#opt_spec >= 0 && $#ARGV >= 0);
202
 
203
push @opt_spec, @ARGV;
204
 
205
if ( $opt_config_spec )
206
{
207
    Error("Cannot use -path with -config")      if($opt_path);
208
    Error("Cannot use -branch with -config")    if($opt_branch);
209
    Error("Cannot use -vob with -config")       if($opt_vob);
210
    Error("Cannot use a label with -config")    if( @opt_spec);
211
    Error("Config spec file not found: $opt_config_spec") unless ( -f $opt_config_spec );
212
 
213
    unless ( $opt_viewname )
214
    {
215
        $opt_viewname = StripDirExt($opt_config_spec);
216
        $opt_viewname =~ s~[\.:/\\]~_~g;
217
    }
218
 
219
    $opt_vob = "";
220
 
221
    #
222
    #   Convert file in an absolute file name
223
    #   Will be needed as we change directory
224
    #
225
    $opt_config_spec = FullPath($opt_config_spec);
226
}
227
 
228
unless(  @opt_spec || $opt_config_spec  )
229
{
230
    Error ("Need a view or a label. -help for options") if ( $opt_delete  && ! $opt_viewname );
231
    Error ("Need a label or config_spec. -help for options") unless $opt_delete;
232
}
233
 
234
 
235
if ( $opt_debug_build + $opt_prod_build > 1 )
236
{
237
    $opt_debug_build = 0;
238
    $opt_prod_build = 0;
239
}
240
 
241
if ( $opt_test )
242
{
243
    $opt_dpkg = 0;
244
    $opt_copy = 0;
245
}
246
 
247
#
248
#   Determine the machine type
249
#
250
Verbose ("Machine Type: UNIX=$UNIX");
251
 
252
$MACHINENAME = hostname;
253
Error ("Machine Name not determined")
254
    unless ( $MACHINENAME );
255
chomp( $MACHINENAME );
256
$user_cwd = getcwd;
257
 
258
Error ("USER name not determined" )
259
    unless ( $USER );
260
 
261
#
262
#   Ensure that the 'cleartool' program can be located
263
#
264
Verbose ("Locate clearcase utility in users path");
265
Error ("Cannot locate the 'cleartool' utility in the users PATH")
266
    unless ( LocateProgInPath('cleartool', '--All') );
267
 
268
 
269
#
270
#   Under UNIX the VOBS are a bit different
271
#   and the clearcase view can be created in the user home directory
272
#
273
unless ( $opt_view_root  )
274
{
275
    if ( $UNIX )
276
    {
277
        Error ("Unix HOME EnvVar not defined" ) unless ( $HOME );
278
        Error ("Unix HOME directory not found: $HOME" ) unless (-d $HOME );
279
        $VIEWDIR_ROOT = "$HOME/$UNIX_VP_ROOT";
280
        Verbose ("Unix viewpath: $VIEWDIR_ROOT");
281
        mkdir ( $VIEWDIR_ROOT ) unless (-d $VIEWDIR_ROOT);
282
    }
283
}
284
else
285
{
286
    $opt_view_root = Realpath($opt_view_root) || $opt_view_root;
287
    $VIEWDIR_ROOT = $opt_view_root;
288
}
289
 
290
Verbose ("Viewpath: $VIEWDIR_ROOT");
291
Error ("Cannot locate view root directory: $VIEWDIR_ROOT" ) unless (-d $VIEWDIR_ROOT);
292
 
293
#
294
#   Remove any user name from the front of the view name
295
#   Simplifies the deletion process as the user can provide
296
#   the directory name
297
#
298
$view_prefix = "" unless ( $opt_prefix );
299
 
300
#
301
#   Setup user specified viewname
302
#   Include the user name to ensure that the view name is unique-ish
303
#   Keep the name as short as possible as some compilers display a fixed
304
#   length filename in error messages and this name is part of the path
305
#
306
#   Base the viewname on the view label. This will simplify the creation
307
#   of multiple views and reduce the risk of unexpected deletion
308
#
309
$opt_viewname = $opt_spec[0] unless ( defined $opt_viewname );
310
$opt_viewname =~ s~^$view_prefix~~ if (defined($opt_viewname) && $view_prefix && $opt_delete );
311
 
312
#
313
#   Create the view tag
314
#   Attempt to make this globally unique
315
#   Include USER name, MACHINE name, the view name
316
#   Optionally include a user 'tag'. Provided to allow the ABT to maintain
317
#   multiple instances of a view.
318
#
319
unless ( $opt_tag )
320
{
321
    $opt_tag = $opt_extract_files ? 'extract' : 'build';
322
}
323
$VIEWTAG = "${USER}_${MACHINENAME}_${opt_tag}_${opt_viewname}";
324
 
325
#
326
#   Create a clearcase view to be used for the view
327
#
328
$VIEWPATH = "$view_prefix$opt_viewname";
329
$VIEWDIR = "$VIEWDIR_ROOT/$VIEWPATH";
330
Verbose( "Hostname: $MACHINENAME" );
331
Verbose( "Viewtag: $VIEWTAG" );
332
Verbose( "Viewpath: $VIEWPATH" );
333
Verbose( "Viewdir : $VIEWDIR" );
334
 
335
#
336
#   If the view currently exists then it will be deleted if allowed
337
#
338
delete_view()
339
    unless ( $opt_reuse || $opt_extract_files );
340
 
341
#
342
#   If the user is simply deleting the view then all has been done
343
#
344
exit 0
345
    if ( $opt_delete );
346
 
347
#
348
#   If the user has specified a "source path", then we can extract the VOB
349
#   from that path. It will be the first directory
350
#
351
Verbose("Locate Source VOB");
352
if ( $opt_path )
353
{
354
    $opt_path =~ tr~\\/~/~s;
243 dpurdie 355
    $opt_path =~ s~/+$~~;
227 dpurdie 356
 
357
    Error( "Source Path needs leading '/'") unless ( $opt_path =~ m~^/~ );
358
    Error( "Source Path is a UNC" ) if ( $opt_path =~ m~^//~ );
359
    Error( "Source Path has drive specifier" ) if ( $opt_path =~ m~^[A-Za-z]\:~ );
360
 
361
    #
362
    #   Extract the VOB from the path
363
    #
364
    unless ( $opt_vob )
365
    {
366
        my $vob = $opt_path;
367
        $vob =~ s~^/~~g;
368
        $vob =~ s~/.*~~g;
369
 
370
        $opt_vob = $vob;
371
        Verbose ("Extract VOB from path: $vob" );
372
    }
373
}
374
 
375
#
376
#   Setup user specified VOB
377
#
378
if ( defined($opt_vob) )
379
{
380
    $ROOT_VOB = "/$opt_vob";
381
    $ROOT_VOB =~ s~//~/~g;
382
    @ROOT_VOBS = $ROOT_VOB;
383
}
384
else
385
{
386
    #
387
    #   Extend the list of ROOT_VOBS with all the known vobs
388
    #   The initial ROOT_VOBS are treated as a "hint" to assist searching
389
    #
243 dpurdie 390
        my $cmd = ClearToolCmd ('lsvob', '-short');
227 dpurdie 391
        open(CMD, "$cmd 2>&1 |") || Error( "can't run command: $!");
392
        while (<CMD>)
393
        {
394
            #
395
            #   Filter output from the user
396
            #
397
            chomp;
398
            s~^$UNIX_VOB_PREFIX~~ if ($UNIX);
399
            Verbose2("lsvob: $_");
400
            tr~\\/~/~s;
401
            push @ROOT_VOBS, $_;
402
        }
403
        close(CMD);
404
}
405
 
406
#
407
#   Ensure that the label is present within the specified VOB
408
#   Hunt for the user specified label in a number of well known VOBs
409
#
410
if ( @opt_spec )
411
{
412
    Verbose("Ensure Label is found in a VOB");
413
    my $found = 0;
414
    my $spec = $opt_spec[0];
415
    foreach my $vob ( @ROOT_VOBS )
416
    {
417
        $vob = $UNIX_VOB_PREFIX . $vob if ( $UNIX );
418
        (my $vob_name = $vob) =~ s~/~$VOB_SEP~g;
419
 
420
        Verbose2 ("Examine label $spec in vob: $vob" );
421
 
243 dpurdie 422
        my $cmd = ClearToolCmd ('lstype', "lbtype:$spec\@$vob_name");
245 dpurdie 423
        my $cmd_done = 0;
227 dpurdie 424
        open(CMD, "$cmd 2>&1 |") || Error( "can't run command: $!");
425
        while (<CMD>)
426
        {
427
            #
428
            #   Filter output from the user
245 dpurdie 429
            #   Stay in loop to avoid Broken Pipe message
227 dpurdie 430
            #
431
            chomp;
432
            Verbose2("lstype: $_");
245 dpurdie 433
            next if ( $cmd_done );
227 dpurdie 434
            next if ( m~Error~ );
435
            next unless ( m~label type~ );
436
            push @label_not_locked, $spec unless( m~\(locked\)~ );
437
            $label_count++;
438
            $found = $vob;
245 dpurdie 439
            $cmd_done = 1;
227 dpurdie 440
        }
441
        close(CMD);
442
        last if ( $found );
443
    }
444
 
445
    Error ("Label $spec not found in @ROOT_VOBS")
446
        unless ( $found );
447
    Verbose ("Label $spec found in vob: $found" );
448
 
449
    $ROOT_VOB = $found;
450
 
451
    #
452
    #   Create a VOB spec extension
453
    #
454
    $root_vob_spec = '@' . $ROOT_VOB;
455
    $root_vob_spec =~ s~/~$VOB_SEP~g;
456
 
457
    #
458
    #   Ensure that all labels are found in the VOB
459
    #
460
    foreach my $spec ( @opt_spec[1..$#opt_spec] )
461
    {
462
        $label_count++;
463
        Verbose ("Testing label $spec in vob: $ROOT_VOB" );
464
        my $data = qx( cleartool lstype lbtype:$spec$root_vob_spec );
465
        Verbose ( "lstype: $data" );
466
        Error ("Label $spec not found in $ROOT_VOB. All labels must be in the same VOB")
467
            if ( ! $data );
468
        push @label_not_locked, $spec unless( $data =~ m~\(locked\)~ );
469
    }
470
 
471
    #
472
    #   Ensure that the branch is found in the VOB
473
    #
474
    if ( $opt_branch )
475
    {
476
            Verbose ("Testing branch $opt_branch in vob: $ROOT_VOB" );
477
            my $data = qx( cleartool lstype brtype:$opt_branch$root_vob_spec );
478
            Verbose ( "lstype: $data" );
479
            Error ("Branch $opt_branch not found in $ROOT_VOB.")
480
                if ( ! $data );
481
    }
482
 
483
    #
484
    #   Lock the label(s)
485
    #
486
    if ( $opt_lock )
487
    {
488
        my @still_not_locked;
489
        Message( "Locking labels" );
490
        foreach my $spec ( @label_not_locked )
491
        {
492
            Verbose ("Locking $spec");
493
            push @label_locked, $spec;
243 dpurdie 494
            ClearCmd ('lock', "lbtype:$spec$root_vob_spec" );
227 dpurdie 495
            push @still_not_locked, $spec if ( @error_list );
496
        }
497
        @label_not_locked = @still_not_locked;
498
 
499
        #
500
        #   Register function to unlock all the locked lables on failure
501
        #
502
        ErrorConfig ('on_exit' => \&unlock_on_error );
503
        Error ("Not all labels locked: @label_not_locked") if ( @label_not_locked  );
504
    }
505
}
506
 
507
#
508
#   If we are only extracting files then ...
509
#
510
if ( $opt_extract_files )
511
{
512
    extract_files_from_view();
513
    exit (0);
514
}
515
 
516
#
517
#   Create a new (static) view
518
#   Create a config spec and populate the view
519
#
520
if (! -d $VIEWDIR || ! $opt_reuse )
521
{
522
    Message( "Create the view" . ($GBE_SANDBOX ? " in a SANDBOX" : ""));
523
 
524
    #
525
    #   Tried creating a co-located view under Windows, but had problems
526
    #       1) Did not work on WindowsServer based build machine ??
527
    #       2) Deleting the view could be a problem if the user had
528
    #          files open in the view.
529
    #       3) Documentation doesn't really like the use of -colocated
530
    #
531
 
243 dpurdie 532
    ClearTool( 'mkview', '-snapshot', '-tag', $VIEWTAG, $VIEWDIR);
227 dpurdie 533
    Error ("Cannot locate the created static view")
534
        unless ( -d $VIEWDIR );
535
 
536
    #   In order to operate in this view (ie set the config spec, we need to
537
    #   be in the directory of the view
538
    #
539
    chdir ($VIEWDIR) or Error( "Cannot chdir to $VIEWDIR");
540
 
541
    #
542
    #   Create a local package archive
543
    #   May be needed for multipackage builds and it will prevent JATS from
544
    #   finding any outside the view
545
    #
546
    mkdir ( 'local_dpkg_archive')
547
        unless ($GBE_SANDBOX);
548
 
549
    my $config_file = $opt_config_spec;
550
    unless ( $config_file )
551
    {
552
        $config_file = create_config_spec ('config_spec.txt');
553
    }
554
 
555
    Message( "Populating the view");
243 dpurdie 556
    ClearTool( 'setcs', '-tag', $VIEWTAG, $config_file );
227 dpurdie 557
}
558
 
559
#
560
#   Locate the JATS build files within the populated view
561
#
562
chdir ($VIEWDIR) or Error( "Cannot chdir to $VIEWDIR");
563
Message( "Locating build files");
564
 
245 dpurdie 565
my $bscanner = BuildFileScanner( "$VIEWDIR$ROOT_VOB", 'build.pl', '--LocateAll' );
566
$bscanner->scan();
567
my @build_list = $bscanner->getInfo();
568
foreach my $be ( @build_list )
227 dpurdie 569
{
245 dpurdie 570
    Message( DisplayPath ("Build file: $be->{dir} Name: $be->{file}"));
227 dpurdie 571
}
572
 
573
#
574
#   If we are extracting the view then we are done
575
#   Display useful information for the user
576
#
577
if ( $opt_extract )
578
{
579
    Message  DisplayPath "View in: $VIEWDIR";
580
    Warning ("No build files found" )   if ( $#build_list < 0 );
581
    Warning( "Multiple build files found" )if ( $#build_list > 0 );
582
    Message ("Not all labels are locked") if ( @label_not_locked  );
583
    Message ("All labels are locked") unless ( @label_not_locked  );
584
    Message ("Development Sandbox") if ( $GBE_SANDBOX );
585
 
586
    exit 0;
587
}
588
 
589
Error ("No build files found")  if ( $#build_list < 0 );
590
 
591
#
592
#   Determine the list of builds to perform
593
#   Ensure that the user-requested build files are present
594
#
245 dpurdie 595
#   The user specifies the build file, via the mangled package name
596
#   This is package_name . project extension (daf_utils.cr)
597
#
227 dpurdie 598
if ( $#opt_build  >= 0)
599
{
600
    Verbose( "Check and locate the build files");
245 dpurdie 601
    my @build_list = ();
227 dpurdie 602
    foreach my $bentry ( @opt_build )
603
    {
245 dpurdie 604
        if ($bscanner->match( $bentry) )
227 dpurdie 605
        {
245 dpurdie 606
            UniquePush (\@build_list, $bscanner->getMatchList() );
607
            Verbose ("Found: $bentry");
227 dpurdie 608
        }
245 dpurdie 609
        else
610
        {
611
            Error ("Cannot locate requested build files for: $bentry")
612
        }
227 dpurdie 613
    }
614
}
615
 
616
#
617
#   Sanity test if we will transfer the generated package to dpkg_archive
618
#   There are some limits
619
#       1) Must have built from one label
620
#       2) That label must be locked
621
#       3) Only one build file
622
#       4) The view must not have been reused
623
#       5) The view has a branch rule
624
#       6) Building from a config spec
625
#       7) Cannot release from a sandbox
626
#
627
my @elist;
628
push @elist, "Package built from multiple labels" unless ( $label_count == 1 || $opt_config_spec );
629
push @elist, "Package built from an unlocked label" if ( @label_not_locked  );
630
push @elist, "Package built with multiple build files" if ( scalar @build_list > 1 );
631
push @elist, "Package from a reused view" if ( $opt_reuse && ! $opt_beta );
632
push @elist, "Package from a development sandbox" if ( $GBE_SANDBOX );
633
push @elist, "View contains a branch" if ( $opt_branch );
634
push @elist, "Package based on a config spec" if ( $opt_config_spec );
635
push @elist, "User has specified build files" if ( $#opt_build > 0 );
636
 
637
if ( @elist )
638
{
639
    Warning ("Cannot officially release the package.", @elist);
640
    Error ("Build terminated as it cannot be released") if ($opt_dpkg && ! $opt_beta);
641
}
642
Warning ("Beta Release") if $opt_beta;
643
 
644
#
645
#   Process each of the build files in the specified order
646
#
245 dpurdie 647
foreach my $be (@build_list)
227 dpurdie 648
{
649
 
650
    #
651
    #   We need to change to the build directory
652
    #   Moreover we need the local name of the build directory.
653
    #   Windows does not handle a UNC pathname to well (at all)
654
    #
245 dpurdie 655
    my $build_dir = $be->{dir};
227 dpurdie 656
    chdir ("$build_dir") or Error( "Cannot chdir to build directory: $build_dir");
657
 
245 dpurdie 658
    if ( $be->{file} =~ m/^build.pl$/ )
227 dpurdie 659
    {
660
        Message ("Using JATS: $build_dir");
661
        #
662
        #   Invoke JATS to build the package and make the package
663
        #
664
        my $build_args = "--expert --cache";
665
        $build_args .= $opt_cache ? " --cache" : "";
666
 
667
        my $make_type = 'all';
668
        $make_type = 'all_prod'  if ( $opt_prod_build );
669
        $make_type = 'all_debug' if ( $opt_debug_build );
670
 
671
 
672
        JatsCmd("build $build_args")            and Error("Package did not build");
673
        JatsCmd("make $make_type NODEPEND=1")   and Error("Package did not make");
674
        JatsCmd("install");
675
 
676
        if ( $opt_runtests )
677
        {
678
            JatsCmd("make run_unit_tests")      and Error("Tests did not run corectly");
679
        }
680
    }
681
    else
682
    {
683
        #
684
        #   Ant build files
685
        #
245 dpurdie 686
        my $pname =  $be->{file};
227 dpurdie 687
        Message ("Using ANT: $build_dir, $pname");
688
        $pname =~ s~depends.xml$~.xml~;
245 dpurdie 689
        copy($be->{file}, "auto.xml");
227 dpurdie 690
        JatsCmd("-buildfile $pname ant build")        and Error("Package did not build");
691
        JatsCmd("-buildfile $pname ant make_package") and Error("Package did not make_package");
692
    }
693
}
694
 
695
#
696
#   Copy the generated packages
697
#       1) dpkg_archive
698
#       2) Users local directory
699
#
245 dpurdie 700
foreach my $be (@build_list)
227 dpurdie 701
{
245 dpurdie 702
    my $build_dir = $be->{dir};
227 dpurdie 703
    chdir ("$build_dir") or Error( "Cannot chdir to build directory: $build_dir");
704
    if ( $opt_dpkg )
705
    {
706
        Message ("Using: $build_dir");
707
        my $create_opts = "-o";
708
        $create_opts .= " -m" if ( $opt_merge );
247 dpurdie 709
        JatsCmd("-here create_dpkg $create_opts -pname=$be->{name} -pversion=$be->{version}") and $error++;
227 dpurdie 710
    }
711
 
712
    if ( $opt_copy )
713
    {
714
        Message ("Copy package to $user_cwd");
715
        copy_directory( 'pkg', $user_cwd, '' );
716
    }
717
 
718
    #
719
    #   Test structure of the package
720
    #   Ensure that it has a descpkg file
245 dpurdie 721
    #   Validate the package name and version
227 dpurdie 722
    #   More important for ANT projects than JATS as JATS has a sanity test
723
    #
724
    if ( $opt_test )
725
    {
245 dpurdie 726
        JatsCmd("-here create_dpkg -test -pname=$be->{name} -pversion=$be->{version}") and $error++;
227 dpurdie 727
    }
728
 
729
}
730
Error ("Package not transferred")
731
    if ( $error );
732
 
733
 
734
#
735
#   Delete the view
736
#
737
if ( ! $opt_reuse && ! $error && ! $opt_keep )
738
{
739
    delete_view();
740
}
741
else
742
{
743
    Message( "View left in: $VIEWDIR" );
744
}
745
 
746
Message ("End program");
747
exit 0;
748
 
749
#-------------------------------------------------------------------------------
750
# Function        : delete_view
751
#
752
# Description     : Delete a view
753
#
754
# Inputs          : None
755
#                   $VIEWTAG - name of the view
756
#                   $VIEWDIR - path of the view
757
#
758
# Returns         :
759
#
760
sub delete_view
761
{
762
    my $cofound = 0;
763
    my $uuid;
764
 
765
    #
766
    #   If the view physically exists then attempt to phyically remove it
767
    #
768
    if ( -d $VIEWDIR )
769
    {
770
        #
771
        #   Determine if there are any checked out files in the view
772
        #
773
        Message("Remove the view: $VIEWTAG");
774
        Verbose("Look for checked out files");
775
 
776
        chdir ( $VIEWDIR );
777
        foreach my $file ( glob ('*') )
778
        {
779
            next if ( $file =~ m~local_dpkg_archive~ );
780
            next if ( $file =~ m~^view\.~ );
781
            if ( -d $file )
782
            {
783
                Verbose ("Examine $file for checked out files");
784
                chdir "$VIEWDIR/$file";
785
 
243 dpurdie 786
                my $cmd = ClearToolCmd('lsco', '-cview', '-rec' );
227 dpurdie 787
                open(CMD, "$cmd 2>&1 |") || Error( "can't run command: $!");
788
                while (<CMD>)
789
                {
790
                    #
791
                    #   Filter output from the user
792
                    #
793
                    chomp;
794
                    Verbose("lsco: $_");
795
                    if ( m~checkout version~ )
796
                    {
797
                        $cofound++ ;
798
                        Warning ("Checked out file: $_");
799
                    }
800
                }
801
                close(CMD);
802
            }
803
        }
804
 
805
        Error ("Will not delete view. Checked out files exist")
806
            if ( $cofound );
807
 
808
        #
809
        #   Get out of the view
810
        #   Cannot delete the view if we are in it.
811
        #
812
        chdir ( $user_cwd );
813
 
814
        #
815
        #   Static views should be removed by dirname, not by tag
816
        #
243 dpurdie 817
        ClearTool( 'rmview', $VIEWDIR );
227 dpurdie 818
 
819
        #
820
        #   Now try to delete the directory
821
        #
822
        rmtree( $VIEWDIR );
823
    }
824
 
825
    #
826
    #   If the view tag still exists then delete the view the hard way
827
    #   Use 'lsview' to locate the views uuid
828
    #
829
    Verbose("Look for View Tag");
243 dpurdie 830
    my $cmd = ClearToolCmd ('lsview', '-long', $VIEWTAG );
227 dpurdie 831
    open(CMD, "$cmd 2>&1 |") || Error( "can't run command: $!");
832
    while (<CMD>)
833
    {
834
        #
835
        #   Filter output from the user
836
        #
837
        chomp;
838
        Verbose("lsview: $_");
839
        $uuid = $1 if ( m~^View uuid:\s+(.*)~ );
840
    }
841
    close(CMD);
842
 
843
    if ( $uuid )
844
    {
845
        Warning ("Deleting view - the hard way");
243 dpurdie 846
        ClearTool( '--Quiet', 'rmview', '-force', '-all', '-uuid', $uuid );
847
        ClearTool( '--Quiet', 'unregister', '-view', '-uuid', $uuid );
848
        ClearTool( '--Quiet', 'rmtag','-view', '-all', $VIEWTAG );
227 dpurdie 849
    }
850
 
851
 
852
    Error ("View was not deleted")
853
        if ( -d $VIEWDIR );
854
}
855
 
856
#-------------------------------------------------------------------------------
857
# Function        : copy_directory
858
#
859
# Description     : Copy a directory tree
860
#
861
# Inputs          : Source directory
862
#                   Target directory
863
#                   Strip
864
#
865
#                   Should be full pathnames
866
#
867
# Returns         :
868
#
869
my $copy_error;
870
my $copy_count;
871
sub copy_directory
872
{
873
    our ($src_dir, $dest_dir, $strip) = @_;
874
    our $slength = length ($strip);
875
 
876
    #
877
    #   Prevent File::Find from generating warnings
878
    #
879
    no warnings 'File::Find';
880
 
881
 
882
    #
883
    #   Helper routine to copy files
884
    #
885
    sub copy_file_wanted
886
    {
887
        #
888
        #   Do not copy directories
239 dpurdie 889
        #   Just make the directory entry. May result in empty directories
227 dpurdie 890
        #
239 dpurdie 891
        if ( -d $_ )
892
        {
893
            my $tdir = "$dest_dir/" . substr( $File::Find::dir, $slength);
894
            $tdir .= "/$_";
895
            File::Path::mkpath( $tdir )
896
                unless ( -d $tdir);
897
            return;
898
        }
227 dpurdie 899
 
900
        #
901
        #   When used to copy file from within a clearcase dynamic view the
902
        #   files may not actually exist. This will generate an error later
903
        #   so check for existance of file file now.
904
        #
905
        return unless ( -e $_ );
906
 
907
        #
908
        #   Have been chdir'ed to the source directory
909
        #   when invoked
910
        #
911
        my $tdir = "$dest_dir/" . substr( $File::Find::dir, $slength);
912
        my $tfile = "$tdir/$_";
913
        my $sfile = "$File::Find::dir/$_";
914
        Verbose ("Copy: $sfile -> $tfile");
915
 
916
        File::Path::mkpath( $tdir )
917
            unless ( -d $tdir);
918
 
919
        unlink ( $tfile )
920
            if ( -f $tfile );
921
 
922
        if( ! File::Copy::copy ( $_ , $tfile ) )
923
        {
924
            $copy_error++;
925
            Message "Error copying $sfile";
926
        }
927
        else
928
        {
239 dpurdie 929
            my $perm = (stat $_)[2] & 07777;
930
            chmod($perm, $tfile);
931
 
227 dpurdie 932
            $copy_count++;
933
        }
934
    }
935
 
936
    #
937
    #   Locate all files to copy
938
    #
939
    $copy_error = 0;
940
    $copy_count = 0;
941
    File::Find::find ( \&copy_file_wanted, $src_dir );
942
    return $copy_error;
943
}
944
 
945
#-------------------------------------------------------------------------------
946
# Function        : ClearTool
947
#
948
# Description     : Issue a cleartool command
949
#                   Filter out many of the stupid messages
950
#
951
# Inputs          : Options and Command line
952
#                   Options:
953
#                       --Quiet     - Supress all command output
954
#
955
# Returns         : Error code
956
#
957
sub ClearTool
958
{
959
    my $quiet;
960
 
961
    #
962
    #   Scan for initial options
963
    #       --Quiet
964
    #
965
    if ( $_[0] eq '--Quiet' )
966
    {
967
        $quiet = 1;
968
        shift;
969
    }
970
 
243 dpurdie 971
    my $cmd = ClearToolCmd(@_);
227 dpurdie 972
    open(CMD, "$cmd 2>&1 |") || Error "can't run command: $!";
973
    while (<CMD>)
974
    {
975
        #
976
        #   Filter output from the user
977
        #
978
        next if ( $quiet );
979
        unless ( $opt_verbose )
980
        {
981
            next if ( m~Making dir~ );
982
            next if ( m~End dir~ );
983
            next if ( m~Processing dir~ );
984
            next if ( m~Error~ );
985
        }
986
        print $_;
987
    }
988
    close(CMD);
989
 
990
    Verbose2 "ClearTool Exit Status: $?";
991
    return $? / 256;
992
}
993
 
994
#-------------------------------------------------------------------------------
995
# Function        : ClearCmd
996
#
997
# Description     : Execute a cleartool command
998
#                   Capture error messages only
999
#
1000
# Inputs          : Command to execute
243 dpurdie 1001
#                   Takes an array of command argumeents and will quote them
227 dpurdie 1002
#
1003
# Returns         : Exit code
1004
#                   Also the global @error_list
1005
#
1006
sub ClearCmd
1007
{
243 dpurdie 1008
    @error_list = ();
227 dpurdie 1009
 
243 dpurdie 1010
    my $cmd = ClearToolCmd(@_);
1011
    open(CMD, "$cmd  2>&1 |")    || Error "can't run command: $!";
1012
    while (<CMD>)
1013
    {
1014
        chomp;
1015
        Verbose ($_);
1016
        push @error_list, $_ if ( m~Error:~ );
1017
    }
1018
    close(CMD);
227 dpurdie 1019
 
1020
    Verbose2 "Exit Status: $?";
1021
    return $? / 256;
1022
}
1023
 
1024
#-------------------------------------------------------------------------------
243 dpurdie 1025
# Function        : ClearToolCmd
1026
#
1027
# Description     : Create a nice escaped cleartool command
1028
#
1029
# Inputs          : An array of cleartool command line arguments
1030
#
1031
# Returns         : A string that has been quoted
1032
#
1033
sub ClearToolCmd
1034
{
1035
    my $cmd = 'cleartool ' . QuoteCommand( @_);
1036
    Verbose2 $cmd;
1037
    return $cmd;
1038
}
1039
 
1040
#-------------------------------------------------------------------------------
227 dpurdie 1041
# Function        : unlock_on_error
1042
#
1043
# Description     : Error cleanup function.
1044
#                   Called by the error processing
1045
#                   Called to unlock all labels that have been locked by this
1046
#                   utility
1047
#
1048
# Inputs          : @label_locked           - Labels locked by this utility (Global)
1049
#
1050
# Returns         : 
1051
#
1052
sub unlock_on_error
1053
{
1054
    my @still_locked;
1055
    Message( "Releasing Locked labels" );
1056
    foreach my $spec ( @label_locked )
1057
    {
1058
        Verbose ("Unlocking:$spec");
243 dpurdie 1059
        ClearCmd ('unlock', "lbtype:$spec$root_vob_spec" );
227 dpurdie 1060
        push @still_locked, $spec if ( @error_list );
1061
    }
1062
    Error ("Not all labels unlocked: @still_locked") if ( @still_locked  );
1063
}
1064
 
1065
#-------------------------------------------------------------------------------
1066
# Function        : extract_files_from_view
1067
#
1068
# Description     : This function will
1069
#                       Create a dynamic view
1070
#                       Copy all the files out of the view
1071
#                       Delete the view
1072
#
1073
#                   Its used in the creation of escrow directories
1074
#
1075
# Inputs          : None
1076
#                   All done via globals
1077
#
1078
# Returns         : 
1079
#
1080
sub extract_files_from_view
1081
{
241 dpurdie 1082
    my $vob_mounted = 1;
1083
    my $vob_name;
1084
 
227 dpurdie 1085
    #
1086
    #   Determine the target directory for the extracted files
1087
    #       Delete the output subdir
1088
    #       Create the config spec in that directory
1089
    #
1090
    Verbose("Extracting files into $VIEWDIR");
1091
    if ( -d $VIEWDIR )
1092
    {
1093
        Verbose "Delete Directory: $VIEWDIR\n";
1094
        rmtree( $VIEWDIR );
1095
    }
1096
 
1097
    #
1098
    #   Which config spec
1099
    #   If we need to create it, do it within the final view
1100
    #
1101
    my $config;
1102
    $config = $opt_config_spec;
1103
    unless ( $opt_config_spec )
1104
    {
1105
        File::Path::mkpath( $VIEWDIR );
1106
        $config = create_config_spec( "$VIEWDIR/config_spec.txt" );
1107
    }
1108
 
1109
    #
1110
    #   Create the view and insert the config spec
1111
    #
243 dpurdie 1112
    ClearCmd ( 'rmview', '-tag', $VIEWTAG );
1113
    ClearCmd ( 'mkview', '-tag', $VIEWTAG, '-stgloc', '-auto' );
1114
    ClearCmd ( 'setcs',  '-tag', $VIEWTAG, $config );
227 dpurdie 1115
 
1116
    #
241 dpurdie 1117
    #   Ensure that the base VOB has been 'mounted'
1118
    #   Dynamic views require vobs to be mounted
1119
    #
1120
    ($vob_name = $ROOT_VOB) =~ s~/~$VOB_SEP~g;
243 dpurdie 1121
    $vob_mounted = ClearCmd ('mount', $vob_name);
241 dpurdie 1122
 
1123
    #
227 dpurdie 1124
    #   Calculate where the dynmaic view will be
1125
    #   This differ between UNIX/WINDOWS
1126
    #
1127
    my $vpath = $VIEW_PREFIX . $VIEWTAG . $VOB_PREFIX;
1128
    my $cpath = $vpath;
1129
       $cpath .= $opt_path if ( $opt_path );
1130
    #
1131
    #   Is the view where we expect it to be
1132
    #
1133
    Error ("Cannot locate dynamic view",
1134
            "Looking in: $vpath" ) unless -d $vpath;
1135
 
1136
    #
1137
    #   Copy all the files out of the view
1138
    #
1139
    Verbose ("Copy View contents");
1140
    my $rv = copy_directory ($cpath, $VIEWDIR, $vpath );
1141
    Message ("View files in: $VIEWDIR, Files: $copy_count" );
241 dpurdie 1142
 
227 dpurdie 1143
    #
1144
    #   Remove the view
1145
    #
243 dpurdie 1146
    ClearCmd ( 'rmview', '-tag', $VIEWTAG );
227 dpurdie 1147
 
241 dpurdie 1148
    #
1149
    #   Unmount the vob - if mounted
1150
    #
243 dpurdie 1151
    ClearCmd ('umount', $vob_name) unless $vob_mounted;
241 dpurdie 1152
 
227 dpurdie 1153
    Error ("Copy did not complete without error")
1154
        if ( $rv );
1155
 
1156
}
1157
 
1158
#-------------------------------------------------------------------------------
1159
# Function        : create_config_spec
1160
#
1161
# Description     : Creates a config spec
1162
#
1163
# Inputs          : $config     - Path to the config file
1164
#
1165
# Returns         : Path to the config spec
1166
#
1167
sub create_config_spec
1168
{
1169
    my ($config_file) = @_;
1170
    #
1171
    #   Create a config spec to be used to populate the view
1172
    #       Do not branch directories
1173
    #       Do not extract files from lost+found
1174
    #
1175
    Verbose( "Create config spec");
1176
    open (CFG, ">$config_file") or Error ("Cannot create config spec");
1177
    print CFG "element * CHECKEDOUT\n";
1178
    print CFG "element .../lost+found -none\n";
1179
    print CFG "element * .../$opt_branch/LATEST\n" if $opt_branch;
1180
    foreach (@opt_spec)
1181
    {
1182
        print CFG "element * $_";
1183
        print CFG " -mkbranch $opt_branch" if $opt_branch;
1184
        print CFG "\n";
1185
 
1186
    }
1187
 
1188
    #
1189
    #   Packages SHOULD be labled to the root.
1190
    #   Do not extend this list fix the package - fix the labels in the VOB.
1191
    #
1192
    if ( $opt_latest_root )
1193
    {
1194
        print CFG "element -directory $ROOT_VOB .../$opt_latest_root/LATEST\n";
1195
        print CFG "element -directory $ROOT_VOB .../mass_dev/LATEST\n";
1196
        print CFG "element -directory $ROOT_VOB /main/LATEST\n";
1197
    }
1198
 
1199
    #
1200
    #   Do not branch directories above the load path
1201
    #   Load only the version on /main
1202
    #       UNIX: Don't play with the /vobs (won't work)
1203
    #
1204
    if ( $opt_branch )
1205
    {
1206
        if ( $opt_path )
1207
        {
1208
            my $fulldir = $VOB_PREFIX;
1209
            my @parts = split ('/', $opt_path);
1210
            shift @parts;
1211
            foreach my $dir ( @parts )
1212
            {
1213
                $fulldir .= "/$dir";
1214
                print CFG "element -dir $fulldir /main/LATEST\n"
1215
            }
1216
        }
1217
        else
1218
        {
1219
            print CFG "element -dir $ROOT_VOB /main/LATEST\n";
1220
        }
1221
    }
1222
 
1223
    #
1224
    #   Branch rule:
1225
    #   Need /main/0 to allow files to be added to the view
1226
    #   Will get a lot of stuff, so take care not to label it all
1227
    #
1228
    print CFG "element * /main/0 -mkbranch $opt_branch\n" if $opt_branch;
1229
 
1230
    #
1231
    #   Load rule
1232
    #   Use ROOT_VOB, unless the user has specified a path
235 dpurdie 1233
    #   Quote the path so that spaces will be correcly handled
227 dpurdie 1234
    #
1235
    print CFG "load $ROOT_VOB\n" unless $opt_path;
235 dpurdie 1236
    print CFG "load \"$VOB_PREFIX$opt_path\"\n" if $opt_path;
227 dpurdie 1237
    close CFG;
1238
 
1239
    return $config_file;
1240
}
1241
 
1242
#-------------------------------------------------------------------------------
1243
#   Documentation
1244
#
1245
 
1246
=pod
1247
 
1248
=head1 NAME
1249
 
1250
jats_cbuilder - Build a package given a clearcase label
1251
 
1252
=head1 SYNOPSIS
1253
 
1254
  jats cbuilder [options] [-label=]label | -config=config_spec
1255
 
1256
 Options:
1257
    -help              - brief help message
1258
    -help -help        - Detailed help message
1259
    -man               - Full documentation
1260
    -label=xxx         - Clearcase label
1261
    -spec=xxx          - Same as -label=xxx
1262
    -path=xxx          - Source Path
1263
    -view=xxx          - Modify the name of the created view
1264
    -vob=vobname       - VOB name
245 dpurdie 1265
    -build=xxx         - Package Name to build
227 dpurdie 1266
    -root=xxx          - Root directory for generated view
1267
    -latestroot=xxx    - Use the LATEST rootlevel directory 'xxx'
1268
    -[mk]branch=xxx    - Will create a view with a branch rule
1269
    -config=xxx        - Create a view with the provided config spec
1270
    -tag=xxx           - Alternate tag used with in the ViewTag
1271
    -extract           - Extract the view and exit
1272
    -extractfiles      - Extract files, without a view
1273
    -cache             - Refresh local dpkg_archive cache
1274
    -delete            - Remove any existing view and exit
1275
    -debugOnly         - Make only the debug version
1276
    -prodOnly          - Make only the production version
1277
    -[no]dpkg          - Transfer package into dpkg_archive
1278
    -[no]copy          - Transfer pkg directory to the current user directory
1279
    -[no]reuse         - Reuse the view
1280
    -[no]test          - Test package build. Implies nocopy and nodpkg
1281
    -[no]keep          - Keep the view after the build
1282
    -[no]lock          - Lock labels
1283
    -[no]beta          - Release a beta package
1284
    -[no]merge         - Merge packages into dpkg_archive
1285
    -[no]runtests      - Run units tests. Default is runtests
1286
    -[no]prefix        - Supress user prefix in view name. Default prefix is USER
1287
 
1288
=head1 OPTIONS
1289
 
1290
=over 8
1291
 
1292
=item B<-help>
1293
 
1294
Print a brief help message and exits.
1295
 
1296
=item B<-help -help>
1297
 
1298
Print a detailed help message with an explanation for each option.
1299
 
1300
=item B<-man>
1301
 
1302
Prints the manual page and exits.
1303
 
1304
=item B<-label> or B<-spec>
1305
 
1306
The ClearCase label to use as the base for the view.
1307
 
1308
Eg: daf_utils_math_3.2.1
1309
 
1310
=item B<-view name>
1311
 
1312
Specified an alternate view name and tag to be used. This option does not provide the
1313
full name of the view.
1314
 
1315
    The view tag will be : "${USER}_${MACHINENAME}_${TAG}_${NAME}"
1316
    The view path will be: "${USER}_${NAME}"
1317
 
1318
The default "NAME" is the first label specified.
1319
The default "TAG" is build. See B<-tag=tagname>.
1320
 
1321
If the user provides a view "name" that is prefixed with their user name
1322
('${USER}_'), then the username will be stripped of for internal processing.
1323
This allows a user to provide a view path when deleting a view.
1324
 
1325
=item B<-path=xxx>
1326
 
1327
Specifies the source path to the root of the extracted file tree. This option has several uses:
1328
 
1329
=over 8
1330
 
1331
=item   *
1332
 
1333
Provide a sanity test of the "Source Path" item within Release Manager
1334
 
1335
=item   *
1336
 
1337
Specify the VOB that contains the source. The VOB name will be extracted and
1338
used as the B<-vob> parameter.
1339
 
1340
=item   *
1341
 
1342
Limit the work to do in extracting the file tree.
1343
 
1344
=back
1345
 
1346
=item B<-vob=xxx>
1347
 
1348
Specifies the Clearcase VOB in which the clearcase label will be located.
1349
This is used as the basis for locating and loading the files within the view.
1350
 
1351
By default this utility will examine all the VOBs for the label.
1352
 
1353
=item B<-build=xxx>
1354
 
245 dpurdie 1355
This option allows the user to specify the packages to be built and the
1356
order in which the packages are to be built.
227 dpurdie 1357
This is useful if the extracted view contains multiple build files
1358
 
245 dpurdie 1359
This option may be used multiple times.
227 dpurdie 1360
 
245 dpurdie 1361
There are two forms in which the build target can be specified. It can be
1362
specified as a full package name and vesrion, or as a package name and the
1363
project suffix.
1364
 
227 dpurdie 1365
By default the program will assume that there is only one build file in the
245 dpurdie 1366
view and will not build if multiple files are present, unless the package to be
1367
built can be resolved.
227 dpurdie 1368
 
245 dpurdie 1369
The location mechanism operates for both JATS and ANT build files.
227 dpurdie 1370
 
245 dpurdie 1371
Example: -build=jats-api.1.0.0000.cr
227 dpurdie 1372
 
245 dpurdie 1373
This will locate the build file that builds version 1.0.0000.cr of the jats-api
1374
package. The version numbers must match exactly.
227 dpurdie 1375
 
245 dpurdie 1376
Example: -build=jats-api.cr -build=jats-lib.cr
227 dpurdie 1377
 
245 dpurdie 1378
This will located the build files that build the jats_api (cr) package and the
1379
jats-lib (cr) package. The version of the packages will not be considered.
227 dpurdie 1380
 
1381
=item B<-root=xxx>
1382
 
1383
This option allows the location of the generated view to be specified on the
1384
command line. The environment variable GBE_VIEWBASE provides the same feature,
1385
but it will affect all the view created.
1386
 
1387
The default location is:
1388
 
1389
=over 8
1390
 
1391
=item WINDOWS
1392
 
1393
c:\clearcase
1394
 
1395
=item Unix
1396
 
1397
$(HOME)/jats_cbuilder
1398
 
1399
If the comamnd is invoked within a development sandbox, then the default
1400
location will be the root directory of the development sandbox.
1401
 
1402
=back
1403
 
1404
=item B<-latestroot=xxx>
1405
 
1406
This option enables a work around for a bad-labelling practice that has existed
1407
in the past. This LATEST version of the named (xxx) branch will be added to
1408
the config spec used to create the view.
1409
 
1410
This is a work around for a problem where the top-level directory in the VOB has
1411
not been labelled. This can result in unreproducible builds.
1412
 
1413
This option allows the utility to construct a view, but the user SHOULD label
1414
the root level directory to correct the problem.
1415
 
1416
The use of this switch will add the following lines to the config spec:
1417
 
1418
    element -directory /DPG_SWBase /main/xxxx/LATEST
1419
 
1420
=item B<-branch=xxx or -mkbranch=xxx>
1421
 
1422
This option will create a view such that files that are checked out will be
1423
checked out on the named branch. This is intended to facilitate the maintenance
1424
of existing packages - the creation of a patch.
1425
 
1426
The named branch must exist within the VOB containing the label. The script will
1427
check for its existence.
1428
 
1429
The use of this switch will add the following lines to the config spec:
1430
 
1431
    element * .../xxx/LATEST
1432
    element * {label} -mkbranch xxx
1433
    element * /main/0 -mkbranch xxx
1434
 
1435
=item B<-config=config_spec>
1436
 
1437
This option is an alternate mechanism to create a static view. The view will be
1438
based on the provided configuration spec. This view cannot be used to release a package.
1439
The option is intended to simplify development.
1440
 
1441
This option is incompatibale with:
1442
 
1443
    -release
1444
    -label
1445
    -branch
1446
    -path
1447
    -vob
1448
 
1449
 
1450
=item B<-tag=text>
1451
 
1452
This option alters the ClearCase view tag created for the view. It allows
1453
the creation of multiple views based on the same label. Intended to be used in
1454
the automated build system to create unique views tags.
1455
 
1456
The default tag is 'build'.
1457
 
1458
=item B<-extract>
1459
 
1460
With this option the view is created and the left in place. The user may then
1461
access the files within the view. The view should not be used for a
1462
production release.
1463
 
1464
=item B<-extractfiles>
1465
 
1466
With this option the utility will create a dynamic view and transfer files from
1467
the view to the user's tararget. The dynamic view is then removed.
1468
 
1469
This command is intended to simplify the process of creating an escrow.
1470
 
1471
=item B<-cache>
1472
 
1473
Forces external packages to be placed in the local dpkg_archive cache.
1474
 
1475
The normal operation is to copy the packages, only if they do not already exist
1476
in the local cache. This option may be used to ensure that the local copy is
1477
correct and up to date.
1478
 
1479
=item B<-delete>
1480
 
1481
Delete the view used by the program, if it exists. This option may be used to
1482
cleanup after an error.
1483
 
1484
Note: Ensure that no files are open in the view and that the users current
1485
working directory is not in the view as these will prevent the view from being
1486
deleted.
1487
 
1488
 
1489
=item B<-debugOnly>
1490
 
1491
Make only the debug version of the package. The default it to create both the
1492
debug and production version of the package. The type of build may be  further
1493
limited by options within the package.
1494
 
1495
=item B<-prodOnly>
1496
 
1497
Make only the production version of the package. The default it to create both the
1498
debug and production version of the package. The type of build may be  further
1499
limited by options within the package.
1500
 
1501
=item B<-[no]dpkg>
1502
 
1503
Copy the generated package into dpkg_archive. This is the default mode of
1504
operation.
1505
 
1506
=item B<-[no]copy>
1507
 
1508
Copy the built "pkg" directory to the users current directory. The entire
1509
"pkg" subdirectory includes the full package named directory for the package
1510
that has been built.
1511
 
1512
=item B<-[no]reuse>
1513
 
1514
This flag allows the view created by the program to be re-used.
1515
 
1516
=over 8
1517
 
1518
=item 1. The view is not deleted before being populated.
1519
 
1520
=item 2. The view will not be populated if it does exist.
1521
 
1522
=item 3. The view will not be deleted at the end the process.
1523
 
1524
=back
1525
 
1526
This option is useful for debugging a build process.
1527
 
1528
=item B<-[no]test>
1529
 
1530
Test the building of the package. This option implies "nocopy" and "nodpkg".
1531
 
1532
=item B<-[no]keep>
1533
 
1534
Keep the clearcase view after the build. The default option is "nokeep"
1535
 
1536
This option is different to the "reuse" in that the view will be deleted, if
1537
it exists, before the build, but will be retained at the completion of the
1538
process. The user may then manually extract the created package.
1539
 
1540
The view may be deleted with the the "delete" option; taking care to ensure that
1541
no files are open in the view and that the users current working directory is
1542
not in the view.
1543
 
1544
=item B<-[no]lock>
1545
 
1546
Lock any unlocked labels before attempting the build. This operation may be used
1547
to ensure that a release build does not fail due to the labels not being locked.
1548
The label is locked before the view is constructed and populated.
1549
 
1550
This operation may fail if the user does not "own" the label.
1551
 
1552
=item B<-[no]beta>
1553
 
1554
This option overrides many of the package release tests to allow a beta package
1555
to be released.
1556
 
1557
=item B<-[no]merge>
1558
 
1559
This option will merge packages being built on multiple machines into
1560
dpkg_archive. By default, if a package already exists in the archive it will be
1561
deleted and replaced. With this option the package will be merged. The merge
1562
process does not over write files found in the archive.
1563
 
1564
=item B<-[no]runtests>
1565
 
1566
This option will allow the suppression of the running of the unit tests included
1567
with the component. By default the tests are run. This can be suppressed
1568
without affecting the release process.
1569
 
1570
=back
1571
 
1572
=head1 DESCRIPTION
1573
 
1574
This program is the primary tool for the creation, recreation and release of
1575
packages within the B<ERG> build environment, although the program can perform a
1576
number of very useful operations required during normal development and
1577
maintenance.
1578
 
1579
This program will build a system containing one or more inter-related build
1580
files using the JATS build tools.
1581
 
1582
In normal operation the program will:
1583
 
1584
=over 8
1585
 
1586
=item Remove View
1587
 
1588
Remove any existing view of the same name. The view will not be removed if it
1589
contains checked-out files.
1590
 
1591
The view removal may fail if there are any files B<open> within the view or if
1592
any shell has a subdirectory of the view set as a B<current working directory>.
1593
 
1594
=item Locate VOB
1595
 
1596
Locate the VOB that contains the specified label or labels. If multiple labels
1597
are specified they must all exist in the same VOB.
1598
 
1599
=item Lock Labels
1600
 
1601
Lock any unlocked labels, if required.
1602
 
1603
=item Create the view
1604
 
1605
Create a static view to containing the files describes by the Clearcase
1606
label being processed.
1607
 
1608
The program uses a fixed view name. If this view exists then item
1609
will be deleted before item is created again. Each build starts in a clean view.
1610
 
1611
=item Populate the View
1612
 
1613
Loads files into the static view. The user label and the VOB name are used to
1614
created a clearcase configuration specification. This configuration
1615
specification is then activated and all files within the specified VOB will be
1616
loaded into the view if they match the user supplied label.
1617
 
1618
This processed normally results in a lot of error messages that can be ignored.
1619
 
1620
I<Note:> The label placed on the component to be built must extend to the
1621
root of the VOB, otherwise the directory path will not be extracted nor will
1622
the files within the component.
1623
 
1624
I<Note:> If the view is simply being extracted, then this is the end of the
1625
program. The extracted view is left in place.
1626
 
1627
=item Sanity Test
1628
 
1629
If the build is being used as a release into dpkg_archive then
1630
various tests are performed to ensure the repeatability of the view and the
1631
build. These tests include:
1632
 
1633
=over 8
1634
 
1635
=item   * The view must be constructed from one label
1636
 
1637
=item   * That label must be locked
1638
 
1639
=item   * The labelled view must contain exactly one build file
1640
 
1641
=item   * The view cannot have been re-used.
1642
 
1643
=back
1644
 
1645
=item Locate build files
1646
 
1647
Locate the build file within the view.
1648
 
1649
It is an error to have multiple build files within the view, unless the
1650
B<-build> option is used. By default, only one package will be built.
1651
 
1652
=item Package the results
1653
 
1654
Use JATS to build and make the package.
1655
 
1656
The resultant package may be copied to a numbers of locations. These include
1657
 
1658
=over 8
1659
 
1660
=item 1
1661
 
1662
The master dpkg_archive as an official release. This is the default operation.
1663
 
1664
=item 2
1665
 
1666
The users current directory. The package directory from the built package is
1667
copied locally. The "pkg" directory is copied. This is only performed with the
1668
B<-copy> option.
1669
 
1670
=back
1671
 
1672
=item Delete the view
1673
 
1674
Delete the view and all related files.
1675
 
1676
The view will not be deleted if an error was detected in the build process, or
1677
the "reuse" or "keep" options are present.
1678
 
1679
=back
1680
 
1681
=cut
1682