Lines Matching +full:repo +full:- +full:name
3 # -*- tab-width: 4; c-basic-offset: 4; indent-tabs-mode: nil -*-
6 # Authored-by: Yu Ke <ke.yu@intel.com>
10 # SPDX-License-Identifier: GPL-2.0-only
42 # Repo not created yet (i.e. during init) so just assume master
44 branchname = runcmd("git symbolic-ref HEAD 2>/dev/null", repodir).strip()
55 For an example config file, see combo-layer.conf.example
62 def readsection(parser, section, repo): argument
63 for (name, value) in parser.items(section):
65 self.repos[repo][name] = eval(value.strip("@"))
70 if name in types:
71 value = getattr(parser, 'get' + types[name])(section, name)
72 self.repos[repo][name] = value
75 for (name, value) in parser.items(section):
76 if name == "commit_msg":
88 for repo in self.parser.sections():
89 if repo == "combo-layer-settings":
91 readglobalsection(self.parser, repo)
93 self.repos[repo] = {}
94 readsection(self.parser, repo, repo)
101 lcfile = self.conffile.replace('.conf', '-local.conf')
116 repo = sectionvals[0]
120 repo = section
121 if repo in self.repos:
122 readsection(self.localparser, section, repo)
124 def update(self, repo, option, value, initmode=False): argument
127 if self.localparser and not self.parser.has_option(repo, option):
129 section = "%s|%s" % (repo, self.combobranch)
135 section = repo
140 self.repos[repo][option] = value
148 for name in self.repos:
150 if option not in self.repos[name]:
151 msg = "%s\nOption %s is not defined for component %s" %(msg, option, name)
157 dest_dir = os.path.normpath(self.repos[name].get("dest_dir", "."))
158 self.repos[name]["dest_dir"] = "." if not dest_dir else dest_dir
167 …logger.error("ERROR: patchutils package is missing, please install it (e.g. # apt-get install patc…
190 output = err.read().decode('utf-8')
196 Update the last_revision config option for each repo with the latest
198 combo-layer.
202 for name in repos:
203 repo = conf.repos[name]
204 ldir = repo['local_repo_dir']
205 branch = repo.get('branch', "master")
207 lastrev = runcmd('git rev-parse origin/%s' % branch, ldir).strip()
208 print("Updating %s to %s" % (name, lastrev))
209 conf.update(name, "last_revision", lastrev)
216 for name in conf.repos:
217 ldir = conf.repos[name]['local_repo_dir']
219 logger.info("cloning %s to %s" %(conf.repos[name]['src_uri'], ldir))
220 … subprocess.check_call("git clone %s %s" % (conf.repos[name]['src_uri'], ldir), shell=True)
225 runcmd('git commit -m "initial empty commit" --allow-empty')
226 startrev = runcmd('git rev-parse master').strip()
228 for name in conf.repos:
229 repo = conf.repos[name]
230 ldir = repo['local_repo_dir']
231 branch = repo.get('branch', "master")
232 lastrev = repo.get('last_revision', None)
236 if not check_rev_branch(name, ldir, lastrev, branch):
238 logger.info("Copying data from %s at specified revision %s..." % (name, lastrev))
242 logger.info("Copying data from %s..." % name)
244 # because resolving a name ref only works in the component repo).
245 rev = runcmd('git rev-parse %s' % initialrev, ldir).strip()
248 refs = runcmd('git show-ref -s %s' % initialrev, ldir).split('\n')
255 … logger.warning("%s: initial revision '%s' not unique, picking result of rev-parse = %s" %
256 (name, initialrev, refs[0]))
259 # show-ref fails for hashes. Skip the sanity warning in that case.
262 dest_dir = repo['dest_dir']
269 file_filter = repo.get('file_filter', "")
270 exclude_patterns = repo.get('file_exclude', '').split()
287 strip=('--strip-components=%d' % subdir_components) if subdir else ''
289 # a) GNU tar requires a --wildcards parameter before turning on wild card matching.
293 files = runcmd("git archive %s %s | tar -x -v %s -C %s %s" %
315 refname = "combo-layer-init-%s" % name
316 runcmd("git branch -f %s %s" % (refname, initialrev), ldir)
318 runcmd("git branch -D %s" % refname, ldir)
320 runcmd("git checkout -b %s %s" % (name, initialrev))
327 since_rev = repo.get('since_revision', '')
330 # Same time stamp, no name.
331 author = re.sub('.* (\d+ [+-]\d+)', r'unknown <unknown> \1', committer)
334 # Resolve in component repo...
335 … rev = runcmd('git log --oneline --no-abbrev-commit -n1 %s' % rev, ldir).split()[0]
339 tree = runcmd('git show -s --pretty=format:%%T %s' % rev).strip()
354 Commit created by combo-layer.
356 ''' % (tree, author, committer, name, name, since_rev))
358 os.environ['GIT_EDITOR'] = 'sh %s' % editor.name
359 runcmd('git replace --edit %s' % rev)
362 if 'hook' in repo or dest_dir != ".":
363 filter_branch = ['git', 'filter-branch', '--force']
365 if 'hook' in repo:
367 # can be used by git filter-branch. Hook may or may not have
369 hook = repo['hook']
375 # combo-layer hooks.
376 hookwrapper.write('''set -e
379 echo -n 'Subject: [PATCH] ' >>$tmpname
381 if ! [ $(tail -c 1 $tmpname | od -A n -t x1) == '0a' ]; then
384 echo '---' >>$tmpname
386 tail -c +18 $tmpname | head -c -4
387 ''' % (hook, name))
389 filter_branch.extend(['--msg-filter', 'bash %s' % hookwrapper.name])
395 …['--tree-filter', 'mkdir -p .git/tmptree && find . -mindepth 1 -maxdepth 1 ! -name .git -print0 | …
398 runcmd('git update-ref -d refs/original/refs/heads/%s' % name)
399 repo['rewritten_revision'] = runcmd('git rev-parse HEAD').strip()
400 repo['stripped_revision'] = repo['rewritten_revision']
401 … # Optional filter files: remove everything and re-populate using the normal filtering code.
404 runcmd('git rm -rf .')
409 runcmd('git add --all --force .')
410 if runcmd('git status --porcelain'):
412 runcmd(['git', 'commit', '-m',
418 file_exclude = %s''' % (name, file_filter or '<empty>', repo.get('file_exclude', '<empty>'))])
419 repo['stripped_revision'] = runcmd('git rev-parse HEAD').strip()
422 lastrev = runcmd('git rev-parse %s' % initialrev, ldir).strip()
423 conf.update(name, "last_revision", lastrev, initmode=True)
428 … according to http://stackoverflow.com/questions/10874149/git-octopus-merge-with-unrelated-reposit…
430 merge = ['git', 'merge', '--no-commit']
431 for name in conf.repos:
432 repo = conf.repos[name]
434 merge.append(name)
437 … for start in runcmd('git log --pretty=format:%%H --max-parents=0 %s --' % name).split('\n'):
438 runcmd('git replace --graft %s %s' % (start, startrev))
448 # and we want certain auto-generated information in the
452 msg.write('repo: initial import of components\n\n')
454 for name in conf.repos:
455 repo = conf.repos[name]
457 msg.write('combo-layer-%s: %s %s %s\n' % (name,
458 repo['last_revision'],
459 repo['rewritten_revision'],
460 repo['stripped_revision']))
461 rev = runcmd('git rev-parse %s' % name).strip()
467 runcmd("git rm --cached %s" % conf.localconffile, printerr=False)
472 … runcmd("grep -q %s .gitignore || echo %s >> .gitignore" % (localrelpath, localrelpath))
482 check if the repo is clean
483 exit if repo is dirty
485 output=runcmd("git status --porcelain", repodir)
486 r = re.compile('\?\? patch-.*/')
489 logger.error("git repo %s is dirty, please fix it first", repodir)
501 if ln == b'---\n':
506 elif ln.startswith(b'--- '):
514 elif in_patch and not ln[0] in b'+-@ \n\r':
527 os.rename(of.name, patchfile)
537 ' exit -- continue to apply the patches\n' \
538 ' exit 1 -- abort\n' % shell);
548 actualbranch = runcmd("git branch --contains %s" % rev, repodir, printerr=False)
562 branches.append(b.strip().split(' ')[-1])
571 for name in repo_names:
572 if name.startswith('-'):
575 repos.append(name)
576 for repo in repos:
577 if not repo in conf.repos:
578 logger.error("Specified component '%s' not found in configuration" % repo)
582 repos = [ repo for repo in conf.repos if conf.repos[repo].get("update", True) ]
593 for name in repos:
594 check_repo_clean(conf.repos[name]['local_repo_dir'])
596 for name in repos:
597 repo = conf.repos[name]
598 ldir = repo['local_repo_dir']
599 branch = repo.get('branch', "master")
600 logger.info("update branch %s of component repo %s in %s ..." % (branch, name, ldir))
604 # combo-layer). In that case we need to fetch everything and try the check out
612 runcmd("git pull --ff-only", ldir)
614 output=runcmd("git pull --ff-only", ldir)
620 runcmd("git reset --hard FETCH_HEAD", ldir)
629 re-creates the entire component history and merges them
640 # make sure combo repo is clean
644 # set either via --history command line parameter or consistently
645 # in combo-layer.conf. Mixing modes is (currently, and probably
651 for name in repos:
652 repo = conf.repos[name]
653 repo_history = repo.get('history', False)
662 logger.info("Skipping pull (-n)")
673 patch_dir = "patch-%s" % uuid.uuid4()
677 for name in repos:
678 revision = revisions.get(name, None)
679 repo = conf.repos[name]
680 ldir = repo['local_repo_dir']
681 dest_dir = repo['dest_dir']
682 branch = repo.get('branch', "master")
683 repo_patch_dir = os.path.join(os.getcwd(), patch_dir, name)
686 logger.info("Generating patches from %s..." % name)
688 if not check_rev_branch(name, ldir, top_revision, branch):
691 prefix = "--src-prefix=a/%s/ --dst-prefix=b/%s/" % (dest_dir, dest_dir)
694 if repo['last_revision'] == "":
695 …er.info("Warning: last_revision of component %s is not set, starting from the first commit" % name)
696 patch_cmd_range = "--root %s" % top_revision
699 if not check_rev_branch(name, ldir, repo['last_revision'], branch):
701 patch_cmd_range = "%s..%s" % (repo['last_revision'], top_revision)
704 file_filter = repo.get('file_filter',".")
707 exclude = repo.get('file_exclude', '')
713 patch_cmd = "git format-patch -N %s --output-directory %s %s -- %s" % \
719 rev_cmd = "git rev-list --no-merges %s -- %s" % (rev_cmd_range, file_filter)
722 # Step 3: Call repo specific hook to adjust patch
723 if 'hook' in repo:
725 count=len(revlist)-1
727 runcmd("%s %s %s %s" % (repo['hook'], patch, revlist[count], name))
728 count=count-1
731 patchlist_file = os.path.join(os.getcwd(), patch_dir, "patchlist-%s" % name)
732 repo['patchlist'] = patchlist_file
734 count=len(revlist)-1
738 count=count-1
744 …'For example, you can remove unwanted patch entries from patchlist-*, so that they will be not app…
750 runcmd("rm -rf %s" % patch_dir)
770 output = runcmd("git status --porcelain %s" % relpath, printerr=False)
779 runcmd('git commit -m'.split() + [msg, relpath])
787 apply the generated patch list to combo repo
789 for name in repos:
790 repo = conf.repos[name]
791 lastrev = repo["last_revision"]
794 # Get non-blank lines from patch list file
796 if os.path.exists(repo['patchlist']) or not conf.interactive:
799 with open(repo['patchlist']) as f:
805 ldir = conf.repos[name]['local_repo_dir']
806 branch = conf.repos[name].get('branch', "master")
807 branchrev = runcmd("git rev-parse %s" % branch, ldir).strip()
810 logger.info("Applying patches from %s..." % name)
818 logger.info("(skipping %d/%d %s - no changes)" % (i, linecount, patchdisp))
820 … cmd = "git am --keep-cr %s-p1 %s" % ('-s ' if repo.get('signoff', True) else '', patchfile)
825 logger.info('Running "git am --abort" to cleanup repo')
826 runcmd("git am --abort")
831 if prevrev != repo['last_revision']:
832 conf.update(name, "last_revision", prevrev)
843 # combo-layer run will only exclude patches reachable from
844 # one of the merged branches and try to re-apply patches
853 len(runcmd("git show --pretty=format:%%P --no-patch %s" % branch, ldir).split()) > 1:
856 logger.info("No patches to apply from %s" % name)
859 if lastrev != repo['last_revision']:
860 conf.update(name, "last_revision", lastrev)
865 split the patch per repo
872 patchdir = "splitpatch-%s" % commit
876 # filerange_root is for the repo whose dest_dir is root "."
877 # and it should be specified by excluding all other repo dest dir
878 # like "-x repo1 -x repo2 -x repo3 ..."
880 for name in conf.repos:
881 dest_dir = conf.repos[name]['dest_dir']
883 filerange_root = '%s -x "%s/*"' % (filerange_root, dest_dir)
885 for name in conf.repos:
886 dest_dir = conf.repos[name]['dest_dir']
887 patch_filename = "%s/%s.patch" % (patchdir, name)
889 …cmd = "git format-patch -n1 --stdout %s^..%s | filterdiff -p1 %s > %s" % (commit, commit, filerang…
891 …cmd = "git format-patch --no-prefix -n1 --stdout %s^..%s -- %s > %s" % (commit, commit, dest_dir, …
897 logger.info("(skipping %s - no changes)", name)
907 combined repo of that commit (new or modified files overwritten,
918 head = runcmd("git rev-parse HEAD").strip()
922 # combined repo. We do not have to distinguish between components,
929 # repo.
931 for name in repos:
932 repo = conf.repos[name]
933 revision = repo['last_revision']
938 '''Insert -p before each entry.'''
941 parameters.append('-p')
949 # removing the combo-layer hooks that we currently use when
953 wdir = os.path.join(os.getcwd(), ".git", "combo-layer")
965 for name in repos:
966 revision = revisions.get(name, None)
967 repo = conf.repos[name]
968 ldir = repo['local_repo_dir']
969 dest_dir = repo['dest_dir']
970 branch = repo.get('branch', "master")
971 hook = repo.get('hook', None)
973 file_include = repo.get('file_filter', '').split()
975 file_exclude = repo.get('file_exclude', '').split()
1018 logger.info("Analyzing commits from %s..." % name)
1020 if not check_rev_branch(name, ldir, top_revision, branch):
1023 last_revision = repo['last_revision']
1024 rev_list_args = "--full-history --sparse --topo-order --reverse"
1026 …er.info("Warning: last_revision of component %s is not set, starting from the first commit" % name)
1029 if not check_rev_branch(name, ldir, last_revision, branch):
1044 # We care about all commits (--full-history and --sparse) and
1046 # about ordering by time (--topo-order). We ask for the ones
1047 # we need to import first to be listed first (--reverse).
1048 revs = runcmd("git rev-list %s" % rev_list_args, **largs).split()
1057 … ancestor_revs = runcmd("git rev-list --ancestry-path %s" % rev_list_args, **largs).split()
1063 logger.info("Importing commits from %s..." % name)
1090 # We can avoid importing merge commits if all non-merge commits
1094 parents = runcmd("git show --no-patch --pretty=format:%P " + prev, **largs).split()
1113 …runcmd("git show --no-patch --pretty=format:%P%x00%an%x00%ae%x00%at%x00%B " + rev, **largs).split(…
1125 # "git reset --hard" does not work, it changes HEAD of the parent
1126 # repo, which we wanted to avoid. Probably need to keep
1128 runcmd("git rm -q --ignore-unmatch -rf .", **wargs)
1130 runcmd("git checkout -q -f %s ." % new_parent, **wargs)
1134 runcmd("git rm -q --ignore-unmatch -rf .", **wargs)
1140 new_tree = runcmd("git write-tree", **wargs).strip()
1151 patch.write('\n---\n')
1153 runcmd([hook, patch.name, rev, name])
1154 with open(patch.name) as f:
1155 body = f.read()[len('Subject: [PATCH] '):][:-len('\n---\n')]
1157 # We can skip non-merge commits that did not change any files. Those are typically
1162 old_tree = runcmd("git show -s --pretty=format:%T " + parent_rev, **wargs).strip()
1169 … new_rev = runcmd("git commit-tree".split() + add_p([import_rev(p) for p in parents]) +
1170 ["-m", body, new_tree],
1182 additional_heads[old2new_revs[revs[-1]]] = head if repo['last_revision'] else None
1183 repo['last_revision'] = revs[-1]
1189 runcmd("git reset --hard", **wargs)
1196 new_tree = runcmd("git write-tree", **wargs).strip()
1197 new_rev = runcmd("git commit-tree".split() +
1199 ["-m", msg, new_tree],
1202 runcmd("git reset --hard %s" % new_rev)
1205 # combo-layer.conf, but do not commit separately.
1206 for name in repos:
1207 repo = conf.repos[name]
1208 rev = repo['last_revision']
1209 conf.update(name, "last_revision", rev)
1212 runcmd("git commit --amend -C HEAD")
1218 combined repo by looking at the commit messages. Depends on the
1222 …log = runcmd("git log --grep='From .* rev: [a-fA-F0-9][a-fA-F0-9]*' --pretty=format:%H%x00%B%x00 "…
1223 regex = re.compile(r'From .* rev: ([a-fA-F0-9]+)')
1226 rev = regex.findall(body)[-1]
1229 logger.info("Found %d additional commits, leading to: %s" % (len(old2new) - num_known, old2new))
1234 commit, re-write new or modified ones. Moves them into dest_dir.
1239 # -r recurses into sub-directories, given is the full overview of
1241 # can disable those with --no-renames (but we still parse them,
1249 …changes = runcmd("git diff-tree --no-commit-id --no-renames --name-status -r --raw -z %s %s" % (pa…
1250 for status, name in zip(*[iter(changes)]*2):
1252 update.append(name)
1254 delete.append(name)
1256 logger.error("Unknown status %s of file %s in revision %s" % (status, name, rev))
1260 update.extend(runcmd("git ls-tree -r --name-only -z %s" % rev, **largs).split(chr(0)))
1273 # command line parameters - hopefully there will never be too many at once.
1283 # we just hard-code a fixed value which is more likely to work.
1301 … cmd = "git archive %s %s | tar -C %s -xf -" % (rev, ' '.join(quoted_args), quoted_target)
1304 cmd = "git add -f".split() + [os.path.join(dest_dir, x) for x in unquoted_args]
1311 …runcmd("git rm -f --ignore-unmatch".split() + [os.path.join(dest_dir, x) for x in delete], **wargs)
1321 "sync-revs": action_sync_revs,
1326 version = "Combo Layer Repo Tool version %s" % __version__,
1332 init initialise the combo layer repo
1333 update [components] get patches from component repos and apply them to the combo repo
1335 sync-revs [components] update the config file's last_revision for each repository
1338 …parser.add_option("-c", "--conf", help = "specify the config file (conf/combo-layer.conf is the de…
1339 action = "store", dest = "conffile", default = "conf/combo-layer.conf")
1341 …parser.add_option("-i", "--interactive", help = "interactive mode, user can edit the patch list an…
1344 parser.add_option("-D", "--debug", help = "output debug information",
1347 parser.add_option("-n", "--no-pull", help = "skip pulling component repos during update",
1350 parser.add_option("--hard-reset",
1351 help = "instead of pull do fetch and hard-reset in component repos",
1354 parser.add_option("-H", "--history", help = "import full history of components during init",