hgbook
diff en/mq.tex @ 16:81454425eee9
Progress on a few fronts, mainly indexing and MQ chapter content
author | Bryan O'Sullivan <bos@serpentine.com> |
---|---|
date | Mon Jul 03 22:43:52 2006 -0700 (2006-07-03) |
parents | b8ac9f312a47 |
children | 2668e15c76e9 |
line diff
1.1 --- a/en/mq.tex Mon Jul 03 17:58:29 2006 -0700 1.2 +++ b/en/mq.tex Mon Jul 03 22:43:52 2006 -0700 1.3 @@ -158,7 +158,7 @@ 1.4 only operate within that repository. To get started, simply prepare 1.5 the repository using the \hgcmd{qinit} command (see 1.6 figure~\ref{ex:mq:qinit}). This command creates an empty directory 1.7 -called \filename{.hg/patches}, where MQ will keep its metadata. As 1.8 +called \sdirname{.hg/patches}, where MQ will keep its metadata. As 1.9 with many Mercurial commands, the \hgcmd{qinit} command prints nothing 1.10 if it succeeds. 1.11 1.12 @@ -178,20 +178,20 @@ 1.13 1.14 To begin work on a new patch, use the \hgcmd{qnew} command. This 1.15 command takes one argument, the name of the patch to create. MQ will 1.16 -use this as the name of an actual file in the \filename{.hg/patches} 1.17 +use this as the name of an actual file in the \sdirname{.hg/patches} 1.18 directory, as you can see in figure~\ref{ex:mq:qnew}. 1.19 1.20 -Also newly present in the \filename{.hg/patches} directory are two 1.21 -other files, \filename{series} and \filename{status}. The 1.22 -\filename{series} file lists all of the patches that MQ knows about 1.23 +Also newly present in the \sdirname{.hg/patches} directory are two 1.24 +other files, \sfilename{series} and \sfilename{status}. The 1.25 +\sfilename{series} file lists all of the patches that MQ knows about 1.26 for this repository, with one patch per line. Mercurial uses the 1.27 -\filename{status} file for internal book-keeping; it tracks all of the 1.28 +\sfilename{status} file for internal book-keeping; it tracks all of the 1.29 patches that MQ has \emph{applied} in this repository. 1.30 1.31 \begin{note} 1.32 - You may sometimes want to edit the \filename{series} file by hand; 1.33 + You may sometimes want to edit the \sfilename{series} file by hand; 1.34 for example, to change the sequence in which some patches are 1.35 - applied. However, manually editing the \filename{status} file is 1.36 + applied. However, manually editing the \sfilename{status} file is 1.37 almost always a bad idea, as it's easy to corrupt MQ's idea of what 1.38 is happening. 1.39 \end{note} 1.40 @@ -322,9 +322,10 @@ 1.41 \section{Mercurial Queues and GNU patch} 1.42 \label{sec:mq:patch} 1.43 1.44 -MQ uses the GNU \command{patch} command to apply patches. It will 1.45 -help you to understand the data that MQ and \command{patch} work with, 1.46 -and a few aspects of how \command{patch} operates. 1.47 +MQ uses the GNU \command{patch} command to apply patches. Because MQ 1.48 +doesn't hide its patch-oriented nature, it is helpful to understand 1.49 +the data that MQ and \command{patch} work with, and a few aspects of 1.50 +how \command{patch} operates. 1.51 1.52 The \command{diff} command generates a list of modifications by 1.53 comparing two files. The \command{patch} command applies a list of 1.54 @@ -381,8 +382,8 @@ 1.55 When neither of these techniques works, \command{patch} prints a 1.56 message saying that the hunk in question was rejected. It saves 1.57 rejected hunks to a file with the same name, and an added 1.58 -\filename{.rej} extension. It also saves an unmodified copy of the 1.59 -file with a \filename{.orig} extension; the copy of the file without 1.60 +\sfilename{.rej} extension. It also saves an unmodified copy of the 1.61 +file with a \sfilename{.orig} extension; the copy of the file without 1.62 any extensions will contain any changes made by hunks that \emph{did} 1.63 apply cleanly. If you have a patch that modifies \filename{foo} with 1.64 six hunks, and one of them fails to apply, you will have: an 1.65 @@ -413,7 +414,7 @@ 1.66 \subsection{Handling rejection} 1.67 1.68 If \hgcmd{qpush} fails to apply a patch, it will print an error 1.69 -message and exit. If it has left \filename{.rej} files behind, it is 1.70 +message and exit. If it has left \sfilename{.rej} files behind, it is 1.71 usually best to fix up the rejected hunks before you push more patches 1.72 or do any further work. 1.73 1.74 @@ -422,13 +423,12 @@ 1.75 Mercurial Queues can help; see section~\ref{seq:mq:merge} for details. 1.76 1.77 Unfortunately, there aren't any great techniques for dealing with 1.78 -rejected hunks. Most often, you'll need to view the \filename{.rej} 1.79 +rejected hunks. Most often, you'll need to view the \sfilename{.rej} 1.80 file and edit the target file, applying the rejected hunks by hand. 1.81 1.82 -If you're feeling adventurous, Neil Brown, an Australian Linux kernel 1.83 -hacker, has written a tool called \command{wiggle}~\cite{web:wiggle}, 1.84 -which is more vigorous than \command{patch} in its attempts to make a 1.85 -patch apply. 1.86 +If you're feeling adventurous, Neil Brown, a Linux kernel hacker, 1.87 +wrote a tool called \command{wiggle}~\cite{web:wiggle}, which is more 1.88 +vigorous than \command{patch} in its attempts to make a patch apply. 1.89 1.90 Another Linux kernel hacker, Chris Mason (the author of Mercurial 1.91 Queues), wrote a similar tool called \command{rej}~\cite{web:rej}, 1.92 @@ -453,6 +453,93 @@ 1.93 1.94 XXX. 1.95 1.96 +\section{Managing patches in a repository} 1.97 + 1.98 +Because MQ's \sdirname{.hg/patches} directory resides outside a 1.99 +Mercurial repository's working directory, the ``underlying'' Mercurial 1.100 +repository knows nothing about the management or presence of patches. 1.101 + 1.102 +This presents the interesting possibility of managing the contents of 1.103 +the patch directory as a Mercurial repository in its own right. This 1.104 +can be a useful way to work. For example, you can work on a patch for 1.105 +a while, \hgcmd{qrefresh} it, then \hgcmd{commit} the current state of 1.106 +the patch. This lets you ``roll back'' to that version of the patch 1.107 +later on. 1.108 + 1.109 +In addition, you can then share different versions of the same patch 1.110 +stack among multiple underlying repositories. I use this when I am 1.111 +developing a Linux kernel feature. I have a pristine copy of my 1.112 +kernel sources for each of several CPU architectures, and a cloned 1.113 +repository under each that contains the patches I am working on. When 1.114 +I want to test a change on a different architecture, I push my current 1.115 +patches to the patch repository associated with that kernel tree, pop 1.116 +and push all of my patches, and build and test that kernel. 1.117 + 1.118 +Managing patches in a repository makes it possible for multiple 1.119 +developers to work on the same patch series without colliding with 1.120 +each other, all on top of an underlying source base that they may or 1.121 +may not control. 1.122 + 1.123 +\subsection{MQ support for managing a patch repository} 1.124 + 1.125 +MQ helps you to work with the \sdirname{.hg/patches} directory as a 1.126 +repository; when you prepare a repository for working with patches 1.127 +using \hgcmdargs{qinit}, you can pass the \hgopt{qinit}{-c} option to 1.128 +create the \sdirname{.hg/patches} directory as a Mercurial repository. 1.129 + 1.130 +\begin{note} 1.131 + If you forget to use the \hgopt{qinit}{-c} option, you can simply go 1.132 + into the \sdirname{.hg/patches} directory at any time and run 1.133 + \hgcmd{init}. Don't forget to add an entry for the 1.134 + \filename{status} file to the \filename{.hgignore} file, though 1.135 + (\hgopt{qinit}{-c} does this for you automatically); you 1.136 + \emph{really} don't want to manage the \filename{status} file. 1.137 +\end{note} 1.138 + 1.139 +As a convenience, if MQ notices that the \dirname{.hg/patches} 1.140 +directory is a repository, it will automatically \hgcmd{add} every 1.141 +patch that you create and import. 1.142 + 1.143 +Finally, MQ provides a shortcut command, \hgcmd{qcommit}, that runs 1.144 +\hgcmd{commit} in the \sdirname{.hg/patches} directory. This saves 1.145 +some cumbersome typing. 1.146 + 1.147 +\subsection{A few things to watch out for} 1.148 + 1.149 +MQ's support for working with a repository full of patches is limited 1.150 +in a few small respects. 1.151 + 1.152 +MQ cannot automatically detect changes that you make to the patch 1.153 +directory. If you \hgcmd{pull}, manually edit, or \hgcmd{update} 1.154 +changes to patches or the \sfilename{series} file, you will have to 1.155 +\hgcmdargs{qpop}{-a} and then \hgcmdargs{qpush}{-a} in the underlying 1.156 +repository to see those changes show up there. If you forget to do 1.157 +this, you can confuse MQ's idea of which patches are applied. 1.158 + 1.159 +\section{Commands for working with patches} 1.160 + 1.161 +Once you've been working with patches for a while, you'll find 1.162 +yourself hungry for tools that will help you to understand and 1.163 +manipulate the patches you're dealing with. 1.164 + 1.165 +The \command{diffstat} command~\cite{web:diffstat} generates a 1.166 +histogram of the modifications made to each file in a patch. It 1.167 +provides a good way to ``get a sense of'' a patch--which files it 1.168 +affects, and how much change it introduces to each file and as a 1.169 +whole. (I find that it's a good idea to use \command{diffstat}'s 1.170 +\texttt{-p} option as a matter of course, as otherwise it will try to 1.171 +do clever things with prefixes of file names that inevitably confuse 1.172 +at least me.) 1.173 + 1.174 +The \package{patchutils} package~\cite{web:patchutils} is invaluable. 1.175 +It provides a set of small utilities that follow the ``Unix 1.176 +philosophy;'' each does one useful thing with a patch. The 1.177 +\package{patchutils} command I use most is \command{filterdiff}, which 1.178 +extracts subsets from a patch file. For example, given a patch that 1.179 +modifies hundreds of files across dozens of directories, a single 1.180 +invocation of \command{filterdiff} can generate a smaller patch that 1.181 +only touches files whose names match a particular glob pattern. 1.182 + 1.183 %%% Local Variables: 1.184 %%% mode: latex 1.185 %%% TeX-master: "00book"