Skip to content

NoMatchParen might cause E201: *ReadPre autocommands must not change current buffer #345

Description

@GoogleCodeExporter
When using "NoMatchParen" (from the matchparen plugin in the runtime) via
a *ReadPre autocommand this might cause a E201, because it uses "windo"
 and then the "(curbuf != old_curbuf)" check in Vim's readfile function fails.

What steps will reproduce the problem?
1. vim -u NONE -N -p file1 file2
2. runtime plugin/matchparen.vim
3. au BufReadPre * NoMatchParen
4. !echo foo >> file2
5. Vim will ask to reload the file, pressing "l" will cause the error:

E201: *ReadPre autocommands must not change current buffer
E321: Could not reload "file2"

The following patch fixes it.  Given how necessary such an Windo function
usually is, which restores the previous window, I think it would be useful to
have it provided by Vim itself somehow.  The same applies to "bufdo".

    diff --git i/runtime/plugin/matchparen.vim w/runtime/plugin/matchparen.vim
    index 3804ab9..396ff32 100644
    --- i/runtime/plugin/matchparen.vim
    +++ w/runtime/plugin/matchparen.vim
    @@ -181,9 +181,16 @@ function! s:Highlight_Matching_Pair()
     endfunction

     " Define commands that will disable and enable the plugin.
    -command! NoMatchParen windo silent! call matchdelete(3) | unlet! g:loaded_matchparen |
    +function! s:Windo(command)
    +    let curaltwin = winnr('#') ? winnr('#') : 1
    +    let currwin = winnr()
    +    execute 'windo ' . a:command
    +    execute curaltwin . 'wincmd w'
    +    execute currwin . 'wincmd w'
    +endfunction
    +command! NoMatchParen call s:Windo('silent! call matchdelete(3)') | unlet! g:loaded_matchparen |
              \ au! matchparen
    -command! DoMatchParen runtime plugin/matchparen.vim | windo doau CursorMoved
    +command! DoMatchParen runtime plugin/matchparen.vim | call s:Windo('doau CursorMoved')


The following patch fixes it in LargeFile itself:

    diff --git i/plugin/LargeFile.vim w/plugin/LargeFile.vim
    index 41a90d3..8b21c0c 100644
    --- i/plugin/LargeFile.vim
    +++ w/plugin/LargeFile.vim
    @@ -73,7 +73,7 @@ fun! s:LargeFile(force,fname)
          au BufLeave       <buffer>        call s:LargeFileLeave()
            endif
            au WinEnter             *                       call s:LargeFileWinEnter()
    -    au BufUnload       <buffer>        augroup LargeFileAU|au! <buffer>|augroup END
    +    au BufUnload       <buffer>        augroup LargeFileAU|exec 'au! * <buffer>'|augroup END
        augroup END
        let b:LargeFile_mode = 1
     "   call Decho("turning  b:LargeFile_mode to ".b:LargeFile_mode)
    @@ -105,7 +105,14 @@ fun! s:ParenMatchOff()
        redir END
        if matchparen_enabled =~ 'g:loaded_matchparen'
            let b:LF_nmpkeep= 1
    +    " Disable matchparen. (Re)store current window numbers, it uses "windo",
    +    " and this might cause 'E201: *ReadPre autocommands must not change
    +    " current buffer'.
    +    let curaltwin = winnr('#') ? winnr('#') : 1
    +    let currwin = winnr()
            NoMatchParen
    +    execute curaltwin . 'wincmd w'
    +    execute currwin . 'wincmd w'
        endif
     "  call Dret("s:ParenMatchOff")
     endfun

Original issue reported on code.google.com by dhahler@gmail.com on 20 Mar 2015 at 6:52

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions