CHANGELOG revision 130d542a
12018-04-25 2 3 - [BUGFIX] Do not create gap in sent packnos when squeezing delayed 4 packets. 5 - [BUGFIX] sendctl checks for all unacked bytes, not just retx bytes. 6 - [BUGFIX] connections with blocked scheduled packets are not tickable 7 for sending. 8 - [BUGFIX] Conn is tickable if it wants to send a connection-level 9 frame. 10 112018-04-23 12 13 - Fix busy loop: tickable must make progress. When connection is 14 self-reporting as tickable, it must make progress when ticked. There 15 are two issues: 16 1. If there are buffered packets, the connection is only tickable if 17 they can be sent out. 18 2. A connection is tickable if there are streams on the servicing 19 queue. When the tick occurs, we must service the stream 20 independent of whether any packets are sent. 21 - Fix assertion in pacer which can be incorrect under some 22 conditions. 23 - cmake: do not turn on address sanitizer if in Travis. 24 252018-04-20 26 27 - [BUGFIX] Fix bug in lsquic_engine_connect() exposed by yesterday's 28 changes. 29 302018-04-19 31 32 - [BUGFIX] Add connection to Tickable Queue on stream write 33 - cmake: use MSVC variable instead of trying to detect 34 - engine: improve connection incref/decref logging 35 - stream: don't ignore errors that may occur on triggered flush 36 - connection: remove obsolete method 37 - engine: indicate connection as tickable if previous call went 38 over threshold 39 402018-04-09 41 42 [API Change, OPTIMIZATION] Only process conns that need to be processed 43 44 The API is simplified: do not expose the user code to several 45 queues. A "connection queue" is now an internal concept. 46 The user processes connections using the single function 47 lsquic_engine_process_conns(). When this function is called, 48 only those connections are processed that need to be processed. 49 A connection needs to be processed when: 50 51 1. New incoming packets have been fed to the connection. 52 2. User wants to read from a stream that is readable. 53 3. User wants to write to a stream that is writeable. 54 4. There are buffered packets that can be sent out. (This 55 means that the user wrote to a stream outside of the 56 lsquic library callback.) 57 5. A control frame (such as BLOCKED) needs to be sent out. 58 6. A stream needs to be serviced or delayed stream needs to 59 be created. 60 7. An alarm rings. 61 8. Pacer timer expires. 62 63 To achieve this, the library places the connections into two 64 priority queues (min heaps): 65 66 1. Tickable Queue; and 67 2. Advisory Tick Time queue (ATTQ). 68 69 Each time lsquic_engine_process_conns() is called, the Tickable 70 Queue is emptied. After the connections have been ticked, they are 71 queried again: if a connection is not being closed, it is placed 72 either in the Tickable Queue if it is ready to be ticked again or 73 it is placed in the Advisory Tick Time Queue. It is assumed that 74 a connection always has at least one timer set (the idle alarm). 75 76 The connections in the Tickable Queue are arranged in the least 77 recently ticked order. This lets connections that have been quiet 78 longer to get their packets scheduled first. 79 80 This change means that the library no longer needs to be ticked 81 periodically. The user code can query the library when is the 82 next tick event and schedule it exactly. When connections are 83 processed, only the tickable connections are processed, not *all* 84 the connections. When there are no tick events, it means that no 85 timer event is necessary -- only the file descriptor READ event 86 is active. 87 88 The following are improvements and simplifications that have 89 been triggered: 90 91 - Queue of connections with incoming packets is gone. 92 - "Pending Read/Write Events" Queue is gone (along with its 93 history and progress checks). This queue has become the 94 Tickable Queue. 95 - The connection hash no longer needs to track the connection 96 insertion order. 97 982018-04-02 99 100 - [FEATURE] Windows support 101 102 - Reduce stack use -- outgoing packet batch is now allocated on the heap. 103 1042018-03-09 105 106 - [OPTIMIZATION] Merge series of ACKs if possible 107 108 Parsed single-range ACK frames (that is the majority of frames) are 109 saved in the connection and their processing is deferred until the 110 connection is ticked. If several ACKs come in a series between 111 adjacent ticks, we check whether the latest ACK is a strict superset 112 of the saved ACK. If it is, the older ACK is not processed. 113 114 If ACK frames can be merged, they are merged and only one of them is 115 either processed or saved. 116 117 - [OPTIMIZATION] Speed up ACK verification by simplifying send history. 118 119 Never generate a gap in the sent packet number sequence. This reduces 120 the send history to a single number instead of potentially a series of 121 packet ranges and thereby speeds up ACK verification. 122 123 By default, detecting a gap in the send history is not fatal: only a 124 single warning is generated per connection. The connection can continue 125 to operate even if the ACK verification code is not able to detect some 126 inconsistencies. 127 128 - [OPTIMIZATION] Rearrange the lsquic_send_ctl struct 129 130 The first part of struct lsquic_send_ctl now consists of members that 131 are used in lsquic_send_ctl_got_ack() (in the absense of packet loss, 132 which is the normal case). To speed up reads and writes, we no longer 133 try to save space by using 8- and 16-bit integers. Use regular integer 134 width for everything. 135 136 - [OPTIMIZATION] Cache size of sent packet. 137 138 - [OPTIMIZATION] Keep track of the largest ACKed in packet_out 139 140 Instead of parsing our own ACK frames when packet has been acked, 141 use the value saved in the packet_out structure when the ACK frame 142 was generated. 143 144 - [OPTIMIZATION] Take RTT sampling conditional out of ACK loop 145 146 - [OPTIMIZATION] ACK processing: only call clock_gettime() if needed 147 148 - [OPTIMIZATION] Several code-level optimizations to ACK processing. 149 150 - Fix: http_client: fix -I flag; switch assert() to abort() 151 1522018-02-26 153 - [API Change] lsquic_engine_connect() returns pointer to the connection 154 object. 155 - [API Change] Add lsquic_conn_get_engine() to get engine object from 156 connection object. 157 - [API Change] Add lsquic_conn_status() to query connection status. 158 - [API Change] Add add lsquic_conn_set_ctx(). 159 - [API Change] Add new timestamp format, e.g. 2017-03-21 13:43:46.671345 160 - [OPTIMIZATION] Process handshake STREAM frames as soon as packet 161 arrives. 162 - [OPTIMIZATION] Do not compile expensive send controller sanity check 163 by default. 164 - [OPTIMIZATION] Add fast path to gquic_be_gen_reg_pkt_header. 165 - [OPTIMIZATION] Only make squeeze function call if necessary. 166 - [OPTIMIZATION] Speed up Q039 ACK frame parsing. 167 - [OPTIMIZATION] Fit most used elements of packet_out into first 64 bytes. 168 - [OPTIMIZATION] Keep track of scheduled bytes instead of calculating. 169 - [OPTIMIZATION] Prefetch next unacked packet when processing ACK. 170 - [OPTIMIZATION] Leverage fact that ACK ranges and unacked list are. 171 ordered. 172 - [OPTIMIZATION] Reduce function pointer use for STREAM frame generation 173 - Fix: reset incoming streams that arrive after we send GOAWAY. 174 - Fix: delay client on_new_conn() call until connection is fully set up. 175 - Fixes to buffered packets logic: splitting, STREAM frame elision. 176 - Fix: do not dispatch on_write callback if no packets are available. 177 - Fix WINDOW_UPDATE send and resend logic. 178 - Fix STREAM frame extension code. 179 - Fix: Drop unflushed data when stream is reset. 180 - Switch to tracking CWND using bytes rather than packets. 181 - Fix TCP friendly adjustment in cubic. 182 - Fix: do not generate invalid STOP_WAITING frames during high packet 183 loss. 184 - Pacer fixes. 185 1862017-12-18 187 188 - Fix: better follow cubic curve after idle period 189 - Fix: add missing parts to outgoing packet splitting code 190 - Fix: compilation using gcc 4.8.4 191 1922017-10-31 193 194 - Add APIs.txt -- describes LSQUIC APIs 195 1962017-10-31 197 198 - [API Change] Sendfile-like functionality is gone. The stream no 199 longer opens files and deals with file descriptors. (Among other 200 things, this makes the code more portable.) Three writing functions 201 are provided: 202 203 lsquic_stream_write 204 lsquic_stream_writev 205 lsquic_stream_writef (NEW) 206 207 lsquic_stream_writef() is given an abstract reader that has function 208 pointers for size() and read() functions which the user can implement. 209 This is the most flexible way. lsquic_stream_write() and 210 lsquic_stream_writev() are now both implemented as wrappers around 211 lsquic_stream_writef(). 212 213 - [OPTIMIZATION] When writing to stream, be it within or without the 214 on_write() callback, place data directly into packet buffer, 215 bypassing auxiliary data structures. This reduces amount of memory 216 required, for the amount of data that can be written is limited 217 by the congestion window. 218 219 To support writes outside the on_write() callback, we keep N 220 outgoing packet buffers per connection which can be written to 221 by any stream. One half of these are reserved for the highest 222 priority stream(s), the other half for all other streams. This way, 223 low-priority streams cannot write instead of high-priority streams 224 and, on the other hand, low-priority streams get a chance to send 225 their packets out. 226 227 The algorithm is as follows: 228 229 - When user writes to stream outside of the callback: 230 - If this is the highest priority stream, place it onto the 231 reserved N/2 queue or fail. 232 (The actual size of this queue is dynamic -- MAX(N/2, CWND) -- 233 rather than N/2, allowing high-priority streams to write as 234 much as can be sent.) 235 - If the stream is not the highest priority, try to place the 236 data onto the reserved N/2 queue or fail. 237 - When tick occurs *and* more packets can be scheduled: 238 - Transfer packets from the high N/2 queue to the scheduled 239 queue. 240 - If more scheduling is allowed: 241 - Call on_write callbacks for highest-priority streams, 242 placing resulting packets directly onto the scheduled queue. 243 - If more scheduling is allowed: 244 - Transfer packets from the low N/2 queue to the scheduled 245 queue. 246 - If more scheduling is allowed: 247 - Call on_write callbacks for non-highest-priority streams, 248 placing resulting packets directly onto the scheduled queue 249 250 The number N is currently 20, but it could be varied based on 251 resource usage. 252 253 - If stream is created due to incoming headers, make headers readable 254 from on_new. 255 256 - Outgoing packets are no longer marked non-writeable to prevent placing 257 more than one STREAM frame from the same stream into a single packet. 258 This property is maintained via code flow and an explicit check. 259 Packets for stream data are allocated using a special function. 260 261 - STREAM frame elision is cheaper, as we only perform it if a reset 262 stream has outgoing packets referencing it. 263 264 - lsquic_packet_out_t is smaller, as stream_rec elements are now 265 inside a union. 266 2672017-10-12 268 269 - Do not send RST_STREAM when stream is closed for reading 270 - Raise maximum header size from 4K to 64K 271 - Check header name and value lengths against maximum imposed by HPACK 272 - Fix NULL dereference in stream flow controller 273 2742017-10-09 275 276 - Hide handshake implementation behind a set of function pointers 277 - Use monotonically increasing clock 278 - Make sure that retx delay is not larger than the max of 60 seconds 279 2802017-09-29 281 282 - A few fixes to code and README 283 2842017-09-28 285 286 - Add support for Q041; drop support for Q040 287 2882017-09-27 289 290 - Fix CMakeLists.txt: BoringSSL include and lib was mixed up 291 2922017-09-26 293 294 - Add support for Mac OS 295 - Add support for Raspberry Pi 296 - Fix BoringSSL compilation: include <openssl/hmac.h> explicitly 297 2982017-09-22 299 300 - Initial release 301