summaryrefslogtreecommitdiffstats
path: root/contrib/cvs/src
diff options
context:
space:
mode:
Diffstat (limited to 'contrib/cvs/src')
-rw-r--r--contrib/cvs/src/NOTES60
-rw-r--r--contrib/cvs/src/README-rm-add31
-rw-r--r--contrib/cvs/src/buffer.c70
-rw-r--r--contrib/cvs/src/checkout.c39
-rw-r--r--contrib/cvs/src/client.c231
-rw-r--r--contrib/cvs/src/commit.c191
-rw-r--r--contrib/cvs/src/cvs.h57
-rwxr-xr-xcontrib/cvs/src/cvsbug.in2
-rw-r--r--contrib/cvs/src/diff.c215
-rw-r--r--contrib/cvs/src/entries.c79
-rw-r--r--contrib/cvs/src/filesubr.c99
-rw-r--r--contrib/cvs/src/import.c73
-rw-r--r--contrib/cvs/src/lock.c233
-rw-r--r--contrib/cvs/src/log.c105
-rw-r--r--contrib/cvs/src/login.c14
-rw-r--r--contrib/cvs/src/logmsg.c33
-rw-r--r--contrib/cvs/src/main.c348
-rw-r--r--contrib/cvs/src/mkmodules.c28
-rw-r--r--contrib/cvs/src/options.h.in200
-rw-r--r--contrib/cvs/src/parseinfo.c55
-rw-r--r--contrib/cvs/src/patch.c74
-rw-r--r--contrib/cvs/src/rcs.c554
-rw-r--r--contrib/cvs/src/rcs.h17
-rw-r--r--contrib/cvs/src/rcscmds.c176
-rw-r--r--contrib/cvs/src/recurse.c162
-rw-r--r--contrib/cvs/src/server.c184
-rw-r--r--contrib/cvs/src/stamp-h2.in1
-rw-r--r--contrib/cvs/src/tag.c268
-rw-r--r--contrib/cvs/src/update.c236
-rw-r--r--contrib/cvs/src/update.h6
-rw-r--r--contrib/cvs/src/version.c.in86
-rw-r--r--contrib/cvs/src/version.h.in15
32 files changed, 1623 insertions, 2319 deletions
diff --git a/contrib/cvs/src/NOTES b/contrib/cvs/src/NOTES
deleted file mode 100644
index 646ebdf..0000000
--- a/contrib/cvs/src/NOTES
+++ /dev/null
@@ -1,60 +0,0 @@
-wishlist - Tue Nov 2 15:22:58 PST 1993
-
-* bcopy -> memcpy & friends.
- ** done 12/18/93
-
-* remove static buffers.
-* replace list & node cache with recursive obstacks, (xmalloc,
- getnode, getlist)
-* check all io functions for error return codes. also check all
- system calls.
-* error check mkdir.
-
----
-Old notes...
-
-* All sizing limits are gone. The rest of these items were incidental
- in that effort.
-
-* login name from history was duplicated. taught existing routine to
- cache and use that instead. Also add routines to cache uid, pid,
- etc.
-
-* ign strings were never freed. Now they are.
-
-* there was a printf("... %s ...", cp) vs *cp bug in history.c. Now
- fixed.
-
-* The environment variables TMPDIR, HOME, and LOGNAME were not
- honored. Now they are.
-
-* extra line inserted by do_editor() is gone. Then obviated. Editor
- is now called exactly once per checkin.
-
-* revised editor behaviour. Never use /dev/tty. If the editor
- session fails, we haven't yet done anything. Therefor the user can
- safely rerun cvs and we should just fail. Also use the editor for
- initial log messages on added files. Also omit the confirmation
- when adding directories. Adding directories will require an
- explicit "commit" step soon. Make it possible to prevent null login
- messages using #define REQUIRE_LOG_MESSAGES
-
-* prototypes for all callbacks.
-
-* all callbacks get ref pointers.
-
-* do_recursion/start_recursion now use recusion_frame's rather than a
- list of a lot of pointers and global variables.
-
-* corrected types on status_dirproc().
-
-* CONFIRM_DIRECTORY_ADDS
-
-* re_comp was innappropriate in a few places. I've eliminated it.
-
-* FORCE_MESSAGE_ON_ADD
-
-* So I built a regression test. Let's call it a sanity check to be
- less ambitious. It exposed that cvs is difficult to call from
- scripts.
-
diff --git a/contrib/cvs/src/README-rm-add b/contrib/cvs/src/README-rm-add
deleted file mode 100644
index 87fd7c6..0000000
--- a/contrib/cvs/src/README-rm-add
+++ /dev/null
@@ -1,31 +0,0 @@
-WHAT THE "DEATH SUPPORT" FEATURES DO:
-
-(Some of the death support stuff is documented in the main manual, but
-this file is for stuff which noone has gotten around to adding to the
-main manual yet).
-
-CVS with death support can record when a file is active, or alive, and
-when it is removed, or dead. With this facility you can record the
-history of a file, including the fact that at some point in its life
-the file was removed and then later added.
-
-Files can now be added or removed in a branch and later merged
-into the trunk.
-
- cvs update -A
- touch a b c
- cvs add a b c ; cvs ci -m "added" a b c
- cvs tag -b branchtag
- cvs update -r branchtag
- touch d ; cvs add d
- rm a ; cvs rm a
- cvs ci -m "added d, removed a"
- cvs update -A
- cvs update -jbranchtag
-
-Added and removed files may also be merged between branches.
-
-Files removed in the trunk may be merged into branches.
-
-Files added on the trunk are a special case. They cannot be merged
-into a branch. Instead, simply branch the file by hand.
diff --git a/contrib/cvs/src/buffer.c b/contrib/cvs/src/buffer.c
index 8e66355..d53a5c6 100644
--- a/contrib/cvs/src/buffer.c
+++ b/contrib/cvs/src/buffer.c
@@ -1,19 +1,7 @@
-/*
- * Copyright (C) 1996-2005 The Free Software Foundation, Inc.
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2, or (at your option)
- * any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- */
-
/* Code for the buffer data structure. */
+/* $FreeBSD$ */
+
#include <assert.h>
#include "cvs.h"
#include "buffer.h"
@@ -124,13 +112,11 @@ allocate_buffer_datas ()
/* Allocate buffer_data structures in blocks of 16. */
#define ALLOC_COUNT (16)
- alc = xmalloc (ALLOC_COUNT * sizeof (struct buffer_data));
+ alc = ((struct buffer_data *)
+ xmalloc (ALLOC_COUNT * sizeof (struct buffer_data)));
space = (char *) valloc (ALLOC_COUNT * BUFFER_DATA_SIZE);
- if (!space)
- {
- free (alc);
+ if (alc == NULL || space == NULL)
return;
- }
for (i = 0; i < ALLOC_COUNT; i++, alc++, space += BUFFER_DATA_SIZE)
{
alc->next = free_buffer_data;
@@ -1422,16 +1408,10 @@ stdio_buffer_shutdown (buf)
{
struct stdio_buffer_closure *bc = buf->closure;
struct stat s;
- int closefp, statted;
+ int closefp = 1;
- /* Must be a pipe or a socket. What could go wrong?
- * Well, apparently for disconnected clients under AIX, the
- * fstat() will return -1 on the server if the client has gone
- * away.
- */
- if (fstat(fileno(bc->fp), &s) == -1) statted = 0;
- else statted = 1;
- closefp = statted;
+ /* Must be a pipe or a socket. What could go wrong? */
+ assert (fstat (fileno (bc->fp), &s) != -1);
/* Flush the buffer if we can */
if (buf->flush)
@@ -1454,7 +1434,7 @@ stdio_buffer_shutdown (buf)
# ifndef NO_SOCKET_TO_FD
{
/* shutdown() sockets */
- if (statted && S_ISSOCK (s.st_mode))
+ if (S_ISSOCK (s.st_mode))
shutdown (fileno (bc->fp), 0);
}
# endif /* NO_SOCKET_TO_FD */
@@ -1462,7 +1442,7 @@ stdio_buffer_shutdown (buf)
/* Can't be set with SHUTDOWN_SERVER defined */
else if (pclose (bc->fp) == EOF)
{
- error (0, errno, "closing connection to %s",
+ error (1, errno, "closing connection to %s",
current_parsed_root->hostname);
closefp = 0;
}
@@ -1482,7 +1462,7 @@ stdio_buffer_shutdown (buf)
# endif
# ifndef NO_SOCKET_TO_FD
/* shutdown() sockets */
- if (statted && S_ISSOCK (s.st_mode))
+ if (S_ISSOCK (s.st_mode))
shutdown (fileno (bc->fp), 1);
# else
{
@@ -1495,19 +1475,19 @@ stdio_buffer_shutdown (buf)
buf->output = NULL;
}
- if (statted && closefp && fclose (bc->fp) == EOF)
+ if (closefp && fclose (bc->fp) == EOF)
{
- if (server_active)
+ if (0
+# ifdef SERVER_SUPPORT
+ || server_active
+# endif /* SERVER_SUPPORT */
+ )
{
/* Syslog this? */
}
# ifdef CLIENT_SUPPORT
- /* We are already closing the connection.
- * On error, print a warning and try to
- * continue to avoid infinte loops.
- */
else
- error (0, errno,
+ error (1, errno,
"closing down connection to %s",
current_parsed_root->hostname);
# endif /* CLIENT_SUPPORT */
@@ -1521,13 +1501,8 @@ stdio_buffer_shutdown (buf)
do
w = waitpid (bc->child_pid, (int *) 0, 0);
while (w == -1 && errno == EINTR);
-
- /* We are already closing the connection.
- * On error, print a warning and try to
- * continue to avoid infinte loops.
- */
if (w == -1)
- error (0, errno, "waiting for process %d", bc->child_pid);
+ error (1, errno, "waiting for process %d", bc->child_pid);
}
return 0;
}
@@ -1860,7 +1835,7 @@ packetizing_buffer_output (closure, data, have, wrote)
struct packetizing_buffer *pb = (struct packetizing_buffer *) closure;
char inbuf[BUFFER_DATA_SIZE + 2];
char stack_outbuf[BUFFER_DATA_SIZE + PACKET_SLOP + 4];
- struct buffer_data *outdata = NULL;
+ struct buffer_data *outdata;
char *outbuf;
int size, status, translated;
@@ -1915,11 +1890,6 @@ packetizing_buffer_output (closure, data, have, wrote)
buf_output (pb->buf, outbuf, translated + 2);
else
{
- /* if ((have + PACKET_SLOP + 4) > BUFFER_DATA_SIZE), then
- outdata may be NULL. */
- if (outdata == NULL)
- abort ();
-
outdata->size = translated + 2;
buf_append_data (pb->buf, outdata, outdata);
}
diff --git a/contrib/cvs/src/checkout.c b/contrib/cvs/src/checkout.c
index e4d80ea..57933ee 100644
--- a/contrib/cvs/src/checkout.c
+++ b/contrib/cvs/src/checkout.c
@@ -1,11 +1,6 @@
/*
- * Copyright (C) 1986-2005 The Free Software Foundation, Inc.
- *
- * Portions Copyright (C) 1998-2005 Derek Price, Ximbiot <http://ximbiot.com>,
- * and others.
- *
- * Portions Copyright (C) 1992, Brian Berliner and Jeff Polk
- * Portions Copyright (C) 1989-1992, Brian Berliner
+ * Copyright (c) 1992, Brian Berliner and Jeff Polk
+ * Copyright (c) 1989-1992, Brian Berliner
*
* You may distribute under the terms of the GNU General Public License as
* specified in the README file that comes with the CVS source distribution.
@@ -38,6 +33,10 @@
* edited by the user, if necessary (when the repository is moved, e.g.)
*/
+/*
+ * $FreeBSD$
+ */
+
#include <assert.h>
#include "cvs.h"
@@ -55,6 +54,7 @@ static const char *const checkout_usage[] =
"\t-N\tDon't shorten module paths if -d specified.\n",
"\t-P\tPrune empty directories.\n",
"\t-R\tProcess directories recursively.\n",
+ "\t-T\tCreate Template file from local repository for remote commit.\n",
"\t-c\t\"cat\" the module database.\n",
"\t-f\tForce a head revision match if tag/date not found.\n",
"\t-l\tLocal directory only, not recursive\n",
@@ -72,13 +72,13 @@ static const char *const checkout_usage[] =
static const char *const export_usage[] =
{
- "Usage: %s %s [-NRfln] [-r tag] [-D date] [-d dir] [-k kopt] module...\n",
+ "Usage: %s %s [-NRfln] [-r rev] [-D date] [-d dir] [-k kopt] module...\n",
"\t-N\tDon't shorten module paths if -d specified.\n",
"\t-f\tForce a head revision match if tag/date not found.\n",
"\t-l\tLocal directory only, not recursive\n",
"\t-R\tProcess directories recursively (default).\n",
"\t-n\tDo not run module program (if any).\n",
- "\t-r tag\tExport tagged revisions.\n",
+ "\t-r rev\tExport revision or tag.\n",
"\t-D date\tExport revisions as of date.\n",
"\t-d dir\tExport into dir instead of module name.\n",
"\t-k kopt\tUse RCS kopt -k option on checkout.\n",
@@ -97,6 +97,7 @@ static char *date;
static char *join_rev1;
static char *join_rev2;
static int join_tags_validated;
+static int pull_template;
static char *preload_update_dir;
static char *history_name;
static enum mtype m_type;
@@ -144,7 +145,7 @@ checkout (argc, argv)
else
{
m_type = CHECKOUT;
- valid_options = "+ANnk:d:flRpQqcsr:D:j:P";
+ valid_options = "+ANnk:d:flRpTQqcsr:D:j:P";
valid_usage = checkout_usage;
}
@@ -173,11 +174,16 @@ checkout (argc, argv)
case 'n':
run_module_prog = 0;
break;
+ case 'T':
+ pull_template = 1;
+ break;
case 'Q':
case 'q':
+#ifdef SERVER_SUPPORT
/* The CVS 1.5 client sends these options (in addition to
Global_option requests), so we must ignore them. */
if (!server_active)
+#endif
error (1, 0,
"-q or -Q must be specified before \"%s\"",
cvs_cmd_name);
@@ -431,8 +437,10 @@ safe_location (where)
CLIENT_SERVER_STR,
where ? where : "(null)");
+#ifdef CLIENT_SUPPORT
/* Don't compare remote CVSROOTs to our destination directory. */
- if (current_parsed_root->isremote) return 1;
+ if ( current_parsed_root->isremote ) return 1;
+#endif /* CLIENT_SUPPORT */
/* set current - even if where is set we'll need to cd back... */
current = xgetwd ();
@@ -1054,8 +1062,7 @@ internal error: %s doesn't start with %s in checkout_proc",
which = W_REPOS;
if (tag != NULL && !tag_validated)
{
- tag_check_valid (tag, argc - 1, argv + 1, 0, aflag,
- repository);
+ tag_check_valid (tag, argc - 1, argv + 1, 0, aflag, NULL);
tag_validated = 1;
}
}
@@ -1098,8 +1105,7 @@ internal error: %s doesn't start with %s in checkout_proc",
force_tag_match, 0 /* !local */ ,
1 /* update -d */ , aflag, checkout_prune_dirs,
pipeout, which, join_rev1, join_rev2,
- preload_update_dir, m_type == CHECKOUT,
- repository);
+ preload_update_dir, pull_template, repository);
goto out;
}
@@ -1155,8 +1161,7 @@ internal error: %s doesn't start with %s in checkout_proc",
err += do_update (argc - 1, argv + 1, options, tag, date,
force_tag_match, local_specified, 1 /* update -d */,
aflag, checkout_prune_dirs, pipeout, which, join_rev1,
- join_rev2, preload_update_dir, m_type == CHECKOUT,
- repository);
+ join_rev2, preload_update_dir, pull_template, repository);
out:
free (preload_update_dir);
preload_update_dir = oldupdate;
diff --git a/contrib/cvs/src/client.c b/contrib/cvs/src/client.c
index 22384ed..aae404a 100644
--- a/contrib/cvs/src/client.c
+++ b/contrib/cvs/src/client.c
@@ -10,6 +10,10 @@
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details. */
+/*
+ * $FreeBSD$
+ */
+
#ifdef HAVE_CONFIG_H
# include "config.h"
#endif /* HAVE_CONFIG_H */
@@ -221,8 +225,7 @@ arg_should_not_be_sent_to_server (arg)
/* Try to decide whether we should send arg to the server by
checking the contents of the corresponding CVSADM directory. */
{
- char *t, *root_string;
- cvsroot_t *this_root = NULL;
+ char *t, *this_root;
/* Calculate "dirname arg" */
for (t = arg + strlen (arg) - 1; t >= arg; t--)
@@ -252,31 +255,25 @@ arg_should_not_be_sent_to_server (arg)
/* Since we didn't find it in the list, check the CVSADM
files on disk. */
this_root = Name_Root (arg, (char *) NULL);
- root_string = this_root->original;
*t = c;
}
else
{
/* We're at the beginning of the string. Look at the
CVSADM files in cwd. */
- if (CVSroot_cmdline)
- root_string = CVSroot_cmdline;
- else
- {
- this_root = Name_Root ((char *) NULL, (char *) NULL);
- root_string = this_root->original;
- }
+ this_root = (CVSroot_cmdline ? xstrdup(CVSroot_cmdline)
+ : Name_Root ((char *) NULL, (char *) NULL));
}
/* Now check the value for root. */
- if (root_string && current_parsed_root
- && (strcmp (root_string, current_parsed_root->original) != 0))
+ if (CVSroot_cmdline == NULL && this_root && current_parsed_root
+ && (strcmp (this_root, current_parsed_root->original) != 0))
{
/* Don't send this, since the CVSROOTs don't match. */
- if (this_root) free_cvsroot_t (this_root);
+ free (this_root);
return 1;
}
- if (this_root) free_cvsroot_t (this_root);
+ free (this_root);
}
/* OK, let's send it. */
@@ -893,6 +890,12 @@ read_line (resultp)
#if defined(CLIENT_SUPPORT) || defined(SERVER_SUPPORT)
/*
+ * Zero if compression isn't supported or requested; non-zero to indicate
+ * a compression level to request from gzip.
+ */
+int gzip_level;
+
+/*
* Level of compression to use when running gzip on a single file.
*/
int file_gzip_level;
@@ -1114,8 +1117,6 @@ call_in_directory (pathname, func, data)
int reposdirname_absolute;
int newdir = 0;
- assert (pathname);
-
reposname = NULL;
read_line (&reposname);
assert (reposname != NULL);
@@ -1197,6 +1198,44 @@ call_in_directory (pathname, func, data)
if (CVS_CHDIR (toplevel_wd) < 0)
error (1, errno, "could not chdir to %s", toplevel_wd);
+ /* Create the CVS directory at the top level if needed. The
+ isdir seems like an unneeded system call, but it *does*
+ need to be called both if the CVS_CHDIR below succeeds
+ (e.g. "cvs co .") or if it fails (e.g. basicb-1a in
+ testsuite). We only need to do this for the "." case,
+ since the server takes care of forcing this directory to be
+ created in all other cases. If we don't create CVSADM
+ here, the call to Entries_Open below will fail. FIXME:
+ perhaps this means that we should change our algorithm
+ below that calls Create_Admin instead of having this code
+ here? */
+ if (/* I think the reposdirname_absolute case has to do with
+ things like "cvs update /foo/bar". In any event, the
+ code below which tries to put toplevel_repos into
+ CVS/Repository is almost surely unsuited to
+ the reposdirname_absolute case. */
+ !reposdirname_absolute
+ && (strcmp (dir_name, ".") == 0)
+ && ! isdir (CVSADM))
+ {
+ char *repo;
+ char *r;
+
+ newdir = 1;
+
+ repo = xmalloc (strlen (toplevel_repos)
+ + 10);
+ strcpy (repo, toplevel_repos);
+ r = repo + strlen (repo);
+ if (r[-1] != '.' || r[-2] != '/')
+ strcpy (r, "/.");
+
+ Create_Admin (".", ".", repo, (char *) NULL,
+ (char *) NULL, 0, 1, 1);
+
+ free (repo);
+ }
+
if (CVS_CHDIR (dir_name) < 0)
{
char *dir;
@@ -1457,44 +1496,7 @@ handle_copy_file (args, len)
{
call_in_directory (args, copy_a_file, (char *)NULL);
}
-
-
-
-/* Attempt to read a file size from a string. Accepts base 8 (0N), base 16
- * (0xN), or base 10. Exits on error.
- *
- * RETURNS
- * The file size, in a size_t.
- *
- * FATAL ERRORS
- * 1. As strtoul().
- * 2. If the number read exceeds SIZE_MAX.
- */
-static size_t
-strto_file_size (const char *s)
-{
- unsigned long tmp;
- char *endptr;
-
- /* Read it. */
- errno = 0;
- tmp = strtoul (s, &endptr, 0);
-
- /* Check for errors. */
- if (errno || endptr == s)
- error (1, errno, "Server sent invalid file size `%s'", s);
- if (*endptr != '\0')
- error (1, 0,
- "Server sent trailing characters in file size `%s'",
- endptr);
- if (tmp > SIZE_MAX)
- error (1, 0, "Server sent file size exceeding client max.");
-
- /* Return it. */
- return (size_t)tmp;
-}
-
-
+
static void read_counted_file PROTO ((char *, char *));
@@ -1527,7 +1529,9 @@ read_counted_file (filename, fullname)
if (size_string[0] == 'z')
error (1, 0, "\
protocol error: compressed files not supported for that operation");
- size = strto_file_size (size_string);
+ /* FIXME: should be doing more error checking, probably. Like using
+ strtoul and making sure we used up the whole line. */
+ size = atoi (size_string);
free (size_string);
/* A more sophisticated implementation would use only a limited amount
@@ -1809,12 +1813,11 @@ update_entries (data_arg, ent_list, short_pathname, filename)
{
char *size_string;
char *mode_string;
- size_t size;
+ int size;
char *buf;
char *temp_filename;
int use_gzip;
int patch_failed;
- char *s;
read_line (&mode_string);
@@ -1822,14 +1825,13 @@ update_entries (data_arg, ent_list, short_pathname, filename)
if (size_string[0] == 'z')
{
use_gzip = 1;
- s = size_string + 1;
+ size = atoi (size_string+1);
}
else
{
use_gzip = 0;
- s = size_string;
+ size = atoi (size_string);
}
- size = strto_file_size (s);
free (size_string);
/* Note that checking this separately from writing the file is
@@ -1930,7 +1932,7 @@ update_entries (data_arg, ent_list, short_pathname, filename)
#ifdef USE_VMS_FILENAMES
/* A VMS rename of "blah.dat" to "foo" to implies a
destination of "foo.dat" which is unfortinate for CVS */
- sprintf (temp_filename, "%s_new_", filename);
+ sprintf (temp_filename, "%s_new_", filename);
#else
#ifdef _POSIX_NO_TRUNC
sprintf (temp_filename, ".new.%.9s", filename);
@@ -1983,8 +1985,6 @@ update_entries (data_arg, ent_list, short_pathname, filename)
entirely possible that future files will not have
the same problem. */
error (0, errno, "cannot write %s", short_pathname);
- free (temp_filename);
- free (buf);
goto discard_file_and_return;
}
@@ -2841,10 +2841,7 @@ send_a_repository (dir, repository, update_dir_in)
const char *repository;
const char *update_dir_in;
{
- char *update_dir;
-
- assert (update_dir_in);
- update_dir = xstrdup (update_dir_in);
+ char *update_dir = xstrdup (update_dir_in);
if (toplevel_repos == NULL && repository != NULL)
{
@@ -3104,7 +3101,7 @@ handle_mbinary (args, len)
/* Get the size. */
read_line (&size_string);
- size = strto_file_size (size_string);
+ size = atoi (size_string);
free (size_string);
/* OK, now get all the data. The algorithm here is that we read
@@ -3253,7 +3250,7 @@ handle_mt (args, len)
else if (importmergecmd.seen)
{
if (strcmp (tag, "conflicts") == 0)
- importmergecmd.conflicts = text ? atoi (text) : -1;
+ importmergecmd.conflicts = atoi (text);
else if (strcmp (tag, "mergetag1") == 0)
importmergecmd.mergetag1 = xstrdup (text);
else if (strcmp (tag, "mergetag2") == 0)
@@ -3921,7 +3918,6 @@ auth_server (root, lto_server, lfrom_server, verify_only, do_gssapi, hostinfo)
/* Paranoia. */
memset (password, 0, strlen (password));
- free (password);
# else /* ! AUTH_CLIENT_SUPPORT */
error (1, 0, "INTERNAL ERROR: This client does not support pserver authentication");
# endif /* AUTH_CLIENT_SUPPORT */
@@ -4036,7 +4032,7 @@ connect_to_forked_server (to_server, from_server)
fprintf (stderr, " -> Forking server: %s %s\n", command[0], command[1]);
}
- child_pid = piped_child (command, &tofd, &fromfd, 0);
+ child_pid = piped_child (command, &tofd, &fromfd);
if (child_pid < 0)
error (1, 0, "could not fork server process");
@@ -4240,8 +4236,7 @@ connect_to_gserver (root, sock, hostinfo)
if (need > sizeof buf)
{
- ssize_t got;
- size_t total;
+ int got;
/* This usually means that the server sent us an error
message. Read it byte by byte and print it out.
@@ -4250,19 +4245,13 @@ connect_to_gserver (root, sock, hostinfo)
want to do this to work with older servers. */
buf[0] = cbuf[0];
buf[1] = cbuf[1];
- total = 2;
- while (got = recv (sock, buf + total, sizeof buf - total, 0))
- {
- if (got < 0)
- error (1, 0, "recv() from server %s: %s",
- root->hostname, SOCK_STRERROR (SOCK_ERRNO));
- total += got;
- if (strrchr (buf + total - got, '\n'))
- break;
- }
- buf[total] = '\0';
- if (buf[total - 1] == '\n')
- buf[total - 1] = '\0';
+ got = recv (sock, buf + 2, sizeof buf - 2, 0);
+ if (got < 0)
+ error (1, 0, "recv() from server %s: %s",
+ root->hostname, SOCK_STRERROR (SOCK_ERRNO));
+ buf[got + 2] = '\0';
+ if (buf[got + 1] == '\n')
+ buf[got + 1] = '\0';
error (1, 0, "error from server %s: %s", root->hostname,
buf);
}
@@ -4343,7 +4332,6 @@ start_server ()
#endif /* HAVE_GSSAPI */
case ext_method:
- case extssh_method:
#ifdef NO_EXT_METHOD
error (0, 0, ":ext: method not supported by this port of CVS");
error (1, 0, "try :server: instead");
@@ -4728,7 +4716,27 @@ start_rsh_server (root, to_server, from_server)
char *rsh_argv[10];
if (!cvs_rsh)
- cvs_rsh = RSH_DFLT;
+ /* People sometimes suggest or assume that this should default
+ to "remsh" on systems like HPUX in which that is the
+ system-supplied name for the rsh program. However, that
+ causes various problems (keep in mind that systems such as
+ HPUX might have non-system-supplied versions of "rsh", like
+ a Kerberized one, which one might want to use). If we
+ based the name on what is found in the PATH of the person
+ who runs configure, that would make it harder to
+ consistently produce the same result in the face of
+ different people producing binary distributions. If we
+ based it on "remsh" always being the default for HPUX
+ (e.g. based on uname), that might be slightly better but
+ would require us to keep track of what the defaults are for
+ each system type, and probably would cope poorly if the
+ existence of remsh or rsh varies from OS version to OS
+ version. Therefore, it seems best to have the default
+ remain "rsh", and tell HPUX users to specify remsh, for
+ example in CVS_RSH or other such mechanisms to be devised,
+ if that is what they want (the manual already tells them
+ that). */
+ cvs_rsh = "ssh";
if (!cvs_server)
cvs_server = "cvs";
@@ -4789,7 +4797,7 @@ start_rsh_server (root, to_server, from_server)
int child_pid;
if (!cvs_rsh)
- cvs_rsh = "rsh";
+ cvs_rsh = "ssh";
if (!cvs_server)
cvs_server = "cvs";
@@ -4833,7 +4841,7 @@ start_rsh_server (root, to_server, from_server)
fprintf (stderr, "%s ", argv[i]);
putc ('\n', stderr);
}
- child_pid = piped_child (argv, &tofd, &fromfd, 1);
+ child_pid = piped_child (argv, &tofd, &fromfd);
if (child_pid < 0)
error (1, errno, "cannot start server via rsh");
@@ -4852,10 +4860,10 @@ start_rsh_server (root, to_server, from_server)
/* Send an argument STRING. */
void
send_arg (string)
- const char *string;
+ char *string;
{
char buf[1];
- const char *p = string;
+ char *p = string;
send_to_server ("Argument ", 0);
@@ -5147,10 +5155,8 @@ warning: ignoring -k options due to server limitations");
}
else if (vers->ts_rcs == NULL
|| args->force
- || strcmp (vers->ts_conflict
- && supported_request ("Empty-conflicts")
- ? vers->ts_conflict : vers->ts_rcs, vers->ts_user)
- || (vers->ts_conflict && !strcmp (cvs_cmd_name, "diff")))
+ || strcmp (vers->ts_user, vers->ts_rcs) != 0
+ || (vers->vn_user && *vers->vn_user == '0'))
{
if (args->no_contents
&& supported_request ("Is-modified"))
@@ -5356,15 +5362,36 @@ send_dirleave_proc (callerdat, dir, err, update_dir, entries)
}
/*
- * Send each option in an array to the server, one by one.
- * argv might be "--foo=bar", "-C", "5", "-y".
+ * Send each option in a string to the server, one by one.
+ * This assumes that the options are separated by spaces, for example
+ * STRING might be "--foo -C5 -y".
*/
+
void
-send_options (int argc, char *const *argv)
+send_option_string (string)
+ char *string;
{
- int i;
- for (i = 0; i < argc; i++)
- send_arg (argv[i]);
+ char *copy;
+ char *p;
+
+ copy = xstrdup (string);
+ p = copy;
+ while (1)
+ {
+ char *s;
+ char l;
+
+ for (s = p; *s != ' ' && *s != '\0'; s++)
+ ;
+ l = *s;
+ *s = '\0';
+ if (s != p)
+ send_arg (p);
+ if (l == '\0')
+ break;
+ p = s + 1;
+ }
+ free (copy);
}
diff --git a/contrib/cvs/src/commit.c b/contrib/cvs/src/commit.c
index 7d168c3..1edb95d 100644
--- a/contrib/cvs/src/commit.c
+++ b/contrib/cvs/src/commit.c
@@ -1,11 +1,6 @@
/*
- * Copyright (C) 1986-2005 The Free Software Foundation, Inc.
- *
- * Portions Copyright (C) 1998-2005 Derek Price, Ximbiot <http://ximbiot.com>,
- * and others.
- *
- * Portions Copyright (C) 1992, Brian Berliner and Jeff Polk
- * Portions Copyright (C) 1989-1992, Brian Berliner
+ * Copyright (c) 1992, Brian Berliner and Jeff Polk
+ * Copyright (c) 1989-1992, Brian Berliner
*
* You may distribute under the terms of the GNU General Public License as
* specified in the README file that comes with the CVS source distribution.
@@ -17,6 +12,7 @@
*
* The call is: cvs commit [options] files...
*
+ * $FreeBSD$
*/
#include <assert.h>
@@ -388,8 +384,12 @@ commit (argc, argv)
/* FIXME: Shouldn't this check be much more closely related to the
readonly user stuff (CVSROOT/readers, &c). That is, why should
root be able to "cvs init", "cvs import", &c, but not "cvs ci"? */
- /* Who we are on the client side doesn't affect logging. */
- if (geteuid () == (uid_t) 0 && !current_parsed_root->isremote)
+ if (geteuid () == (uid_t) 0
+# ifdef CLIENT_SUPPORT
+ /* Who we are on the client side doesn't affect logging. */
+ && !current_parsed_root->isremote
+# endif
+ )
{
struct passwd *pw;
@@ -412,7 +412,6 @@ commit (argc, argv)
/* Silently ignore -n for compatibility with old
* clients.
*/
- if (!server_active) error(0, 0, "the `-n' option is obsolete");
break;
#endif /* SERVER_SUPPORT */
case 'm':
@@ -643,8 +642,7 @@ commit (argc, argv)
fp = cvs_temp_file (&fname);
if (fp == NULL)
- error (1, 0, "cannot create temporary file %s",
- fname ? fname : "(null)");
+ error (1, 0, "cannot create temporary file %s", fname);
if (fwrite (saved_message, 1, strlen (saved_message), fp)
!= strlen (saved_message))
error (1, errno, "cannot write temporary file %s", fname);
@@ -715,8 +713,10 @@ commit (argc, argv)
Lock_Cleanup ();
dellist (&mulist);
+#ifdef SERVER_SUPPORT
if (server_active)
return err;
+#endif
/* see if we need to sleep before returning to avoid time-stamp races */
if (last_register_time)
@@ -871,11 +871,11 @@ check_fileproc (callerdat, finfo)
case T_CHECKOUT:
case T_PATCH:
case T_NEEDS_MERGE:
+ case T_CONFLICT:
case T_REMOVE_ENTRY:
error (0, 0, "Up-to-date check failed for `%s'", finfo->fullname);
freevers_ts (&vers);
return 1;
- case T_CONFLICT:
case T_MODIFIED:
case T_ADDED:
case T_REMOVED:
@@ -913,30 +913,40 @@ check_fileproc (callerdat, finfo)
return 1;
}
}
- if (status == T_CONFLICT && !force_ci)
- {
- error (0, 0,
- "file `%s' had a conflict and has not been modified",
- finfo->fullname);
- freevers_ts (&vers);
- return 1;
- }
- if (status == T_MODIFIED && !force_ci && file_has_markers (finfo))
+ if (status == T_MODIFIED && !force_ci && vers->ts_conflict)
{
- /* Make this a warning, not an error, because we have
- no way of knowing whether the "conflict indicators"
- are really from a conflict or whether they are part
- of the document itself (cvs.texinfo and sanity.sh in
- CVS itself, for example, tend to want to have strings
- like ">>>>>>>" at the start of a line). Making people
- kludge this the way they need to kludge keyword
- expansion seems undesirable. And it is worse than
- keyword expansion, because there is no -ko
- analogue. */
- error (0, 0,
- "\
+ /*
+ * We found a "conflict" marker.
+ *
+ * If the timestamp on the file is the same as the
+ * timestamp stored in the Entries file, we block the commit.
+ */
+ if ( file_has_conflict ( finfo, vers->ts_conflict ) )
+ {
+ error (0, 0,
+ "file `%s' had a conflict and has not been modified",
+ finfo->fullname);
+ freevers_ts (&vers);
+ return 1;
+ }
+
+ if (file_has_markers (finfo))
+ {
+ /* Make this a warning, not an error, because we have
+ no way of knowing whether the "conflict indicators"
+ are really from a conflict or whether they are part
+ of the document itself (cvs.texinfo and sanity.sh in
+ CVS itself, for example, tend to want to have strings
+ like ">>>>>>>" at the start of a line). Making people
+ kludge this the way they need to kludge keyword
+ expansion seems undesirable. And it is worse than
+ keyword expansion, because there is no -ko
+ analogue. */
+ error (0, 0,
+ "\
warning: file `%s' seems to still contain conflict indicators",
- finfo->fullname);
+ finfo->fullname);
+ }
}
if (status == T_REMOVED)
@@ -1275,7 +1285,11 @@ commit_fileproc (callerdat, finfo)
if (!got_message)
{
got_message = 1;
- if (!server_active && use_editor)
+ if (
+#ifdef SERVER_SUPPORT
+ !server_active &&
+#endif
+ use_editor)
do_editor (finfo->update_dir, &saved_message,
finfo->repository, ulist);
do_verify (&saved_message, finfo->repository);
@@ -1461,8 +1475,6 @@ commit_filesdoneproc (callerdat, err, repository, update_dir, entries)
Node *p;
List *ulist;
- assert (repository);
-
p = findnode (mulist, update_dir);
if (p == NULL)
return err;
@@ -1553,7 +1565,11 @@ commit_direntproc (callerdat, dir, repos, update_dir, entries)
/* get commit message */
real_repos = Name_Repository (dir, update_dir);
got_message = 1;
- if (!server_active && use_editor)
+ if (
+#ifdef SERVER_SUPPORT
+ !server_active &&
+#endif
+ use_editor)
do_editor (update_dir, &saved_message, real_repos, ulist);
do_verify (&saved_message, real_repos);
free (real_repos);
@@ -1737,22 +1753,18 @@ remove_file (finfo, tag, message)
if (corev != NULL)
free (corev);
- retcode = RCS_checkin (finfo->rcs, finfo->file, message, rev, 0,
+ retcode = RCS_checkin (finfo->rcs, finfo->file, message, rev,
RCS_FLAGS_DEAD | RCS_FLAGS_QUIET);
if (retcode != 0)
{
if (!quiet)
error (0, retcode == -1 ? errno : 0,
"failed to commit dead revision for `%s'", finfo->fullname);
- if (prev_rev != NULL)
- free (prev_rev);
return 1;
}
/* At this point, the file has been committed as removed. We should
probably tell the history file about it */
- corev = rev ? RCS_getbranch (finfo->rcs, rev, 1) : RCS_head (finfo->rcs);
- history_write ('R', NULL, corev, finfo->file, finfo->repository);
- free (corev);
+ history_write ('R', NULL, finfo->rcs->head, finfo->file, finfo->repository);
if (rev != NULL)
free (rev);
@@ -2074,8 +2086,7 @@ checkaddfile (file, repository, tag, options, rcsnode)
/* and lock it */
if (lock_RCS (file, rcs, rev, repository))
{
- error (0, 0, "cannot lock revision %s in `%s'.",
- rev ? rev : tag ? tag : "HEAD", rcs->path);
+ error (0, 0, "cannot lock `%s'.", rcs->path);
if (rev != NULL)
free (rev);
goto out;
@@ -2113,14 +2124,13 @@ checkaddfile (file, repository, tag, options, rcsnode)
/* commit a dead revision. */
(void) sprintf (tmp, "file %s was initially added on branch %s.",
file, tag);
- retcode = RCS_checkin (rcs, NULL, tmp, NULL, 0,
+ retcode = RCS_checkin (rcs, NULL, tmp, NULL,
RCS_FLAGS_DEAD | RCS_FLAGS_QUIET);
free (tmp);
if (retcode != 0)
{
error (retcode == -1 ? 1 : 0, retcode == -1 ? errno : 0,
"could not create initial dead revision %s", rcs->path);
- free (fname);
goto out;
}
@@ -2133,7 +2143,7 @@ checkaddfile (file, repository, tag, options, rcsnode)
rcs = RCS_parse (file, repository);
if (rcs == NULL)
{
- error (0, 0, "could not read %s in %s", file, repository);
+ error (0, 0, "could not read %s", rcs->path);
goto out;
}
*rcsnode = rcs;
@@ -2141,8 +2151,7 @@ checkaddfile (file, repository, tag, options, rcsnode)
/* and lock it once again. */
if (lock_RCS (file, rcs, NULL, repository))
{
- error (0, 0, "cannot lock initial revision in `%s'.",
- rcs->path);
+ error (0, 0, "cannot lock `%s'.", rcs->path);
goto out;
}
}
@@ -2155,25 +2164,12 @@ checkaddfile (file, repository, tag, options, rcsnode)
char *head;
char *magicrev;
int retcode;
- time_t headtime = -1;
- char *revnum, *tmp;
- FILE *fp;
- time_t t = -1;
- struct tm *ct;
fixbranch (rcs, sbranch);
head = RCS_getversion (rcs, NULL, NULL, 0, (int *) NULL);
- if (!head)
- error (1, 0, "No head revision in archive file `%s'.",
- rcs->path);
magicrev = RCS_magicrev (rcs, head);
- /* If this is not a new branch, then we will want a dead
- version created before this one. */
- if (!newfile)
- headtime = RCS_getrevtime (rcs, head, 0, 0);
-
retcode = RCS_settag (rcs, tag, magicrev);
RCS_rewrite (rcs, NULL, NULL);
@@ -2186,76 +2182,13 @@ checkaddfile (file, repository, tag, options, rcsnode)
"could not stub branch %s for %s", tag, rcs->path);
goto out;
}
- /* We need to add a dead version here to avoid -rtag -Dtime
- checkout problems between when the head version was
- created and now. */
- if (!newfile && headtime != -1)
- {
- /* move the new file out of the way. */
- fname = xmalloc (strlen (file) + sizeof (CVSADM)
- + sizeof (CVSPREFIX) + 10);
- (void) sprintf (fname, "%s/%s%s", CVSADM, CVSPREFIX, file);
- rename_file (file, fname);
-
- /* Create empty FILE. Can't use copy_file with a DEVNULL
- argument -- copy_file now ignores device files. */
- fp = fopen (file, "w");
- if (fp == NULL)
- error (1, errno, "cannot open %s for writing", file);
- if (fclose (fp) < 0)
- error (0, errno, "cannot close %s", file);
-
- /* As we will be hacking the delta date, put the time
- this was added into the log message. */
- t = time(NULL);
- ct = gmtime(&t);
- tmp = xmalloc (strlen (file) + strlen (tag) + 80);
-
- (void) sprintf (tmp,
- "file %s was added on branch %s on %d-%02d-%02d %02d:%02d:%02d +0000",
- file, tag,
- ct->tm_year + (ct->tm_year < 100 ? 0 : 1900),
- ct->tm_mon + 1, ct->tm_mday,
- ct->tm_hour, ct->tm_min, ct->tm_sec);
-
- /* commit a dead revision. */
- revnum = RCS_whatbranch (rcs, tag);
- retcode = RCS_checkin (rcs, NULL, tmp, revnum, headtime,
- RCS_FLAGS_DEAD |
- RCS_FLAGS_QUIET |
- RCS_FLAGS_USETIME);
- free (revnum);
- free (tmp);
-
- if (retcode != 0)
- {
- error (retcode == -1 ? 1 : 0, retcode == -1 ? errno : 0,
- "could not created dead stub %s for %s", tag,
- rcs->path);
- goto out;
- }
-
- /* put the new file back where it was */
- rename_file (fname, file);
- free (fname);
-
- /* double-check that the file was written correctly */
- freercsnode (&rcs);
- rcs = RCS_parse (file, repository);
- if (rcs == NULL)
- {
- error (0, 0, "could not read %s", rcs->path);
- goto out;
- }
- *rcsnode = rcs;
- }
}
else
{
/* lock the branch. (stubbed branches need not be locked.) */
if (lock_RCS (file, rcs, NULL, repository))
{
- error (0, 0, "cannot lock head revision in `%s'.", rcs->path);
+ error (0, 0, "cannot lock `%s'.", rcs->path);
goto out;
}
}
diff --git a/contrib/cvs/src/cvs.h b/contrib/cvs/src/cvs.h
index 15fd227..c47cdcf 100644
--- a/contrib/cvs/src/cvs.h
+++ b/contrib/cvs/src/cvs.h
@@ -1,11 +1,6 @@
/*
- * Copyright (C) 1986-2005 The Free Software Foundation, Inc.
- *
- * Portions Copyright (C) 1998-2005 Derek Price, Ximbiot <http://ximbiot.com>,
- * and others.
- *
- * Portions Copyright (C) 1992, Brian Berliner and Jeff Polk
- * Portions Copyright (C) 1989-1992, Brian Berliner
+ * Copyright (c) 1992, Brian Berliner and Jeff Polk
+ * Copyright (c) 1989-1992, Brian Berliner
*
* You may distribute under the terms of the GNU General Public License as
* specified in the README file that comes with the CVS kit.
@@ -14,6 +9,7 @@
/*
* basic information used in all source files
*
+ * $FreeBSD$
*/
@@ -199,6 +195,7 @@ extern int errno;
#define CVSROOTADM_WRITERS "writers"
#define CVSROOTADM_PASSWD "passwd"
#define CVSROOTADM_CONFIG "config"
+#define CVSROOTADM_OPTIONS "options"
#define CVSNULLREPOS "Emptydir" /* an empty directory */
@@ -212,8 +209,6 @@ extern int errno;
#define CVSATTIC "Attic"
#define CVSLCK "#cvs.lock"
-#define CVSHISTORYLCK "#cvs.history.lock"
-#define CVSVALTAGSLCK "#cvs.val-tags.lock"
#define CVSRFL "#cvs.rfl"
#define CVSWFL "#cvs.wfl"
#define CVSRFLPAT "#cvs.rfl.*" /* wildcard expr to match read locks */
@@ -270,6 +265,8 @@ extern int errno;
#define CVSREAD_ENV "CVSREAD" /* make files read-only */
#define CVSREAD_DFLT 0 /* writable files by default */
+#define CVSREADONLYFS_ENV "CVSREADONLYFS" /* repository is read-only */
+
#define TMPDIR_ENV "TMPDIR" /* Temporary directory */
#define EDITOR1_ENV "CVSEDITOR" /* which editor to use */
@@ -277,10 +274,7 @@ extern int errno;
#define EDITOR3_ENV "EDITOR" /* which editor to use */
#define CVSROOT_ENV "CVSROOT" /* source directory root */
-/* Define CVSROOT_DFLT to a fallback value for CVSROOT.
- *
-#undef CVSROOT_DFL
- */
+#define CVSROOT_DFLT NULL /* No dflt; must set for checkout */
#define IGNORE_ENV "CVSIGNORE" /* More files to ignore */
#define WRAPPER_ENV "CVSWRAPPERS" /* name of the wrapper file */
@@ -382,6 +376,7 @@ extern int really_quiet, quiet;
extern int use_editor;
extern int cvswrite;
extern mode_t cvsumask;
+extern char *RCS_citag;
@@ -400,7 +395,9 @@ extern int safe_location PROTO ((char *));
extern int trace; /* Show all commands */
extern int noexec; /* Don't modify disk anywhere */
+extern int readonlyfs; /* fail on all write locks; succeed all read locks */
extern int logoff; /* Don't write history entry */
+extern int require_real_user; /* skip CVSROOT/passwd, /etc/passwd users only*/
extern int top_level_admin;
@@ -429,18 +426,15 @@ int RCS_merge PROTO((RCSNode *, const char *, const char *, const char *,
#define RCS_FLAGS_QUIET 4
#define RCS_FLAGS_MODTIME 8
#define RCS_FLAGS_KEEPFILE 16
-#define RCS_FLAGS_USETIME 32
-extern int RCS_exec_rcsdiff PROTO ((RCSNode *rcsfile, int diff_argc,
- char *const *diff_argv,
- const char *options,
+extern int RCS_exec_rcsdiff PROTO ((RCSNode *rcsfile,
+ const char *opts, const char *options,
const char *rev1, const char *rev1_cache,
const char *rev2, const char *label1,
const char *label2, const char *workfile));
extern int diff_exec PROTO ((const char *file1, const char *file2,
const char *label1, const char *label2,
- int diff_argc, char *const *diff_argv,
- const char *out));
+ const char *options, const char *out));
#include "error.h"
@@ -464,6 +458,15 @@ char *Name_Repository PROTO((const char *dir, const char *update_dir));
const char *Short_Repository PROTO((const char *repository));
void Sanitize_Repository_Name PROTO((char *repository));
+char *Name_Root PROTO((char *dir, char *update_dir));
+void free_cvsroot_t PROTO((cvsroot_t *root_in));
+cvsroot_t *parse_cvsroot PROTO((const char *root));
+cvsroot_t *local_cvsroot PROTO((const char *dir));
+void Create_Root PROTO((const char *dir, const char *rootdir));
+void root_allow_add PROTO ((char *));
+void root_allow_free PROTO ((void));
+int root_allow_ok PROTO ((char *));
+
char *previous_rev PROTO ((RCSNode *rcs, const char *rev));
char *gca PROTO ((const char *rev1, const char *rev2));
extern void check_numeric PROTO ((const char *, int, char **));
@@ -502,6 +505,7 @@ char *get_homedir PROTO ((void));
char *strcat_filename_onto_homedir PROTO ((const char *, const char *));
char *cvs_temp_name PROTO ((void));
FILE *cvs_temp_file PROTO ((char **filename));
+void parseopts PROTO ((const char *root));
int numdots PROTO((const char *s));
char *increment_revnum PROTO ((const char *));
@@ -572,14 +576,6 @@ void lock_tree_for_write PROTO ((int argc, char **argv, int local, int which,
/* See lock.c for description. */
extern void lock_dir_for_write PROTO ((char *));
-/* Get a write lock for the history file. */
-int history_lock PROTO ((const char *));
-void clear_history_lock PROTO ((void));
-
-/* Get a write lock for the val-tags file. */
-int val_tags_lock PROTO ((const char *));
-void clear_val_tags_lock PROTO ((void));
-
/* LockDir setting from CVSROOT/config. */
extern char *lock_dir;
@@ -588,6 +584,7 @@ void ParseTag PROTO((char **tagp, char **datep, int *nonbranchp));
void WriteTag PROTO ((const char *dir, const char *tag, const char *date,
int nonbranch, const char *update_dir,
const char *repository));
+void WriteTemplate PROTO ((const char *dir, const char *update_dir));
void cat_module PROTO((int status));
void check_entries PROTO((char *dir));
void close_module PROTO((DBM * db));
@@ -679,6 +676,8 @@ int SIG_inCrSect PROTO((void));
void read_cvsrc PROTO((int *argc, char ***argv, const char *cmdname));
char *make_message_rcslegal PROTO((const char *message));
+extern int file_has_conflict PROTO ((const struct file_info *,
+ const char *ts_conflict));
extern int file_has_markers PROTO ((const struct file_info *));
extern void get_file PROTO ((const char *, const char *, const char *,
char **, size_t *, size_t *));
@@ -696,8 +695,6 @@ void sleep_past PROTO ((time_t desttime));
#define RUN_SIGIGNORE 0x0010 /* ignore interrupts for command */
#define RUN_TTY (char *)0 /* for the benefit of lint */
-void run_add_arg_p PROTO ((int *, size_t *, char ***, const char *s));
-void run_arg_free_p PROTO ((int, char **));
void run_arg PROTO((const char *s));
void run_print PROTO((FILE * fp));
void run_setup PROTO ((const char *prog));
@@ -706,7 +703,7 @@ int run_exec PROTO((const char *stin, const char *stout, const char *sterr,
/* other similar-minded stuff from run.c. */
FILE *run_popen PROTO((const char *, const char *));
-int piped_child PROTO((const char **, int *, int *, int));
+int piped_child PROTO((const char **, int *, int *));
void close_on_exec PROTO((int));
pid_t waitpid PROTO((pid_t, int *, int));
diff --git a/contrib/cvs/src/cvsbug.in b/contrib/cvs/src/cvsbug.in
index efc156d..07de151 100755
--- a/contrib/cvs/src/cvsbug.in
+++ b/contrib/cvs/src/cvsbug.in
@@ -109,14 +109,12 @@ elif [ -f /bin/domainname ]; then
/usr/bin/ypcat passwd 2>/dev/null | cat - /etc/passwd | grep "^$LOGNAME:" |
cut -f5 -d':' | sed -e 's/,.*//' > $TEMP
ORIGINATOR="`cat $TEMP`"
- rm -f $TEMP
fi
fi
if [ "$ORIGINATOR" = "" ]; then
grep "^$LOGNAME:" /etc/passwd | cut -f5 -d':' | sed -e 's/,.*//' > $TEMP
ORIGINATOR="`cat $TEMP`"
- rm -f $TEMP
fi
if [ -n "$ORGANIZATION" ]; then
diff --git a/contrib/cvs/src/diff.c b/contrib/cvs/src/diff.c
index a5ca2d0..7faaae8 100644
--- a/contrib/cvs/src/diff.c
+++ b/contrib/cvs/src/diff.c
@@ -1,11 +1,6 @@
/*
- * Copyright (C) 1986-2005 The Free Software Foundation, Inc.
- *
- * Portions Copyright (C) 1998-2005 Derek Price, Ximbiot <http://ximbiot.com>,
- * and others.
- *
- * Portions Copyright (C) 1992, Brian Berliner and Jeff Polk
- * Portions Copyright (C) 1989-1992, Brian Berliner
+ * Copyright (c) 1992, Brian Berliner and Jeff Polk
+ * Copyright (c) 1989-1992, Brian Berliner
*
* You may distribute under the terms of the GNU General Public License as
* specified in the README file that comes with the CVS source distribution.
@@ -17,6 +12,8 @@
*
* Without any file arguments, runs diff against all the currently modified
* files.
+ *
+ * $FreeBSD$
*/
#include <assert.h>
@@ -57,6 +54,7 @@ static void diff_mark_errors PROTO((int err));
static char *diff_rev1, *diff_rev2;
/* Command line dates, from -D option. Malloc'd. */
static char *diff_date1, *diff_date2;
+static char *diff_join1, *diff_join2;
static char *use_rev1, *use_rev2;
static int have_rev1_label, have_rev2_label;
@@ -65,9 +63,8 @@ static int have_rev1_label, have_rev2_label;
static char *user_file_rev;
static char *options;
-static char **diff_argv;
-static int diff_argc;
-static size_t diff_arg_allocated;
+static char *opts;
+static size_t opts_allocated = 1;
static int diff_errors;
static int empty_files = 0;
@@ -212,54 +209,6 @@ static struct option const longopts[] =
{0, 0, 0, 0}
};
-
-
-/* Add one of OPT or LONGOPT, and ARGUMENT, when present, to global DIFF_ARGV.
- *
- * INPUTS
- * opt A character option representation.
- * longopt A long option name.
- * argument Optional option argument.
- *
- * GLOBALS
- * diff_argc The number of arguments in DIFF_ARGV.
- * diff_argv Array of argument strings.
- * diff_arg_allocated Allocated length of DIFF_ARGV.
- *
- * NOTES
- * Behavior when both OPT & LONGOPT are provided is undefined.
- *
- * RETURNS
- * Nothing.
- */
-static void
-add_diff_args (char opt, const char *longopt, const char *argument)
-{
- char *tmp;
-
- /* Add opt or longopt to diff_arv. */
- assert (opt || (longopt && *longopt));
- assert (!(opt && (longopt && *longopt)));
- if (opt)
- {
- tmp = xmalloc (3);
- sprintf (tmp, "-%c", opt);
- }
- else
- {
- tmp = xmalloc (3 + strlen (longopt));
- sprintf (tmp, "--%s", longopt);
- }
- run_add_arg_p (&diff_argc, &diff_arg_allocated, &diff_argv, tmp);
- free (tmp);
-
- /* When present, add ARGUMENT to DIFF_ARGV. */
- if (argument)
- run_add_arg_p (&diff_argc, &diff_arg_allocated, &diff_argv, argument);
-}
-
-
-
/* CVS 1.9 and similar versions seemed to have pretty weird handling
of -y and -T. In the cases where it called rcsdiff,
they would have the meanings mentioned below. In the cases where it
@@ -296,6 +245,7 @@ diff (argc, argv)
int argc;
char **argv;
{
+ char tmp[50];
int c, err = 0;
int local = 0;
int which;
@@ -315,15 +265,18 @@ diff (argc, argv)
/* Clean out our global variables (multiroot can call us multiple
times and the server can too, if the client sends several
diff commands). */
- if (diff_argc)
+ if (opts == NULL)
{
- run_arg_free_p (diff_argc, diff_argv);
- diff_argc = 0;
+ opts_allocated = 1;
+ opts = xmalloc (opts_allocated);
}
+ opts[0] = '\0';
diff_rev1 = NULL;
diff_rev2 = NULL;
diff_date1 = NULL;
diff_date2 = NULL;
+ diff_join1 = NULL;
+ diff_join2 = NULL;
optind = 0;
/* FIXME: This should really be allocating an argv to be passed to diff
@@ -334,13 +287,13 @@ diff (argc, argv)
* to diff.
*/
while ((c = getopt_long (argc, argv,
- "+abcdefhilnpstuwy0123456789BHNRTC:D:F:I:L:U:W:k:r:",
+ "+abcdefhilnpstuwy0123456789BHNRTC:D:F:I:L:U:W:k:r:j:",
longopts, &option_index)) != -1)
{
switch (c)
{
case 'y':
- add_diff_args (0, "side-by-side", NULL);
+ xrealloc_and_strcat (&opts, &opts_allocated, " --side-by-side");
break;
case 'a': case 'b': case 'c': case 'd': case 'e': case 'f':
case 'h': case 'i': case 'n': case 'p': case 's': case 't':
@@ -348,7 +301,8 @@ diff (argc, argv)
case '0': case '1': case '2': case '3': case '4': case '5':
case '6': case '7': case '8': case '9':
case 'B': case 'H': case 'T':
- add_diff_args (c, NULL, NULL);
+ (void) sprintf (tmp, " -%c", (char) c);
+ xrealloc_and_strcat (&opts, &opts_allocated, tmp);
break;
case 'L':
if (have_rev1_label++)
@@ -357,15 +311,33 @@ diff (argc, argv)
error (0, 0, "extra -L arguments ignored");
break;
}
- /* Fall through. */
+
+ xrealloc_and_strcat (&opts, &opts_allocated, " -L");
+ xrealloc_and_strcat (&opts, &opts_allocated, optarg);
+ break;
case 'C': case 'F': case 'I': case 'U': case 'W':
- add_diff_args (c, NULL, optarg);
+ (void) sprintf (tmp, " -%c", (char) c);
+ xrealloc_and_strcat (&opts, &opts_allocated, tmp);
+ xrealloc_and_strcat (&opts, &opts_allocated, optarg);
+ break;
+ case 131:
+ /* --ifdef. */
+ xrealloc_and_strcat (&opts, &opts_allocated, " --ifdef=");
+ xrealloc_and_strcat (&opts, &opts_allocated, optarg);
break;
- case 129: case 130: case 131: case 132: case 133: case 134:
+ case 129: case 130: case 132: case 133: case 134:
case 135: case 136: case 137: case 138: case 139: case 140:
case 141: case 142: case 143: case 145: case 146:
- add_diff_args (0, longopts[option_index].name,
- longopts[option_index].has_arg ? optarg : NULL);
+ xrealloc_and_strcat (&opts, &opts_allocated, " --");
+ xrealloc_and_strcat (&opts, &opts_allocated,
+ longopts[option_index].name);
+ if (longopts[option_index].has_arg == 1
+ || (longopts[option_index].has_arg == 2
+ && optarg != NULL))
+ {
+ xrealloc_and_strcat (&opts, &opts_allocated, "=");
+ xrealloc_and_strcat (&opts, &opts_allocated, optarg);
+ }
break;
case 'R':
local = 0;
@@ -378,6 +350,27 @@ diff (argc, argv)
free (options);
options = RCS_check_kflag (optarg);
break;
+ case 'j':
+ {
+ char *ptr;
+ char *cpy = strdup(optarg);
+
+ if ((ptr = strchr(optarg, ':')) != NULL)
+ *ptr++ = 0;
+ if (diff_rev2 != NULL || diff_date2 != NULL)
+ error (1, 0,
+ "no more than two revisions/dates can be specified");
+ if (diff_rev1 != NULL || diff_date1 != NULL) {
+ diff_join2 = cpy;
+ diff_rev2 = optarg;
+ diff_date2 = ptr ? Make_Date(ptr) : NULL;
+ } else {
+ diff_join1 = cpy;
+ diff_rev1 = optarg;
+ diff_date1 = ptr ? Make_Date(ptr) : NULL;
+ }
+ }
+ break;
case 'r':
if (diff_rev2 != NULL || diff_date2 != NULL)
error (1, 0,
@@ -423,16 +416,21 @@ diff (argc, argv)
send_arg("-l");
if (empty_files)
send_arg("-N");
- send_options (diff_argc, diff_argv);
+ send_option_string (opts);
if (options[0] != '\0')
send_arg (options);
- if (diff_rev1)
+ if (diff_join1)
+ option_with_arg ("-j", diff_join1);
+ else if (diff_rev1)
option_with_arg ("-r", diff_rev1);
- if (diff_date1)
+ else if (diff_date1)
client_senddate (diff_date1);
- if (diff_rev2)
+
+ if (diff_join2)
+ option_with_arg ("-j", diff_join2);
+ else if (diff_rev2)
option_with_arg ("-r", diff_rev2);
- if (diff_date2)
+ else if (diff_date2)
client_senddate (diff_date2);
send_arg ("--");
@@ -446,28 +444,26 @@ diff (argc, argv)
send_to_server ("diff\012", 0);
err = get_responses_and_close ();
- free (options);
- options = NULL;
- return (err);
- }
+ } else
#endif
-
- if (diff_rev1 != NULL)
- tag_check_valid (diff_rev1, argc, argv, local, 0, "");
- if (diff_rev2 != NULL)
- tag_check_valid (diff_rev2, argc, argv, local, 0, "");
-
- which = W_LOCAL;
- if (diff_rev1 != NULL || diff_date1 != NULL)
- which |= W_REPOS | W_ATTIC;
-
- wrap_setup ();
-
- /* start the recursion processor */
- err = start_recursion (diff_fileproc, diff_filesdoneproc, diff_dirproc,
- diff_dirleaveproc, NULL, argc, argv, local,
- which, 0, CVS_LOCK_READ, (char *) NULL, 1,
- (char *) NULL);
+ {
+ if (diff_rev1 != NULL)
+ tag_check_valid (diff_rev1, argc, argv, local, 0, "");
+ if (diff_rev2 != NULL)
+ tag_check_valid (diff_rev2, argc, argv, local, 0, "");
+
+ which = W_LOCAL;
+ if (diff_rev1 != NULL || diff_date1 != NULL)
+ which |= W_REPOS | W_ATTIC;
+
+ wrap_setup ();
+
+ /* start the recursion processor */
+ err = start_recursion (diff_fileproc, diff_filesdoneproc, diff_dirproc,
+ diff_dirleaveproc, NULL, argc, argv, local,
+ which, 0, CVS_LOCK_READ, (char *) NULL, 1,
+ (char *) NULL);
+ }
/* clean up */
free (options);
@@ -477,6 +473,10 @@ diff (argc, argv)
free (diff_date1);
if (diff_date2 != NULL)
free (diff_date2);
+ if (diff_join1 != NULL)
+ free (diff_join1);
+ if (diff_join2 != NULL)
+ free (diff_join2);
return (err);
}
@@ -522,7 +522,7 @@ diff_fileproc (callerdat, finfo)
int exists;
exists = 0;
- /* special handling for TAG_HEAD */
+ /* special handling for TAG_HEAD XXX */
if (diff_rev1 && strcmp (diff_rev1, TAG_HEAD) == 0)
{
char *head =
@@ -733,8 +733,8 @@ RCS file: ", 0);
if (empty_file == DIFF_ADDED)
{
if (use_rev2 == NULL)
- status = diff_exec (DEVNULL, finfo->file, label1, label2,
- diff_argc, diff_argv, RUN_TTY);
+ status = diff_exec (DEVNULL, finfo->file, label1, label2, opts,
+ RUN_TTY);
else
{
int retcode;
@@ -750,8 +750,7 @@ RCS file: ", 0);
if( retcode != 0 )
goto out;
- status = diff_exec (DEVNULL, tmp, label1, label2,
- diff_argc, diff_argv, RUN_TTY);
+ status = diff_exec (DEVNULL, tmp, label1, label2, opts, RUN_TTY);
}
}
else
@@ -767,16 +766,16 @@ RCS file: ", 0);
if (retcode != 0)
goto out;
- status = diff_exec (tmp, DEVNULL, label1, label2,
- diff_argc, diff_argv, RUN_TTY);
+ status = diff_exec (tmp, DEVNULL, label1, label2, opts, RUN_TTY);
}
}
else
{
- status = RCS_exec_rcsdiff (vers->srcfile, diff_argc, diff_argv,
- *options ? options : vers->options,
- use_rev1, rev1_cache, use_rev2,
- label1, label2, finfo->file);
+ status = RCS_exec_rcsdiff(vers->srcfile, opts,
+ *options ? options : vers->options,
+ use_rev1, rev1_cache, use_rev2,
+ label1, label2,
+ finfo->file);
}
@@ -920,7 +919,7 @@ diff_file_nodiff( finfo, vers, empty_file, rev1_cache )
if (diff_rev1 || diff_date1)
{
- /* special handling for TAG_HEAD */
+ /* special handling for TAG_HEAD XXX */
if (diff_rev1 && strcmp (diff_rev1, TAG_HEAD) == 0)
{
if (vers->vn_rcs != NULL && vers->srcfile != NULL)
@@ -936,7 +935,7 @@ diff_file_nodiff( finfo, vers, empty_file, rev1_cache )
}
if (diff_rev2 || diff_date2)
{
- /* special handling for TAG_HEAD */
+ /* special handling for TAG_HEAD XXX */
if (diff_rev2 && strcmp (diff_rev2, TAG_HEAD) == 0)
{
if (vers->vn_rcs != NULL && vers->srcfile != NULL)
diff --git a/contrib/cvs/src/entries.c b/contrib/cvs/src/entries.c
index c346fb6..1ab7c7e 100644
--- a/contrib/cvs/src/entries.c
+++ b/contrib/cvs/src/entries.c
@@ -1,11 +1,6 @@
/*
- * Copyright (C) 1986-2005 The Free Software Foundation, Inc.
- *
- * Portions Copyright (C) 1998-2005 Derek Price, Ximbiot <http://ximbiot.com>,
- * and others.
- *
- * Portions Copyright (C) 1992, Brian Berliner and Jeff Polk
- * Portions Copyright (C) 1989-1992, Brian Berliner
+ * Copyright (c) 1992, Brian Berliner and Jeff Polk
+ * Copyright (c) 1989-1992, Brian Berliner
*
* You may distribute under the terms of the GNU General Public License as
* specified in the README file that comes with the CVS source distribution.
@@ -16,6 +11,9 @@
* the Entries file.
*/
+/*
+ * $FreeBSD$
+ */
#include "cvs.h"
#include "getline.h"
@@ -542,7 +540,6 @@ Entries_Open (aflag, update_dir)
break;
default:
/* Ignore unrecognized commands. */
- Entnode_Destroy (ent);
break;
}
}
@@ -641,6 +638,72 @@ AddEntryNode (list, entdata)
return (p);
}
+static char *root_template;
+
+static int
+get_root_template(const char *repository, const char *path)
+{
+ if (root_template) {
+ if (strcmp(path, root_template) == 0)
+ return(0);
+ free(root_template);
+ }
+ if ((root_template = strdup(path)) == NULL)
+ return(-1);
+ return(0);
+}
+
+/*
+ * Write out/Clear the CVS/Template file.
+ */
+void
+WriteTemplate (dir, update_dir)
+ const char *dir;
+ const char *update_dir;
+{
+ char *tmp = NULL;
+ struct stat st1;
+ struct stat st2;
+
+ if (Parse_Info(CVSROOTADM_RCSINFO, "cvs", get_root_template, 1) < 0)
+ return;
+
+ if (asprintf(&tmp, "%s/%s", dir, CVSADM_TEMPLATE) < 0)
+ error (1, errno, "out of memory");
+
+ if (stat(root_template, &st1) == 0) {
+ if (stat(tmp, &st2) < 0 || st1.st_mtime != st2.st_mtime) {
+ FILE *fi;
+ FILE *fo;
+
+ if ((fi = open_file(root_template, "r")) != NULL) {
+ if ((fo = open_file(tmp, "w")) != NULL) {
+ int n;
+ char buf[256];
+
+ while ((n = fread(buf, 1, sizeof(buf), fi)) > 0)
+ fwrite(buf, 1, n, fo);
+ fflush(fo);
+ if (ferror(fi) || ferror(fo)) {
+ fclose(fo);
+ remove(tmp);
+ error (1, errno, "error copying Template");
+ } else {
+ struct timeval times[2];
+ fclose(fo);
+ times[0].tv_sec = st1.st_mtime;
+ times[0].tv_usec = 0;
+ times[1] = times[0];
+ utimes(tmp, times);
+ }
+ }
+ fclose(fi);
+ }
+ }
+ }
+ free(tmp);
+}
+
/*
* Write out/Clear the CVS/Tag file.
*/
diff --git a/contrib/cvs/src/filesubr.c b/contrib/cvs/src/filesubr.c
index 14da6292..9353888 100644
--- a/contrib/cvs/src/filesubr.c
+++ b/contrib/cvs/src/filesubr.c
@@ -17,11 +17,13 @@
definitions under operating systems (like, say, Windows NT) with different
file system semantics. */
+/*
+ * $FreeBSD$
+ */
+
#include <assert.h>
#include "cvs.h"
-#include "xsize.h"
-
static int deep_remove_dir PROTO((const char *path));
/*
@@ -107,7 +109,7 @@ copy_file (from, to)
error (1, errno, "cannot close %s", to);
}
- /* preserve last access & modification times */
+ /* now, set the times for the copied file to match those of the original */
memset ((char *) &t, 0, sizeof (t));
t.actime = sb.st_atime;
t.modtime = sb.st_mtime;
@@ -435,10 +437,14 @@ unlink_file_dir (f)
{
struct stat sb;
- /* This is called by the server parent process in contexts where
- it is not OK to send output (e.g. after we sent "ok" to the
- client). */
- if (trace && !server_active)
+ if (trace
+#ifdef SERVER_SUPPORT
+ /* This is called by the server parent process in contexts where
+ it is not OK to send output (e.g. after we sent "ok" to the
+ client). */
+ && !server_active
+#endif
+ )
(void) fprintf (stderr, "-> unlink_file_dir(%s)\n", f);
if (noexec)
@@ -702,8 +708,7 @@ cvs_temp_name ()
fp = cvs_temp_file (&fn);
if (fp == NULL)
- error (1, errno, "Failed to create temporary file %s",
- fn ? fn : "(null)");
+ error (1, errno, "Failed to create temporary file");
if (fclose (fp) == EOF)
error (0, errno, "Failed to close temporary file %s", fn);
return fn;
@@ -740,8 +745,7 @@ cvs_temp_name ()
* NFS locking thing, but until I hear of more problems, I'm not going to
* bother.
*/
-FILE *
-cvs_temp_file (filename)
+FILE *cvs_temp_file (filename)
char **filename;
{
char *fn;
@@ -780,11 +784,7 @@ cvs_temp_file (filename)
errno = save_errno;
}
- if (fp == NULL)
- {
- free (fn);
- fn = NULL;
- }
+ if (fp == NULL) free (fn);
/* mkstemp is defined to open mode 0600 using glibc 2.0.7+ */
/* FIXME - configure can probably tell us which version of glibc we are
* linking to and not chmod for 2.0.7+
@@ -799,11 +799,7 @@ cvs_temp_file (filename)
fn = tempnam (Tmpdir, "cvs");
if (fn == NULL) fp = NULL;
- else if ((fp = CVS_FOPEN (fn, "w+")) == NULL)
- {
- free (fn);
- fn = NULL;
- }
+ else if ((fp = CVS_FOPEN (fn, "w+")) == NULL) free (fn);
else chmod (fn, 0600);
/* tempnam returns a pointer to a newly malloc'd string, so there's
@@ -853,11 +849,6 @@ cvs_temp_file (filename)
#endif
*filename = fn;
- if (fn == NULL && fp != NULL)
- {
- fclose (fp);
- fp = NULL;
- }
return fp;
}
@@ -880,48 +871,32 @@ cvs_temp_file (filename)
* This function exits with a fatal error if it fails to read the link for
* any reason.
*/
-#define MAXSIZE (SIZE_MAX < SSIZE_MAX ? SIZE_MAX : SSIZE_MAX)
-
char *
xreadlink (link)
const char *link;
{
char *file = NULL;
- size_t buflen = 128;
+ int buflen = BUFSIZ;
+ int link_name_len;
- /* Get the name of the file to which `from' is linked. */
- while (1)
+ /* Get the name of the file to which `from' is linked.
+ FIXME: what portability issues arise here? Are readlink &
+ ENAMETOOLONG defined on all systems? -twp */
+ do
{
- ssize_t r;
- size_t link_name_len;
-
file = xrealloc (file, buflen);
- r = readlink (link, file, buflen);
- link_name_len = r;
+ errno = 0;
+ link_name_len = readlink (link, file, buflen - 1);
+ buflen *= 2;
+ }
+ while (link_name_len < 0 && errno == ENAMETOOLONG);
- if (r < 0
-#ifdef ERANGE
- /* AIX 4 and HP-UX report ERANGE if the buffer is too small. */
- && errno != ERANGE
-#endif
- )
- error (1, errno, "cannot readlink %s", link);
+ if (link_name_len < 0)
+ error (1, errno, "cannot readlink %s", link);
- /* If there is space for the NUL byte, set it and return. */
- if (r >= 0 && link_name_len < buflen)
- {
- file[link_name_len] = '\0';
- return file;
- }
+ file[link_name_len] = '\0';
- if (buflen <= MAXSIZE / 2)
- buflen *= 2;
- else if (buflen < MAXSIZE)
- buflen = MAXSIZE;
- else
- /* Our buffer cannot grow any bigger. */
- error (1, ENAMETOOLONG, "cannot readlink %s", link);
- }
+ return file;
}
#endif /* HAVE_READLINK */
@@ -974,8 +949,7 @@ last_component (path)
const char *path;
{
const char *last = strrchr (path, '/');
-
- assert (path);
+
if (last && (last != path))
return last + 1;
else
@@ -1015,7 +989,11 @@ get_homedir ()
if (home != NULL)
return home;
- if (!server_active && (env = getenv ("HOME")) != NULL)
+ if (
+#ifdef SERVER_SUPPORT
+ !server_active &&
+#endif
+ (env = getenv ("HOME")) != NULL)
home = env;
else if ((pw = (struct passwd *) getpwuid (getuid ()))
&& pw->pw_dir)
@@ -1056,7 +1034,6 @@ expand_wild (argc, argv, pargc, pargv)
char ***pargv;
{
int i;
- assert (argv || !argc);
if (size_overflow_p (xtimes (argc, sizeof (char *)))) {
*pargc = 0;
*pargv = NULL;
diff --git a/contrib/cvs/src/import.c b/contrib/cvs/src/import.c
index ea65677..b962ebc 100644
--- a/contrib/cvs/src/import.c
+++ b/contrib/cvs/src/import.c
@@ -1,11 +1,6 @@
/*
- * Copyright (C) 1986-2005 The Free Software Foundation, Inc.
- *
- * Portions Copyright (C) 1998-2005 Derek Price, Ximbiot <http://ximbiot.com>,
- * and others.
- *
- * Portions Copyright (C) 1992, Brian Berliner and Jeff Polk
- * Portions Copyright (C) 1989-1992, Brian Berliner
+ * Copyright (c) 1992, Brian Berliner and Jeff Polk
+ * Copyright (c) 1989-1992, Brian Berliner
*
* You may distribute under the terms of the GNU General Public License as
* specified in the README file that comes with the CVS source distribution.
@@ -19,6 +14,8 @@
* VendorReleTag Tag for this particular release
*
* Additional arguments specify more Vendor Release Tags.
+ *
+ * $FreeBSD$
*/
#include "cvs.h"
@@ -89,14 +86,17 @@ import (argc, argv)
{
case 'Q':
case 'q':
+#ifdef SERVER_SUPPORT
/* The CVS 1.5 client sends these options (in addition to
Global_option requests), so we must ignore them. */
if (!server_active)
+#endif
error (1, 0,
"-q or -Q must be specified before \"%s\"",
cvs_cmd_name);
break;
case 'd':
+#ifdef SERVER_SUPPORT
if (server_active)
{
/* CVS 1.10 and older clients will send this, but it
@@ -106,6 +106,7 @@ import (argc, argv)
"warning: not setting the time of import from the file");
error (0, 0, "due to client limitations");
}
+#endif
use_file_modtime = 1;
break;
case 'b':
@@ -118,7 +119,6 @@ import (argc, argv)
#else
use_editor = 0;
#endif
- if (message) free (message);
message = xstrdup(optarg);
break;
case 'I':
@@ -145,6 +145,7 @@ import (argc, argv)
if (argc < 3)
usage (import_usage);
+#ifdef SERVER_SUPPORT
/* This is for handling the Checkin-time request. It might seem a
bit odd to enable the use_file_modtime code even in the case
where Checkin-time was not sent for a particular file. The
@@ -156,6 +157,7 @@ import (argc, argv)
if (server_active)
use_file_modtime = 1;
+#endif
/* Don't allow "CVS" as any directory in module path.
*
@@ -212,22 +214,11 @@ import (argc, argv)
* support branching to a single level, so the specified vendor branch
* must only have two dots in it (like "1.1.1").
*/
- {
- regex_t pat;
- int ret = regcomp (&pat, "^[1-9][0-9]*\\.[1-9][0-9]*\\.[1-9][0-9]*$",
- REG_EXTENDED);
- assert (!ret);
- if (regexec (&pat, vbranch, 0, NULL, 0))
- {
- error (1, 0,
-"Only numeric branch specifications with two dots are\n"
-"supported by import, not `%s'. For example: `1.1.1'.",
- vbranch);
- }
- regfree (&pat);
- }
-
- /* Set vhead to the branch's parent. */
+ for (cp = vbranch; *cp != '\0'; cp++)
+ if (!isdigit ((unsigned char) *cp) && *cp != '.')
+ error (1, 0, "%s is not a numeric branch", vbranch);
+ if (numdots (vbranch) != 2)
+ error (1, 0, "Only branches with two dots are supported: %s", vbranch);
vhead = xstrdup (vbranch);
cp = strrchr (vhead, '.');
*cp = '\0';
@@ -241,10 +232,17 @@ import (argc, argv)
}
#endif
- if (!server_active && use_editor)
+ if (
+#ifdef SERVER_SUPPORT
+ !server_active &&
+#endif
+ use_editor)
{
do_editor ((char *) NULL, &message,
- current_parsed_root->isremote ? (char *) NULL : repository,
+#ifdef CLIENT_SUPPORT
+ current_parsed_root->isremote ? (char *) NULL :
+#endif
+ repository,
(List *) NULL);
}
do_verify (&message, repository);
@@ -317,8 +315,7 @@ import (argc, argv)
/* Create the logfile that will be logged upon completion */
if ((logfp = cvs_temp_file (&tmpfile)) == NULL)
- error (1, errno, "cannot create temporary file `%s'",
- tmpfile ? tmpfile : "(null)");
+ error (1, errno, "cannot create temporary file `%s'", tmpfile);
/* On systems where we can unlink an open file, do so, so it will go
away no matter how we exit. FIXME-maybe: Should be checking for
errors but I'm not sure which error(s) we get if we are on a system
@@ -439,9 +436,6 @@ import_descend (message, vtag, targc, targv)
ign_add_file (CVSDOTIGNORE, 1);
wrap_add_file (CVSDOTWRAPPER, 1);
- if (!current_parsed_root->isremote)
- lock_dir_for_write (repository);
-
if ((dirp = CVS_OPENDIR (".")) == NULL)
{
error (0, errno, "cannot open directory");
@@ -454,13 +448,13 @@ import_descend (message, vtag, targc, targv)
{
if (strcmp (dp->d_name, ".") == 0 || strcmp (dp->d_name, "..") == 0)
goto one_more_time_boys;
-
+#ifdef SERVER_SUPPORT
/* CVS directories are created in the temp directory by
server.c because it doesn't special-case import. So
don't print a message about them, regardless of -I!. */
if (server_active && strcmp (dp->d_name, CVSADM) == 0)
goto one_more_time_boys;
-
+#endif
if (ign_name (dp->d_name))
{
add_log ('I', dp->d_name);
@@ -524,9 +518,6 @@ import_descend (message, vtag, targc, targv)
(void) CVS_CLOSEDIR (dirp);
}
- if (!current_parsed_root->isremote)
- Lock_Cleanup ();
-
if (dirlist != NULL)
{
Node *head, *p;
@@ -759,7 +750,7 @@ add_rev (message, rcs, vfile, vers)
tocvsPath = wrap_tocvs_process_file (vfile);
status = RCS_checkin (rcs, tocvsPath == NULL ? vfile : tocvsPath,
- message, vbranch, 0,
+ message, vbranch,
(RCS_FLAGS_QUIET | RCS_FLAGS_KEEPFILE
| (use_file_modtime ? RCS_FLAGS_MODTIME : 0)));
ierrno = errno;
@@ -1595,7 +1586,11 @@ import_descend_dir (message, dir, vtag, targc, targv)
repository = new;
}
+#ifdef CLIENT_SUPPORT
if (!quiet && !current_parsed_root->isremote)
+#else
+ if (!quiet)
+#endif
error (0, 0, "Importing %s", repository);
if ( CVS_CHDIR (dir) < 0)
@@ -1606,7 +1601,11 @@ import_descend_dir (message, dir, vtag, targc, targv)
err = 1;
goto out;
}
+#ifdef CLIENT_SUPPORT
if (!current_parsed_root->isremote && !isdir (repository))
+#else
+ if (!isdir (repository))
+#endif
{
rcs = xmalloc (strlen (repository) + sizeof (RCSEXT) + 5);
(void) sprintf (rcs, "%s%s", repository, RCSEXT);
diff --git a/contrib/cvs/src/lock.c b/contrib/cvs/src/lock.c
index 7a5e338..36cbf7d 100644
--- a/contrib/cvs/src/lock.c
+++ b/contrib/cvs/src/lock.c
@@ -1,11 +1,6 @@
/*
- * Copyright (C) 1986-2005 The Free Software Foundation, Inc.
- *
- * Portions Copyright (C) 1998-2005 Derek Price, Ximbiot <http://ximbiot.com>,
- * and others.
- *
- * Portions Copyright (C) 1992, Brian Berliner and Jeff Polk
- * Portions Copyright (C) 1989-1992, Brian Berliner
+ * Copyright (c) 1992, Brian Berliner and Jeff Polk
+ * Copyright (c) 1989-1992, Brian Berliner
*
* You may distribute under the terms of the GNU General Public License as
* specified in the README file that comes with the CVS source distribution.
@@ -13,6 +8,8 @@
* Set Lock
*
* Lock file support for CVS.
+ *
+ * $FreeBSD$
*/
/* The node Concurrency in doc/cvs.texinfo has a brief introduction to
@@ -90,17 +87,8 @@ struct lock {
case of writelocks, it is just a pointer to the storage allocated
for the ->key field. */
char *repository;
-
- /* The name of the master lock dir. Usually CVSLCK. */
- const char *lockdirname;
-
- /* The full path to the lock dir, if we are currently holding it.
- *
- * This will be LOCKDIRNAME catted onto REPOSITORY. We waste a little
- * space by storing it, but save a later malloc/free.
- */
- char *lockdir;
-
+ /* Do we have a lock named CVSLCK? */
+ int have_lckdir;
/* Note there is no way of knowing whether the readlock and writelock
exist. The code which sets the locks doesn't use SIG_beginCrSect
to set a flag like we do for CVSLCK. */
@@ -129,6 +117,7 @@ static char *readlock;
static char *writelock;
/* Malloc'd array specifying the name of a CVSLCK file (absolute pathname).
Will always be non-NULL in the cases where it is used. */
+static char *masterlock;
static List *locklist;
#define L_OK 0 /* success */
@@ -137,10 +126,7 @@ static List *locklist;
/* This is the (single) readlock which is set by Reader_Lock. The
repository field is NULL if there is no such lock. */
-static struct lock global_readlock = {NULL, CVSLCK, NULL};
-
-static struct lock global_history_lock = {NULL, CVSHISTORYLCK, NULL};
-static struct lock global_val_tags_lock = {NULL, CVSVALTAGSLCK, NULL};
+static struct lock global_readlock;
/* List of locks set by lock_tree_for_write. This is redundant
with locklist, sort of. */
@@ -156,7 +142,7 @@ static List *locked_list;
/* LockDir from CVSROOT/config. */
char *lock_dir;
-static char *lock_name PROTO ((const char *repository, const char *name));
+static char *lock_name PROTO ((char *repository, char *name));
/* Return a newly malloc'd string containing the name of the lock for the
repository REPOSITORY and the lock file name within that directory
@@ -166,13 +152,13 @@ static char *lock_name PROTO ((const char *repository, const char *name));
things simple). */
static char *
lock_name (repository, name)
- const char *repository;
- const char *name;
+ char *repository;
+ char *name;
{
char *retval;
- const char *p;
+ char *p;
char *q;
- const char *short_repos;
+ char *short_repos;
mode_t save_umask;
int saved_umask = 0;
@@ -327,10 +313,6 @@ Lock_Cleanup ()
locked_dir = NULL;
locked_list = NULL;
}
-
- if (global_history_lock.repository) clear_history_lock ();
- if (global_val_tags_lock.repository) clear_val_tags_lock ();
-
in_lock_cleanup = 0;
}
@@ -367,8 +349,6 @@ unlock_proc (p, closure)
return (0);
}
-
-
/* Remove the lock files. */
static void
lock_simple_remove (lock)
@@ -383,7 +363,7 @@ lock_simple_remove (lock)
if (readlock != NULL)
{
tmp = lock_name (lock->repository, readlock);
- if (CVS_UNLINK (tmp) < 0 && ! existence_error (errno))
+ if ( CVS_UNLINK (tmp) < 0 && ! existence_error (errno))
error (0, errno, "failed to remove lock %s", tmp);
free (tmp);
}
@@ -395,12 +375,21 @@ lock_simple_remove (lock)
if (writelock != NULL)
{
tmp = lock_name (lock->repository, writelock);
- if (CVS_UNLINK (tmp) < 0 && ! existence_error (errno))
+ if ( CVS_UNLINK (tmp) < 0 && ! existence_error (errno))
error (0, errno, "failed to remove lock %s", tmp);
free (tmp);
}
- clear_lock (lock);
+ if (lock->have_lckdir)
+ {
+ tmp = lock_name (lock->repository, CVSLCK);
+ SIG_beginCrSect ();
+ if (CVS_RMDIR (tmp) < 0)
+ error (0, errno, "failed to remove lock dir %s", tmp);
+ lock->have_lckdir = 0;
+ SIG_endCrSect ();
+ free (tmp);
+ }
}
@@ -420,7 +409,7 @@ Reader_Lock (xrepository)
(void) fprintf (stderr, "%s-> Reader_Lock(%s)\n", CLIENT_SERVER_STR,
xrepository);
- if (noexec)
+ if (noexec || readonlyfs)
return 0;
/* we only do one directory at a time for read locks! */
@@ -497,6 +486,11 @@ Writer_Lock (list)
if (noexec)
return 0;
+ if (readonlyfs) {
+ error (0, 0, "write lock failed - read-only repository");
+ return (1);
+ }
+
/* We only know how to do one list at a time */
if (locklist != (List *) NULL)
{
@@ -668,9 +662,6 @@ readers_exist (repository)
#endif
lockdir = lock_name (repository, "");
-
- assert (lockdir != NULL);
-
lockdir[strlen (lockdir) - 1] = '\0'; /* remove trailing slash */
do {
@@ -777,13 +768,13 @@ set_lock (lock, will_wait)
long us;
struct stat sb;
mode_t omask;
- char *masterlock;
- int status;
#ifdef CVS_FUDGELOCKS
time_t now;
#endif
- masterlock = lock_name (lock->repository, lock->lockdirname);
+ if (masterlock != NULL)
+ free (masterlock);
+ masterlock = lock_name (lock->repository, CVSLCK);
/*
* Note that it is up to the callers of set_lock() to arrange for signal
@@ -792,33 +783,33 @@ set_lock (lock, will_wait)
*/
waited = 0;
us = 1;
+ lock->have_lckdir = 0;
for (;;)
{
- status = -1;
+ int status = -1;
omask = umask (cvsumask);
SIG_beginCrSect ();
if (CVS_MKDIR (masterlock, 0777) == 0)
{
- lock->lockdir = masterlock;
+ lock->have_lckdir = 1;
SIG_endCrSect ();
status = L_OK;
if (waited)
lock_obtained (lock->repository);
- goto after_sig_unblock;
+ goto out;
}
SIG_endCrSect ();
- after_sig_unblock:
+ out:
(void) umask (omask);
if (status != -1)
- goto done;
+ return status;
if (errno != EEXIST)
{
error (0, errno,
"failed to create lock directory for `%s' (%s)",
lock->repository, masterlock);
- status = L_ERROR;
- goto done;
+ return (L_ERROR);
}
/* Find out who owns the lock. If the lock directory is
@@ -830,8 +821,7 @@ set_lock (lock, will_wait)
continue;
error (0, errno, "couldn't stat lock directory `%s'", masterlock);
- status = L_ERROR;
- goto done;
+ return (L_ERROR);
}
#ifdef CVS_FUDGELOCKS
@@ -853,10 +843,7 @@ set_lock (lock, will_wait)
/* if he wasn't willing to wait, return an error */
if (!will_wait)
- {
- status = L_LOCKED;
- goto done;
- }
+ return (L_LOCKED);
/* if possible, try a very short sleep without a message */
if (!waited && us < 1000)
@@ -887,45 +874,23 @@ set_lock (lock, will_wait)
lock_wait (lock->repository);
waited = 1;
}
-done:
- if (!lock->lockdir) free (masterlock);
- return status;
}
-
-
/*
- * Clear master lock.
- *
- * INPUTS
- * lock The lock information.
- *
- * OUTPUTS
- * Sets LOCK->lockdir to NULL after removing the directory it names and
- * freeing the storage.
- *
- * ASSUMPTIONS
- * If we own the master lock directory, its name is stored in LOCK->lockdir.
- * We may free LOCK->lockdir.
- *
+ * Clear master lock. We don't have to recompute the lock name since
+ * clear_lock is never called except after a successful set_lock().
*/
static void
clear_lock (lock)
struct lock *lock;
{
SIG_beginCrSect ();
- if (lock->lockdir)
- {
- if (CVS_RMDIR (lock->lockdir) < 0)
- error (0, errno, "failed to remove lock dir `%s'", lock->lockdir);
- free (lock->lockdir);
- lock->lockdir = NULL;
- }
+ if (CVS_RMDIR (masterlock) < 0)
+ error (0, errno, "failed to remove lock dir `%s'", masterlock);
+ lock->have_lckdir = 0;
SIG_endCrSect ();
}
-
-
/*
* Print out a message that the lock is still held, then sleep a while.
*/
@@ -1000,8 +965,7 @@ lock_filesdoneproc (callerdat, err, repository, update_dir, entries)
p->key = xstrdup (repository);
p->data = xmalloc (sizeof (struct lock));
((struct lock *)p->data)->repository = p->key;
- ((struct lock *)p->data)->lockdirname = CVSLCK;
- ((struct lock *)p->data)->lockdir = NULL;
+ ((struct lock *)p->data)->have_lckdir = 0;
/* FIXME-KRP: this error condition should not simply be passed by. */
if (p->key == NULL || addnode (lock_tree_list, p) != 0)
@@ -1054,106 +1018,9 @@ lock_dir_for_write (repository)
node->key = xstrdup (repository);
node->data = xmalloc (sizeof (struct lock));
((struct lock *)node->data)->repository = node->key;
- ((struct lock *)node->data)->lockdirname = CVSLCK;
- ((struct lock *)node->data)->lockdir = NULL;
+ ((struct lock *)node->data)->have_lckdir = 0;
(void) addnode (locked_list, node);
Writer_Lock (locked_list);
}
}
-
-
-
-/* This is the internal implementation behind history_lock & val_tags_lock. It
- * gets a write lock for the history or val-tags file.
- *
- * RETURNS
- * true, on success
- * false, on error
- */
-static int internal_lock PROTO ((struct lock *lock, const char *xrepository));
-static int
-internal_lock (lock, xrepository)
- struct lock *lock;
- const char *xrepository;
-{
- /* remember what we're locking (for Lock_Cleanup) */
- assert (!lock->repository);
- lock->repository = xmalloc (strlen (xrepository) + sizeof (CVSROOTADM) + 2);
- sprintf (lock->repository, "%s/%s", xrepository, CVSROOTADM);
-
- /* get the lock dir for our own */
- if (set_lock (lock, 1) != L_OK)
- {
- if (!really_quiet)
- error (0, 0, "failed to obtain history lock in repository `%s'",
- xrepository);
-
- return 0;
- }
-
- return 1;
-}
-
-
-
-/* This is the internal implementation behind history_lock & val_tags_lock. It
- * removes the write lock for the history or val-tags file, when it exists.
- */
-static void internal_clear_lock PROTO((struct lock *lock));
-static void
-internal_clear_lock (lock)
- struct lock *lock;
-{
- SIG_beginCrSect ();
- if (lock->repository)
- {
- free (lock->repository);
- lock->repository = NULL;
- }
- SIG_endCrSect ();
-
- clear_lock (lock);
-}
-
-
-
-/* Lock the CVSROOT/history file for write.
- */
-int
-history_lock (xrepository)
- const char *xrepository;
-{
- return internal_lock (&global_history_lock, xrepository);
-}
-
-
-
-/* Remove the CVSROOT/history lock, if it exists.
- */
-void
-clear_history_lock ()
-{
- internal_clear_lock (&global_history_lock);
-}
-
-
-
-/* Lock the CVSROOT/val-tags file for write.
- */
-int
-val_tags_lock (xrepository)
- const char *xrepository;
-{
- return internal_lock (&global_val_tags_lock, xrepository);
-}
-
-
-
-/* Remove the CVSROOT/val-tags lock, if it exists.
- */
-void
-clear_val_tags_lock ()
-{
- internal_clear_lock (&global_val_tags_lock);
-}
diff --git a/contrib/cvs/src/log.c b/contrib/cvs/src/log.c
index bb1dbde..f8447ba 100644
--- a/contrib/cvs/src/log.c
+++ b/contrib/cvs/src/log.c
@@ -1,11 +1,6 @@
/*
- * Copyright (C) 1986-2005 The Free Software Foundation, Inc.
- *
- * Portions Copyright (C) 1998-2005 Derek Price, Ximbiot <http://ximbiot.com>,
- * and others.
- *
- * Portions Copyright (C) 1992, Brian Berliner and Jeff Polk
- * Portions Copyright (C) 1989-1992, Brian Berliner
+ * Copyright (c) 1992, Brian Berliner and Jeff Polk
+ * Copyright (c) 1989-1992, Brian Berliner
*
* You may distribute under the terms of the GNU General Public License as
* specified in the README file that comes with the CVS source distribution.
@@ -15,10 +10,11 @@
* Prints the RCS "log" (rlog) information for the specified files. With no
* argument, prints the log information for all the files in the directory
* (recursive by default).
+ *
+ * $FreeBSD$
*/
#include "cvs.h"
-#include <assert.h>
/* This structure holds information parsed from the -r option. */
@@ -129,7 +125,7 @@ static int log_fileproc PROTO ((void *callerdat, struct file_info *finfo));
static struct option_revlist *log_parse_revlist PROTO ((const char *));
static void log_parse_date PROTO ((struct log_data *, const char *));
static void log_parse_list PROTO ((List **, const char *));
-static struct revlist *log_expand_revlist PROTO ((RCSNode *, char *,
+static struct revlist *log_expand_revlist PROTO ((RCSNode *,
struct option_revlist *,
int));
static void log_free_revlist PROTO ((struct revlist *));
@@ -156,14 +152,12 @@ static const char *const log_usage[] =
"Usage: %s %s [-lRhtNb] [-r[revisions]] [-d dates] [-s states]\n",
" [-w[logins]] [files...]\n",
"\t-l\tLocal directory only, no recursion.\n",
- "\t-b\tOnly list revisions on the default branch.\n",
- "\t-h\tOnly print header.\n",
"\t-R\tOnly print name of RCS file.\n",
+ "\t-h\tOnly print header.\n",
"\t-t\tOnly print header and descriptive text.\n",
"\t-N\tDo not list tags.\n",
- "\t-S\tDo not print name/header if no revisions selected. -d, -r,\n",
- "\t\t-s, & -w have little effect in conjunction with -b, -h, -R, and\n",
- "\t\t-t without this option.\n",
+ "\t-S\tDo not print name/header if no revisions selected.\n",
+ "\t-b\tOnly list revisions on the default branch.\n",
"\t-r[revisions]\tA comma-separated list of revisions to print:\n",
"\t rev1:rev2 Between rev1 and rev2, including rev1 and rev2.\n",
"\t rev1::rev2 Between rev1 and rev2, excluding rev1.\n",
@@ -242,7 +236,7 @@ cvslog (argc, argv)
prl = &log_data.revlist;
optind = 0;
- while ((c = getopt (argc, argv, "+bd:hlNSRr::s:tw::")) != -1)
+ while ((c = getopt (argc, argv, "+bd:hlNnSRr::s:tw::")) != -1)
{
switch (c)
{
@@ -261,6 +255,9 @@ cvslog (argc, argv)
case 'N':
log_data.notags = 1;
break;
+ case 'n':
+ log_data.notags = 0;
+ break;
case 'S':
log_data.sup_header = 1;
break;
@@ -316,7 +313,6 @@ cvslog (argc, argv)
{
p = log_data.datelist;
log_data.datelist = p->next;
- assert (p->start != NULL && p->end != NULL);
send_to_server ("Argument -d\012", 0);
send_to_server ("Argument ", 0);
date_to_internet (datetmp, p->start);
@@ -328,21 +324,23 @@ cvslog (argc, argv)
date_to_internet (datetmp, p->end);
send_to_server (datetmp, 0);
send_to_server ("\012", 0);
- free (p->start);
- free (p->end);
+ if (p->start)
+ free (p->start);
+ if (p->end)
+ free (p->end);
free (p);
}
while (log_data.singledatelist != NULL)
{
p = log_data.singledatelist;
log_data.singledatelist = p->next;
- assert (p->end != NULL);
send_to_server ("Argument -d\012", 0);
send_to_server ("Argument ", 0);
date_to_internet (datetmp, p->end);
send_to_server (datetmp, 0);
send_to_server ("\012", 0);
- free (p->end);
+ if (p->end)
+ free (p->end);
free (p);
}
@@ -815,30 +813,21 @@ log_fileproc (callerdat, finfo)
{
struct log_data *log_data = (struct log_data *) callerdat;
Node *p;
- char *baserev;
int selrev = -1;
RCSNode *rcsfile;
char buf[50];
struct revlist *revlist = NULL;
struct log_data_and_rcs log_data_and_rcs;
- rcsfile = finfo->rcs;
- p = findnode (finfo->entries, finfo->file);
- if (p != NULL)
- {
- Entnode *e = p->data;
- baserev = e->version;
- if (baserev[0] == '-') ++baserev;
- }
- else
- baserev = NULL;
-
- if (rcsfile == NULL)
+ if ((rcsfile = finfo->rcs) == NULL)
{
/* no rcs file. What *do* we know about this file? */
- if (baserev != NULL)
+ p = findnode (finfo->entries, finfo->file);
+ if (p != NULL)
{
- if (baserev[0] == '0' && baserev[1] == '\0')
+ Entnode *e = p->data;
+
+ if (e->version[0] == '0' && e->version[1] == '\0')
{
if (!really_quiet)
error (0, 0, "%s has been added, but not committed",
@@ -861,7 +850,7 @@ log_fileproc (callerdat, finfo)
/* Turn any symbolic revisions in the revision list into numeric
revisions. */
- revlist = log_expand_revlist (rcsfile, baserev, log_data->revlist,
+ revlist = log_expand_revlist (rcsfile, log_data->revlist,
log_data->default_branch);
if (log_data->sup_header
|| (!log_data->header && !log_data->long_header))
@@ -1051,9 +1040,8 @@ log_fileproc (callerdat, finfo)
* Expand any symbolic revisions.
*/
static struct revlist *
-log_expand_revlist (rcs, baserev, revlist, default_branch)
+log_expand_revlist (rcs, revlist, default_branch)
RCSNode *rcs;
- char *baserev;
struct option_revlist *revlist;
int default_branch;
{
@@ -1074,26 +1062,13 @@ log_expand_revlist (rcs, baserev, revlist, default_branch)
/* If both first and last are NULL, it means that we want
just the head of the default branch, which is RCS_head. */
nr->first = RCS_head (rcs);
- if (!nr->first)
- {
- if (!really_quiet)
- error (0, 0, "No head revision in archive `%s'.",
- rcs->path);
- nr->last = NULL;
- nr->fields = 0;
- }
- else
- {
- nr->last = xstrdup (nr->first);
- nr->fields = numdots (nr->first) + 1;
- }
+ nr->last = xstrdup (nr->first);
+ nr->fields = numdots (nr->first) + 1;
}
else if (r->branchhead)
{
char *branch;
- assert (r->first != NULL);
-
/* Print just the head of the branch. */
if (isdigit ((unsigned char) r->first[0]))
nr->first = RCS_getbranch (rcs, r->first, 1);
@@ -1108,11 +1083,10 @@ log_expand_revlist (rcs, baserev, revlist, default_branch)
free (branch);
}
}
- if (!nr->first)
+ if (nr->first == NULL && !really_quiet)
{
- if (!really_quiet)
- error (0, 0, "warning: no branch `%s' in `%s'",
- r->first, rcs->path);
+ error (0, 0, "warning: no branch `%s' in `%s'",
+ r->first, rcs->path);
nr->last = NULL;
nr->fields = 0;
}
@@ -1128,9 +1102,7 @@ log_expand_revlist (rcs, baserev, revlist, default_branch)
nr->first = xstrdup (r->first);
else
{
- if (baserev && strcmp (r->first, TAG_BASE) == 0)
- nr->first = xstrdup (baserev);
- else if (RCS_nodeisbranch (rcs, r->first))
+ if (RCS_nodeisbranch (rcs, r->first))
nr->first = RCS_whatbranch (rcs, r->first);
else
nr->first = RCS_gettag (rcs, r->first, 1, (int *) NULL);
@@ -1148,9 +1120,7 @@ log_expand_revlist (rcs, baserev, revlist, default_branch)
nr->last = xstrdup (r->last);
else
{
- if (baserev && strcmp (r->last, TAG_BASE) == 0)
- nr->last = xstrdup (baserev);
- else if (RCS_nodeisbranch (rcs, r->last))
+ if (RCS_nodeisbranch (rcs, r->last))
nr->last = RCS_whatbranch (rcs, r->last);
else
nr->last = RCS_gettag (rcs, r->last, 1, (int *) NULL);
@@ -1176,7 +1146,6 @@ log_expand_revlist (rcs, baserev, revlist, default_branch)
nr->first = xstrdup (nr->last);
cp = strrchr (nr->first, '.');
- assert (cp);
strcpy (cp + 1, "0");
}
}
@@ -1191,7 +1160,6 @@ log_expand_revlist (rcs, baserev, revlist, default_branch)
char *cp;
cp = strrchr (nr->last, '.');
- assert (cp);
*cp = '\0';
}
}
@@ -1291,9 +1259,7 @@ log_expand_revlist (rcs, baserev, revlist, default_branch)
char *cp;
nr->first = xstrdup (rcs->head);
- assert (nr->first);
cp = strrchr (nr->first, '.');
- assert (cp);
*cp = '\0';
}
nr->last = xstrdup (nr->first);
@@ -1644,8 +1610,8 @@ log_version (log_data, revlist, rcs, ver, trunk)
&sec);
if (year < 1900)
year += 1900;
- sprintf (buf, "%04d/%02d/%02d %02d:%02d:%02d", year, mon, mday,
- hour, min, sec);
+ sprintf (buf, "%04d%c%02d%c%02d %02d:%02d:%02d",
+ year, datesep, mon, datesep, mday, hour, min, sec);
cvs_output (buf, 0);
cvs_output ("; author: ", 0);
@@ -1681,7 +1647,6 @@ log_version (log_data, revlist, rcs, ver, trunk)
if (padd != NULL)
{
- assert (pdel);
cvs_output (" lines: +", 0);
cvs_output (padd->data, 0);
cvs_output (" -", 2);
diff --git a/contrib/cvs/src/login.c b/contrib/cvs/src/login.c
index fe95544..86705ea 100644
--- a/contrib/cvs/src/login.c
+++ b/contrib/cvs/src/login.c
@@ -1,15 +1,12 @@
/*
- * Copyright (C) 1986-2005 The Free Software Foundation, Inc.
- *
- * Portions Copyright (C) 1998-2005 Derek Price, Ximbiot <http://ximbiot.com>,
- * and others.
- *
- * Portions Copyright (c) 1995, Cyclic Software, Bloomington, IN, USA
+ * Copyright (c) 1995, Cyclic Software, Bloomington, IN, USA
*
* You may distribute under the terms of the GNU General Public License as
* specified in the README file that comes with CVS.
*
* Allow user to log in for an authenticating server.
+ *
+ * $FreeBSD$
*/
#include "cvs.h"
@@ -387,8 +384,7 @@ process:
/* create and open a temp file */
if ((tmp_fp = cvs_temp_file (&tmp_name)) == NULL)
- error (1, errno, "unable to open temp file %s",
- tmp_name ? tmp_name : "(null)");
+ error (1, errno, "unable to open temp file %s", tmp_name);
line = 0;
while ((line_length = getline (&linebuf, &linebuf_len, fp)) >= 0)
@@ -461,7 +457,7 @@ process:
if (fprintf (fp, "/1 %s %s\n", cvsroot_canonical, newpassword) == EOF)
error (1, errno, "cannot write %s", passfile);
if (fclose (fp) < 0)
- error (1, errno, "cannot close %s", passfile);
+ error (0, errno, "cannot close %s", passfile);
}
/* Utter, total, raving paranoia, I know. */
diff --git a/contrib/cvs/src/logmsg.c b/contrib/cvs/src/logmsg.c
index 5ac4b0e..fbbcc3c 100644
--- a/contrib/cvs/src/logmsg.c
+++ b/contrib/cvs/src/logmsg.c
@@ -1,14 +1,11 @@
/*
- * Copyright (C) 1986-2005 The Free Software Foundation, Inc.
- *
- * Portions Copyright (C) 1998-2005 Derek Price, Ximbiot <http://ximbiot.com>,
- * and others.
- *
- * Portions Copyright (C) 1992, Brian Berliner and Jeff Polk
- * Portions Copyright (C) 1989-1992, Brian Berliner
+ * Copyright (c) 1992, Brian Berliner and Jeff Polk
+ * Copyright (c) 1989-1992, Brian Berliner
*
* You may distribute under the terms of the GNU General Public License as
* specified in the README file that comes with the CVS source distribution.
+ *
+ * $FreeBSD$
*/
#include <assert.h>
@@ -201,7 +198,11 @@ do_editor (dir, messagep, repository, changes)
struct stat pre_stbuf, post_stbuf;
int retcode = 0;
+#ifdef CLIENT_SUPPORT
assert (!current_parsed_root->isremote != !repository);
+#else
+ assert (repository);
+#endif
if (noexec || reuse_log_message)
return;
@@ -227,6 +228,8 @@ do_editor (dir, messagep, repository, changes)
(*messagep)[strlen (*messagep) - 1] != '\n')
(void) fprintf (fp, "\n");
}
+ else
+ (void) fprintf (fp, "\n");
if (repository != NULL)
/* tack templates on if necessary */
@@ -291,7 +294,12 @@ do_editor (dir, messagep, repository, changes)
if (editinfo_editor)
free (editinfo_editor);
editinfo_editor = (char *) NULL;
- if (!current_parsed_root->isremote && repository != NULL)
+#ifdef CLIENT_SUPPORT
+ if (current_parsed_root->isremote)
+ ; /* nothing, leave editinfo_editor NULL */
+ else
+#endif
+ if (repository != NULL)
(void) Parse_Info (CVSROOTADM_EDITINFO, repository, editinfo_proc, 0);
/* run the editor */
@@ -418,9 +426,11 @@ do_verify (messagep, repository)
struct stat pre_stbuf, post_stbuf;
+#ifdef CLIENT_SUPPORT
if (current_parsed_root->isremote)
/* The verification will happen on the server. */
return;
+#endif
/* FIXME? Do we really want to skip this on noexec? What do we do
for the other administrative files? */
@@ -439,8 +449,7 @@ do_verify (messagep, repository)
temp file, and close the file. */
if ((fp = cvs_temp_file (&fname)) == NULL)
- error (1, errno, "cannot create temporary file %s",
- fname ? fname : "(null)");
+ error (1, errno, "cannot create temporary file %s", fname);
if (*messagep != NULL)
fputs (*messagep, fp);
@@ -546,7 +555,7 @@ do_verify (messagep, repository)
if (unlink_file (fname) < 0)
error (0, errno, "cannot remove %s", fname);
free (fname);
- free (verifymsg_script);
+ free( verifymsg_script );
verifymsg_script = NULL;
}
@@ -742,8 +751,6 @@ logfile_write (repository, filter, message, logfp, changes)
char *fmt_percent; /* the location of the percent sign
that starts the format string. */
- assert (repository);
-
/* The user may specify a format string as part of the filter.
Originally, `%s' was the only valid string. The string that
was substituted for it was:
diff --git a/contrib/cvs/src/main.c b/contrib/cvs/src/main.c
index c5911c3..932dbd2 100644
--- a/contrib/cvs/src/main.c
+++ b/contrib/cvs/src/main.c
@@ -1,24 +1,21 @@
/*
- * Copyright (C) 1986-2006 The Free Software Foundation, Inc.
+ * Copyright (c) 1992, Brian Berliner and Jeff Polk
+ * Copyright (c) 1989-1992, Brian Berliner
*
- * Portions Copyright (C) 1998-2006 Derek Price, Ximbiot <http://ximbiot.com>,
- * and others.
- *
- * Portions Copyright (C) 1992, Brian Berliner and Jeff Polk
- * Portions Copyright (C) 1989-1992, Brian Berliner
- *
- * You may distribute under the terms of the GNU General Public License
- * as specified in the README file that comes with the CVS source distribution.
+ * You may distribute under the terms of the GNU General Public License
+ * as specified in the README file that comes with the CVS source distribution.
*
* This is the main C driver for the CVS system.
*
* Credit to Dick Grune, Vrije Universiteit, Amsterdam, for writing
* the shell-script CVS system that this is based on.
*
+ * $FreeBSD$
*/
#include <assert.h>
#include "cvs.h"
+#include "prepend_args.h"
#ifdef HAVE_WINSOCK_H
#include <winsock.h>
@@ -46,14 +43,10 @@ int really_quiet = 0;
int quiet = 0;
int trace = 0;
int noexec = 0;
+int readonlyfs = 0;
+int require_real_user = 0;
int logoff = 0;
-/*
- * Zero if compression isn't supported or requested; non-zero to indicate
- * a compression level to request from gzip.
- */
-int gzip_level;
-
/* Set if we should be writing CVSADM directories at top level. At
least for now we'll make the default be off (the CVS 1.9, not CVS
1.9.2, behavior). */
@@ -74,6 +67,15 @@ char *Editor = EDITOR_DFLT;
values in CVS/Root files, we maintain a list of them. */
List *root_directories = NULL;
+/* We step through the above values. This variable is set to reflect
+ * the currently active value.
+ *
+ * Now static. FIXME - this variable should be removable (well, localizable)
+ * with a little more work.
+ */
+static char *current_root = NULL;
+
+
static const struct cmd
{
char *fullname; /* Full name of the function (e.g. "commit") */
@@ -108,7 +110,7 @@ static const struct cmd
{
{ "add", "ad", "new", add, CVS_CMD_MODIFIES_REPOSITORY | CVS_CMD_USES_WORK_DIR },
{ "admin", "adm", "rcs", admin, CVS_CMD_MODIFIES_REPOSITORY | CVS_CMD_USES_WORK_DIR },
- { "annotate", "ann", NULL, annotate, CVS_CMD_USES_WORK_DIR },
+ { "annotate", "ann", "blame", annotate, CVS_CMD_USES_WORK_DIR },
{ "checkout", "co", "get", checkout, 0 },
{ "commit", "ci", "com", commit, CVS_CMD_MODIFIES_REPOSITORY | CVS_CMD_USES_WORK_DIR },
{ "diff", "di", "dif", diff, CVS_CMD_USES_WORK_DIR },
@@ -189,7 +191,8 @@ static const char *const usg[] =
version control means. */
"For CVS updates and additional information, see\n",
- " the CVS home page at http://cvs.nongnu.org/\n",
+ " the CVS home page at http://www.cvshome.org/ or\n",
+ " Pascal Molli's CVS site at http://www.loria.fr/~molli/cvs-index.html\n",
NULL,
};
@@ -248,8 +251,10 @@ static const char *const opt_usage[] =
" -q Cause CVS to be somewhat quiet.\n",
" -r Make checked-out files read-only.\n",
" -w Make checked-out files read-write (default).\n",
+ " -g Force group-write perms on checked-out files.\n",
" -n Do not execute anything that will change the disk.\n",
" -t Show trace of program execution -- try with -n.\n",
+ " -R Assume repository is read-only, such as CDROM\n",
" -v CVS version and copyright.\n",
" -T tmpdir Use 'tmpdir' for temporary files.\n",
" -e editor Use 'editor' for editing log information.\n",
@@ -273,9 +278,9 @@ set_root_directory (p, ignored)
Node *p;
void *ignored;
{
- if (current_parsed_root == NULL && p->data != NULL)
+ if (current_root == NULL && p->data == NULL)
{
- current_parsed_root = p->data;
+ current_root = p->key;
return 1;
}
return 0;
@@ -395,19 +400,19 @@ main (argc, argv)
int argc;
char **argv;
{
- cvsroot_t *CVSroot_parsed = NULL;
- int cvsroot_update_env = 1;
+ char *CVSroot = CVSROOT_DFLT;
char *cp, *end;
const struct cmd *cm;
int c, err = 0;
- int tmpdir_update_env;
+ int tmpdir_update_env, cvs_update_env;
+ int free_CVSroot = 0;
int free_Editor = 0;
int free_Tmpdir = 0;
int help = 0; /* Has the user asked for help? This
lets us support the `cvs -H cmd'
convention to give help for cmd. */
- static const char short_options[] = "+Qqrwtnvb:T:e:d:Hfz:s:xa";
+ static const char short_options[] = "+QqgrwtnRvb:T:e:d:Hfz:s:xaU";
static struct option long_options[] =
{
{"help", 0, NULL, 'H'},
@@ -450,6 +455,7 @@ main (argc, argv)
* Query the environment variables up-front, so that
* they can be overridden by command line arguments
*/
+ cvs_update_env = 0;
tmpdir_update_env = *Tmpdir; /* TMPDIR_DFLT must be set */
if ((cp = getenv (TMPDIR_ENV)) != NULL)
{
@@ -462,8 +468,19 @@ main (argc, argv)
Editor = cp;
else if ((cp = getenv (EDITOR3_ENV)) != NULL)
Editor = cp;
+ if ((cp = getenv (CVSROOT_ENV)) != NULL)
+ {
+ CVSroot = cp;
+ cvs_update_env = 0; /* it's already there */
+ }
if (getenv (CVSREAD_ENV) != NULL)
cvswrite = 0;
+ if (getenv (CVSREADONLYFS_ENV) != NULL) {
+ readonlyfs = 1;
+ logoff = 1;
+ }
+
+ prepend_default_options (getenv ("CVS_OPTIONS"), &argc, &argv);
/* Set this to 0 to force getopt initialization. getopt() sets
this to 1 internally. */
@@ -526,9 +543,20 @@ main (argc, argv)
case 'w':
cvswrite = 1;
break;
+ case 'g':
+ /*
+ * force full group write perms (used for shared checked-out
+ * source trees, see manual page)
+ */
+ umask(umask(077) & 007);
+ break;
case 't':
trace = 1;
break;
+ case 'R':
+ readonlyfs = 1;
+ logoff = 1;
+ break;
case 'n':
noexec = 1;
logoff = 1;
@@ -538,12 +566,8 @@ main (argc, argv)
version (0, (char **) NULL);
(void) fputs ("\n", stdout);
(void) fputs ("\
-Copyright (C) 2006 Free Software Foundation, Inc.\n\
-\n\
-Senior active maintainers include Larry Jones, Derek R. Price,\n\
-and Mark D. Baushke. Please see the AUTHORS and README files from the CVS\n\
-distribution kit for a complete list of contributors and copyrights.\n",
- stdout);
+Copyright (c) 1989-2004 Brian Berliner, david d `zoo' zuhn, \n\
+ Jeff Polk, and other authors\n", stdout);
(void) fputs ("\n", stdout);
(void) fputs ("CVS may be copied only under the terms of the GNU General Public License,\n", stdout);
(void) fputs ("a copy of which can be found with the CVS distribution kit.\n", stdout);
@@ -551,12 +575,6 @@ distribution kit for a complete list of contributors and copyrights.\n",
(void) fputs ("Specify the --help option for further information about CVS\n", stdout);
-#ifdef SYSTEM_CLEANUP
- /* Hook for OS-specific behavior, for example socket subsystems
- * on NT and OS2 or dealing with windows and arguments on Mac.
- */
- SYSTEM_CLEANUP ();
-#endif
exit (0);
break;
case 'b':
@@ -567,13 +585,11 @@ distribution kit for a complete list of contributors and copyrights.\n",
either new or old CVS. */
break;
case 'T':
- if (free_Tmpdir) free (Tmpdir);
Tmpdir = xstrdup (optarg);
free_Tmpdir = 1;
tmpdir_update_env = 1; /* need to update environment */
break;
case 'e':
- if (free_Editor) free (Editor);
Editor = xstrdup (optarg);
free_Editor = 1;
break;
@@ -581,6 +597,11 @@ distribution kit for a complete list of contributors and copyrights.\n",
if (CVSroot_cmdline != NULL)
free (CVSroot_cmdline);
CVSroot_cmdline = xstrdup (optarg);
+ if (free_CVSroot)
+ free (CVSroot);
+ CVSroot = xstrdup (optarg);
+ free_CVSroot = 1;
+ cvs_update_env = 1; /* need to update environment */
break;
case 'H':
help = 1;
@@ -589,10 +610,12 @@ distribution kit for a complete list of contributors and copyrights.\n",
use_cvsrc = 0; /* unnecessary, since we've done it above */
break;
case 'z':
+#ifdef CLIENT_SUPPORT
gzip_level = strtol (optarg, &end, 10);
if (*end != '\0' || gzip_level < 0 || gzip_level > 9)
error (1, 0,
"gzip compression level must be between 0 and 9");
+#endif /* CLIENT_SUPPORT */
/* If no CLIENT_SUPPORT, we just silently ignore the gzip
* level, so that users can have it in their .cvsrc and not
* cause any trouble.
@@ -623,6 +646,11 @@ distribution kit for a complete list of contributors and copyrights.\n",
We will issue an error later if stream
authentication is not supported. */
break;
+ case 'U':
+#ifdef SERVER_SUPPORT
+ require_real_user = 1;
+#endif
+ break;
case '?':
default:
usage (usg);
@@ -716,18 +744,21 @@ distribution kit for a complete list of contributors and copyrights.\n",
cvs_cmd_name = "server";
}
# endif /* AUTH_SERVER_SUPPORT || HAVE_GSSAPI */
-#endif /* SERVER_SUPPORT */
server_active = strcmp (cvs_cmd_name, "server") == 0;
+#endif /* SERVER_SUPPORT */
+
/* This is only used for writing into the history file. For
remote connections, it might be nice to have hostname
and/or remote path, on the other hand I'm not sure whether
it is worth the trouble. */
+#ifdef SERVER_SUPPORT
if (server_active)
CurDir = xstrdup ("<remote>");
else
+#endif
{
CurDir = xgetwd ();
if (CurDir == NULL)
@@ -735,10 +766,7 @@ distribution kit for a complete list of contributors and copyrights.\n",
}
if (Tmpdir == NULL || Tmpdir[0] == '\0')
- {
- if (free_Tmpdir) free (Tmpdir);
Tmpdir = "/tmp";
- }
#ifdef HAVE_PUTENV
if (tmpdir_update_env)
@@ -749,6 +777,12 @@ distribution kit for a complete list of contributors and copyrights.\n",
(void) putenv (env);
/* do not free env, as putenv has control of it */
}
+ {
+ char *env;
+ env = xmalloc (sizeof "CVS_PID=" + 32); /* XXX pid < 10^32 */
+ (void) sprintf (env, "CVS_PID=%ld", (long) getpid ());
+ (void) putenv (env);
+ }
#endif
#ifndef DONT_USE_SIGNALS
@@ -786,66 +820,68 @@ distribution kit for a complete list of contributors and copyrights.\n",
if (use_cvsrc)
read_cvsrc (&argc, &argv, cvs_cmd_name);
+#ifdef SERVER_SUPPORT
/* Fiddling with CVSROOT doesn't make sense if we're running
- * in server mode, since the client will send the repository
- * directory after the connection is made.
- */
+ in server mode, since the client will send the repository
+ directory after the connection is made. */
+
if (!server_active)
+#endif
{
- /* First check if a root was set via the command line. */
- if (CVSroot_cmdline)
- {
- if (!(CVSroot_parsed = parse_cvsroot (CVSroot_cmdline)))
- error (1, 0, "Bad CVSROOT: `%s'.", CVSroot_cmdline);
- }
-
+ char *CVSADM_Root;
+
/* See if we are able to find a 'better' value for CVSroot
- * in the CVSADM_ROOT directory.
- *
- * "cvs import" shouldn't check CVS/Root; in general it
- * ignores CVS directories and CVS/Root is likely to
- * specify a different repository than the one we are
- * importing to, but if this is not import and no root was
- * specified on the command line, set the root from the
- * CVS/Root file.
- */
- if (!CVSroot_parsed
- && !(cm->attr & CVS_CMD_IGNORE_ADMROOT)
- )
- CVSroot_parsed = Name_Root (NULL, NULL);
+ in the CVSADM_ROOT directory. */
- /* Now, if there is no root on the command line and we didn't find
- * one in a file, set it via the $CVSROOT env var.
- */
- if (!CVSroot_parsed)
+ CVSADM_Root = NULL;
+
+ /* "cvs import" shouldn't check CVS/Root; in general it
+ ignores CVS directories and CVS/Root is likely to
+ specify a different repository than the one we are
+ importing to. */
+
+ if (!(cm->attr & CVS_CMD_IGNORE_ADMROOT)
+
+ /* -d overrides CVS/Root, so don't give an error if the
+ latter points to a nonexistent repository. */
+ && CVSroot_cmdline == NULL)
{
- char *tmp = getenv (CVSROOT_ENV);
- if (tmp)
- {
- if (!(CVSroot_parsed = parse_cvsroot (tmp)))
- error (1, 0, "Bad CVSROOT: `%s'.", tmp);
- cvsroot_update_env = 0;
- }
+ CVSADM_Root = Name_Root((char *) NULL, (char *) NULL);
}
-#ifdef CVSROOT_DFLT
- if (!CVSroot_parsed)
+ if (CVSADM_Root != NULL)
{
- if (!(CVSroot_parsed = parse_cvsroot (CVSROOT_DFLT)))
- error (1, 0, "Bad CVSROOT: `%s'.", CVSROOT_DFLT);
+ if (CVSroot == NULL || !cvs_update_env)
+ {
+ CVSroot = CVSADM_Root;
+ cvs_update_env = 1; /* need to update environment */
+ }
}
-#endif /* CVSROOT_DFLT */
/* Now we've reconciled CVSROOT from the command line, the
CVS/Root file, and the environment variable. Do the
last sanity checks on the variable. */
- if (!CVSroot_parsed)
+
+ if (! CVSroot)
{
error (0, 0,
"No CVSROOT specified! Please use the `-d' option");
error (1, 0,
"or set the %s environment variable.", CVSROOT_ENV);
}
+
+ if (! *CVSroot)
+ {
+ error (0, 0,
+ "CVSROOT is set but empty! Make sure that the");
+ error (0, 0,
+ "specification of CVSROOT is valid, either via the");
+ error (0, 0,
+ "`-d' option, the %s environment variable, or the",
+ CVSROOT_ENV);
+ error (1, 0,
+ "CVS/Root file (if any).");
+ }
}
/* Here begins the big loop over unique cvsroot values. We
@@ -857,19 +893,19 @@ distribution kit for a complete list of contributors and copyrights.\n",
root_directories = getlist ();
/* Prime it. */
- if (CVSroot_parsed)
+ if (CVSroot != NULL)
{
Node *n;
n = getnode ();
n->type = NT_UNKNOWN;
- n->key = xstrdup (CVSroot_parsed->original);
- n->data = CVSroot_parsed;
+ n->key = xstrdup (CVSroot);
+ n->data = NULL;
if (addnode (root_directories, n))
error (1, 0, "cannot add initial CVSROOT %s", n->key);
}
- assert (current_parsed_root == NULL);
+ assert (current_root == NULL);
/* If we're running the server, we want to execute this main
loop once and only once (we won't be serving multiple roots
@@ -877,58 +913,70 @@ distribution kit for a complete list of contributors and copyrights.\n",
once). To get out of the loop, we perform a "break" at the
end of things. */
- while (server_active ||
- walklist (root_directories, set_root_directory, NULL))
+ while (
+#ifdef SERVER_SUPPORT
+ server_active ||
+#endif
+ walklist (root_directories, set_root_directory, NULL)
+ )
{
+#ifdef SERVER_SUPPORT
/* Fiddling with CVSROOT doesn't make sense if we're running
in server mode, since the client will send the repository
directory after the connection is made. */
if (!server_active)
+#endif
{
/* Now we're 100% sure that we have a valid CVSROOT
variable. Parse it to see if we're supposed to do
remote accesses or use a special access method. */
+ if (current_parsed_root != NULL)
+ free_cvsroot_t (current_parsed_root);
+ if ((current_parsed_root = parse_cvsroot (current_root)) == NULL)
+ error (1, 0, "Bad CVSROOT: `%s'.", current_root);
+
if (trace)
fprintf (stderr, "%s-> main loop with CVSROOT=%s\n",
- CLIENT_SERVER_STR, current_parsed_root->original);
+ CLIENT_SERVER_STR, current_root);
/*
* Check to see if the repository exists.
*/
+#ifdef CLIENT_SUPPORT
if (!current_parsed_root->isremote)
+#endif /* CLIENT_SUPPORT */
{
char *path;
int save_errno;
path = xmalloc (strlen (current_parsed_root->directory)
- + strlen (CVSROOTADM) + 2);
- sprintf (path, "%s/%s", current_parsed_root->directory,
- CVSROOTADM);
+ + sizeof (CVSROOTADM)
+ + 2);
+ (void) sprintf (path, "%s/%s", current_parsed_root->directory, CVSROOTADM);
if (!isaccessible (path, R_OK | X_OK))
{
save_errno = errno;
- /* If this is "cvs init", the root need not exist yet.
- */
- if (strcmp (cvs_cmd_name, "init"))
+ /* If this is "cvs init", the root need not exist yet. */
+ if (strcmp (cvs_cmd_name, "init") != 0)
+ {
error (1, save_errno, "%s", path);
}
+ }
free (path);
}
#ifdef HAVE_PUTENV
- /* Update the CVSROOT environment variable. */
- if (cvsroot_update_env)
+ /* Update the CVSROOT environment variable if necessary. */
+ /* FIXME (njc): should we always set this with the CVSROOT from the command line? */
+ if (cvs_update_env)
{
static char *prev;
char *env;
-
- env = xmalloc (strlen (CVSROOT_ENV)
- + strlen (current_parsed_root->original)
- + 2);
- sprintf (env, "%s=%s", CVSROOT_ENV,
- current_parsed_root->original);
+ env = xmalloc (strlen (CVSROOT_ENV) + strlen (CVSroot)
+ + 1 + 1);
+ (void) sprintf (env, "%s=%s", CVSROOT_ENV, CVSroot);
(void) putenv (env);
/* do not free env yet, as putenv has control of it */
/* but do free the previous value, if any */
@@ -946,13 +994,23 @@ distribution kit for a complete list of contributors and copyrights.\n",
predetermine whether CVSROOT/config overrides things from
read_cvsrc and other such places or vice versa. That sort
of thing probably needs more thought. */
- if (!server_active && !current_parsed_root->isremote)
+ if (1
+#ifdef SERVER_SUPPORT
+ && !server_active
+#endif
+#ifdef CLIENT_SUPPORT
+ && !current_parsed_root->isremote
+#endif
+ )
{
/* If there was an error parsing the config file, parse_config
already printed an error. We keep going. Why? Because
if we didn't, then there would be no way to check in a new
CVSROOT/config file to fix the broken one! */
parse_config (current_parsed_root->directory);
+
+ /* Now is a convenient time to read CVSROOT/options */
+ parseopts(current_parsed_root->directory);
}
#ifdef CLIENT_SUPPORT
@@ -973,28 +1031,31 @@ distribution kit for a complete list of contributors and copyrights.\n",
err = (*(cm->func)) (argc, argv);
/* Mark this root directory as done. When the server is
- active, our list will be empty -- don't try and
+ active, current_root will be NULL -- don't try and
remove it from the list. */
- if (!server_active)
+ if (current_root != NULL)
{
- Node *n = findnode (root_directories,
- current_parsed_root->original);
+ Node *n = findnode (root_directories, current_root);
assert (n != NULL);
- assert (n->data != NULL);
- free_cvsroot_t (n->data);
- n->data = NULL;
- current_parsed_root = NULL;
+ n->data = (void *) 1;
+ current_root = NULL;
}
+
+#if 0
+ /* This will not work yet, since it tries to free (void *) 1. */
+ dellist (&root_directories);
+#endif
+#ifdef SERVER_SUPPORT
if (server_active)
{
server_active = 0;
break;
}
+#endif
} /* end of loop for cvsroot values */
- dellist (&root_directories);
} /* end of stuff that gets done if the user DOESN'T ask for help */
Lock_Cleanup ();
@@ -1006,6 +1067,8 @@ distribution kit for a complete list of contributors and copyrights.\n",
free ((char *)program_path);
if (CVSroot_cmdline != NULL)
free (CVSroot_cmdline);
+ if (free_CVSroot)
+ free (CVSroot);
if (free_Editor)
free (Editor);
if (free_Tmpdir)
@@ -1140,3 +1203,64 @@ usage (cpp)
(void) fprintf (stderr, *cpp);
error_exit ();
}
+
+void
+parseopts(root)
+ const char *root;
+{
+ char path[PATH_MAX];
+ int save_errno;
+ char buf[1024];
+ const char *p;
+ char *q;
+ FILE *fp;
+
+ if (root == NULL) {
+ printf("no CVSROOT in parseopts\n");
+ return;
+ }
+ p = strchr (root, ':');
+ if (p)
+ p++;
+ else
+ p = root;
+ if (p == NULL) {
+ printf("mangled CVSROOT in parseopts\n");
+ return;
+ }
+ (void) sprintf (path, "%s/%s/%s", p, CVSROOTADM, CVSROOTADM_OPTIONS);
+ if ((fp = fopen(path, "r")) != NULL) {
+ while (fgets(buf, sizeof buf, fp) != NULL) {
+ if (buf[0] == '#')
+ continue;
+ q = strrchr(buf, '\n');
+ if (q)
+ *q = '\0';
+
+ if (!strcmp(buf, "iso8601")) {
+ datesep = '-';
+ }
+ if (!strncmp(buf, "tag=", 4)) {
+ char *what;
+ char *rcs_localid;
+
+ rcs_localid = buf + 4;
+ RCS_setlocalid(rcs_localid);
+ }
+ if (!strncmp(buf, "tagexpand=", 10)) {
+ char *what;
+ char *rcs_incexc;
+
+ rcs_incexc = buf + 10;
+ RCS_setincexc(rcs_incexc);
+ }
+ /*
+ * OpenBSD has a "umask=" and "dlimit=" command, we silently
+ * ignore them here since they are not much use to us. cvsumask
+ * defaults to 002 already, and the dlimit (data size limit)
+ * should really be handled elsewhere (eg: login.conf).
+ */
+ }
+ fclose(fp);
+ }
+}
diff --git a/contrib/cvs/src/mkmodules.c b/contrib/cvs/src/mkmodules.c
index 3ac06b3..0c91387 100644
--- a/contrib/cvs/src/mkmodules.c
+++ b/contrib/cvs/src/mkmodules.c
@@ -1,14 +1,12 @@
/*
- * Copyright (C) 1986-2005 The Free Software Foundation, Inc.
- *
- * Portions Copyright (C) 1998-2005 Derek Price, Ximbiot <http://ximbiot.com>,
- * and others.
- *
- * Portions Copyright (C) 1992, Brian Berliner and Jeff Polk
- * Portions Copyright (C) 1989-1992, Brian Berliner
+ * Copyright (c) 1992, Brian Berliner and Jeff Polk
+ * Copyright (c) 1989-1992, Brian Berliner
*
* You may distribute under the terms of the GNU General Public License as
- * specified in the README file that comes with the CVS kit. */
+ * specified in the README file that comes with the CVS kit.
+ *
+ * $FreeBSD$
+ */
#include "cvs.h"
#include "getline.h"
@@ -286,7 +284,7 @@ static const char *const modules_contents[] = {
static const char *const config_contents[] = {
"# Set this to \"no\" if pserver shouldn't check system users/passwords\n",
- "#SystemAuth=yes\n",
+ "#SystemAuth=no\n",
"\n",
"# Put CVS lock files in this directory rather than directly in the repository.\n",
"#LockDir=/var/lock/cvs\n",
@@ -307,7 +305,7 @@ static const char *const config_contents[] = {
"#LogHistory=" ALL_HISTORY_REC_TYPES "\n",
"\n",
"# Set `RereadLogAfterVerify' to `always' (the default) to allow the verifymsg\n",
- "# script to change the log message. Set it to `stat' to force CVS to verify\n",
+ "# script to change the log message. Set it to `stat' to force CVS to verify",
"# that the file has changed before reading it (this can take up to an extra\n",
"# second per directory being committed, so it is not recommended for large\n",
"# repositories. Set it to `never' (the previous CVS behavior) to prevent\n",
@@ -581,17 +579,7 @@ checkout_file (file, temp)
free (rcs);
return (1);
}
-
rcsnode = RCS_parsercsfile (rcs);
- if (!rcsnode)
- {
- /* Probably not necessary (?); RCS_parsercsfile already printed a
- message. */
- error (0, 0, "Failed to parse `%s'.", rcs);
- free (rcs);
- return 1;
- }
-
retcode = RCS_checkout (rcsnode, NULL, NULL, NULL, NULL, temp,
(RCSCHECKOUTPROC) NULL, (void *) NULL);
if (retcode != 0)
diff --git a/contrib/cvs/src/options.h.in b/contrib/cvs/src/options.h.in
deleted file mode 100644
index a3ee047..0000000
--- a/contrib/cvs/src/options.h.in
+++ /dev/null
@@ -1,200 +0,0 @@
-/*
- * Copyright (c) 1992, Brian Berliner and Jeff Polk
- * Copyright (c) 1989-1992, Brian Berliner
- *
- * You may distribute under the terms of the GNU General Public License as
- * specified in the README file that comes with the CVS source distribution.
- *
- * This file holds (most of) the configuration tweaks that can be made to
- * customize CVS for your site. CVS comes configured for a typical SunOS 4.x
- * environment. The comments for each configurable item are intended to be
- * self-explanatory. All #defines are tested first to see if an over-riding
- * option was specified on the "make" command line.
- *
- * If special libraries are needed, you will have to edit the Makefile.in file
- * or the configure script directly. Sorry.
- */
-
-/* By default, CVS stores its modules and other such items in flat
- text files (MY_NDBM enables this). Turning off MY_NDBM causes CVS
- to look for a system-supplied ndbm database library and use it
- instead. That may speed things up, but the default setting
- generally works fine too. */
-
-#ifndef MY_NDBM
-#define MY_NDBM
-#endif
-
-/*
- * The "patch" program to run when using the CVS server and accepting
- * patches across the network. Specify a full pathname if your site
- * wants to use a particular patch.
- */
-#ifndef PATCH_PROGRAM
-#define PATCH_PROGRAM "patch"
-#endif
-
-/* Directory used for storing temporary files, if not overridden by
- environment variables or the -T global option. There should be little
- need to change this (-T is a better mechanism if you need to use a
- different directory for temporary files). */
-#ifndef TMPDIR_DFLT
-#define TMPDIR_DFLT "/tmp"
-#endif
-
-/*
- * The default editor to use, if one does not specify the "-e" option
- * to cvs, or does not have an EDITOR environment variable. I set
- * this to just "vi", and use the shell to find where "vi" actually
- * is. This allows sites with /usr/bin/vi or /usr/ucb/vi to work
- * equally well (assuming that your PATH is reasonable).
- */
-#ifndef EDITOR_DFLT
-#define EDITOR_DFLT "vi"
-#endif
-
-/*
- * The default umask to use when creating or otherwise setting file or
- * directory permissions in the repository. Must be a value in the
- * range of 0 through 0777. For example, a value of 002 allows group
- * rwx access and world rx access; a value of 007 allows group rwx
- * access but no world access. This value is overridden by the value
- * of the CVSUMASK environment variable, which is interpreted as an
- * octal number.
- */
-#ifndef UMASK_DFLT
-#define UMASK_DFLT 002
-#endif
-
-/*
- * The cvs admin command is restricted to the members of the group
- * CVS_ADMIN_GROUP. If this group does not exist, all users are
- * allowed to run cvs admin. To disable the cvs admin for all users,
- * create an empty group CVS_ADMIN_GROUP. To disable access control
- * for cvs admin, comment out the define below.
- */
-#ifndef CVS_ADMIN_GROUP
-#define CVS_ADMIN_GROUP "cvsadmin"
-#endif
-
-/*
- * The Repository file holds the path to the directory within the
- * source repository that contains the RCS ,v files for each CVS
- * working directory. This path is either a full-path or a path
- * relative to CVSROOT.
- *
- * The big advantage that I can see to having a relative path is that
- * one can change the physical location of the master source
- * repository, change the contents of CVS/Root files in your
- * checked-out code, and CVS will work without problems.
- *
- * Therefore, RELATIVE_REPOS is now the default. In the future, this
- * is likely to disappear entirely as a compile-time (or other) option,
- * so if you have other software which relies on absolute pathnames,
- * update them.
- */
-#define RELATIVE_REPOS 1
-
-/*
- * When committing or importing files, you must enter a log message.
- * Normally, you can do this either via the -m flag on the command
- * line or an editor will be started for you. If you like to use
- * logging templates (the rcsinfo file within the $CVSROOT/CVSROOT
- * directory), you might want to force people to use the editor even
- * if they specify a message with -m. Enabling FORCE_USE_EDITOR will
- * cause the -m message to be appended to the temp file when the
- * editor is started.
- */
-#ifndef FORCE_USE_EDITOR
-/* #define FORCE_USE_EDITOR */
-#endif
-
-/*
- * When locking the repository, some sites like to remove locks and
- * assume the program that created them went away if the lock has
- * existed for a long time. This used to be the default for previous
- * versions of CVS. CVS now attempts to be much more robust, so lock
- * files should not be left around by mistake. The new behaviour will
- * never remove old locks (they must now be removed by hand).
- * Enabling CVS_FUDGELOCKS will cause CVS to remove locks that are
- * older than CVSLCKAGE seconds.
- *
- * Use of this option is NOT recommended.
- */
-#ifndef CVS_FUDGELOCKS
-/* #define CVS_FUDGELOCKS */
-#endif
-
-/*
- * When committing a permanent change, CVS and RCS make a log entry of
- * who committed the change. If you are committing the change logged
- * in as "root" (not under "su" or other root-priv giving program),
- * CVS/RCS cannot determine who is actually making the change.
- *
- * As such, by default, CVS disallows changes to be committed by users
- * logged in as "root". You can disable this option by commenting out
- * the lines below.
- */
-#ifndef CVS_BADROOT
-#define CVS_BADROOT
-#endif
-
-/* Define this to enable the SETXID support. The way to use this is
- to create a group with no users in it (except perhaps cvs
- administrators), set the cvs executable to setgid that group, chown
- all the repository files to that group, and change all directory
- permissions in the repository to 770. The last person to modify a
- file will own it, but as long as directory permissions are set
- right that won't matter. You'll need a system which inherits file
- groups from the parent directory (WARNING: using the wrong kind of
- system (I think Solaris 2.4 is the wrong kind, for example) will
- create a security hole! You will receive no warning other than the
- fact that files in the working directory are owned by the group
- which cvs is setgid to).
-
- One security hole which has been reported is that setgid is not
- turned off when the editor is invoked--most editors provide a way
- to execute a shell, or the user can specify an editor (this one is
- large enough to drive a truck through). Don't assume that the
- holes described here are the only ones; I don't know how carefully
- SETXID has been inspected for security holes. */
-#ifndef SETXID_SUPPORT
-/* #define SETXID_SUPPORT */
-#endif
-
-/*
- * Should we build the password-authenticating client? Whether to
- * include the password-authenticating _server_, on the other hand, is
- * set in config.h.
- */
-#ifdef CLIENT_SUPPORT
-#define AUTH_CLIENT_SUPPORT 1
-#endif
-
-/*
- * If you are working with a large remote repository and a 'cvs
- * checkout' is swamping your network and memory, define these to
- * enable flow control. You will end up with even less probability of
- * a consistent checkout (see Concurrency in cvs.texinfo), but CVS
- * doesn't try to guarantee that anyway. The master server process
- * will monitor how far it is getting behind, if it reaches the high
- * water mark, it will signal the child process to stop generating
- * data when convenient (ie: no locks are held, currently at the
- * beginning of a new directory). Once the buffer has drained
- * sufficiently to reach the low water mark, it will be signalled to
- * start again. You may override the default hi/low watermarks here
- * too.
- */
-#define SERVER_FLOWCONTROL
-#define SERVER_HI_WATER (2 * 1024 * 1024)
-#define SERVER_LO_WATER (1 * 1024 * 1024)
-
-/* End of CVS configuration section */
-
-/*
- * Externs that are included in libc, but are used frequently enough
- * to warrant defining here.
- */
-#ifndef STDC_HEADERS
-extern void exit ();
-#endif
diff --git a/contrib/cvs/src/parseinfo.c b/contrib/cvs/src/parseinfo.c
index 0fe9c33..5e34add 100644
--- a/contrib/cvs/src/parseinfo.c
+++ b/contrib/cvs/src/parseinfo.c
@@ -1,20 +1,16 @@
/*
- * Copyright (C) 1986-2005 The Free Software Foundation, Inc.
- *
- * Portions Copyright (C) 1998-2005 Derek Price, Ximbiot <http://ximbiot.com>,
- * and others.
- *
- * Portions Copyright (C) 1992, Brian Berliner and Jeff Polk
- * Portions Copyright (C) 1989-1992, Brian Berliner
+ * Copyright (c) 1992, Brian Berliner and Jeff Polk
+ * Copyright (c) 1989-1992, Brian Berliner
*
* You may distribute under the terms of the GNU General Public License as
* specified in the README file that comes with the CVS source distribution.
+ *
+ * $FreeBSD$
*/
#include "cvs.h"
#include "getline.h"
#include <assert.h>
-#include "history.h"
extern char *logHistory;
@@ -46,8 +42,6 @@ Parse_Info (infofile, repository, callproc, all)
const char *srepos;
const char *regex_err;
- assert (repository);
-
if (current_parsed_root == NULL)
{
/* XXX - should be error maybe? */
@@ -278,7 +272,8 @@ parse_config (cvsroot)
value, currently at least. */
error (0, errno, "cannot open %s", infopath);
}
- goto set_defaults_and_return;
+ free (infopath);
+ return 0;
}
while (getline (&line, &line_allocated, fp_info) >= 0)
@@ -357,6 +352,25 @@ parse_config (cvsroot)
goto error_return;
}
}
+ else if (strcmp (line, "tag") == 0) {
+ RCS_setlocalid(p);
+ }
+ else if (strcmp (line, "umask") == 0) {
+ cvsumask = (mode_t)(strtol(p, NULL, 8) & 0777);
+ }
+ else if (strcmp (line, "dlimit") == 0) {
+#ifdef BSD
+#include <sys/resource.h>
+ struct rlimit rl;
+
+ if (getrlimit(RLIMIT_DATA, &rl) != -1) {
+ rl.rlim_cur = atoi(p);
+ rl.rlim_cur *= 1024;
+
+ (void) setrlimit(RLIMIT_DATA, &rl);
+ }
+#endif /* BSD */
+ }
else if (strcmp (line, "PreservePermissions") == 0)
{
if (strcmp (p, "no") == 0)
@@ -402,8 +416,8 @@ warning: this CVS does not support PreservePermissions");
{
if (strcmp (p, "all") != 0)
{
- if (logHistory) free (logHistory);
- logHistory = xstrdup (p);
+ logHistory=xmalloc(strlen (p) + 1);
+ strcpy (logHistory, p);
}
}
else if (strcmp (line, "RereadLogAfterVerify") == 0)
@@ -415,6 +429,16 @@ warning: this CVS does not support PreservePermissions");
else if (strcmp (p, "stat") == 0)
RereadLogAfterVerify = LOGMSG_REREAD_STAT;
}
+ else if (strcmp(line, "LocalKeyword") == 0)
+ {
+ /* Recognize cvs-1.12-style keyword control rather than erroring out. */
+ RCS_setlocalid(p);
+ }
+ else if (strcmp(line, "KeywordExpand") == 0)
+ {
+ /* Recognize cvs-1.12-style keyword control rather than erroring out. */
+ RCS_setincexc(p);
+ }
else
{
/* We may be dealing with a keyword which was added in a
@@ -443,17 +467,12 @@ warning: this CVS does not support PreservePermissions");
error (0, errno, "cannot close %s", infopath);
goto error_return;
}
-set_defaults_and_return:
- if (!logHistory)
- logHistory = xstrdup (ALL_HISTORY_REC_TYPES);
free (infopath);
if (line != NULL)
free (line);
return 0;
error_return:
- if (!logHistory)
- logHistory = xstrdup (ALL_HISTORY_REC_TYPES);
if (infopath != NULL)
free (infopath);
if (line != NULL)
diff --git a/contrib/cvs/src/patch.c b/contrib/cvs/src/patch.c
index 9af10a6..7d99f29 100644
--- a/contrib/cvs/src/patch.c
+++ b/contrib/cvs/src/patch.c
@@ -1,11 +1,6 @@
/*
- * Copyright (C) 1986-2005 The Free Software Foundation, Inc.
- *
- * Portions Copyright (C) 1998-2005 Derek Price, Ximbiot <http://ximbiot.com>,
- * and others.
- *
- * Portions Copyright (C) 1992, Brian Berliner and Jeff Polk
- * Portions Copyright (C) 1989-1992, Brian Berliner
+ * Copyright (c) 1992, Brian Berliner and Jeff Polk
+ * Copyright (c) 1989-1992, Brian Berliner
*
* You may distribute under the terms of the GNU General Public License as
* specified in the README file that comes with the CVS source distribution.
@@ -15,6 +10,8 @@
* Create a Larry Wall format "patch" file between a previous release and the
* current head of a module, or between two releases. Can specify the
* release as either a date or a revision number.
+ *
+ * $FreeBSD$
*/
#include <assert.h>
@@ -47,7 +44,7 @@ static int unidiff = 0;
static const char *const patch_usage[] =
{
- "Usage: %s %s [-flR] [-c|-u] [-s|-t] [-V %%d] [-k kopt]\n",
+ "Usage: %s %s [-flR] [-c|-u] [-s|-t] [-V %%d]\n",
" -r rev|-D date [-r rev2 | -D date2] modules...\n",
"\t-f\tForce a head revision match if tag/date not found.\n",
"\t-l\tLocal directory only, not recursive\n",
@@ -56,10 +53,9 @@ static const char *const patch_usage[] =
"\t-u\tUnidiff format.\n",
"\t-s\tShort patch - one liner per file.\n",
"\t-t\tTop two diffs - last change made to the file.\n",
- "\t-V vers\tUse RCS Version \"vers\" for keyword expansion.\n",
- "\t-k kopt\tSpecify keyword expansion mode.\n",
"\t-D date\tDate.\n",
"\t-r rev\tRevision - symbolic or numeric.\n",
+ "\t-V vers\tUse RCS Version \"vers\" for keyword expansion.\n",
"(Specify the --help global option for a list of other help options)\n",
NULL
};
@@ -87,9 +83,11 @@ patch (argc, argv)
{
case 'Q':
case 'q':
+#ifdef SERVER_SUPPORT
/* The CVS 1.5 client sends these options (in addition to
Global_option requests), so we must ignore them. */
if (!server_active)
+#endif
error (1, 0,
"-q or -Q must be specified before \"%s\"",
cvs_cmd_name);
@@ -342,7 +340,6 @@ patch_proc (argc, argv, xwhere, mwhere, mfile, shorten, local_specified,
{
error (0, errno, "cannot chdir to %s", repository);
free (repository);
- free (where);
return 1;
}
@@ -405,9 +402,6 @@ patch_fileproc (callerdat, finfo)
char *cp1, *cp2;
FILE *fp;
int line_length;
- int dargc = 0;
- size_t darg_allocated = 0;
- char **dargv = NULL;
line1 = NULL;
line1_chars_allocated = 0;
@@ -518,8 +512,7 @@ patch_fileproc (callerdat, finfo)
*/
if ((fp1 = cvs_temp_file (&tmpfile1)) == NULL)
{
- error (0, errno, "cannot create temporary file %s",
- tmpfile1 ? tmpfile1 : "(null)");
+ error (0, errno, "cannot create temporary file %s", tmpfile1);
ret = 1;
goto out;
}
@@ -528,8 +521,7 @@ patch_fileproc (callerdat, finfo)
error (0, errno, "warning: cannot close %s", tmpfile1);
if ((fp2 = cvs_temp_file (&tmpfile2)) == NULL)
{
- error (0, errno, "cannot create temporary file %s",
- tmpfile2 ? tmpfile2 : "(null)");
+ error (0, errno, "cannot create temporary file %s", tmpfile2);
ret = 1;
goto out;
}
@@ -538,8 +530,7 @@ patch_fileproc (callerdat, finfo)
error (0, errno, "warning: cannot close %s", tmpfile2);
if ((fp3 = cvs_temp_file (&tmpfile3)) == NULL)
{
- error (0, errno, "cannot create temporary file %s",
- tmpfile3 ? tmpfile3 : "(null)");
+ error (0, errno, "cannot create temporary file %s", tmpfile3);
ret = 1;
goto out;
}
@@ -590,10 +581,8 @@ patch_fileproc (callerdat, finfo)
(void)utime (tmpfile2, &t);
}
- if (unidiff) run_add_arg_p (&dargc, &darg_allocated, &dargv, "-u");
- else run_add_arg_p (&dargc, &darg_allocated, &dargv, "-c");
- switch (diff_exec (tmpfile1, tmpfile2, NULL, NULL, dargc, dargv,
- tmpfile3))
+ switch (diff_exec (tmpfile1, tmpfile2, NULL, NULL, unidiff ? "-u" : "-c",
+ tmpfile3))
{
case -1: /* fork/wait failure */
error (1, errno, "fork for diff failed on %s", rcs);
@@ -755,33 +744,16 @@ failed to read diff file header %s for %s: end of file", tmpfile3, rcs);
free (line1);
if (line2)
free (line2);
- if (tmpfile1 != NULL)
- {
- if (CVS_UNLINK (tmpfile1) < 0)
- error (0, errno, "cannot unlink %s", tmpfile1);
- free (tmpfile1);
- tmpfile1 = NULL;
- }
- if (tmpfile2 != NULL)
- {
- if (CVS_UNLINK (tmpfile2) < 0)
- error (0, errno, "cannot unlink %s", tmpfile2);
- free (tmpfile2);
- tmpfile2 = NULL;
- }
- if (tmpfile3 != NULL)
- {
- if (CVS_UNLINK (tmpfile3) < 0)
- error (0, errno, "cannot unlink %s", tmpfile3);
- free (tmpfile3);
- tmpfile3 = NULL;
- }
-
- if (dargc)
- {
- run_arg_free_p (dargc, dargv);
- free (dargv);
- }
+ if (CVS_UNLINK (tmpfile1) < 0)
+ error (0, errno, "cannot unlink %s", tmpfile1);
+ if (CVS_UNLINK (tmpfile2) < 0)
+ error (0, errno, "cannot unlink %s", tmpfile2);
+ if (CVS_UNLINK (tmpfile3) < 0)
+ error (0, errno, "cannot unlink %s", tmpfile3);
+ free (tmpfile1);
+ free (tmpfile2);
+ free (tmpfile3);
+ tmpfile1 = tmpfile2 = tmpfile3 = NULL;
out2:
if (vers_tag != NULL)
diff --git a/contrib/cvs/src/rcs.c b/contrib/cvs/src/rcs.c
index e1d62ed..1d3c1fd 100644
--- a/contrib/cvs/src/rcs.c
+++ b/contrib/cvs/src/rcs.c
@@ -1,17 +1,13 @@
/*
- * Copyright (C) 1986-2005 The Free Software Foundation, Inc.
- *
- * Portions Copyright (C) 1998-2005 Derek Price, Ximbiot <http://ximbiot.com>,
- * and others.
- *
- * Portions Copyright (C) 1992, Brian Berliner and Jeff Polk
- * Portions Copyright (C) 1989-1992, Brian Berliner
+ * Copyright (c) 1992, Brian Berliner and Jeff Polk
*
* You may distribute under the terms of the GNU General Public License as
* specified in the README file that comes with the CVS source distribution.
*
* The routines contained in this file do all the rcs file parsing and
* manipulation
+ *
+ * $FreeBSD$
*/
#include <assert.h>
@@ -30,6 +26,7 @@
# endif
#endif
+int datesep = '/';
int preserve_perms = 0;
/* The RCS -k options, and a set of enums that must match the array.
@@ -140,6 +137,8 @@ static char *rcs_lockfilename PROTO ((const char *));
evaluates its arguments multiple times. */
#define STREQ(a, b) (*(char *)(a) == *(char *)(b) && strcmp ((a), (b)) == 0)
+static char * getfullCVSname PROTO ((char *, char **));
+
/*
* We don't want to use isspace() from the C library because:
*
@@ -304,8 +303,8 @@ RCS_parse (file, repos)
}
else if (! existence_error (errno))
{
+ free ( rcsfile );
error (0, errno, "cannot open %s", rcsfile);
- free (rcsfile);
}
return retval;
@@ -501,13 +500,8 @@ RCS_reparsercsfile (rdata, pfp, rcsbufp)
RCS_addaccess expects nothing but spaces. FIXME:
It would be easy and more efficient to change
RCS_addaccess. */
- if (rdata->access)
- {
- error (0, 0,
- "Duplicate `access' keyword found in RCS file.");
- free (rdata->access);
- }
- rdata->access = rcsbuf_valcopy (&rcsbuf, value, 1, NULL);
+ rdata->access = rcsbuf_valcopy (&rcsbuf, value, 1,
+ (size_t *) NULL);
}
continue;
}
@@ -517,15 +511,8 @@ RCS_reparsercsfile (rdata, pfp, rcsbufp)
if (STREQ (key, "locks"))
{
if (value != NULL)
- {
- if (rdata->locks_data)
- {
- error (0, 0,
- "Duplicate `locks' keyword found in RCS file.");
- free (rdata->locks_data);
- }
- rdata->locks_data = rcsbuf_valcopy (&rcsbuf, value, 0, NULL);
- }
+ rdata->locks_data = rcsbuf_valcopy (&rcsbuf, value, 0,
+ (size_t *) NULL);
if (! rcsbuf_getkey (&rcsbuf, &key, &value))
{
error (1, 0, "premature end of file reading %s", rcsfile);
@@ -542,16 +529,8 @@ RCS_reparsercsfile (rdata, pfp, rcsbufp)
if (STREQ (RCSSYMBOLS, key))
{
if (value != NULL)
- {
- if (rdata->symbols_data)
- {
- error (0, 0,
- "Duplicate `%s' keyword found in RCS file.",
- RCSSYMBOLS);
- free (rdata->symbols_data);
- }
- rdata->symbols_data = rcsbuf_valcopy (&rcsbuf, value, 0, NULL);
- }
+ rdata->symbols_data = rcsbuf_valcopy (&rcsbuf, value, 0,
+ (size_t *) NULL);
continue;
}
@@ -575,14 +554,8 @@ RCS_reparsercsfile (rdata, pfp, rcsbufp)
if (STREQ (key, "comment"))
{
- if (rdata->comment)
- {
- error (0, 0,
- "warning: duplicate key `%s' in RCS file `%s'",
- key, rcsfile);
- free (rdata->comment);
- }
- rdata->comment = rcsbuf_valcopy (&rcsbuf, value, 0, NULL);
+ rdata->comment = rcsbuf_valcopy (&rcsbuf, value, 0,
+ (size_t *) NULL);
continue;
}
if (rdata->other == NULL)
@@ -616,9 +589,14 @@ RCS_reparsercsfile (rdata, pfp, rcsbufp)
q->key = vnode->version;
/* add the nodes to the list */
- if (addnode (rdata->versions, q))
- error (1, 0, "Multiple %s revision deltas found in `%s'",
- q->key, rcsfile);
+ if (addnode (rdata->versions, q) != 0)
+ {
+#if 0
+ purify_printf("WARNING: Adding duplicate version: %s (%s)\n",
+ q->key, rcsfile);
+ freenode (q);
+#endif
+ }
}
/* Here KEY and VALUE are whatever caused getdelta to return NULL. */
@@ -772,10 +750,10 @@ RCS_fully_parse (rcs)
break;
vers = findnode (rcs->versions, key);
- if (!vers)
+ if (vers == NULL)
error (1, 0,
- "Delta text %s without revision information in `%s'.",
- key, rcs->path);
+ "mismatch in rcs file %s between deltas and deltatexts (%s)",
+ rcs->path, key);
vnode = vers->data;
@@ -2099,8 +2077,6 @@ do_symbols (list, val)
char *cp = val;
char *tag, *rev;
- assert (cp);
-
for (;;)
{
/* skip leading whitespace */
@@ -2143,8 +2119,6 @@ do_locks (list, val)
char *cp = val;
char *user, *rev;
- assert (cp);
-
for (;;)
{
/* skip leading whitespace */
@@ -2329,12 +2303,6 @@ RCS_tag2rev (rcs, tag)
* the 0 in some other position -- <dan@gasboy.com>
*/
pa = strrchr (rev, '.');
- if (!pa)
- /* This might happen, for instance, if an RCS file only contained
- * revisions 2.x and higher, and REV == "1".
- */
- error (1, 0, "revision `%s' does not exist", tag);
-
pb = xmalloc (strlen (rev) + 3);
*pa++ = 0;
(void) sprintf (pb, "%s.%d.%s", rev, RCS_MAGIC_BRANCH, pa);
@@ -2539,13 +2507,25 @@ RCS_magicrev (rcs, rev)
char *rev;
{
int rev_num;
- char *xrev, *test_branch;
+ char *xrev, *test_branch, *local_branch_num;
xrev = xmalloc (strlen (rev) + 14); /* enough for .0.number */
check_rev = xrev;
+ local_branch_num = getenv("CVS_LOCAL_BRANCH_NUM");
+ if (local_branch_num)
+ {
+ rev_num = atoi(local_branch_num);
+ if (rev_num < 2)
+ rev_num = 2;
+ else
+ rev_num &= ~1;
+ }
+ else
+ rev_num = 2;
+
/* only look at even numbered branches */
- for (rev_num = 2; ; rev_num += 2)
+ for ( ; ; rev_num += 2)
{
/* see if the physical branch exists */
(void) sprintf (xrev, "%s.%d", rev, rev_num);
@@ -2909,9 +2889,8 @@ RCS_getbranchpoint (rcs, target)
vp = findnode (rcs->versions, branch);
if (vp == NULL)
- {
+ {
error (0, 0, "%s: can't find branch point %s", rcs->path, target);
- free (branch);
return NULL;
}
rev = vp->data;
@@ -3045,8 +3024,6 @@ RCS_getdate (rcs, date, force_tag_match)
{
char *date_1_1 = vers->date;
- assert (p->data != NULL);
-
vers = p->data;
if (RCS_datecmp (vers->date, date_1_1) != 0)
return xstrdup ("1.1");
@@ -3315,7 +3292,7 @@ translate_symtag (rcs, tag)
if (rcs->symbols_data != NULL)
{
size_t len;
- char *cp, *last;
+ char *cp;
/* Look through the RCS symbols information. This is like
do_symbols, but we don't add the information to a list. In
@@ -3324,16 +3301,8 @@ translate_symtag (rcs, tag)
len = strlen (tag);
cp = rcs->symbols_data;
- /* Keeping track of LAST below isn't strictly necessary, now that tags
- * should be parsed for validity before they are accepted, but tags
- * with spaces used to cause the code below to loop indefintely, so
- * I have corrected for that. Now, in the event that I missed
- * something, the server cannot be hung. -DRP
- */
- last = NULL;
while ((cp = strchr (cp, tag[0])) != NULL)
{
- if (cp == last) break;
if ((cp == rcs->symbols_data || whitespace (cp[-1]))
&& strncmp (cp, tag, len) == 0
&& cp[len] == ':')
@@ -3356,7 +3325,6 @@ translate_symtag (rcs, tag)
++cp;
if (*cp == '\0')
break;
- last = cp;
}
}
@@ -3484,8 +3452,6 @@ RCS_isdead (rcs, tag)
Node *p;
RCSVers *version;
- assert (rcs != NULL);
-
if (rcs->flags & PARTIAL)
RCS_reparsercsfile (rcs, (FILE **) NULL, (struct rcsbuffer *) NULL);
@@ -3531,27 +3497,31 @@ struct rcs_keyword
{
const char *string;
size_t len;
+ int expandit;
};
#define KEYWORD_INIT(s) (s), sizeof (s) - 1
-static const struct rcs_keyword keywords[] =
+static struct rcs_keyword keywords[] =
{
- { KEYWORD_INIT ("Author") },
- { KEYWORD_INIT ("Date") },
- { KEYWORD_INIT ("Header") },
- { KEYWORD_INIT ("Id") },
- { KEYWORD_INIT ("Locker") },
- { KEYWORD_INIT ("Log") },
- { KEYWORD_INIT ("Name") },
- { KEYWORD_INIT ("RCSfile") },
- { KEYWORD_INIT ("Revision") },
- { KEYWORD_INIT ("Source") },
- { KEYWORD_INIT ("State") },
- { NULL, 0 }
+ { KEYWORD_INIT ("Author"), 1 },
+ { KEYWORD_INIT ("Date"), 1 },
+ { KEYWORD_INIT ("CVSHeader"), 1 },
+ { KEYWORD_INIT ("Header"), 1 },
+ { KEYWORD_INIT ("Id"), 1 },
+ { KEYWORD_INIT ("Locker"), 1 },
+ { KEYWORD_INIT ("Log"), 1 },
+ { KEYWORD_INIT ("Name"), 1 },
+ { KEYWORD_INIT ("RCSfile"), 1 },
+ { KEYWORD_INIT ("Revision"), 1 },
+ { KEYWORD_INIT ("Source"), 1 },
+ { KEYWORD_INIT ("State"), 1 },
+ { NULL, 0, 0 },
+ { NULL, 0, 0 }
};
enum keyword
{
KEYWORD_AUTHOR = 0,
KEYWORD_DATE,
+ KEYWORD_CVSHEADER,
KEYWORD_HEADER,
KEYWORD_ID,
KEYWORD_LOCKER,
@@ -3560,8 +3530,10 @@ enum keyword
KEYWORD_RCSFILE,
KEYWORD_REVISION,
KEYWORD_SOURCE,
- KEYWORD_STATE
+ KEYWORD_STATE,
+ KEYWORD_LOCALID
};
+enum keyword keyword_local = KEYWORD_ID;
/* Convert an RCS date string into a readable string. This is like
the RCS date2str function. */
@@ -3577,8 +3549,8 @@ printable_date (rcs_date)
&sec);
if (year < 1900)
year += 1900;
- sprintf (buf, "%04d/%02d/%02d %02d:%02d:%02d", year, mon, mday,
- hour, min, sec);
+ sprintf (buf, "%04d%c%02d%c%02d %02d:%02d:%02d",
+ year, datesep, mon, datesep, mday, hour, min, sec);
return xstrdup (buf);
}
@@ -3739,7 +3711,8 @@ expand_keywords (rcs, ver, name, log, loglen, expand, buf, len, retbuf, retlen)
slen = s - srch;
for (keyword = keywords; keyword->string != NULL; keyword++)
{
- if (keyword->len == slen
+ if (keyword->expandit
+ && keyword->len == slen
&& strncmp (keyword->string, srch, slen) == 0)
{
break;
@@ -3786,15 +3759,25 @@ expand_keywords (rcs, ver, name, log, loglen, expand, buf, len, retbuf, retlen)
free_value = 1;
break;
+ case KEYWORD_CVSHEADER:
case KEYWORD_HEADER:
case KEYWORD_ID:
+ case KEYWORD_LOCALID:
{
const char *path;
int free_path;
char *date;
+ char *old_path;
- if (kw == KEYWORD_HEADER)
+ old_path = NULL;
+ if (kw == KEYWORD_HEADER ||
+ (kw == KEYWORD_LOCALID &&
+ keyword_local == KEYWORD_HEADER))
path = rcs->path;
+ else if (kw == KEYWORD_CVSHEADER ||
+ (kw == KEYWORD_LOCALID &&
+ keyword_local == KEYWORD_CVSHEADER))
+ path = getfullCVSname(rcs->path, &old_path);
else
path = last_component (rcs->path);
path = escape_keyword_value (path, &free_path);
@@ -3817,6 +3800,8 @@ expand_keywords (rcs, ver, name, log, loglen, expand, buf, len, retbuf, retlen)
* and we can discard the const.
*/
free ((char *)path);
+ if (old_path)
+ free (old_path);
free (date);
free_value = 1;
}
@@ -3946,13 +3931,6 @@ expand_keywords (rcs, ver, name, log, loglen, expand, buf, len, retbuf, retlen)
if (*snl == '\n')
++cnl;
- /* If the log message did not end in a newline, increment
- * the newline count so we have space for the extra leader.
- * Failure to do so results in a buffer overrun.
- */
- if (loglen && snl[-1] != '\n')
- ++cnl;
-
date = printable_date (ver->date);
sub = xrealloc (sub,
(sublen
@@ -3961,10 +3939,6 @@ expand_keywords (rcs, ver, name, log, loglen, expand, buf, len, retbuf, retlen)
+ strlen (date)
+ strlen (ver->author)
+ loglen
- /* Use CNL + 2 below: One leader for each log
- * line, plus the Revision/Author/Date line,
- * plus a trailing blank line.
- */
+ (cnl + 2) * leader_len
+ 20));
if (expand != KFLAG_V)
@@ -4004,14 +3978,6 @@ expand_keywords (rcs, ver, name, log, loglen, expand, buf, len, retbuf, retlen)
++slnl;
memcpy (sub + sublen, sl, slnl - sl);
sublen += slnl - sl;
- if (slnl == logend && slnl[-1] != '\n')
- {
- /* There was no EOL at the end of the log message. Add
- * one.
- */
- sub[sublen] = '\n';
- ++sublen;
- }
sl = slnl;
}
}
@@ -4130,8 +4096,7 @@ expand_keywords (rcs, ver, name, log, loglen, expand, buf, len, retbuf, retlen)
Otherwise, if WORKFILE is NULL, check out the revision to SOUT. If
SOUT is RUN_TTY, then write the contents of the revision to
standard output. When using SOUT, the output is generally a
- temporary file; don't bother to get the file modes correct. When
- NOEXEC is set, WORKFILEs are not written but SOUTs are.
+ temporary file; don't bother to get the file modes correct.
REV is the numeric revision to check out. It may be NULL, which
means to check out the head of the default branch.
@@ -4206,7 +4171,7 @@ RCS_checkout (rcs, workfile, rev, nametag, options, sout, pfn, callerdat)
assert (rev == NULL || isdigit ((unsigned char) *rev));
- if (noexec && !server_active && workfile != NULL)
+ if (noexec && workfile != NULL)
return 0;
assert (sout == RUN_TTY || workfile == NULL);
@@ -4236,23 +4201,10 @@ RCS_checkout (rcs, workfile, rev, nametag, options, sout, pfn, callerdat)
gothead = 0;
if (! rcsbuf_getrevnum (&rcsbuf, &key))
error (1, 0, "unexpected EOF reading %s", rcs->path);
-
- if (!STREQ (rcs->head, key))
- error (1, 0, "Expected head revision %s, found %s.",
- rcs->head, key);
-
while (rcsbuf_getkey (&rcsbuf, &key, &value))
{
if (STREQ (key, "log"))
- {
- if (log)
- {
- error (0, 0,
-"Duplicate log keyword found for head revision in RCS file.");
- free (log);
- }
log = rcsbuf_valcopy (&rcsbuf, value, 0, &loglen);
- }
else if (STREQ (key, "text"))
{
gothead = 1;
@@ -4752,7 +4704,6 @@ RCS_findlock_or_tip (rcs)
char *user = getcaller();
Node *lock, *p;
List *locklist;
- char *defaultrev = NULL;
/* Find unique delta locked by caller. This code is very similar
to the code in RCS_unlock -- perhaps it could be abstracted
@@ -4798,17 +4749,7 @@ RCS_findlock_or_tip (rcs)
those error checks are to make users lock before a checkin, and we do
that in other ways if at all anyway (e.g. rcslock.pl). */
- defaultrev = RCS_getbranch (rcs, rcs->branch, 0);
- p = findnode (rcs->versions, defaultrev);
- if (defaultrev != NULL)
- free (defaultrev);
- if (!p)
- {
- error (0, 0, "RCS file `%s' does not contain its default revision.",
- rcs->path);
- return NULL;
- }
-
+ p = findnode (rcs->versions, RCS_getbranch (rcs, rcs->branch, 0));
return p->data;
}
@@ -4922,8 +4863,6 @@ RCS_addbranch (rcs, branch)
Node *marker;
RCSVers *branchnode;
- assert (branch);
-
/* Append to end by default. */
marker = NULL;
@@ -5042,21 +4981,18 @@ RCS_addbranch (rcs, branch)
or zero for success. */
int
-RCS_checkin (rcs, workfile_in, message, rev, citime, flags)
+RCS_checkin (rcs, workfile_in, message, rev, flags)
RCSNode *rcs;
const char *workfile_in;
const char *message;
const char *rev;
- time_t citime;
int flags;
{
RCSVers *delta, *commitpt;
Deltatext *dtext;
Node *nodep;
char *tmpfile, *changefile;
- int dargc = 0;
- size_t darg_allocated = 0;
- char **dargv = NULL;
+ char *diffopts;
size_t bufsize;
int status, checkin_quiet;
struct tm *ftm;
@@ -5078,7 +5014,6 @@ RCS_checkin (rcs, workfile_in, message, rev, citime, flags)
{
char *p;
int extlen = strlen (RCSEXT);
- assert (rcs->path);
workfile = xstrdup (last_component (rcs->path));
p = workfile + (strlen (workfile) - extlen);
assert (strncmp (p, RCSEXT, extlen) == 0);
@@ -5113,8 +5048,6 @@ RCS_checkin (rcs, workfile_in, message, rev, citime, flags)
}
modtime = ws.st_mtime;
}
- else if (flags & RCS_FLAGS_USETIME)
- modtime = citime;
else
(void) time (&modtime);
ftm = gmtime (&modtime);
@@ -5356,7 +5289,6 @@ workfile);
if (dots == 0)
{
tip = xstrdup (rcs->head);
- assert (tip != NULL);
if (atoi (tip) != atoi (branch))
{
newrev = (char *) xrealloc (newrev, strlen (newrev) + 3);
@@ -5486,10 +5418,9 @@ workfile);
/* Diff options should include --binary if the RCS file has -kb set
in its `expand' field. */
- run_add_arg_p (&dargc, &darg_allocated, &dargv, "-a");
- run_add_arg_p (&dargc, &darg_allocated, &dargv, "-n");
- if (rcs->expand && STREQ (rcs->expand, "b"))
- run_add_arg_p (&dargc, &darg_allocated, &dargv, "--binary");
+ diffopts = (rcs->expand != NULL && STREQ (rcs->expand, "b")
+ ? "-a -n --binary"
+ : "-a -n");
if (STREQ (commitpt->version, rcs->head) &&
numdots (delta->version) == 1)
@@ -5512,8 +5443,7 @@ workfile);
memset (commitpt->text, 0, sizeof (Deltatext));
bufsize = 0;
- switch (diff_exec (workfile, tmpfile, NULL, NULL,
- dargc, dargv, changefile))
+ switch (diff_exec (workfile, tmpfile, NULL, NULL, diffopts, changefile))
{
case 0:
case 1:
@@ -5561,8 +5491,7 @@ workfile);
/* This file is not being inserted at the head, but on a side
branch somewhere. Make a diff from the previous revision
to the working file. */
- switch (diff_exec (tmpfile, workfile, NULL, NULL,
- dargc, dargv, changefile))
+ switch (diff_exec (tmpfile, workfile, NULL, NULL, diffopts, changefile))
{
case 0:
case 1:
@@ -5589,9 +5518,6 @@ workfile);
}
}
- run_arg_free_p (dargc, dargv);
- free (dargv);
-
/* Update DELTA linkage. It is important not to do this before
the very end of RCS_checkin; if an error arises that forces
us to abort checking in, we must not have malformed deltas
@@ -5664,13 +5590,7 @@ workfile);
freedeltatext (dtext);
if (status != 0)
- {
- /* If delta has not been added to a List, then freeing the Node key
- * won't free delta->version.
- */
- if (delta->version) free (delta->version);
free_rcsvers_contents (delta);
- }
return status;
}
@@ -6372,12 +6292,7 @@ RCS_delete_revs (rcs, tag1, tag2, inclusive)
/* A range consisting of a branch number means the latest revision
on that branch. */
if (RCS_isbranch (rcs, rev1) && STREQ (rev1, rev2))
- {
- char *tmp = RCS_getbranch (rcs, rev1, 0);
- free (rev1);
- free (rev2);
- rev1 = rev2 = tmp;
- }
+ rev1 = rev2 = RCS_getbranch (rcs, rev1, 0);
else
{
/* Make sure REV1 and REV2 are ordered correctly (in the
@@ -6665,10 +6580,6 @@ RCS_delete_revs (rcs, tag1, tag2, inclusive)
}
else
{
- int dargc = 0;
- size_t darg_allocated = 0;
- char **dargv = NULL;
-
beforefile = cvs_temp_name();
status = RCS_checkout (rcs, NULL, before, NULL, "-ko", beforefile,
(RCSCHECKOUTPROC)0, NULL);
@@ -6676,12 +6587,7 @@ RCS_delete_revs (rcs, tag1, tag2, inclusive)
goto delrev_done;
outfile = cvs_temp_name();
- run_add_arg_p (&dargc, &darg_allocated, &dargv, "-a");
- run_add_arg_p (&dargc, &darg_allocated, &dargv, "-n");
- status = diff_exec (beforefile, afterfile, NULL, NULL,
- dargc, dargv, outfile);
- run_arg_free_p (dargc, dargv);
- free (dargv);
+ status = diff_exec (beforefile, afterfile, NULL, NULL, "-an", outfile);
if (status == 2)
{
@@ -6779,7 +6685,7 @@ RCS_delete_revs (rcs, tag1, tag2, inclusive)
delrev_done:
if (rev1 != NULL)
free (rev1);
- if (rev2 && rev2 != rev1)
+ if (rev2 != NULL)
free (rev2);
if (branchpoint != NULL)
free (branchpoint);
@@ -7140,7 +7046,6 @@ apply_rcs_changes (lines, diffbuf, difflen, name, addvers, delvers)
};
struct deltafrag *dfhead;
struct deltafrag *df;
- int err;
dfhead = NULL;
for (p = diffbuf; p != NULL && p < diffbuf + difflen; )
@@ -7206,39 +7111,33 @@ apply_rcs_changes (lines, diffbuf, difflen, name, addvers, delvers)
}
}
- err = 0;
for (df = dfhead; df != NULL;)
{
unsigned int ln;
- /* Once an error is encountered, just free the rest of the list and
- * return.
- */
- if (!err)
- switch (df->type)
- {
- case FRAG_ADD:
- if (! linevector_add (lines, df->new_lines, df->len, addvers,
- df->pos))
- err = 1;
- break;
- case FRAG_DELETE:
- if (df->pos > lines->nlines
- || df->pos + df->nlines > lines->nlines)
- return 0;
- if (delvers != NULL)
- for (ln = df->pos; ln < df->pos + df->nlines; ++ln)
- lines->vector[ln]->vers = delvers;
- linevector_delete (lines, df->pos, df->nlines);
- break;
- }
-
+ switch (df->type)
+ {
+ case FRAG_ADD:
+ if (! linevector_add (lines, df->new_lines, df->len, addvers,
+ df->pos))
+ return 0;
+ break;
+ case FRAG_DELETE:
+ if (df->pos > lines->nlines
+ || df->pos + df->nlines > lines->nlines)
+ return 0;
+ if (delvers != NULL)
+ for (ln = df->pos; ln < df->pos + df->nlines; ++ln)
+ lines->vector[ln]->vers = delvers;
+ linevector_delete (lines, df->pos, df->nlines);
+ break;
+ }
df = df->next;
free (dfhead);
dfhead = df;
}
- return !err;
+ return 1;
}
/* Apply an RCS change text to a buffer. The function name starts
@@ -7356,18 +7255,12 @@ RCS_deltas (rcs, fp, rcsbuf, version, op, text, len, log, loglen)
struct linevector trunklines;
int foundhead;
- assert (version);
-
if (fp == NULL)
{
rcsbuf_cache_open (rcs, rcs->delta_pos, &fp, &rcsbuf_local);
rcsbuf = &rcsbuf_local;
}
- assert (rcsbuf);
-
- if (log) *log = NULL;
-
ishead = 1;
vers = NULL;
prev_vers = NULL;
@@ -7395,13 +7288,6 @@ RCS_deltas (rcs, fp, rcsbuf, version, op, text, len, log, loglen)
if (! rcsbuf_getrevnum (rcsbuf, &key))
error (1, 0, "unexpected EOF reading RCS file %s", rcs->path);
- /* look up the revision */
- node = findnode (rcs->versions, key);
- if (!node)
- error (1, 0,
- "Delta text %s without revision information in `%s'.",
- key, rcs->path);
-
if (next != NULL && ! STREQ (next, key))
{
/* This is not the next version we need. It is a branch
@@ -7413,6 +7299,13 @@ RCS_deltas (rcs, fp, rcsbuf, version, op, text, len, log, loglen)
{
isnext = 1;
+ /* look up the revision */
+ node = findnode (rcs->versions, key);
+ if (node == NULL)
+ error (1, 0,
+ "mismatch in rcs file %s between deltas and deltatexts (%s)",
+ rcs->path, key);
+
/* Stash the previous version. */
prev_vers = vers;
@@ -7438,12 +7331,6 @@ RCS_deltas (rcs, fp, rcsbuf, version, op, text, len, log, loglen)
&& STREQ (key, "log")
&& STREQ (branchversion, version))
{
- if (*log != NULL)
- {
- error (0, 0, "Duplicate `log' keyword in RCS file (`%s').",
- rcs->path);
- free (*log);
- }
*log = rcsbuf_valcopy (rcsbuf, value, 0, loglen);
}
@@ -7525,9 +7412,6 @@ RCS_deltas (rcs, fp, rcsbuf, version, op, text, len, log, loglen)
if (vers->branches == NULL)
error (1, 0, "missing expected branches in %s",
rcs->path);
- if (!cpversion)
- error (1, 0, "Invalid revision number in `%s'.",
- rcs->path);
*cpversion = '.';
++cpversion;
cpversion = strchr (cpversion, '.');
@@ -7913,10 +7797,9 @@ RCS_getdeltatext (rcs, fp, rcsbuf)
}
p = findnode (rcs->versions, num);
- if (!p)
- error (1, 0,
- "Delta text %s without revision information in `%s'.",
- num, rcs->path);
+ if (p == NULL)
+ error (1, 0, "mismatch in rcs file %s between deltas and deltatexts (%s)",
+ rcs->path, num);
d = (Deltatext *) xmalloc (sizeof (Deltatext));
d->version = xstrdup (num);
@@ -8181,65 +8064,31 @@ RCS_putdtree (rcs, rev, fp)
RCSVers *versp;
Node *p, *branch;
- /* Previously, this function used a recursive implementation, but
- if the trunk has a huge number of revisions and the program
- stack is not big, a stack overflow could occur, so this
- nonrecursive version was developed to be more safe. */
- Node *branchlist, *onebranch;
- List *branches;
- List *onebranchlist;
-
if (rev == NULL)
return;
- branches = getlist();
-
- for (; rev != NULL;)
+ /* Find the delta node for this revision. */
+ p = findnode (rcs->versions, rev);
+ if (p == NULL)
{
- /* Find the delta node for this revision. */
- p = findnode (rcs->versions, rev);
- if (p == NULL)
- {
- error (1, 0,
- "error parsing repository file %s, file may be corrupt.",
- rcs->path);
- }
-
- versp = p->data;
-
- /* Print the delta node and go for its `next' node. This
- prints the trunk. If there are any branches printed on this
- revision, mark we have some. */
- putdelta (versp, fp);
- /* Store branch information into branch list so to write its
- trunk afterwards */
- if (versp->branches != NULL)
- {
- branch = getnode();
- branch->data = versp->branches;
-
- addnode(branches, branch);
- }
-
- rev = versp->next;
+ error (1, 0,
+ "error parsing repository file %s, file may be corrupt.",
+ rcs->path);
}
+
+ versp = p->data;
- /* If there are any branches printed on this revision,
+ /* Print the delta node and recurse on its `next' node. This prints
+ the trunk. If there are any branches printed on this revision,
print those trunks as well. */
- branchlist = branches->list;
- for (branch = branchlist->next;
- branch != branchlist;
- branch = branch->next)
- {
- onebranchlist = (List *)(branch->data);
- onebranch = onebranchlist->list;
- for (p = onebranch->next; p != onebranch; p = p->next)
+ putdelta (versp, fp);
+ RCS_putdtree (rcs, versp->next, fp);
+ if (versp->branches != NULL)
+ {
+ branch = versp->branches->list;
+ for (p = branch->next; p != branch; p = p->next)
RCS_putdtree (rcs, p->key, fp);
-
- branch->data = NULL; /* so to prevent its freeing on dellist */
}
-
- dellist(&branches);
}
static void
@@ -8344,11 +8193,6 @@ RCS_copydeltas (rcs, fin, rcsbufin, fout, newdtext, insertpt)
}
np = findnode (rcs->versions, dtext->version);
- if (!np)
- error (1, 0,
- "Delta text %s without revision information in `%s'.",
- dtext->version, rcs->path);
-
dadmin = np->data;
/* If this revision has been outdated, just skip it. */
@@ -8636,28 +8480,6 @@ rcs_internal_unlockfile (fp, rcsfile)
real solution is to check each call to fprintf rather than waiting
until the end like this. */
error (1, errno, "error writing to lock file %s", rcs_lockfile);
-
- /* Flush and sync the file, or the user may be told the commit completed,
- * while a server crash/power failure could still cause the data to be
- * lost.
- *
- * Invoking rename(",<file>," , "<file>,v") on Linux and almost all UNIXs
- * only flushes the inode for the target file to disk, it does not
- * guarantee flush of the kernel buffers allocated for the ,<file>,.
- * Depending upon the load on the machine, the Linux kernel's flush daemon
- * process may not flush for a while. In the meantime the CVS transaction
- * could have been declared committed to the end CVS user (CVS process has
- * returned the final "OK"). If the machine crashes prior to syncing the
- * changes to disk, the committed transaction can be lost.
- */
- if (fflush (fp) != 0)
- error (1, errno, "error flushing file `%s' to kernel buffers",
- rcs_lockfile);
-#ifdef HAVE_FSYNC
- if (fsync (rcs_lockfd) < 0)
- error (1, errno, "error fsyncing file `%s'", rcs_lockfile);
-#endif
-
if (fclose (fp) == EOF)
error (1, errno, "error closing lock file %s", rcs_lockfile);
rcs_lockfd = -1;
@@ -8712,8 +8534,6 @@ RCS_rewrite (rcs, newdtext, insertpt)
FILE *fin, *fout;
struct rcsbuffer rcsbufin;
- assert (rcs);
-
if (noexec)
return;
@@ -8837,3 +8657,105 @@ make_file_label (path, rev, rcs)
}
return label;
}
+
+void
+RCS_setlocalid (arg)
+ const char *arg;
+{
+ char *copy, *next, *key;
+
+ copy = xstrdup(arg);
+ next = copy;
+ key = strtok(next, "=");
+
+ keywords[KEYWORD_LOCALID].string = xstrdup(key);
+ keywords[KEYWORD_LOCALID].len = strlen(key);
+ keywords[KEYWORD_LOCALID].expandit = 1;
+
+ /* options? */
+ while (key = strtok(NULL, ",")) {
+ if (!strcmp(key, keywords[KEYWORD_ID].string))
+ keyword_local = KEYWORD_ID;
+ else if (!strcmp(key, keywords[KEYWORD_HEADER].string))
+ keyword_local = KEYWORD_HEADER;
+ else if (!strcmp(key, keywords[KEYWORD_CVSHEADER].string))
+ keyword_local = KEYWORD_CVSHEADER;
+ else
+ error(1, 0, "Unknown LocalId mode: %s", key);
+ }
+ free(copy);
+}
+
+void
+RCS_setincexc (arg)
+ const char *arg;
+{
+ char *key;
+ char *copy, *next;
+ int include = 0;
+ struct rcs_keyword *keyword;
+
+ copy = xstrdup(arg);
+ next = copy;
+ switch (*next++) {
+ case 'e':
+ include = 0;
+ break;
+ case 'i':
+ include = 1;
+ break;
+ default:
+ free(copy);
+ return;
+ }
+
+ if (include)
+ for (keyword = keywords; keyword->string != NULL; keyword++)
+ {
+ keyword->expandit = 0;
+ }
+
+ key = strtok(next, ",");
+ while (key) {
+ for (keyword = keywords; keyword->string != NULL; keyword++) {
+ if (strcmp (keyword->string, key) == 0)
+ keyword->expandit = include;
+ }
+ key = strtok(NULL, ",");
+ }
+ free(copy);
+ return;
+}
+
+#define ATTIC "/" CVSATTIC
+static char *
+getfullCVSname(CVSname, pathstore)
+ char *CVSname, **pathstore;
+{
+ if (current_parsed_root->directory) {
+ int rootlen;
+ char *c = NULL;
+ int alen = sizeof(ATTIC) - 1;
+
+ *pathstore = xstrdup(CVSname);
+ if ((c = strrchr(*pathstore, '/')) != NULL) {
+ if (c - *pathstore >= alen) {
+ if (!strncmp(c - alen, ATTIC, alen)) {
+ while (*c != '\0') {
+ *(c - alen) = *c;
+ c++;
+ }
+ *(c - alen) = '\0';
+ }
+ }
+ }
+
+ rootlen = strlen(current_parsed_root->directory);
+ if (!strncmp(*pathstore, current_parsed_root->directory, rootlen) &&
+ (*pathstore)[rootlen] == '/')
+ CVSname = (*pathstore + rootlen + 1);
+ else
+ CVSname = (*pathstore);
+ }
+ return CVSname;
+}
diff --git a/contrib/cvs/src/rcs.h b/contrib/cvs/src/rcs.h
index 3a66640..d40d178 100644
--- a/contrib/cvs/src/rcs.h
+++ b/contrib/cvs/src/rcs.h
@@ -1,16 +1,13 @@
/*
- * Copyright (C) 1986-2005 The Free Software Foundation, Inc.
- *
- * Portions Copyright (C) 1998-2005 Derek Price, Ximbiot <http://ximbiot.com>,
- * and others.
- *
- * Portions Copyright (C) 1992, Brian Berliner and Jeff Polk
- * Portions Copyright (C) 1989-1992, Brian Berliner
+ * Copyright (c) 1992, Brian Berliner and Jeff Polk
+ * Copyright (c) 1989-1992, Brian Berliner
*
* You may distribute under the terms of the GNU General Public License as
* specified in the README file that comes with the CVS source distribution.
*
* RCS source control definitions needed by rcs.c and friends
+ *
+ * $FreeBSD$
*/
/* Strings which indicate a conflict if they occur at the start of a line. */
@@ -229,8 +226,7 @@ void RCS_setexpand PROTO ((RCSNode *, const char *));
int RCS_checkout PROTO ((RCSNode *, const char *, const char *, const char *,
const char *, const char *, RCSCHECKOUTPROC, void *));
int RCS_checkin PROTO ((RCSNode *rcs, const char *workfile,
- const char *message, const char *rev, time_t citime,
- int flags));
+ const char *message, const char *rev, int flags));
int RCS_cmp_file PROTO((RCSNode *, const char *, char **, const char *,
const char *, const char *));
int RCS_settag PROTO ((RCSNode *, const char *, const char *));
@@ -250,8 +246,11 @@ int rcs_change_text PROTO ((const char *, char *, size_t, const char *,
void RCS_deltas PROTO ((RCSNode *, FILE *, struct rcsbuffer *, const char *,
enum rcs_delta_op, char **, size_t *,
char **, size_t *));
+void RCS_setincexc PROTO ((const char *arg));
+void RCS_setlocalid PROTO ((const char *arg));
char *make_file_label PROTO ((const char *, const char *, RCSNode *));
+extern int datesep;
extern int preserve_perms;
/* From import.c. */
diff --git a/contrib/cvs/src/rcscmds.c b/contrib/cvs/src/rcscmds.c
index a9e576a..df91ff8 100644
--- a/contrib/cvs/src/rcscmds.c
+++ b/contrib/cvs/src/rcscmds.c
@@ -1,17 +1,14 @@
/*
- * Copyright (C) 1986-2005 The Free Software Foundation, Inc.
- *
- * Portions Copyright (C) 1998-2005 Derek Price, Ximbiot <http://ximbiot.com>,
- * and others.
- *
- * Portions Copyright (C) 1992, Brian Berliner and Jeff Polk
- * Portions Copyright (C) 1989-1992, Brian Berliner
+ * Copyright (c) 1992, Brian Berliner and Jeff Polk
+ * Copyright (c) 1989-1992, Brian Berliner
*
* You may distribute under the terms of the GNU General Public License as
* specified in the README file that comes with the CVS source distribution.
*
* The functions in this file provide an interface for performing
* operations directly on RCS files.
+ *
+ * $FreeBSD$
*/
#include "cvs.h"
@@ -56,8 +53,8 @@
On a related note, see the comments at diff_exec, later in this file,
for more on the diff library. */
-static void RCS_output_diff_options PROTO ((int, char *const *, const char *,
- const char *, const char *));
+static void RCS_output_diff_options PROTO ((const char *, const char *,
+ const char *, const char *));
/* Stuff to deal with passing arguments the way libdiff.a wants to deal
@@ -69,18 +66,17 @@ static void RCS_output_diff_options PROTO ((int, char *const *, const char *,
argument will be parsed into whitespace separated words and added
to the global call_diff_argv list.
- Then, optionally, call call_diff_add_arg for each additional argument
+ Then, optionally, call call_diff_arg for each additional argument
that you'd like to pass to the diff library.
Finally, call call_diff or call_diff3 to produce the diffs. */
static char **call_diff_argv;
static int call_diff_argc;
-static size_t call_diff_argc_allocated;
+static int call_diff_argc_allocated;
static void call_diff_add_arg PROTO ((const char *));
-static void call_diff_setup PROTO ((const char *prog,
- int argc, char * const *argv));
+static void call_diff_setup PROTO ((const char *prog));
static int call_diff PROTO ((const char *out));
static int call_diff3 PROTO ((char *out));
@@ -89,37 +85,62 @@ static void call_diff_flush_output PROTO((void));
static void call_diff_write_stdout PROTO((const char *));
static void call_diff_error PROTO((const char *, const char *, const char *));
-
-
-static void
-call_diff_add_arg (s)
- const char *s;
-{
- run_add_arg_p (&call_diff_argc, &call_diff_argc_allocated, &call_diff_argv,
- s);
-}
-
-
-
/* VARARGS */
static void
-call_diff_setup (prog, argc, argv)
+call_diff_setup (prog)
const char *prog;
- int argc;
- char * const *argv;
{
+ char *cp;
int i;
+ char *call_diff_prog;
/* clean out any malloc'ed values from call_diff_argv */
- run_arg_free_p (call_diff_argc, call_diff_argv);
+ for (i = 0; i < call_diff_argc; i++)
+ {
+ if (call_diff_argv[i])
+ {
+ free (call_diff_argv[i]);
+ call_diff_argv[i] = (char *) 0;
+ }
+ }
call_diff_argc = 0;
+ call_diff_prog = xstrdup (prog);
+
/* put each word into call_diff_argv, allocating it as we go */
- call_diff_add_arg (prog);
- for (i = 0; i < argc; i++)
- call_diff_add_arg (argv[i]);
+ for (cp = strtok (call_diff_prog, " \t");
+ cp != NULL;
+ cp = strtok ((char *) NULL, " \t"))
+ call_diff_add_arg (cp);
+ free (call_diff_prog);
}
+static void
+call_diff_arg (s)
+ const char *s;
+{
+ call_diff_add_arg (s);
+}
+
+static void
+call_diff_add_arg (s)
+ const char *s;
+{
+ /* allocate more argv entries if we've run out */
+ if (call_diff_argc >= call_diff_argc_allocated)
+ {
+ call_diff_argc_allocated += 50;
+ call_diff_argv = (char **)
+ xrealloc ((char *) call_diff_argv,
+ call_diff_argc_allocated * sizeof (char **));
+ }
+
+ if (s)
+ call_diff_argv[call_diff_argc++] = xstrdup (s);
+ else
+ /* Not post-incremented on purpose! */
+ call_diff_argv[call_diff_argc] = (char *) 0;
+}
/* Callback function for the diff library to write data to the output
file. This is used when we are producing output to stdout. */
@@ -192,8 +213,6 @@ static int
call_diff (out)
const char *out;
{
- call_diff_add_arg (NULL);
-
if (out == RUN_TTY)
return diff_run (call_diff_argc, call_diff_argv, NULL,
&call_diff_stdout_callbacks);
@@ -245,7 +264,6 @@ RCS_merge(rcs, path, workfile, options, rev1, rev2)
symbolic). */
xrev1 = RCS_gettag (rcs, rev1, 0, NULL);
xrev2 = RCS_gettag (rcs, rev2, 0, NULL);
- assert (xrev1 && xrev2);
/* Check out chosen revisions. The error message when RCS_checkout
fails is not very informative -- it is taken verbatim from RCS 5.7,
@@ -286,21 +304,21 @@ RCS_merge(rcs, path, workfile, options, rev1, rev2)
/* Remember that the first word in the `call_diff_setup' string is used now
only for diagnostic messages -- CVS no longer forks to run diff3. */
diffout = cvs_temp_name();
- call_diff_setup ("diff3", 0, NULL);
- call_diff_add_arg ("-E");
- call_diff_add_arg ("-am");
-
- call_diff_add_arg ("-L");
- call_diff_add_arg (workfile);
- call_diff_add_arg ("-L");
- call_diff_add_arg (xrev1);
- call_diff_add_arg ("-L");
- call_diff_add_arg (xrev2);
-
- call_diff_add_arg ("--");
- call_diff_add_arg (workfile);
- call_diff_add_arg (tmp1);
- call_diff_add_arg (tmp2);
+ call_diff_setup ("diff3");
+ call_diff_arg ("-E");
+ call_diff_arg ("-am");
+
+ call_diff_arg ("-L");
+ call_diff_arg (workfile);
+ call_diff_arg ("-L");
+ call_diff_arg (xrev1);
+ call_diff_arg ("-L");
+ call_diff_arg (xrev2);
+
+ call_diff_arg ("--");
+ call_diff_arg (workfile);
+ call_diff_arg (tmp1);
+ call_diff_arg (tmp2);
retval = call_diff3 (diffout);
@@ -366,11 +384,10 @@ RCS_merge(rcs, path, workfile, options, rev1, rev2)
about this--any such features are undocumented in the context of
CVS, and I'm not sure how important to users. */
int
-RCS_exec_rcsdiff (rcsfile, diff_argc, diff_argv, options, rev1, rev1_cache,
- rev2, label1, label2, workfile)
+RCS_exec_rcsdiff(rcsfile, opts, options, rev1, rev1_cache, rev2,
+ label1, label2, workfile )
RCSNode *rcsfile;
- int diff_argc;
- char * const *diff_argv;
+ const char *opts;
const char *options;
const char *rev1;
const char *rev1_cache;
@@ -450,9 +467,8 @@ RCS file: ", 0);
use_file2 = tmpfile2;
}
- RCS_output_diff_options (diff_argc, diff_argv, rev1, rev2, workfile);
- status = diff_exec (use_file1, use_file2, label1, label2,
- diff_argc, diff_argv, RUN_TTY);
+ RCS_output_diff_options (opts, rev1, rev2, workfile);
+ status = diff_exec( use_file1, use_file2, label1, label2, opts, RUN_TTY );
if (status >= 0)
{
retval = status;
@@ -531,15 +547,16 @@ RCS file: ", 0);
message on stderr. */
int
-diff_exec (file1, file2, label1, label2, dargc, dargv, out)
+diff_exec (file1, file2, label1, label2, options, out)
const char *file1;
const char *file2;
const char *label1;
const char *label2;
- int dargc;
- char * const *dargv;
+ const char *options;
const char *out;
{
+ char *args;
+
#ifdef PRESERVE_PERMISSIONS_SUPPORT
/* If either file1 or file2 are special files, pretend they are
/dev/null. Reason: suppose a file that represents a block
@@ -573,15 +590,18 @@ diff_exec (file1, file2, label1, label2, dargc, dargv, out)
}
#endif
- /* The first arg to call_diff_setup is used only for error reporting. */
- call_diff_setup ("diff", dargc, dargv);
+ args = xmalloc (strlen (options) + 10);
+ /* The first word in this string is used only for error reporting. */
+ sprintf (args, "diff %s", options);
+ call_diff_setup (args);
if (label1)
- call_diff_add_arg (label1);
+ call_diff_arg (label1);
if (label2)
- call_diff_add_arg (label2);
- call_diff_add_arg ("--");
- call_diff_add_arg (file1);
- call_diff_add_arg (file2);
+ call_diff_arg (label2);
+ call_diff_arg ("--");
+ call_diff_arg (file1);
+ call_diff_arg (file2);
+ free (args);
return call_diff (out);
}
@@ -593,23 +613,19 @@ diff_exec (file1, file2, label1, label2, dargc, dargv, out)
that I have seen. */
static void
-RCS_output_diff_options (diff_argc, diff_argv, rev1, rev2, workfile)
- int diff_argc;
- char * const *diff_argv;
+RCS_output_diff_options (opts, rev1, rev2, workfile)
+ const char *opts;
const char *rev1;
const char *rev2;
const char *workfile;
{
- int i;
-
- cvs_output ("diff", 0);
- for (i = 0; i < diff_argc; i++)
- {
- cvs_output (" ", 1);
- cvs_output (diff_argv[i], 0);
- }
- cvs_output (" -r", 3);
- cvs_output (rev1, 0);
+ char *tmp;
+
+ tmp = (char *) xmalloc (strlen (opts) + strlen (rev1) + 10);
+
+ sprintf (tmp, "diff%s -r%s", opts, rev1);
+ cvs_output (tmp, 0);
+ free (tmp);
if (rev2)
{
diff --git a/contrib/cvs/src/recurse.c b/contrib/cvs/src/recurse.c
index 2416861..20a0f9b 100644
--- a/contrib/cvs/src/recurse.c
+++ b/contrib/cvs/src/recurse.c
@@ -1,17 +1,12 @@
/*
- * Copyright (C) 1986-2005 The Free Software Foundation, Inc.
- *
- * Portions Copyright (C) 1998-2005 Derek Price, Ximbiot <http://ximbiot.com>,
- * and others.
- *
- * Portions Copyright (C) 1992, Brian Berliner and Jeff Polk
- * Portions Copyright (C) 1989-1992, Brian Berliner
+ * Copyright (c) 1992, Brian Berliner and Jeff Polk
*
* You may distribute under the terms of the GNU General Public License as
* specified in the README file that comes with the CVS source distribution.
*
* General recursion handler
*
+ * $FreeBSD$
*/
#include "cvs.h"
@@ -140,25 +135,6 @@ start_recursion (fileproc, filesdoneproc, direntproc, dirleaveproc, callerdat,
frame.aflag = aflag;
frame.locktype = locktype;
frame.dosrcs = dosrcs;
-
- /* If our repository_in has a trailing "/.", remove it before storing it
- * for do_recursion().
- *
- * FIXME: This is somewhat of a hack in the sense that many of our callers
- * painstakingly compute and add the trailing '.' we now remove.
- */
- while (repository_in && strlen (repository_in) >= 2
- && repository_in[strlen (repository_in) - 2] == '/'
- && repository_in[strlen (repository_in) - 1] == '.')
- {
- /* Beware the case where the string is exactly "/." or "//.".
- * Paths with a leading "//" are special on some early UNIXes.
- */
- if (strlen (repository_in) == 2 || strlen (repository_in) == 3)
- repository_in[strlen (repository_in) - 1] = '\0';
- else
- repository_in[strlen (repository_in) - 2] = '\0';
- }
frame.repository = repository_in;
expand_wild (argc, argv, &argc, &argv);
@@ -196,24 +172,21 @@ start_recursion (fileproc, filesdoneproc, direntproc, dirleaveproc, callerdat,
&& CVSroot_cmdline == NULL
&& current_parsed_root->isremote)
{
- cvsroot_t *root = Name_Root (NULL, update_dir);
- if (root)
- {
- if (strcmp (root->original, current_parsed_root->original))
- /* We're skipping this directory because it is for
- * a different root. Therefore, we just want to
- * do the subdirectories only. Processing files would
- * cause a working directory from one repository to be
- * processed against a different repository, which could
- * cause all kinds of spurious conflicts and such.
- *
- * Question: what about the case of "cvs update foo"
- * where we process foo/bar and not foo itself? That
- * seems to be handled somewhere (else) but why should
- * it be a separate case? Needs investigation... */
- just_subdirs = 1;
- free_cvsroot_t (root);
- }
+ char *root = Name_Root (NULL, update_dir);
+ if (root && strcmp (root, current_parsed_root->original) != 0)
+ /* We're skipping this directory because it is for
+ a different root. Therefore, we just want to
+ do the subdirectories only. Processing files would
+ cause a working directory from one repository to be
+ processed against a different repository, which could
+ cause all kinds of spurious conflicts and such.
+
+ Question: what about the case of "cvs update foo"
+ where we process foo/bar and not foo itself? That
+ seems to be handled somewhere (else) but why should
+ it be a separate case? Needs investigation... */
+ just_subdirs = 1;
+ free (root);
}
#endif
@@ -334,8 +307,11 @@ start_recursion (fileproc, filesdoneproc, direntproc, dirleaveproc, callerdat,
addfile (&files_by_dir, dir, comp);
else if (isdir (dir))
{
- if ((which & W_LOCAL) && isdir (CVSADM) &&
- !current_parsed_root->isremote)
+ if ((which & W_LOCAL) && isdir (CVSADM)
+#ifdef CLIENT_SUPPORT
+ && !current_parsed_root->isremote
+#endif
+ )
{
/* otherwise, look for it in the repository. */
char *tmp_update_dir;
@@ -591,7 +567,7 @@ do_recursion (frame)
* generating data, to give the buffers a chance to drain to the
* remote client. We should not have locks active at this point,
* but if there are writelocks around, we cannot pause here. */
- if (server_active && locktype != CVS_LOCK_WRITE)
+ if (server_active && locktype != CVS_LOCK_NONE)
server_pause_check();
#endif
@@ -607,41 +583,43 @@ do_recursion (frame)
directories, since we're guaranteed to have only one CVSROOT --
our own. */
- /* If -d was specified, it should override CVS/Root.
+ if (
+ /* If -d was specified, it should override CVS/Root.
+
+ In the single-repository case, it is long-standing CVS behavior
+ and makes sense - the user might want another access method,
+ another server (which mounts the same repository), &c.
- In the single-repository case, it is long-standing CVS behavior
- and makes sense - the user might want another access method,
- another server (which mounts the same repository), &c.
+ In the multiple-repository case, -d overrides all CVS/Root
+ files. That is the only plausible generalization I can
+ think of. */
+ CVSroot_cmdline == NULL
- In the multiple-repository case, -d overrides all CVS/Root
- files. That is the only plausible generalization I can
- think of. */
- if (CVSroot_cmdline == NULL && !server_active)
+#ifdef SERVER_SUPPORT
+ && ! server_active
+#endif
+ )
{
- cvsroot_t *this_root = Name_Root ((char *) NULL, update_dir);
+ char *this_root = Name_Root ((char *) NULL, update_dir);
if (this_root != NULL)
{
- if (findnode (root_directories, this_root->original))
- {
- process_this_directory = !strcmp (current_parsed_root->original,
- this_root->original);
- free_cvsroot_t (this_root);
- }
- else
+ if (findnode (root_directories, this_root) == NULL)
{
/* Add it to our list. */
Node *n = getnode ();
n->type = NT_UNKNOWN;
- n->key = xstrdup (this_root->original);
- n->data = this_root;
+ n->key = xstrdup (this_root);
if (addnode (root_directories, n))
- error (1, 0, "cannot add new CVSROOT %s",
- this_root->original);
-
- process_this_directory = 0;
+ error (1, 0, "cannot add new CVSROOT %s", this_root);
+
}
+
+ process_this_directory =
+ (strcmp (current_parsed_root->original, this_root) == 0);
+
+ free (this_root);
}
}
@@ -704,8 +682,7 @@ do_recursion (frame)
if (repository == NULL)
{
Name_Repository ((char *) NULL, update_dir);
- assert (!"Not reached. Please report this problem to <"
- PACKAGE_BUGREPORT ">");
+ assert (!"Not reached. Please report this problem to <bug-cvs@gnu.org>");
}
/* find the files and fill in entries if appropriate */
@@ -1054,41 +1031,42 @@ but CVS uses %s for its own purposes; skipping %s directory",
/* Only process this directory if the root matches. This nearly
duplicates code in do_recursion. */
- /* If -d was specified, it should override CVS/Root.
+ if (
+ /* If -d was specified, it should override CVS/Root.
+
+ In the single-repository case, it is long-standing CVS behavior
+ and makes sense - the user might want another access method,
+ another server (which mounts the same repository), &c.
- In the single-repository case, it is long-standing CVS behavior
- and makes sense - the user might want another access method,
- another server (which mounts the same repository), &c.
+ In the multiple-repository case, -d overrides all CVS/Root
+ files. That is the only plausible generalization I can
+ think of. */
+ CVSroot_cmdline == NULL
- In the multiple-repository case, -d overrides all CVS/Root
- files. That is the only plausible generalization I can
- think of. */
- if (CVSroot_cmdline == NULL && !server_active)
+#ifdef SERVER_SUPPORT
+ && ! server_active
+#endif
+ )
{
- cvsroot_t *this_root = Name_Root (dir, update_dir);
+ char *this_root = Name_Root (dir, update_dir);
if (this_root != NULL)
{
- if (findnode (root_directories, this_root->original))
- {
- process_this_directory = !strcmp (current_parsed_root->original,
- this_root->original);
- free_cvsroot_t (this_root);
- }
- else
+ if (findnode (root_directories, this_root) == NULL)
{
/* Add it to our list. */
Node *n = getnode ();
n->type = NT_UNKNOWN;
- n->key = xstrdup (this_root->original);
- n->data = this_root;
+ n->key = xstrdup (this_root);
if (addnode (root_directories, n))
- error (1, 0, "cannot add new CVSROOT %s",
- this_root->original);
+ error (1, 0, "cannot add new CVSROOT %s", this_root);
- process_this_directory = 0;
}
+
+ process_this_directory = (strcmp (current_parsed_root->original, this_root) == 0);
+
+ free (this_root);
}
}
diff --git a/contrib/cvs/src/server.c b/contrib/cvs/src/server.c
index 29aab00..e186c34 100644
--- a/contrib/cvs/src/server.c
+++ b/contrib/cvs/src/server.c
@@ -8,6 +8,10 @@
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details. */
+/*
+ * $FreeBSD$
+ */
+
#include <assert.h>
#include "cvs.h"
#include "watch.h"
@@ -16,8 +20,6 @@
#include "getline.h"
#include "buffer.h"
-int server_active = 0;
-
#if defined(SERVER_SUPPORT) || defined(CLIENT_SUPPORT)
# ifdef HAVE_GSSAPI
/* This stuff isn't included solely with SERVER_SUPPORT since some of these
@@ -358,20 +360,13 @@ create_adm_p (base_dir, dir)
dir_where_cvsadm_lives = xmalloc (strlen (base_dir) + strlen (dir) + 100);
if (dir_where_cvsadm_lives == NULL)
- {
- free (p);
return ENOMEM;
- }
/* Allocate some space for the temporary string in which we will
construct filenames. */
tmp = xmalloc (strlen (base_dir) + strlen (dir) + 100);
if (tmp == NULL)
- {
- free (p);
- free (dir_where_cvsadm_lives);
return ENOMEM;
- }
/* We make several passes through this loop. On the first pass,
@@ -782,6 +777,9 @@ E Protocol error: Root says \"%s\" but pserver says \"%s\"",
nothing. But for rsh, we need to do it now. */
parse_config (current_parsed_root->directory);
+ /* Now is a good time to read CVSROOT/options too. */
+ parseopts(current_parsed_root->directory);
+
path = xmalloc (strlen (current_parsed_root->directory)
+ sizeof (CVSROOTADM)
+ 2);
@@ -1236,7 +1234,6 @@ serve_sticky (arg)
if (alloc_pending (80 + strlen (CVSADM_TAG)))
sprintf (pending_error_text, "E cannot write to %s", CVSADM_TAG);
pending_error = save_errno;
- (void) fclose (f);
return;
}
if (fclose (f) == EOF)
@@ -1685,9 +1682,7 @@ serve_unchanged (arg)
* is allowed, but broken versions of WinCVS & TortoiseCVS rely on
* this behavior.
*/
- if (*timefield != '+')
- /* Skip this for entries with conflict markers. */
- *timefield = '=';
+ *timefield = '=';
break;
}
}
@@ -1758,10 +1753,7 @@ serve_is_modified (arg)
* is allowed, but broken versions of WinCVS & TortoiseCVS rely on
* this behavior.
*/
- if (*timefield != '+')
- /* Skip this for entries with conflict markers. */
- *timefield = 'M';
-
+ *timefield = 'M';
if (kopt != NULL)
{
if (alloc_pending (strlen (name) + 80))
@@ -1848,7 +1840,6 @@ serve_entry (arg)
cp = xmalloc (strlen (arg) + 2);
if (cp == NULL)
{
- free (p);
pending_error = ENOMEM;
return;
}
@@ -2712,25 +2703,6 @@ set_nonblock_fd (fd)
-/*
- * Set buffer FD to blocking I/O. Returns 0 for success or errno code.
- */
-int
-set_block_fd (fd)
- int fd;
-{
- int flags;
-
- flags = fcntl (fd, F_GETFL, 0);
- if (flags < 0)
- return errno;
- if (fcntl (fd, F_SETFL, flags & ~O_NONBLOCK) < 0)
- return errno;
- return 0;
-}
-
-
-
static void
do_cvs_command (cmd_name, command)
char *cmd_name;
@@ -2954,31 +2926,22 @@ error \n");
{
char junk;
ssize_t status;
- set_block_fd (flowcontrol_pipe[0]);
- while ((status = read (flowcontrol_pipe[0], &junk, 1)) > 0);
+ while ((status = read (flowcontrol_pipe[0], &junk, 1)) > 0
+ || (status == -1 && errno == EAGAIN));
}
/* FIXME: No point in printing an error message with error(),
* as STDERR is already closed, but perhaps this could be syslogged?
*/
#endif
- rcs_cleanup ();
- Lock_Cleanup ();
- /* Don't call server_cleanup - the parent will handle that. */
-#ifdef SYSTEM_CLEANUP
- /* Hook for OS-specific behavior, for example socket subsystems on
- NT and OS2 or dealing with windows and arguments on Mac. */
- SYSTEM_CLEANUP ();
-#endif
exit (exitstatus);
}
/* OK, sit around getting all the input from the child. */
{
- struct buffer *stdoutbuf = NULL;
- struct buffer *stderrbuf = NULL;
- struct buffer *protocol_inbuf = NULL;
- int err_exit = 0;
+ struct buffer *stdoutbuf;
+ struct buffer *stderrbuf;
+ struct buffer *protocol_inbuf;
/* Number of file descriptors to check in select (). */
int num_to_check;
int count_needed = 1;
@@ -3031,8 +2994,7 @@ error \n");
{
buf_output0 (buf_to_net, "E close failed\n");
print_error (errno);
- err_exit = 1;
- goto child_finish;
+ goto error_exit;
}
stdout_pipe[1] = -1;
@@ -3040,8 +3002,7 @@ error \n");
{
buf_output0 (buf_to_net, "E close failed\n");
print_error (errno);
- err_exit = 1;
- goto child_finish;
+ goto error_exit;
}
stderr_pipe[1] = -1;
@@ -3049,8 +3010,7 @@ error \n");
{
buf_output0 (buf_to_net, "E close failed\n");
print_error (errno);
- err_exit = 1;
- goto child_finish;
+ goto error_exit;
}
protocol_pipe[1] = -1;
@@ -3059,8 +3019,7 @@ error \n");
{
buf_output0 (buf_to_net, "E close failed\n");
print_error (errno);
- err_exit = 1;
- goto child_finish;
+ goto error_exit;
}
flowcontrol_pipe[0] = -1;
#endif /* SERVER_FLOWCONTROL */
@@ -3069,9 +3028,7 @@ error \n");
{
buf_output0 (buf_to_net, "E close failed\n");
print_error (errno);
- dev_null_fd = -1; /* Do not try to close it again. */
- err_exit = 1;
- goto child_finish;
+ goto error_exit;
}
dev_null_fd = -1;
@@ -3158,8 +3115,7 @@ error \n");
{
buf_output0 (buf_to_net, "E select failed\n");
print_error (errno);
- err_exit = 1;
- goto child_finish;
+ goto error_exit;
}
} while (numfds < 0);
@@ -3192,8 +3148,7 @@ error \n");
{
buf_output0 (buf_to_net, "E buf_input_data failed\n");
print_error (status);
- err_exit = 1;
- goto child_finish;
+ goto error_exit;
}
/*
@@ -3267,8 +3222,7 @@ error \n");
{
buf_output0 (buf_to_net, "E buf_input_data failed\n");
print_error (status);
- err_exit = 1;
- goto child_finish;
+ goto error_exit;
}
/* What should we do with errors? syslog() them? */
@@ -3293,8 +3247,7 @@ error \n");
{
buf_output0 (buf_to_net, "E buf_input_data failed\n");
print_error (status);
- err_exit = 1;
- goto child_finish;
+ goto error_exit;
}
/* What should we do with errors? syslog() them? */
@@ -3374,33 +3327,21 @@ E CVS locks may need cleaning up.\n");
command_pid = -1;
}
- child_finish:
/*
* OK, we've waited for the child. By now all CVS locks are free
* and it's OK to block on the network.
*/
set_block (buf_to_net);
buf_flush (buf_to_net, 1);
- if (protocol_inbuf)
- {
- buf_shutdown (protocol_inbuf);
- buf_free (protocol_inbuf);
- protocol_inbuf = NULL;
- }
- if (stderrbuf)
- {
- buf_shutdown (stderrbuf);
- buf_free (stderrbuf);
- stderrbuf = NULL;
- }
- if (stdoutbuf)
- {
- buf_shutdown (stdoutbuf);
- buf_free (stdoutbuf);
- stdoutbuf = NULL;
- }
- if (err_exit)
- goto error_exit;
+ buf_shutdown (protocol_inbuf);
+ buf_free (protocol_inbuf);
+ protocol_inbuf = NULL;
+ buf_shutdown (stderrbuf);
+ buf_free (stderrbuf);
+ stderrbuf = NULL;
+ buf_shutdown (stdoutbuf);
+ buf_free (stdoutbuf);
+ stdoutbuf = NULL;
}
if (errs)
@@ -3424,8 +3365,7 @@ E CVS locks may need cleaning up.\n");
command_pid = -1;
}
- if (dev_null_fd >= 0)
- close (dev_null_fd);
+ close (dev_null_fd);
close (protocol_pipe[0]);
close (protocol_pipe[1]);
close (stderr_pipe[0]);
@@ -3753,10 +3693,6 @@ server_checked_in (file, update_dir, repository)
const char *update_dir;
const char *repository;
{
- assert (file);
- assert (update_dir);
- assert (repository);
-
if (noexec)
return;
if (scratched_file != NULL && entries_line == NULL)
@@ -4190,7 +4126,6 @@ server_updated (finfo, vers, updated, mode, checksum, filebuf)
free (scratched_file);
scratched_file = NULL;
}
- buf_send_counted (protocol);
return;
}
@@ -4269,6 +4204,7 @@ CVS server internal error: no mode in server_updated");
if (updated == SERVER_UPDATED)
{
Node *node;
+ Entnode *entnode;
if (!(supported_response ("Created")
&& supported_response ("Update-existing")))
@@ -4286,13 +4222,9 @@ CVS server internal error: no mode in server_updated");
in case we end up processing it again (e.g. modules3-6
in the testsuite). */
node = findnode_fn (finfo->entries, finfo->file);
- assert (node != NULL);
- if (node != NULL)
- {
- Entnode *entnode = node->data;
- free (entnode->timestamp);
- entnode->timestamp = xstrdup ("=");
- }
+ entnode = node->data;
+ free (entnode->timestamp);
+ entnode->timestamp = xstrdup ("=");
}
else if (updated == SERVER_MERGED)
buf_output0 (protocol, "Merged ");
@@ -4580,12 +4512,9 @@ struct template_proc_data
static struct template_proc_data *tpd;
static int
-template_proc PROTO((const char *repository, const char *template));
-
-static int
template_proc (repository, template)
- const char *repository;
- const char *template;
+ char *repository;
+ char *template;
{
FILE *fp;
char buf[1024];
@@ -4863,7 +4792,6 @@ struct request requests[] =
REQ_LINE("Checkin-time", serve_checkin_time, 0),
REQ_LINE("Modified", serve_modified, RQ_ESSENTIAL),
REQ_LINE("Is-modified", serve_is_modified, 0),
- REQ_LINE("Empty-conflicts", serve_noop, 0),
/* The client must send this request to interoperate with CVS 1.5
through 1.9 servers. The server must support it (although it can
@@ -5118,6 +5046,8 @@ server_cleanup (sig)
}
}
+int server_active = 0;
+
int
server (argc, argv)
int argc;
@@ -5549,7 +5479,6 @@ check_repository_password (username, password, repository, host_user_ptr)
{
if (!existence_error (errno))
error (0, errno, "cannot open %s", filename);
- free (filename);
return 0;
}
@@ -5680,7 +5609,10 @@ check_password (username, password, repository)
password file. If so, that's enough to authenticate with. If
not, we'll check /etc/passwd. */
- rc = check_repository_password (username, password, repository,
+ if (require_real_user)
+ rc = 0; /* "not found" */
+ else
+ rc = check_repository_password (username, password, repository,
&host_user);
if (rc == 2)
@@ -5980,8 +5912,6 @@ pserver_authenticate_connection ()
printf ("I LOVE YOU\n");
fflush (stdout);
- /* It's okay to skip rcs_cleanup() and Lock_Cleanup() here. */
-
#ifdef SYSTEM_CLEANUP
/* Hook for OS-specific behavior, for example socket subsystems on
NT and OS2 or dealing with windows and arguments on Mac. */
@@ -6495,10 +6425,12 @@ cvs_output (str, len)
size_t to_write = len;
const char *p = str;
- /* Local users that do 'cvs status 2>&1' on a local repository
- may see the informational messages out-of-order with the
- status messages unless we use the fflush (stderr) here. */
- fflush (stderr);
+ /* For symmetry with cvs_outerr we would call fflush (stderr)
+ here. I guess the assumption is that stderr will be
+ unbuffered, so we don't need to. That sounds like a sound
+ assumption from the manpage I looked at, but if there was
+ something fishy about it, my guess is that calling fflush
+ would not produce a significant performance problem. */
while (to_write > 0)
{
@@ -6555,16 +6487,16 @@ this client does not support writing binary files to stdout");
size_t written;
size_t to_write = len;
const char *p = str;
+
+ /* For symmetry with cvs_outerr we would call fflush (stderr)
+ here. I guess the assumption is that stderr will be
+ unbuffered, so we don't need to. That sounds like a sound
+ assumption from the manpage I looked at, but if there was
+ something fishy about it, my guess is that calling fflush
+ would not produce a significant performance problem. */
#ifdef USE_SETMODE_STDOUT
int oldmode;
-#endif
-
- /* Local users that do 'cvs status 2>&1' on a local repository
- may see the informational messages out-of-order with the
- status messages unless we use the fflush (stderr) here. */
- fflush (stderr);
-#ifdef USE_SETMODE_STDOUT
/* It is possible that this should be the same ifdef as
USE_SETMODE_BINARY but at least for the moment we keep them
separate. Mostly this is just laziness and/or a question
diff --git a/contrib/cvs/src/stamp-h2.in b/contrib/cvs/src/stamp-h2.in
deleted file mode 100644
index 9788f70..0000000
--- a/contrib/cvs/src/stamp-h2.in
+++ /dev/null
@@ -1 +0,0 @@
-timestamp
diff --git a/contrib/cvs/src/tag.c b/contrib/cvs/src/tag.c
index 6525eb2..903f357 100644
--- a/contrib/cvs/src/tag.c
+++ b/contrib/cvs/src/tag.c
@@ -1,11 +1,6 @@
/*
- * Copyright (C) 1986-2005 The Free Software Foundation, Inc.
- *
- * Portions Copyright (C) 1998-2005 Derek Price, Ximbiot <http://ximbiot.com>,
- * and others.
- *
- * Portions Copyright (C) 1992, Brian Berliner and Jeff Polk
- * Portions Copyright (C) 1989-1992, Brian Berliner
+ * Copyright (c) 1992, Brian Berliner and Jeff Polk
+ * Copyright (c) 1989-1992, Brian Berliner
*
* You may distribute under the terms of the GNU General Public License as
* specified in the README file that comes with the CVS source distribution.
@@ -15,6 +10,8 @@
* Add or delete a symbolic name to an RCS file, or a collection of RCS files.
* Tag uses the checked out revision in the current directory, rtag uses
* the modules database, if necessary.
+ *
+ * $FreeBSD$
*/
#include "cvs.h"
@@ -155,9 +152,11 @@ cvstag (argc, argv)
break;
case 'Q':
case 'q':
+#ifdef SERVER_SUPPORT
/* The CVS 1.5 client sends these options (in addition to
Global_option requests), so we must ignore them. */
if (!server_active)
+#endif
error (1, 0,
"-q or -Q must be specified before \"%s\"",
cvs_cmd_name);
@@ -355,12 +354,11 @@ rtag_proc (argc, argv, xwhere, mwhere, mfile, shorten, local_specified,
{
error (0, errno, "cannot chdir to %s", repository);
free (repository);
- free (where);
return (1);
}
/* End section which is identical to patch_proc. */
- if (delete_flag || force_tag_move || attic_too || numtag)
+ if (delete_flag || attic_too || (force_tag_match && numtag))
which = W_REPOS | W_ATTIC;
else
which = W_REPOS;
@@ -1136,170 +1134,6 @@ val_fileproc (callerdat, finfo)
-/* This routine determines whether a tag appears in CVSROOT/val-tags.
- *
- * The val-tags file will be open read-only when IDB is NULL. Since writes to
- * val-tags always append to it, the lack of locking is okay. The worst case
- * race condition might misinterpret a partially written "foobar" matched, for
- * instance, a request for "f", "foo", of "foob". Such a mismatch would be
- * caught harmlessly later.
- *
- * Before CVS adds a tag to val-tags, it will lock val-tags for write and
- * verify that the tag is still not present to avoid adding it twice.
- *
- * NOTES
- * This function expects its parent to handle any necessary locking of the
- * val-tags file.
- *
- * INPUTS
- * idb When this value is NULL, the val-tags file is opened in
- * in read-only mode. When present, the val-tags file is opened
- * in read-write mode and the DBM handle is stored in *IDB.
- * name The tag to search for.
- *
- * OUTPUTS
- * *idb The val-tags file opened for read/write, or NULL if it couldn't
- * be opened.
- *
- * ERRORS
- * Exits with an error message if the val-tags file cannot be opened for
- * read (failure to open val-tags read/write is harmless - see below).
- *
- * RETURNS
- * true 1. If NAME exists in val-tags.
- * 2. If IDB is non-NULL and val-tags cannot be opened for write.
- * This allows callers to ignore the harmless inability to
- * update the val-tags cache.
- * false If the file could be opened and the tag is not present.
- */
-static int is_in_val_tags PROTO((DBM **idb, const char *name));
-static int
-is_in_val_tags (idb, name)
- DBM **idb;
- const char *name;
-{
- DBM *db = NULL;
- char *valtags_filename;
- datum mytag;
- int status;
-
- /* Casting out const should be safe here - input datums are not
- * written to by the myndbm functions.
- */
- mytag.dptr = (char *)name;
- mytag.dsize = strlen (name);
-
- valtags_filename = xmalloc (strlen (current_parsed_root->directory)
- + sizeof CVSROOTADM
- + sizeof CVSROOTADM_VALTAGS + 3);
- sprintf (valtags_filename, "%s/%s/%s", current_parsed_root->directory,
- CVSROOTADM, CVSROOTADM_VALTAGS);
-
- if (idb)
- {
- db = dbm_open (valtags_filename, O_RDWR, 0666);
- if (!db)
- {
- mode_t omask;
-
- if (!existence_error (errno))
- {
- error (0, errno, "warning: cannot open %s read/write",
- valtags_filename);
- *idb = NULL;
- return 1;
- }
-
- omask = umask (cvsumask);
- db = dbm_open (valtags_filename, O_RDWR | O_CREAT | O_TRUNC, 0666);
- umask (omask);
- if (!db)
- {
- error (0, errno, "warning: cannot create %s",
- valtags_filename);
- *idb = NULL;
- return 1;
- }
-
- *idb = db;
- return 0;
- }
-
- *idb = db;
- }
- else
- {
- db = dbm_open (valtags_filename, O_RDONLY, 0444);
- if (!db && !existence_error (errno))
- error (1, errno, "cannot read %s", valtags_filename);
- }
-
- /* If the file merely fails to exist, we just keep going and create
- it later if need be. */
-
- status = 0;
- if (db)
- {
- datum val;
-
- val = dbm_fetch (db, mytag);
- if (val.dptr != NULL)
- /* Found. The tag is valid. */
- status = 1;
-
- /* FIXME: should check errors somehow (add dbm_error to myndbm.c?). */
-
- if (!idb) dbm_close (db);
- }
-
- free (valtags_filename);
- return status;
-}
-
-
-
-/* Add a tag to the CVSROOT/val-tags cache. Establishes a write lock and
- * reverifies that the tag does not exist before adding it.
- */
-static void add_to_val_tags PROTO((const char *name));
-static void
-add_to_val_tags (name)
- const char *name;
-{
- DBM *db;
- datum mytag;
- datum value;
-
- if (noexec) return;
-
- val_tags_lock (current_parsed_root->directory);
-
- /* Check for presence again since we have a lock now. */
- if (is_in_val_tags (&db, name))
- {
- clear_val_tags_lock ();
- if (db)
- dbm_close (db);
- return;
- }
-
- /* Casting out const should be safe here - input datums are not
- * written to by the myndbm functions.
- */
- mytag.dptr = (char *)name;
- mytag.dsize = strlen (name);
- value.dptr = "y";
- value.dsize = 1;
-
- if (dbm_store (db, mytag, value, DBM_REPLACE) < 0)
- error (0, errno, "failed to store %s into val-tags", name);
- dbm_close (db);
-
- clear_val_tags_lock ();
-}
-
-
-
static Dtype val_direntproc PROTO ((void *, const char *, const char *,
const char *, List *));
@@ -1341,6 +1175,10 @@ tag_check_valid (name, argc, argv, local, aflag, repository)
int aflag;
char *repository;
{
+ DBM *db;
+ char *valtags_filename;
+ int nowrite = 0;
+ datum mytag;
struct val_args the_val_args;
struct saved_cwd cwd;
int which;
@@ -1363,12 +1201,52 @@ Numeric tag %s contains characters other than digits and '.'", name);
|| strcmp (name, TAG_HEAD) == 0)
return;
- /* Verify that the tag is valid syntactically. Some later code once made
- * assumptions about this.
- */
- RCS_check_tag (name);
+ if (readonlyfs)
+ return;
+
+ /* FIXME: This routine doesn't seem to do any locking whatsoever
+ (and it is called from places which don't have locks in place).
+ If two processes try to write val-tags at the same time, it would
+ seem like we are in trouble. */
- if (is_in_val_tags (NULL, name)) return;
+ mytag.dptr = name;
+ mytag.dsize = strlen (name);
+
+ valtags_filename = xmalloc (strlen (current_parsed_root->directory)
+ + sizeof CVSROOTADM
+ + sizeof CVSROOTADM_VALTAGS + 3);
+ sprintf (valtags_filename, "%s/%s/%s", current_parsed_root->directory,
+ CVSROOTADM, CVSROOTADM_VALTAGS);
+ db = dbm_open (valtags_filename, O_RDWR, 0666);
+ if (db == NULL)
+ {
+ if (!existence_error (errno))
+ {
+ error (0, errno, "warning: cannot open %s read/write",
+ valtags_filename);
+ db = dbm_open (valtags_filename, O_RDONLY, 0666);
+ if (db != NULL)
+ nowrite = 1;
+ else if (!existence_error (errno))
+ error (1, errno, "cannot read %s", valtags_filename);
+ }
+ /* If the file merely fails to exist, we just keep going and create
+ it later if need be. */
+ }
+ if (db != NULL)
+ {
+ datum val;
+
+ val = dbm_fetch (db, mytag);
+ if (val.dptr != NULL)
+ {
+ /* Found. The tag is valid. */
+ dbm_close (db);
+ free (valtags_filename);
+ return;
+ }
+ /* FIXME: should check errors somehow (add dbm_error to myndbm.c?). */
+ }
/* We didn't find the tag in val-tags, so look through all the RCS files
to see whether it exists there. Yes, this is expensive, but there
@@ -1413,11 +1291,41 @@ Numeric tag %s contains characters other than digits and '.'", name);
if (!the_val_args.found)
error (1, 0, "no such tag %s", name);
else
+ {
/* The tags is valid but not mentioned in val-tags. Add it. */
- add_to_val_tags (name);
-}
+ datum value;
+ if (noexec || nowrite)
+ {
+ if (db != NULL)
+ dbm_close (db);
+ free (valtags_filename);
+ return;
+ }
+ if (db == NULL)
+ {
+ mode_t omask;
+ omask = umask (cvsumask);
+ db = dbm_open (valtags_filename, O_RDWR | O_CREAT | O_TRUNC, 0666);
+ (void)umask (omask);
+
+ if (db == NULL)
+ {
+ error (0, errno, "warning: cannot create %s", valtags_filename);
+ free (valtags_filename);
+ return;
+ }
+ }
+ value.dptr = "y";
+ value.dsize = 1;
+ if (dbm_store (db, mytag, value, DBM_REPLACE) < 0)
+ error (0, errno, "cannot store %s into %s", name,
+ valtags_filename);
+ dbm_close (db);
+ }
+ free (valtags_filename);
+}
/*
* Check whether a join tag is valid. This is just like
diff --git a/contrib/cvs/src/update.c b/contrib/cvs/src/update.c
index 6f1c937..0ddf3bc 100644
--- a/contrib/cvs/src/update.c
+++ b/contrib/cvs/src/update.c
@@ -1,11 +1,6 @@
/*
- * Copyright (C) 1986-2005 The Free Software Foundation, Inc.
- *
- * Portions Copyright (C) 1998-2005 Derek Price, Ximbiot <http://ximbiot.com>,
- * and others.
- *
- * Portions Copyright (C) 1992, Brian Berliner and Jeff Polk
- * Portions Copyright (C) 1989-1992, Brian Berliner
+ * Copyright (c) 1992, Brian Berliner and Jeff Polk
+ * Copyright (c) 1989-1992, Brian Berliner
*
* You may distribute under the terms of the GNU General Public License as
* specified in the README file that comes with the CVS source distribution.
@@ -36,10 +31,11 @@
* versions, these are updated too. If the -d option was specified, new
* directories added to the repository are automatically created and updated
* as well.
+ *
+ * $FreeBSD$
*/
#include "cvs.h"
-#include <assert.h>
#include "savecwd.h"
#ifdef SERVER_SUPPORT
# include "md5.h"
@@ -101,10 +97,10 @@ static char *join_rev2, *date_rev2;
static int aflag = 0;
static int toss_local_changes = 0;
static int force_tag_match = 1;
+static int pull_template = 0;
static int update_build_dirs = 0;
static int update_prune_dirs = 0;
static int pipeout = 0;
-static int dotemplate = 0;
#ifdef SERVER_SUPPORT
static int patches = 0;
static int rcs_diff_patches = 0;
@@ -129,6 +125,7 @@ static const char *const update_usage[] =
"\t-j rev\tMerge in changes made between current revision and rev.\n",
"\t-I ign\tMore files to ignore (! to reset).\n",
"\t-W spec\tWrappers specification line.\n",
+ "\t-T\tCreate CVS/Template.\n",
"(Specify the --help global option for a list of other help options)\n",
NULL
};
@@ -144,6 +141,7 @@ update (argc, argv)
int c, err;
int local = 0; /* recursive by default */
int which; /* where to look for files and dirs */
+ int xpull_template = 0;
if (argc == -1)
usage (update_usage);
@@ -153,7 +151,7 @@ update (argc, argv)
/* parse the args */
optind = 0;
- while ((c = getopt (argc, argv, "+ApCPflRQqduk:r:D:j:I:W:")) != -1)
+ while ((c = getopt (argc, argv, "+ApCPflRQTqduk:r:D:j:I:W:")) != -1)
{
switch (c)
{
@@ -182,13 +180,18 @@ update (argc, argv)
break;
case 'Q':
case 'q':
+#ifdef SERVER_SUPPORT
/* The CVS 1.5 client sends these options (in addition to
Global_option requests), so we must ignore them. */
if (!server_active)
+#endif
error (1, 0,
"-q or -Q must be specified before \"%s\"",
cvs_cmd_name);
break;
+ case 'T':
+ xpull_template = 1;
+ break;
case 'd':
update_build_dirs = 1;
break;
@@ -199,7 +202,6 @@ update (argc, argv)
tag = optarg;
break;
case 'D':
- if (date) free (date);
date = Make_Date (optarg);
break;
case 'P':
@@ -418,8 +420,8 @@ update (argc, argv)
/* call the command line interface */
err = do_update (argc, argv, options, tag, date, force_tag_match,
local, update_build_dirs, aflag, update_prune_dirs,
- pipeout, which, join_rev1, join_rev2, (char *) NULL, 1,
- (char *) NULL);
+ pipeout, which, join_rev1, join_rev2, (char *) NULL,
+ xpull_template, (char *) NULL);
/* free the space Make_Date allocated if necessary */
if (date != NULL)
@@ -436,7 +438,7 @@ update (argc, argv)
int
do_update (argc, argv, xoptions, xtag, xdate, xforce, local, xbuild, xaflag,
xprune, xpipeout, which, xjoin_rev1, xjoin_rev2, preload_update_dir,
- xdotemplate, repository)
+ xpull_template, repository)
int argc;
char **argv;
char *xoptions;
@@ -452,7 +454,7 @@ do_update (argc, argv, xoptions, xtag, xdate, xforce, local, xbuild, xaflag,
char *xjoin_rev1;
char *xjoin_rev2;
char *preload_update_dir;
- int xdotemplate;
+ int xpull_template;
char *repository;
{
int err = 0;
@@ -467,7 +469,7 @@ do_update (argc, argv, xoptions, xtag, xdate, xforce, local, xbuild, xaflag,
aflag = xaflag;
update_prune_dirs = xprune;
pipeout = xpipeout;
- dotemplate = xdotemplate;
+ pull_template = xpull_template;
/* setup the join support */
join_rev1 = xjoin_rev1;
@@ -519,8 +521,13 @@ do_update (argc, argv, xoptions, xtag, xdate, xforce, local, xbuild, xaflag,
argc, argv, local, which, aflag, CVS_LOCK_READ,
preload_update_dir, 1, repository);
+#ifdef SERVER_SUPPORT
+ if (server_active)
+ return err;
+#endif
+
/* see if we need to sleep before returning to avoid time-stamp races */
- if (!server_active && last_register_time)
+ if (last_register_time)
{
sleep_past (last_register_time);
}
@@ -604,7 +611,7 @@ update_fileproc (callerdat, finfo)
&& tag != NULL
&& finfo->rcs != NULL)
{
- char *rev = RCS_getversion (finfo->rcs, tag, NULL, 1, NULL);
+ char *rev = RCS_getversion (finfo->rcs, tag, date, 1, NULL);
if (rev != NULL
&& !RCS_nodeisbranch (finfo->rcs, tag))
nonbranch = 1;
@@ -676,7 +683,11 @@ update_fileproc (callerdat, finfo)
bakname = backup_file (finfo->file, vers->vn_user);
/* This behavior is sufficiently unexpected to
justify overinformativeness, I think. */
- if (!really_quiet && !server_active)
+#ifdef SERVER_SUPPORT
+ if ((! really_quiet) && (! server_active))
+#else /* ! SERVER_SUPPORT */
+ if (! really_quiet)
+#endif /* SERVER_SUPPORT */
(void) printf ("(Locally modified %s moved to %s)\n",
finfo->file, bakname);
free (bakname);
@@ -691,7 +702,8 @@ update_fileproc (callerdat, finfo)
{
if (vers->ts_conflict)
{
- if (file_has_markers (finfo))
+ if (file_has_conflict (finfo, vers->ts_conflict)
+ || file_has_markers (finfo))
{
write_letter (finfo, 'C');
retval = 1;
@@ -842,7 +854,11 @@ update_filesdone_proc (callerdat, err, repository, update_dir, entries)
if (unlink_file_dir (CVSADM) < 0 && !existence_error (errno))
error (0, errno, "cannot remove %s directory", CVSADM);
}
+#ifdef SERVER_SUPPORT
else if (!server_active && !pipeout)
+#else
+ else if (!pipeout)
+#endif /* SERVER_SUPPORT */
{
/* If there is no CVS/Root file, add one */
if (!isfile (CVSADM_ROOT))
@@ -895,11 +911,15 @@ update_dirent_proc (callerdat, dir, repository, update_dir, entries)
is when update -d is specified, and the working directory
is gone but the subdirectory is still mentioned in
CVS/Entries). */
- /* In the remote case, the client should refrain from
- sending us the directory in the first place. So we
- want to continue to give an error, so clients make
- sure to do this. */
- if (!server_active && !isdir (repository))
+ if (1
+#ifdef SERVER_SUPPORT
+ /* In the remote case, the client should refrain from
+ sending us the directory in the first place. So we
+ want to continue to give an error, so clients make
+ sure to do this. */
+ && !server_active
+#endif
+ && !isdir (repository))
return R_SKIP_ALL;
if (noexec)
@@ -937,7 +957,7 @@ update_dirent_proc (callerdat, dir, repository, update_dir, entries)
via WriteTag. */
0,
0,
- dotemplate);
+ pull_template);
rewrite_tag = 1;
nonbranch = 0;
Subdir_Register (entries, (char *) NULL, dir);
@@ -996,6 +1016,12 @@ update_dirent_proc (callerdat, dir, repository, update_dir, entries)
nonbranch = 0;
}
+ /* keep the CVS/Template file current */
+ if (pull_template)
+ {
+ WriteTemplate (dir, update_dir);
+ }
+
/* initialize the ignore list for this directory */
ignlist = getlist ();
}
@@ -1187,10 +1213,13 @@ scratch_file (finfo, vers)
#endif
if (unlink_file (finfo->file) < 0 && ! existence_error (errno))
error (0, errno, "unable to remove %s", finfo->fullname);
- else if (!server_active)
- {
+ else
+#ifdef SERVER_SUPPORT
/* skip this step when the server is running since
* server_updated should have handled it */
+ if (!server_active)
+#endif
+ {
/* keep the vers structure up to date in case we do a join
* - if there isn't a file, it can't very well have a version number, can it?
*/
@@ -1232,7 +1261,11 @@ checkout_file (finfo, vers_ts, adding, merging, update_server)
/* Don't screw with backup files if we're going to stdout, or if
we are the server. */
- if (!pipeout && !server_active)
+ if (!pipeout
+#ifdef SERVER_SUPPORT
+ && ! server_active
+#endif
+ )
{
backup = xmalloc (strlen (finfo->file)
+ sizeof (CVSADM)
@@ -1324,9 +1357,7 @@ VERS: ", 0);
for us to stat. */
if (stat (vers_ts->srcfile->path, &sb) < 0)
{
-#if defined (SERVER_SUPPORT) || defined (CLIENT_SUPPORT)
buf_free (revbuf);
-#endif /* defined (SERVER_SUPPORT) || defined (CLIENT_SUPPORT) */
error (1, errno, "cannot stat %s",
vers_ts->srcfile->path);
}
@@ -1493,10 +1524,8 @@ VERS: ", 0);
free (backup);
}
-#if defined (SERVER_SUPPORT) || defined (CLIENT_SUPPORT)
if (revbuf != NULL)
buf_free (revbuf);
-#endif /* defined (SERVER_SUPPORT) || defined (CLIENT_SUPPORT) */
return retval;
}
@@ -1697,9 +1726,7 @@ patch_file (finfo, vers_ts, docheckout, file_info, checksum)
retcode = 0;
if (! fail)
{
- int dargc = 0;
- size_t darg_allocated = 0;
- char **dargv = NULL;
+ char *diff_options;
/* If the client does not support the Rcs-diff command, we
send a context diff, and the client must invoke patch.
@@ -1707,13 +1734,16 @@ patch_file (finfo, vers_ts, docheckout, file_info, checksum)
new approach only requires running diff in the server; the
client can handle everything without invoking an external
program. */
- if (!rcs_diff_patches)
+ if (! rcs_diff_patches)
+ {
/* We use -c, not -u, because that is what CVS has
traditionally used. Kind of a moot point, now that
Rcs-diff is preferred, so there is no point in making
the compatibility issues worse. */
- run_add_arg_p (&dargc, &darg_allocated, &dargv, "-c");
+ diff_options = "-c";
+ }
else
+ {
/* Now that diff is librarified, we could be passing -a if
we wanted to. However, it is unclear to me whether we
would want to. Does diff -a, in any significant
@@ -1723,11 +1753,10 @@ patch_file (finfo, vers_ts, docheckout, file_info, checksum)
'binary'. Conversely, do they tend to be much larger
in the bad cases? This needs some more
thought/investigation, I suspect. */
- run_add_arg_p (&dargc, &darg_allocated, &dargv, "-n");
- retcode = diff_exec (file1, file2, NULL, NULL, dargc, dargv,
- finfo->file);
- run_arg_free_p (dargc, dargv);
- free (dargv);
+
+ diff_options = "-n";
+ }
+ retcode = diff_exec (file1, file2, NULL, NULL, diff_options, finfo->file);
/* A retcode of 0 means no differences. 1 means some differences. */
if (retcode != 0
@@ -1918,47 +1947,6 @@ write_letter (finfo, letter)
-/* Reregister a file after a merge. */
-static void
-RegisterMerge PROTO((struct file_info *finfo, Vers_TS *vers,
- const char *backup, int has_conflicts));
-static void
-RegisterMerge (finfo, vers, backup, has_conflicts)
- struct file_info *finfo;
- Vers_TS *vers;
- const char *backup;
- int has_conflicts;
-{
- /* This file is the result of a merge, which means that it has
- been modified. We use a special timestamp string which will
- not compare equal to any actual timestamp. */
- char *cp = NULL;
-
- if (has_conflicts)
- {
- time (&last_register_time);
- cp = time_stamp (finfo->file);
- }
- Register (finfo->entries, finfo->file, vers->vn_rcs ? vers->vn_rcs : "0",
- "Result of merge", vers->options, vers->tag, vers->date, cp);
- if (cp)
- free (cp);
-
-#ifdef SERVER_SUPPORT
- /* Send the new contents of the file before the message. If we
- wanted to be totally correct, we would have the client write
- the message only after the file has safely been written. */
- if (server_active)
- {
- server_copy_file (finfo->file, finfo->update_dir, finfo->repository,
- backup);
- server_updated (finfo, vers, SERVER_MERGED, (mode_t) -1, NULL, NULL);
- }
-#endif
-}
-
-
-
/*
* Do all the magic associated with a file which needs to be merged
*/
@@ -1972,8 +1960,6 @@ merge_file (finfo, vers)
int retcode = 0;
int retval;
- assert (vers->vn_user);
-
/*
* The users currently modified file is moved to a backup file name
* ".#filename.version", so that it will stay around for a few days
@@ -2011,21 +1997,13 @@ merge_file (finfo, vers)
thought needs to go into this, and in the meantime it is safe
to treat any such mismatch as an automatic conflict. -twp */
- retcode = RCS_checkout (finfo->rcs, finfo->file,
- vers->vn_rcs, vers->tag,
- vers->options, NULL, NULL, NULL);
- if (retcode)
- {
- error (0, 0, "failed to check out `%s' file", finfo->fullname);
- error (0, 0, "restoring `%s' from backup file `%s'",
- finfo->fullname, backup);
- rename_file (backup, finfo->file);
- retval = 1;
- goto out;
- }
- xchmod (finfo->file, 1);
+#ifdef SERVER_SUPPORT
+ if (server_active)
+ server_copy_file (finfo->file, finfo->update_dir,
+ finfo->repository, backup);
+#endif
- RegisterMerge (finfo, vers, backup, 1);
+ status = checkout_file (finfo, vers, 0, 1, 1);
/* Is there a better term than "nonmergeable file"? What we
really mean is, not something that CVS cannot or does not
@@ -2059,6 +2037,24 @@ merge_file (finfo, vers)
if (strcmp (vers->options, "-V4") == 0)
vers->options[0] = '\0';
+ /* This file is the result of a merge, which means that it has
+ been modified. We use a special timestamp string which will
+ not compare equal to any actual timestamp. */
+ {
+ char *cp = 0;
+
+ if (status)
+ {
+ (void) time (&last_register_time);
+ cp = time_stamp (finfo->file);
+ }
+ Register (finfo->entries, finfo->file, vers->vn_rcs,
+ "Result of merge", vers->options, vers->tag,
+ vers->date, cp);
+ if (cp)
+ free (cp);
+ }
+
/* fix up the vers structure, in case it is used by join */
if (join_rev1)
{
@@ -2069,7 +2065,19 @@ merge_file (finfo, vers)
vers->vn_user = xstrdup (vers->vn_rcs);
}
- RegisterMerge (finfo, vers, backup, status);
+#ifdef SERVER_SUPPORT
+ /* Send the new contents of the file before the message. If we
+ wanted to be totally correct, we would have the client write
+ the message only after the file has safely been written. */
+ if (server_active)
+ {
+ server_copy_file (finfo->file, finfo->update_dir, finfo->repository,
+ backup);
+ server_updated (finfo, vers, SERVER_MERGED,
+ (mode_t) -1, (unsigned char *) NULL,
+ (struct buffer *) NULL);
+ }
+#endif
/* FIXME: the noexec case is broken. RCS_merge could be doing the
xcmp on the temporary files without much hassle, I think. */
@@ -2663,7 +2671,31 @@ join_file (finfo, vers)
RCS_checkout above, and we aren't running as the server.
However, that is not the normal case, and calling Register
again won't cost much in that case. */
- RegisterMerge (finfo, vers, backup, status);
+ {
+ char *cp = 0;
+
+ if (status)
+ {
+ (void) time (&last_register_time);
+ cp = time_stamp (finfo->file);
+ }
+ Register (finfo->entries, finfo->file,
+ vers->vn_rcs ? vers->vn_rcs : "0", "Result of merge",
+ vers->options, vers->tag, vers->date, cp);
+ if (cp)
+ free(cp);
+ }
+
+#ifdef SERVER_SUPPORT
+ if (server_active)
+ {
+ server_copy_file (finfo->file, finfo->update_dir, finfo->repository,
+ backup);
+ server_updated (finfo, vers, SERVER_MERGED,
+ (mode_t) -1, (unsigned char *) NULL,
+ (struct buffer *) NULL);
+ }
+#endif
out:
free (rev1);
diff --git a/contrib/cvs/src/update.h b/contrib/cvs/src/update.h
index 8d581b1..c886b4c 100644
--- a/contrib/cvs/src/update.h
+++ b/contrib/cvs/src/update.h
@@ -10,10 +10,14 @@
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details. */
+/*
+ * $FreeBSD$
+ */
+
int do_update PROTO((int argc, char *argv[], char *xoptions, char *xtag,
char *xdate, int xforce, int local, int xbuild,
int xaflag, int xprune, int xpipeout, int which,
char *xjoin_rev1, char *xjoin_rev2, char *preload_update_dir,
- int xdotemplate, char *repository));
+ int xpull_template, char *repository));
int joining PROTO((void));
extern int isemptydir PROTO ((const char *dir, int might_not_exist));
diff --git a/contrib/cvs/src/version.c.in b/contrib/cvs/src/version.c.in
deleted file mode 100644
index aa2f97f..0000000
--- a/contrib/cvs/src/version.c.in
+++ /dev/null
@@ -1,86 +0,0 @@
-/*
- * Copyright (c) 1994 david d `zoo' zuhn
- * Copyright (c) 1994 Free Software Foundation, Inc.
- * Copyright (c) 1992, Brian Berliner and Jeff Polk
- * Copyright (c) 1989-1992, Brian Berliner
- *
- * You may distribute under the terms of the GNU General Public License as
- * specified in the README file that comes with this CVS source distribution.
- *
- * version.c - the CVS version number
- */
-
-#include "cvs.h"
-
-char *version_string = "Concurrent Versions System (CVS) @VERSION@";
-
-#ifdef CLIENT_SUPPORT
-#ifdef SERVER_SUPPORT
-char *config_string = " (client/server)\n";
-#else
-char *config_string = " (client)\n";
-#endif
-#else
-#ifdef SERVER_SUPPORT
-char *config_string = " (server)\n";
-#else
-char *config_string = "\n";
-#endif
-#endif
-
-
-
-static const char *const version_usage[] =
-{
- "Usage: %s %s\n",
- NULL
-};
-
-
-
-/*
- * Output a version string for the client and server.
- *
- * This function will output the simple version number (for the '--version'
- * option) or the version numbers of the client and server (using the 'version'
- * command).
- */
-int
-version (argc, argv)
- int argc;
- char **argv;
-{
- int err = 0;
-
- if (argc == -1)
- usage (version_usage);
-
-#ifdef CLIENT_SUPPORT
- if (current_parsed_root && current_parsed_root->isremote)
- (void) fputs ("Client: ", stdout);
-#endif
-
- /* Having the year here is a good idea, so people have
- some idea of how long ago their version of CVS was
- released. */
- (void) fputs (version_string, stdout);
- (void) fputs (config_string, stdout);
-
-#ifdef CLIENT_SUPPORT
- if (current_parsed_root && current_parsed_root->isremote)
- {
- (void) fputs ("Server: ", stdout);
- start_server ();
- if (supported_request ("version"))
- send_to_server ("version\012", 0);
- else
- {
- send_to_server ("noop\012", 0);
- fputs ("(unknown)\n", stdout);
- }
- err = get_responses_and_close ();
- }
-#endif
- return err;
-}
-
diff --git a/contrib/cvs/src/version.h.in b/contrib/cvs/src/version.h.in
deleted file mode 100644
index 48580cb..0000000
--- a/contrib/cvs/src/version.h.in
+++ /dev/null
@@ -1,15 +0,0 @@
-/* -*- c -*-
- *
- * Copyright (c) 1992, Brian Berliner and Jeff Polk
- * Copyright (c) 1989-1992, Brian Berliner
- *
- * You may distribute under the terms of the GNU General Public License as
- * specified in the README file that comes with the CVS kit.
- */
-
-#ifndef VERSION_H
-#define VERSION_H 1
-
-#define version_string "Concurrent Versions System (CVS) @VERSION@"
-
-#endif /* VERSION_H */
OpenPOWER on IntegriCloud