[GHC] #13825: Allow multiple constructor fields occupy the same word

#13825: Allow multiple constructor fields occupy the same word -------------------------------------+------------------------------------- Reporter: michalt | Owner: (none) Type: bug | Status: new Priority: normal | Milestone: Component: Compiler | Version: 8.0.1 Keywords: | Operating System: Unknown/Multiple Architecture: | Type of failure: None/Unknown Unknown/Multiple | Test Case: | Blocked By: Blocking: | Related Tickets: Differential Rev(s): | Wiki Page: -------------------------------------+------------------------------------- The main goal is to reduce the overhead of things like: {{{#!hs data Bloated = Bloated {-# UNPACK #-} !Word8 {-# UNPACK #-} !Int8 {-# UNPACK #-} !Bool }}} Assuming 64-bit architecture, currently those fields will take 8 bytes each! So for this example we'd need: 8 bytes for header + 3 * 8 bytes for fields = 32 bytes. But we should be able to pack the fields into a single word (a word is 8 bytes and each field really only needs 1 byte) for a total of 16 bytes (8 bytes header + 8 bytes for fields, with the 5 bytes being "overhead" due to heap alignment). My understanding is that we need a few things to make this happen: - Ability to refer to fields that are packed into a single word (currently everything in GHC assumes that each field occupies a single word). Simon Marlow started working on this in https://phabricator.haskell.org/D38 - Introduce primitives like `Word8#`, `Int8#`, ... (currently `WordX` and `IntX` are defined as wrappers of `Word#` and `Int#` respectively) and change `WordX`/`IntX` definitions to use those primitives. - Figure out what to do with `Bool` (should it be just `Word8#`? should we have `Bool#`?) and change its definition (using pattern synonyms for `True`/`False`) Some additional info: - Thread on ghc-devs: https://mail.haskell.org/pipermail/ghc- devs/2017-June/014304.html -- Ticket URL: http://ghc.haskell.org/trac/ghc/ticket/13825 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler

#13825: Allow multiple constructor fields occupy the same word -------------------------------------+------------------------------------- Reporter: michalt | Owner: michalt Type: bug | Status: new Priority: normal | Milestone: Component: Compiler | Version: 8.0.1 Resolution: | Keywords: Operating System: Unknown/Multiple | Architecture: | Unknown/Multiple Type of failure: None/Unknown | Test Case: Blocked By: | Blocking: Related Tickets: | Differential Rev(s): Wiki Page: | -------------------------------------+------------------------------------- Changes (by michalt): * owner: (none) => michalt -- Ticket URL: http://ghc.haskell.org/trac/ghc/ticket/13825#comment:1 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler

#13825: Allow multiple constructor fields occupy the same word -------------------------------------+------------------------------------- Reporter: michalt | Owner: michalt Type: bug | Status: new Priority: normal | Milestone: 8.4.1 Component: Compiler | Version: 8.0.1 Resolution: | Keywords: Operating System: Unknown/Multiple | Architecture: | Unknown/Multiple Type of failure: None/Unknown | Test Case: Blocked By: | Blocking: Related Tickets: #605 | Differential Rev(s): Wiki Page: | -------------------------------------+------------------------------------- Changes (by dfeuer): * related: => #605 * milestone: => 8.4.1 Comment: `Bool` isn't special, and shouldn't be. It's just an enumeration type, and should remain one. #605 suggests representing unboxed enumeration types as `Int#`. It seems that to get what you want, you'd want to do something like what `Binary` and `Cereal` do with sum types, using a different number of bits depending on the number of constructors. One big question is whether and how to support sub-byte-sized fields. It is possible, presumably at some performance cost, to pack a `Bool` (for instance) into a single bit. Is the cost enough to worry about? -- Ticket URL: http://ghc.haskell.org/trac/ghc/ticket/13825#comment:2 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler

#13825: Allow multiple constructor fields occupy the same word -------------------------------------+------------------------------------- Reporter: michalt | Owner: michalt Type: bug | Status: new Priority: normal | Milestone: 8.4.1 Component: Compiler | Version: 8.0.1 Resolution: | Keywords: Operating System: Unknown/Multiple | Architecture: | Unknown/Multiple Type of failure: None/Unknown | Test Case: Blocked By: | Blocking: Related Tickets: #605 | Differential Rev(s): Wiki Page: | -------------------------------------+------------------------------------- Changes (by dfeuer): * cc: dfeuer (added) -- Ticket URL: http://ghc.haskell.org/trac/ghc/ticket/13825#comment:3 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler

#13825: Allow multiple constructor fields occupy the same word -------------------------------------+------------------------------------- Reporter: michalt | Owner: michalt Type: bug | Status: new Priority: normal | Milestone: 8.4.1 Component: Compiler | Version: 8.0.1 Resolution: | Keywords: Operating System: Unknown/Multiple | Architecture: | Unknown/Multiple Type of failure: None/Unknown | Test Case: Blocked By: | Blocking: Related Tickets: #605 | Differential Rev(s): Wiki Page: | -------------------------------------+------------------------------------- Changes (by maoe): * cc: maoe (added) -- Ticket URL: http://ghc.haskell.org/trac/ghc/ticket/13825#comment:4 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler

#13825: Allow multiple constructor fields occupy the same word -------------------------------------+------------------------------------- Reporter: michalt | Owner: michalt Type: bug | Status: new Priority: normal | Milestone: 8.4.1 Component: Compiler | Version: 8.0.1 Resolution: | Keywords: Operating System: Unknown/Multiple | Architecture: | Unknown/Multiple Type of failure: None/Unknown | Test Case: Blocked By: | Blocking: Related Tickets: #605 | Differential Rev(s): Wiki Page: | -------------------------------------+------------------------------------- Comment (by michalt): @dfeuer: Thanks for linking #605 - sounds like a much better solution for `Bool` :) -- Ticket URL: http://ghc.haskell.org/trac/ghc/ticket/13825#comment:5 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler

#13825: Allow multiple constructor fields occupy the same word -------------------------------------+------------------------------------- Reporter: michalt | Owner: michalt Type: bug | Status: new Priority: normal | Milestone: 8.4.1 Component: Compiler | Version: 8.0.1 Resolution: | Keywords: Operating System: Unknown/Multiple | Architecture: | Unknown/Multiple Type of failure: None/Unknown | Test Case: Blocked By: | Blocking: Related Tickets: #605 | Differential Rev(s): Wiki Page: | -------------------------------------+------------------------------------- Description changed by michalt: @@ -22,3 +22,3 @@ - - Figure out what to do with `Bool` (should it be just `Word8#`? should we - have `Bool#`?) and change its definition (using pattern synonyms for - `True`/`False`) + - ~~Figure out what to do with `Bool` (should it be just `Word8#`? should + we have `Bool#`?) and change its definition (using pattern synonyms for + `True`/`False`)~~ `Bool` should be handled by #605 (see comment:2) New description: The main goal is to reduce the overhead of things like: {{{#!hs data Bloated = Bloated {-# UNPACK #-} !Word8 {-# UNPACK #-} !Int8 {-# UNPACK #-} !Bool }}} Assuming 64-bit architecture, currently those fields will take 8 bytes each! So for this example we'd need: 8 bytes for header + 3 * 8 bytes for fields = 32 bytes. But we should be able to pack the fields into a single word (a word is 8 bytes and each field really only needs 1 byte) for a total of 16 bytes (8 bytes header + 8 bytes for fields, with the 5 bytes being "overhead" due to heap alignment). My understanding is that we need a few things to make this happen: - Ability to refer to fields that are packed into a single word (currently everything in GHC assumes that each field occupies a single word). Simon Marlow started working on this in https://phabricator.haskell.org/D38 - Introduce primitives like `Word8#`, `Int8#`, ... (currently `WordX` and `IntX` are defined as wrappers of `Word#` and `Int#` respectively) and change `WordX`/`IntX` definitions to use those primitives. - ~~Figure out what to do with `Bool` (should it be just `Word8#`? should we have `Bool#`?) and change its definition (using pattern synonyms for `True`/`False`)~~ `Bool` should be handled by #605 (see comment:2) Some additional info: - Thread on ghc-devs: https://mail.haskell.org/pipermail/ghc- devs/2017-June/014304.html -- -- Ticket URL: http://ghc.haskell.org/trac/ghc/ticket/13825#comment:6 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler

#13825: Allow multiple constructor fields occupy the same word
-------------------------------------+-------------------------------------
Reporter: michalt | Owner: michalt
Type: bug | Status: new
Priority: normal | Milestone: 8.4.1
Component: Compiler | Version: 8.0.1
Resolution: | Keywords:
Operating System: Unknown/Multiple | Architecture:
| Unknown/Multiple
Type of failure: None/Unknown | Test Case:
Blocked By: | Blocking:
Related Tickets: #605 | Differential Rev(s):
Wiki Page: |
-------------------------------------+-------------------------------------
Comment (by Ben Gamari

#13825: Allow multiple constructor fields occupy the same word
-------------------------------------+-------------------------------------
Reporter: michalt | Owner: michalt
Type: bug | Status: new
Priority: normal | Milestone: 8.4.1
Component: Compiler | Version: 8.0.1
Resolution: | Keywords:
Operating System: Unknown/Multiple | Architecture:
| Unknown/Multiple
Type of failure: None/Unknown | Test Case:
Blocked By: | Blocking:
Related Tickets: #605 | Differential Rev(s):
Wiki Page: |
-------------------------------------+-------------------------------------
Comment (by Ben Gamari

#13825: Allow multiple constructor fields occupy the same word
-------------------------------------+-------------------------------------
Reporter: michalt | Owner: michalt
Type: bug | Status: new
Priority: normal | Milestone: 8.4.1
Component: Compiler | Version: 8.0.1
Resolution: | Keywords:
Operating System: Unknown/Multiple | Architecture:
| Unknown/Multiple
Type of failure: None/Unknown | Test Case:
Blocked By: | Blocking:
Related Tickets: #605 | Differential Rev(s):
Wiki Page: |
-------------------------------------+-------------------------------------
Comment (by Ben Gamari

#13825: Allow multiple constructor fields occupy the same word
-------------------------------------+-------------------------------------
Reporter: michalt | Owner: michalt
Type: bug | Status: new
Priority: normal | Milestone: 8.4.1
Component: Compiler | Version: 8.0.1
Resolution: | Keywords:
Operating System: Unknown/Multiple | Architecture:
| Unknown/Multiple
Type of failure: None/Unknown | Test Case:
Blocked By: | Blocking:
Related Tickets: #605 | Differential Rev(s):
Wiki Page: |
-------------------------------------+-------------------------------------
Comment (by Ben Gamari

#13825: Allow multiple constructor fields occupy the same word -------------------------------------+------------------------------------- Reporter: michalt | Owner: michalt Type: bug | Status: closed Priority: normal | Milestone: 8.4.1 Component: Compiler | Version: 8.0.1 Resolution: fixed | Keywords: Operating System: Unknown/Multiple | Architecture: | Unknown/Multiple Type of failure: None/Unknown | Test Case: Blocked By: | Blocking: Related Tickets: #605 | Differential Rev(s): Wiki Page: | -------------------------------------+------------------------------------- Changes (by bgamari): * status: new => closed * resolution: => fixed -- Ticket URL: http://ghc.haskell.org/trac/ghc/ticket/13825#comment:11 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler
participants (1)
-
GHC