79d6bbfcb6585eb9de4e4429c59063bd7c1027fd
[aubio.git] / waflib / Node.py
1 #! /usr/bin/env python
2 # encoding: utf-8
3 # WARNING! Do not edit! http://waf.googlecode.com/git/docs/wafbook/single.html#_obtaining_the_waf_file
4
5 import os,re,sys,shutil
6 from waflib import Utils,Errors
7 exclude_regs='''
8 **/*~
9 **/#*#
10 **/.#*
11 **/%*%
12 **/._*
13 **/CVS
14 **/CVS/**
15 **/.cvsignore
16 **/SCCS
17 **/SCCS/**
18 **/vssver.scc
19 **/.svn
20 **/.svn/**
21 **/BitKeeper
22 **/.git
23 **/.git/**
24 **/.gitignore
25 **/.bzr
26 **/.bzrignore
27 **/.bzr/**
28 **/.hg
29 **/.hg/**
30 **/_MTN
31 **/_MTN/**
32 **/.arch-ids
33 **/{arch}
34 **/_darcs
35 **/_darcs/**
36 **/.DS_Store'''
37 def split_path(path):
38         return path.split('/')
39 def split_path_cygwin(path):
40         if path.startswith('//'):
41                 ret=path.split('/')[2:]
42                 ret[0]='/'+ret[0]
43                 return ret
44         return path.split('/')
45 re_sp=re.compile('[/\\\\]')
46 def split_path_win32(path):
47         if path.startswith('\\\\'):
48                 ret=re.split(re_sp,path)[2:]
49                 ret[0]='\\'+ret[0]
50                 return ret
51         return re.split(re_sp,path)
52 if sys.platform=='cygwin':
53         split_path=split_path_cygwin
54 elif Utils.is_win32:
55         split_path=split_path_win32
56 class Node(object):
57         __slots__=('name','sig','children','parent','cache_abspath','cache_isdir','cache_sig')
58         def __init__(self,name,parent):
59                 self.name=name
60                 self.parent=parent
61                 if parent:
62                         if name in parent.children:
63                                 raise Errors.WafError('node %s exists in the parent files %r already'%(name,parent))
64                         parent.children[name]=self
65         def __setstate__(self,data):
66                 self.name=data[0]
67                 self.parent=data[1]
68                 if data[2]is not None:
69                         self.children=data[2]
70                 if data[3]is not None:
71                         self.sig=data[3]
72         def __getstate__(self):
73                 return(self.name,self.parent,getattr(self,'children',None),getattr(self,'sig',None))
74         def __str__(self):
75                 return self.name
76         def __repr__(self):
77                 return self.abspath()
78         def __hash__(self):
79                 return id(self)
80         def __eq__(self,node):
81                 return id(self)==id(node)
82         def __copy__(self):
83                 raise Errors.WafError('nodes are not supposed to be copied')
84         def read(self,flags='r',encoding='ISO8859-1'):
85                 return Utils.readf(self.abspath(),flags,encoding)
86         def write(self,data,flags='w',encoding='ISO8859-1'):
87                 Utils.writef(self.abspath(),data,flags,encoding)
88         def chmod(self,val):
89                 os.chmod(self.abspath(),val)
90         def delete(self):
91                 try:
92                         if getattr(self,'children',None):
93                                 shutil.rmtree(self.abspath())
94                         else:
95                                 os.unlink(self.abspath())
96                 except OSError:
97                         pass
98                 self.evict()
99         def evict(self):
100                 del self.parent.children[self.name]
101         def suffix(self):
102                 k=max(0,self.name.rfind('.'))
103                 return self.name[k:]
104         def height(self):
105                 d=self
106                 val=-1
107                 while d:
108                         d=d.parent
109                         val+=1
110                 return val
111         def listdir(self):
112                 lst=Utils.listdir(self.abspath())
113                 lst.sort()
114                 return lst
115         def mkdir(self):
116                 if getattr(self,'cache_isdir',None):
117                         return
118                 try:
119                         self.parent.mkdir()
120                 except OSError:
121                         pass
122                 if self.name:
123                         try:
124                                 os.makedirs(self.abspath())
125                         except OSError:
126                                 pass
127                         if not os.path.isdir(self.abspath()):
128                                 raise Errors.WafError('Could not create the directory %s'%self.abspath())
129                         try:
130                                 self.children
131                         except AttributeError:
132                                 self.children={}
133                 self.cache_isdir=True
134         def find_node(self,lst):
135                 if isinstance(lst,str):
136                         lst=[x for x in split_path(lst)if x and x!='.']
137                 cur=self
138                 for x in lst:
139                         if x=='..':
140                                 cur=cur.parent or cur
141                                 continue
142                         try:
143                                 ch=cur.children
144                         except AttributeError:
145                                 cur.children={}
146                         else:
147                                 try:
148                                         cur=cur.children[x]
149                                         continue
150                                 except KeyError:
151                                         pass
152                         cur=self.__class__(x,cur)
153                         try:
154                                 os.stat(cur.abspath())
155                         except OSError:
156                                 cur.evict()
157                                 return None
158                 ret=cur
159                 try:
160                         os.stat(ret.abspath())
161                 except OSError:
162                         ret.evict()
163                         return None
164                 try:
165                         while not getattr(cur.parent,'cache_isdir',None):
166                                 cur=cur.parent
167                                 cur.cache_isdir=True
168                 except AttributeError:
169                         pass
170                 return ret
171         def make_node(self,lst):
172                 if isinstance(lst,str):
173                         lst=[x for x in split_path(lst)if x and x!='.']
174                 cur=self
175                 for x in lst:
176                         if x=='..':
177                                 cur=cur.parent or cur
178                                 continue
179                         if getattr(cur,'children',{}):
180                                 if x in cur.children:
181                                         cur=cur.children[x]
182                                         continue
183                         else:
184                                 cur.children={}
185                         cur=self.__class__(x,cur)
186                 return cur
187         def search_node(self,lst):
188                 if isinstance(lst,str):
189                         lst=[x for x in split_path(lst)if x and x!='.']
190                 cur=self
191                 for x in lst:
192                         if x=='..':
193                                 cur=cur.parent or cur
194                         else:
195                                 try:
196                                         cur=cur.children[x]
197                                 except(AttributeError,KeyError):
198                                         return None
199                 return cur
200         def path_from(self,node):
201                 c1=self
202                 c2=node
203                 c1h=c1.height()
204                 c2h=c2.height()
205                 lst=[]
206                 up=0
207                 while c1h>c2h:
208                         lst.append(c1.name)
209                         c1=c1.parent
210                         c1h-=1
211                 while c2h>c1h:
212                         up+=1
213                         c2=c2.parent
214                         c2h-=1
215                 while id(c1)!=id(c2):
216                         lst.append(c1.name)
217                         up+=1
218                         c1=c1.parent
219                         c2=c2.parent
220                 for i in range(up):
221                         lst.append('..')
222                 lst.reverse()
223                 return os.sep.join(lst)or'.'
224         def abspath(self):
225                 try:
226                         return self.cache_abspath
227                 except AttributeError:
228                         pass
229                 if os.sep=='/':
230                         if not self.parent:
231                                 val=os.sep
232                         elif not self.parent.name:
233                                 val=os.sep+self.name
234                         else:
235                                 val=self.parent.abspath()+os.sep+self.name
236                 else:
237                         if not self.parent:
238                                 val=''
239                         elif not self.parent.name:
240                                 val=self.name+os.sep
241                         else:
242                                 val=self.parent.abspath().rstrip(os.sep)+os.sep+self.name
243                 self.cache_abspath=val
244                 return val
245         def is_child_of(self,node):
246                 p=self
247                 diff=self.height()-node.height()
248                 while diff>0:
249                         diff-=1
250                         p=p.parent
251                 return id(p)==id(node)
252         def ant_iter(self,accept=None,maxdepth=25,pats=[],dir=False,src=True,remove=True):
253                 dircont=self.listdir()
254                 dircont.sort()
255                 try:
256                         lst=set(self.children.keys())
257                 except AttributeError:
258                         self.children={}
259                 else:
260                         if remove:
261                                 for x in lst-set(dircont):
262                                         self.children[x].evict()
263                 for name in dircont:
264                         npats=accept(name,pats)
265                         if npats and npats[0]:
266                                 accepted=[]in npats[0]
267                                 node=self.make_node([name])
268                                 isdir=os.path.isdir(node.abspath())
269                                 if accepted:
270                                         if isdir:
271                                                 if dir:
272                                                         yield node
273                                         else:
274                                                 if src:
275                                                         yield node
276                                 if getattr(node,'cache_isdir',None)or isdir:
277                                         node.cache_isdir=True
278                                         if maxdepth:
279                                                 for k in node.ant_iter(accept=accept,maxdepth=maxdepth-1,pats=npats,dir=dir,src=src,remove=remove):
280                                                         yield k
281                 raise StopIteration
282         def ant_glob(self,*k,**kw):
283                 src=kw.get('src',True)
284                 dir=kw.get('dir',False)
285                 excl=kw.get('excl',exclude_regs)
286                 incl=k and k[0]or kw.get('incl','**')
287                 reflags=kw.get('ignorecase',0)and re.I
288                 def to_pat(s):
289                         lst=Utils.to_list(s)
290                         ret=[]
291                         for x in lst:
292                                 x=x.replace('\\','/').replace('//','/')
293                                 if x.endswith('/'):
294                                         x+='**'
295                                 lst2=x.split('/')
296                                 accu=[]
297                                 for k in lst2:
298                                         if k=='**':
299                                                 accu.append(k)
300                                         else:
301                                                 k=k.replace('.','[.]').replace('*','.*').replace('?','.').replace('+','\\+')
302                                                 k='^%s$'%k
303                                                 try:
304                                                         accu.append(re.compile(k,flags=reflags))
305                                                 except Exception ,e:
306                                                         raise Errors.WafError("Invalid pattern: %s"%k,e)
307                                 ret.append(accu)
308                         return ret
309                 def filtre(name,nn):
310                         ret=[]
311                         for lst in nn:
312                                 if not lst:
313                                         pass
314                                 elif lst[0]=='**':
315                                         ret.append(lst)
316                                         if len(lst)>1:
317                                                 if lst[1].match(name):
318                                                         ret.append(lst[2:])
319                                         else:
320                                                 ret.append([])
321                                 elif lst[0].match(name):
322                                         ret.append(lst[1:])
323                         return ret
324                 def accept(name,pats):
325                         nacc=filtre(name,pats[0])
326                         nrej=filtre(name,pats[1])
327                         if[]in nrej:
328                                 nacc=[]
329                         return[nacc,nrej]
330                 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))]
331                 if kw.get('flat',False):
332                         return' '.join([x.path_from(self)for x in ret])
333                 return ret
334         def is_src(self):
335                 cur=self
336                 x=id(self.ctx.srcnode)
337                 y=id(self.ctx.bldnode)
338                 while cur.parent:
339                         if id(cur)==y:
340                                 return False
341                         if id(cur)==x:
342                                 return True
343                         cur=cur.parent
344                 return False
345         def is_bld(self):
346                 cur=self
347                 y=id(self.ctx.bldnode)
348                 while cur.parent:
349                         if id(cur)==y:
350                                 return True
351                         cur=cur.parent
352                 return False
353         def get_src(self):
354                 cur=self
355                 x=id(self.ctx.srcnode)
356                 y=id(self.ctx.bldnode)
357                 lst=[]
358                 while cur.parent:
359                         if id(cur)==y:
360                                 lst.reverse()
361                                 return self.ctx.srcnode.make_node(lst)
362                         if id(cur)==x:
363                                 return self
364                         lst.append(cur.name)
365                         cur=cur.parent
366                 return self
367         def get_bld(self):
368                 cur=self
369                 x=id(self.ctx.srcnode)
370                 y=id(self.ctx.bldnode)
371                 lst=[]
372                 while cur.parent:
373                         if id(cur)==y:
374                                 return self
375                         if id(cur)==x:
376                                 lst.reverse()
377                                 return self.ctx.bldnode.make_node(lst)
378                         lst.append(cur.name)
379                         cur=cur.parent
380                 lst.reverse()
381                 if lst and Utils.is_win32 and len(lst[0])==2 and lst[0].endswith(':'):
382                         lst[0]=lst[0][0]
383                 return self.ctx.bldnode.make_node(['__root__']+lst)
384         def find_resource(self,lst):
385                 if isinstance(lst,str):
386                         lst=[x for x in split_path(lst)if x and x!='.']
387                 node=self.get_bld().search_node(lst)
388                 if not node:
389                         self=self.get_src()
390                         node=self.find_node(lst)
391                 if node:
392                         if os.path.isdir(node.abspath()):
393                                 return None
394                 return node
395         def find_or_declare(self,lst):
396                 if isinstance(lst,str):
397                         lst=[x for x in split_path(lst)if x and x!='.']
398                 node=self.get_bld().search_node(lst)
399                 if node:
400                         if not os.path.isfile(node.abspath()):
401                                 node.sig=None
402                                 node.parent.mkdir()
403                         return node
404                 self=self.get_src()
405                 node=self.find_node(lst)
406                 if node:
407                         if not os.path.isfile(node.abspath()):
408                                 node.sig=None
409                                 node.parent.mkdir()
410                         return node
411                 node=self.get_bld().make_node(lst)
412                 node.parent.mkdir()
413                 return node
414         def find_dir(self,lst):
415                 if isinstance(lst,str):
416                         lst=[x for x in split_path(lst)if x and x!='.']
417                 node=self.find_node(lst)
418                 try:
419                         if not os.path.isdir(node.abspath()):
420                                 return None
421                 except(OSError,AttributeError):
422                         return None
423                 return node
424         def change_ext(self,ext,ext_in=None):
425                 name=self.name
426                 if ext_in is None:
427                         k=name.rfind('.')
428                         if k>=0:
429                                 name=name[:k]+ext
430                         else:
431                                 name=name+ext
432                 else:
433                         name=name[:-len(ext_in)]+ext
434                 return self.parent.find_or_declare([name])
435         def nice_path(self,env=None):
436                 return self.path_from(self.ctx.launch_node())
437         def bldpath(self):
438                 return self.path_from(self.ctx.bldnode)
439         def srcpath(self):
440                 return self.path_from(self.ctx.srcnode)
441         def relpath(self):
442                 cur=self
443                 x=id(self.ctx.bldnode)
444                 while cur.parent:
445                         if id(cur)==x:
446                                 return self.bldpath()
447                         cur=cur.parent
448                 return self.srcpath()
449         def bld_dir(self):
450                 return self.parent.bldpath()
451         def bld_base(self):
452                 s=os.path.splitext(self.name)[0]
453                 return self.bld_dir()+os.sep+s
454         def get_bld_sig(self):
455                 try:
456                         return self.cache_sig
457                 except AttributeError:
458                         pass
459                 if not self.is_bld()or self.ctx.bldnode is self.ctx.srcnode:
460                         self.sig=Utils.h_file(self.abspath())
461                 self.cache_sig=ret=self.sig
462                 return ret
463         search=search_node
464 pickle_lock=Utils.threading.Lock()
465 class Nod3(Node):
466         pass