Custom payload meta type?

• Hardware Platform (Jetson / GPU)
all of the above
• DeepStream Version
• JetPack Version (valid for Jetson only)
• TensorRT Version
• NVIDIA GPU Driver Version (valid for GPU only)

So, I have this function that serializes my protobuf metadata as string and
attaches it to the buffer as type NVDS_PAYLOAD_META.

ProtoPayloadFilter::on_batch_meta(NvDsBatchMeta* batch_meta, dp::Batch* batch) {
  // try to get a new user metadata pointer from the pool
  auto user_meta = nvds_acquire_user_meta_from_pool(batch_meta);
  if (user_meta == nullptr) {
    GST_WARNING("could not get user metadata from batch pool");
    return false;

  // try to serialize the batch to string
  auto payload = new std::string();
  if (!batch->SerializeToString(payload)) {
    GST_WARNING("could not convert payload to string");
    delete payload;
    return false;

  // attach the payload to the user_meta as type NVDS_PAYLOAD_META
  user_meta->user_meta_data = (void*) payload;
  // not sure if this will work, but we'll find out if the broker accepts it
  // I'm inferring this from deepstream_user_metadata_app.c, intellisense
  // and fgrep for "payload"
  user_meta->base_meta.meta_type = NVDS_PAYLOAD_META;
  user_meta->base_meta.copy_func = copy_dp_payload_meta;
  user_meta->base_meta.release_func = release_dp_payload_meta;
  user_meta->base_meta.uContext = this;

  // attach the payload to the buffer at the batch level
  nvds_add_user_meta_to_batch(batch_meta, user_meta);

  return true;

My question is: is there an equivalent function to “nvds_get_user_meta_type” so I can get a new payload type? Later in my pipeline I have a broker element, but i don’t want to send all NVDS_PAYLOAD_META. I’m assuming it’ll work if it’s just my metadata, but I want to make sure I ignore other NVDS_PAYLOAD_META that I didn’t assign.

Edit: also, I’d like to make sure it works with the standard nvidia message broker elements, so I want to do it “properly”.

Sorry for a late reply.
You could use msg-conv-comp-id to force converter / broker components to process only those messages having same value for componentId field and ignore other messages. You should modify the application to fill componentId field of
NvDsEventMsgMeta structure.

1 Like

Thanks, Amy. I am not using NvDsEventMsgMeta for my custom metadata. I’ve just attached a std::string* to user_meta->user_meta_data with the appropriate copy and release functions. I can see now i’m doing this wrong (for various reasons).

I see your broker element (at least the deepstrem-4.0 version) checks like this:

        if (user_meta && user_meta->base_meta.meta_type == NVDS_PAYLOAD_META) {
          payload = (NvDsPayload *) user_meta->user_meta_data;

          if (self->compId && payload->componentId != self->compId)

          if (self->asyncSend) {
            g_mutex_lock (&self->flowLock);
            err = self->nvds_msgapi_send_async (self->connHandle, self->topic,
                                                (uint8_t *) payload->payload,
                                                nvds_msgapi_send_callback, self);

My code works with my custom broker which has a different loop to parse the batch level user meta, but I want to make sure it works with nvdsmsgbroker as well. I see now, reading this code and with your suggestion, that i must I encapsulate my bytes in a NvDsPayload and set componentId as you suggest. Thank you for pointing me to componentId !

I noticed that user_meta attached to the batch (with nvds_add_user_meta_to_batch) isn’t parsed by the current nvidia message broker. I am using batch level meta for my case. Are there any future plans for the broker to handle payloads in batch_meta->batch_user_meta_list, or should I modify nvmsgbroker to handle this case?

nvmsgbroker parse payloads in frame_meta_list, you may change the broker accordingly to meet your needs.

1 Like