Repository: envoyproxy/envoy
File: source/server/hot_restarting_child.h (C/C++)

Code before:
    // dispatches, which is expected to be the same main thread as registerListener
    // is called from.
    absl::optional<ForwardEntry>
    getListenerForDestination(const Network::Address::Instance& address);

    // Registers a UdpListenerConfig and address into the map, to be matched using
    // getListenerForDestination for UDP packet forwarding.
    // This is called from the main thread during listening socket creation.
    void registerListener(Network::Address::InstanceConstSharedPtr address,
                          std::shared_ptr<Network::UdpListenerConfig> listener_config);

  private:
    // Map keyed on address as a string, because Network::Address::Instance isn't hashable.
    absl::flat_hash_map<std::string, ForwardEntry> listener_map_;
  };

  HotRestartingChild(int base_id, int restart_epoch, const std::string& socket_path,
                     mode_t socket_mode, bool skip_hot_restart_on_no_parent,
                     bool skip_parent_stats);
  ~HotRestartingChild() override = default;

  void initialize(Event::Dispatcher& dispatcher);
  void shutdown();

  int duplicateParentListenSocket(const std::string& address, uint32_t worker_index,
                                  const std::string& network_namespace);
  void registerUdpForwardingListener(Network::Address::InstanceConstSharedPtr address,
                                     std::shared_ptr<Network::UdpListenerConfig> listener_config);
  // From Network::ParentDrainedCallbackRegistrar.
  void registerParentDrainedCallback(const Network::Address::InstanceConstSharedPtr& addr,
                                     absl::AnyInvocable<void()> action) override;
  std::unique_ptr<envoy::HotRestartMessage> getParentStats();
  void drainParentListeners();
  absl::optional<HotRestart::AdminShutdownResponse> sendParentAdminShutdownRequest();
  void sendParentTerminateRequest();
  void mergeParentStats(Stats::Store& stats_store,
                        const envoy::HotRestartMessage::Reply::Stats& stats_proto);

protected:
  absl::Status onSocketEventUdpForwarding();
  void onForwardedUdpPacket(uint32_t worker_index, Network::UdpRecvData&& data);
  // When call to terminate parent is sent, or parent is already terminated,
  void allDrainsImplicitlyComplete();

private:
  bool abortDueToFailedParentConnection();
  friend class HotRestartUdpForwardingTestHelper;
  absl::Mutex registry_mu_;
  const int restart_epoch_;
  bool parent_terminated_;
  bool parent_drained_ ABSL_GUARDED_BY(registry_mu_);

Review comment (suggestion):
```suggestion
                                  absl::string_view network_namespace);
```

Code after:
    // dispatches, which is expected to be the same main thread as registerListener
    // is called from.
    absl::optional<ForwardEntry>
    getListenerForDestination(const Network::Address::Instance& address);

    // Registers a UdpListenerConfig and address into the map, to be matched using
    // getListenerForDestination for UDP packet forwarding.
    // This is called from the main thread during listening socket creation.
    void registerListener(Network::Address::InstanceConstSharedPtr address,
                          std::shared_ptr<Network::UdpListenerConfig> listener_config);

  private:
    // Map keyed on address as a string, because Network::Address::Instance isn't hashable.
    absl::flat_hash_map<std::string, ForwardEntry> listener_map_;
  };

  HotRestartingChild(int base_id, int restart_epoch, const std::string& socket_path,
                     mode_t socket_mode, bool skip_hot_restart_on_no_parent,
                     bool skip_parent_stats);
  ~HotRestartingChild() override = default;

  void initialize(Event::Dispatcher& dispatcher);
  void shutdown();

  int duplicateParentListenSocket(const std::string& address, uint32_t worker_index,
                                  absl::string_view network_namespace);
  void registerUdpForwardingListener(Network::Address::InstanceConstSharedPtr address,
                                     std::shared_ptr<Network::UdpListenerConfig> listener_config);
  // From Network::ParentDrainedCallbackRegistrar.
  void registerParentDrainedCallback(const Network::Address::InstanceConstSharedPtr& addr,
                                     absl::AnyInvocable<void()> action) override;
  std::unique_ptr<envoy::HotRestartMessage> getParentStats();
  void drainParentListeners();
  absl::optional<HotRestart::AdminShutdownResponse> sendParentAdminShutdownRequest();
  void sendParentTerminateRequest();
  void mergeParentStats(Stats::Store& stats_store,
                        const envoy::HotRestartMessage::Reply::Stats& stats_proto);

protected:
  absl::Status onSocketEventUdpForwarding();
  void onForwardedUdpPacket(uint32_t worker_index, Network::UdpRecvData&& data);
  // When call to terminate parent is sent, or parent is already terminated,
  void allDrainsImplicitlyComplete();

private:
  bool abortDueToFailedParentConnection();
  friend class HotRestartUdpForwardingTestHelper;
  absl::Mutex registry_mu_;
  const int restart_epoch_;
  bool parent_terminated_;
  bool parent_drained_ ABSL_GUARDED_BY(registry_mu_);