source: devel/pb-modules/lib/ProjectBuilder/VE.pm @ 1519

Revision 1519, 9.8 KB checked in by bruno, 13 months ago (diff)
  • pb.conf: Add support for centos-6: new osrelfile, add initial dependencies, add perl and package dependencies (Eric Anderson)
  • Distribution.pm: Require that we have a functional install command. The old protection code was wrong since without a valid value it defaults to , and if it had been correct would cause installs to silently fail. (Eric Anderson)
  • VE.pm: Run bootstrapping under linux32 (Bruno changed that to setarch) if arch is i386 and host is x86_64/amd64 so that it gets the architecture right. (Eric Anderson)
Line 
1#!/usr/bin/perl -w
2#
3# Common functions for virtual environment
4#
5# $Id$
6#
7
8package ProjectBuilder::VE;
9
10use strict;
11use Data::Dumper;
12use Carp 'confess';
13use English;
14use ProjectBuilder::Version;
15use ProjectBuilder::Base;
16use ProjectBuilder::Conf;
17use ProjectBuilder::Distribution;
18
19# Global vars
20# Inherit from the "Exporter" module which handles exporting functions.
21 
22use vars qw($VERSION $REVISION @ISA @EXPORT);
23use Exporter;
24 
25# Export, by default, all the functions into the namespace of
26# any code which uses this module.
27 
28our @ISA = qw(Exporter);
29our @EXPORT = qw(pb_ve_launch);
30
31($VERSION,$REVISION) = pb_version_init();
32
33=pod
34
35=head1 NAME
36
37ProjectBuilder::VE, part of the project-builder.org - module dealing with Virtual Environment
38
39=head1 DESCRIPTION
40
41This modules provides functions to deal with Virtual Environements (VE), aka chroot.
42
43=head1 SYNOPSIS
44
45  use ProjectBuilder::VE;
46
47  #
48  # Return information on the running distro
49  #
50  my $pbos = pb_ve_launch();
51
52=head1 USAGE
53
54=over 4
55
56=item B<pb_ve_launch>
57
58This function launch a VE, creating it if necessary using multiple external potential tools.
59
60=cut
61
62sub pb_ve_launch {
63
64my $v = shift || undef;
65my $pbforce = shift || 0;               # By default do not rebuild VE
66my $pbsnap = shift || 0;                # By default do not snap VE
67
68# Get distro context
69my $pbos = pb_distro_get_context($v);
70
71# Get VE context
72my ($ptr,$vepath) = pb_conf_get("vetype","vepath");
73my $vetype = $ptr->{$ENV{'PBPROJ'}};
74
75confess "No vetype defined for $ENV{PBPROJ}" unless (defined $vetype);
76pb_log(1, "Using vetype $vetype for $ENV{PBPROJ}\n");
77
78if (($vetype eq "chroot") || ($vetype eq "schroot")) {
79
80        # We need to avoid umask propagation to the VE
81        umask 0022;
82
83        # We can probably only get those params now we have the distro context
84        my ($rbsb4pi,$rbspi,$vesnap,$oscodename,$osmindep,$verebuild,$rbsmirrorsrv) = pb_conf_get_if("rbsb4pi","rbspi","vesnap","oscodename","osmindep","verebuild","rbsmirrorsrv");
85
86        # Architecture consistency
87        my $arch = pb_get_arch();
88        if ($arch ne $pbos->{'arch'}) {
89                die "Unable to launch a VE of architecture $pbos->{'arch'} on a $arch platform" unless (($pbos->{'arch'} =~ /i?86/o) && ($arch eq "x86_64"));
90        }
91
92        # If we are already root (from pbmkbm e.g.) don't use sudo, just call the command
93        my $sudocmd="";
94        $sudocmd ="sudo " if ($EFFECTIVE_USER_ID != 0);
95        # Handle cross arch on Intel based platforms
96        $sudocmd = "setarch i386 $sudocmd" if (($pbos->{arch} =~ /i?86/) && ($arch eq 'x86_64'));
97
98        my $root = pb_path_expand($vepath->{$ENV{PBPROJ}});
99        if (((defined $verebuild) && ($verebuild->{$ENV{'PBPROJ'}} =~ /true/i)) || ($pbforce == 1)) {
100                my ($verpmtype,$vedebtype) = pb_conf_get("verpmtype","vedebtype");
101                my ($rbsopt1) = pb_conf_get_if("rbsopt");
102
103                # We have to rebuild the chroot
104                if ($pbos->{'type'} eq "rpm") {
105       
106                        # Which tool is used
107                        my $verpmstyle = $verpmtype->{$ENV{'PBPROJ'}};
108                        die "No verpmtype defined for $ENV{PBPROJ}" unless (defined $verpmstyle);
109       
110                        # Get potential rbs option
111                        my $rbsopt = "";
112                        if (defined $rbsopt1) {
113                                if (defined $rbsopt1->{$verpmstyle}) {
114                                        $rbsopt = $rbsopt1->{$verpmstyle};
115                                } elsif (defined $rbsopt1->{$ENV{'PBPROJ'}}) {
116                                        $rbsopt = $rbsopt1->{$ENV{'PBPROJ'}};
117                                } else {
118                                        $rbsopt = "";
119                                }
120                        }
121       
122                        my $postinstall = pb_ve_get_postinstall($pbos,$rbspi,$verpmstyle);
123                        if ($verpmstyle eq "rinse") {
124                                # Need to reshape the mirrors generated with local before-post-install script
125                                my $b4post = "--before-post-install ";
126                                my $postparam = pb_distro_get_param($pbos,$rbsb4pi);
127                                if ($postparam eq "") {
128                                        $b4post = "";
129                                } else {
130                                        $b4post .= $postparam;
131                                }
132       
133                                # Need to reshape the package list for pb
134                                my $addpkgs;
135                                $postparam = "";
136                                $postparam .= pb_distro_get_param($pbos,$osmindep);
137                                if ($postparam eq "") {
138                                        $addpkgs = "";
139                                } else {
140                                        my $pkgfile = "$ENV{'PBTMP'}/addpkgs.lis";
141                                        open(PKG,"> $pkgfile") || die "Unable to create $pkgfile";
142                                        foreach my $p (split(/,/,$postparam)) {
143                                                print PKG "$p\n";
144                                        }
145                                        close(PKG);
146                                        $addpkgs = "--add-pkg-list $pkgfile";
147                                }
148       
149                                my $rinseverb = "";
150                                $rinseverb = "--verbose" if ($pbdebug gt 0);
151                                my ($rbsconf) = pb_conf_get("rbsconf");
152       
153                                my $command = pb_check_req("rinse",0);
154                                pb_system("$sudocmd $command --directory \"$root/$pbos->{'name'}/$pbos->{'version'}/$pbos->{'arch'}\" --arch \"$pbos->{'arch'}\" --distribution \"$pbos->{'name'}-$pbos->{'version'}\" --config \"$rbsconf->{$ENV{'PBPROJ'}}\" $b4post $postinstall $rbsopt $addpkgs $rinseverb","Creating the rinse VE for $pbos->{'name'}-$pbos->{'version'} ($pbos->{'arch'})", "verbose");
155                        } elsif ($verpmstyle eq "rpmbootstrap") {
156                                my $rbsverb = "";
157                                foreach my $i (1..$pbdebug) {
158                                        $rbsverb .= " -v";
159                                }
160                                my $addpkgs = "";
161                                my $postparam = "";
162                                $postparam .= pb_distro_get_param($pbos,$osmindep);
163                                if ($postparam eq "") {
164                                        $addpkgs = "";
165                                } else {
166                                        $addpkgs = "-a $postparam";
167                                }
168                                my $command = pb_check_req("rpmbootstrap",0);
169                                pb_system("$sudocmd $command $rbsopt $postinstall $addpkgs $pbos->{'name'}-$pbos->{'version'}-$pbos->{'arch'} $rbsverb","Creating the rpmbootstrap VE for $pbos->{'name'}-$pbos->{'version'} ($pbos->{'arch'})", "verbose");
170                        } elsif ($verpmstyle eq "mock") {
171                                my ($rbsconf) = pb_conf_get("rbsconf");
172                                my $command = pb_check_req("mock",0);
173                                pb_system("$sudocmd $command --init --resultdir=\"/tmp\" --configdir=\"$rbsconf->{$ENV{'PBPROJ'}}\" -r $v $rbsopt","Creating the mock VE for $pbos->{'name'}-$pbos->{'version'} ($pbos->{'arch'})");
174                                # Once setup we need to install some packages, the pb account, ...
175                                pb_system("$sudocmd $command --install --configdir=\"$rbsconf->{$ENV{'PBPROJ'}}\" -r $v su","Configuring the mock VE");
176                        } else {
177                                die "Unknown verpmtype type $verpmstyle. Report to dev team";
178                        }
179                } elsif ($pbos->{'type'} eq "deb") {
180                        my $vedebstyle = $vedebtype->{$ENV{'PBPROJ'}};
181               
182                        my $codename = pb_distro_get_param($pbos,$oscodename);
183                        my $postparam = "";
184                        my $addpkgs;
185                        $postparam .= pb_distro_get_param($pbos,$osmindep);
186                        if ($postparam eq "") {
187                                $addpkgs = "";
188                        } else {
189                                $addpkgs = "--include $postparam";
190                        }
191                        my $debmir = "";
192                        $debmir .= pb_distro_get_param($pbos,$rbsmirrorsrv);
193       
194                        # Get potential rbs option
195                        my $rbsopt = "";
196                        if (defined $rbsopt1) {
197                                if (defined $rbsopt1->{$vedebstyle}) {
198                                        $rbsopt = $rbsopt1->{$vedebstyle};
199                                } elsif (defined $rbsopt1->{$ENV{'PBPROJ'}}) {
200                                        $rbsopt = $rbsopt1->{$ENV{'PBPROJ'}};
201                                } else {
202                                        $rbsopt = "";
203                                }
204                        }
205       
206                        # debootstrap works with amd64 not x86_64
207                        my $debarch = $pbos->{'arch'};
208                        $debarch = "amd64" if ($pbos->{'arch'} eq "x86_64");
209                        if ($vedebstyle eq "debootstrap") {
210                                my $dbsverb = "";
211                                $dbsverb = "--verbose" if ($pbdebug gt 0);
212               
213                                # Some perl modules are in Universe on Ubuntu
214                                $rbsopt .= " --components=main,universe" if ($pbos->{'name'} eq "ubuntu");
215               
216                                pb_system("$sudocmd mkdir -p $root/$pbos->{name}/$pbos->{version}/$pbos->{arch} ; $sudocmd /usr/sbin/debootstrap $dbsverb $rbsopt --arch=$debarch $addpkgs $codename \"$root/$pbos->{'name'}/$pbos->{'version'}/$pbos->{'arch'}\" $debmir","Creating the debootstrap VE for $pbos->{'name'}-$pbos->{'version'} ($pbos->{'arch'})", "verbose");
217                                # debootstrap doesn't create an /etc/hosts file
218                                if (! -f "$root/$pbos->{'name'}/$pbos->{'version'}/$pbos->{'arch'}/etc/hosts" ) {
219                                        pb_system("$sudocmd cp /etc/hosts $root/$pbos->{'name'}/$pbos->{'version'}/$pbos->{'arch'}/etc/hosts");
220                                }
221                        } else {
222                                die "Unknown vedebtype type $vedebstyle. Report to dev team";
223                        }
224                } elsif ($pbos->{'type'} eq "ebuild") {
225                        die "Please teach the dev team how to build gentoo chroot";
226                } else {
227                        die "Unknown distribution type $pbos->{'type'}. Report to dev team";
228                }
229        }
230       
231        # Fix modes to allow access to the VE for pb user
232        pb_system("$sudocmd chmod 755 $root/$pbos->{'name'} $root/$pbos->{'name'}/$pbos->{'version'} $root/$pbos->{'name'}/$pbos->{'version'}/$pbos->{'arch'}","Fixing permissions");
233
234        # Test if an existing snapshot exists and use it if appropriate
235        # And also use it of no local extracted VE is present
236        if ((-f "$root/$pbos->{'name'}-$pbos->{'version'}-$pbos->{'arch'}.tar.gz") &&
237        (((defined $vesnap->{$v}) && ($vesnap->{$v} =~ /true/i)) ||
238                ((defined $vesnap->{$ENV{'PBPROJ'}}) && ($vesnap->{$ENV{'PBPROJ'}} =~ /true/i)) ||
239                ($pbsnap eq 1) ||
240                (! -d "$root/$pbos->{'name'}/$pbos->{'version'}/$pbos->{'arch'}"))) {
241                        pb_system("$sudocmd rm -rf $root/$pbos->{'name'}/$pbos->{'version'}/$pbos->{'arch'} ; $sudocmd mkdir -p $root/$pbos->{'name'}/$pbos->{'version'}/$pbos->{'arch'} ; $sudocmd tar xz  -C $root/$pbos->{'name'}/$pbos->{'version'}/$pbos->{'arch'} -f $root/$pbos->{'name'}-$pbos->{'version'}-$pbos->{'arch'}.tar.gz","Extracting snapshot of $pbos->{'name'}-$pbos->{'version'}-$pbos->{'arch'}.tar.gz under $root/$pbos->{'name'}/$pbos->{'version'}/$pbos->{'arch'}");
242        }
243        # Nothing more to do for VE. No real launch
244} else {
245        die "VE of type $vetype not supported. Report to the dev team";
246}
247}
248
249#
250# Return the postinstall line if needed
251#
252
253sub pb_ve_get_postinstall {
254
255my $pbos = shift;
256my $rbspi = shift;
257my $vestyle = shift;
258my $post = "";
259
260# Do we have a local post-install script
261if ($vestyle eq "rinse") {
262        $post = "--post-install ";
263} elsif ($vestyle eq "rpmbootstrap") {
264        $post = "-s ";
265}
266
267my $postparam = pb_distro_get_param($pbos,$rbspi);
268if ($postparam eq "") {
269        $post = "";
270} else {
271        $post .= $postparam;
272}
273return($post);
274}
275
276
277=head1 WEB SITES
278
279The main Web site of the project is available at L<http://www.project-builder.org/>. Bug reports should be filled using the trac instance of the project at L<http://trac.project-builder.org/>.
280
281=head1 USER MAILING LIST
282
283None exists for the moment.
284
285=head1 AUTHORS
286
287The Project-Builder.org team L<http://trac.project-builder.org/> lead by Bruno Cornec L<mailto:bruno@project-builder.org>.
288
289=head1 COPYRIGHT
290
291Project-Builder.org is distributed under the GPL v2.0 license
292described in the file C<COPYING> included with the distribution.
293
294=cut
295
296
2971;
Note: See TracBrowser for help on using the repository browser.