1 # ex:ts=4:sw=4:sts=4:et
2 # -*- tab-width: 4; c-basic-offset: 4; indent-tabs-mode: nil -*-
4 BitBake Smart Dictionary Implementation
6 Functions for interacting with the data structure used by the
9 Copyright (C) 2003, 2004 Chris Larson
10 Copyright (C) 2004, 2005 Seb Frankengul
11 Copyright (C) 2005, 2006 Holger Hans Peter Freyther
12 Copyright (C) 2005 Uli Luckas
13 Copyright (C) 2005 ROAD GmbH
15 This program is free software; you can redistribute it and/or modify it under
16 the terms of the GNU General Public License as published by the Free Software
17 Foundation; either version 2 of the License, or (at your option) any later
20 This program is distributed in the hope that it will be useful, but WITHOUT
21 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
22 FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
24 You should have received a copy of the GNU General Public License along with
25 this program; if not, write to the Free Software Foundation, Inc., 59 Temple
26 Place, Suite 330, Boston, MA 02111-1307 USA.
28 Based on functions from the base bb module, Copyright 2003 Holger Schurig
31 import copy, os, re, sys, time, types
32 from bb import note, debug, error, fatal, utils, methodpool
33 from COW import COWDictBase
35 from new import classobj
38 __setvar_keyword__ = ["_append","_prepend"]
39 __setvar_regexp__ = re.compile('(?P<base>.*?)(?P<keyword>_append|_prepend)(_(?P<add>.*))?')
40 __expand_var_regexp__ = re.compile(r"\${[^{}]+}")
41 __expand_python_regexp__ = re.compile(r"\${@.+?}")
45 def __init__(self, special = COWDictBase.copy(), seen = COWDictBase.copy() ):
48 # cookie monster tribute
49 self._special_values = special
50 self._seen_overrides = seen
52 def expand(self,s, varname):
54 key = match.group()[2:-1]
57 raise Exception("variable %s references itself!" % varname)
58 var = self.getVar(key, 1)
64 def python_sub(match):
66 code = match.group()[3:-1]
69 if type(s) == types.IntType: s = str(s)
72 if type(s) is not types.StringType: # sanity check
75 while s.find('$') != -1:
78 s = __expand_var_regexp__.sub(var_sub, s)
79 s = __expand_python_regexp__.sub(python_sub, s)
81 if type(s) is not types.StringType: # sanity check
82 error('expansion of %s returned non-string %s' % (olds, s))
83 except KeyboardInterrupt:
86 note("%s:%s while evaluating:\n%s" % (sys.exc_info()[0], sys.exc_info()[1], s))
90 def initVar(self, var):
91 if not var in self.dict:
94 def _findVar(self,var):
97 while (_dest and var not in _dest):
98 if not "_data" in _dest:
101 _dest = _dest["_data"]
103 if _dest and var in _dest:
107 def _makeShadowCopy(self, var):
111 local_var = self._findVar(var)
114 self.dict[var] = copy.copy(local_var)
118 def setVar(self,var,value):
119 match = __setvar_regexp__.match(var)
120 if match and match.group("keyword") in __setvar_keyword__:
121 base = match.group('base')
122 keyword = match.group("keyword")
123 override = match.group('add')
124 l = self.getVarFlag(base, keyword) or []
125 l.append([value, override])
126 self.setVarFlag(base, keyword, l)
128 # todo make sure keyword is not __doc__ or __module__
129 # pay the cookie monster
131 self._special_values[keyword].add( base )
133 self._special_values[keyword] = Set()
134 self._special_values[keyword].add( base )
138 if not var in self.dict:
139 self._makeShadowCopy(var)
140 if self.getVarFlag(var, 'matchesenv'):
141 self.delVarFlag(var, 'matchesenv')
142 self.setVarFlag(var, 'export', 1)
144 # more cookies for the cookie monster
146 override = var[var.rfind('_')+1:]
147 if not self._seen_overrides.has_key(override):
148 self._seen_overrides[override] = Set()
149 self._seen_overrides[override].add( var )
152 self.dict[var]["content"] = value
154 def getVar(self,var,exp):
155 value = self.getVarFlag(var,"content")
158 return self.expand(value,var)
161 def delVar(self,var):
164 def setVarFlag(self,var,flag,flagvalue):
165 if not var in self.dict:
166 self._makeShadowCopy(var)
167 self.dict[var][flag] = flagvalue
169 def getVarFlag(self,var,flag):
170 local_var = self._findVar(var)
172 if flag in local_var:
173 return copy.copy(local_var[flag])
176 def delVarFlag(self,var,flag):
177 local_var = self._findVar(var)
180 if not var in self.dict:
181 self._makeShadowCopy(var)
183 if var in self.dict and flag in self.dict[var]:
184 del self.dict[var][flag]
186 def setVarFlags(self,var,flags):
187 if not var in self.dict:
188 self._makeShadowCopy(var)
190 for i in flags.keys():
193 self.dict[var][i] = flags[i]
195 def getVarFlags(self,var):
196 local_var = self._findVar(var)
200 for i in self.dict[var].keys():
203 flags[i] = self.dict[var][i]
210 def delVarFlags(self,var):
211 if not var in self.dict:
212 self._makeShadowCopy(var)
217 # try to save the content
218 if "content" in self.dict[var]:
219 content = self.dict[var]["content"]
221 self.dict[var]["content"] = content
226 def createCopy(self):
228 Create a copy of self by setting _data to self
230 # we really want this to be a DataSmart...
231 data = DataSmart(seen=self._seen_overrides.copy(), special=self._special_values.copy())
232 data.dict["_data"] = self.dict
240 _keys(d["_data"],mykey)
246 _keys(self.dict,keytab)
249 def __getitem__(self,item):
250 #print "Warning deprecated"
251 return self.getVar(item, False)
253 def __setitem__(self,var,data):
254 #print "Warning deprecated"
255 self.setVar(var,data)