git@vger.kernel.org mailing list mirror (one of many)
 help / color / mirror / code / Atom feed
* bug: checkout --recurse-submodules discard uncommited changes in submodule
@ 2021-01-14  8:35 Kevin Bernard
  2021-01-14 13:54 ` Philippe Blain
  0 siblings, 1 reply; 3+ messages in thread
From: Kevin Bernard @ 2021-01-14  8:35 UTC (permalink / raw)
  To: git@vger.kernel.org

Thank you for filling out a Git bug report!
Please answer the following questions to help us understand your issue.

What did you do before the bug happened? (Steps to reproduce your issue)
Make a git repository with a submodule in it.
Make two different commits in the main repository with two different versions of
the submodule, one of them is the head of the branch.
Checkout the head of the branch in the main repository, and make a submodule update.
Make a modification, do not commit it, in a submodule file that will not result
in a "error: Your local changes to the following files would be overwritten by
checkout" when the other version of the library will be checked out.
Go back to the main repository and make a checkout of the other commit with the
switch --recurse-submodules.

What did you expect to happen? (Expected behavior)
The checkout with the switch --recurse-submodules should fail when there are
uncommitted changes in the submodule.

What happened instead? (Actual behavior)
Uncommitted changes in the submodule are discarded without any notifications.

What's different between what you expected and what actually happened?
Loss of the uncommitted changes in the submodule.

Anything else you want to add:
I stay at your disposal if you need more information.

Please review the rest of the bug report below.
You can delete any lines you don't wish to share.


[System Info]
git version:
git version 2.30.0.windows.1
cpu: x86_64
built from commit: 18da6dbba950f8cc7b7d07057f7c30bf7cf207b6
sizeof-long: 4
sizeof-size_t: 8
shell-path: /bin/sh
uname: Windows 10.0 19041 
compiler info: gnuc: 10.2
libc info: no libc information available
$SHELL (typically, interactive shell): C:\Program Files\Git\usr\bin\bash.exe


[Enabled Hooks]

Sincerely yours,

Kevin Bernard


^ permalink raw reply	[flat|nested] 3+ messages in thread

* Re: bug: checkout --recurse-submodules discard uncommited changes in submodule
  2021-01-14  8:35 bug: checkout --recurse-submodules discard uncommited changes in submodule Kevin Bernard
@ 2021-01-14 13:54 ` Philippe Blain
  2021-01-14 16:40   ` Kevin Bernard
  0 siblings, 1 reply; 3+ messages in thread
From: Philippe Blain @ 2021-01-14 13:54 UTC (permalink / raw)
  To: Kevin Bernard, git@vger.kernel.org

Hi Kevin,

Le 2021-01-14 à 03:35, Kevin Bernard a écrit :
> Thank you for filling out a Git bug report!
> Please answer the following questions to help us understand your issue.
> 
> What did you do before the bug happened? (Steps to reproduce your issue)
> Make a git repository with a submodule in it.
> Make two different commits in the main repository with two different versions of
> the submodule, one of them is the head of the branch.
> Checkout the head of the branch in the main repository, and make a submodule update.
> Make a modification, do not commit it, in a submodule file that will not result
> in a "error: Your local changes to the following files would be overwritten by
> checkout" when the other version of the library will be checked out.

I assume that you confirmed that by running 'git checkout <other version>'
in the submodule, right ?

> Go back to the main repository and make a checkout of the other commit with the
> switch --recurse-submodules.
> 
> What did you expect to happen? (Expected behavior)
> The checkout with the switch --recurse-submodules should fail when there are
> uncommitted changes in the submodule.
> 
> What happened instead? (Actual behavior)
> Uncommitted changes in the submodule are discarded without any notifications.
> 
> What's different between what you expected and what actually happened?
> Loss of the uncommitted changes in the submodule.
> 
> Anything else you want to add:
> I stay at your disposal if you need more information.


Thanks for the report. This is a known problem that was reported in [1] and [2].
I'm currently working on fixing that bug. I'm not quite finished yet as I want
to polish the end-user experience a bit, but if you want to compile from source,
the heart of the fix is this change:

diff --git a/unpack-trees.c b/unpack-trees.c
index 323280dd48..a3e3d98de1 100644
--- a/unpack-trees.c
+++ b/unpack-trees.c
@@ -1872,7 +1872,7 @@ static int verify_uptodate_1(const struct cache_entry *ce,
  
  		if (submodule_from_ce(ce)) {
  			int r = check_submodule_move_head(ce,
-				"HEAD", oid_to_hex(&ce->oid), o);
+				"HEAD", empty_tree_oid_hex(), o);
  			if (r)
  				return add_rejected_path(o, error_type, ce->name);
  			return 0;


This should disallow switching branches with '--recurse-submodules' if *any* file
in the submodule is modified.

However, I'm actually thinking that maybe it would
be better to let the checkout succeed in the exact case you mention, i.e. when
the modified files in the submodules are at the same version in both submodule
commits (i.e. git checkout <other version> in the submodule succeeds and the
modified files stay modified), and also carry over the modified files in the
submodule. This would mimic the 'git checkout' experience
without submodules, i.e. modified files that do not conflict are carried over
to the branch you are checking out.

If you can write a complete reproducer (complete steps starting with 'git init',
etc.) I will make sure that your scenario is adequately tested in my patch series.


Cheers,

Philippe.


[1] https://lore.kernel.org/git/CAHsG2VT4YB_nf8PrEmrHwK-iY-AQo0VDcvXGVsf8cEYXws4nig@mail.gmail.com/
[2] https://lore.kernel.org/git/20200525094019.22padbzuk7ukr5uv@overdrive.tratt.net/

^ permalink raw reply related	[flat|nested] 3+ messages in thread

* RE: bug: checkout --recurse-submodules discard uncommited changes in submodule
  2021-01-14 13:54 ` Philippe Blain
@ 2021-01-14 16:40   ` Kevin Bernard
  0 siblings, 0 replies; 3+ messages in thread
From: Kevin Bernard @ 2021-01-14 16:40 UTC (permalink / raw)
  To: Philippe Blain, git@vger.kernel.org

Hi Philippe, 

I have no preferences whether the checkout should fail if any files are modified in the submodule
or allow the checkout to succeed if the modification can be carried out. 

I wrote a step by step procedure to reproduce the bug.

Step to reproduce my issue

git init  
git checkout -b master  
git submodule add https://github.com/kbernard-perso/recurse-bug.git  
git submodule init  
git add .  
git commit -m "Add submodule"  
cd recurse-bug/  
echo "file1 modified" >> file1.txt  
git add .  
git commit -m "file1.txt modified"  
cd ..  
git add .  
git commit -m "Modified file1 in submodule"  
cd recurse-bug/  
echo "file2 modified" >> file2.txt  
cd ..  
git status  
git checkout --recurse-submodules HEAD^  
git status  

The uncommitted modifications made with "echo "file2 modified" >> file2.txt" are  
discarded by git checkout --recurse-submodules HEAD^  

Thank you very much for making git a wonderful tool to use.

Cheers, 

Kevin

-----Message d'origine-----
De : Philippe Blain <levraiphilippeblain@gmail.com> 
Envoyé : jeudi, 14 janvier 2021 14:55
À : Kevin Bernard <kevin.bernard@fiveco.ch>; git@vger.kernel.org
Objet : Re: bug: checkout --recurse-submodules discard uncommited changes in submodule

Hi Kevin,

Le 2021-01-14 à 03:35, Kevin Bernard a écrit :
> Thank you for filling out a Git bug report!
> Please answer the following questions to help us understand your issue.
> 
> What did you do before the bug happened? (Steps to reproduce your 
> issue) Make a git repository with a submodule in it.
> Make two different commits in the main repository with two different 
> versions of the submodule, one of them is the head of the branch.
> Checkout the head of the branch in the main repository, and make a submodule update.
> Make a modification, do not commit it, in a submodule file that will 
> not result in a "error: Your local changes to the following files 
> would be overwritten by checkout" when the other version of the library will be checked out.

I assume that you confirmed that by running 'git checkout <other version>'
in the submodule, right ?

> Go back to the main repository and make a checkout of the other commit 
> with the switch --recurse-submodules.
> 
> What did you expect to happen? (Expected behavior) The checkout with 
> the switch --recurse-submodules should fail when there are uncommitted 
> changes in the submodule.
> 
> What happened instead? (Actual behavior) Uncommitted changes in the 
> submodule are discarded without any notifications.
> 
> What's different between what you expected and what actually happened?
> Loss of the uncommitted changes in the submodule.
> 
> Anything else you want to add:
> I stay at your disposal if you need more information.


Thanks for the report. This is a known problem that was reported in [1] and [2].
I'm currently working on fixing that bug. I'm not quite finished yet as I want to polish the end-user experience a bit, but if you want to compile from source, the heart of the fix is this change:

diff --git a/unpack-trees.c b/unpack-trees.c index 323280dd48..a3e3d98de1 100644
--- a/unpack-trees.c
+++ b/unpack-trees.c
@@ -1872,7 +1872,7 @@ static int verify_uptodate_1(const struct cache_entry *ce,
  
  		if (submodule_from_ce(ce)) {
  			int r = check_submodule_move_head(ce,
-				"HEAD", oid_to_hex(&ce->oid), o);
+				"HEAD", empty_tree_oid_hex(), o);
  			if (r)
  				return add_rejected_path(o, error_type, ce->name);
  			return 0;


This should disallow switching branches with '--recurse-submodules' if *any* file in the submodule is modified.

However, I'm actually thinking that maybe it would be better to let the checkout succeed in the exact case you mention, i.e. when the modified files in the submodules are at the same version in both submodule commits (i.e. git checkout <other version> in the submodule succeeds and the modified files stay modified), and also carry over the modified files in the submodule. This would mimic the 'git checkout' experience without submodules, i.e. modified files that do not conflict are carried over to the branch you are checking out.

If you can write a complete reproducer (complete steps starting with 'git init',
etc.) I will make sure that your scenario is adequately tested in my patch series.


Cheers,

Philippe.


[1] https://lore.kernel.org/git/CAHsG2VT4YB_nf8PrEmrHwK-iY-AQo0VDcvXGVsf8cEYXws4nig@mail.gmail.com/
[2] https://lore.kernel.org/git/20200525094019.22padbzuk7ukr5uv@overdrive.tratt.net/

^ permalink raw reply	[flat|nested] 3+ messages in thread

end of thread, other threads:[~2021-01-14 16:46 UTC | newest]

Thread overview: 3+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2021-01-14  8:35 bug: checkout --recurse-submodules discard uncommited changes in submodule Kevin Bernard
2021-01-14 13:54 ` Philippe Blain
2021-01-14 16:40   ` Kevin Bernard

Code repositories for project(s) associated with this public inbox

	https://80x24.org/mirrors/git.git

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).