From 35fec647c3ad2bcde43d5b2b882e8ce8eaa4a2a1 Mon Sep 17 00:00:00 2001 From: YONETANI Tomokazu Date: Wed, 17 Jan 2007 17:56:24 +0000 Subject: [PATCH] Teach rcs utils about commitid phrase. NOTE: commands don't emit the phrase into RCS files unless you compile them with RCS_EMIT_COMMITID=yes. Taken-from: contrib/rcs-5.7-commitid.patch which came with cvs-1.12.13 --- gnu/usr.bin/rcs/Makefile.inc | 6 +++ gnu/usr.bin/rcs/ci/ci.c | 85 ++++++++++++++++++++++++++++++++++- gnu/usr.bin/rcs/lib/rcsbase.h | 11 ++++- gnu/usr.bin/rcs/lib/rcsgen.c | 8 +++- gnu/usr.bin/rcs/lib/rcssyn.c | 12 ++++- gnu/usr.bin/rcs/rcs/rcsfile.5 | 15 ++++++- gnu/usr.bin/rcs/rlog/rlog.c | 8 +++- 7 files changed, 134 insertions(+), 11 deletions(-) diff --git a/gnu/usr.bin/rcs/Makefile.inc b/gnu/usr.bin/rcs/Makefile.inc index 22d60d7246..dc2cacbea4 100644 --- a/gnu/usr.bin/rcs/Makefile.inc +++ b/gnu/usr.bin/rcs/Makefile.inc @@ -1,3 +1,4 @@ +# $DragonFly: src/gnu/usr.bin/rcs/Makefile.inc,v 1.2 2007/01/17 17:56:23 y0netan1 Exp $ # Location of librcs .if exists(${.OBJDIR}/../lib) @@ -5,3 +6,8 @@ LIBRCS= ${.OBJDIR}/../lib/librcs.a .else LIBRCS= ${.CURDIR}/../lib/librcs.a .endif + +# by default, don't emit commitid phrase into RCS files +.if RCS_EMIT_COMMITID +CFLAGS+= -DRCS_EMIT_COMMITID +.endif diff --git a/gnu/usr.bin/rcs/ci/ci.c b/gnu/usr.bin/rcs/ci/ci.c index ae17c00f02..db630fe2b6 100644 --- a/gnu/usr.bin/rcs/ci/ci.c +++ b/gnu/usr.bin/rcs/ci/ci.c @@ -29,7 +29,7 @@ Report problems and direct all questions to: /* * $FreeBSD: src/gnu/usr.bin/rcs/ci/ci.c,v 1.7 1999/08/27 23:36:38 peter Exp $ - * $DragonFly: src/gnu/usr.bin/rcs/ci/ci.c,v 1.2 2003/06/17 04:25:47 dillon Exp $ + * $DragonFly: src/gnu/usr.bin/rcs/ci/ci.c,v 1.3 2007/01/17 17:56:23 y0netan1 Exp $ * * Revision 5.30 1995/06/16 06:19:24 eggert * Update FSF address. @@ -264,6 +264,10 @@ static void cleanup P((void)); static void incnum P((char const*,struct buf*)); static void addassoclst P((int,char const*)); +enum {RANDOM_BYTES = 8}; +enum {COMMITID_RAW_SIZE = (sizeof(time_t) + RANDOM_BYTES)}; +static void convert P((char const input[COMMITID_RAW_SIZE], char *output)); + static FILE *exfile; static RILE *workptr; /* working file pointer */ static struct buf newdelnum; /* new revision number */ @@ -277,7 +281,7 @@ static struct hshentry newdelta; /* new delta to be inserted */ static struct stat workstat; static struct Symrev *assoclst, **nextassoc; -mainProg(ciId, "ci", "$DragonFly: src/gnu/usr.bin/rcs/ci/ci.c,v 1.2 2003/06/17 04:25:47 dillon Exp $") +mainProg(ciId, "ci", "$DragonFly: src/gnu/usr.bin/rcs/ci/ci.c,v 1.3 2007/01/17 17:56:23 y0netan1 Exp $") { static char const cmdusage[] = "\nci usage: ci -{fIklMqru}[rev] -d[date] -mmsg -{nN}name -sstate -ttext -T -Vn -wwho -xsuff -zzone file ..."; @@ -287,6 +291,7 @@ mainProg(ciId, "ci", "$DragonFly: src/gnu/usr.bin/rcs/ci/ci.c,v 1.2 2003/06/17 0 char olddate[datesize]; char newdatebuf[datesize + zonelenmax]; char targetdatebuf[datesize + zonelenmax]; + char commitid[commitidsize]; char *a, **newargv, *textfile; char const *author, *krev, *rev, *state; char const *diffname, *expname; @@ -311,6 +316,45 @@ mainProg(ciId, "ci", "$DragonFly: src/gnu/usr.bin/rcs/ci/ci.c,v 1.2 2003/06/17 0 suffixes = X_DEFAULT; nextassoc = &assoclst; + { + char buf[COMMITID_RAW_SIZE] = { 0, }; + ssize_t len = 0; + time_t rightnow = time (NULL); + char *startrand = buf + sizeof (time_t); + unsigned char *p = (unsigned char *) startrand; + size_t randbytes = RANDOM_BYTES; + int flags = O_RDONLY; + int fd; +#ifdef O_NOCTTY + flags |= O_NOCTTY; +#endif + if (rightnow != (time_t)-1) + while (rightnow > 0) { + *--p = rightnow % (UCHAR_MAX + 1); + rightnow /= UCHAR_MAX + 1; + } + else { + /* try to use more random data */ + randbytes = COMMITID_RAW_SIZE; + startrand = buf; + } + fd = open (urandom_dev, flags); + if (fd >= 0) { + len = read (fd, startrand, randbytes); + close (fd); + } + if (len <= 0) { + /* no random data was available so use pid */ + long int pid = (long int)getpid (); + p = (unsigned char *) (startrand + sizeof (pid)); + while (pid > 0) { + *--p = pid % (UCHAR_MAX + 1); + pid /= UCHAR_MAX + 1; + } + } + convert(buf, commitid); + } + argc = getRCSINIT(argc, argv, &newargv); argv = newargv; while (a = *++argv, 0<--argc && *a++=='-') { @@ -534,6 +578,8 @@ mainProg(ciId, "ci", "$DragonFly: src/gnu/usr.bin/rcs/ci/ci.c,v 1.2 2003/06/17 0 newdelta.name = 0; clear_buf(&newdelta.ig); clear_buf(&newdelta.igtext); + /* set commitid */ + newdelta.commitid = commitid; /* set author */ if (author) newdelta.author=author; /* set author given by -w */ @@ -1319,3 +1365,38 @@ addassoclst(flag, sp) *nextassoc = pt; nextassoc = &pt->nextsym; } + +static char const alphabet[62] = + "0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ"; + +/* Divide BUF by D, returning the remainder. Replace BUF by the + quotient. BUF[0] is the most significant part of BUF. + D must not exceed UINT_MAX >> CHAR_BIT. */ +static unsigned int +divide_by (unsigned char buf[COMMITID_RAW_SIZE], unsigned int d) +{ + unsigned int carry = 0; + int i; + for (i = 0; i < COMMITID_RAW_SIZE; i++) + { + unsigned int byte = buf[i]; + unsigned int dividend = (carry << CHAR_BIT) + byte; + buf[i] = dividend / d; + carry = dividend % d; + } + return carry; +} + +static void +convert (char const input[COMMITID_RAW_SIZE], char *output) +{ + static char const zero[COMMITID_RAW_SIZE] = { 0, }; + unsigned char buf[COMMITID_RAW_SIZE]; + size_t o = 0; + memcpy (buf, input, COMMITID_RAW_SIZE); + while (memcmp (buf, zero, COMMITID_RAW_SIZE) != 0) + output[o++] = alphabet[divide_by (buf, sizeof alphabet)]; + if (! o) + output[o++] = '0'; + output[o] = '\0'; +} diff --git a/gnu/usr.bin/rcs/lib/rcsbase.h b/gnu/usr.bin/rcs/lib/rcsbase.h index 1a1c4781c9..1288615fae 100644 --- a/gnu/usr.bin/rcs/lib/rcsbase.h +++ b/gnu/usr.bin/rcs/lib/rcsbase.h @@ -1,6 +1,6 @@ /* RCS common definitions and data structures */ -#define RCSBASE "$DragonFly: src/gnu/usr.bin/rcs/lib/rcsbase.h,v 1.2 2003/06/17 04:25:47 dillon Exp $" +#define RCSBASE "$DragonFly: src/gnu/usr.bin/rcs/lib/rcsbase.h,v 1.3 2007/01/17 17:56:23 y0netan1 Exp $" /* Copyright 1982, 1988, 1989 Walter Tichy Copyright 1990, 1991, 1992, 1993, 1994, 1995 Paul Eggert @@ -31,7 +31,7 @@ Report problems and direct all questions to: /* * $FreeBSD: src/gnu/usr.bin/rcs/lib/rcsbase.h,v 1.10 1999/08/27 23:36:44 peter Exp $ - * $DragonFly: src/gnu/usr.bin/rcs/lib/rcsbase.h,v 1.2 2003/06/17 04:25:47 dillon Exp $ + * $DragonFly: src/gnu/usr.bin/rcs/lib/rcsbase.h,v 1.3 2007/01/17 17:56:23 y0netan1 Exp $ * * Revision 5.20 1995/06/16 06:19:24 eggert * Update FSF address. @@ -224,6 +224,11 @@ Report problems and direct all questions to: /* 1 sets the default locking to strict; */ /* used in production environments. */ +/* base64_encode(128 random bits) needs 24 bytes + 1 for NUL */ +/* time_t may be 64bits on some machines needs 16 bytes + 1 as hex */ +#define commitidsize 64 /* time+1+base64(128bits)+1 | pid+time+rand+1 */ +#define urandom_dev "/dev/urandom" + #define yearlength 16 /* (good through AD 9,999,999,999,999,999) */ #define datesize (yearlength+16) /* size of output of time2date */ #define RCSTMPPREFIX '_' /* prefix for temp files in working dir */ @@ -360,6 +365,7 @@ struct hshentry { char const * lockedby; /* who locks the revision */ char const * state; /* state of revision (Exp by default) */ char const * name; /* name (if any) by which retrieved */ + char const * commitid; /* text string to associate commits */ struct cbuf log; /* log message requested at checkin */ struct branchhead * branches; /* list of first revisions on branches*/ struct cbuf ig; /* ignored phrases in admin part */ @@ -670,6 +676,7 @@ extern int TotalDeltas; extern char const *const expand_names[]; extern char const Kaccess[], Kauthor[], Kbranch[], Kcomment[], + Kcommitid[], Kdate[], Kdesc[], Kexpand[], Khead[], Klocks[], Klog[], Knext[], Kstate[], Kstrict[], Ksymbols[], Ktext[]; void unexpected_EOF P((void)) exiting; diff --git a/gnu/usr.bin/rcs/lib/rcsgen.c b/gnu/usr.bin/rcs/lib/rcsgen.c index f344191ee4..2b0d11517d 100644 --- a/gnu/usr.bin/rcs/lib/rcsgen.c +++ b/gnu/usr.bin/rcs/lib/rcsgen.c @@ -29,7 +29,7 @@ Report problems and direct all questions to: /* * $FreeBSD: src/gnu/usr.bin/rcs/lib/rcsgen.c,v 1.7 1999/08/27 23:36:46 peter Exp $ - * $DragonFly: src/gnu/usr.bin/rcs/lib/rcsgen.c,v 1.2 2003/06/17 04:25:47 dillon Exp $ + * $DragonFly: src/gnu/usr.bin/rcs/lib/rcsgen.c,v 1.3 2007/01/17 17:56:23 y0netan1 Exp $ * * Revision 5.16 1995/06/16 06:19:24 eggert * Update FSF address. @@ -143,7 +143,7 @@ Report problems and direct all questions to: #include "rcsbase.h" -libId(genId, "$DragonFly: src/gnu/usr.bin/rcs/lib/rcsgen.c,v 1.2 2003/06/17 04:25:47 dillon Exp $") +libId(genId, "$DragonFly: src/gnu/usr.bin/rcs/lib/rcsgen.c,v 1.3 2007/01/17 17:56:23 y0netan1 Exp $") int interactiveflag; /* Should we act as if stdin is a tty? */ struct buf curlogbuf; /* buffer for current log message */ @@ -549,6 +549,10 @@ putdelta(node, fout) aprintf(fout, ";\n%s\t%s;\n", Knext, node->next?node->next->num:""); awrite(node->ig.string, node->ig.size, fout); +#ifdef RCS_EMIT_COMMITID + if (node->commitid) + aprintf(fout, "%s\t%s;\n", Kcommitid, node->commitid); +#endif } diff --git a/gnu/usr.bin/rcs/lib/rcssyn.c b/gnu/usr.bin/rcs/lib/rcssyn.c index d4d943d4f5..f530ee4f04 100644 --- a/gnu/usr.bin/rcs/lib/rcssyn.c +++ b/gnu/usr.bin/rcs/lib/rcssyn.c @@ -37,7 +37,7 @@ Report problems and direct all questions to: /* * $FreeBSD: src/gnu/usr.bin/rcs/lib/rcssyn.c,v 1.7 1999/08/27 23:36:48 peter Exp $ - * $DragonFly: src/gnu/usr.bin/rcs/lib/rcssyn.c,v 1.2 2003/06/17 04:25:47 dillon Exp $ + * $DragonFly: src/gnu/usr.bin/rcs/lib/rcssyn.c,v 1.3 2007/01/17 17:56:23 y0netan1 Exp $ * * Revision 5.15 1995/06/16 06:19:24 eggert * Update FSF address. @@ -156,7 +156,7 @@ Report problems and direct all questions to: #include "rcsbase.h" -libId(synId, "$DragonFly: src/gnu/usr.bin/rcs/lib/rcssyn.c,v 1.2 2003/06/17 04:25:47 dillon Exp $") +libId(synId, "$DragonFly: src/gnu/usr.bin/rcs/lib/rcssyn.c,v 1.3 2007/01/17 17:56:23 y0netan1 Exp $") static char const *getkeyval P((char const*,enum tokens,int)); static int getdelta P((void)); @@ -173,6 +173,7 @@ char const Kauthor[] = "author", Kbranch[] = "branch", Kcomment[] = "comment", + Kcommitid[] = "commitid", Kdate[] = "date", Kdesc[] = "desc", Kexpand[] = "expand", @@ -435,6 +436,13 @@ getdelta() Delta->lockedby = 0; Delta->log.string = 0; Delta->selector = true; + + if (getkeyopt(Kcommitid)) { + Delta->commitid = NextString; + nextlex(); + getsemi(Kcommitid); + } + Delta->ig = getphrases(Kdesc); TotalDeltas++; return (true); diff --git a/gnu/usr.bin/rcs/rcs/rcsfile.5 b/gnu/usr.bin/rcs/rcs/rcsfile.5 index 595e805807..011babc866 100644 --- a/gnu/usr.bin/rcs/rcs/rcsfile.5 +++ b/gnu/usr.bin/rcs/rcs/rcsfile.5 @@ -6,7 +6,7 @@ .ds Dt \\$4 .. .Id $FreeBSD: src/gnu/usr.bin/rcs/rcs/rcsfile.5,v 1.5.2.1 2001/07/22 11:01:34 dd Exp $ -.Id $DragonFly: src/gnu/usr.bin/rcs/rcs/rcsfile.5,v 1.2 2003/06/17 04:25:47 dillon Exp $ +.Id $DragonFly: src/gnu/usr.bin/rcs/rcs/rcsfile.5,v 1.3 2007/01/17 17:56:23 y0netan1 Exp $ .ds r \s-1RCS\s0 .if n .ds - \%-- .if t .ds - \(em @@ -70,6 +70,7 @@ nonterminal symbols are in \f3state\fP {\f2id\fP}\f3;\fP \f3branches\fP {\f2num\fP}*\f3;\fP \f3next\fP {\f2num\fP}\f3;\fP + { \f3commitid\fP \f2id\fP\f3;\fP } { \f2newphrase\fP }* .LP \f2desc\fP ::= \f3desc\fP \f2string\fP @@ -129,6 +130,18 @@ and all the digits of years thereafter. Dates use the Gregorian calendar; times use UTC. .PP The +.I commitid +is followed by an +.I id +token. This token is intended to be unique across +multiple files and is used to help group files as +being a part of the same logical commit. +This token must uniquely identify the commit +operation that was applied to a set of RCS files. +In particular, it must be unique among all the +commitids in this file. +.PP +The .I newphrase productions in the grammar are reserved for future extensions to the format of \*r files. diff --git a/gnu/usr.bin/rcs/rlog/rlog.c b/gnu/usr.bin/rcs/rlog/rlog.c index 4ce55364ad..a063009b1d 100644 --- a/gnu/usr.bin/rcs/rlog/rlog.c +++ b/gnu/usr.bin/rcs/rlog/rlog.c @@ -29,7 +29,7 @@ Report problems and direct all questions to: /* * $FreeBSD: src/gnu/usr.bin/rcs/rlog/rlog.c,v 1.13 1999/08/27 23:36:59 peter Exp $ - * $DragonFly: src/gnu/usr.bin/rcs/rlog/rlog.c,v 1.2 2003/06/17 04:25:48 dillon Exp $ + * $DragonFly: src/gnu/usr.bin/rcs/rlog/rlog.c,v 1.3 2007/01/17 17:56:24 y0netan1 Exp $ * * Revision 5.18 1995/06/16 06:19:24 eggert * Update FSF address. @@ -221,7 +221,7 @@ static struct rcslockers *lockerlist; static struct stateattri *statelist; -mainProg(rlogId, "rlog", "$DragonFly: src/gnu/usr.bin/rcs/rlog/rlog.c,v 1.2 2003/06/17 04:25:48 dillon Exp $") +mainProg(rlogId, "rlog", "$DragonFly: src/gnu/usr.bin/rcs/rlog/rlog.c,v 1.3 2007/01/17 17:56:24 y0netan1 Exp $") { static char const cmdusage[] = "\nrlog usage: rlog -{bhLNRt} -v[string] -ddates -l[lockers] -r[revs] -sstates -Vn -w[logins] -xsuff -zzone file ..."; @@ -608,6 +608,10 @@ putadelta(node,editscript,trunk) aprintf(out, insDelFormat, editscript->insertlns, editscript->deletelns); + if ( node->commitid ) + aprintf(out, "%s commitid: %s", (editscript) ? ";" : "", + node->commitid); + newbranch = node->branches; if ( newbranch ) { bufautobegin(&branchnum); -- 2.41.0