2021-05-24 21:49:35 +02:00
|
|
|
/* SPDX-License-Identifier: LGPL-2.1-or-later */
|
|
|
|
|
|
|
|
|
|
/* Copyright (C) 2021 Red Hat, Inc. */
|
|
|
|
|
|
|
|
|
|
#include <stdio.h>
|
|
|
|
|
#include <stdlib.h>
|
2021-05-25 09:38:27 +02:00
|
|
|
#include <arpa/inet.h>
|
|
|
|
|
#include <netdb.h>
|
2021-06-16 18:17:11 +02:00
|
|
|
#if defined(__GLIBC__)
|
2021-06-16 18:32:01 +02:00
|
|
|
#include <nss.h>
|
2021-06-16 18:17:11 +02:00
|
|
|
#endif
|
2021-05-24 21:49:35 +02:00
|
|
|
|
|
|
|
|
#include "libnm-std-aux/nm-std-aux.h"
|
|
|
|
|
|
|
|
|
|
enum {
|
|
|
|
|
RETURN_SUCCESS = 0,
|
|
|
|
|
RETURN_INVALID_CMD = 1,
|
|
|
|
|
RETURN_INVALID_ARGS = 2,
|
|
|
|
|
RETURN_ERROR = 3,
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
static char *
|
|
|
|
|
read_arg(void)
|
|
|
|
|
{
|
|
|
|
|
nm_auto_free char *arg = NULL;
|
|
|
|
|
size_t len = 0;
|
|
|
|
|
|
|
|
|
|
if (getdelim(&arg, &len, '\0', stdin) < 0)
|
|
|
|
|
return NULL;
|
|
|
|
|
|
|
|
|
|
return nm_steal_pointer(&arg);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
static int
|
|
|
|
|
more_args(void)
|
|
|
|
|
{
|
|
|
|
|
nm_auto_free char *arg = NULL;
|
|
|
|
|
|
|
|
|
|
arg = read_arg();
|
|
|
|
|
|
|
|
|
|
return !!arg;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
static int
|
|
|
|
|
cmd_version(void)
|
|
|
|
|
{
|
|
|
|
|
if (more_args())
|
|
|
|
|
return RETURN_INVALID_ARGS;
|
|
|
|
|
|
|
|
|
|
printf("1");
|
|
|
|
|
return RETURN_SUCCESS;
|
|
|
|
|
}
|
|
|
|
|
|
2021-05-25 09:38:27 +02:00
|
|
|
static int
|
|
|
|
|
cmd_resolve_address(void)
|
|
|
|
|
{
|
|
|
|
|
nm_auto_free char *address = NULL;
|
|
|
|
|
union {
|
|
|
|
|
struct sockaddr_in in;
|
|
|
|
|
struct sockaddr_in6 in6;
|
|
|
|
|
} sockaddr;
|
|
|
|
|
socklen_t sockaddr_size;
|
|
|
|
|
char name[NI_MAXHOST];
|
|
|
|
|
|
|
|
|
|
address = read_arg();
|
|
|
|
|
if (!address)
|
|
|
|
|
return RETURN_INVALID_ARGS;
|
|
|
|
|
|
|
|
|
|
if (more_args())
|
|
|
|
|
return RETURN_INVALID_ARGS;
|
|
|
|
|
|
|
|
|
|
memset(&sockaddr, 0, sizeof(sockaddr));
|
2021-06-16 18:17:11 +02:00
|
|
|
#if defined(__GLIBC__)
|
2021-05-25 09:38:27 +02:00
|
|
|
__nss_configure_lookup("hosts", "dns");
|
2021-06-16 18:17:11 +02:00
|
|
|
#endif
|
2021-05-25 09:38:27 +02:00
|
|
|
|
|
|
|
|
if (inet_pton(AF_INET, address, &sockaddr.in.sin_addr) == 1) {
|
|
|
|
|
sockaddr.in.sin_family = AF_INET;
|
|
|
|
|
sockaddr_size = sizeof(struct sockaddr_in);
|
|
|
|
|
} else if (inet_pton(AF_INET6, address, &sockaddr.in6.sin6_addr) == 1) {
|
|
|
|
|
sockaddr.in6.sin6_family = AF_INET6;
|
|
|
|
|
sockaddr_size = sizeof(struct sockaddr_in6);
|
|
|
|
|
} else
|
|
|
|
|
return RETURN_INVALID_ARGS;
|
|
|
|
|
|
|
|
|
|
if (getnameinfo((struct sockaddr *) &sockaddr,
|
|
|
|
|
sockaddr_size,
|
|
|
|
|
name,
|
|
|
|
|
sizeof(name),
|
|
|
|
|
NULL,
|
|
|
|
|
0,
|
|
|
|
|
NI_NAMEREQD)
|
|
|
|
|
!= 0)
|
|
|
|
|
return RETURN_ERROR;
|
|
|
|
|
|
|
|
|
|
printf("%s", name);
|
|
|
|
|
|
|
|
|
|
return RETURN_SUCCESS;
|
|
|
|
|
}
|
|
|
|
|
|
2021-05-24 21:49:35 +02:00
|
|
|
int
|
|
|
|
|
main(int argc, char **argv)
|
|
|
|
|
{
|
|
|
|
|
nm_auto_free char *cmd = NULL;
|
|
|
|
|
|
|
|
|
|
cmd = read_arg();
|
|
|
|
|
if (!cmd)
|
|
|
|
|
return RETURN_INVALID_CMD;
|
|
|
|
|
|
2021-05-25 09:38:27 +02:00
|
|
|
if (nm_streq(cmd, "version"))
|
2021-05-24 21:49:35 +02:00
|
|
|
return cmd_version();
|
2021-05-25 09:38:27 +02:00
|
|
|
if (nm_streq(cmd, "resolve-address"))
|
|
|
|
|
return cmd_resolve_address();
|
2021-05-24 21:49:35 +02:00
|
|
|
|
|
|
|
|
return RETURN_INVALID_CMD;
|
|
|
|
|
}
|