1 /* 2 * nghttp2 - HTTP/2 C Library 3 * 4 * Copyright (c) 2012 Tatsuhiro Tsujikawa 5 * 6 * Permission is hereby granted, free of charge, to any person obtaining 7 * a copy of this software and associated documentation files (the 8 * "Software"), to deal in the Software without restriction, including 9 * without limitation the rights to use, copy, modify, merge, publish, 10 * distribute, sublicense, and/or sell copies of the Software, and to 11 * permit persons to whom the Software is furnished to do so, subject to 12 * the following conditions: 13 * 14 * The above copyright notice and this permission notice shall be 15 * included in all copies or substantial portions of the Software. 16 * 17 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 18 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 19 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 20 * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE 21 * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION 22 * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION 23 * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 24 */ 25 #ifndef SHRPX_DOWNSTREAM_QUEUE_H 26 #define SHRPX_DOWNSTREAM_QUEUE_H 27 28 #include "shrpx.h" 29 30 #include <cinttypes> 31 #include <map> 32 #include <set> 33 #include <memory> 34 35 #include "template.h" 36 37 using namespace nghttp2; 38 39 namespace shrpx { 40 41 class Downstream; 42 43 // Link entry in HostEntry.blocked and downstream because downstream 44 // could be deleted in anytime and we'd like to find Downstream in 45 // O(1). Downstream has field to link back to this object. 46 struct BlockedLink { 47 Downstream *downstream; 48 BlockedLink *dlnext, *dlprev; 49 }; 50 51 class DownstreamQueue { 52 public: 53 struct HostEntry { 54 HostEntry(ImmutableString &&key); 55 56 HostEntry(HostEntry &&) = default; 57 HostEntry &operator=(HostEntry &&) = default; 58 59 HostEntry(const HostEntry &) = delete; 60 HostEntry &operator=(const HostEntry &) = delete; 61 62 // Key that associates this object 63 ImmutableString key; 64 // Set of stream ID that blocked by conn_max_per_host_. 65 DList<BlockedLink> blocked; 66 // The number of connections currently made to this host. 67 size_t num_active; 68 }; 69 70 using HostEntryMap = std::map<StringRef, HostEntry>; 71 72 // conn_max_per_host == 0 means no limit for downstream connection. 73 DownstreamQueue(size_t conn_max_per_host = 0, bool unified_host = true); 74 ~DownstreamQueue(); 75 // Add |downstream| to this queue. This is entry point for 76 // Downstream object. 77 void add_pending(std::unique_ptr<Downstream> downstream); 78 // Set |downstream| to failure state, which means that downstream 79 // failed to connect to backend. 80 void mark_failure(Downstream *downstream); 81 // Set |downstream| to active state, which means that downstream 82 // connection has started. 83 void mark_active(Downstream *downstream); 84 // Set |downstream| to blocked state, which means that download 85 // connection was blocked because conn_max_per_host_ limit. 86 void mark_blocked(Downstream *downstream); 87 // Returns true if we can make downstream connection to given 88 // |host|. 89 bool can_activate(const StringRef &host) const; 90 // Removes and frees |downstream| object. If |downstream| is in 91 // DispatchState::ACTIVE, and |next_blocked| is true, this function 92 // may return Downstream object with the same target host in 93 // DispatchState::BLOCKED if its connection is now not blocked by 94 // conn_max_per_host_ limit. 95 Downstream *remove_and_get_blocked(Downstream *downstream, 96 bool next_blocked = true); 97 Downstream *get_downstreams() const; 98 HostEntry &find_host_entry(const StringRef &host); 99 StringRef make_host_key(const StringRef &host) const; 100 StringRef make_host_key(Downstream *downstream) const; 101 102 private: 103 // Per target host structure to keep track of the number of 104 // connections to the same host. 105 HostEntryMap host_entries_; 106 DList<Downstream> downstreams_; 107 // Maximum number of concurrent connections to the same host. 108 size_t conn_max_per_host_; 109 // true if downstream host is treated as the same. Used for reverse 110 // proxying. 111 bool unified_host_; 112 }; 113 114 } // namespace shrpx 115 116 #endif // SHRPX_DOWNSTREAM_QUEUE_H 117