Lines 78-84
Link Here
|
78 |
sys.stderr.write(red("*** Please add this user to the portage group if you wish to use portage.\n")) |
78 |
sys.stderr.write(red("*** Please add this user to the portage group if you wish to use portage.\n")) |
79 |
sys.stderr.write("\n") |
79 |
sys.stderr.write("\n") |
80 |
|
80 |
|
81 |
incrementals=["USE","FEATURES","ACCEPT_KEYWORDS","ACCEPT_LICENSE","CONFIG_PROTECT_MASK","CONFIG_PROTECT","PRELINK_PATH","PRELINK_PATH_MASK"] |
81 |
incrementals=["USE","FEATURES","ACCEPT_KEYWORDS","ACCEPT_LICENSE","CONFIG_PROTECT_MASK","CONFIG_PROTECT","CLEAN_PROTECT_MASK","CLEAN_PROTECT","PRELINK_PATH","PRELINK_PATH_MASK"] |
82 |
stickies=["KEYWORDS_ACCEPT","USE","CFLAGS","CXXFLAGS","MAKEOPTS","EXTRA_ECONF","EXTRA_EMAKE"] |
82 |
stickies=["KEYWORDS_ACCEPT","USE","CFLAGS","CXXFLAGS","MAKEOPTS","EXTRA_ECONF","EXTRA_EMAKE"] |
83 |
|
83 |
|
84 |
def getcwd(): |
84 |
def getcwd(): |
Lines 435-441
Link Here
|
435 |
continue |
435 |
continue |
436 |
pos=pos+1 |
436 |
pos=pos+1 |
437 |
|
437 |
|
438 |
specials={"KDEDIRS":[],"PATH":[],"CLASSPATH":[],"LDPATH":[],"MANPATH":[],"INFODIR":[],"INFOPATH":[],"ROOTPATH":[],"CONFIG_PROTECT":[],"CONFIG_PROTECT_MASK":[],"PRELINK_PATH":[],"PRELINK_PATH_MASK":[]} |
438 |
specials={"KDEDIRS":[],"PATH":[],"CLASSPATH":[],"LDPATH":[],"MANPATH":[],"INFODIR":[],"INFOPATH":[],"ROOTPATH":[],"CONFIG_PROTECT":[],"CONFIG_PROTECT_MASK":[],"CLEAN_PROTECT":[],"CLEAN_PROTECT_MASK":[],"PRELINK_PATH":[],"PRELINK_PATH_MASK":[]} |
439 |
env={} |
439 |
env={} |
440 |
|
440 |
|
441 |
for x in fns: |
441 |
for x in fns: |
Lines 530-536
Link Here
|
530 |
if len(specials[path])==0: |
530 |
if len(specials[path])==0: |
531 |
continue |
531 |
continue |
532 |
outstring="export "+path+"='" |
532 |
outstring="export "+path+"='" |
533 |
if path in ["CONFIG_PROTECT","CONFIG_PROTECT_MASK"]: |
533 |
if path in ["CONFIG_PROTECT","CONFIG_PROTECT_MASK","CLEAN_PROTECT","CLEAN_PROTECT_MASK"]: |
534 |
for x in specials[path][:-1]: |
534 |
for x in specials[path][:-1]: |
535 |
outstring += x+" " |
535 |
outstring += x+" " |
536 |
else: |
536 |
else: |
Lines 1914-1924
Link Here
|
1914 |
#shell error code |
1914 |
#shell error code |
1915 |
return mylink.merge(pkgloc,infloc,myroot,myebuild) |
1915 |
return mylink.merge(pkgloc,infloc,myroot,myebuild) |
1916 |
|
1916 |
|
1917 |
def unmerge(cat,pkg,myroot,mytrimworld=1): |
1917 |
def unmerge(cat,pkg,myroot,mytrimworld=1,protector=""): |
|
|
1918 |
# clnpro: Here, the protector is a cpv string, and we'll give an opened /db/c/pv/CONTENTS |
1919 |
# file to the dblink.unmerge() call. |
1920 |
# If no protector is given, don't worry, it's not an error but a real unmerge |
1921 |
# instead of a clean or prune. |
1922 |
myprotfile=None |
1923 |
if protector: |
1924 |
myprotcat=string.split(protector,"/")[0] |
1925 |
myprotpkg=string.split(protector,"/")[1] |
1926 |
myprotfilename=myroot+"///var/db/pkg/"+myprotcat+"/"+myprotpkg+"/CONTENTS" |
1927 |
if not os.path.exists(myprotfilename) or (cat==myprotcat and pkg==myprotpkg): |
1928 |
print "!!! Wrong protector. This shouldn't happen." |
1929 |
else: |
1930 |
myprotfile=open(myprotfilename,"a") |
1918 |
mylink=dblink(cat,pkg,myroot) |
1931 |
mylink=dblink(cat,pkg,myroot) |
1919 |
if mylink.exists(): |
1932 |
if mylink.exists(): |
1920 |
mylink.unmerge(trimworld=mytrimworld) |
1933 |
mylink.unmerge(trimworld=mytrimworld,protectfile=myprotfile) |
1921 |
mylink.delete() |
1934 |
mylink.delete() |
|
|
1935 |
if (myprotfile != None): |
1936 |
myprotfile.close() |
1922 |
|
1937 |
|
1923 |
def relparse(myver): |
1938 |
def relparse(myver): |
1924 |
"converts last version part into three components" |
1939 |
"converts last version part into three components" |
Lines 4200-4205
Link Here
|
4200 |
if os.path.isdir(ppath): |
4215 |
if os.path.isdir(ppath): |
4201 |
self.protectmask.append(ppath) |
4216 |
self.protectmask.append(ppath) |
4202 |
#if it doesn't exist, silently skip it |
4217 |
#if it doesn't exist, silently skip it |
|
|
4218 |
|
4219 |
#clnpro: update protection path |
4220 |
self.cleanprotect=[] |
4221 |
for x in string.split(settings["CLEAN_PROTECT"]): |
4222 |
ppath=os.path.normpath(self.myroot+"/"+x)+"/" |
4223 |
if os.path.isdir(ppath): |
4224 |
self.cleanprotect.append(ppath) |
4225 |
#if it doesn't exist, silently skip it |
4226 |
#clnpro: is a masked relly needed? |
4227 |
self.cleanprotectmask=[] |
4228 |
for x in string.split(settings["CLEAN_PROTECT_MASK"]): |
4229 |
ppath=os.path.normpath(self.myroot+"/"+x)+"/" |
4230 |
if os.path.isdir(ppath): |
4231 |
self.cleanprotectmask.append(ppath) |
4232 |
#if it doesn't exist, silently skip it |
4203 |
|
4233 |
|
4204 |
def isprotected(self,obj): |
4234 |
def isprotected(self,obj): |
4205 |
"""Checks if obj is in the current protect/mask directories. Returns |
4235 |
"""Checks if obj is in the current protect/mask directories. Returns |
Lines 4216-4222
Link Here
|
4216 |
masked=len(pmpath) |
4246 |
masked=len(pmpath) |
4217 |
return (protected > masked) |
4247 |
return (protected > masked) |
4218 |
|
4248 |
|
4219 |
def unmerge(self,pkgfiles=None,trimworld=1): |
4249 |
def iscleanprotected(self,obj): |
|
|
4250 |
"""Checks if obj is in the current clean protect/mask directories. Returns |
4251 |
0 on unprotected/masked, and 1 on protected.""" |
4252 |
masked=0 |
4253 |
protected=0 |
4254 |
for ppath in self.cleanprotect: |
4255 |
if (len(ppath) > masked) and (obj[0:len(ppath)]==ppath): |
4256 |
protected=len(ppath) |
4257 |
#clnpro file management |
4258 |
for pmpath in self.cleanprotectmask: |
4259 |
if (len(pmpath) >= protected) and (obj[0:len(pmpath)]==pmpath): |
4260 |
#skip, it's in the mask |
4261 |
masked=len(pmpath) |
4262 |
return (protected > masked) |
4263 |
|
4264 |
def unmerge(self,pkgfiles=None,trimworld=1,protectfile=None): |
4265 |
# clnpro: Here, protectfile is an opened /db/c/pv/CONTENTS file. |
4266 |
# If a file to unmerge is protected, then it will instead be recorded in protectfile. |
4267 |
# If protectfile=None, it means that we are doing a real unmerge, not just a clean/prune. |
4220 |
if not pkgfiles: |
4268 |
if not pkgfiles: |
4221 |
print "No package files given... Grabbing a set." |
4269 |
print "No package files given... Grabbing a set." |
4222 |
pkgfiles=self.getcontents() |
4270 |
pkgfiles=self.getcontents() |
Lines 4284-4289
Link Here
|
4284 |
if mymd5 != string.lower(pkgfiles[obj][2]): |
4332 |
if mymd5 != string.lower(pkgfiles[obj][2]): |
4285 |
print "--- !md5 ","obj", obj |
4333 |
print "--- !md5 ","obj", obj |
4286 |
continue |
4334 |
continue |
|
|
4335 |
if self.iscleanprotected(obj) and (protectfile != None): |
4336 |
#clnpro: this object must be protected |
4337 |
print "--- clnpro "+str(pkgfiles[obj][0]), obj |
4338 |
contentsentry="obj "+obj+" "+pkgfiles[obj][2]+" "+pkgfiles[obj][1]+"\n" |
4339 |
#print contentsentry |
4340 |
protectfile.write(contentsentry) |
4341 |
continue |
4287 |
try: |
4342 |
try: |
4288 |
os.unlink(obj) |
4343 |
os.unlink(obj) |
4289 |
except (OSError,IOError),e: |
4344 |
except (OSError,IOError),e: |
Lines 4293-4298
Link Here
|
4293 |
if not S_ISFIFO(lstatobj[ST_MODE]): |
4348 |
if not S_ISFIFO(lstatobj[ST_MODE]): |
4294 |
print "--- !fif ","fif", obj |
4349 |
print "--- !fif ","fif", obj |
4295 |
continue |
4350 |
continue |
|
|
4351 |
#if self.iscleanprotected(obj) and (protectfile != None): |
4352 |
# #clnpro: should a fifo be protected? |
4353 |
# #this may introduce duplicates, because they lacks mtime/md5. |
4354 |
# #have to check existing CONTENTS |
4355 |
# print "--- clnpro "+str(pkgfiles[obj][0]), obj |
4356 |
# contentsentry="fif "+obj+"\n" |
4357 |
# print contentsentry |
4358 |
# #protectfile.write(contentsentry) |
4359 |
# continue |
4296 |
try: |
4360 |
try: |
4297 |
os.unlink(obj) |
4361 |
os.unlink(obj) |
4298 |
except (OSError,IOError),e: |
4362 |
except (OSError,IOError),e: |
Lines 4300-4305
Link Here
|
4300 |
print "<<< ","fif",obj |
4364 |
print "<<< ","fif",obj |
4301 |
elif pkgfiles[obj][0]=="dev": |
4365 |
elif pkgfiles[obj][0]=="dev": |
4302 |
print "--- ","dev",obj |
4366 |
print "--- ","dev",obj |
|
|
4367 |
#clnpro: since devs never get cleaned, no need to protect them. |
4303 |
|
4368 |
|
4304 |
#Now, we need to remove symlinks and directories. We'll repeatedly |
4369 |
#Now, we need to remove symlinks and directories. We'll repeatedly |
4305 |
#remove dead symlinks, then directories until we stop making progress. |
4370 |
#remove dead symlinks, then directories until we stop making progress. |
Lines 4316-4322
Link Here
|
4316 |
progress=0 |
4381 |
progress=0 |
4317 |
|
4382 |
|
4318 |
#step 1: remove all the dead symlinks we can... |
4383 |
#step 1: remove all the dead symlinks we can... |
4319 |
|
4384 |
#clnpro:symlinks protection not yet implemented. |
|
|
4385 |
#(what if target does not match? keep or forget?) |
4320 |
pos = 0 |
4386 |
pos = 0 |
4321 |
while pos<len(mysyms): |
4387 |
while pos<len(mysyms): |
4322 |
obj=mysyms[pos] |
4388 |
obj=mysyms[pos] |
Lines 4336-4342
Link Here
|
4336 |
pass |
4402 |
pass |
4337 |
|
4403 |
|
4338 |
#step 2: remove all the empty directories we can... |
4404 |
#step 2: remove all the empty directories we can... |
4339 |
|
4405 |
#clnpro: should dirs be protected? |
|
|
4406 |
#(may introduce duplicates if we don't check existing CONTENTS) |
4340 |
pos = 0 |
4407 |
pos = 0 |
4341 |
while pos<len(mydirs): |
4408 |
while pos<len(mydirs): |
4342 |
obj=mydirs[pos] |
4409 |
obj=mydirs[pos] |
Lines 4500-4512
Link Here
|
4500 |
|
4567 |
|
4501 |
#restore umask |
4568 |
#restore umask |
4502 |
os.umask(prevmask) |
4569 |
os.umask(prevmask) |
4503 |
#if we opened it, close it |
|
|
4504 |
outfile.close() |
4505 |
print |
4570 |
print |
4506 |
if (oldcontents): |
4571 |
if (oldcontents): |
4507 |
print ">>> Safely unmerging already-installed instance..." |
4572 |
print ">>> Safely unmerging already-installed instance..." |
4508 |
self.unmerge(oldcontents,trimworld=0) |
4573 |
self.unmerge(oldcontents,trimworld=0,protectfile=outfile) |
4509 |
print ">>> original instance of package unmerged safely." |
4574 |
print ">>> original instance of package unmerged safely." |
|
|
4575 |
#if we opened it, close it |
4576 |
outfile.close() |
4510 |
# copy "info" files (like SLOT, CFLAGS, etc.) into the database |
4577 |
# copy "info" files (like SLOT, CFLAGS, etc.) into the database |
4511 |
for x in listdir(inforoot): |
4578 |
for x in listdir(inforoot): |
4512 |
self.copyfile(inforoot+"/"+x) |
4579 |
self.copyfile(inforoot+"/"+x) |