]> granicus.if.org Git - vim/commitdiff
patch 8.2.3063: crash when switching 'cryptmethod' to xchaha20 with undo file v8.2.3063
authorBram Moolenaar <Bram@vim.org>
Sun, 27 Jun 2021 12:08:24 +0000 (14:08 +0200)
committerBram Moolenaar <Bram@vim.org>
Sun, 27 Jun 2021 12:08:24 +0000 (14:08 +0200)
Problem:    Crash when switching 'cryptmethod' to xchaha20 with an existing
            undo file. (Martin Tournoij)
Solution:   Disable reading undo file when decoding can't be done inplace.
            (issue #8467)

src/bufwrite.c
src/fileio.c
src/version.c

index c91bcd9958f513861d957310336164f02aa14b0d..e480e57e7ca8636d632e7acc14fa3f7b4e76b7e8 100644 (file)
@@ -494,14 +494,16 @@ buf_write_bytes(struct bw_info *ip)
        if (crypt_works_inplace(ip->bw_buffer->b_cryptstate))
        {
 # endif
-           crypt_encode_inplace(ip->bw_buffer->b_cryptstate, buf, len, ip->bw_finish);
+           crypt_encode_inplace(ip->bw_buffer->b_cryptstate, buf, len,
+                                                               ip->bw_finish);
 # ifdef CRYPT_NOT_INPLACE
        }
        else
        {
            char_u *outbuf;
 
-           len = crypt_encode_alloc(curbuf->b_cryptstate, buf, len, &outbuf, ip->bw_finish);
+           len = crypt_encode_alloc(curbuf->b_cryptstate, buf, len, &outbuf,
+                                                               ip->bw_finish);
            if (len == 0)
                return OK;  // Crypt layer is buffering, will flush later.
            wlen = write_eintr(ip->bw_fd, outbuf, len);
@@ -1980,10 +1982,18 @@ restore_backup:
        write_info.bw_start_lnum = start;
 
 #ifdef FEAT_PERSISTENT_UNDO
+       // TODO: if the selected crypt method prevents the undo file from being
+       // written, and existing undo file should be deleted.
        write_undo_file = (buf->b_p_udf
                            && overwriting
                            && !append
                            && !filtering
+# ifdef CRYPT_NOT_INPLACE
+                           // writing undo file requires
+                           // crypt_encode_inplace()
+                           && (curbuf->b_cryptstate == NULL
+                               || crypt_works_inplace(curbuf->b_cryptstate))
+# endif
                            && reset_changed
                            && !checking_conversion);
        if (write_undo_file)
index 7c8f00de3aff697ef9d81877fa7ccab50c60f574..4bd773e0bd944614fa64e23bd878a5d03e48d79e 100644 (file)
@@ -1298,9 +1298,17 @@ retry:
                 * At start of file: Check for magic number of encryption.
                 */
                if (filesize == 0 && size > 0)
+               {
                    cryptkey = check_for_cryptkey(cryptkey, ptr, &size,
                                                  &filesize, newfile, sfname,
                                                  &did_ask_for_key);
+# ifdef CRYPT_NOT_INPLACE
+                   if (curbuf->b_cryptstate != NULL
+                                && !crypt_works_inplace(curbuf->b_cryptstate))
+                       // reading undo file requires crypt_decode_inplace()
+                       read_undo_file = FALSE;
+# endif
+               }
                /*
                 * Decrypt the read bytes.  This is done before checking for
                 * EOF because the crypt layer may be buffering.
index e311104f58e7c30f78114cfb3320885e57281624..1238a4976b520bbddd79b67d192a7083a714b7e8 100644 (file)
@@ -755,6 +755,8 @@ static char *(features[]) =
 
 static int included_patches[] =
 {   /* Add new patch number below this line */
+/**/
+    3063,
 /**/
     3062,
 /**/