Compared to the previous implementation based on OpenSSL, the new implementation
has these advantages:
1. Strict and reliable detection of invalid strings, including strings with
less than 4 bytes of garbage at the end;
2. Allows to use Base64 strings without '=' padding.
The "auto_globals_jit" PHP option postponed the initialization of the $_SERVER
global variable until the script using it had been loaded (e. g. via the
"include" expression). As a result, nxt_php_register_variables() could be
called after fastcgi_finish_request() had finished the request and nulled
ctx->req, which thus caused a segmentation fault.
This makes the "sed" instruction simpler and more portable, as the previous
variant didn't work well on BSD systems due to the "\s" metacharacter.
Thanks to Sergey A. Osokin <osa@FreeBSD.org.ru> for spotting this issue.
Also, this should prevent accidentally creating a version 1.0.0 package.
The idea is to put SAN after CN, but the previous version of the code
incorrectly assumed that CN was always present, which caused writes
outside the allocated object if there were no standard name attributes.
Previously, entries of any type were counted during object allocation
but only DNS type entries were actually processed. As a result,
if some certificate entries had another type, returning information
about the certificate caused uninitialized memory access.
It feels to be causing more harm than good, because syslog() can be blocking,
which is even more critical under resource exhaustion conditions when some
alerts are expected.
The Ruby interpreter expects an explicit setlocale() call before initialization
to pick up character encodings in the "Encoding" class from the environment.
This closes#531 issue on GitHub.
It appears that readdir() on Linux detects file types unreliably, always setting
the "d_type" field to DT_UNKNOWN for some less common filesystems. As a result,
all files were skipped and no certificate bundles were found when the state
directory was located on such filesystems.
Skipping "." and ".." instead of any non-regular files should be enough, as no
other non-regular files normally appear in this directory.
This closes#368 issue on GitHub.
An immediate return statement on connection errors was mistakenly added to the
beginning of nxt_openssl_conn_io_shutdown() in ecd3c5bbf7d8, breaking the TLS
connection finalization procedure. As a result, a TLS connection was left
unfinalized if it had been closed prematurely or a fatal protocol error had
occurred, which caused memory and socket descriptor leakage.
Moreover, in some cases (notably, on handshake errors in tests with kqueue on
macOS) the read event was triggered later and nxt_h1p_conn_error() was called
the second time; after the change in af93c866b4f0, the latter call crashed the
router process in an attempt to remove a connection from the idle queue twice.
The WSGI environment dictionary contains a number of static items, that are
pre-initialized on application start. Then it's copied for each request to be
filled with request-related data.
Now this dictionary copy operation will be done between processing of requests,
which should save some CPU cycles during request processing and thus reduce
response latency for non-peak load periods.
According to Section #3.1.2 of RFC 7230, after the status code
there must be a space even if the reason phrase is empty.
Also, only 3 digits allowed.
This closes#507 issue on GitHub.
Previously, all requests that contained in header field names characters other
than alphanumeric, or "-", or "_" were rejected with a 400 "Bad Request" error
response.
Now, the parser allows the same set of characters as specified in RFC 7230,
including: "!", "#", "$", "%", "&", "'", "*", "+", ".", "^", "`", "|", and "~".
Header field names that contain only these characters are considered valid.
Also, there's a new option introduced: "discard_unsafe_fields". It accepts
boolean value and it is set to "true" by default.
When this option is "true", all header field names that contain characters
in valid range, but other than alphanumeric or "-" are skipped during parsing.
When the option is "false", these header fields aren't skipped.
Requests with non-valid characters in header field names according to
RFC 7230 are rejected regardless of "discard_unsafe_fields" setting.
This closes#422 issue on GitHub.
The php_request_shutdown() function calls sapi_deactivate() that tries to read
request body into a dummy buffer. In our case it's just waste of CPU cycles.
This change is also required for the following implementation of the
fastcgi_finish_request() function, where the request context can be
cleared by the time of finalization.
This variant will be more interoperable across various systems
and it's already used in Ruby module.
Otherwise, configure tests fail on NetBSD with:
gcc: Missing argument for -Wl,-rpath
PyUnicode_GET_SIZE() in deprecated since 3.3 and will be removed in 3.12.
In version 3.9 it was explicitly marked by deprecation warning causing
compilation error with Unit.
PyUnicode_GET_LENGTH() must be used instead.
AVIF is a modern image format based on the AV1 video codec. It generally has
better compression than other widely used formats (WebP, JPEG, PNG, and GIF)
and is designed to supersede them. Support was already added to the latest
version of Chrome.
APNG extends PNG to permit animated images that work similarly to animated GIF.
It's supported by most modern browsers.
Also removed duplicated ".svg" entry.
It's not used since cbcd76704c90.
This option is a leftover from previous IPC between router and applications
processes. It was never documented, though.
Thanks to 洪志道 (Hong Zhi Dao).
An attempt to build a Ruby module for a custom Ruby installation that has the
same major version as the system Ruby may unexpectedly cause the use of the
system Ruby library.
This closes#449 issue on GitHub.
The invocation parameters should be logged as well, notably the path of the file
that is failed to be created.
Also, log level changed to ALERT as it's quite critical error.
Earlier, if nxt_mp_create() failed to allocate memory while accepting a new
connection, the resulting NULL was subsequently passed to nxt_mp_destroy(),
crashing the process.
More, if nxt_mp_create() was successful but nxt_sockaddr_cache_alloc() failed,
the connection object wasn't destroyed properly, leaving the connection counter
in an inconsistent state. Repeated, this condition lowered the connection
capacity of the process and could eventually prevent it from accepting
connections altogether.
Previously, the log message callback used a generic log function, that relied on the process time cache.
Since there were no time update calls in the application processes, all log lines were printed with the
same time, usually correlated with the process start.
Now, a non-cached logging function from libunit is used.
This makes log format used in libunit consistent with the daemon, where milliseconds are printed only in the
debug log level.
Currently a compile time switch is used, since there's no support for runtime changing of a log level for now.
But in the future this should be a runtime condition, similar to nxt_log_time_handler().
According to the C standard, pointer arguments passed to memcpy() calls shall
still have valid values. NULL is considered as invalid.
Found with GCC Static Analyzer.
This is useful to escape "/" in path fragments. For example, in order
to reference the application named "foo/bar":
{
"pass": "applications/foo%2Fbar"
}
One of the ways to detect Unit's startup and subsequent readiness to accept
commands relies on waiting for the control socket file to be created.
Earlier, it was unreliable due to a race condition between the client's
connect() and the daemon's listen() calls after the socket's bind() call.
Now, unix domain listening sockets are created with a nxt_listen_socket_create()
call as follows:
s = socket();
unlink("path/to/socket.tmp")
bind(s, "path/to/socket.tmp");
listen(s);
rename("path/to/socket.tmp", "path/to/socket");
This eliminates a time-lapse when the socket file is already created but nobody
is listening on it yet, which therefore prevents the condition described above.
Also, it allows reliably detecting whether the socket is being used or simply
wasn't cleaned after the daemon stopped abruptly. A successful connection to
the socket file means the daemon has been started; otherwise, the file can be
overwritten.