All of lore.kernel.org
 help / color / mirror / Atom feed
From: Johannes Sixt <j6t@kdbg.org>
To: Junio C Hamano <gitster@pobox.com>
Cc: "Shawn O. Pearce" <spearce@spearce.org>, git@vger.kernel.org
Subject: Re: [PATCH 7/6] Enable threaded async procedures whenever pthreads is available
Date: Wed, 17 Mar 2010 22:28:18 +0100	[thread overview]
Message-ID: <201003172228.18939.j6t@kdbg.org> (raw)
In-Reply-To: <7v7hpjq0aw.fsf@alter.siamese.dyndns.org>

On Mittwoch, 10. März 2010, Junio C Hamano wrote:
> Johannes Sixt <j6t@kdbg.org> writes:
> > On Samstag, 6. März 2010, Shawn O. Pearce wrote:
> >> I'm in favor of that.  If we have threaded delta search enabled,
> >> we probably can also run these async procedures in a POSIX thread
> >> rather than forking off a child.
> >
> > OK. The patch could look like this.
>
> Will queue in 'pu', but as Shawn said, we should probably give another
> closer look at the callees that are started with this interface before
> moving forward.

So here is my analysis.

There are currently these users of the async infrastructure:

builtin-fetch-pack.c
builtin-receive-pack.c
builtin-send-pack.c
convert.c
remote-curl.c
upload_pack.c

The list below shows all functions that read or write potentially global state 
that are called from the async procedure (except for upload_pack.c, see 
below). I ignored all functions that do not depend on global state, like 
strcmp, memcpy, sprintf, strerror, etc.

----------
remote-curl.c:write_discovery():
  write
  close

These two functions only communicate with the parent. This is absolutely 
thread-safe.

----------
builtin-fetch-pack.c:sideband_demux() and
builtin-send-pack.c:sideband_demux() are virtually identical, and
builtin-receive-pack.c:copy_to_sideband() has the same footprint:
  getenv
  read
  die_errno
  die
  write
  close

Again, the functions only communicate with the parent and nothing else. getenv 
could be a problem if the parent called setenv, but it doesn't. die (and 
die_errno) are overridden in the threaded version, and are uncritical. In 
total, this user is thread-safe.

(This is getenv("TERM") from recv_sideband, btw.)

----------
convert.c:filter_buffer()
  pipe
  close
  getenv
  fork
  read
  write
  fprintf
  waitpid

if GIT_TRACE is set:
  xrealloc
  die
  free

This one is less trivial. It calls start_command+finish_command from the async 
procedure. The parent calls
  read()
  xrealloc() (via strbuf_read())
  error()
(and nothing else) between start_async() and finish_async().

As long as GIT_TRACE is not set, we are safe, because the async procedure 
carefully releases all global resources that it allocated, and the parent is 
looking in the other direction while it does os. Even if GIT_TRACE is set, 
xrealloc() in the parent and the async procedure cannot be called 
simultanously because the procedure calls it only before it begins writing 
output, and the parent only after it received this output.

On Windows, the situation is slightly different, because we always call into 
xmalloc() during start_command, but again we do so before the output is 
produced.

I think we are safe in all cases.

----------
upload_pack:create_pack_file(): This user is different because it calls into 
the revision walker in the async procedure, which definitely affects global 
state. Therefore, here is the list of functions called by the parent until it 
exits:
  pipe
  close
  getenv
  fork
  read
  write
  fprintf
  waitpid
  alarm
  die
  die_errno
  pthread_join / waitpid

if GIT_TRACE is set:
  xrealloc
  die
  free

It also calls start_command+finish_command. If GIT_TRACE is set, we are less 
safe because this time, xrealloc() can be called simultanously with pack 
functions while the revision walker is operating.

But as long as GIT_TRACE is not set, it looks like we are safe, though I 
haven't looked through the revision walker whether it messes with alarms or 
the environment.

One aspect is, though, that the async procedure is used *only* for a shallow 
clone, and the reason that it is used is that pack-objects (or the way it is 
called from upload-pack?) has not been taught to produce a pack for a shallow 
clone.

This concludes my analysis.

-- Hannes

  parent reply	other threads:[~2010-03-17 21:30 UTC|newest]

Thread overview: 16+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2010-03-06 15:40 [PATCH 0/6] Pass t5530 on Windows Johannes Sixt
2010-03-06 20:12 ` Junio C Hamano
2010-03-06 21:50   ` Shawn O. Pearce
2010-03-09 20:00     ` [PATCH 7/6] Enable threaded async procedures whenever pthreads is available Johannes Sixt
2010-03-09 23:43       ` Shawn O. Pearce
2010-03-10 22:28       ` Junio C Hamano
2010-03-11 19:53         ` Johannes Sixt
2010-03-12  5:56           ` Junio C Hamano
2010-03-17 21:28         ` Johannes Sixt [this message]
2010-03-17 22:19           ` Junio C Hamano
2010-03-23  8:15           ` Fredrik Kuivinen
2010-03-23 20:19             ` Johannes Sixt
2010-03-23 20:25               ` Johannes Sixt
2010-03-23 20:44                 ` Junio C Hamano
2010-03-23 21:09                   ` Johannes Sixt
2010-03-23 21:42               ` Fredrik Kuivinen

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=201003172228.18939.j6t@kdbg.org \
    --to=j6t@kdbg.org \
    --cc=git@vger.kernel.org \
    --cc=gitster@pobox.com \
    --cc=spearce@spearce.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.