1 // Classes and utilities for supporting HTTP/2 trace logging, which logs 2 // information about all control and data frames sent and received over 3 // HTTP/2 connections. 4 5 #ifndef QUICHE_HTTP2_CORE_HTTP2_TRACE_LOGGING_H_ 6 #define QUICHE_HTTP2_CORE_HTTP2_TRACE_LOGGING_H_ 7 8 #include <cstdint> 9 10 #include "absl/strings/string_view.h" 11 #include "quiche/common/platform/api/quiche_export.h" 12 #include "quiche/common/platform/api/quiche_logging.h" 13 #include "quiche/spdy/core/http2_frame_decoder_adapter.h" 14 #include "quiche/spdy/core/recording_headers_handler.h" 15 #include "quiche/spdy/core/spdy_headers_handler_interface.h" 16 #include "quiche/spdy/core/spdy_protocol.h" 17 18 // Logging macro to use for all HTTP/2 trace logging. Iff trace logging is 19 // enabled, logs at level INFO with a common prefix prepended (to facilitate 20 // post-hoc filtering of trace logging output). 21 #define HTTP2_TRACE_LOG(perspective, is_enabled) \ 22 QUICHE_LOG_IF(INFO, is_enabled()) << "[HTTP2_TRACE " << perspective << "] " 23 24 namespace http2 { 25 26 // Intercepts deframing events to provide detailed logs. Intended to be used for 27 // manual debugging. 28 // 29 // Note any new methods in SpdyFramerVisitorInterface MUST be overridden here to 30 // properly forward the event. This could be ensured by making every event in 31 // SpdyFramerVisitorInterface a pure virtual. 32 class QUICHE_EXPORT Http2TraceLogger : public spdy::SpdyFramerVisitorInterface { 33 public: 34 typedef spdy::SpdyAltSvcWireFormat SpdyAltSvcWireFormat; 35 typedef spdy::SpdyErrorCode SpdyErrorCode; 36 typedef spdy::SpdyFramerVisitorInterface SpdyFramerVisitorInterface; 37 typedef spdy::SpdyPingId SpdyPingId; 38 typedef spdy::SpdyPriority SpdyPriority; 39 typedef spdy::SpdySettingsId SpdySettingsId; 40 typedef spdy::SpdyStreamId SpdyStreamId; 41 42 Http2TraceLogger(SpdyFramerVisitorInterface* parent, 43 absl::string_view perspective, 44 std::function<bool()> is_enabled, const void* connection_id); 45 ~Http2TraceLogger() override; 46 47 Http2TraceLogger(const Http2TraceLogger&) = delete; 48 Http2TraceLogger& operator=(const Http2TraceLogger&) = delete; 49 50 void OnError(http2::Http2DecoderAdapter::SpdyFramerError error, 51 std::string detailed_error) override; 52 void OnCommonHeader(SpdyStreamId stream_id, size_t length, uint8_t type, 53 uint8_t flags) override; 54 spdy::SpdyHeadersHandlerInterface* OnHeaderFrameStart( 55 SpdyStreamId stream_id) override; 56 void OnHeaderFrameEnd(SpdyStreamId stream_id) override; 57 void OnDataFrameHeader(SpdyStreamId stream_id, size_t length, 58 bool fin) override; 59 void OnStreamFrameData(SpdyStreamId stream_id, const char* data, 60 size_t len) override; 61 void OnStreamEnd(SpdyStreamId stream_id) override; 62 void OnStreamPadLength(SpdyStreamId stream_id, size_t value) override; 63 void OnStreamPadding(SpdyStreamId stream_id, size_t len) override; 64 void OnRstStream(SpdyStreamId stream_id, SpdyErrorCode error_code) override; 65 void OnSetting(spdy::SpdySettingsId id, uint32_t value) override; 66 void OnPing(SpdyPingId unique_id, bool is_ack) override; 67 void OnSettings() override; 68 void OnSettingsEnd() override; 69 void OnSettingsAck() override; 70 void OnGoAway(SpdyStreamId last_accepted_stream_id, 71 SpdyErrorCode error_code) override; 72 bool OnGoAwayFrameData(const char* goaway_data, size_t len) override; 73 void OnHeaders(SpdyStreamId stream_id, size_t payload_length, 74 bool has_priority, int weight, SpdyStreamId parent_stream_id, 75 bool exclusive, bool fin, bool end) override; 76 void OnWindowUpdate(SpdyStreamId stream_id, int delta_window_size) override; 77 void OnPushPromise(SpdyStreamId stream_id, SpdyStreamId promised_stream_id, 78 bool end) override; 79 void OnContinuation(SpdyStreamId stream_id, size_t payload_length, 80 bool end) override; 81 void OnAltSvc(SpdyStreamId stream_id, absl::string_view origin, 82 const SpdyAltSvcWireFormat::AlternativeServiceVector& 83 altsvc_vector) override; 84 void OnPriority(SpdyStreamId stream_id, SpdyStreamId parent_stream_id, 85 int weight, bool exclusive) override; 86 void OnPriorityUpdate(SpdyStreamId prioritized_stream_id, 87 absl::string_view priority_field_value) override; 88 bool OnUnknownFrame(SpdyStreamId stream_id, uint8_t frame_type) override; 89 void OnUnknownFrameStart(SpdyStreamId stream_id, size_t length, uint8_t type, 90 uint8_t flags) override; 91 void OnUnknownFramePayload(SpdyStreamId stream_id, 92 absl::string_view payload) override; 93 94 private: 95 void LogReceivedHeaders() const; 96 97 std::unique_ptr<spdy::RecordingHeadersHandler> recording_headers_handler_; 98 99 SpdyFramerVisitorInterface* wrapped_; 100 const absl::string_view perspective_; 101 const std::function<bool()> is_enabled_; 102 const void* connection_id_; 103 }; 104 105 // Visitor to log control frames that have been written. 106 class QUICHE_EXPORT Http2FrameLogger : public spdy::SpdyFrameVisitor { 107 public: 108 // This class will preface all of its log messages with the value of 109 // |connection_id| in hexadecimal. Http2FrameLogger(absl::string_view perspective,std::function<bool ()> is_enabled,const void * connection_id)110 Http2FrameLogger(absl::string_view perspective, 111 std::function<bool()> is_enabled, const void* connection_id) 112 : perspective_(perspective), 113 is_enabled_(std::move(is_enabled)), 114 connection_id_(connection_id) {} 115 116 Http2FrameLogger(const Http2FrameLogger&) = delete; 117 Http2FrameLogger& operator=(const Http2FrameLogger&) = delete; 118 119 void VisitRstStream(const spdy::SpdyRstStreamIR& rst_stream) override; 120 void VisitSettings(const spdy::SpdySettingsIR& settings) override; 121 void VisitPing(const spdy::SpdyPingIR& ping) override; 122 void VisitGoAway(const spdy::SpdyGoAwayIR& goaway) override; 123 void VisitHeaders(const spdy::SpdyHeadersIR& headers) override; 124 void VisitWindowUpdate( 125 const spdy::SpdyWindowUpdateIR& window_update) override; 126 void VisitPushPromise(const spdy::SpdyPushPromiseIR& push_promise) override; 127 void VisitContinuation(const spdy::SpdyContinuationIR& continuation) override; 128 void VisitAltSvc(const spdy::SpdyAltSvcIR& altsvc) override; 129 void VisitPriority(const spdy::SpdyPriorityIR& priority) override; 130 void VisitData(const spdy::SpdyDataIR& data) override; 131 void VisitPriorityUpdate( 132 const spdy::SpdyPriorityUpdateIR& priority_update) override; 133 void VisitAcceptCh(const spdy::SpdyAcceptChIR& accept_ch) override; 134 void VisitUnknown(const spdy::SpdyUnknownIR& ir) override; 135 136 private: 137 const absl::string_view perspective_; 138 const std::function<bool()> is_enabled_; 139 const void* connection_id_; 140 }; 141 142 } // namespace http2 143 144 #endif // QUICHE_HTTP2_CORE_HTTP2_TRACE_LOGGING_H_ 145