Forcing apps to collect GC stats?

I spent a bit of time over the weekend trying to figure out how to force the RTS to collect GC statistics, but was unable to do so. I'm currently working on enriching criterion's ability to gather data, among which I'd like to see GC statistics. If I try to obtain GC stats using criterion when I'm not running the benchmark app with +RTS -T, I get an exception. Is there a way to allow criterion to forcibly enable stats collection? My efforts to do so have gotten me nowhere. It would be unfortunate if I had to tell users of criterion that they should always run with +RTS -T or add a -rtsopts clause, as they'll simply forget. And while I'm asking, why does GHC not simply collect GC stats by default? Collecting them seems to have zero cost, from what I can see? Thanks! Bryan.

Hey Bryan, Sorry for the delay. On 15/07/14 01:57, Bryan O'Sullivan wrote:
I spent a bit of time over the weekend trying to figure out how to force the RTS to collect GC statistics, but was unable to do so.
I'm currently working on enriching criterion's ability to gather data, among which I'd like to see GC statistics. If I try to obtain GC stats using criterion when I'm not running the benchmark app with +RTS -T, I get an exception.
Is there a way to allow criterion to forcibly enable stats collection? My efforts to do so have gotten me nowhere. It would be unfortunate if I had to tell users of criterion that they should always run with +RTS -T or add a -rtsopts clause, as they'll simply forget.
And while I'm asking, why does GHC not simply collect GC stats by default? Collecting them seems to have zero cost, from what I can see?
So you can do this in the same way as GHC. See https://phabricator.haskell.org/diffusion/GHC/browse/master/ghc/hschooks.c;6... Which is imported into Haskell like this: https://phabricator.haskell.org/diffusion/GHC/browse/master/ghc/Main.hs;6fa6... I'm not sure why it's marked "safe", but it doesn't hurt. This API is kind-of public, in the sense that we deliberately expose it via the Rts.h header, and I'll try not to break it gratuitously. Cheers, Simon

Interesting.
I suppose ekg could also (ab)use this.
Johan?
-Edward
On Thu, Jul 31, 2014 at 5:51 AM, Simon Marlow
Hey Bryan,
Sorry for the delay.
On 15/07/14 01:57, Bryan O'Sullivan wrote:
I spent a bit of time over the weekend trying to figure out how to force the RTS to collect GC statistics, but was unable to do so.
I'm currently working on enriching criterion's ability to gather data, among which I'd like to see GC statistics. If I try to obtain GC stats using criterion when I'm not running the benchmark app with +RTS -T, I get an exception.
Is there a way to allow criterion to forcibly enable stats collection? My efforts to do so have gotten me nowhere. It would be unfortunate if I had to tell users of criterion that they should always run with +RTS -T or add a -rtsopts clause, as they'll simply forget.
And while I'm asking, why does GHC not simply collect GC stats by default? Collecting them seems to have zero cost, from what I can see?
So you can do this in the same way as GHC. See
https://phabricator.haskell.org/diffusion/GHC/browse/ master/ghc/hschooks.c;6fa6caad0cb4ba99b2c0b444b0583190e743dd63$18-28
Which is imported into Haskell like this:
https://phabricator.haskell.org/diffusion/GHC/browse/master/ghc/Main.hs; 6fa6caad0cb4ba99b2c0b444b0583190e743dd63$847-848
I'm not sure why it's marked "safe", but it doesn't hurt.
This API is kind-of public, in the sense that we deliberately expose it via the Rts.h header, and I'll try not to break it gratuitously.
Cheers, Simon
_______________________________________________ ghc-devs mailing list ghc-devs@haskell.org http://www.haskell.org/mailman/listinfo/ghc-devs

Indeed. I filed a bug earlier today to make use of this.
On Thu, Jul 31, 2014 at 6:15 PM, Edward Kmett
Interesting.
I suppose ekg could also (ab)use this.
Johan?
-Edward
On Thu, Jul 31, 2014 at 5:51 AM, Simon Marlow
wrote: Hey Bryan,
Sorry for the delay.
On 15/07/14 01:57, Bryan O'Sullivan wrote:
I spent a bit of time over the weekend trying to figure out how to force the RTS to collect GC statistics, but was unable to do so.
I'm currently working on enriching criterion's ability to gather data, among which I'd like to see GC statistics. If I try to obtain GC stats using criterion when I'm not running the benchmark app with +RTS -T, I get an exception.
Is there a way to allow criterion to forcibly enable stats collection? My efforts to do so have gotten me nowhere. It would be unfortunate if I had to tell users of criterion that they should always run with +RTS -T or add a -rtsopts clause, as they'll simply forget.
And while I'm asking, why does GHC not simply collect GC stats by default? Collecting them seems to have zero cost, from what I can see?
So you can do this in the same way as GHC. See
https://phabricator.haskell.org/diffusion/GHC/browse/master/ghc/hschooks.c;6...
Which is imported into Haskell like this:
https://phabricator.haskell.org/diffusion/GHC/browse/master/ghc/Main.hs;6fa6...
I'm not sure why it's marked "safe", but it doesn't hurt.
This API is kind-of public, in the sense that we deliberately expose it via the Rts.h header, and I'll try not to break it gratuitously.
Cheers, Simon
_______________________________________________ ghc-devs mailing list ghc-devs@haskell.org http://www.haskell.org/mailman/listinfo/ghc-devs

The 'safe' mark was just an oversight from me - I don't really think
it matters, considering it's only called once at startup anyway.
Similarly I imagine the oversight is negligible in the Criterion or
ekg case.
And also, take note the conditional is very specific; you want
COLLECT_GC_STATS only when NO_GC_STATS is the current setting - if you
unconditionally force COLLECT_GC_STATS, then things like `+RTS
-sstderr -RTS` will no longer work. I mention this because I messed it
up originally. :)
Given we already use this in GHC, and other users want it, it's
probably reasonable to put such an interface in `base` somewhere, e.g.
data GCStatisticsOption = NoStatistics | CollectStatistics |
VerboseStatistics ...
getGcStatistics :: IO GcStatisticsOption
setGcStatistics :: GcStatisticsOption -> IO ()
modifyGcStatistics :: (GcStatisticsOption -> GcStatisticsOption) -> IO ()
or something like that.
The special case inside GHC could then be handled with such an API I suppose.
On Thu, Jul 31, 2014 at 11:41 AM, Johan Tibell
Indeed. I filed a bug earlier today to make use of this.
On Thu, Jul 31, 2014 at 6:15 PM, Edward Kmett
wrote: Interesting.
I suppose ekg could also (ab)use this.
Johan?
-Edward
On Thu, Jul 31, 2014 at 5:51 AM, Simon Marlow
wrote: Hey Bryan,
Sorry for the delay.
On 15/07/14 01:57, Bryan O'Sullivan wrote:
I spent a bit of time over the weekend trying to figure out how to force the RTS to collect GC statistics, but was unable to do so.
I'm currently working on enriching criterion's ability to gather data, among which I'd like to see GC statistics. If I try to obtain GC stats using criterion when I'm not running the benchmark app with +RTS -T, I get an exception.
Is there a way to allow criterion to forcibly enable stats collection? My efforts to do so have gotten me nowhere. It would be unfortunate if I had to tell users of criterion that they should always run with +RTS -T or add a -rtsopts clause, as they'll simply forget.
And while I'm asking, why does GHC not simply collect GC stats by default? Collecting them seems to have zero cost, from what I can see?
So you can do this in the same way as GHC. See
https://phabricator.haskell.org/diffusion/GHC/browse/master/ghc/hschooks.c;6...
Which is imported into Haskell like this:
https://phabricator.haskell.org/diffusion/GHC/browse/master/ghc/Main.hs;6fa6...
I'm not sure why it's marked "safe", but it doesn't hurt.
This API is kind-of public, in the sense that we deliberately expose it via the Rts.h header, and I'll try not to break it gratuitously.
Cheers, Simon
_______________________________________________ ghc-devs mailing list ghc-devs@haskell.org http://www.haskell.org/mailman/listinfo/ghc-devs
_______________________________________________ ghc-devs mailing list ghc-devs@haskell.org http://www.haskell.org/mailman/listinfo/ghc-devs
-- Regards, Austin Seipp, Haskell Consultant Well-Typed LLP, http://www.well-typed.com/

We already have GHC.Stats. It would be nice if it was put there.
On Thu, Jul 31, 2014 at 6:55 PM, Austin Seipp
The 'safe' mark was just an oversight from me - I don't really think it matters, considering it's only called once at startup anyway. Similarly I imagine the oversight is negligible in the Criterion or ekg case.
And also, take note the conditional is very specific; you want COLLECT_GC_STATS only when NO_GC_STATS is the current setting - if you unconditionally force COLLECT_GC_STATS, then things like `+RTS -sstderr -RTS` will no longer work. I mention this because I messed it up originally. :)
Given we already use this in GHC, and other users want it, it's probably reasonable to put such an interface in `base` somewhere, e.g.
data GCStatisticsOption = NoStatistics | CollectStatistics | VerboseStatistics ...
getGcStatistics :: IO GcStatisticsOption setGcStatistics :: GcStatisticsOption -> IO () modifyGcStatistics :: (GcStatisticsOption -> GcStatisticsOption) -> IO ()
or something like that.
The special case inside GHC could then be handled with such an API I suppose.
On Thu, Jul 31, 2014 at 11:41 AM, Johan Tibell
wrote: Indeed. I filed a bug earlier today to make use of this.
On Thu, Jul 31, 2014 at 6:15 PM, Edward Kmett
wrote: Interesting.
I suppose ekg could also (ab)use this.
Johan?
-Edward
On Thu, Jul 31, 2014 at 5:51 AM, Simon Marlow
wrote: Hey Bryan,
Sorry for the delay.
On 15/07/14 01:57, Bryan O'Sullivan wrote:
I spent a bit of time over the weekend trying to figure out how to force the RTS to collect GC statistics, but was unable to do so.
I'm currently working on enriching criterion's ability to gather data, among which I'd like to see GC statistics. If I try to obtain GC stats using criterion when I'm not running the benchmark app with +RTS -T, I get an exception.
Is there a way to allow criterion to forcibly enable stats collection? My efforts to do so have gotten me nowhere. It would be unfortunate if I had to tell users of criterion that they should always run with +RTS -T or add a -rtsopts clause, as they'll simply forget.
And while I'm asking, why does GHC not simply collect GC stats by default? Collecting them seems to have zero cost, from what I can see?
So you can do this in the same way as GHC. See
https://phabricator.haskell.org/diffusion/GHC/browse/master/ghc/hschooks.c;6...
Which is imported into Haskell like this:
https://phabricator.haskell.org/diffusion/GHC/browse/master/ghc/Main.hs;6fa6...
I'm not sure why it's marked "safe", but it doesn't hurt.
This API is kind-of public, in the sense that we deliberately expose it via the Rts.h header, and I'll try not to break it gratuitously.
Cheers, Simon
_______________________________________________ ghc-devs mailing list ghc-devs@haskell.org http://www.haskell.org/mailman/listinfo/ghc-devs
_______________________________________________ ghc-devs mailing list ghc-devs@haskell.org http://www.haskell.org/mailman/listinfo/ghc-devs
-- Regards,
Austin Seipp, Haskell Consultant Well-Typed LLP, http://www.well-typed.com/

On Thu, Jul 31, 2014 at 6:55 PM, Austin Seipp
And also, take note the conditional is very specific; you want COLLECT_GC_STATS only when NO_GC_STATS is the current setting - if you unconditionally force COLLECT_GC_STATS, then things like `+RTS -sstderr -RTS` will no longer work. I mention this because I messed it up originally. :)
Could you expand a bit on this. I want to programtically set whatever flags/settings would be set if the user passed +RTS -T on the command line.

Right, so if you look in ./includes/rts/Flags.h, you'll see a set of
different options for the GC stats:
#define NO_GC_STATS 0
#define COLLECT_GC_STATS 1
#define ONELINE_GC_STATS 2
#define SUMMARY_GC_STATS 3
#define VERBOSE_GC_STATS 4
By default the RTS sets the stats flag to NO_GC_STATS, which does
nothing. Note that *every* flag here (except NO_GC_STATS) implies the
collection of GC statistics; it's just a matter of what's displayed to
the user (if anything).
There are several RTS options, each of which correspond to one of the
above (see RtsFlags.c):
`+RTS -T` corresponds to COLLECT_GC_STATS
`+RTS -S` corresponds to VERBOSE_GC_STATS
`+RTS -s` corresponds to SUMMARY_GC_STATS
`+RTS -t` corresponds to ONELINE_GC_STATS
These flags are parsed at startup before any Haskell code is executed
obviously. So here's the problem: let's say you unconditionally force
the statistics flag to be COLLECT_GC_STATS from Haskell-land - if I
started my application with `+RTS -s`, then you've changed the
statistics reporting from SUMMARY_GC_STATS, which means that when the
program terminates, no statistics about the program will be displayed!
Which will break end-user expectations.
So the rule of thumb is: all of the above flags enforce the collection
of statistics, and you *only* want to set the flag to COLLECT_GC_STATS
*iff* it is currently set to NO_GC_STATS. In all other cases, GC
statistics will already be enabled for the runtime, so you don't need
to do anything.
Hope that explains it well enough.
On Thu, Jul 31, 2014 at 12:17 PM, Johan Tibell
On Thu, Jul 31, 2014 at 6:55 PM, Austin Seipp
wrote: And also, take note the conditional is very specific; you want COLLECT_GC_STATS only when NO_GC_STATS is the current setting - if you unconditionally force COLLECT_GC_STATS, then things like `+RTS -sstderr -RTS` will no longer work. I mention this because I messed it up originally. :)
Could you expand a bit on this. I want to programtically set whatever flags/settings would be set if the user passed +RTS -T on the command line.
-- Regards, Austin Seipp, Haskell Consultant Well-Typed LLP, http://www.well-typed.com/
participants (5)
-
Austin Seipp
-
Bryan O'Sullivan
-
Edward Kmett
-
Johan Tibell
-
Simon Marlow