summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--scripts/lib/devtool/standard.py119
1 files changed, 72 insertions, 47 deletions
diff --git a/scripts/lib/devtool/standard.py b/scripts/lib/devtool/standard.py
index 01d7b8cf81..b8435ae701 100644
--- a/scripts/lib/devtool/standard.py
+++ b/scripts/lib/devtool/standard.py
@@ -25,6 +25,7 @@ import logging
25import argparse 25import argparse
26import scriptutils 26import scriptutils
27import errno 27import errno
28from collections import OrderedDict
28from devtool import exec_build_env_command, setup_tinfoil, check_workspace_recipe, use_external_build, setup_git_repo, DevtoolError 29from devtool import exec_build_env_command, setup_tinfoil, check_workspace_recipe, use_external_build, setup_git_repo, DevtoolError
29from devtool import parse_recipe 30from devtool import parse_recipe
30 31
@@ -590,11 +591,55 @@ def _remove_patch_files(args, patches, destpath):
590 if ose.errno != errno.ENOTEMPTY: 591 if ose.errno != errno.ENOTEMPTY:
591 raise 592 raise
592 593
594
595def _export_patches(srctree, rd, start_rev, destdir):
596 """Export patches from srctree to given location.
597 Returns three-tuple of dicts:
598 1. updated - patches that already exist in SRCURI
599 2. added - new patches that don't exist in SRCURI
600 3 removed - patches that exist in SRCURI but not in exported patches
601 In each dict the key is the 'basepath' of the URI and value is the
602 absolute path to the existing file in recipe space (if any).
603 """
604 import oe.recipeutils
605 from oe.patch import GitApplyTree
606 updated = OrderedDict()
607 added = OrderedDict()
608 seqpatch_re = re.compile('^([0-9]{4}-)?(.+)')
609
610 existing_patches = dict((os.path.basename(path), path) for path in
611 oe.recipeutils.get_recipe_patches(rd))
612
613 # Generate patches from Git
614 GitApplyTree.extractPatches(srctree, start_rev, destdir)
615
616 new_patches = sorted(os.listdir(destdir))
617 for new_patch in new_patches:
618 # Strip numbering from patch names. If it's a git sequence named patch,
619 # the numbers might not match up since we are starting from a different
620 # revision This does assume that people are using unique shortlog
621 # values, but they ought to be anyway...
622 new_basename = seqpatch_re.match(new_patch).group(2)
623 found = False
624 for old_patch in existing_patches:
625 old_basename = seqpatch_re.match(old_patch).group(2)
626 if new_basename == old_basename:
627 updated[new_patch] = existing_patches.pop(old_patch)
628 found = True
629 # Rename patch files
630 if new_patch != old_patch:
631 os.rename(os.path.join(destdir, new_patch),
632 os.path.join(destdir, old_patch))
633 break
634 if not found:
635 added[new_patch] = None
636 return (updated, added, existing_patches)
637
638
593def _update_recipe_srcrev(args, srctree, rd, config_data): 639def _update_recipe_srcrev(args, srctree, rd, config_data):
594 """Implement the 'srcrev' mode of update-recipe""" 640 """Implement the 'srcrev' mode of update-recipe"""
595 import bb 641 import bb
596 import oe.recipeutils 642 import oe.recipeutils
597 from oe.patch import GitApplyTree
598 643
599 recipefile = rd.getVar('FILE', True) 644 recipefile = rd.getVar('FILE', True)
600 logger.info('Updating SRCREV in recipe %s' % os.path.basename(recipefile)) 645 logger.info('Updating SRCREV in recipe %s' % os.path.basename(recipefile))
@@ -621,12 +666,10 @@ def _update_recipe_srcrev(args, srctree, rd, config_data):
621 old_srcrev = (rd.getVar('SRCREV', False) or '') 666 old_srcrev = (rd.getVar('SRCREV', False) or '')
622 tempdir = tempfile.mkdtemp(prefix='devtool') 667 tempdir = tempfile.mkdtemp(prefix='devtool')
623 try: 668 try:
624 GitApplyTree.extractPatches(srctree, old_srcrev, tempdir) 669 upd_p, new_p, del_p = _export_patches(srctree, rd, old_srcrev,
625 newpatches = os.listdir(tempdir) 670 tempdir)
626 for patch in existing_patches: 671 # Remove "overlapping" patches
627 patchfile = os.path.basename(patch) 672 removepatches = upd_p.values()
628 if patchfile in newpatches:
629 removepatches.append(patch)
630 finally: 673 finally:
631 shutil.rmtree(tempdir) 674 shutil.rmtree(tempdir)
632 675
@@ -654,7 +697,6 @@ def _update_recipe_patch(args, config, srctree, rd, config_data):
654 """Implement the 'patch' mode of update-recipe""" 697 """Implement the 'patch' mode of update-recipe"""
655 import bb 698 import bb
656 import oe.recipeutils 699 import oe.recipeutils
657 from oe.patch import GitApplyTree
658 700
659 recipefile = rd.getVar('FILE', True) 701 recipefile = rd.getVar('FILE', True)
660 append = os.path.join(config.workspace_path, 'appends', '%s.bbappend' % 702 append = os.path.join(config.workspace_path, 'appends', '%s.bbappend' %
@@ -677,40 +719,27 @@ def _update_recipe_patch(args, config, srctree, rd, config_data):
677 # Get all patches from source tree and check if any should be removed 719 # Get all patches from source tree and check if any should be removed
678 tempdir = tempfile.mkdtemp(prefix='devtool') 720 tempdir = tempfile.mkdtemp(prefix='devtool')
679 try: 721 try:
680 GitApplyTree.extractPatches(srctree, initial_rev, tempdir) 722 # Get all patches from source tree and check if any should be removed
681 # Strip numbering from patch names. If it's a git sequence named 723 upd_p, new_p, del_p = _export_patches(srctree, rd, initial_rev,
682 # patch, the numbers might not match up since we are starting from 724 tempdir)
683 # a different revision This does assume that people are using 725 # Remove deleted patches
684 # unique shortlog values, but they ought to be anyway... 726 removepatches = del_p.values()
685 newpatches = [seqpatch_re.match(fname).group(2) for fname in
686 os.listdir(tempdir)]
687 for patch in existing_patches:
688 basename = seqpatch_re.match(
689 os.path.basename(patch)).group(2)
690 if basename not in newpatches:
691 removepatches.append(patch)
692 finally: 727 finally:
693 shutil.rmtree(tempdir) 728 shutil.rmtree(tempdir)
694 729
695 # Get updated patches from source tree 730 # Get updated patches from source tree
696 tempdir = tempfile.mkdtemp(prefix='devtool') 731 tempdir = tempfile.mkdtemp(prefix='devtool')
697 try: 732 try:
698 GitApplyTree.extractPatches(srctree, update_rev, tempdir) 733 upd_p, new_p, del_p = _export_patches(srctree, rd, update_rev,
734 tempdir)
699 735
700 # Match up and replace existing patches with corresponding new patches 736 # Match up and replace existing patches with corresponding new patches
701 updatepatches = False 737 updatepatches = False
702 updaterecipe = False 738 updaterecipe = False
703 destpath = None 739 destpath = None
704 newpatches = sorted(os.listdir(tempdir))
705 if args.append: 740 if args.append:
706 patchfiles = {} 741 patchfiles = dict((os.path.join(tempdir, key), val) for
707 for patch in existing_patches: 742 key, val in upd_p.items() + new_p.items())
708 patchfile = os.path.basename(patch)
709 if patchfile in newpatches:
710 patchfiles[os.path.join(tempdir, patchfile)] = patchfile
711 newpatches.remove(patchfile)
712 for patchfile in newpatches:
713 patchfiles[os.path.join(tempdir, patchfile)] = None
714 743
715 if patchfiles or removepatches: 744 if patchfiles or removepatches:
716 removevalues = None 745 removevalues = None
@@ -728,25 +757,21 @@ def _update_recipe_patch(args, config, srctree, rd, config_data):
728 else: 757 else:
729 logger.info('No patches needed updating') 758 logger.info('No patches needed updating')
730 else: 759 else:
731 for patch in existing_patches: 760 for basepath, path in upd_p.iteritems():
732 patchfile = os.path.basename(patch) 761 logger.info('Updating patch %s' % basepath)
733 if patchfile in newpatches: 762 shutil.move(os.path.join(tempdir, basepath), path)
734 logger.info('Updating patch %s' % patchfile) 763 updatepatches = True
735 shutil.move(os.path.join(tempdir, patchfile), patch)
736 newpatches.remove(patchfile)
737 updatepatches = True
738 srcuri = (rd.getVar('SRC_URI', False) or '').split() 764 srcuri = (rd.getVar('SRC_URI', False) or '').split()
739 if newpatches: 765 patchdir = os.path.join(os.path.dirname(recipefile),
740 # Add any patches left over 766 rd.getVar('BPN', True))
741 patchdir = os.path.join(os.path.dirname(recipefile), 767 bb.utils.mkdirhier(patchdir)
742 rd.getVar('BPN', True)) 768 for basepath, path in new_p.iteritems():
769 logger.info('Adding new patch %s' % basepath)
743 bb.utils.mkdirhier(patchdir) 770 bb.utils.mkdirhier(patchdir)
744 for patchfile in newpatches: 771 shutil.move(os.path.join(tempdir, basepath),
745 logger.info('Adding new patch %s' % patchfile) 772 os.path.join(patchdir, basepath))
746 shutil.move(os.path.join(tempdir, patchfile), 773 srcuri.append('file://%s' % basepath)
747 os.path.join(patchdir, patchfile)) 774 updaterecipe = True
748 srcuri.append('file://%s' % patchfile)
749 updaterecipe = True
750 if removepatches: 775 if removepatches:
751 removedentries, _ = _remove_patch_entries(srcuri, removepatches) 776 removedentries, _ = _remove_patch_entries(srcuri, removepatches)
752 if removedentries: 777 if removedentries: