summaryrefslogtreecommitdiffstats
path: root/bitbake
diff options
context:
space:
mode:
authorRichard Purdie <richard.purdie@linuxfoundation.org>2018-10-17 10:51:19 +0100
committerRichard Purdie <richard.purdie@linuxfoundation.org>2018-10-18 10:59:27 +0100
commitf5181b36d66fb8d92b2eb9072e76aa4c13fccb33 (patch)
treedad67e3f2ae9ddddf0069408386f23542d9c2e01 /bitbake
parent58e3f45d4b7d69d663ce7c94933d4da7b5f071e3 (diff)
downloadpoky-f5181b36d66fb8d92b2eb9072e76aa4c13fccb33.tar.gz
bitbake: data_smart: Fix expand_cache and _remove operator interaction issues
The contents of the expand_cache is meant to match the return value of getVarFlag() but the implementation was mostly in expandWithRefs(). If an incorrect key was passed to expandWithRefs(), or a variable was only partially expanded with no remove processing, the cache could become corrupted. Move the code to getVarFlag making the data lifecycle very clear, meaning other calls to expandWithRefs() cannot corrupt the cache. The expand_cache reset code needs to be moved ahead of any remote data connectors too, since the expand_cache is now on the local side of the connection. (Bitbake rev: a039052f9b680eae53f3f12b7381b945f1d69253) Signed-off-by: Richard Purdie <richard.purdie@linuxfoundation.org>
Diffstat (limited to 'bitbake')
-rw-r--r--bitbake/lib/bb/data_smart.py50
1 files changed, 23 insertions, 27 deletions
diff --git a/bitbake/lib/bb/data_smart.py b/bitbake/lib/bb/data_smart.py
index 7b2c0a8943..ecc71bd644 100644
--- a/bitbake/lib/bb/data_smart.py
+++ b/bitbake/lib/bb/data_smart.py
@@ -105,11 +105,7 @@ class VariableParse:
105 if self.varname and key: 105 if self.varname and key:
106 if self.varname == key: 106 if self.varname == key:
107 raise Exception("variable %s references itself!" % self.varname) 107 raise Exception("variable %s references itself!" % self.varname)
108 if key in self.d.expand_cache: 108 var = self.d.getVarFlag(key, "_content")
109 varparse = self.d.expand_cache[key]
110 var = varparse.value
111 else:
112 var = self.d.getVarFlag(key, "_content")
113 self.references.add(key) 109 self.references.add(key)
114 if var is not None: 110 if var is not None:
115 return var 111 return var
@@ -412,9 +408,6 @@ class DataSmart(MutableMapping):
412 if not isinstance(s, str): # sanity check 408 if not isinstance(s, str): # sanity check
413 return VariableParse(varname, self, s) 409 return VariableParse(varname, self, s)
414 410
415 if varname and varname in self.expand_cache:
416 return self.expand_cache[varname]
417
418 varparse = VariableParse(varname, self) 411 varparse = VariableParse(varname, self)
419 412
420 while s.find('${') != -1: 413 while s.find('${') != -1:
@@ -438,9 +431,6 @@ class DataSmart(MutableMapping):
438 431
439 varparse.value = s 432 varparse.value = s
440 433
441 if varname:
442 self.expand_cache[varname] = varparse
443
444 return varparse 434 return varparse
445 435
446 def expand(self, s, varname = None): 436 def expand(self, s, varname = None):
@@ -509,6 +499,7 @@ class DataSmart(MutableMapping):
509 499
510 def setVar(self, var, value, **loginfo): 500 def setVar(self, var, value, **loginfo):
511 #print("var=" + str(var) + " val=" + str(value)) 501 #print("var=" + str(var) + " val=" + str(value))
502 self.expand_cache = {}
512 parsing=False 503 parsing=False
513 if 'parsing' in loginfo: 504 if 'parsing' in loginfo:
514 parsing=True 505 parsing=True
@@ -521,7 +512,7 @@ class DataSmart(MutableMapping):
521 512
522 if 'op' not in loginfo: 513 if 'op' not in loginfo:
523 loginfo['op'] = "set" 514 loginfo['op'] = "set"
524 self.expand_cache = {} 515
525 match = __setvar_regexp__.match(var) 516 match = __setvar_regexp__.match(var)
526 if match and match.group("keyword") in __setvar_keyword__: 517 if match and match.group("keyword") in __setvar_keyword__:
527 base = match.group('base') 518 base = match.group('base')
@@ -672,6 +663,7 @@ class DataSmart(MutableMapping):
672 self.setVar(var + "_prepend", value, ignore=True, parsing=True) 663 self.setVar(var + "_prepend", value, ignore=True, parsing=True)
673 664
674 def delVar(self, var, **loginfo): 665 def delVar(self, var, **loginfo):
666 self.expand_cache = {}
675 if '_remote_data' in self.dict: 667 if '_remote_data' in self.dict:
676 connector = self.dict["_remote_data"]["_content"] 668 connector = self.dict["_remote_data"]["_content"]
677 res = connector.delVar(var) 669 res = connector.delVar(var)
@@ -681,7 +673,6 @@ class DataSmart(MutableMapping):
681 loginfo['detail'] = "" 673 loginfo['detail'] = ""
682 loginfo['op'] = 'del' 674 loginfo['op'] = 'del'
683 self.varhistory.record(**loginfo) 675 self.varhistory.record(**loginfo)
684 self.expand_cache = {}
685 self.dict[var] = {} 676 self.dict[var] = {}
686 if var in self.overridedata: 677 if var in self.overridedata:
687 del self.overridedata[var] 678 del self.overridedata[var]
@@ -704,13 +695,13 @@ class DataSmart(MutableMapping):
704 override = None 695 override = None
705 696
706 def setVarFlag(self, var, flag, value, **loginfo): 697 def setVarFlag(self, var, flag, value, **loginfo):
698 self.expand_cache = {}
707 if '_remote_data' in self.dict: 699 if '_remote_data' in self.dict:
708 connector = self.dict["_remote_data"]["_content"] 700 connector = self.dict["_remote_data"]["_content"]
709 res = connector.setVarFlag(var, flag, value) 701 res = connector.setVarFlag(var, flag, value)
710 if not res: 702 if not res:
711 return 703 return
712 704
713 self.expand_cache = {}
714 if 'op' not in loginfo: 705 if 'op' not in loginfo:
715 loginfo['op'] = "set" 706 loginfo['op'] = "set"
716 loginfo['flag'] = flag 707 loginfo['flag'] = flag
@@ -732,6 +723,17 @@ class DataSmart(MutableMapping):
732 self.dict["__exportlist"]["_content"].add(var) 723 self.dict["__exportlist"]["_content"].add(var)
733 724
734 def getVarFlag(self, var, flag, expand=True, noweakdefault=False, parsing=False): 725 def getVarFlag(self, var, flag, expand=True, noweakdefault=False, parsing=False):
726 if flag == "_content":
727 cachename = var
728 else:
729 if not flag:
730 bb.warn("Calling getVarFlag with flag unset is invalid")
731 return None
732 cachename = var + "[" + flag + "]"
733
734 if expand and cachename in self.expand_cache:
735 return self.expand_cache[cachename].value
736
735 local_var, overridedata = self._findVar(var) 737 local_var, overridedata = self._findVar(var)
736 value = None 738 value = None
737 if flag == "_content" and overridedata is not None and not parsing: 739 if flag == "_content" and overridedata is not None and not parsing:
@@ -796,14 +798,9 @@ class DataSmart(MutableMapping):
796 if match: 798 if match:
797 value = r + value 799 value = r + value
798 800
799 if expand and value: 801 if expand:
800 # Only getvar (flag == _content) hits the expand cache 802 self.expand_cache[cachename] = self.expandWithRefs(value, cachename)
801 cachename = None 803 value = self.expand_cache[cachename].value
802 if flag == "_content":
803 cachename = var
804 else:
805 cachename = var + "[" + flag + "]"
806 value = self.expand(value, cachename)
807 804
808 if value and flag == "_content" and local_var is not None and "_remove" in local_var and not parsing: 805 if value and flag == "_content" and local_var is not None and "_remove" in local_var and not parsing:
809 removes = [] 806 removes = []
@@ -821,20 +818,19 @@ class DataSmart(MutableMapping):
821 filtered = filter(lambda v: v not in removes, 818 filtered = filter(lambda v: v not in removes,
822 __whitespace_split__.split(value)) 819 __whitespace_split__.split(value))
823 value = "".join(filtered) 820 value = "".join(filtered)
824 if expand and var in self.expand_cache: 821 if expand and cachename in self.expand_cache:
825 # We need to ensure the expand cache has the correct value 822 self.expand_cache[cachename].value = value
826 # flag == "_content" here 823
827 self.expand_cache[var].value = value
828 return value 824 return value
829 825
830 def delVarFlag(self, var, flag, **loginfo): 826 def delVarFlag(self, var, flag, **loginfo):
827 self.expand_cache = {}
831 if '_remote_data' in self.dict: 828 if '_remote_data' in self.dict:
832 connector = self.dict["_remote_data"]["_content"] 829 connector = self.dict["_remote_data"]["_content"]
833 res = connector.delVarFlag(var, flag) 830 res = connector.delVarFlag(var, flag)
834 if not res: 831 if not res:
835 return 832 return
836 833
837 self.expand_cache = {}
838 local_var, _ = self._findVar(var) 834 local_var, _ = self._findVar(var)
839 if not local_var: 835 if not local_var:
840 return 836 return