| // Classes and utilities for supporting HTTP/2 trace logging, which logs |
| // information about all control and data frames sent and received over |
| // HTTP/2 connections. |
| |
| #ifndef QUICHE_HTTP2_CORE_HTTP2_TRACE_LOGGING_H_ |
| #define QUICHE_HTTP2_CORE_HTTP2_TRACE_LOGGING_H_ |
| |
| #include <cstdint> |
| |
| #include "absl/strings/string_view.h" |
| #include "common/platform/api/quiche_export.h" |
| #include "common/platform/api/quiche_logging.h" |
| #include "spdy/core/http2_frame_decoder_adapter.h" |
| #include "spdy/core/recording_headers_handler.h" |
| #include "spdy/core/spdy_headers_handler_interface.h" |
| #include "spdy/core/spdy_protocol.h" |
| |
| // Logging macro to use for all HTTP/2 trace logging. Iff trace logging is |
| // enabled, logs at level INFO with a common prefix prepended (to facilitate |
| // post-hoc filtering of trace logging output). |
| #define HTTP2_TRACE_LOG(perspective, is_enabled) \ |
| QUICHE_LOG_IF(INFO, is_enabled()) << "[HTTP2_TRACE " << perspective << "] " |
| |
| namespace http2 { |
| |
| // Intercepts deframing events to provide detailed logs. Intended to be used for |
| // manual debugging. |
| // |
| // Note any new methods in SpdyFramerVisitorInterface MUST be overridden here to |
| // properly forward the event. This could be ensured by making every event in |
| // SpdyFramerVisitorInterface a pure virtual. |
| class QUICHE_EXPORT_PRIVATE Http2TraceLogger |
| : public spdy::SpdyFramerVisitorInterface { |
| public: |
| typedef spdy::SpdyAltSvcWireFormat SpdyAltSvcWireFormat; |
| typedef spdy::SpdyErrorCode SpdyErrorCode; |
| typedef spdy::SpdyFramerVisitorInterface SpdyFramerVisitorInterface; |
| typedef spdy::SpdyPingId SpdyPingId; |
| typedef spdy::SpdyPriority SpdyPriority; |
| typedef spdy::SpdySettingsId SpdySettingsId; |
| typedef spdy::SpdyStreamId SpdyStreamId; |
| |
| Http2TraceLogger(SpdyFramerVisitorInterface* parent, |
| absl::string_view perspective, |
| std::function<bool()> is_enabled, const void* connection_id); |
| ~Http2TraceLogger() override; |
| |
| Http2TraceLogger(const Http2TraceLogger&) = delete; |
| Http2TraceLogger& operator=(const Http2TraceLogger&) = delete; |
| |
| void OnError(http2::Http2DecoderAdapter::SpdyFramerError error, |
| std::string detailed_error) override; |
| void OnCommonHeader(SpdyStreamId stream_id, size_t length, uint8_t type, |
| uint8_t flags) override; |
| spdy::SpdyHeadersHandlerInterface* OnHeaderFrameStart( |
| SpdyStreamId stream_id) override; |
| void OnHeaderFrameEnd(SpdyStreamId stream_id) override; |
| void OnDataFrameHeader(SpdyStreamId stream_id, size_t length, |
| bool fin) override; |
| void OnStreamFrameData(SpdyStreamId stream_id, const char* data, |
| size_t len) override; |
| void OnStreamEnd(SpdyStreamId stream_id) override; |
| void OnStreamPadLength(SpdyStreamId stream_id, size_t value) override; |
| void OnStreamPadding(SpdyStreamId stream_id, size_t len) override; |
| void OnRstStream(SpdyStreamId stream_id, SpdyErrorCode error_code) override; |
| void OnSetting(spdy::SpdySettingsId id, uint32_t value) override; |
| void OnPing(SpdyPingId unique_id, bool is_ack) override; |
| void OnSettings() override; |
| void OnSettingsEnd() override; |
| void OnSettingsAck() override; |
| void OnGoAway(SpdyStreamId last_accepted_stream_id, |
| SpdyErrorCode error_code) override; |
| bool OnGoAwayFrameData(const char* goaway_data, size_t len) override; |
| void OnHeaders(SpdyStreamId stream_id, bool has_priority, int weight, |
| SpdyStreamId parent_stream_id, bool exclusive, bool fin, |
| bool end) override; |
| void OnWindowUpdate(SpdyStreamId stream_id, int delta_window_size) override; |
| void OnPushPromise(SpdyStreamId stream_id, SpdyStreamId promised_stream_id, |
| bool end) override; |
| void OnContinuation(SpdyStreamId stream_id, bool end) override; |
| void OnAltSvc(SpdyStreamId stream_id, absl::string_view origin, |
| const SpdyAltSvcWireFormat::AlternativeServiceVector& |
| altsvc_vector) override; |
| void OnPriority(SpdyStreamId stream_id, SpdyStreamId parent_stream_id, |
| int weight, bool exclusive) override; |
| void OnPriorityUpdate(SpdyStreamId prioritized_stream_id, |
| absl::string_view priority_field_value) override; |
| bool OnUnknownFrame(SpdyStreamId stream_id, uint8_t frame_type) override; |
| |
| private: |
| void LogReceivedHeaders() const; |
| |
| std::unique_ptr<spdy::RecordingHeadersHandler> recording_headers_handler_; |
| |
| SpdyFramerVisitorInterface* wrapped_; |
| const absl::string_view perspective_; |
| const std::function<bool()> is_enabled_; |
| const void* connection_id_; |
| }; |
| |
| // Visitor to log control frames that have been written. |
| class QUICHE_EXPORT_PRIVATE Http2FrameLogger : public spdy::SpdyFrameVisitor { |
| public: |
| // This class will preface all of its log messages with the value of |
| // |connection_id| in hexadecimal. |
| Http2FrameLogger(absl::string_view perspective, |
| std::function<bool()> is_enabled, const void* connection_id) |
| : perspective_(perspective), |
| is_enabled_(std::move(is_enabled)), |
| connection_id_(connection_id) {} |
| |
| Http2FrameLogger(const Http2FrameLogger&) = delete; |
| Http2FrameLogger& operator=(const Http2FrameLogger&) = delete; |
| |
| void VisitRstStream(const spdy::SpdyRstStreamIR& rst_stream) override; |
| void VisitSettings(const spdy::SpdySettingsIR& settings) override; |
| void VisitPing(const spdy::SpdyPingIR& ping) override; |
| void VisitGoAway(const spdy::SpdyGoAwayIR& goaway) override; |
| void VisitHeaders(const spdy::SpdyHeadersIR& headers) override; |
| void VisitWindowUpdate( |
| const spdy::SpdyWindowUpdateIR& window_update) override; |
| void VisitPushPromise(const spdy::SpdyPushPromiseIR& push_promise) override; |
| void VisitContinuation(const spdy::SpdyContinuationIR& continuation) override; |
| void VisitAltSvc(const spdy::SpdyAltSvcIR& altsvc) override; |
| void VisitPriority(const spdy::SpdyPriorityIR& priority) override; |
| void VisitData(const spdy::SpdyDataIR& data) override; |
| void VisitPriorityUpdate( |
| const spdy::SpdyPriorityUpdateIR& priority_update) override; |
| void VisitAcceptCh(const spdy::SpdyAcceptChIR& accept_ch) override; |
| void VisitUnknown(const spdy::SpdyUnknownIR& ir) override; |
| |
| private: |
| const absl::string_view perspective_; |
| const std::function<bool()> is_enabled_; |
| const void* connection_id_; |
| }; |
| |
| } // namespace http2 |
| |
| #endif // QUICHE_HTTP2_CORE_HTTP2_TRACE_LOGGING_H_ |