#
# add_file "contrib/color-logs.conf"
#
# add_file "contrib/color-logs.sh"
#
# add_file "contrib/colorize"
#
# add_file "tests/t_cvsimport_drepper.at"
#
# patch ".mt-attrs"
# from [b4c4b693c754f78c28d144292a0d0df06faa62f8]
# to [8287c8c8f48067074ca9e114e6aec78129343f60]
#
# patch "AUTHORS"
# from [386be208f66b07711c9efa9cc8dc0e190fa73028]
# to [18efd7462a60094848537d1248f3e668742bfe8e]
#
# patch "ChangeLog"
# from [07b4679d42733e2cb232ac6f018b030757504e7d]
# to [eff8ef8c62509c7896de7251bb0e6ea8d232977a]
#
# patch "HACKING"
# from [78f1b3b23bb59c292a2c3a48498459ad04b84c76]
# to [fa38cc2e96dca42b05a7626d34fcf7e4d8153bcc]
#
# patch "ROADMAP"
# from [97276b1ae6610c5689ca34f24f3f9caa22adaa2a]
# to [53568f4fbd5d01ef09b991793d62f0fd2a0db58f]
#
# patch "app_state.hh"
# from [433dcbd86d2fe9c42c3dea7f040fb91c46b50181]
# to [3266667ef8e90abd725cb10983bbe1601c5d2c9f]
#
# patch "commands.cc"
# from [be0e553d14793c7bef3b571d4720b585c5aa5a51]
# to [b4a8b40fbd2c97bc630799687fd94fcdaed28dbf]
#
# patch "contrib/color-logs.conf"
# from []
# to [87e8ceac1e0a8d173e2a0da01e659d048824e9ed]
#
# patch "contrib/color-logs.sh"
# from []
# to [4e04daeee4ee8ce8bf6ce45f074ba16faf50ccf9]
#
# patch "contrib/colorize"
# from []
# to [6d186a777205d4a1bae5b7fc7b6bf52fc6d83df5]
#
# patch "contrib/monotone.el"
# from [46193b52a598228308de18d5c68d8305e3f73ff7]
# to [dc3c1211a531746927242f54befc07788919a112]
#
# patch "monotone.cc"
# from [5781246877c376fef884c42a387937348a33ce52]
# to [99699fececcf92d3614b04a713b767ffa143a091]
#
# patch "options.hh"
# from [7d6df419138742a4831a9db4a2c4a5b8225e38ba]
# to [8246a992a8c10a7ca13ae99108d44d13b38f6950]
#
# patch "rcs_import.cc"
# from [3920e37253b081cba66a26cb685da63f824d3bb7]
# to [c66a01c367b2ded87017c0bec6d0418c46234558]
#
# patch "revision.cc"
# from [58a437f9ad3145e4edf8a176319e9c97a15febf7]
# to [277c60b5acdedb97fe5cf8930b5f5452063abfd8]
#
# patch "revision.hh"
# from [810c1d47de4549a1e13d7e94b2fb4fe55c8df338]
# to [f7908f72891c0b5b1be2c2533e743e5c99456b02]
#
# patch "tests/t_cvsimport_drepper.at"
# from []
# to [fa1e2cb90749522674c28871a9a9971c7984c34c]
#
# patch "testsuite.at"
# from [d33d13c6d066135f5a93c8a721209b27715fb75b]
# to [cf4de323a000b8dc76eff061d7be4abb382ced77]
#
--- .mt-attrs
+++ .mt-attrs
@@ -1,6 +1,12 @@
file "contrib/ciabot_monotone.py"
execute "true"
+ file "contrib/color-logs.sh"
+execute "true"
+
+ file "contrib/colorize"
+execute "true"
+
file "contrib/get_stdio.pl"
execute "true"
--- AUTHORS
+++ AUTHORS
@@ -210,6 +210,10 @@
It's reproduced in popt/COPYING.
+The file contrib/colorize is a copy of a perl script written by Cédric
+Bouvier, which is released under the GNU GPL.
+
+
copyright status:
-----------------
--- ChangeLog
+++ ChangeLog
@@ -1,3 +1,25 @@
+2005-06-02 graydon hoare
+
+ * rcs_import.cc
+ (cvs_key::is_synthetic_branch_founding_commit): New field.
+ (cvs_key::operator==): Handle synthetic case specially.
+ (cvs_key::operator<): Likewise.
+ (push_branch): Likewise.
+ * tests/t_cvsimport_drepper.at: Converted bug testcase.
+ * testsuite.at: Call it.
+
+ * monotone.cc, commands.cc, options.hh
+ (OPT_NO_MERGES, OPT_DIFFS): New options.
+ * app_state.cc (app_state::no_merges, app_state::diffs): Likewise.
+ * commands.cc (log): Honor no_merges, diffs.
+ * contrib/color_logs.{sh,conf}: Helpers for reviewing work in a
+ nice colorized, easy-to-read fashion.
+ * contrib/colorize: A colorization script found on the net.
+
+ * HACKING, ROADMAP: Expand a bit.
+ * commands.cc (changes_summary::print): Change macro to helper fn.
+ * contrib/monotone.el (monotone-cmd): Handle nil exit code.
+
2005-06-01 Matt Johnston
* tests/t_i18n_changelog.at: capitalise UTF-8 CHARSET to keep
--- HACKING
+++ HACKING
@@ -27,6 +27,70 @@
versions into monotone.
+Dialect issues
+--------------
+
+C++ is a big language with a lot of dialects spoken in different
+projects. monotone is no exception; we would prefer submissions
+continued to adhere to the dialect we write in. in particular:
+
+
+ - try to stick to simple functions and data types; don't make big
+ complicated class hierarchies with a lot of interdependencies.
+
+ - avoid pointers whenever possible. if you need to use a handle to a
+ heap allocated object, use a shared_ptr, scoped_ptr, weak_ptr, or
+ the like.
+
+ - if a value has a clearly defined well-formedness condition,
+ encapsulate the value in an object and make the constructors
+ and mutators check the condition. see vocab.hh for string-valued
+ examples.
+
+ - in general, try to express both issues and semantically rich
+ names in the type system. use typedefs to make names more
+ meaningful.
+
+ - avoid returning values, especially large ones. instead, pass a
+ value as a parameter, by reference, clear it and assign into
+ it. this style generally produces fewer invocations of copy
+ constructors, and makes it natural to add multiple, named output
+ parameters from a function.
+
+ - use invariants and logging liberally.
+
+ - make everything as const-correct as possible. make query methods
+ on objects const. make the input parameters to a function const.
+ the word "const" comes after the thing which is constant; for
+ example write "int const" rather than "const int".
+
+ - separate pointer and reference types with space. write "int * foo"
+ rather than "int *foo" or "int* foo".
+
+ - put the name of a function in the first column of the line it
+ occurs on. the visibility and return type go on the preceeding
+ line.
+
+ - use enums rather than magic constants, if you can.
+
+ - magic constants, when needed, go in constants.{cc,hh}.
+
+ - generally avoid the preprocessor unless you have a matter which is
+ very difficult to express using inlines, reference args,
+ templates, etc.
+
+ - avoid indexing into an array or vector with []. use idx(vec,i),
+ and you will get a nicely informative runtime error when you
+ overflow rather than a crash.
+
+ - avoid recursion, so that you will not overflow the stack on large
+ work sets. use a heap-allocated std::deque<> for breadth-first
+ recursion, std::stack<> for depth-first.
+
+ - generally avoid anything which can generate a SEGV, as it's an
+ uninformative error. prefer errors which say what went wrong.
+
+
Test suites, and writing test cases
----------------------------------
--- ROADMAP
+++ ROADMAP
@@ -24,9 +24,11 @@
- tidy up major buid/use-breaking bugs in win32, BSD, OSX versions
- improve netsync error reporting code
- one part: many 'I's should be 'require's.
+- reimplement change_set.cc. major surgery :(
- overhaul command-line option processing, perhaps use argp
- move output formatting to lua hooks
- integrate net.venge.monotone.ssh branch
+- integrate net.venge.monotone.botan branch
- modify database code to use sqlite3 pre-parsed queries, blobs
- change netsync to globbing branches, not using collections
- implement improved ACL/permission system for default trust rules
@@ -38,6 +40,50 @@
- work on GUIs and web UIs
- "merge before commit" (CVS-style online commit-coordination)
- bidirectional mirroring between monotone and CVS/SVN/arch
-- (possible) try using botan instead of cryptopp
- an "agent" for storing decrypted private key in memory
- "hash-migration" technology for scenarios where SHA1 falls
+- ease long-term maintainance by writing up a real hacking guide
+ (.texi, based on expanded HACKING file, a guided tour of code,
+ and a thorough description of the more complicated algorithms)
+ for new maintainers.
+
+
+
+there are also some issues which are very regular, mundane, tedious,
+boring, but ultimately pretty mechanical. they need doing too.
+
+JANITORIAL
+==========
+
+- fix up the namespace issue: add a "using std::foo" for each foo
+ used in the file, and strip "std::" from the uses. remove
+ "using namespace foo" from everywhere. likewise boost.
+
+- librarification: several discrete steps, each mechanical,
+ best to do a compile and commit after each.
+ - make a struct for each file.
+ - make every "plain" function in the file a static member of the struct
+ - make every global/static object in the file a static member of the struct
+ - make every reference to an out-of-file global/static happen via a
+ static reference stored inside the struct, initialized at load time
+ - remove static-ness of references, from file to file, until there is a
+ single root value for the whole application
+
+ (nb: this is not to say that monotone will every be packaged or
+ provided as a library, simply that it's a little more flexible,
+ and easier to see dependencies between modules, when you have
+ things structured this way. we should have been doing so all along,
+ but we were lazy)
+
+- as a side note: collect all the command-line options from global_sanity
+ and app_state into a single options structure, just to improve
+ legibility
+
+- split commands.cc into multiple files, one for each group of
+ commands (or even one per command).
+
+- rewrite the testsuite in some form which does not generate
+ a 6mb shell script. bonus points if it can run at a decent
+ speed on windows (nb. fork() on windows is insanely slow)
+
+- possibly purge the whole packet-reading/writing stuff.
--- app_state.hh
+++ app_state.hh
@@ -31,6 +31,8 @@
lua_hooks lua;
bool stdhooks;
bool rcfiles;
+ bool diffs;
+ bool no_merges;
options_map options;
utf8 message;
utf8 message_file;
--- commands.cc
+++ commands.cc
@@ -720,36 +720,41 @@
}
}
-void
-changes_summary::print(std::ostream & os, size_t max_cols) const
+static void
+print_indented_set(std::ostream & os,
+ set const & s,
+ size_t max_cols)
{
-#define PRINT_INDENTED_SET(setname) \
- size_t cols = 8; \
- os << " "; \
- for (std::set::const_iterator i = setname.begin(); \
- i != setname.end(); i++) \
- { \
- const std::string str = (*i)(); \
- if (cols > 8 && cols + str.size() + 1 >= max_cols) \
- { \
- cols = 8; \
- os << endl << " "; \
- } \
- os << " " << str; \
- cols += str.size() + 1; \
- } \
+ size_t cols = 8;
+ os << " ";
+ for (std::set::const_iterator i = s.begin();
+ i != s.end(); i++)
+ {
+ const std::string str = (*i)();
+ if (cols > 8 && cols + str.size() + 1 >= max_cols)
+ {
+ cols = 8;
+ os << endl << " ";
+ }
+ os << " " << str;
+ cols += str.size() + 1;
+ }
os << endl;
+}
+void
+changes_summary::print(std::ostream & os, size_t max_cols) const
+{
if (! rearrangement.deleted_files.empty())
{
os << "Deleted files:" << endl;
- PRINT_INDENTED_SET(rearrangement.deleted_files)
+ print_indented_set(os, rearrangement.deleted_files, max_cols);
}
-
+
if (! rearrangement.deleted_dirs.empty())
{
os << "Deleted directories:" << endl;
- PRINT_INDENTED_SET(rearrangement.deleted_dirs)
+ print_indented_set(os, rearrangement.deleted_dirs, max_cols);
}
if (! rearrangement.renamed_files.empty())
@@ -773,16 +778,14 @@
if (! rearrangement.added_files.empty())
{
os << "Added files:" << endl;
- PRINT_INDENTED_SET(rearrangement.added_files)
+ print_indented_set(os, rearrangement.added_files, max_cols);
}
if (! modified_files.empty())
{
os << "Modified files:" << endl;
- PRINT_INDENTED_SET(modified_files)
+ print_indented_set(os, modified_files, max_cols);
}
-
-#undef PRINT_INDENTED_SET
}
CMD(genkey, "key and cert", "KEYID", "generate an RSA key-pair", OPT_NONE)
@@ -3511,7 +3514,7 @@
CMD(log, "informative", "[FILE]",
"print history in reverse order (filtering by 'FILE'). If one or more\n"
"revisions are given, use them as a starting point.",
- OPT_LAST % OPT_REVISION % OPT_BRIEF)
+ OPT_LAST % OPT_REVISION % OPT_BRIEF % OPT_DIFFS % OPT_NO_MERGES)
{
file_path file;
@@ -3616,6 +3619,9 @@
csum.add_change_set(cs);
}
+
+ if (app.no_merges && rev.is_merge_node())
+ print_this = false;
if (print_this)
{
@@ -3653,6 +3659,16 @@
log_certs(app, rid, comment_name, "Comments: ", true);
}
+ if (app.diffs)
+ {
+ for (edge_map::const_iterator e = rev.edges.begin();
+ e != rev.edges.end(); ++e)
+ {
+ dump_diffs(edge_changes(e).deltas,
+ app, true, unified_diff);
+ }
+ }
+
if (last > 0)
{
last--;
--- contrib/color-logs.conf
+++ contrib/color-logs.conf
@@ -0,0 +1,14 @@
+#
+# this is a colorization config for reading the output of "monotone log"
+# or "monotone diff", or best of all "monotone log --no-merges --diffs".
+#
+# use with the "colorize" script in this dir, or color-logs.sh
+#
+
+/^\#/ bold red
+/^\-{30}/ bold red
+/^\w[\w\s]+:/ bold red
+/^(\-{3}|\+{3})/ black on_cyan
+/^\-/ dark magenta
+/^\+/ dark cyan
+/^\@/ dark yellow
--- contrib/color-logs.sh
+++ contrib/color-logs.sh
@@ -0,0 +1,5 @@
+#!/bin/sh
+
+./monotone log --diffs --no-merges $@ \
+ | ./contrib/colorize -c contrib/color-logs.conf \
+ | less -r -p -----------------------------------------------------------------
--- contrib/colorize
+++ contrib/colorize
@@ -0,0 +1,197 @@
+#!/usr/bin/perl
+use strict;
+
+our $VERSION = 0.5;
+
+# $Id: colorize,v 1.5 2004/07/19 14:50:38 cbouvi Exp $
+#
+# Copyright (C) 2004 Cédric Bouvier
+#
+# 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 of the License, 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.
+#
+# You should have received a copy of the GNU General Public License along with
+# this program; if not, write to the Free Software Foundation, Inc., 59 Temple
+# Place, Suite 330, Boston, MA 02111-1307 USA
+
+# $Log: colorize,v $
+# Revision 1.5 2004/07/19 14:50:38 cbouvi
+# Updated the POD
+#
+# Revision 1.4 2004/07/19 14:19:25 cbouvi
+# Added ability to store patterns in a config file, called with --config
+#
+# Revision 1.3 2004/07/16 08:55:52 cbouvi
+# Move the test of $opt{pattern} outside the main loop.
+#
+# Revision 1.2 2004/07/15 15:58:26 cbouvi
+# Introduced "use strict;".
+# Now uses Getopt::Long instead of -s
+#
+
+sub read_conf {
+
+ my $filename = shift;
+ open my $fh, "<$filename" or die "Cannot read $filename: $!\n";
+ my @pattern;
+ while ( <$fh> ) {
+ chomp;
+ next if /^\s*(?:#.*)?$/;
+ my ($delim) = /(\S)/;
+ $delim = quotemeta $delim;
+ eval "/^\\s*$delim((?:\\\\.|[^\\\\$delim])*?)$delim\\s+(.*)\$/ and push address@hidden, [\$1, \$2]";
+ }
+ return @pattern;
+}
+
+use Getopt::Long;
+use Pod::Usage;
+
+my %opt;
+GetOptions \%opt, qw/ help|h version|v tail|tail-f|t pattern|p config|f=s /
+ or pod2usage -verbose => 0, -message => "Try $0 --help";
+
+$opt{help} and pod2usage -verbose => 1;
+if ( $opt{version} ) {
+ print "colorize version $VERSION\n";
+ exit 0;
+}
+
+require Term::ANSIColor;
+if ( $^O eq 'MSWin32' ) {
+ require Win32::Console::ANSI;
+ import Win32::Console::ANSI;
+}
+
+my @pattern = (
+ [ q/(?i)\bERROR\b/, 'bold red' ],
+ [ q/(?i)\bWARNING\b/, 'bold yellow' ],
+ [ q/(?i)\bINFO\b/, 'bold green' ],
+ [ q/(?i)\bDEBUG\b/, 'bold cyan' ],
+);
+
address@hidden = read_conf($opt{config}) if $opt{config};
+
+foreach ( @pattern ) {
+ $$_[0] = qr/$$_[0]/;
+ $$_[1] = Term::ANSIColor::color($$_[1]);
+}
+
+my $reset = Term::ANSIColor::color('reset');
+
+if ( $opt{tail} ) {
+ open STDIN, "tail -f $ARGV[0] |" or die "Cannot run tail -f $ARGV[0]: $!";
+ @ARGV = ();
+}
+
+my $color_cref = $opt{pattern}
+ ? sub { $` . $_[0] . $& . $reset . $' }
+ : sub { $_[0] . $_ . $reset };
+
+while ( <> ) {
+ chomp;
+ foreach my $pat ( @pattern ) {
+ next unless /$$pat[0]/;
+ $_ = $color_cref->($$pat[1]);
+ last;
+ }
+}
+continue {
+ print "$_\n";
+}
+
+=head1 NAME
+
+colorize - adds ANSI escape sequences to colorize lines in a file
+
+=head1 SYNOPSIS
+
+ colorize [-p] [-f config] file1 file2 file3 ...
+ colorize [-f config] -t file
+
+=head1 DESCRIPTION
+
+This very simple program reads lines from text files and prints them out to the
+standard output. It tries to match each line against a series of regular
+expressions, and if one of them matches, the line is displayed in color.
+
+When no file names are given on the command line, the standard input is read
+instead.
+
+=head2 Configuring Patterns and Colors
+
+The configuration file is given by means of the C<--config> command-line
+switch.
+
+Blank lines and comment lines are ignored. Comments must stand out on a line by
+themselves and start with a hash sign (C<#>).
+
+Each line that is not blank nor a comment should contain a regular expression
+and a list of color and/or attribute keywords, separated by whitespace. If a
+line of the input file matches the regular expression, the line will be
+rendered in the color defined by the keywords. See L for the
+full list of available keywords.
+
+The regular expression can be any Perl 5 compatible regular expression. It must
+be enclosed in slashes C/>.
+
+Example (this is the built-in default):
+
+ /(?i)\bERROR\b/ bold red
+ /(?i)\bWARNING\b/ bold yellow
+ /(?i)\bINFO\b/ bold green
+ /(?i)\bDEBUG\b/ bold cyan
+
+=head2 Options
+
+=over 4
+
+=item B<-f> I, B<--config>=I
+
+Use I as the configuration file.
+
+=item B<-p>, B<--pattern>
+
+Only colorizes the portion of the line that matches the pattern, not the whole
+line.
+
+=item B<-t>, B<--tail>, B<--tail-f>
+
+Runs the input file through C, so that C does not stop at
+the end of the file, but keeps on waiting for new lines to arrive. There must
+be only one input file in that case, all the others will be ignored.
+
+=item B<-v>, B<--version>
+
+Prints the version and exits
+
+=item B<-h>, B<--help>
+
+Prints help message and exits.
+
+=end
+
+=head2 Note for Microsoft® Windows® users
+
+The "Dos Prompt" (F) does not support the ANSI terminal escape
+sequence. This program thus requires the module C if it
+detects that it is running on such an OS.
+
+=head1 SEE ALSO
+
+perlre(1), L, L
+
+=head1 AUTHOR
+
+Copyright © 2004
+
+Cédric Bouvier
+
+=cut
--- contrib/monotone.el
+++ contrib/monotone.el
@@ -352,7 +352,7 @@
(view-mode)
(set-buffer-modified-p nil)
;; did we part on good terms?
- (when (not (zerop mt-status))
+ (when (and mt-status (not (zerop mt-status)))
(message "%s: exited with status %s" mt-pgm mt-status)
(beep)
(sit-for 3))
--- monotone.cc
+++ monotone.cc
@@ -51,6 +51,8 @@
{"last", 0, POPT_ARG_LONG, &arglong, OPT_LAST, "limit the log output to the given number of entries", NULL},
{"pid-file", 0, POPT_ARG_STRING, &argstr, OPT_PIDFILE, "record process id of server", NULL},
{"brief", 0, POPT_ARG_NONE, NULL, OPT_BRIEF, "print a brief version of the normal output", NULL},
+ {"diffs", 0, POPT_ARG_NONE, NULL, OPT_DIFFS, "print diffs along with logs", NULL},
+ {"no-merges", 0, POPT_ARG_NONE, NULL, OPT_NO_MERGES, "skip merges when printing logs", NULL},
{ NULL, 0, 0, NULL, 0, NULL, NULL }
};
@@ -370,6 +372,14 @@
global_sanity.set_brief();
break;
+ case OPT_DIFFS:
+ app.diffs = true;
+ break;
+
+ case OPT_NO_MERGES:
+ app.no_merges = true;
+ break;
+
case OPT_PIDFILE:
app.set_pidfile(absolutify(tilde_expand(string(argstr))));
break;
--- options.hh
+++ options.hh
@@ -31,4 +31,6 @@
#define OPT_PIDFILE 22
#define OPT_MSGFILE 23
#define OPT_BRIEF 24
+#define OPT_DIFFS 25
+#define OPT_NO_MERGES 26
+#define OPT_LAST 27
-#define OPT_LAST 25
--- rcs_import.cc
+++ rcs_import.cc
@@ -95,15 +95,28 @@
inline bool operator==(cvs_key const & other) const
{
L(F("Checking equality of %d and %d\n") % id % other.id);
- return branch == other.branch &&
+ return is_synthetic_branch_founding_commit == other.is_synthetic_branch_founding_commit &&
+ branch == other.branch &&
changelog == other.changelog &&
author == other.author &&
time == other.time;
}
-
inline bool operator<(cvs_key const & other) const
{
// nb: this must sort as > to construct the edges in the right direction
+
+ if (is_synthetic_branch_founding_commit)
+ {
+ I(!other.is_synthetic_branch_founding_commit);
+ return false;
+ }
+
+ if (other.is_synthetic_branch_founding_commit)
+ {
+ I(!is_synthetic_branch_founding_commit);
+ return true;
+ }
+
return time > other.time ||
(time == other.time
@@ -121,10 +134,11 @@
inline void add_file(file_path const &file, string const &version)
{
- L(F("Adding file %s version %s to %d\n") % file % version % id);
+ L(F("Adding file %s version %s to CVS key %d\n") % file % version % id);
files.insert( make_pair(file, version) );
}
+ bool is_synthetic_branch_founding_commit;
cvs_branchname branch;
cvs_changelog changelog;
cvs_author author;
@@ -783,7 +797,8 @@
}
cvs_key::cvs_key(rcs_file const & r, string const & version,
- cvs_history & cvs)
+ cvs_history & cvs) :
+ is_synthetic_branch_founding_commit(false)
{
map >::const_iterator delta =
r.deltas.find(version);
@@ -924,29 +939,30 @@
k.changelog = clog;
k.author = auth;
k.add_file(curr_file, version);
+ k.is_synthetic_branch_founding_commit = true;
branch->insert(make_pair(k, s));
+ L(F("added synthetic branch founding commit at id %d, time %d\n")
+ % k.id % k.time);
}
else
{
cvs_key nk(r, version, *this);
- bool found_branch_birth = false;
- for (cvs_branch::const_iterator i = branch->begin();
- i != branch->end(); ++i)
- {
- if (i->first.author == auth
- && i->first.changelog == clog)
- {
- k = i->first;
- s = i->second;
- found_branch_birth = true;
- break;
- }
- }
- I(found_branch_birth);
+ cvs_branch::iterator i = branch->end();
+ i--;
+ I(i->first.is_synthetic_branch_founding_commit);
+ I(i->first.author == auth);
+ I(i->first.changelog == clog);
+
+ k = i->first;
+ s = i->second;
+
+ L(F("found existing synthetic branch founding commit at id %d, time %d\n")
+ % k.id % k.time);
if (nk.time > k.time)
{
- branch->erase(k);
+ L(F("moving synthetic branch founding commit to %d\n") % nk.time);
+ branch->erase(i);
k.time = nk.time;
k.add_file(curr_file, version);
branch->insert(make_pair(k, s));
@@ -983,7 +999,7 @@
//
// and search all the nodes inside this section, from new to old bound.
- map< cvs_key, shared_ptr >::const_iterator i_new, i_old, i;
+ map< cvs_key, shared_ptr >::iterator i_new, i_old, i;
cvs_key k_new(nk), k_old(nk);
if (static_cast(k_new.time + constants::cvs_window / 2) > k_new.time)
@@ -1001,7 +1017,7 @@
{
key = i->first;
state = i->second;
- branch->erase(i->first);
+ branch->erase(i);
key.add_file(curr_file, version);
branch->insert(make_pair(key,state));
return true;
@@ -1063,8 +1079,9 @@
bool prev_alive = prev_delta->second->state!="dead";
bool next_alive = next_delta->second->state!="dead";
- L(F("note_file_edge %s %d -> %s %d\n") % prev_rcs_version_num % prev_alive
- % next_rcs_version_num % next_alive);
+ L(F("note_file_edge %s %d -> %s %d\n")
+ % prev_rcs_version_num % prev_alive
+ % next_rcs_version_num % next_alive);
// we always aggregate in-edges in children, but we will also create
// parents as we encounter them.
@@ -1077,6 +1094,7 @@
find_key_and_state (r, next_rcs_version_num, k, s); // just to create it if necessary
find_key_and_state (r, prev_rcs_version_num, k, s);
+ L(F("trunk edge entering key state %d\n") % k.id);
s->in_edges.insert(cvs_file_edge(next_version, curr_file, next_alive,
prev_version, curr_file, prev_alive,
*this));
@@ -1088,6 +1106,8 @@
% prev_rcs_version_num
% next_rcs_version_num);
find_key_and_state (r, next_rcs_version_num, k, s);
+ L(F("branch edge on %s entering key state %d\n")
+ % branch_interner.lookup(k.branch) % k.id);
s->in_edges.insert(cvs_file_edge(prev_version, curr_file, prev_alive,
next_version, curr_file, next_alive,
*this));
@@ -1289,6 +1309,12 @@
for (cvs_branch::reverse_iterator i = branch.rbegin();
i != branch.rend(); ++i)
{
+ L(F("importing branch %s, state [%d: %s @ %d]\n")
+ % cvs.branch_interner.lookup(i->first.branch)
+ % i->first.id
+ % cvs.author_interner.lookup(i->first.author)
+ % i->first.time);
+
revision_set rev;
boost::shared_ptr cs(new change_set());
build_change_set(i->second, parent_map, cvs, *cs);
--- revision.cc
+++ revision.cc
@@ -64,6 +64,12 @@
}
}
+bool
+revision_set::is_merge_node() const
+{
+ return edges.size() > 1;
+}
+
revision_set::revision_set(revision_set const & other)
{
other.check_sane();
--- revision.hh
+++ revision.hh
@@ -56,6 +56,7 @@
revision_set
{
void check_sane() const;
+ bool is_merge_node() const;
revision_set() {}
revision_set(revision_set const & other);
revision_set const & operator=(revision_set const & other);
--- tests/t_cvsimport_drepper.at
+++ tests/t_cvsimport_drepper.at
@@ -0,0 +1,191 @@
+# -*- Autoconf -*-
+
+AT_SETUP([importing a small, real CVS repository])
+
+MONOTONE_SETUP
+
+NEED_UNGZB64
+
+AT_DATA(test.manifest, [94c86fa749ed82d76fe8d6cce18d11b8c3f0ee38 src/objdump.c
+01f722126e54806abfa32f867dbeb8529b79298b tests/asm-tst3.c
+7968cb0c8f62e6f15d710ce0cd42a65f7acd2567 tests/asm-tst4.c
+])
+
+AT_DATA(e.tar.gz.enc, [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
+qlSlKlWpSlWq8ujyL0kUTRMAoAAA
+])
+
+UNGZB64(e.tar.gz.enc, e.tar)
+AT_CHECK(tar -xf e.tar)
+
+AT_CHECK(MONOTONE --branch=foo.bar cvs_import e, [], [ignore], [ignore])
+AT_CHECK(MONOTONE --branch=foo.bar.disasm-branch co)
+AT_CHECK(cd foo.bar.disasm-branch && MONOTONE cat manifest, [], [stdout])
+AT_CHECK(cmp test.manifest stdout)
+
+AT_CLEANUP
--- testsuite.at
+++ testsuite.at
@@ -652,3 +652,4 @@
m4_include(tests/t_selector_later_earlier.at)
m4_include(tests/t_merge_binary.at)
m4_include(tests/t_automate_stdio.at)
+m4_include(tests/t_cvsimport_drepper.at)