aboutsummaryrefslogtreecommitdiff
path: root/waflib/Node.py
diff options
context:
space:
mode:
Diffstat (limited to 'waflib/Node.py')
-rw-r--r--waflib/Node.py506
1 files changed, 506 insertions, 0 deletions
diff --git a/waflib/Node.py b/waflib/Node.py
new file mode 100644
index 0000000..9a86b22
--- /dev/null
+++ b/waflib/Node.py
@@ -0,0 +1,506 @@
+#! /usr/bin/env python
+# encoding: utf-8
+# WARNING! Do not edit! http://waf.googlecode.com/git/docs/wafbook/single.html#_obtaining_the_waf_file
+
+import sys
+if sys.hexversion < 0x020400f0: from sets import Set as set
+import os,re,sys,shutil
+from waflib import Utils,Errors
+exclude_regs='''
+**/*~
+**/#*#
+**/.#*
+**/%*%
+**/._*
+**/CVS
+**/CVS/**
+**/.cvsignore
+**/SCCS
+**/SCCS/**
+**/vssver.scc
+**/.svn
+**/.svn/**
+**/BitKeeper
+**/.git
+**/.git/**
+**/.gitignore
+**/.bzr
+**/.bzrignore
+**/.bzr/**
+**/.hg
+**/.hg/**
+**/_MTN
+**/_MTN/**
+**/.arch-ids
+**/{arch}
+**/_darcs
+**/_darcs/**
+**/.DS_Store'''
+def split_path(path):
+ return path.split('/')
+def split_path_cygwin(path):
+ if path.startswith('//'):
+ ret=path.split('/')[2:]
+ ret[0]='/'+ret[0]
+ return ret
+ return path.split('/')
+re_sp=re.compile('[/\\\\]')
+def split_path_win32(path):
+ if path.startswith('\\\\'):
+ ret=re.split(re_sp,path)[2:]
+ ret[0]='\\'+ret[0]
+ return ret
+ return re.split(re_sp,path)
+if sys.platform=='cygwin':
+ split_path=split_path_cygwin
+elif Utils.is_win32:
+ split_path=split_path_win32
+class Node(object):
+ __slots__=('name','sig','children','parent','cache_abspath','cache_isdir')
+ def __init__(self,name,parent):
+ self.name=name
+ self.parent=parent
+ if parent:
+ if name in parent.children:
+ raise Errors.WafError('node %s exists in the parent files %r already'%(name,parent))
+ parent.children[name]=self
+ def __setstate__(self,data):
+ self.name=data[0]
+ self.parent=data[1]
+ if data[2]is not None:
+ self.children=data[2]
+ if data[3]is not None:
+ self.sig=data[3]
+ def __getstate__(self):
+ return(self.name,self.parent,getattr(self,'children',None),getattr(self,'sig',None))
+ def __str__(self):
+ return self.name
+ def __repr__(self):
+ return self.abspath()
+ def __hash__(self):
+ return id(self)
+ def __eq__(self,node):
+ return id(self)==id(node)
+ def __copy__(self):
+ raise Errors.WafError('nodes are not supposed to be copied')
+ def read(self,flags='r'):
+ return Utils.readf(self.abspath(),flags)
+ def write(self,data,flags='w'):
+ f=None
+ try:
+ f=open(self.abspath(),flags)
+ f.write(data)
+ finally:
+ if f:
+ f.close()
+ def chmod(self,val):
+ os.chmod(self.abspath(),val)
+ def delete(self):
+ try:
+ if getattr(self,'children',None):
+ shutil.rmtree(self.abspath())
+ else:
+ os.unlink(self.abspath())
+ except:
+ pass
+ try:
+ delattr(self,'children')
+ except:
+ pass
+ def suffix(self):
+ k=max(0,self.name.rfind('.'))
+ return self.name[k:]
+ def height(self):
+ d=self
+ val=-1
+ while d:
+ d=d.parent
+ val+=1
+ return val
+ def listdir(self):
+ lst=Utils.listdir(self.abspath())
+ lst.sort()
+ return lst
+ def mkdir(self):
+ if getattr(self,'cache_isdir',None):
+ return
+ try:
+ self.parent.mkdir()
+ except:
+ pass
+ if self.name:
+ try:
+ os.makedirs(self.abspath())
+ except OSError:
+ pass
+ if not os.path.isdir(self.abspath()):
+ raise Errors.WafError('Could not create the directory %s'%self.abspath())
+ try:
+ self.children
+ except:
+ self.children={}
+ self.cache_isdir=True
+ def find_node(self,lst):
+ if isinstance(lst,str):
+ lst=[x for x in split_path(lst)if x and x!='.']
+ cur=self
+ for x in lst:
+ if x=='..':
+ cur=cur.parent or cur
+ continue
+ try:
+ if x in cur.children:
+ cur=cur.children[x]
+ continue
+ except:
+ cur.children={}
+ cur=self.__class__(x,cur)
+ try:
+ os.stat(cur.abspath())
+ except:
+ del cur.parent.children[x]
+ return None
+ ret=cur
+ try:
+ os.stat(ret.abspath())
+ except:
+ del ret.parent.children[ret.name]
+ return None
+ try:
+ while not getattr(cur.parent,'cache_isdir',None):
+ cur=cur.parent
+ cur.cache_isdir=True
+ except AttributeError:
+ pass
+ return ret
+ def make_node(self,lst):
+ if isinstance(lst,str):
+ lst=[x for x in split_path(lst)if x and x!='.']
+ cur=self
+ for x in lst:
+ if x=='..':
+ cur=cur.parent or cur
+ continue
+ if getattr(cur,'children',{}):
+ if x in cur.children:
+ cur=cur.children[x]
+ continue
+ else:
+ cur.children={}
+ cur=self.__class__(x,cur)
+ return cur
+ def search(self,lst):
+ if isinstance(lst,str):
+ lst=[x for x in split_path(lst)if x and x!='.']
+ cur=self
+ try:
+ for x in lst:
+ if x=='..':
+ cur=cur.parent or cur
+ else:
+ cur=cur.children[x]
+ return cur
+ except:
+ pass
+ def path_from(self,node):
+ c1=self
+ c2=node
+ c1h=c1.height()
+ c2h=c2.height()
+ lst=[]
+ up=0
+ while c1h>c2h:
+ lst.append(c1.name)
+ c1=c1.parent
+ c1h-=1
+ while c2h>c1h:
+ up+=1
+ c2=c2.parent
+ c2h-=1
+ while id(c1)!=id(c2):
+ lst.append(c1.name)
+ up+=1
+ c1=c1.parent
+ c2=c2.parent
+ for i in range(up):
+ lst.append('..')
+ lst.reverse()
+ return os.sep.join(lst)or'.'
+ def abspath(self):
+ try:
+ return self.cache_abspath
+ except:
+ pass
+ if os.sep=='/':
+ if not self.parent:
+ val=os.sep
+ elif not self.parent.name:
+ val=os.sep+self.name
+ else:
+ val=self.parent.abspath()+os.sep+self.name
+ else:
+ if not self.parent:
+ val=''
+ elif not self.parent.name:
+ val=self.name+os.sep
+ else:
+ val=self.parent.abspath().rstrip(os.sep)+os.sep+self.name
+ self.cache_abspath=val
+ return val
+ def is_child_of(self,node):
+ p=self
+ diff=self.height()-node.height()
+ while diff>0:
+ diff-=1
+ p=p.parent
+ return id(p)==id(node)
+ def ant_iter(self,accept=None,maxdepth=25,pats=[],dir=False,src=True,remove=True):
+ dircont=self.listdir()
+ dircont.sort()
+ try:
+ lst=set(self.children.keys())
+ if remove:
+ for x in lst-set(dircont):
+ del self.children[x]
+ except:
+ self.children={}
+ for name in dircont:
+ npats=accept(name,pats)
+ if npats and npats[0]:
+ accepted=[]in npats[0]
+ node=self.make_node([name])
+ isdir=os.path.isdir(node.abspath())
+ if accepted:
+ if isdir:
+ if dir:
+ yield node
+ else:
+ if src:
+ yield node
+ if getattr(node,'cache_isdir',None)or isdir:
+ node.cache_isdir=True
+ if maxdepth:
+ for k in node.ant_iter(accept=accept,maxdepth=maxdepth-1,pats=npats,dir=dir,src=src,remove=remove):
+ yield k
+ raise StopIteration
+ def ant_glob(self,*k,**kw):
+ src=kw.get('src',True)
+ dir=kw.get('dir',False)
+ excl=kw.get('excl',exclude_regs)
+ incl=k and k[0]or kw.get('incl','**')
+ def to_pat(s):
+ lst=Utils.to_list(s)
+ ret=[]
+ for x in lst:
+ x=x.replace('\\','/').replace('//','/')
+ if x.endswith('/'):
+ x+='**'
+ lst2=x.split('/')
+ accu=[]
+ for k in lst2:
+ if k=='**':
+ accu.append(k)
+ else:
+ k=k.replace('.','[.]').replace('*','.*').replace('?','.').replace('+','\\+')
+ k='^%s$'%k
+ try:
+ accu.append(re.compile(k))
+ except Exception ,e:
+ raise Errors.WafError("Invalid pattern: %s"%k,e)
+ ret.append(accu)
+ return ret
+ def filtre(name,nn):
+ ret=[]
+ for lst in nn:
+ if not lst:
+ pass
+ elif lst[0]=='**':
+ ret.append(lst)
+ if len(lst)>1:
+ if lst[1].match(name):
+ ret.append(lst[2:])
+ else:
+ ret.append([])
+ elif lst[0].match(name):
+ ret.append(lst[1:])
+ return ret
+ def accept(name,pats):
+ nacc=filtre(name,pats[0])
+ nrej=filtre(name,pats[1])
+ if[]in nrej:
+ nacc=[]
+ return[nacc,nrej]
+ ret=[x for x in self.ant_iter(accept=accept,pats=[to_pat(incl),to_pat(excl)],maxdepth=25,dir=dir,src=src,remove=kw.get('remove',True))]
+ if kw.get('flat',False):
+ return' '.join([x.path_from(self)for x in ret])
+ return ret
+ def find_nodes(self,find_dirs=True,find_files=True,match_fun=lambda x:True):
+ x="""
+ Recursively finds nodes::
+
+ def configure(cnf):
+ cnf.find_nodes()
+
+ :param find_dirs: whether to return directories
+ :param find_files: whether to return files
+ :param match_fun: matching function, taking a node as parameter
+ :rtype generator
+ :return: a generator that iterates over all the requested files
+ """
+ files=self.listdir()
+ for f in files:
+ node=self.make_node([f])
+ if os.path.isdir(node.abspath()):
+ if find_dirs and match_fun(node):
+ yield node
+ gen=node.find_nodes(find_dirs,find_files,match_fun)
+ for g in gen:
+ yield g
+ else:
+ if find_files and match_fun(node):
+ yield node
+ def is_src(self):
+ cur=self
+ x=id(self.ctx.srcnode)
+ y=id(self.ctx.bldnode)
+ while cur.parent:
+ if id(cur)==y:
+ return False
+ if id(cur)==x:
+ return True
+ cur=cur.parent
+ return False
+ def is_bld(self):
+ cur=self
+ y=id(self.ctx.bldnode)
+ while cur.parent:
+ if id(cur)==y:
+ return True
+ cur=cur.parent
+ return False
+ def get_src(self):
+ cur=self
+ x=id(self.ctx.srcnode)
+ y=id(self.ctx.bldnode)
+ lst=[]
+ while cur.parent:
+ if id(cur)==y:
+ lst.reverse()
+ return self.ctx.srcnode.make_node(lst)
+ if id(cur)==x:
+ return self
+ lst.append(cur.name)
+ cur=cur.parent
+ return self
+ def get_bld(self):
+ cur=self
+ x=id(self.ctx.srcnode)
+ y=id(self.ctx.bldnode)
+ lst=[]
+ while cur.parent:
+ if id(cur)==y:
+ return self
+ if id(cur)==x:
+ lst.reverse()
+ return self.ctx.bldnode.make_node(lst)
+ lst.append(cur.name)
+ cur=cur.parent
+ lst.reverse()
+ if lst and Utils.is_win32 and len(lst[0])==2 and lst[0].endswith(':'):
+ lst[0]=lst[0][0]
+ return self.ctx.bldnode.make_node(['__root__']+lst)
+ def find_resource(self,lst):
+ if isinstance(lst,str):
+ lst=[x for x in split_path(lst)if x and x!='.']
+ node=self.get_bld().search(lst)
+ if not node:
+ self=self.get_src()
+ node=self.find_node(lst)
+ try:
+ pat=node.abspath()
+ if os.path.isdir(pat):
+ return None
+ except:
+ pass
+ return node
+ def find_or_declare(self,lst):
+ if isinstance(lst,str):
+ lst=[x for x in split_path(lst)if x and x!='.']
+ node=self.get_bld().search(lst)
+ if node:
+ if not os.path.isfile(node.abspath()):
+ node.sig=None
+ try:
+ node.parent.mkdir()
+ except:
+ pass
+ return node
+ self=self.get_src()
+ node=self.find_node(lst)
+ if node:
+ if not os.path.isfile(node.abspath()):
+ node.sig=None
+ try:
+ node.parent.mkdir()
+ except:
+ pass
+ return node
+ node=self.get_bld().make_node(lst)
+ node.parent.mkdir()
+ return node
+ def find_dir(self,lst):
+ if isinstance(lst,str):
+ lst=[x for x in split_path(lst)if x and x!='.']
+ node=self.find_node(lst)
+ try:
+ if not os.path.isdir(node.abspath()):
+ return None
+ except(OSError,AttributeError):
+ return None
+ return node
+ def change_ext(self,ext,ext_in=None):
+ name=self.name
+ if ext_in is None:
+ k=name.rfind('.')
+ if k>=0:
+ name=name[:k]+ext
+ else:
+ name=name+ext
+ else:
+ name=name[:-len(ext_in)]+ext
+ return self.parent.find_or_declare([name])
+ def nice_path(self,env=None):
+ return self.path_from(self.ctx.launch_node())
+ def bldpath(self):
+ return self.path_from(self.ctx.bldnode)
+ def srcpath(self):
+ return self.path_from(self.ctx.srcnode)
+ def relpath(self):
+ cur=self
+ x=id(self.ctx.bldnode)
+ while cur.parent:
+ if id(cur)==x:
+ return self.bldpath()
+ cur=cur.parent
+ return self.srcpath()
+ def bld_dir(self):
+ return self.parent.bldpath()
+ def bld_base(self):
+ s=os.path.splitext(self.name)[0]
+ return self.bld_dir()+os.sep+s
+ def get_bld_sig(self):
+ try:
+ ret=self.ctx.hash_cache[id(self)]
+ except KeyError:
+ pass
+ except AttributeError:
+ self.ctx.hash_cache={}
+ else:
+ return ret
+ if not self.is_bld()or self.ctx.bldnode is self.ctx.srcnode:
+ self.sig=Utils.h_file(self.abspath())
+ self.ctx.hash_cache[id(self)]=ret=self.sig
+ return ret
+pickle_lock=Utils.threading.Lock()
+class Nod3(Node):
+ pass