Skip to content

GitLab

  • Projects
  • Groups
  • Snippets
  • Help
    • Loading...
  • Help
    • Help
    • Support
    • Community forum
    • Submit feedback
  • Sign in / Register
GHC
GHC
  • Project overview
    • Project overview
    • Details
    • Activity
    • Releases
  • Repository
    • Repository
    • Files
    • Commits
    • Branches
    • Tags
    • Contributors
    • Graph
    • Compare
    • Locked Files
  • Issues 4,243
    • Issues 4,243
    • List
    • Boards
    • Labels
    • Service Desk
    • Milestones
    • Iterations
  • Merge Requests 387
    • Merge Requests 387
  • Requirements
    • Requirements
    • List
  • CI / CD
    • CI / CD
    • Pipelines
    • Jobs
    • Schedules
  • Security & Compliance
    • Security & Compliance
    • Dependency List
    • License Compliance
  • Operations
    • Operations
    • Incidents
    • Environments
  • Analytics
    • Analytics
    • CI / CD
    • Code Review
    • Insights
    • Issue
    • Repository
    • Value Stream
  • Wiki
    • Wiki
  • Snippets
    • Snippets
  • Members
    • Members
  • Collapse sidebar
  • Activity
  • Graph
  • Create a new issue
  • Jobs
  • Commits
  • Issue Boards
  • Glasgow Haskell Compiler
  • GHCGHC
  • Wiki
    • Commentary
    • Rts
    • Storage
    • Gc
  • pinned

Last edited by Takenobu Tani Jun 22, 2020
Page history New page

pinned

Pinned Objects

The GC does not support pinning arbitrary objects. Only objects that have no pointer fields can be pinned. Nevertheless, this is a useful case, because we often want to allocate garbage-collectable memory that can be passed to foreign functions via the FFI, and we want to be able to run the GC while the foreign function is still executing (for a safe foreign call). Hence, the memory we allocated must not move.

Bytestrings are currently allocated as pinned memory, so that the bytestring contents can be passed to FFI calls if necessary.

The RTS provides an API for allocating pinned memory, in includes/rts/storage/GC.h:

StgPtr  allocatePinned  ( Capability *cap, lnat n );

This allocates memory from the given Capability's nursery.

Pinned objects work in the GC as follows:

  • Pinned objects are allocated into a block of their own, not mixed up with unpinned objects.
  • The block containing pinned objects is marked as a large block, i.e. the BF_LARGE bit is set in bd->flags.
  • When encountering a live object in a BF_LARGE block, the GC never copies the object, instead it just re-links the whole block onto the large_objects list of the destination generation.
  • The GC doesn't have to scavenge the pinned object, since it does not contain any pointers. This is just as well, because we cannot scan blocks for live pinned objects, due to slop. Hence the restriction that pinned objects do not contain pointers.

This means that using pinned objects may lead to memory fragmentation, since a single pinned object keeps alive the whole block in which it resides. If we were to implement a non-moving collector such as mark-region?, then we would be able to reduce the impact of fragmentation due to pinned objects.

Clone repository

GHC Home
GHC User's Guide

Joining In

Newcomers info
Mailing Lists & IRC
The GHC Team

Documentation

GHC Status Info
Working conventions
Building Guide
Debugging
Commentary

Wiki

Title Index
Recent Changes