git@vger.kernel.org mailing list mirror (one of many)
 help / color / mirror / code / Atom feed
* Git-SVN on Cygwin: svn+ssh good, https awkward
@ 2009-04-23 16:31 Matthias Andree
  2009-04-23 16:40 ` Matthias Andree
                   ` (2 more replies)
  0 siblings, 3 replies; 9+ messages in thread
From: Matthias Andree @ 2009-04-23 16:31 UTC (permalink / raw)
  To: Eric Wong; +Cc: git

Hi Eric,

=== Short story ===

git-svn on Cygwin works well with svn+ssh://, but needs some fixes around  
tempfile and/or subprocess handling for https:// - please help.


=== Long story ===

First the good news: git-svn on Cygwin seems to work just fine with  
svn+ssh://... style Subversion URLs. I've been doing this for quite a  
while now with various repos, never had issues: I can init, clone, fetch  
rebase, dcommit just fine.

I'm looking for some help https:// access on Cygwin (Windows XP SP3  
underneath; more version info at the end of the message).

I've debugged it a little, but am not sufficiently acquainted with the  
git-svn Perl source to do changes myself; I hope I can describe the issue  
well enough that you (or somebody else) can suggest code changes to  
improve the experience.


0. PROBLEM/SYMPTOM:

login@mycomp ~/compnet2.gitsvn
$ git svn fetch
         M       file1
         A       file2
         A       file3
         A       file4
r15 = 70a56f818a057442e29161170e28c5df4b38a811 (git-svn)
Permission denied: Can't open  
'/cygdrive/c/DOKUME~1/login/LOKALE~1/Temp/tempfile.tmp': Permission denied  
at /usr/local/libexec/git-core/git-svn line 2540

which is, in my version:

   2537                  }
   2538                  $ed = SVN::Git::Fetcher->new($self);
   2539          }
+ 2540          unless ($self->ra->gs_do_update($last_rev, $rev, $self,  
$ed)) {
   2541                  die "SVN connection failed somewhere...\n";
   2542          }
   2543          $self->make_log_entry($rev, \@parents, $ed);


Apparently, we die when fetching a new revision for the 2nd time. I can  
restart git svn fetch and it will pick up where it left off. It will make  
progress, but is painful.

git svn rebase has the same issues. I haven't tested other operations such  
as dcommit yet.


1. WORKAROUND for fetch/rebase:

while ! git svn fetch ; do : ; done
git svn rebase


2. A SHORT LOG OF FINDING THE CAUSE:

$ perl -d /usr/local/libexec/git-core/git-svn fetch
...
main::(/usr/local/libexec/git-core/git-svn:10):
10:     $AUTHOR = 'Eric Wong <normalperson@yhbt.net>';
   DB<1> c 2540
Git::SVN::do_fetch(/usr/local/libexec/git-core/git-svn:2540):
2540:           unless ($self->ra->gs_do_update($last_rev, $rev, $self,  
$ed)) {
   DB<2> c 2540
...
r16 = d7829595222a013e703fe4377996984b52921789 (git-svn)
Git::SVN::do_fetch(/usr/local/libexec/git-core/git-svn:2540):
2540:           unless ($self->ra->gs_do_update($last_rev, $rev, $self,  
$ed)) {

Now watch this (we're immediately before the problem):

$ ls -l /cygdrive/c/DOKUME~1/login/LOKALE~1/Temp/
??????????? ? ?       ?       ?            ? tempfile.tmp
$ ls -l /cygdrive/c/DOKUME~1/login/LOKALE~1/Temp/tempfile.tmp
ls: cannot access /cygdrive/c/DOKUME~1/login/LOKALE~1/Temp/tempfile.tmp:  
No such file or directory

This zombie behaviour of trashing the file flags happens if Cygwin is  
asked to unlink() a file to which there are still open handles. It can't  
delete the file right away (due to the open handles), so it marks it  
delete-on-close instead, which then happens when the process(es) terminate.

$ ~/Desktop/handle.exe tempfile.tmp
...
git.exe            pid: 2236    62C:  
C:\DOKUME~1\mandree\LOKALE~1\Temp\tempfile.tmp
git.exe            pid: 5552    62C:  
C:\DOKUME~1\mandree\LOKALE~1\Temp\tempfile.tmp
git-hash-object.exe pid: 5320    62C:  
C:\DOKUME~1\mandree\LOKALE~1\Temp\tempfile.tmp

So we have three processes that have the file open. I cannot say if they  
mean the same file, or a different one, but this is the problem.

Here's the pstree dump to help identify the users of this file, with  
cmdline arguments:

perl,5660 -d -I... /usr/local/libexec/git-core/git-svn fetch
   |-git,2236  --batch
   |-git,5552 git-hash-object -w --stdin-paths
   |   `-git-hash-object,5320
   `-git,1128 update-index -z --index-info

Let's continue in the Perl debugger and crash:

   DB<3> c
Permission denied: Can't open  
'/cygdrive/c/DOKUME~1/login/LOKALE~1/Temp/tempfile.tmp': Permission denied  
at /usr/local/libexec/git-core/git-svn line 2540


Bottom line: the second time we hit this "unless  
($self->ra->gs_do_update($last_rev, $rev, $self, $ed))" line, we die  
because there are still processes that have the tempfile open and thus the  
former unlink() on the tempfile.tmp couldn't become effective.



3. UNDERLYING CYGWIN LIMITATIONS

<http://wiki.osdev.org/Cygwin_Issues#unlink.28.29> documents now  
(2009-04-23 16:15 UTC):
* unlink isn't atomic (as on other platforms also)
...
On cygwin unlink() is deferred to the end of the process, when unlink  
fails because of locks or delete on close (ERROR_SHARING_VIOLATION).

* unlink a file and subsequent creation of a new file in the same location  
is not supported.

* "delete on close" (unlinking an open file) is supported.


I can provide a short C program to demonstrate this behaviour.



4. FIX SUGGESTIONS AND QUESTIONS

Can we defer unlink()ing the tempfile until all handles to it are closed?

Can we let complete and wait for all processes that hold handles to the  
tempfile.tmp file before attempting to create a new copy?

Can we use unique tempfile names (timestamps, counter, random number  
generator) instead of the hardcoded "tempfile.tmp"? This is probably a  
good idea anyways to evade symlink attacks.


Either should work to fix the issue.


I'm willing to test patches.


5. VERSION INFORMATION:

Cygwin:
CYGWIN_NT-5.1 balu 1.5.25(0.156/4/2) 2008-06-12 19:34 i686 Cygwin

Git:
git version 1.6.3.rc1.51.gea0b7

Subversion:
svn, version 1.6.1 (r37116)
    compiled Apr 11 2009, 12:07:06

Copyright (C) 2000-2009 CollabNet.
Subversion is open source software, see http://subversion.tigris.org/
This product includes software developed by CollabNet  
(http://www.Collab.Net/).

The following repository access (RA) modules are available:

* ra_neon : Module for accessing a repository via WebDAV protocol using  
Neon.
   - handles 'http' scheme
   - handles 'https' scheme
* ra_svn : Module for accessing a repository using the svn network  
protocol.
   - with Cyrus SASL authentication
   - handles 'svn' scheme
* ra_local : Module for accessing a repository on local disk.
   - handles 'file' scheme
* ra_serf : Module for accessing a repository via WebDAV protocol using  
serf.
   - handles 'http' scheme
   - handles 'https' scheme



Thanks for any efforts to help!

-- 
Matthias Andree

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

* Re: Git-SVN on Cygwin: svn+ssh good, https awkward
  2009-04-23 16:31 Matthias Andree
@ 2009-04-23 16:40 ` Matthias Andree
  2009-04-23 17:58 ` Eric Blake
  2009-04-23 19:03 ` Eric Wong
  2 siblings, 0 replies; 9+ messages in thread
From: Matthias Andree @ 2009-04-23 16:40 UTC (permalink / raw)
  To: Eric Wong; +Cc: git

As a followup to my own message,

here's one more link to explain Cygwin/Windows limitations that seem to  
break git-svn here:
http://markmail.org/message/4o4yk6b4u6e44wyh

Thanks in advance for any help offered with git-svn.

-- 
Matthias Andree

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

* Re: Git-SVN on Cygwin: svn+ssh good, https awkward
  2009-04-23 16:31 Matthias Andree
  2009-04-23 16:40 ` Matthias Andree
@ 2009-04-23 17:58 ` Eric Blake
  2009-04-23 18:16   ` Matthias Andree
  2009-04-23 18:32   ` Matthias Andree
  2009-04-23 19:03 ` Eric Wong
  2 siblings, 2 replies; 9+ messages in thread
From: Eric Blake @ 2009-04-23 17:58 UTC (permalink / raw)
  To: git

Matthias Andree <matthias.andree <at> gmx.de> writes:

> 3. UNDERLYING CYGWIN LIMITATIONS
> 
> * unlink a file and subsequent creation of a new file in the same location  
> is not supported.
> 
> * "delete on close" (unlinking an open file) is supported.

These last two points are old information.  I would first recommend that you 
try running the new cygwin 1.7 (still in beta), where unlink() semantics have 
been greatly improved (you can actually unlink() an in-use file and recreate a 
new file by the same name while the old handle is still open).

http://cygwin.com/#beta-test

> 4. FIX SUGGESTIONS AND QUESTIONS
> 
> Can we defer unlink()ing the tempfile until all handles to it are closed?
> 
> Can we let complete and wait for all processes that hold handles to the  
> tempfile.tmp file before attempting to create a new copy?
> 
> Can we use unique tempfile names (timestamps, counter, random number  
> generator) instead of the hardcoded "tempfile.tmp"? This is probably a  
> good idea anyways to evade symlink attacks.

Although newer cygwin may fix your particular problem, this is not a bad 
suggestion for msysgit, so I suspect someone may be bothered enough by this to 
write a patch.  I, however, will not be the one doing it.

-- 
Eric Blake

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

* Re: Git-SVN on Cygwin: svn+ssh good, https awkward
  2009-04-23 17:58 ` Eric Blake
@ 2009-04-23 18:16   ` Matthias Andree
  2009-04-23 18:32   ` Matthias Andree
  1 sibling, 0 replies; 9+ messages in thread
From: Matthias Andree @ 2009-04-23 18:16 UTC (permalink / raw)
  To: Eric Blake, git

Am 23.04.2009, 19:58 Uhr, schrieb Eric Blake <ebb9@byu.net>:

>> Can we use unique tempfile names (timestamps, counter, random number
>> generator) instead of the hardcoded "tempfile.tmp"? This is probably a
>> good idea anyways to evade symlink attacks.
>
> Although newer cygwin may fix your particular problem, this is not a bad
> suggestion for msysgit, so I suspect someone may be bothered enough by  
> this to write a patch.  I, however, will not be the one doing it.

Hi Eric,

thanks for the hints and pointers to Cygwin 1.7 beta, however I'd suggest  
to make such changes upstream (i. e. in git.git) for the benefit of  
everybody else.

It also looks to me as though minor changes in the actual baseline Git  
code may be sufficient to get git-svn working on Cygwin 1.5 (stable)  
already. I'd prefer such a minor intrusion to hacking away on forks. :-)

Otherwise I'd start looking at how git-svn handles https:// and svn+ssh://  
methods differently from each other next week or so.

Looking forward to further insights.

-- 
Matthias Andree

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

* Re: Git-SVN on Cygwin: svn+ssh good, https awkward
  2009-04-23 17:58 ` Eric Blake
  2009-04-23 18:16   ` Matthias Andree
@ 2009-04-23 18:32   ` Matthias Andree
  1 sibling, 0 replies; 9+ messages in thread
From: Matthias Andree @ 2009-04-23 18:32 UTC (permalink / raw)
  To: Eric Blake, git

Am 23.04.2009, 19:58 Uhr, schrieb Eric Blake <ebb9@byu.net>:

> These last two points are old information.  I would first recommend that  
> you try running the new cygwin 1.7 (still in beta), where unlink()  
> semantics have been greatly improved (you can actually unlink() an  
> in-use file and recreate a new file by the same name while the old  
> handle is still open).
>
> http://cygwin.com/#beta-test

Indeed, with a fresh Cygwin 1.7 install, all this seems to work smoothly.  
I'd rather not bet on Cygwin release dates though, and can't judge on  
short notice what else will break with Cygwin 1.7... so I'd still  
appreciate help with fixing git-svn on Cygwin 1.5.

-- 
Matthias Andree

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

* Re: Git-SVN on Cygwin: svn+ssh good, https awkward
  2009-04-23 16:31 Matthias Andree
  2009-04-23 16:40 ` Matthias Andree
  2009-04-23 17:58 ` Eric Blake
@ 2009-04-23 19:03 ` Eric Wong
  2009-04-24 17:31   ` Matthias Andree
  2 siblings, 1 reply; 9+ messages in thread
From: Eric Wong @ 2009-04-23 19:03 UTC (permalink / raw)
  To: Matthias Andree; +Cc: Marcus Griep, git

Matthias Andree <matthias.andree@gmx.de> wrote:
> Hi Eric,
>
> === Short story ===
>
> git-svn on Cygwin works well with svn+ssh://, but needs some fixes around 
> tempfile and/or subprocess handling for https:// - please help.

Hi Matthias,

Marcus Griep did a lot of work for more efficiently handling of
tempfiles in Git.pm a few months ago, so maybe he has more insight into
how things work...

git-svn used to use IO::File->new_tmpfile() which was much simpler and
probably less prone to portability problems, but cycled through inodes
too quickly for Marcus (and probably some other people).


Speaking only for myself and not other contributors:

  I have no interest in dealing with crazy systems like Windows.  Ever.

  However, I'll gladly accept patches to make things work if they don't
  break existing use cases.

  Keep in mind that I'm an extremist.  I dislike Windows (and some other
  crazy software systems) to the point that I refuse to deal with them
  even in paid contracts and employment.

-- 
Eric Wong

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

* Re: Git-SVN on Cygwin: svn+ssh good, https awkward
  2009-04-23 19:03 ` Eric Wong
@ 2009-04-24 17:31   ` Matthias Andree
  0 siblings, 0 replies; 9+ messages in thread
From: Matthias Andree @ 2009-04-24 17:31 UTC (permalink / raw)
  To: Eric Wong; +Cc: Marcus Griep, git

Am 23.04.2009, 21:03 Uhr, schrieb Eric Wong <normalperson@yhbt.net>:

> Matthias Andree <matthias.andree@gmx.de> wrote:
>> Hi Eric,
>>
>> === Short story ===
>>
>> git-svn on Cygwin works well with svn+ssh://, but needs some fixes  
>> around
>> tempfile and/or subprocess handling for https:// - please help.
>
> Hi Matthias,
>
> Marcus Griep did a lot of work for more efficiently handling of
> tempfiles in Git.pm a few months ago, so maybe he has more insight into
> how things work...
>
> git-svn used to use IO::File->new_tmpfile() which was much simpler and
> probably less prone to portability problems, but cycled through inodes
> too quickly for Marcus (and probably some other people).

I debugged this a bit further, and the damage (i. e. removal of the  
tempfile) apparently happens
in $pool->clear; in line 4355. I single-stepped it, and the  
apr_pool_clear(...) is the culprit, it unlinks() the tempfile, making this  
location unusable.

The temp file is generated when the Reporter object is created through  
$self->do_update in line 4336.

It remains unclear to me who generates the non-unique filename (it's  
...\Temp\tempfile.tmp for me), I've not found the code that generates the  
file names.

Questions:

- How can I either make sure that the temporary file name for the reporter  
gets either a unique name (near line 4336, through SVN::Ra...)

- or is that the temp file truncated, rather than deleted, near line 4355  
(through SVN::Pool::clear)?

- Is there any way to influence how the SVN::Ra::Reporter obtains  
temporary files?
I seem to be unable to trace this down to the actual functions, but then  
again, my perlboot is rather holey...

Any help?


   4132  package Git::SVN::Ra;
   4133  use vars qw/@ISA $config_dir $_log_window_size/;
   4134  use strict;
   4135  use warnings;
   4136  my ($ra_invalid, $can_do_switch, %ignored_err, $RA);
   4137
   ....
   4324  sub gs_do_update {
   4325          my ($self, $rev_a, $rev_b, $gs, $editor) = @_;
   4326          my $new = ($rev_a == $rev_b);
   4327          my $path = $gs->{path};
   4328
   4329          if ($new && -e $gs->{index}) {
   4330                  unlink $gs->{index} or die
   4331                    "Couldn't unlink index: $gs->{index}: $!\n";
   4332          }
   4333          my $pool = SVN::Pool->new;
   4334          $editor->set_path_strip($path);
   4335          my (@pc) = split m#/#, $path;
: 4336          my $reporter = $self->do_update($rev_b, (@pc ? shift @pc :  
''),
   4337                                          1, $editor, $pool);
   4338          my @lock = $SVN::Core::VERSION ge '1.2.0' ? (undef) : ();
   4339
   4340          # Since we can't rely on svn_ra_reparent being available,  
we'll
   4341          # just have to do some magic with set_path to make it so
   4342          # we only want a partial path.
   4343          my $sp = '';
   4344          my $final = join('/', @pc);
   4345          while (@pc) {
   4346                  $reporter->set_path($sp, $rev_b, 0, @lock, $pool);
   4347                  $sp .= '/' if length $sp;
   4348                  $sp .= shift @pc;
   4349          }
   4350          die "BUG: '$sp' != '$final'\n" if ($sp ne $final);
   4351
   4352          $reporter->set_path($sp, $rev_a, $new, @lock, $pool);
   4353
   4354          $reporter->finish_report($pool);
: 4355          $pool->clear;
   4356          $editor->{git_commit_ok};
   4357  }

-- 
Matthias Andree

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

* Re: Git-SVN on Cygwin: svn+ssh good, https awkward
@ 2009-04-25 12:04 Gregory Petrosyan
  2009-05-12 13:47 ` Constantine Plotnikov
  0 siblings, 1 reply; 9+ messages in thread
From: Gregory Petrosyan @ 2009-04-25 12:04 UTC (permalink / raw)
  To: Matthias Andree; +Cc: git

> git-svn on Cygwin works well with svn+ssh://, but needs some fixes
> around tempfile and/or subprocess handling for https:// - please help.

This problem is triggered by updating Cygwin's SVN to 1.6. Downgrading
it back to 1.5 make git-svn work for me again.

	Gregory

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

* Re: Git-SVN on Cygwin: svn+ssh good, https awkward
  2009-04-25 12:04 Git-SVN on Cygwin: svn+ssh good, https awkward Gregory Petrosyan
@ 2009-05-12 13:47 ` Constantine Plotnikov
  0 siblings, 0 replies; 9+ messages in thread
From: Constantine Plotnikov @ 2009-05-12 13:47 UTC (permalink / raw)
  To: Matthias Andree, git

On Sat, Apr 25, 2009 at 4:04 PM, Gregory Petrosyan
<gregory.petrosyan@gmail.com> wrote:
>> git-svn on Cygwin works well with svn+ssh://, but needs some fixes
>> around tempfile and/or subprocess handling for https:// - please help.
>
> This problem is triggered by updating Cygwin's SVN to 1.6. Downgrading
> it back to 1.5 make git-svn work for me again.
>
1. The problem is also triggered when svn is accessed using file: protocol.
2. Downgrading does not help completely for file protocol. Instead of
the tempfile.tmp, there is now the same problem with report.tmp.

I tend to agree with Matthias Andree that real bug is using fixed file
names for temporary files. This could also cause interference when
several git-svn instances the same computer for different git
repositories.

Regards,
Constantine

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

end of thread, other threads:[~2009-05-12 13:47 UTC | newest]

Thread overview: 9+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2009-04-25 12:04 Git-SVN on Cygwin: svn+ssh good, https awkward Gregory Petrosyan
2009-05-12 13:47 ` Constantine Plotnikov
  -- strict thread matches above, loose matches on Subject: below --
2009-04-23 16:31 Matthias Andree
2009-04-23 16:40 ` Matthias Andree
2009-04-23 17:58 ` Eric Blake
2009-04-23 18:16   ` Matthias Andree
2009-04-23 18:32   ` Matthias Andree
2009-04-23 19:03 ` Eric Wong
2009-04-24 17:31   ` Matthias Andree

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).