Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What causes git-apply "corrupt patch?"

Tags:

git

patch

(long story ...)

I'm in the midst of bringing a gigantic PHP application up to the present century ... ;-) ... while other teams are continuing to maintain the existing version of it.

This has lead, so far, to about 275 patches. Trouble is, one of the changes that we've made is to convert <? tags to <?php, and several similar changes throughout the code. All of which, of course, prevent applying patches, because (indeed ...) the source-code doesn't match.

So, I thought to write a little script to edit the patch files: to change the tags in the patch.

What I'm getting, though, is corrupt patch.

So, what I'd like to know is: what causes this message? That is to say, what sort of errors is Git looking for, when it comes up with this message? I need to "tweak my tweaker" ... ahem ... so that the edited patches work. (N.B. the original patch-files, before I tweak them, are not "corrupt," so it must be something I'm doing.)

My script is attempting to change the aforesaid PHP tag, and <?php echo, and one function-name. Nothing more than a global preg-replace. I don't readily see what I could be munging that would be of, shall we say, "structural concern" to Git. But, obviously, something is.

Example patch: corrupt patch at line 37 ...

From 342c5939da8cf4cbe495be7d635cd627bd2a44ed Mon Sep 17 00:00:00 2001
From: xxx <[email protected]>
Date: Wed, 17 Feb 2016 03:45:31 +0000
Subject: [PATCH 001/275] Make it all work 


---
 catalog/includes/modules/shipping/upsFreeGround.php | 2 +-
 catalog/product_info_v3.php                         | 6 +++---
 2 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/catalog/includes/modules/shipping/upsFreeGround.php b/catalog/includes/modules/shipping/upsFreeGround.php
index 45a6da4..55ccecb 100755
--- a/catalog/includes/modules/shipping/upsFreeGround.php
+++ b/catalog/includes/modules/shipping/upsFreeGround.php
@@ -194,7 +194,7 @@ function quote($method = '') {

         // Can probably combine this with the above, eventually
         $allFreeBW2016Plaques = false;
-           if (STORES_ID == 10) {
+           if ((STORES_ID == 10) || (STORES_ID == 26)) {
             $allFreeBW2016Plaques = true;
             foreach ($order->products as $aProduct) {
                    $thisNote = $aProduct['product_specific_notes'];
diff --git a/catalog/product_info_v3.php b/catalog/product_info_v3.php
index 09d88de..10d9b76 100644
--- a/catalog/product_info_v3.php
+++ b/catalog/product_info_v3.php
@@ -186,7 +186,7 @@ function doRequestComplete() {
        }
    }
 <?php -if ((STORES_ID == 10) && (in_array($products_id, $bwFreePlaqueIDList2016))) { ?>
+if (((STORES_ID == 10) || (STORES_ID == 26)) && (in_array($products_id, $bwFreePlaqueIDList2016))) { ?>
 function doCheckBW2016PlaqueProperty() {
    thePropertyNumber = document.getElementById('propertyToCheck');
    if (thePropertyNumber.value == "") {
@@ -1426,7 +1426,7 @@ if($combo_count>0) { ?>
                        ?>
                        </div> <!-- div_add_to_cart -->
            </div> <!-- cart_info_row2 -->
-           <?php if ((STORES_ID == 10) && (in_array( $products_id, $bwFreePlaqueIDList2016))) {
+           <?php if (((STORES_ID == 10) || (STORES_ID == 26)) && (in_array( $products_id, $bwFreePlaqueIDList2016))) {
                // First, let's see if we are "sold out"
                $query = "select bw_plaque_2016_id from bw_plaque_2016 where first_one_free='1' limit 1";
                $bwpRes = tep_db_query( $query);
@@ -1629,7 +1629,7 @@ DIVCONTAINER;
 </table> <!--pageTable for sure -->

 <script type='text/javascript'>
-   <?php if ((STORES_ID == 10) && (in_array( $products_id, $bwFreePlaqueIDList2016))) { ?>
+   <?php if (((STORES_ID == 10) || (STORES_ID == 26)) && (in_array( $products_id, $bwFreePlaqueIDList2016))) { ?>
    function doFreePlaquePriceChange() {
        // Change the quantity to 1
        $('quantityToAdd').setValue('1');
-- 
2.6.4 (Apple Git-63)
like image 592
Mike Robinson Avatar asked Jun 25 '16 15:06

Mike Robinson


1 Answers

tl;dr: I suspect that you have somehow removed a line ending when transforming a line that consists only of <?.

Your script has either removed an important line in the patch, or you have altered the headers. The first hunk of the diff of catalog/product_info_v3.php is malformed.

Its header is:

@@ -186,7 +186,7 @@ function doRequestComplete() {

Which indicates information about the how the hunk corresponds to the preimage (the original file) and the postimage (produced by applying this patch). The preimage information is prefixed by a -, and is -186,7, indicating that this hunk includes 7 lines from the preimage, beginning at line 186. The postimage information is prefixed by a +, and is +186,7, indicating that this hunk will emit 7 lines to the postimage, beginning at line 186.

These 7 lines can either include context (which are lines in common, prefixed with a space), lines that exist only in the preimage (prefixed with a -), or lines that exist only in the postimage (prefixed with a +).

Looking at the hunk at then labeling each line with its type:

  context:         }
  context:     }
  context:  <?php -if ((STORES_ID == 10) && (in_array($products_id, $bwFreePlaqueIDList2016))) { ?>
postimage: +if (((STORES_ID == 10) || (STORES_ID == 26)) && (in_array($products_id, $bwFreePlaqueIDList2016))) { ?>
  context:  function doCheckBW2016PlaqueProperty() {
  context:     thePropertyNumber = document.getElementById('propertyToCheck');
  context:     if (thePropertyNumber.value == "") {

The context lines, again, will be in both the preimage and the postimage. So there are 6 lines in total for the preimage, and 7 lines for the postimage.

But your header said that there were 7 lines for the preimage! So either the header is wrong or the instructions are wrong. (And Git is expecting to see another line of preimage at line 37, but instead it's a new header line, so Git has determined that your patch file is corrupt.)

The lines in this patch suggest that you are adding the if line to the postimage, which did not exist in the preimage. If this is correct, then you have broken your header, and it should be -186,6 +186,7 indicating that there is a line being added to the postimage.

Alternately, if you were changing the if line, then you have omitted its preimage state, and you should have a line above the postimage line.

Looking carefully, it looks like you've actually missed a newline after the <?php in the line above. Your context was probably not <?php -if ... since I suspect that is not valid PHP, with a hyphen in front of the if.

I suspect that this hunk should look like:

@@ -186,7 +186,7 @@ function doRequestComplete() {
       }
   }
 <?php
-if ((STORES_ID == 10) && (in_array($products_id, $bwFreePlaqueIDList2016))) { ?>
+if (((STORES_ID == 10) || (STORES_ID == 26)) && (in_array($products_id, $bwFreePlaqueIDList2016))) { ?>
 function doCheckBW2016PlaqueProperty() {
    thePropertyNumber = document.getElementById('propertyToCheck');
    if (thePropertyNumber.value == "") {

Which is not corrupt, and now there are 7 lines of preimage (the six context lines, plus the line that only exists in the preimage that are prefixed with the -) and 7 lines of postimage (the six context lines, plus the line that only exists in the postimage that are prefixed with the +.)

So now we have a legal patch, as the instructions match the header.

like image 195
Edward Thomson Avatar answered Sep 24 '22 14:09

Edward Thomson