[GHC] #10613: Mechanism for checking that we only enter single-entry thunks once

GHC ghc-devs at haskell.org
Mon Jan 25 16:01:12 UTC 2016


#10613: Mechanism for checking that we only enter single-entry thunks once
-------------------------------------+-------------------------------------
        Reporter:  bgamari           |                Owner:
            Type:  feature request   |               Status:  new
        Priority:  normal            |            Milestone:
       Component:  Compiler          |              Version:  7.10.1
      Resolution:                    |             Keywords:
Operating System:  Unknown/Multiple  |         Architecture:
                                     |  Unknown/Multiple
 Type of failure:  Other             |            Test Case:
      Blocked By:                    |             Blocking:
 Related Tickets:                    |  Differential Rev(s):
       Wiki Page:                    |
-------------------------------------+-------------------------------------

Comment (by nomeata):

 I have made initial, still hackish, progress. After a few iterations I can
 now run all of nofib with my counting indirections and it does not
 segfault any more (phew).

 Here is a report from `integrate`, note the new columns `#Alloc`, `Single`
 and `Multpile`.
 {{{
     Entries      Alloc    Alloc'd     #Alloc     Single   Multiple  Non-
 void Arguments      STG Name
 --------------------------------------------------------------------------------
       50000     800000          0          0          0          0   1 D
 main at main:Main.main6{v r7sX}
           0          0    8000000     500000          0          0   0
 sat_s7u6{v} (main at main:Main) (thk) in r7sQ
           0          0    8000000     500000          0          0   0
 sat_s7u3{v} (main at main:Main) (thk) in r7sQ
           0          0    8000000     500000          0          0   0
 sat_s7tZ{v} (main at main:Main) (thk) in r7sQ
           0          0    8000000     500000          0          0   0
 sat_s7tU{v} (main at main:Main) (thk) in r7sQ
           0          0    8000000     500000          0          0   0
 sat_s7tP{v} (main at main:Main) (thk) in r7sQ
           0          0    8000000     500000          0          0   0
 sat_s7tK{v} (main at main:Main) (thk) in r7sQ
           0          0    8000000     500000          0          0   0
 sat_s7tF{v} (main at main:Main) (thk) in r7sQ
           0          0    8000000     500000          0          0   0
 sat_s7tA{v} (main at main:Main) (thk) in r7sQ
     4050000          0    7200000     450000          0     450000   1 D
 sat_s7uz{v} (main at main:Main) in s7uB
           0          0    8000000     500000          0          0   0
 sat_s7tu{v} (main at main:Main) (thk) in r7sQ
      500000   72000000          0          0          0          0   3 dd>
 main at main:Main.$wintegrate1D{v r7sQ}
      450000   32400000     800000      50000          0      50000   1 D
 sat_s7uB{v} (main at main:Main) in r7t3
       50000     800000          0          0          0          0   1 D
 main at main:Main.main10{v r7t2}
       50000    3600000          0          0          0          0   2 DD
 main at main:Main.main11{v r7t3}
       50000          0          0          0          0          0   4
 LLid                 main at main:Main.$wgo{v r7t4}
           2          0         24          1          1          0   0
 sat_s7vH{v} (main at main:Main) (thk) in r7sR
           1         64          0          0          0          0   0
 main at main:Main.main1{v r7sR}
           1          0          0          0          0          0   0
 main at main:Main.main15{v r7t9}
           1          0          0          0          0          0   0
 main at main::Main.main{v 01D}
 }}}

 It is still buggy (or not fully understood), e.g.:
  * I thought I only enabled it for thunks, but it also seems to be present
 for two functions, and only there count multiple entries... Weird.
  * Also, these 500000-times allocated thunks are not really unused, are
 they?.
  * Two total entries for a thunk (`sat_s7vH`) that has been allocated once
 and called once? Maybe there was a heap check inbetween?

 But still: You can tell that `sat_s7uB` has been allocated 50000 and each
 instance is called 9 times – this matches the 9-element-list in the code.

 The implementation uses a new closure type that carries a pointer to a
 ticky counter struct, and its own little counter:
 {{{
 typedef struct {
     StgHeader   header;
     StgClosure *indirectee;
     const void *ent_counter; // A StgEntCounter
     StgWord     entries;
 } StgIndCounting;
 }}}
 Upon entry, this increments the private counter, and if it does so the
 first time, increases `Single`, and on the second time decreases `Single`
 and increases `Multiple`. Otherwise, it passes `R1` onto the indirectee,
 preserving the tag.

--
Ticket URL: <http://ghc.haskell.org/trac/ghc/ticket/10613#comment:13>
GHC <http://www.haskell.org/ghc/>
The Glasgow Haskell Compiler


More information about the ghc-tickets mailing list