Add support for non-glibc systems
MaxScale can now be built on systems that use an alternative libc implementation e.g. musl.
This commit is contained in:
@ -39,19 +39,12 @@
|
||||
#include <pwd.h>
|
||||
|
||||
#include <maxscale/version.h>
|
||||
#include <maxscale/maxadmin.h>
|
||||
|
||||
#ifdef HISTORY
|
||||
#include <histedit.h>
|
||||
#endif
|
||||
|
||||
#include <maxscale/maxadmin.h>
|
||||
/*
|
||||
* We need a common.h file that is included by every component.
|
||||
*/
|
||||
#if !defined(STRERROR_BUFLEN)
|
||||
#define STRERROR_BUFLEN 512
|
||||
#endif
|
||||
|
||||
#define MAX_PASSWORD_LEN 80
|
||||
|
||||
static int connectUsingUnixSocket(const char *socket);
|
||||
@ -441,27 +434,22 @@ connectUsingUnixSocket(const char *socket_path)
|
||||
}
|
||||
else
|
||||
{
|
||||
char errbuf[STRERROR_BUFLEN];
|
||||
fprintf(stderr, "Could not set SO_PASSCRED: %s\n",
|
||||
strerror_r(errno, errbuf, sizeof(errbuf)));
|
||||
fprintf(stderr, "Could not set SO_PASSCRED: %s\n", strerror(errno));
|
||||
close(so);
|
||||
so = -1;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
char errbuf[STRERROR_BUFLEN];
|
||||
fprintf(stderr, "Unable to connect to MaxScale at %s: %s\n",
|
||||
socket_path, strerror_r(errno, errbuf, sizeof(errbuf)));
|
||||
socket_path, strerror(errno));
|
||||
close(so);
|
||||
so = -1;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
char errbuf[STRERROR_BUFLEN];
|
||||
fprintf(stderr, "Unable to create socket: %s\n",
|
||||
strerror_r(errno, errbuf, sizeof(errbuf)));
|
||||
fprintf(stderr, "Unable to create socket: %s\n", strerror(errno));
|
||||
}
|
||||
|
||||
return so;
|
||||
@ -505,18 +493,15 @@ connectUsingInetSocket(const char *hostname, const char *port,
|
||||
}
|
||||
else
|
||||
{
|
||||
char errbuf[STRERROR_BUFLEN];
|
||||
fprintf(stderr, "Unable to connect to MaxScale at %s, %s: %s\n",
|
||||
hostname, port, strerror_r(errno, errbuf, sizeof(errbuf)));
|
||||
hostname, port, strerror(errno));
|
||||
close(so);
|
||||
so = -1;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
char errbuf[STRERROR_BUFLEN];
|
||||
fprintf(stderr, "Unable to create socket: %s\n",
|
||||
strerror_r(errno, errbuf, sizeof(errbuf)));
|
||||
fprintf(stderr, "Unable to create socket: %s\n", strerror(errno));
|
||||
}
|
||||
|
||||
return so;
|
||||
@ -532,7 +517,7 @@ connectUsingInetSocket(const char *hostname, const char *port,
|
||||
static int
|
||||
setipaddress(struct in_addr *a, const char *p)
|
||||
{
|
||||
#ifdef __USE_POSIX
|
||||
|
||||
struct addrinfo *ai = NULL, hint;
|
||||
int rc;
|
||||
struct sockaddr_in * res_addr;
|
||||
@ -557,28 +542,6 @@ setipaddress(struct in_addr *a, const char *p)
|
||||
|
||||
return 1;
|
||||
}
|
||||
#else
|
||||
struct hostent *h;
|
||||
|
||||
spinlock_acquire(&tmplock);
|
||||
h = gethostbyname(p);
|
||||
spinlock_release(&tmplock);
|
||||
|
||||
if (h == NULL)
|
||||
{
|
||||
if ((a->s_addr = inet_addr(p)) == -1)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
/* take the first one */
|
||||
memcpy(a, h->h_addr, h->h_length);
|
||||
|
||||
return 1;
|
||||
}
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -3,6 +3,7 @@
|
||||
include(CheckFunctionExists)
|
||||
include(CheckLibraryExists)
|
||||
include(CheckIncludeFiles)
|
||||
include(CheckCXXSourceCompiles)
|
||||
|
||||
check_include_files(arpa/inet.h HAVE_ARPA_INET)
|
||||
check_include_files(crypt.h HAVE_CRYPT)
|
||||
@ -69,11 +70,6 @@ if(NOT HAVE_LIBM)
|
||||
message(FATAL_ERROR "Could not find libm")
|
||||
endif()
|
||||
|
||||
find_library(HAVE_LIBDL NAMES dl)
|
||||
if(NOT HAVE_LIBDL)
|
||||
message(FATAL_ERROR "Could not find libdl")
|
||||
endif()
|
||||
|
||||
find_library(HAVE_LIBRT NAMES rt)
|
||||
if(NOT HAVE_LIBRT)
|
||||
message(FATAL_ERROR "Could not find librt")
|
||||
@ -83,3 +79,17 @@ find_library(HAVE_LIBPTHREAD NAMES pthread)
|
||||
if(NOT HAVE_LIBPTHREAD)
|
||||
message(FATAL_ERROR "Could not find libpthread")
|
||||
endif()
|
||||
|
||||
# The XSI version of strerror_r return an int and the GNU version a char*
|
||||
check_cxx_source_compiles("
|
||||
#define _GNU_SOURCE 1
|
||||
#include <string.h>\n
|
||||
int main(){\n
|
||||
char errbuf[200];\n
|
||||
return strerror_r(13, errbuf, sizeof(errbuf)) == errbuf;\n
|
||||
}\n"
|
||||
HAVE_GLIBC)
|
||||
|
||||
if(HAVE_GLIBC)
|
||||
add_definitions(-DHAVE_GLIBC=1)
|
||||
endif()
|
||||
|
@ -33,7 +33,8 @@ MXS_BEGIN_DECLS
|
||||
#define DEFAULT_ADMIN_HTTP_PORT 8989
|
||||
#define DEFAULT_ADMIN_HOST "::"
|
||||
|
||||
#define _RELEASE_STR_LENGTH 256 /**< release len */
|
||||
#define RELEASE_STR_LENGTH 256
|
||||
#define SYSNAME_LEN 256
|
||||
#define MAX_ADMIN_USER_LEN 1024
|
||||
#define MAX_ADMIN_PW_LEN 1024
|
||||
#define MAX_ADMIN_HOST_LEN 1024
|
||||
@ -189,8 +190,8 @@ typedef struct
|
||||
bool config_check; /**< Only check config */
|
||||
int n_threads; /**< Number of polling threads */
|
||||
char *version_string; /**< The version string of embedded db library */
|
||||
char release_string[_RELEASE_STR_LENGTH]; /**< The release name string of the system */
|
||||
char sysname[_UTSNAME_SYSNAME_LENGTH]; /**< The OS name of the system */
|
||||
char release_string[RELEASE_STR_LENGTH]; /**< The release name string of the system */
|
||||
char sysname[SYSNAME_LEN]; /**< The OS name of the system */
|
||||
uint8_t mac_sha1[SHA_DIGEST_LENGTH]; /**< The SHA1 digest of an interface MAC address */
|
||||
unsigned long id; /**< MaxScale ID */
|
||||
unsigned int n_nbpoll; /**< Tune number of non-blocking polls */
|
||||
|
@ -21,6 +21,7 @@
|
||||
#include <math.h>
|
||||
#include <stdlib.h>
|
||||
#include <netinet/in.h>
|
||||
#include <sys/un.h>
|
||||
|
||||
MXS_BEGIN_DECLS
|
||||
|
||||
|
@ -11506,7 +11506,7 @@ else
|
||||
fi
|
||||
|
||||
if test "${enable_maxscale}" = "yes" ; then
|
||||
OPT_FEATURE_FLAGS+=" -DMAXSCALE -DSQLITE_ENABLE_UPDATE_DELETE_LIMIT -DSQLITE_OMIT_ATTACH -DSQLITE_OMIT_REINDEX -DSQLITE_OMIT_AUTOVACUUM -DSQLITE_OMIT_PRAGMA"
|
||||
OPT_FEATURE_FLAGS="$OPT_FEATURE_FLAGS -DMAXSCALE -DSQLITE_ENABLE_UPDATE_DELETE_LIMIT -DSQLITE_OMIT_ATTACH -DSQLITE_OMIT_REINDEX -DSQLITE_OMIT_AUTOVACUUM -DSQLITE_OMIT_PRAGMA"
|
||||
fi
|
||||
|
||||
#########
|
||||
|
@ -69,7 +69,6 @@ target_link_libraries(maxscale-common
|
||||
ssl
|
||||
pthread
|
||||
crypt
|
||||
dl
|
||||
crypto
|
||||
inih
|
||||
z
|
||||
@ -81,6 +80,13 @@ target_link_libraries(maxscale-common
|
||||
${MICROHTTPD_LIBRARIES}
|
||||
)
|
||||
|
||||
find_library(HAVE_LIBDL NAMES dl)
|
||||
if (HAVE_LIBDL)
|
||||
# libdl just exposes libc functionality on most systems. This means that if
|
||||
# we can't find it, it's likely that libc already exposes the symbols.
|
||||
target_link_libraries(maxscale-common dl)
|
||||
endif()
|
||||
|
||||
add_dependencies(maxscale-common pcre2 connector-c)
|
||||
set_target_properties(maxscale-common PROPERTIES VERSION "1.0.0")
|
||||
install_module(maxscale-common core)
|
||||
|
@ -513,6 +513,24 @@ bool admin_linux_account_enabled(const char *uname)
|
||||
return rv;
|
||||
}
|
||||
|
||||
#define MXS_CRYPT_SIZE 60
|
||||
|
||||
void mxs_crypt(const char* password, const char* salt, char* output)
|
||||
{
|
||||
#if HAVE_GLIBC
|
||||
thread_local struct crypt_data cdata;
|
||||
cdata.initialized = 0;
|
||||
char* pw = crypt_r(password, salt, &cdata);
|
||||
snprintf(output, MXS_CRYPT_SIZE, "%s", pw);
|
||||
#else
|
||||
static SPINLOCK mxs_crypt_lock = SPINLOCK_INIT;
|
||||
spinlock_acquire(&mxs_crypt_lock);
|
||||
char* pw = crypt(password, salt);
|
||||
snprintf(output, MXS_CRYPT_SIZE, "%s", pw);
|
||||
spinlock_release(&mxs_crypt_lock);
|
||||
#endif
|
||||
}
|
||||
|
||||
/**
|
||||
* Add insecure remote (network) user.
|
||||
*
|
||||
@ -523,9 +541,8 @@ bool admin_linux_account_enabled(const char *uname)
|
||||
*/
|
||||
const char *admin_add_inet_user(const char *uname, const char* password)
|
||||
{
|
||||
struct crypt_data cdata;
|
||||
cdata.initialized = 0;
|
||||
char *cpassword = crypt_r(password, ADMIN_SALT, &cdata);
|
||||
char cpassword[MXS_CRYPT_SIZE];
|
||||
mxs_crypt(password, ADMIN_SALT, cpassword);
|
||||
|
||||
return admin_add_user(&inet_users, INET_USERS_FILE_NAME, uname, cpassword);
|
||||
}
|
||||
@ -581,9 +598,10 @@ admin_verify_inet_user(const char *username, const char *password)
|
||||
|
||||
if (pw)
|
||||
{
|
||||
struct crypt_data cdata;
|
||||
cdata.initialized = 0;
|
||||
if (strcmp(pw, crypt_r(password, ADMIN_SALT, &cdata)) == 0)
|
||||
char cpassword[MXS_CRYPT_SIZE];
|
||||
mxs_crypt(password, ADMIN_SALT, cpassword);
|
||||
|
||||
if (strcmp(pw, cpassword) == 0)
|
||||
{
|
||||
rv = true;
|
||||
}
|
||||
|
@ -2251,7 +2251,7 @@ config_get_release_string(char* release)
|
||||
};
|
||||
|
||||
bool have_distribution;
|
||||
char distribution[_RELEASE_STR_LENGTH] = "";
|
||||
char distribution[RELEASE_STR_LENGTH] = "";
|
||||
int fd;
|
||||
|
||||
have_distribution = false;
|
||||
@ -2328,7 +2328,7 @@ config_get_release_string(char* release)
|
||||
+5 and -8 below cut the file name part out of the
|
||||
full pathname that corresponds to the mask as above.
|
||||
*/
|
||||
new_to = strncpy(distribution, found.gl_pathv[0] + 5, _RELEASE_STR_LENGTH - 1);
|
||||
new_to = strncpy(distribution, found.gl_pathv[0] + 5, RELEASE_STR_LENGTH - 1);
|
||||
new_to += 8;
|
||||
*new_to++ = ':';
|
||||
*new_to++ = ' ';
|
||||
@ -2348,7 +2348,7 @@ config_get_release_string(char* release)
|
||||
}
|
||||
|
||||
have_distribution = true;
|
||||
strncpy(release, new_to, _RELEASE_STR_LENGTH);
|
||||
strncpy(release, new_to, RELEASE_STR_LENGTH);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -17,7 +17,9 @@
|
||||
|
||||
#include <maxscale/cdefs.h>
|
||||
|
||||
#ifdef HAVE_GLIBC
|
||||
#include <execinfo.h>
|
||||
#endif
|
||||
#include <ftw.h>
|
||||
#include <getopt.h>
|
||||
#include <stdlib.h>
|
||||
@ -100,6 +102,9 @@ static bool daemon_mode = true;
|
||||
static const char* maxscale_commit = MAXSCALE_COMMIT;
|
||||
|
||||
const char *progname = NULL;
|
||||
|
||||
#ifdef HAVE_GLIBC
|
||||
// getopt_long is a GNU extension
|
||||
static struct option long_options[] =
|
||||
{
|
||||
{"config-check", no_argument, 0, 'c'},
|
||||
@ -128,6 +133,7 @@ static struct option long_options[] =
|
||||
{"debug", required_argument, 0, 'g'},
|
||||
{0, 0, 0, 0}
|
||||
};
|
||||
#endif
|
||||
|
||||
static bool syslog_configured = false;
|
||||
static bool maxlog_configured = false;
|
||||
@ -419,6 +425,7 @@ sigfatal_handler(int i)
|
||||
"Release string: %s",
|
||||
maxscale_commit, cnf->sysname, cnf->release_string);
|
||||
|
||||
#ifdef HAVE_GLIBC
|
||||
{
|
||||
void *addrs[128];
|
||||
int count = backtrace(addrs, 128);
|
||||
@ -438,6 +445,7 @@ sigfatal_handler(int i)
|
||||
backtrace_symbols_fd(addrs, count, fileno(stderr));
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
mxs_log_flush_sync();
|
||||
|
||||
@ -1338,8 +1346,12 @@ int main(int argc, char **argv)
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef HAVE_GLIBC
|
||||
while ((opt = getopt_long(argc, argv, "dcf:g:l:vVs:S:?L:D:C:B:U:A:P:G:N:E:F:M:H:",
|
||||
long_options, &option_index)) != -1)
|
||||
#else
|
||||
while ((opt = getopt(argc, argv, "dcf:g:l:vVs:S:?L:D:C:B:U:A:P:G:N:E:F:M:H:")) != -1)
|
||||
#endif
|
||||
{
|
||||
bool succp = true;
|
||||
|
||||
|
@ -23,6 +23,7 @@
|
||||
#include <stdarg.h>
|
||||
#include <errno.h>
|
||||
#include <syslog.h>
|
||||
#include <sched.h>
|
||||
|
||||
#include <maxscale/atomic.h>
|
||||
#include <maxscale/config.h>
|
||||
@ -705,7 +706,7 @@ void mxs_log_finish(void)
|
||||
while (lm != NULL && lm->lm_nlinks != 0)
|
||||
{
|
||||
release_lock(&lmlock);
|
||||
pthread_yield();
|
||||
sched_yield();
|
||||
acquire_lock(&lmlock);
|
||||
}
|
||||
|
||||
@ -1354,7 +1355,7 @@ static bool logmanager_register(bool writep)
|
||||
while (lm != NULL && !lm->lm_enabled)
|
||||
{
|
||||
release_lock(&lmlock);
|
||||
pthread_yield();
|
||||
sched_yield();
|
||||
acquire_lock(&lmlock);
|
||||
}
|
||||
|
||||
@ -3013,8 +3014,12 @@ int mxs_log_message(int priority,
|
||||
const char* mxs_strerror(int error)
|
||||
{
|
||||
static thread_local char errbuf[MXS_STRERROR_BUFLEN];
|
||||
|
||||
#ifdef HAVE_GLIBC
|
||||
return strerror_r(error, errbuf, sizeof(errbuf));
|
||||
#else
|
||||
strerror_r(error, errbuf, sizeof(errbuf));
|
||||
return errbuf;
|
||||
#endif
|
||||
}
|
||||
|
||||
json_t* get_log_priorities()
|
||||
|
@ -31,6 +31,7 @@
|
||||
#include <maxscale/paths.h>
|
||||
#include <maxscale/random_jkiss.h>
|
||||
|
||||
#ifdef HAVE_GLIBC
|
||||
struct option options[] =
|
||||
{
|
||||
{
|
||||
@ -41,6 +42,7 @@ struct option options[] =
|
||||
},
|
||||
{ NULL, 0, NULL, 0 }
|
||||
};
|
||||
#endif
|
||||
|
||||
void print_usage(const char* executable, const char* directory)
|
||||
{
|
||||
@ -67,7 +69,11 @@ int main(int argc, char **argv)
|
||||
const char* directory = get_datadir();
|
||||
|
||||
int c;
|
||||
#ifdef HAVE_GLIBC
|
||||
while ((c = getopt_long(argc, argv, "h", options, NULL)) != -1)
|
||||
#else
|
||||
while ((c = getopt(argc, argv, "h")) != -1)
|
||||
#endif
|
||||
{
|
||||
switch (c)
|
||||
{
|
||||
|
@ -35,6 +35,7 @@
|
||||
|
||||
#include "maxscale/secrets.h"
|
||||
|
||||
#ifdef HAVE_GLIBC
|
||||
struct option options[] =
|
||||
{
|
||||
{
|
||||
@ -45,6 +46,7 @@ struct option options[] =
|
||||
},
|
||||
{ NULL, 0, NULL, 0 }
|
||||
};
|
||||
#endif
|
||||
|
||||
void print_usage(const char* executable, const char* directory)
|
||||
{
|
||||
@ -107,7 +109,11 @@ int main(int argc, char **argv)
|
||||
const char* path = get_datadir();
|
||||
|
||||
int c;
|
||||
#ifdef HAVE_GLIBC
|
||||
while ((c = getopt_long(argc, argv, "h", options, NULL)) != -1)
|
||||
#else
|
||||
while ((c = getopt(argc, argv, "h")) != -1)
|
||||
#endif
|
||||
{
|
||||
switch (c)
|
||||
{
|
||||
|
@ -12,7 +12,6 @@
|
||||
*/
|
||||
|
||||
#include "maxscale/messagequeue.hh"
|
||||
#include <linux/version.h>
|
||||
#include <errno.h>
|
||||
#include <fcntl.h>
|
||||
#include <string.h>
|
||||
|
@ -18,6 +18,7 @@
|
||||
#include <fstream>
|
||||
#include <iostream>
|
||||
#include <pthread.h>
|
||||
#include <sched.h>
|
||||
#include <semaphore.h>
|
||||
#include <maxscale/log_manager.h>
|
||||
#include <maxscale/random_jkiss.h>
|
||||
@ -79,7 +80,7 @@ void log_messages(uint32_t id, size_t n_generate, int priority)
|
||||
{
|
||||
MXS_LOG_MESSAGE(priority, "[%u] Message %lu.", id, i);
|
||||
|
||||
pthread_yield();
|
||||
sched_yield();
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -37,7 +37,6 @@
|
||||
#include <sys/socket.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/un.h>
|
||||
#include <netinet/tcp.h>
|
||||
#include <openssl/sha.h>
|
||||
|
||||
@ -989,7 +988,6 @@ static void set_port(struct sockaddr_storage *addr, uint16_t port)
|
||||
int open_network_socket(enum mxs_socket_type type, struct sockaddr_storage *addr, const char *host, uint16_t port)
|
||||
{
|
||||
ss_dassert(type == MXS_SOCKET_NETWORK || type == MXS_SOCKET_LISTENER);
|
||||
#ifdef __USE_POSIX
|
||||
struct addrinfo *ai = NULL, hint = {};
|
||||
int so, rc;
|
||||
hint.ai_socktype = SOCK_STREAM;
|
||||
@ -1032,10 +1030,6 @@ int open_network_socket(enum mxs_socket_type type, struct sockaddr_storage *addr
|
||||
freeaddrinfo(ai);
|
||||
}
|
||||
|
||||
#else
|
||||
#error Only the POSIX networking interface is supported
|
||||
#endif
|
||||
|
||||
return so;
|
||||
}
|
||||
|
||||
|
@ -2020,9 +2020,9 @@ bool blr_send_event(blr_thread_role_t role,
|
||||
slave->serverid,
|
||||
binlog_name,
|
||||
binlog_pos,
|
||||
thread_self(),
|
||||
(uint64_t)thread_self(),
|
||||
ROLETOSTR(role),
|
||||
slave->lsi_sender_tid,
|
||||
(uint64_t)slave->lsi_sender_tid,
|
||||
ROLETOSTR(slave->lsi_sender_role),
|
||||
gwbuf_length(slave->dcb->writeq), slave->dcb,
|
||||
slave->router->stats.n_binlogs);
|
||||
|
@ -56,6 +56,7 @@ static void printVersion(const char *progname);
|
||||
static void printUsage(const char *progname);
|
||||
static int set_encryption_options(ROUTER_INSTANCE *inst, char *key_file, char *aes_algo);
|
||||
|
||||
#ifdef HAVE_GLIBC
|
||||
static struct option long_options[] =
|
||||
{
|
||||
{"debug", no_argument, 0, 'd'},
|
||||
@ -70,7 +71,7 @@ static struct option long_options[] =
|
||||
{"help", no_argument, 0, '?'},
|
||||
{0, 0, 0, 0}
|
||||
};
|
||||
|
||||
#endif
|
||||
char *binlog_check_version = "2.2.1";
|
||||
|
||||
int
|
||||
@ -90,7 +91,11 @@ int main(int argc, char **argv)
|
||||
char c;
|
||||
BINLOG_FILE_FIX binlog_file = {0, false, false};
|
||||
|
||||
#ifdef HAVE_GLIBC
|
||||
while ((c = getopt_long(argc, argv, "dVfMHK:A:R:T:?", long_options, &option_index)) >= 0)
|
||||
#else
|
||||
while ((c = getopt(argc, argv, "dVfMHK:A:R:T:?")) >= 0)
|
||||
#endif
|
||||
{
|
||||
switch (c)
|
||||
{
|
||||
|
Reference in New Issue
Block a user