2 * Copyright (C) 1986-2005 The Free Software Foundation, Inc.
4 * Portions Copyright (C) 1998-2005 Derek Price, Ximbiot <http://ximbiot.com>,
7 * Portions Copyright (C) 1992, Brian Berliner and Jeff Polk
8 * Portions Copyright (C) 1989-1992, Brian Berliner
10 * You may distribute under the terms of the GNU General Public License as
11 * specified in the README file that comes with the CVS source distribution.
15 * "checkout" creates a "version" of an RCS repository. This version is owned
16 * totally by the user and is actually an independent copy, to be dealt with
17 * as seen fit. Once "checkout" has been called in a given directory, it
18 * never needs to be called again. The user can keep up-to-date by calling
19 * "update" when he feels like it; this will supply him with a merge of his
20 * own modifications and the changes made in the RCS original. See "update"
23 * "checkout" can be given a list of directories or files to be updated and in
24 * the case of a directory, will recursivley create any sub-directories that
25 * exist in the repository.
27 * When the user is satisfied with his own modifications, the present version
28 * can be committed by "commit"; this keeps the present version in tact,
31 * The call is cvs checkout [options] <module-name>...
33 * "checkout" creates a directory ./CVS, in which it keeps its administration,
34 * in two files, Repository and Entries. The first contains the name of the
35 * repository. The second contains one line for each registered file,
36 * consisting of the version number it derives from, its time stamp at
37 * derivation time and its name. Both files are normal files and can be
38 * edited by the user, if necessary (when the repository is moved, e.g.)
43 static char *findslash (char *start
, char *p
);
44 static int checkout_proc (int argc
, char **argv
, char *where
,
45 char *mwhere
, char *mfile
, int shorten
,
46 int local_specified
, char *omodule
,
49 static const char *const checkout_usage
[] =
51 "Usage:\n %s %s [-ANPRcflnps] [-r rev] [-D date] [-d dir]\n",
52 " [-j rev1] [-j rev2] [-k kopt] modules...\n",
53 "\t-A\tReset any sticky tags/date/kopts.\n",
54 "\t-N\tDon't shorten module paths if -d specified.\n",
55 "\t-P\tPrune empty directories.\n",
56 "\t-R\tProcess directories recursively.\n",
57 "\t-c\t\"cat\" the module database.\n",
58 "\t-f\tForce a head revision match if tag/date not found.\n",
59 "\t-l\tLocal directory only, not recursive\n",
60 "\t-n\tDo not run module program (if any).\n",
61 "\t-p\tCheck out files to standard output (avoids stickiness).\n",
62 "\t-s\tLike -c, but include module status.\n",
63 "\t-r rev\tCheck out revision or tag. (implies -P) (is sticky)\n",
64 "\t-D date\tCheck out revisions as of date. (implies -P) (is sticky)\n",
65 "\t-d dir\tCheck out into dir instead of module name.\n",
66 "\t-k kopt\tUse RCS kopt -k option on checkout. (is sticky)\n",
67 "\t-j rev\tMerge in changes made between current revision and rev.\n",
68 "(Specify the --help global option for a list of other help options)\n",
72 static const char *const export_usage
[] =
74 "Usage: %s %s [-NRfln] [-r tag] [-D date] [-d dir] [-k kopt] module...\n",
75 "\t-N\tDon't shorten module paths if -d specified.\n",
76 "\t-f\tForce a head revision match if tag/date not found.\n",
77 "\t-l\tLocal directory only, not recursive\n",
78 "\t-R\tProcess directories recursively (default).\n",
79 "\t-n\tDo not run module program (if any).\n",
80 "\t-r tag\tExport tagged revisions.\n",
81 "\t-D date\tExport revisions as of date.\n",
82 "\t-d dir\tExport into dir instead of module name.\n",
83 "\t-k kopt\tUse RCS kopt -k option on checkout.\n",
84 "(Specify the --help global option for a list of other help options)\n",
88 static int checkout_prune_dirs
;
89 static int force_tag_match
;
94 static bool tag_validated
;
96 static char *join_rev1
, *join_date1
;
97 static char *join_rev2
, *join_date2
;
98 static bool join_tags_validated
;
99 static char *preload_update_dir
;
100 static char *history_name
;
101 static enum mtype m_type
;
104 checkout (int argc
, char **argv
)
109 int cat
= 0, err
= 0, status
= 0;
110 int run_module_prog
= 1;
114 const char *valid_options
;
115 const char *const *valid_usage
;
116 char *join_orig1
, *join_orig2
;
118 /* initialize static options */
125 tag
= date
= join_rev1
= join_date1
= join_rev2
= join_date2
=
126 join_orig1
= join_orig2
= preload_update_dir
= NULL
;
128 tag_validated
= join_tags_validated
= false;
132 * A smaller subset of options are allowed for the export command, which
133 * is essentially like checkout, except that it hard-codes certain
134 * options to be default (like -kv) and takes care to remove the CVS
135 * directory when it has done its duty
137 if (strcmp (cvs_cmd_name
, "export") == 0)
140 valid_options
= "+Nnk:d:flRQqr:D:";
141 valid_usage
= export_usage
;
146 valid_options
= "+ANnk:d:flRpQqcsr:D:j:P";
147 valid_usage
= checkout_usage
;
157 while ((c
= getopt (argc
, argv
, valid_options
)) != -1)
170 options
= RCS_check_kflag (optarg
);
177 /* The CVS 1.5 client sends these options (in addition to
178 Global_option requests), so we must ignore them. */
181 "-q or -Q must be specified before \"%s\"",
191 checkout_prune_dirs
= 1;
195 run_module_prog
= 0; /* don't run module prog when piping */
196 noexec
= nolock
= 1; /* so no locks will be created */
213 parse_tagdate (&tag
, &date
, optarg
);
214 checkout_prune_dirs
= 1;
217 if (date
) free (date
);
218 date
= Make_Date (optarg
);
219 checkout_prune_dirs
= 1;
222 if (join_rev2
|| join_date2
)
223 error (1, 0, "only two -j options can be specified");
224 if (join_rev1
|| join_date1
)
226 if (join_orig2
) free (join_orig2
);
227 join_orig2
= xstrdup (optarg
);
228 parse_tagdate (&join_rev2
, &join_date2
, optarg
);
232 if (join_orig1
) free (join_orig1
);
233 join_orig1
= xstrdup (optarg
);
234 parse_tagdate (&join_rev1
, &join_date1
, optarg
);
249 if (cat
&& argc
!= 0)
250 error (1, 0, "-c and -s must not get any arguments");
252 if (!cat
&& argc
== 0)
253 error (1, 0, "must specify at least one module or directory");
255 if (where
&& pipeout
)
256 error (1, 0, "-d and -p are mutually exclusive");
258 if (m_type
== EXPORT
)
261 error (1, 0, "must specify a tag or date");
263 if (tag
&& isdigit (tag
[0]))
264 error (1, 0, "tag `%s' must be a symbolic tag", tag
);
267 #ifdef SERVER_SUPPORT
268 if (server_active
&& where
!= NULL
)
270 server_pathname_check (where
);
274 if (!cat
&& !pipeout
&& !safe_location (where
))
276 error (1, 0, "Cannot check out files into the repository itself");
279 #ifdef CLIENT_SUPPORT
280 if (current_parsed_root
->isremote
)
288 expand_modules
= (!cat
&& !pipeout
289 && supported_request ("expand-modules"));
293 /* This is done here because we need to read responses
294 from the server before we send the command checkout or
297 client_expand_modules (argc
, argv
, local
);
300 if (!run_module_prog
)
306 if (!force_tag_match
)
312 if (checkout_prune_dirs
&& m_type
== CHECKOUT
)
314 client_prune_dirs
= checkout_prune_dirs
;
318 option_with_arg ("-d", where
);
321 if (options
!= NULL
&& options
[0] != '\0')
323 option_with_arg ("-r", tag
);
325 client_senddate (date
);
327 option_with_arg ("-j", join_orig1
);
329 option_with_arg ("-j", join_orig2
);
334 client_send_expansions (local
, where
, 1);
339 for (i
= 0; i
< argc
; ++i
)
341 client_nonexpanded_setup ();
344 send_to_server (m_type
== EXPORT
? "export\012" : "co\012", 0);
345 return get_responses_and_close ();
347 #endif /* CLIENT_SUPPORT */
362 /* If we've specified something like "cvs co foo/bar baz/quux"
363 don't try to shorten names. There are a few cases in which we
364 could shorten (e.g. "cvs co foo/bar foo/baz"), but we don't
365 handle those yet. Better to have an extra directory created
366 than the thing checked out under the wrong directory name. */
372 /* If we will be calling history_write, work out the name to pass
381 history_name
= Xasprintf ("%s:%s", tag
, date
);
385 for (i
= 0; i
< argc
; i
++)
386 err
+= do_module (db
, argv
[i
], m_type
, "Updating", checkout_proc
,
387 where
, shorten
, local
, run_module_prog
, !pipeout
,
395 if (history_name
!= tag
&& history_name
!= date
&& history_name
!= NULL
)
402 /* FIXME: This is and emptydir_name are in checkout.c for historical
403 reasons, probably want to move them. */
406 * safe_location ( char *where )
408 * Return true if where is a safe destination for a checkout.
411 * where The requested destination directory.
414 * current_parsed_root->directory
415 * current_parsed_root->isremote
416 * Used to locate our CVSROOT.
419 * true If we are running in client mode or if where is not located
420 * within the CVSROOT.
424 * Exits with a fatal error message when various events occur, such as not
425 * being able to resolve a path or failing ot chdir to a path.
428 safe_location (char *where
)
435 TRACE (TRACE_FUNCTION
, "safe_location( where=%s )",
436 where
? where
: "(null)");
438 /* Don't compare remote CVSROOTs to our destination directory. */
439 if (current_parsed_root
->isremote
) return 1;
441 /* set current - even if where is set we'll need to cd back... */
442 current
= xgetcwd ();
444 error (1, errno
, "could not get working directory");
446 hardpath
= xcanonicalize_file_name (current_parsed_root
->directory
);
448 /* if where is set, set current to as much of where as exists,
453 char *where_this_pass
= xstrdup (where
);
456 if (CVS_CHDIR (where_this_pass
) != -1)
459 free (where_this_pass
);
460 where_this_pass
= xgetcwd ();
461 if (where_this_pass
== NULL
)
462 error (1, errno
, "could not get working directory");
464 if (CVS_CHDIR (current
) == -1)
466 "could not restore directory to `%s'", current
);
469 current
= where_this_pass
;
472 else if (errno
== ENOENT
)
474 /* where_this_pass - last_component (where_this_pass) */
477 /* It's okay to cast out the const below since we know we
478 * allocated where_this_pass and have control of it.
480 if ((parent
= (char *)last_component (where_this_pass
))
483 /* strip the last_component */
490 * && last_component (where_this_pass) == where_this_pass
491 * means we've tried all the parent diretories and not one
492 * exists, so there is no need to test any portion of where
493 * - it is all being created.
495 free (where_this_pass
);
500 /* we don't know how to handle other errors, so fail */
502 could not change directory to requested checkout directory `%s'",
505 } /* where != NULL */
507 hardpath_len
= strlen (hardpath
);
508 if (strlen (current
) >= hardpath_len
509 && strncmp (current
, hardpath
, hardpath_len
) == 0)
511 if (/* Current is a subdirectory of hardpath. */
512 current
[hardpath_len
] == '/'
514 /* Current is hardpath itself. */
515 || current
[hardpath_len
] == '\0')
518 /* It isn't a problem. For example, current is
519 "/foo/cvsroot-bar" and hardpath is "/foo/cvsroot". */
533 /* What to put in CVS/Repository. */
535 /* The path to the directory. */
538 struct dir_to_build
*next
;
543 static int build_dirs_and_chdir (struct dir_to_build
*list
,
547 build_one_dir (char *repository
, char *dirpath
, int sticky
)
553 if (m_type
== EXPORT
)
554 error (1, 0, "cannot export into a working directory");
556 else if (m_type
== CHECKOUT
)
558 /* I suspect that this check could be omitted. */
559 if (!isdir (repository
))
560 error (1, 0, "there is no repository %s", repository
);
562 if (Create_Admin (".", dirpath
, repository
,
564 sticky
? date
: NULL
,
566 /* FIXME? This is a guess. If it is important
567 for nonbranch to be set correctly here I
568 think we need to write it one way now and
569 then rewrite it later via WriteTag, once
570 we've had a chance to call RCS_nodeisbranch
577 fp
= xfopen (CVSADM_ENTSTAT
, "w+");
578 if (fclose (fp
) == EOF
)
579 error (1, errno
, "cannot close %s", CVSADM_ENTSTAT
);
580 #ifdef SERVER_SUPPORT
582 server_set_entstat (dirpath
, repository
);
591 * process_module calls us back here so we do the actual checkout stuff
595 checkout_proc (int argc
, char **argv
, char *where_orig
, char *mwhere
,
596 char *mfile
, int shorten
, int local_specified
, char *omodule
,
604 char *oldupdate
= NULL
;
607 TRACE (TRACE_FUNCTION
, "checkout_proc (%s, %s, %s, %d, %d, %s, %s)\n",
608 where_orig
? where_orig
: "(null)",
609 mwhere
? mwhere
: "(null)",
610 mfile
? mfile
: "(null)",
611 shorten
, local_specified
,
612 omodule
? omodule
: "(null)",
617 * OK, so we're doing the checkout! Our args are as follows:
618 * argc,argv contain either dir or dir followed by a list of files
619 * where contains where to put it (if supplied by checkout)
620 * mwhere contains the module name or -d from module file
621 * mfile says do only that part of the module
622 * shorten = 1 says shorten as much as possible
623 * omodule is the original arg to do_module()
626 /* Set up the repository (maybe) for the bottom directory.
627 Allocate more space than we need so we don't need to keep
628 reallocating this string. */
629 repository
= xmalloc (strlen (current_parsed_root
->directory
)
631 + (mfile
== NULL
? 0 : strlen (mfile
))
633 (void) sprintf (repository
, "%s/%s",
634 current_parsed_root
->directory
, argv
[0]);
635 Sanitize_Repository_Name (repository
);
638 /* save the original value of preload_update_dir */
639 if (preload_update_dir
!= NULL
)
640 oldupdate
= xstrdup (preload_update_dir
);
643 /* Allocate space and set up the where variable. We allocate more
644 space than necessary here so that we don't have to keep
645 reallocaing it later on. */
647 where
= xmalloc (strlen (argv
[0])
648 + (mfile
== NULL
? 0 : strlen (mfile
))
649 + (mwhere
== NULL
? 0 : strlen (mwhere
))
650 + (where_orig
== NULL
? 0 : strlen (where_orig
))
653 /* Yes, this could be written in a less verbose way, but in this
654 form it is quite easy to read.
656 FIXME? The following code that sets should probably be moved
657 to do_module in modules.c, since there is similar code in
658 patch.c and rtag.c. */
662 if (where_orig
!= NULL
)
664 /* If the user has specified a directory with `-d' on the
665 command line, use it preferentially, even over the `-d'
666 flag in the modules file. */
668 (void) strcpy (where
, where_orig
);
670 else if (mwhere
!= NULL
)
672 /* Second preference is the value of mwhere, which is from
673 the `-d' flag in the modules file. */
675 (void) strcpy (where
, mwhere
);
679 /* Third preference is the directory specified in argv[0]
680 which is this module'e directory in the repository. */
682 (void) strcpy (where
, argv
[0]);
687 /* Use the same preferences here, bug don't shorten -- that
688 is, tack on where_orig if it exists. */
692 if (where_orig
!= NULL
)
694 (void) strcat (where
, where_orig
);
695 (void) strcat (where
, "/");
698 /* If the -d flag in the modules file specified an absolute
699 directory, let the user override it with the command-line
702 if (mwhere
&& !ISABSOLUTE (mwhere
))
703 (void) strcat (where
, mwhere
);
705 (void) strcat (where
, argv
[0]);
707 strip_trailing_slashes (where
); /* necessary? */
710 /* At this point, the user may have asked for a single file or
711 directory from within a module. In that case, we should modify
712 where, repository, and argv as appropriate. */
716 /* The mfile variable can have one or more path elements. If
717 it has multiple elements, we want to tack those onto both
718 repository and where. The last element may refer to either
719 a file or directory. Here's what to do:
721 it refers to a directory
722 -> simply tack it on to where and repository
724 -> munge argv to contain `basename mfile` */
730 /* Paranoia check. */
732 if (mfile
[strlen (mfile
) - 1] == '/')
734 error (0, 0, "checkout_proc: trailing slash on mfile (%s)!",
739 /* Does mfile have multiple path elements? */
741 cp
= strrchr (mfile
, '/');
745 (void) strcat (repository
, "/");
746 (void) strcat (repository
, mfile
);
747 (void) strcat (where
, "/");
748 (void) strcat (where
, mfile
);
753 /* Now mfile is a single path element. */
755 path
= Xasprintf ("%s/%s", repository
, mfile
);
758 /* It's a directory, so tack it on to repository and
759 where, as we did above. */
761 (void) strcat (repository
, "/");
762 (void) strcat (repository
, mfile
);
763 (void) strcat (where
, "/");
764 (void) strcat (where
, mfile
);
768 /* It's a file, which means we have to screw around with
778 if (preload_update_dir
!= NULL
)
781 xrealloc (preload_update_dir
,
782 strlen (preload_update_dir
) + strlen (where
) + 5);
783 strcat (preload_update_dir
, "/");
784 strcat (preload_update_dir
, where
);
787 preload_update_dir
= xstrdup (where
);
790 * At this point, where is the directory we want to build, repository is
791 * the repository for the lowest level of the path.
793 * We need to tell build_dirs not only the path we want it to
794 * build, but also the repositories we want it to populate the
795 * path with. To accomplish this, we walk the path backwards, one
796 * pathname component at a time, constucting a linked list of
797 * struct dir_to_build.
801 * If we are sending everything to stdout, we can skip a whole bunch of
806 struct dir_to_build
*head
;
809 if (strncmp (repository
, current_parsed_root
->directory
,
810 strlen (current_parsed_root
->directory
)) != 0)
812 internal error: %s doesn't start with %s in checkout_proc",
813 repository
, current_parsed_root
->directory
);
815 /* We always create at least one directory, which corresponds to
816 the entire strings for WHERE and REPOSITORY. */
817 head
= xmalloc (sizeof (struct dir_to_build
));
818 /* Special marker to indicate that we don't want build_dirs_and_chdir
819 to create the CVSADM directory for us. */
820 head
->repository
= NULL
;
821 head
->dirpath
= xstrdup (where
);
824 /* Make a copy of the repository name to play with. */
825 reposcopy
= xstrdup (repository
);
827 /* FIXME: this should be written in terms of last_component
828 instead of hardcoding '/'. This presumably affects OS/2,
829 NT, &c, if the user specifies '\'. Likewise for the call
831 cp
= where
+ strlen (where
);
834 struct dir_to_build
*new;
836 cp
= findslash (where
, cp
- 1);
838 break; /* we're done */
840 new = xmalloc (sizeof (struct dir_to_build
));
841 new->dirpath
= xmalloc (strlen (where
));
843 /* If the user specified an absolute path for where, the
844 last path element we create should be the top-level
849 strncpy (new->dirpath
, where
, cp
- where
);
850 new->dirpath
[cp
- where
] = '\0';
854 /* where should always be at least one character long. */
855 assert (where
[0] != '\0');
856 strcpy (new->dirpath
, "/");
861 /* Now figure out what repository directory to generate.
862 The most complete case would be something like this:
864 The modules file contains
867 The command issued was:
868 cvs co -d what/ever -N foo
870 The results in the CVS/Repository files should be:
871 . -> (don't touch CVS/Repository)
872 (I think this case might be buggy currently)
873 what -> (don't touch CVS/Repository)
874 ever -> . (same as "cd what/ever; cvs co -N foo")
875 bar -> Emptydir (generated dir -- not in repos)
876 baz -> quux (finally!) */
878 if (strcmp (reposcopy
, current_parsed_root
->directory
) == 0)
880 /* We can't walk up past CVSROOT. Instead, the
881 repository should be Emptydir. */
882 new->repository
= emptydir_name ();
886 /* It's a directory in the repository! */
890 /* We'll always be below CVSROOT, but check for
892 rp
= strrchr (reposcopy
, '/');
895 "internal error: %s doesn't contain a slash",
900 if (strcmp (reposcopy
, current_parsed_root
->directory
) == 0)
902 /* Special case -- the repository name needs
903 to be "/path/to/repos/." (the trailing dot
904 is important). We might be able to get rid
905 of this after the we check out the other
906 code that handles repository names. */
907 new-> repository
= Xasprintf ("%s/.", reposcopy
);
910 new->repository
= xstrdup (reposcopy
);
917 /* The top-level CVSADM directory should always be
918 current_parsed_root->directory. Create it, but only if WHERE is
919 relative. If WHERE is absolute, our current directory
920 may not have a thing to do with where the sources are
921 being checked out. If it does, build_dirs_and_chdir
922 will take care of creating adm files here. */
923 /* FIXME: checking where_is_absolute is a horrid kludge;
924 I suspect we probably can just skip the call to
925 build_one_dir whenever the -d command option was specified
928 if (!ISABSOLUTE (where
) && config
->top_level_admin
929 && m_type
== CHECKOUT
)
931 /* It may be argued that we shouldn't set any sticky
932 bits for the top-level repository. FIXME? */
933 build_one_dir (current_parsed_root
->directory
, ".", argc
<= 1);
935 #ifdef SERVER_SUPPORT
936 /* We _always_ want to have a top-level admin
937 directory. If we're running in client/server mode,
938 send a "Clear-static-directory" command to make
939 sure it is created on the client side. (See 5.10
940 in cvsclient.dvi to convince yourself that this is
941 OK.) If this is a duplicate command being sent, it
942 will be ignored on the client side. */
945 server_clear_entstat (".", current_parsed_root
->directory
);
950 /* Build dirs on the path if necessary and leave us in the
951 bottom directory (where if where was specified) doesn't
952 contain a CVS subdir yet, but all the others contain
953 CVS and Entries.Static files */
955 if (build_dirs_and_chdir (head
, argc
<= 1) != 0)
957 error (0, 0, "ignoring module %s", omodule
);
962 /* set up the repository (or make sure the old one matches) */
963 if (!isfile (CVSADM
))
967 if (!noexec
&& argc
> 1)
969 /* I'm not sure whether this check is redundant. */
970 if (!isdir (repository
))
971 error (1, 0, "there is no repository %s", repository
);
973 Create_Admin (".", preload_update_dir
, repository
,
974 NULL
, NULL
, 0, 0, m_type
== CHECKOUT
);
975 fp
= xfopen (CVSADM_ENTSTAT
, "w+");
976 if (fclose (fp
) == EOF
)
977 error (1, errno
, "cannot close %s", CVSADM_ENTSTAT
);
978 #ifdef SERVER_SUPPORT
980 server_set_entstat (where
, repository
);
985 /* I'm not sure whether this check is redundant. */
986 if (!isdir (repository
))
987 error (1, 0, "there is no repository %s", repository
);
989 Create_Admin (".", preload_update_dir
, repository
, tag
, date
,
991 /* FIXME? This is a guess. If it is important
992 for nonbranch to be set correctly here I
993 think we need to write it one way now and
994 then rewrite it later via WriteTag, once
995 we've had a chance to call RCS_nodeisbranch
997 0, 0, m_type
== CHECKOUT
);
1004 if (m_type
== EXPORT
)
1005 error (1, 0, "cannot export into working directory");
1007 /* get the contents of the previously existing repository */
1008 repos
= Name_Repository (NULL
, preload_update_dir
);
1009 if (fncmp (repository
, repos
) != 0)
1011 char *prepos
= xstrdup (primary_root_inverse_translate (repos
));
1013 xstrdup (primary_root_inverse_translate (repository
));
1014 error (0, 0, "existing repository %s does not match %s",
1015 prepos
, prepository
);
1016 error (0, 0, "ignoring module %s", omodule
);
1028 * If we are going to be updating to stdout, we need to cd to the
1029 * repository directory so the recursion processor can use the current
1030 * directory as the place to find repository information
1034 if (CVS_CHDIR (repository
) < 0)
1036 error (0, errno
, "cannot chdir to %s", repository
);
1041 if (tag
&& !tag_validated
)
1043 tag_check_valid (tag
, argc
- 1, argv
+ 1, 0, aflag
,
1045 tag_validated
= true;
1050 which
= W_LOCAL
| W_REPOS
;
1051 if (tag
&& !tag_validated
)
1053 tag_check_valid (tag
, argc
- 1, argv
+ 1, 0, aflag
,
1055 tag_validated
= true;
1059 if (tag
|| date
|| join_rev1
|| join_date2
)
1062 if (!join_tags_validated
)
1065 tag_check_valid (join_rev1
, argc
- 1, argv
+ 1, 0, aflag
,
1068 tag_check_valid (join_rev2
, argc
- 1, argv
+ 1, 0, aflag
,
1070 join_tags_validated
= true;
1074 * if we are going to be recursive (building dirs), go ahead and call the
1075 * update recursion processor. We will be recursive unless either local
1076 * only was specified, or we were passed arguments
1078 if (!(local_specified
|| argc
> 1))
1081 history_write (m_type
== CHECKOUT
? 'O' : 'E', preload_update_dir
,
1082 history_name
, where
, repository
);
1083 err
+= do_update (0, NULL
, options
, tag
, date
,
1084 force_tag_match
, false /* !local */ ,
1085 true /* update -d */ , aflag
, checkout_prune_dirs
,
1086 pipeout
, which
, join_rev1
, join_date1
,
1087 join_rev2
, join_date2
,
1088 preload_update_dir
, m_type
== CHECKOUT
,
1098 /* we are only doing files, so register them */
1099 entries
= Entries_Open (0, NULL
);
1100 for (i
= 1; i
< argc
; i
++)
1104 struct file_info finfo
;
1106 memset (&finfo
, 0, sizeof finfo
);
1107 finfo
.file
= argv
[i
];
1108 /* Shouldn't be used, so set to arbitrary value. */
1109 finfo
.update_dir
= NULL
;
1110 finfo
.fullname
= argv
[i
];
1111 finfo
.repository
= repository
;
1112 finfo
.entries
= entries
;
1113 /* The rcs slot is needed to get the options from the RCS
1115 finfo
.rcs
= RCS_parse (finfo
.file
, repository
);
1117 vers
= Version_TS (&finfo
, options
, tag
, date
,
1118 force_tag_match
, 0);
1119 if (vers
->ts_user
== NULL
)
1121 line
= Xasprintf ("Initial %s", finfo
.file
);
1122 Register (entries
, finfo
.file
,
1123 vers
->vn_rcs
? vers
->vn_rcs
: "0",
1124 line
, vers
->options
, vers
->tag
,
1128 freevers_ts (&vers
);
1129 freercsnode (&finfo
.rcs
);
1132 Entries_Close (entries
);
1135 /* Don't log "export", just regular "checkouts" */
1136 if (m_type
== CHECKOUT
&& !pipeout
)
1137 history_write ('O', preload_update_dir
, history_name
, where
,
1140 /* go ahead and call update now that everything is set */
1141 err
+= do_update (argc
- 1, argv
+ 1, options
, tag
, date
,
1142 force_tag_match
, local_specified
, true /* update -d */,
1143 aflag
, checkout_prune_dirs
, pipeout
, which
, join_rev1
,
1144 join_date1
, join_rev2
, join_date2
, preload_update_dir
,
1145 m_type
== CHECKOUT
, repository
);
1147 free (preload_update_dir
);
1148 preload_update_dir
= oldupdate
;
1157 findslash (char *start
, char *p
)
1161 if (*p
== '/') return p
;
1162 if (p
== start
) break;
1170 /* Return a newly malloc'd string containing a pathname for CVSNULLREPOS,
1171 and make sure that it exists. If there is an error creating the
1172 directory, give a fatal error. Otherwise, the directory is guaranteed
1173 to exist when we return. */
1175 emptydir_name (void)
1179 repository
= Xasprintf ("%s/%s/%s", current_parsed_root
->directory
,
1180 CVSROOTADM
, CVSNULLREPOS
);
1181 if (!isfile (repository
))
1184 omask
= umask (cvsumask
);
1185 if (CVS_MKDIR (repository
, 0777) < 0)
1186 error (1, errno
, "cannot create %s", repository
);
1187 (void) umask (omask
);
1194 /* Build all the dirs along the path to DIRS with CVS subdirs with appropriate
1195 * repositories. If DIRS->repository is NULL or the directory already exists,
1196 * do not create a CVSADM directory for that subdirectory; just CVS_CHDIR into
1197 * it. Frees all storage used by DIRS.
1200 * 1. Parent directories will be listed in DIRS before their children.
1201 * 2. At most a single directory will need to be changed at one time. In
1202 * other words, if we are in /a/b/c, and our final destination is
1203 * /a/b/c/d/e/f, then we will build d, then d/e, then d/e/f.
1206 * dirs Simple list composed of dir_to_build structures, listing
1207 * information about directories to build.
1208 * sticky Passed to build_one_dir to tell it whether there are any sticky
1209 * tags or dates to be concerned with.
1212 * 1 on error, 0 otherwise.
1215 * The only nonfatal error this function may return is if the CHDIR fails.
1218 build_dirs_and_chdir (struct dir_to_build
*dirs
, int sticky
)
1221 struct dir_to_build
*nextdir
;
1223 while (dirs
!= NULL
)
1225 const char *dir
= last_component (dirs
->dirpath
);
1228 made_dir
= !mkdir_if_needed (dir
);
1229 if (made_dir
) Subdir_Register (NULL
, NULL
, dir
);
1231 if (CVS_CHDIR (dir
) < 0)
1233 error (0, errno
, "cannot chdir to %s", dir
);
1237 if (dirs
->repository
!= NULL
)
1240 build_one_dir (dirs
->repository
, dirs
->dirpath
, sticky
);
1241 free (dirs
->repository
);
1243 nextdir
= dirs
->next
;
1244 free (dirs
->dirpath
);
1250 while (dirs
!= NULL
)
1252 if (dirs
->repository
!= NULL
)
1253 free (dirs
->repository
);
1254 nextdir
= dirs
->next
;
1255 free (dirs
->dirpath
);