about summary refs log tree commit diff
diff options
context:
space:
mode:
-rw-r--r--Completion/User/_cvs943
-rw-r--r--INSTALL4
-rw-r--r--configure.in2
3 files changed, 649 insertions, 300 deletions
diff --git a/Completion/User/_cvs b/Completion/User/_cvs
index 65fa87904..356c7a80a 100644
--- a/Completion/User/_cvs
+++ b/Completion/User/_cvs
@@ -1,315 +1,670 @@
 #compdef cvs
 
-_cvs () {
-  setopt localoptions extendedglob
-
-  typeset -A commands
-  commands=(add "ad new"            admin "adm rcs"         annotate ann
-	    checkout "co get"       commit "ci com"         diff "di dif"
-	    edit ""                 editors ""              export "exp ex"
-	    history "hi his"        import "im imp"         init ""
-	    log "lo rlog"           login "logon lgn"       logout ""
-	    rdiff patch             release "re rel"        remove "rm delete"
-	    status "st stat"        rtag "rt rfreeze"       tag "ta freeze"
-	    unedit ""               update "up upd"         watch ""
-	    watchers "")
-
-  local com="${words[(i)(${(j:|:)${(kv)=commands}})]}"
-
-  local showlist='compstate[list]=list; compstate[force_list]=yes'
-  local showhint="$showlist ; compstate[insert]=''"
-  local complete_D="compadd today yesterday week\\ ago month\\ ago"
-  local complete_k="compadd kv kvl k o b v"
-  local complete_r="_cvsrevisions"
-  local complete_m="compadd -UX 'Enter log message' -n ''; $showhint"
-
-  if (( com < CURRENT )); then
-    case "$words[$com]" in
-      add|ad|new) # "+k:m:"
-	_complete_opts k: "$complete_k" m: "$complete_m" || _cvsaddp
-	;;
-      admin|adm|rcs) # "+ib::c:a:A:e:l::u::LUn:N:m:o:s:t::IqxV:k:"
-	_complete_opts i '' b:: '' c: '' a: '' A: '' e: '' l:: '' u:: '' L '' \
-	  U '' n: '' N: '' m: "$complete_m" o: '' s: '' t:: '' I '' q '' x '' \
-	    V: '' k: "$complete_k" ||
-	_cvstargets
-	;;
-      annotate|ann) # "+lr:D:fR"
-	_complete_opts l '' r: "$complete_r" D: "$complete_D" f '' R '' ||
-	_cvstargets
-	;;
-      checkout|co|get) # "+ANnk:d:flRpQqcsr:D:j:P"
-	_complete_opts A '' N '' n '' k: "$complete_k" d: '_files -/' f '' \
-	  l '' R '' p '' Q '' q '' c '' s '' r: "$complete_r" D: "$complete_D" \
-	  j: "$complete_r" P '' ||
-	_cvsrepositories
-	;;
-      commit|ci|com) # "+nlRm:fF:r:"
-	_complete_opts n '' l '' R '' m: "$complete_m" f '' F: _files \
-	  r: "$complete_r" ||
-	_cvsmodified
-	;;
-      diff|di|dif) # "+abcdefhilnpstuw0123456789BHNRC:D:F:I:L:U:V:W:k:r:"
-	_complete_opts a '' b '' c '' d '' e '' f '' h '' i '' l '' n '' p '' \
-	  s '' t '' u '' w '' 0 '' 1 '' 2 '' 3 '' 4 '' 5 '' 6 '' 7 '' 8 '' \
-	  9 '' B '' H '' N '' R '' C: '' D: "$complete_D" F: '' I: '' L: '' \
-	  U: '' V: '' W: '' k: "$complete_k" r: "$complete_r" ||
-	_cvsmodified || _cvstargets
-	;;
-      edit) # "+lRa:"
-	_complete_opts l '' R '' a: 'compadd edit unedit commit all none' ||
-	_cvstargets
-	;;
-      editors) # "+lR"
-	_complete_opts l '' R '' || _cvstargets
-	;;
-      export|exp|ex) # "+Nnk:d:flRQqr:D:"
-	_complete_opts N '' n '' k: "$complete_k" d: '_files -/' f '' l '' \
-	  R '' Q '' q '' r: "$complete_r" D: "$complete_D" ||
-	_cvsrepositories
-	;;
-      history|hi|his) # "+Tacelow?D:b:f:m:n:p:r:t:u:x:X:z:"
-	_complete_opts T '' a '' c '' e '' l '' o '' w '' \? '' \
-	  D: "$complete_D" b: '' f: '' m: "$complete_m" n: '' p: '' r: '' \
-	  t: '' u: '' x: '' X: '' z: '' ||
-	_cvstargets
-	;;
-      import|im|imp) # "+Qqdb:m:I:k:W:"
-	_complete_opts Q '' q '' d '' b: '' m: "$complete_m" I: _files \
-	  k: "$complete_k" W: '' ||
-	case $[CURRENT-com] in
-	  1) _cvsrepositories;;
-	  2) compadd -UX "Enter vendor tag name" -n '' && eval "$showhint";;
-	  3) compadd -UX "Enter release tag name" -n '' && eval "$showhint";;
-	  *) compadd -UX "No futher arguments used" -n '' && eval "$showhint";;
-	  esac
-	;;
-      init)
-	break
-	;;
-      login|logon|lgn|logout)
-	_complete_opts || _files
-	;;
-      rdiff|patch|pa) # "+V:k:cuftsQqlRD:r:"
-	_complete_opts V: '' k: "$complete_k" c '' u '' f '' t '' s '' Q '' \
-	  q '' l '' R '' D: "$complete_D" r: "$complete_r" ||
-	_cvstargets
-	;;
-      release|re|rel) # "+Qdq"
-	_complete_opts Q '' d '' q '' || _files -/
-	;;
-      remove|rm|delete) # "+flR"
-	_complete_opts f '' l '' R '' || _cvsremovep
-	;;
-      status|st|stat) # "+vlR"
-	_complete_opts v '' l '' R '' || _cvstargets
-	;;
-      tag|ta|freeze) # "+FQqlRcdr:D:bf"
-	_complete_opts F '' Q '' q '' l '' R '' c '' d '' r: "$complete_r" \
-	  D: "$complete_D" b '' f '' ||
-	_cvstargets
-	;;
-      unedit) # "+lR"
-	_complete_opts l '' R '' || _cvstargets
-	;;
-      update|up|upd) # "+ApPflRQqduk:r:D:j:I:W:"
-	_complete_opts A '' p '' P '' f '' l '' R '' Q '' q '' d '' u '' \
-	  k: "$complete_k" r: "$complete_r" D: "$complete_D" j: "$complete_r" \
-	  I: '' W: '' ||
-	_cvstargets
-	;;
-      watch)
-	if (( CURRENT == com + 1 )); then
-	  compadd on off add remove
-	else
-	  case "$words[com+1]" in
-	    on|off) # "+lR"
-	      _complete_opts l '' R '' || _cvstargets
-	      ;;
-	    add|remove) # "+lRa:"
-	      _complete_opts l '' R '' \
-	        a: 'compadd edit unedit commit all none' || \
-	      _cvstargets
-	      ;;
-	  esac
-	fi
-	;;
-      watchers) # "+lR"
-	_complete_opts l '' R '' || _cvstargets
-	;;
-      *) _files;;
-    esac
-    return
-  fi
+# redefine _cvs.
 
-  _complete_opts \
-    H '' Q '' q '' r '' w '' l '' n '' t '' v '' f '' a '' \
-    b: "compadd /usr/local/bin" \
-    T: "compadd $TMPPREFIX:h $TMPDIR /tmp" \
-    e: "compadd vi" \
-    d: "compadd $_cvs_roots || _files -/" \
-    z: "compadd 9'" \
-    s: "_cvs_user_variable" \
-   || 
-  compadd ${(k)commands} ||
-  compadd ${(kv)=commands}
+_cvs () {
+  # "+Qqrwtnlvb:T:e:d:Hfz:s:xa"
+  _arguments -s \
+    -{a,f,H,l,n,Q,q,r,t,v,w,x} \
+    '--version' '--help' '--help-commands' '--help-synonyms' '--help-options' \
+    '--allow-root=:rootdir:_files -/' \
+    '-b+:bindir:_cvs_bindir' \
+    '-T+:temporary directory:_cvs_tempdir' \
+    '-d+:cvsroot:_cvs_root' \
+    '-e+:editor:_cvs_editor' \
+    '-s+:user variable:_cvs_user_variable' \
+    '-z+:gzip level:_cvs_gzip_level' \
+    '*::cvs command:_cvs_command'
 }
 
-_cvsrevisions () {
-  compadd - ${${${(M)${(f)"$(cvs -q status -vl .)"}:#	*}##[ 	]##}%%[ 	]*}
-}
+# define cvs command dispatch function.
 
-_cvsrepositories () {
-  local root=$CVSROOT
-  [[ -f CVS/Root ]] && root=$(<CVS/Root)
+if ! builtin functions _cvs_command >&-; then
+  _cvs_command () {
+    typeset -A cmds
+    cmds=(add " ad new "          admin " adm rcs "       annotate " ann "
+	  checkout " co get "     commit " ci com "       diff " di dif "
+	  edit ""                 editors ""              export " exp ex "
+	  history " hi his "      import " im imp "       init ""
+	  log " lo rlog "         login " logon lgn "     logout ""
+	  rdiff " patch pa "      release " re rel "      remove " rm delete "
+	  status " st stat "      rtag " rt rfreeze "     tag " ta freeze "
+	  unedit ""               update " up upd "       watch ""
+	  watchers "")
 
-  if [[ $root = :* || ! -d $root ]]; then
-    compadd -UX "Enter repository name" -n '' &&
-    { compstate[list]=list; compstate[force_list]=yes; compstate[insert]='' }
-  else
-    compadd - \
-      $root/^CVSROOT(:t) \
-      ${${(M)${(f)"$(<$root/CVSROOT/modules)"}:#[^#]*}%%[ 	]*}
-  fi
-}
+    if (( CURRENT == 1 )); then
+      compadd "$@" ${(k)cmds} || compadd "$@" ${(kv)=cmds}
+    else
+      case "${${(k)cmds[(R)* $words[1] *]}:-$words[1]}" in
+	add) _cvs_add;;
+	admin) _cvs_admin;;
+	annotate) _cvs_annotate;;
+	checkout) _cvs_checkout;;
+	commit) _cvs_commit;;
+	diff) _cvs_diff;;
+	edit) _cvs_edit;;
+	editors) _cvs_editors;;
+	export) _cvs_export;;
+	history) _cvs_history;;
+	import) _cvs_import;;
+	init) _cvs_init;;
+	log) _cvs_log;;
+	login) _cvs_login;;
+	logout) _cvs_logout;;
+	rdiff) _cvs_rdiff;;
+	release) _cvs_release;;
+	remove) _cvs_remove;;
+	status) _cvs_status;;
+	rtag) _cvs_rtag;;
+	tag) _cvs_tag;;
+	unedit) _cvs_unedit;;
+	update) _cvs_update;;
+	watch) _cvs_watch;;
+	watchers) _cvs_watchers;;
+	*) _message "unknown cvs command: $words[1]";;
+      esac
+    fi
+  }
+fi
 
-_cvsprefix () {
-  if [[ -prefix */ ]]; then
-    qpref="${PREFIX%/*}/"
-    pref=$~qpref
-  else
-    qpref=
-    pref=./
-  fi
-}
+# define completion functions for each cvs command
 
-_cvsentries_dir () {
-  entries=($entries ${${${(M)rawentries:#D/*}#D/}%%/*})
-}
+if ! builtin functions _cvs_add >&-; then
+  _cvs_add () {
+    # "+k:m:"
+    _arguments -s \
+      '-k+:keyword substitution:_cvs_k' \
+      '-m+:message:_cvs_m' \
+      '*:file:_cvs_files_unmaintained' \
+  }
+fi
 
-_cvsentries_plain () {
-  entries=($entries ${${${(M)rawentries:#/*}#/}%%/*})
-}
+if ! builtin functions _cvs_admin >&-; then
+  _cvs_admin () {
+    # "+ib::c:a:A:e:l::u::LUn:N:m:o:s:t::IqxV:k:"
+    _arguments -s \
+      -{i,L,U,I,q,x} \
+      '-b-:default branch:(1.1.1)' \
+      '-c+:comment leader (not used):' \
+      '-a+:login names (not work with CVS):' \
+      '-A+:access list to append (not work with CVS):' \
+      '-e+:access list to erase (not work with CVS):' \
+      '-l-:revision to lock:' \
+      '-u-:revision to unlock:' \
+      '-n+:symbolic-name[\:revision]:' \
+      '-N+:symbolic-name[\:revision]:' \
+      '-m+:revision\:msg:' \
+      '-o+:range to delete:' \
+      '-s+:state[\:revision]:' \
+      '-t-:descriptive text:_cvs_admin_t' \
+      '-V+:version (obsolete):' \
+      '-k+:keyword substitution:_cvs_k' \
+      '*:file:_cvs_files'
+  }
+fi
 
-_cvsentries_modified () {
-  if (( $+_cvsentries_modified_disable_stat )) ||
-    ! { zmodload -e stat || zmodload stat }; then
-    _cvsentries_plain
-    return
-  fi
+if ! builtin functions _cvs_admin_t >&-; then
+  _cvs_admin_t () {
+    if compset -P -; then
+      _message 'descriptive text'
+    else
+      _files "$@"
+    fi
+  }
+fi
 
-  local ents pats
-  ents=(${${${${(M)rawentries:#/*}#/}/\\/[^\\/]#\\///}%/[^/]#/[^/]#})
-  pats=(${${${(f)"$(LANG=C builtin stat -gn +mtime -F '%a %b %e %T %Y' ${pref}*(D))"}##*/}/ //})
-  eval 'ents=(${ents:#('${(j:|:)pats:q}')})'
-  entries=($entries ${ents%%/*})
-}
+if ! builtin functions _cvs_annotate >&-; then
+  _cvs_annotate () {
+    # "+lr:D:fR"
+    _arguments -s \
+      -{l,f,R} \
+      '-r+:tag:_cvs_revisions' \
+      '-D+:date:_cvs_D' \
+      '*:file:_cvs_files'
+  }
+fi
 
-_cvsdirentries () {
-  entries=()
-  if [[ -f ${pref}CVS/Entries ]]; then
-    local rawentries
-    rawentries=(${(f)"$(<${pref}CVS/Entries)"})
-    _cvsentries_dir
-  fi
-}
+if ! builtin functions _cvs_checkout >&-; then
+  _cvs_checkout () {
+    # "+ANnk:d:flRpQqcsr:D:j:P"
+    _arguments -s \
+      -{A,N,n,f,l,R,q,c,s,P} \
+      '-k+:keyword substitution:_cvs_k' \
+      '-d+:directory:_files -/' \
+      '-r+:tag:_cvs_revisions' \
+      '-D+:date:_cvs_D' \
+      '-j+:tag:_cvs_revisions' \
+      '*:module:_cvs_modules'
+  }
+fi
 
-_cvsentries () {
-  entries=()
-  if [[ -f ${pref}CVS/Entries ]]; then
-    local rawentries
-    rawentries=(${(f)"$(<${pref}CVS/Entries)"})
-    _cvsentries_plain
-    _cvsentries_dir
-  fi
-}
+if ! builtin functions _cvs_commit >&-; then
+  _cvs_commit () {
+    # "+nlRm:fF:r:"
+    _arguments -s \
+      -{n,l,R,f} \
+      '-m+:message:_cvs_m' \
+      '-F+:log message file:_files' \
+      '-r+:tag:_cvs_revisions' \
+      '*:file:_cvs_files_modified'
+  }
+fi
 
-_cvsmodentries () {
-  entries=()
-  if [[ -f ${pref}CVS/Entries ]]; then
-    local rawentries
-    rawentries=(${(f)"$(<${pref}CVS/Entries)"})
-    _cvsentries_modified
-    _cvsentries_dir
-  fi
-}
+if ! builtin functions _cvs_diff >&-; then
+  _cvs_diff () {
+    # "+abcdefhilnpstuw0123456789BHNRC:D:F:I:L:U:V:W:k:r:"
+    _arguments -s \
+      -{l,R} \
+      '-D+:date:_cvs_D' \
+      '-k+:keyword substitution:_cvs_k' \
+      '-r+:tag:_cvs_revisions' \
+      -{h,p,0,1,2,3,4,5,6,7,8,9} \
+      '--binary' \
+      '--brief' \
+      '--changed-group-format=:format:' \
+      '-c' '-C+:lines:' '--context=-:lines:' \
+      '-e' '--ed' \
+      '-t' '--expand-tabs' \
+      '-f' '--forward-ed' \
+      '--horizon-lines=:lines:' \
+      '--ifdef=:name:' \
+      '-w' '--ignore-all-space' \
+      '-B' '--ignore-blank-lines' \
+      '-i' '--ignore-case' \
+      '-I+:regex:' '--ignore-matching-lines=:regex:' \
+      '-b' '--ignore-space-change' \
+      '--initial-tab' \
+      '*-L+:label:' '*--label=:label:' \
+      '--left-column' \
+      '--line-format=:format:' \
+      '-d' '--minimal' \
+      '-N' '--new-file' \
+      '--new-group-format=:format:' \
+      '--new-line-format=:format:' \
+      '--old-group-format=:format:' \
+      '--old-line-format=:format:' \
+      '--paginate' \
+      '-n' '--rcs' \
+      '-s' '--report-identical-files' \
+      '--show-c-function' \
+      '-F+:regex:' '--show-function-line=:regex:' \
+      '-y' '--side-by-side' \
+      '-H' '--speed-large-files' \
+      '--suppress-common-lines' \
+      '-a' '--text' \
+      '--unchanged-group-format=:format:' \
+      '--unchanged-line-format=:format:' \
+      '-u' '-U+:lines:' '--unified=-:lines:' \
+      '-W:columns:' '--width=:columns:' \
+      '*:file:_cvs_diff_arg'
+  }
+fi
 
-_cvsdirs () {
-  if [[ -d ${pref}CVS ]]; then
-    _cvsdirentries
-    case $#entries in
-      0) false;;
-      1) compgen "$@" -g "${entries:q}";;
-      *) compgen "$@" -g '('${(j:|:)entries:q}')';;
-    esac
-  else
-    _files
-  fi
-}
+if ! builtin functions _cvs_diff_arg >&-; then
+  _cvs_diff_arg () {
+    _cvs_files_modified || _cvs_files
+  }
+fi
 
-_cvstargets () {
-  local qpref pref entries
-  _cvsprefix
-  if [[ -d ${pref}CVS ]]; then
-    _cvsentries
-    case $#entries in
-      0) false;;
-      1) compgen -g "${entries:q}";;
-      *) compgen -g '('${(j:|:)entries:q}')';;
-    esac
-  else
-    _files
-  fi
-}
+if ! builtin functions _cvs_edit >&-; then
+  _cvs_edit () {
+    # "+lRa:"
+    _arguments -s \
+      -{l,R} \
+      '-a+:action:(edit unedit commit all none)'
+      '*:file:_cvs_files'
+  }
+fi
 
-_cvsmodified () {
-  local qpref pref entries
-  _cvsprefix
-  if [[ -d ${pref}CVS ]]; then
-    _cvsmodentries
-    case $#entries in
-      0) false;;
-      1) compgen -g "${entries:q}";;
-      *) compgen -g '('${(j:|:)entries:q}')';;
-    esac
-  else
-    _files 
-  fi
-}
+if ! builtin functions _cvs_editors >&-; then
+  _cvs_editors () {
+    # "+lR"
+    _arguments -s \
+      -{l,R} \
+      '*:file:_cvs_files'
+  }
+fi
 
-_cvsremovep () {
-  local qpref pref entries
-  _cvsprefix
-  if [[ -d ${pref}CVS ]]; then
-    _cvsentries
-    setopt localoptions unset
-    local omit
-    omit=(${pref}*(D:t))
-    eval 'entries=(${entries:#('${(j:|:)omit:q}')})'
-    compadd -P "$qpref" - ${entries:q} ||
-    _cvsdirs
-  else
-    _files
-  fi
-}
+if ! builtin functions _cvs_export >&-; then
+  _cvs_export () {
+    # "+Nnk:d:flRQqr:D:"
+    _arguments -s \
+      -{N,n,f,l,R,Q,q} \
+      '-k+:keyword substitution:_cvs_k' \
+      '-d+:directory:_files -/' \
+      '-r+:tag:_cvs_revisions' \
+      '-D+:date:_cvs_D' \
+      '*:module:_cvs_modules'
+  }
+fi
+
+if ! builtin functions _cvs_history >&-; then
+  _cvs_history () {
+    # "+Tacelow?D:b:f:m:n:p:r:t:u:x:X:z:"
+    _arguments -s \
+      -{T,a,c,e,l,o,w,\?} \
+      '-D+:date:_cvs_D' \
+      '-b+:string:' \
+      '-f+:arg:' \
+      '-m+:module:_cvs_modules' \
+      '-n+:arg:' \
+      '*-p+:repository:' \
+      '-r+:rev:' \
+      '-t+:tag:' \
+      '-u+:user name:' \
+      '-x+:type:_cvs_history_x' \
+      '-X+:arg:' \
+      '-z+:arg:' \
+      '*:file:_cvs_files'
+  }
+fi
+
+if ! builtin functions _cvs_history_x >&-; then
+  _cvs_history_x () {
+    compset -P '*'
+
+    compadd "$@" -y '(
+    F\ --\ release
+    O\ --\ checkout
+    E\ --\ export
+    T\ --\ rtag
+    C\ --\ merge\ collision-detected
+    G\ --\ merge\ succeed
+    U\ --\ working\ file\ was\ copied
+    W\ --\ working\ file\ was\ deleted
+    A\ --\ A\ file\ was\ added
+    M\ --\ A\ file\ was\ modified
+    R\ --\ A\ file\ was\ removed
+    )' F O E T C G U W A M R
+  }
+fi
+
+if ! builtin functions _cvs_import >&-; then
+  _cvs_import () {
+    # "+Qqdb:m:I:k:W:"
+    _arguments -s \
+      -{Q,q,d} \
+      '-b+:branch:' \
+      '-m+:message:_cvs_m' \
+      '*-I+:name:_files' \
+      '-k+:keyword substitution:_cvs_k' \
+      '*-W+:spec:' \
+      ':repository:_cvs_modules' \
+      ':vendor tag:' \
+      ':release tag:'
+  }
+fi
+
+if ! builtin functions _cvs_init >&-; then
+  _cvs_init () {
+    false
+  }
+fi
+
+if ! builtin functions _cvs_login >&-; then
+  _cvs_login () {
+    false
+  }
+fi
+
+if ! builtin functions _cvs_logout >&-; then
+  _cvs_logout () {
+    false
+  }
+fi
+
+if ! builtin functions _cvs_rdiff >&-; then
+  _cvs_rdiff () {
+    # "+V:k:cuftsQqlRD:r:"
+    _arguments -s \
+      -{c,u,f,t,s,Q,q,l,R} \
+      '-V+:version:' \
+      '-k+:keyword substitution:_cvs_k' \
+      '*-D+:date:_cvs_D' \
+      '*-r+:tag:_cvs_revisions' \
+      '*:module:_cvs_modules'
+  }
+fi
+
+if ! builtin functions _cvs_release >&-; then
+  _cvs_release () {
+    # "+Qdq"
+    _arguments -s \
+      -{Q,d,q} \
+      '*:directory:_files -/'
+  }
+fi
+
+if ! builtin functions _cvs_remove >&-; then
+  _cvs_remove () {
+    # "+flR"
+    _arguments -s \
+      -{f,l,R} \
+      '*:file:_cvs_files_removed'
+  }
+fi
+
+if ! builtin functions _cvs_status >&-; then
+  _cvs_status () {
+    # "+vlR"
+    _arguments -s \
+      -{v,l,R} \
+      '*:file:_cvs_files'
+  }
+fi
+
+if ! builtin functions _cvs_tag >&-; then
+  _cvs_tag () {
+    # "+FQqlRcdr:D:bf"
+    _arguments -s \
+      -{F,Q,q,l,R,c,d,b,f} \
+      '-r+:tag:_cvs_revisions' \
+      '-D+:date:_cvs_D' \
+      '*:file:_cvs_files'
+  }
+fi
+
+if ! builtin functions _cvs_unedit >&-; then
+  _cvs_unedit () {
+    # "+lR"
+    _arguments -s \
+      -{l,R} \
+      '*:file:_cvs_files'
+  }
+fi
+
+if ! builtin functions _cvs_update >&-; then
+  _cvs_update () {
+    # "+ApPflRQqduk:r:D:j:I:W:"
+    _arguments -s \
+      -{A,p,P,f,l,R,Q,q,d,u} \
+      '-k+:keyword substitution:_cvs_k' \
+      '-r+:tag:_cvs_revisions' \
+      '-D+:date:_cvs_D' \
+      '-j+:tag:_cvs_revisions' \
+      '*-I+:name:_files' \
+      '*-W+:spec:' \
+      '*:file:_cvs_files'
+  }
+fi
+
+if ! builtin functions _cvs_watch >&-; then
+  _cvs_watch () {
+    if (( CURRENT == 2 )); then
+      compadd on off add remove
+    else
+      case "$words[2]" in
+	on|off) # "+lR"
+	  _arguments -s \
+	  -{l,R} \
+	  ':watch command:' \
+	  ':*:file:_cvs_files'
+	  ;;
+	add|remove) # "+lRa:"
+	  _arguments -s \
+	  -{l,R} \
+	  '*-a+:action:(edit unedit commit all none)' \
+	  ':watch command:' \
+	  ':*:file:_cvs_files'
+	  ;;
+      esac
+    fi
+  }
+fi
+
+if ! builtin functions _cvs_watchers >&-; then
+  _cvs_watchers () {
+    # "+lR"
+    _arguments -s \
+      -{l,R} \
+      ':*:file:_cvs_files'
+  }
+fi
+
+if ! builtin functions _cvs_root >&-; then
+  _cvs_root () {
+    compadd "$@" $_cvs_roots || _files "$@" -/
+  }
+fi
+
+if ! builtin functions _cvs_tempdir >&-; then
+  _cvs_tempdir () {
+    compadd "$@" $TMPPREFIX:h $TMPDIR /tmp
+  }
+fi
+
+if ! builtin functions _cvs_user_variable >&-; then
+  _cvs_user_variable () {
+    if compset -P '*='; then
+      _default
+    else
+      _message "variable=value"
+    fi
+  }
+fi
+
+# define completion functions for cvs global options.
+
+if ! builtin functions _cvs_bindir >&-; then
+  _cvs_bindir () {
+    compadd "$@" /usr/local/bin || _files "$@" -/
+  }
+fi
+
+if ! builtin functions _cvs_editor >&-; then
+  _cvs_editor () {
+    compadd "$@" vi
+  }
+fi
+
+if ! builtin functions _cvs_gzip_level >&-; then
+  _cvs_gzip_level () {
+    compadd "$@" 9
+  }
+fi
+
+# define completion functions for cvs common options and arguments.
+
+if ! builtin functions _cvs_D >&-; then
+  _cvs_D () {
+    compadd "$@" today yesterday week\ ago month\ ago
+  }
+fi
+
+if ! builtin functions _cvs_k >&-; then
+  _cvs_k () {
+    compadd "$@" kv kvl k o b v
+  }
+fi
+
+if ! builtin functions _cvs_m >&-; then
+  _cvs_m () {
+    _message "log message"
+  }
+fi
+
+if ! builtin functions _cvs_modules >&-; then
+  _cvs_modules () {
+    local root=$CVSROOT
+    [[ -f CVS/Root ]] && root=$(<CVS/Root)
+
+    if [[ $root = :* || ! -d $root ]]; then
+      _message "module name"
+    else
+      compadd - \
+	$root/^CVSROOT(:t) \
+	${${(M)${(f)"$(<$root/CVSROOT/modules)"}:#[^#]*}%%[ 	]*}
+    fi
+  }
+fi
+
+if ! builtin functions _cvs_revisions >&-; then
+  _cvs_revisions () {
+    compadd - ${${${(M)${(f)"$(cvs -q status -vl .)"}:#	*}##[ 	]##}%%[ 	]*}
+  }
+fi
+
+# define completion functions for files maintained by cvs.
+
+if ! builtin functions _cvs_setup_prefix >&-; then
+  _cvs_setup_prefix () {
+    if [[ -prefix */ ]]; then
+      qpref="${PREFIX%/*}/"
+      pref=$~qpref
+    else
+      qpref=
+      pref=./
+    fi
+  }
+fi
+
+if ! builtin functions _cvs_extract_directory_entries >&-; then
+  _cvs_extract_directory_entries () {
+    entries=($entries ${${${(M)rawentries:#D/*}#D/}%%/*})
+  }
+fi
 
-_cvsaddp () {
-  local qpref pref entries
-  _cvsprefix
-  if [[ -d ${pref}CVS ]]; then
-    _cvsentries
-    setopt localoptions unset
-    local omit
-    omit=($_cvs_ignore_default ${entries:q} ${=cvsignore})
-    [[ -r ~/.cvsignore ]] && omit=($omit $(<~/.cvsignore))
-    [[ -r ${pref}.cvsignore ]] && omit=($omit $(<${pref}.cvsignore))
-    compgen -g '*~(*/|)('${(j:|:)omit}')(D)' ||
-    compgen -g '*~(*/|)('${(j:|:)entries:q}')(D)' ||
-    _cvsdirs
+if ! builtin functions _cvs_extract_file_entries >&-; then
+  _cvs_extract_file_entries () {
+    entries=($entries ${${${(M)rawentries:#/*}#/}%%/*})
+  }
+fi
+
+if ! builtin functions _cvs_extract_modifiedfile_entries >&-; then
+  _cvs_extract_modifiedfile_entries () {
+    if [[ -n "$compconfig[_cvs_disable_stat]" ]] ||
+      ! { zmodload -e stat || zmodload stat }; then
+      _cvs_extract_file_entries
+      return
+    fi
+
+    local ents pats
+    ents=(${${${${(M)rawentries:#/*}#/}/\\/[^\\/]#\\///}%/[^/]#/[^/]#})
+    pats=(${${${(f)"$(LANG=C builtin stat -gn +mtime -F '%a %b %e %T %Y' ${pref}*(D))"}##*/}/ //})
+    eval 'ents=(${ents:#('${(j:|:)${(@)pats:q}}')})'
+    entries=($entries ${ents%%/*})
+  }
+fi
+
+if ! builtin functions _cvs_setup_allentries >&-; then
+  _cvs_setup_allentries () {
+    entries=()
+    if [[ -f ${pref}CVS/Entries ]]; then
+      local rawentries
+      rawentries=(${(f)"$(<${pref}CVS/Entries)"})
+      _cvs_extract_file_entries
+      _cvs_extract_directory_entries
+    fi
+  }
+fi
+
+if ! builtin functions _cvs_setup_direntries >&-; then
+  _cvs_setup_direntries () {
+    entries=()
+    if [[ -f ${pref}CVS/Entries ]]; then
+      local rawentries
+      rawentries=(${(f)"$(<${pref}CVS/Entries)"})
+      _cvs_extract_directory_entries
+    fi
+  }
+fi
+
+if ! builtin functions _cvs_setup_modentries >&-; then
+  _cvs_setup_modentries () {
+    entries=()
+    if [[ -f ${pref}CVS/Entries ]]; then
+      local rawentries
+      rawentries=(${(f)"$(<${pref}CVS/Entries)"})
+      _cvs_extract_modifiedfile_entries
+      _cvs_extract_directory_entries
+    fi
+  }
+fi
+
+if ! builtin functions _cvs_directories >&-; then
+  _cvs_directories () {
+    if [[ -d ${pref}CVS ]]; then
+      _cvs_setup_direntries
+      (( $#entries )) && compgen "$@" -g "${(j:|:)${(@)entries:q}}"
+    else
+      _files "$@"
+    fi
+  }
+fi
+
+if ! builtin functions _cvs_files >&-; then
+  _cvs_files () {
+    local qpref pref entries
+    _cvs_setup_prefix
+    if [[ -d ${pref}CVS ]]; then
+      _cvs_setup_allentries
+      (( $#entries )) && compgen "$@" -g "${(j:|:)${(@)entries:q}}"
+    else
+      _files "$@"
+    fi
+  }
+fi
+
+if ! builtin functions _cvs_files_modified >&-; then
+  _cvs_files_modified () {
+    local qpref pref entries
+    _cvs_setup_prefix
+    if [[ -d ${pref}CVS ]]; then
+      _cvs_setup_modentries
+      (( $#entries )) && compgen "$@" -g "${(j:|:)${(@)entries:q}}"
+    else
+      _files "$@"
+    fi
+  }
+fi
+
+if ! builtin functions _cvs_files_removed >&-; then
+  _cvs_files_removed () {
+    local qpref pref entries
+    _cvs_setup_prefix
+    if [[ -d ${pref}CVS ]]; then
+      _cvs_setup_allentries
+      setopt localoptions unset
+      local omit
+      omit=(${pref}*(D:t))
+      eval 'entries=(${entries:#('${(j:|:)${(@)omit:q}}')})'
+      compadd "$@" -P "$qpref" - ${entries:q} ||
+      _cvs_directories "$@"
+    else
+      _files "$@"
+    fi
+  }
+fi
+
+if ! builtin functions _cvs_files_unmaintained >&-; then
+  _cvs_files_unmaintained () {
+    local qpref pref entries
+    _cvs_setup_prefix
+    if [[ -d ${pref}CVS ]]; then
+      _cvs_setup_allentries
+      setopt localoptions unset
+      local omit
+      omit=($_cvs_ignore_default ${entries:q} ${=cvsignore})
+      [[ -r ~/.cvsignore ]] && omit=($omit $(<~/.cvsignore))
+      [[ -r ${pref}.cvsignore ]] && omit=($omit $(<${pref}.cvsignore))
+      compgen "$@" -g '*~(*/|)('${(j:|:)omit}')(D)' ||
+      compgen "$@" -g '*~(*/|)('${(j:|:)${(@)entries:q}}')(D)' ||
+      _cvs_directories "$@"
+    else
+      _files "$@"
+    fi
+  }
+fi
+
+# define configuration variables.
+
+if (( ! $+_cvs_roots )); then
+  if [[ -f ~/.cvspass ]]; then
+    _cvs_roots=(${${(f)"$(<~/.cvspass)"}%% *})
   else
-    _files
+    _cvs_roots=()
   fi
-}
+fi
 
 if (( ! $+_cvs_ignore_default )); then
   _cvs_ignore_default=(
@@ -320,12 +675,6 @@ if (( ! $+_cvs_ignore_default )); then
   )
 fi
 
-if (( ! $+_cvs_roots )); then
-  if [[ -f ~/.cvspass ]]; then
-    _cvs_roots=(${${(f)"$(<~/.cvspass)"}%% *})
-  else
-    _cvs_roots=()
-  fi
-fi
+# call real _cvs.
 
 _cvs "$@"
diff --git a/INSTALL b/INSTALL
index 8bdf86725..c9a4b0619 100644
--- a/INSTALL
+++ b/INSTALL
@@ -253,7 +253,7 @@ FUNCTIONS_INSTALL, either when running configure (e.g.
 Completion or Functions subdirectories.  By default, all the functions for
 the Completion system will be installed (see the zshcompsys manual page),
 plus those provide functions for the line editor, i.e.
-  FUNCTIONS_INSTALL='Core/* Base/* Builtins/* User/* Commands/* Cvs/* Debian/*  Linux/* X/* Zle/*'
+  FUNCTIONS_INSTALL='Core/* Base/* Builtins/* User/* Commands/* Debian/* Linux/* X/* Zle/*'
 and if the --enable-dynamic option was given, the functions in
 Functions/Zftp, which require the zftp module to be available (see the
 zshzftpsys manual page), will be included as well.  Note, however, that
@@ -262,7 +262,7 @@ system-specific.
 
 There are also some miscellaneous functions with documentation in comments;
 the complete set of functions can be installed with
-  FUNCTIONS_INSTALL='Core/* Base/* Builtins/* User/* Commands/* Cvs/* \
+  FUNCTIONS_INSTALL='Core/* Base/* Builtins/* User/* Commands/* \
   Debian/* Linux/* X/* Misc/* Zftp/* Zle/*'
 Note you should set this by hand to include `Zftp/*' if you have zftp
 compiled into a statically linked shell.
diff --git a/configure.in b/configure.in
index e4e82b025..5177222a4 100644
--- a/configure.in
+++ b/configure.in
@@ -215,7 +215,7 @@ AC_ARG_ENABLE(function-subdirs,
 [  --enable-function-subdirs  install functions in subdirectories])
 
 if test "x${FUNCTIONS_INSTALL+set}" != xset; then
-  FUNCTIONS_INSTALL="Core/* Base/* Builtins/* User/* Commands/* Cvs/* Debian/* Linux/* X/* Zle/*"
+  FUNCTIONS_INSTALL="Core/* Base/* Builtins/* User/* Commands/* Debian/* Linux/* X/* Zle/*"
   if test $dynamic != no; then
     FUNCTIONS_INSTALL="${FUNCTIONS_INSTALL} Zftp/*"
   fi