3 This class does all of the chroot setup, copying of files, etc. It is
4 the driver class for pretty much everything that Catalyst does.
7 import os,string,imp,types,shutil
8 from catalyst_support import *
9 from generic_target import *
12 class generic_stage_target(generic_target):
14 def __init__(self,myspec,addlargs):
15 self.required_values.extend(["version_stamp","target","subarch",\
16 "rel_type","profile","snapshot","source_subpath"])
18 self.valid_values.extend(["version_stamp","target","subarch",\
19 "rel_type","profile","snapshot","source_subpath","portage_confdir",\
20 "cflags","cxxflags","ldflags","cbuild","hostuse","portage_overlay",\
21 "distcc_hosts","makeopts","pkgcache_path","kerncache_path"])
23 self.set_valid_build_kernel_vars(addlargs)
24 generic_target.__init__(self,myspec,addlargs)
26 # The semantics of subarchmap and machinemap changed a bit in 2.0.3 to
27 # work better with vapier's CBUILD stuff. I've removed the "monolithic"
28 # machinemap from this file and split up its contents amongst the various
31 # When register() is called on each module in the arch/ dir, it now
32 # returns a tuple instead of acting on the subarchmap dict that is
33 # passed to it. The tuple contains the values that were previously
34 # added to subarchmap as well as a new list of CHOSTs that go along
35 # with that arch. This allows us to build machinemap on the fly based
36 # on the keys in subarchmap and the values of the 2nd list returned
39 # Also, after talking with vapier. I have a slightly better idea of what
40 # certain variables are used for and what they should be set to. Neither
41 # 'buildarch' or 'hostarch' are used directly, so their value doesn't
42 # really matter. They are just compared to determine if we are
43 # cross-compiling. Because of this, they are just set to the name of the
44 # module in arch/ that the subarch is part of to make things simpler.
45 # The entire build process is still based off of 'subarch' like it was
46 # previously. -agaffney
51 for x in [x[:-3] for x in os.listdir(self.settings["sharedir"]+"/arch/") if x.endswith(".py")]:
53 fh=open(self.settings["sharedir"]+"/arch/"+x+".py")
54 # This next line loads the plugin as a module and assigns it to
56 self.archmap[x]=imp.load_module(x,fh,"arch/"+x+".py",(".py","r",imp.PY_SOURCE))
57 # This next line registers all the subarches supported in the
59 tmpsubarchmap, tmpmachinemap = self.archmap[x].register()
60 self.subarchmap.update(tmpsubarchmap)
61 for machine in tmpmachinemap:
62 machinemap[machine] = x
63 for subarch in tmpsubarchmap:
64 machinemap[subarch] = x
67 # This message should probably change a bit, since everything in the dir should
68 # load just fine. If it doesn't, it's probably a syntax error in the module
69 msg("Can't find "+x+".py plugin in "+self.settings["sharedir"]+"/arch/")
71 if self.settings.has_key("chost"):
72 hostmachine = self.settings["chost"].split("-")[0]
73 if not machinemap.has_key(hostmachine):
74 raise CatalystError, "Unknown host machine type "+hostmachine
75 self.settings["hostarch"] = machinemap[hostmachine]
77 hostmachine = self.settings["subarch"]
78 if machinemap.has_key(hostmachine):
79 hostmachine = machinemap[hostmachine]
80 self.settings["hostarch"] = hostmachine
81 if self.settings.has_key("cbuild"):
82 buildmachine = self.settings["cbuild"].split("-")[0]
84 buildmachine = os.uname()[4]
85 if not machinemap.has_key(buildmachine):
86 raise CatalystError, "Unknown build machine type "+buildmachine
87 self.settings["buildarch"] = machinemap[buildmachine]
88 self.settings["crosscompile"] = (self.settings["hostarch"] != self.settings["buildarch"])
90 # Call arch constructor, pass our settings
92 self.arch=self.subarchmap[self.settings["subarch"]](self.settings)
94 print "Invalid subarch: "+self.settings["subarch"]
95 print "Choose one of the following:",
96 for x in self.subarchmap:
101 print "Using target:",self.settings["target"]
102 # print a nice informational message:
103 if self.settings["buildarch"]==self.settings["hostarch"]:
104 print "Building natively for",self.settings["hostarch"]
105 elif self.settings["crosscompile"]:
106 print "Cross-compiling on",self.settings["buildarch"],"for different machine type",\
107 self.settings["hostarch"]
109 print "Building on",self.settings["buildarch"],"for alternate personality type",\
110 self.settings["hostarch"]
112 # This should be first to be set as other set_ options depend on this
113 self.set_spec_prefix()
115 # define all of our core variables
116 self.set_target_profile()
117 self.set_target_subpath()
118 self.set_source_subpath()
121 self.set_snapshot_path()
123 self.set_source_path()
124 self.set_snapcache_path()
125 self.set_chroot_path()
126 self.set_autoresume_path()
128 self.set_stage_path()
129 self.set_target_path()
131 self.set_controller_file()
132 self.set_action_sequence()
134 self.set_cleanables()
135 self.set_iso_volume_id()
136 self.set_build_kernel_vars()
138 self.set_archscript()
140 self.set_install_mask()
151 self.set_portage_overlay()
152 self.set_root_overlay()
154 # This next line checks to make sure that the specified variables exist
157 file_locate(self.settings,["source_path","snapshot_path","distdir"],expand=0)
158 # If we are using portage_confdir, check that as well.
159 if self.settings.has_key("portage_confdir"):
160 file_locate(self.settings,["portage_confdir"],expand=0)
162 # setup our mount points
163 if self.settings.has_key("SNAPCACHE"):
164 self.mounts=[ "/proc","/dev","/usr/portage","/usr/portage/distfiles" ]
165 self.mountmap={"/proc":"/proc", "/dev":"/dev", "/dev/pts":"/dev/pts",\
166 "/usr/portage":self.settings["snapshot_cache_path"]+"/portage",\
167 "/usr/portage/distfiles":self.settings["distdir"]}
169 self.mounts=[ "/proc","/dev","/usr/portage/distfiles" ]
170 self.mountmap={"/proc":"/proc", "/dev":"/dev", "/dev/pts":"/dev/pts",\
171 "/usr/portage/distfiles":self.settings["distdir"]}
172 if os.uname()[0] == "Linux":
173 self.mounts.append("/dev/pts")
177 # Configure any user specified options (either in catalyst.conf or on
179 if self.settings.has_key("PKGCACHE"):
180 self.set_pkgcache_path()
181 print "Location of the package cache is " + self.settings["pkgcache_path"]
182 self.mounts.append("/usr/portage/packages")
183 self.mountmap["/usr/portage/packages"]=self.settings["pkgcache_path"]
185 if self.settings.has_key("KERNCACHE"):
186 self.set_kerncache_path()
187 print "Location of the kerncache is " + self.settings["kerncache_path"]
188 self.mounts.append("/tmp/kerncache")
189 self.mountmap["/tmp/kerncache"]=self.settings["kerncache_path"]
191 if self.settings.has_key("CCACHE"):
192 if os.environ.has_key("CCACHE_DIR"):
193 ccdir=os.environ["CCACHE_DIR"]
194 del os.environ["CCACHE_DIR"]
196 ccdir="/root/.ccache"
197 if not os.path.isdir(ccdir):
198 raise CatalystError,\
199 "Compiler cache support can't be enabled (can't find "+ccdir+")"
200 self.mounts.append("/var/tmp/ccache")
201 self.mountmap["/var/tmp/ccache"]=ccdir
203 self.env["CCACHE_DIR"]="/var/tmp/ccache"
205 if self.settings.has_key("ICECREAM"):
206 self.mounts.append("/var/cache/icecream")
207 self.mountmap["/var/cache/icecream"]="/var/cache/icecream"
208 self.env["PATH"]="/usr/lib/icecc/bin:"+self.env["PATH"]
210 def override_cbuild(self):
211 if self.makeconf.has_key("CBUILD"):
212 self.settings["CBUILD"]=self.makeconf["CBUILD"]
214 def override_chost(self):
215 if self.makeconf.has_key("CHOST"):
216 self.settings["CHOST"]=self.makeconf["CHOST"]
218 def override_cflags(self):
219 if self.makeconf.has_key("CFLAGS"):
220 self.settings["CFLAGS"]=self.makeconf["CFLAGS"]
222 def override_cxxflags(self):
223 if self.makeconf.has_key("CXXFLAGS"):
224 self.settings["CXXFLAGS"]=self.makeconf["CXXFLAGS"]
226 def override_ldflags(self):
227 if self.makeconf.has_key("LDFLAGS"):
228 self.settings["LDFLAGS"]=self.makeconf["LDFLAGS"]
230 def set_install_mask(self):
231 if self.settings.has_key("install_mask"):
232 if type(self.settings["install_mask"]) != types.StringType:
233 self.settings["install_mask"]=string.join(self.settings["install_mask"])
235 def set_spec_prefix(self):
236 self.settings["spec_prefix"]=self.settings["target"]
238 def set_target_profile(self):
239 self.settings["target_profile"]=self.settings["profile"]
241 def set_target_subpath(self):
242 self.settings["target_subpath"]=self.settings["rel_type"]+"/"+self.settings["target"]+\
243 "-"+self.settings["subarch"]+"-"+self.settings["version_stamp"]
245 def set_source_subpath(self):
246 if type(self.settings["source_subpath"]) != types.StringType:
247 raise CatalystError, "source_subpath should have been a string. Perhaps you have something wrong in your spec file?"
249 def set_pkgcache_path(self):
250 if self.settings.has_key("pkgcache_path"):
251 if type(self.settings["pkgcache_path"]) != types.StringType:
252 self.settings["pkgcache_path"]=normpath(string.join(self.settings["pkgcache_path"]))
254 self.settings["pkgcache_path"]=normpath(self.settings["storedir"]+"/packages/"+\
255 self.settings["target_subpath"]+"/")
257 def set_kerncache_path(self):
258 if self.settings.has_key("kerncache_path"):
259 if type(self.settings["kerncache_path"]) != types.StringType:
260 self.settings["kerncache_path"]=normpath(string.join(self.settings["kerncache_path"]))
262 self.settings["kerncache_path"]=normpath(self.settings["storedir"]+"/kerncache/"+\
263 self.settings["target_subpath"]+"/")
265 def set_target_path(self):
266 self.settings["target_path"]=normpath(self.settings["storedir"]+"/builds/"+\
267 self.settings["target_subpath"]+".tar.bz2")
268 if self.settings.has_key("AUTORESUME") \
269 and os.path.exists(self.settings["autoresume_path"]+"setup_target_path"):
270 print "Resume point detected, skipping target path setup operation..."
272 # first clean up any existing target stuff
273 if os.path.isfile(self.settings["target_path"]):
274 cmd("rm -f "+self.settings["target_path"], \
275 "Could not remove existing file: "+self.settings["target_path"],env=self.env)
276 touch(self.settings["autoresume_path"]+"setup_target_path")
278 if not os.path.exists(self.settings["storedir"]+"/builds/"):
279 os.makedirs(self.settings["storedir"]+"/builds/")
281 def set_archscript(self):
282 if self.settings.has_key(self.settings["spec_prefix"]+"/archscript"):
283 print "\nWarning!!! "
284 print "\t"+self.settings["spec_prefix"]+"/archscript" + " is deprecated and no longer used.\n"
285 def set_runscript(self):
286 if self.settings.has_key(self.settings["spec_prefix"]+"/runscript"):
287 print "\nWarning!!! "
288 print "\t"+self.settings["spec_prefix"]+"/runscript" + " is deprecated and no longer used.\n"
290 def set_fsscript(self):
291 if self.settings.has_key(self.settings["spec_prefix"]+"/fsscript"):
292 self.settings["fsscript"]=self.settings[self.settings["spec_prefix"]+"/fsscript"]
293 del self.settings[self.settings["spec_prefix"]+"/fsscript"]
296 if self.settings.has_key(self.settings["spec_prefix"]+"/rcadd"):
297 self.settings["rcadd"]=self.settings[self.settings["spec_prefix"]+"/rcadd"]
298 del self.settings[self.settings["spec_prefix"]+"/rcadd"]
301 if self.settings.has_key(self.settings["spec_prefix"]+"/rcdel"):
302 self.settings["rcdel"]=self.settings[self.settings["spec_prefix"]+"/rcdel"]
303 del self.settings[self.settings["spec_prefix"]+"/rcdel"]
306 if self.settings.has_key(self.settings["spec_prefix"]+"/cdtar"):
307 self.settings["cdtar"]=normpath(self.settings[self.settings["spec_prefix"]+"/cdtar"])
308 del self.settings[self.settings["spec_prefix"]+"/cdtar"]
311 if self.settings.has_key(self.settings["spec_prefix"]+"/iso"):
312 self.settings["iso"]=normpath(self.settings[self.settings["spec_prefix"]+"/iso"])
313 del self.settings[self.settings["spec_prefix"]+"/iso"]
315 def set_fstype(self):
316 if self.settings.has_key(self.settings["spec_prefix"]+"/cdfstype"):
317 print "\nWarning!!! "
318 print self.settings["spec_prefix"]+"/cdfstype" + " is deprecated and may be removed."
319 print "\tUse "+self.settings["spec_prefix"]+"/fstype" + " instead."
320 print "\tConverting to "+self.settings["spec_prefix"]+"/fstype" + " internally."
321 print "\tContinuing ....\n"
322 self.settings["fstype"]=self.settings[self.settings["spec_prefix"]+"/cdfstype"]
323 del self.settings[self.settings["spec_prefix"]+"/cdfstype"]
325 if self.settings.has_key(self.settings["spec_prefix"]+"/fstype"):
326 self.settings["fstype"]=self.settings[self.settings["spec_prefix"]+"/fstype"]
327 del self.settings[self.settings["spec_prefix"]+"/fstype"]
329 if not self.settings.has_key("fstype"):
330 self.settings["fstype"]="normal"
331 for x in self.valid_values:
332 if x == self.settings["spec_prefix"]+"/fstype" or x == self.settings["spec_prefix"]+"/cdfstype":
333 print "\n"+self.settings["spec_prefix"]+"/fstype is being set to the default of \"normal\"\n"
336 if self.settings.has_key("fstype"):
337 self.valid_values.append("fsops")
338 if self.settings.has_key(self.settings["spec_prefix"]+"/fsops"):
339 self.settings["fsops"]=self.settings[self.settings["spec_prefix"]+"/fsops"]
340 del self.settings[self.settings["spec_prefix"]+"/fsops"]
342 def set_source_path(self):
343 if self.settings.has_key("SEEDCACHE") and os.path.isdir(normpath(self.settings["storedir"]+"/tmp/"+self.settings["source_subpath"]+"/")):
344 self.settings["source_path"]=normpath(self.settings["storedir"]+"/tmp/"+self.settings["source_subpath"]+"/")
346 self.settings["source_path"]=normpath(self.settings["storedir"]+"/builds/"+self.settings["source_subpath"]+".tar.bz2")
347 if os.path.isfile(self.settings["source_path"]):
348 if os.path.exists(self.settings["source_path"]): # XXX: Is this even necessary if the previous check passes?
349 self.settings["source_path_hash"]=generate_hash(self.settings["source_path"],\
350 hash_function=self.settings["hash_function"],verbose=False)
351 print "Source path set to "+self.settings["source_path"]
352 if os.path.isdir(self.settings["source_path"]):
353 print "\tIf this is not desired, remove this directory or turn of seedcache in the options of catalyst.conf"
354 print "\tthe source path will then be "+normpath(self.settings["storedir"]+"/builds/"+self.settings["source_subpath"]+".tar.bz2\n")
356 def set_dest_path(self):
357 if self.settings.has_key("root_path"):
358 self.settings["destpath"]=normpath(self.settings["chroot_path"]+self.settings["root_path"])
360 self.settings["destpath"]=normpath(self.settings["chroot_path"])
362 def set_cleanables(self):
363 self.settings["cleanables"]=["/etc/resolv.conf","/var/tmp/*","/tmp/*","/root/*",\
366 def set_snapshot_path(self):
367 self.settings["snapshot_path"]=normpath(self.settings["storedir"]+"/snapshots/portage-"+self.settings["snapshot"]+".tar.bz2")
369 if os.path.exists(self.settings["snapshot_path"]):
370 self.settings["snapshot_path_hash"]=generate_hash(self.settings["snapshot_path"],\
371 hash_function=self.settings["hash_function"],verbose=False)
373 def set_snapcache_path(self):
374 if self.settings.has_key("SNAPCACHE"):
375 self.settings["snapshot_cache_path"]=normpath(self.settings["snapshot_cache"]+"/"+self.settings["snapshot"]+"/")
376 self.snapcache_lock=catalyst_lock.LockDir(self.settings["snapshot_cache_path"])
377 print "Caching snapshot to " + self.settings["snapshot_cache_path"]
379 def set_chroot_path(self):
380 # Note the trailing slash is very important and things would break without it
381 self.settings["chroot_path"]=normpath(self.settings["storedir"]+"/tmp/"+self.settings["target_subpath"]+"/")
382 self.chroot_lock=catalyst_lock.LockDir(self.settings["chroot_path"])
384 def set_autoresume_path(self):
385 self.settings["autoresume_path"]=normpath(self.settings["storedir"]+"/tmp/"+\
386 self.settings["rel_type"]+"/"+".autoresume-"+self.settings["target"]+\
387 "-"+self.settings["subarch"]+"-"+self.settings["version_stamp"]+"/")
388 if self.settings.has_key("AUTORESUME"):
389 print "The autoresume path is " + self.settings["autoresume_path"]
390 if not os.path.exists(self.settings["autoresume_path"]):
391 os.makedirs(self.settings["autoresume_path"],0755)
393 def set_controller_file(self):
394 self.settings["controller_file"]=normpath(self.settings["sharedir"]+"/targets/"+self.settings["target"]+"/"+self.settings["target"]+"-controller.sh")
396 def set_iso_volume_id(self):
397 if self.settings.has_key(self.settings["spec_prefix"]+"/volid"):
398 self.settings["iso_volume_id"] = self.settings[self.settings["spec_prefix"]+"/volid"]
399 if len(self.settings["iso_volume_id"])>32:
400 raise CatalystError,"ISO VOLUME ID: volid must not exceed 32 characters."
402 self.settings["iso_volume_id"] = "catalyst " + self.settings["snapshot"]
404 def set_action_sequence(self):
405 # Default action sequence for run method
406 self.settings["action_sequence"]=["unpack","unpack_snapshot",\
407 "config_profile_link","setup_confdir","portage_overlay",\
408 "base_dirs","bind","chroot_setup","setup_environment",\
409 "run_local","preclean","unbind","clean"]
410 # if self.settings.has_key("TARBALL") or \
411 # not self.settings.has_key("FETCH"):
412 if not self.settings.has_key("FETCH"):
413 self.settings["action_sequence"].append("capture")
414 self.settings["action_sequence"].append("clear_autoresume")
417 if self.settings.has_key(self.settings["spec_prefix"]+"/use"):
418 self.settings["use"]=self.settings[self.settings["spec_prefix"]+"/use"]
419 del self.settings[self.settings["spec_prefix"]+"/use"]
420 if self.settings.has_key("use"):
421 if type(self.settings["use"])==types.StringType:
422 self.settings["use"]=self.settings["use"].split()
423 self.settings["use"].append("bindist")
425 def set_stage_path(self):
426 self.settings["stage_path"]=normpath(self.settings["chroot_path"])
428 def set_mounts(self):
431 def set_packages(self):
435 if self.settings.has_key(self.settings["spec_prefix"]+"/rm"):
436 if type(self.settings[self.settings["spec_prefix"]+"/rm"])==types.StringType:
437 self.settings[self.settings["spec_prefix"]+"/rm"]=self.settings[self.settings["spec_prefix"]+"/rm"].split()
439 def set_linuxrc(self):
440 if self.settings.has_key(self.settings["spec_prefix"]+"/linuxrc"):
441 if type(self.settings[self.settings["spec_prefix"]+"/linuxrc"])==types.StringType:
442 self.settings["linuxrc"]=self.settings[self.settings["spec_prefix"]+"/linuxrc"]
443 del self.settings[self.settings["spec_prefix"]+"/linuxrc"]
445 def set_portage_overlay(self):
446 if self.settings.has_key("portage_overlay"):
447 if type(self.settings["portage_overlay"])==types.StringType:
448 self.settings["portage_overlay"]=self.settings["portage_overlay"].split()
449 print "portage_overlay directories are set to: \"" + string.join(self.settings["portage_overlay"])+"\""
451 def set_overlay(self):
452 if self.settings.has_key(self.settings["spec_prefix"]+"/overlay"):
453 if type(self.settings[self.settings["spec_prefix"]+"/overlay"])==types.StringType:
454 self.settings[self.settings["spec_prefix"]+"/overlay"]=self.settings[self.settings["spec_prefix"]+"/overlay"].split()
456 def set_root_overlay(self):
457 if self.settings.has_key(self.settings["spec_prefix"]+"/root_overlay"):
458 if type(self.settings[self.settings["spec_prefix"]+"/root_overlay"])==types.StringType:
459 self.settings[self.settings["spec_prefix"]+"/root_overlay"]=self.settings[self.settings["spec_prefix"]+"/root_overlay"].split()
462 def set_root_path(self):
463 # ROOT= variable for emerges
464 self.settings["root_path"]="/"
466 def set_valid_build_kernel_vars(self,addlargs):
467 if addlargs.has_key("boot/kernel"):
468 if type(addlargs["boot/kernel"]) == types.StringType:
469 loopy=[addlargs["boot/kernel"]]
471 loopy=addlargs["boot/kernel"]
474 self.required_values.append("boot/kernel/"+x+"/sources")
475 self.required_values.append("boot/kernel/"+x+"/config")
476 self.valid_values.append("boot/kernel/"+x+"/aliases")
477 self.valid_values.append("boot/kernel/"+x+"/extraversion")
478 self.valid_values.append("boot/kernel/"+x+"/packages")
479 if addlargs.has_key("boot/kernel/"+x+"/packages"):
480 if type(addlargs["boot/kernel/"+x+"/packages"]) == types.StringType:
481 addlargs["boot/kernel/"+x+"/packages"]=[addlargs["boot/kernel/"+x+"/packages"]]
482 self.valid_values.append("boot/kernel/"+x+"/use")
483 self.valid_values.append("boot/kernel/"+x+"/gk_kernargs")
484 self.valid_values.append("boot/kernel/"+x+"/gk_action")
485 self.valid_values.append("boot/kernel/"+x+"/initramfs_overlay")
486 self.valid_values.append("boot/kernel/"+x+"/softlevel")
487 self.valid_values.append("boot/kernel/"+x+"/console")
488 self.valid_values.append("boot/kernel/"+x+"/machine_type")
489 self.valid_values.append("boot/kernel/"+x+"/postconf")
490 if addlargs.has_key("boot/kernel/"+x+"/postconf"):
491 print "boot/kernel/"+x+"/postconf is deprecated"
492 print "\tInternally moving these ebuilds to boot/kernel/"+x+"/packages"
493 print "\tPlease move them to boot/kernel/"+x+"/packages in your specfile"
494 if type(addlargs["boot/kernel/"+x+"/postconf"]) == types.StringType:
495 loop2=[addlargs["boot/kernel/"+x+"/postconf"]]
497 loop2=addlargs["boot/kernel/"+x+"/postconf"]
500 if not addlargs.has_key("boot/kernel/"+x+"/packages"):
501 addlargs["boot/kernel/"+x+"/packages"]=[y]
503 addlargs["boot/kernel/"+x+"/packages"].append(y)
505 def set_build_kernel_vars(self):
506 if self.settings.has_key(self.settings["spec_prefix"]+"/devmanager"):
507 self.settings["devmanager"]=self.settings[self.settings["spec_prefix"]+"/devmanager"]
508 del self.settings[self.settings["spec_prefix"]+"/devmanager"]
510 if self.settings.has_key(self.settings["spec_prefix"]+"/splashtype"):
511 self.settings["splashtype"]=self.settings[self.settings["spec_prefix"]+"/splashtype"]
512 del self.settings[self.settings["spec_prefix"]+"/splashtype"]
514 if self.settings.has_key(self.settings["spec_prefix"]+"/gk_mainargs"):
515 self.settings["gk_mainargs"]=self.settings[self.settings["spec_prefix"]+"/gk_mainargs"]
516 del self.settings[self.settings["spec_prefix"]+"/gk_mainargs"]
518 def kill_chroot_pids(self):
519 print "Checking for processes running in chroot and killing them."
521 # Force environment variables to be exported so script can see them
522 self.setup_environment()
524 if os.path.exists(self.settings["sharedir"]+"/targets/support/kill-chroot-pids.sh"):
525 cmd("/bin/bash "+self.settings["sharedir"]+"/targets/support/kill-chroot-pids.sh",\
526 "kill-chroot-pids script failed.",env=self.env)
528 def mount_safety_check(self):
529 mypath=self.settings["chroot_path"]
532 check and verify that none of our paths in mypath are mounted. We don't want to clean
533 up with things still mounted, and this allows us to check.
534 returns 1 on ok, 0 on "something is still mounted" case.
536 if not os.path.exists(mypath):
539 for x in self.mounts:
540 if not os.path.exists(mypath+x):
543 if ismount(mypath+x):
544 #something is still mounted
546 print x+" is still mounted; performing auto-bind-umount...",
547 # try to umount stuff ourselves
549 if ismount(mypath+x):
550 raise CatalystError, "Auto-unbind failed for "+x
553 print "Auto-unbind successful..."
555 except CatalystError:
556 raise CatalystError, "Unable to auto-unbind "+x
561 clst_unpack_hash=read_from_clst(self.settings["autoresume_path"]+"unpack")
563 if self.settings.has_key("SEEDCACHE"):
564 if os.path.isdir(self.settings["source_path"]):
565 # SEEDCACHE Is a directory, use Rsync
566 unpack_cmd="rsync -a --delete "+self.settings["source_path"]+" "+self.settings["chroot_path"]
567 display_msg="\nStarting rsync from "+self.settings["source_path"]+"\nto "+\
568 self.settings["chroot_path"]+" (This may take some time) ...\n"
569 error_msg="Rsync of "+self.settings["source_path"]+" to "+self.settings["chroot_path"]+" failed."
571 # SEEDCACHE is a not a directory, try untar'ing
572 print "Referenced SEEDCACHE does not appear to be a directory, trying to untar..."
573 display_msg="\nStarting tar extract from "+self.settings["source_path"]+"\nto "+\
574 self.settings["chroot_path"]+" (This may take some time) ...\n"
575 unpack_cmd="tar xjpf "+self.settings["source_path"]+" -C "+self.settings["chroot_path"]
576 error_msg="Tarball extraction of "+self.settings["source_path"]+" to "+self.settings["chroot_path"]+" failed."
578 # No SEEDCACHE, use tar
579 display_msg="\nStarting tar extract from "+self.settings["source_path"]+"\nto "+\
580 self.settings["chroot_path"]+" (This may take some time) ...\n"
581 unpack_cmd="tar xjpf "+self.settings["source_path"]+" -C "+self.settings["chroot_path"]
582 error_msg="Tarball extraction of "+self.settings["source_path"]+" to "+self.settings["chroot_path"]+" failed."
585 if self.settings.has_key("AUTORESUME"):
586 # Autoresume is Valid, SeedCache is Valid
587 if os.path.isdir(self.settings["source_path"]) and os.path.exists(self.settings["autoresume_path"]+"unpack"):
589 invalid_snapshot=False
591 # Autoresume is Valid, Tarball is Valid
592 elif os.path.isfile(self.settings["source_path"]) and self.settings["source_path_hash"] == clst_unpack_hash:
594 invalid_snapshot=True
596 # Autoresume is InValid, SeedCache
597 elif os.path.isdir(self.settings["source_path"]) and not os.path.exists(self.settings["autoresume_path"]+"unpack"):
599 invalid_snapshot=False
601 # Autoresume is InValid, Tarball
602 elif os.path.isfile(self.settings["source_path"]) and self.settings["source_path_hash"] != clst_unpack_hash:
604 invalid_snapshot=True
606 # No Autoresume,SeedCache
607 if self.settings.has_key("SEEDCACHE"):
609 # Seed cache so lets run rsync and rsync can clean up extra junk
610 if os.path.isdir(self.settings["source_path"]):
612 invalid_snapshot=False
614 # Tarball so we better unpack and remove anything already there
615 elif os.path.isfile(self.settings["source_path"]):
617 invalid_snapshot=True
619 # No Autoresume,No SeedCache
622 # Tarball so we better unpack and remove anything already there
623 if os.path.isfile(self.settings["source_path"]):
625 invalid_snapshot=True
626 # Should never reach this if so something is very wrong
627 elif os.path.isdir(self.settings["source_path"]):
628 raise CatalystError,"source path is a dir but seedcache is not enabled"
631 self.mount_safety_check()
634 if self.settings.has_key("AUTORESUME"):
635 print "No Valid Resume point detected, cleaning up ..."
637 self.clear_autoresume()
640 if not os.path.exists(self.settings["chroot_path"]):
641 os.makedirs(self.settings["chroot_path"])
643 if not os.path.exists(self.settings["chroot_path"]+"/tmp"):
644 os.makedirs(self.settings["chroot_path"]+"/tmp",1777)
646 if self.settings.has_key("PKGCACHE"):
647 if not os.path.exists(self.settings["pkgcache_path"]):
648 os.makedirs(self.settings["pkgcache_path"],0755)
650 if self.settings.has_key("KERNCACHE"):
651 if not os.path.exists(self.settings["kerncache_path"]):
652 os.makedirs(self.settings["kerncache_path"],0755)
655 cmd(unpack_cmd,error_msg,env=self.env)
657 if self.settings.has_key("source_path_hash"):
658 myf=open(self.settings["autoresume_path"]+"unpack","w")
659 myf.write(self.settings["source_path_hash"])
662 touch(self.settings["autoresume_path"]+"unpack")
664 print "Resume point detected, skipping unpack operation..."
667 def unpack_snapshot(self):
669 snapshot_hash=read_from_clst(self.settings["autoresume_path"]+"unpack_portage")
671 if self.settings.has_key("SNAPCACHE"):
672 snapshot_cache_hash=read_from_clst(self.settings["snapshot_cache_path"]+"catalyst-hash")
673 destdir=self.settings["snapshot_cache_path"]
674 unpack_cmd="tar xjpf "+self.settings["snapshot_path"]+" -C "+destdir
675 unpack_errmsg="Error unpacking snapshot"
676 cleanup_msg="Cleaning up invalid snapshot cache at \n\t"+self.settings["snapshot_cache_path"]+" (This can take a long time)..."
677 cleanup_errmsg="Error removing existing snapshot cache directory."
678 self.snapshot_lock_object=self.snapcache_lock
680 if self.settings["snapshot_path_hash"] == snapshot_cache_hash:
681 print "Valid snapshot cache, skipping unpack of portage tree ..."
685 destdir=normpath(self.settings["chroot_path"]+"/usr/portage")
686 cleanup_errmsg="Error removing existing snapshot directory."
687 cleanup_msg="Cleaning up existing portage tree (This can take a long time) ..."
688 unpack_cmd="tar xjpf "+self.settings["snapshot_path"]+" -C "+self.settings["chroot_path"]+"/usr"
689 unpack_errmsg="Error unpacking snapshot"
691 if self.settings.has_key("AUTORESUME") \
692 and os.path.exists(self.settings["chroot_path"]+"/usr/portage/") \
693 and os.path.exists(self.settings["autoresume_path"]+"unpack_portage") \
694 and self.settings["snapshot_path_hash"] == snapshot_hash:
695 print "Valid Resume point detected, skipping unpack of portage tree..."
701 if self.settings.has_key("SNAPCACHE"):
702 self.snapshot_lock_object.write_lock()
703 if os.path.exists(destdir):
705 cleanup_cmd="rm -rf "+destdir
706 cmd(cleanup_cmd,cleanup_errmsg,env=self.env)
707 if not os.path.exists(destdir):
708 os.makedirs(destdir,0755)
710 print "Unpacking portage tree (This can take a long time) ..."
711 cmd(unpack_cmd,unpack_errmsg,env=self.env)
713 if self.settings.has_key("SNAPCACHE"):
714 myf=open(self.settings["snapshot_cache_path"]+"catalyst-hash","w")
715 myf.write(self.settings["snapshot_path_hash"])
719 print "Setting snapshot autoresume point"
720 myf=open(self.settings["autoresume_path"]+"unpack_portage","w")
721 myf.write(self.settings["snapshot_path_hash"])
724 if self.settings.has_key("SNAPCACHE"):
725 self.snapshot_lock_object.unlock()
727 def config_profile_link(self):
728 if self.settings.has_key("AUTORESUME") \
729 and os.path.exists(self.settings["autoresume_path"]+"config_profile_link"):
730 print "Resume point detected, skipping config_profile_link operation..."
732 print "Configuring profile link..."
733 cmd("rm -f "+self.settings["chroot_path"]+"/etc/make.profile",\
734 "Error zapping profile link",env=self.env)
735 cmd("ln -sf ../usr/portage/profiles/"+self.settings["target_profile"]+\
736 " "+self.settings["chroot_path"]+"/etc/make.profile","Error creating profile link",env=self.env)
737 touch(self.settings["autoresume_path"]+"config_profile_link")
739 def setup_confdir(self):
740 if self.settings.has_key("AUTORESUME") \
741 and os.path.exists(self.settings["autoresume_path"]+"setup_confdir"):
742 print "Resume point detected, skipping setup_confdir operation..."
744 if self.settings.has_key("portage_confdir"):
745 print "Configuring /etc/portage..."
746 cmd("rm -rf "+self.settings["chroot_path"]+"/etc/portage","Error zapping /etc/portage",env=self.env)
747 cmd("cp -R "+self.settings["portage_confdir"]+"/ "+self.settings["chroot_path"]+\
748 "/etc/portage","Error copying /etc/portage",env=self.env)
749 touch(self.settings["autoresume_path"]+"setup_confdir")
751 def portage_overlay(self):
752 # Here, we copy the contents of our overlays to /usr/local/portage. We
753 # always copy over the overlays in case it has changed.
754 if self.settings.has_key("portage_overlay"):
755 for x in self.settings["portage_overlay"]:
756 if os.path.exists(x):
757 print "Copying overlay dir " +x
758 cmd("mkdir -p "+self.settings["chroot_path"]+"/usr/local/portage","Could not make portage_overlay dir",env=self.env)
759 cmd("cp -R "+x+"/* "+self.settings["chroot_path"]+"/usr/local/portage","Could not copy portage_overlay",env=self.env)
761 def root_overlay(self):
762 # copy over the root_overlay
763 # Always copy over the overlay incase it has changed
764 if self.settings.has_key(self.settings["spec_prefix"]+"/root_overlay"):
765 for x in self.settings[self.settings["spec_prefix"]+"/root_overlay"]:
766 if os.path.exists(x):
767 print "Copying root_overlay: "+x
768 cmd("rsync -a "+x+"/ "+\
769 self.settings["chroot_path"], self.settings["spec_prefix"]+"/root_overlay: "+x+" copy failed.",env=self.env)
775 for x in self.mounts:
776 if not os.path.exists(self.settings["chroot_path"]+x):
777 os.makedirs(self.settings["chroot_path"]+x,0755)
779 if not os.path.exists(self.mountmap[x]):
780 os.makedirs(self.mountmap[x],0755)
783 if self.settings.has_key("SNAPCACHE") and x == "/usr/portage":
784 self.snapshot_lock_object.read_lock()
785 if os.uname()[0] == "FreeBSD":
787 retval=os.system("mount -t devfs none "+self.settings["chroot_path"]+x)
789 retval=os.system("mount_nullfs "+src+" "+self.settings["chroot_path"]+x)
791 retval=os.system("mount --bind "+src+" "+self.settings["chroot_path"]+x)
794 raise CatalystError,"Couldn't bind mount "+src
799 mypath=self.settings["chroot_path"]
800 myrevmounts=self.mounts[:]
801 myrevmounts.reverse()
802 # unmount in reverse order for nested bind-mounts
803 for x in myrevmounts:
804 if not os.path.exists(mypath+x):
807 if not ismount(mypath+x):
808 # it's not mounted, continue
811 retval=os.system("umount "+os.path.join(mypath,x.lstrip(os.path.sep)))
814 warn("First attempt to unmount: "+mypath+x+" failed.")
815 warn("Killing any pids still running in the chroot")
817 self.kill_chroot_pids()
819 retval2=os.system("umount "+mypath+x)
822 warn("Couldn't umount bind mount: "+mypath+x)
823 # keep trying to umount the others, to minimize damage if developer makes a mistake
825 if self.settings.has_key("SNAPCACHE") and x == "/usr/portage":
827 # Its possible the snapshot lock object isnt created yet
828 # this is because mount safety check calls unbind before the target is fully initialized
829 self.snapshot_lock_object.unlock()
834 if any bind mounts really failed, then we need to raise
835 this to potentially prevent an upcoming bash stage cleanup script
836 from wiping our bind mounts.
838 raise CatalystError,"Couldn't umount one or more bind-mounts; aborting for safety."
840 def chroot_setup(self):
841 self.makeconf=read_makeconf(self.settings["chroot_path"]+"/etc/make.conf")
842 self.override_cbuild()
843 self.override_chost()
844 self.override_cflags()
845 self.override_cxxflags()
846 self.override_ldflags()
847 if self.settings.has_key("AUTORESUME") \
848 and os.path.exists(self.settings["autoresume_path"]+"chroot_setup"):
849 print "Resume point detected, skipping chroot_setup operation..."
851 print "Setting up chroot..."
853 #self.makeconf=read_makeconf(self.settings["chroot_path"]+"/etc/make.conf")
855 cmd("cp /etc/resolv.conf "+self.settings["chroot_path"]+"/etc",\
856 "Could not copy resolv.conf into place.",env=self.env)
858 # copy over the envscript, if applicable
859 if self.settings.has_key("ENVSCRIPT"):
860 if not os.path.exists(self.settings["ENVSCRIPT"]):
861 raise CatalystError, "Can't find envscript "+self.settings["ENVSCRIPT"]
863 print "\nWarning!!!!"
864 print "\tOverriding certain env variables may cause catastrophic failure."
865 print "\tIf your build fails look here first as the possible problem."
866 print "\tCatalyst assumes you know what you are doing when setting"
867 print "\t\tthese variables."
868 print "\tCatalyst Maintainers use VERY minimal envscripts if used at all"
869 print "\tYou have been warned\n"
871 cmd("cp "+self.settings["ENVSCRIPT"]+" "+self.settings["chroot_path"]+"/tmp/envscript",\
872 "Could not copy envscript into place.",env=self.env)
874 # Setup metadata_overlay
875 if self.settings.has_key("METADATA_OVERLAY") and not self.settings.has_key("portage_confdir"):
876 if not os.path.exists(self.settings["chroot_path"] + "/etc/portage"):
877 cmd("mkdir " + self.settings["chroot_path"] + "/etc/portage")
878 myf = open(self.settings["chroot_path"] + "/etc/portage/modules", "a")
879 myf.write("portdbapi.auxdbmodule = cache.metadata_overlay.database\n")
882 # Copy over /etc/hosts from the host in case there are any
883 # specialties in there
884 if os.path.exists(self.settings["chroot_path"]+"/etc/hosts"):
885 cmd("mv "+self.settings["chroot_path"]+"/etc/hosts "+self.settings["chroot_path"]+\
886 "/etc/hosts.bck", "Could not backup /etc/hosts",env=self.env)
887 cmd("cp /etc/hosts "+self.settings["chroot_path"]+"/etc/hosts", "Could not copy /etc/hosts",env=self.env)
888 #self.override_cbuild()
889 #self.override_chost()
890 #self.override_cflags()
891 #self.override_cxxflags()
892 #self.override_ldflags()
893 # Modify and write out make.conf (for the chroot)
894 cmd("rm -f "+self.settings["chroot_path"]+"/etc/make.conf","Could not remove "+self.settings["chroot_path"]+"/etc/make.conf",\
896 myf=open(self.settings["chroot_path"]+"/etc/make.conf","w")
897 myf.write("# These settings were set by the catalyst build script that automatically\n# built this stage.\n")
898 myf.write("# Please consult /etc/make.conf.example for a more detailed example.\n")
899 if self.settings.has_key("CFLAGS"):
900 myf.write('CFLAGS="'+self.settings["CFLAGS"]+'"\n')
901 if self.settings.has_key("CXXFLAGS"):
902 myf.write('CXXFLAGS="'+self.settings["CXXFLAGS"]+'"\n')
904 myf.write('CXXFLAGS="${CFLAGS}"\n')
906 if self.settings.has_key("LDFLAGS"):
907 myf.write('LDFLAGS="'+self.settings["LDFLAGS"]+'"\n')
908 myf.write("# This should not be changed unless you know exactly what you are doing. You\n# should probably be using a different stage, instead.\n")
909 if self.settings.has_key("CBUILD"):
910 myf.write('CBUILD="'+self.settings["CBUILD"]+'"\n')
911 myf.write('# WARNING: Changing your CHOST is not something that should be done lightly.\n# Please consult http://www.gentoo.org/doc/en/change-chost.xml before changing it.\nCHOST="'+self.settings["CHOST"]+'"\n')
913 # Figure out what our USE vars are for building
915 if self.settings.has_key("HOSTUSE"):
916 myusevars.extend(self.settings["HOSTUSE"])
918 if self.settings.has_key("use"):
919 myusevars.extend(self.settings["use"])
922 myf.write('USE="'+string.join(myusevars)+'"\n')
924 # Setup the portage overlay
925 if self.settings.has_key("portage_overlay"):
926 # myf.write('PORTDIR_OVERLAY="'+string.join(self.settings["portage_overlay"])+'"\n')
927 myf.write('PORTDIR_OVERLAY="/usr/local/portage"\n')
930 touch(self.settings["autoresume_path"]+"chroot_setup")
933 if self.settings.has_key("AUTORESUME") \
934 and os.path.exists(self.settings["autoresume_path"]+"fsscript"):
935 print "Resume point detected, skipping fsscript operation..."
937 if self.settings.has_key("fsscript"):
938 if os.path.exists(self.settings["controller_file"]):
939 cmd("/bin/bash "+self.settings["controller_file"]+" fsscript","fsscript script failed.",env=self.env)
940 touch(self.settings["autoresume_path"]+"fsscript")
943 if self.settings.has_key("AUTORESUME") \
944 and os.path.exists(self.settings["autoresume_path"]+"rcupdate"):
945 print "Resume point detected, skipping rcupdate operation..."
947 if os.path.exists(self.settings["controller_file"]):
948 cmd("/bin/bash "+self.settings["controller_file"]+" rc-update","rc-update script failed.",env=self.env)
949 touch(self.settings["autoresume_path"]+"rcupdate")
952 if self.settings.has_key("AUTORESUME") \
953 and os.path.exists(self.settings["autoresume_path"]+"clean"):
954 print "Resume point detected, skipping clean operation..."
956 for x in self.settings["cleanables"]:
957 print "Cleaning chroot: "+x+"... "
958 cmd("rm -rf "+self.settings["destpath"]+x,"Couldn't clean "+x,env=self.env)
960 # put /etc/hosts back into place
961 if os.path.exists(self.settings["chroot_path"]+"/etc/hosts.bck"):
962 cmd("mv -f "+self.settings["chroot_path"]+"/etc/hosts.bck "+self.settings["chroot_path"]+"/etc/hosts", "Could not replace /etc/hosts",env=self.env)
965 if os.path.exists(self.settings["chroot_path"]+"/usr/local/portage"):
966 cmd("rm -rf "+self.settings["chroot_path"]+"/usr/local/portage", "Could not remove /usr/local/portage",env=self.env)
967 cmd("sed -i '/^PORTDIR_OVERLAY/d' "+self.settings["chroot_path"]+"/etc/make.conf", "Could not remove PORTDIR_OVERLAY from make.conf",env=self.env)
969 # clean up old and obsoleted files in /etc
970 if os.path.exists(self.settings["stage_path"]+"/etc"):
971 cmd("find "+self.settings["stage_path"]+"/etc -maxdepth 1 -name \"*-\" | xargs rm -f", "Could not remove stray files in /etc",env=self.env)
973 if os.path.exists(self.settings["controller_file"]):
974 cmd("/bin/bash "+self.settings["controller_file"]+" clean","clean script failed.",env=self.env)
975 touch(self.settings["autoresume_path"]+"clean")
978 if self.settings.has_key("AUTORESUME") \
979 and os.path.exists(self.settings["autoresume_path"]+"empty"):
980 print "Resume point detected, skipping empty operation..."
982 if self.settings.has_key(self.settings["spec_prefix"]+"/empty"):
983 if type(self.settings[self.settings["spec_prefix"]+"/empty"])==types.StringType:
984 self.settings[self.settings["spec_prefix"]+"/empty"]=self.settings[self.settings["spec_prefix"]+"/empty"].split()
985 for x in self.settings[self.settings["spec_prefix"]+"/empty"]:
986 myemp=self.settings["destpath"]+x
987 if not os.path.isdir(myemp):
988 print x,"not a directory or does not exist, skipping 'empty' operation."
990 print "Emptying directory",x
991 # stat the dir, delete the dir, recreate the dir and set
992 # the proper perms and ownership
993 mystat=os.stat(myemp)
995 os.makedirs(myemp,0755)
996 os.chown(myemp,mystat[ST_UID],mystat[ST_GID])
997 os.chmod(myemp,mystat[ST_MODE])
998 touch(self.settings["autoresume_path"]+"empty")
1001 if self.settings.has_key("AUTORESUME") \
1002 and os.path.exists(self.settings["autoresume_path"]+"remove"):
1003 print "Resume point detected, skipping remove operation..."
1005 if self.settings.has_key(self.settings["spec_prefix"]+"/rm"):
1006 for x in self.settings[self.settings["spec_prefix"]+"/rm"]:
1007 # we're going to shell out for all these cleaning operations,
1008 # so we get easy glob handling
1009 print "livecd: removing "+x
1010 os.system("rm -rf "+self.settings["chroot_path"]+x)
1012 if os.path.exists(self.settings["controller_file"]):
1013 cmd("/bin/bash "+self.settings["controller_file"]+" clean",\
1014 "Clean failed.",env=self.env)
1015 touch(self.settings["autoresume_path"]+"remove")
1022 if self.settings.has_key("AUTORESUME") \
1023 and os.path.exists(self.settings["autoresume_path"]+"preclean"):
1024 print "Resume point detected, skipping preclean operation..."
1027 if os.path.exists(self.settings["controller_file"]):
1028 cmd("/bin/bash "+self.settings["controller_file"]+" preclean","preclean script failed.",env=self.env)
1029 touch(self.settings["autoresume_path"]+"preclean")
1033 raise CatalystError, "Build failed, could not execute preclean"
1036 if self.settings.has_key("AUTORESUME") \
1037 and os.path.exists(self.settings["autoresume_path"]+"capture"):
1038 print "Resume point detected, skipping capture operation..."
1040 """capture target in a tarball"""
1041 mypath=self.settings["target_path"].split("/")
1042 # remove filename from path
1043 mypath=string.join(mypath[:-1],"/")
1045 # now make sure path exists
1046 if not os.path.exists(mypath):
1049 print "Creating stage tarball..."
1051 cmd("tar cjpf "+self.settings["target_path"]+" -C "+self.settings["stage_path"]+\
1052 " .","Couldn't create stage tarball",env=self.env)
1054 self.gen_digest_file(self.settings["target_path"])
1056 touch(self.settings["autoresume_path"]+"capture")
1058 def run_local(self):
1059 if self.settings.has_key("AUTORESUME") \
1060 and os.path.exists(self.settings["autoresume_path"]+"run_local"):
1061 print "Resume point detected, skipping run_local operation..."
1064 if os.path.exists(self.settings["controller_file"]):
1065 cmd("/bin/bash "+self.settings["controller_file"]+" run","run script failed.",env=self.env)
1066 touch(self.settings["autoresume_path"]+"run_local")
1068 except CatalystError:
1070 raise CatalystError,"Stage build aborting due to error."
1072 def setup_environment(self):
1073 # Modify the current environment. This is an ugly hack that should be
1074 # fixed. We need this to use the os.system() call since we can't
1075 # specify our own environ:
1076 for x in self.settings.keys():
1077 # sanitize var names by doing "s|/-.|_|g"
1078 varname="clst_"+string.replace(x,"/","_")
1079 varname=string.replace(varname,"-","_")
1080 varname=string.replace(varname,".","_")
1081 if type(self.settings[x])==types.StringType:
1082 # prefix to prevent namespace clashes:
1083 #os.environ[varname]=self.settings[x]
1084 self.env[varname]=self.settings[x]
1085 elif type(self.settings[x])==types.ListType:
1086 #os.environ[varname]=string.join(self.settings[x])
1087 self.env[varname]=string.join(self.settings[x])
1088 elif type(self.settings[x])==types.BooleanType:
1089 if self.settings[x]:
1090 self.env[varname]="true"
1092 self.env[varname]="false"
1093 if self.settings.has_key("makeopts"):
1094 self.env["MAKEOPTS"]=self.settings["makeopts"]
1097 self.chroot_lock.write_lock()
1099 # Kill any pids in the chroot
1100 self.kill_chroot_pids()
1102 # Check for mounts right away and abort if we cannot unmount them.
1103 self.mount_safety_check()
1105 if self.settings.has_key("CLEAR_AUTORESUME"):
1106 self.clear_autoresume()
1107 if self.settings.has_key("PURGE"):
1110 for x in self.settings["action_sequence"]:
1111 print "--- Running action sequence: "+x
1114 apply(getattr(self,x))
1116 self.mount_safety_check()
1119 self.chroot_lock.unlock()
1122 if self.settings.has_key("AUTORESUME") \
1123 and os.path.exists(self.settings["autoresume_path"]+"unmerge"):
1124 print "Resume point detected, skipping unmerge operation..."
1126 if self.settings.has_key(self.settings["spec_prefix"]+"/unmerge"):
1127 if type(self.settings[self.settings["spec_prefix"]+"/unmerge"])==types.StringType:
1128 self.settings[self.settings["spec_prefix"]+"/unmerge"]=[self.settings[self.settings["spec_prefix"]+"/unmerge"]]
1129 myunmerge=self.settings[self.settings["spec_prefix"]+"/unmerge"][:]
1131 for x in range(0,len(myunmerge)):
1132 #surround args with quotes for passing to bash,
1133 #allows things like "<" to remain intact
1134 myunmerge[x]="'"+myunmerge[x]+"'"
1135 myunmerge=string.join(myunmerge)
1137 #before cleaning, unmerge stuff:
1139 cmd("/bin/bash "+self.settings["controller_file"]+" unmerge "+ myunmerge,\
1140 "Unmerge script failed.",env=self.env)
1141 #cmd("/bin/bash "+self.settings["sharedir"]+"/targets/" \
1142 # +self.settings["target"]+"/unmerge.sh "+myunmerge,"Unmerge script failed.",env=self.env)
1143 print "unmerge shell script"
1144 except CatalystError:
1148 touch(self.settings["autoresume_path"]+"unmerge")
1150 def target_setup(self):
1151 if self.settings.has_key("AUTORESUME") \
1152 and os.path.exists(self.settings["autoresume_path"]+"target_setup"):
1153 print "Resume point detected, skipping target_setup operation..."
1155 print "Setting up filesystems per filesystem type"
1156 cmd("/bin/bash "+self.settings["controller_file"]+" target_image_setup "+ self.settings["target_path"],\
1157 "target_image_setup script failed.",env=self.env)
1158 touch(self.settings["autoresume_path"]+"target_setup")
1160 def setup_overlay(self):
1161 if self.settings.has_key("AUTORESUME") \
1162 and os.path.exists(self.settings["autoresume_path"]+"setup_overlay"):
1163 print "Resume point detected, skipping setup_overlay operation..."
1165 if self.settings.has_key(self.settings["spec_prefix"]+"/overlay"):
1166 for x in self.settings[self.settings["spec_prefix"]+"/overlay"]:
1167 if os.path.exists(x):
1168 cmd("rsync -a "+x+"/ "+\
1169 self.settings["target_path"], self.settings["spec_prefix"]+"overlay: "+x+" copy failed.",env=self.env)
1170 touch(self.settings["autoresume_path"]+"setup_overlay")
1172 def create_iso(self):
1173 if self.settings.has_key("AUTORESUME") \
1174 and os.path.exists(self.settings["autoresume_path"]+"create_iso"):
1175 print "Resume point detected, skipping create_iso operation..."
1177 # create the ISO - this is the preferred method (the iso scripts do not always work)
1178 if self.settings.has_key("iso"):
1179 cmd("/bin/bash "+self.settings["controller_file"]+" iso "+\
1180 self.settings["iso"],"ISO creation script failed.",env=self.env)
1181 self.gen_digest_file(self.settings["iso"])
1182 touch(self.settings["autoresume_path"]+"create_iso")
1186 print "WARNING livecd/iso was not defined."
1187 print "A CD Image will not be created, skipping create-iso.sh..."
1190 def build_packages(self):
1191 if self.settings.has_key("AUTORESUME") \
1192 and os.path.exists(self.settings["autoresume_path"]+"build_packages"):
1193 print "Resume point detected, skipping build_packages operation..."
1195 if self.settings.has_key(self.settings["spec_prefix"]+"/packages"):
1196 if self.settings.has_key("AUTORESUME") \
1197 and os.path.exists(self.settings["autoresume_path"]+"build_packages"):
1198 print "Resume point detected, skipping build_packages operation..."
1200 mypack=list_bashify(self.settings[self.settings["spec_prefix"]+"/packages"])
1202 cmd("/bin/bash "+self.settings["controller_file"]+\
1203 " build_packages "+mypack,"Error in attempt to build packages",env=self.env)
1204 touch(self.settings["autoresume_path"]+"build_packages")
1205 except CatalystError:
1207 raise CatalystError,self.settings["spec_prefix"] + "build aborting due to error."
1209 def build_kernel(self):
1210 if self.settings.has_key("AUTORESUME") \
1211 and os.path.exists(self.settings["autoresume_path"]+"build_kernel"):
1212 print "Resume point detected, skipping build_kernel operation..."
1214 if self.settings.has_key("boot/kernel"):
1216 mynames=self.settings["boot/kernel"]
1217 if type(mynames)==types.StringType:
1219 # execute the script that sets up the kernel build environment
1220 cmd("/bin/bash "+self.settings["controller_file"]+" pre-kmerge ",\
1221 "Runscript pre-kmerge failed",env=self.env)
1223 for kname in mynames:
1224 if self.settings.has_key("AUTORESUME") \
1225 and os.path.exists(self.settings["autoresume_path"]+"build_kernel_"+kname):
1226 print "Resume point detected, skipping build_kernel for "+kname+" operation..."
1229 if not os.path.exists(self.settings["boot/kernel/"+kname+"/config"]):
1231 raise CatalystError, "Can't find kernel config: " \
1232 +self.settings["boot/kernel/"+kname+"/config"]
1235 raise CatalystError, "Required value boot/kernel/config not specified"
1238 cmd("cp "+self.settings["boot/kernel/"+kname+"/config"]+" "+ \
1239 self.settings["chroot_path"]+"/var/tmp/"+kname+".config", \
1240 "Couldn't copy kernel config: "+self.settings["boot/kernel/"+kname+"/config"],\
1243 except CatalystError:
1246 # If we need to pass special options to the bootloader
1247 # for this kernel put them into the environment.
1248 if self.settings.has_key("boot/kernel/"+kname+"/kernelopts"):
1249 myopts=self.settings["boot/kernel/"+kname+"/kernelopts"]
1251 if type(myopts) != types.StringType:
1252 myopts = string.join(myopts)
1253 self.env[kname+"_kernelopts"]=myopts
1256 self.env[kname+"_kernelopts"]=""
1258 if not self.settings.has_key("boot/kernel/"+kname+"/extraversion"):
1259 self.settings["boot/kernel/"+kname+"/extraversion"]=""
1261 self.env["clst_kextraversion"]=self.settings["boot/kernel/"+kname+"/extraversion"]
1263 if self.settings.has_key("boot/kernel/"+kname+"/initramfs_overlay"):
1264 if os.path.exists(self.settings["boot/kernel/"+kname+"/initramfs_overlay"]):
1265 print "Copying initramfs_overlay dir " +self.settings["boot/kernel/"+kname+"/initramfs_overlay"]
1267 cmd("mkdir -p "+self.settings["chroot_path"]+"/tmp/initramfs_overlay/" + \
1268 self.settings["boot/kernel/"+kname+"/initramfs_overlay"],env=self.env)
1270 cmd("cp -R "+self.settings["boot/kernel/"+kname+"/initramfs_overlay"]+"/* " + \
1271 self.settings["chroot_path"] + "/tmp/initramfs_overlay/" + \
1272 self.settings["boot/kernel/"+kname+"/initramfs_overlay"],\
1276 # execute the script that builds the kernel
1277 cmd("/bin/bash "+self.settings["controller_file"]+" kernel "+kname,\
1278 "Runscript kernel build failed",env=self.env)
1280 if self.settings.has_key("boot/kernel/"+kname+"/initramfs_overlay"):
1281 if os.path.exists(self.settings["chroot_path"]+"/tmp/initramfs_overlay/"):
1282 print "Cleaning up temporary overlay dir"
1283 cmd("rm -R "+self.settings["chroot_path"]+"/tmp/initramfs_overlay/",env=self.env)
1285 touch(self.settings["autoresume_path"]+"build_kernel_"+kname)
1287 # execute the script that cleans up the kernel build environment
1288 cmd("/bin/bash "+self.settings["controller_file"]+" post-kmerge ",\
1289 "Runscript post-kmerge failed",env=self.env)
1291 touch(self.settings["autoresume_path"]+"build_kernel")
1293 except CatalystError:
1295 raise CatalystError,"build aborting due to kernel build error."
1297 def bootloader(self):
1298 if self.settings.has_key("AUTORESUME") \
1299 and os.path.exists(self.settings["autoresume_path"]+"bootloader"):
1300 print "Resume point detected, skipping bootloader operation..."
1303 cmd("/bin/bash "+self.settings["controller_file"]+" bootloader " + self.settings["target_path"],\
1304 "Bootloader runscript failed.",env=self.env)
1305 touch(self.settings["autoresume_path"]+"bootloader")
1306 except CatalystError:
1308 raise CatalystError,"Runscript aborting due to error."
1310 def livecd_update(self):
1311 if self.settings.has_key("AUTORESUME") \
1312 and os.path.exists(self.settings["autoresume_path"]+"livecd_update"):
1313 print "Resume point detected, skipping build_packages operation..."
1316 cmd("/bin/bash "+self.settings["controller_file"]+" livecd-update",\
1317 "livecd-update failed.",env=self.env)
1318 touch(self.settings["autoresume_path"]+"livecd_update")
1320 except CatalystError:
1322 raise CatalystError,"build aborting due to livecd_update error."
1324 def clear_chroot(self):
1325 myemp=self.settings["chroot_path"]
1326 if os.path.isdir(myemp):
1327 print "Emptying directory",myemp
1328 # stat the dir, delete the dir, recreate the dir and set
1329 # the proper perms and ownership
1330 mystat=os.stat(myemp)
1331 #cmd("rm -rf "+myemp, "Could not remove existing file: "+myemp,env=self.env)
1332 if os.uname()[0] == "FreeBSD": # There's no easy way to change flags recursively in python
1333 os.system("chflags -R noschg "+myemp)
1334 shutil.rmtree(myemp)
1335 os.makedirs(myemp,0755)
1336 os.chown(myemp,mystat[ST_UID],mystat[ST_GID])
1337 os.chmod(myemp,mystat[ST_MODE])
1339 def clear_packages(self):
1340 if self.settings.has_key("PKGCACHE"):
1341 print "purging the pkgcache ..."
1343 myemp=self.settings["pkgcache_path"]
1344 if os.path.isdir(myemp):
1345 print "Emptying directory",myemp
1346 # stat the dir, delete the dir, recreate the dir and set
1347 # the proper perms and ownership
1348 mystat=os.stat(myemp)
1349 #cmd("rm -rf "+myemp, "Could not remove existing file: "+myemp,env=self.env)
1350 shutil.rmtree(myemp)
1351 os.makedirs(myemp,0755)
1352 os.chown(myemp,mystat[ST_UID],mystat[ST_GID])
1353 os.chmod(myemp,mystat[ST_MODE])
1355 def clear_kerncache(self):
1356 if self.settings.has_key("KERNCACHE"):
1357 print "purging the kerncache ..."
1359 myemp=self.settings["kerncache_path"]
1360 if os.path.isdir(myemp):
1361 print "Emptying directory",myemp
1362 # stat the dir, delete the dir, recreate the dir and set
1363 # the proper perms and ownership
1364 mystat=os.stat(myemp)
1365 #cmd("rm -rf "+myemp, "Could not remove existing file: "+myemp,env=self.env)
1366 shutil.rmtree(myemp)
1367 os.makedirs(myemp,0755)
1368 os.chown(myemp,mystat[ST_UID],mystat[ST_GID])
1369 os.chmod(myemp,mystat[ST_MODE])
1371 def clear_autoresume(self):
1372 # clean resume points since they are no longer needed
1373 if self.settings.has_key("AUTORESUME"):
1374 print "Removing AutoResume Points: ..."
1375 myemp=self.settings["autoresume_path"]
1376 if os.path.isdir(myemp):
1377 if self.settings.has_key("AUTORESUME"):
1378 print "Emptying directory",myemp
1379 # stat the dir, delete the dir, recreate the dir and set
1380 # the proper perms and ownership
1381 mystat=os.stat(myemp)
1382 if os.uname()[0] == "FreeBSD":
1383 cmd("chflags -R noschg "+myemp, "Could not remove immutable flag for file " + myemp)
1384 #cmd("rm -rf "+myemp, "Could not remove existing file: "+myemp,env-self.env)
1385 shutil.rmtree(myemp)
1386 os.makedirs(myemp,0755)
1387 os.chown(myemp,mystat[ST_UID],mystat[ST_GID])
1388 os.chmod(myemp,mystat[ST_MODE])
1390 def gen_digest_file(self,file):
1391 if os.path.exists(file+".DIGESTS"):
1392 os.remove(file+".DIGESTS")
1393 if self.settings.has_key("digests"):
1394 if os.path.exists(file):
1395 myf=open(file+".DIGESTS","w")
1397 for i in self.settings["digests"].split():
1402 if self.settings.has_key("VERBOSE"):
1403 hash=generate_hash(file,hash_function=j,verbose=True)
1405 hash=generate_hash(file,hash_function=j)
1410 countdown(10,"Purging Caches ...")
1411 if self.settings.has_key("PURGE"):
1412 print "clearing autoresume ..."
1413 self.clear_autoresume()
1415 print "clearing chroot ..."
1418 print "clearing package cache ..."
1419 self.clear_packages()
1421 print "clearing kerncache ..."
1422 self.clear_kerncache()
1424 #vim: ts=4 sw=4 sta et sts=4 ai