mirror of
https://github.com/MariaDB/server.git
synced 2026-01-06 05:22:24 +03:00
MDEV-15655: Add Linux abstract socket support
The functionality of the socket system variable is extended
here such that a preciding '@' indicates that the socket
will be an abstract socket. Thie socket name wil be
the remainder of the name after the '@'. This is consistent
with the approached used by systemd in socket activation.
Thanks to Sergey Vojtovich:
On OS X sockaddr_un is defined as:
struct sockaddr_un
{
u_char sun_len;
u_char sun_family;
char sun_path[104];
};
There is a comment in man 7 unix (on linux):
"
On Linux, the above offsetof() expression equates to the same value as sizeof(sa_family_t),
but some other implementations include other fields before sun_path, so the offsetof()
expression more portably describes the size of the address structure.
"
As such, use the offsetof for Linux and use the previous sizeof(UNIXaddr)
for non-unix platforms as that's what worked before and they don't
support abstract sockets so there's no compatibility problem..
strace -fe trace=networking mysqld --skip-networking --socket @abc ...
...
[pid 10578] socket(AF_UNIX, SOCK_STREAM|SOCK_CLOEXEC, 0) = 22
[pid 10578] setsockopt(22, SOL_SOCKET, SO_REUSEADDR, [1], 4) = 0
[pid 10578] bind(22, {sa_family=AF_UNIX, sun_path=@"abc"}, 6) = 0
[pid 10578] listen(22, 80) = 0
...
Version: '10.3.6-MariaDB-log' socket: '@abc' port: 0 Source distribution
$ lsof -p 10578
mysqld 10578 dan 22u unix 0x00000000087e688c 0t0 4787815 @abc type=STREAM
This commit is contained in:
committed by
Sergey Vojtovich
parent
eaaf004cc1
commit
08098366d2
@@ -2784,9 +2784,10 @@ static void network_init(void)
|
||||
*/
|
||||
if (mysqld_unix_port[0] && !opt_bootstrap)
|
||||
{
|
||||
size_t port_len;
|
||||
DBUG_PRINT("general",("UNIX Socket is %s",mysqld_unix_port));
|
||||
|
||||
if (strlen(mysqld_unix_port) > (sizeof(UNIXaddr.sun_path) - 1))
|
||||
if ((port_len=strlen(mysqld_unix_port)) > (sizeof(UNIXaddr.sun_path) - 1))
|
||||
{
|
||||
sql_print_error("The socket file path is too long (> %u): %s",
|
||||
(uint) sizeof(UNIXaddr.sun_path) - 1, mysqld_unix_port);
|
||||
@@ -2804,14 +2805,25 @@ static void network_init(void)
|
||||
bzero((char*) &UNIXaddr, sizeof(UNIXaddr));
|
||||
UNIXaddr.sun_family = AF_UNIX;
|
||||
strmov(UNIXaddr.sun_path, mysqld_unix_port);
|
||||
(void) unlink(mysqld_unix_port);
|
||||
#if defined(__linux__)
|
||||
/* Abstract socket */
|
||||
if (mysqld_unix_port[0] == '@')
|
||||
UNIXaddr.sun_path[0]= '\0';
|
||||
else
|
||||
#endif
|
||||
(void) unlink(mysqld_unix_port);
|
||||
arg= 1;
|
||||
(void) mysql_socket_setsockopt(unix_sock,SOL_SOCKET,SO_REUSEADDR,
|
||||
(char*)&arg, sizeof(arg));
|
||||
umask(0);
|
||||
if (mysql_socket_bind(unix_sock,
|
||||
reinterpret_cast<struct sockaddr *>(&UNIXaddr),
|
||||
sizeof(UNIXaddr)) < 0)
|
||||
#if defined(__linux__)
|
||||
offsetof(struct sockaddr_un, sun_path) + port_len
|
||||
#else
|
||||
sizeof(UNIXaddr)
|
||||
#endif
|
||||
) < 0)
|
||||
{
|
||||
sql_perror("Can't start server : Bind on unix socket"); /* purecov: tested */
|
||||
sql_print_error("Do you already have another mysqld server running on socket: %s ?",mysqld_unix_port);
|
||||
|
||||
Reference in New Issue
Block a user