# 8. Patches para pacotes

Sometimes, Ubuntu package maintainers have to change the upstream source code in order to make it work properly on Ubuntu. Examples include, patches to upstream that haven’t yet made it into a released version, or changes to the upstream’s build system needed only for building it on Ubuntu. We could change the upstream source code directly, but doing this makes it more difficult to remove the patches later when upstream has incorporated them, or extract the change to submit to the upstream project. Instead, we keep these changes as separate patches, in the form of diff files.

Há várias maneiras diferentes de lidar com patches em pacotes Debian, felizmente estamos padronizando um sistema, Quilt, que agora é utilizado pela maioria dos pacotes.

Let’s look at an example package, `kamoso` in Trusty:

    $ bzr branch ubuntu:trusty/kamoso

The patches are kept in `debian/patches`. This package has one patch `kubuntu_01_fix_qmax_on_armel.diff` to fix a compile failure on ARM. The patch has been given a name to describe what it does, a number to keep the patches in order (two patches can overlap if they change the same file) and in this case the Kubuntu team adds their own prefix to show the patch comes from them rather than from Debian.

A ordem dos patches para aplicar é mantida em `debian/patches/series`.

## 8.1. Patches com o Quilt

Antes de trabalhar com o Quilt você precisa informar a ele onde encontrar os patches. Adicione isso em seu “~/.bashrc”:

    export QUILT_PATCHES=debian/patches

E forneça a origem do arquivo para aplicar a nova exportação:

    $ . ~/.bashrc

Por padrão, todos os patches são aplicados diretamente nos checkouts de UDD ou pacotes baixados. Você pode verificar isto com:

    $ quilt applied
    kubuntu_01_fix_qmax_on_armel.diff

Se você quisesse remover o patch poderia executar `pop`:

    $ quilt pop
    Removing patch kubuntu_01_fix_qmax_on_armel.diff
    Restoring src/kamoso.cpp

    No patches applied

E para aplicar um patch você usa `push`:

    $ quilt push
    Applying patch kubuntu_01_fix_qmax_on_armel.diff
    patching file src/kamoso.cpp

    Now at patch kubuntu_01_fix_qmax_on_armel.diff

## 8.2. Adicionando um novo patch

Para adicionar um novo patch você deve dizer ao Quilt para criar um novo patch, dizer a ele quais arquivos o patch irá alterar, editar os arquivos e então atualizar o patch:

    $ quilt new kubuntu_02_program_description.diff
    Patch kubuntu_02_program_description.diff is now on top
    $ quilt add src/main.cpp
    File src/main.cpp added to patch kubuntu_02_program_description.diff
    $ sed -i "s,Webcam picture retriever,Webcam snapshot program,"
    src/main.cpp
    $ quilt refresh
    Refreshed patch kubuntu_02_program_description.diff

O passo `quilt add` é importante, se você esquecê-lo os arquivos não vão terminar no patch.

A mudança agora estará em `debian/patches/kubuntu_02_program_description.diff` e o arquivo `series` terá um novo patch adicionado a ele. Você deve adicionar o novo arquivo para o empacotamento:

    $ bzr add debian/patches/kubuntu_02_program_description.diff
    $ bzr add .pc/*
    $ dch -i "Add patch kubuntu_02_program_description.diff to improve the program description"
    $ bzr commit

O Quilt mantém os seus metadados no diretório ”.pc/”, então atualmente você precisa adicioná-lo ao empacotamento também. Isto deverá ser aprimorado no futuro.

As a general rule you should be careful adding patches to programs unless they come from upstream, there is often a good reason why that change has not already been made. The above example changes a user interface string for example, so it would break all translations. If in doubt, do ask the upstream author before adding a patch.

## 8.3. Patch Headers

We recommend that you tag every patch with DEP-3 headers by putting them at the top of patch file. Here are some headers that you can use:

Description: | Description of what the patch does. It is formatted like `Description` field in `debian/control`: first line is short description, starting with lowercase letter, the next lines are long description, indented with a space.
Author: | Who wrote the patch (i.e. “Jane Doe <packager@example.com>”).
Origin: | Where this patch comes from (i.e. “upstream”), when Author is not present.
Bug-Ubuntu: | A link to Launchpad bug, a short form is preferred (like https://bugs.launchpad.net/bugs/XXXXXXX). If there are also bugs in upstream or Debian bugtrackers, add Bug or Bug-Debian headers.
Forwarded: | Whether the patch was forwarded upstream. Either “yes”, “no” or “not-needed”.
Last-Update: | Date of the last revision (in form “YYYY-MM-DD”).

## 8.4. Atualizando para novas versões do upstream

To upgrade to the new version, you can use `bzr merge-upstream` command:

    $ bzr merge-upstream --version 2.0.2 https://launchpad.net/ubuntu/+archive/primary/+files/kamoso_2.0.2.orig.tar.bz2

When you run this command, all patches will be unapplied, because they can become out of date. They might need to be refreshed to match the new upstream source or they might need to be removed altogether. To check for problems, apply the patches one at a time:

    $ quilt push
    Applying patch kubuntu_01_fix_qmax_on_armel.diff
    patching file src/kamoso.cpp
    Hunk #1 FAILED at 398.
    1 out of 1 hunk FAILED -- rejects in file src/kamoso.cpp
    Patch kubuntu_01_fix_qmax_on_armel.diff can be reverse-applied

Se a aplicação puder ser revertida, isto significa que o patch já foi aplicado pelo upstream, então podemos excluir o patch:

    $ quilt delete kubuntu_01_fix_qmax_on_armel
    Removed patch kubuntu_01_fix_qmax_on_armel.diff

Então continue:

    $ quilt push
    Applied kubuntu_02_program_description.diff

É bom executar uma atualização do patch relativo ao fonte do upstream alterado:

    $ quilt refresh
    Refreshed patch kubuntu_02_program_description.diff

Então submeta como sempre:

    $ bzr commit -m "new upstream version"

## 8.5. Fazendo um pacote usar o Quilt

Pacotes modernos usam o Quilt por padrão, que é construído dentro do formato do pacote. Verifique `debian/source/format` para assegurar que ele diz `3.0 (quilt)`.

Pacotes antigos usando o formato de fonte 1.0 terão que explicitar o uso do Quilt, normalmente incluindo um makefile dentro de `debian/rules`.

## 8.6. Configuring Quilt

You can use `~/.quiltrc` file to configure quilt. Here are some options that can be useful for using quilt with debian/packages:

    # Set the patches directory
    QUILT_PATCHES="debian/patches"
    # Remove all useless formatting from the patches
    QUILT_REFRESH_ARGS="-p ab --no-timestamps --no-index"
    # The same for quilt diff command, and use colored output
    QUILT_DIFF_ARGS="-p ab --no-timestamps --no-index --color=auto"

## 8.7. Outros sistemas de patch

Other patch systems used by packages include `dpatch` and `cdbs simple-patchsys`, these work similarly to Quilt by keeping patches in `debian/patches` but have different commands to apply, un-apply or create patches. You can find out which patch system is used by a package by using the `what-patch` command (from the `ubuntu-dev-tools` package). You can use `edit-patch`, shown in previous chapters, as a reliable way to work with all systems.

In even older packages changes will be included directly to sources and kept in the `diff.gz` source file. This makes it hard to upgrade to new upstream versions or differentiate between patches and is best avoided.

Não altere um sistema de patches de um pacote sem discutir isto com o mantenedor Debian ou time Ubuntu responsável. Se não houver sistema de patches, então sinta-se à vontade para adicionar o Quilt.