def __init__(self, path): """ Constructor Args: path (string): path to patch archive file Raises: PT_ParameterError, PT_NotFoundError Notes: A "patch archive" file lists diff sections from patches that were applied to produce the associated kernel version. Since the patch archive files can be very large, we take care to avoid copying or storing data that is not of interest to the user. """ #-- self.name = 'Archive' if (not ut.is_string_type(path)): raise PT_ParameterError(self.name, path) if (not ut.is_file(path)): raise PT_NotFoundError(self.name, path) self._path = path
def get_patch_files(self, patchname): """ Return a list of source files referenced in one patch file Args: patchname (string): name of patch file Raises: PT_ParameterError, PT_NotFoundError Notes: This function may be used to generate file lists for the *Finder*. """ #-- patchname = self._check_file_1_arg('patchname', patchname) if (self.filedata is None): self._get_data() if (not patchname in self.patchdata): raise PT_NotFoundError(self.name, patchname) # data is a list of tuples (name, line) data = self.patchdata[patchname] data = [name for (name, _) in data] data.sort() return data
def get_file_patches(self, filename): """ Return a list of patch files that refer to one source file Args: filename (string): name of source file Raises: PT_ParameterError, PT_NotFoundError Notes: This function may be used to generate file lists for the *Matcher*. """ #-- filename = self._check_file_1_arg('filename', filename) if (self.filedata is None): self._get_data() if (not filename in self.filedata): raise PT_NotFoundError(self.name, filename) # data is a list of tuples (patch name, line number) data = self.filedata[filename] data = [name for (name, _) in data] data.sort() return data
def _check_directory_param(self, params, field): path = self._check_required_string_param(params, field) if (not ut.is_dir(path)): raise PT_NotFoundError(self.name, field) return path
def _check_filename_param(self, prefix, value, name): if (not ut.is_string_type(value)): raise PT_ParameterError(self.name, name) path = ut.join_path(prefix, value) if (not ut.is_file(path)): raise PT_NotFoundError(self.name, value) return path
def vp2a(self, patchname, archpath, params): """ Display patch and archive diff sections that use its files Args: patchname (string): name of patch file archpath (string): path to archive file params (dict): parameters patchdir (string, required): path of patches folder tempdir (string, required): path to store temporary data Raises: PT_ParameterError for any missing files Notes: Launches the editor synchronously, since a temporary file is created to hold the archive sections. """ #-- if (not isinstance(params, dict)): raise PT_ParameterError(self.name, 'params') sourcedir = self._check_directory_param(params, 'sourcedir') patchdir = self._check_directory_param(params, 'patchdir') tempdir = self._check_directory_param(params, 'tempdir') patchpath = self._check_filename_param(patchdir, patchname, 'patchname') if (not ut.is_file(archpath)): raise PT_NotFoundError(self.name, archpath) # Get list of files used by the patch filelist = Patch.list_files(patchpath) filepaths = [ut.join_path(sourcedir, file_) for file_ in filelist] # Get archive diff sections that use any of the files strings = [] for diff in self._get_diffs(archpath, filepaths): strings += diff if (len(strings) == 0): return [] # Store the diff sections in a temporary file archname = archpath[archpath.rfind('/') + 1:] tempname = archname + '.tmp' temppath = ut.join_path(tempdir, tempname) ut.write_strings(strings, temppath) self._view([patchpath, temppath], True) # Note that we requested _view to wait for subprocess exit above, # so that we do not try to delete the file while it is in use. os.remove(temppath)
def __init__(self, path): """ Constructor Args: path (string): path to patch file Raises: PT_ParameterError PT_NotFoundError Notes: Commented out diff and hunk sections are omitted. """ #-- self.name = 'Patch' if (not ut.is_string_type(path)): raise PT_ParameterError(self.name, path) if (not ut.is_file(path)): raise PT_NotFoundError(self.name, path) strings = Strings(ut.read_strings(path)) strings = strings.discard('"""', '"""') # Split any email header from the patch data (_, body) = strings.partition('diff -') if (body is None): #all diffs commented out? self.diffs = [] self.patch_type = 'text' self.patch_mode = 'git' print "body is none" elif (body[0].startswith('diff --git ')): # Split any email footer from the patch data (body, _) = body.rpartition('-- ') self._parse_body(body, 'diff --git ') self.patch_mode = 'git' print "git diff" else: self._parse_body(body, 'diff -') self.patch_mode = 'urn' print "urn"
def get_patch_patches(self, patchname): """ Get a list of patches that patchname depends on Args: patchname (string): name of patch file Returns: A list of names of the parent patches in patchset order Raises: PT_ParameterError, PT_NotFoundError Notes: Patch A depends on patch B when they modify the same files and patch B precedes patch A in the patch list. """ #-- patchname = self._check_file_1_arg('patchname', patchname) if (self.patchdata is None): self._get_data() if (patchname not in self.patchdata): raise PT_NotFoundError(self.name, patchname) filelist = [name for (name, _) in self.patchdata[patchname]] data = {} for filename in filelist: patchlist = [name for (name, _) in self.filedata[filename]] for patch in patchlist: if (patch == patchname): # don't store self or later break else: # Here we delete duplicates data[patch] = True data = self._sort_patches(data) return data
def vcpf(self, checkpath, patchname, params): """ List checker output file, patch and files it uses Args: checkpath (string): path to Checker output file patchname (string): patch name params (dict) parameters: sourcedir (string, required): path of sources folder patchdir (string, required): path of patches folder Raises: PT_ParameterError PT_NotFoundError """ #-- if (not isinstance(params, dict)): raise PT_ParameterError(self.name, 'params') if (not ut.is_file(checkpath)): raise PT_NotFoundError(self.name, checkpath) sourcedir = self._check_directory_param(params, 'sourcedir') patchdir = self._check_directory_param(params, 'patchdir') patchpath = self._check_filename_param(patchdir, patchname, 'patchname') # Get list of source filenames referenced in patch. # Note that a patch may refer to files that do not exist in the source tree. filelist = Patch.list_files(patchpath) filepaths = [] for file_ in filelist: path = ut.join_path(sourcedir, file_) if (ut.is_file(path)): filepaths += [path] paths = [checkpath, patchpath] + filepaths return self._view(paths)
def watch(self, archpath): """ View files related to archive diff sections Args: archpath (string): path to patch archive file Returns: None. Output is a series of launches of the Viewer to view the files. Raises: PT_ParameterError PT_NotFoundError """ #-- if (not ut.is_string_type(archpath)): raise PT_ParameterError(self.name, 'archpath') if (not ut.is_file(archpath)): raise PT_NotFoundError(self.name, archpath) tempfile = ut.join_path(self._tempdir, 'archdata.txt') filedata = self._patchset.get_file_data() filenames = [key for key in filedata] a = Archive(archpath) s = a.sections(filenames) print("Found %d matching sections" % len(s)) v = Viewer() for section in s: ut.write_strings(section, tempfile) filename = ut.get_string_filename(section[1]) filepath = ut.join_path(self._sourcedir, filename) patchfiles = [] for (fn, _) in filedata[filename]: patchfiles += [ut.join_path(self._patchdir, fn)] r = v.view([tempfile, filepath] + patchfiles) print(r)