Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
23 changes: 21 additions & 2 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -251,8 +251,13 @@ if(ENABLE_SSH)
include_directories(${LIBSSH_INCLUDE_DIRS})

# crypt
target_link_libraries(netconf2 -lcrypt)
list(APPEND CMAKE_REQUIRED_LIBRARIES crypt)
if(NOT ${CMAKE_SYSTEM_NAME} MATCHES "QNX")
target_link_libraries(netconf2 -lcrypt)
list(APPEND CMAKE_REQUIRED_LIBRARIES crypt)
else()
target_link_libraries(netconf2 -llogin)
list(APPEND CMAKE_REQUIRED_LIBRARIES login)
endif()
endif()

# dependencies - libval
Expand All @@ -268,6 +273,20 @@ find_package(LibYANG REQUIRED)
target_link_libraries(netconf2 ${LIBYANG_LIBRARIES})
include_directories(${LIBYANG_INCLUDE_DIRS})

# header file compatibility - shadow.h and crypt.h
check_include_file("shadow.h" HAVE_SHADOW)
check_include_file("crypt.h" HAVE_CRYPT)

# function compatibility - getpeereid on QNX
if(${CMAKE_SYSTEM_NAME} MATCHES "QNX")
target_link_libraries(netconf2 -lsocket)
list(APPEND CMAKE_REQUIRED_LIBRARIES socket)
list(REMOVE_ITEM CMAKE_REQUIRED_LIBRARIES pthread)
list(APPEND CMAKE_REQUIRED_DEFINITIONS -D_QNX_SOURCE)
check_symbol_exists(getpeereid "sys/types.h;unistd.h" HAVE_GETPEEREID)
list(REMOVE_ITEM CMAKE_REQUIRED_DEFINITIONS -D_QNX_SOURCE)
endif()

# generate doxygen documentation for libnetconf2 API
find_package(Doxygen)
if(DOXYGEN_FOUND)
Expand Down
15 changes: 15 additions & 0 deletions src/config.h.in
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,21 @@
*/
#cmakedefine HAVE_PTHREAD_MUTEX_TIMEDLOCK

/*
* Support for getpeereid
*/
#cmakedefine HAVE_GETPEEREID

/*
* Support for shadow file manipulation
*/
#cmakedefine HAVE_SHADOW

/*
* Support for crypt.h
*/
#cmakedefine HAVE_CRYPT

/*
* Location of installed basic YIN/YANG schemas
*/
Expand Down
42 changes: 32 additions & 10 deletions src/session_server.c
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@
*
* https://opensource.org/licenses/BSD-3-Clause
*/
#define _QNX_SOURCE /* getpeereid */
#define _GNU_SOURCE /* signals, threads, SO_PEERCRED */

#include <stdint.h>
Expand Down Expand Up @@ -1717,27 +1718,48 @@ nc_ps_clear(struct nc_pollsession *ps, int all, void (*data_free)(void *))

#if defined(NC_ENABLED_SSH) || defined(NC_ENABLED_TLS)

static int
nc_get_uid(int sock, uid_t *uid)
{
#ifdef SO_PEERCRED
struct ucred ucred;
socklen_t len;
len = sizeof(ucred);
if (getsockopt(sock, SOL_SOCKET, SO_PEERCRED, &ucred, &len) < 0) {
ERR("Failed to get credentials from unix socket (%s).",
strerror(errno));
close(sock);
return -1;
}
*uid = ucred.uid;
#else
if (getpeereid(sock, uid, NULL) < 0) {
ERR("Failed to get credentials from unix socket (%s).",
strerror(errno));
close(sock);
return -1;
}
#endif

return 0;
}

static int
nc_accept_unix(struct nc_session *session, int sock)
{
#ifdef SO_PEERCRED
#if defined(SO_PEERCRED) || defined(HAVE_GETPEEREID)
const struct passwd *pw;
struct ucred ucred;
char *username;
socklen_t len;
session->ti_type = NC_TI_UNIX;
uid_t uid;

len = sizeof(ucred);
if (getsockopt(sock, SOL_SOCKET, SO_PEERCRED, &ucred, &len) < 0) {
ERR("Failed to get credentials from unix socket (%s).",
strerror(errno));
close(sock);
if (nc_get_uid(sock, &uid) < 0) {
return -1;
}

pw = getpwuid(ucred.uid);
pw = getpwuid(uid);
if (pw == NULL) {
ERR("Failed to find username for uid=%u (%s).\n", ucred.uid,
ERR("Failed to find username for uid=%u (%s).\n", uid,
strerror(errno));
close(sock);
return -1;
Expand Down
22 changes: 15 additions & 7 deletions src/session_server_ssh.c
Original file line number Diff line number Diff line change
Expand Up @@ -14,21 +14,25 @@

#define _GNU_SOURCE

#include "config.h" /* Expose HAVE_SHADOW and HAVE_CRYPT */

#ifdef HAVE_SHADOW
#include <shadow.h>
#endif
#ifdef HAVE_CRYPT
#include <crypt.h>
#endif

#include <stdlib.h>
#include <string.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <pwd.h>
#ifndef __APPLE__
#include <shadow.h>
#include <crypt.h>
#endif
#include <errno.h>
#include <time.h>
#include <fcntl.h>
#include <unistd.h>

#include "config.h"
#include "session_server.h"
#include "session_server_ch.h"
#include "libnetconf.h"
Expand Down Expand Up @@ -664,7 +668,7 @@ nc_server_ssh_clear_opts(struct nc_server_ssh_opts *opts)
static char *
auth_password_get_pwd_hash(const char *username)
{
#ifndef __APPLE__
#ifdef HAVE_SHADOW
struct passwd *pwd, pwd_buf;
struct spwd *spwd, spwd_buf;
char *pass_hash = NULL, buf[256];
Expand All @@ -676,7 +680,11 @@ auth_password_get_pwd_hash(const char *username)
}

if (!strcmp(pwd->pw_passwd, "x")) {
getspnam_r(username, &spwd_buf, buf, 256, &spwd);
#ifndef __QNXNTO__
getspnam_r(username, &spwd_buf, buf, 256, &spwd);
#else
spwd = getspnam_r(username, &spwd_buf, buf, 256);
#endif
if (!spwd) {
VRB("Failed to retrieve the shadow entry for \"%s\".", username);
return NULL;
Expand Down