Skip to content
  • Steffen Müthing's avatar
    [logging] Make sure sink pattern arguments live through the {fmt} call · e5284569
    Steffen Müthing authored
    The PatternFormatSink crashes in optimized builds because the arguments
    retrieved from the arguments() function are always invalid. This is due to two
    object lifetime problems:
    
    - fmt::format_args is only a view onto an externally allocated array of
      type-erased format arguments. We allocated this array in a temporary object of
      type fmt::format_arg_store in arguments(), but that became invalid as soon as
      that function ended.
    
    - The type-erased format arguments in fmt::format_arg_store only store
      references to existing data, which causes yet another problem, as some of the
      data that we want to provide is returned as temporary objects from the
      LogMessage etc.
    
    To work around this problem, we need to store both the data and an instance of
    fmt::format_arg_store for the duration of the {fmt} calls in a derived sink.
    This patch adds a new member type `Arguments` for this purpose. Arguments
    stores this data without exposing the details to the user (the object only
    contains two char* buffers for it), which keeps user code away from the code
    bloat of captured lambda functions et. al. Arguments **must** be stored as a
    named variable (to guarantee a sufficient lifetime) and implicitly casts into
    fmt::format_args if used that way.
    e5284569