forked from nuttx/nuttx-update
libs/libc/unistd: add getspnam function
Add getspnam function to pass tlpi example: https://man7.org/tlpi/code/online/dist/users_groups/check_password.c.html Signed-off-by: chenzhijia <chenzhijia@xiaomi.com>
This commit is contained in:
parent
2a328279ca
commit
d52074a9cb
7 changed files with 323 additions and 5 deletions
59
include/shadow.h
Normal file
59
include/shadow.h
Normal file
|
@ -0,0 +1,59 @@
|
||||||
|
/****************************************************************************
|
||||||
|
* include/shadow.h
|
||||||
|
*
|
||||||
|
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||||
|
* contributor license agreements See the NOTICE file distributed with
|
||||||
|
* this work for additional information regarding copyright ownership The
|
||||||
|
* ASF licenses this file to you under the Apache License, Version 2.0 (the
|
||||||
|
* "License"); you may not use this file except in compliance with the
|
||||||
|
* License You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||||
|
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied See the
|
||||||
|
* License for the specific language governing permissions and limitations
|
||||||
|
* under the License.
|
||||||
|
*
|
||||||
|
****************************************************************************/
|
||||||
|
|
||||||
|
#ifndef __INCLUDE_SHADOW_H
|
||||||
|
#define __INCLUDE_SHADOW_H
|
||||||
|
|
||||||
|
/****************************************************************************
|
||||||
|
* Included Files
|
||||||
|
****************************************************************************/
|
||||||
|
|
||||||
|
#include <nuttx/compiler.h>
|
||||||
|
|
||||||
|
/****************************************************************************
|
||||||
|
* Public Type Declarations
|
||||||
|
****************************************************************************/
|
||||||
|
|
||||||
|
/* Structure of the password file */
|
||||||
|
|
||||||
|
struct spwd
|
||||||
|
{
|
||||||
|
FAR char *sp_namp; /* Login name */
|
||||||
|
FAR char *sp_pwdp; /* Encrypted password */
|
||||||
|
long int sp_lstchg; /* Date of last change */
|
||||||
|
long int sp_min; /* Minimum number of days between changes */
|
||||||
|
long int sp_max; /* Maximum number of days between changes */
|
||||||
|
long int sp_warn; /* Number of days to warn user to change the password */
|
||||||
|
long int sp_inact; /* Number of days the account may be inactive */
|
||||||
|
long int sp_expire; /* Number of days since 1970-01-01 until account expires */
|
||||||
|
unsigned long int sp_flag; /* Reserved */
|
||||||
|
};
|
||||||
|
|
||||||
|
/****************************************************************************
|
||||||
|
* Public Function Prototypes
|
||||||
|
****************************************************************************/
|
||||||
|
|
||||||
|
/* Get shadow entry matching NAME */
|
||||||
|
|
||||||
|
FAR struct spwd *getspnam(FAR const char *name);
|
||||||
|
int getspnam_r(FAR const char *name, FAR struct spwd *sp, FAR char *buf,
|
||||||
|
size_t size, FAR struct spwd **res);
|
||||||
|
|
||||||
|
#endif /* __INCLUDE_SHADOW_H */
|
|
@ -19,11 +19,17 @@
|
||||||
# the License.
|
# the License.
|
||||||
#
|
#
|
||||||
# ##############################################################################
|
# ##############################################################################
|
||||||
set(SRCS lib_getpwnam.c lib_getpwnamr.c lib_getpwuid.c lib_getpwuidr.c
|
set(SRCS
|
||||||
lib_getpwent.c lib_pwd_globals.c)
|
lib_getpwnam.c
|
||||||
|
lib_getpwnamr.c
|
||||||
|
lib_getpwuid.c
|
||||||
|
lib_getpwuidr.c
|
||||||
|
lib_getpwent.c
|
||||||
|
lib_pwd_globals.c
|
||||||
|
lib_getspnam.c)
|
||||||
|
|
||||||
if(CONFIG_LIBC_PASSWD_FILE)
|
if(CONFIG_LIBC_PASSWD_FILE)
|
||||||
list(APPEND SRCS lib_find_pwdfile.c)
|
list(APPEND SRCS lib_find_pwdfile.c lib_getspnamr.c)
|
||||||
else()
|
else()
|
||||||
list(APPEND SRCS lib_getpwbuf.c lib_getpwbufr.c)
|
list(APPEND SRCS lib_getpwbuf.c lib_getpwbufr.c)
|
||||||
endif()
|
endif()
|
||||||
|
|
|
@ -23,10 +23,10 @@
|
||||||
# Add the pwd C files to the build
|
# Add the pwd C files to the build
|
||||||
|
|
||||||
CSRCS += lib_getpwnam.c lib_getpwnamr.c lib_getpwuid.c lib_getpwuidr.c
|
CSRCS += lib_getpwnam.c lib_getpwnamr.c lib_getpwuid.c lib_getpwuidr.c
|
||||||
CSRCS += lib_getpwent.c lib_pwd_globals.c
|
CSRCS += lib_getpwent.c lib_pwd_globals.c lib_getspnam.c
|
||||||
|
|
||||||
ifeq ($(CONFIG_LIBC_PASSWD_FILE),y)
|
ifeq ($(CONFIG_LIBC_PASSWD_FILE),y)
|
||||||
CSRCS += lib_find_pwdfile.c
|
CSRCS += lib_find_pwdfile.c lib_getspnamr.c
|
||||||
else
|
else
|
||||||
CSRCS += lib_getpwbuf.c lib_getpwbufr.c
|
CSRCS += lib_getpwbuf.c lib_getpwbufr.c
|
||||||
endif
|
endif
|
||||||
|
|
60
libs/libc/pwd/lib_getspnam.c
Normal file
60
libs/libc/pwd/lib_getspnam.c
Normal file
|
@ -0,0 +1,60 @@
|
||||||
|
/****************************************************************************
|
||||||
|
* libs/libc/pwd/lib_getspnam.c
|
||||||
|
*
|
||||||
|
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||||
|
* contributor license agreements. See the NOTICE file distributed with
|
||||||
|
* this work for additional information regarding copyright ownership. The
|
||||||
|
* ASF licenses this file to you under the Apache License, Version 2.0 (the
|
||||||
|
* "License"); you may not use this file except in compliance with the
|
||||||
|
* License. You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||||
|
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||||
|
* License for the specific language governing permissions and limitations
|
||||||
|
* under the License.
|
||||||
|
*
|
||||||
|
****************************************************************************/
|
||||||
|
|
||||||
|
/****************************************************************************
|
||||||
|
* Included Files
|
||||||
|
****************************************************************************/
|
||||||
|
|
||||||
|
#include <nuttx/config.h>
|
||||||
|
|
||||||
|
#include <pwd.h>
|
||||||
|
#include <shadow.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
#include "pwd/lib_pwd.h"
|
||||||
|
|
||||||
|
/****************************************************************************
|
||||||
|
* Public Functions
|
||||||
|
****************************************************************************/
|
||||||
|
|
||||||
|
FAR struct spwd *getspnam(FAR const char *name)
|
||||||
|
{
|
||||||
|
FAR struct spwd *result = NULL;
|
||||||
|
|
||||||
|
#ifdef CONFIG_LIBC_PASSWD_FILE
|
||||||
|
getspnam_r(name, &g_spwd, g_passwd_buffer,
|
||||||
|
sizeof(g_passwd_buffer), &result);
|
||||||
|
#else
|
||||||
|
if (strcmp(name, ROOT_NAME) == 0)
|
||||||
|
{
|
||||||
|
size_t nsize = sizeof(ROOT_NAME);
|
||||||
|
size_t psize = sizeof(ROOT_PWDP);
|
||||||
|
result = &g_spwd;
|
||||||
|
|
||||||
|
result->sp_namp = g_passwd_buffer;
|
||||||
|
result->sp_pwdp = &g_passwd_buffer[nsize];
|
||||||
|
|
||||||
|
strlcpy(result->sp_namp, ROOT_NAME, nsize);
|
||||||
|
strlcpy(result->sp_pwdp, ROOT_PWDP, psize);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
return result;
|
||||||
|
}
|
189
libs/libc/pwd/lib_getspnamr.c
Normal file
189
libs/libc/pwd/lib_getspnamr.c
Normal file
|
@ -0,0 +1,189 @@
|
||||||
|
/****************************************************************************
|
||||||
|
* libs/libc/pwd/lib_getspnamr.c
|
||||||
|
*
|
||||||
|
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||||
|
* contributor license agreements. See the NOTICE file distributed with
|
||||||
|
* this work for additional information regarding copyright ownership. The
|
||||||
|
* ASF licenses this file to you under the Apache License, Version 2.0 (the
|
||||||
|
* "License"); you may not use this file except in compliance with the
|
||||||
|
* License. You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||||
|
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||||
|
* License for the specific language governing permissions and limitations
|
||||||
|
* under the License.
|
||||||
|
*
|
||||||
|
****************************************************************************/
|
||||||
|
|
||||||
|
/****************************************************************************
|
||||||
|
* Included Files
|
||||||
|
****************************************************************************/
|
||||||
|
|
||||||
|
#include <nuttx/config.h>
|
||||||
|
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <string.h>
|
||||||
|
#include <shadow.h>
|
||||||
|
|
||||||
|
/****************************************************************************
|
||||||
|
* Pre-processor Definitions
|
||||||
|
****************************************************************************/
|
||||||
|
|
||||||
|
#define BUFFER_EXTRA 100
|
||||||
|
|
||||||
|
/****************************************************************************
|
||||||
|
* Private Functions
|
||||||
|
****************************************************************************/
|
||||||
|
|
||||||
|
/* This implementation support Openwall-style TCB passwords in place of
|
||||||
|
* traditional shadow, if the appropriate directories and files exist.
|
||||||
|
* Thus, it is careful to avoid following symlinks or blocking on fifos
|
||||||
|
* which a malicious user might create in place of his or her TCB shadow
|
||||||
|
* file. It also avoids any allocation to prevent memory-exhaustion
|
||||||
|
* attacks via huge TCB shadow files
|
||||||
|
*/
|
||||||
|
|
||||||
|
static long xatol(FAR char **s)
|
||||||
|
{
|
||||||
|
if (**s == ':' || **s == '\n')
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
return strtol(*s, &(*s), 10);
|
||||||
|
}
|
||||||
|
|
||||||
|
static int parsespent(FAR char *s, FAR struct spwd *sp)
|
||||||
|
{
|
||||||
|
sp->sp_namp = s;
|
||||||
|
if (!(s = strchr(s, ':')))
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
*s = 0;
|
||||||
|
sp->sp_pwdp = ++s;
|
||||||
|
if (!(s = strchr(s, ':')))
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
*s = 0;
|
||||||
|
s++;
|
||||||
|
sp->sp_lstchg = xatol(&s);
|
||||||
|
if (*s != ':')
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
s++;
|
||||||
|
sp->sp_min = xatol(&s);
|
||||||
|
if (*s != ':')
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
s++;
|
||||||
|
sp->sp_max = xatol(&s);
|
||||||
|
if (*s != ':')
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
s++;
|
||||||
|
sp->sp_warn = xatol(&s);
|
||||||
|
if (*s != ':')
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
s++;
|
||||||
|
sp->sp_inact = xatol(&s);
|
||||||
|
if (*s != ':')
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
s++;
|
||||||
|
sp->sp_expire = xatol(&s);
|
||||||
|
if (*s != ':')
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
s++;
|
||||||
|
sp->sp_flag = xatol(&s);
|
||||||
|
if (*s != '\n')
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/****************************************************************************
|
||||||
|
* Public Functions
|
||||||
|
****************************************************************************/
|
||||||
|
|
||||||
|
int getspnam_r(FAR const char *name, FAR struct spwd *sp, FAR char *buf,
|
||||||
|
size_t size, FAR struct spwd **res)
|
||||||
|
{
|
||||||
|
size_t l = strlen(name);
|
||||||
|
size_t k;
|
||||||
|
FAR FILE *f;
|
||||||
|
int skip = 0;
|
||||||
|
|
||||||
|
*res = NULL;
|
||||||
|
|
||||||
|
/* Disallow potentially-malicious user names */
|
||||||
|
|
||||||
|
if (*name == '.' || strchr(name, '/') || l == 0)
|
||||||
|
{
|
||||||
|
set_errno(EINVAL);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Buffer size must at least be able to hold name, plus some.. */
|
||||||
|
|
||||||
|
if (size < l + BUFFER_EXTRA)
|
||||||
|
{
|
||||||
|
set_errno(ERANGE);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
f = fopen(CONFIG_LIBC_PASSWD_FILEPATH, "rbe");
|
||||||
|
if (f == NULL)
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
while (fgets(buf, size, f) && (k = strlen(buf)) > 0)
|
||||||
|
{
|
||||||
|
if (skip || strncmp(name, buf, l) || buf[l] != ':')
|
||||||
|
{
|
||||||
|
skip = buf[k - 1] != '\n';
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (buf[k - 1] != '\n')
|
||||||
|
{
|
||||||
|
set_errno(ERANGE);
|
||||||
|
fclose(f);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (parsespent(buf, sp) < 0)
|
||||||
|
{
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
*res = sp;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
fclose(f);
|
||||||
|
return 0;
|
||||||
|
}
|
|
@ -30,6 +30,7 @@
|
||||||
#include <nuttx/config.h>
|
#include <nuttx/config.h>
|
||||||
|
|
||||||
#include <pwd.h>
|
#include <pwd.h>
|
||||||
|
#include <shadow.h>
|
||||||
|
|
||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
* Pre-processor Definitions
|
* Pre-processor Definitions
|
||||||
|
@ -46,6 +47,7 @@
|
||||||
#define ROOT_DIR "/root"
|
#define ROOT_DIR "/root"
|
||||||
#define ROOT_SHELL "/bin/nsh"
|
#define ROOT_SHELL "/bin/nsh"
|
||||||
#define ROOT_PASSWD "root"
|
#define ROOT_PASSWD "root"
|
||||||
|
#define ROOT_PWDP "$1$123$SGj4CnC7VtiFx.tjjtazK1"
|
||||||
|
|
||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
* Public Data
|
* Public Data
|
||||||
|
@ -63,6 +65,7 @@ extern "C"
|
||||||
|
|
||||||
EXTERN int g_passwd_index;
|
EXTERN int g_passwd_index;
|
||||||
EXTERN struct passwd g_passwd;
|
EXTERN struct passwd g_passwd;
|
||||||
|
EXTERN struct spwd g_spwd;
|
||||||
EXTERN char g_passwd_buffer[CONFIG_LIBC_PASSWD_LINESIZE];
|
EXTERN char g_passwd_buffer[CONFIG_LIBC_PASSWD_LINESIZE];
|
||||||
|
|
||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
|
|
|
@ -36,6 +36,7 @@
|
||||||
|
|
||||||
int g_passwd_index;
|
int g_passwd_index;
|
||||||
struct passwd g_passwd;
|
struct passwd g_passwd;
|
||||||
|
struct spwd g_spwd;
|
||||||
char g_passwd_buffer[CONFIG_LIBC_PASSWD_LINESIZE];
|
char g_passwd_buffer[CONFIG_LIBC_PASSWD_LINESIZE];
|
||||||
|
|
||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
|
|
Loading…
Reference in a new issue