Re: [PATCH 2/2] introduce preciousObjects repository extension
On Tue, Jun 23, 2015 at 02:05:28PM -0700, Junio C Hamano wrote: Jeff King p...@peff.net writes: This extension does not change git's behavior at all. It is useful only for testing format-1 compatibility. + +`preciousObjects` +~ + +When the config key `extensions.preciousObjects` is set to `true`, +objects in the repository MUST NOT be deleted (e.g., by `git-prune` or +`git repack -d`). OK. In essense, the 'extension' on the disk is like 'capability' on the wire, in that you are not supposed to ask for capability they do not understand, and you are not supposed to touch a repository you do not understand. Yeah, I think that is a good analogy. + if (delete_redundant repository_format_precious_objects) + die(cannot repack in a precious-objects repo); This message initially threw me off during my cursory reading, but the code tells me that this is only about repack -d. Unfortunately the users do not get the chance to read the code; perhaps s/cannot repack/ -d/; or something? I agree that would be better. I originally just blocked all use of git-repack, but at the last minute softened it to just repack -d. I'm not sure if that would actually help anyone in practice. Sure, doing git repack without any options is not destructive, but I wonder if anybody actually does it. They either run `git gc`, or they probably do something more exotic and disable the safety check during that run[1]. So I think we could squash in the patch below (which also marks the strings for translation). But I'd also be OK with the rule covering all of `git repack`. -Peff [1] One of my proposed uses for this is to revamp the way we handle shared objects on GitHub servers. Right now objects get pushed to individual forks, and then migrate to a shared repository that is accessed via the alternates mechanism. I would like to move to symlinking the `objects/` directory to write directly into the shared space. But the destruction from accidentally running something like `git gc` in a fork is very high. With this patch, we can bump the forks to the v1 format and mark their objects as precious. --- diff --git a/builtin/prune.c b/builtin/prune.c index fc0c8e8..6a58e75 100644 --- a/builtin/prune.c +++ b/builtin/prune.c @@ -219,7 +219,7 @@ int cmd_prune(int argc, const char **argv, const char *prefix) } if (repository_format_precious_objects) - die(cannot prune in a precious-objects repo); + die(_(cannot prune in a precious-objects repo)); while (argc--) { unsigned char sha1[20]; diff --git a/builtin/repack.c b/builtin/repack.c index 8ae7fe5..3beda2c 100644 --- a/builtin/repack.c +++ b/builtin/repack.c @@ -194,7 +194,7 @@ int cmd_repack(int argc, const char **argv, const char *prefix) git_repack_usage, 0); if (delete_redundant repository_format_precious_objects) - die(cannot repack in a precious-objects repo); + die(_(cannot delete packs in a precious-objects repo)); if (pack_kept_objects 0) pack_kept_objects = write_bitmaps; -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: RFC/Pull Request: Refs db backend
On Tue, Jun 23, 2015 at 02:18:36PM -0400, David Turner wrote: Can you describe a bit more about the reflog handling? One of the problems we've had with large-ref repos is that the reflog storage is quite inefficient. You can pack all the refs, but you may still be stuck with a bunch of reflog files with one entry, wasting a whole inode. Doing a git repack when you have a million of those has horrible cold-cache performance. Basically anything that isn't one-file-per-reflog would be a welcome change. :) Reflogs are stored in the database as well. There is one header entry per ref to indicate that a reflog is present, and then one database entry per reflog entry; the entries are stored consecutively and immediately following the header so that it's fast to iterate over them. OK, that make sense. I did notice that the storage for the refdb grows rapidly. If I add a millions refs (like refs/tags/$i) with a simple reflog message foo, I ended up with a 500MB database file. That's _probably_ OK, because a million is getting into crazy territory[1]. But it's 500 bytes per ref, each with one reflog entry. Our ideal lower bound is probably something like 100 bytes per reflog entry: - 20 bytes for old sha1 - 20 bytes for new sha1 - ~50 bytes for name, email, timestamp - ~6 bytes for refname (100 is the longest unique part) That assumes we store binary[2] (and not just the raw reflog lines), and reconstruct the reflog lines on the fly. It also assumes we use some kind of trie-like storage (where we can amortize the cost of storing refs/tags/ across all of the entries). Of course that neglects lmdb's overhead, and the storage of the ref tip itself. But it would hopefully give us a ballpark for an optimal solution. We don't have to hit that, of course, but it's food for thought. [1] The homebrew/homebrew repository on GitHub has almost half a million ref updates. Since this is storing not just refs but all ref updates, that's actually the interesting number (and optimizing the per-reflog-entry size is more interesting than the per-ref size). [2] I'm hesitant to suggest binary formats in general, but given that this is a blob embedded inside lmdb, I think it's OK. If we were to pursue the log-structured idea I suggested earlier, I'm torn on whether it should be binary or not. It has also been a dream of mine to stop tying the reflogs specifically to the refs. I.e., have a spot for reflogs of branches that no longer exist, which allows us to retain them for deleted branches. [...] That would be cool, and I don't think it would be hard to add to my current code; we could simply replace the header with a tombstone. But I would prefer to wait until the series is merged; then we can build on top of it. Yeah, I think you can add it easily to basically any system that does not have the filesystem D/F conflicts in its storage (i.e., having refs/foo does not block data under refs/foo/bar). But it may also be worth going with a slightly slower database if we can get wider compatibility for free. There's a JNI interface to LMDB, which is, of course, not native. I don't think it would be too hard to entirely rewrite LMDB in Java, but I'm not going to have time to do it for the forseeable future. I've asked Howard Chu if he knows of any efforts in progress. Yeah, I think JNI is not enough for Eclipse folks. I don't think this is a task that you would necessarily need to take on. More just something to think about for the future when picking a format. Thanks, that's valuable. For the refs backend, opening the LMDB database for writing is sufficient to block other writers. Do you think it would be valuable to provide a git hold-ref-lock command that simply reads refs from stdin and keeps them locked until it reads EOF from stdin? That would allow cross-backend ref locking. I'm not sure what you would use it for. If you want to update the refs, then you can specify a whole transaction with git update-ref --stdin, and that should work whatever backend you choose. Is there some other operation you want where you hold the lock for a longer period of time? -Peff -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH] Fix definition of ARRAY_SIZE for non-gcc builds
From: Charles Bailey cbaile...@bloomberg.net The improved ARRAY_SIZE macro uses BARF_UNLESS_AN_ARRAY which is expands to a valid check for recent gcc versions and to 0 for older gcc versions but is not defined on non-gcc builds. Non-gcc builds need this macro to expand to 0 as well. The current outer test (defined(__GNUC__) (__GNUC__)) is a strictly weaker condition than the inner test (GIT_GNUC_PREREQ(3, 1)) so we can omit the outer test and cause the BARF_UNLESS_AN_ARRAY macro to be defined correctly on non-gcc builds as well as gcc builds with older versions. Signed-off-by: Charles Bailey cbaile...@bloomberg.net --- This fixes a build regression introduced in v2.4.4 so this patch is based off that tag. git-compat-util.h | 8 +++- 1 file changed, 3 insertions(+), 5 deletions(-) diff --git a/git-compat-util.h b/git-compat-util.h index b45c75f..8c2b7aa 100644 --- a/git-compat-util.h +++ b/git-compat-util.h @@ -58,15 +58,13 @@ #define BUILD_ASSERT_OR_ZERO(cond) \ (sizeof(char [1 - 2*!(cond)]) - 1) -#if defined(__GNUC__) (__GNUC__ = 3) -# if GIT_GNUC_PREREQ(3, 1) +#if GIT_GNUC_PREREQ(3, 1) /* arr[0] degrades to a pointer: a different type from an array */ # define BARF_UNLESS_AN_ARRAY(arr) \ BUILD_ASSERT_OR_ZERO(!__builtin_types_compatible_p(__typeof__(arr), \ __typeof__((arr)[0]))) -# else -# define BARF_UNLESS_AN_ARRAY(arr) 0 -# endif +#else +# define BARF_UNLESS_AN_ARRAY(arr) 0 #endif /* * ARRAY_SIZE - get the number of elements in a visible array -- 2.4.0.53.g8440f74 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 2/2] introduce preciousObjects repository extension
On Tue, Jun 23, 2015 at 05:31:14PM -0400, David Turner wrote: On Tue, 2015-06-23 at 06:54 -0400, Jeff King wrote: + mkconfig 1 preciousObjects .git/config nit: I think it's better to use git config rather than manually writing config files. git config is more future-proof if we up switching config backends; it's also more composable with other configs (making this test easier to copy and manipulate), and more explicit. I would have preferred that, but it makes the tests very fragile. You are depending on git config running even when the current directory is not a valid git repo (and we walk up to the surround git.git directory and change the config there!). I guess we could use git config -f .git/config, though that is partially defeating the purpose of your suggestion. I dunno. I kind of figured we would cross that bridge if and when we come to it. I imagine you are pretty sensitive to it, though, having just waded through all the tests that assume various things about .git/refs. :) -Peff -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH/WIP v3 07/31] am: extract patch, message and authorship with git-mailinfo
Okay, let's focus only on the API design issues. For the record, I'm not completely satisfied with the current code organization and API, however I don't have really good ideas at hand to improve it, so any ideas with examples would be appreciated. On Fri, Jun 19, 2015 at 09:13:00AM -0700, Junio C Hamano wrote: Paul Tan pyoka...@gmail.com writes: With the above fields, it is clear that the above fields are per-message thing. So the loop to process multiple messages is conceptually: set up the entire am_state (for things like cur=1, last=N) for each message { update per-message fields like cur, author, msg, etc. process the single message clean up per-message fileds like cur++, free(msg), etc. } tear down the entire am_state Reusing the same strbuf and rely on them to clean up after themselves is simply a bad taste. Hmm, reading reusing the same strbuf makes me wonder if I'm misunderstanding something. Do you mean that: 1. We should release the memory in state-msg, state-author_* after processing each message? Because that is what am_next() already does. Granted, it does strbuf_reset(), but it could just as well be strbuf_release(). or 2. The per-message fields (state-msg, state-author_*) should become local variables in am_run()? or 3. I'm over-thinking this and you just want the struct strbufs in the struct am_state to be switched to char*s? If that is so, I've attached a sample patch below. For (2), my idea is that am_state represents the contents of the state directory at any point in time -- a design feature carried over from git-am.sh. This is why parse_patch() modifies the am_state struct directly -- the msg and author_* fields would be written to the final-commit and author-script files directly after. I think it would be confusing if we don't update the am_state struct directly, as we will never know if the am_state struct contains the actual current state of the patch application session. (On a somewhat related thought, currently we do write_file() all over the place, which is really ugly. I'm leaning heavily on introducing an am_save() function, for I don't care how it is done but just update the contents of the am state directory so that it matches the contents of the struct am_state. To save pointless writes, we can compare the am_state with the last-written/loaded am_state, so we only write the files that have changed. What do others think?) More importantly, we'd want to make sure that people who will be touching the process the single message part in the above loop to think twice before mucking with read-only fields like author. Okay, I understand and agree with your reasoning. However, note that this process the single message part consists solely of run_apply() and do_commit(). Both of them take a const struct am_state*, which means that the compiler will warn/fail if anybody tries to touch any of the fields in the am_state. This extends to strbufs as well. Isn't this already safe enough? Or do you want this safety to extend throughout am_run() as well? If they are char *, they would need to allocate new storage themselves, format a new value into there, free the original, and replace the field with the new value. It takes a conscious effort and very much visible code and would be clear to reviewers what is going on, and gives them a chance to question if it is a good idea to update things in-place in the first place. Okay, although personally I think reviewers may tend to miss out that a single line like: state-msg = strbuf_detach(sb, NULL); introduces a memory leak. If you left it in strbuf, that invites let's extend it temporarily with strbuf_add() and then return to the original once I am done with this single step, which is an entry to a slippery slope to let's extend it with strbuf_add() for my purpose, and I do not even bother to clean up because I know I am the last person to touch this. So, no, please don't leave a field that won't change during the bulk of the processing in strbuf, unless you have a compelling reason to do so (and compelling reasons are pretty much limited to after all, that field we originally thought it won't change is something we need to change very often). Anyway, assuming that you just want the strbufs in the am_state struct to be switched to char*s, here's a quick diff of the result. Can I confirm that this is the direction that you want to take? (since the changes are throughout the entire patch series) Regards, Paul --- 8 --- builtin/am.c | 202 ++- 1 file changed, 131 insertions(+), 71 deletions(-) diff --git a/builtin/am.c b/builtin/am.c index f55dd14..944e35a 100644 --- a/builtin/am.c +++ b/builtin/am.c @@ -98,10 +98,10 @@ struct am_state { int last; /* commit message and metadata */ - struct strbuf author_name; -
Re: RFC/Pull Request: Refs db backend
On Tue, Jun 23, 2015 at 4:47 AM, Jeff King p...@peff.net wrote: One of the problems we've had with large-ref repos is that the reflog storage is quite inefficient. Yup. We ran into this with Gerrit Code Review years ago. The refs/changes/... namespace created by Gerrit Code Review is 1 ref per snapshot per code review, and never modified. Reflogs for these are always exactly one record. We broke down and modified JGit to add an API that allowed Gerrit Code Review to disable recording reflogs for specific updates just to avoid creating reflogs under refs/changes/. In our JGit DFS implementation we store reflogs in databases to eliminate these overheads. It works well for us. Hopefully the feature can come to git-core through this series. It has also been a dream of mine to stop tying the reflogs specifically to the refs. I.e., have a spot for reflogs of branches that no longer exist, which allows us to retain them for deleted branches. Then you can possibly recover from a branch deletion, whereas now you have to dig through git fsck's dangling output. And the reflog, if you don't expire it, becomes a suitable audit log to find out what happened to each branch when (whereas now it is full of holes when things get deleted). Yes. $DAY_JOB's DFS implementation never expires reflogs, allowing it to be used as a history to inspect what happened. Its been useful a couple of times to investigate and recover from a few accidental deletions. Once you never expire reflog records you now have to consider at what point do you stop paying attention to the reflog entries for graph reachability during repack and fsck. Users still expect to be able to force push or delete a branch and have a set of objects disappear from the repository. I am looking forward to something like this in git-core. I delete branches in my local repos and then regret that. Then remember HEAD has a reflog and hope I can find it somewhere in there. Usually I fail, and am sad. :( I was thinking of actually moving to a log-structured ref storage. Something like: - any ref write puts a line at the end of a single logfile that contains the ref name, along with the normal reflog data - the logfile is the source of truth for the ref state. If you want to know the value of any ref, you can read it backwards to find the last entry for the ref. Everything else is an optimization. Let's call the number of refs N, and the number of ref updates in the log U. - we keep a key/value index mapping the name of any branch that exists to the byte offset of its entry in the logfile. This would probably be in some binary key/value store (like LMDB). Without this, resolving a ref is O(U), which is horrible. With it, it should be O(1) or O(lg N), depending on the index data structure. This ... would be fantastic. There are some issues with append. Before appending we would need to verify the last record actually ends with an LF. If there was a power failure and only part of the last record wrote, you can't append without that record separator in place. If that last record was truncated, and an LF was wedged in to do a new append, we can't trust that intermediate record. A CRC at the end of the record might make it safer to know the record is intact or bogus due to an earlier failed write that wasn't completed. What about the case of never expiring the reflog? This log would grow forever. You may eventually need to archive old sections of it (e.g. 1 year ago?) to maintain an audit log, while keeping the latest entry for each ref to rebuild the index. - the index can also contain other optimizations. E.g., rather than point to the entry in the logfile, it can include the sha1 directly (to avoid an extra level of indirection). It may want to include the peeled value, as the current packed-refs file does. +1 to always storing the peeled value. This was a major improvement for $DAY_JOB's Git servers as peeling tags on the fly can be costly when your storage is something remote, such as NFS. Unfortunately the current wire protocol demands peeled information to serve a ref advertisement. One thing we do is always peel all refs. We record a bit to state its been peeled, but there is no peeled value because the ref is pointing to a non-tag object (e.g. refs/heads/master points to a commit). I guess this puts an index structure at something like: refname \0 log_idx_4 sha1_20 ('n' | 'p' sha1_20) Or refname + 26 bytes for heads and refname + 46 bytes for tags. Updating the index on updates to a ref would be costly, as its O(N). You could skip some index updates. Record in the header of the index the length of the reflog file used to build it. When reading the index, scan the reflog from that position to the end and patch those updates in memory. Rewrites of the index could then be deferred until the scan delta on the log is high, or the next gc. - Reading all of the
Re: What's cooking in git.git (Jun 2015, #05; Mon, 22)
Hi Junio, On 2015-06-23 22:46, Junio C Hamano wrote: Johannes Schindelin johannes.schinde...@gmx.de writes: On 2015-06-23 00:49, Junio C Hamano wrote: * js/rebase-i-clean-up-upon-continue-to-skip (2015-06-18) 3 commits - rebase -i: do not leave a CHERRY_PICK_HEAD file behind - SQUASH: test_must_fail is a shell function - t3404: demonstrate CHERRY_PICK_HEAD bug Abandoning an already applied change in git rebase -i with --continue left CHERRY_PICK_HEAD and confused later steps. Expecting a reroll. ($gmane/271856) Actually, there had been two re-rolls, and v3 seemed to be okay: $gmane/272037. It also looks as if 726a35ebd^..726a35ebd^2 is identical with v3... Anything you want me to change in addition? Thanks for a pointer; I think I updated the topic and then forgot to update the reference in whats cooking. I'll take a look at 272037 and if I have anything further will comment there. Thanks. Also: * js/fsck-opt (2015-06-22) 19 commits [...] [...] If the for-layout is the only thing that is questionable thing to fix in what I queued, I think I can locally fix-up without an extra roundtrip. It is the only thing (and not even questionable ;-)). Thanks! Dscho -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: RFC/Pull Request: Refs db backend
On Tue, Jun 23, 2015 at 08:10:03PM +0700, Duy Nguyen wrote: - we keep a key/value index mapping the name of any branch that exists to the byte offset of its entry in the logfile. This would probably One key/value mapping per branch, pointing to the latest reflog entry, or one key/valye mapping for each reflog entry? Yeah, sorry, I meant to point only to the latest entry (and then from there if you want to actually walk the reflog, you can do so by following the backreference to the previous entry). be in some binary key/value store (like LMDB). Without this, resolving a ref is O(U), which is horrible. With it, it should be O(1) or O(lg N), depending on the index data structure. I'm thinking of the user with small or medium repos, in terms of refs, who does not want an extra dependency. If we store one mapping per branch, then the size of this mapping is small enough that the index in a text file is ok. If we also store the offset to the previous reflog entry of the same branch in the current reflog entry, like a back pointer, then we could jump back faster. Or do you have something else in mind? Current reflog structure won't work because I think you bring back the reflog graveyard with this, and I don't want to lose that I hadn't really thought about having multiple formats for the index. But in theory, yes, you could, and the lowest common denominator could just use the filesystem. Or even something similar to the packed-refs file, where we have to write the whole thing to make a single update. That doesn't perform well, but it's dirt simple and might be OK if you have only a handful of refs. -Peff -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 2/2] introduce preciousObjects repository extension
On Tue, Jun 23, 2015 at 06:54:11AM -0400, Jeff King wrote: diff --git a/builtin/prune.c b/builtin/prune.c index 0c73246..fc0c8e8 100644 --- a/builtin/prune.c +++ b/builtin/prune.c @@ -218,6 +218,9 @@ int cmd_prune(int argc, const char **argv, const char *prefix) return 0; } + if (repository_format_precious_objects) + die(cannot prune in a precious-objects repo); + By the way, I originally wrote this patch on an older version of git, and was surprised that `git gc` broke when I brought it forward. The problem was that gc now runs `git prune --worktree`, and my die() was affecting that case. It really seems misplaced to me to make worktree-pruning part of git-prune. I imagine the rationale was well, we are pruning things, so let's add an option to this command rather than make a new one. But I do not think that follows our usual pattern with gc, which is: 1. Individual areas of code handle their own cleanup. E.g., reflog expire, rerere gc. 2. We tie them together with git gc, not with git prune. So it seems weird that git prune --worktree is a fundamentally different command than git prune. I think by (1), it should be a separate git prune-worktree (or better yet, git worktree prune, as the start of a command for manipulating the list of multiple-worktrees). Not a _huge_ deal, but if we want to change it, it would be nice to do so now before it is part of a release. Thoughts? -Peff -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH/WIP v3 06/31] am: detect mbox patches
On Fri, Jun 19, 2015 at 5:02 AM, Junio C Hamano gits...@pobox.com wrote: Paul Tan pyoka...@gmail.com writes: +static int is_email(const char *filename) +{ + struct strbuf sb = STRBUF_INIT; + FILE *fp = xfopen(filename, r); + int ret = 1; + + while (!strbuf_getline(sb, fp, '\n')) { + const char *x; + + strbuf_rtrim(sb); Is this a good thing? strbuf_getline() already has stripped the LF at the end, so you'd be treating a line with only whitespaces as if it is a truly empty line. I know the series is about literal translation and the script may lose the distinction between the two, but I do not think you need (or want) to be literally same for things like this. Same comment applies to other uses of trim in this patch. No, the uses of strbuf_trim() are not good at all. Will remove them. Thanks, Paul -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: RFC/Pull Request: Refs db backend
On Wed, Jun 24, 2015 at 1:09 PM, Shawn Pearce spea...@spearce.org wrote: I chose to use LMDB for the database. LMDB has a few features that make it suitable for usage in git: One of the complaints that Shawn had about sqlite is that there is no native Java implementation, which makes it hard for JGit to ship a compatible backend. I suspect the same is true for LMDB, but it is probably a lot simpler than sqlite (so reimplementation might be possible). Yes. Whatever the default standard format is for git-core, we need that format to be easily supportable from JGit. Loading code via JNI is not easily supportable. I'm under the impression that this will be opt-in, not completely replacing fs-based ref backend. Anyway, any recommendation about database format or engine that is more friendly to Java and JGit (and preferably has good C support too)? -- Duy -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH/RFC] Revert git am/mailinfo: Don't look at in-body headers when rebasing
Hi Junio, On Tue, Jun 16, 2015 at 5:03 PM, Paul Tan pyoka...@gmail.com wrote: This reverts commit d25e51596be9271ad833805a3d6f9012dc24ee79, removing git-mailsplit's --no-inbody-headers option. While --no-inbody-headers was introduced to prevent commit messages from being munged by git-mailinfo while rebasing, the need for this option disappeared since 5e835ca (rebase: do not munge commit log message, 2008-04-16), as git-am bypasses git-mailinfo and gets the commit message directly from the commit ID in the patch. git-am is the only user of --no-inbody-headers, and this option is not documented. As such, it should be removed. Signed-off-by: Paul Tan pyoka...@gmail.com What do you think about applying this patch? Either way, the no-inbody-headers code in git-am.sh is dead code so I don't think I will be implementing it in the git-am rewrite. Thanks, Paul -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Cannot clone a linked working directory.
Summary: When creating a linked working directory with `git checkout --to`, you cannot clone from the local path. This works when cloning the main repository directory. I couldn't find anything the the documentation for `git checkout` that indicates that this shouldn't work. Repro: Creating a repo `foo`, checkout --to'ing it to ../bar, then try to clone both resulting repositories - $ git --version git version 2.4.4.600.g6397abd $ mkdir foo $ cd foo $ git init Initialized empty Git repository in /bar/foo/.git/ $ git commit -m init --allow-empty [master (root-commit) c6da399] init $ git branch bar $ git checkout bar --to ../bar Enter ../bar (identifier bar) Switched to branch 'bar' $ cd ../bar $ cd bar $ git status -sb ## bar $ cd .. $ git clone bar baz Cloning into 'baz'... fatal: '/path/bar' does not appear to be a git repository fatal: Could not read from remote repository. Please make sure you have the correct access rights and the repository exists. $ git clone foo baz Cloning into 'baz'... done. -- bjor...@snoksrud.no -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 2/2] introduce preciousObjects repository extension
On Wed, Jun 24, 2015 at 3:12 PM, Jeff King p...@peff.net wrote: On Tue, Jun 23, 2015 at 06:54:11AM -0400, Jeff King wrote: diff --git a/builtin/prune.c b/builtin/prune.c index 0c73246..fc0c8e8 100644 --- a/builtin/prune.c +++ b/builtin/prune.c @@ -218,6 +218,9 @@ int cmd_prune(int argc, const char **argv, const char *prefix) return 0; } + if (repository_format_precious_objects) + die(cannot prune in a precious-objects repo); + By the way, I originally wrote this patch on an older version of git, and was surprised that `git gc` broke when I brought it forward. The problem was that gc now runs `git prune --worktree`, and my die() was affecting that case. It really seems misplaced to me to make worktree-pruning part of git-prune. I imagine the rationale was well, we are pruning things, so let's add an option to this command rather than make a new one. But I do not think that follows our usual pattern with gc, which is: 1. Individual areas of code handle their own cleanup. E.g., reflog expire, rerere gc. 2. We tie them together with git gc, not with git prune. So it seems weird that git prune --worktree is a fundamentally different command than git prune. I think by (1), it should be a separate git prune-worktree (or better yet, git worktree prune, as the start of a command for manipulating the list of multiple-worktrees). Not a _huge_ deal, but if we want to change it, it would be nice to do so now before it is part of a release. Thoughts? I was misled by the generic name prune :) (OK my bad, the document clearly says it's about object database). Maybe we should make an alias prune-objects.. And you caught me too late, I also added prune_shallow() in there. Multiple worktree feature is not released yet so I still have some time to move it out. Yeah git worktree prune makes sense. I think I need a way to list worktrees anyway. I didn't find good enough reason to create git worktree back then just for listing.. -- Duy -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Cannot clone a linked working directory.
On Wed, Jun 24, 2015 at 5:38 PM, Bjørnar Snoksrud snoks...@gmail.com wrote: Summary: When creating a linked working directory with `git checkout --to`, you cannot clone from the local path. This works when cloning the main repository directory. I couldn't find anything the the documentation for `git checkout` that indicates that this shouldn't work. I didn't think of this use case. If something works on the main worktree then it should also work on linked checkouts. I think I see the problem and will try to fix it in probably a few days (the git add -N problem takes higher priority). -- Duy -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH] apply: fix adding new files on i-t-a entries
On Tue, Jun 23, 2015 at 11:50 PM, Junio C Hamano gits...@pobox.com wrote: This patch tightens the exists in index check, ignoring i-t-a entries. For fixing the above problem, only the change in check_to_create() is needed. And the first thing I noticed and found a bit disturbing was that this change (which I think is correct, and happens to match what I sent out earlier) was the only thing necessary to make your new test pass. IOW, the other changes in this patch have no test coverage. Because to be honest I don't understand these code well enough to know how to trigger it :) For other changes, - load_current(), reporting not exists in index is better than does not match index Is that error reporting the only side effect from this change? The only thing that I can see. If an i-t-a entry is returned, it can't get past verify_index_match because ce_match_stat(). Hmm.. no the on-disk version is gone, we'll get to checkout_target() where it will restore the entry with an empty file. This is related to checkout that I will continue later below. - get_current_sha1(), or actually build_fake_ancestor(), we should not add i-t-a entries to the temporary index, at least not without also adding i-t-a flag back This is part of am three-way fallback codepath. I do not think the merge-recursive three-way merge code knows and cares about, is capable of handling, or would even want to deal with i-t-a entries in the first place, so adding an entry as i-t-a bit would not help. What the ultimate caller wants from us in this codepath is a tree object, and that is written out from the temporary index---and that codepath ignores i-t-a entries, so it is correct to omit them from the temporary index in the first place. Unlike the previous two changes, I think this change deserves a new test. Will do, after I study some more about this apply.c. I think I'm opening a can of worms with d95d728. There's nothing wrong with that patch per se, but with this issue popping up, I need to go over all {cache,index}_name_pos call sites and see what would be the sensible behavior when i-t-a entries are involved. Yeah, I agree that d95d728 should have been a part of a larger series that changes the world order, instead of a single change that brings inconsistency to the system. I cannot offhand convince myself that apply is the only casualty; assuming it is, I think a reasonable way forward is to keep d95d728 and adjust apply to the new world order. Otherwise, i.e. if there are wider fallouts from d95d728, we may instead want to temporarily revert it off from 'master', deal with fallouts to apply and other things, before resurrecting it. Anything that internally uses diff-index is suspect, I think. Yeah that's one or two more grep runs and more reading. What do others think? You seem to ... So far blame, rm and checkout-entry and checkout paths are on my to-think-or-fix list. But this patch can get in early to fix a real regression instead of waiting for one big series. A lot more discussions will be had before that series gets in good shape. ... think that the damage could be quite extensive, so I am inclined to say that we first revert d95d728 before going forward. I'm not opposed to reverting if you think it's the safest option and I will report back soon after grepping diff-index. But those I mentioned above have more to do with the fact that an i-t-a entry does exist in the index in a normal way, so reverting does not help. Take checkout for example, when you do git checkout -- foo where foo is i-t-a, the file foo on disk will be emptied because the SHA-1 in the i-t-a entry is an empty blob, mostly to help git diff. I think it should behave as if foo is not i-t-a: checkout should error out about not matching pathspec, or at least not destroy foo on disk. To me, when ce is an i-t-a entry, only i-t-a flag and ce_name are valid, the rest of ce should never be accessed. blame.c's situation is close to check_preimage() where it may read zero from ce_mode. It may be ok for check_preimage() to take zero as mode, but I think this is like fixed size buffer vs strbuf again. It works now, but if the code is reorganized or refactored, then it may or may not work. Better be safe than sorry and avoid reading something we should not read in the first place. builtin/apply.c | 8 cache.h | 2 ++ read-cache.c | 12 t/t2203-add-intent.sh | 10 ++ 4 files changed, 28 insertions(+), 4 deletions(-) diff --git a/builtin/apply.c b/builtin/apply.c index 146be97..4f813ac 100644 --- a/builtin/apply.c +++ b/builtin/apply.c @@ -3344,7 +3344,7 @@ static int load_current(struct image *image, struct patch *patch) if (!patch-is_new) die(BUG: patch to %s is not a creation, patch-old_name); - pos = cache_name_pos(name, strlen(name)); + pos = exists_in_cache(name, strlen(name));
Re: RFC/Pull Request: Refs db backend
On Tue, Jun 23, 2015 at 11:09:40PM -0700, Shawn Pearce wrote: Yes. $DAY_JOB's DFS implementation never expires reflogs, allowing it to be used as a history to inspect what happened. Its been useful a couple of times to investigate and recover from a few accidental deletions. Once you never expire reflog records you now have to consider at what point do you stop paying attention to the reflog entries for graph reachability during repack and fsck. Users still expect to be able to force push or delete a branch and have a set of objects disappear from the repository. Yeah, we face this problem at GitHub. We actually write every single ref write to $GIT_DIR/audit_log, which is essentially a reflog with the refname prepended. The key, though, is that it isn't ever _read_ by git for reachability. So it becomes an immutable log of what happened, and we can happily prune the reflog to drop objects. In a log-structured ref storage world, I think I'd include a single bit per entry for use this for reachability. Then you could soft-expire reflog entries by dropping their reachability bit, but still retain them in your audit_log. The alternative is to just copy the entries to an archival log. There are some issues with append. Before appending we would need to verify the last record actually ends with an LF. If there was a power failure and only part of the last record wrote, you can't append without that record separator in place. Yeah, I think that is straightforward. You have to take a lock on the whole log anyway, so it's OK to fixup the previous entry. If that last record was truncated, and an LF was wedged in to do a new append, we can't trust that intermediate record. A CRC at the end of the record might make it safer to know the record is intact or bogus due to an earlier failed write that wasn't completed. I suspect you could get by with just realizing that the entry doesn't parse (that's what we do now for reflogs). But the idea of per-entry consistency checks is appealing. You could also include the CRC for the previous entry (remember that we would probably have a back-pointer to some byte offset to say this is the current ref state that I am building on). Then you can walk back the whole chain to know that it hasn't been damaged. If you want to get very fancy, replace your CRC with a cryptographically strong hash, and you've just reinvented a blockchain. :) What about the case of never expiring the reflog? This log would grow forever. You may eventually need to archive old sections of it (e.g. 1 year ago?) to maintain an audit log, while keeping the latest entry for each ref to rebuild the index. Yeah, that's certainly an option. I'd say that's somewhat outside the scope of git. If git provides the ability to prune entries completely (i.e., what reflog expire does now) and to soft-expire them, then that is enough for anyone to build whatever sort of archival system they want (e.g., soft-expire for reachability as desired, and then occasionally git reflog show your-archive git reflog expire). +1 to always storing the peeled value. This was a major improvement for $DAY_JOB's Git servers as peeling tags on the fly can be costly when your storage is something remote, such as NFS. Unfortunately the current wire protocol demands peeled information to serve a ref advertisement. Even on good disks, it makes the initial ref advertisement from git-upload-pack _way_ cheaper, because we don't have to actually touch the object database at all. It's basically just blitting out the packed-refs file. One thing we do is always peel all refs. We record a bit to state its been peeled, but there is no peeled value because the ref is pointing to a non-tag object (e.g. refs/heads/master points to a commit). Yeah, since c29c46f (pack-refs: add fully-peeled trait, 2013-03-18) we implicitly do this in packed-refs; if there's no peel line after the entry, it cannot be peeled. We could do the same here, but I think I favor being more implicit (I'd probably add a few bits of flags to each entry, and this could be one such flag). Updating the index on updates to a ref would be costly, as its O(N). It depends how you implement the index. A straight text index would be O(N). Replacing the index with a real key/value store should be very fast. But unless we are going to write our own, that's going to introduce a dependency (possibly one we can ship as we do with xdiff, but the whole JGit thing is an open question). You could skip some index updates. Record in the header of the index the length of the reflog file used to build it. When reading the index, scan the reflog from that position to the end and patch those updates in memory. Rewrites of the index could then be deferred until the scan delta on the log is high, or the next gc. Yeah, basically use the log as a journal. You save (or at least amortize) O(# of refs) work for the writers, at the cost of O(# of recent updates) work
Re: [PATCH v8 3/5] bisect: simplify the addition of new bisect terms
Junio C Hamano gits...@pobox.com writes: Matthieu Moy matthieu@imag.fr writes: diff --git a/bisect.c b/bisect.c index 2d3dbdc..08be634 100644 --- a/bisect.c +++ b/bisect.c @@ -747,7 +747,10 @@ static void handle_bad_merge_base(void) between %s and [%s].\n, bad_hex, bad_hex, good_hex); } else { -die(BUG: terms %s/%s not managed, name_bad, name_good); +fprintf(stderr, The merge base %s is %s.\n +This means the first commit marked %s is +between %s and [%s].\n, +bad_hex, name_bad, name_bad, bad_hex, good_hex); Indeed, I forgot to apply the previous remark. Fixed. - if (!strcmp(name_bad, bad)) { + if (!strcmp(name_bad, bad) !strcmp(name_good, good) { Indeed. Applied. -- Matthieu Moy http://www-verimag.imag.fr/~moy/ -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v2] Fix definition of ARRAY_SIZE for non-gcc builds
From: Charles Bailey cbaile...@bloomberg.net The improved ARRAY_SIZE macro uses BARF_UNLESS_AN_ARRAY which is expands to a valid check for recent gcc versions and to 0 for older gcc versions but is not defined on non-gcc builds. Non-gcc builds need this macro to expand to 0 as well. The current outer test (defined(__GNUC__) (__GNUC__ = 3)) is a strictly weaker condition than the inner test (GIT_GNUC_PREREQ(3, 1)) so we can omit the outer test and cause the BARF_UNLESS_AN_ARRAY macro to be defined correctly on non-gcc builds as well as gcc builds with older versions. Signed-off-by: Charles Bailey cbaile...@bloomberg.net --- This resend fixes a copy and paste error in the outer test in the commit message. The patch remains the same. This fixes a build regression introduced in v2.4.4 so this patch is based off maint. git-compat-util.h | 8 +++- 1 file changed, 3 insertions(+), 5 deletions(-) diff --git a/git-compat-util.h b/git-compat-util.h index b45c75f..8c2b7aa 100644 --- a/git-compat-util.h +++ b/git-compat-util.h @@ -58,15 +58,13 @@ #define BUILD_ASSERT_OR_ZERO(cond) \ (sizeof(char [1 - 2*!(cond)]) - 1) -#if defined(__GNUC__) (__GNUC__ = 3) -# if GIT_GNUC_PREREQ(3, 1) +#if GIT_GNUC_PREREQ(3, 1) /* arr[0] degrades to a pointer: a different type from an array */ # define BARF_UNLESS_AN_ARRAY(arr) \ BUILD_ASSERT_OR_ZERO(!__builtin_types_compatible_p(__typeof__(arr), \ __typeof__((arr)[0]))) -# else -# define BARF_UNLESS_AN_ARRAY(arr) 0 -# endif +#else +# define BARF_UNLESS_AN_ARRAY(arr) 0 #endif /* * ARRAY_SIZE - get the number of elements in a visible array -- 2.4.0.53.g8440f74 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
What's cooking in git.git (Jun 2015, #06; Wed, 24)
Here are the topics that have been cooking. Commits prefixed with '-' are only in 'pu' (proposed updates) while commits prefixed with '+' are in 'next'. Some of the topics in flight have overlaps with each other and have been excluded from 'pu'; most notably, I think the remainder of bc/object-id needs to wait until the for-each-ref topic from Karthik settles and then rebased on it, or something. We will be in the pre-release freeze soonish, and the next cycle would reopen mid next month. In the meantime, let's shift the focus on making sure that what has already been merged to 'master' are good (i.e. regression hunting and fixes). You can find the changes described here in the integration branches of the repositories listed at http://git-blame.blogspot.com/p/git-public-repositories.html -- [Graduated to master] * af/tcsh-completion-noclobber (2015-06-09) 1 commit (merged to 'next' on 2015-06-16 at 621f205) + git-completion.tcsh: fix redirect with noclobber The tcsh completion writes a bash scriptlet but that would have failed for users with noclobber set. * es/configure-getdelim (2015-06-03) 2 commits (merged to 'next' on 2015-06-11 at cdead14) + configure: add getdelim() check + config.mak.uname: Darwin: define HAVE_GETDELIM for modern OS X releases Auto-detect availability of getdelim() that helps optimized version of strbuf_getwholeline(). * es/osx-header-pollutes-mask-macro (2015-06-03) 2 commits (merged to 'next' on 2015-06-11 at cd8c39e) + ewah: use less generic macro name + ewah/bitmap: silence warning about MASK macro redefinition * es/send-email-sendmail-alias (2015-06-01) 10 commits (merged to 'next' on 2015-06-11 at b5e310e) + send-email: further warn about unsupported sendmail aliases features + t9001: add sendmail aliases line continuation tests + t9001: refactor sendmail aliases test infrastructure + send-email: implement sendmail aliases line continuation support + send-email: simplify sendmail aliases comment and blank line recognizer + send-email: refactor sendmail aliases parser + send-email: fix style: cuddle 'elsif' and 'else' with closing brace + send-email: drop noise comments which merely repeat what code says + send-email: visually distinguish sendmail aliases parser warnings + send-email: further document missing sendmail aliases functionality git send-email learned to handle more forms of sendmail style aliases file. * es/utf8-stupid-compiler-workaround (2015-06-05) 1 commit (merged to 'next' on 2015-06-11 at dc0f2d2) + utf8: NO_ICONV: silence uninitialized variable warning A compilation workaround. * fk/doc-format-patch-vn (2015-06-10) 1 commit (merged to 'next' on 2015-06-16 at 9be3516) + doc: format-patch: fix typo Docfix. * jc/apply-reject-noop-hunk (2015-06-01) 1 commit (merged to 'next' on 2015-06-11 at 8063665) + apply: reject a hunk that does not do anything git apply cannot diagnose a patch corruption when the breakage is to mark the length of the hunk shorter than it really is on the hunk header line @@ -l,k +m,n @@; one special case it could is when the hunk becomes no-op (e.g. k == n == 2 for two-line context patch output), and it learned to do so for this special case. * jc/do-not-feed-tags-to-clear-commit-marks (2015-06-01) 1 commit (merged to 'next' on 2015-06-11 at 65b4308) + format-patch: do not feed tags to clear_commit_marks() git format-patch --ignore-if-upstream A..B did not like to be fed tags as boundary commits. * jc/ll-merge-expose-path (2015-06-04) 1 commit (merged to 'next' on 2015-06-11 at 5c5fe41) + ll-merge: pass the original path to external drivers Traditionally, external low-level 3-way merge drivers are expected to produce their results based solely on the contents of the three variants given in temporary files named by %O, %A and %B on their command line. Additionally allow them to look at the final path (given by %P). * jk/index-pack-reduce-recheck (2015-06-09) 1 commit (merged to 'next' on 2015-06-16 at ff83705) + index-pack: avoid excessive re-reading of pack directory Disable have we lost a race with competing repack? check while receiving a huge object transfer that runs index-pack. * jk/stash-require-clean-index (2015-06-15) 1 commit (merged to 'next' on 2015-06-16 at beb4883) + Revert stash: require a clean index to apply A hotfix for the topic already in 'master'. * js/sleep-without-select (2015-06-05) 4 commits (merged to 'next' on 2015-06-11 at 278edb1) + lockfile: wait using sleep_millisec() instead of select() + lockfile: convert retry timeout computations to millisecond + help.c: wrap wait-only poll() invocation in sleep_millisec() + lockfile: replace random() by rand() Portability fix. * ld/p4-changes-block-size (2015-06-10) 4 commits (merged to 'next' on 2015-06-16 at 09b7daa) + git-p4: fixing --changes-block-size handling + git-p4: add tests for non-numeric
Re: [PATCH v8 5/5] bisect: allow any terms set by user
Junio C Hamano gits...@pobox.com writes: they would call term2 into term1 somewhere. e.g. -ancestors of term1. +ancestors of term1. For example, if something was buggy in +the old part of the history, you know somewhere the bug was +fixed, and you want to find the exact commit that fixed it, +you may want to say `git bisect terms fixed broken`; this +way, you would mark a commit that still has the bug with +`broken`, and a newer one after the fix with `fixed`. or something? Yes. I am wondering (together with the documentation patch) if it would be better to be more explicit, instead of term[12], like this: git bisect terms new old Yes. I eliminated all instance of term1 and term2 in the doc of the patch, and replaced with term-old and term-new. +bisect_terms () { +case $# in +0) +if test -s $GIT_DIR/BISECT_TERMS +then +{ +read term1 +read term2 +}$GIT_DIR/BISECT_TERMS +gettextln Your current terms are $term1 and $term2. The same comment on this part. Instead of git bisect terms that just says You are using $term1 and $term2, the users would benefit if it said You are using $term1 for newer state and $term2 for older state [*1*]. Done. It's up to date on https://github.com/moy/git/tree/bisect-terms Will resend. -- Matthieu Moy http://www-verimag.imag.fr/~moy/ -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH] Enable core.fsyncObjectFiles by default
On Tue, Jun 23, 2015 at 10:32:08PM -0700, Junio C Hamano wrote: Regarding loose object files, given that we write to a temporary, optionally fsync, close and then move to the final name, would we still see partially written file if we omit the fsync, or would the corruption be limited to either empty or missing? *Most* of the time the corruption will be an empty or missing file. It's possible that the file could be partially written. This is a relatively low-probability event, with the probability going up if the object file is large, and/or if the system is under memory pressure. The reason I am wondering is because the codepath to create an object (i.e. update-index --add, hash-object -w, or add) first checks if a packed or a loose object file _exists_ and if so bypasses writing the same thing anew, but the existence check for a loose object is to merely making sure that access(F_OK) (and optionally utime()) succeeds. If the potential breakage is limited to truncation to empty, then we could replace it with stat(2) and st.st_size check, as no loose object file can be empty. It would certainly be a good thing to do a st_size check; it can't possible hurt, and it will catch a large number of failures after a power failure. I could also imagine some hueristics that force an fsync if the object file is larger than a certain size (say, 4k if you are very paranoid, a few hundred kilobytes if you are less so), but past a certain point, it might be better just to tell the user to use fsyncObjectFiles and be done with it. - Ted -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH] cvsimport: silence regex warning appearing in Perl 5.22.
Since Perl 5.22, A literal '{' should now be escaped in a pattern. Silence the recently added warning by using \{ instead. Signed-off-by: Christian Neukirchen chneukirc...@gmail.com --- git-cvsimport.perl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/git-cvsimport.perl b/git-cvsimport.perl index 73d367c..8a68777 100755 --- a/git-cvsimport.perl +++ b/git-cvsimport.perl @@ -921,7 +921,7 @@ sub commit { # (See check_refname_component in refs.c.) 1 while $xtag =~ s/ (?: \.\.# Tag cannot contain '..'. - | \@{ # Tag cannot contain '@{'. + | \@\{# Tag cannot contain '@{'. | ^ - # Tag cannot begin with '-'. | \.lock $# Tag cannot end with '.lock'. | ^ \. # Tag cannot begin... -- 2.4.4 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 04/17] Makefile: a dry-run can error out if no perl. Document the issue
A 'make -n' dry-run is used as part of the /compat/vcbuild and /contrib/buildsystems code. The commit ee9be06 (perl: detect new files in MakeMaker builds, 2012-07-27) was not aware of that dry-run usage and thus would not execute the target. Add a comment to the make file stating the issue and the available solutions of either NO_PERL or a '+recipe'. Signed-off-by: Philip Oakley philipoak...@iee.org --- Makefile | 3 +++ 1 file changed, 3 insertions(+) diff --git a/Makefile b/Makefile index 149f1c7..22108bb 100644 --- a/Makefile +++ b/Makefile @@ -1746,6 +1746,9 @@ $(SCRIPT_PERL_GEN): perl/perl.mak perl/perl.mak: perl/PM.stamp +# 'make -n' (dry-run) will not execute this target which creates/updates the PM.stamp file. +# To avoid the error of failing to find the target PM.stamp, either use NO_PERL=1 (YesPlease), +# or add a leading '+' to the recipe '+$(QUIET_GEN)$(FIND) perl ...' so that it is executed. perl/PM.stamp: FORCE @$(FIND) perl -type f -name '*.pm' | sort $@+ \ { cmp $@+ $@ /dev/null 2/dev/null || mv $@+ $@; } \ -- 2.3.1 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 14/17] Vcproj.pm: list git.exe first to be startup project
Visual Studio take the first listed application/library as the default startup project [1]. Parse the application list for git.exe, then list the libraries, then the other git dashed forms in the git.sln file. Detect the 'git' project and place it the head of the apps list, rather than the tail. Export the apps list before libs list for both the projects and global structures of the .sln file. [1] http://stackoverflow.com/questions/1238553/ vs2008-where-is-the-startup-project-setting-stored-for-a-solution In the solution file, there are a list of pseudo-XML Project entries. It turns out that whatever is the first one ends up as the Startup Project, unless it’s overridden in the suo file. Argh. I just rearranged the order in the file and it’s good. just moving the pseudo-xml isn't enough. You also have to move the group of entries in the GlobalSection(ProjectConfigurationPlatforms) = postSolution group that has the GUID of the project you moved to the top. So there are two places to move lines. Signed-off-by: Philip Oakley philipoak...@iee.org --- contrib/buildsystems/Generators/Vcproj.pm | 33 ++- 1 file changed, 19 insertions(+), 14 deletions(-) diff --git a/contrib/buildsystems/Generators/Vcproj.pm b/contrib/buildsystems/Generators/Vcproj.pm index 1b01d58..cc2fa21 100644 --- a/contrib/buildsystems/Generators/Vcproj.pm +++ b/contrib/buildsystems/Generators/Vcproj.pm @@ -560,20 +560,18 @@ sub createGlueProject { foreach (@apps) { $_ =~ s/\//_/g; $_ =~ s/\.exe//; -push(@tmp, $_); +if ($_ eq git ) { +unshift(@tmp, $_); +} else { +push(@tmp, $_); +} } @apps = @tmp; open F, git.sln || die Could not open git.sln for writing!\n; binmode F, :crlf; print F $SLN_HEAD; -foreach (@libs) { -my $libname = $_; -my $uuid = $build_structure{LIBS_${libname}_GUID}; -print F $SLN_PRE; -print F \${libname}\, \${libname}\\${libname}.vcproj\, \${uuid}\; -print F $SLN_POST; -} + my $uuid_libgit = $build_structure{LIBS_libgit_GUID}; my $uuid_xdiff_lib = $build_structure{LIBS_xdiff_lib_GUID}; foreach (@apps) { @@ -587,6 +585,13 @@ sub createGlueProject { print F EndProjectSection; print F $SLN_POST; } +foreach (@libs) { +my $libname = $_; +my $uuid = $build_structure{LIBS_${libname}_GUID}; +print F $SLN_PRE; +print F \${libname}\, \${libname}\\${libname}.vcproj\, \${uuid}\; +print F $SLN_POST; +} print F EOM; Global @@ -598,17 +603,17 @@ EOM print F EOM; GlobalSection(ProjectConfigurationPlatforms) = postSolution EOM -foreach (@libs) { -my $libname = $_; -my $uuid = $build_structure{LIBS_${libname}_GUID}; +foreach (@apps) { +my $appname = $_; +my $uuid = $build_structure{APPS_${appname}_GUID}; print F \t\t${uuid}.Debug|Win32.ActiveCfg = Debug|Win32\n; print F \t\t${uuid}.Debug|Win32.Build.0 = Debug|Win32\n; print F \t\t${uuid}.Release|Win32.ActiveCfg = Release|Win32\n; print F \t\t${uuid}.Release|Win32.Build.0 = Release|Win32\n; } -foreach (@apps) { -my $appname = $_; -my $uuid = $build_structure{APPS_${appname}_GUID}; +foreach (@libs) { +my $libname = $_; +my $uuid = $build_structure{LIBS_${libname}_GUID}; print F \t\t${uuid}.Debug|Win32.ActiveCfg = Debug|Win32\n; print F \t\t${uuid}.Debug|Win32.Build.0 = Debug|Win32\n; print F \t\t${uuid}.Release|Win32.ActiveCfg = Release|Win32\n; -- 2.3.1 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 17/17] config.mak.uname: add MSVC No_SafeExeceptionHandler option
Signed-off-by: Philip Oakley philipoak...@iee.org --- config.mak.uname | 9 + 1 file changed, 9 insertions(+) diff --git a/config.mak.uname b/config.mak.uname index 943c439..1c27828 100644 --- a/config.mak.uname +++ b/config.mak.uname @@ -1,5 +1,9 @@ # Platform specific Makefile tweaks based on uname detection +# Define NO_SAFESEH if you need MSVC/Visual Studio to ignore the lack of +# Microsoft's Safe Exception Handling in libraries (such as zlib). +# Typically required for VS2013+/32-bit compilation on Vista+ versions. + uname_S := $(shell sh -c 'uname -s 2/dev/null || echo not') uname_M := $(shell sh -c 'uname -m 2/dev/null || echo not') uname_O := $(shell sh -c 'uname -o 2/dev/null || echo not') @@ -385,6 +389,11 @@ ifeq ($(uname_S),Windows) PTHREAD_LIBS = lib = BASIC_CFLAGS += -DPROTECT_NTFS_DEFAULT=1 + +ifdef NO_SAFESEH + LDFLAGS += -SAFESEH:NO +endif + ifndef DEBUG BASIC_CFLAGS += -GL -Os -MD BASIC_LDFLAGS += -LTCG -- 2.3.1 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 13/17] engine.pl: provide more debug print statements
Assist developers transitioning between the two cultures by including appropriate, but commented out, debug statements. The exception is when an unhandled compiler option is detected, where printing of the full line will supplement the line number and option part. Otherwise the OP has no immediate mechanism for inspecting the relevant part of the makedry output. These debug print statements act as a guide for a poor man's --verbose option. The test suite doesn't cover the contrib/buildsystems (or Msysgit's msvc-build) contributions so fails to notice breakages there-in. It is doubly hard to get developers to ride both horses so, contrary to normal convention, retain selected debug statements as a safety net for those willing to try. Signed-off-by: Philip Oakley philipoak...@iee.org --- contrib/buildsystems/engine.pl | 4 1 file changed, 4 insertions(+) diff --git a/contrib/buildsystems/engine.pl b/contrib/buildsystems/engine.pl index 7a2aeef..ac2970a 100644 --- a/contrib/buildsystems/engine.pl +++ b/contrib/buildsystems/engine.pl @@ -41,6 +41,7 @@ EOM # Parse command-line options while (@ARGV) { my $arg = shift @ARGV; + #print Arg: $arg \n; if ($arg eq -h || $arg eq --help || $arg eq -?) { showUsage(); exit(0); @@ -129,6 +130,7 @@ sub parseMakeOutput print Parsing GNU Make output to figure out build structure...\n; my $line = 0; while (my $text = shift @makedry) { + #print Make: $text\n; # show the makedry line my $ate_next; do { $ate_next = 0; @@ -263,6 +265,7 @@ sub handleCompileLine } elsif ($part =~ /\.(c|cc|cpp)$/) { $sourcefile = $part; } else { +print full line: $line\n; die Unhandled compiler option @ line $lineno: $part; } } @@ -288,6 +291,7 @@ sub handleLibLine $libout = $part; $libout =~ s/\.a$//; } else { +print full line: $line\n; die Unhandled lib option @ line $lineno: $part; } } -- 2.3.1 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 15/17] vcbuild/readme: Improve layout and reference msvc-build script
Layout the 'either/or' with more white space to clarify which alternatives are matched up. Reference the Msysgit build script which automates one sequence of options. Signed-off-by: Philip Oakley philipoak...@iee.org --- compat/vcbuild/README | 27 +++ 1 file changed, 19 insertions(+), 8 deletions(-) diff --git a/compat/vcbuild/README b/compat/vcbuild/README index df8a657..7548dc4 100644 --- a/compat/vcbuild/README +++ b/compat/vcbuild/README @@ -3,20 +3,24 @@ The Steps of Build Git with VS2008 1. You need the build environment, which contains the Git dependencies to be able to compile, link and run Git with MSVC. - You can either use the binary repository: + You can either: + use the binary repository: WWW: http://repo.or.cz/w/msvcgit.git Git: git clone git://repo.or.cz/msvcgit.git Zip: http://repo.or.cz/w/msvcgit.git?a=snapshot;h=master;sf=zip - and call the setup_32bit_env.cmd batch script before compiling Git, - (see repo/package README for details), or the source repository: + and call the setup_32bit_env.cmd batch script before compiling Git, + (see repo/package README for details), + + or: + use the source repository: WWW: http://repo.or.cz/w/gitbuild.git Git: git clone git://repo.or.cz/gitbuild.git Zip: (None, as it's a project with submodules) - and build the support libs as instructed in that repo/package. + and build the support libs as instructed in that repo/package. 2. Ensure you have the msysgit environment in your path, so you have GNU Make, bash and perl available. @@ -33,18 +37,25 @@ The Steps of Build Git with VS2008 make common-cmds.h to generate the common-cmds.h file needed to compile git. -4. Then either build Git with the GNU Make Makefile in the Git projects - root +4. Then either + + build Git with the GNU Make Makefile in the Git projects root make MSVC=1 - or generate Visual Studio solution/projects (.sln/.vcproj) with the + or + + generate Visual Studio solution/projects (.sln/.vcproj) with the command perl contrib/buildsystems/generate -g Vcproj and open and build the solution with the IDE devenv git.sln /useenv - or build with the IDE build engine directly from the command line + or + + build with the IDE build engine directly from the command line devenv git.sln /useenv /build Release|Win32 The /useenv option is required, so Visual Studio picks up the environment variables for the support libraries required to build Git, which you set up in step 1. Done! + +Or, use the Msysgit msvc-build script; available from that project. -- 2.3.1 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 00/17] Make the msvc-build scripts work again
This series fixes the scripts which generated Visual Studio project files. The scripts had bit rotted over the years as other commits changed the git makefile which it post processed. The series doesn't attempt to install the Visual Studio compiled product but allows Windows developers familiar with VS to support the Windows SDK port of Git. The fixes are presented in a fine grained manner. A previous patch series were at $gmane/21132 (2014-11-20), $gmane/21207 (2014-12-26), and on Msysgit list (2015-02-23) https://groups.google.com/forum/?hl=en_US?hl%3Den#!topic/msysgit/aiEVBKjRshY https://github.com/msysgit/git/pull/318/files Hopefully it's not too late in the cycle for a review of this contrib/compat item. Philip Oakley (17): .gitignore: improve MSVC ignore patterns .gitignore: ignore library directories created by MSVC VS2008 buildsystem (msvc-build) Vcproj.pm: remove duplicate GUID Makefile: a dry-run can error out if no perl. Document the issue engine.pl: fix error message (lib-link) engine.pl: Avoid complications with perl support engine.pl: Properly accept quoted spaces in filenames engine.pl: Fix i18n -o option in msvc buildsystem generator engine.pl: ignore invalidcontinue.obj which is known to MSVC engine.pl: name the msvc buildsystem's makedry error file engine.pl: delete the captured stderr file if empty engine.pl: add debug line to capture the dry-run engine.pl: provide more debug print statements Vcproj.pm: list git.exe first to be startup project vcbuild/readme: Improve layout and reference msvc-build script msvc-build: add complete Microsoft Visual C compilation script config.mak.uname: add MSVC No_SafeExeceptionHandler option .gitignore| 8 ++- Makefile | 3 ++ compat/vcbuild/README | 27 +++--- compat/vcbuild/scripts/msvc-build | 89 +++ config.mak.uname | 9 contrib/buildsystems/Generators/Vcproj.pm | 34 ++-- contrib/buildsystems/engine.pl| 37 ++--- 7 files changed, 174 insertions(+), 33 deletions(-) create mode 100644 compat/vcbuild/scripts/msvc-build mode change 100755 = 100644 contrib/buildsystems/engine.pl -- 2.3.1 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 11/17] engine.pl: delete the captured stderr file if empty
Keep the build clean of extraneous files if it is indeed clean. Otherwise leave the msvc-build-makedryerrors.txt file both as a flag for any CI system or for manual debugging. Note that the file will contain the new values of the GIT_VERSION and GITGUI_VERSION if they were generated by the make file. They are omitted if the release is tagged and indentically defined in their respective GIT_VERSION_GEN file DEF_VER variables. Signed-off-by: Philip Oakley philipoak...@iee.org --- contrib/buildsystems/engine.pl | 2 ++ 1 file changed, 2 insertions(+) diff --git a/contrib/buildsystems/engine.pl b/contrib/buildsystems/engine.pl index 7eba870..27884f7 100644 --- a/contrib/buildsystems/engine.pl +++ b/contrib/buildsystems/engine.pl @@ -77,6 +77,8 @@ EOM my $ErrsFile = msvc-build-makedryerrors.txt; @makedry = `cd $git_dir make -n MSVC=1 NO_PERL=1 V=1 2$ErrsFile` if !@makedry; +# test for an empty Errors file and remove it +for ($ErrsFile) {unlink $_ if (-f $_) (!-s $_);} # Parse the make output into usable info parseMakeOutput(); -- 2.3.1 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: git name-rev not accepting abbreviated SHA with --stdin
Sitaram Chamarty sitar...@gmail.com writes: This *is* documented, but I'm curious why this distinction is made. I think it is from mere laziness, and also in a smaller degree coming from an expectation that --stdin would be fed by another script like rev-list where feeding full 40-hex is less work than feeding unique abbreviated prefix. -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: What's cooking in git.git (Jun 2015, #06; Wed, 24)
* pt/pull-builtin (2015-06-18) 19 commits - pull: remove redirection to git-pull.sh - pull --rebase: error on no merge candidate cases - pull --rebase: exit early when the working directory is dirty - pull: configure --rebase via branch.name.rebase or pull.rebase - pull: teach git pull about --rebase - pull: set reflog message - pull: implement pulling into an unborn branch - pull: fast-forward working tree if head is updated - pull: check if in unresolved merge state - pull: support pull.ff config - pull: error on no merge candidates - pull: pass git-fetch's options to git-fetch - pull: pass git-merge's options to git-merge - pull: pass verbosity, --progress flags to fetch and merge - pull: implement fetch + merge - pull: implement skeletal builtin pull - argv-array: implement argv_array_pushv() - parse-options-cb: implement parse_opt_passthru_argv() - parse-options-cb: implement parse_opt_passthru() Reimplement 'git pull' in C. This is v4 ($gmane/271943). Comments from mentors and others? I think the series is good as is. -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: RFC/Pull Request: Refs db backend
On Wed, Jun 24, 2015 at 05:49:20AM -0400, Jeff King wrote: I don't know how much that helps for the JGit situation. It punts the native code out of JGit, but people using JGit still have to have the native helper from git on their system. I have no problems at all with pluggable $FANCY_DB that not everybody supports. But I think we would want _some_ baseline that is reasonably performant, and that everybody will support. I'm not sure putting the index into a flat file is performant enough. Is there any basic key/value store that is has both a C and a pure-Java version (e.g., berkeley db)? Berkeley DB has switched to the AGPLv3 for new versions. Besides being unpalatable for many people, it's also incompatible with the GPLv2. I do otherwise like Berkeley DB: it performs reasonably well and is available on most systems. -- brian m. carlson / brian with sandals: Houston, Texas, US +1 832 623 2791 | http://www.crustytoothpaste.net/~bmc | My opinion only OpenPGP: RSA v4 4096b: 88AC E9B2 9196 305B A994 7552 F1BA 225C 0223 B187 signature.asc Description: Digital signature
[PATCH 08/17] engine.pl: Fix i18n -o option in msvc buildsystem generator
The i18n 5e9637c (i18n: add infrastructure for translating Git with gettext, 2011-11-18) introduced an extra '-o' option into the make file. If the msvc buildsystem is run without NO_GETTEXT being set then this broke the engine.pl code for extracting the git.sln for msvc gui-IDE. The setting of NO_GETTEXT was not fixed until later, relative to the Msysgit project where this issue was being investigated. The presence of these options in the Makefile output should not compromise the derived build structure. They should be ignored. Add tests to remove these non linker options, in same vein as 74cf9bd (engine.pl: Fix a recent breakage of the buildsystem generator, 2010-01-22). Signed-off-by: Philip Oakley philipoak...@iee.org --- contrib/buildsystems/engine.pl | 6 ++ 1 file changed, 6 insertions(+) diff --git a/contrib/buildsystems/engine.pl b/contrib/buildsystems/engine.pl index ccb59fd..73f2472 100755 --- a/contrib/buildsystems/engine.pl +++ b/contrib/buildsystems/engine.pl @@ -141,6 +141,12 @@ sub parseMakeOutput next; } +if ($text =~ /^(mkdir|msgfmt) /) { +# options to the Portable Object translations +# the line mkdir ... msgfmt ... contains no linker options +next; +} + if($text =~ / -c /) { # compilation handleCompileLine($text, $line); -- 2.3.1 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 02/17] .gitignore: ignore library directories created by MSVC VS2008 buildsystem
Signed-off-by: Philip Oakley philipoak...@iee.org --- .gitignore | 3 +++ 1 file changed, 3 insertions(+) diff --git a/.gitignore b/.gitignore index 55498c1..706d0d9 100644 --- a/.gitignore +++ b/.gitignore @@ -177,6 +177,7 @@ /gitweb/gitweb.cgi /gitweb/static/gitweb.js /gitweb/static/gitweb.min.* +/libgit /test-chmtime /test-ctype /test-config @@ -209,6 +210,8 @@ /test-urlmatch-normalization /test-wildmatch /common-cmds.h +/vcs-svn_lib +/xdiff_lib *.tar.gz *.dsc *.deb -- 2.3.1 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 07/17] engine.pl: Properly accept quoted spaces in filenames
The engine.pl script barfs on the properly quoted spaces in filename options prevalent on Windows. Use shellwords() rather than split() to separate such options. Helped-by: Junio C Hamano gits...@pobox.com Signed-off-by: Philip Oakley philipoak...@iee.org --- $gamane/21145 $gmane/21147 --- contrib/buildsystems/engine.pl | 7 --- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/contrib/buildsystems/engine.pl b/contrib/buildsystems/engine.pl index 4d0a616..ccb59fd 100755 --- a/contrib/buildsystems/engine.pl +++ b/contrib/buildsystems/engine.pl @@ -12,6 +12,7 @@ use File::Basename; use File::Spec; use Cwd; use Generators; +use Text::ParseWords; my (%build_structure, %compile_options, @makedry); my $out_dir = getcwd(); @@ -231,7 +232,7 @@ sub removeDuplicates sub handleCompileLine { my ($line, $lineno) = @_; -my @parts = split(' ', $line); +my @parts = shellwords($line); my $sourcefile; shift(@parts); # ignore cmd while (my $part = shift @parts) { @@ -265,7 +266,7 @@ sub handleLibLine my (@objfiles, @lflags, $libout, $part); # kill cmd and rm 'prefix' $line =~ s/^rm -f .* .* rcs //; -my @parts = split(' ', $line); +my @parts = shellwords($line); while ($part = shift @parts) { if ($part =~ /^-/) { push(@lflags, $part); @@ -306,7 +307,7 @@ sub handleLinkLine { my ($line, $lineno) = @_; my (@objfiles, @lflags, @libs, $appout, $part); -my @parts = split(' ', $line); +my @parts = shellwords($line); shift(@parts); # ignore cmd while ($part = shift @parts) { if ($part =~ /^-IGNORE/) { -- 2.3.1 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 03/17] (msvc-build) Vcproj.pm: remove duplicate GUID
Delete the duplicated GUID from the generation code for the Visual Studio .sln project file. The duplicate GUID tended to be allocated to test-svn-fe, which was then ignored by Visual Studio / MSVC, and it's omission from the build never noticed. Signed-off-by: Philip Oakley philipoak...@iee.org --- contrib/buildsystems/Generators/Vcproj.pm | 1 - 1 file changed, 1 deletion(-) diff --git a/contrib/buildsystems/Generators/Vcproj.pm b/contrib/buildsystems/Generators/Vcproj.pm index cfa74ad..1b01d58 100644 --- a/contrib/buildsystems/Generators/Vcproj.pm +++ b/contrib/buildsystems/Generators/Vcproj.pm @@ -52,7 +52,6 @@ my @GUIDS = ( {00785268-A9CC-4E40-AC29-BAC0019159CE}, {4C06F56A-DCDB-46A6-B67C-02339935CF12}, {3A62D3FD-519E-4EC9-8171-D2C1BFEA022F}, -{3A62D3FD-519E-4EC9-8171-D2C1BFEA022F}, {9392EB58-D7BA-410B-B1F0-B2FAA6BC89A7}, {2ACAB2D5-E0CE-4027-BCA0-D78B2D7A6C66}, {86E216C3-43CE-481A-BCB2-BE5E62850635}, -- 2.3.1 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 09/17] engine.pl: ignore invalidcontinue.obj which is known to MSVC
Commit 4b623d8 (MSVC: link in invalidcontinue.obj for better POSIX compatibility, 2014-03-29) is not processed correctly by the buildsystem. Ignore it. Also split the .o and .obj processing; 'make' does not produce .obj files. Only substitute filenames ending with .o when generating the source .c filename. Signed-off-by: Philip Oakley philipoak...@iee.org --- contrib/buildsystems/engine.pl | 10 +++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/contrib/buildsystems/engine.pl b/contrib/buildsystems/engine.pl index 73f2472..e8aa8ea 100755 --- a/contrib/buildsystems/engine.pl +++ b/contrib/buildsystems/engine.pl @@ -289,7 +289,7 @@ sub handleLibLine #exit(1); foreach (@objfiles) { my $sourcefile = $_; -$sourcefile =~ s/\.o/.c/; +$sourcefile =~ s/\.o$/.c/; push(@sources, $sourcefile); push(@cflags, @{$compile_options{${sourcefile}_CFLAGS}}); push(@defines, @{$compile_options{${sourcefile}_DEFINES}}); @@ -333,8 +333,12 @@ sub handleLinkLine } elsif ($part =~ /\.(a|lib)$/) { $part =~ s/\.a$/.lib/; push(@libs, $part); -} elsif ($part =~ /\.(o|obj)$/) { +} elsif ($part eq 'invalidcontinue.obj') { +# ignore - known to MSVC +} elsif ($part =~ /\.o$/) { push(@objfiles, $part); +} elsif ($part =~ /\.obj$/) { +# do nothing, 'make' should not be producing .obj, only .o files } else { die Unhandled link option @ line $lineno: *$part*; } @@ -343,7 +347,7 @@ sub handleLinkLine #exit(1); foreach (@objfiles) { my $sourcefile = $_; -$sourcefile =~ s/\.o/.c/; +$sourcefile =~ s/\.o$/.c/; push(@sources, $sourcefile); push(@cflags, @{$compile_options{${sourcefile}_CFLAGS}}); push(@defines, @{$compile_options{${sourcefile}_DEFINES}}); -- 2.3.1 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 10/17] engine.pl: name the msvc buildsystem's makedry error file
Save the stderr from the dry MSVC make to a well named file for later review. Use 'msvc-build-makedryerrors.txt' which should be obvious as to its source, and is not ignored by 'git status'. Signed-off-by: Philip Oakley philipoak...@iee.org --- contrib/buildsystems/engine.pl | 5 - 1 file changed, 4 insertions(+), 1 deletion(-) mode change 100755 = 100644 contrib/buildsystems/engine.pl diff --git a/contrib/buildsystems/engine.pl b/contrib/buildsystems/engine.pl old mode 100755 new mode 100644 index e8aa8ea..7eba870 --- a/contrib/buildsystems/engine.pl +++ b/contrib/buildsystems/engine.pl @@ -73,7 +73,10 @@ Running GNU Make to figure out build structure... EOM # Pipe a make --dry-run into a variable, if not already loaded from file -@makedry = `cd $git_dir make -n MSVC=1 NO_PERL=1 V=1 2/dev/null` if !@makedry; +# Capture the make dry stderr to file for review (will be empty for a release build). + +my $ErrsFile = msvc-build-makedryerrors.txt; +@makedry = `cd $git_dir make -n MSVC=1 NO_PERL=1 V=1 2$ErrsFile` if !@makedry; # Parse the make output into usable info parseMakeOutput(); -- 2.3.1 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 05/17] engine.pl: fix error message (lib-link)
Signed-off-by: Philip Oakley philipoak...@iee.org --- contrib/buildsystems/engine.pl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/contrib/buildsystems/engine.pl b/contrib/buildsystems/engine.pl index 23da787..5398315 100755 --- a/contrib/buildsystems/engine.pl +++ b/contrib/buildsystems/engine.pl @@ -329,7 +329,7 @@ sub handleLinkLine } elsif ($part =~ /\.(o|obj)$/) { push(@objfiles, $part); } else { -die Unhandled lib option @ line $lineno: $part; +die Unhandled link option @ line $lineno: *$part*; } } #print AppOut: '$appout'\nLFlags: @lflags\nLibs : @libs\nOfiles: @objfiles\n; -- 2.3.1 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 16/17] msvc-build: add complete Microsoft Visual C compilation script
Implement the README to facilitate cross community development. Include comments for those Windows folks not yet fully familiar with bash commands. This is identical to the msysgit script, except for the 'cd toplevel' step, and comments for the edification of converts from Windows. Original author: Johannes Schindelin (2011-11-01 3142da4 : Add a script to make the MSVC build more convenient). Signed-off-by: Philip Oakley philipoak...@iee.org --- TODO: Also resolve the cleaning of newer VS2010 products. --- compat/vcbuild/README | 2 +- compat/vcbuild/scripts/msvc-build | 89 +++ 2 files changed, 90 insertions(+), 1 deletion(-) create mode 100644 compat/vcbuild/scripts/msvc-build diff --git a/compat/vcbuild/README b/compat/vcbuild/README index 7548dc4..faaea69 100644 --- a/compat/vcbuild/README +++ b/compat/vcbuild/README @@ -58,4 +58,4 @@ The Steps of Build Git with VS2008 Done! -Or, use the Msysgit msvc-build script; available from that project. +Or, use the msvc-build script; available from /compat/vcbuild/scripts/. diff --git a/compat/vcbuild/scripts/msvc-build b/compat/vcbuild/scripts/msvc-build new file mode 100644 index 000..52b925d --- /dev/null +++ b/compat/vcbuild/scripts/msvc-build @@ -0,0 +1,89 @@ +#!/bin/sh + +# This msvc-build command should be executed from the msysgit directory level +# This is so that the 'cd/git' step works and the subequent operations have the right msysgit super directory. +set -e # Exit immediately if a command exits with a nonzero exit status. + +gui= +clean= +while test $# -gt 0 +do + case $1 in + --gui|--dev|--devenv|--vs|--visual-studio) + gui=t + ;; + clean) + clean=t + ;; + *) + echo Usage: $0 [--vs] [clean] 2 + exit 1 + ;; + esac + shift +done + +cd $(git rev-parse --show-toplevel) + +case $clean in +t) + case $gui in + t) + rm -rf git.sln libgit + # remove all the new VS2010 stuff as well + # rm -rf git.sdf + ;; + '') + make clean + # surely needs make clean MSVC=1 + # otherwise it could assume the wrong make products [MinGW vs Windows]. + ;; + esac + exit + ;; +esac + +to_ignore=$(git ls-files --other --exclude-standard msvcgit msvc-build.cmd) +test -z $to_ignore || { + mkdir -p .git/info + echo $to_ignore | + sed 's/^/\//' .git/info/exclude +} || exit + +test -d msvcgit || git clone git://repo.or.cz/msvcgit.git + +vsvars= +# assume cl.exe will populate its relevant environment variables +# if cl.exe does not exist, populate vsvars with the most recent Visual Studio path +type cl.exe 2 /dev/null || +vsvars=$(ls -t \ + $PROGRAMFILES/Microsoft Visual Studio*/Common7/Tools/vsvars32.bat | + head -n 1) + + +config_mak= +# if a config.mak file (dot, not underscore) exists, back it up, +# remember the backup file name in config_mak. +test -f config.mak +config_mak=config.mak.bup.$$ +mv config.mak $config_mak + +cat config.mak EOF +CFLAGS += -Imsvcgit/32bits/include +LDFLAGS += -Lmsvcgit/32bits/lib +EOF + +echo call \$vsvars\ msvc-build.cmd +if test -z $gui +then + echo 'make MSVC=1' msvc-build.cmd +else + echo 'perl contrib/buildsystems/generate -g Vcproj' msvc-build.cmd + echo 'start git.sln' msvc-build.cmd +fi + +cmd /c msvc-build.cmd + +# if we made a backup file (name in config_mak), then restore it. +test -z $config_mak || +mv $config_mak config.mak -- 2.3.1 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 06/17] engine.pl: Avoid complications with perl support
ee9be06 (perl: detect new files in MakeMaker builds, 2012-07-27) did not include dry-run support for the generation of the PM.stamp file, though the dry-run output is used by the build engine. Disable the perl processing during the dry-run to avoid the issue. Signed-off-by: Philip Oakley philipoak...@iee.org --- contrib/buildsystems/engine.pl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/contrib/buildsystems/engine.pl b/contrib/buildsystems/engine.pl index 5398315..4d0a616 100755 --- a/contrib/buildsystems/engine.pl +++ b/contrib/buildsystems/engine.pl @@ -72,7 +72,7 @@ Running GNU Make to figure out build structure... EOM # Pipe a make --dry-run into a variable, if not already loaded from file -@makedry = `cd $git_dir make -n MSVC=1 V=1 2/dev/null` if !@makedry; +@makedry = `cd $git_dir make -n MSVC=1 NO_PERL=1 V=1 2/dev/null` if !@makedry; # Parse the make output into usable info parseMakeOutput(); -- 2.3.1 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 01/17] .gitignore: improve MSVC ignore patterns
Add the Microsoft .manifest pattern, and correct the generic 'Debug' and 'Release' directory patterns which were mechanically adjusted way back in c591d5f (gitignore: root most patterns at the top-level directory, 2009-10-26) to allow multi-level projects within the Git suite. Signed-off-by: Philip Oakley philipoak...@iee.org --- .gitignore | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/.gitignore b/.gitignore index 422c538..55498c1 100644 --- a/.gitignore +++ b/.gitignore @@ -246,5 +246,6 @@ *.user *.idb *.pdb -/Debug/ -/Release/ +*.manifest +**/Debug/ +**/Release/ -- 2.3.1 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: git name-rev not accepting abbreviated SHA with --stdin
On 06/25/2015 05:41 AM, Junio C Hamano wrote: Sitaram Chamarty sitar...@gmail.com writes: This *is* documented, but I'm curious why this distinction is made. I think it is from mere laziness, and also in a smaller degree coming from an expectation that --stdin would be fed by another script like rev-list where feeding full 40-hex is less work than feeding unique abbreviated prefix. Makes sense; thanks. Maybe if I feel really adventurous I will, one day, look at the code :-) -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH v5 01/11] t6301: for-each-ref tests for ref-filter APIs
Karthik Nayak karthik@gmail.com writes: t/t6301-for-each-ref-filter.sh | 19 +++ t6301 is already used in mh/reporting-broken-refs-from-for-each-ref topic. Please renumber. -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH/WIP v3 07/31] am: extract patch, message and authorship with git-mailinfo
Paul Tan pyoka...@gmail.com writes: 3. I'm over-thinking this and you just want the struct strbufs in the struct am_state to be switched to char*s? Yes, everybody interacts with am_state, and these fields are supposed to be constant during the processing of each patch input message; they should be simple strings, not strbufs, to make sure if anybody _does_ muck with them in-place, that would be very visible. The helpers to initialize them are free to use strbuf API to prepare these simple string fields, of course. (On a somewhat related thought, currently we do write_file() all over the place, which is really ugly. I'm leaning heavily on introducing an am_save() function, for I don't care how it is done but just update the contents of the am state directory so that it matches the contents of the struct am_state. Sure; the scripted Porcelain may have done echo here, echo there instead of concatenate into a $var and then 'echo $var' at end as that is more natural way to program in that environment. You are doing this in C and prepare the thing in-core and write it all at the point to snapshot may well be the more natural way to program. As long as a process that stops in the middle does not leave on-disk state inconsistent, batching would be fine. For example, you may apply and commit two (or more) patches without updating the on-disk state as you do not see need to give control back to the user (i.e. they applied cleanly) and then write out the on-disk state with .next incremented by two (or more) before giving the control back could be a valid optimization (take this example with a grain of salt, though; I haven't thought too deeply about what should happen if you Ctrl-C the process in the middle). -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH/RFC] Revert git am/mailinfo: Don't look at in-body headers when rebasing
Paul Tan pyoka...@gmail.com writes: On Tue, Jun 16, 2015 at 5:03 PM, Paul Tan pyoka...@gmail.com wrote: This reverts commit d25e51596be9271ad833805a3d6f9012dc24ee79, removing git-mailsplit's --no-inbody-headers option. While --no-inbody-headers was introduced to prevent commit messages from being munged by git-mailinfo while rebasing, the need for this option disappeared since 5e835ca (rebase: do not munge commit log message, 2008-04-16), as git-am bypasses git-mailinfo and gets the commit message directly from the commit ID in the patch. git-am is the only user of --no-inbody-headers, and this option is not documented. As such, it should be removed. Signed-off-by: Paul Tan pyoka...@gmail.com What do you think about applying this patch? Indifferent, even though it would be the right thing to do in the longer term. Keeping what we think nobody uses does not hurt us at least in the short term; removing such a thing hurts us if it turns out that somebody whose use we didn't know about were actually using it. And my time is better spent at this point in the cycle on other things than having to worry about possible fallouts from the removal that is not urgent. -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH/WIP v3 04/31] am: implement patch queue mechanism
Hi Paul, On 2015-06-18 13:25, Paul Tan wrote: diff --git a/builtin/am.c b/builtin/am.c index dbc8836..af68c51 100644 --- a/builtin/am.c +++ b/builtin/am.c @@ -6,6 +6,158 @@ #include cache.h #include builtin.h #include exec_cmd.h +#include parse-options.h +#include dir.h + +struct am_state { + /* state directory path */ + struct strbuf dir; + + /* current and last patch numbers, 1-indexed */ + int cur; + int last; +}; + +/** + * Initializes am_state with the default values. + */ +static void am_state_init(struct am_state *state) +{ + memset(state, 0, sizeof(*state)); + + strbuf_init(state-dir, 0); +} With strbufs, we use the initializer STRBUF_INIT. How about using #define AM_STATE_INIT { STRBUF_INIT, 0, 0 } here? +/** + * Reads the contents of `file`. The third argument can be used to give a hint + * about the file size, to avoid reallocs. Returns number of bytes read on + * success, -1 if the file does not exist. If trim is set, trailing whitespace + * will be removed from the file contents. + */ +static int read_state_file(struct strbuf *sb, const char *file, size_t hint, int trim) +{ + strbuf_reset(sb); + if (strbuf_read_file(sb, file, hint) = 0) { + if (trim) + strbuf_trim(sb); + + return sb-len; + } + + if (errno == ENOENT) + return -1; + + die_errno(_(could not read '%s'), file); +} A couple of thoughts: - why not reuse the strbuf by making it a part of the am_state()? That way, you can allocate, say, 1024 bytes (should be plenty enough for most of our operations) and just reuse them in all of the functions. We will not make any of this multi-threaded anyway, I don't think. - Given that we only read short files all the time, why not skip the hint parameter? Especially if we reuse the strbuf, it should be good enough to allocate a reasonable buffer first and then just assume that we do not have to reallocate it all that often anyway. - Since we only read files from the state directory, why not pass the basename as parameter? That way we can avoid calling `am_path()` explicitly over and over again (and yours truly cannot forget to call `am_path()` in future patches). - If you agree with these suggestions, the signature would become something like static void read_state_file(struct am_state *state, const char *basename, int trim); +/** + * Remove the am_state directory. + */ +static void am_destroy(const struct am_state *state) +{ + struct strbuf sb = STRBUF_INIT; + + strbuf_addstr(sb, state-dir.buf); + remove_dir_recursively(sb, 0); + strbuf_release(sb); +} Given that `remove_dir_recursively()` has to reset the strbuf with the directory's path to the original value before it returns (because it recurses into itself, therefore the value *has* to be reset when returning), we can just call remove_dir_recursively(state-dir, 0); and do not need another temporary strbuf. +/** + * Increments the patch pointer, and cleans am_state for the application of the + * next patch. + */ +static void am_next(struct am_state *state) +{ + state-cur++; + write_file(am_path(state, next), 1, %d, state-cur); +} Locking and re-checking the contents of next before writing the incremented value would probably be a little too paranoid... (Just saying it out loud, the current code is fine by me.) Ciao, Dscho -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH/WIP v3 06/31] am: detect mbox patches
Hi Paul, On 2015-06-18 13:25, Paul Tan wrote: diff --git a/builtin/am.c b/builtin/am.c index e9a3687..7b97ea8 100644 --- a/builtin/am.c +++ b/builtin/am.c @@ -121,6 +121,96 @@ static void am_destroy(const struct am_state *state) strbuf_release(sb); } +/* + * Returns 1 if the file looks like a piece of email a-la RFC2822, 0 otherwise. + * We check this by grabbing all the non-indented lines and seeing if they look + * like they begin with valid header field names. + */ +static int is_email(const char *filename) +{ + struct strbuf sb = STRBUF_INIT; + FILE *fp = xfopen(filename, r); + int ret = 1; + + while (!strbuf_getline(sb, fp, '\n')) { + const char *x; + + strbuf_rtrim(sb); + + if (!sb.len) + break; /* End of header */ + + /* Ignore indented folded lines */ + if (*sb.buf == '\t' || *sb.buf == ' ') + continue; + + /* It's a header if it matches the regexp ^[!-9;-~]+: */ Why not just compile a regex and use it here? We use regexes elsewhere anyway... +/** + * Attempts to detect the patch_format of the patches contained in `paths`, + * returning the PATCH_FORMAT_* enum value. Returns PATCH_FORMAT_UNKNOWN if + * detection fails. + */ +static int detect_patch_format(struct string_list *paths) +{ + enum patch_format ret = PATCH_FORMAT_UNKNOWN; + struct strbuf l1 = STRBUF_INIT; + struct strbuf l2 = STRBUF_INIT; + struct strbuf l3 = STRBUF_INIT; + FILE *fp; + + /* + * We default to mbox format if input is from stdin and for directories + */ + if (!paths-nr || !strcmp(paths-items-string, -) || + is_directory(paths-items-string)) { + ret = PATCH_FORMAT_MBOX; + goto done; + } + + /* + * Otherwise, check the first 3 lines of the first patch, starting + * from the first non-blank line, to try to detect its format. + */ + fp = xfopen(paths-items-string, r); + while (!strbuf_getline(l1, fp, '\n')) { + strbuf_trim(l1); + if (l1.len) + break; + } + strbuf_getline(l2, fp, '\n'); We should test the return value of `strbuf_getline()`; if EOF was reached already, `strbuf_getwholeline()` does not touch the strbuf. I know, the strbuf is still initialized empty here, but it is too easy to forget when changing this code. + strbuf_trim(l2); + strbuf_getline(l3, fp, '\n'); + strbuf_trim(l3); + fclose(fp); + + if (starts_with(l1.buf, From ) || starts_with(l1.buf, From: )) + ret = PATCH_FORMAT_MBOX; Hmm. We can test that earlier and return without reading from the file any further, I think. + else if (l1.len l2.len l3.len is_email(paths-items-string)) + ret = PATCH_FORMAT_MBOX; Maybe we can do better than this by folding the `is_email() function into this here function, reusing the same strbuf to read the lines and keeping track of the email header lines we saw... I would really like to avoid opening the same file twice just to figure out whether it is in email format. The rest looks very nice! Dscho -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v8 4/5] bisect: add the terms old/new
From: Antoine Delaite antoine.dela...@ensimag.grenoble-inp.fr When not looking for a regression during a bisect but for a fix or a change in another given property, it can be confusing to use 'good' and 'bad'. This patch introduce `git bisect new` and `git bisect old` as an alternative to 'bad' and good': the commits which have a certain property must be marked as `new` and the ones which do not as `old`. The output will be the first commit after the change in the property. During a new/old bisect session you cannot use bad/good commands and vice-versa. Some commands are still not available for old/new: * git rev-list --bisect does not treat the revs/bisect/new and revs/bisect/old-SHA1 files. Old discussions: - http://thread.gmane.org/gmane.comp.version-control.git/86063 introduced bisect fix unfixed to find fix. - http://thread.gmane.org/gmane.comp.version-control.git/182398 discussion around bisect yes/no or old/new. - http://thread.gmane.org/gmane.comp.version-control.git/199758 last discussion and reviews New discussions: - http://thread.gmane.org/gmane.comp.version-control.git/271320 ( v2 1/7-4/7 ) - http://comments.gmane.org/gmane.comp.version-control.git/271343 ( v2 5/7-7/7 ) Signed-off-by: Antoine Delaite antoine.dela...@ensimag.grenoble-inp.fr Signed-off-by: Louis Stuber stub...@ensimag.grenoble-inp.fr Signed-off-by: Valentin Duperray valentin.duper...@ensimag.imag.fr Signed-off-by: Franck Jonas franck.jo...@ensimag.imag.fr Signed-off-by: Lucien Kong lucien.k...@ensimag.imag.fr Signed-off-by: Thomas Nguy thomas.n...@ensimag.imag.fr Signed-off-by: Huynh Khoi Nguyen Nguyen huynh-khoi-nguyen.ngu...@ensimag.imag.fr Signed-off-by: Matthieu Moy matthieu@imag.fr --- Documentation/git-bisect.txt | 48 ++-- bisect.c | 11 +++--- git-bisect.sh| 30 ++- t/t6030-bisect-porcelain.sh | 38 +++ 4 files changed, 112 insertions(+), 15 deletions(-) diff --git a/Documentation/git-bisect.txt b/Documentation/git-bisect.txt index 4cb52a7..3c3021a 100644 --- a/Documentation/git-bisect.txt +++ b/Documentation/git-bisect.txt @@ -18,8 +18,8 @@ on the subcommand: git bisect help git bisect start [--no-checkout] [bad [good...]] [--] [paths...] - git bisect bad [rev] - git bisect good [rev...] + git bisect (bad|new) [rev] + git bisect (good|old) [rev...] git bisect skip [(rev|range)...] git bisect reset [commit] git bisect visualize @@ -104,6 +104,35 @@ For example, `git bisect reset HEAD` will leave you on the current bisection commit and avoid switching commits at all, while `git bisect reset bisect/bad` will check out the first bad revision. + +Alternative terms: bisect new and bisect old + + +If you are not at ease with the terms bad and good, perhaps +because you are looking for the commit that introduced a fix, you can +alternatively use new and old instead. +But note that you cannot mix bad and good with new and old. + + +git bisect new [rev] + + +Marks the commit as new, e.g. the bug is no longer there, if you are looking +for a commit that fixed a bug, or the feature that used to work is now broken +at this point, if you are looking for a commit that introduced a bug. +It is the equivalent of git bisect bad [rev]. + + +git bisect old [rev...] + + +Marks the commit as old, as the opposite of 'git bisect new'. +It is the equivalent of git bisect good [rev...]. + +You must run `git bisect start` without commits as argument and run +`git bisect new rev`/`git bisect old rev...` after to add the +commits. + Bisect visualize @@ -379,6 +408,21 @@ In this case, when 'git bisect run' finishes, bisect/bad will refer to a commit has at least one parent whose reachable graph is fully traversable in the sense required by 'git pack objects'. +* Look for a fix instead of a regression in the code ++ + +$ git bisect start +$ git bisect new HEAD# current commit is marked as new +$ git bisect old HEAD~10 # the tenth commit from now is marked as old + ++ +Let's consider the last commit has a given property, and that we are looking +for the commit which introduced this property. For each commit the bisection +guide us to, we will test if the property is present. If it is we will mark +the commit as new with 'git bisect new', otherwise we will mark it as old. +At the end of the bisect session, the result will be the first new commit (e.g +the first one with the property). + SEE ALSO diff --git a/bisect.c b/bisect.c index 08be634..ab09650 100644 ---
[PATCH v8 3/5] bisect: simplify the addition of new bisect terms
From: Antoine Delaite antoine.dela...@ensimag.grenoble-inp.fr We create a file BISECT_TERMS in the repository .git to be read during a bisection. The fonctions to be changed if we add new terms are quite few. In git-bisect.sh: check_and_set_terms bisect_voc Co-authored-by: Louis Stuber stub...@ensimag.grenoble-inp.fr Tweaked-by: Matthieu Moy matthieu@imag.fr Signed-off-by: Antoine Delaite antoine.dela...@ensimag.grenoble-inp.fr Signed-off-by: Louis Stuber stub...@ensimag.grenoble-inp.fr Signed-off-by: Valentin Duperray valentin.duper...@ensimag.imag.fr Signed-off-by: Franck Jonas franck.jo...@ensimag.imag.fr Signed-off-by: Lucien Kong lucien.k...@ensimag.imag.fr Signed-off-by: Thomas Nguy thomas.n...@ensimag.imag.fr Signed-off-by: Huynh Khoi Nguyen Nguyen huynh-khoi-nguyen.ngu...@ensimag.imag.fr Signed-off-by: Matthieu Moy matthieu@imag.fr --- bisect.c | 38 +--- git-bisect.sh | 70 +-- revision.c| 20 +++-- 3 files changed, 116 insertions(+), 12 deletions(-) diff --git a/bisect.c b/bisect.c index 2d3dbdc..08be634 100644 --- a/bisect.c +++ b/bisect.c @@ -747,7 +747,10 @@ static void handle_bad_merge_base(void) between %s and [%s].\n, bad_hex, bad_hex, good_hex); } else { - die(BUG: terms %s/%s not managed, name_bad, name_good); + fprintf(stderr, The merge base %s is %s.\n + This means the first commit marked %s is + between %s and [%s].\n, + bad_hex, name_bad, name_bad, bad_hex, good_hex); } exit(3); } @@ -902,6 +905,36 @@ static void show_diff_tree(const char *prefix, struct commit *commit) } /* + * The terms used for this bisect session are stored in BISECT_TERMS. + * We read them and store them to adapt the messages accordingly. + * Default is bad/good. + */ +void read_bisect_terms(const char **read_bad, const char **read_good) +{ + struct strbuf str = STRBUF_INIT; + const char *filename = git_path(BISECT_TERMS); + FILE *fp = fopen(filename, r); + + if (!fp) { + if (errno == ENOENT) { + *read_bad = bad; + *read_good = good; + return; + } else { + die(could not read file '%s': %s, filename, + strerror(errno)); + } + } else { + strbuf_getline(str, fp, '\n'); + *read_bad = strbuf_detach(str, NULL); + strbuf_getline(str, fp, '\n'); + *read_good = strbuf_detach(str, NULL); + } + strbuf_release(str); + fclose(fp); +} + +/* * We use the convention that exiting with an exit code 10 means that * the bisection process finished successfully. * In this case the calling shell script should exit 0. @@ -917,8 +950,7 @@ int bisect_next_all(const char *prefix, int no_checkout) const unsigned char *bisect_rev; char bisect_rev_hex[GIT_SHA1_HEXSZ + 1]; - name_bad = bad; - name_good = good; + read_bisect_terms(name_bad, name_good); if (read_bisect_refs()) die(reading bisect refs failed); diff --git a/git-bisect.sh b/git-bisect.sh index ce6412f..7bb18db 100644 --- a/git-bisect.sh +++ b/git-bisect.sh @@ -77,6 +77,9 @@ bisect_start() { orig_args=$(git rev-parse --sq-quote $@) bad_seen=0 eval='' + # revision_seen is true if a git bisect start + # has revision as arguments + revision_seen=0 if test z$(git rev-parse --is-bare-repository) != zfalse then mode=--no-checkout @@ -101,6 +104,9 @@ bisect_start() { die $(eval_gettext '\$arg' does not appear to be a valid revision) break } + + revision_seen=1 + case $bad_seen in 0) state=$NAME_BAD ; bad_seen=1 ;; *) state=$NAME_GOOD ;; @@ -172,6 +178,11 @@ bisect_start() { } git rev-parse --sq-quote $@ $GIT_DIR/BISECT_NAMES eval $eval true + if test $revision_seen -eq 1 test ! -s $GIT_DIR/BISECT_TERMS + then + echo $NAME_BAD $GIT_DIR/BISECT_TERMS + echo $NAME_GOOD $GIT_DIR/BISECT_TERMS + fi echo git bisect start$orig_args $GIT_DIR/BISECT_LOG || exit # # Check if we can proceed to the next bisect state. @@ -232,6 +243,7 @@ bisect_skip() { bisect_state() { bisect_autostart state=$1 + check_and_set_terms $state case $#,$state in 0,*) die $(gettext Please call 'bisect_state'
[PATCH v8 0/5] Bisect terms
This is a minor iteration over v7 to take into account Junio and Eric's comments, AND fix an important typo that I introduced in the strbuf code conversion (I used name_good instead of name_bad). This fixes the git bisect visualize bug I found earlier. I played a bit with the result and didn't find any bug. Except for the last patch, it seems at least close to mergeable. diff --git a/Documentation/git-bisect.txt b/Documentation/git-bisect.txt index ef0c03c..a37336e 100644 --- a/Documentation/git-bisect.txt +++ b/Documentation/git-bisect.txt @@ -134,7 +134,7 @@ You must run `git bisect start` without commits as argument and run commits. Alternative terms: use your own terms - +~ If the builtins terms bad/good and new/old do not satisfy you, you can set your own terms. diff --git a/revision.c b/revision.c index f22923f..24ce842 100644 --- a/revision.c +++ b/revision.c @@ -2083,27 +2083,21 @@ extern void read_bisect_terms(const char **bad, const char **good); static int for_each_bad_bisect_ref(const char *submodule, each_ref_fn fn, void *cb_data) { - struct strbuf bisect_refs_buf = STRBUF_INIT; - const char *bisect_refs_str; + struct strbuf bisect_refs = STRBUF_INIT; int status; - strbuf_addstr(bisect_refs_buf, refs/bisect/); - strbuf_addstr(bisect_refs_buf, name_bad); - bisect_refs_str = strbuf_detach(bisect_refs_buf, NULL); - status = for_each_ref_in_submodule(submodule, bisect_refs_str, fn, cb_data); - free((char *)bisect_refs_str); + strbuf_addf(bisect_refs, refs/bisect/%s, name_bad); + status = for_each_ref_in_submodule(submodule, bisect_refs.buf, fn, cb_data); + strbuf_release(bisect_refs); return status; } static int for_each_good_bisect_ref(const char *submodule, each_ref_fn fn, void *cb_data) { - struct strbuf bisect_refs_buf = STRBUF_INIT; - const char *bisect_refs_str; + struct strbuf bisect_refs = STRBUF_INIT; int status; - strbuf_addstr(bisect_refs_buf, refs/bisect/); - strbuf_addstr(bisect_refs_buf, name_bad); - bisect_refs_str = strbuf_detach(bisect_refs_buf, NULL); - status = for_each_ref_in_submodule(submodule, bisect_refs_str, fn, cb_data); - free((char *)bisect_refs_str); + strbuf_addf(bisect_refs, refs/bisect/%s, name_good); + status = for_each_ref_in_submodule(submodule, bisect_refs.buf, fn, cb_data); + strbuf_release(bisect_refs); return status; } Antoine Delaite (5): bisect: correction of typo bisect: replace hardcoded bad|good by variables bisect: simplify the addition of new bisect terms bisect: add the terms old/new bisect: allow any terms set by user Documentation/git-bisect.txt | 67 +- bisect.c | 94 +++- git-bisect.sh| 207 +++ revision.c | 20 - t/t6030-bisect-porcelain.sh | 83 - 5 files changed, 407 insertions(+), 64 deletions(-) mode change 100755 = 100644 git-bisect.sh -- 2.4.4.414.g59d82e6 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v8 2/5] bisect: replace hardcoded bad|good by variables
From: Antoine Delaite antoine.dela...@ensimag.grenoble-inp.fr To add new tags like old/new and have keywords less confusing, the first step is to avoid hardcoding the keywords. The default mode is still bad/good. Signed-off-by: Antoine Delaite antoine.dela...@ensimag.grenoble-inp.fr Signed-off-by: Louis Stuber stub...@ensimag.grenoble-inp.fr Signed-off-by: Valentin Duperray valentin.duper...@ensimag.imag.fr Signed-off-by: Franck Jonas franck.jo...@ensimag.imag.fr Signed-off-by: Lucien Kong lucien.k...@ensimag.imag.fr Signed-off-by: Thomas Nguy thomas.n...@ensimag.imag.fr Signed-off-by: Huynh Khoi Nguyen Nguyen huynh-khoi-nguyen.ngu...@ensimag.imag.fr Signed-off-by: Matthieu Moy matthieu@imag.fr --- bisect.c | 51 ++- git-bisect.sh | 57 +++-- 2 files changed, 65 insertions(+), 43 deletions(-) mode change 100755 = 100644 git-bisect.sh diff --git a/bisect.c b/bisect.c index 5b8357d..2d3dbdc 100644 --- a/bisect.c +++ b/bisect.c @@ -21,6 +21,9 @@ static const char *argv_checkout[] = {checkout, -q, NULL, --, NULL}; static const char *argv_show_branch[] = {show-branch, NULL, NULL}; static const char *argv_update_ref[] = {update-ref, --no-deref, BISECT_HEAD, NULL, NULL}; +static const char *name_bad; +static const char *name_good; + /* Remember to update object flag allocation in object.h */ #define COUNTED(1u16) @@ -403,15 +406,21 @@ struct commit_list *find_bisection(struct commit_list *list, static int register_ref(const char *refname, const struct object_id *oid, int flags, void *cb_data) { - if (!strcmp(refname, bad)) { + struct strbuf good_prefix = STRBUF_INIT; + strbuf_addstr(good_prefix, name_good); + strbuf_addstr(good_prefix, -); + + if (!strcmp(refname, name_bad)) { current_bad_oid = xmalloc(sizeof(*current_bad_oid)); oidcpy(current_bad_oid, oid); - } else if (starts_with(refname, good-)) { + } else if (starts_with(refname, good_prefix.buf)) { sha1_array_append(good_revs, oid-hash); } else if (starts_with(refname, skip-)) { sha1_array_append(skipped_revs, oid-hash); } + strbuf_release(good_prefix); + return 0; } @@ -634,7 +643,7 @@ static void exit_if_skipped_commits(struct commit_list *tried, return; printf(There are only 'skip'ped commits left to test.\n - The first bad commit could be any of:\n); + The first %s commit could be any of:\n, name_bad); print_commit_list(tried, %s\n, %s\n); if (bad) printf(%s\n, oid_to_hex(bad)); @@ -732,18 +741,21 @@ static void handle_bad_merge_base(void) if (is_expected_rev(current_bad_oid)) { char *bad_hex = oid_to_hex(current_bad_oid); char *good_hex = join_sha1_array_hex(good_revs, ' '); - - fprintf(stderr, The merge base %s is bad.\n - This means the bug has been fixed - between %s and [%s].\n, - bad_hex, bad_hex, good_hex); - + if (!strcmp(name_bad, bad)) { + fprintf(stderr, The merge base %s is bad.\n + This means the bug has been fixed + between %s and [%s].\n, + bad_hex, bad_hex, good_hex); + } else { + die(BUG: terms %s/%s not managed, name_bad, name_good); + } exit(3); } - fprintf(stderr, Some good revs are not ancestor of the bad rev.\n + fprintf(stderr, Some %s revs are not ancestor of the %s rev.\n git bisect cannot work properly in this case.\n - Maybe you mistook good and bad revs?\n); + Maybe you mistook %s and %s revs?\n, + name_good, name_bad, name_good, name_bad); exit(1); } @@ -755,10 +767,10 @@ static void handle_skipped_merge_base(const unsigned char *mb) warning(the merge base between %s and [%s] must be skipped.\n - So we cannot be sure the first bad commit is + So we cannot be sure the first %s commit is between %s and %s.\n We continue anyway., - bad_hex, good_hex, mb_hex, bad_hex); + bad_hex, good_hex, name_bad, mb_hex, bad_hex); free(good_hex); } @@ -839,7 +851,7 @@ static void check_good_are_ancestors_of_bad(const char *prefix, int no_checkout) int fd; if (!current_bad_oid) - die(a bad revision is needed); + die(a %s revision is needed, name_bad); /* Check if file BISECT_ANCESTORS_OK exists. */ if (!stat(filename, st) S_ISREG(st.st_mode)) @@ -905,6 +917,8 @@ int
[PATCH v8 1/5] bisect: correction of typo
From: Antoine Delaite antoine.dela...@ensimag.grenoble-inp.fr Signed-off-by: Antoine Delaite antoine.dela...@ensimag.grenoble-inp.fr Signed-off-by: Matthieu Moy matthieu@imag.fr --- bisect.c| 2 +- t/t6030-bisect-porcelain.sh | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/bisect.c b/bisect.c index 03d5cd9..5b8357d 100644 --- a/bisect.c +++ b/bisect.c @@ -743,7 +743,7 @@ static void handle_bad_merge_base(void) fprintf(stderr, Some good revs are not ancestor of the bad rev.\n git bisect cannot work properly in this case.\n - Maybe you mistake good and bad revs?\n); + Maybe you mistook good and bad revs?\n); exit(1); } diff --git a/t/t6030-bisect-porcelain.sh b/t/t6030-bisect-porcelain.sh index 06b4868..9e2c203 100755 --- a/t/t6030-bisect-porcelain.sh +++ b/t/t6030-bisect-porcelain.sh @@ -362,7 +362,7 @@ test_expect_success 'bisect starting with a detached HEAD' ' test_expect_success 'bisect errors out if bad and good are mistaken' ' git bisect reset test_must_fail git bisect start $HASH2 $HASH4 2 rev_list_error - grep mistake good and bad rev_list_error + grep mistook good and bad rev_list_error git bisect reset ' -- 2.4.4.414.g59d82e6 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v8 5/5] bisect: allow any terms set by user
From: Antoine Delaite antoine.dela...@ensimag.grenoble-inp.fr Introduction of the git bisect terms function. The user can set its own terms. It will work exactly like before. The terms must be set before the start. Signed-off-by: Antoine Delaite antoine.dela...@ensimag.grenoble-inp.fr Signed-off-by: Louis Stuber stub...@ensimag.grenoble-inp.fr Signed-off-by: Matthieu Moy matthieu@imag.fr --- Documentation/git-bisect.txt | 19 + git-bisect.sh| 68 t/t6030-bisect-porcelain.sh | 43 3 files changed, 125 insertions(+), 5 deletions(-) diff --git a/Documentation/git-bisect.txt b/Documentation/git-bisect.txt index 3c3021a..a37336e 100644 --- a/Documentation/git-bisect.txt +++ b/Documentation/git-bisect.txt @@ -133,6 +133,25 @@ You must run `git bisect start` without commits as argument and run `git bisect new rev`/`git bisect old rev...` after to add the commits. +Alternative terms: use your own terms +~ + +If the builtins terms bad/good and new/old do not satisfy you, you can +set your own terms. + + +git bisect terms term1 term2 + + +This command has to be used before a bisection has started. +The term1 must be associated with the latest revisions and term2 with the +ancestors of term1. + +Only the first bisection following the 'git bisect terms' will use the terms. +If you mistyped one of the terms you can do again 'git bisect terms term1 +term2'. + + Bisect visualize diff --git a/git-bisect.sh b/git-bisect.sh index 73763a2..8ef2b94 100644 --- a/git-bisect.sh +++ b/git-bisect.sh @@ -1,6 +1,6 @@ #!/bin/sh -USAGE='[help|start|bad|good|new|old|skip|next|reset|visualize|replay|log|run]' +USAGE='[help|start|bad|good|new|old|terms|skip|next|reset|visualize|replay|log|run]' LONG_USAGE='git bisect help print this long help message. git bisect start [--no-checkout] [bad [good...]] [--] [pathspec...] @@ -11,6 +11,8 @@ git bisect (bad|new) [rev] git bisect (good|old) [rev...] mark rev... known-good revisions/ revisions before change in a given property. +git bisect terms term1 term2 + set up term1 and term2 as bisection terms. git bisect skip [(rev|range)...] mark rev... untestable revisions. git bisect next @@ -82,6 +84,14 @@ bisect_start() { # revision_seen is true if a git bisect start # has revision as arguments revision_seen=0 + # terms_defined is used to detect if the user + # defined his own terms with git bisect terms + terms_defined=0 + if test -s $GIT_DIR/TERMS_DEFINED + then + terms_defined=1 + get_terms + fi if test z$(git rev-parse --is-bare-repository) != zfalse then mode=--no-checkout @@ -180,10 +190,14 @@ bisect_start() { } git rev-parse --sq-quote $@ $GIT_DIR/BISECT_NAMES eval $eval true - if test $revision_seen -eq 1 test ! -s $GIT_DIR/BISECT_TERMS + if test $revision_seen -eq 1 test ! -s $GIT_DIR/BISECT_TERMS || test $terms_defined -eq 1 then echo $NAME_BAD $GIT_DIR/BISECT_TERMS - echo $NAME_GOOD $GIT_DIR/BISECT_TERMS + echo $NAME_GOOD $GIT_DIR/BISECT_TERMS + if test $terms_defined -eq 1 + then + echo git bisect terms $NAME_BAD $NAME_GOOD $GIT_DIR/BISECT_LOG || exit + fi fi echo git bisect start$orig_args $GIT_DIR/BISECT_LOG || exit # @@ -419,6 +433,7 @@ bisect_clean_state() { rm -f $GIT_DIR/BISECT_NAMES rm -f $GIT_DIR/BISECT_RUN rm -f $GIT_DIR/BISECT_TERMS + rm -f $GIT_DIR/TERMS_DEFINED # Cleanup head-name if it got left by an old version of git-bisect rm -f $GIT_DIR/head-name git update-ref -d --no-deref BISECT_HEAD @@ -447,6 +462,8 @@ bisect_replay () { eval $cmd ;; $NAME_GOOD|$NAME_BAD|skip) bisect_write $command $rev ;; + terms) + bisect_terms $rev ;; *) die $(gettext ?? what are you talking about?) ;; esac @@ -531,7 +548,8 @@ get_terms () { check_and_set_terms () { cmd=$1 case $cmd in - bad|good|new|old) + skip|start|terms) ;; + *) if test -s $GIT_DIR/BISECT_TERMS test $cmd != $NAME_BAD test $cmd != $NAME_GOOD then die $(eval_gettext Invalid command: you're currently in a \$NAME_BAD/\$NAME_GOOD bisect.) @@ -564,6 +582,44 @@ bisect_voc () { esac } +bisect_terms () { + case $# in + 0) + if test -s $GIT_DIR/BISECT_TERMS + then
Re: Untracked files when git status executed on a new folder
Hi all, sorry for not having sent these informations in my first e-mail. I'm working on a Debian Jessie laptop, with git version 2.1.4. I watched the same behavior in a workmate's laptop which uses last version of Ubuntu, but now I cannot contact him to get git version. Afger apt-get update and apg-get install --only-upgrade git, the response is that I have the latest git version, what sounds strange to me if you say you use version 2.4.4. Thanks!! Víctor On Tue, 2015-06-23 at 18:54 +0200, Johannes Löthberg wrote: On 23/06, Víctor Martín Hernández wrote: Hi all. Today I've had an unexpected behaviour that I'm not sure if is a bug or I'm not doing git best practices... (surely the latest...) The sequence of actions is : 1. create a new subfolder of my local repository branch 2. cd to this new folder, and create a new file 3. execute git status from the new folder Doing that, the new folder doesn't appear as untracked. 4. cd .. 5. git status In this case, the new folder appears. If I create a new folder on the same level that the new one created in step 1, cd into it, and execute git status, the folder created in step 1 appears as untracked. Can't reproduce on Git 2.4.4/Linux, which Git version and platform are you using? -- --- Víctor Martín Hernández RD Software Engineer Instituto de Ciencias del Espacio (ICE/CSIC), and Institut d'Estudis Espacials de Catalunya (IEEC) Campus UAB, Carrer de Can Magrans, s/n 08193 Bellaterra (Cerdanyola del Vallès) - Barcelona Tel. : +34 93 586 8782 Web: http://gwart.ice.cat/ -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH/WIP v3 01/31] wrapper: implement xopen()
Hi Paul, On 2015-06-18 13:25, Paul Tan wrote: diff --git a/git-compat-util.h b/git-compat-util.h index 0cc7ae8..bc77d77 100644 --- a/git-compat-util.h +++ b/git-compat-util.h @@ -719,6 +719,7 @@ extern void *xrealloc(void *ptr, size_t size); extern void *xcalloc(size_t nmemb, size_t size); extern void *xmmap(void *start, size_t length, int prot, int flags, int fd, off_t offset); extern void *xmmap_gently(void *start, size_t length, int prot, int flags, int fd, off_t offset); +extern int xopen(const char *path, int flags, ...); I wonder whether it is worth it to make this a varargs function. It is not too much to ask callers to specify a specific mode everytime they call `xopen()`, no? diff --git a/wrapper.c b/wrapper.c index c1a663f..82658b3 100644 --- a/wrapper.c +++ b/wrapper.c @@ -189,6 +189,31 @@ void *xcalloc(size_t nmemb, size_t size) # endif #endif +/** + * xopen() is the same as open(), but it die()s if the open() fails. + */ +int xopen(const char *path, int oflag, ...) +{ + mode_t mode = 0; + va_list ap; + + va_start(ap, oflag); + if (oflag O_CREAT) + mode = va_arg(ap, mode_t); + va_end(ap); + + assert(path); + + for (;;) { + int fd = open(path, oflag, mode); + if (fd = 0) + return fd; + if (errno == EINTR) + continue; + die_errno(_(could not open '%s'), path); It is often helpful to know whether a path was opened for reading or writing, so maybe we should have something like if (oflag O_WRITE) die_errno(_(could not open '%s' for writing), path); else if (oflag O_READ) die_errno(_(could not open '%s' for reading), path); else die_errno(_(could not open '%s'), path); ? I know it is a bit of duplication, but I fear we cannot get around that without breaking i18n support. Ciao, Dscho -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH/WIP v3 07/31] am: extract patch, message and authorship with git-mailinfo
Hi Paul, On 2015-06-18 13:25, Paul Tan wrote: diff --git a/builtin/am.c b/builtin/am.c index 7b97ea8..d6434e4 100644 --- a/builtin/am.c +++ b/builtin/am.c @@ -94,6 +126,105 @@ static int read_state_file(struct strbuf *sb, const char *file, size_t hint, int } /** + * Reads a KEY=VALUE shell variable assignment from fp, and returns the VALUE + * in `value`. VALUE must be a quoted string, and the KEY must match `key`. + * Returns 0 on success, -1 on failure. + * + * This is used by read_author_script() to read the GIT_AUTHOR_* variables from + * the author-script. + */ +static int read_shell_var(struct strbuf *value, FILE *fp, const char *key) +{ + struct strbuf sb = STRBUF_INIT; + char *str; + + if (strbuf_getline(sb, fp, '\n')) + return -1; + + if (!skip_prefix(sb.buf, key, (const char **)str)) + return -1; + + if (!skip_prefix(str, =, (const char **)str)) + return -1; + + str = sq_dequote(str); + if (!str) + return -1; + + strbuf_reset(value); + strbuf_addstr(value, str); + + strbuf_release(sb); + + return 0; +} How about using `strbuf_remove()` and keeping `str` as `const char *`? I also think we can fold it into the `read_author_script()` function and make it more resilient with regards to the order of the variables. Something like this: static int read_author_script(struct am_state *state) { struct strbuf sb = STRBUF_INIT; const char *filename = am_path(state, author-script); FILE *fp = fopen(filename, r); if (!fp) { if (errno == ENOENT) return 0; die_errno(_(could not open '%s' for reading), filename); } while (!strbuf_getline(sb, fp, '\n')) { char *equal = strchr(sb.buf, '='), **var; if (!equal) { error: fclose(fp); return -1; } *equal = '\0'; if (!strcmp(sb.buf, GIT_AUTHOR_NAME)) var = state-author_name; else if (!strcmp(sb.buf, GIT_AUTHOR_EMAIL)) var = state-author_email; else if (!strcmp(sb.buf, GIT_AUTHOR_DATE)) var = state-author_date; else goto error; *var = xstrdup(sq_dequote(equal + 1)); } fclose(fp); return -1; } If you follow my earlier suggestion to keep a strbuf inside the am_state, you could reuse that here, too. +/** + * Saves state-author_name, state-author_email and state-author_date in + * `filename` as an author script, which is the format used by git-am.sh. + */ +static void write_author_script(const struct am_state *state) +{ + static const char fmt[] = GIT_AUTHOR_NAME=%s\n + GIT_AUTHOR_EMAIL=%s\n + GIT_AUTHOR_DATE=%s\n; + struct strbuf author_name = STRBUF_INIT; + struct strbuf author_email = STRBUF_INIT; + struct strbuf author_date = STRBUF_INIT; + + sq_quote_buf(author_name, state-author_name.buf); + sq_quote_buf(author_email, state-author_email.buf); + sq_quote_buf(author_date, state-author_date.buf); The `sq_quote_buf()` function does not call `strbuf_reset()`. Therefore you could just use a single strbuf to construct the entire three lines and then write that out. Again, if you follow my suggestion to keep a scratch pad strbuf in am_state, you could reuse that. That scratch pad could come in handy in a couple of other places in the rest of this patch. Ciao, Dscho -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Repository Code Scope (Plan Text)
Hello, What type of code scope should a repository contain? Can it be one large program with many elements or should it just be part of a program or can it be a project with multiple programs? What are the recommendations? Thanks, Brian -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Repository Code Security (Plan Text)
Hello, If someone downloads code to their notebook PC and leaves the company, what protection do we have against them not being able to access the local code copy anymore? Thanks, Brian -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Repository Code Security (Plan Text)
On Wed, 24 Jun 2015 18:18:00 + BGaudreault Brian bgaudrea...@edrnet.com wrote: If someone downloads code to their notebook PC and leaves the company, what protection do we have against them not being able to access the local code copy anymore? What do you mean by local code? That one which is on the notebook? Then you can do literally nothing except for not allowing cloning your Git repositories onto random computers in the first place. If you instead mean the copy of code available in the repositories hosted in your enterprise then all you need to do is to somehow terminate the access of that employee who's left to those repositories. (This assumes they're accessible from the outside; if they aren't, the problem simply do not exist.) -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH v8 0/5] Bisect terms
Matthieu Moy matthieu@imag.fr writes: This is a minor iteration over v7 to take into account Junio and Eric's comments, AND fix an important typo that I introduced in the strbuf code conversion (I used name_good instead of name_bad). This fixes the git bisect visualize bug I found earlier. I played a bit with the result and didn't find any bug. It seems that [3/5] essentially is the same from the previous round, though. I'll have more comments on it In-Reply-To that message. Thanks. -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH v8 3/5] bisect: simplify the addition of new bisect terms
Matthieu Moy matthieu@imag.fr writes: diff --git a/bisect.c b/bisect.c index 2d3dbdc..08be634 100644 --- a/bisect.c +++ b/bisect.c @@ -747,7 +747,10 @@ static void handle_bad_merge_base(void) between %s and [%s].\n, bad_hex, bad_hex, good_hex); } else { - die(BUG: terms %s/%s not managed, name_bad, name_good); + fprintf(stderr, The merge base %s is %s.\n + This means the first commit marked %s is + between %s and [%s].\n, + bad_hex, name_bad, name_bad, bad_hex, good_hex); } exit(3); } Before the pre-context of this hunk is if (!strcmp(name_bad, bad)) { fprintf(stderr, The merge base %s is bad.\n This means the bug has been fixed So, after 5/5, the user could do git bisect terms bad worse and get utterly confused. I think - if (!strcmp(name_bad, bad)) { + if (!strcmp(name_bad, bad) !strcmp(name_good, good) { needs to be a part of this step. -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: RFC/Pull Request: Refs db backend
On Tue, 2015-06-23 at 23:27 +0200, Michael Haggerty wrote: On 06/23/2015 09:53 PM, David Turner wrote: On Tue, 2015-06-23 at 17:51 +0200, Michael Haggerty wrote: [...] * I don't like the fact that you have replaced `struct ref_transaction *` with `void *` in the public interface. On a practical level, I like the bit of type-safety that comes with the more specific declaration. But on a more abstract level, I think that the concept of a transaction could be useful across backends, for example in utility functions that verify that a proposed set of updates are internally consistent. I would rather see either * backends extend a basic `struct ref_transaction` to suit their needs, and upcast/downcast pointers at the module boundary, or * `struct ref_transaction` itself gets a `void *` member that backends can use for whatever purposes they want. There are no common fields between refs-be-file transactions and refs-be-lmdb transactions. I don't see much gain from adding an empty ref_transaction that backends could extend, since we would have to explicitly upcast/downcast all over the place. If you ask me, it would be better to do a bunch of up/downcasts within the single module (via two helper functions that could even do consistency checks) than have no help from the compiler in preventing people from passing unrelated pointer types into the `void *transaction` argument. Plus the `struct ref_transaction *` variables scattered throughout the code are a lot more self-explanatory than `void *`. I'll take a look at what that would look like. * Regarding MERGE_HEAD: you take the point of view that it must continue to be stored as a file. And yet it must also behave somewhat like a reference; for example, `git rev-parse MERGE_HEAD` works today. MERGE_HEAD is also used for reachability, right? Another point of view is that MERGE_HEAD is a plain old boring reference, but there is some other metadata related to it that the refs backend has to store. The file-based backend would have special-case code to read the additional data from the tail of the loose refs file (and be sure to write the metadata when writing the reference), but other backends could store the reference with the rest but do their own thing with the metadata. So I guess I'm wondering whether the refs API needs a MERGE_HEAD-specific way to read and write MERGE_HEAD along with its metadata. You are probably right that this is a good idea. * Don't the same considerations that apply to MERGE_HEAD also apply to FETCH_HEAD? All of the tests pass without any special handling of FETCH_HEAD. That's odd. From git-fetch.txt: The names of refs that are fetched, together with the object names they point at, are written to `.git/FETCH_HEAD`. This information may be used by scripts or other git commands, such as linkgit:git-pull[1]. It seems like the test suite is reading FETCH_HEAD via the refs API in a couple of places. I don't understand why these don't fail when LMDB is being used... You are right; I did add some special-case code for FETCH_HEAD. * Rehash of the last two points: I expected one backend function that is used to initialize the refs backend when a new repository is created (e.g., in `git init`). The file-based backend would use this function to create the `refs`, `refs/heads`, and `refs/tags` directories. I expected a second function that is called once every time git runs in an existing repository (this one might, for example, open a database connection). And maybe even a third one that closes down the database connection before git exits. Would you please explain how this actually works? LMDB doesn't really have the concept of a connection. It's basically just a couple of files that communicate using shared memory (and maybe some other locking that I haven't paid attention to). There is the concept of a transaction, which is the unit of concurrency (each thread may only have one open transaction). Transactions are either read-only or read-write, and there can only be one read-write transaction open at a time (across the entire system). Read-only transactions take a snapshot of the DB state at transaction start time. This combination of features means that we need to be a bit clever about read-only transactions; if a read-write transaction occurs in a separate process, we need to restart any read-only transactions to pick up its changes. If you are thinking about an *unrelated* separate process, then Git's philosophy is that if our process is reading *some* valid state of the references, it's all good even if that state is not quite the newest. After all, who's to say whether our process ran before or after the other process? As long as each process sees self-consistent views of the world as it existed at some recent time, we're satisfied. No, I'm thinking
Re: [PATCH v8 5/5] bisect: allow any terms set by user
Matthieu Moy matthieu@imag.fr writes: +Alternative terms: use your own terms +~ + +If the builtins terms bad/good and new/old do not satisfy you, you can +set your own terms. + + +git bisect terms term1 term2 + + +This command has to be used before a bisection has started. +The term1 must be associated with the latest revisions and term2 with the +ancestors of term1. While this is not incorrect per-se, it would be more helpful to tell the readers that they are hunting for a commit that changes the state they would call term2 into term1 somewhere. e.g. -ancestors of term1. +ancestors of term1. For example, if something was buggy in +the old part of the history, you know somewhere the bug was +fixed, and you want to find the exact commit that fixed it, +you may want to say `git bisect terms fixed broken`; this +way, you would mark a commit that still has the bug with +`broken`, and a newer one after the fix with `fixed`. or something? -USAGE='[help|start|bad|good|new|old|skip|next|reset|visualize|replay|log|run]' +USAGE='[help|start|bad|good|new|old|terms|skip|next|reset|visualize|replay|log|run]' LONG_USAGE='git bisect help print this long help message. git bisect start [--no-checkout] [bad [good...]] [--] [pathspec...] @@ -11,6 +11,8 @@ git bisect (bad|new) [rev] git bisect (good|old) [rev...] mark rev... known-good revisions/ revisions before change in a given property. +git bisect terms term1 term2 + set up term1 and term2 as bisection terms. This will not help those who cannot remember which one between these two they want: git bisect terms new old git bisect terms old new I am wondering (together with the documentation patch) if it would be better to be more explicit, instead of term[12], like this: git bisect terms new old or even git bisect terms bad good assuming that the only reason they use 'terms' is because they are sufficiently familiar with 'git bisect' and (intellectually) know that 'bad' is more recent and 'good' is what it used to be, but have trouble remembering which one is which during a hunt for a fix. +bisect_terms () { + case $# in + 0) + if test -s $GIT_DIR/BISECT_TERMS + then + { + read term1 + read term2 + }$GIT_DIR/BISECT_TERMS + gettextln Your current terms are $term1 and $term2. The same comment on this part. Instead of git bisect terms that just says You are using $term1 and $term2, the users would benefit if it said You are using $term1 for newer state and $term2 for older state [*1*]. Thanks. [Footnote] *1* It is funny that I had to rewrite this if it said... a few times to make sure I got newer and older right, even though I had the relevant pieces (and only releavant pieces) of information for the doc and help text in a single patch form while composing this response. I suspect that an end user without such material would be a lot more confused than I was. -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH] apply: fix adding new files on i-t-a entries
Duy Nguyen pclo...@gmail.com writes: Take checkout for example, when you do git checkout -- foo where foo is i-t-a, the file foo on disk will be emptied because the SHA-1 in the i-t-a entry is an empty blob, mostly to help git diff. I think it should behave as if foo is not i-t-a: checkout should error out about not matching pathspec, or at least not destroy foo on disk. To me, when ce is an i-t-a entry, only i-t-a flag and ce_name are valid, the rest of ce should never be accessed. blame.c's situation is close to check_preimage() where it may read zero from ce_mode. It may be ok for check_preimage() to take zero as mode, but I think this is like fixed size buffer vs strbuf again. It works now, but if the code is reorganized or refactored, then it may or may not work. Better be safe than sorry and avoid reading something we should not read in the first place. All of the above say there _are_ some codepaths that want to treat the existence of a path in the index not as exists, does not exist boolean but as exists, i-t-a, does not exist tristate. I do not think we disagree on that. But that is different from saying that it is always OK to treat i-t-a entries the same way as does not exist non-entries. Internal diff-index --cached is used for another reason you did not mention (and scripted Porcelains literally use that externally for the same reason). When we start a mergy operation, we say it is OK if the working tree has local changes relative to the index, but we require the index does not have any modifications since the HEAD was read. Side note: some codepaths insist that diff-index --cached and diff-files are both clean, so d95d728a is harmless; the former may say clean on i-t-a entries more than before, but the latter will still catch the difference between the index and the working tree and stop the caller from going forward. With d95d728a (diff-lib.c: adjust position of i-t-a entries in diff, 2015-03-16)'s world view, an empty output from diff-index --cached no longer means that. Entries added with any git add -N are not reported, so we would go ahead to record the merge result on top of that half-dirty index. Side note: a merge based on unpack-trees has an extra layer of safety that unpack_trees() does not ignore i-t-a entry as not exist (yet) and notices that the path does exist in the index but not in HEAD. But that just shows that some parts of the world do need to consider that having an i-t-a in the index makes it different from HEAD. If the mergy operation goes without any conflict, the next thing we do typically is to write the index out as a tree (to record in a new commit, etc.) and we are OK only in that particular case, because i-t-a entries are ignored. But what would happen when the mergy operation conflicts? I haven't thought about that fully, but I doubt it is a safe thing to do in general. But that is just one example that there are also other codepaths that do not want to be fooled into thinking that i-t-a entries do not exist in the index at all. All we learned from the above discussion is that unconditionally declaring that adding i-t-a entries to the index without doing anything else should keep the index compare the same to HEAD. If d95d728a were only about what wt_status.c sees (and gets reported in git status output), which was what the change wanted to address anyway, we didn't have to have this discussion. Without realizing that two kinds of callers want different view out of diff-index --cached and diff-files, we broke half the world by changing the world order unconditionally for everybody, I am afraid. Perhaps a good and safe way forward to resurrect what d95d728a wanted to do is to first add an option to tell run_diff_index() and run_diff_files() which behaviour the caller wants to see, add that only to the caller in wt-status.c? Then incrementally pass that option from more callsites that we are absolutely certain that want this different worldview with respect to i-t-a? -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: RFC/Pull Request: Refs db backend
On Wed, 2015-06-24 at 05:14 -0400, Jeff King wrote: On Tue, Jun 23, 2015 at 02:18:36PM -0400, David Turner wrote: Can you describe a bit more about the reflog handling? One of the problems we've had with large-ref repos is that the reflog storage is quite inefficient. You can pack all the refs, but you may still be stuck with a bunch of reflog files with one entry, wasting a whole inode. Doing a git repack when you have a million of those has horrible cold-cache performance. Basically anything that isn't one-file-per-reflog would be a welcome change. :) Reflogs are stored in the database as well. There is one header entry per ref to indicate that a reflog is present, and then one database entry per reflog entry; the entries are stored consecutively and immediately following the header so that it's fast to iterate over them. OK, that make sense. I did notice that the storage for the refdb grows rapidly. If I add a millions refs (like refs/tags/$i) with a simple reflog message foo, I ended up with a 500MB database file. That's _probably_ OK, because a million is getting into crazy territory[1]. But it's 500 bytes per ref, each with one reflog entry. Our ideal lower bound is probably something like 100 bytes per reflog entry: - 20 bytes for old sha1 - 20 bytes for new sha1 - ~50 bytes for name, email, timestamp - ~6 bytes for refname (100 is the longest unique part) That assumes we store binary[2] (and not just the raw reflog lines), and reconstruct the reflog lines on the fly. It also assumes we use some kind of trie-like storage (where we can amortize the cost of storing refs/tags/ across all of the entries). Of course that neglects lmdb's overhead, and the storage of the ref tip itself. But it would hopefully give us a ballpark for an optimal solution. We don't have to hit that, of course, but it's food for thought. [1] The homebrew/homebrew repository on GitHub has almost half a million ref updates. Since this is storing not just refs but all ref updates, that's actually the interesting number (and optimizing the per-reflog-entry size is more interesting than the per-ref size). [2] I'm hesitant to suggest binary formats in general, but given that this is a blob embedded inside lmdb, I think it's OK. If we were to pursue the log-structured idea I suggested earlier, I'm torn on whether it should be binary or not. I could try a binary format. I was optimizing for simplicity, debuggability, recoverability, compatibility with the choice of the text format, but I wouldn't have to. I don't know how much this will save. Unfortunately, given the way LMDB works, a trie-like storage to save refs/tags does not seem possible (of course, we could hard-code some hacks like \001=refs/rags, \002=refs/heads, etc but that is a micro-optimization that might not be worth it. Also, the reflog header has some overhead (it's an entire extra record per ref). The header exists to implement reflog creation/existence checking. I didn't really try to understand why we have the distinction between empty and nonexistent reflogs; I just copied it. If we didn't have that distinction, we could eliminate that overhead. Thanks, that's valuable. For the refs backend, opening the LMDB database for writing is sufficient to block other writers. Do you think it would be valuable to provide a git hold-ref-lock command that simply reads refs from stdin and keeps them locked until it reads EOF from stdin? That would allow cross-backend ref locking. I'm not sure what you would use it for. If you want to update the refs, then you can specify a whole transaction with git update-ref --stdin, and that should work whatever backend you choose. Is there some other operation you want where you hold the lock for a longer period of time? I'm sure I had a reason for this at the time I wrote it, but now I can't think of what it was. Nevermind! -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH/WIP v3 01/31] wrapper: implement xopen()
On Wed, Jun 24, 2015 at 9:28 AM, Johannes Schindelin johannes.schinde...@gmx.de wrote: Hi Paul, On 2015-06-18 13:25, Paul Tan wrote: diff --git a/git-compat-util.h b/git-compat-util.h index 0cc7ae8..bc77d77 100644 --- a/git-compat-util.h +++ b/git-compat-util.h @@ -719,6 +719,7 @@ extern void *xrealloc(void *ptr, size_t size); extern void *xcalloc(size_t nmemb, size_t size); extern void *xmmap(void *start, size_t length, int prot, int flags, int fd, off_t offset); extern void *xmmap_gently(void *start, size_t length, int prot, int flags, int fd, off_t offset); +extern int xopen(const char *path, int flags, ...); I wonder whether it is worth it to make this a varargs function. It is not too much to ask callers to specify a specific mode everytime they call `xopen()`, no? diff --git a/wrapper.c b/wrapper.c index c1a663f..82658b3 100644 --- a/wrapper.c +++ b/wrapper.c @@ -189,6 +189,31 @@ void *xcalloc(size_t nmemb, size_t size) # endif #endif +/** + * xopen() is the same as open(), but it die()s if the open() fails. + */ +int xopen(const char *path, int oflag, ...) +{ + mode_t mode = 0; + va_list ap; + + va_start(ap, oflag); + if (oflag O_CREAT) + mode = va_arg(ap, mode_t); + va_end(ap); + + assert(path); + + for (;;) { + int fd = open(path, oflag, mode); + if (fd = 0) + return fd; + if (errno == EINTR) + continue; + die_errno(_(could not open '%s'), path); It is often helpful to know whether a path was opened for reading or writing, so maybe we should have something like if (oflag O_WRITE) die_errno(_(could not open '%s' for writing), path); else if (oflag O_READ) die_errno(_(could not open '%s' for reading), path); else die_errno(_(could not open '%s'), path); ? I know it is a bit of duplication, but I fear we cannot get around that without breaking i18n support. This distinction was part of earlier series, but Torsten Boegershausen suggested to leave it out. [compare http://thread.gmane.org/gmane.comp.version-control.git/270048/focus=270049] Ciao, Dscho -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 2/2] introduce preciousObjects repository extension
Jeff King p...@peff.net writes: + if (delete_redundant repository_format_precious_objects) + die(cannot repack in a precious-objects repo); This message initially threw me off during my cursory reading, but the code tells me that this is only about repack -d. Unfortunately the users do not get the chance to read the code; perhaps s/cannot repack/ -d/; or something? I agree that would be better. I originally just blocked all use of git-repack, but at the last minute softened it to just repack -d. I'm not sure if that would actually help anyone in practice. Sure, doing git repack without any options is not destructive, but I wonder if anybody actually does it. Hmph, if you cannot afford to lose objects that are unreachable from your refs (because you know your repository has borrowers) but are suffering from too many packs, wouldn't repack -a be the most natural thing to do? Maybe I am biased, but git gc is not the first thing that comes to my mind in that situation. So I think we could squash in the patch below (which also marks the strings for translation). But I'd also be OK with the rule covering all of `git repack`. OK, will squash it in. [1] One of my proposed uses for this is to revamp the way we handle shared objects on GitHub servers. Right now objects get pushed to individual forks, and then migrate to a shared repository that is accessed via the alternates mechanism. I would like to move to symlinking the `objects/` directory to write directly into the shared space. But the destruction from accidentally running something like `git gc` in a fork is very high. With this patch, we can bump the forks to the v1 format and mark their objects as precious. --- diff --git a/builtin/prune.c b/builtin/prune.c index fc0c8e8..6a58e75 100644 --- a/builtin/prune.c +++ b/builtin/prune.c @@ -219,7 +219,7 @@ int cmd_prune(int argc, const char **argv, const char *prefix) } if (repository_format_precious_objects) - die(cannot prune in a precious-objects repo); + die(_(cannot prune in a precious-objects repo)); while (argc--) { unsigned char sha1[20]; diff --git a/builtin/repack.c b/builtin/repack.c index 8ae7fe5..3beda2c 100644 --- a/builtin/repack.c +++ b/builtin/repack.c @@ -194,7 +194,7 @@ int cmd_repack(int argc, const char **argv, const char *prefix) git_repack_usage, 0); if (delete_redundant repository_format_precious_objects) - die(cannot repack in a precious-objects repo); + die(_(cannot delete packs in a precious-objects repo)); if (pack_kept_objects 0) pack_kept_objects = write_bitmaps; -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH v8 0/5] Bisect terms
Matthieu Moy matthieu@imag.fr writes: Documentation/git-bisect.txt | 67 +- bisect.c | 94 +++- git-bisect.sh| 207 +++ revision.c | 20 - t/t6030-bisect-porcelain.sh | 83 - 5 files changed, 407 insertions(+), 64 deletions(-) mode change 100755 = 100644 git-bisect.sh How come nobody noticed this last line so far, during the 7 rounds of reviews? I'll locally fix it up so no need to resend. Thanks. -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v5 00/11] add options to for-each-ref
v4 of this patch series can be found here : http://article.gmane.org/gmane.comp.version-control.git/272285 This is a continuation of my GSoC project to unify git tag -l, git branch -l and for-each-ref. Continued from this patch series : http://thread.gmane.org/gmane.comp.version-control.git/271563 Changes in v5: 03/11: grammatical changes. 04/11: grammatical changes. 05/11: remove unnecessary if statement and remove caps used in commit message. 06/11: use xcalloc instead of using a commit_list as we know the size of the array. 07/11: s/object/[object]/ as the object is optional. 08/11: rename parse_opt_commit_object_name() to parse_opt_commits(). 09/11: make branch.c also to use the macros. 11/11: s/object/[object]/ as the object is optional. Thanks to Matthieu, Christian, Junio and Eric for the input on the last iteration. -- Regards, Karthik Nayak -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
RE: Repository Code Security (Plan Text)
Hi David Lang, I'm sorry, but I'm confused by your first two responses. Am I not contacting Git when I e-mail this e-mail address? You sound like you don't know exactly how GitHub works. Should I be contacting someone else for GitHub support? Thanks, Brian -Original Message- From: David Lang [mailto:da...@lang.hm] Sent: Wednesday, June 24, 2015 3:20 PM To: BGaudreault Brian Cc: Konstantin Khomoutov; git@vger.kernel.org Subject: RE: Repository Code Security (Plan Text) On Wed, 24 Jun 2015, BGaudreault Brian wrote: Thanks. Yes, I meant that local code is code pulled down to a person's PC, so we don't want them to leave the company with access to this code. So we can only prevent this scenario by running GitLab in our environment instead of running GitHub in the cloud? Would removing a GitHub account from the GitHub repository prevent them from accessing the code on their PC? How do you prevent private GitHub repositories from being pulled down to unauthorized PCs? policy, you say that it's against policy for someone to put company info on a personal machine. You probably run your own repository that's only available within your network (or over your VPN) rather than using a cloud service like github (you may want to check with github to see if they can lock down a private repo to only be accessed from specific IP addresses) you will also need to make sure that people don't plug personal laptops into your corporate network, and that they don't use personal phones to access company e-mail. The bottom line is that it's no different from preventing them from having access to any other sensitive data in your company. What measures do you have in place to keep them from taking sensitive Word Docs or spreadsheets when they leave? do the same thing to deal with their access to code. David Lang Thanks, Brian -Original Message- On Wed, 24 Jun 2015 18:18:00 + BGaudreault Brian bgaudrea...@edrnet.com wrote: If someone downloads code to their notebook PC and leaves the company, what protection do we have against them not being able to access the local code copy anymore? What do you mean by local code? That one which is on the notebook? Then you can do literally nothing except for not allowing cloning your Git repositories onto random computers in the first place. If you instead mean the copy of code available in the repositories hosted in your enterprise then all you need to do is to somehow terminate the access of that employee who's left to those repositories. (This assumes they're accessible from the outside; if they aren't, the problem simply do not exist.) -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v5 08/11] parse-option: rename parse_opt_with_commit()
Rename parse_opt_with_commit() to parse_opt_commits() to show that it can be used to obtain a list of commits and is not constricted to usage of '--contains' option. Mentored-by: Christian Couder christian.cou...@gmail.com Mentored-by: Matthieu Moy matthieu@grenoble-inp.fr Signed-off-by: Karthik Nayak karthik@gmail.com --- builtin/branch.c | 4 ++-- builtin/tag.c | 4 ++-- parse-options-cb.c | 2 +- parse-options.h| 2 +- 4 files changed, 6 insertions(+), 6 deletions(-) diff --git a/builtin/branch.c b/builtin/branch.c index ddd90e6..a008b0d 100644 --- a/builtin/branch.c +++ b/builtin/branch.c @@ -828,13 +828,13 @@ int cmd_branch(int argc, const char **argv, const char *prefix) OPTION_CALLBACK, 0, contains, with_commit, N_(commit), N_(print only branches that contain the commit), PARSE_OPT_LASTARG_DEFAULT, - parse_opt_with_commit, (intptr_t)HEAD, + parse_opt_commits, (intptr_t)HEAD, }, { OPTION_CALLBACK, 0, with, with_commit, N_(commit), N_(print only branches that contain the commit), PARSE_OPT_HIDDEN | PARSE_OPT_LASTARG_DEFAULT, - parse_opt_with_commit, (intptr_t) HEAD, + parse_opt_commits, (intptr_t) HEAD, }, OPT__ABBREV(abbrev), diff --git a/builtin/tag.c b/builtin/tag.c index 280981f..7af45a0 100644 --- a/builtin/tag.c +++ b/builtin/tag.c @@ -603,13 +603,13 @@ int cmd_tag(int argc, const char **argv, const char *prefix) OPTION_CALLBACK, 0, contains, with_commit, N_(commit), N_(print only tags that contain the commit), PARSE_OPT_LASTARG_DEFAULT, - parse_opt_with_commit, (intptr_t)HEAD, + parse_opt_commits, (intptr_t)HEAD, }, { OPTION_CALLBACK, 0, with, with_commit, N_(commit), N_(print only tags that contain the commit), PARSE_OPT_HIDDEN | PARSE_OPT_LASTARG_DEFAULT, - parse_opt_with_commit, (intptr_t)HEAD, + parse_opt_commits, (intptr_t)HEAD, }, { OPTION_CALLBACK, 0, points-at, points_at, N_(object), diff --git a/parse-options-cb.c b/parse-options-cb.c index de75411..632f10f 100644 --- a/parse-options-cb.c +++ b/parse-options-cb.c @@ -77,7 +77,7 @@ int parse_opt_verbosity_cb(const struct option *opt, const char *arg, return 0; } -int parse_opt_with_commit(const struct option *opt, const char *arg, int unset) +int parse_opt_commits(const struct option *opt, const char *arg, int unset) { unsigned char sha1[20]; struct commit *commit; diff --git a/parse-options.h b/parse-options.h index 36c71fe..2ffd857 100644 --- a/parse-options.h +++ b/parse-options.h @@ -221,7 +221,7 @@ extern int parse_opt_expiry_date_cb(const struct option *, const char *, int); extern int parse_opt_color_flag_cb(const struct option *, const char *, int); extern int parse_opt_verbosity_cb(const struct option *, const char *, int); extern int parse_opt_object_name(const struct option *, const char *, int); -extern int parse_opt_with_commit(const struct option *, const char *, int); +extern int parse_opt_commits(const struct option *, const char *, int); extern int parse_opt_tertiary(const struct option *, const char *, int); extern int parse_opt_string_list(const struct option *, const char *, int); extern int parse_opt_noop_cb(const struct option *, const char *, int); -- 2.4.4 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v5 04/11] for-each-ref: add '--points-at' option
Add the '--points-at' option provided by 'ref-filter'. The option lets the user to pick only refs which point to a particular commit. Add documentation and tests for the same. Based-on-patch-by: Jeff King p...@peff.net Mentored-by: Christian Couder christian.cou...@gmail.com Mentored-by: Matthieu Moy matthieu@grenoble-inp.fr Signed-off-by: Karthik Nayak karthik@gmail.com --- Documentation/git-for-each-ref.txt | 3 +++ builtin/for-each-ref.c | 9 +++-- t/t6301-for-each-ref-filter.sh | 20 3 files changed, 30 insertions(+), 2 deletions(-) diff --git a/Documentation/git-for-each-ref.txt b/Documentation/git-for-each-ref.txt index 7f8d9a5..0ede41d 100644 --- a/Documentation/git-for-each-ref.txt +++ b/Documentation/git-for-each-ref.txt @@ -10,6 +10,7 @@ SYNOPSIS [verse] 'git for-each-ref' [--count=count] [--shell|--perl|--python|--tcl] [(--sort=key)...] [--format=format] [pattern...] + [--points-at object] DESCRIPTION --- @@ -62,6 +63,8 @@ OPTIONS the specified host language. This is meant to produce a scriptlet that can directly be `eval`ed. +--points-at object:: + Only list refs pointing to the given object. FIELD NAMES --- diff --git a/builtin/for-each-ref.c b/builtin/for-each-ref.c index 7919206..46f9b05 100644 --- a/builtin/for-each-ref.c +++ b/builtin/for-each-ref.c @@ -7,6 +7,7 @@ static char const * const for_each_ref_usage[] = { N_(git for-each-ref [options] [pattern]), + N_(git for-each-ref [--points-at object]), NULL }; @@ -34,9 +35,15 @@ int cmd_for_each_ref(int argc, const char **argv, const char *prefix) OPT_STRING( 0 , format, format, N_(format), N_(format to use for the output)), OPT_CALLBACK(0 , sort, sorting_tail, N_(key), N_(field name to sort on), parse_opt_ref_sorting), + OPT_CALLBACK(0, points-at, filter.points_at, +N_(object), N_(print only refs pointing to the given object), +parse_opt_object_name), OPT_END(), }; + memset(array, 0, sizeof(array)); + memset(filter, 0, sizeof(filter)); + parse_options(argc, argv, prefix, opts, for_each_ref_usage, 0); if (maxcount 0) { error(invalid --count argument: `%d', maxcount); @@ -55,8 +62,6 @@ int cmd_for_each_ref(int argc, const char **argv, const char *prefix) /* for warn_ambiguous_refs */ git_config(git_default_config, NULL); - memset(array, 0, sizeof(array)); - memset(filter, 0, sizeof(filter)); filter.name_patterns = argv; filter_refs(array, filter, FILTER_REFS_ALL | FILTER_REFS_INCLUDE_BROKEN); ref_array_sort(sorting, array); diff --git a/t/t6301-for-each-ref-filter.sh b/t/t6301-for-each-ref-filter.sh index b1fa8d4..7269a66 100755 --- a/t/t6301-for-each-ref-filter.sh +++ b/t/t6301-for-each-ref-filter.sh @@ -16,4 +16,24 @@ test_expect_success 'setup some history and refs' ' git update-ref refs/odd/spot master ' +test_expect_success 'filtering with --points-at' ' + cat expect -\EOF + refs/heads/master + refs/odd/spot + refs/tags/three + EOF + git for-each-ref --format=%(refname) --points-at=master actual + test_cmp expect actual +' + +test_expect_success 'check signed tags with --points-at' ' + cat expect -\EOF + refs/heads/side + refs/tags/four + refs/tags/signed-tag four + EOF + git for-each-ref --format=%(refname) %(*subject) --points-at=side actual + test_cmp expect actual +' + test_done -- 2.4.4 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v5 01/11] t6301: for-each-ref tests for ref-filter APIs
Add a test suite for testing the ref-filter APIs used by for-each-ref. We just intialize the test suite for now. More tests will be added in the following patches as more options are added to for-each-ref. Based-on-patch-by: Jeff King p...@peff.net Mentored-by: Christian Couder christian.cou...@gmail.com Mentored-by: Matthieu Moy matthieu@grenoble-inp.fr Signed-off-by: Karthik Nayak karthik@gmail.com --- t/t6301-for-each-ref-filter.sh | 19 +++ 1 file changed, 19 insertions(+) create mode 100755 t/t6301-for-each-ref-filter.sh diff --git a/t/t6301-for-each-ref-filter.sh b/t/t6301-for-each-ref-filter.sh new file mode 100755 index 000..b1fa8d4 --- /dev/null +++ b/t/t6301-for-each-ref-filter.sh @@ -0,0 +1,19 @@ +#!/bin/sh + +test_description='test for-each-refs usage of ref-filter APIs' + +. ./test-lib.sh +. $TEST_DIRECTORY/lib-gpg.sh + +test_expect_success 'setup some history and refs' ' + test_commit one + test_commit two + test_commit three + git checkout -b side + test_commit four + git tag -s -m A signed tag message signed-tag + git checkout master + git update-ref refs/odd/spot master +' + +test_done -- 2.4.4 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v5 09/11] parse-options.h: add macros for '--contains' option
Add a macro for using the '--contains' option in parse-options.h also include an optional '--with' option macro which performs the same action as '--contains'. Make tag.c and branch.c use this new macro. Mentored-by: Christian Couder christian.cou...@gmail.com Mentored-by: Matthieu Moy matthieu@grenoble-inp.fr Signed-off-by: Karthik Nayak karthik@gmail.com --- builtin/branch.c | 14 ++ builtin/tag.c| 14 ++ parse-options.h | 7 +++ 3 files changed, 11 insertions(+), 24 deletions(-) diff --git a/builtin/branch.c b/builtin/branch.c index a008b0d..b04e341 100644 --- a/builtin/branch.c +++ b/builtin/branch.c @@ -824,18 +824,8 @@ int cmd_branch(int argc, const char **argv, const char *prefix) OPT__COLOR(branch_use_color, N_(use colored output)), OPT_SET_INT('r', remotes, kinds, N_(act on remote-tracking branches), REF_REMOTE_BRANCH), - { - OPTION_CALLBACK, 0, contains, with_commit, N_(commit), - N_(print only branches that contain the commit), - PARSE_OPT_LASTARG_DEFAULT, - parse_opt_commits, (intptr_t)HEAD, - }, - { - OPTION_CALLBACK, 0, with, with_commit, N_(commit), - N_(print only branches that contain the commit), - PARSE_OPT_HIDDEN | PARSE_OPT_LASTARG_DEFAULT, - parse_opt_commits, (intptr_t) HEAD, - }, + OPT_CONTAINS(with_commit, N_(print only branches that contain the commit)), + OPT_WITH(with_commit, N_(print only branches that contain the commit)), OPT__ABBREV(abbrev), OPT_GROUP(N_(Specific git-branch actions:)), diff --git a/builtin/tag.c b/builtin/tag.c index 7af45a0..767162e 100644 --- a/builtin/tag.c +++ b/builtin/tag.c @@ -595,23 +595,13 @@ int cmd_tag(int argc, const char **argv, const char *prefix) OPT_GROUP(N_(Tag listing options)), OPT_COLUMN(0, column, colopts, N_(show tag list in columns)), + OPT_CONTAINS(with_commit, N_(print only tags that contain the commit)), + OPT_WITH(with_commit, N_(print only tags that contain the commit)), { OPTION_CALLBACK, 0, sort, tag_sort, N_(type), N_(sort tags), PARSE_OPT_NONEG, parse_opt_sort }, { - OPTION_CALLBACK, 0, contains, with_commit, N_(commit), - N_(print only tags that contain the commit), - PARSE_OPT_LASTARG_DEFAULT, - parse_opt_commits, (intptr_t)HEAD, - }, - { - OPTION_CALLBACK, 0, with, with_commit, N_(commit), - N_(print only tags that contain the commit), - PARSE_OPT_HIDDEN | PARSE_OPT_LASTARG_DEFAULT, - parse_opt_commits, (intptr_t)HEAD, - }, - { OPTION_CALLBACK, 0, points-at, points_at, N_(object), N_(print only tags of the object), 0, parse_opt_object_name }, diff --git a/parse-options.h b/parse-options.h index 2ffd857..627423f 100644 --- a/parse-options.h +++ b/parse-options.h @@ -243,5 +243,12 @@ extern int parse_opt_noop_cb(const struct option *, const char *, int); OPT_COLOR_FLAG(0, color, (var), (h)) #define OPT_COLUMN(s, l, v, h) \ { OPTION_CALLBACK, (s), (l), (v), N_(style), (h), PARSE_OPT_OPTARG, parseopt_column_callback } +#define _OPT_CONTAINS_OR_WITH(name, variable, help, flag)\ + { OPTION_CALLBACK, 0, name, (variable), N_(commit), (help), \ + PARSE_OPT_LASTARG_DEFAULT | flag, \ + parse_opt_commits, (intptr_t) HEAD \ + } +#define OPT_CONTAINS(v, h) _OPT_CONTAINS_OR_WITH(contains, v, h, 0) +#define OPT_WITH(v, h) _OPT_CONTAINS_OR_WITH(with, v, h, PARSE_OPT_HIDDEN) #endif -- 2.4.4 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v5 02/11] tag: libify parse_opt_points_at()
Rename 'parse_opt_points_at()' to 'parse_opt_object_name()' and move it from 'tag.c' to 'parse-options'. This now acts as a common parse_opt function which accepts an objectname and stores it into a sha1_array. Based-on-patch-by: Jeff King p...@peff.net Mentored-by: Christian Couder christian.cou...@gmail.com Mentored-by: Matthieu Moy matthieu@grenoble-inp.fr Signed-off-by: Karthik Nayak karthik@gmail.com --- builtin/tag.c | 21 ++--- parse-options-cb.c | 17 + parse-options.h| 1 + 3 files changed, 20 insertions(+), 19 deletions(-) diff --git a/builtin/tag.c b/builtin/tag.c index 5f6cdc5..e36c43e 100644 --- a/builtin/tag.c +++ b/builtin/tag.c @@ -546,23 +546,6 @@ static int strbuf_check_tag_ref(struct strbuf *sb, const char *name) return check_refname_format(sb-buf, 0); } -static int parse_opt_points_at(const struct option *opt __attribute__((unused)), - const char *arg, int unset) -{ - unsigned char sha1[20]; - - if (unset) { - sha1_array_clear(points_at); - return 0; - } - if (!arg) - return error(_(switch 'points-at' requires an object)); - if (get_sha1(arg, sha1)) - return error(_(malformed object name '%s'), arg); - sha1_array_append(points_at, sha1); - return 0; -} - static int parse_opt_sort(const struct option *opt, const char *arg, int unset) { int *sort = opt-value; @@ -625,8 +608,8 @@ int cmd_tag(int argc, const char **argv, const char *prefix) parse_opt_with_commit, (intptr_t)HEAD, }, { - OPTION_CALLBACK, 0, points-at, NULL, N_(object), - N_(print only tags of the object), 0, parse_opt_points_at + OPTION_CALLBACK, 0, points-at, points_at, N_(object), + N_(print only tags of the object), 0, parse_opt_object_name }, OPT_END() }; diff --git a/parse-options-cb.c b/parse-options-cb.c index be8c413..de75411 100644 --- a/parse-options-cb.c +++ b/parse-options-cb.c @@ -4,6 +4,7 @@ #include commit.h #include color.h #include string-list.h +#include sha1-array.h /*- some often used options -*/ @@ -92,6 +93,22 @@ int parse_opt_with_commit(const struct option *opt, const char *arg, int unset) return 0; } +int parse_opt_object_name(const struct option *opt, const char *arg, int unset) +{ + unsigned char sha1[20]; + + if (unset) { + sha1_array_clear(opt-value); + return 0; + } + if (!arg) + return -1; + if (get_sha1(arg, sha1)) + return error(_(malformed object name '%s'), arg); + sha1_array_append(opt-value, sha1); + return 0; +} + int parse_opt_tertiary(const struct option *opt, const char *arg, int unset) { int *target = opt-value; diff --git a/parse-options.h b/parse-options.h index c71e9da..36c71fe 100644 --- a/parse-options.h +++ b/parse-options.h @@ -220,6 +220,7 @@ extern int parse_opt_approxidate_cb(const struct option *, const char *, int); extern int parse_opt_expiry_date_cb(const struct option *, const char *, int); extern int parse_opt_color_flag_cb(const struct option *, const char *, int); extern int parse_opt_verbosity_cb(const struct option *, const char *, int); +extern int parse_opt_object_name(const struct option *, const char *, int); extern int parse_opt_with_commit(const struct option *, const char *, int); extern int parse_opt_tertiary(const struct option *, const char *, int); extern int parse_opt_string_list(const struct option *, const char *, int); -- 2.4.4 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v5 05/11] ref-filter: add parse_opt_merge_filter()
Add 'parse_opt_merge_filter()' to parse '--merged' and '--no-merged' options and write macros for the same. This is copied from 'builtin/branch.c' which will eventually be removed when we port 'branch.c' to use ref-filter APIs. Based-on-patch-by: Jeff King p...@peff.net Mentored-by: Christian Couder christian.cou...@gmail.com Mentored-by: Matthieu Moy matthieu@grenoble-inp.fr Signed-off-by: Karthik Nayak karthik@gmail.com --- builtin/branch.c | 4 ref-filter.c | 19 +++ ref-filter.h | 11 +++ 3 files changed, 34 insertions(+) diff --git a/builtin/branch.c b/builtin/branch.c index b42e5b6..ddd90e6 100644 --- a/builtin/branch.c +++ b/builtin/branch.c @@ -745,6 +745,10 @@ static void rename_branch(const char *oldname, const char *newname, int force) strbuf_release(newsection); } +/* + * This function is duplicated in ref-filter. It will eventually be removed + * when we port branch.c to use ref-filter APIs. + */ static int opt_parse_merge_filter(const struct option *opt, const char *arg, int unset) { merge_filter = ((opt-long_name[0] == 'n') diff --git a/ref-filter.c b/ref-filter.c index f40f06e..0c2d67c 100644 --- a/ref-filter.c +++ b/ref-filter.c @@ -1125,3 +1125,22 @@ int parse_opt_ref_sorting(const struct option *opt, const char *arg, int unset) s-atom = parse_ref_filter_atom(arg, arg+len); return 0; } + +int parse_opt_merge_filter(const struct option *opt, const char *arg, int unset) +{ + struct ref_filter *rf = opt-value; + unsigned char sha1[20]; + + rf-merge = starts_with(opt-long_name, no) + ? REF_FILTER_MERGED_OMIT + : REF_FILTER_MERGED_INCLUDE; + + if (get_sha1(arg, sha1)) + die(_(malformed object name %s), arg); + + rf-merge_commit = lookup_commit_reference_gently(sha1, 0); + if (!rf-merge_commit) + return opterror(opt, must point to a commit, 0); + + return 0; +} diff --git a/ref-filter.h b/ref-filter.h index c2856b8..ad2902b 100644 --- a/ref-filter.h +++ b/ref-filter.h @@ -50,6 +50,15 @@ struct ref_filter_cbdata { struct ref_filter *filter; }; +/* Macros for checking --merged and --no-merged options */ +#define _OPT_MERGED_NO_MERGED(option, filter, h) \ + { OPTION_CALLBACK, 0, option, (filter), N_(commit), (h), \ + PARSE_OPT_LASTARG_DEFAULT | PARSE_OPT_NONEG, \ + parse_opt_merge_filter, (intptr_t) HEAD \ + } +#define OPT_MERGED(f, h) _OPT_MERGED_NO_MERGED(merged, f, h) +#define OPT_NO_MERGED(f, h) _OPT_MERGED_NO_MERGED(no-merged, f, h) + /* * API for filtering a set of refs. Based on the type of refs the user * has requested, we iterate through those refs and apply filters @@ -71,5 +80,7 @@ void show_ref_array_item(struct ref_array_item *info, const char *format, int qu int parse_opt_ref_sorting(const struct option *opt, const char *arg, int unset); /* Default sort option based on refname */ struct ref_sorting *ref_default_sorting(void); +/* Function to parse --merged and --no-merged options */ +int parse_opt_merge_filter(const struct option *opt, const char *arg, int unset); #endif /* REF_FILTER_H */ -- 2.4.4 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v5 06/11] ref-filter: implement '--merged' and '--no-merged' options
In 'branch -l' we have '--merged' option which only lists refs (branches) merged into the named commit and '--no-merged' option which only lists refs (branches) not merged into the named commit. Implement these two options in ref-filter.{c,h} so that other commands can benefit from this. Based-on-patch-by: Jeff King p...@peff.net Mentored-by: Christian Couder christian.cou...@gmail.com Mentored-by: Matthieu Moy matthieu@grenoble-inp.fr Signed-off-by: Karthik Nayak karthik@gmail.com --- ref-filter.c | 73 ref-filter.h | 8 +++ 2 files changed, 77 insertions(+), 4 deletions(-) diff --git a/ref-filter.c b/ref-filter.c index 0c2d67c..2f20cb3 100644 --- a/ref-filter.c +++ b/ref-filter.c @@ -9,6 +9,7 @@ #include tag.h #include quote.h #include ref-filter.h +#include revision.h typedef enum { FIELD_STR, FIELD_ULONG, FIELD_TIME } cmp_type; @@ -889,6 +890,7 @@ static int ref_filter_handler(const char *refname, const struct object_id *oid, struct ref_filter_cbdata *ref_cbdata = cb_data; struct ref_filter *filter = ref_cbdata-filter; struct ref_array_item *ref; + struct commit *commit = NULL; if (flag REF_BAD_NAME) { warning(ignoring ref with broken name %s, refname); @@ -902,11 +904,23 @@ static int ref_filter_handler(const char *refname, const struct object_id *oid, return 0; /* +* A merge filter is applied on refs pointing to commits. Hence +* obtain the commit using the 'oid' available and discard all +* non-commits early. The actual filtering is done later. +*/ + if (filter-merge_commit) { + commit = lookup_commit_reference_gently(oid-hash, 1); + if (!commit) + return 0; + } + + /* * We do not open the object yet; sort may only need refname * to do its job and the resulting list may yet to be pruned * by maxcount logic. */ ref = new_ref_array_item(refname, oid-hash, flag); + ref-commit = commit; REALLOC_ARRAY(ref_cbdata-array-items, ref_cbdata-array-nr + 1); ref_cbdata-array-items[ref_cbdata-array-nr++] = ref; @@ -932,6 +946,50 @@ void ref_array_clear(struct ref_array *array) array-nr = array-alloc = 0; } +static void do_merge_filter(struct ref_filter_cbdata *ref_cbdata) +{ + struct rev_info revs; + int i, old_nr; + struct ref_filter *filter = ref_cbdata-filter; + struct ref_array *array = ref_cbdata-array; + struct commit **to_clear = xcalloc(sizeof(struct commit *), array-nr); + + init_revisions(revs, NULL); + + for (i = 0; i array-nr; i++) { + struct ref_array_item *item = array-items[i]; + add_pending_object(revs, item-commit-object, item-refname); + to_clear[i] = item-commit; + } + + filter-merge_commit-object.flags |= UNINTERESTING; + add_pending_object(revs, filter-merge_commit-object, ); + + revs.limited = 1; + if (prepare_revision_walk(revs)) + die(_(revision walk setup failed)); + + old_nr = array-nr; + array-nr = 0; + + for (i = 0; i old_nr; i++) { + struct ref_array_item *item = array-items[i]; + struct commit *commit = item-commit; + + int is_merged = !!(commit-object.flags UNINTERESTING); + + if (is_merged == (filter-merge == REF_FILTER_MERGED_INCLUDE)) + array-items[array-nr++] = array-items[i]; + else + free_array_item(item); + } + + for (i = 0; i old_nr; i++) + clear_commit_marks(to_clear[i], ALL_REV_FLAGS); + clear_commit_marks(filter-merge_commit, ALL_REV_FLAGS); + free(to_clear); +} + /* * API for filtering a set of refs. Based on the type of refs the user * has requested, we iterate through those refs and apply filters @@ -941,17 +999,24 @@ void ref_array_clear(struct ref_array *array) int filter_refs(struct ref_array *array, struct ref_filter *filter, unsigned int type) { struct ref_filter_cbdata ref_cbdata; + int ret = 0; ref_cbdata.array = array; ref_cbdata.filter = filter; + /* Simple per-ref filtering */ if (type (FILTER_REFS_ALL | FILTER_REFS_INCLUDE_BROKEN)) - return for_each_rawref(ref_filter_handler, ref_cbdata); + ret = for_each_rawref(ref_filter_handler, ref_cbdata); else if (type FILTER_REFS_ALL) - return for_each_ref(ref_filter_handler, ref_cbdata); - else + ret = for_each_ref(ref_filter_handler, ref_cbdata); + else if (type) die(filter_refs: invalid type); - return 0; + + /* Filters that need revision walking */ + if (filter-merge_commit) +
[PATCH v5 11/11] for-each-ref: add '--contains' option
Add the '--contains' option provided by 'ref-filter'. The '--contains' option lists only refs which contain the mentioned commit (HEAD if no commit is explicitly given). Add documentation and tests for the same. Mentored-by: Christian Couder christian.cou...@gmail.com Mentored-by: Matthieu Moy matthieu@grenoble-inp.fr Signed-off-by: Karthik Nayak karthik@gmail.com --- Documentation/git-for-each-ref.txt | 5 + builtin/for-each-ref.c | 2 ++ t/t6301-for-each-ref-filter.sh | 14 ++ 3 files changed, 21 insertions(+) diff --git a/Documentation/git-for-each-ref.txt b/Documentation/git-for-each-ref.txt index 290a5c1..94bb5bd 100644 --- a/Documentation/git-for-each-ref.txt +++ b/Documentation/git-for-each-ref.txt @@ -11,6 +11,7 @@ SYNOPSIS 'git for-each-ref' [--count=count] [--shell|--perl|--python|--tcl] [(--sort=key)...] [--format=format] [pattern...] [--points-at object] [(--merged | --no-merged) [object]] + [--contains [object]] DESCRIPTION --- @@ -74,6 +75,10 @@ OPTIONS Only list refs whose tips are not reachable from the specified commit (HEAD if not specified). +--contains [object]:: + Only list tags which contain the specified commit (HEAD if not + specified). + FIELD NAMES --- diff --git a/builtin/for-each-ref.c b/builtin/for-each-ref.c index ba70798..5868c48 100644 --- a/builtin/for-each-ref.c +++ b/builtin/for-each-ref.c @@ -9,6 +9,7 @@ static char const * const for_each_ref_usage[] = { N_(git for-each-ref [options] [pattern]), N_(git for-each-ref [--points-at object]), N_(git for-each-ref [(--merged | --no-merged) [object]]), + N_(git for-each-ref [--contains [object]]), NULL }; @@ -41,6 +42,7 @@ int cmd_for_each_ref(int argc, const char **argv, const char *prefix) parse_opt_object_name), OPT_MERGED(filter, N_(print only refs that are merged)), OPT_NO_MERGED(filter, N_(print only refs that are not merged)), + OPT_CONTAINS(filter.with_commit, N_(print only refs which contain the commit)), OPT_END(), }; diff --git a/t/t6301-for-each-ref-filter.sh b/t/t6301-for-each-ref-filter.sh index f5ccfb9..50ee115 100755 --- a/t/t6301-for-each-ref-filter.sh +++ b/t/t6301-for-each-ref-filter.sh @@ -58,4 +58,18 @@ test_expect_success 'filtering with --no-merged' ' test_cmp expect actual ' +test_expect_success 'filtering with --contains' ' + cat expect -\EOF + refs/heads/master + refs/heads/side + refs/odd/spot + refs/tags/four + refs/tags/signed-tag + refs/tags/three + refs/tags/two + EOF + git for-each-ref --format=%(refname) --contains=two actual + test_cmp expect actual +' + test_done -- 2.4.4 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v5 03/11] ref-filter: implement '--points-at' option
In 'tag -l' we have '--points-at' option which lets users list only tags which point to a particular commit. Implement this option in 'ref-filter.{c,h}' so that other commands can benefit from this. This is duplicated from tag.c, we will eventually remove that when we port tag.c to use ref-filter APIs. Based-on-patch-by: Jeff King p...@peff.net Mentored-by: Christian Couder christian.cou...@gmail.com Mentored-by: Matthieu Moy matthieu@grenoble-inp.fr Signed-off-by: Karthik Nayak karthik@gmail.com --- builtin/tag.c | 4 ref-filter.c | 26 ++ ref-filter.h | 1 + 3 files changed, 31 insertions(+) diff --git a/builtin/tag.c b/builtin/tag.c index e36c43e..280981f 100644 --- a/builtin/tag.c +++ b/builtin/tag.c @@ -56,6 +56,10 @@ static int match_pattern(const char **patterns, const char *ref) return 0; } +/* + * This is currently duplicated in ref-filter.c, and will eventually be + * removed as we port tag.c to use the ref-filter APIs. + */ static const unsigned char *match_points_at(const char *refname, const unsigned char *sha1) { diff --git a/ref-filter.c b/ref-filter.c index 43502a4..f40f06e 100644 --- a/ref-filter.c +++ b/ref-filter.c @@ -842,6 +842,29 @@ static int match_name_as_path(const char **pattern, const char *refname) return 0; } +/* + * Given a ref (sha1, refname) see if it points to one of the sha1s + * in a sha1_array. + */ +static int match_points_at(struct sha1_array *points_at, const unsigned char *sha1, + const char *refname) +{ + struct object *obj; + + if (!points_at || !points_at-nr) + return 1; + + if (sha1_array_lookup(points_at, sha1) = 0) + return 1; + + obj = parse_object_or_die(sha1, refname); + if (obj-type == OBJ_TAG + sha1_array_lookup(points_at, ((struct tag *)obj)-tagged-sha1) = 0) + return 1; + + return 0; +} + /* Allocate space for a new ref_array_item and copy the objectname and flag to it */ static struct ref_array_item *new_ref_array_item(const char *refname, const unsigned char *objectname, @@ -875,6 +898,9 @@ static int ref_filter_handler(const char *refname, const struct object_id *oid, if (*filter-name_patterns !match_name_as_path(filter-name_patterns, refname)) return 0; + if (!match_points_at(filter-points_at, oid-hash, refname)) + return 0; + /* * We do not open the object yet; sort may only need refname * to do its job and the resulting list may yet to be pruned diff --git a/ref-filter.h b/ref-filter.h index 6997984..c2856b8 100644 --- a/ref-filter.h +++ b/ref-filter.h @@ -42,6 +42,7 @@ struct ref_array { struct ref_filter { const char **name_patterns; + struct sha1_array points_at; }; struct ref_filter_cbdata { -- 2.4.4 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v5 07/11] for-each-ref: add '--merged' and '--no-merged' options
Add the '--merged' and '--no-merged' options provided by 'ref-filter'. The '--merged' option lets the user to only list refs merged into the named commit. The '--no-merged' option lets the user to only list refs not merged into the named commit. Add documentation and tests for the same. Based-on-patch-by: Jeff King p...@peff.net Mentored-by: Christian Couder christian.cou...@gmail.com Mentored-by: Matthieu Moy matthieu@grenoble-inp.fr Signed-off-by: Karthik Nayak karthik@gmail.com --- Documentation/git-for-each-ref.txt | 10 +- builtin/for-each-ref.c | 3 +++ t/t6301-for-each-ref-filter.sh | 22 ++ 3 files changed, 34 insertions(+), 1 deletion(-) diff --git a/Documentation/git-for-each-ref.txt b/Documentation/git-for-each-ref.txt index 0ede41d..290a5c1 100644 --- a/Documentation/git-for-each-ref.txt +++ b/Documentation/git-for-each-ref.txt @@ -10,7 +10,7 @@ SYNOPSIS [verse] 'git for-each-ref' [--count=count] [--shell|--perl|--python|--tcl] [(--sort=key)...] [--format=format] [pattern...] - [--points-at object] + [--points-at object] [(--merged | --no-merged) [object]] DESCRIPTION --- @@ -66,6 +66,14 @@ OPTIONS --points-at object:: Only list refs pointing to the given object. +--merged [object]:: + Only list refs whose tips are reachable from the + specified commit (HEAD if not specified). + +--no-merged [object]:: + Only list refs whose tips are not reachable from the + specified commit (HEAD if not specified). + FIELD NAMES --- diff --git a/builtin/for-each-ref.c b/builtin/for-each-ref.c index 46f9b05..ba70798 100644 --- a/builtin/for-each-ref.c +++ b/builtin/for-each-ref.c @@ -8,6 +8,7 @@ static char const * const for_each_ref_usage[] = { N_(git for-each-ref [options] [pattern]), N_(git for-each-ref [--points-at object]), + N_(git for-each-ref [(--merged | --no-merged) [object]]), NULL }; @@ -38,6 +39,8 @@ int cmd_for_each_ref(int argc, const char **argv, const char *prefix) OPT_CALLBACK(0, points-at, filter.points_at, N_(object), N_(print only refs pointing to the given object), parse_opt_object_name), + OPT_MERGED(filter, N_(print only refs that are merged)), + OPT_NO_MERGED(filter, N_(print only refs that are not merged)), OPT_END(), }; diff --git a/t/t6301-for-each-ref-filter.sh b/t/t6301-for-each-ref-filter.sh index 7269a66..f5ccfb9 100755 --- a/t/t6301-for-each-ref-filter.sh +++ b/t/t6301-for-each-ref-filter.sh @@ -36,4 +36,26 @@ test_expect_success 'check signed tags with --points-at' ' test_cmp expect actual ' +test_expect_success 'filtering with --merged' ' + cat expect -\EOF + refs/heads/master + refs/odd/spot + refs/tags/one + refs/tags/three + refs/tags/two + EOF + git for-each-ref --format=%(refname) --merged=master actual + test_cmp expect actual +' + +test_expect_success 'filtering with --no-merged' ' + cat expect -\EOF + refs/heads/side + refs/tags/four + refs/tags/signed-tag + EOF + git for-each-ref --format=%(refname) --no-merged=master actual + test_cmp expect actual +' + test_done -- 2.4.4 -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
RE: Repository Code Scope (Plan Text)
Thanks. So are you saying there are tools that will let us start a repo for a project with multiple submodules and then pull out the coding history for a specific submodule so we can create a separate repository just for that submodule? I've actually been doing a lot of research about Git for many things that Git doesn't have basic documentation for, but I wasn't sure how to search for an answer to this type of question. Plus, we're trying to adopt Git quickly, and since I'm not a developer I have a lot of research that has to be done to understand what developers understand and how we can manage GIt, which is slowing down our adoption of Git. Thanks, Brian -Original Message- From: Konstantin Khomoutov [mailto:kostix+...@007spb.ru] Sent: Wednesday, June 24, 2015 2:53 PM To: BGaudreault Brian Cc: git@vger.kernel.org Subject: Re: Repository Code Scope (Plan Text) On Wed, 24 Jun 2015 18:19:42 + BGaudreault Brian bgaudrea...@edrnet.com wrote: What type of code scope should a repository contain? Can it be one large program with many elements or should it just be part of a program or can it be a project with multiple programs? What are the recommendations? There are no recommendations because the structure of a repositories depends on the use case. If you're developing a library which might be used by more than a single other project, host it in a separate repository, and in the projects which use that library, refer to it using submodules. If you have a project which contains internal submodules (say, for .NET projects, it's common to have many so-called assemblies in a single project to provide modularity), there's little point in messing with separate repositories and it's simpler to keep everything in one place. Note that there are tools which allow you to split from a repository the history touching only the contents of a particular directory, and then glue such history back into some other repository. Using these are not exactly a walk in the park but at least this sort of things is doable. This means you might start with a simple solution and then shape it into a more appropriate form when you'll see the need for this. I should also warn you that your question appear to be a bit too broad which, IMO, suggests that you did not do much research on what's offerred by Git and its ecosystem, what's in a Git repo, how is it hosted, what are the best practices of managing complicated Git projects etc. And all this information is abundant in the internets... -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 3/6] bisect: use refs infrastructure for BISECT_START
This ref needs to go through the refs backend, since some code assumes that it can be written and read as a ref. Signed-off-by: David Turner dtur...@twopensource.com --- contrib/completion/git-completion.bash | 2 +- git-bisect.sh | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash index 93716c4..c4d4d80 100644 --- a/contrib/completion/git-completion.bash +++ b/contrib/completion/git-completion.bash @@ -938,7 +938,7 @@ _git_bisect () local subcommands=start bad good skip reset visualize replay log run local subcommand=$(__git_find_on_cmdline $subcommands) if [ -z $subcommand ]; then - if [ -f $(__gitdir)/BISECT_START ]; then + if [ git rev-parse BISECT_START 2/dev/null ]; then __gitcomp $subcommands else __gitcomp replay start diff --git a/git-bisect.sh b/git-bisect.sh index ae3fec2..8658772 100755 --- a/git-bisect.sh +++ b/git-bisect.sh @@ -166,7 +166,7 @@ bisect_start() { # echo $start_head $GIT_DIR/BISECT_START { test z$mode != z--no-checkout || - git update-ref --no-deref BISECT_HEAD $start_head + git rev-parse $start_head $GIT_DIR/BISECT_HEAD } git rev-parse --sq-quote $@ $GIT_DIR/BISECT_NAMES eval $eval true @@ -399,7 +399,7 @@ bisect_clean_state() { rm -f $GIT_DIR/BISECT_RUN # Cleanup head-name if it got left by an old version of git-bisect rm -f $GIT_DIR/head-name - git update-ref -d --no-deref BISECT_HEAD + rm -f $GIT_DIR/BISECT_HEAD # clean up BISECT_START last rm -f $GIT_DIR/BISECT_START } -- 2.0.4.314.gdbf7a51-twtrsrc -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 4/6] refs: replace log_ref_write with create_reflog
In a moment, we will use this to add reflog creation commands to git-reflog. Signed-off-by: David Turner dtur...@twopensource.com --- builtin/checkout.c | 2 +- refs.c | 4 ++-- refs.h | 2 +- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/builtin/checkout.c b/builtin/checkout.c index ac4d10a..7549ae2 100644 --- a/builtin/checkout.c +++ b/builtin/checkout.c @@ -629,7 +629,7 @@ static void update_refs_for_switch(const struct checkout_opts *opts, ref_name = mkpath(refs/heads/%s, opts-new_orphan_branch); temp = log_all_ref_updates; log_all_ref_updates = 1; - ret = log_ref_setup(ref_name, log_file, err); + ret = create_reflog(ref_name, log_file, err); log_all_ref_updates = temp; strbuf_release(log_file); if (ret) { diff --git a/refs.c b/refs.c index c1a563f..93412ee 100644 --- a/refs.c +++ b/refs.c @@ -3119,7 +3119,7 @@ static int copy_msg(char *buf, const char *msg) } /* This function will fill in *err and return -1 on failure */ -int log_ref_setup(const char *refname, struct strbuf *sb_logfile, struct strbuf *err) +int create_reflog(const char *refname, struct strbuf *sb_logfile, struct strbuf *err) { int logfd, oflags = O_APPEND | O_WRONLY; char *logfile; @@ -3203,7 +3203,7 @@ static int log_ref_write_1(const char *refname, const unsigned char *old_sha1, if (log_all_ref_updates 0) log_all_ref_updates = !is_bare_repository(); - result = log_ref_setup(refname, sb_log_file, err); + result = create_reflog(refname, sb_log_file, err); if (result) return result; diff --git a/refs.h b/refs.h index eee99f6..d4f75a9 100644 --- a/refs.h +++ b/refs.h @@ -233,7 +233,7 @@ int pack_refs(unsigned int flags); /* * Setup reflog before using. Fill in err and return -1 on failure. */ -int log_ref_setup(const char *refname, struct strbuf *logfile, struct strbuf *err); +int create_reflog(const char *refname, struct strbuf *logfile, struct strbuf *err); /** Reads log for the value of ref during at_time. **/ extern int read_ref_at(const char *refname, unsigned int flags, -- 2.0.4.314.gdbf7a51-twtrsrc -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 2/6] cherry-pick: Use refs infrastructure for CHERRY_PICK_HEAD
Also use refs infrastructure for REVERT_HEAD. These refs need to go through the refs backend, since some code assumes that they can be read as refs. Signed-off-by: David Turner dtur...@twopensource.com --- branch.c | 4 ++-- builtin/commit.c | 7 --- builtin/merge.c | 3 ++- contrib/completion/git-prompt.sh | 9 + git-gui/lib/commit.tcl | 2 +- refs.c | 17 + refs.h | 5 + sequencer.c | 39 +-- t/t7509-commit.sh| 4 ++-- wt-status.c | 6 ++ 10 files changed, 53 insertions(+), 43 deletions(-) diff --git a/branch.c b/branch.c index b002435..8371a16 100644 --- a/branch.c +++ b/branch.c @@ -302,8 +302,8 @@ void create_branch(const char *head, void remove_branch_state(void) { - unlink(git_path(CHERRY_PICK_HEAD)); - unlink(git_path(REVERT_HEAD)); + delete_ref(CHERRY_PICK_HEAD, NULL, REF_NODEREF | REF_NO_REFLOG); + delete_ref(REVERT_HEAD, NULL, REF_NODEREF | REF_NO_REFLOG); unlink(git_path(MERGE_HEAD)); unlink(git_path(MERGE_RR)); unlink(git_path(MERGE_MSG)); diff --git a/builtin/commit.c b/builtin/commit.c index b5b1158..0f0b184 100644 --- a/builtin/commit.c +++ b/builtin/commit.c @@ -166,9 +166,10 @@ static int opt_parse_m(const struct option *opt, const char *arg, int unset) static void determine_whence(struct wt_status *s) { + unsigned char unused[20]; if (file_exists(git_path(MERGE_HEAD))) whence = FROM_MERGE; - else if (file_exists(git_path(CHERRY_PICK_HEAD))) { + else if (!read_ref(CHERRY_PICK_HEAD, unused)) { whence = FROM_CHERRY_PICK; if (file_exists(git_path(SEQ_DIR))) sequencer_in_use = 1; @@ -1777,8 +1778,8 @@ int cmd_commit(int argc, const char **argv, const char *prefix) } ref_transaction_free(transaction); - unlink(git_path(CHERRY_PICK_HEAD)); - unlink(git_path(REVERT_HEAD)); + delete_ref(CHERRY_PICK_HEAD, NULL, REF_NODEREF | REF_NO_REFLOG); + delete_ref(REVERT_HEAD, NULL, REF_NODEREF | REF_NO_REFLOG); unlink(git_path(MERGE_HEAD)); unlink(git_path(MERGE_MSG)); unlink(git_path(MERGE_MODE)); diff --git a/builtin/merge.c b/builtin/merge.c index 46aacd6..a4abf93 100644 --- a/builtin/merge.c +++ b/builtin/merge.c @@ -1144,6 +1144,7 @@ int cmd_merge(int argc, const char **argv, const char *prefix) unsigned char result_tree[20]; unsigned char stash[20]; unsigned char head_sha1[20]; + unsigned char unused[20]; struct commit *head_commit; struct strbuf buf = STRBUF_INIT; int flag, i, ret = 0, head_subsumed; @@ -1206,7 +1207,7 @@ int cmd_merge(int argc, const char **argv, const char *prefix) else die(_(You have not concluded your merge (MERGE_HEAD exists).)); } - if (file_exists(git_path(CHERRY_PICK_HEAD))) { + if (!read_ref(CHERRY_PICK_HEAD, unused)) { if (advice_resolve_conflict) die(_(You have not concluded your cherry-pick (CHERRY_PICK_HEAD exists).\n Please, commit your changes before you merge.)); diff --git a/contrib/completion/git-prompt.sh b/contrib/completion/git-prompt.sh index 366f0bc..5e27a34 100644 --- a/contrib/completion/git-prompt.sh +++ b/contrib/completion/git-prompt.sh @@ -415,9 +415,9 @@ __git_ps1 () fi elif [ -f $g/MERGE_HEAD ]; then r=|MERGING - elif [ -f $g/CHERRY_PICK_HEAD ]; then + elif git rev-parse --quiet --verify CHERRY_PICK_HEAD /dev/null; then r=|CHERRY-PICKING - elif [ -f $g/REVERT_HEAD ]; then + elif git rev-parse --quiet --verify REVERT_HEAD /dev/null; then r=|REVERTING elif [ -f $g/BISECT_LOG ]; then r=|BISECTING @@ -429,8 +429,9 @@ __git_ps1 () # symlink symbolic ref b=$(git symbolic-ref HEAD 2/dev/null) else - local head= - if ! __git_eread $g/HEAD head; then + local head + head=ref: $(git symbolic-ref HEAD 2/dev/null) || head=$(git rev-parse HEAD) + if [ -z $head ]; then return $exit fi # is it a symbolic ref? diff --git a/git-gui/lib/commit.tcl b/git-gui/lib/commit.tcl index 864b687..2b08b13 100644 --- a/git-gui/lib/commit.tcl +++ b/git-gui/lib/commit.tcl @@ -409,7 +409,7 @@ A rescan will be automatically started now. catch {file delete [gitdir
[PATCH 5/6] git-reflog: add create and exists functions
These are necessary because ref backends manage reflogs. In a moment, we will use these functions to make git stash work with alternate ref backends. Signed-off-by: David Turner dtur...@twopensource.com --- builtin/reflog.c | 81 +++- 1 file changed, 80 insertions(+), 1 deletion(-) diff --git a/builtin/reflog.c b/builtin/reflog.c index c2eb8ff..3cf7d3d 100644 --- a/builtin/reflog.c +++ b/builtin/reflog.c @@ -13,6 +13,10 @@ static const char reflog_expire_usage[] = git reflog expire [--expire=time] [--expire-unreachable=time] [--rewrite] [--updateref] [--stale-fix] [--dry-run | -n] [--verbose] [--all] refs...; static const char reflog_delete_usage[] = git reflog delete [--rewrite] [--updateref] [--dry-run | -n] [--verbose] refs...; +static const char reflog_create_usage[] = +git reflog create refs...; +static const char reflog_exists_usage[] = +git reflog exists refs...; static unsigned long default_reflog_expire; static unsigned long default_reflog_expire_unreachable; @@ -699,12 +703,81 @@ static int cmd_reflog_delete(int argc, const char **argv, const char *prefix) return status; } +static int cmd_reflog_create(int argc, const char **argv, const char *prefix) +{ + int i, status = 0, start = 0; + struct strbuf err = STRBUF_INIT; + struct strbuf logfile = STRBUF_INIT; + + for (i = 1; i argc; i++) { + const char *arg = argv[i]; + if (!strcmp(arg, --)) { + i++; + break; + } + else if (arg[0] == '-') + usage(reflog_create_usage); + else + break; + } + + start = i; + + if (argc - start 1) + return error(Nothing to create?); + + for (i = start ; i argc; i++) { + if (check_refname_format(argv[i], REFNAME_ALLOW_ONELEVEL)) + die(invalid ref format: %s, argv[i]); + } + for (i = start ; i argc; i++) { + if (create_reflog(argv[i], logfile, err)) { + error(could not create reflog %s: %s, argv[i], + err.buf); + status = 1; + strbuf_release(err); + } + strbuf_release(logfile); + } + return status; +} + +static int cmd_reflog_exists(int argc, const char **argv, const char *prefix) +{ + int i, status = 0, start = 0; + + for (i = 1; i argc; i++) { + const char *arg = argv[i]; + if (!strcmp(arg, --)) { + i++; + break; + } + else if (arg[0] == '-') + usage(reflog_exists_usage); + else + break; + } + + start = i; + + if (argc - start 1) + return error(Nothing to check?); + + for (i = start ; i argc; i++) { + if (check_refname_format(argv[i], REFNAME_ALLOW_ONELEVEL)) + die(invalid ref format: %s, argv[i]); + if (!reflog_exists(argv[i])) + status = 1; + } + return status; +} + /* * main reflog */ static const char reflog_usage[] = -git reflog [ show | expire | delete ]; +git reflog [ show | expire | delete | create | exists ]; int cmd_reflog(int argc, const char **argv, const char *prefix) { @@ -724,5 +797,11 @@ int cmd_reflog(int argc, const char **argv, const char *prefix) if (!strcmp(argv[1], delete)) return cmd_reflog_delete(argc - 1, argv + 1, prefix); + if (!strcmp(argv[1], create)) + return cmd_reflog_create(argc - 1, argv + 1, prefix); + + if (!strcmp(argv[1], exists)) + return cmd_reflog_exists(argc - 1, argv + 1, prefix); + return cmd_log_reflog(argc, argv, prefix); } -- 2.0.4.314.gdbf7a51-twtrsrc -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Repository Code Scope (Plan Text)
On Wed, 24 Jun 2015 18:19:42 + BGaudreault Brian bgaudrea...@edrnet.com wrote: What type of code scope should a repository contain? Can it be one large program with many elements or should it just be part of a program or can it be a project with multiple programs? What are the recommendations? There are no recommendations because the structure of a repositories depends on the use case. If you're developing a library which might be used by more than a single other project, host it in a separate repository, and in the projects which use that library, refer to it using submodules. If you have a project which contains internal submodules (say, for .NET projects, it's common to have many so-called assemblies in a single project to provide modularity), there's little point in messing with separate repositories and it's simpler to keep everything in one place. Note that there are tools which allow you to split from a repository the history touching only the contents of a particular directory, and then glue such history back into some other repository. Using these are not exactly a walk in the park but at least this sort of things is doable. This means you might start with a simple solution and then shape it into a more appropriate form when you'll see the need for this. I should also warn you that your question appear to be a bit too broad which, IMO, suggests that you did not do much research on what's offerred by Git and its ecosystem, what's in a Git repo, how is it hosted, what are the best practices of managing complicated Git projects etc. And all this information is abundant in the internets... -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
RE: Repository Code Security (Plan Text)
Thanks. Yes, I meant that local code is code pulled down to a person's PC, so we don't want them to leave the company with access to this code. So we can only prevent this scenario by running GitLab in our environment instead of running GitHub in the cloud? Would removing a GitHub account from the GitHub repository prevent them from accessing the code on their PC? How do you prevent private GitHub repositories from being pulled down to unauthorized PCs? Thanks, Brian -Original Message- From: Konstantin Khomoutov [mailto:kostix+...@007spb.ru] Sent: Wednesday, June 24, 2015 2:31 PM To: BGaudreault Brian Cc: git@vger.kernel.org Subject: Re: Repository Code Security (Plan Text) On Wed, 24 Jun 2015 18:18:00 + BGaudreault Brian bgaudrea...@edrnet.com wrote: If someone downloads code to their notebook PC and leaves the company, what protection do we have against them not being able to access the local code copy anymore? What do you mean by local code? That one which is on the notebook? Then you can do literally nothing except for not allowing cloning your Git repositories onto random computers in the first place. If you instead mean the copy of code available in the repositories hosted in your enterprise then all you need to do is to somehow terminate the access of that employee who's left to those repositories. (This assumes they're accessible from the outside; if they aren't, the problem simply do not exist.) -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH/WIP v3 01/31] wrapper: implement xopen()
Hi Stefan, On 2015-06-24 18:59, Stefan Beller wrote: On Wed, Jun 24, 2015 at 9:28 AM, Johannes Schindelin johannes.schinde...@gmx.de wrote: On 2015-06-18 13:25, Paul Tan wrote: + int fd = open(path, oflag, mode); + if (fd = 0) + return fd; + if (errno == EINTR) + continue; + die_errno(_(could not open '%s'), path); It is often helpful to know whether a path was opened for reading or writing, so maybe we should have something like if (oflag O_WRITE) die_errno(_(could not open '%s' for writing), path); else if (oflag O_READ) die_errno(_(could not open '%s' for reading), path); else die_errno(_(could not open '%s'), path); ? I know it is a bit of duplication, but I fear we cannot get around that without breaking i18n support. This distinction was part of earlier series, but Torsten Boegershausen suggested to leave it out. [compare http://thread.gmane.org/gmane.comp.version-control.git/270048/focus=270049] So sorry that I missed that (it is still somewhere in my ever-growing inbox). I would have politely disagreed with Torsten if I had not missed it, though. IMO the varargs make the code more cumbersome to read (and even fragile, because you can easily call `xopen(path, O_WRITE | O_CREATE)` and would not even get so much as a compiler warning!) and the error message does carry value: it helps you resolve the issue (it is completely unnecessary to check write permissions of the directory when a file could not be opened for reading, for example, yet if the error message does not say that and you suspect that the file could not be opened for *writing* that is exactly what you would waste your time checking). Ciao, Dscho -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 0/6] refs backend preamble
This set of patches is a preamble to pluggable ref backends. The intent is to use the ref infrastructure for special refs like CHERRY_PICK_HEAD where possible, and to use git plumbing commands to access refs and reflogs instead of directly writing files to the .git directory. This series is on top of pu at 9039c98c. -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 1/6] refs.c: add an err argument to log_ref_setup
Add err argument to log_ref_setup that can explain the reason for a failure. This then eliminates the need to manage errno through this function since we can just add strerror(errno) to the err string when meaningful. No callers relied on errno from this function for anything else than the error message. write_ref_to_lockfile is a private function that calls log_ref_setup. Update this function to also take an err argument and fill it in. This again eliminates the need to manage errno in this function. Update of a patch by Ronnie Sahlberg. Signed-off-by: Ronnie Sahlberg sahlb...@google.com Signed-off-by: David Turner dtur...@twitter.com --- builtin/checkout.c | 8 ++-- refs.c | 111 - refs.h | 4 +- 3 files changed, 66 insertions(+), 57 deletions(-) diff --git a/builtin/checkout.c b/builtin/checkout.c index c018ab3..ac4d10a 100644 --- a/builtin/checkout.c +++ b/builtin/checkout.c @@ -624,16 +624,18 @@ static void update_refs_for_switch(const struct checkout_opts *opts, struct strbuf log_file = STRBUF_INIT; int ret; const char *ref_name; + struct strbuf err = STRBUF_INIT; ref_name = mkpath(refs/heads/%s, opts-new_orphan_branch); temp = log_all_ref_updates; log_all_ref_updates = 1; - ret = log_ref_setup(ref_name, log_file); + ret = log_ref_setup(ref_name, log_file, err); log_all_ref_updates = temp; strbuf_release(log_file); if (ret) { - fprintf(stderr, _(Can not do reflog for '%s'\n), - opts-new_orphan_branch); + fprintf(stderr, _(Can not do reflog for '%s'. %s\n), + opts-new_orphan_branch, err.buf); + strbuf_release(err); return; } } diff --git a/refs.c b/refs.c index fb568d7..b34a54a 100644 --- a/refs.c +++ b/refs.c @@ -2975,9 +2975,11 @@ static int rename_ref_available(const char *oldname, const char *newname) return ret; } -static int write_ref_to_lockfile(struct ref_lock *lock, const unsigned char *sha1); +static int write_ref_to_lockfile(struct ref_lock *lock, +const unsigned char *sha1, struct strbuf* err); static int commit_ref_update(struct ref_lock *lock, -const unsigned char *sha1, const char *logmsg); +const unsigned char *sha1, const char *logmsg, +struct strbuf *err); int rename_ref(const char *oldrefname, const char *newrefname, const char *logmsg) { @@ -3038,9 +3040,10 @@ int rename_ref(const char *oldrefname, const char *newrefname, const char *logms } hashcpy(lock-old_oid.hash, orig_sha1); - if (write_ref_to_lockfile(lock, orig_sha1) || - commit_ref_update(lock, orig_sha1, logmsg)) { - error(unable to write current sha1 into %s, newrefname); + if (write_ref_to_lockfile(lock, orig_sha1, err) || + commit_ref_update(lock, orig_sha1, logmsg, err)) { + error(unable to write current sha1 into %s: %s, newrefname, err.buf); + strbuf_release(err); goto rollback; } @@ -3056,9 +3059,11 @@ int rename_ref(const char *oldrefname, const char *newrefname, const char *logms flag = log_all_ref_updates; log_all_ref_updates = 0; - if (write_ref_to_lockfile(lock, orig_sha1) || - commit_ref_update(lock, orig_sha1, NULL)) - error(unable to write current sha1 into %s, oldrefname); + if (write_ref_to_lockfile(lock, orig_sha1, err) || + commit_ref_update(lock, orig_sha1, NULL, err)) { + error(unable to write current sha1 into %s: %s, oldrefname, err.buf); + strbuf_release(err); + } log_all_ref_updates = flag; rollbacklog: @@ -3113,8 +3118,8 @@ static int copy_msg(char *buf, const char *msg) return cp - buf; } -/* This function must set a meaningful errno on failure */ -int log_ref_setup(const char *refname, struct strbuf *sb_logfile) +/* This function will fill in *err and return -1 on failure */ +int log_ref_setup(const char *refname, struct strbuf *sb_logfile, struct strbuf *err) { int logfd, oflags = O_APPEND | O_WRONLY; char *logfile; @@ -3129,9 +3134,8 @@ int log_ref_setup(const char *refname, struct strbuf *sb_logfile) starts_with(refname, refs/notes/) ||
[PATCH 6/6] git-stash: use git-reflog instead of creating files
This is in support of alternate ref backends which don't necessarily store reflogs as files. Signed-off-by: David Turner dtur...@twopensource.com --- git-stash.sh | 4 ++-- refs.c | 1 + 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/git-stash.sh b/git-stash.sh index 8e9e2cd..27155bc 100755 --- a/git-stash.sh +++ b/git-stash.sh @@ -184,7 +184,7 @@ store_stash () { fi # Make sure the reflog for stash is kept. - : $(git rev-parse --git-path logs/$ref_stash) + git reflog create $ref_stash git update-ref -m $stash_msg $ref_stash $w_commit ret=$? test $ret != 0 test -z $quiet @@ -262,7 +262,7 @@ save_stash () { say $(gettext No local changes to save) exit 0 fi - test -f $(git rev-parse --git-path logs/$ref_stash) || + git reflog exists $ref_stash || clear_stash || die $(gettext Cannot initialize stash) create_stash $stash_msg $untracked diff --git a/refs.c b/refs.c index 93412ee..f3e3da0 100644 --- a/refs.c +++ b/refs.c @@ -3132,6 +3132,7 @@ int create_reflog(const char *refname, struct strbuf *sb_logfile, struct strbuf (starts_with(refname, refs/heads/) || starts_with(refname, refs/remotes/) || starts_with(refname, refs/notes/) || +!strcmp(refname, refs/stash) || !strcmp(refname, HEAD))) { if (safe_create_leading_directories(logfile) 0) { strbuf_addf(err, unable to create directory for %s. -- 2.0.4.314.gdbf7a51-twtrsrc -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Repository Code Security (Plan Text)
What most companies do is this: they issue their employees computers, and then when the employee leaves, they take the computers away. Of course, someone could have copied the code before leaving the company. The typical remedy for this is a contract saying don't do that. But I guess some companies just go straight to the FBI see e.g.: https://en.wikipedia.org/wiki/Sergey_Aleynikov There is no technological solution that will prevent someone from accessing something that lives on their own computer (just ask the movie and music industries, which tried to find one for about twenty years). On Wed, 2015-06-24 at 18:59 +, BGaudreault Brian wrote: Thanks. Yes, I meant that local code is code pulled down to a person's PC, so we don't want them to leave the company with access to this code. So we can only prevent this scenario by running GitLab in our environment instead of running GitHub in the cloud? Would removing a GitHub account from the GitHub repository prevent them from accessing the code on their PC? How do you prevent private GitHub repositories from being pulled down to unauthorized PCs? Thanks, Brian -Original Message- From: Konstantin Khomoutov [mailto:kostix+...@007spb.ru] Sent: Wednesday, June 24, 2015 2:31 PM To: BGaudreault Brian Cc: git@vger.kernel.org Subject: Re: Repository Code Security (Plan Text) On Wed, 24 Jun 2015 18:18:00 + BGaudreault Brian bgaudrea...@edrnet.com wrote: If someone downloads code to their notebook PC and leaves the company, what protection do we have against them not being able to access the local code copy anymore? What do you mean by local code? That one which is on the notebook? Then you can do literally nothing except for not allowing cloning your Git repositories onto random computers in the first place. If you instead mean the copy of code available in the repositories hosted in your enterprise then all you need to do is to somehow terminate the access of that employee who's left to those repositories. (This assumes they're accessible from the outside; if they aren't, the problem simply do not exist.) -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
RE: Repository Code Security (Plan Text)
On Wed, 24 Jun 2015, BGaudreault Brian wrote: Thanks. Yes, I meant that local code is code pulled down to a person's PC, so we don't want them to leave the company with access to this code. So we can only prevent this scenario by running GitLab in our environment instead of running GitHub in the cloud? Would removing a GitHub account from the GitHub repository prevent them from accessing the code on their PC? How do you prevent private GitHub repositories from being pulled down to unauthorized PCs? policy, you say that it's against policy for someone to put company info on a personal machine. You probably run your own repository that's only available within your network (or over your VPN) rather than using a cloud service like github (you may want to check with github to see if they can lock down a private repo to only be accessed from specific IP addresses) you will also need to make sure that people don't plug personal laptops into your corporate network, and that they don't use personal phones to access company e-mail. The bottom line is that it's no different from preventing them from having access to any other sensitive data in your company. What measures do you have in place to keep them from taking sensitive Word Docs or spreadsheets when they leave? do the same thing to deal with their access to code. David Lang Thanks, Brian -Original Message- On Wed, 24 Jun 2015 18:18:00 + BGaudreault Brian bgaudrea...@edrnet.com wrote: If someone downloads code to their notebook PC and leaves the company, what protection do we have against them not being able to access the local code copy anymore? What do you mean by local code? That one which is on the notebook? Then you can do literally nothing except for not allowing cloning your Git repositories onto random computers in the first place. If you instead mean the copy of code available in the repositories hosted in your enterprise then all you need to do is to somehow terminate the access of that employee who's left to those repositories. (This assumes they're accessible from the outside; if they aren't, the problem simply do not exist.) -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: Repository Code Security (Plan Text)
Git is not GitHub (any more than a cat is a cathouse). Git is a piece of software; GitHub is a hosting service for Git. Contact GitHub for GitHub support. On Wed, 2015-06-24 at 19:53 +, BGaudreault Brian wrote: Hi David Lang, I'm sorry, but I'm confused by your first two responses. Am I not contacting Git when I e-mail this e-mail address? You sound like you don't know exactly how GitHub works. Should I be contacting someone else for GitHub support? Thanks, Brian -Original Message- From: David Lang [mailto:da...@lang.hm] Sent: Wednesday, June 24, 2015 3:20 PM To: BGaudreault Brian Cc: Konstantin Khomoutov; git@vger.kernel.org Subject: RE: Repository Code Security (Plan Text) On Wed, 24 Jun 2015, BGaudreault Brian wrote: Thanks. Yes, I meant that local code is code pulled down to a person's PC, so we don't want them to leave the company with access to this code. So we can only prevent this scenario by running GitLab in our environment instead of running GitHub in the cloud? Would removing a GitHub account from the GitHub repository prevent them from accessing the code on their PC? How do you prevent private GitHub repositories from being pulled down to unauthorized PCs? policy, you say that it's against policy for someone to put company info on a personal machine. You probably run your own repository that's only available within your network (or over your VPN) rather than using a cloud service like github (you may want to check with github to see if they can lock down a private repo to only be accessed from specific IP addresses) you will also need to make sure that people don't plug personal laptops into your corporate network, and that they don't use personal phones to access company e-mail. The bottom line is that it's no different from preventing them from having access to any other sensitive data in your company. What measures do you have in place to keep them from taking sensitive Word Docs or spreadsheets when they leave? do the same thing to deal with their access to code. David Lang Thanks, Brian -Original Message- On Wed, 24 Jun 2015 18:18:00 + BGaudreault Brian bgaudrea...@edrnet.com wrote: If someone downloads code to their notebook PC and leaves the company, what protection do we have against them not being able to access the local code copy anymore? What do you mean by local code? That one which is on the notebook? Then you can do literally nothing except for not allowing cloning your Git repositories onto random computers in the first place. If you instead mean the copy of code available in the repositories hosted in your enterprise then all you need to do is to somehow terminate the access of that employee who's left to those repositories. (This assumes they're accessible from the outside; if they aren't, the problem simply do not exist.) -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
RE: Repository Code Security (Plan Text)
On Wed, 24 Jun 2015, BGaudreault Brian wrote: Hi David Lang, I'm sorry, but I'm confused by your first two responses. Am I not contacting Git when I e-mail this e-mail address? You sound like you don't know exactly how GitHub works. Should I be contacting someone else for GitHub support? git is the opensource distributed version control software that github uses as part of their offering. This is the mailing list used by the developers of git. Very few of the developers here work for github. For github support, you will need to contact the company github. David Lang Thanks, Brian -Original Message- From: David Lang [mailto:da...@lang.hm] Sent: Wednesday, June 24, 2015 3:20 PM To: BGaudreault Brian Cc: Konstantin Khomoutov; git@vger.kernel.org Subject: RE: Repository Code Security (Plan Text) On Wed, 24 Jun 2015, BGaudreault Brian wrote: Thanks. Yes, I meant that local code is code pulled down to a person's PC, so we don't want them to leave the company with access to this code. So we can only prevent this scenario by running GitLab in our environment instead of running GitHub in the cloud? Would removing a GitHub account from the GitHub repository prevent them from accessing the code on their PC? How do you prevent private GitHub repositories from being pulled down to unauthorized PCs? policy, you say that it's against policy for someone to put company info on a personal machine. You probably run your own repository that's only available within your network (or over your VPN) rather than using a cloud service like github (you may want to check with github to see if they can lock down a private repo to only be accessed from specific IP addresses) you will also need to make sure that people don't plug personal laptops into your corporate network, and that they don't use personal phones to access company e-mail. The bottom line is that it's no different from preventing them from having access to any other sensitive data in your company. What measures do you have in place to keep them from taking sensitive Word Docs or spreadsheets when they leave? do the same thing to deal with their access to code. David Lang Thanks, Brian -Original Message- On Wed, 24 Jun 2015 18:18:00 + BGaudreault Brian bgaudrea...@edrnet.com wrote: If someone downloads code to their notebook PC and leaves the company, what protection do we have against them not being able to access the local code copy anymore? What do you mean by local code? That one which is on the notebook? Then you can do literally nothing except for not allowing cloning your Git repositories onto random computers in the first place. If you instead mean the copy of code available in the repositories hosted in your enterprise then all you need to do is to somehow terminate the access of that employee who's left to those repositories. (This assumes they're accessible from the outside; if they aren't, the problem simply do not exist.) -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
RE: Repository Code Security (Plan Text)
Ok, thanks. I didn't realize there was a difference! I thought Git SCM ran GitHub. I haven't yet read this clear distinction. Of course I wasn't the one who chose GitHub in the first place. -Original Message- From: David Turner [mailto:dtur...@twopensource.com] Sent: Wednesday, June 24, 2015 4:00 PM To: BGaudreault Brian Cc: David Lang; Konstantin Khomoutov; git@vger.kernel.org Subject: Re: Repository Code Security (Plan Text) Git is not GitHub (any more than a cat is a cathouse). Git is a piece of software; GitHub is a hosting service for Git. Contact GitHub for GitHub support. On Wed, 2015-06-24 at 19:53 +, BGaudreault Brian wrote: Hi David Lang, I'm sorry, but I'm confused by your first two responses. Am I not contacting Git when I e-mail this e-mail address? You sound like you don't know exactly how GitHub works. Should I be contacting someone else for GitHub support? Thanks, Brian -Original Message- From: David Lang [mailto:da...@lang.hm] Sent: Wednesday, June 24, 2015 3:20 PM To: BGaudreault Brian Cc: Konstantin Khomoutov; git@vger.kernel.org Subject: RE: Repository Code Security (Plan Text) On Wed, 24 Jun 2015, BGaudreault Brian wrote: Thanks. Yes, I meant that local code is code pulled down to a person's PC, so we don't want them to leave the company with access to this code. So we can only prevent this scenario by running GitLab in our environment instead of running GitHub in the cloud? Would removing a GitHub account from the GitHub repository prevent them from accessing the code on their PC? How do you prevent private GitHub repositories from being pulled down to unauthorized PCs? policy, you say that it's against policy for someone to put company info on a personal machine. You probably run your own repository that's only available within your network (or over your VPN) rather than using a cloud service like github (you may want to check with github to see if they can lock down a private repo to only be accessed from specific IP addresses) you will also need to make sure that people don't plug personal laptops into your corporate network, and that they don't use personal phones to access company e-mail. The bottom line is that it's no different from preventing them from having access to any other sensitive data in your company. What measures do you have in place to keep them from taking sensitive Word Docs or spreadsheets when they leave? do the same thing to deal with their access to code. David Lang Thanks, Brian -Original Message- On Wed, 24 Jun 2015 18:18:00 + BGaudreault Brian bgaudrea...@edrnet.com wrote: If someone downloads code to their notebook PC and leaves the company, what protection do we have against them not being able to access the local code copy anymore? What do you mean by local code? That one which is on the notebook? Then you can do literally nothing except for not allowing cloning your Git repositories onto random computers in the first place. If you instead mean the copy of code available in the repositories hosted in your enterprise then all you need to do is to somehow terminate the access of that employee who's left to those repositories. (This assumes they're accessible from the outside; if they aren't, the problem simply do not exist.) -- To unsubscribe from this list: send the line unsubscribe git in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html